diff options
author | Stephane Eranian <eranian@hpl.hp.com> | 2007-02-13 07:26:22 -0500 |
---|---|---|
committer | Andi Kleen <andi@basil.nowhere.org> | 2007-02-13 07:26:22 -0500 |
commit | 2ff2d3d74705d34ab71b21f54634fcf50d57bdd5 (patch) | |
tree | b74849c0a55f3eb4458e7399c6d30a0f8b270d58 /arch/i386/kernel/apic.c | |
parent | 86a978837ca739842317c4cf433de36aeb85ea3b (diff) |
[PATCH] i386: add idle notifier
Add a notifier mechanism to the low level idle loop. You can register a
callback function which gets invoked on entry and exit from the low level idle
loop. The low level idle loop is defined as the polling loop, low-power call,
or the mwait instruction. Interrupts processed by the idle thread are not
considered part of the low level loop.
The notifier can be used to measure precisely how much is spent in useless
execution (or low power mode). The perfmon subsystem uses it to turn on/off
monitoring.
Signed-off-by: stephane eranian <eranian@hpl.hp.com>
Signed-off-by: Andrew Morton <akpm@osdl.org>
Signed-off-by: Andi Kleen <ak@suse.de>
Diffstat (limited to 'arch/i386/kernel/apic.c')
-rw-r--r-- | arch/i386/kernel/apic.c | 4 |
1 files changed, 4 insertions, 0 deletions
diff --git a/arch/i386/kernel/apic.c b/arch/i386/kernel/apic.c index 629c5ed94260..f4159e0a7ae9 100644 --- a/arch/i386/kernel/apic.c +++ b/arch/i386/kernel/apic.c | |||
@@ -36,6 +36,7 @@ | |||
36 | #include <asm/hpet.h> | 36 | #include <asm/hpet.h> |
37 | #include <asm/i8253.h> | 37 | #include <asm/i8253.h> |
38 | #include <asm/nmi.h> | 38 | #include <asm/nmi.h> |
39 | #include <asm/idle.h> | ||
39 | 40 | ||
40 | #include <mach_apic.h> | 41 | #include <mach_apic.h> |
41 | #include <mach_apicdef.h> | 42 | #include <mach_apicdef.h> |
@@ -1255,6 +1256,7 @@ fastcall void smp_apic_timer_interrupt(struct pt_regs *regs) | |||
1255 | * Besides, if we don't timer interrupts ignore the global | 1256 | * Besides, if we don't timer interrupts ignore the global |
1256 | * interrupt lock, which is the WrongThing (tm) to do. | 1257 | * interrupt lock, which is the WrongThing (tm) to do. |
1257 | */ | 1258 | */ |
1259 | exit_idle(); | ||
1258 | irq_enter(); | 1260 | irq_enter(); |
1259 | smp_local_timer_interrupt(); | 1261 | smp_local_timer_interrupt(); |
1260 | irq_exit(); | 1262 | irq_exit(); |
@@ -1305,6 +1307,7 @@ fastcall void smp_spurious_interrupt(struct pt_regs *regs) | |||
1305 | { | 1307 | { |
1306 | unsigned long v; | 1308 | unsigned long v; |
1307 | 1309 | ||
1310 | exit_idle(); | ||
1308 | irq_enter(); | 1311 | irq_enter(); |
1309 | /* | 1312 | /* |
1310 | * Check if this really is a spurious interrupt and ACK it | 1313 | * Check if this really is a spurious interrupt and ACK it |
@@ -1329,6 +1332,7 @@ fastcall void smp_error_interrupt(struct pt_regs *regs) | |||
1329 | { | 1332 | { |
1330 | unsigned long v, v1; | 1333 | unsigned long v, v1; |
1331 | 1334 | ||
1335 | exit_idle(); | ||
1332 | irq_enter(); | 1336 | irq_enter(); |
1333 | /* First tickle the hardware, only then report what went on. -- REW */ | 1337 | /* First tickle the hardware, only then report what went on. -- REW */ |
1334 | v = apic_read(APIC_ESR); | 1338 | v = apic_read(APIC_ESR); |