summaryrefslogtreecommitdiffstats
path: root/sys/dev/hwpmc
diff options
context:
space:
mode:
authorjkoshy <jkoshy@FreeBSD.org>2008-09-15 06:47:52 +0000
committerjkoshy <jkoshy@FreeBSD.org>2008-09-15 06:47:52 +0000
commita9cbfb55cdc6f2ac0c38c5c9877fafbaad0c70ee (patch)
treed678c3a6dd0d4adcb19f4dae801ffb2b9ad8f0d6 /sys/dev/hwpmc
parent557d36f2a868b261d969813154cf130ba8c32029 (diff)
downloadFreeBSD-src-a9cbfb55cdc6f2ac0c38c5c9877fafbaad0c70ee.zip
FreeBSD-src-a9cbfb55cdc6f2ac0c38c5c9877fafbaad0c70ee.tar.gz
Correct a callchain capture bug on the i386.
On the i386 architecture, the processor only saves the current value of `%esp' on stack if a privilege switch is necessary when entering the interrupt handler. Thus, `frame->tf_esp' is only valid for an entry from user mode. For interrupts taken in kernel mode, we need to determine the top-of-stack for the interrupted kernel procedure by adding the appropriate offset to the current frame pointer. Reported by: kris, Fabien Thomas Tested by: Fabien Thomas <fabien.thomas at netasq dot com>
Diffstat (limited to 'sys/dev/hwpmc')
-rw-r--r--sys/dev/hwpmc/hwpmc_x86.c6
1 files changed, 3 insertions, 3 deletions
diff --git a/sys/dev/hwpmc/hwpmc_x86.c b/sys/dev/hwpmc/hwpmc_x86.c
index 2fc7cd9..8720c0e 100644
--- a/sys/dev/hwpmc/hwpmc_x86.c
+++ b/sys/dev/hwpmc/hwpmc_x86.c
@@ -1,5 +1,5 @@
/*-
- * Copyright (c) 2005, Joseph Koshy
+ * Copyright (c) 2005,2008 Joseph Koshy
* Copyright (c) 2007 The FreeBSD Foundation
* All rights reserved.
*
@@ -90,7 +90,7 @@ pmc_save_user_callchain(uintptr_t *cc, int nframes, struct trapframe *tf)
pc = PMC_TRAPFRAME_TO_PC(tf);
oldfp = fp = PMC_TRAPFRAME_TO_FP(tf);
- sp = PMC_TRAPFRAME_TO_SP(tf);
+ sp = PMC_TRAPFRAME_TO_USER_SP(tf);
*cc++ = pc; n = 1;
@@ -171,7 +171,7 @@ pmc_save_kernel_callchain(uintptr_t *cc, int nframes, struct trapframe *tf)
pc = PMC_TRAPFRAME_TO_PC(tf);
fp = PMC_TRAPFRAME_TO_FP(tf);
- sp = PMC_TRAPFRAME_TO_SP(tf);
+ sp = PMC_TRAPFRAME_TO_KERNEL_SP(tf);
*cc++ = pc;
r = fp + sizeof(uintptr_t); /* points to return address */
OpenPOWER on IntegriCloud