diff options
Diffstat (limited to '3.0.9/1008_linux-3.0.9.patch')
-rw-r--r-- | 3.0.9/1008_linux-3.0.9.patch | 10991 |
1 files changed, 10991 insertions, 0 deletions
diff --git a/3.0.9/1008_linux-3.0.9.patch b/3.0.9/1008_linux-3.0.9.patch new file mode 100644 index 0000000..1679a52 --- /dev/null +++ b/3.0.9/1008_linux-3.0.9.patch @@ -0,0 +1,10991 @@ +diff --git a/Documentation/hwspinlock.txt b/Documentation/hwspinlock.txt +index 7dcd1a4..6996681 100644 +--- a/Documentation/hwspinlock.txt ++++ b/Documentation/hwspinlock.txt +@@ -39,23 +39,20 @@ independent, drivers. + in case an unused hwspinlock isn't available. Users of this + API will usually want to communicate the lock's id to the remote core + before it can be used to achieve synchronization. +- Can be called from an atomic context (this function will not sleep) but +- not from within interrupt context. ++ Should be called from a process context (might sleep). + + struct hwspinlock *hwspin_lock_request_specific(unsigned int id); + - assign a specific hwspinlock id and return its address, or NULL + if that hwspinlock is already in use. Usually board code will + be calling this function in order to reserve specific hwspinlock + ids for predefined purposes. +- Can be called from an atomic context (this function will not sleep) but +- not from within interrupt context. ++ Should be called from a process context (might sleep). + + int hwspin_lock_free(struct hwspinlock *hwlock); + - free a previously-assigned hwspinlock; returns 0 on success, or an + appropriate error code on failure (e.g. -EINVAL if the hwspinlock + is already free). +- Can be called from an atomic context (this function will not sleep) but +- not from within interrupt context. ++ Should be called from a process context (might sleep). + + int hwspin_lock_timeout(struct hwspinlock *hwlock, unsigned int timeout); + - lock a previously-assigned hwspinlock with a timeout limit (specified in +@@ -232,15 +229,14 @@ int hwspinlock_example2(void) + + int hwspin_lock_register(struct hwspinlock *hwlock); + - to be called from the underlying platform-specific implementation, in +- order to register a new hwspinlock instance. Can be called from an atomic +- context (this function will not sleep) but not from within interrupt +- context. Returns 0 on success, or appropriate error code on failure. ++ order to register a new hwspinlock instance. Should be called from ++ a process context (this function might sleep). ++ Returns 0 on success, or appropriate error code on failure. + + struct hwspinlock *hwspin_lock_unregister(unsigned int id); + - to be called from the underlying vendor-specific implementation, in order + to unregister an existing (and unused) hwspinlock instance. +- Can be called from an atomic context (will not sleep) but not from +- within interrupt context. ++ Should be called from a process context (this function might sleep). + Returns the address of hwspinlock on success, or NULL on error (e.g. + if the hwspinlock is sill in use). + +diff --git a/Documentation/power/runtime_pm.txt b/Documentation/power/runtime_pm.txt +index b24875b..6ade987 100644 +--- a/Documentation/power/runtime_pm.txt ++++ b/Documentation/power/runtime_pm.txt +@@ -708,6 +708,16 @@ will behave normally, not taking the autosuspend delay into account. + Similarly, if the power.use_autosuspend field isn't set then the autosuspend + helper functions will behave just like the non-autosuspend counterparts. + ++Under some circumstances a driver or subsystem may want to prevent a device ++from autosuspending immediately, even though the usage counter is zero and the ++autosuspend delay time has expired. If the ->runtime_suspend() callback ++returns -EAGAIN or -EBUSY, and if the next autosuspend delay expiration time is ++in the future (as it normally would be if the callback invoked ++pm_runtime_mark_last_busy()), the PM core will automatically reschedule the ++autosuspend. The ->runtime_suspend() callback can't do this rescheduling ++itself because no suspend requests of any kind are accepted while the device is ++suspending (i.e., while the callback is running). ++ + The implementation is well suited for asynchronous use in interrupt contexts. + However such use inevitably involves races, because the PM core can't + synchronize ->runtime_suspend() callbacks with the arrival of I/O requests. +diff --git a/Documentation/stable_kernel_rules.txt b/Documentation/stable_kernel_rules.txt +index e213f45..21fd05c 100644 +--- a/Documentation/stable_kernel_rules.txt ++++ b/Documentation/stable_kernel_rules.txt +@@ -24,10 +24,10 @@ Rules on what kind of patches are accepted, and which ones are not, into the + Procedure for submitting patches to the -stable tree: + + - Send the patch, after verifying that it follows the above rules, to +- stable@kernel.org. You must note the upstream commit ID in the changelog +- of your submission. ++ stable@vger.kernel.org. You must note the upstream commit ID in the ++ changelog of your submission. + - To have the patch automatically included in the stable tree, add the tag +- Cc: stable@kernel.org ++ Cc: stable@vger.kernel.org + in the sign-off area. Once the patch is merged it will be applied to + the stable tree without anything else needing to be done by the author + or subsystem maintainer. +@@ -35,10 +35,10 @@ Procedure for submitting patches to the -stable tree: + cherry-picked than this can be specified in the following format in + the sign-off area: + +- Cc: <stable@kernel.org> # .32.x: a1f84a3: sched: Check for idle +- Cc: <stable@kernel.org> # .32.x: 1b9508f: sched: Rate-limit newidle +- Cc: <stable@kernel.org> # .32.x: fd21073: sched: Fix affinity logic +- Cc: <stable@kernel.org> # .32.x ++ Cc: <stable@vger.kernel.org> # .32.x: a1f84a3: sched: Check for idle ++ Cc: <stable@vger.kernel.org> # .32.x: 1b9508f: sched: Rate-limit newidle ++ Cc: <stable@vger.kernel.org> # .32.x: fd21073: sched: Fix affinity logic ++ Cc: <stable@vger.kernel.org> # .32.x + Signed-off-by: Ingo Molnar <mingo@elte.hu> + + The tag sequence has the meaning of: +diff --git a/MAINTAINERS b/MAINTAINERS +index 187282d..34e2418 100644 +--- a/MAINTAINERS ++++ b/MAINTAINERS +@@ -1221,7 +1221,7 @@ F: Documentation/aoe/ + F: drivers/block/aoe/ + + ATHEROS ATH GENERIC UTILITIES +-M: "Luis R. Rodriguez" <lrodriguez@atheros.com> ++M: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com> + L: linux-wireless@vger.kernel.org + S: Supported + F: drivers/net/wireless/ath/* +@@ -1229,7 +1229,7 @@ F: drivers/net/wireless/ath/* + ATHEROS ATH5K WIRELESS DRIVER + M: Jiri Slaby <jirislaby@gmail.com> + M: Nick Kossifidis <mickflemm@gmail.com> +-M: "Luis R. Rodriguez" <lrodriguez@atheros.com> ++M: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com> + M: Bob Copeland <me@bobcopeland.com> + L: linux-wireless@vger.kernel.org + L: ath5k-devel@lists.ath5k.org +@@ -1238,10 +1238,10 @@ S: Maintained + F: drivers/net/wireless/ath/ath5k/ + + ATHEROS ATH9K WIRELESS DRIVER +-M: "Luis R. Rodriguez" <lrodriguez@atheros.com> +-M: Jouni Malinen <jmalinen@atheros.com> +-M: Vasanthakumar Thiagarajan <vasanth@atheros.com> +-M: Senthil Balasubramanian <senthilkumar@atheros.com> ++M: "Luis R. Rodriguez" <mcgrof@qca.qualcomm.com> ++M: Jouni Malinen <jouni@qca.qualcomm.com> ++M: Vasanthakumar Thiagarajan <vthiagar@qca.qualcomm.com> ++M: Senthil Balasubramanian <senthilb@qca.qualcomm.com> + L: linux-wireless@vger.kernel.org + L: ath9k-devel@lists.ath9k.org + W: http://wireless.kernel.org/en/users/Drivers/ath9k +@@ -1269,7 +1269,7 @@ F: drivers/input/misc/ati_remote2.c + ATLX ETHERNET DRIVERS + M: Jay Cliburn <jcliburn@gmail.com> + M: Chris Snook <chris.snook@gmail.com> +-M: Jie Yang <jie.yang@atheros.com> ++M: Jie Yang <yangjie@qca.qualcomm.com> + L: netdev@vger.kernel.org + W: http://sourceforge.net/projects/atl1 + W: http://atl1.sourceforge.net +diff --git a/Makefile b/Makefile +index 9f6e3cd..438c11a 100644 +--- a/Makefile ++++ b/Makefile +@@ -1,6 +1,6 @@ + VERSION = 3 + PATCHLEVEL = 0 +-SUBLEVEL = 8 ++SUBLEVEL = 9 + EXTRAVERSION = + NAME = Sneaky Weasel + +diff --git a/arch/arm/mach-ux500/cpu.c b/arch/arm/mach-ux500/cpu.c +index 1da23bb..8aa104a 100644 +--- a/arch/arm/mach-ux500/cpu.c ++++ b/arch/arm/mach-ux500/cpu.c +@@ -99,7 +99,27 @@ static void ux500_l2x0_inv_all(void) + ux500_cache_sync(); + } + +-static int ux500_l2x0_init(void) ++static int __init ux500_l2x0_unlock(void) ++{ ++ int i; ++ ++ /* ++ * Unlock Data and Instruction Lock if locked. Ux500 U-Boot versions ++ * apparently locks both caches before jumping to the kernel. The ++ * l2x0 core will not touch the unlock registers if the l2x0 is ++ * already enabled, so we do it right here instead. The PL310 has ++ * 8 sets of registers, one per possible CPU. ++ */ ++ for (i = 0; i < 8; i++) { ++ writel_relaxed(0x0, l2x0_base + L2X0_LOCKDOWN_WAY_D_BASE + ++ i * L2X0_LOCKDOWN_STRIDE); ++ writel_relaxed(0x0, l2x0_base + L2X0_LOCKDOWN_WAY_I_BASE + ++ i * L2X0_LOCKDOWN_STRIDE); ++ } ++ return 0; ++} ++ ++static int __init ux500_l2x0_init(void) + { + if (cpu_is_u5500()) + l2x0_base = __io_address(U5500_L2CC_BASE); +@@ -108,6 +128,9 @@ static int ux500_l2x0_init(void) + else + ux500_unknown_soc(); + ++ /* Unlock before init */ ++ ux500_l2x0_unlock(); ++ + /* 64KB way size, 8 way associativity, force WA */ + l2x0_init(l2x0_base, 0x3e060000, 0xc0000fff); + +diff --git a/arch/arm/plat-mxc/include/mach/iomux-v3.h b/arch/arm/plat-mxc/include/mach/iomux-v3.h +index ebbce33..4509956 100644 +--- a/arch/arm/plat-mxc/include/mach/iomux-v3.h ++++ b/arch/arm/plat-mxc/include/mach/iomux-v3.h +@@ -89,11 +89,11 @@ typedef u64 iomux_v3_cfg_t; + #define PAD_CTL_HYS (1 << 8) + + #define PAD_CTL_PKE (1 << 7) +-#define PAD_CTL_PUE (1 << 6) +-#define PAD_CTL_PUS_100K_DOWN (0 << 4) +-#define PAD_CTL_PUS_47K_UP (1 << 4) +-#define PAD_CTL_PUS_100K_UP (2 << 4) +-#define PAD_CTL_PUS_22K_UP (3 << 4) ++#define PAD_CTL_PUE (1 << 6 | PAD_CTL_PKE) ++#define PAD_CTL_PUS_100K_DOWN (0 << 4 | PAD_CTL_PUE) ++#define PAD_CTL_PUS_47K_UP (1 << 4 | PAD_CTL_PUE) ++#define PAD_CTL_PUS_100K_UP (2 << 4 | PAD_CTL_PUE) ++#define PAD_CTL_PUS_22K_UP (3 << 4 | PAD_CTL_PUE) + + #define PAD_CTL_ODE (1 << 3) + +diff --git a/arch/powerpc/include/asm/sparsemem.h b/arch/powerpc/include/asm/sparsemem.h +index 54a47ea..0c5fa31 100644 +--- a/arch/powerpc/include/asm/sparsemem.h ++++ b/arch/powerpc/include/asm/sparsemem.h +@@ -16,7 +16,7 @@ + #endif /* CONFIG_SPARSEMEM */ + + #ifdef CONFIG_MEMORY_HOTPLUG +-extern void create_section_mapping(unsigned long start, unsigned long end); ++extern int create_section_mapping(unsigned long start, unsigned long end); + extern int remove_section_mapping(unsigned long start, unsigned long end); + #ifdef CONFIG_NUMA + extern int hot_add_scn_to_nid(unsigned long scn_addr); +diff --git a/arch/powerpc/mm/gup.c b/arch/powerpc/mm/gup.c +index fec1320..d7efdbf 100644 +--- a/arch/powerpc/mm/gup.c ++++ b/arch/powerpc/mm/gup.c +@@ -16,16 +16,6 @@ + + #ifdef __HAVE_ARCH_PTE_SPECIAL + +-static inline void get_huge_page_tail(struct page *page) +-{ +- /* +- * __split_huge_page_refcount() cannot run +- * from under us. +- */ +- VM_BUG_ON(atomic_read(&page->_count) < 0); +- atomic_inc(&page->_count); +-} +- + /* + * The performance critical leaf functions are made noinline otherwise gcc + * inlines everything into a single function which results in too much +@@ -57,8 +47,6 @@ static noinline int gup_pte_range(pmd_t pmd, unsigned long addr, + put_page(page); + return 0; + } +- if (PageTail(page)) +- get_huge_page_tail(page); + pages[*nr] = page; + (*nr)++; + +diff --git a/arch/powerpc/mm/hash_utils_64.c b/arch/powerpc/mm/hash_utils_64.c +index 26b2872..07f9e9f 100644 +--- a/arch/powerpc/mm/hash_utils_64.c ++++ b/arch/powerpc/mm/hash_utils_64.c +@@ -534,11 +534,11 @@ static unsigned long __init htab_get_table_size(void) + } + + #ifdef CONFIG_MEMORY_HOTPLUG +-void create_section_mapping(unsigned long start, unsigned long end) ++int create_section_mapping(unsigned long start, unsigned long end) + { +- BUG_ON(htab_bolt_mapping(start, end, __pa(start), ++ return htab_bolt_mapping(start, end, __pa(start), + pgprot_val(PAGE_KERNEL), mmu_linear_psize, +- mmu_kernel_ssize)); ++ mmu_kernel_ssize); + } + + int remove_section_mapping(unsigned long start, unsigned long end) +diff --git a/arch/powerpc/mm/hugetlbpage.c b/arch/powerpc/mm/hugetlbpage.c +index 0b9a5c1..da5eb38 100644 +--- a/arch/powerpc/mm/hugetlbpage.c ++++ b/arch/powerpc/mm/hugetlbpage.c +@@ -390,7 +390,7 @@ static noinline int gup_hugepte(pte_t *ptep, unsigned long sz, unsigned long add + { + unsigned long mask; + unsigned long pte_end; +- struct page *head, *page; ++ struct page *head, *page, *tail; + pte_t pte; + int refs; + +@@ -413,6 +413,7 @@ static noinline int gup_hugepte(pte_t *ptep, unsigned long sz, unsigned long add + head = pte_page(pte); + + page = head + ((addr & (sz-1)) >> PAGE_SHIFT); ++ tail = page; + do { + VM_BUG_ON(compound_head(page) != head); + pages[*nr] = page; +@@ -428,10 +429,20 @@ static noinline int gup_hugepte(pte_t *ptep, unsigned long sz, unsigned long add + + if (unlikely(pte_val(pte) != pte_val(*ptep))) { + /* Could be optimized better */ +- while (*nr) { +- put_page(page); +- (*nr)--; +- } ++ *nr -= refs; ++ while (refs--) ++ put_page(head); ++ return 0; ++ } ++ ++ /* ++ * Any tail page need their mapcount reference taken before we ++ * return. ++ */ ++ while (refs--) { ++ if (PageTail(tail)) ++ get_huge_page_tail(tail); ++ tail++; + } + + return 1; +diff --git a/arch/powerpc/mm/mem.c b/arch/powerpc/mm/mem.c +index 29d4dde..278ec8e 100644 +--- a/arch/powerpc/mm/mem.c ++++ b/arch/powerpc/mm/mem.c +@@ -123,7 +123,8 @@ int arch_add_memory(int nid, u64 start, u64 size) + pgdata = NODE_DATA(nid); + + start = (unsigned long)__va(start); +- create_section_mapping(start, start + size); ++ if (create_section_mapping(start, start + size)) ++ return -EINVAL; + + /* this should work for most non-highmem platforms */ + zone = pgdata->node_zones; +diff --git a/arch/powerpc/mm/mmu_context_hash64.c b/arch/powerpc/mm/mmu_context_hash64.c +index 3bafc3d..4ff587e 100644 +--- a/arch/powerpc/mm/mmu_context_hash64.c ++++ b/arch/powerpc/mm/mmu_context_hash64.c +@@ -136,8 +136,8 @@ int use_cop(unsigned long acop, struct mm_struct *mm) + if (!mm || !acop) + return -EINVAL; + +- /* We need to make sure mm_users doesn't change */ +- down_read(&mm->mmap_sem); ++ /* The page_table_lock ensures mm_users won't change under us */ ++ spin_lock(&mm->page_table_lock); + spin_lock(mm->context.cop_lockp); + + if (mm->context.cop_pid == COP_PID_NONE) { +@@ -164,7 +164,7 @@ int use_cop(unsigned long acop, struct mm_struct *mm) + + out: + spin_unlock(mm->context.cop_lockp); +- up_read(&mm->mmap_sem); ++ spin_unlock(&mm->page_table_lock); + + return ret; + } +@@ -185,8 +185,8 @@ void drop_cop(unsigned long acop, struct mm_struct *mm) + if (WARN_ON_ONCE(!mm)) + return; + +- /* We need to make sure mm_users doesn't change */ +- down_read(&mm->mmap_sem); ++ /* The page_table_lock ensures mm_users won't change under us */ ++ spin_lock(&mm->page_table_lock); + spin_lock(mm->context.cop_lockp); + + mm->context.acop &= ~acop; +@@ -213,7 +213,7 @@ void drop_cop(unsigned long acop, struct mm_struct *mm) + } + + spin_unlock(mm->context.cop_lockp); +- up_read(&mm->mmap_sem); ++ spin_unlock(&mm->page_table_lock); + } + EXPORT_SYMBOL_GPL(drop_cop); + +diff --git a/arch/powerpc/mm/numa.c b/arch/powerpc/mm/numa.c +index 2164006..2c1ae7a 100644 +--- a/arch/powerpc/mm/numa.c ++++ b/arch/powerpc/mm/numa.c +@@ -1214,11 +1214,12 @@ int hot_add_node_scn_to_nid(unsigned long scn_addr) + break; + } + +- of_node_put(memory); + if (nid >= 0) + break; + } + ++ of_node_put(memory); ++ + return nid; + } + +diff --git a/arch/powerpc/platforms/pseries/dlpar.c b/arch/powerpc/platforms/pseries/dlpar.c +index 57ceb92..82766e5 100644 +--- a/arch/powerpc/platforms/pseries/dlpar.c ++++ b/arch/powerpc/platforms/pseries/dlpar.c +@@ -112,6 +112,7 @@ void dlpar_free_cc_nodes(struct device_node *dn) + dlpar_free_one_cc_node(dn); + } + ++#define COMPLETE 0 + #define NEXT_SIBLING 1 + #define NEXT_CHILD 2 + #define NEXT_PROPERTY 3 +@@ -158,6 +159,9 @@ struct device_node *dlpar_configure_connector(u32 drc_index) + spin_unlock(&rtas_data_buf_lock); + + switch (rc) { ++ case COMPLETE: ++ break; ++ + case NEXT_SIBLING: + dn = dlpar_parse_cc_node(ccwa); + if (!dn) +diff --git a/arch/powerpc/platforms/pseries/eeh.c b/arch/powerpc/platforms/pseries/eeh.c +index 46b55cf..3608704 100644 +--- a/arch/powerpc/platforms/pseries/eeh.c ++++ b/arch/powerpc/platforms/pseries/eeh.c +@@ -1338,7 +1338,7 @@ static const struct file_operations proc_eeh_operations = { + static int __init eeh_init_proc(void) + { + if (machine_is(pseries)) +- proc_create("ppc64/eeh", 0, NULL, &proc_eeh_operations); ++ proc_create("powerpc/eeh", 0, NULL, &proc_eeh_operations); + return 0; + } + __initcall(eeh_init_proc); +diff --git a/arch/s390/kernel/ptrace.c b/arch/s390/kernel/ptrace.c +index ef86ad2..ae0e14b 100644 +--- a/arch/s390/kernel/ptrace.c ++++ b/arch/s390/kernel/ptrace.c +@@ -47,29 +47,31 @@ enum s390_regset { + + void update_per_regs(struct task_struct *task) + { +- static const struct per_regs per_single_step = { +- .control = PER_EVENT_IFETCH, +- .start = 0, +- .end = PSW_ADDR_INSN, +- }; + struct pt_regs *regs = task_pt_regs(task); + struct thread_struct *thread = &task->thread; +- const struct per_regs *new; +- struct per_regs old; +- +- /* TIF_SINGLE_STEP overrides the user specified PER registers. */ +- new = test_tsk_thread_flag(task, TIF_SINGLE_STEP) ? +- &per_single_step : &thread->per_user; ++ struct per_regs old, new; ++ ++ /* Copy user specified PER registers */ ++ new.control = thread->per_user.control; ++ new.start = thread->per_user.start; ++ new.end = thread->per_user.end; ++ ++ /* merge TIF_SINGLE_STEP into user specified PER registers. */ ++ if (test_tsk_thread_flag(task, TIF_SINGLE_STEP)) { ++ new.control |= PER_EVENT_IFETCH; ++ new.start = 0; ++ new.end = PSW_ADDR_INSN; ++ } + + /* Take care of the PER enablement bit in the PSW. */ +- if (!(new->control & PER_EVENT_MASK)) { ++ if (!(new.control & PER_EVENT_MASK)) { + regs->psw.mask &= ~PSW_MASK_PER; + return; + } + regs->psw.mask |= PSW_MASK_PER; + __ctl_store(old, 9, 11); +- if (memcmp(new, &old, sizeof(struct per_regs)) != 0) +- __ctl_load(*new, 9, 11); ++ if (memcmp(&new, &old, sizeof(struct per_regs)) != 0) ++ __ctl_load(new, 9, 11); + } + + void user_enable_single_step(struct task_struct *task) +diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c +index 67345ae..2ada634 100644 +--- a/arch/s390/kvm/kvm-s390.c ++++ b/arch/s390/kvm/kvm-s390.c +@@ -301,11 +301,17 @@ int kvm_arch_vcpu_setup(struct kvm_vcpu *vcpu) + struct kvm_vcpu *kvm_arch_vcpu_create(struct kvm *kvm, + unsigned int id) + { +- struct kvm_vcpu *vcpu = kzalloc(sizeof(struct kvm_vcpu), GFP_KERNEL); +- int rc = -ENOMEM; ++ struct kvm_vcpu *vcpu; ++ int rc = -EINVAL; ++ ++ if (id >= KVM_MAX_VCPUS) ++ goto out; ++ ++ rc = -ENOMEM; + ++ vcpu = kzalloc(sizeof(struct kvm_vcpu), GFP_KERNEL); + if (!vcpu) +- goto out_nomem; ++ goto out; + + vcpu->arch.sie_block = (struct kvm_s390_sie_block *) + get_zeroed_page(GFP_KERNEL); +@@ -341,7 +347,7 @@ out_free_sie_block: + free_page((unsigned long)(vcpu->arch.sie_block)); + out_free_cpu: + kfree(vcpu); +-out_nomem: ++out: + return ERR_PTR(rc); + } + +diff --git a/arch/s390/mm/gup.c b/arch/s390/mm/gup.c +index 45b405c..65cb06e 100644 +--- a/arch/s390/mm/gup.c ++++ b/arch/s390/mm/gup.c +@@ -52,7 +52,7 @@ static inline int gup_huge_pmd(pmd_t *pmdp, pmd_t pmd, unsigned long addr, + unsigned long end, int write, struct page **pages, int *nr) + { + unsigned long mask, result; +- struct page *head, *page; ++ struct page *head, *page, *tail; + int refs; + + result = write ? 0 : _SEGMENT_ENTRY_RO; +@@ -64,6 +64,7 @@ static inline int gup_huge_pmd(pmd_t *pmdp, pmd_t pmd, unsigned long addr, + refs = 0; + head = pmd_page(pmd); + page = head + ((addr & ~PMD_MASK) >> PAGE_SHIFT); ++ tail = page; + do { + VM_BUG_ON(compound_head(page) != head); + pages[*nr] = page; +@@ -81,6 +82,17 @@ static inline int gup_huge_pmd(pmd_t *pmdp, pmd_t pmd, unsigned long addr, + *nr -= refs; + while (refs--) + put_page(head); ++ return 0; ++ } ++ ++ /* ++ * Any tail page need their mapcount reference taken before we ++ * return. ++ */ ++ while (refs--) { ++ if (PageTail(tail)) ++ get_huge_page_tail(tail); ++ tail++; + } + + return 1; +diff --git a/arch/s390/mm/pgtable.c b/arch/s390/mm/pgtable.c +index 37a23c22..458893f 100644 +--- a/arch/s390/mm/pgtable.c ++++ b/arch/s390/mm/pgtable.c +@@ -291,8 +291,9 @@ void page_table_free_rcu(struct mmu_gather *tlb, unsigned long *table) + + void __tlb_remove_table(void *_table) + { +- void *table = (void *)((unsigned long) _table & PAGE_MASK); +- unsigned type = (unsigned long) _table & ~PAGE_MASK; ++ const unsigned long mask = (FRAG_MASK << 4) | FRAG_MASK; ++ void *table = (void *)((unsigned long) _table & ~mask); ++ unsigned type = (unsigned long) _table & mask; + + if (type) + __page_table_free_rcu(table, type); +diff --git a/arch/um/drivers/ubd_kern.c b/arch/um/drivers/ubd_kern.c +index 620f5b7..0491e40 100644 +--- a/arch/um/drivers/ubd_kern.c ++++ b/arch/um/drivers/ubd_kern.c +@@ -513,8 +513,37 @@ __uml_exitcall(kill_io_thread); + static inline int ubd_file_size(struct ubd *ubd_dev, __u64 *size_out) + { + char *file; ++ int fd; ++ int err; ++ ++ __u32 version; ++ __u32 align; ++ char *backing_file; ++ time_t mtime; ++ unsigned long long size; ++ int sector_size; ++ int bitmap_offset; ++ ++ if (ubd_dev->file && ubd_dev->cow.file) { ++ file = ubd_dev->cow.file; ++ ++ goto out; ++ } + +- file = ubd_dev->cow.file ? ubd_dev->cow.file : ubd_dev->file; ++ fd = os_open_file(ubd_dev->file, global_openflags, 0); ++ if (fd < 0) ++ return fd; ++ ++ err = read_cow_header(file_reader, &fd, &version, &backing_file, \ ++ &mtime, &size, §or_size, &align, &bitmap_offset); ++ os_close_file(fd); ++ ++ if(err == -EINVAL) ++ file = ubd_dev->file; ++ else ++ file = backing_file; ++ ++out: + return os_file_size(file, size_out); + } + +diff --git a/arch/x86/include/asm/apic.h b/arch/x86/include/asm/apic.h +index 4a0b7c7..244ac77 100644 +--- a/arch/x86/include/asm/apic.h ++++ b/arch/x86/include/asm/apic.h +@@ -495,7 +495,7 @@ static inline void default_wait_for_init_deassert(atomic_t *deassert) + return; + } + +-extern struct apic *generic_bigsmp_probe(void); ++extern void generic_bigsmp_probe(void); + + + #ifdef CONFIG_X86_LOCAL_APIC +diff --git a/arch/x86/include/asm/uv/uv_bau.h b/arch/x86/include/asm/uv/uv_bau.h +index a291c40..5d62d65 100644 +--- a/arch/x86/include/asm/uv/uv_bau.h ++++ b/arch/x86/include/asm/uv/uv_bau.h +@@ -55,6 +55,7 @@ + #define UV_BAU_TUNABLES_DIR "sgi_uv" + #define UV_BAU_TUNABLES_FILE "bau_tunables" + #define WHITESPACE " \t\n" ++#define uv_mmask ((1UL << uv_hub_info->m_val) - 1) + #define uv_physnodeaddr(x) ((__pa((unsigned long)(x)) & uv_mmask)) + #define cpubit_isset(cpu, bau_local_cpumask) \ + test_bit((cpu), (bau_local_cpumask).bits) +diff --git a/arch/x86/include/asm/uv/uv_hub.h b/arch/x86/include/asm/uv/uv_hub.h +index f26544a..54a13aa 100644 +--- a/arch/x86/include/asm/uv/uv_hub.h ++++ b/arch/x86/include/asm/uv/uv_hub.h +@@ -46,6 +46,13 @@ + * PNODE - the low N bits of the GNODE. The PNODE is the most useful variant + * of the nasid for socket usage. + * ++ * GPA - (global physical address) a socket physical address converted ++ * so that it can be used by the GRU as a global address. Socket ++ * physical addresses 1) need additional NASID (node) bits added ++ * to the high end of the address, and 2) unaliased if the ++ * partition does not have a physical address 0. In addition, on ++ * UV2 rev 1, GPAs need the gnode left shifted to bits 39 or 40. ++ * + * + * NumaLink Global Physical Address Format: + * +--------------------------------+---------------------+ +@@ -141,6 +148,8 @@ struct uv_hub_info_s { + unsigned int gnode_extra; + unsigned char hub_revision; + unsigned char apic_pnode_shift; ++ unsigned char m_shift; ++ unsigned char n_lshift; + unsigned long gnode_upper; + unsigned long lowmem_remap_top; + unsigned long lowmem_remap_base; +@@ -177,6 +186,16 @@ static inline int is_uv2_hub(void) + return uv_hub_info->hub_revision >= UV2_HUB_REVISION_BASE; + } + ++static inline int is_uv2_1_hub(void) ++{ ++ return uv_hub_info->hub_revision == UV2_HUB_REVISION_BASE; ++} ++ ++static inline int is_uv2_2_hub(void) ++{ ++ return uv_hub_info->hub_revision == UV2_HUB_REVISION_BASE + 1; ++} ++ + union uvh_apicid { + unsigned long v; + struct uvh_apicid_s { +@@ -276,7 +295,10 @@ static inline unsigned long uv_soc_phys_ram_to_gpa(unsigned long paddr) + { + if (paddr < uv_hub_info->lowmem_remap_top) + paddr |= uv_hub_info->lowmem_remap_base; +- return paddr | uv_hub_info->gnode_upper; ++ paddr |= uv_hub_info->gnode_upper; ++ paddr = ((paddr << uv_hub_info->m_shift) >> uv_hub_info->m_shift) | ++ ((paddr >> uv_hub_info->m_val) << uv_hub_info->n_lshift); ++ return paddr; + } + + +@@ -300,16 +322,19 @@ static inline unsigned long uv_gpa_to_soc_phys_ram(unsigned long gpa) + unsigned long remap_base = uv_hub_info->lowmem_remap_base; + unsigned long remap_top = uv_hub_info->lowmem_remap_top; + ++ gpa = ((gpa << uv_hub_info->m_shift) >> uv_hub_info->m_shift) | ++ ((gpa >> uv_hub_info->n_lshift) << uv_hub_info->m_val); ++ gpa = gpa & uv_hub_info->gpa_mask; + if (paddr >= remap_base && paddr < remap_base + remap_top) + paddr -= remap_base; + return paddr; + } + + +-/* gnode -> pnode */ ++/* gpa -> pnode */ + static inline unsigned long uv_gpa_to_gnode(unsigned long gpa) + { +- return gpa >> uv_hub_info->m_val; ++ return gpa >> uv_hub_info->n_lshift; + } + + /* gpa -> pnode */ +@@ -320,6 +345,12 @@ static inline int uv_gpa_to_pnode(unsigned long gpa) + return uv_gpa_to_gnode(gpa) & n_mask; + } + ++/* gpa -> node offset*/ ++static inline unsigned long uv_gpa_to_offset(unsigned long gpa) ++{ ++ return (gpa << uv_hub_info->m_shift) >> uv_hub_info->m_shift; ++} ++ + /* pnode, offset --> socket virtual */ + static inline void *uv_pnode_offset_to_vaddr(int pnode, unsigned long offset) + { +diff --git a/arch/x86/kernel/amd_iommu.c b/arch/x86/kernel/amd_iommu.c +index d3d9d50..bfd75ff 100644 +--- a/arch/x86/kernel/amd_iommu.c ++++ b/arch/x86/kernel/amd_iommu.c +@@ -1203,7 +1203,7 @@ static int alloc_new_range(struct dma_ops_domain *dma_dom, + if (!pte || !IOMMU_PTE_PRESENT(*pte)) + continue; + +- dma_ops_reserve_addresses(dma_dom, i << PAGE_SHIFT, 1); ++ dma_ops_reserve_addresses(dma_dom, i >> PAGE_SHIFT, 1); + } + + update_domain(&dma_dom->domain); +diff --git a/arch/x86/kernel/apic/bigsmp_32.c b/arch/x86/kernel/apic/bigsmp_32.c +index efd737e..521bead 100644 +--- a/arch/x86/kernel/apic/bigsmp_32.c ++++ b/arch/x86/kernel/apic/bigsmp_32.c +@@ -255,12 +255,24 @@ static struct apic apic_bigsmp = { + .x86_32_early_logical_apicid = bigsmp_early_logical_apicid, + }; + +-struct apic * __init generic_bigsmp_probe(void) ++void __init generic_bigsmp_probe(void) + { +- if (probe_bigsmp()) +- return &apic_bigsmp; ++ unsigned int cpu; + +- return NULL; ++ if (!probe_bigsmp()) ++ return; ++ ++ apic = &apic_bigsmp; ++ ++ for_each_possible_cpu(cpu) { ++ if (early_per_cpu(x86_cpu_to_logical_apicid, ++ cpu) == BAD_APICID) ++ continue; ++ early_per_cpu(x86_cpu_to_logical_apicid, cpu) = ++ bigsmp_early_logical_apicid(cpu); ++ } ++ ++ pr_info("Overriding APIC driver with %s\n", apic_bigsmp.name); + } + + apic_driver(apic_bigsmp); +diff --git a/arch/x86/kernel/apic/probe_32.c b/arch/x86/kernel/apic/probe_32.c +index b5254ad..0787bb3 100644 +--- a/arch/x86/kernel/apic/probe_32.c ++++ b/arch/x86/kernel/apic/probe_32.c +@@ -200,14 +200,8 @@ void __init default_setup_apic_routing(void) + * - we find more than 8 CPUs in acpi LAPIC listing with xAPIC support + */ + +- if (!cmdline_apic && apic == &apic_default) { +- struct apic *bigsmp = generic_bigsmp_probe(); +- if (bigsmp) { +- apic = bigsmp; +- printk(KERN_INFO "Overriding APIC driver with %s\n", +- apic->name); +- } +- } ++ if (!cmdline_apic && apic == &apic_default) ++ generic_bigsmp_probe(); + #endif + + if (apic->setup_apic_routing) +diff --git a/arch/x86/kernel/apic/x2apic_uv_x.c b/arch/x86/kernel/apic/x2apic_uv_x.c +index 34b1859..cfeb978 100644 +--- a/arch/x86/kernel/apic/x2apic_uv_x.c ++++ b/arch/x86/kernel/apic/x2apic_uv_x.c +@@ -832,6 +832,10 @@ void __init uv_system_init(void) + uv_cpu_hub_info(cpu)->apic_pnode_shift = uvh_apicid.s.pnode_shift; + uv_cpu_hub_info(cpu)->hub_revision = uv_hub_info->hub_revision; + ++ uv_cpu_hub_info(cpu)->m_shift = 64 - m_val; ++ uv_cpu_hub_info(cpu)->n_lshift = is_uv2_1_hub() ? ++ (m_val == 40 ? 40 : 39) : m_val; ++ + pnode = uv_apicid_to_pnode(apicid); + blade = boot_pnode_to_blade(pnode); + lcpu = uv_blade_info[blade].nr_possible_cpus; +@@ -862,8 +866,7 @@ void __init uv_system_init(void) + if (uv_node_to_blade[nid] >= 0) + continue; + paddr = node_start_pfn(nid) << PAGE_SHIFT; +- paddr = uv_soc_phys_ram_to_gpa(paddr); +- pnode = (paddr >> m_val) & pnode_mask; ++ pnode = uv_gpa_to_pnode(uv_soc_phys_ram_to_gpa(paddr)); + blade = boot_pnode_to_blade(pnode); + uv_node_to_blade[nid] = blade; + } +diff --git a/arch/x86/kernel/kprobes.c b/arch/x86/kernel/kprobes.c +index f1a6244..794bc95 100644 +--- a/arch/x86/kernel/kprobes.c ++++ b/arch/x86/kernel/kprobes.c +@@ -75,8 +75,10 @@ DEFINE_PER_CPU(struct kprobe_ctlblk, kprobe_ctlblk); + /* + * Undefined/reserved opcodes, conditional jump, Opcode Extension + * Groups, and some special opcodes can not boost. ++ * This is non-const to keep gcc from statically optimizing it out, as ++ * variable_test_bit makes gcc think only *(unsigned long*) is used. + */ +-static const u32 twobyte_is_boostable[256 / 32] = { ++static u32 twobyte_is_boostable[256 / 32] = { + /* 0 1 2 3 4 5 6 7 8 9 a b c d e f */ + /* ---------------------------------------------- */ + W(0x00, 0, 0, 1, 1, 0, 0, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0) | /* 00 */ +diff --git a/arch/x86/mm/gup.c b/arch/x86/mm/gup.c +index dbe34b9..ea30585 100644 +--- a/arch/x86/mm/gup.c ++++ b/arch/x86/mm/gup.c +@@ -108,16 +108,6 @@ static inline void get_head_page_multiple(struct page *page, int nr) + SetPageReferenced(page); + } + +-static inline void get_huge_page_tail(struct page *page) +-{ +- /* +- * __split_huge_page_refcount() cannot run +- * from under us. +- */ +- VM_BUG_ON(atomic_read(&page->_count) < 0); +- atomic_inc(&page->_count); +-} +- + static noinline int gup_huge_pmd(pmd_t pmd, unsigned long addr, + unsigned long end, int write, struct page **pages, int *nr) + { +diff --git a/arch/x86/platform/uv/tlb_uv.c b/arch/x86/platform/uv/tlb_uv.c +index 68e467f..82cff4a 100644 +--- a/arch/x86/platform/uv/tlb_uv.c ++++ b/arch/x86/platform/uv/tlb_uv.c +@@ -115,9 +115,6 @@ early_param("nobau", setup_nobau); + + /* base pnode in this partition */ + static int uv_base_pnode __read_mostly; +-/* position of pnode (which is nasid>>1): */ +-static int uv_nshift __read_mostly; +-static unsigned long uv_mmask __read_mostly; + + static DEFINE_PER_CPU(struct ptc_stats, ptcstats); + static DEFINE_PER_CPU(struct bau_control, bau_control); +@@ -1426,7 +1423,7 @@ static void activation_descriptor_init(int node, int pnode, int base_pnode) + { + int i; + int cpu; +- unsigned long pa; ++ unsigned long gpa; + unsigned long m; + unsigned long n; + size_t dsize; +@@ -1442,9 +1439,9 @@ static void activation_descriptor_init(int node, int pnode, int base_pnode) + bau_desc = kmalloc_node(dsize, GFP_KERNEL, node); + BUG_ON(!bau_desc); + +- pa = uv_gpa(bau_desc); /* need the real nasid*/ +- n = pa >> uv_nshift; +- m = pa & uv_mmask; ++ gpa = uv_gpa(bau_desc); ++ n = uv_gpa_to_gnode(gpa); ++ m = uv_gpa_to_offset(gpa); + + /* the 14-bit pnode */ + write_mmr_descriptor_base(pnode, (n << UV_DESC_PSHIFT | m)); +@@ -1516,9 +1513,9 @@ static void pq_init(int node, int pnode) + bcp->queue_last = pqp + (DEST_Q_SIZE - 1); + } + /* +- * need the pnode of where the memory was really allocated ++ * need the gnode of where the memory was really allocated + */ +- pn = uv_gpa(pqp) >> uv_nshift; ++ pn = uv_gpa_to_gnode(uv_gpa(pqp)); + first = uv_physnodeaddr(pqp); + pn_first = ((unsigned long)pn << UV_PAYLOADQ_PNODE_SHIFT) | first; + last = uv_physnodeaddr(pqp + (DEST_Q_SIZE - 1)); +@@ -1812,8 +1809,6 @@ static int __init uv_bau_init(void) + zalloc_cpumask_var_node(mask, GFP_KERNEL, cpu_to_node(cur_cpu)); + } + +- uv_nshift = uv_hub_info->m_val; +- uv_mmask = (1UL << uv_hub_info->m_val) - 1; + nuvhubs = uv_num_possible_blades(); + spin_lock_init(&disable_lock); + congested_cycles = usec_2_cycles(congested_respns_us); +diff --git a/block/genhd.c b/block/genhd.c +index 3608289..8c0829a 100644 +--- a/block/genhd.c ++++ b/block/genhd.c +@@ -611,6 +611,12 @@ void add_disk(struct gendisk *disk) + register_disk(disk); + blk_register_queue(disk); + ++ /* ++ * Take an extra ref on queue which will be put on disk_release() ++ * so that it sticks around as long as @disk is there. ++ */ ++ WARN_ON_ONCE(blk_get_queue(disk->queue)); ++ + retval = sysfs_create_link(&disk_to_dev(disk)->kobj, &bdi->dev->kobj, + "bdi"); + WARN_ON(retval); +@@ -1103,6 +1109,8 @@ static void disk_release(struct device *dev) + disk_replace_part_tbl(disk, NULL); + free_part_stats(&disk->part0); + free_part_info(&disk->part0); ++ if (disk->queue) ++ blk_put_queue(disk->queue); + kfree(disk); + } + struct class block_class = { +diff --git a/crypto/cryptd.c b/crypto/cryptd.c +index e46d21a..671d4d6 100644 +--- a/crypto/cryptd.c ++++ b/crypto/cryptd.c +@@ -945,7 +945,7 @@ static void __exit cryptd_exit(void) + crypto_unregister_template(&cryptd_tmpl); + } + +-module_init(cryptd_init); ++subsys_initcall(cryptd_init); + module_exit(cryptd_exit); + + MODULE_LICENSE("GPL"); +diff --git a/drivers/acpi/atomicio.c b/drivers/acpi/atomicio.c +index 7489b89..f151afe 100644 +--- a/drivers/acpi/atomicio.c ++++ b/drivers/acpi/atomicio.c +@@ -76,7 +76,7 @@ static void __iomem *__acpi_ioremap_fast(phys_addr_t paddr, + { + struct acpi_iomap *map; + +- map = __acpi_find_iomap(paddr, size); ++ map = __acpi_find_iomap(paddr, size/8); + if (map) + return map->vaddr + (paddr - map->paddr); + else +diff --git a/drivers/ata/ata_piix.c b/drivers/ata/ata_piix.c +index 6f6e771..6da6deb 100644 +--- a/drivers/ata/ata_piix.c ++++ b/drivers/ata/ata_piix.c +@@ -113,6 +113,8 @@ enum { + PIIX_PATA_FLAGS = ATA_FLAG_SLAVE_POSS, + PIIX_SATA_FLAGS = ATA_FLAG_SATA | PIIX_FLAG_CHECKINTR, + ++ PIIX_FLAG_PIO16 = (1 << 30), /*support 16bit PIO only*/ ++ + PIIX_80C_PRI = (1 << 5) | (1 << 4), + PIIX_80C_SEC = (1 << 7) | (1 << 6), + +@@ -147,6 +149,7 @@ enum piix_controller_ids { + ich8m_apple_sata, /* locks up on second port enable */ + tolapai_sata, + piix_pata_vmw, /* PIIX4 for VMware, spurious DMA_ERR */ ++ ich8_sata_snb, + }; + + struct piix_map_db { +@@ -177,6 +180,7 @@ static int piix_sidpr_scr_write(struct ata_link *link, + static int piix_sidpr_set_lpm(struct ata_link *link, enum ata_lpm_policy policy, + unsigned hints); + static bool piix_irq_check(struct ata_port *ap); ++static int piix_port_start(struct ata_port *ap); + #ifdef CONFIG_PM + static int piix_pci_device_suspend(struct pci_dev *pdev, pm_message_t mesg); + static int piix_pci_device_resume(struct pci_dev *pdev); +@@ -298,21 +302,21 @@ static const struct pci_device_id piix_pci_tbl[] = { + /* SATA Controller IDE (PCH) */ + { 0x8086, 0x3b2e, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, + /* SATA Controller IDE (CPT) */ +- { 0x8086, 0x1c00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, ++ { 0x8086, 0x1c00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata_snb }, + /* SATA Controller IDE (CPT) */ +- { 0x8086, 0x1c01, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, ++ { 0x8086, 0x1c01, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata_snb }, + /* SATA Controller IDE (CPT) */ + { 0x8086, 0x1c08, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, + /* SATA Controller IDE (CPT) */ + { 0x8086, 0x1c09, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, + /* SATA Controller IDE (PBG) */ +- { 0x8086, 0x1d00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, ++ { 0x8086, 0x1d00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata_snb }, + /* SATA Controller IDE (PBG) */ + { 0x8086, 0x1d08, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, + /* SATA Controller IDE (Panther Point) */ +- { 0x8086, 0x1e00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, ++ { 0x8086, 0x1e00, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata_snb }, + /* SATA Controller IDE (Panther Point) */ +- { 0x8086, 0x1e01, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata }, ++ { 0x8086, 0x1e01, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_sata_snb }, + /* SATA Controller IDE (Panther Point) */ + { 0x8086, 0x1e08, PCI_ANY_ID, PCI_ANY_ID, 0, 0, ich8_2port_sata }, + /* SATA Controller IDE (Panther Point) */ +@@ -338,6 +342,7 @@ static struct scsi_host_template piix_sht = { + static struct ata_port_operations piix_sata_ops = { + .inherits = &ata_bmdma32_port_ops, + .sff_irq_check = piix_irq_check, ++ .port_start = piix_port_start, + }; + + static struct ata_port_operations piix_pata_ops = { +@@ -478,6 +483,7 @@ static const struct piix_map_db *piix_map_db_table[] = { + [ich8_2port_sata] = &ich8_2port_map_db, + [ich8m_apple_sata] = &ich8m_apple_map_db, + [tolapai_sata] = &tolapai_map_db, ++ [ich8_sata_snb] = &ich8_map_db, + }; + + static struct ata_port_info piix_port_info[] = { +@@ -606,6 +612,19 @@ static struct ata_port_info piix_port_info[] = { + .port_ops = &piix_vmw_ops, + }, + ++ /* ++ * some Sandybridge chipsets have broken 32 mode up to now, ++ * see https://bugzilla.kernel.org/show_bug.cgi?id=40592 ++ */ ++ [ich8_sata_snb] = ++ { ++ .flags = PIIX_SATA_FLAGS | PIIX_FLAG_SIDPR | PIIX_FLAG_PIO16, ++ .pio_mask = ATA_PIO4, ++ .mwdma_mask = ATA_MWDMA2, ++ .udma_mask = ATA_UDMA6, ++ .port_ops = &piix_sata_ops, ++ }, ++ + }; + + static struct pci_bits piix_enable_bits[] = { +@@ -649,6 +668,14 @@ static const struct ich_laptop ich_laptop[] = { + { 0, } + }; + ++static int piix_port_start(struct ata_port *ap) ++{ ++ if (!(ap->flags & PIIX_FLAG_PIO16)) ++ ap->pflags |= ATA_PFLAG_PIO32 | ATA_PFLAG_PIO32CHANGE; ++ ++ return ata_bmdma_port_start(ap); ++} ++ + /** + * ich_pata_cable_detect - Probe host controller cable detect info + * @ap: Port for which cable detect info is desired +diff --git a/drivers/base/power/runtime.c b/drivers/base/power/runtime.c +index 0d4587b..1023392 100644 +--- a/drivers/base/power/runtime.c ++++ b/drivers/base/power/runtime.c +@@ -278,6 +278,9 @@ static int rpm_callback(int (*cb)(struct device *), struct device *dev) + * If a deferred resume was requested while the callback was running then carry + * it out; otherwise send an idle notification for the device (if the suspend + * failed) or for its parent (if the suspend succeeded). ++ * If ->runtime_suspend failed with -EAGAIN or -EBUSY, and if the RPM_AUTO ++ * flag is set and the next autosuspend-delay expiration time is in the ++ * future, schedule another autosuspend attempt. + * + * This function must be called under dev->power.lock with interrupts disabled. + */ +@@ -389,10 +392,21 @@ static int rpm_suspend(struct device *dev, int rpmflags) + if (retval) { + __update_runtime_status(dev, RPM_ACTIVE); + dev->power.deferred_resume = 0; +- if (retval == -EAGAIN || retval == -EBUSY) ++ if (retval == -EAGAIN || retval == -EBUSY) { + dev->power.runtime_error = 0; +- else ++ ++ /* ++ * If the callback routine failed an autosuspend, and ++ * if the last_busy time has been updated so that there ++ * is a new autosuspend expiration time, automatically ++ * reschedule another autosuspend. ++ */ ++ if ((rpmflags & RPM_AUTO) && ++ pm_runtime_autosuspend_expiration(dev) != 0) ++ goto repeat; ++ } else { + pm_runtime_cancel_pending(dev); ++ } + } else { + no_callback: + __update_runtime_status(dev, RPM_SUSPENDED); +diff --git a/drivers/block/cciss.c b/drivers/block/cciss.c +index 8f4ef65..c2f9b3e 100644 +--- a/drivers/block/cciss.c ++++ b/drivers/block/cciss.c +@@ -4533,6 +4533,13 @@ static int cciss_controller_hard_reset(struct pci_dev *pdev, + pmcsr &= ~PCI_PM_CTRL_STATE_MASK; + pmcsr |= PCI_D0; + pci_write_config_word(pdev, pos + PCI_PM_CTRL, pmcsr); ++ ++ /* ++ * The P600 requires a small delay when changing states. ++ * Otherwise we may think the board did not reset and we bail. ++ * This for kdump only and is particular to the P600. ++ */ ++ msleep(500); + } + return 0; + } +diff --git a/drivers/block/xen-blkback/blkback.c b/drivers/block/xen-blkback/blkback.c +index 5cf2993..54139d0 100644 +--- a/drivers/block/xen-blkback/blkback.c ++++ b/drivers/block/xen-blkback/blkback.c +@@ -667,7 +667,7 @@ static int dispatch_rw_block_io(struct xen_blkif *blkif, + + if (operation == READ) + blkif->st_rd_sect += preq.nr_sects; +- else if (operation == WRITE || operation == WRITE_FLUSH) ++ else if (operation & WRITE) + blkif->st_wr_sect += preq.nr_sects; + + return 0; +diff --git a/drivers/bluetooth/ath3k.c b/drivers/bluetooth/ath3k.c +index 6bacef3..db7cb81 100644 +--- a/drivers/bluetooth/ath3k.c ++++ b/drivers/bluetooth/ath3k.c +@@ -63,6 +63,7 @@ static struct usb_device_id ath3k_table[] = { + /* Atheros AR3011 with sflash firmware*/ + { USB_DEVICE(0x0CF3, 0x3002) }, + { USB_DEVICE(0x13d3, 0x3304) }, ++ { USB_DEVICE(0x0930, 0x0215) }, + + /* Atheros AR9285 Malbec with sflash firmware */ + { USB_DEVICE(0x03F0, 0x311D) }, +@@ -375,6 +376,11 @@ static int ath3k_probe(struct usb_interface *intf, + + /* load patch and sysconfig files for AR3012 */ + if (id->driver_info & BTUSB_ATH3012) { ++ ++ /* New firmware with patch and sysconfig files already loaded */ ++ if (le16_to_cpu(udev->descriptor.bcdDevice) > 0x0001) ++ return -ENODEV; ++ + ret = ath3k_load_patch(udev); + if (ret < 0) { + BT_ERR("Loading patch file failed"); +diff --git a/drivers/bluetooth/btusb.c b/drivers/bluetooth/btusb.c +index c2de895..b9af6db 100644 +--- a/drivers/bluetooth/btusb.c ++++ b/drivers/bluetooth/btusb.c +@@ -54,11 +54,15 @@ static struct usb_driver btusb_driver; + #define BTUSB_BCM92035 0x10 + #define BTUSB_BROKEN_ISOC 0x20 + #define BTUSB_WRONG_SCO_MTU 0x40 ++#define BTUSB_ATH3012 0x80 + + static struct usb_device_id btusb_table[] = { + /* Generic Bluetooth USB device */ + { USB_DEVICE_INFO(0xe0, 0x01, 0x01) }, + ++ /* Broadcom SoftSailing reporting vendor specific */ ++ { USB_DEVICE(0x05ac, 0x21e1) }, ++ + /* Apple MacBookPro 7,1 */ + { USB_DEVICE(0x05ac, 0x8213) }, + +@@ -71,9 +75,15 @@ static struct usb_device_id btusb_table[] = { + /* Apple MacBookAir3,1, MacBookAir3,2 */ + { USB_DEVICE(0x05ac, 0x821b) }, + ++ /* Apple MacBookAir4,1 */ ++ { USB_DEVICE(0x05ac, 0x821f) }, ++ + /* Apple MacBookPro8,2 */ + { USB_DEVICE(0x05ac, 0x821a) }, + ++ /* Apple MacMini5,1 */ ++ { USB_DEVICE(0x05ac, 0x8281) }, ++ + /* AVM BlueFRITZ! USB v2.0 */ + { USB_DEVICE(0x057c, 0x3800) }, + +@@ -105,12 +115,13 @@ static struct usb_device_id blacklist_table[] = { + /* Atheros 3011 with sflash firmware */ + { USB_DEVICE(0x0cf3, 0x3002), .driver_info = BTUSB_IGNORE }, + { USB_DEVICE(0x13d3, 0x3304), .driver_info = BTUSB_IGNORE }, ++ { USB_DEVICE(0x0930, 0x0215), .driver_info = BTUSB_IGNORE }, + + /* Atheros AR9285 Malbec with sflash firmware */ + { USB_DEVICE(0x03f0, 0x311d), .driver_info = BTUSB_IGNORE }, + + /* Atheros 3012 with sflash firmware */ +- { USB_DEVICE(0x0cf3, 0x3004), .driver_info = BTUSB_IGNORE }, ++ { USB_DEVICE(0x0cf3, 0x3004), .driver_info = BTUSB_ATH3012 }, + + /* Atheros AR5BBU12 with sflash firmware */ + { USB_DEVICE(0x0489, 0xe02c), .driver_info = BTUSB_IGNORE }, +@@ -914,6 +925,15 @@ static int btusb_probe(struct usb_interface *intf, + if (ignore_sniffer && id->driver_info & BTUSB_SNIFFER) + return -ENODEV; + ++ if (id->driver_info & BTUSB_ATH3012) { ++ struct usb_device *udev = interface_to_usbdev(intf); ++ ++ /* Old firmware would otherwise let ath3k driver load ++ * patch and sysconfig files */ ++ if (le16_to_cpu(udev->descriptor.bcdDevice) <= 0x0001) ++ return -ENODEV; ++ } ++ + data = kzalloc(sizeof(*data), GFP_KERNEL); + if (!data) + return -ENOMEM; +diff --git a/drivers/gpu/drm/i915/intel_dp.c b/drivers/gpu/drm/i915/intel_dp.c +index e2aced6..14264a8 100644 +--- a/drivers/gpu/drm/i915/intel_dp.c ++++ b/drivers/gpu/drm/i915/intel_dp.c +@@ -1658,6 +1658,31 @@ g4x_dp_detect(struct intel_dp *intel_dp) + return status; + } + ++static struct edid * ++intel_dp_get_edid(struct drm_connector *connector, struct i2c_adapter *adapter) ++{ ++ struct intel_dp *intel_dp = intel_attached_dp(connector); ++ struct edid *edid; ++ ++ ironlake_edp_panel_vdd_on(intel_dp); ++ edid = drm_get_edid(connector, adapter); ++ ironlake_edp_panel_vdd_off(intel_dp); ++ return edid; ++} ++ ++static int ++intel_dp_get_edid_modes(struct drm_connector *connector, struct i2c_adapter *adapter) ++{ ++ struct intel_dp *intel_dp = intel_attached_dp(connector); ++ int ret; ++ ++ ironlake_edp_panel_vdd_on(intel_dp); ++ ret = intel_ddc_get_modes(connector, adapter); ++ ironlake_edp_panel_vdd_off(intel_dp); ++ return ret; ++} ++ ++ + /** + * Uses CRT_HOTPLUG_EN and CRT_HOTPLUG_STAT to detect DP connection. + * +@@ -1684,7 +1709,7 @@ intel_dp_detect(struct drm_connector *connector, bool force) + if (intel_dp->force_audio) { + intel_dp->has_audio = intel_dp->force_audio > 0; + } else { +- edid = drm_get_edid(connector, &intel_dp->adapter); ++ edid = intel_dp_get_edid(connector, &intel_dp->adapter); + if (edid) { + intel_dp->has_audio = drm_detect_monitor_audio(edid); + connector->display_info.raw_edid = NULL; +@@ -1705,7 +1730,7 @@ static int intel_dp_get_modes(struct drm_connector *connector) + /* We should parse the EDID data and find out if it has an audio sink + */ + +- ret = intel_ddc_get_modes(connector, &intel_dp->adapter); ++ ret = intel_dp_get_edid_modes(connector, &intel_dp->adapter); + if (ret) { + if (is_edp(intel_dp) && !dev_priv->panel_fixed_mode) { + struct drm_display_mode *newmode; +@@ -1741,7 +1766,7 @@ intel_dp_detect_audio(struct drm_connector *connector) + struct edid *edid; + bool has_audio = false; + +- edid = drm_get_edid(connector, &intel_dp->adapter); ++ edid = intel_dp_get_edid(connector, &intel_dp->adapter); + if (edid) { + has_audio = drm_detect_monitor_audio(edid); + +diff --git a/drivers/gpu/drm/i915/intel_panel.c b/drivers/gpu/drm/i915/intel_panel.c +index 05f500c..f8aa821 100644 +--- a/drivers/gpu/drm/i915/intel_panel.c ++++ b/drivers/gpu/drm/i915/intel_panel.c +@@ -226,7 +226,7 @@ static void intel_pch_panel_set_backlight(struct drm_device *dev, u32 level) + I915_WRITE(BLC_PWM_CPU_CTL, val | level); + } + +-void intel_panel_set_backlight(struct drm_device *dev, u32 level) ++static void intel_panel_actually_set_backlight(struct drm_device *dev, u32 level) + { + struct drm_i915_private *dev_priv = dev->dev_private; + u32 tmp; +@@ -254,16 +254,21 @@ void intel_panel_set_backlight(struct drm_device *dev, u32 level) + I915_WRITE(BLC_PWM_CTL, tmp | level); + } + +-void intel_panel_disable_backlight(struct drm_device *dev) ++void intel_panel_set_backlight(struct drm_device *dev, u32 level) + { + struct drm_i915_private *dev_priv = dev->dev_private; + +- if (dev_priv->backlight_enabled) { +- dev_priv->backlight_level = intel_panel_get_backlight(dev); +- dev_priv->backlight_enabled = false; +- } ++ dev_priv->backlight_level = level; ++ if (dev_priv->backlight_enabled) ++ intel_panel_actually_set_backlight(dev, level); ++} ++ ++void intel_panel_disable_backlight(struct drm_device *dev) ++{ ++ struct drm_i915_private *dev_priv = dev->dev_private; + +- intel_panel_set_backlight(dev, 0); ++ dev_priv->backlight_enabled = false; ++ intel_panel_actually_set_backlight(dev, 0); + } + + void intel_panel_enable_backlight(struct drm_device *dev) +@@ -273,8 +278,8 @@ void intel_panel_enable_backlight(struct drm_device *dev) + if (dev_priv->backlight_level == 0) + dev_priv->backlight_level = intel_panel_get_max_backlight(dev); + +- intel_panel_set_backlight(dev, dev_priv->backlight_level); + dev_priv->backlight_enabled = true; ++ intel_panel_actually_set_backlight(dev, dev_priv->backlight_level); + } + + void intel_panel_setup_backlight(struct drm_device *dev) +diff --git a/drivers/gpu/drm/radeon/atombios_dp.c b/drivers/gpu/drm/radeon/atombios_dp.c +index 79e8ebc..b5628ce 100644 +--- a/drivers/gpu/drm/radeon/atombios_dp.c ++++ b/drivers/gpu/drm/radeon/atombios_dp.c +@@ -553,6 +553,7 @@ static void radeon_dp_set_panel_mode(struct drm_encoder *encoder, + { + struct drm_device *dev = encoder->dev; + struct radeon_device *rdev = dev->dev_private; ++ struct radeon_connector *radeon_connector = to_radeon_connector(connector); + int panel_mode = DP_PANEL_MODE_EXTERNAL_DP_MODE; + + if (!ASIC_IS_DCE4(rdev)) +@@ -560,10 +561,20 @@ static void radeon_dp_set_panel_mode(struct drm_encoder *encoder, + + if (radeon_connector_encoder_is_dp_bridge(connector)) + panel_mode = DP_PANEL_MODE_INTERNAL_DP1_MODE; ++ else if (connector->connector_type == DRM_MODE_CONNECTOR_eDP) { ++ u8 tmp = radeon_read_dpcd_reg(radeon_connector, DP_EDP_CONFIGURATION_CAP); ++ if (tmp & 1) ++ panel_mode = DP_PANEL_MODE_INTERNAL_DP2_MODE; ++ } + + atombios_dig_encoder_setup(encoder, + ATOM_ENCODER_CMD_SETUP_PANEL_MODE, + panel_mode); ++ ++ if ((connector->connector_type == DRM_MODE_CONNECTOR_eDP) && ++ (panel_mode == DP_PANEL_MODE_INTERNAL_DP2_MODE)) { ++ radeon_write_dpcd_reg(radeon_connector, DP_EDP_CONFIGURATION_SET, 1); ++ } + } + + void radeon_dp_set_link_config(struct drm_connector *connector, +diff --git a/drivers/gpu/drm/radeon/evergreen.c b/drivers/gpu/drm/radeon/evergreen.c +index ea7a24e..f1bdb58 100644 +--- a/drivers/gpu/drm/radeon/evergreen.c ++++ b/drivers/gpu/drm/radeon/evergreen.c +@@ -353,6 +353,7 @@ void evergreen_hpd_init(struct radeon_device *rdev) + default: + break; + } ++ radeon_hpd_set_polarity(rdev, radeon_connector->hpd.hpd); + } + if (rdev->irq.installed) + evergreen_irq_set(rdev); +diff --git a/drivers/gpu/drm/radeon/r100.c b/drivers/gpu/drm/radeon/r100.c +index 7fcdbbb..c9a0dae 100644 +--- a/drivers/gpu/drm/radeon/r100.c ++++ b/drivers/gpu/drm/radeon/r100.c +@@ -434,6 +434,7 @@ void r100_hpd_init(struct radeon_device *rdev) + default: + break; + } ++ radeon_hpd_set_polarity(rdev, radeon_connector->hpd.hpd); + } + if (rdev->irq.installed) + r100_irq_set(rdev); +diff --git a/drivers/gpu/drm/radeon/r600.c b/drivers/gpu/drm/radeon/r600.c +index 1dea9d6..1a4ed43 100644 +--- a/drivers/gpu/drm/radeon/r600.c ++++ b/drivers/gpu/drm/radeon/r600.c +@@ -762,13 +762,14 @@ void r600_hpd_init(struct radeon_device *rdev) + struct drm_device *dev = rdev->ddev; + struct drm_connector *connector; + +- if (ASIC_IS_DCE3(rdev)) { +- u32 tmp = DC_HPDx_CONNECTION_TIMER(0x9c4) | DC_HPDx_RX_INT_TIMER(0xfa); +- if (ASIC_IS_DCE32(rdev)) +- tmp |= DC_HPDx_EN; ++ list_for_each_entry(connector, &dev->mode_config.connector_list, head) { ++ struct radeon_connector *radeon_connector = to_radeon_connector(connector); ++ ++ if (ASIC_IS_DCE3(rdev)) { ++ u32 tmp = DC_HPDx_CONNECTION_TIMER(0x9c4) | DC_HPDx_RX_INT_TIMER(0xfa); ++ if (ASIC_IS_DCE32(rdev)) ++ tmp |= DC_HPDx_EN; + +- list_for_each_entry(connector, &dev->mode_config.connector_list, head) { +- struct radeon_connector *radeon_connector = to_radeon_connector(connector); + switch (radeon_connector->hpd.hpd) { + case RADEON_HPD_1: + WREG32(DC_HPD1_CONTROL, tmp); +@@ -798,10 +799,7 @@ void r600_hpd_init(struct radeon_device *rdev) + default: + break; + } +- } +- } else { +- list_for_each_entry(connector, &dev->mode_config.connector_list, head) { +- struct radeon_connector *radeon_connector = to_radeon_connector(connector); ++ } else { + switch (radeon_connector->hpd.hpd) { + case RADEON_HPD_1: + WREG32(DC_HOT_PLUG_DETECT1_CONTROL, DC_HOT_PLUG_DETECTx_EN); +@@ -819,6 +817,7 @@ void r600_hpd_init(struct radeon_device *rdev) + break; + } + } ++ radeon_hpd_set_polarity(rdev, radeon_connector->hpd.hpd); + } + if (rdev->irq.installed) + r600_irq_set(rdev); +diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h +index 0bb4ddf..59d72d0 100644 +--- a/drivers/gpu/drm/radeon/radeon.h ++++ b/drivers/gpu/drm/radeon/radeon.h +@@ -93,6 +93,7 @@ extern int radeon_audio; + extern int radeon_disp_priority; + extern int radeon_hw_i2c; + extern int radeon_pcie_gen2; ++extern int radeon_msi; + + /* + * Copy from radeon_drv.h so we don't have to include both and have conflicting +diff --git a/drivers/gpu/drm/radeon/radeon_combios.c b/drivers/gpu/drm/radeon/radeon_combios.c +index cd3c86c..859df6b 100644 +--- a/drivers/gpu/drm/radeon/radeon_combios.c ++++ b/drivers/gpu/drm/radeon/radeon_combios.c +@@ -620,8 +620,8 @@ static struct radeon_i2c_bus_rec combios_setup_i2c_bus(struct radeon_device *rde + i2c.y_data_mask = 0x80; + } else { + /* default masks for ddc pads */ +- i2c.mask_clk_mask = RADEON_GPIO_EN_1; +- i2c.mask_data_mask = RADEON_GPIO_EN_0; ++ i2c.mask_clk_mask = RADEON_GPIO_MASK_1; ++ i2c.mask_data_mask = RADEON_GPIO_MASK_0; + i2c.a_clk_mask = RADEON_GPIO_A_1; + i2c.a_data_mask = RADEON_GPIO_A_0; + i2c.en_clk_mask = RADEON_GPIO_EN_1; +diff --git a/drivers/gpu/drm/radeon/radeon_connectors.c b/drivers/gpu/drm/radeon/radeon_connectors.c +index 05b8b2c..2109c17 100644 +--- a/drivers/gpu/drm/radeon/radeon_connectors.c ++++ b/drivers/gpu/drm/radeon/radeon_connectors.c +@@ -715,6 +715,7 @@ radeon_vga_detect(struct drm_connector *connector, bool force) + dret = radeon_ddc_probe(radeon_connector, + radeon_connector->requires_extended_probe); + if (dret) { ++ radeon_connector->detected_by_load = false; + if (radeon_connector->edid) { + kfree(radeon_connector->edid); + radeon_connector->edid = NULL; +@@ -741,12 +742,21 @@ radeon_vga_detect(struct drm_connector *connector, bool force) + } else { + + /* if we aren't forcing don't do destructive polling */ +- if (!force) +- return connector->status; ++ if (!force) { ++ /* only return the previous status if we last ++ * detected a monitor via load. ++ */ ++ if (radeon_connector->detected_by_load) ++ return connector->status; ++ else ++ return ret; ++ } + + if (radeon_connector->dac_load_detect && encoder) { + encoder_funcs = encoder->helper_private; + ret = encoder_funcs->detect(encoder, connector); ++ if (ret != connector_status_disconnected) ++ radeon_connector->detected_by_load = true; + } + } + +@@ -888,6 +898,7 @@ radeon_dvi_detect(struct drm_connector *connector, bool force) + dret = radeon_ddc_probe(radeon_connector, + radeon_connector->requires_extended_probe); + if (dret) { ++ radeon_connector->detected_by_load = false; + if (radeon_connector->edid) { + kfree(radeon_connector->edid); + radeon_connector->edid = NULL; +@@ -950,8 +961,18 @@ radeon_dvi_detect(struct drm_connector *connector, bool force) + if ((ret == connector_status_connected) && (radeon_connector->use_digital == true)) + goto out; + ++ /* DVI-D and HDMI-A are digital only */ ++ if ((connector->connector_type == DRM_MODE_CONNECTOR_DVID) || ++ (connector->connector_type == DRM_MODE_CONNECTOR_HDMIA)) ++ goto out; ++ ++ /* if we aren't forcing don't do destructive polling */ + if (!force) { +- ret = connector->status; ++ /* only return the previous status if we last ++ * detected a monitor via load. ++ */ ++ if (radeon_connector->detected_by_load) ++ ret = connector->status; + goto out; + } + +@@ -976,6 +997,8 @@ radeon_dvi_detect(struct drm_connector *connector, bool force) + if (ret == connector_status_connected) { + radeon_connector->use_digital = false; + } ++ if (ret != connector_status_disconnected) ++ radeon_connector->detected_by_load = true; + } + break; + } +diff --git a/drivers/gpu/drm/radeon/radeon_drv.c b/drivers/gpu/drm/radeon/radeon_drv.c +index 73dfbe8..60e1605 100644 +--- a/drivers/gpu/drm/radeon/radeon_drv.c ++++ b/drivers/gpu/drm/radeon/radeon_drv.c +@@ -117,6 +117,7 @@ int radeon_audio = 0; + int radeon_disp_priority = 0; + int radeon_hw_i2c = 0; + int radeon_pcie_gen2 = 0; ++int radeon_msi = -1; + + MODULE_PARM_DESC(no_wb, "Disable AGP writeback for scratch registers"); + module_param_named(no_wb, radeon_no_wb, int, 0444); +@@ -163,6 +164,9 @@ module_param_named(hw_i2c, radeon_hw_i2c, int, 0444); + MODULE_PARM_DESC(pcie_gen2, "PCIE Gen2 mode (1 = enable)"); + module_param_named(pcie_gen2, radeon_pcie_gen2, int, 0444); + ++MODULE_PARM_DESC(msi, "MSI support (1 = enable, 0 = disable, -1 = auto)"); ++module_param_named(msi, radeon_msi, int, 0444); ++ + static int radeon_suspend(struct drm_device *dev, pm_message_t state) + { + drm_radeon_private_t *dev_priv = dev->dev_private; +diff --git a/drivers/gpu/drm/radeon/radeon_irq_kms.c b/drivers/gpu/drm/radeon/radeon_irq_kms.c +index 9ec830c..fecc1aa 100644 +--- a/drivers/gpu/drm/radeon/radeon_irq_kms.c ++++ b/drivers/gpu/drm/radeon/radeon_irq_kms.c +@@ -108,6 +108,46 @@ void radeon_driver_irq_uninstall_kms(struct drm_device *dev) + radeon_irq_set(rdev); + } + ++static bool radeon_msi_ok(struct radeon_device *rdev) ++{ ++ /* RV370/RV380 was first asic with MSI support */ ++ if (rdev->family < CHIP_RV380) ++ return false; ++ ++ /* MSIs don't work on AGP */ ++ if (rdev->flags & RADEON_IS_AGP) ++ return false; ++ ++ /* force MSI on */ ++ if (radeon_msi == 1) ++ return true; ++ else if (radeon_msi == 0) ++ return false; ++ ++ /* Quirks */ ++ /* HP RS690 only seems to work with MSIs. */ ++ if ((rdev->pdev->device == 0x791f) && ++ (rdev->pdev->subsystem_vendor == 0x103c) && ++ (rdev->pdev->subsystem_device == 0x30c2)) ++ return true; ++ ++ /* Dell RS690 only seems to work with MSIs. */ ++ if ((rdev->pdev->device == 0x791f) && ++ (rdev->pdev->subsystem_vendor == 0x1028) && ++ (rdev->pdev->subsystem_device == 0x01fd)) ++ return true; ++ ++ if (rdev->flags & RADEON_IS_IGP) { ++ /* APUs work fine with MSIs */ ++ if (rdev->family >= CHIP_PALM) ++ return true; ++ /* lots of IGPs have problems with MSIs */ ++ return false; ++ } ++ ++ return true; ++} ++ + int radeon_irq_kms_init(struct radeon_device *rdev) + { + int i; +@@ -124,12 +164,8 @@ int radeon_irq_kms_init(struct radeon_device *rdev) + } + /* enable msi */ + rdev->msi_enabled = 0; +- /* MSIs don't seem to work reliably on all IGP +- * chips. Disable MSI on them for now. +- */ +- if ((rdev->family >= CHIP_RV380) && +- ((!(rdev->flags & RADEON_IS_IGP)) || (rdev->family >= CHIP_PALM)) && +- (!(rdev->flags & RADEON_IS_AGP))) { ++ ++ if (radeon_msi_ok(rdev)) { + int ret = pci_enable_msi(rdev->pdev); + if (!ret) { + rdev->msi_enabled = 1; +diff --git a/drivers/gpu/drm/radeon/radeon_mode.h b/drivers/gpu/drm/radeon/radeon_mode.h +index 68820f5..ed0178f 100644 +--- a/drivers/gpu/drm/radeon/radeon_mode.h ++++ b/drivers/gpu/drm/radeon/radeon_mode.h +@@ -447,6 +447,7 @@ struct radeon_connector { + struct edid *edid; + void *con_priv; + bool dac_load_detect; ++ bool detected_by_load; /* if the connection status was determined by load */ + uint16_t connector_object_id; + struct radeon_hpd hpd; + struct radeon_router router; +diff --git a/drivers/gpu/drm/radeon/rs600.c b/drivers/gpu/drm/radeon/rs600.c +index 1f5850e..aea28c3 100644 +--- a/drivers/gpu/drm/radeon/rs600.c ++++ b/drivers/gpu/drm/radeon/rs600.c +@@ -287,6 +287,7 @@ void rs600_hpd_init(struct radeon_device *rdev) + default: + break; + } ++ radeon_hpd_set_polarity(rdev, radeon_connector->hpd.hpd); + } + if (rdev->irq.installed) + rs600_irq_set(rdev); +diff --git a/drivers/hid/Kconfig b/drivers/hid/Kconfig +index 36ca465..7e0acf4 100644 +--- a/drivers/hid/Kconfig ++++ b/drivers/hid/Kconfig +@@ -69,7 +69,7 @@ config HID_ACRUX + Say Y here if you want to enable support for ACRUX game controllers. + + config HID_ACRUX_FF +- tristate "ACRUX force feedback support" ++ bool "ACRUX force feedback support" + depends on HID_ACRUX + select INPUT_FF_MEMLESS + ---help--- +@@ -314,6 +314,7 @@ config HID_MULTITOUCH + - Hanvon dual touch panels + - Ilitek dual touch panels + - IrTouch Infrared USB panels ++ - LG Display panels (Dell ST2220Tc) + - Lumio CrystalTouch panels + - MosArt dual-touch panels + - PenMount dual touch panels +diff --git a/drivers/hid/hid-apple.c b/drivers/hid/hid-apple.c +index b85744f..299d238 100644 +--- a/drivers/hid/hid-apple.c ++++ b/drivers/hid/hid-apple.c +@@ -444,11 +444,20 @@ static const struct hid_device_id apple_devices[] = { + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER4_HF_JIS), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN | + APPLE_RDESC_JIS }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_REVB_ANSI), ++ .driver_data = APPLE_HAS_FN }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_REVB_ISO), ++ .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_REVB_JIS), ++ .driver_data = APPLE_HAS_FN }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_ANSI), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_ISO), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN | + APPLE_ISO_KEYBOARD }, ++ { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2011_ISO), ++ .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN | ++ APPLE_ISO_KEYBOARD }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_JIS), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING_ANSI), +@@ -487,6 +496,24 @@ static const struct hid_device_id apple_devices[] = { + .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_JIS), + .driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_ANSI), ++ .driver_data = APPLE_HAS_FN }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_ISO), ++ .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_JIS), ++ .driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_ANSI), ++ .driver_data = APPLE_HAS_FN }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_ISO), ++ .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_JIS), ++ .driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ANSI), ++ .driver_data = APPLE_HAS_FN }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ISO), ++ .driver_data = APPLE_HAS_FN | APPLE_ISO_KEYBOARD }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_JIS), ++ .driver_data = APPLE_HAS_FN | APPLE_RDESC_JIS }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ANSI), + .driver_data = APPLE_NUMLOCK_EMULATION | APPLE_HAS_FN }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ISO), +diff --git a/drivers/hid/hid-core.c b/drivers/hid/hid-core.c +index 6f3289a..4f81d20 100644 +--- a/drivers/hid/hid-core.c ++++ b/drivers/hid/hid-core.c +@@ -1340,9 +1340,22 @@ static const struct hid_device_id hid_have_special_driver[] = { + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_ANSI) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_ISO) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_JIS) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ANSI) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ISO) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_JIS) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_ANSI) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_ISO) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6_JIS) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_ANSI) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_ISO) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING6A_JIS) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_REVB_ANSI) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_REVB_ISO) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_REVB_JIS) }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ANSI) }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ISO) }, + { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_JIS) }, ++ { HID_BLUETOOTH_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_ALU_WIRELESS_2011_ISO) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY) }, + { HID_USB_DEVICE(USB_VENDOR_ID_ASUS, USB_DEVICE_ID_ASUS_T91MT) }, +@@ -1395,6 +1408,7 @@ static const struct hid_device_id hid_have_special_driver[] = { + { HID_USB_DEVICE(USB_VENDOR_ID_KYE, USB_DEVICE_ID_KYE_ERGO_525V) }, + { HID_USB_DEVICE(USB_VENDOR_ID_LABTEC, USB_DEVICE_ID_LABTEC_WIRELESS_KEYBOARD) }, + { HID_USB_DEVICE(USB_VENDOR_ID_LCPOWER, USB_DEVICE_ID_LCPOWER_LC1000 ) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_LG, USB_DEVICE_ID_LG_MULTITOUCH) }, + { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_MX3000_RECEIVER) }, + { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_S510_RECEIVER) }, + { HID_USB_DEVICE(USB_VENDOR_ID_LOGITECH, USB_DEVICE_ID_S510_RECEIVER_2) }, +@@ -1883,6 +1897,9 @@ static const struct hid_device_id hid_mouse_ignore_list[] = { + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_ANSI) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_ISO) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5_JIS) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ANSI) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_ISO) }, ++ { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_WELLSPRING5A_JIS) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY) }, + { HID_USB_DEVICE(USB_VENDOR_ID_APPLE, USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY) }, + { } +diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h +index c946d90..c97003c 100644 +--- a/drivers/hid/hid-ids.h ++++ b/drivers/hid/hid-ids.h +@@ -109,9 +109,22 @@ + #define USB_DEVICE_ID_APPLE_WELLSPRING5_ANSI 0x0245 + #define USB_DEVICE_ID_APPLE_WELLSPRING5_ISO 0x0246 + #define USB_DEVICE_ID_APPLE_WELLSPRING5_JIS 0x0247 ++#define USB_DEVICE_ID_APPLE_WELLSPRING6A_ANSI 0x0249 ++#define USB_DEVICE_ID_APPLE_WELLSPRING6A_ISO 0x024a ++#define USB_DEVICE_ID_APPLE_WELLSPRING6A_JIS 0x024b ++#define USB_DEVICE_ID_APPLE_WELLSPRING6_ANSI 0x024c ++#define USB_DEVICE_ID_APPLE_WELLSPRING6_ISO 0x024d ++#define USB_DEVICE_ID_APPLE_WELLSPRING6_JIS 0x024e ++#define USB_DEVICE_ID_APPLE_ALU_REVB_ANSI 0x024f ++#define USB_DEVICE_ID_APPLE_ALU_REVB_ISO 0x0250 ++#define USB_DEVICE_ID_APPLE_ALU_REVB_JIS 0x0251 ++#define USB_DEVICE_ID_APPLE_WELLSPRING5A_ANSI 0x0252 ++#define USB_DEVICE_ID_APPLE_WELLSPRING5A_ISO 0x0253 ++#define USB_DEVICE_ID_APPLE_WELLSPRING5A_JIS 0x0254 + #define USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ANSI 0x0239 + #define USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_ISO 0x023a + #define USB_DEVICE_ID_APPLE_ALU_WIRELESS_2009_JIS 0x023b ++#define USB_DEVICE_ID_APPLE_ALU_WIRELESS_2011_ISO 0x0256 + #define USB_DEVICE_ID_APPLE_FOUNTAIN_TP_ONLY 0x030a + #define USB_DEVICE_ID_APPLE_GEYSER1_TP_ONLY 0x030b + #define USB_DEVICE_ID_APPLE_ATV_IRCONTROL 0x8241 +@@ -274,6 +287,7 @@ + #define USB_DEVICE_ID_PENPOWER 0x00f4 + + #define USB_VENDOR_ID_GREENASIA 0x0e8f ++#define USB_DEVICE_ID_GREENASIA_DUAL_USB_JOYPAD 0x3013 + + #define USB_VENDOR_ID_GRETAGMACBETH 0x0971 + #define USB_DEVICE_ID_GRETAGMACBETH_HUEY 0x2005 +@@ -416,6 +430,9 @@ + #define USB_DEVICE_ID_LD_HYBRID 0x2090 + #define USB_DEVICE_ID_LD_HEATCONTROL 0x20A0 + ++#define USB_VENDOR_ID_LG 0x1fd2 ++#define USB_DEVICE_ID_LG_MULTITOUCH 0x0064 ++ + #define USB_VENDOR_ID_LOGITECH 0x046d + #define USB_DEVICE_ID_LOGITECH_RECEIVER 0xc101 + #define USB_DEVICE_ID_LOGITECH_HARMONY_FIRST 0xc110 +diff --git a/drivers/hid/hid-multitouch.c b/drivers/hid/hid-multitouch.c +index 62cac4d..685d8e4 100644 +--- a/drivers/hid/hid-multitouch.c ++++ b/drivers/hid/hid-multitouch.c +@@ -672,6 +672,11 @@ static const struct hid_device_id mt_devices[] = { + HID_USB_DEVICE(USB_VENDOR_ID_IRTOUCHSYSTEMS, + USB_DEVICE_ID_IRTOUCH_INFRARED_USB) }, + ++ /* LG Display panels */ ++ { .driver_data = MT_CLS_DEFAULT, ++ HID_USB_DEVICE(USB_VENDOR_ID_LG, ++ USB_DEVICE_ID_LG_MULTITOUCH) }, ++ + /* Lumio panels */ + { .driver_data = MT_CLS_CONFIDENCE_MINUS_ONE, + HID_USB_DEVICE(USB_VENDOR_ID_LUMIO, +diff --git a/drivers/hid/usbhid/hid-quirks.c b/drivers/hid/usbhid/hid-quirks.c +index 4bdb5d4..3146fdc 100644 +--- a/drivers/hid/usbhid/hid-quirks.c ++++ b/drivers/hid/usbhid/hid-quirks.c +@@ -47,6 +47,7 @@ static const struct hid_blacklist { + { USB_VENDOR_ID_AFATECH, USB_DEVICE_ID_AFATECH_AF9016, HID_QUIRK_FULLSPEED_INTERVAL }, + + { USB_VENDOR_ID_ETURBOTOUCH, USB_DEVICE_ID_ETURBOTOUCH, HID_QUIRK_MULTI_INPUT }, ++ { USB_VENDOR_ID_GREENASIA, USB_DEVICE_ID_GREENASIA_DUAL_USB_JOYPAD, HID_QUIRK_MULTI_INPUT }, + { USB_VENDOR_ID_PANTHERLORD, USB_DEVICE_ID_PANTHERLORD_TWIN_USB_JOYSTICK, HID_QUIRK_MULTI_INPUT | HID_QUIRK_SKIP_OUTPUT_REPORTS }, + { USB_VENDOR_ID_PLAYDOTCOM, USB_DEVICE_ID_PLAYDOTCOM_EMS_USBII, HID_QUIRK_MULTI_INPUT }, + { USB_VENDOR_ID_TOUCHPACK, USB_DEVICE_ID_TOUCHPACK_RTS, HID_QUIRK_MULTI_INPUT }, +diff --git a/drivers/hwmon/coretemp.c b/drivers/hwmon/coretemp.c +index 0070d54..f642194 100644 +--- a/drivers/hwmon/coretemp.c ++++ b/drivers/hwmon/coretemp.c +@@ -50,14 +50,13 @@ + #ifdef CONFIG_SMP + #define TO_PHYS_ID(cpu) cpu_data(cpu).phys_proc_id + #define TO_CORE_ID(cpu) cpu_data(cpu).cpu_core_id +-#define TO_ATTR_NO(cpu) (TO_CORE_ID(cpu) + BASE_SYSFS_ATTR_NO) + #define for_each_sibling(i, cpu) for_each_cpu(i, cpu_sibling_mask(cpu)) + #else + #define TO_PHYS_ID(cpu) (cpu) + #define TO_CORE_ID(cpu) (cpu) +-#define TO_ATTR_NO(cpu) (cpu) + #define for_each_sibling(i, cpu) for (i = 0; false; ) + #endif ++#define TO_ATTR_NO(cpu) (TO_CORE_ID(cpu) + BASE_SYSFS_ATTR_NO) + + /* + * Per-Core Temperature Data +diff --git a/drivers/hwmon/w83627ehf.c b/drivers/hwmon/w83627ehf.c +index 36d7f27..4b2fc50 100644 +--- a/drivers/hwmon/w83627ehf.c ++++ b/drivers/hwmon/w83627ehf.c +@@ -1756,7 +1756,17 @@ static inline void __devinit w83627ehf_init_device(struct w83627ehf_data *data, + diode = 0x70; + } + for (i = 0; i < 3; i++) { +- if ((tmp & (0x02 << i))) ++ const char *label = NULL; ++ ++ if (data->temp_label) ++ label = data->temp_label[data->temp_src[i]]; ++ ++ /* Digital source overrides analog type */ ++ if (label && strncmp(label, "PECI", 4) == 0) ++ data->temp_type[i] = 6; ++ else if (label && strncmp(label, "AMD", 3) == 0) ++ data->temp_type[i] = 5; ++ else if ((tmp & (0x02 << i))) + data->temp_type[i] = (diode & (0x10 << i)) ? 1 : 3; + else + data->temp_type[i] = 4; /* thermistor */ +diff --git a/drivers/hwspinlock/hwspinlock_core.c b/drivers/hwspinlock/hwspinlock_core.c +index 43a6271..12f7c83 100644 +--- a/drivers/hwspinlock/hwspinlock_core.c ++++ b/drivers/hwspinlock/hwspinlock_core.c +@@ -26,6 +26,7 @@ + #include <linux/radix-tree.h> + #include <linux/hwspinlock.h> + #include <linux/pm_runtime.h> ++#include <linux/mutex.h> + + #include "hwspinlock_internal.h" + +@@ -52,10 +53,12 @@ + static RADIX_TREE(hwspinlock_tree, GFP_KERNEL); + + /* +- * Synchronization of access to the tree is achieved using this spinlock, ++ * Synchronization of access to the tree is achieved using this mutex, + * as the radix-tree API requires that users provide all synchronisation. ++ * A mutex is needed because we're using non-atomic radix tree allocations. + */ +-static DEFINE_SPINLOCK(hwspinlock_tree_lock); ++static DEFINE_MUTEX(hwspinlock_tree_lock); ++ + + /** + * __hwspin_trylock() - attempt to lock a specific hwspinlock +@@ -261,8 +264,7 @@ EXPORT_SYMBOL_GPL(__hwspin_unlock); + * This function should be called from the underlying platform-specific + * implementation, to register a new hwspinlock instance. + * +- * Can be called from an atomic context (will not sleep) but not from +- * within interrupt context. ++ * Should be called from a process context (might sleep) + * + * Returns 0 on success, or an appropriate error code on failure + */ +@@ -279,7 +281,7 @@ int hwspin_lock_register(struct hwspinlock *hwlock) + + spin_lock_init(&hwlock->lock); + +- spin_lock(&hwspinlock_tree_lock); ++ mutex_lock(&hwspinlock_tree_lock); + + ret = radix_tree_insert(&hwspinlock_tree, hwlock->id, hwlock); + if (ret) +@@ -293,7 +295,7 @@ int hwspin_lock_register(struct hwspinlock *hwlock) + WARN_ON(tmp != hwlock); + + out: +- spin_unlock(&hwspinlock_tree_lock); ++ mutex_unlock(&hwspinlock_tree_lock); + return ret; + } + EXPORT_SYMBOL_GPL(hwspin_lock_register); +@@ -305,8 +307,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_register); + * This function should be called from the underlying platform-specific + * implementation, to unregister an existing (and unused) hwspinlock. + * +- * Can be called from an atomic context (will not sleep) but not from +- * within interrupt context. ++ * Should be called from a process context (might sleep) + * + * Returns the address of hwspinlock @id on success, or NULL on failure + */ +@@ -315,7 +316,7 @@ struct hwspinlock *hwspin_lock_unregister(unsigned int id) + struct hwspinlock *hwlock = NULL; + int ret; + +- spin_lock(&hwspinlock_tree_lock); ++ mutex_lock(&hwspinlock_tree_lock); + + /* make sure the hwspinlock is not in use (tag is set) */ + ret = radix_tree_tag_get(&hwspinlock_tree, id, HWSPINLOCK_UNUSED); +@@ -331,7 +332,7 @@ struct hwspinlock *hwspin_lock_unregister(unsigned int id) + } + + out: +- spin_unlock(&hwspinlock_tree_lock); ++ mutex_unlock(&hwspinlock_tree_lock); + return hwlock; + } + EXPORT_SYMBOL_GPL(hwspin_lock_unregister); +@@ -400,9 +401,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_get_id); + * to the remote core before it can be used for synchronization (to get the + * id of a given hwlock, use hwspin_lock_get_id()). + * +- * Can be called from an atomic context (will not sleep) but not from +- * within interrupt context (simply because there is no use case for +- * that yet). ++ * Should be called from a process context (might sleep) + * + * Returns the address of the assigned hwspinlock, or NULL on error + */ +@@ -411,7 +410,7 @@ struct hwspinlock *hwspin_lock_request(void) + struct hwspinlock *hwlock; + int ret; + +- spin_lock(&hwspinlock_tree_lock); ++ mutex_lock(&hwspinlock_tree_lock); + + /* look for an unused lock */ + ret = radix_tree_gang_lookup_tag(&hwspinlock_tree, (void **)&hwlock, +@@ -431,7 +430,7 @@ struct hwspinlock *hwspin_lock_request(void) + hwlock = NULL; + + out: +- spin_unlock(&hwspinlock_tree_lock); ++ mutex_unlock(&hwspinlock_tree_lock); + return hwlock; + } + EXPORT_SYMBOL_GPL(hwspin_lock_request); +@@ -445,9 +444,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_request); + * Usually early board code will be calling this function in order to + * reserve specific hwspinlock ids for predefined purposes. + * +- * Can be called from an atomic context (will not sleep) but not from +- * within interrupt context (simply because there is no use case for +- * that yet). ++ * Should be called from a process context (might sleep) + * + * Returns the address of the assigned hwspinlock, or NULL on error + */ +@@ -456,7 +453,7 @@ struct hwspinlock *hwspin_lock_request_specific(unsigned int id) + struct hwspinlock *hwlock; + int ret; + +- spin_lock(&hwspinlock_tree_lock); ++ mutex_lock(&hwspinlock_tree_lock); + + /* make sure this hwspinlock exists */ + hwlock = radix_tree_lookup(&hwspinlock_tree, id); +@@ -482,7 +479,7 @@ struct hwspinlock *hwspin_lock_request_specific(unsigned int id) + hwlock = NULL; + + out: +- spin_unlock(&hwspinlock_tree_lock); ++ mutex_unlock(&hwspinlock_tree_lock); + return hwlock; + } + EXPORT_SYMBOL_GPL(hwspin_lock_request_specific); +@@ -495,9 +492,7 @@ EXPORT_SYMBOL_GPL(hwspin_lock_request_specific); + * Should only be called with an @hwlock that was retrieved from + * an earlier call to omap_hwspin_lock_request{_specific}. + * +- * Can be called from an atomic context (will not sleep) but not from +- * within interrupt context (simply because there is no use case for +- * that yet). ++ * Should be called from a process context (might sleep) + * + * Returns 0 on success, or an appropriate error code on failure + */ +@@ -511,7 +506,7 @@ int hwspin_lock_free(struct hwspinlock *hwlock) + return -EINVAL; + } + +- spin_lock(&hwspinlock_tree_lock); ++ mutex_lock(&hwspinlock_tree_lock); + + /* make sure the hwspinlock is used */ + ret = radix_tree_tag_get(&hwspinlock_tree, hwlock->id, +@@ -538,7 +533,7 @@ int hwspin_lock_free(struct hwspinlock *hwlock) + module_put(hwlock->owner); + + out: +- spin_unlock(&hwspinlock_tree_lock); ++ mutex_unlock(&hwspinlock_tree_lock); + return ret; + } + EXPORT_SYMBOL_GPL(hwspin_lock_free); +diff --git a/drivers/leds/led-class.c b/drivers/leds/led-class.c +index dc3d3d8..661b692 100644 +--- a/drivers/leds/led-class.c ++++ b/drivers/leds/led-class.c +@@ -267,9 +267,14 @@ void led_blink_set(struct led_classdev *led_cdev, + unsigned long *delay_on, + unsigned long *delay_off) + { ++ del_timer_sync(&led_cdev->blink_timer); ++ + if (led_cdev->blink_set && +- !led_cdev->blink_set(led_cdev, delay_on, delay_off)) ++ !led_cdev->blink_set(led_cdev, delay_on, delay_off)) { ++ led_cdev->blink_delay_on = *delay_on; ++ led_cdev->blink_delay_off = *delay_off; + return; ++ } + + /* blink with 1 Hz as default if nothing specified */ + if (!*delay_on && !*delay_off) +diff --git a/drivers/md/raid5.c b/drivers/md/raid5.c +index 2581ba1..e509147 100644 +--- a/drivers/md/raid5.c ++++ b/drivers/md/raid5.c +@@ -3369,7 +3369,7 @@ static void handle_stripe6(struct stripe_head *sh) + /* Not in-sync */; + else if (test_bit(In_sync, &rdev->flags)) + set_bit(R5_Insync, &dev->flags); +- else { ++ else if (!test_bit(Faulty, &rdev->flags)) { + /* in sync if before recovery_offset */ + if (sh->sector + STRIPE_SECTORS <= rdev->recovery_offset) + set_bit(R5_Insync, &dev->flags); +diff --git a/drivers/media/dvb/dvb-usb/dib0700_core.c b/drivers/media/dvb/dvb-usb/dib0700_core.c +index 5eb91b4..a224e94 100644 +--- a/drivers/media/dvb/dvb-usb/dib0700_core.c ++++ b/drivers/media/dvb/dvb-usb/dib0700_core.c +@@ -30,6 +30,11 @@ int dib0700_get_version(struct dvb_usb_device *d, u32 *hwversion, + struct dib0700_state *st = d->priv; + int ret; + ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } ++ + ret = usb_control_msg(d->udev, usb_rcvctrlpipe(d->udev, 0), + REQUEST_GET_VERSION, + USB_TYPE_VENDOR | USB_DIR_IN, 0, 0, +@@ -46,6 +51,7 @@ int dib0700_get_version(struct dvb_usb_device *d, u32 *hwversion, + if (fwtype != NULL) + *fwtype = (st->buf[12] << 24) | (st->buf[13] << 16) | + (st->buf[14] << 8) | st->buf[15]; ++ mutex_unlock(&d->usb_mutex); + return ret; + } + +@@ -108,7 +114,12 @@ int dib0700_ctrl_rd(struct dvb_usb_device *d, u8 *tx, u8 txlen, u8 *rx, u8 rxlen + int dib0700_set_gpio(struct dvb_usb_device *d, enum dib07x0_gpios gpio, u8 gpio_dir, u8 gpio_val) + { + struct dib0700_state *st = d->priv; +- s16 ret; ++ int ret; ++ ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } + + st->buf[0] = REQUEST_SET_GPIO; + st->buf[1] = gpio; +@@ -116,6 +127,7 @@ int dib0700_set_gpio(struct dvb_usb_device *d, enum dib07x0_gpios gpio, u8 gpio_ + + ret = dib0700_ctrl_wr(d, st->buf, 3); + ++ mutex_unlock(&d->usb_mutex); + return ret; + } + +@@ -125,6 +137,11 @@ static int dib0700_set_usb_xfer_len(struct dvb_usb_device *d, u16 nb_ts_packets) + int ret; + + if (st->fw_version >= 0x10201) { ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } ++ + st->buf[0] = REQUEST_SET_USB_XFER_LEN; + st->buf[1] = (nb_ts_packets >> 8) & 0xff; + st->buf[2] = nb_ts_packets & 0xff; +@@ -132,6 +149,7 @@ static int dib0700_set_usb_xfer_len(struct dvb_usb_device *d, u16 nb_ts_packets) + deb_info("set the USB xfer len to %i Ts packet\n", nb_ts_packets); + + ret = dib0700_ctrl_wr(d, st->buf, 3); ++ mutex_unlock(&d->usb_mutex); + } else { + deb_info("this firmware does not allow to change the USB xfer len\n"); + ret = -EIO; +@@ -208,6 +226,10 @@ static int dib0700_i2c_xfer_new(struct i2c_adapter *adap, struct i2c_msg *msg, + + } else { + /* Write request */ ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } + st->buf[0] = REQUEST_NEW_I2C_WRITE; + st->buf[1] = msg[i].addr << 1; + st->buf[2] = (en_start << 7) | (en_stop << 6) | +@@ -227,6 +249,7 @@ static int dib0700_i2c_xfer_new(struct i2c_adapter *adap, struct i2c_msg *msg, + USB_TYPE_VENDOR | USB_DIR_OUT, + 0, 0, st->buf, msg[i].len + 4, + USB_CTRL_GET_TIMEOUT); ++ mutex_unlock(&d->usb_mutex); + if (result < 0) { + deb_info("i2c write error (status = %d)\n", result); + break; +@@ -249,6 +272,10 @@ static int dib0700_i2c_xfer_legacy(struct i2c_adapter *adap, + + if (mutex_lock_interruptible(&d->i2c_mutex) < 0) + return -EAGAIN; ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } + + for (i = 0; i < num; i++) { + /* fill in the address */ +@@ -279,6 +306,7 @@ static int dib0700_i2c_xfer_legacy(struct i2c_adapter *adap, + break; + } + } ++ mutex_unlock(&d->usb_mutex); + mutex_unlock(&d->i2c_mutex); + + return i; +@@ -337,7 +365,12 @@ static int dib0700_set_clock(struct dvb_usb_device *d, u8 en_pll, + u16 pll_loopdiv, u16 free_div, u16 dsuScaler) + { + struct dib0700_state *st = d->priv; +- s16 ret; ++ int ret; ++ ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } + + st->buf[0] = REQUEST_SET_CLOCK; + st->buf[1] = (en_pll << 7) | (pll_src << 6) | +@@ -352,6 +385,7 @@ static int dib0700_set_clock(struct dvb_usb_device *d, u8 en_pll, + st->buf[9] = dsuScaler & 0xff; /* LSB */ + + ret = dib0700_ctrl_wr(d, st->buf, 10); ++ mutex_unlock(&d->usb_mutex); + + return ret; + } +@@ -360,10 +394,16 @@ int dib0700_set_i2c_speed(struct dvb_usb_device *d, u16 scl_kHz) + { + struct dib0700_state *st = d->priv; + u16 divider; ++ int ret; + + if (scl_kHz == 0) + return -EINVAL; + ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } ++ + st->buf[0] = REQUEST_SET_I2C_PARAM; + divider = (u16) (30000 / scl_kHz); + st->buf[1] = 0; +@@ -379,7 +419,11 @@ int dib0700_set_i2c_speed(struct dvb_usb_device *d, u16 scl_kHz) + deb_info("setting I2C speed: %04x %04x %04x (%d kHz).", + (st->buf[2] << 8) | (st->buf[3]), (st->buf[4] << 8) | + st->buf[5], (st->buf[6] << 8) | st->buf[7], scl_kHz); +- return dib0700_ctrl_wr(d, st->buf, 8); ++ ++ ret = dib0700_ctrl_wr(d, st->buf, 8); ++ mutex_unlock(&d->usb_mutex); ++ ++ return ret; + } + + +@@ -515,6 +559,11 @@ int dib0700_streaming_ctrl(struct dvb_usb_adapter *adap, int onoff) + } + } + ++ if (mutex_lock_interruptible(&adap->dev->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } ++ + st->buf[0] = REQUEST_ENABLE_VIDEO; + /* this bit gives a kind of command, + * rather than enabling something or not */ +@@ -548,7 +597,10 @@ int dib0700_streaming_ctrl(struct dvb_usb_adapter *adap, int onoff) + + deb_info("data for streaming: %x %x\n", st->buf[1], st->buf[2]); + +- return dib0700_ctrl_wr(adap->dev, st->buf, 4); ++ ret = dib0700_ctrl_wr(adap->dev, st->buf, 4); ++ mutex_unlock(&adap->dev->usb_mutex); ++ ++ return ret; + } + + int dib0700_change_protocol(struct rc_dev *rc, u64 rc_type) +@@ -557,6 +609,11 @@ int dib0700_change_protocol(struct rc_dev *rc, u64 rc_type) + struct dib0700_state *st = d->priv; + int new_proto, ret; + ++ if (mutex_lock_interruptible(&d->usb_mutex) < 0) { ++ deb_info("could not acquire lock"); ++ return 0; ++ } ++ + st->buf[0] = REQUEST_SET_RC; + st->buf[1] = 0; + st->buf[2] = 0; +@@ -567,23 +624,29 @@ int dib0700_change_protocol(struct rc_dev *rc, u64 rc_type) + else if (rc_type == RC_TYPE_NEC) + new_proto = 0; + else if (rc_type == RC_TYPE_RC6) { +- if (st->fw_version < 0x10200) +- return -EINVAL; ++ if (st->fw_version < 0x10200) { ++ ret = -EINVAL; ++ goto out; ++ } + + new_proto = 2; +- } else +- return -EINVAL; ++ } else { ++ ret = -EINVAL; ++ goto out; ++ } + + st->buf[1] = new_proto; + + ret = dib0700_ctrl_wr(d, st->buf, 3); + if (ret < 0) { + err("ir protocol setup failed"); +- return ret; ++ goto out; + } + + d->props.rc.core.protocol = rc_type; + ++out: ++ mutex_unlock(&d->usb_mutex); + return ret; + } + +diff --git a/drivers/media/dvb/frontends/dib0070.c b/drivers/media/dvb/frontends/dib0070.c +index 1d47d4d..dc1cb17 100644 +--- a/drivers/media/dvb/frontends/dib0070.c ++++ b/drivers/media/dvb/frontends/dib0070.c +@@ -27,6 +27,7 @@ + #include <linux/kernel.h> + #include <linux/slab.h> + #include <linux/i2c.h> ++#include <linux/mutex.h> + + #include "dvb_frontend.h" + +@@ -78,10 +79,18 @@ struct dib0070_state { + struct i2c_msg msg[2]; + u8 i2c_write_buffer[3]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + +-static uint16_t dib0070_read_reg(struct dib0070_state *state, u8 reg) ++static u16 dib0070_read_reg(struct dib0070_state *state, u8 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + state->i2c_write_buffer[0] = reg; + + memset(state->msg, 0, 2 * sizeof(struct i2c_msg)); +@@ -96,13 +105,23 @@ static uint16_t dib0070_read_reg(struct dib0070_state *state, u8 reg) + + if (i2c_transfer(state->i2c, state->msg, 2) != 2) { + printk(KERN_WARNING "DiB0070 I2C read failed\n"); +- return 0; +- } +- return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ ret = 0; ++ } else ++ ret = (state->i2c_read_buffer[0] << 8) ++ | state->i2c_read_buffer[1]; ++ ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + static int dib0070_write_reg(struct dib0070_state *state, u8 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } + state->i2c_write_buffer[0] = reg; + state->i2c_write_buffer[1] = val >> 8; + state->i2c_write_buffer[2] = val & 0xff; +@@ -115,9 +134,12 @@ static int dib0070_write_reg(struct dib0070_state *state, u8 reg, u16 val) + + if (i2c_transfer(state->i2c, state->msg, 1) != 1) { + printk(KERN_WARNING "DiB0070 I2C write failed\n"); +- return -EREMOTEIO; +- } +- return 0; ++ ret = -EREMOTEIO; ++ } else ++ ret = 0; ++ ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + #define HARD_RESET(state) do { \ +@@ -734,6 +756,7 @@ struct dvb_frontend *dib0070_attach(struct dvb_frontend *fe, struct i2c_adapter + state->cfg = cfg; + state->i2c = i2c; + state->fe = fe; ++ mutex_init(&state->i2c_buffer_lock); + fe->tuner_priv = state; + + if (dib0070_reset(fe) != 0) +diff --git a/drivers/media/dvb/frontends/dib0090.c b/drivers/media/dvb/frontends/dib0090.c +index c9c935a..b174d1c 100644 +--- a/drivers/media/dvb/frontends/dib0090.c ++++ b/drivers/media/dvb/frontends/dib0090.c +@@ -27,6 +27,7 @@ + #include <linux/kernel.h> + #include <linux/slab.h> + #include <linux/i2c.h> ++#include <linux/mutex.h> + + #include "dvb_frontend.h" + +@@ -196,6 +197,7 @@ struct dib0090_state { + struct i2c_msg msg[2]; + u8 i2c_write_buffer[3]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + + struct dib0090_fw_state { +@@ -208,10 +210,18 @@ struct dib0090_fw_state { + struct i2c_msg msg; + u8 i2c_write_buffer[2]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + + static u16 dib0090_read_reg(struct dib0090_state *state, u8 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + state->i2c_write_buffer[0] = reg; + + memset(state->msg, 0, 2 * sizeof(struct i2c_msg)); +@@ -226,14 +236,24 @@ static u16 dib0090_read_reg(struct dib0090_state *state, u8 reg) + + if (i2c_transfer(state->i2c, state->msg, 2) != 2) { + printk(KERN_WARNING "DiB0090 I2C read failed\n"); +- return 0; +- } ++ ret = 0; ++ } else ++ ret = (state->i2c_read_buffer[0] << 8) ++ | state->i2c_read_buffer[1]; + +- return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + static int dib0090_write_reg(struct dib0090_state *state, u32 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ + state->i2c_write_buffer[0] = reg & 0xff; + state->i2c_write_buffer[1] = val >> 8; + state->i2c_write_buffer[2] = val & 0xff; +@@ -246,13 +266,23 @@ static int dib0090_write_reg(struct dib0090_state *state, u32 reg, u16 val) + + if (i2c_transfer(state->i2c, state->msg, 1) != 1) { + printk(KERN_WARNING "DiB0090 I2C write failed\n"); +- return -EREMOTEIO; +- } +- return 0; ++ ret = -EREMOTEIO; ++ } else ++ ret = 0; ++ ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + static u16 dib0090_fw_read_reg(struct dib0090_fw_state *state, u8 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + state->i2c_write_buffer[0] = reg; + + memset(&state->msg, 0, sizeof(struct i2c_msg)); +@@ -262,13 +292,24 @@ static u16 dib0090_fw_read_reg(struct dib0090_fw_state *state, u8 reg) + state->msg.len = 2; + if (i2c_transfer(state->i2c, &state->msg, 1) != 1) { + printk(KERN_WARNING "DiB0090 I2C read failed\n"); +- return 0; +- } +- return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ ret = 0; ++ } else ++ ret = (state->i2c_read_buffer[0] << 8) ++ | state->i2c_read_buffer[1]; ++ ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + static int dib0090_fw_write_reg(struct dib0090_fw_state *state, u8 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ + state->i2c_write_buffer[0] = val >> 8; + state->i2c_write_buffer[1] = val & 0xff; + +@@ -279,9 +320,12 @@ static int dib0090_fw_write_reg(struct dib0090_fw_state *state, u8 reg, u16 val) + state->msg.len = 2; + if (i2c_transfer(state->i2c, &state->msg, 1) != 1) { + printk(KERN_WARNING "DiB0090 I2C write failed\n"); +- return -EREMOTEIO; +- } +- return 0; ++ ret = -EREMOTEIO; ++ } else ++ ret = 0; ++ ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + #define HARD_RESET(state) do { if (cfg->reset) { if (cfg->sleep) cfg->sleep(fe, 0); msleep(10); cfg->reset(fe, 1); msleep(10); cfg->reset(fe, 0); msleep(10); } } while (0) +@@ -2440,6 +2484,7 @@ struct dvb_frontend *dib0090_register(struct dvb_frontend *fe, struct i2c_adapte + st->config = config; + st->i2c = i2c; + st->fe = fe; ++ mutex_init(&st->i2c_buffer_lock); + fe->tuner_priv = st; + + if (config->wbd == NULL) +@@ -2471,6 +2516,7 @@ struct dvb_frontend *dib0090_fw_register(struct dvb_frontend *fe, struct i2c_ada + st->config = config; + st->i2c = i2c; + st->fe = fe; ++ mutex_init(&st->i2c_buffer_lock); + fe->tuner_priv = st; + + if (dib0090_fw_reset_digital(fe, st->config) != 0) +diff --git a/drivers/media/dvb/frontends/dib7000m.c b/drivers/media/dvb/frontends/dib7000m.c +index 79cb1c2..dbb76d7 100644 +--- a/drivers/media/dvb/frontends/dib7000m.c ++++ b/drivers/media/dvb/frontends/dib7000m.c +@@ -11,6 +11,7 @@ + #include <linux/kernel.h> + #include <linux/slab.h> + #include <linux/i2c.h> ++#include <linux/mutex.h> + + #include "dvb_frontend.h" + +@@ -55,6 +56,7 @@ struct dib7000m_state { + struct i2c_msg msg[2]; + u8 i2c_write_buffer[4]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + + enum dib7000m_power_mode { +@@ -69,6 +71,13 @@ enum dib7000m_power_mode { + + static u16 dib7000m_read_word(struct dib7000m_state *state, u16 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + state->i2c_write_buffer[0] = (reg >> 8) | 0x80; + state->i2c_write_buffer[1] = reg & 0xff; + +@@ -85,11 +94,21 @@ static u16 dib7000m_read_word(struct dib7000m_state *state, u16 reg) + if (i2c_transfer(state->i2c_adap, state->msg, 2) != 2) + dprintk("i2c read error on %d",reg); + +- return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ ret = (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ mutex_unlock(&state->i2c_buffer_lock); ++ ++ return ret; + } + + static int dib7000m_write_word(struct dib7000m_state *state, u16 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ + state->i2c_write_buffer[0] = (reg >> 8) & 0xff; + state->i2c_write_buffer[1] = reg & 0xff; + state->i2c_write_buffer[2] = (val >> 8) & 0xff; +@@ -101,7 +120,10 @@ static int dib7000m_write_word(struct dib7000m_state *state, u16 reg, u16 val) + state->msg[0].buf = state->i2c_write_buffer; + state->msg[0].len = 4; + +- return i2c_transfer(state->i2c_adap, state->msg, 1) != 1 ? -EREMOTEIO : 0; ++ ret = (i2c_transfer(state->i2c_adap, state->msg, 1) != 1 ? ++ -EREMOTEIO : 0); ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + static void dib7000m_write_tab(struct dib7000m_state *state, u16 *buf) + { +@@ -1385,6 +1407,7 @@ struct dvb_frontend * dib7000m_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, + demod = &st->demod; + demod->demodulator_priv = st; + memcpy(&st->demod.ops, &dib7000m_ops, sizeof(struct dvb_frontend_ops)); ++ mutex_init(&st->i2c_buffer_lock); + + st->timf_default = cfg->bw->timf; + +diff --git a/drivers/media/dvb/frontends/dib7000p.c b/drivers/media/dvb/frontends/dib7000p.c +index 0c9f40c..292bc19 100644 +--- a/drivers/media/dvb/frontends/dib7000p.c ++++ b/drivers/media/dvb/frontends/dib7000p.c +@@ -10,6 +10,7 @@ + #include <linux/kernel.h> + #include <linux/slab.h> + #include <linux/i2c.h> ++#include <linux/mutex.h> + + #include "dvb_math.h" + #include "dvb_frontend.h" +@@ -68,6 +69,7 @@ struct dib7000p_state { + struct i2c_msg msg[2]; + u8 i2c_write_buffer[4]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + + enum dib7000p_power_mode { +@@ -81,6 +83,13 @@ static int dib7090_set_diversity_in(struct dvb_frontend *fe, int onoff); + + static u16 dib7000p_read_word(struct dib7000p_state *state, u16 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + state->i2c_write_buffer[0] = reg >> 8; + state->i2c_write_buffer[1] = reg & 0xff; + +@@ -97,11 +106,20 @@ static u16 dib7000p_read_word(struct dib7000p_state *state, u16 reg) + if (i2c_transfer(state->i2c_adap, state->msg, 2) != 2) + dprintk("i2c read error on %d", reg); + +- return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ ret = (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + static int dib7000p_write_word(struct dib7000p_state *state, u16 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ + state->i2c_write_buffer[0] = (reg >> 8) & 0xff; + state->i2c_write_buffer[1] = reg & 0xff; + state->i2c_write_buffer[2] = (val >> 8) & 0xff; +@@ -113,7 +131,10 @@ static int dib7000p_write_word(struct dib7000p_state *state, u16 reg, u16 val) + state->msg[0].buf = state->i2c_write_buffer; + state->msg[0].len = 4; + +- return i2c_transfer(state->i2c_adap, state->msg, 1) != 1 ? -EREMOTEIO : 0; ++ ret = (i2c_transfer(state->i2c_adap, state->msg, 1) != 1 ? ++ -EREMOTEIO : 0); ++ mutex_unlock(&state->i2c_buffer_lock); ++ return ret; + } + + static void dib7000p_write_tab(struct dib7000p_state *state, u16 * buf) +@@ -1646,6 +1667,7 @@ int dib7000p_i2c_enumeration(struct i2c_adapter *i2c, int no_of_demods, u8 defau + return -ENOMEM; + + dpst->i2c_adap = i2c; ++ mutex_init(&dpst->i2c_buffer_lock); + + for (k = no_of_demods - 1; k >= 0; k--) { + dpst->cfg = cfg[k]; +@@ -2324,6 +2346,7 @@ struct dvb_frontend *dib7000p_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, + demod = &st->demod; + demod->demodulator_priv = st; + memcpy(&st->demod.ops, &dib7000p_ops, sizeof(struct dvb_frontend_ops)); ++ mutex_init(&st->i2c_buffer_lock); + + dib7000p_write_word(st, 1287, 0x0003); /* sram lead in, rdy */ + +@@ -2333,8 +2356,9 @@ struct dvb_frontend *dib7000p_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, + st->version = dib7000p_read_word(st, 897); + + /* FIXME: make sure the dev.parent field is initialized, or else +- request_firmware() will hit an OOPS (this should be moved somewhere +- more common) */ ++ request_firmware() will hit an OOPS (this should be moved somewhere ++ more common) */ ++ st->i2c_master.gated_tuner_i2c_adap.dev.parent = i2c_adap->dev.parent; + + dibx000_init_i2c_master(&st->i2c_master, DIB7000P, st->i2c_adap, st->i2c_addr); + +diff --git a/drivers/media/dvb/frontends/dib8000.c b/drivers/media/dvb/frontends/dib8000.c +index 7d2ea11..fe284d5 100644 +--- a/drivers/media/dvb/frontends/dib8000.c ++++ b/drivers/media/dvb/frontends/dib8000.c +@@ -10,6 +10,8 @@ + #include <linux/kernel.h> + #include <linux/slab.h> + #include <linux/i2c.h> ++#include <linux/mutex.h> ++ + #include "dvb_math.h" + + #include "dvb_frontend.h" +@@ -37,6 +39,7 @@ struct i2c_device { + u8 addr; + u8 *i2c_write_buffer; + u8 *i2c_read_buffer; ++ struct mutex *i2c_buffer_lock; + }; + + struct dib8000_state { +@@ -77,6 +80,7 @@ struct dib8000_state { + struct i2c_msg msg[2]; + u8 i2c_write_buffer[4]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + + enum dib8000_power_mode { +@@ -86,24 +90,39 @@ enum dib8000_power_mode { + + static u16 dib8000_i2c_read16(struct i2c_device *i2c, u16 reg) + { ++ u16 ret; + struct i2c_msg msg[2] = { +- {.addr = i2c->addr >> 1, .flags = 0, +- .buf = i2c->i2c_write_buffer, .len = 2}, +- {.addr = i2c->addr >> 1, .flags = I2C_M_RD, +- .buf = i2c->i2c_read_buffer, .len = 2}, ++ {.addr = i2c->addr >> 1, .flags = 0, .len = 2}, ++ {.addr = i2c->addr >> 1, .flags = I2C_M_RD, .len = 2}, + }; + ++ if (mutex_lock_interruptible(i2c->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ ++ msg[0].buf = i2c->i2c_write_buffer; + msg[0].buf[0] = reg >> 8; + msg[0].buf[1] = reg & 0xff; ++ msg[1].buf = i2c->i2c_read_buffer; + + if (i2c_transfer(i2c->adap, msg, 2) != 2) + dprintk("i2c read error on %d", reg); + +- return (msg[1].buf[0] << 8) | msg[1].buf[1]; ++ ret = (msg[1].buf[0] << 8) | msg[1].buf[1]; ++ mutex_unlock(i2c->i2c_buffer_lock); ++ return ret; + } + + static u16 dib8000_read_word(struct dib8000_state *state, u16 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + state->i2c_write_buffer[0] = reg >> 8; + state->i2c_write_buffer[1] = reg & 0xff; + +@@ -120,7 +139,10 @@ static u16 dib8000_read_word(struct dib8000_state *state, u16 reg) + if (i2c_transfer(state->i2c.adap, state->msg, 2) != 2) + dprintk("i2c read error on %d", reg); + +- return (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ ret = (state->i2c_read_buffer[0] << 8) | state->i2c_read_buffer[1]; ++ mutex_unlock(&state->i2c_buffer_lock); ++ ++ return ret; + } + + static u32 dib8000_read32(struct dib8000_state *state, u16 reg) +@@ -135,22 +157,35 @@ static u32 dib8000_read32(struct dib8000_state *state, u16 reg) + + static int dib8000_i2c_write16(struct i2c_device *i2c, u16 reg, u16 val) + { +- struct i2c_msg msg = {.addr = i2c->addr >> 1, .flags = 0, +- .buf = i2c->i2c_write_buffer, .len = 4}; ++ struct i2c_msg msg = {.addr = i2c->addr >> 1, .flags = 0, .len = 4}; + int ret = 0; + ++ if (mutex_lock_interruptible(i2c->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ ++ msg.buf = i2c->i2c_write_buffer; + msg.buf[0] = (reg >> 8) & 0xff; + msg.buf[1] = reg & 0xff; + msg.buf[2] = (val >> 8) & 0xff; + msg.buf[3] = val & 0xff; + + ret = i2c_transfer(i2c->adap, &msg, 1) != 1 ? -EREMOTEIO : 0; ++ mutex_unlock(i2c->i2c_buffer_lock); + + return ret; + } + + static int dib8000_write_word(struct dib8000_state *state, u16 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&state->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ + state->i2c_write_buffer[0] = (reg >> 8) & 0xff; + state->i2c_write_buffer[1] = reg & 0xff; + state->i2c_write_buffer[2] = (val >> 8) & 0xff; +@@ -162,7 +197,11 @@ static int dib8000_write_word(struct dib8000_state *state, u16 reg, u16 val) + state->msg[0].buf = state->i2c_write_buffer; + state->msg[0].len = 4; + +- return i2c_transfer(state->i2c.adap, state->msg, 1) != 1 ? -EREMOTEIO : 0; ++ ret = (i2c_transfer(state->i2c.adap, state->msg, 1) != 1 ? ++ -EREMOTEIO : 0); ++ mutex_unlock(&state->i2c_buffer_lock); ++ ++ return ret; + } + + static const s16 coeff_2k_sb_1seg_dqpsk[8] = { +@@ -2434,8 +2473,15 @@ int dib8000_i2c_enumeration(struct i2c_adapter *host, int no_of_demods, u8 defau + if (!client.i2c_read_buffer) { + dprintk("%s: not enough memory", __func__); + ret = -ENOMEM; +- goto error_memory; ++ goto error_memory_read; ++ } ++ client.i2c_buffer_lock = kzalloc(sizeof(struct mutex), GFP_KERNEL); ++ if (!client.i2c_buffer_lock) { ++ dprintk("%s: not enough memory", __func__); ++ ret = -ENOMEM; ++ goto error_memory_lock; + } ++ mutex_init(client.i2c_buffer_lock); + + for (k = no_of_demods - 1; k >= 0; k--) { + /* designated i2c address */ +@@ -2476,8 +2522,10 @@ int dib8000_i2c_enumeration(struct i2c_adapter *host, int no_of_demods, u8 defau + } + + error: ++ kfree(client.i2c_buffer_lock); ++error_memory_lock: + kfree(client.i2c_read_buffer); +-error_memory: ++error_memory_read: + kfree(client.i2c_write_buffer); + + return ret; +@@ -2581,6 +2629,8 @@ struct dvb_frontend *dib8000_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, s + state->i2c.addr = i2c_addr; + state->i2c.i2c_write_buffer = state->i2c_write_buffer; + state->i2c.i2c_read_buffer = state->i2c_read_buffer; ++ mutex_init(&state->i2c_buffer_lock); ++ state->i2c.i2c_buffer_lock = &state->i2c_buffer_lock; + state->gpio_val = cfg->gpio_val; + state->gpio_dir = cfg->gpio_dir; + +diff --git a/drivers/media/dvb/frontends/dib9000.c b/drivers/media/dvb/frontends/dib9000.c +index a085588..b931074 100644 +--- a/drivers/media/dvb/frontends/dib9000.c ++++ b/drivers/media/dvb/frontends/dib9000.c +@@ -38,6 +38,15 @@ struct i2c_device { + #define DibInitLock(lock) mutex_init(lock) + #define DibFreeLock(lock) + ++struct dib9000_pid_ctrl { ++#define DIB9000_PID_FILTER_CTRL 0 ++#define DIB9000_PID_FILTER 1 ++ u8 cmd; ++ u8 id; ++ u16 pid; ++ u8 onoff; ++}; ++ + struct dib9000_state { + struct i2c_device i2c; + +@@ -99,6 +108,10 @@ struct dib9000_state { + struct i2c_msg msg[2]; + u8 i2c_write_buffer[255]; + u8 i2c_read_buffer[255]; ++ DIB_LOCK demod_lock; ++ u8 get_frontend_internal; ++ struct dib9000_pid_ctrl pid_ctrl[10]; ++ s8 pid_ctrl_index; /* -1: empty list; -2: do not use the list */ + }; + + static const u32 fe_info[44] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, +@@ -1743,19 +1756,56 @@ EXPORT_SYMBOL(dib9000_set_gpio); + int dib9000_fw_pid_filter_ctrl(struct dvb_frontend *fe, u8 onoff) + { + struct dib9000_state *state = fe->demodulator_priv; +- u16 val = dib9000_read_word(state, 294 + 1) & 0xffef; ++ u16 val; ++ int ret; ++ ++ if ((state->pid_ctrl_index != -2) && (state->pid_ctrl_index < 9)) { ++ /* postpone the pid filtering cmd */ ++ dprintk("pid filter cmd postpone"); ++ state->pid_ctrl_index++; ++ state->pid_ctrl[state->pid_ctrl_index].cmd = DIB9000_PID_FILTER_CTRL; ++ state->pid_ctrl[state->pid_ctrl_index].onoff = onoff; ++ return 0; ++ } ++ ++ DibAcquireLock(&state->demod_lock); ++ ++ val = dib9000_read_word(state, 294 + 1) & 0xffef; + val |= (onoff & 0x1) << 4; + + dprintk("PID filter enabled %d", onoff); +- return dib9000_write_word(state, 294 + 1, val); ++ ret = dib9000_write_word(state, 294 + 1, val); ++ DibReleaseLock(&state->demod_lock); ++ return ret; ++ + } + EXPORT_SYMBOL(dib9000_fw_pid_filter_ctrl); + + int dib9000_fw_pid_filter(struct dvb_frontend *fe, u8 id, u16 pid, u8 onoff) + { + struct dib9000_state *state = fe->demodulator_priv; ++ int ret; ++ ++ if (state->pid_ctrl_index != -2) { ++ /* postpone the pid filtering cmd */ ++ dprintk("pid filter postpone"); ++ if (state->pid_ctrl_index < 9) { ++ state->pid_ctrl_index++; ++ state->pid_ctrl[state->pid_ctrl_index].cmd = DIB9000_PID_FILTER; ++ state->pid_ctrl[state->pid_ctrl_index].id = id; ++ state->pid_ctrl[state->pid_ctrl_index].pid = pid; ++ state->pid_ctrl[state->pid_ctrl_index].onoff = onoff; ++ } else ++ dprintk("can not add any more pid ctrl cmd"); ++ return 0; ++ } ++ ++ DibAcquireLock(&state->demod_lock); + dprintk("Index %x, PID %d, OnOff %d", id, pid, onoff); +- return dib9000_write_word(state, 300 + 1 + id, onoff ? (1 << 13) | pid : 0); ++ ret = dib9000_write_word(state, 300 + 1 + id, ++ onoff ? (1 << 13) | pid : 0); ++ DibReleaseLock(&state->demod_lock); ++ return ret; + } + EXPORT_SYMBOL(dib9000_fw_pid_filter); + +@@ -1778,6 +1828,7 @@ static void dib9000_release(struct dvb_frontend *demod) + DibFreeLock(&state->platform.risc.mbx_lock); + DibFreeLock(&state->platform.risc.mem_lock); + DibFreeLock(&state->platform.risc.mem_mbx_lock); ++ DibFreeLock(&state->demod_lock); + dibx000_exit_i2c_master(&st->i2c_master); + + i2c_del_adapter(&st->tuner_adap); +@@ -1795,14 +1846,19 @@ static int dib9000_sleep(struct dvb_frontend *fe) + { + struct dib9000_state *state = fe->demodulator_priv; + u8 index_frontend; +- int ret; ++ int ret = 0; + ++ DibAcquireLock(&state->demod_lock); + for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) { + ret = state->fe[index_frontend]->ops.sleep(state->fe[index_frontend]); + if (ret < 0) +- return ret; ++ goto error; + } +- return dib9000_mbx_send(state, OUT_MSG_FE_SLEEP, NULL, 0); ++ ret = dib9000_mbx_send(state, OUT_MSG_FE_SLEEP, NULL, 0); ++ ++error: ++ DibReleaseLock(&state->demod_lock); ++ return ret; + } + + static int dib9000_fe_get_tune_settings(struct dvb_frontend *fe, struct dvb_frontend_tune_settings *tune) +@@ -1816,7 +1872,10 @@ static int dib9000_get_frontend(struct dvb_frontend *fe, struct dvb_frontend_par + struct dib9000_state *state = fe->demodulator_priv; + u8 index_frontend, sub_index_frontend; + fe_status_t stat; +- int ret; ++ int ret = 0; ++ ++ if (state->get_frontend_internal == 0) ++ DibAcquireLock(&state->demod_lock); + + for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) { + state->fe[index_frontend]->ops.read_status(state->fe[index_frontend], &stat); +@@ -1846,14 +1905,15 @@ static int dib9000_get_frontend(struct dvb_frontend *fe, struct dvb_frontend_par + state->fe[index_frontend]->dtv_property_cache.rolloff; + } + } +- return 0; ++ ret = 0; ++ goto return_value; + } + } + + /* get the channel from master chip */ + ret = dib9000_fw_get_channel(fe, fep); + if (ret != 0) +- return ret; ++ goto return_value; + + /* synchronize the cache with the other frontends */ + for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) { +@@ -1866,8 +1926,12 @@ static int dib9000_get_frontend(struct dvb_frontend *fe, struct dvb_frontend_par + state->fe[index_frontend]->dtv_property_cache.code_rate_LP = fe->dtv_property_cache.code_rate_LP; + state->fe[index_frontend]->dtv_property_cache.rolloff = fe->dtv_property_cache.rolloff; + } ++ ret = 0; + +- return 0; ++return_value: ++ if (state->get_frontend_internal == 0) ++ DibReleaseLock(&state->demod_lock); ++ return ret; + } + + static int dib9000_set_tune_state(struct dvb_frontend *fe, enum frontend_tune_state tune_state) +@@ -1912,6 +1976,10 @@ static int dib9000_set_frontend(struct dvb_frontend *fe, struct dvb_frontend_par + dprintk("dib9000: must specify bandwidth "); + return 0; + } ++ ++ state->pid_ctrl_index = -1; /* postpone the pid filtering cmd */ ++ DibAcquireLock(&state->demod_lock); ++ + fe->dtv_property_cache.delivery_system = SYS_DVBT; + + /* set the master status */ +@@ -1974,13 +2042,18 @@ static int dib9000_set_frontend(struct dvb_frontend *fe, struct dvb_frontend_par + /* check the tune result */ + if (exit_condition == 1) { /* tune failed */ + dprintk("tune failed"); ++ DibReleaseLock(&state->demod_lock); ++ /* tune failed; put all the pid filtering cmd to junk */ ++ state->pid_ctrl_index = -1; + return 0; + } + + dprintk("tune success on frontend%i", index_frontend_success); + + /* synchronize all the channel cache */ ++ state->get_frontend_internal = 1; + dib9000_get_frontend(state->fe[0], fep); ++ state->get_frontend_internal = 0; + + /* retune the other frontends with the found channel */ + channel_status.status = CHANNEL_STATUS_PARAMETERS_SET; +@@ -2025,6 +2098,28 @@ static int dib9000_set_frontend(struct dvb_frontend *fe, struct dvb_frontend_par + /* turn off the diversity for the last frontend */ + dib9000_fw_set_diversity_in(state->fe[index_frontend - 1], 0); + ++ DibReleaseLock(&state->demod_lock); ++ if (state->pid_ctrl_index >= 0) { ++ u8 index_pid_filter_cmd; ++ u8 pid_ctrl_index = state->pid_ctrl_index; ++ ++ state->pid_ctrl_index = -2; ++ for (index_pid_filter_cmd = 0; ++ index_pid_filter_cmd <= pid_ctrl_index; ++ index_pid_filter_cmd++) { ++ if (state->pid_ctrl[index_pid_filter_cmd].cmd == DIB9000_PID_FILTER_CTRL) ++ dib9000_fw_pid_filter_ctrl(state->fe[0], ++ state->pid_ctrl[index_pid_filter_cmd].onoff); ++ else if (state->pid_ctrl[index_pid_filter_cmd].cmd == DIB9000_PID_FILTER) ++ dib9000_fw_pid_filter(state->fe[0], ++ state->pid_ctrl[index_pid_filter_cmd].id, ++ state->pid_ctrl[index_pid_filter_cmd].pid, ++ state->pid_ctrl[index_pid_filter_cmd].onoff); ++ } ++ } ++ /* do not postpone any more the pid filtering */ ++ state->pid_ctrl_index = -2; ++ + return 0; + } + +@@ -2041,6 +2136,7 @@ static int dib9000_read_status(struct dvb_frontend *fe, fe_status_t * stat) + u8 index_frontend; + u16 lock = 0, lock_slave = 0; + ++ DibAcquireLock(&state->demod_lock); + for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) + lock_slave |= dib9000_read_lock(state->fe[index_frontend]); + +@@ -2059,6 +2155,8 @@ static int dib9000_read_status(struct dvb_frontend *fe, fe_status_t * stat) + if ((lock & 0x0008) || (lock_slave & 0x0008)) + *stat |= FE_HAS_LOCK; + ++ DibReleaseLock(&state->demod_lock); ++ + return 0; + } + +@@ -2066,10 +2164,14 @@ static int dib9000_read_ber(struct dvb_frontend *fe, u32 * ber) + { + struct dib9000_state *state = fe->demodulator_priv; + u16 *c; ++ int ret = 0; + ++ DibAcquireLock(&state->demod_lock); + DibAcquireLock(&state->platform.risc.mem_mbx_lock); +- if (dib9000_fw_memmbx_sync(state, FE_SYNC_CHANNEL) < 0) +- return -EIO; ++ if (dib9000_fw_memmbx_sync(state, FE_SYNC_CHANNEL) < 0) { ++ ret = -EIO; ++ goto error; ++ } + dib9000_risc_mem_read(state, FE_MM_R_FE_MONITOR, + state->i2c_read_buffer, 16 * 2); + DibReleaseLock(&state->platform.risc.mem_mbx_lock); +@@ -2077,7 +2179,10 @@ static int dib9000_read_ber(struct dvb_frontend *fe, u32 * ber) + c = (u16 *)state->i2c_read_buffer; + + *ber = c[10] << 16 | c[11]; +- return 0; ++ ++error: ++ DibReleaseLock(&state->demod_lock); ++ return ret; + } + + static int dib9000_read_signal_strength(struct dvb_frontend *fe, u16 * strength) +@@ -2086,7 +2191,9 @@ static int dib9000_read_signal_strength(struct dvb_frontend *fe, u16 * strength) + u8 index_frontend; + u16 *c = (u16 *)state->i2c_read_buffer; + u16 val; ++ int ret = 0; + ++ DibAcquireLock(&state->demod_lock); + *strength = 0; + for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) { + state->fe[index_frontend]->ops.read_signal_strength(state->fe[index_frontend], &val); +@@ -2097,8 +2204,10 @@ static int dib9000_read_signal_strength(struct dvb_frontend *fe, u16 * strength) + } + + DibAcquireLock(&state->platform.risc.mem_mbx_lock); +- if (dib9000_fw_memmbx_sync(state, FE_SYNC_CHANNEL) < 0) +- return -EIO; ++ if (dib9000_fw_memmbx_sync(state, FE_SYNC_CHANNEL) < 0) { ++ ret = -EIO; ++ goto error; ++ } + dib9000_risc_mem_read(state, FE_MM_R_FE_MONITOR, (u8 *) c, 16 * 2); + DibReleaseLock(&state->platform.risc.mem_mbx_lock); + +@@ -2107,7 +2216,10 @@ static int dib9000_read_signal_strength(struct dvb_frontend *fe, u16 * strength) + *strength = 65535; + else + *strength += val; +- return 0; ++ ++error: ++ DibReleaseLock(&state->demod_lock); ++ return ret; + } + + static u32 dib9000_get_snr(struct dvb_frontend *fe) +@@ -2151,6 +2263,7 @@ static int dib9000_read_snr(struct dvb_frontend *fe, u16 * snr) + u8 index_frontend; + u32 snr_master; + ++ DibAcquireLock(&state->demod_lock); + snr_master = dib9000_get_snr(fe); + for (index_frontend = 1; (index_frontend < MAX_NUMBER_OF_FRONTENDS) && (state->fe[index_frontend] != NULL); index_frontend++) + snr_master += dib9000_get_snr(state->fe[index_frontend]); +@@ -2161,6 +2274,8 @@ static int dib9000_read_snr(struct dvb_frontend *fe, u16 * snr) + } else + *snr = 0; + ++ DibReleaseLock(&state->demod_lock); ++ + return 0; + } + +@@ -2168,15 +2283,22 @@ static int dib9000_read_unc_blocks(struct dvb_frontend *fe, u32 * unc) + { + struct dib9000_state *state = fe->demodulator_priv; + u16 *c = (u16 *)state->i2c_read_buffer; ++ int ret = 0; + ++ DibAcquireLock(&state->demod_lock); + DibAcquireLock(&state->platform.risc.mem_mbx_lock); +- if (dib9000_fw_memmbx_sync(state, FE_SYNC_CHANNEL) < 0) +- return -EIO; ++ if (dib9000_fw_memmbx_sync(state, FE_SYNC_CHANNEL) < 0) { ++ ret = -EIO; ++ goto error; ++ } + dib9000_risc_mem_read(state, FE_MM_R_FE_MONITOR, (u8 *) c, 16 * 2); + DibReleaseLock(&state->platform.risc.mem_mbx_lock); + + *unc = c[12]; +- return 0; ++ ++error: ++ DibReleaseLock(&state->demod_lock); ++ return ret; + } + + int dib9000_i2c_enumeration(struct i2c_adapter *i2c, int no_of_demods, u8 default_addr, u8 first_addr) +@@ -2322,6 +2444,10 @@ struct dvb_frontend *dib9000_attach(struct i2c_adapter *i2c_adap, u8 i2c_addr, c + DibInitLock(&st->platform.risc.mbx_lock); + DibInitLock(&st->platform.risc.mem_lock); + DibInitLock(&st->platform.risc.mem_mbx_lock); ++ DibInitLock(&st->demod_lock); ++ st->get_frontend_internal = 0; ++ ++ st->pid_ctrl_index = -2; + + st->fe[0] = fe; + fe->demodulator_priv = st; +diff --git a/drivers/media/dvb/frontends/dibx000_common.c b/drivers/media/dvb/frontends/dibx000_common.c +index dc5d17a..774d507 100644 +--- a/drivers/media/dvb/frontends/dibx000_common.c ++++ b/drivers/media/dvb/frontends/dibx000_common.c +@@ -1,4 +1,5 @@ + #include <linux/i2c.h> ++#include <linux/mutex.h> + + #include "dibx000_common.h" + +@@ -10,6 +11,13 @@ MODULE_PARM_DESC(debug, "turn on debugging (default: 0)"); + + static int dibx000_write_word(struct dibx000_i2c_master *mst, u16 reg, u16 val) + { ++ int ret; ++ ++ if (mutex_lock_interruptible(&mst->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ + mst->i2c_write_buffer[0] = (reg >> 8) & 0xff; + mst->i2c_write_buffer[1] = reg & 0xff; + mst->i2c_write_buffer[2] = (val >> 8) & 0xff; +@@ -21,11 +29,21 @@ static int dibx000_write_word(struct dibx000_i2c_master *mst, u16 reg, u16 val) + mst->msg[0].buf = mst->i2c_write_buffer; + mst->msg[0].len = 4; + +- return i2c_transfer(mst->i2c_adap, mst->msg, 1) != 1 ? -EREMOTEIO : 0; ++ ret = i2c_transfer(mst->i2c_adap, mst->msg, 1) != 1 ? -EREMOTEIO : 0; ++ mutex_unlock(&mst->i2c_buffer_lock); ++ ++ return ret; + } + + static u16 dibx000_read_word(struct dibx000_i2c_master *mst, u16 reg) + { ++ u16 ret; ++ ++ if (mutex_lock_interruptible(&mst->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return 0; ++ } ++ + mst->i2c_write_buffer[0] = reg >> 8; + mst->i2c_write_buffer[1] = reg & 0xff; + +@@ -42,7 +60,10 @@ static u16 dibx000_read_word(struct dibx000_i2c_master *mst, u16 reg) + if (i2c_transfer(mst->i2c_adap, mst->msg, 2) != 2) + dprintk("i2c read error on %d", reg); + +- return (mst->i2c_read_buffer[0] << 8) | mst->i2c_read_buffer[1]; ++ ret = (mst->i2c_read_buffer[0] << 8) | mst->i2c_read_buffer[1]; ++ mutex_unlock(&mst->i2c_buffer_lock); ++ ++ return ret; + } + + static int dibx000_is_i2c_done(struct dibx000_i2c_master *mst) +@@ -257,6 +278,7 @@ static int dibx000_i2c_gated_gpio67_xfer(struct i2c_adapter *i2c_adap, + struct i2c_msg msg[], int num) + { + struct dibx000_i2c_master *mst = i2c_get_adapdata(i2c_adap); ++ int ret; + + if (num > 32) { + dprintk("%s: too much I2C message to be transmitted (%i).\ +@@ -264,10 +286,15 @@ static int dibx000_i2c_gated_gpio67_xfer(struct i2c_adapter *i2c_adap, + return -ENOMEM; + } + +- memset(mst->msg, 0, sizeof(struct i2c_msg) * (2 + num)); +- + dibx000_i2c_select_interface(mst, DIBX000_I2C_INTERFACE_GPIO_6_7); + ++ if (mutex_lock_interruptible(&mst->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ ++ memset(mst->msg, 0, sizeof(struct i2c_msg) * (2 + num)); ++ + /* open the gate */ + dibx000_i2c_gate_ctrl(mst, &mst->i2c_write_buffer[0], msg[0].addr, 1); + mst->msg[0].addr = mst->i2c_addr; +@@ -282,7 +309,11 @@ static int dibx000_i2c_gated_gpio67_xfer(struct i2c_adapter *i2c_adap, + mst->msg[num + 1].buf = &mst->i2c_write_buffer[4]; + mst->msg[num + 1].len = 4; + +- return i2c_transfer(mst->i2c_adap, mst->msg, 2 + num) == 2 + num ? num : -EIO; ++ ret = (i2c_transfer(mst->i2c_adap, mst->msg, 2 + num) == 2 + num ? ++ num : -EIO); ++ ++ mutex_unlock(&mst->i2c_buffer_lock); ++ return ret; + } + + static struct i2c_algorithm dibx000_i2c_gated_gpio67_algo = { +@@ -294,6 +325,7 @@ static int dibx000_i2c_gated_tuner_xfer(struct i2c_adapter *i2c_adap, + struct i2c_msg msg[], int num) + { + struct dibx000_i2c_master *mst = i2c_get_adapdata(i2c_adap); ++ int ret; + + if (num > 32) { + dprintk("%s: too much I2C message to be transmitted (%i).\ +@@ -301,10 +333,14 @@ static int dibx000_i2c_gated_tuner_xfer(struct i2c_adapter *i2c_adap, + return -ENOMEM; + } + +- memset(mst->msg, 0, sizeof(struct i2c_msg) * (2 + num)); +- + dibx000_i2c_select_interface(mst, DIBX000_I2C_INTERFACE_TUNER); + ++ if (mutex_lock_interruptible(&mst->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ memset(mst->msg, 0, sizeof(struct i2c_msg) * (2 + num)); ++ + /* open the gate */ + dibx000_i2c_gate_ctrl(mst, &mst->i2c_write_buffer[0], msg[0].addr, 1); + mst->msg[0].addr = mst->i2c_addr; +@@ -319,7 +355,10 @@ static int dibx000_i2c_gated_tuner_xfer(struct i2c_adapter *i2c_adap, + mst->msg[num + 1].buf = &mst->i2c_write_buffer[4]; + mst->msg[num + 1].len = 4; + +- return i2c_transfer(mst->i2c_adap, mst->msg, 2 + num) == 2 + num ? num : -EIO; ++ ret = (i2c_transfer(mst->i2c_adap, mst->msg, 2 + num) == 2 + num ? ++ num : -EIO); ++ mutex_unlock(&mst->i2c_buffer_lock); ++ return ret; + } + + static struct i2c_algorithm dibx000_i2c_gated_tuner_algo = { +@@ -390,8 +429,18 @@ static int i2c_adapter_init(struct i2c_adapter *i2c_adap, + int dibx000_init_i2c_master(struct dibx000_i2c_master *mst, u16 device_rev, + struct i2c_adapter *i2c_adap, u8 i2c_addr) + { +- u8 tx[4]; +- struct i2c_msg m = {.addr = i2c_addr >> 1,.buf = tx,.len = 4 }; ++ int ret; ++ ++ mutex_init(&mst->i2c_buffer_lock); ++ if (mutex_lock_interruptible(&mst->i2c_buffer_lock) < 0) { ++ dprintk("could not acquire lock"); ++ return -EINVAL; ++ } ++ memset(mst->msg, 0, sizeof(struct i2c_msg)); ++ mst->msg[0].addr = i2c_addr >> 1; ++ mst->msg[0].flags = 0; ++ mst->msg[0].buf = mst->i2c_write_buffer; ++ mst->msg[0].len = 4; + + mst->device_rev = device_rev; + mst->i2c_adap = i2c_adap; +@@ -431,9 +480,12 @@ int dibx000_init_i2c_master(struct dibx000_i2c_master *mst, u16 device_rev, + "DiBX000: could not initialize the master i2c_adapter\n"); + + /* initialize the i2c-master by closing the gate */ +- dibx000_i2c_gate_ctrl(mst, tx, 0, 0); ++ dibx000_i2c_gate_ctrl(mst, mst->i2c_write_buffer, 0, 0); ++ ++ ret = (i2c_transfer(i2c_adap, mst->msg, 1) == 1); ++ mutex_unlock(&mst->i2c_buffer_lock); + +- return i2c_transfer(i2c_adap, &m, 1) == 1; ++ return ret; + } + + EXPORT_SYMBOL(dibx000_init_i2c_master); +diff --git a/drivers/media/dvb/frontends/dibx000_common.h b/drivers/media/dvb/frontends/dibx000_common.h +index f031165..5e01147 100644 +--- a/drivers/media/dvb/frontends/dibx000_common.h ++++ b/drivers/media/dvb/frontends/dibx000_common.h +@@ -33,6 +33,7 @@ struct dibx000_i2c_master { + struct i2c_msg msg[34]; + u8 i2c_write_buffer[8]; + u8 i2c_read_buffer[2]; ++ struct mutex i2c_buffer_lock; + }; + + extern int dibx000_init_i2c_master(struct dibx000_i2c_master *mst, +diff --git a/drivers/media/video/cx23885/cx23885-dvb.c b/drivers/media/video/cx23885/cx23885-dvb.c +index 3c315f9..2b5cd21 100644 +--- a/drivers/media/video/cx23885/cx23885-dvb.c ++++ b/drivers/media/video/cx23885/cx23885-dvb.c +@@ -843,7 +843,7 @@ static int dvb_register(struct cx23885_tsport *port) + static struct xc2028_ctrl ctl = { + .fname = XC3028L_DEFAULT_FIRMWARE, + .max_len = 64, +- .demod = 5000, ++ .demod = XC3028_FE_DIBCOM52, + /* This is true for all demods with + v36 firmware? */ + .type = XC2028_D2633, +diff --git a/drivers/media/video/uvc/uvc_driver.c b/drivers/media/video/uvc/uvc_driver.c +index b6eae48..1f962dc 100644 +--- a/drivers/media/video/uvc/uvc_driver.c ++++ b/drivers/media/video/uvc/uvc_driver.c +@@ -1960,7 +1960,7 @@ static int __uvc_resume(struct usb_interface *intf, int reset) + + list_for_each_entry(stream, &dev->streams, list) { + if (stream->intf == intf) +- return uvc_video_resume(stream); ++ return uvc_video_resume(stream, reset); + } + + uvc_trace(UVC_TRACE_SUSPEND, "Resume: video streaming USB interface " +diff --git a/drivers/media/video/uvc/uvc_video.c b/drivers/media/video/uvc/uvc_video.c +index 4999479..6f147de 100644 +--- a/drivers/media/video/uvc/uvc_video.c ++++ b/drivers/media/video/uvc/uvc_video.c +@@ -1104,10 +1104,18 @@ int uvc_video_suspend(struct uvc_streaming *stream) + * buffers, making sure userspace applications are notified of the problem + * instead of waiting forever. + */ +-int uvc_video_resume(struct uvc_streaming *stream) ++int uvc_video_resume(struct uvc_streaming *stream, int reset) + { + int ret; + ++ /* If the bus has been reset on resume, set the alternate setting to 0. ++ * This should be the default value, but some devices crash or otherwise ++ * misbehave if they don't receive a SET_INTERFACE request before any ++ * other video control request. ++ */ ++ if (reset) ++ usb_set_interface(stream->dev->udev, stream->intfnum, 0); ++ + stream->frozen = 0; + + ret = uvc_commit_video(stream, &stream->ctrl); +diff --git a/drivers/media/video/uvc/uvcvideo.h b/drivers/media/video/uvc/uvcvideo.h +index 20107fd..2a38d5e 100644 +--- a/drivers/media/video/uvc/uvcvideo.h ++++ b/drivers/media/video/uvc/uvcvideo.h +@@ -639,7 +639,7 @@ extern void uvc_mc_cleanup_entity(struct uvc_entity *entity); + /* Video */ + extern int uvc_video_init(struct uvc_streaming *stream); + extern int uvc_video_suspend(struct uvc_streaming *stream); +-extern int uvc_video_resume(struct uvc_streaming *stream); ++extern int uvc_video_resume(struct uvc_streaming *stream, int reset); + extern int uvc_video_enable(struct uvc_streaming *stream, int enable); + extern int uvc_probe_video(struct uvc_streaming *stream, + struct uvc_streaming_control *probe); +diff --git a/drivers/mmc/core/core.c b/drivers/mmc/core/core.c +index 38089b2..75db30e6 100644 +--- a/drivers/mmc/core/core.c ++++ b/drivers/mmc/core/core.c +@@ -1057,7 +1057,7 @@ static void mmc_power_up(struct mmc_host *host) + mmc_host_clk_release(host); + } + +-static void mmc_power_off(struct mmc_host *host) ++void mmc_power_off(struct mmc_host *host) + { + mmc_host_clk_hold(host); + +@@ -1147,8 +1147,7 @@ void mmc_attach_bus(struct mmc_host *host, const struct mmc_bus_ops *ops) + } + + /* +- * Remove the current bus handler from a host. Assumes that there are +- * no interesting cards left, so the bus is powered down. ++ * Remove the current bus handler from a host. + */ + void mmc_detach_bus(struct mmc_host *host) + { +@@ -1165,8 +1164,6 @@ void mmc_detach_bus(struct mmc_host *host) + + spin_unlock_irqrestore(&host->lock, flags); + +- mmc_power_off(host); +- + mmc_bus_put(host); + } + +@@ -1675,6 +1672,7 @@ void mmc_stop_host(struct mmc_host *host) + + mmc_claim_host(host); + mmc_detach_bus(host); ++ mmc_power_off(host); + mmc_release_host(host); + mmc_bus_put(host); + return; +@@ -1796,6 +1794,7 @@ int mmc_suspend_host(struct mmc_host *host) + host->bus_ops->remove(host); + mmc_claim_host(host); + mmc_detach_bus(host); ++ mmc_power_off(host); + mmc_release_host(host); + host->pm_flags = 0; + err = 0; +@@ -1883,6 +1882,7 @@ int mmc_pm_notify(struct notifier_block *notify_block, + host->bus_ops->remove(host); + + mmc_detach_bus(host); ++ mmc_power_off(host); + mmc_release_host(host); + host->pm_flags = 0; + break; +diff --git a/drivers/mmc/core/core.h b/drivers/mmc/core/core.h +index d9411ed..14664f1 100644 +--- a/drivers/mmc/core/core.h ++++ b/drivers/mmc/core/core.h +@@ -43,6 +43,7 @@ int mmc_set_signal_voltage(struct mmc_host *host, int signal_voltage, + bool cmd11); + void mmc_set_timing(struct mmc_host *host, unsigned int timing); + void mmc_set_driver_type(struct mmc_host *host, unsigned int drv_type); ++void mmc_power_off(struct mmc_host *host); + + static inline void mmc_delay(unsigned int ms) + { +diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c +index aa7d1d7..20b42c8 100644 +--- a/drivers/mmc/core/mmc.c ++++ b/drivers/mmc/core/mmc.c +@@ -359,6 +359,7 @@ static int mmc_read_ext_csd(struct mmc_card *card, u8 *ext_csd) + * card has the Enhanced area enabled. If so, export enhanced + * area offset and size to user by adding sysfs interface. + */ ++ card->ext_csd.raw_partition_support = ext_csd[EXT_CSD_PARTITION_SUPPORT]; + if ((ext_csd[EXT_CSD_PARTITION_SUPPORT] & 0x2) && + (ext_csd[EXT_CSD_PARTITION_ATTRIBUTE] & 0x1)) { + u8 hc_erase_grp_sz = +@@ -405,6 +406,7 @@ static int mmc_read_ext_csd(struct mmc_card *card, u8 *ext_csd) + if (card->ext_csd.rev >= 5) + card->ext_csd.rel_param = ext_csd[EXT_CSD_WR_REL_PARAM]; + ++ card->ext_csd.raw_erased_mem_count = ext_csd[EXT_CSD_ERASED_MEM_CONT]; + if (ext_csd[EXT_CSD_ERASED_MEM_CONT]) + card->erased_byte = 0xFF; + else +@@ -891,6 +893,7 @@ static void mmc_detect(struct mmc_host *host) + + mmc_claim_host(host); + mmc_detach_bus(host); ++ mmc_power_off(host); + mmc_release_host(host); + } + } +diff --git a/drivers/mmc/core/sd.c b/drivers/mmc/core/sd.c +index ff27741..bd8805c 100644 +--- a/drivers/mmc/core/sd.c ++++ b/drivers/mmc/core/sd.c +@@ -1008,6 +1008,7 @@ static void mmc_sd_detect(struct mmc_host *host) + + mmc_claim_host(host); + mmc_detach_bus(host); ++ mmc_power_off(host); + mmc_release_host(host); + } + } +diff --git a/drivers/mmc/core/sdio.c b/drivers/mmc/core/sdio.c +index 262fff0..ac492ac 100644 +--- a/drivers/mmc/core/sdio.c ++++ b/drivers/mmc/core/sdio.c +@@ -597,6 +597,7 @@ out: + + mmc_claim_host(host); + mmc_detach_bus(host); ++ mmc_power_off(host); + mmc_release_host(host); + } + } +diff --git a/drivers/mtd/mtdchar.c b/drivers/mtd/mtdchar.c +index 3f92731..9f8658e 100644 +--- a/drivers/mtd/mtdchar.c ++++ b/drivers/mtd/mtdchar.c +@@ -320,6 +320,7 @@ static ssize_t mtd_write(struct file *file, const char __user *buf, size_t count + ops.mode = MTD_OOB_RAW; + ops.datbuf = kbuf; + ops.oobbuf = NULL; ++ ops.ooboffs = 0; + ops.len = len; + + ret = mtd->write_oob(mtd, *ppos, &ops); +diff --git a/drivers/mtd/nand/nand_base.c b/drivers/mtd/nand/nand_base.c +index a46e9bb..86f05f4 100644 +--- a/drivers/mtd/nand/nand_base.c ++++ b/drivers/mtd/nand/nand_base.c +@@ -2097,14 +2097,22 @@ static int nand_write_page(struct mtd_info *mtd, struct nand_chip *chip, + + /** + * nand_fill_oob - [Internal] Transfer client buffer to oob +- * @chip: nand chip structure ++ * @mtd: MTD device structure + * @oob: oob data buffer + * @len: oob data write length + * @ops: oob ops structure + */ +-static uint8_t *nand_fill_oob(struct nand_chip *chip, uint8_t *oob, size_t len, +- struct mtd_oob_ops *ops) ++static uint8_t *nand_fill_oob(struct mtd_info *mtd, uint8_t *oob, size_t len, ++ struct mtd_oob_ops *ops) + { ++ struct nand_chip *chip = mtd->priv; ++ ++ /* ++ * Initialise to all 0xFF, to avoid the possibility of left over OOB ++ * data from a previous OOB read. ++ */ ++ memset(chip->oob_poi, 0xff, mtd->oobsize); ++ + switch (ops->mode) { + + case MTD_OOB_PLACE: +@@ -2201,10 +2209,6 @@ static int nand_do_write_ops(struct mtd_info *mtd, loff_t to, + (chip->pagebuf << chip->page_shift) < (to + ops->len)) + chip->pagebuf = -1; + +- /* If we're not given explicit OOB data, let it be 0xFF */ +- if (likely(!oob)) +- memset(chip->oob_poi, 0xff, mtd->oobsize); +- + /* Don't allow multipage oob writes with offset */ + if (oob && ops->ooboffs && (ops->ooboffs + ops->ooblen > oobmaxlen)) + return -EINVAL; +@@ -2226,8 +2230,11 @@ static int nand_do_write_ops(struct mtd_info *mtd, loff_t to, + + if (unlikely(oob)) { + size_t len = min(oobwritelen, oobmaxlen); +- oob = nand_fill_oob(chip, oob, len, ops); ++ oob = nand_fill_oob(mtd, oob, len, ops); + oobwritelen -= len; ++ } else { ++ /* We still need to erase leftover OOB data */ ++ memset(chip->oob_poi, 0xff, mtd->oobsize); + } + + ret = chip->write_page(mtd, chip, wbuf, page, cached, +@@ -2401,10 +2408,8 @@ static int nand_do_write_oob(struct mtd_info *mtd, loff_t to, + if (page == chip->pagebuf) + chip->pagebuf = -1; + +- memset(chip->oob_poi, 0xff, mtd->oobsize); +- nand_fill_oob(chip, ops->oobbuf, ops->ooblen, ops); ++ nand_fill_oob(mtd, ops->oobbuf, ops->ooblen, ops); + status = chip->ecc.write_oob(mtd, chip, page & chip->pagemask); +- memset(chip->oob_poi, 0xff, mtd->oobsize); + + if (status) + return status; +diff --git a/drivers/mtd/nand/pxa3xx_nand.c b/drivers/mtd/nand/pxa3xx_nand.c +index 1fb3b3a..30689cc 100644 +--- a/drivers/mtd/nand/pxa3xx_nand.c ++++ b/drivers/mtd/nand/pxa3xx_nand.c +@@ -685,6 +685,8 @@ static int pxa3xx_nand_read_page_hwecc(struct mtd_info *mtd, + * OOB, ignore such double bit errors + */ + if (is_buf_blank(buf, mtd->writesize)) ++ info->retcode = ERR_NONE; ++ else + mtd->ecc_stats.failed++; + } + +@@ -813,7 +815,7 @@ static int pxa3xx_nand_detect_config(struct pxa3xx_nand_info *info) + info->page_size = ndcr & NDCR_PAGE_SZ ? 2048 : 512; + /* set info fields needed to read id */ + info->read_id_bytes = (info->page_size == 2048) ? 4 : 2; +- info->reg_ndcr = ndcr; ++ info->reg_ndcr = ndcr & ~NDCR_INT_MASK; + info->cmdset = &default_cmdset; + + info->ndtr0cs0 = nand_readl(info, NDTR0CS0); +@@ -882,7 +884,7 @@ static int pxa3xx_nand_scan(struct mtd_info *mtd) + struct pxa3xx_nand_info *info = mtd->priv; + struct platform_device *pdev = info->pdev; + struct pxa3xx_nand_platform_data *pdata = pdev->dev.platform_data; +- struct nand_flash_dev pxa3xx_flash_ids[2] = { {NULL,}, {NULL,} }; ++ struct nand_flash_dev pxa3xx_flash_ids[2], *def = NULL; + const struct pxa3xx_nand_flash *f = NULL; + struct nand_chip *chip = mtd->priv; + uint32_t id = -1; +@@ -942,8 +944,10 @@ static int pxa3xx_nand_scan(struct mtd_info *mtd) + pxa3xx_flash_ids[0].erasesize = f->page_size * f->page_per_block; + if (f->flash_width == 16) + pxa3xx_flash_ids[0].options = NAND_BUSWIDTH_16; ++ pxa3xx_flash_ids[1].name = NULL; ++ def = pxa3xx_flash_ids; + KEEP_CONFIG: +- if (nand_scan_ident(mtd, 1, pxa3xx_flash_ids)) ++ if (nand_scan_ident(mtd, 1, def)) + return -ENODEV; + /* calculate addressing information */ + info->col_addr_cycles = (mtd->writesize >= 2048) ? 2 : 1; +@@ -954,9 +958,9 @@ KEEP_CONFIG: + info->row_addr_cycles = 2; + mtd->name = mtd_names[0]; + chip->ecc.mode = NAND_ECC_HW; +- chip->ecc.size = f->page_size; ++ chip->ecc.size = info->page_size; + +- chip->options = (f->flash_width == 16) ? NAND_BUSWIDTH_16 : 0; ++ chip->options = (info->reg_ndcr & NDCR_DWIDTH_M) ? NAND_BUSWIDTH_16 : 0; + chip->options |= NAND_NO_AUTOINCR; + chip->options |= NAND_NO_READRDY; + +diff --git a/drivers/mtd/redboot.c b/drivers/mtd/redboot.c +index 7a87d07..4938bd0 100644 +--- a/drivers/mtd/redboot.c ++++ b/drivers/mtd/redboot.c +@@ -297,6 +297,9 @@ static struct mtd_part_parser redboot_parser = { + .name = "RedBoot", + }; + ++/* mtd parsers will request the module by parser name */ ++MODULE_ALIAS("RedBoot"); ++ + static int __init redboot_parser_init(void) + { + return register_mtd_parser(&redboot_parser); +diff --git a/drivers/net/bonding/bond_main.c b/drivers/net/bonding/bond_main.c +index 9ea2f21..2065cb4 100644 +--- a/drivers/net/bonding/bond_main.c ++++ b/drivers/net/bonding/bond_main.c +@@ -1500,6 +1500,8 @@ static rx_handler_result_t bond_handle_frame(struct sk_buff **pskb) + struct sk_buff *skb = *pskb; + struct slave *slave; + struct bonding *bond; ++ void (*recv_probe)(struct sk_buff *, struct bonding *, ++ struct slave *); + + skb = skb_share_check(skb, GFP_ATOMIC); + if (unlikely(!skb)) +@@ -1513,11 +1515,12 @@ static rx_handler_result_t bond_handle_frame(struct sk_buff **pskb) + if (bond->params.arp_interval) + slave->dev->last_rx = jiffies; + +- if (bond->recv_probe) { ++ recv_probe = ACCESS_ONCE(bond->recv_probe); ++ if (recv_probe) { + struct sk_buff *nskb = skb_clone(skb, GFP_ATOMIC); + + if (likely(nskb)) { +- bond->recv_probe(nskb, bond, slave); ++ recv_probe(nskb, bond, slave); + dev_kfree_skb(nskb); + } + } +diff --git a/drivers/net/enic/enic_main.c b/drivers/net/enic/enic_main.c +index 2f433fb..51fba5f 100644 +--- a/drivers/net/enic/enic_main.c ++++ b/drivers/net/enic/enic_main.c +@@ -1718,8 +1718,12 @@ static void enic_poll_controller(struct net_device *netdev) + enic_isr_msix_rq(enic->msix_entry[intr].vector, + &enic->napi[i]); + } +- intr = enic_msix_wq_intr(enic, i); +- enic_isr_msix_wq(enic->msix_entry[intr].vector, enic); ++ ++ for (i = 0; i < enic->wq_count; i++) { ++ intr = enic_msix_wq_intr(enic, i); ++ enic_isr_msix_wq(enic->msix_entry[intr].vector, enic); ++ } ++ + break; + case VNIC_DEV_INTR_MODE_MSI: + enic_isr_msi(enic->pdev->irq, enic); +diff --git a/drivers/net/macvlan.c b/drivers/net/macvlan.c +index 2f3c48d..ab4723d 100644 +--- a/drivers/net/macvlan.c ++++ b/drivers/net/macvlan.c +@@ -239,7 +239,7 @@ static int macvlan_queue_xmit(struct sk_buff *skb, struct net_device *dev) + dest = macvlan_hash_lookup(port, eth->h_dest); + if (dest && dest->mode == MACVLAN_MODE_BRIDGE) { + /* send to lowerdev first for its network taps */ +- vlan->forward(vlan->lowerdev, skb); ++ dev_forward_skb(vlan->lowerdev, skb); + + return NET_XMIT_SUCCESS; + } +diff --git a/drivers/net/netconsole.c b/drivers/net/netconsole.c +index dfc8272..4840ab7 100644 +--- a/drivers/net/netconsole.c ++++ b/drivers/net/netconsole.c +@@ -307,6 +307,11 @@ static ssize_t store_enabled(struct netconsole_target *nt, + return err; + if (enabled < 0 || enabled > 1) + return -EINVAL; ++ if (enabled == nt->enabled) { ++ printk(KERN_INFO "netconsole: network logging has already %s\n", ++ nt->enabled ? "started" : "stopped"); ++ return -EINVAL; ++ } + + if (enabled) { /* 1 */ + +diff --git a/drivers/net/phy/dp83640.c b/drivers/net/phy/dp83640.c +index cb6e0b4..364cd67 100644 +--- a/drivers/net/phy/dp83640.c ++++ b/drivers/net/phy/dp83640.c +@@ -875,6 +875,7 @@ static void dp83640_remove(struct phy_device *phydev) + struct dp83640_clock *clock; + struct list_head *this, *next; + struct dp83640_private *tmp, *dp83640 = phydev->priv; ++ struct sk_buff *skb; + + if (phydev->addr == BROADCAST_ADDR) + return; +@@ -882,6 +883,12 @@ static void dp83640_remove(struct phy_device *phydev) + enable_status_frames(phydev, false); + cancel_work_sync(&dp83640->ts_work); + ++ while ((skb = skb_dequeue(&dp83640->rx_queue)) != NULL) ++ kfree_skb(skb); ++ ++ while ((skb = skb_dequeue(&dp83640->tx_queue)) != NULL) ++ skb_complete_tx_timestamp(skb, NULL); ++ + clock = dp83640_clock_get(dp83640->clock); + + if (dp83640 == clock->chosen) { +@@ -1060,7 +1067,7 @@ static void dp83640_txtstamp(struct phy_device *phydev, + struct dp83640_private *dp83640 = phydev->priv; + + if (!dp83640->hwts_tx_en) { +- kfree_skb(skb); ++ skb_complete_tx_timestamp(skb, NULL); + return; + } + skb_queue_tail(&dp83640->tx_queue, skb); +diff --git a/drivers/net/rionet.c b/drivers/net/rionet.c +index ca4694e..1f421d7 100644 +--- a/drivers/net/rionet.c ++++ b/drivers/net/rionet.c +@@ -88,8 +88,8 @@ static struct rio_dev **rionet_active; + #define dev_rionet_capable(dev) \ + is_rionet_capable(dev->src_ops, dev->dst_ops) + +-#define RIONET_MAC_MATCH(x) (*(u32 *)x == 0x00010001) +-#define RIONET_GET_DESTID(x) (*(u16 *)(x + 4)) ++#define RIONET_MAC_MATCH(x) (!memcmp((x), "\00\01\00\01", 4)) ++#define RIONET_GET_DESTID(x) ((*((u8 *)x + 4) << 8) | *((u8 *)x + 5)) + + static int rionet_rx_clean(struct net_device *ndev) + { +diff --git a/drivers/net/tg3.c b/drivers/net/tg3.c +index 38f6859..bc8c183 100644 +--- a/drivers/net/tg3.c ++++ b/drivers/net/tg3.c +@@ -15278,7 +15278,7 @@ static void __devexit tg3_remove_one(struct pci_dev *pdev) + + cancel_work_sync(&tp->reset_task); + +- if (!tg3_flag(tp, USE_PHYLIB)) { ++ if (tg3_flag(tp, USE_PHYLIB)) { + tg3_phy_fini(tp); + tg3_mdio_fini(tp); + } +diff --git a/drivers/net/usb/asix.c b/drivers/net/usb/asix.c +index 5250288..c5c4b4d 100644 +--- a/drivers/net/usb/asix.c ++++ b/drivers/net/usb/asix.c +@@ -314,12 +314,11 @@ static int asix_rx_fixup(struct usbnet *dev, struct sk_buff *skb) + skb_pull(skb, 4); + + while (skb->len > 0) { +- if ((short)(header & 0x0000ffff) != +- ~((short)((header & 0xffff0000) >> 16))) { ++ if ((header & 0x07ff) != ((~header >> 16) & 0x07ff)) + netdev_err(dev->net, "asix_rx_fixup() Bad Header Length\n"); +- } ++ + /* get the packet length */ +- size = (u16) (header & 0x0000ffff); ++ size = (u16) (header & 0x000007ff); + + if ((skb->len) - ((size + 1) & 0xfffe) == 0) { + u8 alignment = (unsigned long)skb->data & 0x3; +diff --git a/drivers/net/usb/cdc_ncm.c b/drivers/net/usb/cdc_ncm.c +index d3b9e95..6a53161 100644 +--- a/drivers/net/usb/cdc_ncm.c ++++ b/drivers/net/usb/cdc_ncm.c +@@ -229,23 +229,40 @@ static u8 cdc_ncm_setup(struct cdc_ncm_ctx *ctx) + if (ctx->rx_max != le32_to_cpu(ctx->ncm_parm.dwNtbInMaxSize)) { + + if (flags & USB_CDC_NCM_NCAP_NTB_INPUT_SIZE) { +- struct usb_cdc_ncm_ndp_input_size ndp_in_sz; ++ struct usb_cdc_ncm_ndp_input_size *ndp_in_sz; ++ ++ ndp_in_sz = kzalloc(sizeof(*ndp_in_sz), GFP_KERNEL); ++ if (!ndp_in_sz) { ++ err = -ENOMEM; ++ goto size_err; ++ } ++ + err = usb_control_msg(ctx->udev, + usb_sndctrlpipe(ctx->udev, 0), + USB_CDC_SET_NTB_INPUT_SIZE, + USB_TYPE_CLASS | USB_DIR_OUT + | USB_RECIP_INTERFACE, +- 0, iface_no, &ndp_in_sz, 8, 1000); ++ 0, iface_no, ndp_in_sz, 8, 1000); ++ kfree(ndp_in_sz); + } else { +- __le32 dwNtbInMaxSize = cpu_to_le32(ctx->rx_max); ++ __le32 *dwNtbInMaxSize; ++ dwNtbInMaxSize = kzalloc(sizeof(*dwNtbInMaxSize), ++ GFP_KERNEL); ++ if (!dwNtbInMaxSize) { ++ err = -ENOMEM; ++ goto size_err; ++ } ++ *dwNtbInMaxSize = cpu_to_le32(ctx->rx_max); ++ + err = usb_control_msg(ctx->udev, + usb_sndctrlpipe(ctx->udev, 0), + USB_CDC_SET_NTB_INPUT_SIZE, + USB_TYPE_CLASS | USB_DIR_OUT + | USB_RECIP_INTERFACE, +- 0, iface_no, &dwNtbInMaxSize, 4, 1000); ++ 0, iface_no, dwNtbInMaxSize, 4, 1000); ++ kfree(dwNtbInMaxSize); + } +- ++size_err: + if (err < 0) + pr_debug("Setting NTB Input Size failed\n"); + } +@@ -326,19 +343,29 @@ static u8 cdc_ncm_setup(struct cdc_ncm_ctx *ctx) + + /* set Max Datagram Size (MTU) */ + if (flags & USB_CDC_NCM_NCAP_MAX_DATAGRAM_SIZE) { +- __le16 max_datagram_size; ++ __le16 *max_datagram_size; + u16 eth_max_sz = le16_to_cpu(ctx->ether_desc->wMaxSegmentSize); ++ ++ max_datagram_size = kzalloc(sizeof(*max_datagram_size), ++ GFP_KERNEL); ++ if (!max_datagram_size) { ++ err = -ENOMEM; ++ goto max_dgram_err; ++ } ++ + err = usb_control_msg(ctx->udev, usb_rcvctrlpipe(ctx->udev, 0), + USB_CDC_GET_MAX_DATAGRAM_SIZE, + USB_TYPE_CLASS | USB_DIR_IN + | USB_RECIP_INTERFACE, +- 0, iface_no, &max_datagram_size, ++ 0, iface_no, max_datagram_size, + 2, 1000); + if (err < 0) { + pr_debug("GET_MAX_DATAGRAM_SIZE failed, use size=%u\n", + CDC_NCM_MIN_DATAGRAM_SIZE); ++ kfree(max_datagram_size); + } else { +- ctx->max_datagram_size = le16_to_cpu(max_datagram_size); ++ ctx->max_datagram_size = ++ le16_to_cpu(*max_datagram_size); + /* Check Eth descriptor value */ + if (eth_max_sz < CDC_NCM_MAX_DATAGRAM_SIZE) { + if (ctx->max_datagram_size > eth_max_sz) +@@ -361,8 +388,10 @@ static u8 cdc_ncm_setup(struct cdc_ncm_ctx *ctx) + USB_TYPE_CLASS | USB_DIR_OUT + | USB_RECIP_INTERFACE, + 0, +- iface_no, &max_datagram_size, ++ iface_no, max_datagram_size, + 2, 1000); ++ kfree(max_datagram_size); ++max_dgram_err: + if (err < 0) + pr_debug("SET_MAX_DATAGRAM_SIZE failed\n"); + } +diff --git a/drivers/net/usb/ipheth.c b/drivers/net/usb/ipheth.c +index 81126ff..8f9b7f7 100644 +--- a/drivers/net/usb/ipheth.c ++++ b/drivers/net/usb/ipheth.c +@@ -59,6 +59,7 @@ + #define USB_PRODUCT_IPHONE_3G 0x1292 + #define USB_PRODUCT_IPHONE_3GS 0x1294 + #define USB_PRODUCT_IPHONE_4 0x1297 ++#define USB_PRODUCT_IPHONE_4_VZW 0x129c + + #define IPHETH_USBINTF_CLASS 255 + #define IPHETH_USBINTF_SUBCLASS 253 +@@ -98,6 +99,10 @@ static struct usb_device_id ipheth_table[] = { + USB_VENDOR_APPLE, USB_PRODUCT_IPHONE_4, + IPHETH_USBINTF_CLASS, IPHETH_USBINTF_SUBCLASS, + IPHETH_USBINTF_PROTO) }, ++ { USB_DEVICE_AND_INTERFACE_INFO( ++ USB_VENDOR_APPLE, USB_PRODUCT_IPHONE_4_VZW, ++ IPHETH_USBINTF_CLASS, IPHETH_USBINTF_SUBCLASS, ++ IPHETH_USBINTF_PROTO) }, + { } + }; + MODULE_DEVICE_TABLE(usb, ipheth_table); +diff --git a/drivers/net/usb/rtl8150.c b/drivers/net/usb/rtl8150.c +index 041fb7d..ef3b236 100644 +--- a/drivers/net/usb/rtl8150.c ++++ b/drivers/net/usb/rtl8150.c +@@ -977,7 +977,6 @@ static void rtl8150_disconnect(struct usb_interface *intf) + usb_set_intfdata(intf, NULL); + if (dev) { + set_bit(RTL8150_UNPLUG, &dev->flags); +- tasklet_disable(&dev->tl); + tasklet_kill(&dev->tl); + unregister_netdev(dev->netdev); + unlink_all_urbs(dev); +diff --git a/drivers/net/wireless/ath/ath9k/ani.c b/drivers/net/wireless/ath/ath9k/ani.c +index bfb6481..4e4e7c3 100644 +--- a/drivers/net/wireless/ath/ath9k/ani.c ++++ b/drivers/net/wireless/ath/ath9k/ani.c +@@ -502,9 +502,6 @@ static void ath9k_ani_reset_old(struct ath_hw *ah, bool is_scanning) + ath9k_hw_ani_control(ah, ATH9K_ANI_CCK_WEAK_SIGNAL_THR, + ATH9K_ANI_CCK_WEAK_SIG_THR); + +- ath9k_hw_setrxfilter(ah, ath9k_hw_getrxfilter(ah) | +- ATH9K_RX_FILTER_PHYERR); +- + ath9k_ani_restart(ah); + return; + } +@@ -525,8 +522,6 @@ static void ath9k_ani_reset_old(struct ath_hw *ah, bool is_scanning) + ath9k_hw_ani_control(ah, ATH9K_ANI_FIRSTEP_LEVEL, + aniState->firstepLevel); + +- ath9k_hw_setrxfilter(ah, ath9k_hw_getrxfilter(ah) & +- ~ATH9K_RX_FILTER_PHYERR); + ath9k_ani_restart(ah); + + ENABLE_REGWRITE_BUFFER(ah); +diff --git a/drivers/net/wireless/ath/ath9k/ar9003_calib.c b/drivers/net/wireless/ath/ath9k/ar9003_calib.c +index f48051c..7c2aaad 100644 +--- a/drivers/net/wireless/ath/ath9k/ar9003_calib.c ++++ b/drivers/net/wireless/ath/ath9k/ar9003_calib.c +@@ -643,8 +643,9 @@ static void ar9003_hw_detect_outlier(int *mp_coeff, int nmeasurement, + outlier_idx = max_idx; + else + outlier_idx = min_idx; ++ ++ mp_coeff[outlier_idx] = mp_avg; + } +- mp_coeff[outlier_idx] = mp_avg; + } + + static void ar9003_hw_tx_iqcal_load_avg_2_passes(struct ath_hw *ah, +diff --git a/drivers/net/wireless/ath/ath9k/ar9003_mac.c b/drivers/net/wireless/ath/ath9k/ar9003_mac.c +index 1f99249..7880dca 100644 +--- a/drivers/net/wireless/ath/ath9k/ar9003_mac.c ++++ b/drivers/net/wireless/ath/ath9k/ar9003_mac.c +@@ -255,8 +255,6 @@ static int ar9003_hw_proc_txdesc(struct ath_hw *ah, void *ds, + return -EIO; + } + +- if (status & AR_TxOpExceeded) +- ts->ts_status |= ATH9K_TXERR_XTXOP; + ts->ts_rateindex = MS(status, AR_FinalTxIdx); + ts->ts_seqnum = MS(status, AR_SeqNum); + ts->tid = MS(status, AR_TxTid); +@@ -267,6 +265,8 @@ static int ar9003_hw_proc_txdesc(struct ath_hw *ah, void *ds, + ts->ts_status = 0; + ts->ts_flags = 0; + ++ if (status & AR_TxOpExceeded) ++ ts->ts_status |= ATH9K_TXERR_XTXOP; + status = ACCESS_ONCE(ads->status2); + ts->ts_rssi_ctl0 = MS(status, AR_TxRSSIAnt00); + ts->ts_rssi_ctl1 = MS(status, AR_TxRSSIAnt01); +diff --git a/drivers/net/wireless/ath/ath9k/ar9003_phy.h b/drivers/net/wireless/ath/ath9k/ar9003_phy.h +index efdbe98..2364b5f 100644 +--- a/drivers/net/wireless/ath/ath9k/ar9003_phy.h ++++ b/drivers/net/wireless/ath/ath9k/ar9003_phy.h +@@ -570,12 +570,12 @@ + + #define AR_PHY_TXGAIN_TABLE (AR_SM_BASE + 0x300) + +-#define AR_PHY_TX_IQCAL_CONTROL_1 (AR_SM_BASE + AR_SREV_9485(ah) ? \ +- 0x3c8 : 0x448) +-#define AR_PHY_TX_IQCAL_START (AR_SM_BASE + AR_SREV_9485(ah) ? \ +- 0x3c4 : 0x440) +-#define AR_PHY_TX_IQCAL_STATUS_B0 (AR_SM_BASE + AR_SREV_9485(ah) ? \ +- 0x3f0 : 0x48c) ++#define AR_PHY_TX_IQCAL_CONTROL_1 (AR_SM_BASE + (AR_SREV_9485(ah) ? \ ++ 0x3c8 : 0x448)) ++#define AR_PHY_TX_IQCAL_START (AR_SM_BASE + (AR_SREV_9485(ah) ? \ ++ 0x3c4 : 0x440)) ++#define AR_PHY_TX_IQCAL_STATUS_B0 (AR_SM_BASE + (AR_SREV_9485(ah) ? \ ++ 0x3f0 : 0x48c)) + #define AR_PHY_TX_IQCAL_CORR_COEFF_B0(_i) (AR_SM_BASE + \ + (AR_SREV_9485(ah) ? \ + 0x3d0 : 0x450) + ((_i) << 2)) +diff --git a/drivers/net/wireless/ath/ath9k/ar9485_initvals.h b/drivers/net/wireless/ath/ath9k/ar9485_initvals.h +index 611ea6c..d16d029 100644 +--- a/drivers/net/wireless/ath/ath9k/ar9485_initvals.h ++++ b/drivers/net/wireless/ath/ath9k/ar9485_initvals.h +@@ -521,7 +521,7 @@ static const u32 ar9485_1_1_radio_postamble[][2] = { + {0x000160ac, 0x24611800}, + {0x000160b0, 0x03284f3e}, + {0x0001610c, 0x00170000}, +- {0x00016140, 0x10804008}, ++ {0x00016140, 0x50804008}, + }; + + static const u32 ar9485_1_1_mac_postamble[][5] = { +@@ -603,7 +603,7 @@ static const u32 ar9485_1_1_radio_core[][2] = { + + static const u32 ar9485_1_1_pcie_phy_pll_on_clkreq_enable_L1[][2] = { + /* Addr allmodes */ +- {0x00018c00, 0x10052e5e}, ++ {0x00018c00, 0x18052e5e}, + {0x00018c04, 0x000801d8}, + {0x00018c08, 0x0000080c}, + }; +@@ -776,7 +776,7 @@ static const u32 ar9485_modes_green_ob_db_tx_gain_1_1[][5] = { + + static const u32 ar9485_1_1_pcie_phy_clkreq_disable_L1[][2] = { + /* Addr allmodes */ +- {0x00018c00, 0x10013e5e}, ++ {0x00018c00, 0x18013e5e}, + {0x00018c04, 0x000801d8}, + {0x00018c08, 0x0000080c}, + }; +@@ -882,7 +882,7 @@ static const u32 ar9485_fast_clock_1_1_baseband_postamble[][3] = { + + static const u32 ar9485_1_1_pcie_phy_pll_on_clkreq_disable_L1[][2] = { + /* Addr allmodes */ +- {0x00018c00, 0x10012e5e}, ++ {0x00018c00, 0x18012e5e}, + {0x00018c04, 0x000801d8}, + {0x00018c08, 0x0000080c}, + }; +@@ -1021,7 +1021,7 @@ static const u32 ar9485_common_rx_gain_1_1[][2] = { + + static const u32 ar9485_1_1_pcie_phy_clkreq_enable_L1[][2] = { + /* Addr allmodes */ +- {0x00018c00, 0x10053e5e}, ++ {0x00018c00, 0x18053e5e}, + {0x00018c04, 0x000801d8}, + {0x00018c08, 0x0000080c}, + }; +diff --git a/drivers/net/wireless/ath/ath9k/hif_usb.c b/drivers/net/wireless/ath/ath9k/hif_usb.c +index 260f1f3..5513c0a 100644 +--- a/drivers/net/wireless/ath/ath9k/hif_usb.c ++++ b/drivers/net/wireless/ath/ath9k/hif_usb.c +@@ -37,6 +37,7 @@ static struct usb_device_id ath9k_hif_usb_ids[] = { + { USB_DEVICE(0x04CA, 0x4605) }, /* Liteon */ + { USB_DEVICE(0x040D, 0x3801) }, /* VIA */ + { USB_DEVICE(0x0cf3, 0xb003) }, /* Ubiquiti WifiStation Ext */ ++ { USB_DEVICE(0x057c, 0x8403) }, /* AVM FRITZ!WLAN 11N v2 USB */ + + { USB_DEVICE(0x0cf3, 0x7015), + .driver_info = AR9287_USB }, /* Atheros */ +diff --git a/drivers/net/wireless/ath/ath9k/hw.c b/drivers/net/wireless/ath/ath9k/hw.c +index 03900ca..7c2f06e 100644 +--- a/drivers/net/wireless/ath/ath9k/hw.c ++++ b/drivers/net/wireless/ath/ath9k/hw.c +@@ -1931,6 +1931,10 @@ int ath9k_hw_fill_cap_info(struct ath_hw *ah) + pCap->num_gpio_pins = AR9271_NUM_GPIO; + else if (AR_DEVID_7010(ah)) + pCap->num_gpio_pins = AR7010_NUM_GPIO; ++ else if (AR_SREV_9300_20_OR_LATER(ah)) ++ pCap->num_gpio_pins = AR9300_NUM_GPIO; ++ else if (AR_SREV_9287_11_OR_LATER(ah)) ++ pCap->num_gpio_pins = AR9287_NUM_GPIO; + else if (AR_SREV_9285_12_OR_LATER(ah)) + pCap->num_gpio_pins = AR9285_NUM_GPIO; + else if (AR_SREV_9280_20_OR_LATER(ah)) +diff --git a/drivers/net/wireless/ath/ath9k/recv.c b/drivers/net/wireless/ath/ath9k/recv.c +index 07e35e5..3b5f9d6 100644 +--- a/drivers/net/wireless/ath/ath9k/recv.c ++++ b/drivers/net/wireless/ath/ath9k/recv.c +@@ -423,12 +423,9 @@ void ath_rx_cleanup(struct ath_softc *sc) + + u32 ath_calcrxfilter(struct ath_softc *sc) + { +-#define RX_FILTER_PRESERVE (ATH9K_RX_FILTER_PHYERR | ATH9K_RX_FILTER_PHYRADAR) +- + u32 rfilt; + +- rfilt = (ath9k_hw_getrxfilter(sc->sc_ah) & RX_FILTER_PRESERVE) +- | ATH9K_RX_FILTER_UCAST | ATH9K_RX_FILTER_BCAST ++ rfilt = ATH9K_RX_FILTER_UCAST | ATH9K_RX_FILTER_BCAST + | ATH9K_RX_FILTER_MCAST; + + if (sc->rx.rxfilter & FIF_PROBE_REQ) +diff --git a/drivers/net/wireless/iwlwifi/iwl-agn-ucode.c b/drivers/net/wireless/iwlwifi/iwl-agn-ucode.c +index 97de5d9..a03dbcc 100644 +--- a/drivers/net/wireless/iwlwifi/iwl-agn-ucode.c ++++ b/drivers/net/wireless/iwlwifi/iwl-agn-ucode.c +@@ -144,13 +144,8 @@ static int iwlagn_load_section(struct iwl_priv *priv, const char *name, + FH_TCSR_TX_CONFIG_REG_VAL_CIRQ_HOST_ENDTFD); + + IWL_DEBUG_INFO(priv, "%s uCode section being loaded...\n", name); +- ret = wait_event_interruptible_timeout(priv->wait_command_queue, +- priv->ucode_write_complete, 5 * HZ); +- if (ret == -ERESTARTSYS) { +- IWL_ERR(priv, "Could not load the %s uCode section due " +- "to interrupt\n", name); +- return ret; +- } ++ ret = wait_event_timeout(priv->wait_command_queue, ++ priv->ucode_write_complete, 5 * HZ); + if (!ret) { + IWL_ERR(priv, "Could not load the %s uCode section\n", + name); +diff --git a/drivers/net/wireless/iwlwifi/iwl-agn.c b/drivers/net/wireless/iwlwifi/iwl-agn.c +index f24165d..baec52d 100644 +--- a/drivers/net/wireless/iwlwifi/iwl-agn.c ++++ b/drivers/net/wireless/iwlwifi/iwl-agn.c +@@ -797,7 +797,7 @@ static void iwl_irq_tasklet(struct iwl_priv *priv) + handled |= CSR_INT_BIT_FH_TX; + /* Wake up uCode load routine, now that load is complete */ + priv->ucode_write_complete = 1; +- wake_up_interruptible(&priv->wait_command_queue); ++ wake_up(&priv->wait_command_queue); + } + + if (inta & ~handled) { +diff --git a/drivers/net/wireless/iwlwifi/iwl-core.c b/drivers/net/wireless/iwlwifi/iwl-core.c +index 45cc51c..5638407 100644 +--- a/drivers/net/wireless/iwlwifi/iwl-core.c ++++ b/drivers/net/wireless/iwlwifi/iwl-core.c +@@ -899,7 +899,7 @@ void iwlagn_fw_error(struct iwl_priv *priv, bool ondemand) + * commands by clearing the ready bit */ + clear_bit(STATUS_READY, &priv->status); + +- wake_up_interruptible(&priv->wait_command_queue); ++ wake_up(&priv->wait_command_queue); + + if (!ondemand) { + /* +@@ -950,7 +950,7 @@ void iwl_irq_handle_error(struct iwl_priv *priv) + */ + clear_bit(STATUS_READY, &priv->status); + clear_bit(STATUS_HCMD_ACTIVE, &priv->status); +- wake_up_interruptible(&priv->wait_command_queue); ++ wake_up(&priv->wait_command_queue); + IWL_ERR(priv, "RF is used by WiMAX\n"); + return; + } +diff --git a/drivers/net/wireless/iwlwifi/iwl-hcmd.c b/drivers/net/wireless/iwlwifi/iwl-hcmd.c +index 76f9966..fc11277 100644 +--- a/drivers/net/wireless/iwlwifi/iwl-hcmd.c ++++ b/drivers/net/wireless/iwlwifi/iwl-hcmd.c +@@ -194,7 +194,7 @@ int iwl_send_cmd_sync(struct iwl_priv *priv, struct iwl_host_cmd *cmd) + return ret; + } + +- ret = wait_event_interruptible_timeout(priv->wait_command_queue, ++ ret = wait_event_timeout(priv->wait_command_queue, + !test_bit(STATUS_HCMD_ACTIVE, &priv->status), + HOST_COMPLETE_TIMEOUT); + if (!ret) { +diff --git a/drivers/net/wireless/iwlwifi/iwl-rx.c b/drivers/net/wireless/iwlwifi/iwl-rx.c +index b774517..865ac1a 100644 +--- a/drivers/net/wireless/iwlwifi/iwl-rx.c ++++ b/drivers/net/wireless/iwlwifi/iwl-rx.c +@@ -738,7 +738,7 @@ static void iwl_rx_card_state_notif(struct iwl_priv *priv, + wiphy_rfkill_set_hw_state(priv->hw->wiphy, + test_bit(STATUS_RF_KILL_HW, &priv->status)); + else +- wake_up_interruptible(&priv->wait_command_queue); ++ wake_up(&priv->wait_command_queue); + } + + static void iwl_rx_missed_beacon_notif(struct iwl_priv *priv, +diff --git a/drivers/net/wireless/iwlwifi/iwl-tx.c b/drivers/net/wireless/iwlwifi/iwl-tx.c +index c368c50..93152c3 100644 +--- a/drivers/net/wireless/iwlwifi/iwl-tx.c ++++ b/drivers/net/wireless/iwlwifi/iwl-tx.c +@@ -821,7 +821,7 @@ void iwl_tx_cmd_complete(struct iwl_priv *priv, struct iwl_rx_mem_buffer *rxb) + clear_bit(STATUS_HCMD_ACTIVE, &priv->status); + IWL_DEBUG_INFO(priv, "Clearing HCMD_ACTIVE for command %s\n", + get_cmd_string(cmd->hdr.cmd)); +- wake_up_interruptible(&priv->wait_command_queue); ++ wake_up(&priv->wait_command_queue); + } + + /* Mark as unmapped */ +diff --git a/drivers/net/wireless/wl12xx/scan.c b/drivers/net/wireless/wl12xx/scan.c +index 56f76ab..9542e46 100644 +--- a/drivers/net/wireless/wl12xx/scan.c ++++ b/drivers/net/wireless/wl12xx/scan.c +@@ -83,14 +83,18 @@ static int wl1271_get_scan_channels(struct wl1271 *wl, + for (i = 0, j = 0; + i < req->n_channels && j < WL1271_SCAN_MAX_CHANNELS; + i++) { +- + flags = req->channels[i]->flags; + + if (!test_bit(i, wl->scan.scanned_ch) && + !(flags & IEEE80211_CHAN_DISABLED) && +- ((!!(flags & IEEE80211_CHAN_PASSIVE_SCAN)) == passive) && +- (req->channels[i]->band == band)) { +- ++ (req->channels[i]->band == band) && ++ /* ++ * In passive scans, we scan all remaining ++ * channels, even if not marked as such. ++ * In active scans, we only scan channels not ++ * marked as passive. ++ */ ++ (passive || !(flags & IEEE80211_CHAN_PASSIVE_SCAN))) { + wl1271_debug(DEBUG_SCAN, "band %d, center_freq %d ", + req->channels[i]->band, + req->channels[i]->center_freq); +@@ -142,6 +146,10 @@ static int wl1271_scan_send(struct wl1271 *wl, enum ieee80211_band band, + int ret; + u16 scan_options = 0; + ++ /* skip active scans if we don't have SSIDs */ ++ if (!passive && wl->scan.req->n_ssids == 0) ++ return WL1271_NOTHING_TO_SCAN; ++ + cmd = kzalloc(sizeof(*cmd), GFP_KERNEL); + trigger = kzalloc(sizeof(*trigger), GFP_KERNEL); + if (!cmd || !trigger) { +@@ -152,8 +160,7 @@ static int wl1271_scan_send(struct wl1271 *wl, enum ieee80211_band band, + /* We always use high priority scans */ + scan_options = WL1271_SCAN_OPT_PRIORITY_HIGH; + +- /* No SSIDs means that we have a forced passive scan */ +- if (passive || wl->scan.req->n_ssids == 0) ++ if (passive) + scan_options |= WL1271_SCAN_OPT_PASSIVE; + + cmd->params.scan_options = cpu_to_le16(scan_options); +diff --git a/drivers/net/xen-netback/interface.c b/drivers/net/xen-netback/interface.c +index 0ca86f9..1825629 100644 +--- a/drivers/net/xen-netback/interface.c ++++ b/drivers/net/xen-netback/interface.c +@@ -327,12 +327,12 @@ int xenvif_connect(struct xenvif *vif, unsigned long tx_ring_ref, + xenvif_get(vif); + + rtnl_lock(); +- if (netif_running(vif->dev)) +- xenvif_up(vif); + if (!vif->can_sg && vif->dev->mtu > ETH_DATA_LEN) + dev_set_mtu(vif->dev, ETH_DATA_LEN); + netdev_update_features(vif->dev); + netif_carrier_on(vif->dev); ++ if (netif_running(vif->dev)) ++ xenvif_up(vif); + rtnl_unlock(); + + return 0; +diff --git a/drivers/pci/quirks.c b/drivers/pci/quirks.c +index 1196f61..cec4629 100644 +--- a/drivers/pci/quirks.c ++++ b/drivers/pci/quirks.c +@@ -2745,20 +2745,6 @@ static void ricoh_mmc_fixup_r5c832(struct pci_dev *dev) + /* disable must be done via function #0 */ + if (PCI_FUNC(dev->devfn)) + return; +- +- pci_read_config_byte(dev, 0xCB, &disable); +- +- if (disable & 0x02) +- return; +- +- pci_read_config_byte(dev, 0xCA, &write_enable); +- pci_write_config_byte(dev, 0xCA, 0x57); +- pci_write_config_byte(dev, 0xCB, disable | 0x02); +- pci_write_config_byte(dev, 0xCA, write_enable); +- +- dev_notice(&dev->dev, "proprietary Ricoh MMC controller disabled (via firewire function)\n"); +- dev_notice(&dev->dev, "MMC cards are now supported by standard SDHCI controller\n"); +- + /* + * RICOH 0xe823 SD/MMC card reader fails to recognize + * certain types of SD/MMC cards. Lowering the SD base +@@ -2781,6 +2767,20 @@ static void ricoh_mmc_fixup_r5c832(struct pci_dev *dev) + + dev_notice(&dev->dev, "MMC controller base frequency changed to 50Mhz.\n"); + } ++ ++ pci_read_config_byte(dev, 0xCB, &disable); ++ ++ if (disable & 0x02) ++ return; ++ ++ pci_read_config_byte(dev, 0xCA, &write_enable); ++ pci_write_config_byte(dev, 0xCA, 0x57); ++ pci_write_config_byte(dev, 0xCB, disable | 0x02); ++ pci_write_config_byte(dev, 0xCA, write_enable); ++ ++ dev_notice(&dev->dev, "proprietary Ricoh MMC controller disabled (via firewire function)\n"); ++ dev_notice(&dev->dev, "MMC cards are now supported by standard SDHCI controller\n"); ++ + } + DECLARE_PCI_FIXUP_EARLY(PCI_VENDOR_ID_RICOH, PCI_DEVICE_ID_RICOH_R5C832, ricoh_mmc_fixup_r5c832); + DECLARE_PCI_FIXUP_RESUME_EARLY(PCI_VENDOR_ID_RICOH, PCI_DEVICE_ID_RICOH_R5C832, ricoh_mmc_fixup_r5c832); +diff --git a/drivers/pci/xen-pcifront.c b/drivers/pci/xen-pcifront.c +index 492b7d8..d4e7a10 100644 +--- a/drivers/pci/xen-pcifront.c ++++ b/drivers/pci/xen-pcifront.c +@@ -400,9 +400,8 @@ static int pcifront_claim_resource(struct pci_dev *dev, void *data) + dev_info(&pdev->xdev->dev, "claiming resource %s/%d\n", + pci_name(dev), i); + if (pci_claim_resource(dev, i)) { +- dev_err(&pdev->xdev->dev, "Could not claim " +- "resource %s/%d! Device offline. Try " +- "giving less than 4GB to domain.\n", ++ dev_err(&pdev->xdev->dev, "Could not claim resource %s/%d! " ++ "Device offline. Try using e820_host=1 in the guest config.\n", + pci_name(dev), i); + } + } +diff --git a/drivers/platform/x86/samsung-laptop.c b/drivers/platform/x86/samsung-laptop.c +index 1658575..ec85987 100644 +--- a/drivers/platform/x86/samsung-laptop.c ++++ b/drivers/platform/x86/samsung-laptop.c +@@ -370,15 +370,17 @@ static u8 read_brightness(void) + &sretval); + if (!retval) { + user_brightness = sretval.retval[0]; +- if (user_brightness != 0) ++ if (user_brightness > sabi_config->min_brightness) + user_brightness -= sabi_config->min_brightness; ++ else ++ user_brightness = 0; + } + return user_brightness; + } + + static void set_brightness(u8 user_brightness) + { +- u8 user_level = user_brightness - sabi_config->min_brightness; ++ u8 user_level = user_brightness + sabi_config->min_brightness; + + sabi_set_command(sabi_config->commands.set_brightness, user_level); + } +@@ -631,6 +633,15 @@ static struct dmi_system_id __initdata samsung_dmi_table[] = { + .callback = dmi_check_cb, + }, + { ++ .ident = "R700", ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD."), ++ DMI_MATCH(DMI_PRODUCT_NAME, "SR700"), ++ DMI_MATCH(DMI_BOARD_NAME, "SR700"), ++ }, ++ .callback = dmi_check_cb, ++ }, ++ { + .ident = "R530/R730", + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD."), +@@ -676,6 +687,24 @@ static struct dmi_system_id __initdata samsung_dmi_table[] = { + }, + .callback = dmi_check_cb, + }, ++ { ++ .ident = "X520", ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD."), ++ DMI_MATCH(DMI_PRODUCT_NAME, "X520"), ++ DMI_MATCH(DMI_BOARD_NAME, "X520"), ++ }, ++ .callback = dmi_check_cb, ++ }, ++ { ++ .ident = "R528/R728", ++ .matches = { ++ DMI_MATCH(DMI_SYS_VENDOR, "SAMSUNG ELECTRONICS CO., LTD."), ++ DMI_MATCH(DMI_PRODUCT_NAME, "R528/R728"), ++ DMI_MATCH(DMI_BOARD_NAME, "R528/R728"), ++ }, ++ .callback = dmi_check_cb, ++ }, + { }, + }; + MODULE_DEVICE_TABLE(dmi, samsung_dmi_table); +@@ -760,7 +789,7 @@ static int __init samsung_init(void) + sabi_iface = ioremap_nocache(ifaceP, 16); + if (!sabi_iface) { + pr_err("Can't remap %x\n", ifaceP); +- goto exit; ++ goto error_no_signature; + } + if (debug) { + printk(KERN_DEBUG "ifaceP = 0x%08x\n", ifaceP); +@@ -792,7 +821,8 @@ static int __init samsung_init(void) + /* create a backlight device to talk to this one */ + memset(&props, 0, sizeof(struct backlight_properties)); + props.type = BACKLIGHT_PLATFORM; +- props.max_brightness = sabi_config->max_brightness; ++ props.max_brightness = sabi_config->max_brightness - ++ sabi_config->min_brightness; + backlight_device = backlight_device_register("samsung", &sdev->dev, + NULL, &backlight_ops, + &props); +@@ -811,7 +841,6 @@ static int __init samsung_init(void) + if (retval) + goto error_file_create; + +-exit: + return 0; + + error_file_create: +diff --git a/drivers/platform/x86/wmi.c b/drivers/platform/x86/wmi.c +index f23d5a8..9b88be4 100644 +--- a/drivers/platform/x86/wmi.c ++++ b/drivers/platform/x86/wmi.c +@@ -754,9 +754,13 @@ static void wmi_free_devices(void) + struct wmi_block *wblock, *next; + + /* Delete devices for all the GUIDs */ +- list_for_each_entry_safe(wblock, next, &wmi_block_list, list) ++ list_for_each_entry_safe(wblock, next, &wmi_block_list, list) { ++ list_del(&wblock->list); + if (wblock->dev.class) + device_unregister(&wblock->dev); ++ else ++ kfree(wblock); ++ } + } + + static bool guid_already_parsed(const char *guid_string) +diff --git a/drivers/power/ds2780_battery.c b/drivers/power/ds2780_battery.c +index 1fefe82..91a783d 100644 +--- a/drivers/power/ds2780_battery.c ++++ b/drivers/power/ds2780_battery.c +@@ -39,6 +39,7 @@ struct ds2780_device_info { + struct device *dev; + struct power_supply bat; + struct device *w1_dev; ++ struct task_struct *mutex_holder; + }; + + enum current_types { +@@ -49,8 +50,8 @@ enum current_types { + static const char model[] = "DS2780"; + static const char manufacturer[] = "Maxim/Dallas"; + +-static inline struct ds2780_device_info *to_ds2780_device_info( +- struct power_supply *psy) ++static inline struct ds2780_device_info * ++to_ds2780_device_info(struct power_supply *psy) + { + return container_of(psy, struct ds2780_device_info, bat); + } +@@ -60,17 +61,28 @@ static inline struct power_supply *to_power_supply(struct device *dev) + return dev_get_drvdata(dev); + } + +-static inline int ds2780_read8(struct device *dev, u8 *val, int addr) ++static inline int ds2780_battery_io(struct ds2780_device_info *dev_info, ++ char *buf, int addr, size_t count, int io) + { +- return w1_ds2780_io(dev, val, addr, sizeof(u8), 0); ++ if (dev_info->mutex_holder == current) ++ return w1_ds2780_io_nolock(dev_info->w1_dev, buf, addr, count, io); ++ else ++ return w1_ds2780_io(dev_info->w1_dev, buf, addr, count, io); ++} ++ ++static inline int ds2780_read8(struct ds2780_device_info *dev_info, u8 *val, ++ int addr) ++{ ++ return ds2780_battery_io(dev_info, val, addr, sizeof(u8), 0); + } + +-static int ds2780_read16(struct device *dev, s16 *val, int addr) ++static int ds2780_read16(struct ds2780_device_info *dev_info, s16 *val, ++ int addr) + { + int ret; + u8 raw[2]; + +- ret = w1_ds2780_io(dev, raw, addr, sizeof(u8) * 2, 0); ++ ret = ds2780_battery_io(dev_info, raw, addr, sizeof(raw), 0); + if (ret < 0) + return ret; + +@@ -79,16 +91,16 @@ static int ds2780_read16(struct device *dev, s16 *val, int addr) + return 0; + } + +-static inline int ds2780_read_block(struct device *dev, u8 *val, int addr, +- size_t count) ++static inline int ds2780_read_block(struct ds2780_device_info *dev_info, ++ u8 *val, int addr, size_t count) + { +- return w1_ds2780_io(dev, val, addr, count, 0); ++ return ds2780_battery_io(dev_info, val, addr, count, 0); + } + +-static inline int ds2780_write(struct device *dev, u8 *val, int addr, +- size_t count) ++static inline int ds2780_write(struct ds2780_device_info *dev_info, u8 *val, ++ int addr, size_t count) + { +- return w1_ds2780_io(dev, val, addr, count, 1); ++ return ds2780_battery_io(dev_info, val, addr, count, 1); + } + + static inline int ds2780_store_eeprom(struct device *dev, int addr) +@@ -122,7 +134,7 @@ static int ds2780_set_sense_register(struct ds2780_device_info *dev_info, + { + int ret; + +- ret = ds2780_write(dev_info->w1_dev, &conductance, ++ ret = ds2780_write(dev_info, &conductance, + DS2780_RSNSP_REG, sizeof(u8)); + if (ret < 0) + return ret; +@@ -134,7 +146,7 @@ static int ds2780_set_sense_register(struct ds2780_device_info *dev_info, + static int ds2780_get_rsgain_register(struct ds2780_device_info *dev_info, + u16 *rsgain) + { +- return ds2780_read16(dev_info->w1_dev, rsgain, DS2780_RSGAIN_MSB_REG); ++ return ds2780_read16(dev_info, rsgain, DS2780_RSGAIN_MSB_REG); + } + + /* Set RSGAIN value from 0 to 1.999 in steps of 0.001 */ +@@ -144,8 +156,8 @@ static int ds2780_set_rsgain_register(struct ds2780_device_info *dev_info, + int ret; + u8 raw[] = {rsgain >> 8, rsgain & 0xFF}; + +- ret = ds2780_write(dev_info->w1_dev, raw, +- DS2780_RSGAIN_MSB_REG, sizeof(u8) * 2); ++ ret = ds2780_write(dev_info, raw, ++ DS2780_RSGAIN_MSB_REG, sizeof(raw)); + if (ret < 0) + return ret; + +@@ -167,7 +179,7 @@ static int ds2780_get_voltage(struct ds2780_device_info *dev_info, + * Bits 2 - 0 of the voltage value are in bits 7 - 5 of the + * voltage LSB register + */ +- ret = ds2780_read16(dev_info->w1_dev, &voltage_raw, ++ ret = ds2780_read16(dev_info, &voltage_raw, + DS2780_VOLT_MSB_REG); + if (ret < 0) + return ret; +@@ -196,7 +208,7 @@ static int ds2780_get_temperature(struct ds2780_device_info *dev_info, + * Bits 2 - 0 of the temperature value are in bits 7 - 5 of the + * temperature LSB register + */ +- ret = ds2780_read16(dev_info->w1_dev, &temperature_raw, ++ ret = ds2780_read16(dev_info, &temperature_raw, + DS2780_TEMP_MSB_REG); + if (ret < 0) + return ret; +@@ -222,13 +234,13 @@ static int ds2780_get_current(struct ds2780_device_info *dev_info, + * The units of measurement for current are dependent on the value of + * the sense resistor. + */ +- ret = ds2780_read8(dev_info->w1_dev, &sense_res_raw, DS2780_RSNSP_REG); ++ ret = ds2780_read8(dev_info, &sense_res_raw, DS2780_RSNSP_REG); + if (ret < 0) + return ret; + + if (sense_res_raw == 0) { + dev_err(dev_info->dev, "sense resistor value is 0\n"); +- return -ENXIO; ++ return -EINVAL; + } + sense_res = 1000 / sense_res_raw; + +@@ -248,7 +260,7 @@ static int ds2780_get_current(struct ds2780_device_info *dev_info, + * Bits 7 - 0 of the current value are in bits 7 - 0 of the current + * LSB register + */ +- ret = ds2780_read16(dev_info->w1_dev, ¤t_raw, reg_msb); ++ ret = ds2780_read16(dev_info, ¤t_raw, reg_msb); + if (ret < 0) + return ret; + +@@ -267,7 +279,7 @@ static int ds2780_get_accumulated_current(struct ds2780_device_info *dev_info, + * The units of measurement for accumulated current are dependent on + * the value of the sense resistor. + */ +- ret = ds2780_read8(dev_info->w1_dev, &sense_res_raw, DS2780_RSNSP_REG); ++ ret = ds2780_read8(dev_info, &sense_res_raw, DS2780_RSNSP_REG); + if (ret < 0) + return ret; + +@@ -285,7 +297,7 @@ static int ds2780_get_accumulated_current(struct ds2780_device_info *dev_info, + * Bits 7 - 0 of the ACR value are in bits 7 - 0 of the ACR + * LSB register + */ +- ret = ds2780_read16(dev_info->w1_dev, ¤t_raw, DS2780_ACR_MSB_REG); ++ ret = ds2780_read16(dev_info, ¤t_raw, DS2780_ACR_MSB_REG); + if (ret < 0) + return ret; + +@@ -299,7 +311,7 @@ static int ds2780_get_capacity(struct ds2780_device_info *dev_info, + int ret; + u8 raw; + +- ret = ds2780_read8(dev_info->w1_dev, &raw, DS2780_RARC_REG); ++ ret = ds2780_read8(dev_info, &raw, DS2780_RARC_REG); + if (ret < 0) + return ret; + +@@ -345,7 +357,7 @@ static int ds2780_get_charge_now(struct ds2780_device_info *dev_info, + * Bits 7 - 0 of the RAAC value are in bits 7 - 0 of the RAAC + * LSB register + */ +- ret = ds2780_read16(dev_info->w1_dev, &charge_raw, DS2780_RAAC_MSB_REG); ++ ret = ds2780_read16(dev_info, &charge_raw, DS2780_RAAC_MSB_REG); + if (ret < 0) + return ret; + +@@ -356,7 +368,7 @@ static int ds2780_get_charge_now(struct ds2780_device_info *dev_info, + static int ds2780_get_control_register(struct ds2780_device_info *dev_info, + u8 *control_reg) + { +- return ds2780_read8(dev_info->w1_dev, control_reg, DS2780_CONTROL_REG); ++ return ds2780_read8(dev_info, control_reg, DS2780_CONTROL_REG); + } + + static int ds2780_set_control_register(struct ds2780_device_info *dev_info, +@@ -364,7 +376,7 @@ static int ds2780_set_control_register(struct ds2780_device_info *dev_info, + { + int ret; + +- ret = ds2780_write(dev_info->w1_dev, &control_reg, ++ ret = ds2780_write(dev_info, &control_reg, + DS2780_CONTROL_REG, sizeof(u8)); + if (ret < 0) + return ret; +@@ -503,7 +515,7 @@ static ssize_t ds2780_get_sense_resistor_value(struct device *dev, + struct power_supply *psy = to_power_supply(dev); + struct ds2780_device_info *dev_info = to_ds2780_device_info(psy); + +- ret = ds2780_read8(dev_info->w1_dev, &sense_resistor, DS2780_RSNSP_REG); ++ ret = ds2780_read8(dev_info, &sense_resistor, DS2780_RSNSP_REG); + if (ret < 0) + return ret; + +@@ -584,7 +596,7 @@ static ssize_t ds2780_get_pio_pin(struct device *dev, + struct power_supply *psy = to_power_supply(dev); + struct ds2780_device_info *dev_info = to_ds2780_device_info(psy); + +- ret = ds2780_read8(dev_info->w1_dev, &sfr, DS2780_SFR_REG); ++ ret = ds2780_read8(dev_info, &sfr, DS2780_SFR_REG); + if (ret < 0) + return ret; + +@@ -611,7 +623,7 @@ static ssize_t ds2780_set_pio_pin(struct device *dev, + return -EINVAL; + } + +- ret = ds2780_write(dev_info->w1_dev, &new_setting, ++ ret = ds2780_write(dev_info, &new_setting, + DS2780_SFR_REG, sizeof(u8)); + if (ret < 0) + return ret; +@@ -632,7 +644,7 @@ static ssize_t ds2780_read_param_eeprom_bin(struct file *filp, + DS2780_EEPROM_BLOCK1_END - + DS2780_EEPROM_BLOCK1_START + 1 - off); + +- return ds2780_read_block(dev_info->w1_dev, buf, ++ return ds2780_read_block(dev_info, buf, + DS2780_EEPROM_BLOCK1_START + off, count); + } + +@@ -650,7 +662,7 @@ static ssize_t ds2780_write_param_eeprom_bin(struct file *filp, + DS2780_EEPROM_BLOCK1_END - + DS2780_EEPROM_BLOCK1_START + 1 - off); + +- ret = ds2780_write(dev_info->w1_dev, buf, ++ ret = ds2780_write(dev_info, buf, + DS2780_EEPROM_BLOCK1_START + off, count); + if (ret < 0) + return ret; +@@ -685,9 +697,8 @@ static ssize_t ds2780_read_user_eeprom_bin(struct file *filp, + DS2780_EEPROM_BLOCK0_END - + DS2780_EEPROM_BLOCK0_START + 1 - off); + +- return ds2780_read_block(dev_info->w1_dev, buf, ++ return ds2780_read_block(dev_info, buf, + DS2780_EEPROM_BLOCK0_START + off, count); +- + } + + static ssize_t ds2780_write_user_eeprom_bin(struct file *filp, +@@ -704,7 +715,7 @@ static ssize_t ds2780_write_user_eeprom_bin(struct file *filp, + DS2780_EEPROM_BLOCK0_END - + DS2780_EEPROM_BLOCK0_START + 1 - off); + +- ret = ds2780_write(dev_info->w1_dev, buf, ++ ret = ds2780_write(dev_info, buf, + DS2780_EEPROM_BLOCK0_START + off, count); + if (ret < 0) + return ret; +@@ -768,6 +779,7 @@ static int __devinit ds2780_battery_probe(struct platform_device *pdev) + dev_info->bat.properties = ds2780_battery_props; + dev_info->bat.num_properties = ARRAY_SIZE(ds2780_battery_props); + dev_info->bat.get_property = ds2780_battery_get_property; ++ dev_info->mutex_holder = current; + + ret = power_supply_register(&pdev->dev, &dev_info->bat); + if (ret) { +@@ -797,6 +809,8 @@ static int __devinit ds2780_battery_probe(struct platform_device *pdev) + goto fail_remove_bin_file; + } + ++ dev_info->mutex_holder = NULL; ++ + return 0; + + fail_remove_bin_file: +@@ -816,6 +830,8 @@ static int __devexit ds2780_battery_remove(struct platform_device *pdev) + { + struct ds2780_device_info *dev_info = platform_get_drvdata(pdev); + ++ dev_info->mutex_holder = current; ++ + /* remove attributes */ + sysfs_remove_group(&dev_info->bat.dev->kobj, &ds2780_attr_group); + +diff --git a/drivers/s390/cio/ccwgroup.c b/drivers/s390/cio/ccwgroup.c +index 5c56741..cda9bd6 100644 +--- a/drivers/s390/cio/ccwgroup.c ++++ b/drivers/s390/cio/ccwgroup.c +@@ -87,6 +87,12 @@ static void __ccwgroup_remove_cdev_refs(struct ccwgroup_device *gdev) + } + } + ++static ssize_t ccwgroup_online_store(struct device *dev, ++ struct device_attribute *attr, ++ const char *buf, size_t count); ++static ssize_t ccwgroup_online_show(struct device *dev, ++ struct device_attribute *attr, ++ char *buf); + /* + * Provide an 'ungroup' attribute so the user can remove group devices no + * longer needed or accidentially created. Saves memory :) +@@ -134,6 +140,20 @@ out: + } + + static DEVICE_ATTR(ungroup, 0200, NULL, ccwgroup_ungroup_store); ++static DEVICE_ATTR(online, 0644, ccwgroup_online_show, ccwgroup_online_store); ++ ++static struct attribute *ccwgroup_attrs[] = { ++ &dev_attr_online.attr, ++ &dev_attr_ungroup.attr, ++ NULL, ++}; ++static struct attribute_group ccwgroup_attr_group = { ++ .attrs = ccwgroup_attrs, ++}; ++static const struct attribute_group *ccwgroup_attr_groups[] = { ++ &ccwgroup_attr_group, ++ NULL, ++}; + + static void + ccwgroup_release (struct device *dev) +@@ -293,25 +313,17 @@ int ccwgroup_create_from_string(struct device *root, unsigned int creator_id, + } + + dev_set_name(&gdev->dev, "%s", dev_name(&gdev->cdev[0]->dev)); +- ++ gdev->dev.groups = ccwgroup_attr_groups; + rc = device_add(&gdev->dev); + if (rc) + goto error; + get_device(&gdev->dev); +- rc = device_create_file(&gdev->dev, &dev_attr_ungroup); +- +- if (rc) { +- device_unregister(&gdev->dev); +- goto error; +- } +- + rc = __ccwgroup_create_symlinks(gdev); + if (!rc) { + mutex_unlock(&gdev->reg_mutex); + put_device(&gdev->dev); + return 0; + } +- device_remove_file(&gdev->dev, &dev_attr_ungroup); + device_unregister(&gdev->dev); + error: + for (i = 0; i < num_devices; i++) +@@ -423,7 +435,7 @@ ccwgroup_online_store (struct device *dev, struct device_attribute *attr, const + int ret; + + if (!dev->driver) +- return -ENODEV; ++ return -EINVAL; + + gdev = to_ccwgroupdev(dev); + gdrv = to_ccwgroupdrv(dev->driver); +@@ -456,8 +468,6 @@ ccwgroup_online_show (struct device *dev, struct device_attribute *attr, char *b + return sprintf(buf, online ? "1\n" : "0\n"); + } + +-static DEVICE_ATTR(online, 0644, ccwgroup_online_show, ccwgroup_online_store); +- + static int + ccwgroup_probe (struct device *dev) + { +@@ -469,12 +479,7 @@ ccwgroup_probe (struct device *dev) + gdev = to_ccwgroupdev(dev); + gdrv = to_ccwgroupdrv(dev->driver); + +- if ((ret = device_create_file(dev, &dev_attr_online))) +- return ret; +- + ret = gdrv->probe ? gdrv->probe(gdev) : -ENODEV; +- if (ret) +- device_remove_file(dev, &dev_attr_online); + + return ret; + } +@@ -485,9 +490,6 @@ ccwgroup_remove (struct device *dev) + struct ccwgroup_device *gdev; + struct ccwgroup_driver *gdrv; + +- device_remove_file(dev, &dev_attr_online); +- device_remove_file(dev, &dev_attr_ungroup); +- + if (!dev->driver) + return 0; + +diff --git a/drivers/scsi/device_handler/scsi_dh.c b/drivers/scsi/device_handler/scsi_dh.c +index 0119b81..d973325 100644 +--- a/drivers/scsi/device_handler/scsi_dh.c ++++ b/drivers/scsi/device_handler/scsi_dh.c +@@ -398,7 +398,15 @@ int scsi_dh_activate(struct request_queue *q, activate_complete fn, void *data) + + spin_lock_irqsave(q->queue_lock, flags); + sdev = q->queuedata; +- if (sdev && sdev->scsi_dh_data) ++ if (!sdev) { ++ spin_unlock_irqrestore(q->queue_lock, flags); ++ err = SCSI_DH_NOSYS; ++ if (fn) ++ fn(data, err); ++ return err; ++ } ++ ++ if (sdev->scsi_dh_data) + scsi_dh = sdev->scsi_dh_data->scsi_dh; + dev = get_device(&sdev->sdev_gendev); + if (!scsi_dh || !dev || +diff --git a/drivers/scsi/hosts.c b/drivers/scsi/hosts.c +index 4f7a582..351dc0b 100644 +--- a/drivers/scsi/hosts.c ++++ b/drivers/scsi/hosts.c +@@ -286,6 +286,7 @@ static void scsi_host_dev_release(struct device *dev) + { + struct Scsi_Host *shost = dev_to_shost(dev); + struct device *parent = dev->parent; ++ struct request_queue *q; + + scsi_proc_hostdir_rm(shost->hostt); + +@@ -293,9 +294,11 @@ static void scsi_host_dev_release(struct device *dev) + kthread_stop(shost->ehandler); + if (shost->work_q) + destroy_workqueue(shost->work_q); +- if (shost->uspace_req_q) { +- kfree(shost->uspace_req_q->queuedata); +- scsi_free_queue(shost->uspace_req_q); ++ q = shost->uspace_req_q; ++ if (q) { ++ kfree(q->queuedata); ++ q->queuedata = NULL; ++ scsi_free_queue(q); + } + + scsi_destroy_command_freelist(shost); +diff --git a/drivers/scsi/hpsa.c b/drivers/scsi/hpsa.c +index 78c2e20..6689d5d 100644 +--- a/drivers/scsi/hpsa.c ++++ b/drivers/scsi/hpsa.c +@@ -3300,6 +3300,13 @@ static int hpsa_controller_hard_reset(struct pci_dev *pdev, + pmcsr &= ~PCI_PM_CTRL_STATE_MASK; + pmcsr |= PCI_D0; + pci_write_config_word(pdev, pos + PCI_PM_CTRL, pmcsr); ++ ++ /* ++ * The P600 requires a small delay when changing states. ++ * Otherwise we may think the board did not reset and we bail. ++ * This for kdump only and is particular to the P600. ++ */ ++ msleep(500); + } + return 0; + } +diff --git a/drivers/scsi/ipr.c b/drivers/scsi/ipr.c +index 888086c..c5c7c3a 100644 +--- a/drivers/scsi/ipr.c ++++ b/drivers/scsi/ipr.c +@@ -8812,7 +8812,7 @@ static int __devinit ipr_probe_ioa(struct pci_dev *pdev, + uproc = readl(ioa_cfg->regs.sense_uproc_interrupt_reg32); + if ((mask & IPR_PCII_HRRQ_UPDATED) == 0 || (uproc & IPR_UPROCI_RESET_ALERT)) + ioa_cfg->needs_hard_reset = 1; +- if (interrupts & IPR_PCII_ERROR_INTERRUPTS) ++ if ((interrupts & IPR_PCII_ERROR_INTERRUPTS) || reset_devices) + ioa_cfg->needs_hard_reset = 1; + if (interrupts & IPR_PCII_IOA_UNIT_CHECKED) + ioa_cfg->ioa_unit_checked = 1; +diff --git a/drivers/scsi/isci/isci.h b/drivers/scsi/isci/isci.h +index d1de633..8efeb6b 100644 +--- a/drivers/scsi/isci/isci.h ++++ b/drivers/scsi/isci/isci.h +@@ -97,7 +97,7 @@ + #define SCU_MAX_COMPLETION_QUEUE_SHIFT (ilog2(SCU_MAX_COMPLETION_QUEUE_ENTRIES)) + + #define SCU_ABSOLUTE_MAX_UNSOLICITED_FRAMES (4096) +-#define SCU_UNSOLICITED_FRAME_BUFFER_SIZE (1024) ++#define SCU_UNSOLICITED_FRAME_BUFFER_SIZE (1024U) + #define SCU_INVALID_FRAME_INDEX (0xFFFF) + + #define SCU_IO_REQUEST_MAX_SGE_SIZE (0x00FFFFFF) +diff --git a/drivers/scsi/isci/port_config.c b/drivers/scsi/isci/port_config.c +index 486b113..38a99d2 100644 +--- a/drivers/scsi/isci/port_config.c ++++ b/drivers/scsi/isci/port_config.c +@@ -678,7 +678,7 @@ static void apc_agent_timeout(unsigned long data) + configure_phy_mask = ~port_agent->phy_configured_mask & port_agent->phy_ready_mask; + + if (!configure_phy_mask) +- return; ++ goto done; + + for (index = 0; index < SCI_MAX_PHYS; index++) { + if ((configure_phy_mask & (1 << index)) == 0) +diff --git a/drivers/scsi/isci/request.c b/drivers/scsi/isci/request.c +index b5d3a8c..225b196 100644 +--- a/drivers/scsi/isci/request.c ++++ b/drivers/scsi/isci/request.c +@@ -1490,29 +1490,30 @@ sci_io_request_frame_handler(struct isci_request *ireq, + return SCI_SUCCESS; + + case SCI_REQ_SMP_WAIT_RESP: { +- struct smp_resp *rsp_hdr = &ireq->smp.rsp; +- void *frame_header; ++ struct sas_task *task = isci_request_access_task(ireq); ++ struct scatterlist *sg = &task->smp_task.smp_resp; ++ void *frame_header, *kaddr; ++ u8 *rsp; + + sci_unsolicited_frame_control_get_header(&ihost->uf_control, +- frame_index, +- &frame_header); +- +- /* byte swap the header. */ +- word_cnt = SMP_RESP_HDR_SZ / sizeof(u32); +- sci_swab32_cpy(rsp_hdr, frame_header, word_cnt); ++ frame_index, ++ &frame_header); ++ kaddr = kmap_atomic(sg_page(sg), KM_IRQ0); ++ rsp = kaddr + sg->offset; ++ sci_swab32_cpy(rsp, frame_header, 1); + +- if (rsp_hdr->frame_type == SMP_RESPONSE) { ++ if (rsp[0] == SMP_RESPONSE) { + void *smp_resp; + + sci_unsolicited_frame_control_get_buffer(&ihost->uf_control, +- frame_index, +- &smp_resp); ++ frame_index, ++ &smp_resp); + +- word_cnt = (sizeof(struct smp_resp) - SMP_RESP_HDR_SZ) / +- sizeof(u32); +- +- sci_swab32_cpy(((u8 *) rsp_hdr) + SMP_RESP_HDR_SZ, +- smp_resp, word_cnt); ++ word_cnt = (sg->length/4)-1; ++ if (word_cnt > 0) ++ word_cnt = min_t(unsigned int, word_cnt, ++ SCU_UNSOLICITED_FRAME_BUFFER_SIZE/4); ++ sci_swab32_cpy(rsp + 4, smp_resp, word_cnt); + + ireq->scu_status = SCU_TASK_DONE_GOOD; + ireq->sci_status = SCI_SUCCESS; +@@ -1528,12 +1529,13 @@ sci_io_request_frame_handler(struct isci_request *ireq, + __func__, + ireq, + frame_index, +- rsp_hdr->frame_type); ++ rsp[0]); + + ireq->scu_status = SCU_TASK_DONE_SMP_FRM_TYPE_ERR; + ireq->sci_status = SCI_FAILURE_CONTROLLER_SPECIFIC_IO_ERR; + sci_change_state(&ireq->sm, SCI_REQ_COMPLETED); + } ++ kunmap_atomic(kaddr, KM_IRQ0); + + sci_controller_release_frame(ihost, frame_index); + +@@ -2603,18 +2605,7 @@ static void isci_request_io_request_complete(struct isci_host *ihost, + status = SAM_STAT_GOOD; + set_bit(IREQ_COMPLETE_IN_TARGET, &request->flags); + +- if (task->task_proto == SAS_PROTOCOL_SMP) { +- void *rsp = &request->smp.rsp; +- +- dev_dbg(&ihost->pdev->dev, +- "%s: SMP protocol completion\n", +- __func__); +- +- sg_copy_from_buffer( +- &task->smp_task.smp_resp, 1, +- rsp, sizeof(struct smp_resp)); +- } else if (completion_status +- == SCI_IO_SUCCESS_IO_DONE_EARLY) { ++ if (completion_status == SCI_IO_SUCCESS_IO_DONE_EARLY) { + + /* This was an SSP / STP / SATA transfer. + * There is a possibility that less data than +diff --git a/drivers/scsi/isci/request.h b/drivers/scsi/isci/request.h +index 7a1d5a9..58d70b6 100644 +--- a/drivers/scsi/isci/request.h ++++ b/drivers/scsi/isci/request.h +@@ -174,9 +174,6 @@ struct isci_request { + }; + } ssp; + struct { +- struct smp_resp rsp; +- } smp; +- struct { + struct isci_stp_request req; + struct host_to_dev_fis cmd; + struct dev_to_host_fis rsp; +diff --git a/drivers/scsi/isci/sas.h b/drivers/scsi/isci/sas.h +index 462b151..dc26b4a 100644 +--- a/drivers/scsi/isci/sas.h ++++ b/drivers/scsi/isci/sas.h +@@ -204,8 +204,6 @@ struct smp_req { + u8 req_data[0]; + } __packed; + +-#define SMP_RESP_HDR_SZ 4 +- + /* + * struct sci_sas_address - This structure depicts how a SAS address is + * represented by SCI. +diff --git a/drivers/scsi/libsas/sas_expander.c b/drivers/scsi/libsas/sas_expander.c +index 16ad97d..37cbe4d 100644 +--- a/drivers/scsi/libsas/sas_expander.c ++++ b/drivers/scsi/libsas/sas_expander.c +@@ -199,6 +199,8 @@ static void sas_set_ex_phy(struct domain_device *dev, int phy_id, + phy->virtual = dr->virtual; + phy->last_da_index = -1; + ++ phy->phy->identify.sas_address = SAS_ADDR(phy->attached_sas_addr); ++ phy->phy->identify.device_type = phy->attached_dev_type; + phy->phy->identify.initiator_port_protocols = phy->attached_iproto; + phy->phy->identify.target_port_protocols = phy->attached_tproto; + phy->phy->identify.phy_identifier = phy_id; +diff --git a/drivers/scsi/megaraid/megaraid_sas_base.c b/drivers/scsi/megaraid/megaraid_sas_base.c +index 2d8cdce..e6e30f4 100644 +--- a/drivers/scsi/megaraid/megaraid_sas_base.c ++++ b/drivers/scsi/megaraid/megaraid_sas_base.c +@@ -1906,7 +1906,6 @@ static int megasas_generic_reset(struct scsi_cmnd *scmd) + static enum + blk_eh_timer_return megasas_reset_timer(struct scsi_cmnd *scmd) + { +- struct megasas_cmd *cmd = (struct megasas_cmd *)scmd->SCp.ptr; + struct megasas_instance *instance; + unsigned long flags; + +@@ -1915,7 +1914,7 @@ blk_eh_timer_return megasas_reset_timer(struct scsi_cmnd *scmd) + return BLK_EH_NOT_HANDLED; + } + +- instance = cmd->instance; ++ instance = (struct megasas_instance *)scmd->device->host->hostdata; + if (!(instance->flag & MEGASAS_FW_BUSY)) { + /* FW is busy, throttle IO */ + spin_lock_irqsave(instance->host->host_lock, flags); +diff --git a/drivers/scsi/mpt2sas/mpt2sas_scsih.c b/drivers/scsi/mpt2sas/mpt2sas_scsih.c +index 8dc2ad4..5690f09 100644 +--- a/drivers/scsi/mpt2sas/mpt2sas_scsih.c ++++ b/drivers/scsi/mpt2sas/mpt2sas_scsih.c +@@ -7318,22 +7318,27 @@ _scsih_probe_sas(struct MPT2SAS_ADAPTER *ioc) + /* SAS Device List */ + list_for_each_entry_safe(sas_device, next, &ioc->sas_device_init_list, + list) { +- spin_lock_irqsave(&ioc->sas_device_lock, flags); +- list_move_tail(&sas_device->list, &ioc->sas_device_list); +- spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + + if (ioc->hide_drives) + continue; + + if (!mpt2sas_transport_port_add(ioc, sas_device->handle, + sas_device->sas_address_parent)) { +- _scsih_sas_device_remove(ioc, sas_device); ++ list_del(&sas_device->list); ++ kfree(sas_device); ++ continue; + } else if (!sas_device->starget) { + mpt2sas_transport_port_remove(ioc, + sas_device->sas_address, + sas_device->sas_address_parent); +- _scsih_sas_device_remove(ioc, sas_device); ++ list_del(&sas_device->list); ++ kfree(sas_device); ++ continue; ++ + } ++ spin_lock_irqsave(&ioc->sas_device_lock, flags); ++ list_move_tail(&sas_device->list, &ioc->sas_device_list); ++ spin_unlock_irqrestore(&ioc->sas_device_lock, flags); + } + } + +diff --git a/drivers/scsi/scsi_lib.c b/drivers/scsi/scsi_lib.c +index 28d9c9d..f97acff 100644 +--- a/drivers/scsi/scsi_lib.c ++++ b/drivers/scsi/scsi_lib.c +@@ -1697,6 +1697,15 @@ struct request_queue *scsi_alloc_queue(struct scsi_device *sdev) + + void scsi_free_queue(struct request_queue *q) + { ++ unsigned long flags; ++ ++ WARN_ON(q->queuedata); ++ ++ /* cause scsi_request_fn() to kill all non-finished requests */ ++ spin_lock_irqsave(q->queue_lock, flags); ++ q->request_fn(q); ++ spin_unlock_irqrestore(q->queue_lock, flags); ++ + blk_cleanup_queue(q); + } + +diff --git a/drivers/scsi/scsi_scan.c b/drivers/scsi/scsi_scan.c +index 44e8ca3..72273a0 100644 +--- a/drivers/scsi/scsi_scan.c ++++ b/drivers/scsi/scsi_scan.c +@@ -322,6 +322,7 @@ out_device_destroy: + scsi_device_set_state(sdev, SDEV_DEL); + transport_destroy_device(&sdev->sdev_gendev); + put_device(&sdev->sdev_dev); ++ scsi_free_queue(sdev->request_queue); + put_device(&sdev->sdev_gendev); + out: + if (display_failure_msg) +diff --git a/drivers/scsi/st.c b/drivers/scsi/st.c +index 1871b8a..9b28f39 100644 +--- a/drivers/scsi/st.c ++++ b/drivers/scsi/st.c +@@ -462,14 +462,16 @@ static void st_scsi_execute_end(struct request *req, int uptodate) + { + struct st_request *SRpnt = req->end_io_data; + struct scsi_tape *STp = SRpnt->stp; ++ struct bio *tmp; + + STp->buffer->cmdstat.midlevel_result = SRpnt->result = req->errors; + STp->buffer->cmdstat.residual = req->resid_len; + ++ tmp = SRpnt->bio; + if (SRpnt->waiting) + complete(SRpnt->waiting); + +- blk_rq_unmap_user(SRpnt->bio); ++ blk_rq_unmap_user(tmp); + __blk_put_request(req->q, req); + } + +diff --git a/drivers/staging/hv/hyperv_storage.h b/drivers/staging/hv/hyperv_storage.h +index a01f9a0..5af82f4 100644 +--- a/drivers/staging/hv/hyperv_storage.h ++++ b/drivers/staging/hv/hyperv_storage.h +@@ -218,6 +218,7 @@ struct vstor_packet { + #define STORVSC_MAX_LUNS_PER_TARGET 64 + #define STORVSC_MAX_TARGETS 1 + #define STORVSC_MAX_CHANNELS 1 ++#define STORVSC_MAX_CMD_LEN 16 + + struct hv_storvsc_request; + +diff --git a/drivers/staging/hv/storvsc_drv.c b/drivers/staging/hv/storvsc_drv.c +index cb4a25b..734076b 100644 +--- a/drivers/staging/hv/storvsc_drv.c ++++ b/drivers/staging/hv/storvsc_drv.c +@@ -729,6 +729,8 @@ static int storvsc_probe(struct hv_device *device) + host->max_id = STORVSC_MAX_TARGETS; + /* max # of channels */ + host->max_channel = STORVSC_MAX_CHANNELS - 1; ++ /* max cmd length */ ++ host->max_cmd_len = STORVSC_MAX_CMD_LEN; + + /* Register the HBA and start the scsi bus scan */ + ret = scsi_add_host(host, &device->device); +diff --git a/drivers/staging/quatech_usb2/quatech_usb2.c b/drivers/staging/quatech_usb2/quatech_usb2.c +index ca098ca..02fafec 100644 +--- a/drivers/staging/quatech_usb2/quatech_usb2.c ++++ b/drivers/staging/quatech_usb2/quatech_usb2.c +@@ -916,9 +916,10 @@ static int qt2_ioctl(struct tty_struct *tty, + dbg("%s() port %d, cmd == TIOCMIWAIT enter", + __func__, port->number); + prev_msr_value = port_extra->shadowMSR & QT2_SERIAL_MSR_MASK; ++ barrier(); ++ __set_current_state(TASK_INTERRUPTIBLE); + while (1) { + add_wait_queue(&port_extra->wait, &wait); +- set_current_state(TASK_INTERRUPTIBLE); + schedule(); + dbg("%s(): port %d, cmd == TIOCMIWAIT here\n", + __func__, port->number); +@@ -926,9 +927,12 @@ static int qt2_ioctl(struct tty_struct *tty, + /* see if a signal woke us up */ + if (signal_pending(current)) + return -ERESTARTSYS; ++ set_current_state(TASK_INTERRUPTIBLE); + msr_value = port_extra->shadowMSR & QT2_SERIAL_MSR_MASK; +- if (msr_value == prev_msr_value) ++ if (msr_value == prev_msr_value) { ++ __set_current_state(TASK_RUNNING); + return -EIO; /* no change - error */ ++ } + if ((arg & TIOCM_RNG && + ((prev_msr_value & QT2_SERIAL_MSR_RI) == + (msr_value & QT2_SERIAL_MSR_RI))) || +@@ -941,6 +945,7 @@ static int qt2_ioctl(struct tty_struct *tty, + (arg & TIOCM_CTS && + ((prev_msr_value & QT2_SERIAL_MSR_CTS) == + (msr_value & QT2_SERIAL_MSR_CTS)))) { ++ __set_current_state(TASK_RUNNING); + return 0; + } + } /* end inifinite while */ +diff --git a/drivers/staging/serqt_usb2/serqt_usb2.c b/drivers/staging/serqt_usb2/serqt_usb2.c +index 12f5eba..48aa61e 100644 +--- a/drivers/staging/serqt_usb2/serqt_usb2.c ++++ b/drivers/staging/serqt_usb2/serqt_usb2.c +@@ -24,7 +24,6 @@ static int debug; + #define DRIVER_DESC "Quatech USB to Serial Driver" + + #define USB_VENDOR_ID_QUATECH 0x061d /* Quatech VID */ +-#define QUATECH_SSU100 0xC020 /* SSU100 */ + #define QUATECH_SSU200 0xC030 /* SSU200 */ + #define QUATECH_DSU100 0xC040 /* DSU100 */ + #define QUATECH_DSU200 0xC050 /* DSU200 */ +@@ -127,7 +126,6 @@ static int debug; + #define RS232_MODE 0x00 + + static const struct usb_device_id serqt_id_table[] = { +- {USB_DEVICE(USB_VENDOR_ID_QUATECH, QUATECH_SSU100)}, + {USB_DEVICE(USB_VENDOR_ID_QUATECH, QUATECH_SSU200)}, + {USB_DEVICE(USB_VENDOR_ID_QUATECH, QUATECH_DSU100)}, + {USB_DEVICE(USB_VENDOR_ID_QUATECH, QUATECH_DSU200)}, +@@ -775,7 +773,6 @@ static int qt_startup(struct usb_serial *serial) + } + + switch (serial->dev->descriptor.idProduct) { +- case QUATECH_SSU100: + case QUATECH_DSU100: + case QUATECH_QSU100: + case QUATECH_ESU100A: +diff --git a/drivers/target/loopback/tcm_loop.c b/drivers/target/loopback/tcm_loop.c +index 70c2e7f..4b5421b 100644 +--- a/drivers/target/loopback/tcm_loop.c ++++ b/drivers/target/loopback/tcm_loop.c +@@ -127,6 +127,24 @@ static struct se_cmd *tcm_loop_allocate_core_cmd( + set_host_byte(sc, DID_NO_CONNECT); + return NULL; + } ++ /* ++ * Because some userspace code via scsi-generic do not memset their ++ * associated read buffers, go ahead and do that here for type ++ * SCF_SCSI_CONTROL_SG_IO_CDB. Also note that this is currently ++ * guaranteed to be a single SGL for SCF_SCSI_CONTROL_SG_IO_CDB ++ * by target core in transport_generic_allocate_tasks() -> ++ * transport_generic_cmd_sequencer(). ++ */ ++ if (se_cmd->se_cmd_flags & SCF_SCSI_CONTROL_SG_IO_CDB && ++ se_cmd->data_direction == DMA_FROM_DEVICE) { ++ struct scatterlist *sg = scsi_sglist(sc); ++ unsigned char *buf = kmap(sg_page(sg)) + sg->offset; ++ ++ if (buf != NULL) { ++ memset(buf, 0, sg->length); ++ kunmap(sg_page(sg)); ++ } ++ } + + transport_device_setup_cmd(se_cmd); + return se_cmd; +diff --git a/drivers/target/target_core_alua.c b/drivers/target/target_core_alua.c +index 47abb42..86b3660 100644 +--- a/drivers/target/target_core_alua.c ++++ b/drivers/target/target_core_alua.c +@@ -60,11 +60,31 @@ int core_emulate_report_target_port_groups(struct se_cmd *cmd) + unsigned char *buf = (unsigned char *)T_TASK(cmd)->t_task_buf; + u32 rd_len = 0, off = 4; /* Skip over RESERVED area to first + Target port group descriptor */ ++ /* ++ * Need at least 4 bytes of response data or else we can't ++ * even fit the return data length. ++ */ ++ if (cmd->data_length < 4) { ++ pr_warn("REPORT TARGET PORT GROUPS allocation length %u" ++ " too small\n", cmd->data_length); ++ return -EINVAL; ++ } + + spin_lock(&T10_ALUA(su_dev)->tg_pt_gps_lock); + list_for_each_entry(tg_pt_gp, &T10_ALUA(su_dev)->tg_pt_gps_list, + tg_pt_gp_list) { + /* ++ * Check if the Target port group and Target port descriptor list ++ * based on tg_pt_gp_members count will fit into the response payload. ++ * Otherwise, bump rd_len to let the initiator know we have exceeded ++ * the allocation length and the response is truncated. ++ */ ++ if ((off + 8 + (tg_pt_gp->tg_pt_gp_members * 4)) > ++ cmd->data_length) { ++ rd_len += 8 + (tg_pt_gp->tg_pt_gp_members * 4); ++ continue; ++ } ++ /* + * PREF: Preferred target port bit, determine if this + * bit should be set for port group. + */ +diff --git a/drivers/tty/pty.c b/drivers/tty/pty.c +index e809e9d..e18604b 100644 +--- a/drivers/tty/pty.c ++++ b/drivers/tty/pty.c +@@ -670,12 +670,18 @@ static int ptmx_open(struct inode *inode, struct file *filp) + + nonseekable_open(inode, filp); + ++ retval = tty_alloc_file(filp); ++ if (retval) ++ return retval; ++ + /* find a device that is not in use. */ + tty_lock(); + index = devpts_new_index(inode); + tty_unlock(); +- if (index < 0) +- return index; ++ if (index < 0) { ++ retval = index; ++ goto err_file; ++ } + + mutex_lock(&tty_mutex); + tty_lock(); +@@ -689,27 +695,27 @@ static int ptmx_open(struct inode *inode, struct file *filp) + + set_bit(TTY_PTY_LOCK, &tty->flags); /* LOCK THE SLAVE */ + +- retval = tty_add_file(tty, filp); +- if (retval) +- goto out; ++ tty_add_file(tty, filp); + + retval = devpts_pty_new(inode, tty->link); + if (retval) +- goto out1; ++ goto err_release; + + retval = ptm_driver->ops->open(tty, filp); + if (retval) +- goto out2; +-out1: ++ goto err_release; ++ + tty_unlock(); +- return retval; +-out2: ++ return 0; ++err_release: + tty_unlock(); + tty_release(inode, filp); + return retval; + out: + devpts_kill_index(inode, index); + tty_unlock(); ++err_file: ++ tty_free_file(filp); + return retval; + } + +diff --git a/drivers/tty/serial/crisv10.c b/drivers/tty/serial/crisv10.c +index 225123b..58be715 100644 +--- a/drivers/tty/serial/crisv10.c ++++ b/drivers/tty/serial/crisv10.c +@@ -4450,7 +4450,7 @@ static int __init rs_init(void) + + #if defined(CONFIG_ETRAX_RS485) + #if defined(CONFIG_ETRAX_RS485_ON_PA) +- if (cris_io_interface_allocate_pins(if_ser0, 'a', rs485_pa_bit, ++ if (cris_io_interface_allocate_pins(if_serial_0, 'a', rs485_pa_bit, + rs485_pa_bit)) { + printk(KERN_CRIT "ETRAX100LX serial: Could not allocate " + "RS485 pin\n"); +@@ -4459,7 +4459,7 @@ static int __init rs_init(void) + } + #endif + #if defined(CONFIG_ETRAX_RS485_ON_PORT_G) +- if (cris_io_interface_allocate_pins(if_ser0, 'g', rs485_pa_bit, ++ if (cris_io_interface_allocate_pins(if_serial_0, 'g', rs485_pa_bit, + rs485_port_g_bit)) { + printk(KERN_CRIT "ETRAX100LX serial: Could not allocate " + "RS485 pin\n"); +diff --git a/drivers/tty/serial/jsm/jsm.h b/drivers/tty/serial/jsm/jsm.h +index b704c8c..5b837e7 100644 +--- a/drivers/tty/serial/jsm/jsm.h ++++ b/drivers/tty/serial/jsm/jsm.h +@@ -183,10 +183,8 @@ struct jsm_board + /* Our Read/Error/Write queue sizes */ + #define RQUEUEMASK 0x1FFF /* 8 K - 1 */ + #define EQUEUEMASK 0x1FFF /* 8 K - 1 */ +-#define WQUEUEMASK 0x0FFF /* 4 K - 1 */ + #define RQUEUESIZE (RQUEUEMASK + 1) + #define EQUEUESIZE RQUEUESIZE +-#define WQUEUESIZE (WQUEUEMASK + 1) + + + /************************************************************************ +@@ -226,10 +224,6 @@ struct jsm_channel { + u16 ch_e_head; /* Head location of the error queue */ + u16 ch_e_tail; /* Tail location of the error queue */ + +- u8 *ch_wqueue; /* Our write queue buffer - malloc'ed */ +- u16 ch_w_head; /* Head location of the write queue */ +- u16 ch_w_tail; /* Tail location of the write queue */ +- + u64 ch_rxcount; /* total of data received so far */ + u64 ch_txcount; /* total of data transmitted so far */ + +@@ -378,7 +372,6 @@ extern int jsm_debug; + * Prototypes for non-static functions used in more than one module + * + *************************************************************************/ +-int jsm_tty_write(struct uart_port *port); + int jsm_tty_init(struct jsm_board *); + int jsm_uart_port_init(struct jsm_board *); + int jsm_remove_uart_port(struct jsm_board *); +diff --git a/drivers/tty/serial/jsm/jsm_driver.c b/drivers/tty/serial/jsm/jsm_driver.c +index 96da178..2aaafa9 100644 +--- a/drivers/tty/serial/jsm/jsm_driver.c ++++ b/drivers/tty/serial/jsm/jsm_driver.c +@@ -211,7 +211,6 @@ static void __devexit jsm_remove_one(struct pci_dev *pdev) + if (brd->channels[i]) { + kfree(brd->channels[i]->ch_rqueue); + kfree(brd->channels[i]->ch_equeue); +- kfree(brd->channels[i]->ch_wqueue); + kfree(brd->channels[i]); + } + } +diff --git a/drivers/tty/serial/jsm/jsm_neo.c b/drivers/tty/serial/jsm/jsm_neo.c +index 4538c3e..bd6e846 100644 +--- a/drivers/tty/serial/jsm/jsm_neo.c ++++ b/drivers/tty/serial/jsm/jsm_neo.c +@@ -496,12 +496,15 @@ static void neo_copy_data_from_queue_to_uart(struct jsm_channel *ch) + int s; + int qlen; + u32 len_written = 0; ++ struct circ_buf *circ; + + if (!ch) + return; + ++ circ = &ch->uart_port.state->xmit; ++ + /* No data to write to the UART */ +- if (ch->ch_w_tail == ch->ch_w_head) ++ if (uart_circ_empty(circ)) + return; + + /* If port is "stopped", don't send any data to the UART */ +@@ -517,11 +520,10 @@ static void neo_copy_data_from_queue_to_uart(struct jsm_channel *ch) + if (ch->ch_cached_lsr & UART_LSR_THRE) { + ch->ch_cached_lsr &= ~(UART_LSR_THRE); + +- writeb(ch->ch_wqueue[ch->ch_w_tail], &ch->ch_neo_uart->txrx); ++ writeb(circ->buf[circ->tail], &ch->ch_neo_uart->txrx); + jsm_printk(WRITE, INFO, &ch->ch_bd->pci_dev, +- "Tx data: %x\n", ch->ch_wqueue[ch->ch_w_head]); +- ch->ch_w_tail++; +- ch->ch_w_tail &= WQUEUEMASK; ++ "Tx data: %x\n", circ->buf[circ->head]); ++ circ->tail = (circ->tail + 1) & (UART_XMIT_SIZE - 1); + ch->ch_txcount++; + } + return; +@@ -536,36 +538,36 @@ static void neo_copy_data_from_queue_to_uart(struct jsm_channel *ch) + n = UART_17158_TX_FIFOSIZE - ch->ch_t_tlevel; + + /* cache head and tail of queue */ +- head = ch->ch_w_head & WQUEUEMASK; +- tail = ch->ch_w_tail & WQUEUEMASK; +- qlen = (head - tail) & WQUEUEMASK; ++ head = circ->head & (UART_XMIT_SIZE - 1); ++ tail = circ->tail & (UART_XMIT_SIZE - 1); ++ qlen = uart_circ_chars_pending(circ); + + /* Find minimum of the FIFO space, versus queue length */ + n = min(n, qlen); + + while (n > 0) { + +- s = ((head >= tail) ? head : WQUEUESIZE) - tail; ++ s = ((head >= tail) ? head : UART_XMIT_SIZE) - tail; + s = min(s, n); + + if (s <= 0) + break; + +- memcpy_toio(&ch->ch_neo_uart->txrxburst, ch->ch_wqueue + tail, s); ++ memcpy_toio(&ch->ch_neo_uart->txrxburst, circ->buf + tail, s); + /* Add and flip queue if needed */ +- tail = (tail + s) & WQUEUEMASK; ++ tail = (tail + s) & (UART_XMIT_SIZE - 1); + n -= s; + ch->ch_txcount += s; + len_written += s; + } + + /* Update the final tail */ +- ch->ch_w_tail = tail & WQUEUEMASK; ++ circ->tail = tail & (UART_XMIT_SIZE - 1); + + if (len_written >= ch->ch_t_tlevel) + ch->ch_flags &= ~(CH_TX_FIFO_EMPTY | CH_TX_FIFO_LWM); + +- if (!jsm_tty_write(&ch->uart_port)) ++ if (uart_circ_empty(circ)) + uart_write_wakeup(&ch->uart_port); + } + +@@ -946,7 +948,6 @@ static void neo_param(struct jsm_channel *ch) + if ((ch->ch_c_cflag & (CBAUD)) == 0) { + ch->ch_r_head = ch->ch_r_tail = 0; + ch->ch_e_head = ch->ch_e_tail = 0; +- ch->ch_w_head = ch->ch_w_tail = 0; + + neo_flush_uart_write(ch); + neo_flush_uart_read(ch); +diff --git a/drivers/tty/serial/jsm/jsm_tty.c b/drivers/tty/serial/jsm/jsm_tty.c +index 7a4a914..434bd88 100644 +--- a/drivers/tty/serial/jsm/jsm_tty.c ++++ b/drivers/tty/serial/jsm/jsm_tty.c +@@ -118,6 +118,19 @@ static void jsm_tty_set_mctrl(struct uart_port *port, unsigned int mctrl) + udelay(10); + } + ++/* ++ * jsm_tty_write() ++ * ++ * Take data from the user or kernel and send it out to the FEP. ++ * In here exists all the Transparent Print magic as well. ++ */ ++static void jsm_tty_write(struct uart_port *port) ++{ ++ struct jsm_channel *channel; ++ channel = container_of(port, struct jsm_channel, uart_port); ++ channel->ch_bd->bd_ops->copy_data_from_queue_to_uart(channel); ++} ++ + static void jsm_tty_start_tx(struct uart_port *port) + { + struct jsm_channel *channel = (struct jsm_channel *)port; +@@ -216,14 +229,6 @@ static int jsm_tty_open(struct uart_port *port) + return -ENOMEM; + } + } +- if (!channel->ch_wqueue) { +- channel->ch_wqueue = kzalloc(WQUEUESIZE, GFP_KERNEL); +- if (!channel->ch_wqueue) { +- jsm_printk(INIT, ERR, &channel->ch_bd->pci_dev, +- "unable to allocate write queue buf"); +- return -ENOMEM; +- } +- } + + channel->ch_flags &= ~(CH_OPENING); + /* +@@ -237,7 +242,6 @@ static int jsm_tty_open(struct uart_port *port) + */ + channel->ch_r_head = channel->ch_r_tail = 0; + channel->ch_e_head = channel->ch_e_tail = 0; +- channel->ch_w_head = channel->ch_w_tail = 0; + + brd->bd_ops->flush_uart_write(channel); + brd->bd_ops->flush_uart_read(channel); +@@ -836,75 +840,3 @@ void jsm_check_queue_flow_control(struct jsm_channel *ch) + } + } + } +- +-/* +- * jsm_tty_write() +- * +- * Take data from the user or kernel and send it out to the FEP. +- * In here exists all the Transparent Print magic as well. +- */ +-int jsm_tty_write(struct uart_port *port) +-{ +- int bufcount; +- int data_count = 0,data_count1 =0; +- u16 head; +- u16 tail; +- u16 tmask; +- u32 remain; +- int temp_tail = port->state->xmit.tail; +- struct jsm_channel *channel = (struct jsm_channel *)port; +- +- tmask = WQUEUEMASK; +- head = (channel->ch_w_head) & tmask; +- tail = (channel->ch_w_tail) & tmask; +- +- if ((bufcount = tail - head - 1) < 0) +- bufcount += WQUEUESIZE; +- +- bufcount = min(bufcount, 56); +- remain = WQUEUESIZE - head; +- +- data_count = 0; +- if (bufcount >= remain) { +- bufcount -= remain; +- while ((port->state->xmit.head != temp_tail) && +- (data_count < remain)) { +- channel->ch_wqueue[head++] = +- port->state->xmit.buf[temp_tail]; +- +- temp_tail++; +- temp_tail &= (UART_XMIT_SIZE - 1); +- data_count++; +- } +- if (data_count == remain) head = 0; +- } +- +- data_count1 = 0; +- if (bufcount > 0) { +- remain = bufcount; +- while ((port->state->xmit.head != temp_tail) && +- (data_count1 < remain)) { +- channel->ch_wqueue[head++] = +- port->state->xmit.buf[temp_tail]; +- +- temp_tail++; +- temp_tail &= (UART_XMIT_SIZE - 1); +- data_count1++; +- +- } +- } +- +- port->state->xmit.tail = temp_tail; +- +- data_count += data_count1; +- if (data_count) { +- head &= tmask; +- channel->ch_w_head = head; +- } +- +- if (data_count) { +- channel->ch_bd->bd_ops->copy_data_from_queue_to_uart(channel); +- } +- +- return data_count; +-} +diff --git a/drivers/tty/serial/pxa.c b/drivers/tty/serial/pxa.c +index 4302e6e..81243a6 100644 +--- a/drivers/tty/serial/pxa.c ++++ b/drivers/tty/serial/pxa.c +@@ -100,6 +100,16 @@ static inline void receive_chars(struct uart_pxa_port *up, int *status) + int max_count = 256; + + do { ++ /* work around Errata #20 according to ++ * Intel(R) PXA27x Processor Family ++ * Specification Update (May 2005) ++ * ++ * Step 2 ++ * Disable the Reciever Time Out Interrupt via IER[RTOEI] ++ */ ++ up->ier &= ~UART_IER_RTOIE; ++ serial_out(up, UART_IER, up->ier); ++ + ch = serial_in(up, UART_RX); + flag = TTY_NORMAL; + up->port.icount.rx++; +@@ -156,6 +166,16 @@ static inline void receive_chars(struct uart_pxa_port *up, int *status) + *status = serial_in(up, UART_LSR); + } while ((*status & UART_LSR_DR) && (max_count-- > 0)); + tty_flip_buffer_push(tty); ++ ++ /* work around Errata #20 according to ++ * Intel(R) PXA27x Processor Family ++ * Specification Update (May 2005) ++ * ++ * Step 6: ++ * No more data in FIFO: Re-enable RTO interrupt via IER[RTOIE] ++ */ ++ up->ier |= UART_IER_RTOIE; ++ serial_out(up, UART_IER, up->ier); + } + + static void transmit_chars(struct uart_pxa_port *up) +diff --git a/drivers/tty/serial/serial_core.c b/drivers/tty/serial/serial_core.c +index db7912c..6bc20d7 100644 +--- a/drivers/tty/serial/serial_core.c ++++ b/drivers/tty/serial/serial_core.c +@@ -2003,6 +2003,8 @@ int uart_resume_port(struct uart_driver *drv, struct uart_port *uport) + if (port->tty && port->tty->termios && termios.c_cflag == 0) + termios = *(port->tty->termios); + ++ if (console_suspend_enabled) ++ uart_change_pm(state, 0); + uport->ops->set_termios(uport, &termios, NULL); + if (console_suspend_enabled) + console_start(uport->cons); +diff --git a/drivers/tty/tty_io.c b/drivers/tty/tty_io.c +index b6f92d3..b44aef0 100644 +--- a/drivers/tty/tty_io.c ++++ b/drivers/tty/tty_io.c +@@ -193,8 +193,7 @@ static inline struct tty_struct *file_tty(struct file *file) + return ((struct tty_file_private *)file->private_data)->tty; + } + +-/* Associate a new file with the tty structure */ +-int tty_add_file(struct tty_struct *tty, struct file *file) ++int tty_alloc_file(struct file *file) + { + struct tty_file_private *priv; + +@@ -202,15 +201,36 @@ int tty_add_file(struct tty_struct *tty, struct file *file) + if (!priv) + return -ENOMEM; + ++ file->private_data = priv; ++ ++ return 0; ++} ++ ++/* Associate a new file with the tty structure */ ++void tty_add_file(struct tty_struct *tty, struct file *file) ++{ ++ struct tty_file_private *priv = file->private_data; ++ + priv->tty = tty; + priv->file = file; +- file->private_data = priv; + + spin_lock(&tty_files_lock); + list_add(&priv->list, &tty->tty_files); + spin_unlock(&tty_files_lock); ++} + +- return 0; ++/** ++ * tty_free_file - free file->private_data ++ * ++ * This shall be used only for fail path handling when tty_add_file was not ++ * called yet. ++ */ ++void tty_free_file(struct file *file) ++{ ++ struct tty_file_private *priv = file->private_data; ++ ++ file->private_data = NULL; ++ kfree(priv); + } + + /* Delete file from its tty */ +@@ -221,8 +241,7 @@ void tty_del_file(struct file *file) + spin_lock(&tty_files_lock); + list_del(&priv->list); + spin_unlock(&tty_files_lock); +- file->private_data = NULL; +- kfree(priv); ++ tty_free_file(file); + } + + +@@ -1811,6 +1830,10 @@ static int tty_open(struct inode *inode, struct file *filp) + nonseekable_open(inode, filp); + + retry_open: ++ retval = tty_alloc_file(filp); ++ if (retval) ++ return -ENOMEM; ++ + noctty = filp->f_flags & O_NOCTTY; + index = -1; + retval = 0; +@@ -1823,6 +1846,7 @@ retry_open: + if (!tty) { + tty_unlock(); + mutex_unlock(&tty_mutex); ++ tty_free_file(filp); + return -ENXIO; + } + driver = tty_driver_kref_get(tty->driver); +@@ -1855,6 +1879,7 @@ retry_open: + } + tty_unlock(); + mutex_unlock(&tty_mutex); ++ tty_free_file(filp); + return -ENODEV; + } + +@@ -1862,6 +1887,7 @@ retry_open: + if (!driver) { + tty_unlock(); + mutex_unlock(&tty_mutex); ++ tty_free_file(filp); + return -ENODEV; + } + got_driver: +@@ -1872,6 +1898,8 @@ got_driver: + if (IS_ERR(tty)) { + tty_unlock(); + mutex_unlock(&tty_mutex); ++ tty_driver_kref_put(driver); ++ tty_free_file(filp); + return PTR_ERR(tty); + } + } +@@ -1887,15 +1915,11 @@ got_driver: + tty_driver_kref_put(driver); + if (IS_ERR(tty)) { + tty_unlock(); ++ tty_free_file(filp); + return PTR_ERR(tty); + } + +- retval = tty_add_file(tty, filp); +- if (retval) { +- tty_unlock(); +- tty_release(inode, filp); +- return retval; +- } ++ tty_add_file(tty, filp); + + check_tty_count(tty, "tty_open"); + if (tty->driver->type == TTY_DRIVER_TYPE_PTY && +diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c +index dac7676..5112f57 100644 +--- a/drivers/usb/class/cdc-acm.c ++++ b/drivers/usb/class/cdc-acm.c +@@ -1534,6 +1534,9 @@ static const struct usb_device_id acm_ids[] = { + { NOKIA_PCSUITE_ACM_INFO(0x03cd), }, /* Nokia C7 */ + { SAMSUNG_PCSUITE_ACM_INFO(0x6651), }, /* Samsung GTi8510 (INNOV8) */ + ++ /* Support for Owen devices */ ++ { USB_DEVICE(0x03eb, 0x0030), }, /* Owen SI30 */ ++ + /* NOTE: non-Nokia COMM/ACM/0xff is likely MSFT RNDIS... NOT a modem! */ + + /* Support Lego NXT using pbLua firmware */ +diff --git a/drivers/usb/core/devio.c b/drivers/usb/core/devio.c +index 37518df..0ca54e2 100644 +--- a/drivers/usb/core/devio.c ++++ b/drivers/usb/core/devio.c +@@ -407,7 +407,7 @@ static void async_completed(struct urb *urb) + sinfo.si_errno = as->status; + sinfo.si_code = SI_ASYNCIO; + sinfo.si_addr = as->userurb; +- pid = as->pid; ++ pid = get_pid(as->pid); + uid = as->uid; + euid = as->euid; + secid = as->secid; +@@ -422,9 +422,11 @@ static void async_completed(struct urb *urb) + cancel_bulk_urbs(ps, as->bulk_addr); + spin_unlock(&ps->lock); + +- if (signr) ++ if (signr) { + kill_pid_info_as_uid(sinfo.si_signo, &sinfo, pid, uid, + euid, secid); ++ put_pid(pid); ++ } + + wake_up(&ps->wait); + } +@@ -607,9 +609,10 @@ static int findintfep(struct usb_device *dev, unsigned int ep) + } + + static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, +- unsigned int index) ++ unsigned int request, unsigned int index) + { + int ret = 0; ++ struct usb_host_interface *alt_setting; + + if (ps->dev->state != USB_STATE_UNAUTHENTICATED + && ps->dev->state != USB_STATE_ADDRESS +@@ -618,6 +621,19 @@ static int check_ctrlrecip(struct dev_state *ps, unsigned int requesttype, + if (USB_TYPE_VENDOR == (USB_TYPE_MASK & requesttype)) + return 0; + ++ /* ++ * check for the special corner case 'get_device_id' in the printer ++ * class specification, where wIndex is (interface << 8 | altsetting) ++ * instead of just interface ++ */ ++ if (requesttype == 0xa1 && request == 0) { ++ alt_setting = usb_find_alt_setting(ps->dev->actconfig, ++ index >> 8, index & 0xff); ++ if (alt_setting ++ && alt_setting->desc.bInterfaceClass == USB_CLASS_PRINTER) ++ index >>= 8; ++ } ++ + index &= 0xff; + switch (requesttype & USB_RECIP_MASK) { + case USB_RECIP_ENDPOINT: +@@ -770,7 +786,8 @@ static int proc_control(struct dev_state *ps, void __user *arg) + + if (copy_from_user(&ctrl, arg, sizeof(ctrl))) + return -EFAULT; +- ret = check_ctrlrecip(ps, ctrl.bRequestType, ctrl.wIndex); ++ ret = check_ctrlrecip(ps, ctrl.bRequestType, ctrl.bRequest, ++ ctrl.wIndex); + if (ret) + return ret; + wLength = ctrl.wLength; /* To suppress 64k PAGE_SIZE warning */ +@@ -1100,7 +1117,7 @@ static int proc_do_submiturb(struct dev_state *ps, struct usbdevfs_urb *uurb, + kfree(dr); + return -EINVAL; + } +- ret = check_ctrlrecip(ps, dr->bRequestType, ++ ret = check_ctrlrecip(ps, dr->bRequestType, dr->bRequest, + le16_to_cpup(&dr->wIndex)); + if (ret) { + kfree(dr); +diff --git a/drivers/usb/core/driver.c b/drivers/usb/core/driver.c +index 34e3da5..75b4bc0 100644 +--- a/drivers/usb/core/driver.c ++++ b/drivers/usb/core/driver.c +@@ -1583,7 +1583,7 @@ int usb_autopm_get_interface_async(struct usb_interface *intf) + dev_vdbg(&intf->dev, "%s: cnt %d -> %d\n", + __func__, atomic_read(&intf->dev.power.usage_count), + status); +- if (status > 0) ++ if (status > 0 || status == -EINPROGRESS) + status = 0; + return status; + } +@@ -1668,6 +1668,11 @@ int usb_runtime_suspend(struct device *dev) + return -EAGAIN; + + status = usb_suspend_both(udev, PMSG_AUTO_SUSPEND); ++ ++ /* Allow a retry if autosuspend failed temporarily */ ++ if (status == -EAGAIN || status == -EBUSY) ++ usb_mark_last_busy(udev); ++ + /* The PM core reacts badly unless the return code is 0, + * -EAGAIN, or -EBUSY, so always return -EBUSY on an error. + */ +diff --git a/drivers/usb/core/hcd.c b/drivers/usb/core/hcd.c +index ace9f84..39ea00b 100644 +--- a/drivers/usb/core/hcd.c ++++ b/drivers/usb/core/hcd.c +@@ -1764,6 +1764,8 @@ int usb_hcd_alloc_bandwidth(struct usb_device *udev, + struct usb_interface *iface = usb_ifnum_to_if(udev, + cur_alt->desc.bInterfaceNumber); + ++ if (!iface) ++ return -EINVAL; + if (iface->resetting_device) { + /* + * The USB core just reset the device, so the xHCI host +diff --git a/drivers/usb/core/quirks.c b/drivers/usb/core/quirks.c +index 81ce6a8..d6a8d82 100644 +--- a/drivers/usb/core/quirks.c ++++ b/drivers/usb/core/quirks.c +@@ -38,6 +38,27 @@ static const struct usb_device_id usb_quirk_list[] = { + /* Creative SB Audigy 2 NX */ + { USB_DEVICE(0x041e, 0x3020), .driver_info = USB_QUIRK_RESET_RESUME }, + ++ /* Logitech Webcam C200 */ ++ { USB_DEVICE(0x046d, 0x0802), .driver_info = USB_QUIRK_RESET_RESUME }, ++ ++ /* Logitech Webcam C250 */ ++ { USB_DEVICE(0x046d, 0x0804), .driver_info = USB_QUIRK_RESET_RESUME }, ++ ++ /* Logitech Webcam C300 */ ++ { USB_DEVICE(0x046d, 0x0805), .driver_info = USB_QUIRK_RESET_RESUME }, ++ ++ /* Logitech Webcam B/C500 */ ++ { USB_DEVICE(0x046d, 0x0807), .driver_info = USB_QUIRK_RESET_RESUME }, ++ ++ /* Logitech Webcam Pro 9000 */ ++ { USB_DEVICE(0x046d, 0x0809), .driver_info = USB_QUIRK_RESET_RESUME }, ++ ++ /* Logitech Webcam C310 */ ++ { USB_DEVICE(0x046d, 0x081b), .driver_info = USB_QUIRK_RESET_RESUME }, ++ ++ /* Logitech Webcam C270 */ ++ { USB_DEVICE(0x046d, 0x0825), .driver_info = USB_QUIRK_RESET_RESUME }, ++ + /* Logitech Harmony 700-series */ + { USB_DEVICE(0x046d, 0xc122), .driver_info = USB_QUIRK_DELAY_INIT }, + +@@ -69,6 +90,9 @@ static const struct usb_device_id usb_quirk_list[] = { + { USB_DEVICE(0x06a3, 0x0006), .driver_info = + USB_QUIRK_CONFIG_INTF_STRINGS }, + ++ /* Guillemot Webcam Hercules Dualpix Exchange*/ ++ { USB_DEVICE(0x06f8, 0x0804), .driver_info = USB_QUIRK_RESET_RESUME }, ++ + /* M-Systems Flash Disk Pioneers */ + { USB_DEVICE(0x08ec, 0x1000), .driver_info = USB_QUIRK_RESET_RESUME }, + +diff --git a/drivers/usb/gadget/printer.c b/drivers/usb/gadget/printer.c +index 271ef94..88a464c 100644 +--- a/drivers/usb/gadget/printer.c ++++ b/drivers/usb/gadget/printer.c +@@ -1602,7 +1602,7 @@ cleanup(void) + if (status) + ERROR(dev, "usb_gadget_unregister_driver %x\n", status); + +- unregister_chrdev_region(g_printer_devno, 2); ++ unregister_chrdev_region(g_printer_devno, 1); + class_destroy(usb_gadget_class); + mutex_unlock(&usb_printer_gadget.lock_printer_io); + } +diff --git a/drivers/usb/host/ehci-dbg.c b/drivers/usb/host/ehci-dbg.c +index 40a844c..3e2ccb0 100644 +--- a/drivers/usb/host/ehci-dbg.c ++++ b/drivers/usb/host/ehci-dbg.c +@@ -808,7 +808,7 @@ static ssize_t fill_registers_buffer(struct debug_buffer *buf) + next += temp; + + temp = scnprintf (next, size, "uframe %04x\n", +- ehci_readl(ehci, &ehci->regs->frame_index)); ++ ehci_read_frame_index(ehci)); + size -= temp; + next += temp; + +diff --git a/drivers/usb/host/ehci-hcd.c b/drivers/usb/host/ehci-hcd.c +index 9ff9abc..b27ceab 100644 +--- a/drivers/usb/host/ehci-hcd.c ++++ b/drivers/usb/host/ehci-hcd.c +@@ -761,6 +761,35 @@ static int ehci_run (struct usb_hcd *hcd) + return 0; + } + ++static int __maybe_unused ehci_setup (struct usb_hcd *hcd) ++{ ++ struct ehci_hcd *ehci = hcd_to_ehci(hcd); ++ int retval; ++ ++ ehci->regs = (void __iomem *)ehci->caps + ++ HC_LENGTH(ehci, ehci_readl(ehci, &ehci->caps->hc_capbase)); ++ dbg_hcs_params(ehci, "reset"); ++ dbg_hcc_params(ehci, "reset"); ++ ++ /* cache this readonly data; minimize chip reads */ ++ ehci->hcs_params = ehci_readl(ehci, &ehci->caps->hcs_params); ++ ++ ehci->sbrn = HCD_USB2; ++ ++ retval = ehci_halt(ehci); ++ if (retval) ++ return retval; ++ ++ /* data structure init */ ++ retval = ehci_init(hcd); ++ if (retval) ++ return retval; ++ ++ ehci_reset(ehci); ++ ++ return 0; ++} ++ + /*-------------------------------------------------------------------------*/ + + static irqreturn_t ehci_irq (struct usb_hcd *hcd) +@@ -1159,8 +1188,7 @@ ehci_endpoint_reset(struct usb_hcd *hcd, struct usb_host_endpoint *ep) + static int ehci_get_frame (struct usb_hcd *hcd) + { + struct ehci_hcd *ehci = hcd_to_ehci (hcd); +- return (ehci_readl(ehci, &ehci->regs->frame_index) >> 3) % +- ehci->periodic_size; ++ return (ehci_read_frame_index(ehci) >> 3) % ehci->periodic_size; + } + + /*-------------------------------------------------------------------------*/ +diff --git a/drivers/usb/host/ehci-hub.c b/drivers/usb/host/ehci-hub.c +index 0f3a724..f5d7fed 100644 +--- a/drivers/usb/host/ehci-hub.c ++++ b/drivers/usb/host/ehci-hub.c +@@ -1120,7 +1120,19 @@ static int ehci_hub_control ( + if (!selector || selector > 5) + goto error; + ehci_quiesce(ehci); ++ ++ /* Put all enabled ports into suspend */ ++ while (ports--) { ++ u32 __iomem *sreg = ++ &ehci->regs->port_status[ports]; ++ ++ temp = ehci_readl(ehci, sreg) & ~PORT_RWC_BITS; ++ if (temp & PORT_PE) ++ ehci_writel(ehci, temp | PORT_SUSPEND, ++ sreg); ++ } + ehci_halt(ehci); ++ temp = ehci_readl(ehci, status_reg); + temp |= selector << 16; + ehci_writel(ehci, temp, status_reg); + break; +diff --git a/drivers/usb/host/ehci-pci.c b/drivers/usb/host/ehci-pci.c +index 1102ce6..1d1caa6 100644 +--- a/drivers/usb/host/ehci-pci.c ++++ b/drivers/usb/host/ehci-pci.c +@@ -224,6 +224,11 @@ static int ehci_pci_setup(struct usb_hcd *hcd) + pci_dev_put(p_smbus); + } + break; ++ case PCI_VENDOR_ID_NETMOS: ++ /* MosChip frame-index-register bug */ ++ ehci_info(ehci, "applying MosChip frame-index workaround\n"); ++ ehci->frame_index_bug = 1; ++ break; + } + + /* optional debug port, normally in the first BAR */ +diff --git a/drivers/usb/host/ehci-sched.c b/drivers/usb/host/ehci-sched.c +index 6c9fbe3..063c630 100644 +--- a/drivers/usb/host/ehci-sched.c ++++ b/drivers/usb/host/ehci-sched.c +@@ -36,6 +36,27 @@ + + static int ehci_get_frame (struct usb_hcd *hcd); + ++#ifdef CONFIG_PCI ++ ++static unsigned ehci_read_frame_index(struct ehci_hcd *ehci) ++{ ++ unsigned uf; ++ ++ /* ++ * The MosChip MCS9990 controller updates its microframe counter ++ * a little before the frame counter, and occasionally we will read ++ * the invalid intermediate value. Avoid problems by checking the ++ * microframe number (the low-order 3 bits); if they are 0 then ++ * re-read the register to get the correct value. ++ */ ++ uf = ehci_readl(ehci, &ehci->regs->frame_index); ++ if (unlikely(ehci->frame_index_bug && ((uf & 7) == 0))) ++ uf = ehci_readl(ehci, &ehci->regs->frame_index); ++ return uf; ++} ++ ++#endif ++ + /*-------------------------------------------------------------------------*/ + + /* +@@ -482,7 +503,7 @@ static int enable_periodic (struct ehci_hcd *ehci) + ehci_to_hcd(ehci)->state = HC_STATE_RUNNING; + + /* make sure ehci_work scans these */ +- ehci->next_uframe = ehci_readl(ehci, &ehci->regs->frame_index) ++ ehci->next_uframe = ehci_read_frame_index(ehci) + % (ehci->periodic_size << 3); + if (unlikely(ehci->broken_periodic)) + ehci->last_periodic_enable = ktime_get_real(); +@@ -1412,7 +1433,7 @@ iso_stream_schedule ( + goto fail; + } + +- now = ehci_readl(ehci, &ehci->regs->frame_index) & (mod - 1); ++ now = ehci_read_frame_index(ehci) & (mod - 1); + + /* Typical case: reuse current schedule, stream is still active. + * Hopefully there are no gaps from the host falling behind +@@ -2279,7 +2300,7 @@ scan_periodic (struct ehci_hcd *ehci) + */ + now_uframe = ehci->next_uframe; + if (HC_IS_RUNNING(ehci_to_hcd(ehci)->state)) { +- clock = ehci_readl(ehci, &ehci->regs->frame_index); ++ clock = ehci_read_frame_index(ehci); + clock_frame = (clock >> 3) & (ehci->periodic_size - 1); + } else { + clock = now_uframe + mod - 1; +@@ -2458,8 +2479,7 @@ restart: + || ehci->periodic_sched == 0) + break; + ehci->next_uframe = now_uframe; +- now = ehci_readl(ehci, &ehci->regs->frame_index) & +- (mod - 1); ++ now = ehci_read_frame_index(ehci) & (mod - 1); + if (now_uframe == now) + break; + +diff --git a/drivers/usb/host/ehci.h b/drivers/usb/host/ehci.h +index 989e0a8..3ffb27f 100644 +--- a/drivers/usb/host/ehci.h ++++ b/drivers/usb/host/ehci.h +@@ -137,6 +137,7 @@ struct ehci_hcd { /* one per controller */ + unsigned fs_i_thresh:1; /* Intel iso scheduling */ + unsigned use_dummy_qh:1; /* AMD Frame List table quirk*/ + unsigned has_synopsys_hc_bug:1; /* Synopsys HC */ ++ unsigned frame_index_bug:1; /* MosChip (AKA NetMos) */ + + /* required for usb32 quirk */ + #define OHCI_CTRL_HCFS (3 << 6) +@@ -738,6 +739,22 @@ static inline u32 hc32_to_cpup (const struct ehci_hcd *ehci, const __hc32 *x) + + /*-------------------------------------------------------------------------*/ + ++#ifdef CONFIG_PCI ++ ++/* For working around the MosChip frame-index-register bug */ ++static unsigned ehci_read_frame_index(struct ehci_hcd *ehci); ++ ++#else ++ ++static inline unsigned ehci_read_frame_index(struct ehci_hcd *ehci) ++{ ++ return ehci_readl(ehci, &ehci->regs->frame_index); ++} ++ ++#endif ++ ++/*-------------------------------------------------------------------------*/ ++ + #ifndef DEBUG + #define STUB_DEBUG_FILES + #endif /* DEBUG */ +diff --git a/drivers/usb/host/fhci-sched.c b/drivers/usb/host/fhci-sched.c +index a42ef38..2df851b 100644 +--- a/drivers/usb/host/fhci-sched.c ++++ b/drivers/usb/host/fhci-sched.c +@@ -1,7 +1,7 @@ + /* + * Freescale QUICC Engine USB Host Controller Driver + * +- * Copyright (c) Freescale Semicondutor, Inc. 2006. ++ * Copyright (c) Freescale Semicondutor, Inc. 2006, 2011. + * Shlomi Gridish <gridish@freescale.com> + * Jerry Huang <Chang-Ming.Huang@freescale.com> + * Copyright (c) Logic Product Development, Inc. 2007 +@@ -810,9 +810,11 @@ void fhci_queue_urb(struct fhci_hcd *fhci, struct urb *urb) + ed->dev_addr = usb_pipedevice(urb->pipe); + ed->max_pkt_size = usb_maxpacket(urb->dev, urb->pipe, + usb_pipeout(urb->pipe)); ++ /* setup stage */ + td = fhci_td_fill(fhci, urb, urb_priv, ed, cnt++, FHCI_TA_SETUP, + USB_TD_TOGGLE_DATA0, urb->setup_packet, 8, 0, 0, true); + ++ /* data stage */ + if (data_len > 0) { + td = fhci_td_fill(fhci, urb, urb_priv, ed, cnt++, + usb_pipeout(urb->pipe) ? FHCI_TA_OUT : +@@ -820,9 +822,18 @@ void fhci_queue_urb(struct fhci_hcd *fhci, struct urb *urb) + USB_TD_TOGGLE_DATA1, data, data_len, 0, 0, + true); + } +- td = fhci_td_fill(fhci, urb, urb_priv, ed, cnt++, +- usb_pipeout(urb->pipe) ? FHCI_TA_IN : FHCI_TA_OUT, +- USB_TD_TOGGLE_DATA1, data, 0, 0, 0, true); ++ ++ /* status stage */ ++ if (data_len > 0) ++ td = fhci_td_fill(fhci, urb, urb_priv, ed, cnt++, ++ (usb_pipeout(urb->pipe) ? FHCI_TA_IN : ++ FHCI_TA_OUT), ++ USB_TD_TOGGLE_DATA1, data, 0, 0, 0, true); ++ else ++ td = fhci_td_fill(fhci, urb, urb_priv, ed, cnt++, ++ FHCI_TA_IN, ++ USB_TD_TOGGLE_DATA1, data, 0, 0, 0, true); ++ + urb_state = US_CTRL_SETUP; + break; + case FHCI_TF_ISO: +diff --git a/drivers/usb/host/isp1760-hcd.c b/drivers/usb/host/isp1760-hcd.c +index 55d3d58..840beda 100644 +--- a/drivers/usb/host/isp1760-hcd.c ++++ b/drivers/usb/host/isp1760-hcd.c +@@ -1583,6 +1583,9 @@ static int isp1760_urb_dequeue(struct usb_hcd *hcd, struct urb *urb, + int retval = 0; + + spin_lock_irqsave(&priv->lock, spinflags); ++ retval = usb_hcd_check_unlink_urb(hcd, urb, status); ++ if (retval) ++ goto out; + + qh = urb->ep->hcpriv; + if (!qh) { +diff --git a/drivers/usb/host/ohci-hub.c b/drivers/usb/host/ohci-hub.c +index 9154615..2f00040 100644 +--- a/drivers/usb/host/ohci-hub.c ++++ b/drivers/usb/host/ohci-hub.c +@@ -356,10 +356,7 @@ static void ohci_finish_controller_resume(struct usb_hcd *hcd) + msleep(20); + } + +- /* Does the root hub have a port wakeup pending? */ +- if (ohci_readl(ohci, &ohci->regs->intrstatus) & +- (OHCI_INTR_RD | OHCI_INTR_RHSC)) +- usb_hcd_resume_root_hub(hcd); ++ usb_hcd_resume_root_hub(hcd); + } + + /* Carry out polling-, autostop-, and autoresume-related state changes */ +diff --git a/drivers/usb/host/xhci-hub.c b/drivers/usb/host/xhci-hub.c +index 723f823..ce9f974 100644 +--- a/drivers/usb/host/xhci-hub.c ++++ b/drivers/usb/host/xhci-hub.c +@@ -392,6 +392,20 @@ static int xhci_get_ports(struct usb_hcd *hcd, __le32 __iomem ***port_array) + return max_ports; + } + ++/* Test and clear port RWC bit */ ++void xhci_test_and_clear_bit(struct xhci_hcd *xhci, __le32 __iomem **port_array, ++ int port_id, u32 port_bit) ++{ ++ u32 temp; ++ ++ temp = xhci_readl(xhci, port_array[port_id]); ++ if (temp & port_bit) { ++ temp = xhci_port_state_to_neutral(temp); ++ temp |= port_bit; ++ xhci_writel(xhci, temp, port_array[port_id]); ++ } ++} ++ + int xhci_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue, + u16 wIndex, char *buf, u16 wLength) + { +@@ -938,12 +952,8 @@ int xhci_bus_resume(struct usb_hcd *hcd) + spin_lock_irqsave(&xhci->lock, flags); + + /* Clear PLC */ +- temp = xhci_readl(xhci, port_array[port_index]); +- if (temp & PORT_PLC) { +- temp = xhci_port_state_to_neutral(temp); +- temp |= PORT_PLC; +- xhci_writel(xhci, temp, port_array[port_index]); +- } ++ xhci_test_and_clear_bit(xhci, port_array, port_index, ++ PORT_PLC); + + slot_id = xhci_find_slot_id_by_port(hcd, + xhci, port_index + 1); +diff --git a/drivers/usb/host/xhci-mem.c b/drivers/usb/host/xhci-mem.c +index fcb7f7e..104620b 100644 +--- a/drivers/usb/host/xhci-mem.c ++++ b/drivers/usb/host/xhci-mem.c +@@ -81,7 +81,7 @@ static void xhci_segment_free(struct xhci_hcd *xhci, struct xhci_segment *seg) + * related flags, such as End TRB, Toggle Cycle, and no snoop. + */ + static void xhci_link_segments(struct xhci_hcd *xhci, struct xhci_segment *prev, +- struct xhci_segment *next, bool link_trbs) ++ struct xhci_segment *next, bool link_trbs, bool isoc) + { + u32 val; + +@@ -97,7 +97,9 @@ static void xhci_link_segments(struct xhci_hcd *xhci, struct xhci_segment *prev, + val &= ~TRB_TYPE_BITMASK; + val |= TRB_TYPE(TRB_LINK); + /* Always set the chain bit with 0.95 hardware */ +- if (xhci_link_trb_quirk(xhci)) ++ /* Set chain bit for isoc rings on AMD 0.96 host */ ++ if (xhci_link_trb_quirk(xhci) || ++ (isoc && (xhci->quirks & XHCI_AMD_0x96_HOST))) + val |= TRB_CHAIN; + prev->trbs[TRBS_PER_SEGMENT-1].link.control = cpu_to_le32(val); + } +@@ -112,18 +114,20 @@ void xhci_ring_free(struct xhci_hcd *xhci, struct xhci_ring *ring) + struct xhci_segment *seg; + struct xhci_segment *first_seg; + +- if (!ring || !ring->first_seg) ++ if (!ring) + return; +- first_seg = ring->first_seg; +- seg = first_seg->next; +- xhci_dbg(xhci, "Freeing ring at %p\n", ring); +- while (seg != first_seg) { +- struct xhci_segment *next = seg->next; +- xhci_segment_free(xhci, seg); +- seg = next; ++ if (ring->first_seg) { ++ first_seg = ring->first_seg; ++ seg = first_seg->next; ++ xhci_dbg(xhci, "Freeing ring at %p\n", ring); ++ while (seg != first_seg) { ++ struct xhci_segment *next = seg->next; ++ xhci_segment_free(xhci, seg); ++ seg = next; ++ } ++ xhci_segment_free(xhci, first_seg); ++ ring->first_seg = NULL; + } +- xhci_segment_free(xhci, first_seg); +- ring->first_seg = NULL; + kfree(ring); + } + +@@ -152,7 +156,7 @@ static void xhci_initialize_ring_info(struct xhci_ring *ring) + * See section 4.9.1 and figures 15 and 16. + */ + static struct xhci_ring *xhci_ring_alloc(struct xhci_hcd *xhci, +- unsigned int num_segs, bool link_trbs, gfp_t flags) ++ unsigned int num_segs, bool link_trbs, bool isoc, gfp_t flags) + { + struct xhci_ring *ring; + struct xhci_segment *prev; +@@ -178,12 +182,12 @@ static struct xhci_ring *xhci_ring_alloc(struct xhci_hcd *xhci, + next = xhci_segment_alloc(xhci, flags); + if (!next) + goto fail; +- xhci_link_segments(xhci, prev, next, link_trbs); ++ xhci_link_segments(xhci, prev, next, link_trbs, isoc); + + prev = next; + num_segs--; + } +- xhci_link_segments(xhci, prev, ring->first_seg, link_trbs); ++ xhci_link_segments(xhci, prev, ring->first_seg, link_trbs, isoc); + + if (link_trbs) { + /* See section 4.9.2.1 and 6.4.4.1 */ +@@ -229,14 +233,14 @@ void xhci_free_or_cache_endpoint_ring(struct xhci_hcd *xhci, + * pointers to the beginning of the ring. + */ + static void xhci_reinit_cached_ring(struct xhci_hcd *xhci, +- struct xhci_ring *ring) ++ struct xhci_ring *ring, bool isoc) + { + struct xhci_segment *seg = ring->first_seg; + do { + memset(seg->trbs, 0, + sizeof(union xhci_trb)*TRBS_PER_SEGMENT); + /* All endpoint rings have link TRBs */ +- xhci_link_segments(xhci, seg, seg->next, 1); ++ xhci_link_segments(xhci, seg, seg->next, 1, isoc); + seg = seg->next; + } while (seg != ring->first_seg); + xhci_initialize_ring_info(ring); +@@ -540,7 +544,7 @@ struct xhci_stream_info *xhci_alloc_stream_info(struct xhci_hcd *xhci, + */ + for (cur_stream = 1; cur_stream < num_streams; cur_stream++) { + stream_info->stream_rings[cur_stream] = +- xhci_ring_alloc(xhci, 1, true, mem_flags); ++ xhci_ring_alloc(xhci, 1, true, false, mem_flags); + cur_ring = stream_info->stream_rings[cur_stream]; + if (!cur_ring) + goto cleanup_rings; +@@ -765,7 +769,7 @@ int xhci_alloc_virt_device(struct xhci_hcd *xhci, int slot_id, + } + + /* Allocate endpoint 0 ring */ +- dev->eps[0].ring = xhci_ring_alloc(xhci, 1, true, flags); ++ dev->eps[0].ring = xhci_ring_alloc(xhci, 1, true, false, flags); + if (!dev->eps[0].ring) + goto fail; + +@@ -1175,10 +1179,10 @@ int xhci_endpoint_init(struct xhci_hcd *xhci, + */ + if (usb_endpoint_xfer_isoc(&ep->desc)) + virt_dev->eps[ep_index].new_ring = +- xhci_ring_alloc(xhci, 8, true, mem_flags); ++ xhci_ring_alloc(xhci, 8, true, true, mem_flags); + else + virt_dev->eps[ep_index].new_ring = +- xhci_ring_alloc(xhci, 1, true, mem_flags); ++ xhci_ring_alloc(xhci, 1, true, false, mem_flags); + if (!virt_dev->eps[ep_index].new_ring) { + /* Attempt to use the ring cache */ + if (virt_dev->num_rings_cached == 0) +@@ -1187,7 +1191,8 @@ int xhci_endpoint_init(struct xhci_hcd *xhci, + virt_dev->ring_cache[virt_dev->num_rings_cached]; + virt_dev->ring_cache[virt_dev->num_rings_cached] = NULL; + virt_dev->num_rings_cached--; +- xhci_reinit_cached_ring(xhci, virt_dev->eps[ep_index].new_ring); ++ xhci_reinit_cached_ring(xhci, virt_dev->eps[ep_index].new_ring, ++ usb_endpoint_xfer_isoc(&ep->desc) ? true : false); + } + virt_dev->eps[ep_index].skip = false; + ep_ring = virt_dev->eps[ep_index].new_ring; +@@ -2001,7 +2006,7 @@ int xhci_mem_init(struct xhci_hcd *xhci, gfp_t flags) + goto fail; + + /* Set up the command ring to have one segments for now. */ +- xhci->cmd_ring = xhci_ring_alloc(xhci, 1, true, flags); ++ xhci->cmd_ring = xhci_ring_alloc(xhci, 1, true, false, flags); + if (!xhci->cmd_ring) + goto fail; + xhci_dbg(xhci, "Allocated command ring at %p\n", xhci->cmd_ring); +@@ -2032,7 +2037,8 @@ int xhci_mem_init(struct xhci_hcd *xhci, gfp_t flags) + * the event ring segment table (ERST). Section 4.9.3. + */ + xhci_dbg(xhci, "// Allocating event ring\n"); +- xhci->event_ring = xhci_ring_alloc(xhci, ERST_NUM_SEGS, false, flags); ++ xhci->event_ring = xhci_ring_alloc(xhci, ERST_NUM_SEGS, false, false, ++ flags); + if (!xhci->event_ring) + goto fail; + if (xhci_check_trb_in_td_math(xhci, flags) < 0) +diff --git a/drivers/usb/host/xhci-pci.c b/drivers/usb/host/xhci-pci.c +index cb16de2..50e7156 100644 +--- a/drivers/usb/host/xhci-pci.c ++++ b/drivers/usb/host/xhci-pci.c +@@ -128,6 +128,9 @@ static int xhci_pci_setup(struct usb_hcd *hcd) + if (pdev->vendor == PCI_VENDOR_ID_NEC) + xhci->quirks |= XHCI_NEC_HOST; + ++ if (pdev->vendor == PCI_VENDOR_ID_AMD && xhci->hci_version == 0x96) ++ xhci->quirks |= XHCI_AMD_0x96_HOST; ++ + /* AMD PLL quirk */ + if (pdev->vendor == PCI_VENDOR_ID_AMD && usb_amd_find_chipset_info()) + xhci->quirks |= XHCI_AMD_PLL_FIX; +diff --git a/drivers/usb/host/xhci-ring.c b/drivers/usb/host/xhci-ring.c +index d0871ea..b20d2f7 100644 +--- a/drivers/usb/host/xhci-ring.c ++++ b/drivers/usb/host/xhci-ring.c +@@ -187,7 +187,7 @@ static void inc_deq(struct xhci_hcd *xhci, struct xhci_ring *ring, bool consumer + * prepare_transfer()? + */ + static void inc_enq(struct xhci_hcd *xhci, struct xhci_ring *ring, +- bool consumer, bool more_trbs_coming) ++ bool consumer, bool more_trbs_coming, bool isoc) + { + u32 chain; + union xhci_trb *next; +@@ -214,11 +214,13 @@ static void inc_enq(struct xhci_hcd *xhci, struct xhci_ring *ring, + if (!chain && !more_trbs_coming) + break; + +- /* If we're not dealing with 0.95 hardware, ++ /* If we're not dealing with 0.95 hardware or ++ * isoc rings on AMD 0.96 host, + * carry over the chain bit of the previous TRB + * (which may mean the chain bit is cleared). + */ +- if (!xhci_link_trb_quirk(xhci)) { ++ if (!(isoc && (xhci->quirks & XHCI_AMD_0x96_HOST)) ++ && !xhci_link_trb_quirk(xhci)) { + next->link.control &= + cpu_to_le32(~TRB_CHAIN); + next->link.control |= +@@ -1345,10 +1347,8 @@ static void handle_port_status(struct xhci_hcd *xhci, + xhci_ring_device(xhci, slot_id); + xhci_dbg(xhci, "resume SS port %d finished\n", port_id); + /* Clear PORT_PLC */ +- temp = xhci_readl(xhci, port_array[faked_port_index]); +- temp = xhci_port_state_to_neutral(temp); +- temp |= PORT_PLC; +- xhci_writel(xhci, temp, port_array[faked_port_index]); ++ xhci_test_and_clear_bit(xhci, port_array, ++ faked_port_index, PORT_PLC); + } else { + xhci_dbg(xhci, "resume HS port %d\n", port_id); + bus_state->resume_done[faked_port_index] = jiffies + +@@ -1359,6 +1359,10 @@ static void handle_port_status(struct xhci_hcd *xhci, + } + } + ++ if (hcd->speed != HCD_USB3) ++ xhci_test_and_clear_bit(xhci, port_array, faked_port_index, ++ PORT_PLC); ++ + cleanup: + /* Update event ring dequeue pointer before dropping the lock */ + inc_deq(xhci, xhci->event_ring, true); +@@ -1940,8 +1944,10 @@ static int handle_tx_event(struct xhci_hcd *xhci, + int status = -EINPROGRESS; + struct urb_priv *urb_priv; + struct xhci_ep_ctx *ep_ctx; ++ struct list_head *tmp; + u32 trb_comp_code; + int ret = 0; ++ int td_num = 0; + + slot_id = TRB_TO_SLOT_ID(le32_to_cpu(event->flags)); + xdev = xhci->devs[slot_id]; +@@ -1963,6 +1969,12 @@ static int handle_tx_event(struct xhci_hcd *xhci, + return -ENODEV; + } + ++ /* Count current td numbers if ep->skip is set */ ++ if (ep->skip) { ++ list_for_each(tmp, &ep_ring->td_list) ++ td_num++; ++ } ++ + event_dma = le64_to_cpu(event->buffer); + trb_comp_code = GET_COMP_CODE(le32_to_cpu(event->transfer_len)); + /* Look for common error cases */ +@@ -2074,7 +2086,18 @@ static int handle_tx_event(struct xhci_hcd *xhci, + goto cleanup; + } + ++ /* We've skipped all the TDs on the ep ring when ep->skip set */ ++ if (ep->skip && td_num == 0) { ++ ep->skip = false; ++ xhci_dbg(xhci, "All tds on the ep_ring skipped. " ++ "Clear skip flag.\n"); ++ ret = 0; ++ goto cleanup; ++ } ++ + td = list_entry(ep_ring->td_list.next, struct xhci_td, td_list); ++ if (ep->skip) ++ td_num--; + + /* Is this a TRB in the currently executing TD? */ + event_seg = trb_in_td(ep_ring->deq_seg, ep_ring->dequeue, +@@ -2398,7 +2421,7 @@ irqreturn_t xhci_msi_irq(int irq, struct usb_hcd *hcd) + * prepare_transfer()? + */ + static void queue_trb(struct xhci_hcd *xhci, struct xhci_ring *ring, +- bool consumer, bool more_trbs_coming, ++ bool consumer, bool more_trbs_coming, bool isoc, + u32 field1, u32 field2, u32 field3, u32 field4) + { + struct xhci_generic_trb *trb; +@@ -2408,7 +2431,7 @@ static void queue_trb(struct xhci_hcd *xhci, struct xhci_ring *ring, + trb->field[1] = cpu_to_le32(field2); + trb->field[2] = cpu_to_le32(field3); + trb->field[3] = cpu_to_le32(field4); +- inc_enq(xhci, ring, consumer, more_trbs_coming); ++ inc_enq(xhci, ring, consumer, more_trbs_coming, isoc); + } + + /* +@@ -2416,7 +2439,7 @@ static void queue_trb(struct xhci_hcd *xhci, struct xhci_ring *ring, + * FIXME allocate segments if the ring is full. + */ + static int prepare_ring(struct xhci_hcd *xhci, struct xhci_ring *ep_ring, +- u32 ep_state, unsigned int num_trbs, gfp_t mem_flags) ++ u32 ep_state, unsigned int num_trbs, bool isoc, gfp_t mem_flags) + { + /* Make sure the endpoint has been added to xHC schedule */ + switch (ep_state) { +@@ -2458,10 +2481,11 @@ static int prepare_ring(struct xhci_hcd *xhci, struct xhci_ring *ep_ring, + next = ring->enqueue; + + while (last_trb(xhci, ring, ring->enq_seg, next)) { +- /* If we're not dealing with 0.95 hardware, +- * clear the chain bit. ++ /* If we're not dealing with 0.95 hardware or isoc rings ++ * on AMD 0.96 host, clear the chain bit. + */ +- if (!xhci_link_trb_quirk(xhci)) ++ if (!xhci_link_trb_quirk(xhci) && !(isoc && ++ (xhci->quirks & XHCI_AMD_0x96_HOST))) + next->link.control &= cpu_to_le32(~TRB_CHAIN); + else + next->link.control |= cpu_to_le32(TRB_CHAIN); +@@ -2494,6 +2518,7 @@ static int prepare_transfer(struct xhci_hcd *xhci, + unsigned int num_trbs, + struct urb *urb, + unsigned int td_index, ++ bool isoc, + gfp_t mem_flags) + { + int ret; +@@ -2511,7 +2536,7 @@ static int prepare_transfer(struct xhci_hcd *xhci, + + ret = prepare_ring(xhci, ep_ring, + le32_to_cpu(ep_ctx->ep_info) & EP_STATE_MASK, +- num_trbs, mem_flags); ++ num_trbs, isoc, mem_flags); + if (ret) + return ret; + +@@ -2734,7 +2759,7 @@ static int queue_bulk_sg_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + + trb_buff_len = prepare_transfer(xhci, xhci->devs[slot_id], + ep_index, urb->stream_id, +- num_trbs, urb, 0, mem_flags); ++ num_trbs, urb, 0, false, mem_flags); + if (trb_buff_len < 0) + return trb_buff_len; + +@@ -2829,7 +2854,7 @@ static int queue_bulk_sg_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + more_trbs_coming = true; + else + more_trbs_coming = false; +- queue_trb(xhci, ep_ring, false, more_trbs_coming, ++ queue_trb(xhci, ep_ring, false, more_trbs_coming, false, + lower_32_bits(addr), + upper_32_bits(addr), + length_field, +@@ -2920,7 +2945,7 @@ int xhci_queue_bulk_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + + ret = prepare_transfer(xhci, xhci->devs[slot_id], + ep_index, urb->stream_id, +- num_trbs, urb, 0, mem_flags); ++ num_trbs, urb, 0, false, mem_flags); + if (ret < 0) + return ret; + +@@ -2992,7 +3017,7 @@ int xhci_queue_bulk_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + more_trbs_coming = true; + else + more_trbs_coming = false; +- queue_trb(xhci, ep_ring, false, more_trbs_coming, ++ queue_trb(xhci, ep_ring, false, more_trbs_coming, false, + lower_32_bits(addr), + upper_32_bits(addr), + length_field, +@@ -3052,7 +3077,7 @@ int xhci_queue_ctrl_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + num_trbs++; + ret = prepare_transfer(xhci, xhci->devs[slot_id], + ep_index, urb->stream_id, +- num_trbs, urb, 0, mem_flags); ++ num_trbs, urb, 0, false, mem_flags); + if (ret < 0) + return ret; + +@@ -3085,7 +3110,7 @@ int xhci_queue_ctrl_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + } + } + +- queue_trb(xhci, ep_ring, false, true, ++ queue_trb(xhci, ep_ring, false, true, false, + setup->bRequestType | setup->bRequest << 8 | le16_to_cpu(setup->wValue) << 16, + le16_to_cpu(setup->wIndex) | le16_to_cpu(setup->wLength) << 16, + TRB_LEN(8) | TRB_INTR_TARGET(0), +@@ -3105,7 +3130,7 @@ int xhci_queue_ctrl_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + if (urb->transfer_buffer_length > 0) { + if (setup->bRequestType & USB_DIR_IN) + field |= TRB_DIR_IN; +- queue_trb(xhci, ep_ring, false, true, ++ queue_trb(xhci, ep_ring, false, true, false, + lower_32_bits(urb->transfer_dma), + upper_32_bits(urb->transfer_dma), + length_field, +@@ -3121,7 +3146,7 @@ int xhci_queue_ctrl_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + field = 0; + else + field = TRB_DIR_IN; +- queue_trb(xhci, ep_ring, false, false, ++ queue_trb(xhci, ep_ring, false, false, false, + 0, + 0, + TRB_INTR_TARGET(0), +@@ -3270,7 +3295,8 @@ static int xhci_queue_isoc_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + trbs_per_td = count_isoc_trbs_needed(xhci, urb, i); + + ret = prepare_transfer(xhci, xhci->devs[slot_id], ep_index, +- urb->stream_id, trbs_per_td, urb, i, mem_flags); ++ urb->stream_id, trbs_per_td, urb, i, true, ++ mem_flags); + if (ret < 0) { + if (i == 0) + return ret; +@@ -3340,7 +3366,7 @@ static int xhci_queue_isoc_tx(struct xhci_hcd *xhci, gfp_t mem_flags, + remainder | + TRB_INTR_TARGET(0); + +- queue_trb(xhci, ep_ring, false, more_trbs_coming, ++ queue_trb(xhci, ep_ring, false, more_trbs_coming, true, + lower_32_bits(addr), + upper_32_bits(addr), + length_field, +@@ -3422,7 +3448,7 @@ int xhci_queue_isoc_tx_prepare(struct xhci_hcd *xhci, gfp_t mem_flags, + * Do not insert any td of the urb to the ring if the check failed. + */ + ret = prepare_ring(xhci, ep_ring, le32_to_cpu(ep_ctx->ep_info) & EP_STATE_MASK, +- num_trbs, mem_flags); ++ num_trbs, true, mem_flags); + if (ret) + return ret; + +@@ -3481,7 +3507,7 @@ static int queue_command(struct xhci_hcd *xhci, u32 field1, u32 field2, + reserved_trbs++; + + ret = prepare_ring(xhci, xhci->cmd_ring, EP_STATE_RUNNING, +- reserved_trbs, GFP_ATOMIC); ++ reserved_trbs, false, GFP_ATOMIC); + if (ret < 0) { + xhci_err(xhci, "ERR: No room for command on command ring\n"); + if (command_must_succeed) +@@ -3489,8 +3515,8 @@ static int queue_command(struct xhci_hcd *xhci, u32 field1, u32 field2, + "unfailable commands failed.\n"); + return ret; + } +- queue_trb(xhci, xhci->cmd_ring, false, false, field1, field2, field3, +- field4 | xhci->cmd_ring->cycle_state); ++ queue_trb(xhci, xhci->cmd_ring, false, false, false, field1, field2, ++ field3, field4 | xhci->cmd_ring->cycle_state); + return 0; + } + +diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c +index 7ea48b3..fb61e9d 100644 +--- a/drivers/usb/host/xhci.c ++++ b/drivers/usb/host/xhci.c +@@ -1889,6 +1889,12 @@ int xhci_check_bandwidth(struct usb_hcd *hcd, struct usb_device *udev) + ctrl_ctx->add_flags |= cpu_to_le32(SLOT_FLAG); + ctrl_ctx->add_flags &= cpu_to_le32(~EP0_FLAG); + ctrl_ctx->drop_flags &= cpu_to_le32(~(SLOT_FLAG | EP0_FLAG)); ++ ++ /* Don't issue the command if there's no endpoints to update. */ ++ if (ctrl_ctx->add_flags == cpu_to_le32(SLOT_FLAG) && ++ ctrl_ctx->drop_flags == 0) ++ return 0; ++ + xhci_dbg(xhci, "New Input Control Context:\n"); + slot_ctx = xhci_get_slot_ctx(xhci, virt_dev->in_ctx); + xhci_dbg_ctx(xhci, virt_dev->in_ctx, +diff --git a/drivers/usb/host/xhci.h b/drivers/usb/host/xhci.h +index d8bbf5c..49ce76c 100644 +--- a/drivers/usb/host/xhci.h ++++ b/drivers/usb/host/xhci.h +@@ -1311,6 +1311,7 @@ struct xhci_hcd { + #define XHCI_EP_LIMIT_QUIRK (1 << 5) + #define XHCI_BROKEN_MSI (1 << 6) + #define XHCI_RESET_ON_RESUME (1 << 7) ++#define XHCI_AMD_0x96_HOST (1 << 9) + unsigned int num_active_eps; + unsigned int limit_active_eps; + /* There are two roothubs to keep track of bus suspend info for */ +@@ -1565,6 +1566,8 @@ void xhci_ring_ep_doorbell(struct xhci_hcd *xhci, unsigned int slot_id, + unsigned int ep_index, unsigned int stream_id); + + /* xHCI roothub code */ ++void xhci_test_and_clear_bit(struct xhci_hcd *xhci, __le32 __iomem **port_array, ++ int port_id, u32 port_bit); + int xhci_hub_control(struct usb_hcd *hcd, u16 typeReq, u16 wValue, u16 wIndex, + char *buf, u16 wLength); + int xhci_hub_status_data(struct usb_hcd *hcd, char *buf); +diff --git a/drivers/usb/mon/mon_bin.c b/drivers/usb/mon/mon_bin.c +index a09dbd2..a04b2ff 100644 +--- a/drivers/usb/mon/mon_bin.c ++++ b/drivers/usb/mon/mon_bin.c +@@ -1101,7 +1101,7 @@ static long mon_bin_ioctl(struct file *file, unsigned int cmd, unsigned long arg + nevents = mon_bin_queued(rp); + + sp = (struct mon_bin_stats __user *)arg; +- if (put_user(rp->cnt_lost, &sp->dropped)) ++ if (put_user(ndropped, &sp->dropped)) + return -EFAULT; + if (put_user(nevents, &sp->queued)) + return -EFAULT; +diff --git a/drivers/usb/serial/ftdi_sio.c b/drivers/usb/serial/ftdi_sio.c +index f968a3d..1b51d43 100644 +--- a/drivers/usb/serial/ftdi_sio.c ++++ b/drivers/usb/serial/ftdi_sio.c +@@ -156,6 +156,7 @@ static struct ftdi_sio_quirk ftdi_8u2232c_quirk = { + * /sys/bus/usb/ftdi_sio/new_id, then send patch/report! + */ + static struct usb_device_id id_table_combined [] = { ++ { USB_DEVICE(FTDI_VID, FTDI_ZEITCONTROL_TAGTRACE_MIFARE_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_CTI_MINI_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_CTI_NANO_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_AMC232_PID) }, +@@ -206,6 +207,8 @@ static struct usb_device_id id_table_combined [] = { + { USB_DEVICE(FTDI_VID, FTDI_XF_640_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_XF_642_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_DSS20_PID) }, ++ { USB_DEVICE(FTDI_VID, FTDI_URBAN_0_PID) }, ++ { USB_DEVICE(FTDI_VID, FTDI_URBAN_1_PID) }, + { USB_DEVICE(FTDI_NF_RIC_VID, FTDI_NF_RIC_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_VNHCPCUSB_D_PID) }, + { USB_DEVICE(FTDI_VID, FTDI_MTXORB_0_PID) }, +@@ -744,6 +747,8 @@ static struct usb_device_id id_table_combined [] = { + .driver_info = (kernel_ulong_t)&ftdi_jtag_quirk }, + { USB_DEVICE(FTDI_VID, LMI_LM3S_EVAL_BOARD_PID), + .driver_info = (kernel_ulong_t)&ftdi_jtag_quirk }, ++ { USB_DEVICE(FTDI_VID, LMI_LM3S_ICDI_BOARD_PID), ++ .driver_info = (kernel_ulong_t)&ftdi_jtag_quirk }, + { USB_DEVICE(FTDI_VID, FTDI_TURTELIZER_PID), + .driver_info = (kernel_ulong_t)&ftdi_jtag_quirk }, + { USB_DEVICE(RATOC_VENDOR_ID, RATOC_PRODUCT_ID_USB60F) }, +diff --git a/drivers/usb/serial/ftdi_sio_ids.h b/drivers/usb/serial/ftdi_sio_ids.h +index 19156d1..571fa96 100644 +--- a/drivers/usb/serial/ftdi_sio_ids.h ++++ b/drivers/usb/serial/ftdi_sio_ids.h +@@ -54,6 +54,7 @@ + /* FTDI 2332C Dual channel device, side A=245 FIFO (JTAG), Side B=RS232 UART */ + #define LMI_LM3S_DEVEL_BOARD_PID 0xbcd8 + #define LMI_LM3S_EVAL_BOARD_PID 0xbcd9 ++#define LMI_LM3S_ICDI_BOARD_PID 0xbcda + + #define FTDI_TURTELIZER_PID 0xBDC8 /* JTAG/RS-232 adapter by egnite GmbH */ + +@@ -420,9 +421,11 @@ + #define PROTEGO_SPECIAL_4 0xFC73 /* special/unknown device */ + + /* +- * DSS-20 Sync Station for Sony Ericsson P800 ++ * Sony Ericsson product ids + */ +-#define FTDI_DSS20_PID 0xFC82 ++#define FTDI_DSS20_PID 0xFC82 /* DSS-20 Sync Station for Sony Ericsson P800 */ ++#define FTDI_URBAN_0_PID 0xFC8A /* Sony Ericsson Urban, uart #0 */ ++#define FTDI_URBAN_1_PID 0xFC8B /* Sony Ericsson Urban, uart #1 */ + + /* www.irtrans.de device */ + #define FTDI_IRTRANS_PID 0xFC60 /* Product Id */ +@@ -1159,4 +1162,8 @@ + /* USB-Nano-485*/ + #define FTDI_CTI_NANO_PID 0xF60B + +- ++/* ++ * ZeitControl cardsystems GmbH rfid-readers http://zeitconrol.de ++ */ ++/* TagTracer MIFARE*/ ++#define FTDI_ZEITCONTROL_TAGTRACE_MIFARE_PID 0xF7C0 +diff --git a/drivers/usb/serial/option.c b/drivers/usb/serial/option.c +index fe22e90..89ae1f6 100644 +--- a/drivers/usb/serial/option.c ++++ b/drivers/usb/serial/option.c +@@ -475,31 +475,54 @@ enum option_blacklist_reason { + OPTION_BLACKLIST_RESERVED_IF = 2 + }; + ++#define MAX_BL_NUM 8 + struct option_blacklist_info { +- const u32 infolen; /* number of interface numbers on blacklist */ +- const u8 *ifaceinfo; /* pointer to the array holding the numbers */ +- enum option_blacklist_reason reason; ++ /* bitfield of interface numbers for OPTION_BLACKLIST_SENDSETUP */ ++ const unsigned long sendsetup; ++ /* bitfield of interface numbers for OPTION_BLACKLIST_RESERVED_IF */ ++ const unsigned long reserved; + }; + +-static const u8 four_g_w14_no_sendsetup[] = { 0, 1 }; + static const struct option_blacklist_info four_g_w14_blacklist = { +- .infolen = ARRAY_SIZE(four_g_w14_no_sendsetup), +- .ifaceinfo = four_g_w14_no_sendsetup, +- .reason = OPTION_BLACKLIST_SENDSETUP ++ .sendsetup = BIT(0) | BIT(1), + }; + +-static const u8 alcatel_x200_no_sendsetup[] = { 0, 1 }; + static const struct option_blacklist_info alcatel_x200_blacklist = { +- .infolen = ARRAY_SIZE(alcatel_x200_no_sendsetup), +- .ifaceinfo = alcatel_x200_no_sendsetup, +- .reason = OPTION_BLACKLIST_SENDSETUP ++ .sendsetup = BIT(0) | BIT(1), ++}; ++ ++static const struct option_blacklist_info zte_0037_blacklist = { ++ .sendsetup = BIT(0) | BIT(1), + }; + +-static const u8 zte_k3765_z_no_sendsetup[] = { 0, 1, 2 }; + static const struct option_blacklist_info zte_k3765_z_blacklist = { +- .infolen = ARRAY_SIZE(zte_k3765_z_no_sendsetup), +- .ifaceinfo = zte_k3765_z_no_sendsetup, +- .reason = OPTION_BLACKLIST_SENDSETUP ++ .sendsetup = BIT(0) | BIT(1) | BIT(2), ++ .reserved = BIT(4), ++}; ++ ++static const struct option_blacklist_info huawei_cdc12_blacklist = { ++ .reserved = BIT(1) | BIT(2), ++}; ++ ++static const struct option_blacklist_info net_intf1_blacklist = { ++ .reserved = BIT(1), ++}; ++ ++static const struct option_blacklist_info net_intf3_blacklist = { ++ .reserved = BIT(3), ++}; ++ ++static const struct option_blacklist_info net_intf4_blacklist = { ++ .reserved = BIT(4), ++}; ++ ++static const struct option_blacklist_info net_intf5_blacklist = { ++ .reserved = BIT(5), ++}; ++ ++static const struct option_blacklist_info zte_mf626_blacklist = { ++ .sendsetup = BIT(0) | BIT(1), ++ .reserved = BIT(4), + }; + + static const struct usb_device_id option_ids[] = { +@@ -599,12 +622,15 @@ static const struct usb_device_id option_ids[] = { + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E143D, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E143E, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E143F, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K4505, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K3765, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K4505, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t) &huawei_cdc12_blacklist }, ++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K3765, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t) &huawei_cdc12_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_ETS1220, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_E14AC, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K3806, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K4605, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K4605, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t) &huawei_cdc12_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K3770, 0xff, 0x02, 0x31) }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K3770, 0xff, 0x02, 0x32) }, + { USB_DEVICE_AND_INTERFACE_INFO(HUAWEI_VENDOR_ID, HUAWEI_PRODUCT_K3771, 0xff, 0x02, 0x31) }, +@@ -705,7 +731,8 @@ static const struct usb_device_id option_ids[] = { + { USB_DEVICE(TELIT_VENDOR_ID, TELIT_PRODUCT_UC864E) }, + { USB_DEVICE(TELIT_VENDOR_ID, TELIT_PRODUCT_UC864G) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, ZTE_PRODUCT_MF622, 0xff, 0xff, 0xff) }, /* ZTE WCDMA products */ +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0002, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0002, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf1_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0003, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0004, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0005, 0xff, 0xff, 0xff) }, +@@ -720,51 +747,62 @@ static const struct usb_device_id option_ids[] = { + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x000f, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0010, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0011, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0012, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0012, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf1_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0013, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0014, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, ZTE_PRODUCT_MF628, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0016, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0017, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0017, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf3_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0018, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0019, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0020, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0021, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0021, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0022, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0023, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0024, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0025, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0025, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf1_blacklist }, + /* { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0026, 0xff, 0xff, 0xff) }, */ + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0028, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0029, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0030, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, ZTE_PRODUCT_MF626, 0xff, +- 0xff, 0xff), .driver_info = (kernel_ulong_t)&four_g_w14_blacklist }, ++ 0xff, 0xff), .driver_info = (kernel_ulong_t)&zte_mf626_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0032, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0033, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0034, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0037, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0037, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&zte_0037_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0038, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0039, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0040, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0042, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0042, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0043, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0044, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0048, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0049, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0049, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf5_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0050, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0051, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0052, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0052, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, + /* { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0053, 0xff, 0xff, 0xff) }, */ + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0054, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0055, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0055, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf1_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0056, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0057, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0058, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0058, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0059, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0061, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0062, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0063, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0063, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0064, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0065, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0066, 0xff, 0xff, 0xff) }, +@@ -779,11 +817,13 @@ static const struct usb_device_id option_ids[] = { + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0083, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0086, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0087, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0104, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0104, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf4_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0105, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0106, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0108, 0xff, 0xff, 0xff) }, +- { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0113, 0xff, 0xff, 0xff) }, ++ { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0113, 0xff, 0xff, 0xff), ++ .driver_info = (kernel_ulong_t)&net_intf5_blacklist }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0117, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0118, 0xff, 0xff, 0xff) }, + { USB_DEVICE_AND_INTERFACE_INFO(ZTE_VENDOR_ID, 0x0121, 0xff, 0xff, 0xff) }, +@@ -1214,10 +1254,35 @@ static void __exit option_exit(void) + module_init(option_init); + module_exit(option_exit); + ++static bool is_blacklisted(const u8 ifnum, enum option_blacklist_reason reason, ++ const struct option_blacklist_info *blacklist) ++{ ++ unsigned long num; ++ const unsigned long *intf_list; ++ ++ if (blacklist) { ++ if (reason == OPTION_BLACKLIST_SENDSETUP) ++ intf_list = &blacklist->sendsetup; ++ else if (reason == OPTION_BLACKLIST_RESERVED_IF) ++ intf_list = &blacklist->reserved; ++ else { ++ BUG_ON(reason); ++ return false; ++ } ++ ++ for_each_set_bit(num, intf_list, MAX_BL_NUM + 1) { ++ if (num == ifnum) ++ return true; ++ } ++ } ++ return false; ++} ++ + static int option_probe(struct usb_serial *serial, + const struct usb_device_id *id) + { + struct usb_wwan_intf_private *data; ++ + /* D-Link DWM 652 still exposes CD-Rom emulation interface in modem mode */ + if (serial->dev->descriptor.idVendor == DLINK_VENDOR_ID && + serial->dev->descriptor.idProduct == DLINK_PRODUCT_DWM_652 && +@@ -1230,14 +1295,14 @@ static int option_probe(struct usb_serial *serial, + serial->interface->cur_altsetting->desc.bInterfaceClass != 0xff) + return -ENODEV; + +- /* Don't bind network interfaces on Huawei K3765, K4505 & K4605 */ +- if (serial->dev->descriptor.idVendor == HUAWEI_VENDOR_ID && +- (serial->dev->descriptor.idProduct == HUAWEI_PRODUCT_K3765 || +- serial->dev->descriptor.idProduct == HUAWEI_PRODUCT_K4505 || +- serial->dev->descriptor.idProduct == HUAWEI_PRODUCT_K4605) && +- (serial->interface->cur_altsetting->desc.bInterfaceNumber == 1 || +- serial->interface->cur_altsetting->desc.bInterfaceNumber == 2)) +- return -ENODEV; ++ /* Don't bind reserved interfaces (like network ones) which often have ++ * the same class/subclass/protocol as the serial interfaces. Look at ++ * the Windows driver .INF files for reserved interface numbers. ++ */ ++ if (is_blacklisted( ++ serial->interface->cur_altsetting->desc.bInterfaceNumber, ++ OPTION_BLACKLIST_RESERVED_IF, ++ (const struct option_blacklist_info *) id->driver_info)) + + /* Don't bind network interface on Samsung GT-B3730, it is handled by a separate module */ + if (serial->dev->descriptor.idVendor == SAMSUNG_VENDOR_ID && +@@ -1246,7 +1311,6 @@ static int option_probe(struct usb_serial *serial, + return -ENODEV; + + data = serial->private = kzalloc(sizeof(struct usb_wwan_intf_private), GFP_KERNEL); +- + if (!data) + return -ENOMEM; + data->send_setup = option_send_setup; +@@ -1255,23 +1319,6 @@ static int option_probe(struct usb_serial *serial, + return 0; + } + +-static enum option_blacklist_reason is_blacklisted(const u8 ifnum, +- const struct option_blacklist_info *blacklist) +-{ +- const u8 *info; +- int i; +- +- if (blacklist) { +- info = blacklist->ifaceinfo; +- +- for (i = 0; i < blacklist->infolen; i++) { +- if (info[i] == ifnum) +- return blacklist->reason; +- } +- } +- return OPTION_BLACKLIST_NONE; +-} +- + static void option_instat_callback(struct urb *urb) + { + int err; +@@ -1343,9 +1390,8 @@ static int option_send_setup(struct usb_serial_port *port) + int val = 0; + dbg("%s", __func__); + +- if (is_blacklisted(ifNum, +- (struct option_blacklist_info *) intfdata->private) +- == OPTION_BLACKLIST_SENDSETUP) { ++ if (is_blacklisted(ifNum, OPTION_BLACKLIST_SENDSETUP, ++ (struct option_blacklist_info *) intfdata->private)) { + dbg("No send_setup on blacklisted interface #%d\n", ifNum); + return -EIO; + } +diff --git a/drivers/usb/serial/pl2303.c b/drivers/usb/serial/pl2303.c +index 1d33260..614fabc 100644 +--- a/drivers/usb/serial/pl2303.c ++++ b/drivers/usb/serial/pl2303.c +@@ -92,6 +92,7 @@ static const struct usb_device_id id_table[] = { + { USB_DEVICE(SANWA_VENDOR_ID, SANWA_PRODUCT_ID) }, + { USB_DEVICE(ADLINK_VENDOR_ID, ADLINK_ND6530_PRODUCT_ID) }, + { USB_DEVICE(WINCHIPHEAD_VENDOR_ID, WINCHIPHEAD_USBSER_PRODUCT_ID) }, ++ { USB_DEVICE(SMART_VENDOR_ID, SMART_PRODUCT_ID) }, + { } /* Terminating entry */ + }; + +diff --git a/drivers/usb/serial/pl2303.h b/drivers/usb/serial/pl2303.h +index ca0d237..3d10d7f 100644 +--- a/drivers/usb/serial/pl2303.h ++++ b/drivers/usb/serial/pl2303.h +@@ -148,3 +148,8 @@ + /* WinChipHead USB->RS 232 adapter */ + #define WINCHIPHEAD_VENDOR_ID 0x4348 + #define WINCHIPHEAD_USBSER_PRODUCT_ID 0x5523 ++ ++/* SMART USB Serial Adapter */ ++#define SMART_VENDOR_ID 0x0b8c ++#define SMART_PRODUCT_ID 0x2303 ++ +diff --git a/drivers/usb/serial/qcserial.c b/drivers/usb/serial/qcserial.c +index 27f9ae4..b9bb247 100644 +--- a/drivers/usb/serial/qcserial.c ++++ b/drivers/usb/serial/qcserial.c +@@ -28,6 +28,7 @@ static const struct usb_device_id id_table[] = { + {USB_DEVICE(0x05c6, 0x9212)}, /* Acer Gobi Modem Device */ + {USB_DEVICE(0x03f0, 0x1f1d)}, /* HP un2400 Gobi Modem Device */ + {USB_DEVICE(0x03f0, 0x201d)}, /* HP un2400 Gobi QDL Device */ ++ {USB_DEVICE(0x03f0, 0x371d)}, /* HP un2430 Mobile Broadband Module */ + {USB_DEVICE(0x04da, 0x250d)}, /* Panasonic Gobi Modem device */ + {USB_DEVICE(0x04da, 0x250c)}, /* Panasonic Gobi QDL device */ + {USB_DEVICE(0x413c, 0x8172)}, /* Dell Gobi Modem device */ +@@ -79,10 +80,12 @@ static const struct usb_device_id id_table[] = { + {USB_DEVICE(0x1199, 0x9008)}, /* Sierra Wireless Gobi 2000 Modem device (VT773) */ + {USB_DEVICE(0x1199, 0x9009)}, /* Sierra Wireless Gobi 2000 Modem device (VT773) */ + {USB_DEVICE(0x1199, 0x900a)}, /* Sierra Wireless Gobi 2000 Modem device (VT773) */ ++ {USB_DEVICE(0x1199, 0x9011)}, /* Sierra Wireless Gobi 2000 Modem device (MC8305) */ + {USB_DEVICE(0x16d8, 0x8001)}, /* CMDTech Gobi 2000 QDL device (VU922) */ + {USB_DEVICE(0x16d8, 0x8002)}, /* CMDTech Gobi 2000 Modem device (VU922) */ + {USB_DEVICE(0x05c6, 0x9204)}, /* Gobi 2000 QDL device */ + {USB_DEVICE(0x05c6, 0x9205)}, /* Gobi 2000 Modem device */ ++ {USB_DEVICE(0x1199, 0x9013)}, /* Sierra Wireless Gobi 3000 Modem device (MC8355) */ + { } /* Terminating entry */ + }; + MODULE_DEVICE_TABLE(usb, id_table); +diff --git a/drivers/usb/storage/transport.c b/drivers/usb/storage/transport.c +index e8ae21b..ff32390 100644 +--- a/drivers/usb/storage/transport.c ++++ b/drivers/usb/storage/transport.c +@@ -691,6 +691,9 @@ void usb_stor_invoke_transport(struct scsi_cmnd *srb, struct us_data *us) + int temp_result; + struct scsi_eh_save ses; + int sense_size = US_SENSE_SIZE; ++ struct scsi_sense_hdr sshdr; ++ const u8 *scdd; ++ u8 fm_ili; + + /* device supports and needs bigger sense buffer */ + if (us->fflags & US_FL_SANE_SENSE) +@@ -774,32 +777,30 @@ Retry_Sense: + srb->sense_buffer[7] = (US_SENSE_SIZE - 8); + } + ++ scsi_normalize_sense(srb->sense_buffer, SCSI_SENSE_BUFFERSIZE, ++ &sshdr); ++ + US_DEBUGP("-- Result from auto-sense is %d\n", temp_result); + US_DEBUGP("-- code: 0x%x, key: 0x%x, ASC: 0x%x, ASCQ: 0x%x\n", +- srb->sense_buffer[0], +- srb->sense_buffer[2] & 0xf, +- srb->sense_buffer[12], +- srb->sense_buffer[13]); ++ sshdr.response_code, sshdr.sense_key, ++ sshdr.asc, sshdr.ascq); + #ifdef CONFIG_USB_STORAGE_DEBUG +- usb_stor_show_sense( +- srb->sense_buffer[2] & 0xf, +- srb->sense_buffer[12], +- srb->sense_buffer[13]); ++ usb_stor_show_sense(sshdr.sense_key, sshdr.asc, sshdr.ascq); + #endif + + /* set the result so the higher layers expect this data */ + srb->result = SAM_STAT_CHECK_CONDITION; + ++ scdd = scsi_sense_desc_find(srb->sense_buffer, ++ SCSI_SENSE_BUFFERSIZE, 4); ++ fm_ili = (scdd ? scdd[3] : srb->sense_buffer[2]) & 0xA0; ++ + /* We often get empty sense data. This could indicate that + * everything worked or that there was an unspecified + * problem. We have to decide which. + */ +- if ( /* Filemark 0, ignore EOM, ILI 0, no sense */ +- (srb->sense_buffer[2] & 0xaf) == 0 && +- /* No ASC or ASCQ */ +- srb->sense_buffer[12] == 0 && +- srb->sense_buffer[13] == 0) { +- ++ if (sshdr.sense_key == 0 && sshdr.asc == 0 && sshdr.ascq == 0 && ++ fm_ili == 0) { + /* If things are really okay, then let's show that. + * Zero out the sense buffer so the higher layers + * won't realize we did an unsolicited auto-sense. +@@ -814,7 +815,10 @@ Retry_Sense: + */ + } else { + srb->result = DID_ERROR << 16; +- srb->sense_buffer[2] = HARDWARE_ERROR; ++ if ((sshdr.response_code & 0x72) == 0x72) ++ srb->sense_buffer[1] = HARDWARE_ERROR; ++ else ++ srb->sense_buffer[2] = HARDWARE_ERROR; + } + } + } +diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c +index 0ca0958..c325e69 100644 +--- a/drivers/usb/storage/usb.c ++++ b/drivers/usb/storage/usb.c +@@ -831,12 +831,22 @@ static int usb_stor_scan_thread(void * __us) + + dev_dbg(dev, "device found\n"); + +- set_freezable(); +- /* Wait for the timeout to expire or for a disconnect */ ++ set_freezable_with_signal(); ++ /* ++ * Wait for the timeout to expire or for a disconnect ++ * ++ * We can't freeze in this thread or we risk causing khubd to ++ * fail to freeze, but we can't be non-freezable either. Nor can ++ * khubd freeze while waiting for scanning to complete as it may ++ * hold the device lock, causing a hang when suspending devices. ++ * So we request a fake signal when freezing and use ++ * interruptible sleep to kick us out of our wait early when ++ * freezing happens. ++ */ + if (delay_use > 0) { + dev_dbg(dev, "waiting for device to settle " + "before scanning\n"); +- wait_event_freezable_timeout(us->delay_wait, ++ wait_event_interruptible_timeout(us->delay_wait, + test_bit(US_FLIDX_DONT_SCAN, &us->dflags), + delay_use * HZ); + } +diff --git a/drivers/video/carminefb.c b/drivers/video/carminefb.c +index caaa27d..cb09aa1f 100644 +--- a/drivers/video/carminefb.c ++++ b/drivers/video/carminefb.c +@@ -32,11 +32,11 @@ + #define CARMINEFB_DEFAULT_VIDEO_MODE 1 + + static unsigned int fb_mode = CARMINEFB_DEFAULT_VIDEO_MODE; +-module_param(fb_mode, uint, 444); ++module_param(fb_mode, uint, 0444); + MODULE_PARM_DESC(fb_mode, "Initial video mode as integer."); + + static char *fb_mode_str; +-module_param(fb_mode_str, charp, 444); ++module_param(fb_mode_str, charp, 0444); + MODULE_PARM_DESC(fb_mode_str, "Initial video mode in characters."); + + /* +@@ -46,7 +46,7 @@ MODULE_PARM_DESC(fb_mode_str, "Initial video mode in characters."); + * 0b010 Display 1 + */ + static int fb_displays = CARMINE_USE_DISPLAY0 | CARMINE_USE_DISPLAY1; +-module_param(fb_displays, int, 444); ++module_param(fb_displays, int, 0444); + MODULE_PARM_DESC(fb_displays, "Bit mode, which displays are used"); + + struct carmine_hw { +diff --git a/drivers/video/fbmem.c b/drivers/video/fbmem.c +index 5aac00e..ad93629 100644 +--- a/drivers/video/fbmem.c ++++ b/drivers/video/fbmem.c +@@ -1738,8 +1738,6 @@ void fb_set_suspend(struct fb_info *info, int state) + { + struct fb_event event; + +- if (!lock_fb_info(info)) +- return; + event.info = info; + if (state) { + fb_notifier_call_chain(FB_EVENT_SUSPEND, &event); +@@ -1748,7 +1746,6 @@ void fb_set_suspend(struct fb_info *info, int state) + info->state = FBINFO_STATE_RUNNING; + fb_notifier_call_chain(FB_EVENT_RESUME, &event); + } +- unlock_fb_info(info); + } + + /** +diff --git a/drivers/video/fbsysfs.c b/drivers/video/fbsysfs.c +index 04251ce..67afa9c 100644 +--- a/drivers/video/fbsysfs.c ++++ b/drivers/video/fbsysfs.c +@@ -399,9 +399,12 @@ static ssize_t store_fbstate(struct device *device, + + state = simple_strtoul(buf, &last, 0); + ++ if (!lock_fb_info(fb_info)) ++ return -ENODEV; + console_lock(); + fb_set_suspend(fb_info, (int)state); + console_unlock(); ++ unlock_fb_info(fb_info); + + return count; + } +diff --git a/drivers/video/sh_mobile_hdmi.c b/drivers/video/sh_mobile_hdmi.c +index 7d54e2c..647ba98 100644 +--- a/drivers/video/sh_mobile_hdmi.c ++++ b/drivers/video/sh_mobile_hdmi.c +@@ -1111,6 +1111,7 @@ static long sh_hdmi_clk_configure(struct sh_hdmi *hdmi, unsigned long hdmi_rate, + static void sh_hdmi_edid_work_fn(struct work_struct *work) + { + struct sh_hdmi *hdmi = container_of(work, struct sh_hdmi, edid_work.work); ++ struct fb_info *info; + struct sh_mobile_hdmi_info *pdata = hdmi->dev->platform_data; + struct sh_mobile_lcdc_chan *ch; + int ret; +@@ -1123,8 +1124,9 @@ static void sh_hdmi_edid_work_fn(struct work_struct *work) + + mutex_lock(&hdmi->mutex); + ++ info = hdmi->info; ++ + if (hdmi->hp_state == HDMI_HOTPLUG_CONNECTED) { +- struct fb_info *info = hdmi->info; + unsigned long parent_rate = 0, hdmi_rate; + + ret = sh_hdmi_read_edid(hdmi, &hdmi_rate, &parent_rate); +@@ -1148,42 +1150,45 @@ static void sh_hdmi_edid_work_fn(struct work_struct *work) + + ch = info->par; + +- console_lock(); ++ if (lock_fb_info(info)) { ++ console_lock(); + +- /* HDMI plug in */ +- if (!sh_hdmi_must_reconfigure(hdmi) && +- info->state == FBINFO_STATE_RUNNING) { +- /* +- * First activation with the default monitor - just turn +- * on, if we run a resume here, the logo disappears +- */ +- if (lock_fb_info(info)) { ++ /* HDMI plug in */ ++ if (!sh_hdmi_must_reconfigure(hdmi) && ++ info->state == FBINFO_STATE_RUNNING) { ++ /* ++ * First activation with the default monitor - just turn ++ * on, if we run a resume here, the logo disappears ++ */ + info->var.width = hdmi->var.width; + info->var.height = hdmi->var.height; + sh_hdmi_display_on(hdmi, info); +- unlock_fb_info(info); ++ } else { ++ /* New monitor or have to wake up */ ++ fb_set_suspend(info, 0); + } +- } else { +- /* New monitor or have to wake up */ +- fb_set_suspend(info, 0); +- } + +- console_unlock(); ++ console_unlock(); ++ unlock_fb_info(info); ++ } + } else { + ret = 0; +- if (!hdmi->info) ++ if (!info) + goto out; + + hdmi->monspec.modedb_len = 0; + fb_destroy_modedb(hdmi->monspec.modedb); + hdmi->monspec.modedb = NULL; + +- console_lock(); ++ if (lock_fb_info(info)) { ++ console_lock(); + +- /* HDMI disconnect */ +- fb_set_suspend(hdmi->info, 1); ++ /* HDMI disconnect */ ++ fb_set_suspend(info, 1); + +- console_unlock(); ++ console_unlock(); ++ unlock_fb_info(info); ++ } + } + + out: +diff --git a/drivers/video/via/via_modesetting.h b/drivers/video/via/via_modesetting.h +index ae35cfd..0138845 100644 +--- a/drivers/video/via/via_modesetting.h ++++ b/drivers/video/via/via_modesetting.h +@@ -28,6 +28,11 @@ + + #include <linux/types.h> + ++ ++#define VIA_PITCH_SIZE (1<<3) ++#define VIA_PITCH_MAX 0x3FF8 ++ ++ + void via_set_primary_address(u32 addr); + void via_set_secondary_address(u32 addr); + void via_set_primary_pitch(u32 pitch); +diff --git a/drivers/video/via/viafbdev.c b/drivers/video/via/viafbdev.c +index cf43c80..dd1276e 100644 +--- a/drivers/video/via/viafbdev.c ++++ b/drivers/video/via/viafbdev.c +@@ -151,7 +151,8 @@ static void viafb_update_fix(struct fb_info *info) + + info->fix.visual = + bpp == 8 ? FB_VISUAL_PSEUDOCOLOR : FB_VISUAL_TRUECOLOR; +- info->fix.line_length = (info->var.xres_virtual * bpp / 8 + 7) & ~7; ++ info->fix.line_length = ALIGN(info->var.xres_virtual * bpp / 8, ++ VIA_PITCH_SIZE); + } + + static void viafb_setup_fixinfo(struct fb_fix_screeninfo *fix, +@@ -238,8 +239,12 @@ static int viafb_check_var(struct fb_var_screeninfo *var, + depth = 24; + + viafb_fill_var_color_info(var, depth); +- line = (var->xres_virtual * var->bits_per_pixel / 8 + 7) & ~7; +- if (line * var->yres_virtual > ppar->memsize) ++ if (var->xres_virtual < var->xres) ++ var->xres_virtual = var->xres; ++ ++ line = ALIGN(var->xres_virtual * var->bits_per_pixel / 8, ++ VIA_PITCH_SIZE); ++ if (line > VIA_PITCH_MAX || line * var->yres_virtual > ppar->memsize) + return -EINVAL; + + /* Based on var passed in to calculate the refresh, +@@ -348,8 +353,9 @@ static int viafb_pan_display(struct fb_var_screeninfo *var, + struct fb_info *info) + { + struct viafb_par *viapar = info->par; +- u32 vram_addr = (var->yoffset * var->xres_virtual + var->xoffset) +- * (var->bits_per_pixel / 8) + viapar->vram_addr; ++ u32 vram_addr = viapar->vram_addr ++ + var->yoffset * info->fix.line_length ++ + var->xoffset * info->var.bits_per_pixel / 8; + + DEBUG_MSG(KERN_DEBUG "viafb_pan_display, address = %d\n", vram_addr); + if (!viafb_dual_fb) { +diff --git a/drivers/w1/slaves/w1_ds2780.c b/drivers/w1/slaves/w1_ds2780.c +index 274c8f3..505b17d 100644 +--- a/drivers/w1/slaves/w1_ds2780.c ++++ b/drivers/w1/slaves/w1_ds2780.c +@@ -26,20 +26,14 @@ + #include "../w1_family.h" + #include "w1_ds2780.h" + +-int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count, +- int io) ++static int w1_ds2780_do_io(struct device *dev, char *buf, int addr, ++ size_t count, int io) + { + struct w1_slave *sl = container_of(dev, struct w1_slave, dev); + +- if (!dev) +- return -ENODEV; ++ if (addr > DS2780_DATA_SIZE || addr < 0) ++ return 0; + +- mutex_lock(&sl->master->mutex); +- +- if (addr > DS2780_DATA_SIZE || addr < 0) { +- count = 0; +- goto out; +- } + count = min_t(int, count, DS2780_DATA_SIZE - addr); + + if (w1_reset_select_slave(sl) == 0) { +@@ -47,7 +41,6 @@ int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count, + w1_write_8(sl->master, W1_DS2780_WRITE_DATA); + w1_write_8(sl->master, addr); + w1_write_block(sl->master, buf, count); +- /* XXX w1_write_block returns void, not n_written */ + } else { + w1_write_8(sl->master, W1_DS2780_READ_DATA); + w1_write_8(sl->master, addr); +@@ -55,13 +48,42 @@ int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count, + } + } + +-out: ++ return count; ++} ++ ++int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count, ++ int io) ++{ ++ struct w1_slave *sl = container_of(dev, struct w1_slave, dev); ++ int ret; ++ ++ if (!dev) ++ return -ENODEV; ++ ++ mutex_lock(&sl->master->mutex); ++ ++ ret = w1_ds2780_do_io(dev, buf, addr, count, io); ++ + mutex_unlock(&sl->master->mutex); + +- return count; ++ return ret; + } + EXPORT_SYMBOL(w1_ds2780_io); + ++int w1_ds2780_io_nolock(struct device *dev, char *buf, int addr, size_t count, ++ int io) ++{ ++ int ret; ++ ++ if (!dev) ++ return -ENODEV; ++ ++ ret = w1_ds2780_do_io(dev, buf, addr, count, io); ++ ++ return ret; ++} ++EXPORT_SYMBOL(w1_ds2780_io_nolock); ++ + int w1_ds2780_eeprom_cmd(struct device *dev, int addr, int cmd) + { + struct w1_slave *sl = container_of(dev, struct w1_slave, dev); +diff --git a/drivers/w1/slaves/w1_ds2780.h b/drivers/w1/slaves/w1_ds2780.h +index a1fba79..7373793 100644 +--- a/drivers/w1/slaves/w1_ds2780.h ++++ b/drivers/w1/slaves/w1_ds2780.h +@@ -124,6 +124,8 @@ + + extern int w1_ds2780_io(struct device *dev, char *buf, int addr, size_t count, + int io); ++extern int w1_ds2780_io_nolock(struct device *dev, char *buf, int addr, ++ size_t count, int io); + extern int w1_ds2780_eeprom_cmd(struct device *dev, int addr, int cmd); + + #endif /* !_W1_DS2780_H */ +diff --git a/drivers/xen/events.c b/drivers/xen/events.c +index 30df85d..a5493f8 100644 +--- a/drivers/xen/events.c ++++ b/drivers/xen/events.c +@@ -1026,7 +1026,7 @@ int bind_ipi_to_irqhandler(enum ipi_vector ipi, + if (irq < 0) + return irq; + +- irqflags |= IRQF_NO_SUSPEND | IRQF_FORCE_RESUME; ++ irqflags |= IRQF_NO_SUSPEND | IRQF_FORCE_RESUME | IRQF_EARLY_RESUME; + retval = request_irq(irq, handler, irqflags, devname, dev_id); + if (retval != 0) { + unbind_from_irq(irq); +diff --git a/drivers/xen/swiotlb-xen.c b/drivers/xen/swiotlb-xen.c +index 6e8c15a..84f317e 100644 +--- a/drivers/xen/swiotlb-xen.c ++++ b/drivers/xen/swiotlb-xen.c +@@ -278,9 +278,10 @@ dma_addr_t xen_swiotlb_map_page(struct device *dev, struct page *page, + /* + * Ensure that the address returned is DMA'ble + */ +- if (!dma_capable(dev, dev_addr, size)) +- panic("map_single: bounce buffer is not DMA'ble"); +- ++ if (!dma_capable(dev, dev_addr, size)) { ++ swiotlb_tbl_unmap_single(dev, map, size, dir); ++ dev_addr = 0; ++ } + return dev_addr; + } + EXPORT_SYMBOL_GPL(xen_swiotlb_map_page); +diff --git a/fs/binfmt_elf.c b/fs/binfmt_elf.c +index 303983f..9ba2ac7 100644 +--- a/fs/binfmt_elf.c ++++ b/fs/binfmt_elf.c +@@ -796,7 +796,16 @@ static int load_elf_binary(struct linux_binprm *bprm, struct pt_regs *regs) + * might try to exec. This is because the brk will + * follow the loader, and is not movable. */ + #if defined(CONFIG_X86) || defined(CONFIG_ARM) +- load_bias = 0; ++ /* Memory randomization might have been switched off ++ * in runtime via sysctl. ++ * If that is the case, retain the original non-zero ++ * load_bias value in order to establish proper ++ * non-randomized mappings. ++ */ ++ if (current->flags & PF_RANDOMIZE) ++ load_bias = 0; ++ else ++ load_bias = ELF_PAGESTART(ELF_ET_DYN_BASE - vaddr); + #else + load_bias = ELF_PAGESTART(ELF_ET_DYN_BASE - vaddr); + #endif +diff --git a/fs/block_dev.c b/fs/block_dev.c +index 194cf66..34503ba 100644 +--- a/fs/block_dev.c ++++ b/fs/block_dev.c +@@ -1075,6 +1075,7 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part); + static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) + { + struct gendisk *disk; ++ struct module *owner; + int ret; + int partno; + int perm = 0; +@@ -1100,6 +1101,7 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) + disk = get_gendisk(bdev->bd_dev, &partno); + if (!disk) + goto out; ++ owner = disk->fops->owner; + + disk_block_events(disk); + mutex_lock_nested(&bdev->bd_mutex, for_part); +@@ -1127,8 +1129,8 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) + bdev->bd_disk = NULL; + mutex_unlock(&bdev->bd_mutex); + disk_unblock_events(disk); +- module_put(disk->fops->owner); + put_disk(disk); ++ module_put(owner); + goto restart; + } + } +@@ -1184,8 +1186,8 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) + goto out_unlock_bdev; + } + /* only one opener holds refs to the module and disk */ +- module_put(disk->fops->owner); + put_disk(disk); ++ module_put(owner); + } + bdev->bd_openers++; + if (for_part) +@@ -1205,8 +1207,8 @@ static int __blkdev_get(struct block_device *bdev, fmode_t mode, int for_part) + out_unlock_bdev: + mutex_unlock(&bdev->bd_mutex); + disk_unblock_events(disk); +- module_put(disk->fops->owner); + put_disk(disk); ++ module_put(owner); + out: + bdput(bdev); + +@@ -1432,14 +1434,15 @@ static int __blkdev_put(struct block_device *bdev, fmode_t mode, int for_part) + if (!bdev->bd_openers) { + struct module *owner = disk->fops->owner; + +- put_disk(disk); +- module_put(owner); + disk_put_part(bdev->bd_part); + bdev->bd_part = NULL; + bdev->bd_disk = NULL; + if (bdev != bdev->bd_contains) + victim = bdev->bd_contains; + bdev->bd_contains = NULL; ++ ++ put_disk(disk); ++ module_put(owner); + } + mutex_unlock(&bdev->bd_mutex); + bdput(bdev); +diff --git a/fs/cifs/connect.c b/fs/cifs/connect.c +index 2451627..cb85825 100644 +--- a/fs/cifs/connect.c ++++ b/fs/cifs/connect.c +@@ -2767,10 +2767,10 @@ void cifs_setup_cifs_sb(struct smb_vol *pvolume_info, + + /* + * When the server doesn't allow large posix writes, only allow a wsize of +- * 128k minus the size of the WRITE_AND_X header. That allows for a write up ++ * 2^17-1 minus the size of the WRITE_AND_X header. That allows for a write up + * to the maximum size described by RFC1002. + */ +-#define CIFS_MAX_RFC1002_WSIZE (128 * 1024 - sizeof(WRITE_REQ) + 4) ++#define CIFS_MAX_RFC1002_WSIZE ((1<<17) - 1 - sizeof(WRITE_REQ) + 4) + + /* + * The default wsize is 1M. find_get_pages seems to return a maximum of 256 +diff --git a/fs/cifs/inode.c b/fs/cifs/inode.c +index a7b2dcd..745e5cd 100644 +--- a/fs/cifs/inode.c ++++ b/fs/cifs/inode.c +@@ -562,7 +562,16 @@ int cifs_get_file_info(struct file *filp) + + xid = GetXid(); + rc = CIFSSMBQFileInfo(xid, tcon, cfile->netfid, &find_data); +- if (rc == -EOPNOTSUPP || rc == -EINVAL) { ++ switch (rc) { ++ case 0: ++ cifs_all_info_to_fattr(&fattr, &find_data, cifs_sb, false); ++ break; ++ case -EREMOTE: ++ cifs_create_dfs_fattr(&fattr, inode->i_sb); ++ rc = 0; ++ break; ++ case -EOPNOTSUPP: ++ case -EINVAL: + /* + * FIXME: legacy server -- fall back to path-based call? + * for now, just skip revalidating and mark inode for +@@ -570,18 +579,14 @@ int cifs_get_file_info(struct file *filp) + */ + rc = 0; + CIFS_I(inode)->time = 0; ++ default: + goto cgfi_exit; +- } else if (rc == -EREMOTE) { +- cifs_create_dfs_fattr(&fattr, inode->i_sb); +- rc = 0; +- } else if (rc) +- goto cgfi_exit; ++ } + + /* + * don't bother with SFU junk here -- just mark inode as needing + * revalidation. + */ +- cifs_all_info_to_fattr(&fattr, &find_data, cifs_sb, false); + fattr.cf_uniqueid = CIFS_I(inode)->uniqueid; + fattr.cf_flags |= CIFS_FATTR_NEED_REVAL; + cifs_fattr_to_inode(inode, &fattr); +diff --git a/fs/eventpoll.c b/fs/eventpoll.c +index f9cfd16..2acaf60 100644 +--- a/fs/eventpoll.c ++++ b/fs/eventpoll.c +@@ -70,6 +70,15 @@ + * simultaneous inserts (A into B and B into A) from racing and + * constructing a cycle without either insert observing that it is + * going to. ++ * It is necessary to acquire multiple "ep->mtx"es at once in the ++ * case when one epoll fd is added to another. In this case, we ++ * always acquire the locks in the order of nesting (i.e. after ++ * epoll_ctl(e1, EPOLL_CTL_ADD, e2), e1->mtx will always be acquired ++ * before e2->mtx). Since we disallow cycles of epoll file ++ * descriptors, this ensures that the mutexes are well-ordered. In ++ * order to communicate this nesting to lockdep, when walking a tree ++ * of epoll file descriptors, we use the current recursion depth as ++ * the lockdep subkey. + * It is possible to drop the "ep->mtx" and to use the global + * mutex "epmutex" (together with "ep->lock") to have it working, + * but having "ep->mtx" will make the interface more scalable. +@@ -464,13 +473,15 @@ static void ep_unregister_pollwait(struct eventpoll *ep, struct epitem *epi) + * @ep: Pointer to the epoll private data structure. + * @sproc: Pointer to the scan callback. + * @priv: Private opaque data passed to the @sproc callback. ++ * @depth: The current depth of recursive f_op->poll calls. + * + * Returns: The same integer error code returned by the @sproc callback. + */ + static int ep_scan_ready_list(struct eventpoll *ep, + int (*sproc)(struct eventpoll *, + struct list_head *, void *), +- void *priv) ++ void *priv, ++ int depth) + { + int error, pwake = 0; + unsigned long flags; +@@ -481,7 +492,7 @@ static int ep_scan_ready_list(struct eventpoll *ep, + * We need to lock this because we could be hit by + * eventpoll_release_file() and epoll_ctl(). + */ +- mutex_lock(&ep->mtx); ++ mutex_lock_nested(&ep->mtx, depth); + + /* + * Steal the ready list, and re-init the original one to the +@@ -670,7 +681,7 @@ static int ep_read_events_proc(struct eventpoll *ep, struct list_head *head, + + static int ep_poll_readyevents_proc(void *priv, void *cookie, int call_nests) + { +- return ep_scan_ready_list(priv, ep_read_events_proc, NULL); ++ return ep_scan_ready_list(priv, ep_read_events_proc, NULL, call_nests + 1); + } + + static unsigned int ep_eventpoll_poll(struct file *file, poll_table *wait) +@@ -737,7 +748,7 @@ void eventpoll_release_file(struct file *file) + + ep = epi->ep; + list_del_init(&epi->fllink); +- mutex_lock(&ep->mtx); ++ mutex_lock_nested(&ep->mtx, 0); + ep_remove(ep, epi); + mutex_unlock(&ep->mtx); + } +@@ -1134,7 +1145,7 @@ static int ep_send_events(struct eventpoll *ep, + esed.maxevents = maxevents; + esed.events = events; + +- return ep_scan_ready_list(ep, ep_send_events_proc, &esed); ++ return ep_scan_ready_list(ep, ep_send_events_proc, &esed, 0); + } + + static inline struct timespec ep_set_mstimeout(long ms) +@@ -1267,7 +1278,7 @@ static int ep_loop_check_proc(void *priv, void *cookie, int call_nests) + struct rb_node *rbp; + struct epitem *epi; + +- mutex_lock(&ep->mtx); ++ mutex_lock_nested(&ep->mtx, call_nests + 1); + for (rbp = rb_first(&ep->rbr); rbp; rbp = rb_next(rbp)) { + epi = rb_entry(rbp, struct epitem, rbn); + if (unlikely(is_file_epoll(epi->ffd.file))) { +@@ -1409,7 +1420,7 @@ SYSCALL_DEFINE4(epoll_ctl, int, epfd, int, op, int, fd, + } + + +- mutex_lock(&ep->mtx); ++ mutex_lock_nested(&ep->mtx, 0); + + /* + * Try to lookup the file inside our RB tree, Since we grabbed "mtx" +diff --git a/fs/ext4/ext4.h b/fs/ext4/ext4.h +index 354619a..1a34c1c 100644 +--- a/fs/ext4/ext4.h ++++ b/fs/ext4/ext4.h +@@ -175,6 +175,7 @@ struct mpage_da_data { + */ + #define EXT4_IO_END_UNWRITTEN 0x0001 + #define EXT4_IO_END_ERROR 0x0002 ++#define EXT4_IO_END_QUEUED 0x0004 + + struct ext4_io_page { + struct page *p_page; +@@ -357,8 +358,7 @@ struct flex_groups { + + /* Flags that should be inherited by new inodes from their parent. */ + #define EXT4_FL_INHERITED (EXT4_SECRM_FL | EXT4_UNRM_FL | EXT4_COMPR_FL |\ +- EXT4_SYNC_FL | EXT4_IMMUTABLE_FL | EXT4_APPEND_FL |\ +- EXT4_NODUMP_FL | EXT4_NOATIME_FL |\ ++ EXT4_SYNC_FL | EXT4_NODUMP_FL | EXT4_NOATIME_FL |\ + EXT4_NOCOMPR_FL | EXT4_JOURNAL_DATA_FL |\ + EXT4_NOTAIL_FL | EXT4_DIRSYNC_FL) + +diff --git a/fs/ext4/inode.c b/fs/ext4/inode.c +index c94774c..1265904 100644 +--- a/fs/ext4/inode.c ++++ b/fs/ext4/inode.c +@@ -190,9 +190,6 @@ void ext4_evict_inode(struct inode *inode) + + trace_ext4_evict_inode(inode); + +- mutex_lock(&inode->i_mutex); +- ext4_flush_completed_IO(inode); +- mutex_unlock(&inode->i_mutex); + ext4_ioend_wait(inode); + + if (inode->i_nlink) { +diff --git a/fs/ext4/namei.c b/fs/ext4/namei.c +index 458a394..3d36d5a 100644 +--- a/fs/ext4/namei.c ++++ b/fs/ext4/namei.c +@@ -1589,7 +1589,7 @@ static int ext4_dx_add_entry(handle_t *handle, struct dentry *dentry, + dxtrace(dx_show_index("node", frames[1].entries)); + dxtrace(dx_show_index("node", + ((struct dx_node *) bh2->b_data)->entries)); +- err = ext4_handle_dirty_metadata(handle, inode, bh2); ++ err = ext4_handle_dirty_metadata(handle, dir, bh2); + if (err) + goto journal_error; + brelse (bh2); +@@ -1615,7 +1615,7 @@ static int ext4_dx_add_entry(handle_t *handle, struct dentry *dentry, + if (err) + goto journal_error; + } +- err = ext4_handle_dirty_metadata(handle, inode, frames[0].bh); ++ err = ext4_handle_dirty_metadata(handle, dir, frames[0].bh); + if (err) { + ext4_std_error(inode->i_sb, err); + goto cleanup; +@@ -1866,7 +1866,7 @@ retry: + ext4_set_de_type(dir->i_sb, de, S_IFDIR); + inode->i_nlink = 2; + BUFFER_TRACE(dir_block, "call ext4_handle_dirty_metadata"); +- err = ext4_handle_dirty_metadata(handle, dir, dir_block); ++ err = ext4_handle_dirty_metadata(handle, inode, dir_block); + if (err) + goto out_clear_inode; + err = ext4_mark_inode_dirty(handle, inode); +@@ -2540,7 +2540,7 @@ static int ext4_rename(struct inode *old_dir, struct dentry *old_dentry, + PARENT_INO(dir_bh->b_data, new_dir->i_sb->s_blocksize) = + cpu_to_le32(new_dir->i_ino); + BUFFER_TRACE(dir_bh, "call ext4_handle_dirty_metadata"); +- retval = ext4_handle_dirty_metadata(handle, old_dir, dir_bh); ++ retval = ext4_handle_dirty_metadata(handle, old_inode, dir_bh); + if (retval) { + ext4_std_error(old_dir->i_sb, retval); + goto end_rename; +diff --git a/fs/ext4/page-io.c b/fs/ext4/page-io.c +index 97e5e98..bd6a85e 100644 +--- a/fs/ext4/page-io.c ++++ b/fs/ext4/page-io.c +@@ -142,7 +142,23 @@ static void ext4_end_io_work(struct work_struct *work) + unsigned long flags; + int ret; + +- mutex_lock(&inode->i_mutex); ++ if (!mutex_trylock(&inode->i_mutex)) { ++ /* ++ * Requeue the work instead of waiting so that the work ++ * items queued after this can be processed. ++ */ ++ queue_work(EXT4_SB(inode->i_sb)->dio_unwritten_wq, &io->work); ++ /* ++ * To prevent the ext4-dio-unwritten thread from keeping ++ * requeueing end_io requests and occupying cpu for too long, ++ * yield the cpu if it sees an end_io request that has already ++ * been requeued. ++ */ ++ if (io->flag & EXT4_IO_END_QUEUED) ++ yield(); ++ io->flag |= EXT4_IO_END_QUEUED; ++ return; ++ } + ret = ext4_end_io_nolock(io); + if (ret < 0) { + mutex_unlock(&inode->i_mutex); +diff --git a/fs/ext4/xattr.c b/fs/ext4/xattr.c +index c757adc..19fe4e3 100644 +--- a/fs/ext4/xattr.c ++++ b/fs/ext4/xattr.c +@@ -820,8 +820,14 @@ inserted: + if (!(ext4_test_inode_flag(inode, EXT4_INODE_EXTENTS))) + goal = goal & EXT4_MAX_BLOCK_FILE_PHYS; + ++ /* ++ * take i_data_sem because we will test ++ * i_delalloc_reserved_flag in ext4_mb_new_blocks ++ */ ++ down_read((&EXT4_I(inode)->i_data_sem)); + block = ext4_new_meta_blocks(handle, inode, goal, 0, + NULL, &error); ++ up_read((&EXT4_I(inode)->i_data_sem)); + if (error) + goto cleanup; + +diff --git a/fs/hppfs/hppfs.c b/fs/hppfs/hppfs.c +index 85c098a..9d71c95 100644 +--- a/fs/hppfs/hppfs.c ++++ b/fs/hppfs/hppfs.c +@@ -16,6 +16,7 @@ + #include <linux/statfs.h> + #include <linux/types.h> + #include <linux/pid_namespace.h> ++#include <linux/namei.h> + #include <asm/uaccess.h> + #include "os.h" + +diff --git a/fs/namei.c b/fs/namei.c +index b456c7a..f7593c0 100644 +--- a/fs/namei.c ++++ b/fs/namei.c +@@ -136,7 +136,7 @@ static int do_getname(const char __user *filename, char *page) + return retval; + } + +-static char *getname_flags(const char __user * filename, int flags) ++static char *getname_flags(const char __user *filename, int flags, int *empty) + { + char *tmp, *result; + +@@ -147,6 +147,8 @@ static char *getname_flags(const char __user * filename, int flags) + + result = tmp; + if (retval < 0) { ++ if (retval == -ENOENT && empty) ++ *empty = 1; + if (retval != -ENOENT || !(flags & LOOKUP_EMPTY)) { + __putname(tmp); + result = ERR_PTR(retval); +@@ -159,7 +161,7 @@ static char *getname_flags(const char __user * filename, int flags) + + char *getname(const char __user * filename) + { +- return getname_flags(filename, 0); ++ return getname_flags(filename, 0, 0); + } + + #ifdef CONFIG_AUDITSYSCALL +@@ -779,17 +781,20 @@ static int follow_automount(struct path *path, unsigned flags, + if ((flags & LOOKUP_NO_AUTOMOUNT) && !(flags & LOOKUP_CONTINUE)) + return -EISDIR; /* we actually want to stop here */ + +- /* We want to mount if someone is trying to open/create a file of any +- * type under the mountpoint, wants to traverse through the mountpoint +- * or wants to open the mounted directory. ++ /* We don't want to mount if someone's just doing a stat - ++ * unless they're stat'ing a directory and appended a '/' to ++ * the name. + * +- * We don't want to mount if someone's just doing a stat and they've +- * set AT_SYMLINK_NOFOLLOW - unless they're stat'ing a directory and +- * appended a '/' to the name. ++ * We do, however, want to mount if someone wants to open or ++ * create a file of any type under the mountpoint, wants to ++ * traverse through the mountpoint or wants to open the ++ * mounted directory. Also, autofs may mark negative dentries ++ * as being automount points. These will need the attentions ++ * of the daemon to instantiate them before they can be used. + */ +- if (!(flags & LOOKUP_FOLLOW) && +- !(flags & (LOOKUP_CONTINUE | LOOKUP_DIRECTORY | +- LOOKUP_OPEN | LOOKUP_CREATE))) ++ if (!(flags & (LOOKUP_CONTINUE | LOOKUP_DIRECTORY | ++ LOOKUP_OPEN | LOOKUP_CREATE | LOOKUP_AUTOMOUNT)) && ++ path->dentry->d_inode) + return -EISDIR; + + current->total_link_count++; +@@ -905,7 +910,7 @@ static int follow_managed(struct path *path, unsigned flags) + mntput(path->mnt); + if (ret == -EISDIR) + ret = 0; +- return ret; ++ return ret < 0 ? ret : need_mntput; + } + + int follow_down_one(struct path *path) +@@ -953,6 +958,7 @@ static bool __follow_mount_rcu(struct nameidata *nd, struct path *path, + break; + path->mnt = mounted; + path->dentry = mounted->mnt_root; ++ nd->flags |= LOOKUP_JUMPED; + nd->seq = read_seqcount_begin(&path->dentry->d_seq); + /* + * Update the inode too. We don't need to re-check the +@@ -1227,6 +1233,8 @@ retry: + path_put_conditional(path, nd); + return err; + } ++ if (err) ++ nd->flags |= LOOKUP_JUMPED; + *inode = path->dentry->d_inode; + return 0; + } +@@ -1747,11 +1755,11 @@ struct dentry *lookup_one_len(const char *name, struct dentry *base, int len) + return __lookup_hash(&this, base, NULL); + } + +-int user_path_at(int dfd, const char __user *name, unsigned flags, +- struct path *path) ++int user_path_at_empty(int dfd, const char __user *name, unsigned flags, ++ struct path *path, int *empty) + { + struct nameidata nd; +- char *tmp = getname_flags(name, flags); ++ char *tmp = getname_flags(name, flags, empty); + int err = PTR_ERR(tmp); + if (!IS_ERR(tmp)) { + +@@ -1765,6 +1773,12 @@ int user_path_at(int dfd, const char __user *name, unsigned flags, + return err; + } + ++int user_path_at(int dfd, const char __user *name, unsigned flags, ++ struct path *path) ++{ ++ return user_path_at_empty(dfd, name, flags, path, 0); ++} ++ + static int user_path_parent(int dfd, const char __user *path, + struct nameidata *nd, char **name) + { +@@ -2107,6 +2121,10 @@ static struct file *do_last(struct nameidata *nd, struct path *path, + } + + /* create side of things */ ++ /* ++ * This will *only* deal with leaving RCU mode - LOOKUP_JUMPED has been ++ * cleared when we got to the last component we are about to look up ++ */ + error = complete_walk(nd); + if (error) + return ERR_PTR(error); +@@ -2175,6 +2193,9 @@ static struct file *do_last(struct nameidata *nd, struct path *path, + if (error < 0) + goto exit_dput; + ++ if (error) ++ nd->flags |= LOOKUP_JUMPED; ++ + error = -ENOENT; + if (!path->dentry->d_inode) + goto exit_dput; +@@ -2184,6 +2205,10 @@ static struct file *do_last(struct nameidata *nd, struct path *path, + + path_to_nameidata(path, nd); + nd->inode = path->dentry->d_inode; ++ /* Why this, you ask? _Now_ we might have grown LOOKUP_JUMPED... */ ++ error = complete_walk(nd); ++ if (error) ++ goto exit; + error = -EISDIR; + if (S_ISDIR(nd->inode->i_mode)) + goto exit; +diff --git a/fs/namespace.c b/fs/namespace.c +index fe59bd1..537dd96 100644 +--- a/fs/namespace.c ++++ b/fs/namespace.c +@@ -1109,6 +1109,7 @@ static int show_vfsstat(struct seq_file *m, void *v) + + /* device */ + if (mnt->mnt_sb->s_op->show_devname) { ++ seq_puts(m, "device "); + err = mnt->mnt_sb->s_op->show_devname(m, mnt); + } else { + if (mnt->mnt_devname) { +@@ -1757,7 +1758,7 @@ static int do_loopback(struct path *path, char *old_name, + return err; + if (!old_name || !*old_name) + return -EINVAL; +- err = kern_path(old_name, LOOKUP_FOLLOW, &old_path); ++ err = kern_path(old_name, LOOKUP_FOLLOW|LOOKUP_AUTOMOUNT, &old_path); + if (err) + return err; + +diff --git a/fs/nfs/super.c b/fs/nfs/super.c +index ce40e5c..858d31b 100644 +--- a/fs/nfs/super.c ++++ b/fs/nfs/super.c +@@ -2793,7 +2793,7 @@ static struct dentry *nfs_follow_remote_path(struct vfsmount *root_mnt, + goto out_put_mnt_ns; + + ret = vfs_path_lookup(root_mnt->mnt_root, root_mnt, +- export_path, LOOKUP_FOLLOW, nd); ++ export_path, LOOKUP_FOLLOW|LOOKUP_AUTOMOUNT, nd); + + nfs_referral_loop_unprotect(); + put_mnt_ns(ns_private); +diff --git a/fs/nfs/write.c b/fs/nfs/write.c +index 7271680..f2f80c0 100644 +--- a/fs/nfs/write.c ++++ b/fs/nfs/write.c +@@ -428,7 +428,6 @@ static void + nfs_mark_request_dirty(struct nfs_page *req) + { + __set_page_dirty_nobuffers(req->wb_page); +- __mark_inode_dirty(req->wb_page->mapping->host, I_DIRTY_DATASYNC); + } + + #if defined(CONFIG_NFS_V3) || defined(CONFIG_NFS_V4) +@@ -762,6 +761,8 @@ int nfs_updatepage(struct file *file, struct page *page, + status = nfs_writepage_setup(ctx, page, offset, count); + if (status < 0) + nfs_set_pageerror(page); ++ else ++ __set_page_dirty_nobuffers(page); + + dprintk("NFS: nfs_updatepage returns %d (isize %lld)\n", + status, (long long)i_size_read(inode)); +@@ -1525,6 +1526,10 @@ static int nfs_commit_unstable_pages(struct inode *inode, struct writeback_contr + int flags = FLUSH_SYNC; + int ret = 0; + ++ /* no commits means nothing needs to be done */ ++ if (!nfsi->ncommit) ++ return ret; ++ + if (wbc->sync_mode == WB_SYNC_NONE) { + /* Don't commit yet if this is a non-blocking flush and there + * are a lot of outstanding writes for this mapping. +@@ -1659,34 +1664,20 @@ out_error: + int nfs_migrate_page(struct address_space *mapping, struct page *newpage, + struct page *page) + { +- struct nfs_page *req; +- int ret; ++ /* ++ * If PagePrivate is set, then the page is currently associated with ++ * an in-progress read or write request. Don't try to migrate it. ++ * ++ * FIXME: we could do this in principle, but we'll need a way to ensure ++ * that we can safely release the inode reference while holding ++ * the page lock. ++ */ ++ if (PagePrivate(page)) ++ return -EBUSY; + + nfs_fscache_release_page(page, GFP_KERNEL); + +- req = nfs_find_and_lock_request(page, false); +- ret = PTR_ERR(req); +- if (IS_ERR(req)) +- goto out; +- +- ret = migrate_page(mapping, newpage, page); +- if (!req) +- goto out; +- if (ret) +- goto out_unlock; +- page_cache_get(newpage); +- spin_lock(&mapping->host->i_lock); +- req->wb_page = newpage; +- SetPagePrivate(newpage); +- set_page_private(newpage, (unsigned long)req); +- ClearPagePrivate(page); +- set_page_private(page, 0); +- spin_unlock(&mapping->host->i_lock); +- page_cache_release(page); +-out_unlock: +- nfs_clear_page_tag_locked(req); +-out: +- return ret; ++ return migrate_page(mapping, newpage, page); + } + #endif + +diff --git a/fs/nfsd/nfs4proc.c b/fs/nfsd/nfs4proc.c +index 3a6dbd7..0b8830c 100644 +--- a/fs/nfsd/nfs4proc.c ++++ b/fs/nfsd/nfs4proc.c +@@ -156,6 +156,8 @@ do_open_permission(struct svc_rqst *rqstp, struct svc_fh *current_fh, struct nfs + !(open->op_share_access & NFS4_SHARE_ACCESS_WRITE)) + return nfserr_inval; + ++ accmode |= NFSD_MAY_READ_IF_EXEC; ++ + if (open->op_share_access & NFS4_SHARE_ACCESS_READ) + accmode |= NFSD_MAY_READ; + if (open->op_share_access & NFS4_SHARE_ACCESS_WRITE) +@@ -682,7 +684,7 @@ nfsd4_readdir(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, + readdir->rd_bmval[1] &= nfsd_suppattrs1(cstate->minorversion); + readdir->rd_bmval[2] &= nfsd_suppattrs2(cstate->minorversion); + +- if ((cookie > ~(u32)0) || (cookie == 1) || (cookie == 2) || ++ if ((cookie == 1) || (cookie == 2) || + (cookie == 0 && memcmp(readdir->rd_verf.data, zeroverf.data, NFS4_VERIFIER_SIZE))) + return nfserr_bad_cookie; + +@@ -921,7 +923,7 @@ _nfsd4_verify(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, + count = 4 + (verify->ve_attrlen >> 2); + buf = kmalloc(count << 2, GFP_KERNEL); + if (!buf) +- return nfserr_resource; ++ return nfserr_jukebox; + + status = nfsd4_encode_fattr(&cstate->current_fh, + cstate->current_fh.fh_export, +diff --git a/fs/nfsd/nfs4recover.c b/fs/nfsd/nfs4recover.c +index ffb59ef..be26814 100644 +--- a/fs/nfsd/nfs4recover.c ++++ b/fs/nfsd/nfs4recover.c +@@ -88,7 +88,7 @@ nfs4_make_rec_clidname(char *dname, struct xdr_netobj *clname) + struct xdr_netobj cksum; + struct hash_desc desc; + struct scatterlist sg; +- __be32 status = nfserr_resource; ++ __be32 status = nfserr_jukebox; + + dprintk("NFSD: nfs4_make_rec_clidname for %.*s\n", + clname->len, clname->data); +diff --git a/fs/nfsd/nfs4state.c b/fs/nfsd/nfs4state.c +index 3b8ad35..ecd8152 100644 +--- a/fs/nfsd/nfs4state.c ++++ b/fs/nfsd/nfs4state.c +@@ -188,8 +188,15 @@ static void nfs4_file_put_fd(struct nfs4_file *fp, int oflag) + static void __nfs4_file_put_access(struct nfs4_file *fp, int oflag) + { + if (atomic_dec_and_test(&fp->fi_access[oflag])) { +- nfs4_file_put_fd(fp, O_RDWR); + nfs4_file_put_fd(fp, oflag); ++ /* ++ * It's also safe to get rid of the RDWR open *if* ++ * we no longer have need of the other kind of access ++ * or if we already have the other kind of open: ++ */ ++ if (fp->fi_fds[1-oflag] ++ || atomic_read(&fp->fi_access[1 - oflag]) == 0) ++ nfs4_file_put_fd(fp, O_RDWR); + } + } + +@@ -1903,7 +1910,7 @@ nfsd4_setclientid(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, + * of 5 bullet points, labeled as CASE0 - CASE4 below. + */ + unconf = find_unconfirmed_client_by_str(dname, strhashval); +- status = nfserr_resource; ++ status = nfserr_jukebox; + if (!conf) { + /* + * RFC 3530 14.2.33 CASE 4: +@@ -2440,7 +2447,7 @@ renew: + if (open->op_stateowner == NULL) { + sop = alloc_init_open_stateowner(strhashval, clp, open); + if (sop == NULL) +- return nfserr_resource; ++ return nfserr_jukebox; + open->op_stateowner = sop; + } + list_del_init(&sop->so_close_lru); +@@ -2576,7 +2583,7 @@ nfs4_new_open(struct svc_rqst *rqstp, struct nfs4_stateid **stpp, + + stp = nfs4_alloc_stateid(); + if (stp == NULL) +- return nfserr_resource; ++ return nfserr_jukebox; + + status = nfs4_get_vfs_file(rqstp, fp, cur_fh, open); + if (status) { +@@ -2807,7 +2814,7 @@ nfsd4_process_open2(struct svc_rqst *rqstp, struct svc_fh *current_fh, struct nf + status = nfserr_bad_stateid; + if (open->op_claim_type == NFS4_OPEN_CLAIM_DELEGATE_CUR) + goto out; +- status = nfserr_resource; ++ status = nfserr_jukebox; + fp = alloc_init_file(ino); + if (fp == NULL) + goto out; +@@ -3381,8 +3388,9 @@ static inline void nfs4_file_downgrade(struct nfs4_stateid *stp, unsigned int to + int i; + + for (i = 1; i < 4; i++) { +- if (test_bit(i, &stp->st_access_bmap) && !(i & to_access)) { +- nfs4_file_put_access(stp->st_file, i); ++ if (test_bit(i, &stp->st_access_bmap) ++ && ((i & to_access) != i)) { ++ nfs4_file_put_access(stp->st_file, nfs4_access_to_omode(i)); + __clear_bit(i, &stp->st_access_bmap); + } + } +@@ -3413,6 +3421,8 @@ nfsd4_open_downgrade(struct svc_rqst *rqstp, + if (!access_valid(od->od_share_access, cstate->minorversion) + || !deny_valid(od->od_share_deny)) + return nfserr_inval; ++ /* We don't yet support WANT bits: */ ++ od->od_share_access &= NFS4_SHARE_ACCESS_MASK; + + nfs4_lock_state(); + if ((status = nfs4_preprocess_seqid_op(cstate, +@@ -3840,7 +3850,7 @@ nfsd4_lock(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, + /* XXX: Do we need to check for duplicate stateowners on + * the same file, or should they just be allowed (and + * create new stateids)? */ +- status = nfserr_resource; ++ status = nfserr_jukebox; + lock_sop = alloc_init_lock_stateowner(strhashval, + open_sop->so_client, open_stp, lock); + if (lock_sop == NULL) +@@ -3924,9 +3934,9 @@ nfsd4_lock(struct svc_rqst *rqstp, struct nfsd4_compound_state *cstate, + case (EDEADLK): + status = nfserr_deadlock; + break; +- default: ++ default: + dprintk("NFSD: nfsd4_lock: vfs_lock_file() failed! status %d\n",err); +- status = nfserr_resource; ++ status = nfserrno(err); + break; + } + out: +diff --git a/fs/nfsd/nfs4xdr.c b/fs/nfsd/nfs4xdr.c +index 9901811..6c74097 100644 +--- a/fs/nfsd/nfs4xdr.c ++++ b/fs/nfsd/nfs4xdr.c +@@ -1548,6 +1548,18 @@ static void write_cinfo(__be32 **p, struct nfsd4_change_info *c) + \ + save = resp->p; + ++static bool seqid_mutating_err(__be32 err) ++{ ++ /* rfc 3530 section 8.1.5: */ ++ return err != nfserr_stale_clientid && ++ err != nfserr_stale_stateid && ++ err != nfserr_bad_stateid && ++ err != nfserr_bad_seqid && ++ err != nfserr_bad_xdr && ++ err != nfserr_resource && ++ err != nfserr_nofilehandle; ++} ++ + /* + * Routine for encoding the result of a "seqid-mutating" NFSv4 operation. This + * is where sequence id's are incremented, and the replay cache is filled. +diff --git a/fs/nfsd/state.h b/fs/nfsd/state.h +index 6bd2f3c..858c7ba 100644 +--- a/fs/nfsd/state.h ++++ b/fs/nfsd/state.h +@@ -447,12 +447,6 @@ struct nfs4_stateid { + #define WR_STATE 0x00000020 + #define CLOSE_STATE 0x00000040 + +-#define seqid_mutating_err(err) \ +- (((err) != nfserr_stale_clientid) && \ +- ((err) != nfserr_bad_seqid) && \ +- ((err) != nfserr_stale_stateid) && \ +- ((err) != nfserr_bad_stateid)) +- + struct nfsd4_compound_state; + + extern __be32 nfs4_preprocess_stateid_op(struct nfsd4_compound_state *cstate, +diff --git a/fs/nfsd/vfs.c b/fs/nfsd/vfs.c +index fd0acca..acf88ae 100644 +--- a/fs/nfsd/vfs.c ++++ b/fs/nfsd/vfs.c +@@ -2114,7 +2114,8 @@ nfsd_permission(struct svc_rqst *rqstp, struct svc_export *exp, + + /* Allow read access to binaries even when mode 111 */ + if (err == -EACCES && S_ISREG(inode->i_mode) && +- acc == (NFSD_MAY_READ | NFSD_MAY_OWNER_OVERRIDE)) ++ (acc == (NFSD_MAY_READ | NFSD_MAY_OWNER_OVERRIDE) || ++ acc == (NFSD_MAY_READ | NFSD_MAY_READ_IF_EXEC))) + err = inode_permission(inode, MAY_EXEC); + + return err? nfserrno(err) : 0; +diff --git a/fs/nfsd/vfs.h b/fs/nfsd/vfs.h +index e0bbac0..a22e40e 100644 +--- a/fs/nfsd/vfs.h ++++ b/fs/nfsd/vfs.h +@@ -25,6 +25,7 @@ + #define NFSD_MAY_BYPASS_GSS_ON_ROOT 256 + #define NFSD_MAY_NOT_BREAK_LEASE 512 + #define NFSD_MAY_BYPASS_GSS 1024 ++#define NFSD_MAY_READ_IF_EXEC 2048 + + #define NFSD_MAY_CREATE (NFSD_MAY_EXEC|NFSD_MAY_WRITE) + #define NFSD_MAY_REMOVE (NFSD_MAY_EXEC|NFSD_MAY_WRITE|NFSD_MAY_TRUNC) +diff --git a/fs/proc/base.c b/fs/proc/base.c +index 5bff4c6..f039017 100644 +--- a/fs/proc/base.c ++++ b/fs/proc/base.c +@@ -1920,6 +1920,14 @@ static int proc_fd_info(struct inode *inode, struct path *path, char *info) + spin_lock(&files->file_lock); + file = fcheck_files(files, fd); + if (file) { ++ unsigned int f_flags; ++ struct fdtable *fdt; ++ ++ fdt = files_fdtable(files); ++ f_flags = file->f_flags & ~O_CLOEXEC; ++ if (FD_ISSET(fd, fdt->close_on_exec)) ++ f_flags |= O_CLOEXEC; ++ + if (path) { + *path = file->f_path; + path_get(&file->f_path); +@@ -1929,7 +1937,7 @@ static int proc_fd_info(struct inode *inode, struct path *path, char *info) + "pos:\t%lli\n" + "flags:\t0%o\n", + (long long) file->f_pos, +- file->f_flags); ++ f_flags); + spin_unlock(&files->file_lock); + put_files_struct(files); + return 0; +diff --git a/fs/proc/task_mmu.c b/fs/proc/task_mmu.c +index 5afaa58..c7d4ee6 100644 +--- a/fs/proc/task_mmu.c ++++ b/fs/proc/task_mmu.c +@@ -1039,6 +1039,9 @@ static int show_numa_map(struct seq_file *m, void *v) + seq_printf(m, " stack"); + } + ++ if (is_vm_hugetlb_page(vma)) ++ seq_printf(m, " huge"); ++ + walk_page_range(vma->vm_start, vma->vm_end, &walk); + + if (!md->pages) +diff --git a/fs/quota/quota.c b/fs/quota/quota.c +index b34bdb2..10b6be3 100644 +--- a/fs/quota/quota.c ++++ b/fs/quota/quota.c +@@ -355,7 +355,7 @@ SYSCALL_DEFINE4(quotactl, unsigned int, cmd, const char __user *, special, + * resolution (think about autofs) and thus deadlocks could arise. + */ + if (cmds == Q_QUOTAON) { +- ret = user_path_at(AT_FDCWD, addr, LOOKUP_FOLLOW, &path); ++ ret = user_path_at(AT_FDCWD, addr, LOOKUP_FOLLOW|LOOKUP_AUTOMOUNT, &path); + if (ret) + pathp = ERR_PTR(ret); + else +diff --git a/fs/stat.c b/fs/stat.c +index 9610391..02a6061 100644 +--- a/fs/stat.c ++++ b/fs/stat.c +@@ -296,15 +296,16 @@ SYSCALL_DEFINE4(readlinkat, int, dfd, const char __user *, pathname, + { + struct path path; + int error; ++ int empty = 0; + + if (bufsiz <= 0) + return -EINVAL; + +- error = user_path_at(dfd, pathname, LOOKUP_EMPTY, &path); ++ error = user_path_at_empty(dfd, pathname, LOOKUP_EMPTY, &path, &empty); + if (!error) { + struct inode *inode = path.dentry->d_inode; + +- error = -EINVAL; ++ error = empty ? -ENOENT : -EINVAL; + if (inode->i_op->readlink) { + error = security_inode_readlink(path.dentry); + if (!error) { +diff --git a/fs/statfs.c b/fs/statfs.c +index 8244924..9cf04a1 100644 +--- a/fs/statfs.c ++++ b/fs/statfs.c +@@ -76,7 +76,7 @@ EXPORT_SYMBOL(vfs_statfs); + int user_statfs(const char __user *pathname, struct kstatfs *st) + { + struct path path; +- int error = user_path(pathname, &path); ++ int error = user_path_at(AT_FDCWD, pathname, LOOKUP_FOLLOW|LOOKUP_AUTOMOUNT, &path); + if (!error) { + error = vfs_statfs(&path, st); + path_put(&path); +diff --git a/include/drm/drm_dp_helper.h b/include/drm/drm_dp_helper.h +index 91567bb..03eb1d6 100644 +--- a/include/drm/drm_dp_helper.h ++++ b/include/drm/drm_dp_helper.h +@@ -72,6 +72,7 @@ + + #define DP_MAIN_LINK_CHANNEL_CODING 0x006 + ++#define DP_EDP_CONFIGURATION_CAP 0x00d + #define DP_TRAINING_AUX_RD_INTERVAL 0x00e + + /* link configuration */ +@@ -133,6 +134,8 @@ + #define DP_MAIN_LINK_CHANNEL_CODING_SET 0x108 + # define DP_SET_ANSI_8B10B (1 << 0) + ++#define DP_EDP_CONFIGURATION_SET 0x10a ++ + #define DP_LANE0_1_STATUS 0x202 + #define DP_LANE2_3_STATUS 0x203 + # define DP_LANE_CR_DONE (1 << 0) +diff --git a/include/linux/ext2_fs.h b/include/linux/ext2_fs.h +index 2dfa707..0bfcb76 100644 +--- a/include/linux/ext2_fs.h ++++ b/include/linux/ext2_fs.h +@@ -196,8 +196,8 @@ struct ext2_group_desc + + /* Flags that should be inherited by new inodes from their parent. */ + #define EXT2_FL_INHERITED (EXT2_SECRM_FL | EXT2_UNRM_FL | EXT2_COMPR_FL |\ +- EXT2_SYNC_FL | EXT2_IMMUTABLE_FL | EXT2_APPEND_FL |\ +- EXT2_NODUMP_FL | EXT2_NOATIME_FL | EXT2_COMPRBLK_FL|\ ++ EXT2_SYNC_FL | EXT2_NODUMP_FL |\ ++ EXT2_NOATIME_FL | EXT2_COMPRBLK_FL |\ + EXT2_NOCOMP_FL | EXT2_JOURNAL_DATA_FL |\ + EXT2_NOTAIL_FL | EXT2_DIRSYNC_FL) + +diff --git a/include/linux/ext3_fs.h b/include/linux/ext3_fs.h +index 5e06acf..7b14d25 100644 +--- a/include/linux/ext3_fs.h ++++ b/include/linux/ext3_fs.h +@@ -180,8 +180,8 @@ struct ext3_group_desc + + /* Flags that should be inherited by new inodes from their parent. */ + #define EXT3_FL_INHERITED (EXT3_SECRM_FL | EXT3_UNRM_FL | EXT3_COMPR_FL |\ +- EXT3_SYNC_FL | EXT3_IMMUTABLE_FL | EXT3_APPEND_FL |\ +- EXT3_NODUMP_FL | EXT3_NOATIME_FL | EXT3_COMPRBLK_FL|\ ++ EXT3_SYNC_FL | EXT3_NODUMP_FL |\ ++ EXT3_NOATIME_FL | EXT3_COMPRBLK_FL |\ + EXT3_NOCOMPR_FL | EXT3_JOURNAL_DATA_FL |\ + EXT3_NOTAIL_FL | EXT3_DIRSYNC_FL) + +diff --git a/include/linux/interrupt.h b/include/linux/interrupt.h +index f6efed0..b9490bf 100644 +--- a/include/linux/interrupt.h ++++ b/include/linux/interrupt.h +@@ -59,6 +59,8 @@ + * IRQF_NO_SUSPEND - Do not disable this IRQ during suspend + * IRQF_FORCE_RESUME - Force enable it on resume even if IRQF_NO_SUSPEND is set + * IRQF_NO_THREAD - Interrupt cannot be threaded ++ * IRQF_EARLY_RESUME - Resume IRQ early during syscore instead of at device ++ * resume time. + */ + #define IRQF_DISABLED 0x00000020 + #define IRQF_SAMPLE_RANDOM 0x00000040 +@@ -72,6 +74,7 @@ + #define IRQF_NO_SUSPEND 0x00004000 + #define IRQF_FORCE_RESUME 0x00008000 + #define IRQF_NO_THREAD 0x00010000 ++#define IRQF_EARLY_RESUME 0x00020000 + + #define IRQF_TIMER (__IRQF_TIMER | IRQF_NO_SUSPEND | IRQF_NO_THREAD) + +diff --git a/include/linux/io-mapping.h b/include/linux/io-mapping.h +index 8cdcc2a1..1feeb52 100644 +--- a/include/linux/io-mapping.h ++++ b/include/linux/io-mapping.h +@@ -117,6 +117,8 @@ io_mapping_unmap(void __iomem *vaddr) + + #else + ++#include <linux/uaccess.h> ++ + /* this struct isn't actually defined anywhere */ + struct io_mapping; + +@@ -138,12 +140,14 @@ static inline void __iomem * + io_mapping_map_atomic_wc(struct io_mapping *mapping, + unsigned long offset) + { ++ pagefault_disable(); + return ((char __force __iomem *) mapping) + offset; + } + + static inline void + io_mapping_unmap_atomic(void __iomem *vaddr) + { ++ pagefault_enable(); + } + + /* Non-atomic map/unmap */ +diff --git a/include/linux/jiffies.h b/include/linux/jiffies.h +index f97672a..265e2c3 100644 +--- a/include/linux/jiffies.h ++++ b/include/linux/jiffies.h +@@ -303,7 +303,7 @@ extern void jiffies_to_timespec(const unsigned long jiffies, + extern unsigned long timeval_to_jiffies(const struct timeval *value); + extern void jiffies_to_timeval(const unsigned long jiffies, + struct timeval *value); +-extern clock_t jiffies_to_clock_t(long x); ++extern clock_t jiffies_to_clock_t(unsigned long x); + extern unsigned long clock_t_to_jiffies(unsigned long x); + extern u64 jiffies_64_to_clock_t(u64 x); + extern u64 nsec_to_clock_t(u64 x); +diff --git a/include/linux/mm.h b/include/linux/mm.h +index ec6e33d..18eea05 100644 +--- a/include/linux/mm.h ++++ b/include/linux/mm.h +@@ -355,36 +355,50 @@ static inline struct page *compound_head(struct page *page) + return page; + } + ++/* ++ * The atomic page->_mapcount, starts from -1: so that transitions ++ * both from it and to it can be tracked, using atomic_inc_and_test ++ * and atomic_add_negative(-1). ++ */ ++static inline void reset_page_mapcount(struct page *page) ++{ ++ atomic_set(&(page)->_mapcount, -1); ++} ++ ++static inline int page_mapcount(struct page *page) ++{ ++ return atomic_read(&(page)->_mapcount) + 1; ++} ++ + static inline int page_count(struct page *page) + { + return atomic_read(&compound_head(page)->_count); + } + ++static inline void get_huge_page_tail(struct page *page) ++{ ++ /* ++ * __split_huge_page_refcount() cannot run ++ * from under us. ++ */ ++ VM_BUG_ON(page_mapcount(page) < 0); ++ VM_BUG_ON(atomic_read(&page->_count) != 0); ++ atomic_inc(&page->_mapcount); ++} ++ ++extern bool __get_page_tail(struct page *page); ++ + static inline void get_page(struct page *page) + { ++ if (unlikely(PageTail(page))) ++ if (likely(__get_page_tail(page))) ++ return; + /* + * Getting a normal page or the head of a compound page +- * requires to already have an elevated page->_count. Only if +- * we're getting a tail page, the elevated page->_count is +- * required only in the head page, so for tail pages the +- * bugcheck only verifies that the page->_count isn't +- * negative. ++ * requires to already have an elevated page->_count. + */ +- VM_BUG_ON(atomic_read(&page->_count) < !PageTail(page)); ++ VM_BUG_ON(atomic_read(&page->_count) <= 0); + atomic_inc(&page->_count); +- /* +- * Getting a tail page will elevate both the head and tail +- * page->_count(s). +- */ +- if (unlikely(PageTail(page))) { +- /* +- * This is safe only because +- * __split_huge_page_refcount can't run under +- * get_page(). +- */ +- VM_BUG_ON(atomic_read(&page->first_page->_count) <= 0); +- atomic_inc(&page->first_page->_count); +- } + } + + static inline struct page *virt_to_head_page(const void *x) +@@ -803,21 +817,6 @@ static inline pgoff_t page_index(struct page *page) + } + + /* +- * The atomic page->_mapcount, like _count, starts from -1: +- * so that transitions both from it and to it can be tracked, +- * using atomic_inc_and_test and atomic_add_negative(-1). +- */ +-static inline void reset_page_mapcount(struct page *page) +-{ +- atomic_set(&(page)->_mapcount, -1); +-} +- +-static inline int page_mapcount(struct page *page) +-{ +- return atomic_read(&(page)->_mapcount) + 1; +-} +- +-/* + * Return true if this page is mapped into pagetables. + */ + static inline int page_mapped(struct page *page) +diff --git a/include/linux/mm_types.h b/include/linux/mm_types.h +index 027935c..059839c 100644 +--- a/include/linux/mm_types.h ++++ b/include/linux/mm_types.h +@@ -36,10 +36,24 @@ struct page { + * updated asynchronously */ + atomic_t _count; /* Usage count, see below. */ + union { +- atomic_t _mapcount; /* Count of ptes mapped in mms, +- * to show when page is mapped +- * & limit reverse map searches. +- */ ++ /* ++ * Count of ptes mapped in ++ * mms, to show when page is ++ * mapped & limit reverse map ++ * searches. ++ * ++ * Used also for tail pages ++ * refcounting instead of ++ * _count. Tail pages cannot ++ * be mapped and keeping the ++ * tail page _count zero at ++ * all times guarantees ++ * get_page_unless_zero() will ++ * never succeed on tail ++ * pages. ++ */ ++ atomic_t _mapcount; ++ + struct { /* SLUB */ + u16 inuse; + u16 objects; +diff --git a/include/linux/namei.h b/include/linux/namei.h +index eba45ea..82ab16b 100644 +--- a/include/linux/namei.h ++++ b/include/linux/namei.h +@@ -49,6 +49,7 @@ enum {LAST_NORM, LAST_ROOT, LAST_DOT, LAST_DOTDOT, LAST_BIND}; + #define LOOKUP_FOLLOW 0x0001 + #define LOOKUP_DIRECTORY 0x0002 + #define LOOKUP_CONTINUE 0x0004 ++#define LOOKUP_AUTOMOUNT 0x0008 + + #define LOOKUP_PARENT 0x0010 + #define LOOKUP_REVAL 0x0020 +@@ -67,6 +68,7 @@ enum {LAST_NORM, LAST_ROOT, LAST_DOT, LAST_DOTDOT, LAST_BIND}; + #define LOOKUP_EMPTY 0x4000 + + extern int user_path_at(int, const char __user *, unsigned, struct path *); ++extern int user_path_at_empty(int, const char __user *, unsigned, struct path *, int *empty); + + #define user_path(name, path) user_path_at(AT_FDCWD, name, LOOKUP_FOLLOW, path) + #define user_lpath(name, path) user_path_at(AT_FDCWD, name, 0, path) +diff --git a/include/linux/phy.h b/include/linux/phy.h +index 7da5fa8..4d3f63a 100644 +--- a/include/linux/phy.h ++++ b/include/linux/phy.h +@@ -418,7 +418,7 @@ struct phy_driver { + + /* + * Requests a Tx timestamp for 'skb'. The phy driver promises +- * to deliver it to the socket's error queue as soon as a ++ * to deliver it using skb_complete_tx_timestamp() as soon as a + * timestamp becomes available. One of the PTP_CLASS_ values + * is passed in 'type'. + */ +diff --git a/include/linux/skbuff.h b/include/linux/skbuff.h +index c0a4f3a..b920a72 100644 +--- a/include/linux/skbuff.h ++++ b/include/linux/skbuff.h +@@ -1996,8 +1996,13 @@ static inline bool skb_defer_rx_timestamp(struct sk_buff *skb) + /** + * skb_complete_tx_timestamp() - deliver cloned skb with tx timestamps + * ++ * PHY drivers may accept clones of transmitted packets for ++ * timestamping via their phy_driver.txtstamp method. These drivers ++ * must call this function to return the skb back to the stack, with ++ * or without a timestamp. ++ * + * @skb: clone of the the original outgoing packet +- * @hwtstamps: hardware time stamps ++ * @hwtstamps: hardware time stamps, may be NULL if not available + * + */ + void skb_complete_tx_timestamp(struct sk_buff *skb, +diff --git a/include/linux/tty.h b/include/linux/tty.h +index 6660c41..1ff6b62 100644 +--- a/include/linux/tty.h ++++ b/include/linux/tty.h +@@ -472,7 +472,9 @@ extern void proc_clear_tty(struct task_struct *p); + extern struct tty_struct *get_current_tty(void); + extern void tty_default_fops(struct file_operations *fops); + extern struct tty_struct *alloc_tty_struct(void); +-extern int tty_add_file(struct tty_struct *tty, struct file *file); ++extern int tty_alloc_file(struct file *file); ++extern void tty_add_file(struct tty_struct *tty, struct file *file); ++extern void tty_free_file(struct file *file); + extern void free_tty_struct(struct tty_struct *tty); + extern void initialize_tty_struct(struct tty_struct *tty, + struct tty_driver *driver, int idx); +diff --git a/include/linux/usb/hcd.h b/include/linux/usb/hcd.h +index 0097136..c0ecc5a 100644 +--- a/include/linux/usb/hcd.h ++++ b/include/linux/usb/hcd.h +@@ -178,7 +178,7 @@ struct usb_hcd { + * this structure. + */ + unsigned long hcd_priv[0] +- __attribute__ ((aligned(sizeof(unsigned long)))); ++ __attribute__ ((aligned(sizeof(s64)))); + }; + + /* 2.4 does this a bit differently ... */ +diff --git a/include/linux/vmalloc.h b/include/linux/vmalloc.h +index 9332e52..687fb11 100644 +--- a/include/linux/vmalloc.h ++++ b/include/linux/vmalloc.h +@@ -13,6 +13,7 @@ struct vm_area_struct; /* vma defining user mapping in mm_types.h */ + #define VM_MAP 0x00000004 /* vmap()ed pages */ + #define VM_USERMAP 0x00000008 /* suitable for remap_vmalloc_range */ + #define VM_VPAGES 0x00000010 /* buffer for pages was vmalloc'ed */ ++#define VM_UNLIST 0x00000020 /* vm_struct is not listed in vmlist */ + /* bits [20..32] reserved for arch specific ioremap internals */ + + /* +diff --git a/include/net/flow.h b/include/net/flow.h +index c6d5fe5..32359fd 100644 +--- a/include/net/flow.h ++++ b/include/net/flow.h +@@ -7,6 +7,7 @@ + #ifndef _NET_FLOW_H + #define _NET_FLOW_H + ++#include <linux/socket.h> + #include <linux/in6.h> + #include <asm/atomic.h> + +@@ -68,7 +69,7 @@ struct flowi4 { + #define fl4_ipsec_spi uli.spi + #define fl4_mh_type uli.mht.type + #define fl4_gre_key uli.gre_key +-}; ++} __attribute__((__aligned__(BITS_PER_LONG/8))); + + static inline void flowi4_init_output(struct flowi4 *fl4, int oif, + __u32 mark, __u8 tos, __u8 scope, +@@ -112,7 +113,7 @@ struct flowi6 { + #define fl6_ipsec_spi uli.spi + #define fl6_mh_type uli.mht.type + #define fl6_gre_key uli.gre_key +-}; ++} __attribute__((__aligned__(BITS_PER_LONG/8))); + + struct flowidn { + struct flowi_common __fl_common; +@@ -127,7 +128,7 @@ struct flowidn { + union flowi_uli uli; + #define fld_sport uli.ports.sport + #define fld_dport uli.ports.dport +-}; ++} __attribute__((__aligned__(BITS_PER_LONG/8))); + + struct flowi { + union { +@@ -161,6 +162,24 @@ static inline struct flowi *flowidn_to_flowi(struct flowidn *fldn) + return container_of(fldn, struct flowi, u.dn); + } + ++typedef unsigned long flow_compare_t; ++ ++static inline size_t flow_key_size(u16 family) ++{ ++ switch (family) { ++ case AF_INET: ++ BUILD_BUG_ON(sizeof(struct flowi4) % sizeof(flow_compare_t)); ++ return sizeof(struct flowi4) / sizeof(flow_compare_t); ++ case AF_INET6: ++ BUILD_BUG_ON(sizeof(struct flowi6) % sizeof(flow_compare_t)); ++ return sizeof(struct flowi6) / sizeof(flow_compare_t); ++ case AF_DECnet: ++ BUILD_BUG_ON(sizeof(struct flowidn) % sizeof(flow_compare_t)); ++ return sizeof(struct flowidn) / sizeof(flow_compare_t); ++ } ++ return 0; ++} ++ + #define FLOW_DIR_IN 0 + #define FLOW_DIR_OUT 1 + #define FLOW_DIR_FWD 2 +diff --git a/kernel/irq/pm.c b/kernel/irq/pm.c +index f76fc00..15e53b1 100644 +--- a/kernel/irq/pm.c ++++ b/kernel/irq/pm.c +@@ -9,6 +9,7 @@ + #include <linux/irq.h> + #include <linux/module.h> + #include <linux/interrupt.h> ++#include <linux/syscore_ops.h> + + #include "internals.h" + +@@ -39,25 +40,58 @@ void suspend_device_irqs(void) + } + EXPORT_SYMBOL_GPL(suspend_device_irqs); + +-/** +- * resume_device_irqs - enable interrupt lines disabled by suspend_device_irqs() +- * +- * Enable all interrupt lines previously disabled by suspend_device_irqs() that +- * have the IRQS_SUSPENDED flag set. +- */ +-void resume_device_irqs(void) ++static void resume_irqs(bool want_early) + { + struct irq_desc *desc; + int irq; + + for_each_irq_desc(irq, desc) { + unsigned long flags; ++ bool is_early = desc->action && ++ desc->action->flags & IRQF_EARLY_RESUME; ++ ++ if (is_early != want_early) ++ continue; + + raw_spin_lock_irqsave(&desc->lock, flags); + __enable_irq(desc, irq, true); + raw_spin_unlock_irqrestore(&desc->lock, flags); + } + } ++ ++/** ++ * irq_pm_syscore_ops - enable interrupt lines early ++ * ++ * Enable all interrupt lines with %IRQF_EARLY_RESUME set. ++ */ ++static void irq_pm_syscore_resume(void) ++{ ++ resume_irqs(true); ++} ++ ++static struct syscore_ops irq_pm_syscore_ops = { ++ .resume = irq_pm_syscore_resume, ++}; ++ ++static int __init irq_pm_init_ops(void) ++{ ++ register_syscore_ops(&irq_pm_syscore_ops); ++ return 0; ++} ++ ++device_initcall(irq_pm_init_ops); ++ ++/** ++ * resume_device_irqs - enable interrupt lines disabled by suspend_device_irqs() ++ * ++ * Enable all non-%IRQF_EARLY_RESUME interrupt lines previously ++ * disabled by suspend_device_irqs() that have the IRQS_SUSPENDED flag ++ * set as well as those with %IRQF_FORCE_RESUME. ++ */ ++void resume_device_irqs(void) ++{ ++ resume_irqs(false); ++} + EXPORT_SYMBOL_GPL(resume_device_irqs); + + /** +diff --git a/kernel/kmod.c b/kernel/kmod.c +index 47613df..fabfe54 100644 +--- a/kernel/kmod.c ++++ b/kernel/kmod.c +@@ -114,10 +114,12 @@ int __request_module(bool wait, const char *fmt, ...) + atomic_inc(&kmod_concurrent); + if (atomic_read(&kmod_concurrent) > max_modprobes) { + /* We may be blaming an innocent here, but unlikely */ +- if (kmod_loop_msg++ < 5) ++ if (kmod_loop_msg < 5) { + printk(KERN_ERR + "request_module: runaway loop modprobe %s\n", + module_name); ++ kmod_loop_msg++; ++ } + atomic_dec(&kmod_concurrent); + return -ENOMEM; + } +diff --git a/kernel/power/suspend.c b/kernel/power/suspend.c +index 1c41ba2..449ccc9 100644 +--- a/kernel/power/suspend.c ++++ b/kernel/power/suspend.c +@@ -307,7 +307,7 @@ int enter_state(suspend_state_t state) + */ + int pm_suspend(suspend_state_t state) + { +- if (state > PM_SUSPEND_ON && state <= PM_SUSPEND_MAX) ++ if (state > PM_SUSPEND_ON && state < PM_SUSPEND_MAX) + return enter_state(state); + return -EINVAL; + } +diff --git a/kernel/signal.c b/kernel/signal.c +index 415d85d..43fee1c 100644 +--- a/kernel/signal.c ++++ b/kernel/signal.c +@@ -1894,21 +1894,19 @@ static int do_signal_stop(int signr) + */ + if (!(sig->flags & SIGNAL_STOP_STOPPED)) + sig->group_exit_code = signr; +- else +- WARN_ON_ONCE(!task_ptrace(current)); + + current->group_stop &= ~GROUP_STOP_SIGMASK; + current->group_stop |= signr | gstop; + sig->group_stop_count = 1; + for (t = next_thread(current); t != current; + t = next_thread(t)) { +- t->group_stop &= ~GROUP_STOP_SIGMASK; + /* + * Setting state to TASK_STOPPED for a group + * stop is always done with the siglock held, + * so this check has no races. + */ + if (!(t->flags & PF_EXITING) && !task_is_stopped(t)) { ++ t->group_stop &= ~GROUP_STOP_SIGMASK; + t->group_stop |= signr | gstop; + sig->group_stop_count++; + signal_wake_up(t, 0); +diff --git a/kernel/time.c b/kernel/time.c +index 8e8dc6d..d776062 100644 +--- a/kernel/time.c ++++ b/kernel/time.c +@@ -575,7 +575,7 @@ EXPORT_SYMBOL(jiffies_to_timeval); + /* + * Convert jiffies/jiffies_64 to clock_t and back. + */ +-clock_t jiffies_to_clock_t(long x) ++clock_t jiffies_to_clock_t(unsigned long x) + { + #if (TICK_NSEC % (NSEC_PER_SEC / USER_HZ)) == 0 + # if HZ < USER_HZ +diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c +index ee9c921..0731e81a 100644 +--- a/kernel/trace/trace.c ++++ b/kernel/trace/trace.c +@@ -3704,8 +3704,6 @@ tracing_buffers_read(struct file *filp, char __user *ubuf, + if (info->read < PAGE_SIZE) + goto read; + +- info->read = 0; +- + trace_access_lock(info->cpu); + ret = ring_buffer_read_page(info->tr->buffer, + &info->spare, +@@ -3715,6 +3713,8 @@ tracing_buffers_read(struct file *filp, char __user *ubuf, + if (ret < 0) + return 0; + ++ info->read = 0; ++ + read: + size = PAGE_SIZE - info->read; + if (size > count) +diff --git a/lib/kobject_uevent.c b/lib/kobject_uevent.c +index 70af0a7..ad72a03 100644 +--- a/lib/kobject_uevent.c ++++ b/lib/kobject_uevent.c +@@ -282,7 +282,7 @@ int kobject_uevent_env(struct kobject *kobj, enum kobject_action action, + kobj_bcast_filter, + kobj); + /* ENOBUFS should be handled in userspace */ +- if (retval == -ENOBUFS) ++ if (retval == -ENOBUFS || retval == -ESRCH) + retval = 0; + } else + retval = -ENOMEM; +diff --git a/lib/nlattr.c b/lib/nlattr.c +index ac09f22..a8408b6 100644 +--- a/lib/nlattr.c ++++ b/lib/nlattr.c +@@ -20,6 +20,7 @@ static const u16 nla_attr_minlen[NLA_TYPE_MAX+1] = { + [NLA_U16] = sizeof(u16), + [NLA_U32] = sizeof(u32), + [NLA_U64] = sizeof(u64), ++ [NLA_MSECS] = sizeof(u64), + [NLA_NESTED] = NLA_HDRLEN, + }; + +diff --git a/mm/huge_memory.c b/mm/huge_memory.c +index 81532f2..cc5acf9 100644 +--- a/mm/huge_memory.c ++++ b/mm/huge_memory.c +@@ -989,7 +989,7 @@ struct page *follow_trans_huge_pmd(struct mm_struct *mm, + page += (addr & ~HPAGE_PMD_MASK) >> PAGE_SHIFT; + VM_BUG_ON(!PageCompound(page)); + if (flags & FOLL_GET) +- get_page(page); ++ get_page_foll(page); + + out: + return page; +@@ -1156,6 +1156,7 @@ static void __split_huge_page_refcount(struct page *page) + unsigned long head_index = page->index; + struct zone *zone = page_zone(page); + int zonestat; ++ int tail_count = 0; + + /* prevent PageLRU to go away from under us, and freeze lru stats */ + spin_lock_irq(&zone->lru_lock); +@@ -1164,11 +1165,27 @@ static void __split_huge_page_refcount(struct page *page) + for (i = 1; i < HPAGE_PMD_NR; i++) { + struct page *page_tail = page + i; + +- /* tail_page->_count cannot change */ +- atomic_sub(atomic_read(&page_tail->_count), &page->_count); +- BUG_ON(page_count(page) <= 0); +- atomic_add(page_mapcount(page) + 1, &page_tail->_count); +- BUG_ON(atomic_read(&page_tail->_count) <= 0); ++ /* tail_page->_mapcount cannot change */ ++ BUG_ON(page_mapcount(page_tail) < 0); ++ tail_count += page_mapcount(page_tail); ++ /* check for overflow */ ++ BUG_ON(tail_count < 0); ++ BUG_ON(atomic_read(&page_tail->_count) != 0); ++ /* ++ * tail_page->_count is zero and not changing from ++ * under us. But get_page_unless_zero() may be running ++ * from under us on the tail_page. If we used ++ * atomic_set() below instead of atomic_add(), we ++ * would then run atomic_set() concurrently with ++ * get_page_unless_zero(), and atomic_set() is ++ * implemented in C not using locked ops. spin_unlock ++ * on x86 sometime uses locked ops because of PPro ++ * errata 66, 92, so unless somebody can guarantee ++ * atomic_set() here would be safe on all archs (and ++ * not only on x86), it's safer to use atomic_add(). ++ */ ++ atomic_add(page_mapcount(page) + page_mapcount(page_tail) + 1, ++ &page_tail->_count); + + /* after clearing PageTail the gup refcount can be released */ + smp_mb(); +@@ -1186,10 +1203,7 @@ static void __split_huge_page_refcount(struct page *page) + (1L << PG_uptodate))); + page_tail->flags |= (1L << PG_dirty); + +- /* +- * 1) clear PageTail before overwriting first_page +- * 2) clear PageTail before clearing PageHead for VM_BUG_ON +- */ ++ /* clear PageTail before overwriting first_page */ + smp_wmb(); + + /* +@@ -1206,7 +1220,6 @@ static void __split_huge_page_refcount(struct page *page) + * status is achieved setting a reserved bit in the + * pmd, not by clearing the present bit. + */ +- BUG_ON(page_mapcount(page_tail)); + page_tail->_mapcount = page->_mapcount; + + BUG_ON(page_tail->mapping); +@@ -1223,6 +1236,8 @@ static void __split_huge_page_refcount(struct page *page) + + lru_add_page_tail(zone, page, page_tail); + } ++ atomic_sub(tail_count, &page->_count); ++ BUG_ON(atomic_read(&page->_count) <= 0); + + __dec_zone_page_state(page, NR_ANON_TRANSPARENT_HUGEPAGES); + __mod_zone_page_state(zone, NR_ANON_PAGES, HPAGE_PMD_NR); +diff --git a/mm/internal.h b/mm/internal.h +index d071d38..2189af4 100644 +--- a/mm/internal.h ++++ b/mm/internal.h +@@ -37,6 +37,52 @@ static inline void __put_page(struct page *page) + atomic_dec(&page->_count); + } + ++static inline void __get_page_tail_foll(struct page *page, ++ bool get_page_head) ++{ ++ /* ++ * If we're getting a tail page, the elevated page->_count is ++ * required only in the head page and we will elevate the head ++ * page->_count and tail page->_mapcount. ++ * ++ * We elevate page_tail->_mapcount for tail pages to force ++ * page_tail->_count to be zero at all times to avoid getting ++ * false positives from get_page_unless_zero() with ++ * speculative page access (like in ++ * page_cache_get_speculative()) on tail pages. ++ */ ++ VM_BUG_ON(atomic_read(&page->first_page->_count) <= 0); ++ VM_BUG_ON(atomic_read(&page->_count) != 0); ++ VM_BUG_ON(page_mapcount(page) < 0); ++ if (get_page_head) ++ atomic_inc(&page->first_page->_count); ++ atomic_inc(&page->_mapcount); ++} ++ ++/* ++ * This is meant to be called as the FOLL_GET operation of ++ * follow_page() and it must be called while holding the proper PT ++ * lock while the pte (or pmd_trans_huge) is still mapping the page. ++ */ ++static inline void get_page_foll(struct page *page) ++{ ++ if (unlikely(PageTail(page))) ++ /* ++ * This is safe only because ++ * __split_huge_page_refcount() can't run under ++ * get_page_foll() because we hold the proper PT lock. ++ */ ++ __get_page_tail_foll(page, true); ++ else { ++ /* ++ * Getting a normal page or the head of a compound page ++ * requires to already have an elevated page->_count. ++ */ ++ VM_BUG_ON(atomic_read(&page->_count) <= 0); ++ atomic_inc(&page->_count); ++ } ++} ++ + extern unsigned long highest_memmap_pfn; + + /* +diff --git a/mm/memory.c b/mm/memory.c +index d961e19..95a7799 100644 +--- a/mm/memory.c ++++ b/mm/memory.c +@@ -1514,7 +1514,7 @@ split_fallthrough: + } + + if (flags & FOLL_GET) +- get_page(page); ++ get_page_foll(page); + if (flags & FOLL_TOUCH) { + if ((flags & FOLL_WRITE) && + !pte_dirty(pte) && !PageDirty(page)) +diff --git a/mm/swap.c b/mm/swap.c +index 3a442f1..87627f1 100644 +--- a/mm/swap.c ++++ b/mm/swap.c +@@ -78,39 +78,22 @@ static void put_compound_page(struct page *page) + { + if (unlikely(PageTail(page))) { + /* __split_huge_page_refcount can run under us */ +- struct page *page_head = page->first_page; +- smp_rmb(); +- /* +- * If PageTail is still set after smp_rmb() we can be sure +- * that the page->first_page we read wasn't a dangling pointer. +- * See __split_huge_page_refcount() smp_wmb(). +- */ +- if (likely(PageTail(page) && get_page_unless_zero(page_head))) { ++ struct page *page_head = compound_trans_head(page); ++ ++ if (likely(page != page_head && ++ get_page_unless_zero(page_head))) { + unsigned long flags; + /* +- * Verify that our page_head wasn't converted +- * to a a regular page before we got a +- * reference on it. ++ * page_head wasn't a dangling pointer but it ++ * may not be a head page anymore by the time ++ * we obtain the lock. That is ok as long as it ++ * can't be freed from under us. + */ +- if (unlikely(!PageHead(page_head))) { +- /* PageHead is cleared after PageTail */ +- smp_rmb(); +- VM_BUG_ON(PageTail(page)); +- goto out_put_head; +- } +- /* +- * Only run compound_lock on a valid PageHead, +- * after having it pinned with +- * get_page_unless_zero() above. +- */ +- smp_mb(); +- /* page_head wasn't a dangling pointer */ + flags = compound_lock_irqsave(page_head); + if (unlikely(!PageTail(page))) { + /* __split_huge_page_refcount run before us */ + compound_unlock_irqrestore(page_head, flags); + VM_BUG_ON(PageHead(page_head)); +- out_put_head: + if (put_page_testzero(page_head)) + __put_single_page(page_head); + out_put_single: +@@ -121,16 +104,17 @@ static void put_compound_page(struct page *page) + VM_BUG_ON(page_head != page->first_page); + /* + * We can release the refcount taken by +- * get_page_unless_zero now that +- * split_huge_page_refcount is blocked on the +- * compound_lock. ++ * get_page_unless_zero() now that ++ * __split_huge_page_refcount() is blocked on ++ * the compound_lock. + */ + if (put_page_testzero(page_head)) + VM_BUG_ON(1); + /* __split_huge_page_refcount will wait now */ +- VM_BUG_ON(atomic_read(&page->_count) <= 0); +- atomic_dec(&page->_count); ++ VM_BUG_ON(page_mapcount(page) <= 0); ++ atomic_dec(&page->_mapcount); + VM_BUG_ON(atomic_read(&page_head->_count) <= 0); ++ VM_BUG_ON(atomic_read(&page->_count) != 0); + compound_unlock_irqrestore(page_head, flags); + if (put_page_testzero(page_head)) { + if (PageHead(page_head)) +@@ -160,6 +144,45 @@ void put_page(struct page *page) + } + EXPORT_SYMBOL(put_page); + ++/* ++ * This function is exported but must not be called by anything other ++ * than get_page(). It implements the slow path of get_page(). ++ */ ++bool __get_page_tail(struct page *page) ++{ ++ /* ++ * This takes care of get_page() if run on a tail page ++ * returned by one of the get_user_pages/follow_page variants. ++ * get_user_pages/follow_page itself doesn't need the compound ++ * lock because it runs __get_page_tail_foll() under the ++ * proper PT lock that already serializes against ++ * split_huge_page(). ++ */ ++ unsigned long flags; ++ bool got = false; ++ struct page *page_head = compound_trans_head(page); ++ ++ if (likely(page != page_head && get_page_unless_zero(page_head))) { ++ /* ++ * page_head wasn't a dangling pointer but it ++ * may not be a head page anymore by the time ++ * we obtain the lock. That is ok as long as it ++ * can't be freed from under us. ++ */ ++ flags = compound_lock_irqsave(page_head); ++ /* here __split_huge_page_refcount won't run anymore */ ++ if (likely(PageTail(page))) { ++ __get_page_tail_foll(page, false); ++ got = true; ++ } ++ compound_unlock_irqrestore(page_head, flags); ++ if (unlikely(!got)) ++ put_page(page_head); ++ } ++ return got; ++} ++EXPORT_SYMBOL(__get_page_tail); ++ + /** + * put_pages_list() - release a list of pages + * @pages: list of pages threaded on page->lru +diff --git a/mm/vmalloc.c b/mm/vmalloc.c +index 45ece89..65d5fd2 100644 +--- a/mm/vmalloc.c ++++ b/mm/vmalloc.c +@@ -1267,18 +1267,22 @@ EXPORT_SYMBOL_GPL(map_vm_area); + DEFINE_RWLOCK(vmlist_lock); + struct vm_struct *vmlist; + +-static void insert_vmalloc_vm(struct vm_struct *vm, struct vmap_area *va, ++static void setup_vmalloc_vm(struct vm_struct *vm, struct vmap_area *va, + unsigned long flags, void *caller) + { +- struct vm_struct *tmp, **p; +- + vm->flags = flags; + vm->addr = (void *)va->va_start; + vm->size = va->va_end - va->va_start; + vm->caller = caller; + va->private = vm; + va->flags |= VM_VM_AREA; ++} ++ ++static void insert_vmalloc_vmlist(struct vm_struct *vm) ++{ ++ struct vm_struct *tmp, **p; + ++ vm->flags &= ~VM_UNLIST; + write_lock(&vmlist_lock); + for (p = &vmlist; (tmp = *p) != NULL; p = &tmp->next) { + if (tmp->addr >= vm->addr) +@@ -1289,6 +1293,13 @@ static void insert_vmalloc_vm(struct vm_struct *vm, struct vmap_area *va, + write_unlock(&vmlist_lock); + } + ++static void insert_vmalloc_vm(struct vm_struct *vm, struct vmap_area *va, ++ unsigned long flags, void *caller) ++{ ++ setup_vmalloc_vm(vm, va, flags, caller); ++ insert_vmalloc_vmlist(vm); ++} ++ + static struct vm_struct *__get_vm_area_node(unsigned long size, + unsigned long align, unsigned long flags, unsigned long start, + unsigned long end, int node, gfp_t gfp_mask, void *caller) +@@ -1327,7 +1338,18 @@ static struct vm_struct *__get_vm_area_node(unsigned long size, + return NULL; + } + +- insert_vmalloc_vm(area, va, flags, caller); ++ /* ++ * When this function is called from __vmalloc_node_range, ++ * we do not add vm_struct to vmlist here to avoid ++ * accessing uninitialized members of vm_struct such as ++ * pages and nr_pages fields. They will be set later. ++ * To distinguish it from others, we use a VM_UNLIST flag. ++ */ ++ if (flags & VM_UNLIST) ++ setup_vmalloc_vm(area, va, flags, caller); ++ else ++ insert_vmalloc_vm(area, va, flags, caller); ++ + return area; + } + +@@ -1395,17 +1417,20 @@ struct vm_struct *remove_vm_area(const void *addr) + va = find_vmap_area((unsigned long)addr); + if (va && va->flags & VM_VM_AREA) { + struct vm_struct *vm = va->private; +- struct vm_struct *tmp, **p; +- /* +- * remove from list and disallow access to this vm_struct +- * before unmap. (address range confliction is maintained by +- * vmap.) +- */ +- write_lock(&vmlist_lock); +- for (p = &vmlist; (tmp = *p) != vm; p = &tmp->next) +- ; +- *p = tmp->next; +- write_unlock(&vmlist_lock); ++ ++ if (!(vm->flags & VM_UNLIST)) { ++ struct vm_struct *tmp, **p; ++ /* ++ * remove from list and disallow access to ++ * this vm_struct before unmap. (address range ++ * confliction is maintained by vmap.) ++ */ ++ write_lock(&vmlist_lock); ++ for (p = &vmlist; (tmp = *p) != vm; p = &tmp->next) ++ ; ++ *p = tmp->next; ++ write_unlock(&vmlist_lock); ++ } + + vmap_debug_free_range(va->va_start, va->va_end); + free_unmap_vmap_area(va); +@@ -1616,8 +1641,8 @@ void *__vmalloc_node_range(unsigned long size, unsigned long align, + if (!size || (size >> PAGE_SHIFT) > totalram_pages) + return NULL; + +- area = __get_vm_area_node(size, align, VM_ALLOC, start, end, node, +- gfp_mask, caller); ++ area = __get_vm_area_node(size, align, VM_ALLOC | VM_UNLIST, ++ start, end, node, gfp_mask, caller); + + if (!area) + return NULL; +@@ -1625,6 +1650,12 @@ void *__vmalloc_node_range(unsigned long size, unsigned long align, + addr = __vmalloc_area_node(area, gfp_mask, prot, node, caller); + + /* ++ * In this function, newly allocated vm_struct is not added ++ * to vmlist at __get_vm_area_node(). so, it is added here. ++ */ ++ insert_vmalloc_vmlist(area); ++ ++ /* + * A ref_count = 3 is needed because the vm_struct and vmap_area + * structures allocated in the __get_vm_area_node() function contain + * references to the virtual address of the vmalloc'ed block. +diff --git a/net/bridge/br_device.c b/net/bridge/br_device.c +index 32b8f9f..ff3ed60 100644 +--- a/net/bridge/br_device.c ++++ b/net/bridge/br_device.c +@@ -91,7 +91,6 @@ static int br_dev_open(struct net_device *dev) + { + struct net_bridge *br = netdev_priv(dev); + +- netif_carrier_off(dev); + netdev_update_features(dev); + netif_start_queue(dev); + br_stp_enable_bridge(br); +@@ -108,8 +107,6 @@ static int br_dev_stop(struct net_device *dev) + { + struct net_bridge *br = netdev_priv(dev); + +- netif_carrier_off(dev); +- + br_stp_disable_bridge(br); + br_multicast_stop(br); + +diff --git a/net/bridge/br_if.c b/net/bridge/br_if.c +index 6f156c1..4490873 100644 +--- a/net/bridge/br_if.c ++++ b/net/bridge/br_if.c +@@ -161,9 +161,10 @@ static void del_nbp(struct net_bridge_port *p) + call_rcu(&p->rcu, destroy_nbp_rcu); + } + +-/* called with RTNL */ +-static void del_br(struct net_bridge *br, struct list_head *head) ++/* Delete bridge device */ ++void br_dev_delete(struct net_device *dev, struct list_head *head) + { ++ struct net_bridge *br = netdev_priv(dev); + struct net_bridge_port *p, *n; + + list_for_each_entry_safe(p, n, &br->port_list, list) { +@@ -268,7 +269,7 @@ int br_del_bridge(struct net *net, const char *name) + } + + else +- del_br(netdev_priv(dev), NULL); ++ br_dev_delete(dev, NULL); + + rtnl_unlock(); + return ret; +@@ -445,7 +446,7 @@ void __net_exit br_net_exit(struct net *net) + rtnl_lock(); + for_each_netdev(net, dev) + if (dev->priv_flags & IFF_EBRIDGE) +- del_br(netdev_priv(dev), &list); ++ br_dev_delete(dev, &list); + + unregister_netdevice_many(&list); + rtnl_unlock(); +diff --git a/net/bridge/br_netlink.c b/net/bridge/br_netlink.c +index ffb0dc4..2c16055 100644 +--- a/net/bridge/br_netlink.c ++++ b/net/bridge/br_netlink.c +@@ -208,6 +208,7 @@ static struct rtnl_link_ops br_link_ops __read_mostly = { + .priv_size = sizeof(struct net_bridge), + .setup = br_dev_setup, + .validate = br_validate, ++ .dellink = br_dev_delete, + }; + + int __init br_netlink_init(void) +diff --git a/net/bridge/br_private.h b/net/bridge/br_private.h +index 78cc364..857a021 100644 +--- a/net/bridge/br_private.h ++++ b/net/bridge/br_private.h +@@ -294,6 +294,7 @@ static inline int br_is_root_bridge(const struct net_bridge *br) + + /* br_device.c */ + extern void br_dev_setup(struct net_device *dev); ++extern void br_dev_delete(struct net_device *dev, struct list_head *list); + extern netdev_tx_t br_dev_xmit(struct sk_buff *skb, + struct net_device *dev); + #ifdef CONFIG_NET_POLL_CONTROLLER +diff --git a/net/caif/caif_dev.c b/net/caif/caif_dev.c +index 682c0fe..dbdaa95 100644 +--- a/net/caif/caif_dev.c ++++ b/net/caif/caif_dev.c +@@ -209,8 +209,7 @@ static int caif_device_notify(struct notifier_block *me, unsigned long what, + enum cfcnfg_phy_preference pref; + enum cfcnfg_phy_type phy_type; + struct cfcnfg *cfg; +- struct caif_device_entry_list *caifdevs = +- caif_device_list(dev_net(dev)); ++ struct caif_device_entry_list *caifdevs; + + if (dev->type != ARPHRD_CAIF) + return 0; +@@ -219,6 +218,8 @@ static int caif_device_notify(struct notifier_block *me, unsigned long what, + if (cfg == NULL) + return 0; + ++ caifdevs = caif_device_list(dev_net(dev)); ++ + switch (what) { + case NETDEV_REGISTER: + caifd = caif_device_alloc(dev); +diff --git a/net/can/bcm.c b/net/can/bcm.c +index 184a657..c6cc66f 100644 +--- a/net/can/bcm.c ++++ b/net/can/bcm.c +@@ -343,6 +343,18 @@ static void bcm_send_to_user(struct bcm_op *op, struct bcm_msg_head *head, + } + } + ++static void bcm_tx_start_timer(struct bcm_op *op) ++{ ++ if (op->kt_ival1.tv64 && op->count) ++ hrtimer_start(&op->timer, ++ ktime_add(ktime_get(), op->kt_ival1), ++ HRTIMER_MODE_ABS); ++ else if (op->kt_ival2.tv64) ++ hrtimer_start(&op->timer, ++ ktime_add(ktime_get(), op->kt_ival2), ++ HRTIMER_MODE_ABS); ++} ++ + static void bcm_tx_timeout_tsklet(unsigned long data) + { + struct bcm_op *op = (struct bcm_op *)data; +@@ -364,26 +376,12 @@ static void bcm_tx_timeout_tsklet(unsigned long data) + + bcm_send_to_user(op, &msg_head, NULL, 0); + } +- } +- +- if (op->kt_ival1.tv64 && (op->count > 0)) { +- +- /* send (next) frame */ + bcm_can_tx(op); +- hrtimer_start(&op->timer, +- ktime_add(ktime_get(), op->kt_ival1), +- HRTIMER_MODE_ABS); + +- } else { +- if (op->kt_ival2.tv64) { ++ } else if (op->kt_ival2.tv64) ++ bcm_can_tx(op); + +- /* send (next) frame */ +- bcm_can_tx(op); +- hrtimer_start(&op->timer, +- ktime_add(ktime_get(), op->kt_ival2), +- HRTIMER_MODE_ABS); +- } +- } ++ bcm_tx_start_timer(op); + } + + /* +@@ -963,23 +961,20 @@ static int bcm_tx_setup(struct bcm_msg_head *msg_head, struct msghdr *msg, + hrtimer_cancel(&op->timer); + } + +- if ((op->flags & STARTTIMER) && +- ((op->kt_ival1.tv64 && op->count) || op->kt_ival2.tv64)) { +- ++ if (op->flags & STARTTIMER) { ++ hrtimer_cancel(&op->timer); + /* spec: send can_frame when starting timer */ + op->flags |= TX_ANNOUNCE; +- +- if (op->kt_ival1.tv64 && (op->count > 0)) { +- /* op->count-- is done in bcm_tx_timeout_handler */ +- hrtimer_start(&op->timer, op->kt_ival1, +- HRTIMER_MODE_REL); +- } else +- hrtimer_start(&op->timer, op->kt_ival2, +- HRTIMER_MODE_REL); + } + +- if (op->flags & TX_ANNOUNCE) ++ if (op->flags & TX_ANNOUNCE) { + bcm_can_tx(op); ++ if (op->count) ++ op->count--; ++ } ++ ++ if (op->flags & STARTTIMER) ++ bcm_tx_start_timer(op); + + return msg_head->nframes * CFSIZ + MHSIZ; + } +diff --git a/net/core/dev.c b/net/core/dev.c +index 9c58c1e..f14f601 100644 +--- a/net/core/dev.c ++++ b/net/core/dev.c +@@ -6105,6 +6105,7 @@ int dev_change_net_namespace(struct net_device *dev, struct net *net, const char + */ + call_netdevice_notifiers(NETDEV_UNREGISTER, dev); + call_netdevice_notifiers(NETDEV_UNREGISTER_BATCH, dev); ++ rtmsg_ifinfo(RTM_DELLINK, dev, ~0U); + + /* + * Flush the unicast and multicast chains +diff --git a/net/core/flow.c b/net/core/flow.c +index 990703b..a6bda2a 100644 +--- a/net/core/flow.c ++++ b/net/core/flow.c +@@ -172,29 +172,26 @@ static void flow_new_hash_rnd(struct flow_cache *fc, + + static u32 flow_hash_code(struct flow_cache *fc, + struct flow_cache_percpu *fcp, +- const struct flowi *key) ++ const struct flowi *key, ++ size_t keysize) + { + const u32 *k = (const u32 *) key; ++ const u32 length = keysize * sizeof(flow_compare_t) / sizeof(u32); + +- return jhash2(k, (sizeof(*key) / sizeof(u32)), fcp->hash_rnd) ++ return jhash2(k, length, fcp->hash_rnd) + & (flow_cache_hash_size(fc) - 1); + } + +-typedef unsigned long flow_compare_t; +- + /* I hear what you're saying, use memcmp. But memcmp cannot make +- * important assumptions that we can here, such as alignment and +- * constant size. ++ * important assumptions that we can here, such as alignment. + */ +-static int flow_key_compare(const struct flowi *key1, const struct flowi *key2) ++static int flow_key_compare(const struct flowi *key1, const struct flowi *key2, ++ size_t keysize) + { + const flow_compare_t *k1, *k1_lim, *k2; +- const int n_elem = sizeof(struct flowi) / sizeof(flow_compare_t); +- +- BUILD_BUG_ON(sizeof(struct flowi) % sizeof(flow_compare_t)); + + k1 = (const flow_compare_t *) key1; +- k1_lim = k1 + n_elem; ++ k1_lim = k1 + keysize; + + k2 = (const flow_compare_t *) key2; + +@@ -215,6 +212,7 @@ flow_cache_lookup(struct net *net, const struct flowi *key, u16 family, u8 dir, + struct flow_cache_entry *fle, *tfle; + struct hlist_node *entry; + struct flow_cache_object *flo; ++ size_t keysize; + unsigned int hash; + + local_bh_disable(); +@@ -222,6 +220,11 @@ flow_cache_lookup(struct net *net, const struct flowi *key, u16 family, u8 dir, + + fle = NULL; + flo = NULL; ++ ++ keysize = flow_key_size(family); ++ if (!keysize) ++ goto nocache; ++ + /* Packet really early in init? Making flow_cache_init a + * pre-smp initcall would solve this. --RR */ + if (!fcp->hash_table) +@@ -230,11 +233,11 @@ flow_cache_lookup(struct net *net, const struct flowi *key, u16 family, u8 dir, + if (fcp->hash_rnd_recalc) + flow_new_hash_rnd(fc, fcp); + +- hash = flow_hash_code(fc, fcp, key); ++ hash = flow_hash_code(fc, fcp, key, keysize); + hlist_for_each_entry(tfle, entry, &fcp->hash_table[hash], u.hlist) { + if (tfle->family == family && + tfle->dir == dir && +- flow_key_compare(key, &tfle->key) == 0) { ++ flow_key_compare(key, &tfle->key, keysize) == 0) { + fle = tfle; + break; + } +@@ -248,7 +251,7 @@ flow_cache_lookup(struct net *net, const struct flowi *key, u16 family, u8 dir, + if (fle) { + fle->family = family; + fle->dir = dir; +- memcpy(&fle->key, key, sizeof(*key)); ++ memcpy(&fle->key, key, keysize * sizeof(flow_compare_t)); + fle->object = NULL; + hlist_add_head(&fle->u.hlist, &fcp->hash_table[hash]); + fcp->hash_count++; +diff --git a/net/core/sock.c b/net/core/sock.c +index 6e81978..aebb419 100644 +--- a/net/core/sock.c ++++ b/net/core/sock.c +@@ -1257,6 +1257,7 @@ struct sock *sk_clone(const struct sock *sk, const gfp_t priority) + /* It is still raw copy of parent, so invalidate + * destructor and make plain sk_free() */ + newsk->sk_destruct = NULL; ++ bh_unlock_sock(newsk); + sk_free(newsk); + newsk = NULL; + goto out; +diff --git a/net/core/timestamping.c b/net/core/timestamping.c +index 7e7ca37..97d036a 100644 +--- a/net/core/timestamping.c ++++ b/net/core/timestamping.c +@@ -57,9 +57,13 @@ void skb_clone_tx_timestamp(struct sk_buff *skb) + case PTP_CLASS_V2_VLAN: + phydev = skb->dev->phydev; + if (likely(phydev->drv->txtstamp)) { ++ if (!atomic_inc_not_zero(&sk->sk_refcnt)) ++ return; + clone = skb_clone(skb, GFP_ATOMIC); +- if (!clone) ++ if (!clone) { ++ sock_put(sk); + return; ++ } + clone->sk = sk; + phydev->drv->txtstamp(phydev, clone, type); + } +@@ -76,8 +80,11 @@ void skb_complete_tx_timestamp(struct sk_buff *skb, + struct sock_exterr_skb *serr; + int err; + +- if (!hwtstamps) ++ if (!hwtstamps) { ++ sock_put(sk); ++ kfree_skb(skb); + return; ++ } + + *skb_hwtstamps(skb) = *hwtstamps; + serr = SKB_EXT_ERR(skb); +@@ -86,6 +93,7 @@ void skb_complete_tx_timestamp(struct sk_buff *skb, + serr->ee.ee_origin = SO_EE_ORIGIN_TIMESTAMPING; + skb->sk = NULL; + err = sock_queue_err_skb(sk, skb); ++ sock_put(sk); + if (err) + kfree_skb(skb); + } +diff --git a/net/ipv4/tcp_input.c b/net/ipv4/tcp_input.c +index b6771f9..c68040f 100644 +--- a/net/ipv4/tcp_input.c ++++ b/net/ipv4/tcp_input.c +@@ -1380,9 +1380,7 @@ static int tcp_shifted_skb(struct sock *sk, struct sk_buff *skb, + + BUG_ON(!pcount); + +- /* Tweak before seqno plays */ +- if (!tcp_is_fack(tp) && tcp_is_sack(tp) && tp->lost_skb_hint && +- !before(TCP_SKB_CB(tp->lost_skb_hint)->seq, TCP_SKB_CB(skb)->seq)) ++ if (skb == tp->lost_skb_hint) + tp->lost_cnt_hint += pcount; + + TCP_SKB_CB(prev)->end_seq += shifted; +diff --git a/net/ipv4/tcp_ipv4.c b/net/ipv4/tcp_ipv4.c +index b3e6956..69790aa 100644 +--- a/net/ipv4/tcp_ipv4.c ++++ b/net/ipv4/tcp_ipv4.c +@@ -909,18 +909,21 @@ int tcp_v4_md5_do_add(struct sock *sk, __be32 addr, + } + sk_nocaps_add(sk, NETIF_F_GSO_MASK); + } +- if (tcp_alloc_md5sig_pool(sk) == NULL) { ++ ++ md5sig = tp->md5sig_info; ++ if (md5sig->entries4 == 0 && ++ tcp_alloc_md5sig_pool(sk) == NULL) { + kfree(newkey); + return -ENOMEM; + } +- md5sig = tp->md5sig_info; + + if (md5sig->alloced4 == md5sig->entries4) { + keys = kmalloc((sizeof(*keys) * + (md5sig->entries4 + 1)), GFP_ATOMIC); + if (!keys) { + kfree(newkey); +- tcp_free_md5sig_pool(); ++ if (md5sig->entries4 == 0) ++ tcp_free_md5sig_pool(); + return -ENOMEM; + } + +@@ -964,6 +967,7 @@ int tcp_v4_md5_do_del(struct sock *sk, __be32 addr) + kfree(tp->md5sig_info->keys4); + tp->md5sig_info->keys4 = NULL; + tp->md5sig_info->alloced4 = 0; ++ tcp_free_md5sig_pool(); + } else if (tp->md5sig_info->entries4 != i) { + /* Need to do some manipulation */ + memmove(&tp->md5sig_info->keys4[i], +@@ -971,7 +975,6 @@ int tcp_v4_md5_do_del(struct sock *sk, __be32 addr) + (tp->md5sig_info->entries4 - i) * + sizeof(struct tcp4_md5sig_key)); + } +- tcp_free_md5sig_pool(); + return 0; + } + } +diff --git a/net/ipv4/xfrm4_policy.c b/net/ipv4/xfrm4_policy.c +index 981e43e..581fe0a 100644 +--- a/net/ipv4/xfrm4_policy.c ++++ b/net/ipv4/xfrm4_policy.c +@@ -79,13 +79,13 @@ static int xfrm4_fill_dst(struct xfrm_dst *xdst, struct net_device *dev, + struct rtable *rt = (struct rtable *)xdst->route; + const struct flowi4 *fl4 = &fl->u.ip4; + +- rt->rt_key_dst = fl4->daddr; +- rt->rt_key_src = fl4->saddr; +- rt->rt_key_tos = fl4->flowi4_tos; +- rt->rt_route_iif = fl4->flowi4_iif; +- rt->rt_iif = fl4->flowi4_iif; +- rt->rt_oif = fl4->flowi4_oif; +- rt->rt_mark = fl4->flowi4_mark; ++ xdst->u.rt.rt_key_dst = fl4->daddr; ++ xdst->u.rt.rt_key_src = fl4->saddr; ++ xdst->u.rt.rt_key_tos = fl4->flowi4_tos; ++ xdst->u.rt.rt_route_iif = fl4->flowi4_iif; ++ xdst->u.rt.rt_iif = fl4->flowi4_iif; ++ xdst->u.rt.rt_oif = fl4->flowi4_oif; ++ xdst->u.rt.rt_mark = fl4->flowi4_mark; + + xdst->u.dst.dev = dev; + dev_hold(dev); +diff --git a/net/ipv6/tcp_ipv6.c b/net/ipv6/tcp_ipv6.c +index 7c43e86..296510a 100644 +--- a/net/ipv6/tcp_ipv6.c ++++ b/net/ipv6/tcp_ipv6.c +@@ -605,7 +605,8 @@ static int tcp_v6_md5_do_add(struct sock *sk, const struct in6_addr *peer, + } + sk_nocaps_add(sk, NETIF_F_GSO_MASK); + } +- if (tcp_alloc_md5sig_pool(sk) == NULL) { ++ if (tp->md5sig_info->entries6 == 0 && ++ tcp_alloc_md5sig_pool(sk) == NULL) { + kfree(newkey); + return -ENOMEM; + } +@@ -614,8 +615,9 @@ static int tcp_v6_md5_do_add(struct sock *sk, const struct in6_addr *peer, + (tp->md5sig_info->entries6 + 1)), GFP_ATOMIC); + + if (!keys) { +- tcp_free_md5sig_pool(); + kfree(newkey); ++ if (tp->md5sig_info->entries6 == 0) ++ tcp_free_md5sig_pool(); + return -ENOMEM; + } + +@@ -661,6 +663,7 @@ static int tcp_v6_md5_do_del(struct sock *sk, const struct in6_addr *peer) + kfree(tp->md5sig_info->keys6); + tp->md5sig_info->keys6 = NULL; + tp->md5sig_info->alloced6 = 0; ++ tcp_free_md5sig_pool(); + } else { + /* shrink the database */ + if (tp->md5sig_info->entries6 != i) +@@ -669,7 +672,6 @@ static int tcp_v6_md5_do_del(struct sock *sk, const struct in6_addr *peer) + (tp->md5sig_info->entries6 - i) + * sizeof (tp->md5sig_info->keys6[0])); + } +- tcp_free_md5sig_pool(); + return 0; + } + } +@@ -1407,6 +1409,8 @@ static struct sock * tcp_v6_syn_recv_sock(struct sock *sk, struct sk_buff *skb, + newtp->af_specific = &tcp_sock_ipv6_mapped_specific; + #endif + ++ newnp->ipv6_ac_list = NULL; ++ newnp->ipv6_fl_list = NULL; + newnp->pktoptions = NULL; + newnp->opt = NULL; + newnp->mcast_oif = inet6_iif(skb); +@@ -1471,6 +1475,7 @@ static struct sock * tcp_v6_syn_recv_sock(struct sock *sk, struct sk_buff *skb, + First: no IPv4 options. + */ + newinet->inet_opt = NULL; ++ newnp->ipv6_ac_list = NULL; + newnp->ipv6_fl_list = NULL; + + /* Clone RX bits */ +diff --git a/net/l2tp/l2tp_core.c b/net/l2tp/l2tp_core.c +index ed8a233..71c292e 100644 +--- a/net/l2tp/l2tp_core.c ++++ b/net/l2tp/l2tp_core.c +@@ -1045,8 +1045,10 @@ int l2tp_xmit_skb(struct l2tp_session *session, struct sk_buff *skb, int hdr_len + headroom = NET_SKB_PAD + sizeof(struct iphdr) + + uhlen + hdr_len; + old_headroom = skb_headroom(skb); +- if (skb_cow_head(skb, headroom)) ++ if (skb_cow_head(skb, headroom)) { ++ dev_kfree_skb(skb); + goto abort; ++ } + + new_headroom = skb_headroom(skb); + skb_orphan(skb); +diff --git a/net/mac80211/cfg.c b/net/mac80211/cfg.c +index be70c70..143a006 100644 +--- a/net/mac80211/cfg.c ++++ b/net/mac80211/cfg.c +@@ -1798,7 +1798,7 @@ ieee80211_offchan_tx_done(struct ieee80211_work *wk, struct sk_buff *skb) + * so in that case userspace will have to deal with it. + */ + +- if (wk->offchan_tx.wait && wk->offchan_tx.frame) ++ if (wk->offchan_tx.wait && !wk->offchan_tx.status) + cfg80211_mgmt_tx_status(wk->sdata->dev, + (unsigned long) wk->offchan_tx.frame, + wk->ie, wk->ie_len, false, GFP_KERNEL); +diff --git a/net/mac80211/ieee80211_i.h b/net/mac80211/ieee80211_i.h +index 090b0ec..3fdac77 100644 +--- a/net/mac80211/ieee80211_i.h ++++ b/net/mac80211/ieee80211_i.h +@@ -328,6 +328,7 @@ struct ieee80211_work { + struct { + struct sk_buff *frame; + u32 wait; ++ bool status; + } offchan_tx; + }; + +@@ -372,6 +373,7 @@ struct ieee80211_if_managed { + + unsigned long timers_running; /* used for quiesce/restart */ + bool powersave; /* powersave requested for this iface */ ++ bool broken_ap; /* AP is broken -- turn off powersave */ + enum ieee80211_smps_mode req_smps, /* requested smps mode */ + ap_smps, /* smps mode AP thinks we're in */ + driver_smps_mode; /* smps mode request */ +diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c +index 7a334fd..1563250 100644 +--- a/net/mac80211/mlme.c ++++ b/net/mac80211/mlme.c +@@ -613,6 +613,9 @@ static bool ieee80211_powersave_allowed(struct ieee80211_sub_if_data *sdata) + if (!mgd->powersave) + return false; + ++ if (mgd->broken_ap) ++ return false; ++ + if (!mgd->associated) + return false; + +@@ -1450,10 +1453,21 @@ static bool ieee80211_assoc_success(struct ieee80211_work *wk, + capab_info = le16_to_cpu(mgmt->u.assoc_resp.capab_info); + + if ((aid & (BIT(15) | BIT(14))) != (BIT(15) | BIT(14))) +- printk(KERN_DEBUG "%s: invalid aid value %d; bits 15:14 not " +- "set\n", sdata->name, aid); ++ printk(KERN_DEBUG ++ "%s: invalid AID value 0x%x; bits 15:14 not set\n", ++ sdata->name, aid); + aid &= ~(BIT(15) | BIT(14)); + ++ ifmgd->broken_ap = false; ++ ++ if (aid == 0 || aid > IEEE80211_MAX_AID) { ++ printk(KERN_DEBUG ++ "%s: invalid AID value %d (out of range), turn off PS\n", ++ sdata->name, aid); ++ aid = 0; ++ ifmgd->broken_ap = true; ++ } ++ + pos = mgmt->u.assoc_resp.variable; + ieee802_11_parse_elems(pos, len - (pos - (u8 *) mgmt), &elems); + +diff --git a/net/mac80211/status.c b/net/mac80211/status.c +index 1658efa..04cdbaf 100644 +--- a/net/mac80211/status.c ++++ b/net/mac80211/status.c +@@ -336,7 +336,7 @@ void ieee80211_tx_status(struct ieee80211_hw *hw, struct sk_buff *skb) + continue; + if (wk->offchan_tx.frame != skb) + continue; +- wk->offchan_tx.frame = NULL; ++ wk->offchan_tx.status = true; + break; + } + rcu_read_unlock(); +diff --git a/net/mac80211/work.c b/net/mac80211/work.c +index d2e7f0e..52b758d 100644 +--- a/net/mac80211/work.c ++++ b/net/mac80211/work.c +@@ -553,7 +553,7 @@ ieee80211_offchannel_tx(struct ieee80211_work *wk) + /* + * After this, offchan_tx.frame remains but now is no + * longer a valid pointer -- we still need it as the +- * cookie for canceling this work. ++ * cookie for canceling this work/status matching. + */ + ieee80211_tx_skb(wk->sdata, wk->offchan_tx.frame); + +@@ -1060,14 +1060,13 @@ static void ieee80211_work_work(struct work_struct *work) + continue; + if (wk->chan != local->tmp_channel) + continue; +- if (ieee80211_work_ct_coexists(wk->chan_type, +- local->tmp_channel_type)) ++ if (!ieee80211_work_ct_coexists(wk->chan_type, ++ local->tmp_channel_type)) + continue; + remain_off_channel = true; + } + + if (!remain_off_channel && local->tmp_channel) { +- bool on_oper_chan = ieee80211_cfg_on_oper_channel(local); + local->tmp_channel = NULL; + /* If tmp_channel wasn't operating channel, then + * we need to go back on-channel. +@@ -1077,7 +1076,7 @@ static void ieee80211_work_work(struct work_struct *work) + * we still need to do a hardware config. Currently, + * we cannot be here while scanning, however. + */ +- if (ieee80211_cfg_on_oper_channel(local) && !on_oper_chan) ++ if (!ieee80211_cfg_on_oper_channel(local)) + ieee80211_hw_config(local, 0); + + /* At the least, we need to disable offchannel_ps, +diff --git a/net/packet/af_packet.c b/net/packet/af_packet.c +index c0c3cda..fafb968 100644 +--- a/net/packet/af_packet.c ++++ b/net/packet/af_packet.c +@@ -654,7 +654,10 @@ static int packet_rcv(struct sk_buff *skb, struct net_device *dev, + return 0; + + drop_n_acct: +- po->stats.tp_drops = atomic_inc_return(&sk->sk_drops); ++ spin_lock(&sk->sk_receive_queue.lock); ++ po->stats.tp_drops++; ++ atomic_inc(&sk->sk_drops); ++ spin_unlock(&sk->sk_receive_queue.lock); + + drop_n_restore: + if (skb_head != skb->data && skb_shared(skb)) { +diff --git a/net/sunrpc/auth_unix.c b/net/sunrpc/auth_unix.c +index 4cb70dc..e50502d 100644 +--- a/net/sunrpc/auth_unix.c ++++ b/net/sunrpc/auth_unix.c +@@ -129,6 +129,9 @@ unx_match(struct auth_cred *acred, struct rpc_cred *rcred, int flags) + for (i = 0; i < groups ; i++) + if (cred->uc_gids[i] != GROUP_AT(acred->group_info, i)) + return 0; ++ if (groups < NFS_NGROUPS && ++ cred->uc_gids[groups] != NOGROUP) ++ return 0; + return 1; + } + +diff --git a/scripts/kconfig/menu.c b/scripts/kconfig/menu.c +index 5fdf10d..b1a3cee 100644 +--- a/scripts/kconfig/menu.c ++++ b/scripts/kconfig/menu.c +@@ -596,11 +596,10 @@ void menu_get_ext_help(struct menu *menu, struct gstr *help) + struct symbol *sym = menu->sym; + + if (menu_has_help(menu)) { +- if (sym->name) { ++ if (sym->name) + str_printf(help, "%s%s:\n\n", CONFIG_, sym->name); +- str_append(help, _(menu_get_help(menu))); +- str_append(help, "\n"); +- } ++ str_append(help, _(menu_get_help(menu))); ++ str_append(help, "\n"); + } else { + str_append(help, nohelp_text); + } +diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c +index cf1fa36..3c2381c 100644 +--- a/sound/pci/hda/patch_conexant.c ++++ b/sound/pci/hda/patch_conexant.c +@@ -136,6 +136,7 @@ struct conexant_spec { + unsigned int thinkpad:1; + unsigned int hp_laptop:1; + unsigned int asus:1; ++ unsigned int single_adc_amp:1; + + unsigned int adc_switching:1; + +@@ -4205,6 +4206,8 @@ static int cx_auto_add_capture_volume(struct hda_codec *codec, hda_nid_t nid, + int idx = get_input_connection(codec, adc_nid, nid); + if (idx < 0) + continue; ++ if (spec->single_adc_amp) ++ idx = 0; + return cx_auto_add_volume_idx(codec, label, pfx, + cidx, adc_nid, HDA_INPUT, idx); + } +@@ -4245,14 +4248,21 @@ static int cx_auto_build_input_controls(struct hda_codec *codec) + struct hda_input_mux *imux = &spec->private_imux; + const char *prev_label; + int input_conn[HDA_MAX_NUM_INPUTS]; +- int i, err, cidx; ++ int i, j, err, cidx; + int multi_connection; + ++ if (!imux->num_items) ++ return 0; ++ + multi_connection = 0; + for (i = 0; i < imux->num_items; i++) { + cidx = get_input_connection(codec, spec->imux_info[i].adc, + spec->imux_info[i].pin); +- input_conn[i] = (spec->imux_info[i].adc << 8) | cidx; ++ if (cidx < 0) ++ continue; ++ input_conn[i] = spec->imux_info[i].adc; ++ if (!spec->single_adc_amp) ++ input_conn[i] |= cidx << 8; + if (i > 0 && input_conn[i] != input_conn[0]) + multi_connection = 1; + } +@@ -4281,6 +4291,15 @@ static int cx_auto_build_input_controls(struct hda_codec *codec) + err = cx_auto_add_capture_volume(codec, nid, + "Capture", "", cidx); + } else { ++ bool dup_found = false; ++ for (j = 0; j < i; j++) { ++ if (input_conn[j] == input_conn[i]) { ++ dup_found = true; ++ break; ++ } ++ } ++ if (dup_found) ++ continue; + err = cx_auto_add_capture_volume(codec, nid, + label, " Capture", cidx); + } +@@ -4357,6 +4376,13 @@ static int patch_conexant_auto(struct hda_codec *codec) + return -ENOMEM; + codec->spec = spec; + codec->pin_amp_workaround = 1; ++ ++ switch (codec->vendor_id) { ++ case 0x14f15045: ++ spec->single_adc_amp = 1; ++ break; ++ } ++ + err = cx_auto_search_adcs(codec); + if (err < 0) + return err; +diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c +index 4c7cd6b..e7dc034 100644 +--- a/sound/pci/hda/patch_realtek.c ++++ b/sound/pci/hda/patch_realtek.c +@@ -2088,25 +2088,27 @@ static void alc_auto_init_digital(struct hda_codec *codec) + static void alc_auto_parse_digital(struct hda_codec *codec) + { + struct alc_spec *spec = codec->spec; +- int i, err; ++ int i, err, nums; + hda_nid_t dig_nid; + + /* support multiple SPDIFs; the secondary is set up as a slave */ ++ nums = 0; + for (i = 0; i < spec->autocfg.dig_outs; i++) { + err = snd_hda_get_connections(codec, + spec->autocfg.dig_out_pins[i], + &dig_nid, 1); +- if (err < 0) ++ if (err <= 0) + continue; +- if (!i) { ++ if (!nums) { + spec->multiout.dig_out_nid = dig_nid; + spec->dig_out_type = spec->autocfg.dig_out_type[0]; + } else { + spec->multiout.slave_dig_outs = spec->slave_dig_outs; +- if (i >= ARRAY_SIZE(spec->slave_dig_outs) - 1) ++ if (nums >= ARRAY_SIZE(spec->slave_dig_outs) - 1) + break; +- spec->slave_dig_outs[i - 1] = dig_nid; ++ spec->slave_dig_outs[nums - 1] = dig_nid; + } ++ nums++; + } + + if (spec->autocfg.dig_in_pin) { +@@ -20126,6 +20128,8 @@ static const struct hda_codec_preset snd_hda_preset_realtek[] = { + .patch = patch_alc882 }, + { .id = 0x10ec0662, .rev = 0x100101, .name = "ALC662 rev1", + .patch = patch_alc662 }, ++ { .id = 0x10ec0662, .rev = 0x100300, .name = "ALC662 rev3", ++ .patch = patch_alc662 }, + { .id = 0x10ec0663, .name = "ALC663", .patch = patch_alc662 }, + { .id = 0x10ec0665, .name = "ALC665", .patch = patch_alc662 }, + { .id = 0x10ec0670, .name = "ALC670", .patch = patch_alc662 }, +diff --git a/sound/pci/hda/patch_sigmatel.c b/sound/pci/hda/patch_sigmatel.c +index 5c42f3e..5d2e97a 100644 +--- a/sound/pci/hda/patch_sigmatel.c ++++ b/sound/pci/hda/patch_sigmatel.c +@@ -5425,9 +5425,7 @@ static void stac92hd8x_fill_auto_spec(struct hda_codec *codec) + static int patch_stac92hd83xxx(struct hda_codec *codec) + { + struct sigmatel_spec *spec; +- hda_nid_t conn[STAC92HD83_DAC_COUNT + 1]; + int err; +- int num_dacs; + + spec = kzalloc(sizeof(*spec), GFP_KERNEL); + if (spec == NULL) +@@ -5467,26 +5465,8 @@ again: + stac92xx_set_config_regs(codec, + stac92hd83xxx_brd_tbl[spec->board_config]); + +- switch (codec->vendor_id) { +- case 0x111d76d1: +- case 0x111d76d9: +- case 0x111d76df: +- case 0x111d76e5: +- case 0x111d7666: +- case 0x111d7667: +- case 0x111d7668: +- case 0x111d7669: +- case 0x111d76e3: +- case 0x111d7604: +- case 0x111d76d4: +- case 0x111d7605: +- case 0x111d76d5: +- case 0x111d76e7: +- if (spec->board_config == STAC_92HD83XXX_PWR_REF) +- break; ++ if (spec->board_config != STAC_92HD83XXX_PWR_REF) + spec->num_pwrs = 0; +- break; +- } + + codec->patch_ops = stac92xx_patch_ops; + +@@ -5506,7 +5486,11 @@ again: + } + #endif + +- err = stac92xx_parse_auto_config(codec, 0x1d, 0); ++ /* 92HD65/66 series has S/PDIF-IN */ ++ if (codec->vendor_id >= 0x111d76e8 && codec->vendor_id <= 0x111d76f3) ++ err = stac92xx_parse_auto_config(codec, 0x1d, 0x22); ++ else ++ err = stac92xx_parse_auto_config(codec, 0x1d, 0); + if (!err) { + if (spec->board_config < 0) { + printk(KERN_WARNING "hda_codec: No auto-config is " +@@ -5522,22 +5506,6 @@ again: + return err; + } + +- /* docking output support */ +- num_dacs = snd_hda_get_connections(codec, 0xF, +- conn, STAC92HD83_DAC_COUNT + 1) - 1; +- /* skip non-DAC connections */ +- while (num_dacs >= 0 && +- (get_wcaps_type(get_wcaps(codec, conn[num_dacs])) +- != AC_WID_AUD_OUT)) +- num_dacs--; +- /* set port E and F to select the last DAC */ +- if (num_dacs >= 0) { +- snd_hda_codec_write_cache(codec, 0xE, 0, +- AC_VERB_SET_CONNECT_SEL, num_dacs); +- snd_hda_codec_write_cache(codec, 0xF, 0, +- AC_VERB_SET_CONNECT_SEL, num_dacs); +- } +- + codec->proc_widget_hook = stac92hd_proc_hook; + + return 0; +@@ -6405,6 +6373,18 @@ static const struct hda_codec_preset snd_hda_preset_sigmatel[] = { + { .id = 0x111d76e3, .name = "92HD98BXX", .patch = patch_stac92hd83xxx}, + { .id = 0x111d76e5, .name = "92HD99BXX", .patch = patch_stac92hd83xxx}, + { .id = 0x111d76e7, .name = "92HD90BXX", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76e8, .name = "92HD66B1X5", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76e9, .name = "92HD66B2X5", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76ea, .name = "92HD66B3X5", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76eb, .name = "92HD66C1X5", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76ec, .name = "92HD66C2X5", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76ed, .name = "92HD66C3X5", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76ee, .name = "92HD66B1X3", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76ef, .name = "92HD66B2X3", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76f0, .name = "92HD66B3X3", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76f1, .name = "92HD66C1X3", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76f2, .name = "92HD66C2X3", .patch = patch_stac92hd83xxx}, ++ { .id = 0x111d76f3, .name = "92HD66C3/65", .patch = patch_stac92hd83xxx}, + {} /* terminator */ + }; + +diff --git a/sound/soc/codecs/ak4535.c b/sound/soc/codecs/ak4535.c +index e1a214e..65abd09 100644 +--- a/sound/soc/codecs/ak4535.c ++++ b/sound/soc/codecs/ak4535.c +@@ -40,11 +40,11 @@ struct ak4535_priv { + /* + * ak4535 register cache + */ +-static const u16 ak4535_reg[AK4535_CACHEREGNUM] = { +- 0x0000, 0x0080, 0x0000, 0x0003, +- 0x0002, 0x0000, 0x0011, 0x0001, +- 0x0000, 0x0040, 0x0036, 0x0010, +- 0x0000, 0x0000, 0x0057, 0x0000, ++static const u8 ak4535_reg[AK4535_CACHEREGNUM] = { ++ 0x00, 0x80, 0x00, 0x03, ++ 0x02, 0x00, 0x11, 0x01, ++ 0x00, 0x40, 0x36, 0x10, ++ 0x00, 0x00, 0x57, 0x00, + }; + + /* +diff --git a/sound/soc/codecs/ak4642.c b/sound/soc/codecs/ak4642.c +index 65f4604..79c1b3d 100644 +--- a/sound/soc/codecs/ak4642.c ++++ b/sound/soc/codecs/ak4642.c +@@ -162,17 +162,17 @@ struct ak4642_priv { + /* + * ak4642 register cache + */ +-static const u16 ak4642_reg[AK4642_CACHEREGNUM] = { +- 0x0000, 0x0000, 0x0001, 0x0000, +- 0x0002, 0x0000, 0x0000, 0x0000, +- 0x00e1, 0x00e1, 0x0018, 0x0000, +- 0x00e1, 0x0018, 0x0011, 0x0008, +- 0x0000, 0x0000, 0x0000, 0x0000, +- 0x0000, 0x0000, 0x0000, 0x0000, +- 0x0000, 0x0000, 0x0000, 0x0000, +- 0x0000, 0x0000, 0x0000, 0x0000, +- 0x0000, 0x0000, 0x0000, 0x0000, +- 0x0000, ++static const u8 ak4642_reg[AK4642_CACHEREGNUM] = { ++ 0x00, 0x00, 0x01, 0x00, ++ 0x02, 0x00, 0x00, 0x00, ++ 0xe1, 0xe1, 0x18, 0x00, ++ 0xe1, 0x18, 0x11, 0x08, ++ 0x00, 0x00, 0x00, 0x00, ++ 0x00, 0x00, 0x00, 0x00, ++ 0x00, 0x00, 0x00, 0x00, ++ 0x00, 0x00, 0x00, 0x00, ++ 0x00, 0x00, 0x00, 0x00, ++ 0x00, + }; + + /* +diff --git a/sound/soc/codecs/wm8711.c b/sound/soc/codecs/wm8711.c +index a537e4a..1dae5c4 100644 +--- a/sound/soc/codecs/wm8711.c ++++ b/sound/soc/codecs/wm8711.c +@@ -150,7 +150,7 @@ static int wm8711_hw_params(struct snd_pcm_substream *substream, + { + struct snd_soc_codec *codec = dai->codec; + struct wm8711_priv *wm8711 = snd_soc_codec_get_drvdata(codec); +- u16 iface = snd_soc_read(codec, WM8711_IFACE) & 0xfffc; ++ u16 iface = snd_soc_read(codec, WM8711_IFACE) & 0xfff3; + int i = get_coeff(wm8711->sysclk, params_rate(params)); + u16 srate = (coeff_div[i].sr << 2) | + (coeff_div[i].bosr << 1) | coeff_div[i].usb; +@@ -231,7 +231,7 @@ static int wm8711_set_dai_fmt(struct snd_soc_dai *codec_dai, + unsigned int fmt) + { + struct snd_soc_codec *codec = codec_dai->codec; +- u16 iface = 0; ++ u16 iface = snd_soc_read(codec, WM8711_IFACE) & 0x000c; + + /* set master/slave audio interface */ + switch (fmt & SND_SOC_DAIFMT_MASTER_MASK) { +diff --git a/sound/soc/codecs/wm8741.c b/sound/soc/codecs/wm8741.c +index 25af901..c173aee 100644 +--- a/sound/soc/codecs/wm8741.c ++++ b/sound/soc/codecs/wm8741.c +@@ -337,10 +337,10 @@ static int wm8741_set_dai_fmt(struct snd_soc_dai *codec_dai, + iface |= 0x0004; + break; + case SND_SOC_DAIFMT_DSP_A: +- iface |= 0x0003; ++ iface |= 0x000C; + break; + case SND_SOC_DAIFMT_DSP_B: +- iface |= 0x0013; ++ iface |= 0x001C; + break; + default: + return -EINVAL; +diff --git a/sound/soc/codecs/wm8904.c b/sound/soc/codecs/wm8904.c +index 9b3bba4..0fce199 100644 +--- a/sound/soc/codecs/wm8904.c ++++ b/sound/soc/codecs/wm8904.c +@@ -868,7 +868,7 @@ SOC_ENUM("Right Capture Mode", rin_mode), + SOC_DOUBLE_R("Capture Volume", WM8904_ANALOGUE_LEFT_INPUT_0, + WM8904_ANALOGUE_RIGHT_INPUT_0, 0, 31, 0), + SOC_DOUBLE_R("Capture Switch", WM8904_ANALOGUE_LEFT_INPUT_0, +- WM8904_ANALOGUE_RIGHT_INPUT_0, 7, 1, 0), ++ WM8904_ANALOGUE_RIGHT_INPUT_0, 7, 1, 1), + + SOC_SINGLE("High Pass Filter Switch", WM8904_ADC_DIGITAL_0, 4, 1, 0), + SOC_ENUM("High Pass Filter Mode", hpf_mode), +diff --git a/sound/soc/codecs/wm8940.c b/sound/soc/codecs/wm8940.c +index 25580e3..d4ecb3f 100644 +--- a/sound/soc/codecs/wm8940.c ++++ b/sound/soc/codecs/wm8940.c +@@ -472,6 +472,8 @@ static int wm8940_set_bias_level(struct snd_soc_codec *codec, + break; + } + ++ codec->dapm.bias_level = level; ++ + return ret; + } + +diff --git a/sound/soc/codecs/wm8962.c b/sound/soc/codecs/wm8962.c +index 5e05eed..4a0f666 100644 +--- a/sound/soc/codecs/wm8962.c ++++ b/sound/soc/codecs/wm8962.c +@@ -1957,7 +1957,13 @@ static int wm8962_readable_register(struct snd_soc_codec *codec, unsigned int re + + static int wm8962_reset(struct snd_soc_codec *codec) + { +- return snd_soc_write(codec, WM8962_SOFTWARE_RESET, 0x6243); ++ int ret; ++ ++ ret = snd_soc_write(codec, WM8962_SOFTWARE_RESET, 0x6243); ++ if (ret != 0) ++ return ret; ++ ++ return snd_soc_write(codec, WM8962_PLL_SOFTWARE_RESET, 0); + } + + static const DECLARE_TLV_DB_SCALE(inpga_tlv, -2325, 75, 0); +@@ -2018,7 +2024,6 @@ static int wm8962_put_spk_sw(struct snd_kcontrol *kcontrol, + struct snd_ctl_elem_value *ucontrol) + { + struct snd_soc_codec *codec = snd_kcontrol_chip(kcontrol); +- u16 *reg_cache = codec->reg_cache; + int ret; + + /* Apply the update (if any) */ +@@ -2027,16 +2032,19 @@ static int wm8962_put_spk_sw(struct snd_kcontrol *kcontrol, + return 0; + + /* If the left PGA is enabled hit that VU bit... */ +- if (reg_cache[WM8962_PWR_MGMT_2] & WM8962_SPKOUTL_PGA_ENA) +- return snd_soc_write(codec, WM8962_SPKOUTL_VOLUME, +- reg_cache[WM8962_SPKOUTL_VOLUME]); ++ ret = snd_soc_read(codec, WM8962_PWR_MGMT_2); ++ if (ret & WM8962_SPKOUTL_PGA_ENA) { ++ snd_soc_write(codec, WM8962_SPKOUTL_VOLUME, ++ snd_soc_read(codec, WM8962_SPKOUTL_VOLUME)); ++ return 1; ++ } + + /* ...otherwise the right. The VU is stereo. */ +- if (reg_cache[WM8962_PWR_MGMT_2] & WM8962_SPKOUTR_PGA_ENA) +- return snd_soc_write(codec, WM8962_SPKOUTR_VOLUME, +- reg_cache[WM8962_SPKOUTR_VOLUME]); ++ if (ret & WM8962_SPKOUTR_PGA_ENA) ++ snd_soc_write(codec, WM8962_SPKOUTR_VOLUME, ++ snd_soc_read(codec, WM8962_SPKOUTR_VOLUME)); + +- return 0; ++ return 1; + } + + static const char *cap_hpf_mode_text[] = { +@@ -2336,7 +2344,6 @@ static int out_pga_event(struct snd_soc_dapm_widget *w, + struct snd_kcontrol *kcontrol, int event) + { + struct snd_soc_codec *codec = w->codec; +- u16 *reg_cache = codec->reg_cache; + int reg; + + switch (w->shift) { +@@ -2359,7 +2366,7 @@ static int out_pga_event(struct snd_soc_dapm_widget *w, + + switch (event) { + case SND_SOC_DAPM_POST_PMU: +- return snd_soc_write(codec, reg, reg_cache[reg]); ++ return snd_soc_write(codec, reg, snd_soc_read(codec, reg)); + default: + BUG(); + return -EINVAL; +@@ -3027,9 +3034,9 @@ static int wm8962_set_dai_fmt(struct snd_soc_dai *dai, unsigned int fmt) + int aif0 = 0; + + switch (fmt & SND_SOC_DAIFMT_FORMAT_MASK) { +- case SND_SOC_DAIFMT_DSP_A: +- aif0 |= WM8962_LRCLK_INV; + case SND_SOC_DAIFMT_DSP_B: ++ aif0 |= WM8962_LRCLK_INV | 3; ++ case SND_SOC_DAIFMT_DSP_A: + aif0 |= 3; + + switch (fmt & SND_SOC_DAIFMT_INV_MASK) { +@@ -3822,6 +3829,11 @@ static int wm8962_probe(struct snd_soc_codec *codec) + */ + snd_soc_update_bits(codec, WM8962_CLOCKING2, WM8962_SYSCLK_ENA, 0); + ++ /* Ensure that the oscillator and PLLs are disabled */ ++ snd_soc_update_bits(codec, WM8962_PLL2, ++ WM8962_OSC_ENA | WM8962_PLL2_ENA | WM8962_PLL3_ENA, ++ 0); ++ + regulator_bulk_disable(ARRAY_SIZE(wm8962->supplies), wm8962->supplies); + + if (pdata) { +diff --git a/sound/soc/codecs/wm8994.c b/sound/soc/codecs/wm8994.c +index 83014a7..fb9f08a 100644 +--- a/sound/soc/codecs/wm8994.c ++++ b/sound/soc/codecs/wm8994.c +@@ -1266,7 +1266,7 @@ SND_SOC_DAPM_MUX("AIF2DAC Mux", SND_SOC_NOPM, 0, 0, &aif2dac_mux), + SND_SOC_DAPM_MUX("AIF2ADC Mux", SND_SOC_NOPM, 0, 0, &aif2adc_mux), + + SND_SOC_DAPM_AIF_IN("AIF3DACDAT", "AIF3 Playback", 0, SND_SOC_NOPM, 0, 0), +-SND_SOC_DAPM_AIF_IN("AIF3ADCDAT", "AIF3 Capture", 0, SND_SOC_NOPM, 0, 0), ++SND_SOC_DAPM_AIF_OUT("AIF3ADCDAT", "AIF3 Capture", 0, SND_SOC_NOPM, 0, 0), + + SND_SOC_DAPM_SUPPLY("TOCLK", WM8994_CLOCKING_1, 4, 0, NULL, 0), + +diff --git a/sound/usb/misc/ua101.c b/sound/usb/misc/ua101.c +index fb5d68f..96c381e 100644 +--- a/sound/usb/misc/ua101.c ++++ b/sound/usb/misc/ua101.c +@@ -459,7 +459,8 @@ static void kill_stream_urbs(struct ua101_stream *stream) + unsigned int i; + + for (i = 0; i < stream->queue_length; ++i) +- usb_kill_urb(&stream->urbs[i]->urb); ++ if (stream->urbs[i]) ++ usb_kill_urb(&stream->urbs[i]->urb); + } + + static int enable_iso_interface(struct ua101 *ua, unsigned int intf_index) +@@ -484,6 +485,9 @@ static void disable_iso_interface(struct ua101 *ua, unsigned int intf_index) + { + struct usb_host_interface *alts; + ++ if (!ua->intf[intf_index]) ++ return; ++ + alts = ua->intf[intf_index]->cur_altsetting; + if (alts->desc.bAlternateSetting != 0) { + int err = usb_set_interface(ua->dev, +@@ -1144,27 +1148,37 @@ static void free_stream_urbs(struct ua101_stream *stream) + { + unsigned int i; + +- for (i = 0; i < stream->queue_length; ++i) ++ for (i = 0; i < stream->queue_length; ++i) { + kfree(stream->urbs[i]); ++ stream->urbs[i] = NULL; ++ } + } + + static void free_usb_related_resources(struct ua101 *ua, + struct usb_interface *interface) + { + unsigned int i; ++ struct usb_interface *intf; + ++ mutex_lock(&ua->mutex); + free_stream_urbs(&ua->capture); + free_stream_urbs(&ua->playback); ++ mutex_unlock(&ua->mutex); + free_stream_buffers(ua, &ua->capture); + free_stream_buffers(ua, &ua->playback); + +- for (i = 0; i < ARRAY_SIZE(ua->intf); ++i) +- if (ua->intf[i]) { +- usb_set_intfdata(ua->intf[i], NULL); +- if (ua->intf[i] != interface) ++ for (i = 0; i < ARRAY_SIZE(ua->intf); ++i) { ++ mutex_lock(&ua->mutex); ++ intf = ua->intf[i]; ++ ua->intf[i] = NULL; ++ mutex_unlock(&ua->mutex); ++ if (intf) { ++ usb_set_intfdata(intf, NULL); ++ if (intf != interface) + usb_driver_release_interface(&ua101_driver, +- ua->intf[i]); ++ intf); + } ++ } + } + + static void ua101_card_free(struct snd_card *card) +diff --git a/tools/perf/util/probe-event.c b/tools/perf/util/probe-event.c +index f022316..8c50da8 100644 +--- a/tools/perf/util/probe-event.c ++++ b/tools/perf/util/probe-event.c +@@ -1869,8 +1869,10 @@ static int __del_trace_probe_event(int fd, struct str_node *ent) + + pr_debug("Writing event: %s\n", buf); + ret = write(fd, buf, strlen(buf)); +- if (ret < 0) ++ if (ret < 0) { ++ ret = -errno; + goto error; ++ } + + printf("Remove event: %s\n", ent->s); + return 0; |