diff options
author | Peter Zijlstra <a.p.zijlstra@chello.nl> | 2006-10-17 03:10:26 -0400 |
---|---|---|
committer | Linus Torvalds <torvalds@g5.osdl.org> | 2006-10-17 11:18:47 -0400 |
commit | 3864c4894a7f4c03d69a90082a5bb0ab10e437ab (patch) | |
tree | 4d7ad8c494593d335f857499a82ddb29e34debec /arch/i386 | |
parent | 6a15f46c1272afd3010259067451bf0df04f6511 (diff) |
[PATCH] lockdep: annotate i386 apm
Lockdep doesn't like to enable interrupts when they are enabled already.
BUG: warning at kernel/lockdep.c:1814/trace_hardirqs_on() (Not tainted)
[<c04051ed>] show_trace_log_lvl+0x58/0x16a
[<c04057fa>] show_trace+0xd/0x10
[<c0405913>] dump_stack+0x19/0x1b
[<c043abfb>] trace_hardirqs_on+0xa2/0x11e
[<c041463c>] apm_bios_call_simple+0xcd/0xfd
[<c0415242>] apm+0x92/0x5b1
[<c0402005>] kernel_thread_helper+0x5/0xb
DWARF2 unwinder stuck at kernel_thread_helper+0x5/0xb
Leftover inexact backtrace:
[<c04057fa>] show_trace+0xd/0x10
[<c0405913>] dump_stack+0x19/0x1b
[<c043abfb>] trace_hardirqs_on+0xa2/0x11e
[<c041463c>] apm_bios_call_simple+0xcd/0xfd
[<c0415242>] apm+0x92/0x5b1
[<c0402005>] kernel_thread_helper+0x5/0xb
Signed-off-by: Peter Zijlstra <a.p.zijlstra@chello.nl>
Cc: Stephen Rothwell <sfr@canb.auug.org.au>
Cc: Ingo Molnar <mingo@elte.hu>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Linus Torvalds <torvalds@osdl.org>
Diffstat (limited to 'arch/i386')
-rw-r--r-- | arch/i386/kernel/apm.c | 37 |
1 files changed, 27 insertions, 10 deletions
diff --git a/arch/i386/kernel/apm.c b/arch/i386/kernel/apm.c index b42f2d914af3..2af65858d322 100644 --- a/arch/i386/kernel/apm.c +++ b/arch/i386/kernel/apm.c | |||
@@ -540,11 +540,30 @@ static inline void apm_restore_cpus(cpumask_t mask) | |||
540 | * Also, we KNOW that for the non error case of apm_bios_call, there | 540 | * Also, we KNOW that for the non error case of apm_bios_call, there |
541 | * is no useful data returned in the low order 8 bits of eax. | 541 | * is no useful data returned in the low order 8 bits of eax. |
542 | */ | 542 | */ |
543 | #define APM_DO_CLI \ | 543 | |
544 | if (apm_info.allow_ints) \ | 544 | static inline unsigned long __apm_irq_save(void) |
545 | local_irq_enable(); \ | 545 | { |
546 | else \ | 546 | unsigned long flags; |
547 | local_save_flags(flags); | ||
548 | if (apm_info.allow_ints) { | ||
549 | if (irqs_disabled_flags(flags)) | ||
550 | local_irq_enable(); | ||
551 | } else | ||
552 | local_irq_disable(); | ||
553 | |||
554 | return flags; | ||
555 | } | ||
556 | |||
557 | #define apm_irq_save(flags) \ | ||
558 | do { flags = __apm_irq_save(); } while (0) | ||
559 | |||
560 | static inline void apm_irq_restore(unsigned long flags) | ||
561 | { | ||
562 | if (irqs_disabled_flags(flags)) | ||
547 | local_irq_disable(); | 563 | local_irq_disable(); |
564 | else if (irqs_disabled()) | ||
565 | local_irq_enable(); | ||
566 | } | ||
548 | 567 | ||
549 | #ifdef APM_ZERO_SEGS | 568 | #ifdef APM_ZERO_SEGS |
550 | # define APM_DECL_SEGS \ | 569 | # define APM_DECL_SEGS \ |
@@ -596,12 +615,11 @@ static u8 apm_bios_call(u32 func, u32 ebx_in, u32 ecx_in, | |||
596 | save_desc_40 = gdt[0x40 / 8]; | 615 | save_desc_40 = gdt[0x40 / 8]; |
597 | gdt[0x40 / 8] = bad_bios_desc; | 616 | gdt[0x40 / 8] = bad_bios_desc; |
598 | 617 | ||
599 | local_save_flags(flags); | 618 | apm_irq_save(flags); |
600 | APM_DO_CLI; | ||
601 | APM_DO_SAVE_SEGS; | 619 | APM_DO_SAVE_SEGS; |
602 | apm_bios_call_asm(func, ebx_in, ecx_in, eax, ebx, ecx, edx, esi); | 620 | apm_bios_call_asm(func, ebx_in, ecx_in, eax, ebx, ecx, edx, esi); |
603 | APM_DO_RESTORE_SEGS; | 621 | APM_DO_RESTORE_SEGS; |
604 | local_irq_restore(flags); | 622 | apm_irq_restore(flags); |
605 | gdt[0x40 / 8] = save_desc_40; | 623 | gdt[0x40 / 8] = save_desc_40; |
606 | put_cpu(); | 624 | put_cpu(); |
607 | apm_restore_cpus(cpus); | 625 | apm_restore_cpus(cpus); |
@@ -640,12 +658,11 @@ static u8 apm_bios_call_simple(u32 func, u32 ebx_in, u32 ecx_in, u32 *eax) | |||
640 | save_desc_40 = gdt[0x40 / 8]; | 658 | save_desc_40 = gdt[0x40 / 8]; |
641 | gdt[0x40 / 8] = bad_bios_desc; | 659 | gdt[0x40 / 8] = bad_bios_desc; |
642 | 660 | ||
643 | local_save_flags(flags); | 661 | apm_irq_save(flags); |
644 | APM_DO_CLI; | ||
645 | APM_DO_SAVE_SEGS; | 662 | APM_DO_SAVE_SEGS; |
646 | error = apm_bios_call_simple_asm(func, ebx_in, ecx_in, eax); | 663 | error = apm_bios_call_simple_asm(func, ebx_in, ecx_in, eax); |
647 | APM_DO_RESTORE_SEGS; | 664 | APM_DO_RESTORE_SEGS; |
648 | local_irq_restore(flags); | 665 | apm_irq_restore(flags); |
649 | gdt[0x40 / 8] = save_desc_40; | 666 | gdt[0x40 / 8] = save_desc_40; |
650 | put_cpu(); | 667 | put_cpu(); |
651 | apm_restore_cpus(cpus); | 668 | apm_restore_cpus(cpus); |