Commit f4112de6b679d84bd9b9681c7504be7bdfb7c7d5
Committed by
Linus Torvalds
1 parent
851a039cc5
Exists in
master
and in
7 other branches
mm: introduce debug_kmap_atomic
x86 has debug_kmap_atomic_prot() which is error checking function for kmap_atomic. It is usefull for the other architectures, although it needs CONFIG_TRACE_IRQFLAGS_SUPPORT. This patch exposes it to the other architectures. Signed-off-by: Akinobu Mita <akinobu.mita@gmail.com> Cc: Thomas Gleixner <tglx@linutronix.de> Cc: Ingo Molnar <mingo@redhat.com> Cc: "H. Peter Anvin" <hpa@zytor.com> Cc: <linux-arch@vger.kernel.org> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Showing 3 changed files with 58 additions and 44 deletions Side-by-side Diff
arch/x86/mm/highmem_32.c
... | ... | @@ -19,49 +19,6 @@ |
19 | 19 | kunmap_high(page); |
20 | 20 | } |
21 | 21 | |
22 | -static void debug_kmap_atomic_prot(enum km_type type) | |
23 | -{ | |
24 | -#ifdef CONFIG_DEBUG_HIGHMEM | |
25 | - static unsigned warn_count = 10; | |
26 | - | |
27 | - if (unlikely(warn_count == 0)) | |
28 | - return; | |
29 | - | |
30 | - if (unlikely(in_interrupt())) { | |
31 | - if (in_irq()) { | |
32 | - if (type != KM_IRQ0 && type != KM_IRQ1 && | |
33 | - type != KM_BIO_SRC_IRQ && type != KM_BIO_DST_IRQ && | |
34 | - type != KM_BOUNCE_READ) { | |
35 | - WARN_ON(1); | |
36 | - warn_count--; | |
37 | - } | |
38 | - } else if (!irqs_disabled()) { /* softirq */ | |
39 | - if (type != KM_IRQ0 && type != KM_IRQ1 && | |
40 | - type != KM_SOFTIRQ0 && type != KM_SOFTIRQ1 && | |
41 | - type != KM_SKB_SUNRPC_DATA && | |
42 | - type != KM_SKB_DATA_SOFTIRQ && | |
43 | - type != KM_BOUNCE_READ) { | |
44 | - WARN_ON(1); | |
45 | - warn_count--; | |
46 | - } | |
47 | - } | |
48 | - } | |
49 | - | |
50 | - if (type == KM_IRQ0 || type == KM_IRQ1 || type == KM_BOUNCE_READ || | |
51 | - type == KM_BIO_SRC_IRQ || type == KM_BIO_DST_IRQ) { | |
52 | - if (!irqs_disabled()) { | |
53 | - WARN_ON(1); | |
54 | - warn_count--; | |
55 | - } | |
56 | - } else if (type == KM_SOFTIRQ0 || type == KM_SOFTIRQ1) { | |
57 | - if (irq_count() == 0 && !irqs_disabled()) { | |
58 | - WARN_ON(1); | |
59 | - warn_count--; | |
60 | - } | |
61 | - } | |
62 | -#endif | |
63 | -} | |
64 | - | |
65 | 22 | /* |
66 | 23 | * kmap_atomic/kunmap_atomic is significantly faster than kmap/kunmap because |
67 | 24 | * no global lock is needed and because the kmap code must perform a global TLB |
... | ... | @@ -81,7 +38,7 @@ |
81 | 38 | if (!PageHighMem(page)) |
82 | 39 | return page_address(page); |
83 | 40 | |
84 | - debug_kmap_atomic_prot(type); | |
41 | + debug_kmap_atomic(type); | |
85 | 42 | |
86 | 43 | idx = type + KM_TYPE_NR*smp_processor_id(); |
87 | 44 | vaddr = __fix_to_virt(FIX_KMAP_BEGIN + idx); |
include/linux/highmem.h
... | ... | @@ -187,5 +187,17 @@ |
187 | 187 | kunmap_atomic(vto, KM_USER1); |
188 | 188 | } |
189 | 189 | |
190 | +#if defined(CONFIG_DEBUG_HIGHMEM) && defined(CONFIG_TRACE_IRQFLAGS_SUPPORT) | |
191 | + | |
192 | +void debug_kmap_atomic(enum km_type type); | |
193 | + | |
194 | +#else | |
195 | + | |
196 | +static inline void debug_kmap_atomic(enum km_type type) | |
197 | +{ | |
198 | +} | |
199 | + | |
200 | +#endif | |
201 | + | |
190 | 202 | #endif /* _LINUX_HIGHMEM_H */ |
mm/highmem.c
... | ... | @@ -422,4 +422,49 @@ |
422 | 422 | } |
423 | 423 | |
424 | 424 | #endif /* defined(CONFIG_HIGHMEM) && !defined(WANT_PAGE_VIRTUAL) */ |
425 | + | |
426 | +#if defined(CONFIG_DEBUG_HIGHMEM) && defined(CONFIG_TRACE_IRQFLAGS_SUPPORT) | |
427 | + | |
428 | +void debug_kmap_atomic(enum km_type type) | |
429 | +{ | |
430 | + static unsigned warn_count = 10; | |
431 | + | |
432 | + if (unlikely(warn_count == 0)) | |
433 | + return; | |
434 | + | |
435 | + if (unlikely(in_interrupt())) { | |
436 | + if (in_irq()) { | |
437 | + if (type != KM_IRQ0 && type != KM_IRQ1 && | |
438 | + type != KM_BIO_SRC_IRQ && type != KM_BIO_DST_IRQ && | |
439 | + type != KM_BOUNCE_READ) { | |
440 | + WARN_ON(1); | |
441 | + warn_count--; | |
442 | + } | |
443 | + } else if (!irqs_disabled()) { /* softirq */ | |
444 | + if (type != KM_IRQ0 && type != KM_IRQ1 && | |
445 | + type != KM_SOFTIRQ0 && type != KM_SOFTIRQ1 && | |
446 | + type != KM_SKB_SUNRPC_DATA && | |
447 | + type != KM_SKB_DATA_SOFTIRQ && | |
448 | + type != KM_BOUNCE_READ) { | |
449 | + WARN_ON(1); | |
450 | + warn_count--; | |
451 | + } | |
452 | + } | |
453 | + } | |
454 | + | |
455 | + if (type == KM_IRQ0 || type == KM_IRQ1 || type == KM_BOUNCE_READ || | |
456 | + type == KM_BIO_SRC_IRQ || type == KM_BIO_DST_IRQ) { | |
457 | + if (!irqs_disabled()) { | |
458 | + WARN_ON(1); | |
459 | + warn_count--; | |
460 | + } | |
461 | + } else if (type == KM_SOFTIRQ0 || type == KM_SOFTIRQ1) { | |
462 | + if (irq_count() == 0 && !irqs_disabled()) { | |
463 | + WARN_ON(1); | |
464 | + warn_count--; | |
465 | + } | |
466 | + } | |
467 | +} | |
468 | + | |
469 | +#endif |