Linux 3.2.81

From: Ben Hutchings
Date: Thu Jun 16 2016 - 06:54:59 EST


I'm announcing the release of the 3.2.81 kernel.

All users of the 3.2 kernel series should upgrade.

The updated 3.2.y git tree can be found at:
https://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable.git linux-3.2.y
and can be browsed at the normal kernel.org git web browser:
https://git.kernel.org/?p=linux/kernel/git/stable/linux-stable.git

The diff from 3.2.80 is attached to this message.

Ben.

------------

Documentation/kernel-parameters.txt | 2 +
Makefile | 2 +-
arch/parisc/kernel/syscall.S | 2 +-
arch/powerpc/include/asm/cputable.h | 1 +
arch/powerpc/kernel/prom.c | 2 +-
arch/s390/include/asm/hugetlb.h | 1 +
arch/x86/include/asm/hugetlb.h | 1 +
arch/x86/include/asm/microcode.h | 1 +
arch/x86/include/asm/uaccess_64.h | 24 +++++++++---
arch/x86/kernel/microcode_amd.c | 54 ++++++++++++++++++++++++++-
arch/x86/kvm/x86.c | 10 ++---
crypto/ahash.c | 3 +-
crypto/gcm.c | 22 ++++++++++-
drivers/acpi/acpica/dsmethod.c | 3 ++
drivers/ata/libahci.c | 1 +
drivers/char/ipmi/ipmi_si_intf.c | 2 +-
drivers/edac/i7core_edac.c | 2 +-
drivers/edac/sb_edac.c | 2 +-
drivers/gpu/drm/i915/i915_drv.c | 29 +++++++++++++++
drivers/gpu/drm/radeon/atombios_encoders.c | 4 ++
drivers/infiniband/core/ucm.c | 4 ++
drivers/infiniband/core/ucma.c | 4 ++
drivers/infiniband/core/uverbs_main.c | 5 +++
drivers/infiniband/hw/ipath/ipath_file_ops.c | 5 +++
drivers/infiniband/hw/qib/qib_file_ops.c | 5 +++
drivers/input/misc/pmic8xxx-pwrkey.c | 8 ++--
drivers/input/tablet/gtco.c | 10 ++++-
drivers/net/ethernet/atheros/atlx/atl2.c | 2 +-
drivers/usb/core/hcd-pci.c | 8 ++++
drivers/usb/host/xhci-mem.c | 5 +++
drivers/usb/host/xhci-pci.c | 4 +-
drivers/usb/serial/cp210x.c | 4 ++
drivers/usb/storage/usb.c | 5 ++-
fs/hugetlbfs/inode.c | 5 +++
fs/isofs/rock.c | 13 +++++--
fs/proc/base.c | 3 +-
include/linux/hash.h | 20 ++++++++++
include/linux/hugetlb.h | 9 +++++
include/linux/netdevice.h | 21 +----------
include/linux/usb_usual.h | 2 +
include/rdma/ib.h | 21 +++++++++++
mm/huge_memory.c | 55 ++++++++++++----------------
mm/hugetlb.c | 16 +++++---
net/ax25/ax25_ip.c | 15 --------
net/batman-adv/routing.c | 9 +++++
net/batman-adv/send.c | 6 +++
net/batman-adv/soft-interface.c | 8 +++-
net/core/rtnetlink.c | 18 +++++----
net/llc/af_llc.c | 1 +
net/netfilter/nf_conntrack_core.c | 4 +-
net/wireless/nl80211.c | 2 +-
net/x25/x25_facilities.c | 1 +
52 files changed, 350 insertions(+), 116 deletions(-)

Al Viro (1):
get_rock_ridge_filename(): handle malformed NM entries

Alex Deucher (1):
drm/radeon: make sure vertical front porch is at least 1

Andi Kleen (1):
x86: Add 1/2/4/8 byte optimization to 64bit __copy_{from,to}_user_inatomic

Anton Blanchard (1):
powerpc: scan_features() updates incorrect bits for REAL_LE

Ben Hutchings (4):
Revert "ax25: add link layer header validation function"
Revert "net: validate variable length ll headers"
atl2: Disable unimplemented scatter/gather feature
Linux 3.2.81

Bob Liu (1):
thp: introduce hugepage_vma_check()

Borislav Petkov (2):
x86/microcode/amd: Extract current patch level read to a function
x86/microcode/amd: Do not overwrite final patch levels

David Matlack (1):
kvm: x86: do not leak guest xcr0 into host interrupt handlers

Dmitry Ivanov (1):
nl80211: check netlink protocol in socket release notification

Dmitry V. Levin (1):
parisc: fix a bug when syscall number of tracee is __NR_Linux_syscalls

Dominik Dingel (2):
mm: hugetlb: allow hugepages_supported to be architecture specific
s390/hugetlb: add hugepages_supported define

Hans de Goede (1):
USB: uas: Add a new NO_REPORT_LUNS quirk

Herbert Xu (2):
crypto: gcm - Fix rfc4543 decryption crash
crypto: hash - Fix page length clamping in hash walk

Imre Deak (1):
drm/i915: Fix system resume if PCI device remained enabled

Jan Beulich (1):
x86/mm/xen: Suppress hugetlbfs in PV guests

Jasem Mutlaq (1):
USB: serial: cp210x: add Straizona Focusers device ids

Jason Gunthorpe (1):
IB/security: Restrict use of the write() interface

Jussi Kivilinna (1):
crypto: gcm - fix rfc4543 to handle async crypto correctly

Kangjie Lu (3):
net: fix infoleak in llc
net: fix infoleak in rtnetlink
net: fix a kernel infoleak in x25 module

Konstantin Khlebnikov (1):
mm/huge_memory: replace VM_NO_THP VM_BUG_ON with actual VMA check

Linus Lüssing (1):
batman-adv: Fix broadcast/ogm queue limit on a removed interface

Linus Torvalds (3):
Make hash_64() use a 64-bit multiply when appropriate
Minimal fix-up of bad hashing behavior of hash_64()
nf_conntrack: avoid kernel pointer value leak in slab name

Lu Baolu (1):
usb: xhci: fix wild pointers in xhci_mem_cleanup

Mathias Krause (1):
proc: prevent accessing /proc/<PID>/environ until it's ready

Mike Manning (1):
USB: serial: cp210x: add ID for Link ECU

Nishanth Aravamudan (1):
hugetlb: ensure hugepage access is denied if hugepages are not supported

Prarit Bhargava (1):
ACPICA: Dispatcher: Update thread ID for recursive method calls

Rafal Redzimski (1):
usb: xhci: applying XHCI_PME_STUCK_QUIRK to Intel BXT B0 host

Robert Dobrowolski (1):
usb: hcd: out of bounds access in for_each_companion

Srinivas Kandagatla (1):
libahci: save port map for forced port map

Stephen Boyd (1):
Input: pmic8xxx-pwrkey - fix algorithm for converting trigger delay

Steven Rostedt (1):
x86, sparse: Do not force removal of __user when calling copy_to/from_user_nocheck()

Sven Eckelmann (2):
batman-adv: Check skb size before using encapsulated ETH+VLAN header
batman-adv: Reduce refcnt of removed router when updating route

Tony Luck (1):
EDAC: i7core, sb_edac: Don't return NOTIFY_BAD from mce_decoder callback

Vladis Dronov (1):
Input: gtco - fix crash on detecting device without endpoints

Xie XiuQi (1):
ipmi: fix timeout calculation when bmc is disconnected

diff --git a/Documentation/kernel-parameters.txt b/Documentation/kernel-parameters.txt
index f0001eb33173..ac601c4b9f57 100644
--- a/Documentation/kernel-parameters.txt
+++ b/Documentation/kernel-parameters.txt
@@ -2699,6 +2699,8 @@ bytes respectively. Such letter suffixes can also be entirely omitted.
sector if the number is odd);
i = IGNORE_DEVICE (don't bind to this
device);
+ j = NO_REPORT_LUNS (don't use report luns
+ command, uas only);
l = NOT_LOCKABLE (don't try to lock and
unlock ejectable media);
m = MAX_SECTORS_64 (don't transfer more
diff --git a/Makefile b/Makefile
index 5b500f93425b..98c276c53906 100644
--- a/Makefile
+++ b/Makefile
@@ -1,6 +1,6 @@
VERSION = 3
PATCHLEVEL = 2
-SUBLEVEL = 80
+SUBLEVEL = 81
EXTRAVERSION =
NAME = Saber-toothed Squirrel

diff --git a/arch/parisc/kernel/syscall.S b/arch/parisc/kernel/syscall.S
index 82a52b2fb13f..ed3df443e02d 100644
--- a/arch/parisc/kernel/syscall.S
+++ b/arch/parisc/kernel/syscall.S
@@ -314,7 +314,7 @@ tracesys_next:
ldo -16(%r30),%r29 /* Reference param save area */
#endif

- comiclr,>>= __NR_Linux_syscalls, %r20, %r0
+ comiclr,>> __NR_Linux_syscalls, %r20, %r0
b,n .Lsyscall_nosys

LDREGX %r20(%r19), %r19
diff --git a/arch/powerpc/include/asm/cputable.h b/arch/powerpc/include/asm/cputable.h
index e30442c539ce..9b604c05fec3 100644
--- a/arch/powerpc/include/asm/cputable.h
+++ b/arch/powerpc/include/asm/cputable.h
@@ -30,6 +30,7 @@
#define PPC_FEATURE_PSERIES_PERFMON_COMPAT \
0x00000040

+/* Reserved - do not use 0x00000004 */
#define PPC_FEATURE_TRUE_LE 0x00000002
#define PPC_FEATURE_PPC_LE 0x00000001

diff --git a/arch/powerpc/kernel/prom.c b/arch/powerpc/kernel/prom.c
index fa1235b0503b..c021af8364a3 100644
--- a/arch/powerpc/kernel/prom.c
+++ b/arch/powerpc/kernel/prom.c
@@ -159,7 +159,7 @@ static struct ibm_pa_feature {
{CPU_FTR_NOEXECUTE, 0, 0, 0, 6, 0},
{CPU_FTR_NODSISRALIGN, 0, 0, 1, 1, 1},
{0, MMU_FTR_CI_LARGE_PAGE, 0, 1, 2, 0},
- {CPU_FTR_REAL_LE, PPC_FEATURE_TRUE_LE, 5, 0, 0},
+ {CPU_FTR_REAL_LE, 0, PPC_FEATURE_TRUE_LE, 5, 0, 0},
};

static void __init scan_features(unsigned long node, unsigned char *ftrs,
diff --git a/arch/s390/include/asm/hugetlb.h b/arch/s390/include/asm/hugetlb.h
index 799ed0f1643d..dcd46cba4ec3 100644
--- a/arch/s390/include/asm/hugetlb.h
+++ b/arch/s390/include/asm/hugetlb.h
@@ -14,6 +14,7 @@

#define is_hugepage_only_range(mm, addr, len) 0
#define hugetlb_free_pgd_range free_pgd_range
+#define hugepages_supported() (MACHINE_HAS_HPAGE)

void set_huge_pte_at(struct mm_struct *mm, unsigned long addr,
pte_t *ptep, pte_t pte);
diff --git a/arch/x86/include/asm/hugetlb.h b/arch/x86/include/asm/hugetlb.h
index 48fa3915fd02..4e8225c25145 100644
--- a/arch/x86/include/asm/hugetlb.h
+++ b/arch/x86/include/asm/hugetlb.h
@@ -3,6 +3,7 @@

#include <asm/page.h>

+#define hugepages_supported() cpu_has_pse

static inline int is_hugepage_only_range(struct mm_struct *mm,
unsigned long addr,
diff --git a/arch/x86/include/asm/microcode.h b/arch/x86/include/asm/microcode.h
index 24215072d0e1..3a7f5f5a405d 100644
--- a/arch/x86/include/asm/microcode.h
+++ b/arch/x86/include/asm/microcode.h
@@ -61,4 +61,5 @@ static inline struct microcode_ops * __init init_amd_microcode(void)
}
#endif

+extern bool check_current_patch_level(u32 *rev, bool early);
#endif /* _ASM_X86_MICROCODE_H */
diff --git a/arch/x86/include/asm/uaccess_64.h b/arch/x86/include/asm/uaccess_64.h
index 1c66d30971ad..31fed191a41e 100644
--- a/arch/x86/include/asm/uaccess_64.h
+++ b/arch/x86/include/asm/uaccess_64.h
@@ -68,11 +68,10 @@ int copy_to_user(void __user *dst, const void *src, unsigned size)
}

static __always_inline __must_check
-int __copy_from_user(void *dst, const void __user *src, unsigned size)
+int __copy_from_user_nocheck(void *dst, const void __user *src, unsigned size)
{
int ret = 0;

- might_fault();
if (!__builtin_constant_p(size))
return copy_user_generic(dst, (__force void *)src, size);
switch (size) {
@@ -112,11 +111,17 @@ int __copy_from_user(void *dst, const void __user *src, unsigned size)
}

static __always_inline __must_check
-int __copy_to_user(void __user *dst, const void *src, unsigned size)
+int __copy_from_user(void *dst, const void __user *src, unsigned size)
+{
+ might_fault();
+ return __copy_from_user_nocheck(dst, src, size);
+}
+
+static __always_inline __must_check
+int __copy_to_user_nocheck(void __user *dst, const void *src, unsigned size)
{
int ret = 0;

- might_fault();
if (!__builtin_constant_p(size))
return copy_user_generic((__force void *)dst, src, size);
switch (size) {
@@ -156,6 +161,13 @@ int __copy_to_user(void __user *dst, const void *src, unsigned size)
}

static __always_inline __must_check
+int __copy_to_user(void __user *dst, const void *src, unsigned size)
+{
+ might_fault();
+ return __copy_to_user_nocheck(dst, src, size);
+}
+
+static __always_inline __must_check
int __copy_in_user(void __user *dst, const void __user *src, unsigned size)
{
int ret = 0;
@@ -221,13 +233,13 @@ __must_check unsigned long __clear_user(void __user *mem, unsigned long len);
static __must_check __always_inline int
__copy_from_user_inatomic(void *dst, const void __user *src, unsigned size)
{
- return copy_user_generic(dst, (__force const void *)src, size);
+ return __copy_from_user_nocheck(dst, src, size);
}

static __must_check __always_inline int
__copy_to_user_inatomic(void __user *dst, const void *src, unsigned size)
{
- return copy_user_generic((__force void *)dst, src, size);
+ return __copy_to_user_nocheck(dst, src, size);
}

extern long __copy_user_nocache(void *dst, const void __user *src,
diff --git a/arch/x86/kernel/microcode_amd.c b/arch/x86/kernel/microcode_amd.c
index f9b9eaa3bbe5..be2fa4d0e814 100644
--- a/arch/x86/kernel/microcode_amd.c
+++ b/arch/x86/kernel/microcode_amd.c
@@ -123,13 +123,62 @@ static int get_matching_microcode(int cpu, struct microcode_header_amd *mc_hdr,
return 1;
}

+/*
+ * Those patch levels cannot be updated to newer ones and thus should be final.
+ */
+static u32 final_levels[] = {
+ 0x01000098,
+ 0x0100009f,
+ 0x010000af,
+ 0, /* T-101 terminator */
+};
+
+/*
+ * Check the current patch level on this CPU.
+ *
+ * @rev: Use it to return the patch level. It is set to 0 in the case of
+ * error.
+ *
+ * Returns:
+ * - true: if update should stop
+ * - false: otherwise
+ */
+bool check_current_patch_level(u32 *rev, bool early)
+{
+ u32 lvl, dummy, i;
+ bool ret = false;
+ u32 *levels;
+
+ rdmsr(MSR_AMD64_PATCH_LEVEL, lvl, dummy);
+
+#ifdef CONFIG_X86_32
+ if (early)
+ levels = (u32 *)__pa_nodebug(&final_levels);
+ else
+#endif
+ levels = final_levels;
+
+ for (i = 0; levels[i]; i++) {
+ if (lvl == levels[i]) {
+ lvl = 0;
+ ret = true;
+ break;
+ }
+ }
+
+ if (rev)
+ *rev = lvl;
+
+ return ret;
+}
+
static int apply_microcode_amd(int cpu)
{
- u32 rev, dummy;
int cpu_num = raw_smp_processor_id();
struct ucode_cpu_info *uci = ucode_cpu_info + cpu_num;
struct microcode_amd *mc_amd = uci->mc;
struct cpuinfo_x86 *c = &cpu_data(cpu);
+ u32 dummy, rev;

/* We should bind the task to the CPU */
BUG_ON(cpu_num != cpu);
@@ -137,6 +186,9 @@ static int apply_microcode_amd(int cpu)
if (mc_amd == NULL)
return 0;

+ if (check_current_patch_level(&rev, false))
+ return -1;
+
wrmsrl(MSR_AMD64_PATCH_LOADER, (u64)(long)&mc_amd->hdr.data_code);
/* get patch id after patching */
rdmsr(MSR_AMD64_PATCH_LEVEL, rev, dummy);
diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c
index da1a1261aac1..a7fd5b336ac7 100644
--- a/arch/x86/kvm/x86.c
+++ b/arch/x86/kvm/x86.c
@@ -5754,8 +5754,6 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)
kvm_x86_ops->prepare_guest_switch(vcpu);
if (vcpu->fpu_active)
kvm_load_guest_fpu(vcpu);
- kvm_load_guest_xcr0(vcpu);
-
vcpu->mode = IN_GUEST_MODE;

/* We should set ->mode before check ->requests,
@@ -5776,6 +5774,8 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)
goto out;
}

+ kvm_load_guest_xcr0(vcpu);
+
srcu_read_unlock(&vcpu->kvm->srcu, vcpu->srcu_idx);

kvm_guest_enter();
@@ -5805,6 +5805,9 @@ static int vcpu_enter_guest(struct kvm_vcpu *vcpu)

vcpu->mode = OUTSIDE_GUEST_MODE;
smp_wmb();
+
+ kvm_put_guest_xcr0(vcpu);
+
local_irq_enable();

++vcpu->stat.exits;
@@ -6378,7 +6381,6 @@ void kvm_load_guest_fpu(struct kvm_vcpu *vcpu)
* and assume host would use all available bits.
* Guest xcr0 would be loaded later.
*/
- kvm_put_guest_xcr0(vcpu);
vcpu->guest_fpu_loaded = 1;
unlazy_fpu(current);
fpu_restore_checking(&vcpu->arch.guest_fpu);
@@ -6387,8 +6389,6 @@ void kvm_load_guest_fpu(struct kvm_vcpu *vcpu)

void kvm_put_guest_fpu(struct kvm_vcpu *vcpu)
{
- kvm_put_guest_xcr0(vcpu);
-
if (!vcpu->guest_fpu_loaded)
return;

diff --git a/crypto/ahash.c b/crypto/ahash.c
index 7fd8ecf71337..8271185d4ad9 100644
--- a/crypto/ahash.c
+++ b/crypto/ahash.c
@@ -64,8 +64,9 @@ static int hash_walk_new_entry(struct crypto_hash_walk *walk)
struct scatterlist *sg;

sg = walk->sg;
- walk->pg = sg_page(sg);
walk->offset = sg->offset;
+ walk->pg = sg_page(walk->sg) + (walk->offset >> PAGE_SHIFT);
+ walk->offset = offset_in_page(walk->offset);
walk->entrylen = sg->length;

if (walk->entrylen > walk->total)
diff --git a/crypto/gcm.c b/crypto/gcm.c
index 1e3356107af2..943cbceca426 100644
--- a/crypto/gcm.c
+++ b/crypto/gcm.c
@@ -1103,6 +1103,21 @@ static int crypto_rfc4543_setauthsize(struct crypto_aead *parent,
return crypto_aead_setauthsize(ctx->child, authsize);
}

+static void crypto_rfc4543_done(struct crypto_async_request *areq, int err)
+{
+ struct aead_request *req = areq->data;
+ struct crypto_aead *aead = crypto_aead_reqtfm(req);
+ struct crypto_rfc4543_req_ctx *rctx = crypto_rfc4543_reqctx(req);
+
+ if (!err) {
+ scatterwalk_map_and_copy(rctx->auth_tag, req->dst,
+ req->cryptlen,
+ crypto_aead_authsize(aead), 1);
+ }
+
+ aead_request_complete(req, err);
+}
+
static struct aead_request *crypto_rfc4543_crypt(struct aead_request *req,
int enc)
{
@@ -1159,8 +1174,11 @@ static struct aead_request *crypto_rfc4543_crypt(struct aead_request *req,
scatterwalk_crypto_chain(assoc, payload, 0, 2);

aead_request_set_tfm(subreq, ctx->child);
- aead_request_set_callback(subreq, req->base.flags, req->base.complete,
- req->base.data);
+ aead_request_set_callback(subreq, req->base.flags, crypto_rfc4543_done,
+ req);
+ if (!enc)
+ aead_request_set_callback(subreq, req->base.flags,
+ req->base.complete, req->base.data);
aead_request_set_crypt(subreq, cipher, cipher, enc ? 0 : authsize, iv);
aead_request_set_assoc(subreq, assoc, assoclen);

diff --git a/drivers/acpi/acpica/dsmethod.c b/drivers/acpi/acpica/dsmethod.c
index 5d797751e205..7e13b71aa10d 100644
--- a/drivers/acpi/acpica/dsmethod.c
+++ b/drivers/acpi/acpica/dsmethod.c
@@ -266,6 +266,9 @@ acpi_ds_begin_method_execution(struct acpi_namespace_node *method_node,
obj_desc->method.mutex->mutex.
original_sync_level =
obj_desc->method.mutex->mutex.sync_level;
+
+ obj_desc->method.mutex->mutex.thread_id =
+ acpi_os_get_thread_id();
}
}

diff --git a/drivers/ata/libahci.c b/drivers/ata/libahci.c
index 1adb71733d05..fbfde7153f78 100644
--- a/drivers/ata/libahci.c
+++ b/drivers/ata/libahci.c
@@ -452,6 +452,7 @@ void ahci_save_initial_config(struct device *dev,
dev_info(dev, "forcing port_map 0x%x -> 0x%x\n",
port_map, force_port_map);
port_map = force_port_map;
+ hpriv->saved_port_map = port_map;
}

if (mask_port_map) {
diff --git a/drivers/char/ipmi/ipmi_si_intf.c b/drivers/char/ipmi/ipmi_si_intf.c
index 636a8dd09ea0..e8e11ff97ece 100644
--- a/drivers/char/ipmi/ipmi_si_intf.c
+++ b/drivers/char/ipmi/ipmi_si_intf.c
@@ -2679,7 +2679,7 @@ static int wait_for_msg_done(struct smi_info *smi_info)
smi_result == SI_SM_CALL_WITH_TICK_DELAY) {
schedule_timeout_uninterruptible(1);
smi_result = smi_info->handlers->event(
- smi_info->si_sm, 100);
+ smi_info->si_sm, jiffies_to_usecs(1));
} else if (smi_result == SI_SM_CALL_WITHOUT_DELAY) {
smi_result = smi_info->handlers->event(
smi_info->si_sm, 0);
diff --git a/drivers/edac/i7core_edac.c b/drivers/edac/i7core_edac.c
index 4c18b3c78f03..03e831e159e8 100644
--- a/drivers/edac/i7core_edac.c
+++ b/drivers/edac/i7core_edac.c
@@ -1921,7 +1921,7 @@ static int i7core_mce_check_error(struct notifier_block *nb, unsigned long val,

i7_dev = get_i7core_dev(mce->socketid);
if (!i7_dev)
- return NOTIFY_BAD;
+ return NOTIFY_DONE;

mci = i7_dev->mci;
pvt = mci->pvt_info;
diff --git a/drivers/edac/sb_edac.c b/drivers/edac/sb_edac.c
index f8f790c0d252..7bcfd9d64672 100644
--- a/drivers/edac/sb_edac.c
+++ b/drivers/edac/sb_edac.c
@@ -1596,7 +1596,7 @@ static int sbridge_mce_check_error(struct notifier_block *nb, unsigned long val,

mci = get_mci_for_node_id(mce->socketid);
if (!mci)
- return NOTIFY_BAD;
+ return NOTIFY_DONE;
pvt = mci->pvt_info;

/*
diff --git a/drivers/gpu/drm/i915/i915_drv.c b/drivers/gpu/drm/i915/i915_drv.c
index 452bc512e6a7..e216c21110e4 100644
--- a/drivers/gpu/drm/i915/i915_drv.c
+++ b/drivers/gpu/drm/i915/i915_drv.c
@@ -538,6 +538,35 @@ int i915_resume(struct drm_device *dev)
if (dev->switch_power_state == DRM_SWITCH_POWER_OFF)
return 0;

+ /*
+ * Note that we need to set the power state explicitly, since we
+ * powered off the device during freeze and the PCI core won't power
+ * it back up for us during thaw. Powering off the device during
+ * freeze is not a hard requirement though, and during the
+ * suspend/resume phases the PCI core makes sure we get here with the
+ * device powered on. So in case we change our freeze logic and keep
+ * the device powered we can also remove the following set power state
+ * call.
+ */
+ ret = pci_set_power_state(dev->pdev, PCI_D0);
+ if (ret) {
+ DRM_ERROR("failed to set PCI D0 power state (%d)\n", ret);
+ return ret;
+ }
+
+ /*
+ * Note that pci_enable_device() first enables any parent bridge
+ * device and only then sets the power state for this device. The
+ * bridge enabling is a nop though, since bridge devices are resumed
+ * first. The order of enabling power and enabling the device is
+ * imposed by the PCI core as described above, so here we preserve the
+ * same order for the freeze/thaw phases.
+ *
+ * TODO: eventually we should remove pci_disable_device() /
+ * pci_enable_enable_device() from suspend/resume. Due to how they
+ * depend on the device enable refcount we can't anyway depend on them
+ * disabling/enabling the device.
+ */
if (pci_enable_device(dev->pdev))
return -EIO;

diff --git a/drivers/gpu/drm/radeon/atombios_encoders.c b/drivers/gpu/drm/radeon/atombios_encoders.c
index a1a7d071eb17..cd8b34146146 100644
--- a/drivers/gpu/drm/radeon/atombios_encoders.c
+++ b/drivers/gpu/drm/radeon/atombios_encoders.c
@@ -90,6 +90,10 @@ static bool radeon_atom_mode_fixup(struct drm_encoder *encoder,
&& (mode->crtc_vsync_start < (mode->crtc_vdisplay + 2)))
adjusted_mode->crtc_vsync_start = adjusted_mode->crtc_vdisplay + 2;

+ /* vertical FP must be at least 1 */
+ if (mode->crtc_vsync_start == mode->crtc_vdisplay)
+ adjusted_mode->crtc_vsync_start++;
+
/* get the native mode for LVDS */
if (radeon_encoder->active_device & (ATOM_DEVICE_LCD_SUPPORT))
radeon_panel_mode_fixup(encoder, adjusted_mode);
diff --git a/drivers/infiniband/core/ucm.c b/drivers/infiniband/core/ucm.c
index b8a0b4a7811b..06c116bdcca0 100644
--- a/drivers/infiniband/core/ucm.c
+++ b/drivers/infiniband/core/ucm.c
@@ -48,6 +48,7 @@

#include <asm/uaccess.h>

+#include <rdma/ib.h>
#include <rdma/ib_cm.h>
#include <rdma/ib_user_cm.h>
#include <rdma/ib_marshall.h>
@@ -1116,6 +1117,9 @@ static ssize_t ib_ucm_write(struct file *filp, const char __user *buf,
struct ib_ucm_cmd_hdr hdr;
ssize_t result;

+ if (WARN_ON_ONCE(!ib_safe_file_access(filp)))
+ return -EACCES;
+
if (len < sizeof(hdr))
return -EINVAL;

diff --git a/drivers/infiniband/core/ucma.c b/drivers/infiniband/core/ucma.c
index b37b0c02a7b9..91e82b7dadfa 100644
--- a/drivers/infiniband/core/ucma.c
+++ b/drivers/infiniband/core/ucma.c
@@ -47,6 +47,7 @@
#include <rdma/ib_marshall.h>
#include <rdma/rdma_cm.h>
#include <rdma/rdma_cm_ib.h>
+#include <rdma/ib.h>

MODULE_AUTHOR("Sean Hefty");
MODULE_DESCRIPTION("RDMA Userspace Connection Manager Access");
@@ -1268,6 +1269,9 @@ static ssize_t ucma_write(struct file *filp, const char __user *buf,
struct rdma_ucm_cmd_hdr hdr;
ssize_t ret;

+ if (WARN_ON_ONCE(!ib_safe_file_access(filp)))
+ return -EACCES;
+
if (len < sizeof(hdr))
return -EINVAL;

diff --git a/drivers/infiniband/core/uverbs_main.c b/drivers/infiniband/core/uverbs_main.c
index f07c6e317771..9cdcb5038622 100644
--- a/drivers/infiniband/core/uverbs_main.c
+++ b/drivers/infiniband/core/uverbs_main.c
@@ -48,6 +48,8 @@

#include <asm/uaccess.h>

+#include <rdma/ib.h>
+
#include "uverbs.h"

MODULE_AUTHOR("Roland Dreier");
@@ -580,6 +582,9 @@ static ssize_t ib_uverbs_write(struct file *filp, const char __user *buf,
struct ib_uverbs_file *file = filp->private_data;
struct ib_uverbs_cmd_hdr hdr;

+ if (WARN_ON_ONCE(!ib_safe_file_access(filp)))
+ return -EACCES;
+
if (count < sizeof hdr)
return -EINVAL;

diff --git a/drivers/infiniband/hw/ipath/ipath_file_ops.c b/drivers/infiniband/hw/ipath/ipath_file_ops.c
index 736d9edbdbe7..eed46ddd2331 100644
--- a/drivers/infiniband/hw/ipath/ipath_file_ops.c
+++ b/drivers/infiniband/hw/ipath/ipath_file_ops.c
@@ -44,6 +44,8 @@
#include <linux/cpu.h>
#include <asm/pgtable.h>

+#include <rdma/ib.h>
+
#include "ipath_kernel.h"
#include "ipath_common.h"
#include "ipath_user_sdma.h"
@@ -2239,6 +2241,9 @@ static ssize_t ipath_write(struct file *fp, const char __user *data,
ssize_t ret = 0;
void *dest;

+ if (WARN_ON_ONCE(!ib_safe_file_access(fp)))
+ return -EACCES;
+
if (count < sizeof(cmd.type)) {
ret = -EINVAL;
goto bail;
diff --git a/drivers/infiniband/hw/qib/qib_file_ops.c b/drivers/infiniband/hw/qib/qib_file_ops.c
index a7403248d83d..81c5bdb194dc 100644
--- a/drivers/infiniband/hw/qib/qib_file_ops.c
+++ b/drivers/infiniband/hw/qib/qib_file_ops.c
@@ -45,6 +45,8 @@
#include <linux/delay.h>
#include <linux/export.h>

+#include <rdma/ib.h>
+
#include "qib.h"
#include "qib_common.h"
#include "qib_user_sdma.h"
@@ -1971,6 +1973,9 @@ static ssize_t qib_write(struct file *fp, const char __user *data,
ssize_t ret = 0;
void *dest;

+ if (WARN_ON_ONCE(!ib_safe_file_access(fp)))
+ return -EACCES;
+
if (count < sizeof(cmd.type)) {
ret = -EINVAL;
goto bail;
diff --git a/drivers/input/misc/pmic8xxx-pwrkey.c b/drivers/input/misc/pmic8xxx-pwrkey.c
index b3cfb9c71e66..61f5b374a473 100644
--- a/drivers/input/misc/pmic8xxx-pwrkey.c
+++ b/drivers/input/misc/pmic8xxx-pwrkey.c
@@ -98,7 +98,9 @@ static int __devinit pmic8xxx_pwrkey_probe(struct platform_device *pdev)
return -EINVAL;
}

- if (pdata->kpd_trigger_delay_us > 62500) {
+ /* Valid range of pwr key trigger delay is 1/64 sec to 2 seconds. */
+ if (pdata->kpd_trigger_delay_us > USEC_PER_SEC * 2 ||
+ pdata->kpd_trigger_delay_us < USEC_PER_SEC / 64) {
dev_err(&pdev->dev, "invalid power key trigger delay\n");
return -EINVAL;
}
@@ -120,8 +122,8 @@ static int __devinit pmic8xxx_pwrkey_probe(struct platform_device *pdev)
pwr->phys = "pmic8xxx_pwrkey/input0";
pwr->dev.parent = &pdev->dev;

- delay = (pdata->kpd_trigger_delay_us << 10) / USEC_PER_SEC;
- delay = 1 + ilog2(delay);
+ delay = (pdata->kpd_trigger_delay_us << 6) / USEC_PER_SEC;
+ delay = ilog2(delay);

err = pm8xxx_readb(pdev->dev.parent, PON_CNTL_1, &pon_cntl);
if (err < 0) {
diff --git a/drivers/input/tablet/gtco.c b/drivers/input/tablet/gtco.c
index 8ea6afe2e992..929215a2dcfa 100644
--- a/drivers/input/tablet/gtco.c
+++ b/drivers/input/tablet/gtco.c
@@ -866,6 +866,14 @@ static int gtco_probe(struct usb_interface *usbinterface,
goto err_free_buf;
}

+ /* Sanity check that a device has an endpoint */
+ if (usbinterface->altsetting[0].desc.bNumEndpoints < 1) {
+ dev_err(&usbinterface->dev,
+ "Invalid number of endpoints\n");
+ error = -EINVAL;
+ goto err_free_urb;
+ }
+
/*
* The endpoint is always altsetting 0, we know this since we know
* this device only has one interrupt endpoint
@@ -887,7 +895,7 @@ static int gtco_probe(struct usb_interface *usbinterface,
* HID report descriptor
*/
if (usb_get_extra_descriptor(usbinterface->cur_altsetting,
- HID_DEVICE_TYPE, &hid_desc) != 0){
+ HID_DEVICE_TYPE, &hid_desc) != 0) {
err("Can't retrieve exta USB descriptor to get hid report descriptor length");
error = -EIO;
goto err_free_urb;
diff --git a/drivers/net/ethernet/atheros/atlx/atl2.c b/drivers/net/ethernet/atheros/atlx/atl2.c
index 1feae5928a4b..12313c8cbe0c 100644
--- a/drivers/net/ethernet/atheros/atlx/atl2.c
+++ b/drivers/net/ethernet/atheros/atlx/atl2.c
@@ -1428,7 +1428,7 @@ static int __devinit atl2_probe(struct pci_dev *pdev,

err = -EIO;

- netdev->hw_features = NETIF_F_SG | NETIF_F_HW_VLAN_RX;
+ netdev->hw_features = NETIF_F_HW_VLAN_RX;
netdev->features |= (NETIF_F_HW_VLAN_TX | NETIF_F_HW_VLAN_RX);

/* Init PHY as early as possible due to power saving issue */
diff --git a/drivers/usb/core/hcd-pci.c b/drivers/usb/core/hcd-pci.c
index 76be3bae3ff8..8312f9547009 100644
--- a/drivers/usb/core/hcd-pci.c
+++ b/drivers/usb/core/hcd-pci.c
@@ -70,6 +70,14 @@ static void companion_common(struct pci_dev *pdev, struct usb_hcd *hcd,
PCI_SLOT(companion->devfn) != slot)
continue;

+ /*
+ * Companion device should be either UHCI,OHCI or EHCI host
+ * controller, otherwise skip.
+ */
+ if (companion->class != CL_UHCI && companion->class != CL_OHCI &&
+ companion->class != CL_EHCI)
+ continue;
+
companion_hcd = pci_get_drvdata(companion);
if (!companion_hcd)
continue;
diff --git a/drivers/usb/host/xhci-mem.c b/drivers/usb/host/xhci-mem.c
index ab023b168732..e3f70d3fb44c 100644
--- a/drivers/usb/host/xhci-mem.c
+++ b/drivers/usb/host/xhci-mem.c
@@ -1789,6 +1789,11 @@ no_bw:
kfree(xhci->port_array);
kfree(xhci->rh_bw);

+ xhci->usb2_ports = NULL;
+ xhci->usb3_ports = NULL;
+ xhci->port_array = NULL;
+ xhci->rh_bw = NULL;
+
xhci->page_size = 0;
xhci->page_shift = 0;
xhci->bus_state[0].bus_suspended = 0;
diff --git a/drivers/usb/host/xhci-pci.c b/drivers/usb/host/xhci-pci.c
index 244e1b12259d..50af559183eb 100644
--- a/drivers/usb/host/xhci-pci.c
+++ b/drivers/usb/host/xhci-pci.c
@@ -40,6 +40,7 @@
#define PCI_DEVICE_ID_INTEL_SUNRISEPOINT_H_XHCI 0xa12f
#define PCI_DEVICE_ID_INTEL_SUNRISEPOINT_LP_XHCI 0x9d2f
#define PCI_DEVICE_ID_INTEL_BROXTON_M_XHCI 0x0aa8
+#define PCI_DEVICE_ID_INTEL_BROXTON_B_XHCI 0x1aa8

static const char hcd_name[] = "xhci_hcd";

@@ -134,7 +135,8 @@ static void xhci_pci_quirks(struct device *dev, struct xhci_hcd *xhci)
(pdev->device == PCI_DEVICE_ID_INTEL_SUNRISEPOINT_LP_XHCI ||
pdev->device == PCI_DEVICE_ID_INTEL_SUNRISEPOINT_H_XHCI ||
pdev->device == PCI_DEVICE_ID_INTEL_CHERRYVIEW_XHCI ||
- pdev->device == PCI_DEVICE_ID_INTEL_BROXTON_M_XHCI)) {
+ pdev->device == PCI_DEVICE_ID_INTEL_BROXTON_M_XHCI ||
+ pdev->device == PCI_DEVICE_ID_INTEL_BROXTON_B_XHCI)) {
xhci->quirks |= XHCI_PME_STUCK_QUIRK;
}
if (pdev->vendor == PCI_VENDOR_ID_ETRON &&
diff --git a/drivers/usb/serial/cp210x.c b/drivers/usb/serial/cp210x.c
index 645687c08baf..e941e2d33265 100644
--- a/drivers/usb/serial/cp210x.c
+++ b/drivers/usb/serial/cp210x.c
@@ -114,6 +114,7 @@ static const struct usb_device_id id_table[] = {
{ USB_DEVICE(0x10C4, 0x826B) }, /* Cygnal Integrated Products, Inc., Fasttrax GPS demonstration module */
{ USB_DEVICE(0x10C4, 0x8281) }, /* Nanotec Plug & Drive */
{ USB_DEVICE(0x10C4, 0x8293) }, /* Telegesis ETRX2USB */
+ { USB_DEVICE(0x10C4, 0x82F4) }, /* Starizona MicroTouch */
{ USB_DEVICE(0x10C4, 0x82F9) }, /* Procyon AVS */
{ USB_DEVICE(0x10C4, 0x8341) }, /* Siemens MC35PU GPRS Modem */
{ USB_DEVICE(0x10C4, 0x8382) }, /* Cygnal Integrated Products, Inc. */
@@ -123,6 +124,7 @@ static const struct usb_device_id id_table[] = {
{ USB_DEVICE(0x10C4, 0x8418) }, /* IRZ Automation Teleport SG-10 GSM/GPRS Modem */
{ USB_DEVICE(0x10C4, 0x846E) }, /* BEI USB Sensor Interface (VCP) */
{ USB_DEVICE(0x10C4, 0x8477) }, /* Balluff RFID */
+ { USB_DEVICE(0x10C4, 0x84B6) }, /* Starizona Hyperion */
{ USB_DEVICE(0x10C4, 0x85EA) }, /* AC-Services IBUS-IF */
{ USB_DEVICE(0x10C4, 0x85EB) }, /* AC-Services CIS-IBUS */
{ USB_DEVICE(0x10C4, 0x85F8) }, /* Virtenio Preon32 */
@@ -146,6 +148,8 @@ static const struct usb_device_id id_table[] = {
{ USB_DEVICE(0x10C4, 0xF004) }, /* Elan Digital Systems USBcount50 */
{ USB_DEVICE(0x10C5, 0xEA61) }, /* Silicon Labs MobiData GPRS USB Modem */
{ USB_DEVICE(0x10CE, 0xEA6A) }, /* Silicon Labs MobiData GPRS USB Modem 100EU */
+ { USB_DEVICE(0x12B8, 0xEC60) }, /* Link G4 ECU */
+ { USB_DEVICE(0x12B8, 0xEC62) }, /* Link G4+ ECU */
{ USB_DEVICE(0x13AD, 0x9999) }, /* Baltech card reader */
{ USB_DEVICE(0x1555, 0x0004) }, /* Owen AC4 USB-RS485 Converter */
{ USB_DEVICE(0x166A, 0x0201) }, /* Clipsal 5500PACA C-Bus Pascal Automation Controller */
diff --git a/drivers/usb/storage/usb.c b/drivers/usb/storage/usb.c
index d582af4a1968..d2817421fc55 100644
--- a/drivers/usb/storage/usb.c
+++ b/drivers/usb/storage/usb.c
@@ -453,7 +453,7 @@ static void adjust_quirks(struct us_data *us)
US_FL_CAPACITY_OK | US_FL_IGNORE_RESIDUE |
US_FL_SINGLE_LUN | US_FL_NO_WP_DETECT |
US_FL_NO_READ_DISC_INFO | US_FL_NO_READ_CAPACITY_16 |
- US_FL_INITIAL_READ10);
+ US_FL_INITIAL_READ10 | US_FL_NO_REPORT_LUNS);

p = quirks;
while (*p) {
@@ -497,6 +497,9 @@ static void adjust_quirks(struct us_data *us)
case 'i':
f |= US_FL_IGNORE_DEVICE;
break;
+ case 'j':
+ f |= US_FL_NO_REPORT_LUNS;
+ break;
case 'l':
f |= US_FL_NOT_LOCKABLE;
break;
diff --git a/fs/hugetlbfs/inode.c b/fs/hugetlbfs/inode.c
index 0aa424a02344..ebab116b0779 100644
--- a/fs/hugetlbfs/inode.c
+++ b/fs/hugetlbfs/inode.c
@@ -979,6 +979,11 @@ static int __init init_hugetlbfs_fs(void)
int error;
struct vfsmount *vfsmount;

+ if (!hugepages_supported()) {
+ pr_info("hugetlbfs: disabling because there are no supported hugepage sizes\n");
+ return -ENOTSUPP;
+ }
+
error = bdi_init(&hugetlbfs_backing_dev_info);
if (error)
return error;
diff --git a/fs/isofs/rock.c b/fs/isofs/rock.c
index 17809499c752..e52a1ac168ef 100644
--- a/fs/isofs/rock.c
+++ b/fs/isofs/rock.c
@@ -203,6 +203,8 @@ int get_rock_ridge_filename(struct iso_directory_record *de,
int retnamlen = 0;
int truncate = 0;
int ret = 0;
+ char *p;
+ int len;

if (!ISOFS_SB(inode->i_sb)->s_rock)
return 0;
@@ -267,12 +269,17 @@ repeat:
rr->u.NM.flags);
break;
}
- if ((strlen(retname) + rr->len - 5) >= 254) {
+ len = rr->len - 5;
+ if (retnamlen + len >= 254) {
truncate = 1;
break;
}
- strncat(retname, rr->u.NM.name, rr->len - 5);
- retnamlen += rr->len - 5;
+ p = memchr(rr->u.NM.name, '\0', len);
+ if (unlikely(p))
+ len = p - rr->u.NM.name;
+ memcpy(retname + retnamlen, rr->u.NM.name, len);
+ retnamlen += len;
+ retname[retnamlen] = '\0';
break;
case SIG('R', 'E'):
kfree(rs.buffer);
diff --git a/fs/proc/base.c b/fs/proc/base.c
index 1ace83d004be..402976ab746a 100644
--- a/fs/proc/base.c
+++ b/fs/proc/base.c
@@ -905,7 +905,8 @@ static ssize_t environ_read(struct file *file, char __user *buf,

mm = mm_for_maps(task);
ret = PTR_ERR(mm);
- if (!mm || IS_ERR(mm))
+ /* Ensure the process spawned far enough to have an environment. */
+ if (!mm || IS_ERR(mm) || !mm->env_end)
goto out_free;

ret = 0;
diff --git a/include/linux/hash.h b/include/linux/hash.h
index b80506bdd733..44a3b95f16c1 100644
--- a/include/linux/hash.h
+++ b/include/linux/hash.h
@@ -31,10 +31,29 @@
#error Wordsize not 32 or 64
#endif

+/*
+ * The above primes are actively bad for hashing, since they are
+ * too sparse. The 32-bit one is mostly ok, the 64-bit one causes
+ * real problems. Besides, the "prime" part is pointless for the
+ * multiplicative hash.
+ *
+ * Although a random odd number will do, it turns out that the golden
+ * ratio phi = (sqrt(5)-1)/2, or its negative, has particularly nice
+ * properties.
+ *
+ * These are the negative, (1 - phi) = (phi^2) = (3 - sqrt(5))/2.
+ * (See Knuth vol 3, section 6.4, exercise 9.)
+ */
+#define GOLDEN_RATIO_32 0x61C88647
+#define GOLDEN_RATIO_64 0x61C8864680B583EBull
+
static inline u64 hash_64(u64 val, unsigned int bits)
{
u64 hash = val;

+#if BITS_PER_LONG == 64
+ hash = hash * GOLDEN_RATIO_64;
+#else
/* Sigh, gcc can't optimise this alone like it does for 32 bits. */
u64 n = hash;
n <<= 18;
@@ -49,6 +68,7 @@ static inline u64 hash_64(u64 val, unsigned int bits)
hash += n;
n <<= 2;
hash += n;
+#endif

/* High bits are more random, so use them. */
return hash >> (64 - bits);
diff --git a/include/linux/hugetlb.h b/include/linux/hugetlb.h
index 4bc9445222f2..533471d8b43b 100644
--- a/include/linux/hugetlb.h
+++ b/include/linux/hugetlb.h
@@ -344,6 +344,15 @@ static inline pgoff_t basepage_index(struct page *page)
return __basepage_index(page);
}

+#ifndef hugepages_supported
+/*
+ * Some platform decide whether they support huge pages at boot
+ * time. Some of them, such as powerpc, set HPAGE_SHIFT to 0
+ * when there is no such support
+ */
+#define hugepages_supported() (HPAGE_SHIFT != 0)
+#endif
+
#else
struct hstate {};
#define alloc_huge_page_node(h, nid) NULL
diff --git a/include/linux/netdevice.h b/include/linux/netdevice.h
index 700c94821db1..4b04097c748c 100644
--- a/include/linux/netdevice.h
+++ b/include/linux/netdevice.h
@@ -293,7 +293,6 @@ struct header_ops {
void (*cache_update)(struct hh_cache *hh,
const struct net_device *dev,
const unsigned char *haddr);
- bool (*validate)(const char *ll_header, unsigned int len);
};

/* These flag bits are private to the generic network queueing
@@ -1120,7 +1119,7 @@ struct net_device {

unsigned int mtu; /* interface MTU value */
unsigned short type; /* interface hardware type */
- unsigned short hard_header_len; /* maximum hardware hdr length */
+ unsigned short hard_header_len; /* hardware hdr length */

/* extra head- and tailroom the hardware may need, but not in all cases
* can this be guaranteed, especially tailroom. Some cases also use
@@ -1729,24 +1728,6 @@ static inline int dev_rebuild_header(struct sk_buff *skb)
return dev->header_ops->rebuild(skb);
}

-/* ll_header must have at least hard_header_len allocated */
-static inline bool dev_validate_header(const struct net_device *dev,
- char *ll_header, int len)
-{
- if (likely(len >= dev->hard_header_len))
- return true;
-
- if (capable(CAP_SYS_RAWIO)) {
- memset(ll_header + len, 0, dev->hard_header_len - len);
- return true;
- }
-
- if (dev->header_ops && dev->header_ops->validate)
- return dev->header_ops->validate(ll_header, len);
-
- return false;
-}
-
typedef int gifconf_func_t(struct net_device * dev, char __user * bufptr, int len);
extern int register_gifconf(unsigned int family, gifconf_func_t * gifconf);
static inline int unregister_gifconf(unsigned int family)
diff --git a/include/linux/usb_usual.h b/include/linux/usb_usual.h
index 88413e9d80b5..a3d6fac653cd 100644
--- a/include/linux/usb_usual.h
+++ b/include/linux/usb_usual.h
@@ -67,6 +67,8 @@
/* Initial READ(10) (and others) must be retried */ \
US_FLAG(BROKEN_FUA, 0x01000000) \
/* Cannot handle FUA in WRITE or READ CDBs */ \
+ US_FLAG(NO_REPORT_LUNS, 0x10000000) \
+ /* Cannot handle REPORT_LUNS */ \

#define US_FLAG(name, value) US_FL_##name = value ,
enum { US_DO_ALL_FLAGS };
diff --git a/include/rdma/ib.h b/include/rdma/ib.h
new file mode 100644
index 000000000000..fcb21882d096
--- /dev/null
+++ b/include/rdma/ib.h
@@ -0,0 +1,21 @@
+#if !defined(_RDMA_IB_H)
+#define _RDMA_IB_H
+
+#include <linux/sched.h>
+
+/*
+ * The IB interfaces that use write() as bi-directional ioctl() are
+ * fundamentally unsafe, since there are lots of ways to trigger "write()"
+ * calls from various contexts with elevated privileges. That includes the
+ * traditional suid executable error message writes, but also various kernel
+ * interfaces that can write to file descriptors.
+ *
+ * This function provides protection for the legacy API by restricting the
+ * calling context.
+ */
+static inline bool ib_safe_file_access(struct file *filp)
+{
+ return filp->f_cred == current_cred() && segment_eq(get_fs(), USER_DS);
+}
+
+#endif /* _RDMA_IB_H */
diff --git a/mm/huge_memory.c b/mm/huge_memory.c
index 79166c2b8f8f..2fde51669cd9 100644
--- a/mm/huge_memory.c
+++ b/mm/huge_memory.c
@@ -1635,14 +1635,14 @@ int khugepaged_enter_vma_merge(struct vm_area_struct *vma,
* page fault if needed.
*/
return 0;
- if (vma->vm_ops)
+ if (vma->vm_ops || (vm_flags & VM_NO_THP))
/* khugepaged not yet working on file or special mappings */
return 0;
/*
* If is_pfn_mapping() is true is_learn_pfn_mapping() must be
* true too, verify it here.
*/
- VM_BUG_ON(is_linear_pfn_mapping(vma) || vm_flags & VM_NO_THP);
+ VM_BUG_ON(is_linear_pfn_mapping(vma));
hstart = (vma->vm_start + ~HPAGE_PMD_MASK) & HPAGE_PMD_MASK;
hend = vma->vm_end & HPAGE_PMD_MASK;
if (hstart < hend)
@@ -1817,6 +1817,24 @@ static void __collapse_huge_page_copy(pte_t *pte, struct page *page,
}
}

+static bool hugepage_vma_check(struct vm_area_struct *vma)
+{
+ if ((!(vma->vm_flags & VM_HUGEPAGE) && !khugepaged_always()) ||
+ (vma->vm_flags & VM_NOHUGEPAGE))
+ return false;
+
+ if (!vma->anon_vma || vma->vm_ops)
+ return false;
+ if (is_vma_temporary_stack(vma))
+ return false;
+ /*
+ * If is_pfn_mapping() is true is_learn_pfn_mapping() must be
+ * true too, verify it here.
+ */
+ VM_BUG_ON(is_linear_pfn_mapping(vma));
+ return !(vma->vm_flags & VM_NO_THP);
+}
+
static void collapse_huge_page(struct mm_struct *mm,
unsigned long address,
struct page **hpage,
@@ -1889,21 +1907,8 @@ static void collapse_huge_page(struct mm_struct *mm,
hend = vma->vm_end & HPAGE_PMD_MASK;
if (address < hstart || address + HPAGE_PMD_SIZE > hend)
goto out;
-
- if ((!(vma->vm_flags & VM_HUGEPAGE) && !khugepaged_always()) ||
- (vma->vm_flags & VM_NOHUGEPAGE))
+ if (!hugepage_vma_check(vma))
goto out;
-
- if (!vma->anon_vma || vma->vm_ops)
- goto out;
- if (is_vma_temporary_stack(vma))
- goto out;
- /*
- * If is_pfn_mapping() is true is_learn_pfn_mapping() must be
- * true too, verify it here.
- */
- VM_BUG_ON(is_linear_pfn_mapping(vma) || vma->vm_flags & VM_NO_THP);
-
pgd = pgd_offset(mm, address);
if (!pgd_present(*pgd))
goto out;
@@ -2133,25 +2138,11 @@ static unsigned int khugepaged_scan_mm_slot(unsigned int pages,
progress++;
break;
}
-
- if ((!(vma->vm_flags & VM_HUGEPAGE) &&
- !khugepaged_always()) ||
- (vma->vm_flags & VM_NOHUGEPAGE)) {
- skip:
+ if (!hugepage_vma_check(vma)) {
+skip:
progress++;
continue;
}
- if (!vma->anon_vma || vma->vm_ops)
- goto skip;
- if (is_vma_temporary_stack(vma))
- goto skip;
- /*
- * If is_pfn_mapping() is true is_learn_pfn_mapping()
- * must be true too, verify it here.
- */
- VM_BUG_ON(is_linear_pfn_mapping(vma) ||
- vma->vm_flags & VM_NO_THP);
-
hstart = (vma->vm_start + ~HPAGE_PMD_MASK) & HPAGE_PMD_MASK;
hend = vma->vm_end & HPAGE_PMD_MASK;
if (hstart >= hend)
diff --git a/mm/hugetlb.c b/mm/hugetlb.c
index 9256590bdd0e..c52095ce40b4 100644
--- a/mm/hugetlb.c
+++ b/mm/hugetlb.c
@@ -1889,11 +1889,7 @@ module_exit(hugetlb_exit);

static int __init hugetlb_init(void)
{
- /* Some platform decide whether they support huge pages at boot
- * time. On these, such as powerpc, HPAGE_SHIFT is set to 0 when
- * there is no such support
- */
- if (HPAGE_SHIFT == 0)
+ if (!hugepages_supported())
return 0;

if (!size_to_hstate(default_hstate_size)) {
@@ -2010,6 +2006,9 @@ static int hugetlb_sysctl_handler_common(bool obey_mempolicy,
unsigned long tmp;
int ret;

+ if (!hugepages_supported())
+ return -ENOTSUPP;
+
tmp = h->max_huge_pages;

if (write && h->order >= MAX_ORDER)
@@ -2075,6 +2074,9 @@ int hugetlb_overcommit_handler(struct ctl_table *table, int write,
unsigned long tmp;
int ret;

+ if (!hugepages_supported())
+ return -ENOTSUPP;
+
tmp = h->nr_overcommit_huge_pages;

if (write && h->order >= MAX_ORDER)
@@ -2100,6 +2102,8 @@ out:
void hugetlb_report_meminfo(struct seq_file *m)
{
struct hstate *h = &default_hstate;
+ if (!hugepages_supported())
+ return;
seq_printf(m,
"HugePages_Total: %5lu\n"
"HugePages_Free: %5lu\n"
@@ -2116,6 +2120,8 @@ void hugetlb_report_meminfo(struct seq_file *m)
int hugetlb_report_node_meminfo(int nid, char *buf)
{
struct hstate *h = &default_hstate;
+ if (!hugepages_supported())
+ return 0;
return sprintf(buf,
"Node %d HugePages_Total: %5u\n"
"Node %d HugePages_Free: %5u\n"
diff --git a/net/ax25/ax25_ip.c b/net/ax25/ax25_ip.c
index a0c9956b5b23..cf0c47a26530 100644
--- a/net/ax25/ax25_ip.c
+++ b/net/ax25/ax25_ip.c
@@ -232,24 +232,9 @@ int ax25_rebuild_header(struct sk_buff *skb)

#endif

-static bool ax25_validate_header(const char *header, unsigned int len)
-{
- ax25_digi digi;
-
- if (!len)
- return false;
-
- if (header[0])
- return true;
-
- return ax25_addr_parse(header + 1, len - 1, NULL, NULL, &digi, NULL,
- NULL);
-}
-
const struct header_ops ax25_header_ops = {
.create = ax25_hard_header,
.rebuild = ax25_rebuild_header,
- .validate = ax25_validate_header,
};

EXPORT_SYMBOL(ax25_hard_header);
diff --git a/net/batman-adv/routing.c b/net/batman-adv/routing.c
index da587ad189f8..cc82ec55283b 100644
--- a/net/batman-adv/routing.c
+++ b/net/batman-adv/routing.c
@@ -98,6 +98,15 @@ static void _update_route(struct bat_priv *bat_priv,
neigh_node = NULL;

spin_lock_bh(&orig_node->neigh_list_lock);
+ /* curr_router used earlier may not be the current orig_node->router
+ * anymore because it was dereferenced outside of the neigh_list_lock
+ * protected region. After the new best neighbor has replace the current
+ * best neighbor the reference counter needs to decrease. Consequently,
+ * the code needs to ensure the curr_router variable contains a pointer
+ * to the replaced best neighbor.
+ */
+ curr_router = rcu_dereference_protected(orig_node->router, true);
+
rcu_assign_pointer(orig_node->router, neigh_node);
spin_unlock_bh(&orig_node->neigh_list_lock);

diff --git a/net/batman-adv/send.c b/net/batman-adv/send.c
index 8a684eb738ad..20570dd6d6b7 100644
--- a/net/batman-adv/send.c
+++ b/net/batman-adv/send.c
@@ -375,6 +375,9 @@ void purge_outstanding_packets(struct bat_priv *bat_priv,

if (pending) {
hlist_del(&forw_packet->list);
+ if (!forw_packet->own)
+ atomic_inc(&bat_priv->bcast_queue_left);
+
forw_packet_free(forw_packet);
}
}
@@ -404,6 +407,9 @@ void purge_outstanding_packets(struct bat_priv *bat_priv,

if (pending) {
hlist_del(&forw_packet->list);
+ if (!forw_packet->own)
+ atomic_inc(&bat_priv->batman_queue_left);
+
forw_packet_free(forw_packet);
}
}
diff --git a/net/batman-adv/soft-interface.c b/net/batman-adv/soft-interface.c
index f9cc95728989..a8f4627a426e 100644
--- a/net/batman-adv/soft-interface.c
+++ b/net/batman-adv/soft-interface.c
@@ -686,10 +686,16 @@ void interface_rx(struct net_device *soft_iface,
skb_pull_rcsum(skb, hdr_size);
skb_reset_mac_header(skb);

+ if (unlikely(!pskb_may_pull(skb, ETH_HLEN)))
+ goto dropped;
+
ethhdr = (struct ethhdr *)skb_mac_header(skb);

switch (ntohs(ethhdr->h_proto)) {
case ETH_P_8021Q:
+ if (!pskb_may_pull(skb, VLAN_ETH_HLEN))
+ goto dropped;
+
vhdr = (struct vlan_ethhdr *)skb->data;
vid = ntohs(vhdr->h_vlan_TCI) & VLAN_VID_MASK;

@@ -726,8 +732,6 @@ void interface_rx(struct net_device *soft_iface,
}

/* skb->dev & skb->pkt_type are set here */
- if (unlikely(!pskb_may_pull(skb, ETH_HLEN)))
- goto dropped;
skb->protocol = eth_type_trans(skb, soft_iface);

/* should not be necessary anymore as we use skb_pull_rcsum()
diff --git a/net/core/rtnetlink.c b/net/core/rtnetlink.c
index e77373a44847..72a7ed82659b 100644
--- a/net/core/rtnetlink.c
+++ b/net/core/rtnetlink.c
@@ -920,14 +920,16 @@ static int rtnl_fill_ifinfo(struct sk_buff *skb, struct net_device *dev,
NLA_PUT_STRING(skb, IFLA_IFALIAS, dev->ifalias);

if (1) {
- struct rtnl_link_ifmap map = {
- .mem_start = dev->mem_start,
- .mem_end = dev->mem_end,
- .base_addr = dev->base_addr,
- .irq = dev->irq,
- .dma = dev->dma,
- .port = dev->if_port,
- };
+ struct rtnl_link_ifmap map;
+
+ memset(&map, 0, sizeof(map));
+ map.mem_start = dev->mem_start;
+ map.mem_end = dev->mem_end;
+ map.base_addr = dev->base_addr;
+ map.irq = dev->irq;
+ map.dma = dev->dma;
+ map.port = dev->if_port;
+
NLA_PUT(skb, IFLA_MAP, sizeof(map), &map);
}

diff --git a/net/llc/af_llc.c b/net/llc/af_llc.c
index f432d7b6d93a..7752b2ffbc43 100644
--- a/net/llc/af_llc.c
+++ b/net/llc/af_llc.c
@@ -627,6 +627,7 @@ static void llc_cmsg_rcv(struct msghdr *msg, struct sk_buff *skb)
if (llc->cmsg_flags & LLC_CMSG_PKTINFO) {
struct llc_pktinfo info;

+ memset(&info, 0, sizeof(info));
info.lpi_ifindex = llc_sk(skb->sk)->dev->ifindex;
llc_pdu_decode_dsap(skb, &info.lpi_sap);
llc_pdu_decode_da(skb, info.lpi_mac);
diff --git a/net/netfilter/nf_conntrack_core.c b/net/netfilter/nf_conntrack_core.c
index 7489bd301da5..c855673ceb23 100644
--- a/net/netfilter/nf_conntrack_core.c
+++ b/net/netfilter/nf_conntrack_core.c
@@ -1493,6 +1493,7 @@ err_proto:

static int nf_conntrack_init_net(struct net *net)
{
+ static atomic64_t unique_id;
int ret;

atomic_set(&net->ct.count, 0);
@@ -1504,7 +1505,8 @@ static int nf_conntrack_init_net(struct net *net)
goto err_stat;
}

- net->ct.slabname = kasprintf(GFP_KERNEL, "nf_conntrack_%p", net);
+ net->ct.slabname = kasprintf(GFP_KERNEL, "nf_conntrack_%llu",
+ (u64)atomic64_inc_return(&unique_id));
if (!net->ct.slabname) {
ret = -ENOMEM;
goto err_slabname;
diff --git a/net/wireless/nl80211.c b/net/wireless/nl80211.c
index e1f73b65af15..446d22439492 100644
--- a/net/wireless/nl80211.c
+++ b/net/wireless/nl80211.c
@@ -7496,7 +7496,7 @@ static int nl80211_netlink_notify(struct notifier_block * nb,
struct cfg80211_registered_device *rdev;
struct wireless_dev *wdev;

- if (state != NETLINK_URELEASE)
+ if (state != NETLINK_URELEASE || notify->protocol != NETLINK_GENERIC)
return NOTIFY_DONE;

rcu_read_lock();
diff --git a/net/x25/x25_facilities.c b/net/x25/x25_facilities.c
index 36384a1fa9f2..887749c8054d 100644
--- a/net/x25/x25_facilities.c
+++ b/net/x25/x25_facilities.c
@@ -271,6 +271,7 @@ int x25_negotiate_facilities(struct sk_buff *skb, struct sock *sk,

memset(&theirs, 0, sizeof(theirs));
memcpy(new, ours, sizeof(*new));
+ memset(dte, 0, sizeof(*dte));

len = x25_parse_facilities(skb, &theirs, dte, &x25->vc_facil_mask);
if (len < 0)

Attachment: signature.asc
Description: Digital signature