public inbox for gentoo-commits@lists.gentoo.org
 help / color / mirror / Atom feed
* [gentoo-commits] proj/hardened-patchset:master commit in: 4.1.3/
@ 2015-07-29 13:20 Anthony G. Basile
  0 siblings, 0 replies; only message in thread
From: Anthony G. Basile @ 2015-07-29 13:20 UTC (permalink / raw
  To: gentoo-commits

commit:     d8f474ed8b41ce8c105ac603af9afbba9f60181d
Author:     Anthony G. Basile <blueness <AT> gentoo <DOT> org>
AuthorDate: Wed Jul 29 13:22:32 2015 +0000
Commit:     Anthony G. Basile <blueness <AT> gentoo <DOT> org>
CommitDate: Wed Jul 29 13:22:32 2015 +0000
URL:        https://gitweb.gentoo.org/proj/hardened-patchset.git/commit/?id=d8f474ed

grsecurity-3.1-4.1.3-201507281943

 4.1.3/0000_README                                  |   2 +-
 ...> 4420_grsecurity-3.1-4.1.3-201507281943.patch} | 770 ++++++++++++++++++---
 2 files changed, 686 insertions(+), 86 deletions(-)

diff --git a/4.1.3/0000_README b/4.1.3/0000_README
index cbe10c3..68a3992 100644
--- a/4.1.3/0000_README
+++ b/4.1.3/0000_README
@@ -2,7 +2,7 @@ README
 -----------------------------------------------------------------------------
 Individual Patch Descriptions:
 -----------------------------------------------------------------------------
-Patch:	4420_grsecurity-3.1-4.1.3-201507261932.patch
+Patch:	4420_grsecurity-3.1-4.1.3-201507281943.patch
 From:	http://www.grsecurity.net
 Desc:	hardened-sources base patch from upstream grsecurity
 

diff --git a/4.1.3/4420_grsecurity-3.1-4.1.3-201507261932.patch b/4.1.3/4420_grsecurity-3.1-4.1.3-201507281943.patch
similarity index 99%
rename from 4.1.3/4420_grsecurity-3.1-4.1.3-201507261932.patch
rename to 4.1.3/4420_grsecurity-3.1-4.1.3-201507281943.patch
index c2c4ded..fc096b0 100644
--- a/4.1.3/4420_grsecurity-3.1-4.1.3-201507261932.patch
+++ b/4.1.3/4420_grsecurity-3.1-4.1.3-201507281943.patch
@@ -16525,20 +16525,19 @@ index acdee09..a553db3 100644
  struct compat_timespec {
  	compat_time_t	tv_sec;
 diff --git a/arch/x86/include/asm/cpufeature.h b/arch/x86/include/asm/cpufeature.h
-index 3d6606f..5e22255 100644
+index 3d6606f..91703f1 100644
 --- a/arch/x86/include/asm/cpufeature.h
 +++ b/arch/x86/include/asm/cpufeature.h
-@@ -214,7 +214,8 @@
+@@ -214,7 +214,7 @@
  #define X86_FEATURE_PAUSEFILTER ( 8*32+13) /* AMD filtered pause intercept */
  #define X86_FEATURE_PFTHRESHOLD ( 8*32+14) /* AMD pause filter threshold */
  #define X86_FEATURE_VMMCALL     ( 8*32+15) /* Prefer vmmcall to vmcall */
 -
-+#define X86_FEATURE_PCIDUDEREF	( 8*32+30) /* PaX PCID based UDEREF */
 +#define X86_FEATURE_STRONGUDEREF (8*32+31) /* PaX PCID based strong UDEREF */
  
  /* Intel-defined CPU features, CPUID level 0x00000007:0 (ebx), word 9 */
  #define X86_FEATURE_FSGSBASE	( 9*32+ 0) /* {RD/WR}{FS/GS}BASE instructions*/
-@@ -222,7 +223,7 @@
+@@ -222,7 +222,7 @@
  #define X86_FEATURE_BMI1	( 9*32+ 3) /* 1st group bit manipulation extensions */
  #define X86_FEATURE_HLE		( 9*32+ 4) /* Hardware Lock Elision */
  #define X86_FEATURE_AVX2	( 9*32+ 5) /* AVX2 instructions */
@@ -16547,7 +16546,7 @@ index 3d6606f..5e22255 100644
  #define X86_FEATURE_BMI2	( 9*32+ 8) /* 2nd group bit manipulation extensions */
  #define X86_FEATURE_ERMS	( 9*32+ 9) /* Enhanced REP MOVSB/STOSB */
  #define X86_FEATURE_INVPCID	( 9*32+10) /* Invalidate Processor Context ID */
-@@ -401,6 +402,7 @@ extern const char * const x86_bug_flags[NBUGINTS*32];
+@@ -401,6 +401,7 @@ extern const char * const x86_bug_flags[NBUGINTS*32];
  #define cpu_has_eager_fpu	boot_cpu_has(X86_FEATURE_EAGER_FPU)
  #define cpu_has_topoext		boot_cpu_has(X86_FEATURE_TOPOEXT)
  #define cpu_has_bpext		boot_cpu_has(X86_FEATURE_BPEXT)
@@ -16555,7 +16554,7 @@ index 3d6606f..5e22255 100644
  
  #if __GNUC__ >= 4
  extern void warn_pre_alternatives(void);
-@@ -454,7 +456,8 @@ static __always_inline __pure bool __static_cpu_has(u16 bit)
+@@ -454,7 +455,8 @@ static __always_inline __pure bool __static_cpu_has(u16 bit)
  
  #ifdef CONFIG_X86_DEBUG_STATIC_CPU_HAS
  	t_warn:
@@ -16565,7 +16564,7 @@ index 3d6606f..5e22255 100644
  		return false;
  #endif
  
-@@ -475,7 +478,7 @@ static __always_inline __pure bool __static_cpu_has(u16 bit)
+@@ -475,7 +477,7 @@ static __always_inline __pure bool __static_cpu_has(u16 bit)
  			     ".section .discard,\"aw\",@progbits\n"
  			     " .byte 0xff + (4f-3f) - (2b-1b)\n" /* size check */
  			     ".previous\n"
@@ -16574,7 +16573,7 @@ index 3d6606f..5e22255 100644
  			     "3: movb $1,%0\n"
  			     "4:\n"
  			     ".previous\n"
-@@ -510,7 +513,7 @@ static __always_inline __pure bool _static_cpu_has_safe(u16 bit)
+@@ -510,7 +512,7 @@ static __always_inline __pure bool _static_cpu_has_safe(u16 bit)
  			 " .byte 5f - 4f\n"		/* repl len */
  			 " .byte 3b - 2b\n"		/* pad len */
  			 ".previous\n"
@@ -16583,7 +16582,7 @@ index 3d6606f..5e22255 100644
  			 "4: jmp %l[t_no]\n"
  			 "5:\n"
  			 ".previous\n"
-@@ -545,7 +548,7 @@ static __always_inline __pure bool _static_cpu_has_safe(u16 bit)
+@@ -545,7 +547,7 @@ static __always_inline __pure bool _static_cpu_has_safe(u16 bit)
  			     ".section .discard,\"aw\",@progbits\n"
  			     " .byte 0xff + (4f-3f) - (2b-1b)\n" /* size check */
  			     ".previous\n"
@@ -16592,7 +16591,7 @@ index 3d6606f..5e22255 100644
  			     "3: movb $0,%0\n"
  			     "4:\n"
  			     ".previous\n"
-@@ -560,7 +563,7 @@ static __always_inline __pure bool _static_cpu_has_safe(u16 bit)
+@@ -560,7 +562,7 @@ static __always_inline __pure bool _static_cpu_has_safe(u16 bit)
  			     ".section .discard,\"aw\",@progbits\n"
  			     " .byte 0xff + (6f-5f) - (4b-3b)\n" /* size check */
  			     ".previous\n"
@@ -17439,7 +17438,7 @@ index 09b9620..923aecd 100644
  	atomic_t perf_rdpmc_allowed;	/* nonzero if rdpmc is allowed */
  } mm_context_t;
 diff --git a/arch/x86/include/asm/mmu_context.h b/arch/x86/include/asm/mmu_context.h
-index 883f6b93..5184058 100644
+index 883f6b93..bb405b5 100644
 --- a/arch/x86/include/asm/mmu_context.h
 +++ b/arch/x86/include/asm/mmu_context.h
 @@ -42,6 +42,20 @@ void destroy_context(struct mm_struct *mm);
@@ -17448,7 +17447,7 @@ index 883f6b93..5184058 100644
  {
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+	if (!(static_cpu_has(X86_FEATURE_PCIDUDEREF))) {
++	if (!(static_cpu_has(X86_FEATURE_PCID))) {
 +		unsigned int i;
 +		pgd_t *pgd;
 +
@@ -17486,7 +17485,7 @@ index 883f6b93..5184058 100644
 +		pax_open_kernel();
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+		if (static_cpu_has(X86_FEATURE_PCIDUDEREF))
++		if (static_cpu_has(X86_FEATURE_PCID))
 +			__clone_user_pgds(get_cpu_pgd(cpu, user), next->pgd);
 +		else
 +#endif
@@ -17497,7 +17496,7 @@ index 883f6b93..5184058 100644
 +		BUG_ON((__pa(get_cpu_pgd(cpu, kernel)) | PCID_KERNEL) != (read_cr3() & __PHYSICAL_MASK) && (__pa(get_cpu_pgd(cpu, user)) | PCID_USER) != (read_cr3() & __PHYSICAL_MASK));
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+		if (static_cpu_has(X86_FEATURE_PCIDUDEREF)) {
++		if (static_cpu_has(X86_FEATURE_PCID)) {
 +			if (static_cpu_has(X86_FEATURE_INVPCID)) {
 +				u64 descriptor[2];
 +				descriptor[0] = PCID_USER;
@@ -17554,7 +17553,7 @@ index 883f6b93..5184058 100644
 +		pax_open_kernel();
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+		if (static_cpu_has(X86_FEATURE_PCIDUDEREF))
++		if (static_cpu_has(X86_FEATURE_PCID))
 +			__clone_user_pgds(get_cpu_pgd(cpu, user), next->pgd);
 +		else
 +#endif
@@ -17565,7 +17564,7 @@ index 883f6b93..5184058 100644
 +		BUG_ON((__pa(get_cpu_pgd(cpu, kernel)) | PCID_KERNEL) != (read_cr3() & __PHYSICAL_MASK) && (__pa(get_cpu_pgd(cpu, user)) | PCID_USER) != (read_cr3() & __PHYSICAL_MASK));
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+		if (static_cpu_has(X86_FEATURE_PCIDUDEREF)) {
++		if (static_cpu_has(X86_FEATURE_PCID)) {
 +			if (static_cpu_has(X86_FEATURE_INVPCID)) {
 +				u64 descriptor[2];
 +				descriptor[0] = PCID_USER;
@@ -19402,7 +19401,7 @@ index b4bdec3..e8af9bc 100644
  #endif
  #endif /* _ASM_X86_THREAD_INFO_H */
 diff --git a/arch/x86/include/asm/tlbflush.h b/arch/x86/include/asm/tlbflush.h
-index cd79194..6a9956f 100644
+index cd79194..e7a9491 100644
 --- a/arch/x86/include/asm/tlbflush.h
 +++ b/arch/x86/include/asm/tlbflush.h
 @@ -86,18 +86,44 @@ static inline void cr4_set_bits_and_update_boot(unsigned long mask)
@@ -19418,7 +19417,7 @@ index cd79194..6a9956f 100644
 +	}
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+	if (static_cpu_has(X86_FEATURE_PCIDUDEREF)) {
++	if (static_cpu_has(X86_FEATURE_PCID)) {
 +		unsigned int cpu = raw_get_cpu();
 +
 +		native_write_cr3(__pa(get_cpu_pgd(cpu, user)) | PCID_USER);
@@ -19456,7 +19455,7 @@ index cd79194..6a9956f 100644
  }
  
  static inline void __native_flush_tlb_global(void)
-@@ -118,6 +144,43 @@ static inline void __native_flush_tlb_global(void)
+@@ -118,6 +144,41 @@ static inline void __native_flush_tlb_global(void)
  
  static inline void __native_flush_tlb_single(unsigned long addr)
  {
@@ -19467,16 +19466,14 @@ index cd79194..6a9956f 100644
 +		descriptor[1] = addr;
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+		if (static_cpu_has(X86_FEATURE_PCIDUDEREF)) {
-+			if (!static_cpu_has(X86_FEATURE_STRONGUDEREF) || addr >= TASK_SIZE_MAX) {
-+				if (addr < TASK_SIZE_MAX)
-+					descriptor[1] += pax_user_shadow_base;
-+				asm volatile(__ASM_INVPCID : : "d"(&descriptor), "a"(INVPCID_SINGLE_ADDRESS) : "memory");
-+			}
-+
-+			descriptor[0] = PCID_USER;
-+			descriptor[1] = addr;
++		if (!static_cpu_has(X86_FEATURE_STRONGUDEREF) || addr >= TASK_SIZE_MAX) {
++			if (addr < TASK_SIZE_MAX)
++				descriptor[1] += pax_user_shadow_base;
++			asm volatile(__ASM_INVPCID : : "d"(&descriptor), "a"(INVPCID_SINGLE_ADDRESS) : "memory");
 +		}
++
++		descriptor[0] = PCID_USER;
++		descriptor[1] = addr;
 +#endif
 +
 +		asm volatile(__ASM_INVPCID : : "d"(&descriptor), "a"(INVPCID_SINGLE_ADDRESS) : "memory");
@@ -19484,7 +19481,7 @@ index cd79194..6a9956f 100644
 +	}
 +
 +#if defined(CONFIG_X86_64) && defined(CONFIG_PAX_MEMORY_UDEREF)
-+	if (static_cpu_has(X86_FEATURE_PCIDUDEREF)) {
++	if (static_cpu_has(X86_FEATURE_PCID)) {
 +		unsigned int cpu = raw_get_cpu();
 +
 +		native_write_cr3(__pa(get_cpu_pgd(cpu, user)) | PCID_USER | PCID_NOFLUSH);
@@ -21131,7 +21128,7 @@ index e4cf633..941f450 100644
  		if (c->x86_model == 3 && c->x86_mask == 0)
  			size = 64;
 diff --git a/arch/x86/kernel/cpu/common.c b/arch/x86/kernel/cpu/common.c
-index a62cf04..56afd65 100644
+index a62cf04..041e39c 100644
 --- a/arch/x86/kernel/cpu/common.c
 +++ b/arch/x86/kernel/cpu/common.c
 @@ -91,60 +91,6 @@ static const struct cpu_dev default_cpu = {
@@ -21195,7 +21192,7 @@ index a62cf04..56afd65 100644
  static int __init x86_xsave_setup(char *s)
  {
  	if (strlen(s))
-@@ -306,6 +252,62 @@ static __always_inline void setup_smap(struct cpuinfo_x86 *c)
+@@ -306,6 +252,59 @@ static __always_inline void setup_smap(struct cpuinfo_x86 *c)
  	}
  }
  
@@ -21216,31 +21213,26 @@ index a62cf04..56afd65 100644
 +
 +static void setup_pcid(struct cpuinfo_x86 *c)
 +{
-+	if (cpu_has(c, X86_FEATURE_PCID)) {
-+		printk("PAX: PCID detected\n");
-+		cr4_set_bits(X86_CR4_PCIDE);
-+	} else
++	if (!cpu_has(c, X86_FEATURE_PCID)) {
 +		clear_cpu_cap(c, X86_FEATURE_INVPCID);
 +
-+	if (cpu_has(c, X86_FEATURE_INVPCID))
-+		printk("PAX: INVPCID detected\n");
-+
 +#ifdef CONFIG_PAX_MEMORY_UDEREF
-+	if (clone_pgd_mask == ~(pgdval_t)0UL) {
-+		printk("PAX: UDEREF disabled\n");
-+		return;
-+	}
++		if (clone_pgd_mask != ~(pgdval_t)0UL) {
++			pax_open_kernel();
++			pax_user_shadow_base = 1UL << TASK_SIZE_MAX_SHIFT;
++			pax_close_kernel();
++			printk("PAX: slow and weak UDEREF enabled\n");
++		} else
++			printk("PAX: UDEREF disabled\n");
++#endif
 +
-+	if (!cpu_has(c, X86_FEATURE_PCID)) {
-+		pax_open_kernel();
-+		pax_user_shadow_base = 1UL << TASK_SIZE_MAX_SHIFT;
-+		pax_close_kernel();
-+		printk("PAX: slow and weak UDEREF enabled\n");
 +		return;
 +	}
 +
-+	set_cpu_cap(c, X86_FEATURE_PCIDUDEREF);
++	printk("PAX: PCID detected\n");
++	cr4_set_bits(X86_CR4_PCIDE);
 +
++#ifdef CONFIG_PAX_MEMORY_UDEREF
 +	pax_open_kernel();
 +	clone_pgd_mask = ~(pgdval_t)0UL;
 +	pax_close_kernel();
@@ -21252,13 +21244,15 @@ index a62cf04..56afd65 100644
 +	}
 +#endif
 +
++	if (cpu_has(c, X86_FEATURE_INVPCID))
++		printk("PAX: INVPCID detected\n");
 +}
 +#endif
 +
  /*
   * Some CPU features depend on higher CPUID levels, which may not always
   * be available due to CPUID level capping or broken virtualization
-@@ -406,7 +408,7 @@ void switch_to_new_gdt(int cpu)
+@@ -406,7 +405,7 @@ void switch_to_new_gdt(int cpu)
  {
  	struct desc_ptr gdt_descr;
  
@@ -21267,7 +21261,7 @@ index a62cf04..56afd65 100644
  	gdt_descr.size = GDT_SIZE - 1;
  	load_gdt(&gdt_descr);
  	/* Reload the per-cpu base */
-@@ -935,6 +937,20 @@ static void identify_cpu(struct cpuinfo_x86 *c)
+@@ -935,6 +934,20 @@ static void identify_cpu(struct cpuinfo_x86 *c)
  	setup_smep(c);
  	setup_smap(c);
  
@@ -21288,7 +21282,7 @@ index a62cf04..56afd65 100644
  	/*
  	 * The vendor-specific functions might have changed features.
  	 * Now we do "generic changes."
-@@ -1009,7 +1025,7 @@ void enable_sep_cpu(void)
+@@ -1009,7 +1022,7 @@ void enable_sep_cpu(void)
  	int cpu;
  
  	cpu = get_cpu();
@@ -21297,7 +21291,7 @@ index a62cf04..56afd65 100644
  
  	if (!boot_cpu_has(X86_FEATURE_SEP))
  		goto out;
-@@ -1155,14 +1171,16 @@ static __init int setup_disablecpuid(char *arg)
+@@ -1155,14 +1168,16 @@ static __init int setup_disablecpuid(char *arg)
  }
  __setup("clearcpuid=", setup_disablecpuid);
  
@@ -21318,7 +21312,7 @@ index a62cf04..56afd65 100644
  
  DEFINE_PER_CPU_FIRST(union irq_stack_union,
  		     irq_stack_union) __aligned(PAGE_SIZE) __visible;
-@@ -1367,7 +1385,7 @@ void cpu_init(void)
+@@ -1367,7 +1382,7 @@ void cpu_init(void)
  	 */
  	load_ucode_ap();
  
@@ -21327,7 +21321,7 @@ index a62cf04..56afd65 100644
  	oist = &per_cpu(orig_ist, cpu);
  
  #ifdef CONFIG_NUMA
-@@ -1399,7 +1417,6 @@ void cpu_init(void)
+@@ -1399,7 +1414,6 @@ void cpu_init(void)
  	wrmsrl(MSR_KERNEL_GS_BASE, 0);
  	barrier();
  
@@ -21335,7 +21329,7 @@ index a62cf04..56afd65 100644
  	x2apic_setup();
  
  	/*
-@@ -1451,7 +1468,7 @@ void cpu_init(void)
+@@ -1451,7 +1465,7 @@ void cpu_init(void)
  {
  	int cpu = smp_processor_id();
  	struct task_struct *curr = current;
@@ -21745,10 +21739,25 @@ index 7795f3f..3535b76 100644
  	__bts_event_stop(event);
  
 diff --git a/arch/x86/kernel/cpu/perf_event_intel_cqm.c b/arch/x86/kernel/cpu/perf_event_intel_cqm.c
-index e4d1b8b..2c6ffa0 100644
+index e4d1b8b..8867302 100644
 --- a/arch/x86/kernel/cpu/perf_event_intel_cqm.c
 +++ b/arch/x86/kernel/cpu/perf_event_intel_cqm.c
-@@ -1352,7 +1352,9 @@ static int __init intel_cqm_init(void)
+@@ -934,6 +934,14 @@ static u64 intel_cqm_event_count(struct perf_event *event)
+ 		return 0;
+ 
+ 	/*
++	 * Getting up-to-date values requires an SMP IPI which is not
++	 * possible if we're being called in interrupt context. Return
++	 * the cached values instead.
++	 */
++	if (unlikely(in_interrupt()))
++		goto out;
++
++	/*
+ 	 * Notice that we don't perform the reading of an RMID
+ 	 * atomically, because we can't hold a spin lock across the
+ 	 * IPIs.
+@@ -1352,7 +1360,9 @@ static int __init intel_cqm_init(void)
  		goto out;
  	}
  
@@ -33559,10 +33568,10 @@ index 9ca35fc..4b2b7b7 100644
  
  	return (void *)vaddr;
 diff --git a/arch/x86/mm/ioremap.c b/arch/x86/mm/ioremap.c
-index 70e7444..75b9a13 100644
+index 70e7444..e9904fd 100644
 --- a/arch/x86/mm/ioremap.c
 +++ b/arch/x86/mm/ioremap.c
-@@ -56,8 +56,8 @@ static int __ioremap_check_ram(unsigned long start_pfn, unsigned long nr_pages,
+@@ -56,12 +56,10 @@ static int __ioremap_check_ram(unsigned long start_pfn, unsigned long nr_pages,
  	unsigned long i;
  
  	for (i = 0; i < nr_pages; ++i)
@@ -33572,8 +33581,50 @@ index 70e7444..75b9a13 100644
 +		    !PageReserved(pfn_to_page(start_pfn + i))))
  			return 1;
  
- 	WARN_ONCE(1, "ioremap on RAM pfn 0x%lx\n", start_pfn);
-@@ -288,7 +288,7 @@ EXPORT_SYMBOL(ioremap_prot);
+-	WARN_ONCE(1, "ioremap on RAM pfn 0x%lx\n", start_pfn);
+-
+ 	return 0;
+ }
+ 
+@@ -91,7 +89,6 @@ static void __iomem *__ioremap_caller(resource_size_t phys_addr,
+ 	pgprot_t prot;
+ 	int retval;
+ 	void __iomem *ret_addr;
+-	int ram_region;
+ 
+ 	/* Don't allow wraparound or zero size */
+ 	last_addr = phys_addr + size - 1;
+@@ -114,23 +111,15 @@ static void __iomem *__ioremap_caller(resource_size_t phys_addr,
+ 	/*
+ 	 * Don't allow anybody to remap normal RAM that we're using..
+ 	 */
+-	/* First check if whole region can be identified as RAM or not */
+-	ram_region = region_is_ram(phys_addr, size);
+-	if (ram_region > 0) {
+-		WARN_ONCE(1, "ioremap on RAM at 0x%lx - 0x%lx\n",
+-				(unsigned long int)phys_addr,
+-				(unsigned long int)last_addr);
++	pfn      = phys_addr >> PAGE_SHIFT;
++	last_pfn = last_addr >> PAGE_SHIFT;
++	if (walk_system_ram_range(pfn, last_pfn - pfn + 1, NULL,
++					  __ioremap_check_ram) == 1) {
++		WARN_ONCE(1, "ioremap on RAM at 0x%llx - 0x%llx\n",
++					phys_addr, last_addr);
+ 		return NULL;
+ 	}
+ 
+-	/* If could not be identified(-1), check page by page */
+-	if (ram_region < 0) {
+-		pfn      = phys_addr >> PAGE_SHIFT;
+-		last_pfn = last_addr >> PAGE_SHIFT;
+-		if (walk_system_ram_range(pfn, last_pfn - pfn + 1, NULL,
+-					  __ioremap_check_ram) == 1)
+-			return NULL;
+-	}
+ 	/*
+ 	 * Mappings have to be page-aligned
+ 	 */
+@@ -288,7 +277,7 @@ EXPORT_SYMBOL(ioremap_prot);
   *
   * Caller must ensure there is only one unmapping for the same pointer.
   */
@@ -33582,7 +33633,7 @@ index 70e7444..75b9a13 100644
  {
  	struct vm_struct *p, *o;
  
-@@ -351,32 +351,36 @@ int arch_ioremap_pmd_supported(void)
+@@ -351,32 +340,36 @@ int arch_ioremap_pmd_supported(void)
   */
  void *xlate_dev_mem_ptr(phys_addr_t phys)
  {
@@ -33635,7 +33686,7 @@ index 70e7444..75b9a13 100644
  
  static inline pmd_t * __init early_ioremap_pmd(unsigned long addr)
  {
-@@ -412,8 +416,7 @@ void __init early_ioremap_init(void)
+@@ -412,8 +405,7 @@ void __init early_ioremap_init(void)
  	early_ioremap_setup();
  
  	pmd = early_ioremap_pmd(fix_to_virt(FIX_BTMAP_BEGIN));
@@ -34407,7 +34458,7 @@ index 90555bf..f5f1828 100644
  }
  
 diff --git a/arch/x86/mm/tlb.c b/arch/x86/mm/tlb.c
-index 3250f23..7a97ba2 100644
+index 3250f23..4197ac2 100644
 --- a/arch/x86/mm/tlb.c
 +++ b/arch/x86/mm/tlb.c
 @@ -45,7 +45,11 @@ void leave_mm(int cpu)
@@ -34422,6 +34473,15 @@ index 3250f23..7a97ba2 100644
  		/*
  		 * This gets called in the idle path where RCU
  		 * functions differently.  Tracing normally
+@@ -117,7 +121,7 @@ static void flush_tlb_func(void *info)
+ 		} else {
+ 			unsigned long addr;
+ 			unsigned long nr_pages =
+-				f->flush_end - f->flush_start / PAGE_SIZE;
++				(f->flush_end - f->flush_start) / PAGE_SIZE;
+ 			addr = f->flush_start;
+ 			while (addr < f->flush_end) {
+ 				__flush_tlb_single(addr);
 diff --git a/arch/x86/mm/uderef_64.c b/arch/x86/mm/uderef_64.c
 new file mode 100644
 index 0000000..3fda3f3
@@ -47683,6 +47743,19 @@ index c439c82..1f20f57 100644
  	union axis_conversion	ac;        /* hw -> logical axis */
  	int			mapped_btns[3];
  
+diff --git a/drivers/misc/mei/main.c b/drivers/misc/mei/main.c
+index 3e29681..e40bcd03 100644
+--- a/drivers/misc/mei/main.c
++++ b/drivers/misc/mei/main.c
+@@ -685,7 +685,7 @@ int mei_register(struct mei_device *dev, struct device *parent)
+ 	/* Fill in the data structures */
+ 	devno = MKDEV(MAJOR(mei_devt), dev->minor);
+ 	cdev_init(&dev->cdev, &mei_fops);
+-	dev->cdev.owner = mei_fops.owner;
++	dev->cdev.owner = parent->driver->owner;
+ 
+ 	/* Add the device */
+ 	ret = cdev_add(&dev->cdev, devno, 1);
 diff --git a/drivers/misc/sgi-gru/gruhandles.c b/drivers/misc/sgi-gru/gruhandles.c
 index 2f30bad..c4c13d0 100644
 --- a/drivers/misc/sgi-gru/gruhandles.c
@@ -96084,6 +96157,34 @@ index 7ee1774..72505b8 100644
  }
  
  /*
+diff --git a/include/linux/ftrace.h b/include/linux/ftrace.h
+index 1da6029..6cd8c0e 100644
+--- a/include/linux/ftrace.h
++++ b/include/linux/ftrace.h
+@@ -116,6 +116,7 @@ ftrace_func_t ftrace_ops_get_func(struct ftrace_ops *ops);
+  *            SAVE_REGS. If another ops with this flag set is already registered
+  *            for any of the functions that this ops will be registered for, then
+  *            this ops will fail to register or set_filter_ip.
++ * PID     - Is affected by set_ftrace_pid (allows filtering on those pids)
+  */
+ enum {
+ 	FTRACE_OPS_FL_ENABLED			= 1 << 0,
+@@ -132,6 +133,7 @@ enum {
+ 	FTRACE_OPS_FL_MODIFYING			= 1 << 11,
+ 	FTRACE_OPS_FL_ALLOC_TRAMP		= 1 << 12,
+ 	FTRACE_OPS_FL_IPMODIFY			= 1 << 13,
++	FTRACE_OPS_FL_PID			= 1 << 14,
+ };
+ 
+ #ifdef CONFIG_DYNAMIC_FTRACE
+@@ -159,6 +161,7 @@ struct ftrace_ops {
+ 	struct ftrace_ops		*next;
+ 	unsigned long			flags;
+ 	void				*private;
++	ftrace_func_t			saved_func;
+ 	int __percpu			*disabled;
+ #ifdef CONFIG_DYNAMIC_FTRACE
+ 	int				nr_trampolines;
 diff --git a/include/linux/genhd.h b/include/linux/genhd.h
 index ec274e0..e678159 100644
 --- a/include/linux/genhd.h
@@ -101287,6 +101388,71 @@ index 0320bbb..938789c 100644
  
  /** inet_connection_sock - INET connection oriented sock
   *
+diff --git a/include/net/inet_frag.h b/include/net/inet_frag.h
+index 8d17655..2f3246d 100644
+--- a/include/net/inet_frag.h
++++ b/include/net/inet_frag.h
+@@ -21,13 +21,11 @@ struct netns_frags {
+  * @INET_FRAG_FIRST_IN: first fragment has arrived
+  * @INET_FRAG_LAST_IN: final fragment has arrived
+  * @INET_FRAG_COMPLETE: frag queue has been processed and is due for destruction
+- * @INET_FRAG_EVICTED: frag queue is being evicted
+  */
+ enum {
+ 	INET_FRAG_FIRST_IN	= BIT(0),
+ 	INET_FRAG_LAST_IN	= BIT(1),
+ 	INET_FRAG_COMPLETE	= BIT(2),
+-	INET_FRAG_EVICTED	= BIT(3)
+ };
+ 
+ /**
+@@ -45,6 +43,7 @@ enum {
+  * @flags: fragment queue flags
+  * @max_size: (ipv4 only) maximum received fragment size with IP_DF set
+  * @net: namespace that this frag belongs to
++ * @list_evictor: list of queues to forcefully evict (e.g. due to low memory)
+  */
+ struct inet_frag_queue {
+ 	spinlock_t		lock;
+@@ -59,6 +58,7 @@ struct inet_frag_queue {
+ 	__u8			flags;
+ 	u16			max_size;
+ 	struct netns_frags	*net;
++	struct hlist_node	list_evictor;
+ };
+ 
+ #define INETFRAGS_HASHSZ	1024
+@@ -125,6 +125,11 @@ static inline void inet_frag_put(struct inet_frag_queue *q, struct inet_frags *f
+ 		inet_frag_destroy(q, f);
+ }
+ 
++static inline bool inet_frag_evicting(struct inet_frag_queue *q)
++{
++	return !hlist_unhashed(&q->list_evictor);
++}
++
+ /* Memory Tracking Functions. */
+ 
+ /* The default percpu_counter batch size is not big enough to scale to
+@@ -139,14 +144,14 @@ static inline int frag_mem_limit(struct netns_frags *nf)
+ 	return percpu_counter_read(&nf->mem);
+ }
+ 
+-static inline void sub_frag_mem_limit(struct inet_frag_queue *q, int i)
++static inline void sub_frag_mem_limit(struct netns_frags *nf, int i)
+ {
+-	__percpu_counter_add(&q->net->mem, -i, frag_percpu_counter_batch);
++	__percpu_counter_add(&nf->mem, -i, frag_percpu_counter_batch);
+ }
+ 
+-static inline void add_frag_mem_limit(struct inet_frag_queue *q, int i)
++static inline void add_frag_mem_limit(struct netns_frags *nf, int i)
+ {
+-	__percpu_counter_add(&q->net->mem, i, frag_percpu_counter_batch);
++	__percpu_counter_add(&nf->mem, i, frag_percpu_counter_batch);
+ }
+ 
+ static inline void init_frag_mem_limit(struct netns_frags *nf)
 diff --git a/include/net/inetpeer.h b/include/net/inetpeer.h
 index d5332dd..10a5c3c 100644
 --- a/include/net/inetpeer.h
@@ -102761,7 +102927,7 @@ index ad1bd77..dca2c1b 100644
  	next_state = Reset;
  	return 0;
 diff --git a/init/main.c b/init/main.c
-index 2a89545..eb9203f 100644
+index 2a89545..449eca2 100644
 --- a/init/main.c
 +++ b/init/main.c
 @@ -97,6 +97,8 @@ extern void radix_tree_init(void);
@@ -102773,7 +102939,7 @@ index 2a89545..eb9203f 100644
  /*
   * Debug helper: via this flag we know that we are in 'early bootup code'
   * where only the boot processor is running with IRQ disabled.  This means
-@@ -158,6 +160,84 @@ static int __init set_reset_devices(char *str)
+@@ -158,6 +160,85 @@ static int __init set_reset_devices(char *str)
  
  __setup("reset_devices", set_reset_devices);
  
@@ -102826,7 +102992,8 @@ index 2a89545..eb9203f 100644
 +	memcpy(pax_exit_kernel_user, (unsigned char []){0xc3}, 1);
 +	clone_pgd_mask = ~(pgdval_t)0UL;
 +	pax_user_shadow_base = 0UL;
-+	setup_clear_cpu_cap(X86_FEATURE_PCIDUDEREF);
++	setup_clear_cpu_cap(X86_FEATURE_PCID);
++	setup_clear_cpu_cap(X86_FEATURE_INVPCID);
 +#endif
 +
 +	return 0;
@@ -102858,7 +103025,7 @@ index 2a89545..eb9203f 100644
  static const char *argv_init[MAX_INIT_ARGS+2] = { "init", NULL, };
  const char *envp_init[MAX_INIT_ENVS+2] = { "HOME=/", "TERM=linux", NULL, };
  static const char *panic_later, *panic_param;
-@@ -726,7 +806,7 @@ static bool __init_or_module initcall_blacklisted(initcall_t fn)
+@@ -726,7 +807,7 @@ static bool __init_or_module initcall_blacklisted(initcall_t fn)
  	struct blacklist_entry *entry;
  	char *fn_name;
  
@@ -102867,7 +103034,7 @@ index 2a89545..eb9203f 100644
  	if (!fn_name)
  		return false;
  
-@@ -778,7 +858,7 @@ int __init_or_module do_one_initcall(initcall_t fn)
+@@ -778,7 +859,7 @@ int __init_or_module do_one_initcall(initcall_t fn)
  {
  	int count = preempt_count();
  	int ret;
@@ -102876,7 +103043,7 @@ index 2a89545..eb9203f 100644
  
  	if (initcall_blacklisted(fn))
  		return -EPERM;
-@@ -788,18 +868,17 @@ int __init_or_module do_one_initcall(initcall_t fn)
+@@ -788,18 +869,17 @@ int __init_or_module do_one_initcall(initcall_t fn)
  	else
  		ret = fn();
  
@@ -102899,7 +103066,7 @@ index 2a89545..eb9203f 100644
  	return ret;
  }
  
-@@ -905,8 +984,8 @@ static int run_init_process(const char *init_filename)
+@@ -905,8 +985,8 @@ static int run_init_process(const char *init_filename)
  {
  	argv_init[0] = init_filename;
  	return do_execve(getname_kernel(init_filename),
@@ -102910,7 +103077,7 @@ index 2a89545..eb9203f 100644
  }
  
  static int try_to_run_init_process(const char *init_filename)
-@@ -923,6 +1002,10 @@ static int try_to_run_init_process(const char *init_filename)
+@@ -923,6 +1003,10 @@ static int try_to_run_init_process(const char *init_filename)
  	return ret;
  }
  
@@ -102921,7 +103088,7 @@ index 2a89545..eb9203f 100644
  static noinline void __init kernel_init_freeable(void);
  
  static int __ref kernel_init(void *unused)
-@@ -947,6 +1030,11 @@ static int __ref kernel_init(void *unused)
+@@ -947,6 +1031,11 @@ static int __ref kernel_init(void *unused)
  		       ramdisk_execute_command, ret);
  	}
  
@@ -102933,7 +103100,7 @@ index 2a89545..eb9203f 100644
  	/*
  	 * We try each of these until one succeeds.
  	 *
-@@ -1002,7 +1090,7 @@ static noinline void __init kernel_init_freeable(void)
+@@ -1002,7 +1091,7 @@ static noinline void __init kernel_init_freeable(void)
  	do_basic_setup();
  
  	/* Open the /dev/console on the rootfs, this should never fail */
@@ -102942,7 +103109,7 @@ index 2a89545..eb9203f 100644
  		pr_err("Warning: unable to open an initial console.\n");
  
  	(void) sys_dup(0);
-@@ -1015,11 +1103,13 @@ static noinline void __init kernel_init_freeable(void)
+@@ -1015,11 +1104,13 @@ static noinline void __init kernel_init_freeable(void)
  	if (!ramdisk_execute_command)
  		ramdisk_execute_command = "/init";
  
@@ -107685,7 +107852,7 @@ index 1f13335..77ebb7f 100644
  }
  
 diff --git a/kernel/resource.c b/kernel/resource.c
-index 90552aa..8c02098 100644
+index 90552aa..ad13346 100644
 --- a/kernel/resource.c
 +++ b/kernel/resource.c
 @@ -162,8 +162,18 @@ static const struct file_operations proc_iomem_operations = {
@@ -107707,6 +107874,31 @@ index 90552aa..8c02098 100644
  	return 0;
  }
  __initcall(ioresources_init);
+@@ -504,13 +514,13 @@ int region_is_ram(resource_size_t start, unsigned long size)
+ {
+ 	struct resource *p;
+ 	resource_size_t end = start + size - 1;
+-	int flags = IORESOURCE_MEM | IORESOURCE_BUSY;
++	unsigned long flags = IORESOURCE_MEM | IORESOURCE_BUSY;
+ 	const char *name = "System RAM";
+ 	int ret = -1;
+ 
+ 	read_lock(&resource_lock);
+ 	for (p = iomem_resource.child; p ; p = p->sibling) {
+-		if (end < p->start)
++		if (p->end < start)
+ 			continue;
+ 
+ 		if (p->start <= start && end <= p->end) {
+@@ -521,7 +531,7 @@ int region_is_ram(resource_size_t start, unsigned long size)
+ 				ret = 1;
+ 			break;
+ 		}
+-		if (p->end < start)
++		if (end < p->start)
+ 			break;	/* not found */
+ 	}
+ 	read_unlock(&resource_lock);
 diff --git a/kernel/sched/auto_group.c b/kernel/sched/auto_group.c
 index eae160d..c9aa22e 100644
 --- a/kernel/sched/auto_group.c
@@ -109195,10 +109387,108 @@ index 483cecf..ac46091 100644
  
  	ret = -EIO;
 diff --git a/kernel/trace/ftrace.c b/kernel/trace/ftrace.c
-index 02bece4..f9b05af 100644
+index 02bece4..43adc29 100644
 --- a/kernel/trace/ftrace.c
 +++ b/kernel/trace/ftrace.c
-@@ -2395,12 +2395,17 @@ ftrace_code_disable(struct module *mod, struct dyn_ftrace *rec)
+@@ -98,6 +98,13 @@ struct ftrace_pid {
+ 	struct pid *pid;
+ };
+ 
++static bool ftrace_pids_enabled(void)
++{
++	return !list_empty(&ftrace_pids);
++}
++
++static void ftrace_update_trampoline(struct ftrace_ops *ops);
++
+ /*
+  * ftrace_disabled is set when an anomaly is discovered.
+  * ftrace_disabled is much stronger than ftrace_enabled.
+@@ -109,7 +116,6 @@ static DEFINE_MUTEX(ftrace_lock);
+ static struct ftrace_ops *ftrace_control_list __read_mostly = &ftrace_list_end;
+ static struct ftrace_ops *ftrace_ops_list __read_mostly = &ftrace_list_end;
+ ftrace_func_t ftrace_trace_function __read_mostly = ftrace_stub;
+-ftrace_func_t ftrace_pid_function __read_mostly = ftrace_stub;
+ static struct ftrace_ops global_ops;
+ static struct ftrace_ops control_ops;
+ 
+@@ -183,14 +189,7 @@ static void ftrace_pid_func(unsigned long ip, unsigned long parent_ip,
+ 	if (!test_tsk_trace_trace(current))
+ 		return;
+ 
+-	ftrace_pid_function(ip, parent_ip, op, regs);
+-}
+-
+-static void set_ftrace_pid_function(ftrace_func_t func)
+-{
+-	/* do not set ftrace_pid_function to itself! */
+-	if (func != ftrace_pid_func)
+-		ftrace_pid_function = func;
++	op->saved_func(ip, parent_ip, op, regs);
+ }
+ 
+ /**
+@@ -202,7 +201,6 @@ static void set_ftrace_pid_function(ftrace_func_t func)
+ void clear_ftrace_function(void)
+ {
+ 	ftrace_trace_function = ftrace_stub;
+-	ftrace_pid_function = ftrace_stub;
+ }
+ 
+ static void control_ops_disable_all(struct ftrace_ops *ops)
+@@ -436,6 +434,12 @@ static int __register_ftrace_function(struct ftrace_ops *ops)
+ 	} else
+ 		add_ftrace_ops(&ftrace_ops_list, ops);
+ 
++	/* Always save the function, and reset at unregistering */
++	ops->saved_func = ops->func;
++
++	if (ops->flags & FTRACE_OPS_FL_PID && ftrace_pids_enabled())
++		ops->func = ftrace_pid_func;
++
+ 	ftrace_update_trampoline(ops);
+ 
+ 	if (ftrace_enabled)
+@@ -463,15 +467,28 @@ static int __unregister_ftrace_function(struct ftrace_ops *ops)
+ 	if (ftrace_enabled)
+ 		update_ftrace_function();
+ 
++	ops->func = ops->saved_func;
++
+ 	return 0;
+ }
+ 
+ static void ftrace_update_pid_func(void)
+ {
++	bool enabled = ftrace_pids_enabled();
++	struct ftrace_ops *op;
++
+ 	/* Only do something if we are tracing something */
+ 	if (ftrace_trace_function == ftrace_stub)
+ 		return;
+ 
++	do_for_each_ftrace_op(op, ftrace_ops_list) {
++		if (op->flags & FTRACE_OPS_FL_PID) {
++			op->func = enabled ? ftrace_pid_func :
++				op->saved_func;
++			ftrace_update_trampoline(op);
++		}
++	} while_for_each_ftrace_op(op);
++
+ 	update_ftrace_function();
+ }
+ 
+@@ -1133,7 +1150,8 @@ static struct ftrace_ops global_ops = {
+ 	.local_hash.filter_hash		= EMPTY_HASH,
+ 	INIT_OPS_HASH(global_ops)
+ 	.flags				= FTRACE_OPS_FL_RECURSION_SAFE |
+-					  FTRACE_OPS_FL_INITIALIZED,
++					  FTRACE_OPS_FL_INITIALIZED |
++					  FTRACE_OPS_FL_PID,
+ };
+ 
+ /*
+@@ -2395,12 +2413,17 @@ ftrace_code_disable(struct module *mod, struct dyn_ftrace *rec)
  	if (unlikely(ftrace_disabled))
  		return 0;
  
@@ -109218,7 +109508,7 @@ index 02bece4..f9b05af 100644
  }
  
  /*
-@@ -4789,8 +4794,10 @@ static int ftrace_process_locs(struct module *mod,
+@@ -4789,8 +4812,10 @@ static int ftrace_process_locs(struct module *mod,
  	if (!count)
  		return 0;
  
@@ -109229,7 +109519,47 @@ index 02bece4..f9b05af 100644
  
  	start_pg = ftrace_allocate_pages(count);
  	if (!start_pg)
-@@ -5659,7 +5666,7 @@ static int alloc_retstack_tasklist(struct ftrace_ret_stack **ret_stack_list)
+@@ -5023,7 +5048,9 @@ static void ftrace_update_trampoline(struct ftrace_ops *ops)
+ 
+ static struct ftrace_ops global_ops = {
+ 	.func			= ftrace_stub,
+-	.flags			= FTRACE_OPS_FL_RECURSION_SAFE | FTRACE_OPS_FL_INITIALIZED,
++	.flags			= FTRACE_OPS_FL_RECURSION_SAFE |
++				  FTRACE_OPS_FL_INITIALIZED |
++				  FTRACE_OPS_FL_PID,
+ };
+ 
+ static int __init ftrace_nodyn_init(void)
+@@ -5080,11 +5107,6 @@ void ftrace_init_array_ops(struct trace_array *tr, ftrace_func_t func)
+ 		if (WARN_ON(tr->ops->func != ftrace_stub))
+ 			printk("ftrace ops had %pS for function\n",
+ 			       tr->ops->func);
+-		/* Only the top level instance does pid tracing */
+-		if (!list_empty(&ftrace_pids)) {
+-			set_ftrace_pid_function(func);
+-			func = ftrace_pid_func;
+-		}
+ 	}
+ 	tr->ops->func = func;
+ 	tr->ops->private = tr;
+@@ -5371,7 +5393,7 @@ static void *fpid_start(struct seq_file *m, loff_t *pos)
+ {
+ 	mutex_lock(&ftrace_lock);
+ 
+-	if (list_empty(&ftrace_pids) && (!*pos))
++	if (!ftrace_pids_enabled() && (!*pos))
+ 		return (void *) 1;
+ 
+ 	return seq_list_start(&ftrace_pids, *pos);
+@@ -5610,6 +5632,7 @@ static struct ftrace_ops graph_ops = {
+ 	.func			= ftrace_stub,
+ 	.flags			= FTRACE_OPS_FL_RECURSION_SAFE |
+ 				   FTRACE_OPS_FL_INITIALIZED |
++				   FTRACE_OPS_FL_PID |
+ 				   FTRACE_OPS_FL_STUB,
+ #ifdef FTRACE_GRAPH_TRAMP_ADDR
+ 	.trampoline		= FTRACE_GRAPH_TRAMP_ADDR,
+@@ -5659,7 +5682,7 @@ static int alloc_retstack_tasklist(struct ftrace_ret_stack **ret_stack_list)
  
  		if (t->ret_stack == NULL) {
  			atomic_set(&t->tracing_graph_pause, 0);
@@ -109238,7 +109568,7 @@ index 02bece4..f9b05af 100644
  			t->curr_ret_stack = -1;
  			/* Make sure the tasks see the -1 first: */
  			smp_wmb();
-@@ -5882,7 +5889,7 @@ static void
+@@ -5882,7 +5905,7 @@ static void
  graph_init_task(struct task_struct *t, struct ftrace_ret_stack *ret_stack)
  {
  	atomic_set(&t->tracing_graph_pause, 0);
@@ -116603,6 +116933,21 @@ index 8e385a0..a5bdd8e 100644
  
  	tty_port_close(&dev->port, tty, filp);
  }
+diff --git a/net/bluetooth/smp.c b/net/bluetooth/smp.c
+index 1ab3dc9..7b815bc 100644
+--- a/net/bluetooth/smp.c
++++ b/net/bluetooth/smp.c
+@@ -2295,6 +2295,10 @@ int smp_conn_security(struct hci_conn *hcon, __u8 sec_level)
+ 		return 1;
+ 
+ 	chan = conn->smp;
++	if (!chan) {
++		BT_ERR("SMP security requested but not available");
++		return 1;
++	}
+ 
+ 	if (!hci_dev_test_flag(hcon->hdev, HCI_LE_ENABLED))
+ 		return 1;
 diff --git a/net/bridge/br_mdb.c b/net/bridge/br_mdb.c
 index e29ad70b..cc00066 100644
 --- a/net/bridge/br_mdb.c
@@ -117842,9 +118187,36 @@ index 0ae5822..3fe3627 100644
  	.priv_size	= sizeof(struct lowpan_dev_info),
  	.setup		= lowpan_setup,
 diff --git a/net/ieee802154/6lowpan/reassembly.c b/net/ieee802154/6lowpan/reassembly.c
-index f46e4d1..30231f1 100644
+index f46e4d1..dcb7f86 100644
 --- a/net/ieee802154/6lowpan/reassembly.c
 +++ b/net/ieee802154/6lowpan/reassembly.c
+@@ -207,7 +207,7 @@ found:
+ 	} else {
+ 		fq->q.meat += skb->len;
+ 	}
+-	add_frag_mem_limit(&fq->q, skb->truesize);
++	add_frag_mem_limit(fq->q.net, skb->truesize);
+ 
+ 	if (fq->q.flags == (INET_FRAG_FIRST_IN | INET_FRAG_LAST_IN) &&
+ 	    fq->q.meat == fq->q.len) {
+@@ -287,7 +287,7 @@ static int lowpan_frag_reasm(struct lowpan_frag_queue *fq, struct sk_buff *prev,
+ 		clone->data_len = clone->len;
+ 		head->data_len -= clone->len;
+ 		head->len -= clone->len;
+-		add_frag_mem_limit(&fq->q, clone->truesize);
++		add_frag_mem_limit(fq->q.net, clone->truesize);
+ 	}
+ 
+ 	WARN_ON(head == NULL);
+@@ -310,7 +310,7 @@ static int lowpan_frag_reasm(struct lowpan_frag_queue *fq, struct sk_buff *prev,
+ 		}
+ 		fp = next;
+ 	}
+-	sub_frag_mem_limit(&fq->q, sum_truesize);
++	sub_frag_mem_limit(fq->q.net, sum_truesize);
+ 
+ 	head->next = NULL;
+ 	head->dev = dev;
 @@ -435,14 +435,13 @@ static struct ctl_table lowpan_frags_ctl_table[] = {
  
  static int __net_init lowpan_frags_ns_sysctl_register(struct net *net)
@@ -118030,6 +118402,117 @@ index 8d695b6..752d427a 100644
  
  	return nh->nh_saddr;
  }
+diff --git a/net/ipv4/inet_fragment.c b/net/ipv4/inet_fragment.c
+index 5e346a0..d0a7c03 100644
+--- a/net/ipv4/inet_fragment.c
++++ b/net/ipv4/inet_fragment.c
+@@ -131,34 +131,22 @@ inet_evict_bucket(struct inet_frags *f, struct inet_frag_bucket *hb)
+ 	unsigned int evicted = 0;
+ 	HLIST_HEAD(expired);
+ 
+-evict_again:
+ 	spin_lock(&hb->chain_lock);
+ 
+ 	hlist_for_each_entry_safe(fq, n, &hb->chain, list) {
+ 		if (!inet_fragq_should_evict(fq))
+ 			continue;
+ 
+-		if (!del_timer(&fq->timer)) {
+-			/* q expiring right now thus increment its refcount so
+-			 * it won't be freed under us and wait until the timer
+-			 * has finished executing then destroy it
+-			 */
+-			atomic_inc(&fq->refcnt);
+-			spin_unlock(&hb->chain_lock);
+-			del_timer_sync(&fq->timer);
+-			inet_frag_put(fq, f);
+-			goto evict_again;
+-		}
++		if (!del_timer(&fq->timer))
++			continue;
+ 
+-		fq->flags |= INET_FRAG_EVICTED;
+-		hlist_del(&fq->list);
+-		hlist_add_head(&fq->list, &expired);
++		hlist_add_head(&fq->list_evictor, &expired);
+ 		++evicted;
+ 	}
+ 
+ 	spin_unlock(&hb->chain_lock);
+ 
+-	hlist_for_each_entry_safe(fq, n, &expired, list)
++	hlist_for_each_entry_safe(fq, n, &expired, list_evictor)
+ 		f->frag_expire((unsigned long) fq);
+ 
+ 	return evicted;
+@@ -240,19 +228,21 @@ void inet_frags_exit_net(struct netns_frags *nf, struct inet_frags *f)
+ 	int i;
+ 
+ 	nf->low_thresh = 0;
+-	local_bh_disable();
+ 
+ evict_again:
++	local_bh_disable();
+ 	seq = read_seqbegin(&f->rnd_seqlock);
+ 
+ 	for (i = 0; i < INETFRAGS_HASHSZ ; i++)
+ 		inet_evict_bucket(f, &f->hash[i]);
+ 
+-	if (read_seqretry(&f->rnd_seqlock, seq))
++	local_bh_enable();
++	cond_resched();
++
++	if (read_seqretry(&f->rnd_seqlock, seq) ||
++	    percpu_counter_sum(&nf->mem))
+ 		goto evict_again;
+ 
+-	local_bh_enable();
+-
+ 	percpu_counter_destroy(&nf->mem);
+ }
+ EXPORT_SYMBOL(inet_frags_exit_net);
+@@ -284,8 +274,8 @@ static inline void fq_unlink(struct inet_frag_queue *fq, struct inet_frags *f)
+ 	struct inet_frag_bucket *hb;
+ 
+ 	hb = get_frag_bucket_locked(fq, f);
+-	if (!(fq->flags & INET_FRAG_EVICTED))
+-		hlist_del(&fq->list);
++	hlist_del(&fq->list);
++	fq->flags |= INET_FRAG_COMPLETE;
+ 	spin_unlock(&hb->chain_lock);
+ }
+ 
+@@ -297,7 +287,6 @@ void inet_frag_kill(struct inet_frag_queue *fq, struct inet_frags *f)
+ 	if (!(fq->flags & INET_FRAG_COMPLETE)) {
+ 		fq_unlink(fq, f);
+ 		atomic_dec(&fq->refcnt);
+-		fq->flags |= INET_FRAG_COMPLETE;
+ 	}
+ }
+ EXPORT_SYMBOL(inet_frag_kill);
+@@ -330,11 +319,12 @@ void inet_frag_destroy(struct inet_frag_queue *q, struct inet_frags *f)
+ 		fp = xp;
+ 	}
+ 	sum = sum_truesize + f->qsize;
+-	sub_frag_mem_limit(q, sum);
+ 
+ 	if (f->destructor)
+ 		f->destructor(q);
+ 	kmem_cache_free(f->frags_cachep, q);
++
++	sub_frag_mem_limit(nf, sum);
+ }
+ EXPORT_SYMBOL(inet_frag_destroy);
+ 
+@@ -390,7 +380,7 @@ static struct inet_frag_queue *inet_frag_alloc(struct netns_frags *nf,
+ 
+ 	q->net = nf;
+ 	f->constructor(q, arg);
+-	add_frag_mem_limit(q, f->qsize);
++	add_frag_mem_limit(nf, f->qsize);
+ 
+ 	setup_timer(&q->timer, f->frag_expire, (unsigned long)q);
+ 	spin_lock_init(&q->lock);
 diff --git a/net/ipv4/inet_hashtables.c b/net/ipv4/inet_hashtables.c
 index c6fb80b..8705495 100644
 --- a/net/ipv4/inet_hashtables.c
@@ -118074,9 +118557,18 @@ index 241afd7..31b95d5 100644
  		p->rate_tokens = 0;
  		/* 60*HZ is arbitrary, but chosen enough high so that the first
 diff --git a/net/ipv4/ip_fragment.c b/net/ipv4/ip_fragment.c
-index cc1da6d..64b1534 100644
+index cc1da6d..593fc73 100644
 --- a/net/ipv4/ip_fragment.c
 +++ b/net/ipv4/ip_fragment.c
+@@ -192,7 +192,7 @@ static void ip_expire(unsigned long arg)
+ 	ipq_kill(qp);
+ 	IP_INC_STATS_BH(net, IPSTATS_MIB_REASMFAILS);
+ 
+-	if (!(qp->q.flags & INET_FRAG_EVICTED)) {
++	if (!inet_frag_evicting(&qp->q)) {
+ 		struct sk_buff *head = qp->q.fragments;
+ 		const struct iphdr *iph;
+ 		int err;
 @@ -268,7 +268,7 @@ static int ip_frag_too_far(struct ipq *qp)
  		return 0;
  
@@ -118086,6 +118578,51 @@ index cc1da6d..64b1534 100644
  	qp->rid = end;
  
  	rc = qp->q.fragments && (end - start) > max;
+@@ -301,7 +301,7 @@ static int ip_frag_reinit(struct ipq *qp)
+ 		kfree_skb(fp);
+ 		fp = xp;
+ 	} while (fp);
+-	sub_frag_mem_limit(&qp->q, sum_truesize);
++	sub_frag_mem_limit(qp->q.net, sum_truesize);
+ 
+ 	qp->q.flags = 0;
+ 	qp->q.len = 0;
+@@ -446,7 +446,7 @@ found:
+ 				qp->q.fragments = next;
+ 
+ 			qp->q.meat -= free_it->len;
+-			sub_frag_mem_limit(&qp->q, free_it->truesize);
++			sub_frag_mem_limit(qp->q.net, free_it->truesize);
+ 			kfree_skb(free_it);
+ 		}
+ 	}
+@@ -470,7 +470,7 @@ found:
+ 	qp->q.stamp = skb->tstamp;
+ 	qp->q.meat += skb->len;
+ 	qp->ecn |= ecn;
+-	add_frag_mem_limit(&qp->q, skb->truesize);
++	add_frag_mem_limit(qp->q.net, skb->truesize);
+ 	if (offset == 0)
+ 		qp->q.flags |= INET_FRAG_FIRST_IN;
+ 
+@@ -573,7 +573,7 @@ static int ip_frag_reasm(struct ipq *qp, struct sk_buff *prev,
+ 		head->len -= clone->len;
+ 		clone->csum = 0;
+ 		clone->ip_summed = head->ip_summed;
+-		add_frag_mem_limit(&qp->q, clone->truesize);
++		add_frag_mem_limit(qp->q.net, clone->truesize);
+ 	}
+ 
+ 	skb_push(head, head->data - skb_network_header(head));
+@@ -601,7 +601,7 @@ static int ip_frag_reasm(struct ipq *qp, struct sk_buff *prev,
+ 		}
+ 		fp = next;
+ 	}
+-	sub_frag_mem_limit(&qp->q, sum_truesize);
++	sub_frag_mem_limit(qp->q.net, sum_truesize);
+ 
+ 	head->next = NULL;
+ 	head->dev = dev;
 @@ -750,12 +750,11 @@ static struct ctl_table ip4_frags_ctl_table[] = {
  
  static int __net_init ip4_frags_ns_ctl_register(struct net *net)
@@ -119380,7 +119917,7 @@ index 62f5b0d..331fdb1 100644
  
  	case IP6T_SO_GET_ENTRIES:
 diff --git a/net/ipv6/netfilter/nf_conntrack_reasm.c b/net/ipv6/netfilter/nf_conntrack_reasm.c
-index 6f187c8..34b367f 100644
+index 6f187c8..55e564f 100644
 --- a/net/ipv6/netfilter/nf_conntrack_reasm.c
 +++ b/net/ipv6/netfilter/nf_conntrack_reasm.c
 @@ -96,12 +96,11 @@ static struct ctl_table nf_ct_frag6_sysctl_table[] = {
@@ -119421,6 +119958,33 @@ index 6f187c8..34b367f 100644
  err_alloc:
  	return -ENOMEM;
  }
+@@ -348,7 +346,7 @@ found:
+ 	fq->ecn |= ecn;
+ 	if (payload_len > fq->q.max_size)
+ 		fq->q.max_size = payload_len;
+-	add_frag_mem_limit(&fq->q, skb->truesize);
++	add_frag_mem_limit(fq->q.net, skb->truesize);
+ 
+ 	/* The first fragment.
+ 	 * nhoffset is obtained from the first fragment, of course.
+@@ -430,7 +428,7 @@ nf_ct_frag6_reasm(struct frag_queue *fq, struct net_device *dev)
+ 		clone->ip_summed = head->ip_summed;
+ 
+ 		NFCT_FRAG6_CB(clone)->orig = NULL;
+-		add_frag_mem_limit(&fq->q, clone->truesize);
++		add_frag_mem_limit(fq->q.net, clone->truesize);
+ 	}
+ 
+ 	/* We have to remove fragment header from datagram and to relocate
+@@ -454,7 +452,7 @@ nf_ct_frag6_reasm(struct frag_queue *fq, struct net_device *dev)
+ 			head->csum = csum_add(head->csum, fp->csum);
+ 		head->truesize += fp->truesize;
+ 	}
+-	sub_frag_mem_limit(&fq->q, head->truesize);
++	sub_frag_mem_limit(fq->q.net, head->truesize);
+ 
+ 	head->ignore_df = 1;
+ 	head->next = NULL;
 diff --git a/net/ipv6/ping.c b/net/ipv6/ping.c
 index 263a516..692f738 100644
 --- a/net/ipv6/ping.c
@@ -119570,9 +120134,45 @@ index 8072bd4..1629245 100644
  		return 0;
  	default:
 diff --git a/net/ipv6/reassembly.c b/net/ipv6/reassembly.c
-index 8ffa2c8..5968612 100644
+index 8ffa2c8..0db5dad 100644
 --- a/net/ipv6/reassembly.c
 +++ b/net/ipv6/reassembly.c
+@@ -144,7 +144,7 @@ void ip6_expire_frag_queue(struct net *net, struct frag_queue *fq,
+ 
+ 	IP6_INC_STATS_BH(net, __in6_dev_get(dev), IPSTATS_MIB_REASMFAILS);
+ 
+-	if (fq->q.flags & INET_FRAG_EVICTED)
++	if (inet_frag_evicting(&fq->q))
+ 		goto out_rcu_unlock;
+ 
+ 	IP6_INC_STATS_BH(net, __in6_dev_get(dev), IPSTATS_MIB_REASMTIMEOUT);
+@@ -330,7 +330,7 @@ found:
+ 	fq->q.stamp = skb->tstamp;
+ 	fq->q.meat += skb->len;
+ 	fq->ecn |= ecn;
+-	add_frag_mem_limit(&fq->q, skb->truesize);
++	add_frag_mem_limit(fq->q.net, skb->truesize);
+ 
+ 	/* The first fragment.
+ 	 * nhoffset is obtained from the first fragment, of course.
+@@ -443,7 +443,7 @@ static int ip6_frag_reasm(struct frag_queue *fq, struct sk_buff *prev,
+ 		head->len -= clone->len;
+ 		clone->csum = 0;
+ 		clone->ip_summed = head->ip_summed;
+-		add_frag_mem_limit(&fq->q, clone->truesize);
++		add_frag_mem_limit(fq->q.net, clone->truesize);
+ 	}
+ 
+ 	/* We have to remove fragment header from datagram and to relocate
+@@ -481,7 +481,7 @@ static int ip6_frag_reasm(struct frag_queue *fq, struct sk_buff *prev,
+ 		}
+ 		fp = next;
+ 	}
+-	sub_frag_mem_limit(&fq->q, sum_truesize);
++	sub_frag_mem_limit(fq->q.net, sum_truesize);
+ 
+ 	head->next = NULL;
+ 	head->dev = dev;
 @@ -626,12 +626,11 @@ static struct ctl_table ip6_frags_ctl_table[] = {
  
  static int __net_init ip6_frags_ns_sysctl_register(struct net *net)


^ permalink raw reply related	[flat|nested] only message in thread

only message in thread, other threads:[~2015-07-29 13:20 UTC | newest]

Thread overview: (only message) (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2015-07-29 13:20 [gentoo-commits] proj/hardened-patchset:master commit in: 4.1.3/ Anthony G. Basile

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox