aboutsummaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorIngo Molnar <mingo@kernel.org>2016-02-18 03:28:03 -0500
committerIngo Molnar <mingo@kernel.org>2016-02-18 03:28:03 -0500
commit3a2f2ac9b96f9a9f5538396a212d3b9fb543bfc5 (patch)
tree294c2f340b11584e58cea90adfc4182ac8742348 /lib
parent4e79e182b419172e35936a47f098509092d69817 (diff)
parentf4eafd8bcd5229e998aa252627703b8462c3b90f (diff)
Merge branch 'x86/urgent' into x86/asm, to pick up fixes
Signed-off-by: Ingo Molnar <mingo@kernel.org>
Diffstat (limited to 'lib')
-rw-r--r--lib/Kconfig.debug15
-rw-r--r--lib/Kconfig.ubsan4
-rw-r--r--lib/debugobjects.c2
-rw-r--r--lib/dump_stack.c7
-rw-r--r--lib/klist.c6
-rw-r--r--lib/radix-tree.c12
-rw-r--r--lib/scatterlist.c6
-rw-r--r--lib/test-string_helpers.c67
-rw-r--r--lib/ucs2_string.c62
-rw-r--r--lib/vsprintf.c26
10 files changed, 163 insertions, 44 deletions
diff --git a/lib/Kconfig.debug b/lib/Kconfig.debug
index ecb9e75614bf..8bfd1aca7a3d 100644
--- a/lib/Kconfig.debug
+++ b/lib/Kconfig.debug
@@ -1400,6 +1400,21 @@ config RCU_EQS_DEBUG
1400 1400
1401endmenu # "RCU Debugging" 1401endmenu # "RCU Debugging"
1402 1402
1403config DEBUG_WQ_FORCE_RR_CPU
1404 bool "Force round-robin CPU selection for unbound work items"
1405 depends on DEBUG_KERNEL
1406 default n
1407 help
1408 Workqueue used to implicitly guarantee that work items queued
1409 without explicit CPU specified are put on the local CPU. This
1410 guarantee is no longer true and while local CPU is still
1411 preferred work items may be put on foreign CPUs. Kernel
1412 parameter "workqueue.debug_force_rr_cpu" is added to force
1413 round-robin CPU selection to flush out usages which depend on the
1414 now broken guarantee. This config option enables the debug
1415 feature by default. When enabled, memory and cache locality will
1416 be impacted.
1417
1403config DEBUG_BLOCK_EXT_DEVT 1418config DEBUG_BLOCK_EXT_DEVT
1404 bool "Force extended block device numbers and spread them" 1419 bool "Force extended block device numbers and spread them"
1405 depends on DEBUG_KERNEL 1420 depends on DEBUG_KERNEL
diff --git a/lib/Kconfig.ubsan b/lib/Kconfig.ubsan
index 49518fb48cab..e07c1ba9ba13 100644
--- a/lib/Kconfig.ubsan
+++ b/lib/Kconfig.ubsan
@@ -18,6 +18,8 @@ config UBSAN_SANITIZE_ALL
18 This option activates instrumentation for the entire kernel. 18 This option activates instrumentation for the entire kernel.
19 If you don't enable this option, you have to explicitly specify 19 If you don't enable this option, you have to explicitly specify
20 UBSAN_SANITIZE := y for the files/directories you want to check for UB. 20 UBSAN_SANITIZE := y for the files/directories you want to check for UB.
21 Enabling this option will get kernel image size increased
22 significantly.
21 23
22config UBSAN_ALIGNMENT 24config UBSAN_ALIGNMENT
23 bool "Enable checking of pointers alignment" 25 bool "Enable checking of pointers alignment"
@@ -25,5 +27,5 @@ config UBSAN_ALIGNMENT
25 default y if !HAVE_EFFICIENT_UNALIGNED_ACCESS 27 default y if !HAVE_EFFICIENT_UNALIGNED_ACCESS
26 help 28 help
27 This option enables detection of unaligned memory accesses. 29 This option enables detection of unaligned memory accesses.
28 Enabling this option on architectures that support unalligned 30 Enabling this option on architectures that support unaligned
29 accesses may produce a lot of false positives. 31 accesses may produce a lot of false positives.
diff --git a/lib/debugobjects.c b/lib/debugobjects.c
index 547f7f923dbc..519b5a10fd70 100644
--- a/lib/debugobjects.c
+++ b/lib/debugobjects.c
@@ -21,7 +21,7 @@
21#define ODEBUG_HASH_BITS 14 21#define ODEBUG_HASH_BITS 14
22#define ODEBUG_HASH_SIZE (1 << ODEBUG_HASH_BITS) 22#define ODEBUG_HASH_SIZE (1 << ODEBUG_HASH_BITS)
23 23
24#define ODEBUG_POOL_SIZE 512 24#define ODEBUG_POOL_SIZE 1024
25#define ODEBUG_POOL_MIN_LEVEL 256 25#define ODEBUG_POOL_MIN_LEVEL 256
26 26
27#define ODEBUG_CHUNK_SHIFT PAGE_SHIFT 27#define ODEBUG_CHUNK_SHIFT PAGE_SHIFT
diff --git a/lib/dump_stack.c b/lib/dump_stack.c
index 6745c6230db3..c30d07e99dba 100644
--- a/lib/dump_stack.c
+++ b/lib/dump_stack.c
@@ -25,6 +25,7 @@ static atomic_t dump_lock = ATOMIC_INIT(-1);
25 25
26asmlinkage __visible void dump_stack(void) 26asmlinkage __visible void dump_stack(void)
27{ 27{
28 unsigned long flags;
28 int was_locked; 29 int was_locked;
29 int old; 30 int old;
30 int cpu; 31 int cpu;
@@ -33,9 +34,8 @@ asmlinkage __visible void dump_stack(void)
33 * Permit this cpu to perform nested stack dumps while serialising 34 * Permit this cpu to perform nested stack dumps while serialising
34 * against other CPUs 35 * against other CPUs
35 */ 36 */
36 preempt_disable();
37
38retry: 37retry:
38 local_irq_save(flags);
39 cpu = smp_processor_id(); 39 cpu = smp_processor_id();
40 old = atomic_cmpxchg(&dump_lock, -1, cpu); 40 old = atomic_cmpxchg(&dump_lock, -1, cpu);
41 if (old == -1) { 41 if (old == -1) {
@@ -43,6 +43,7 @@ retry:
43 } else if (old == cpu) { 43 } else if (old == cpu) {
44 was_locked = 1; 44 was_locked = 1;
45 } else { 45 } else {
46 local_irq_restore(flags);
46 cpu_relax(); 47 cpu_relax();
47 goto retry; 48 goto retry;
48 } 49 }
@@ -52,7 +53,7 @@ retry:
52 if (!was_locked) 53 if (!was_locked)
53 atomic_set(&dump_lock, -1); 54 atomic_set(&dump_lock, -1);
54 55
55 preempt_enable(); 56 local_irq_restore(flags);
56} 57}
57#else 58#else
58asmlinkage __visible void dump_stack(void) 59asmlinkage __visible void dump_stack(void)
diff --git a/lib/klist.c b/lib/klist.c
index d74cf7a29afd..0507fa5d84c5 100644
--- a/lib/klist.c
+++ b/lib/klist.c
@@ -282,9 +282,9 @@ void klist_iter_init_node(struct klist *k, struct klist_iter *i,
282 struct klist_node *n) 282 struct klist_node *n)
283{ 283{
284 i->i_klist = k; 284 i->i_klist = k;
285 i->i_cur = n; 285 i->i_cur = NULL;
286 if (n) 286 if (n && kref_get_unless_zero(&n->n_ref))
287 kref_get(&n->n_ref); 287 i->i_cur = n;
288} 288}
289EXPORT_SYMBOL_GPL(klist_iter_init_node); 289EXPORT_SYMBOL_GPL(klist_iter_init_node);
290 290
diff --git a/lib/radix-tree.c b/lib/radix-tree.c
index fcf5d98574ce..6b79e9026e24 100644
--- a/lib/radix-tree.c
+++ b/lib/radix-tree.c
@@ -1019,9 +1019,13 @@ radix_tree_gang_lookup(struct radix_tree_root *root, void **results,
1019 return 0; 1019 return 0;
1020 1020
1021 radix_tree_for_each_slot(slot, root, &iter, first_index) { 1021 radix_tree_for_each_slot(slot, root, &iter, first_index) {
1022 results[ret] = indirect_to_ptr(rcu_dereference_raw(*slot)); 1022 results[ret] = rcu_dereference_raw(*slot);
1023 if (!results[ret]) 1023 if (!results[ret])
1024 continue; 1024 continue;
1025 if (radix_tree_is_indirect_ptr(results[ret])) {
1026 slot = radix_tree_iter_retry(&iter);
1027 continue;
1028 }
1025 if (++ret == max_items) 1029 if (++ret == max_items)
1026 break; 1030 break;
1027 } 1031 }
@@ -1098,9 +1102,13 @@ radix_tree_gang_lookup_tag(struct radix_tree_root *root, void **results,
1098 return 0; 1102 return 0;
1099 1103
1100 radix_tree_for_each_tagged(slot, root, &iter, first_index, tag) { 1104 radix_tree_for_each_tagged(slot, root, &iter, first_index, tag) {
1101 results[ret] = indirect_to_ptr(rcu_dereference_raw(*slot)); 1105 results[ret] = rcu_dereference_raw(*slot);
1102 if (!results[ret]) 1106 if (!results[ret])
1103 continue; 1107 continue;
1108 if (radix_tree_is_indirect_ptr(results[ret])) {
1109 slot = radix_tree_iter_retry(&iter);
1110 continue;
1111 }
1104 if (++ret == max_items) 1112 if (++ret == max_items)
1105 break; 1113 break;
1106 } 1114 }
diff --git a/lib/scatterlist.c b/lib/scatterlist.c
index bafa9933fa76..004fc70fc56a 100644
--- a/lib/scatterlist.c
+++ b/lib/scatterlist.c
@@ -598,9 +598,9 @@ EXPORT_SYMBOL(sg_miter_next);
598 * 598 *
599 * Description: 599 * Description:
600 * Stops mapping iterator @miter. @miter should have been started 600 * Stops mapping iterator @miter. @miter should have been started
601 * started using sg_miter_start(). A stopped iteration can be 601 * using sg_miter_start(). A stopped iteration can be resumed by
602 * resumed by calling sg_miter_next() on it. This is useful when 602 * calling sg_miter_next() on it. This is useful when resources (kmap)
603 * resources (kmap) need to be released during iteration. 603 * need to be released during iteration.
604 * 604 *
605 * Context: 605 * Context:
606 * Preemption disabled if the SG_MITER_ATOMIC is set. Don't care 606 * Preemption disabled if the SG_MITER_ATOMIC is set. Don't care
diff --git a/lib/test-string_helpers.c b/lib/test-string_helpers.c
index 98866a770770..25b5cbfb7615 100644
--- a/lib/test-string_helpers.c
+++ b/lib/test-string_helpers.c
@@ -327,36 +327,67 @@ out:
327} 327}
328 328
329#define string_get_size_maxbuf 16 329#define string_get_size_maxbuf 16
330#define test_string_get_size_one(size, blk_size, units, exp_result) \ 330#define test_string_get_size_one(size, blk_size, exp_result10, exp_result2) \
331 do { \ 331 do { \
332 BUILD_BUG_ON(sizeof(exp_result) >= string_get_size_maxbuf); \ 332 BUILD_BUG_ON(sizeof(exp_result10) >= string_get_size_maxbuf); \
333 __test_string_get_size((size), (blk_size), (units), \ 333 BUILD_BUG_ON(sizeof(exp_result2) >= string_get_size_maxbuf); \
334 (exp_result)); \ 334 __test_string_get_size((size), (blk_size), (exp_result10), \
335 (exp_result2)); \
335 } while (0) 336 } while (0)
336 337
337 338
338static __init void __test_string_get_size(const u64 size, const u64 blk_size, 339static __init void test_string_get_size_check(const char *units,
339 const enum string_size_units units, 340 const char *exp,
340 const char *exp_result) 341 char *res,
342 const u64 size,
343 const u64 blk_size)
341{ 344{
342 char buf[string_get_size_maxbuf]; 345 if (!memcmp(res, exp, strlen(exp) + 1))
343
344 string_get_size(size, blk_size, units, buf, sizeof(buf));
345 if (!memcmp(buf, exp_result, strlen(exp_result) + 1))
346 return; 346 return;
347 347
348 buf[sizeof(buf) - 1] = '\0'; 348 res[string_get_size_maxbuf - 1] = '\0';
349 pr_warn("Test 'test_string_get_size_one' failed!\n"); 349
350 pr_warn("string_get_size(size = %llu, blk_size = %llu, units = %d\n", 350 pr_warn("Test 'test_string_get_size' failed!\n");
351 pr_warn("string_get_size(size = %llu, blk_size = %llu, units = %s)\n",
351 size, blk_size, units); 352 size, blk_size, units);
352 pr_warn("expected: '%s', got '%s'\n", exp_result, buf); 353 pr_warn("expected: '%s', got '%s'\n", exp, res);
354}
355
356static __init void __test_string_get_size(const u64 size, const u64 blk_size,
357 const char *exp_result10,
358 const char *exp_result2)
359{
360 char buf10[string_get_size_maxbuf];
361 char buf2[string_get_size_maxbuf];
362
363 string_get_size(size, blk_size, STRING_UNITS_10, buf10, sizeof(buf10));
364 string_get_size(size, blk_size, STRING_UNITS_2, buf2, sizeof(buf2));
365
366 test_string_get_size_check("STRING_UNITS_10", exp_result10, buf10,
367 size, blk_size);
368
369 test_string_get_size_check("STRING_UNITS_2", exp_result2, buf2,
370 size, blk_size);
353} 371}
354 372
355static __init void test_string_get_size(void) 373static __init void test_string_get_size(void)
356{ 374{
357 test_string_get_size_one(16384, 512, STRING_UNITS_2, "8.00 MiB"); 375 /* small values */
358 test_string_get_size_one(8192, 4096, STRING_UNITS_10, "32.7 MB"); 376 test_string_get_size_one(0, 512, "0 B", "0 B");
359 test_string_get_size_one(1, 512, STRING_UNITS_10, "512 B"); 377 test_string_get_size_one(1, 512, "512 B", "512 B");
378 test_string_get_size_one(1100, 1, "1.10 kB", "1.07 KiB");
379
380 /* normal values */
381 test_string_get_size_one(16384, 512, "8.39 MB", "8.00 MiB");
382 test_string_get_size_one(500118192, 512, "256 GB", "238 GiB");
383 test_string_get_size_one(8192, 4096, "33.6 MB", "32.0 MiB");
384
385 /* weird block sizes */
386 test_string_get_size_one(3000, 1900, "5.70 MB", "5.44 MiB");
387
388 /* huge values */
389 test_string_get_size_one(U64_MAX, 4096, "75.6 ZB", "64.0 ZiB");
390 test_string_get_size_one(4096, U64_MAX, "75.6 ZB", "64.0 ZiB");
360} 391}
361 392
362static int __init test_string_helpers_init(void) 393static int __init test_string_helpers_init(void)
diff --git a/lib/ucs2_string.c b/lib/ucs2_string.c
index 6f500ef2301d..f0b323abb4c6 100644
--- a/lib/ucs2_string.c
+++ b/lib/ucs2_string.c
@@ -49,3 +49,65 @@ ucs2_strncmp(const ucs2_char_t *a, const ucs2_char_t *b, size_t len)
49 } 49 }
50} 50}
51EXPORT_SYMBOL(ucs2_strncmp); 51EXPORT_SYMBOL(ucs2_strncmp);
52
53unsigned long
54ucs2_utf8size(const ucs2_char_t *src)
55{
56 unsigned long i;
57 unsigned long j = 0;
58
59 for (i = 0; i < ucs2_strlen(src); i++) {
60 u16 c = src[i];
61
62 if (c >= 0x800)
63 j += 3;
64 else if (c >= 0x80)
65 j += 2;
66 else
67 j += 1;
68 }
69
70 return j;
71}
72EXPORT_SYMBOL(ucs2_utf8size);
73
74/*
75 * copy at most maxlength bytes of whole utf8 characters to dest from the
76 * ucs2 string src.
77 *
78 * The return value is the number of characters copied, not including the
79 * final NUL character.
80 */
81unsigned long
82ucs2_as_utf8(u8 *dest, const ucs2_char_t *src, unsigned long maxlength)
83{
84 unsigned int i;
85 unsigned long j = 0;
86 unsigned long limit = ucs2_strnlen(src, maxlength);
87
88 for (i = 0; maxlength && i < limit; i++) {
89 u16 c = src[i];
90
91 if (c >= 0x800) {
92 if (maxlength < 3)
93 break;
94 maxlength -= 3;
95 dest[j++] = 0xe0 | (c & 0xf000) >> 12;
96 dest[j++] = 0x80 | (c & 0x0fc0) >> 6;
97 dest[j++] = 0x80 | (c & 0x003f);
98 } else if (c >= 0x80) {
99 if (maxlength < 2)
100 break;
101 maxlength -= 2;
102 dest[j++] = 0xc0 | (c & 0x7c0) >> 6;
103 dest[j++] = 0x80 | (c & 0x03f);
104 } else {
105 maxlength -= 1;
106 dest[j++] = c & 0x7f;
107 }
108 }
109 if (maxlength)
110 dest[j] = '\0';
111 return j;
112}
113EXPORT_SYMBOL(ucs2_as_utf8);
diff --git a/lib/vsprintf.c b/lib/vsprintf.c
index 48ff9c36644d..f44e178e6ede 100644
--- a/lib/vsprintf.c
+++ b/lib/vsprintf.c
@@ -1590,22 +1590,23 @@ char *pointer(const char *fmt, char *buf, char *end, void *ptr,
1590 return buf; 1590 return buf;
1591 } 1591 }
1592 case 'K': 1592 case 'K':
1593 /*
1594 * %pK cannot be used in IRQ context because its test
1595 * for CAP_SYSLOG would be meaningless.
1596 */
1597 if (kptr_restrict && (in_irq() || in_serving_softirq() ||
1598 in_nmi())) {
1599 if (spec.field_width == -1)
1600 spec.field_width = default_width;
1601 return string(buf, end, "pK-error", spec);
1602 }
1603
1604 switch (kptr_restrict) { 1593 switch (kptr_restrict) {
1605 case 0: 1594 case 0:
1606 /* Always print %pK values */ 1595 /* Always print %pK values */
1607 break; 1596 break;
1608 case 1: { 1597 case 1: {
1598 const struct cred *cred;
1599
1600 /*
1601 * kptr_restrict==1 cannot be used in IRQ context
1602 * because its test for CAP_SYSLOG would be meaningless.
1603 */
1604 if (in_irq() || in_serving_softirq() || in_nmi()) {
1605 if (spec.field_width == -1)
1606 spec.field_width = default_width;
1607 return string(buf, end, "pK-error", spec);
1608 }
1609
1609 /* 1610 /*
1610 * Only print the real pointer value if the current 1611 * Only print the real pointer value if the current
1611 * process has CAP_SYSLOG and is running with the 1612 * process has CAP_SYSLOG and is running with the
@@ -1615,8 +1616,7 @@ char *pointer(const char *fmt, char *buf, char *end, void *ptr,
1615 * leak pointer values if a binary opens a file using 1616 * leak pointer values if a binary opens a file using
1616 * %pK and then elevates privileges before reading it. 1617 * %pK and then elevates privileges before reading it.
1617 */ 1618 */
1618 const struct cred *cred = current_cred(); 1619 cred = current_cred();
1619
1620 if (!has_capability_noaudit(current, CAP_SYSLOG) || 1620 if (!has_capability_noaudit(current, CAP_SYSLOG) ||
1621 !uid_eq(cred->euid, cred->uid) || 1621 !uid_eq(cred->euid, cred->uid) ||
1622 !gid_eq(cred->egid, cred->gid)) 1622 !gid_eq(cred->egid, cred->gid))