* [PATCH]utrace: IA64 RSE bug
@ 2007-08-07 5:23 Shaohua Li
2007-08-07 7:13 ` Roland McGrath
` (5 more replies)
0 siblings, 6 replies; 7+ messages in thread
From: Shaohua Li @ 2007-08-07 5:23 UTC (permalink / raw)
To: linux-ia64
In ptrace case, user space RSE might be newer than kernel RSE. To avoid
stale RSE is used when return to userspace, this patch synchronize user
space RSE to kernel RSE.
Also, as TIF_ALLWORK_MASK bits are limited, TIF_NOTIFY_RESUME is
overrided.
patch is against latest utrace source (2.6.22 base + utrace patches)
Signed-off-by: Bibo Mao<bibo.mao@intel.com>
Signed-off-by: Shaohua Li<shaohua.li@intel.com>
===============================
arch/ia64/kernel/perfmon.c | 21 ++--------------
arch/ia64/kernel/process.c | 14 +++++++++++
arch/ia64/kernel/ptrace.c | 52 +++++++++++++++++++++++++++++++++++++++++
include/asm-ia64/ptrace.h | 1
include/asm-ia64/thread_info.h | 4 +++
5 files changed, 74 insertions(+), 18 deletions(-)
Index: 2.6.22/arch/ia64/kernel/process.c
=================================--- 2.6.22.orig/arch/ia64/kernel/process.c 2007-08-07 10:48:04.000000000 +0800
+++ 2.6.22/arch/ia64/kernel/process.c 2007-08-07 11:40:42.000000000 +0800
@@ -154,6 +154,17 @@ show_regs (struct pt_regs *regs)
show_stack(NULL, NULL);
}
+void tsk_clear_notify_resume(struct task_struct *tsk)
+{
+#ifdef CONFIG_PERFMON
+ if (tsk->thread.pfm_needs_checking)
+ return;
+#endif
+ if (test_ti_thread_flag(task_thread_info(tsk), TIF_RESTORE_RSE))
+ return;
+ clear_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME);
+}
+
void
do_notify_resume_user (sigset_t *unused, struct sigscratch *scr, long in_syscall)
{
@@ -172,6 +183,9 @@ do_notify_resume_user (sigset_t *unused,
/* deal with pending signal delivery */
if (test_thread_flag(TIF_SIGPENDING)||test_thread_flag(TIF_RESTORE_SIGMASK))
ia64_do_signal(scr, in_syscall);
+ /* copy user rbs to kernel rbs */
+ if (unlikely(test_thread_flag(TIF_RESTORE_RSE)))
+ ia64_sync_krbs(current);
}
static int pal_halt = 1;
Index: 2.6.22/arch/ia64/kernel/ptrace.c
=================================--- 2.6.22.orig/arch/ia64/kernel/ptrace.c 2007-08-07 10:48:04.000000000 +0800
+++ 2.6.22/arch/ia64/kernel/ptrace.c 2007-08-07 12:54:26.000000000 +0800
@@ -554,6 +554,25 @@ ia64_sync_user_rbs (struct task_struct *
return 0;
}
+long
+ia64_sync_kernel_rbs (struct task_struct *child, struct switch_stack *sw,
+ unsigned long user_rbs_start, unsigned long user_rbs_end)
+{
+ unsigned long addr, val;
+ long ret;
+
+ /* now copy word for word from user rbs to kernel rbs: */
+ for (addr = user_rbs_start; addr < user_rbs_end; addr += 8) {
+ if (access_process_vm(child, addr, &val, sizeof(val), 0)
+ != sizeof(val))
+ return -EIO;
+ ret = ia64_poke(child, sw, user_rbs_end, addr, val);
+ if (ret < 0)
+ return ret;
+ }
+ return 0;
+}
+
/*
* Write f32-f127 back to task->thread.fph if it has been modified.
*/
@@ -728,6 +747,10 @@ syscall_trace_enter (long arg0, long arg
if (test_thread_flag(TIF_SYSCALL_TRACE))
tracehook_report_syscall(®s, 0);
+ /* copy user rbs to kernel rbs */
+ if (test_thread_flag(TIF_RESTORE_RSE))
+ ia64_sync_krbs(current);
+
if (unlikely(current->audit_context)) {
long syscall;
int arch;
@@ -764,6 +787,10 @@ syscall_trace_leave (long arg0, long arg
if (test_thread_flag(TIF_SYSCALL_TRACE))
tracehook_report_syscall(®s, 1);
+ /* copy user rbs to kernel rbs */
+ if (test_thread_flag(TIF_RESTORE_RSE))
+ ia64_sync_krbs(current);
+
if (test_thread_flag(TIF_SINGLESTEP)) {
force_sig(SIGTRAP, current); /* XXX */
tracehook_report_syscall_step(®s);
@@ -1416,9 +1443,34 @@ gpregs_writeback(struct task_struct *tar
const struct utrace_regset *regset,
int now)
{
+ if (test_and_set_tsk_thread_flag(target, TIF_RESTORE_RSE))
+ return 0;
+ tsk_set_notify_resume(target);
return do_regset_call(do_gpregs_writeback, target, regset, 0, 0, NULL, NULL);
}
+static void do_gpregs_readback(struct unw_frame_info *info, void *arg)
+{
+ struct pt_regs *pt;
+ utrace_getset_t *dst = arg;
+ unsigned long urbs_end;
+
+ if (unw_unwind_to_user(info) < 0)
+ return;
+ pt = task_pt_regs(dst->target);
+ urbs_end = ia64_get_user_rbs_end(dst->target, pt, NULL);
+ dst->ret = ia64_sync_kernel_rbs(dst->target, info->sw, pt->ar_bspstore, urbs_end);
+}
+/*
+ * This is called to read back the register backing store.
+ */
+long ia64_sync_krbs(struct task_struct *target)
+{
+ clear_tsk_thread_flag(target, TIF_RESTORE_RSE);
+ tsk_clear_notify_resume(target);
+ return do_regset_call(do_gpregs_readback, target, NULL, 0, 0, NULL, NULL);
+}
+
static int
fpregs_active(struct task_struct *target, const struct utrace_regset *regset)
{
Index: 2.6.22/include/asm-ia64/ptrace.h
=================================--- 2.6.22.orig/include/asm-ia64/ptrace.h 2007-08-07 10:48:04.000000000 +0800
+++ 2.6.22/include/asm-ia64/ptrace.h 2007-08-07 10:48:21.000000000 +0800
@@ -292,6 +292,7 @@ struct switch_stack {
unsigned long, long);
extern void ia64_flush_fph (struct task_struct *);
extern void ia64_sync_fph (struct task_struct *);
+ extern long ia64_sync_krbs(struct task_struct *);
extern long ia64_sync_user_rbs (struct task_struct *, struct switch_stack *,
unsigned long, unsigned long);
Index: 2.6.22/include/asm-ia64/thread_info.h
=================================--- 2.6.22.orig/include/asm-ia64/thread_info.h 2007-08-07 10:48:04.000000000 +0800
+++ 2.6.22/include/asm-ia64/thread_info.h 2007-08-07 11:08:45.000000000 +0800
@@ -71,6 +71,9 @@ struct thread_info {
#define alloc_task_struct() ((struct task_struct *)__get_free_pages(GFP_KERNEL | __GFP_COMP, KERNEL_STACK_SIZE_ORDER))
#define free_task_struct(tsk) free_pages((unsigned long) (tsk), KERNEL_STACK_SIZE_ORDER)
+#define tsk_set_notify_resume(tsk) \
+ set_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME)
+extern void tsk_clear_notify_resume(struct task_struct *tsk);
#endif /* !__ASSEMBLY */
/*
@@ -86,6 +89,7 @@ struct thread_info {
#define TIF_SYSCALL_AUDIT 4 /* syscall auditing active */
#define TIF_SINGLESTEP 5 /* restore singlestep on return to user mode */
#define TIF_RESTORE_SIGMASK 6 /* restore signal mask in do_signal() */
+#define TIF_RESTORE_RSE 9 /* task need RSE synchronization */
#define TIF_POLLING_NRFLAG 16 /* true if poll_idle() is polling TIF_NEED_RESCHED */
#define TIF_MEMDIE 17
#define TIF_MCA_INIT 18 /* this task is processing MCA or INIT */
Index: 2.6.22/arch/ia64/kernel/perfmon.c
=================================--- 2.6.22.orig/arch/ia64/kernel/perfmon.c 2007-08-07 10:48:04.000000000 +0800
+++ 2.6.22/arch/ia64/kernel/perfmon.c 2007-08-07 11:01:07.000000000 +0800
@@ -586,21 +586,6 @@ pfm_put_task(struct task_struct *task)
}
static inline void
-pfm_set_task_notify(struct task_struct *task)
-{
- struct thread_info *info;
-
- info = (struct thread_info *) ((char *) task + IA64_TASK_SIZE);
- set_bit(TIF_NOTIFY_RESUME, &info->flags);
-}
-
-static inline void
-pfm_clear_task_notify(void)
-{
- clear_thread_flag(TIF_NOTIFY_RESUME);
-}
-
-static inline void
pfm_reserve_page(unsigned long a)
{
SetPageReserved(vmalloc_to_page((void *)a));
@@ -3730,7 +3715,7 @@ pfm_restart(pfm_context_t *ctx, void *ar
PFM_SET_WORK_PENDING(task, 1);
- pfm_set_task_notify(task);
+ tsk_set_notify_resume(task);
/*
* XXX: send reschedule if task runs on another CPU
@@ -5087,7 +5072,7 @@ pfm_handle_work(void)
PFM_SET_WORK_PENDING(current, 0);
- pfm_clear_task_notify();
+ tsk_clear_notify_resume(current);
regs = task_pt_regs(current);
@@ -5455,7 +5440,7 @@ pfm_overflow_handler(struct task_struct
* when coming from ctxsw, current still points to the
* previous task, therefore we must work with task and not current.
*/
- pfm_set_task_notify(task);
+ tsk_set_notify_resume(task);
}
/*
* defer until state is changed (shorten spin window). the context is locked
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH]utrace: IA64 RSE bug
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
@ 2007-08-07 7:13 ` Roland McGrath
2007-08-07 21:55 ` Stephane Eranian
` (4 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: Roland McGrath @ 2007-08-07 7:13 UTC (permalink / raw)
To: linux-ia64
That looks reasonable to me, not being expert on the ia64 details.
I rolled that into utrace-regset-ia64.patch in the 2.6.22 backport version.
> patch is against latest utrace source (2.6.22 base + utrace patches)
The latest utrace source is based on 2.6.23-rc2, and your patch does not
apply there. TIF_NOTIFY_RESUME has been renamed to TIF_PERFMON_WORK.
So you need to rename it back (or to something else) to overload it.
If the gist of your patch here seems right to ia64 folks, then I'd suggest
you do a patch adding ia64_sync_krbs to the upstream kernel. That would be
the necessary prelude to doing the arch_ptrace_stop plan, which I can help
ia64 folks with later.
Thanks,
Roland
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH]utrace: IA64 RSE bug
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
2007-08-07 7:13 ` Roland McGrath
@ 2007-08-07 21:55 ` Stephane Eranian
2007-08-08 2:30 ` Shaohua Li
` (3 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: Stephane Eranian @ 2007-08-07 21:55 UTC (permalink / raw)
To: linux-ia64
Hello,
On Tue, Aug 07, 2007 at 12:13:16AM -0700, Roland McGrath wrote:
> That looks reasonable to me, not being expert on the ia64 details.
> I rolled that into utrace-regset-ia64.patch in the 2.6.22 backport version.
>
> > patch is against latest utrace source (2.6.22 base + utrace patches)
>
> The latest utrace source is based on 2.6.23-rc2, and your patch does not
> apply there. TIF_NOTIFY_RESUME has been renamed to TIF_PERFMON_WORK.
> So you need to rename it back (or to something else) to overload it.
>
Yes, in 2.6.23, TIF_NOTIFY_RESUME has been removed because it was not used
except for perfmon, thus I renamed it. The problem is that you cannot just
override it because you would need a way to further demultiplex the
reason for call do_notify_resume(). Perfmon not simply relies on the
TIF_PERFMON_WORK bit being set. As you realize now this flag would
mean you have some RSE work or some perfmon work.
--
-Stephane
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH]utrace: IA64 RSE bug
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
2007-08-07 7:13 ` Roland McGrath
2007-08-07 21:55 ` Stephane Eranian
@ 2007-08-08 2:30 ` Shaohua Li
2007-08-08 23:10 ` Stephane Eranian
` (2 subsequent siblings)
5 siblings, 0 replies; 7+ messages in thread
From: Shaohua Li @ 2007-08-08 2:30 UTC (permalink / raw)
To: linux-ia64
On Tue, 2007-08-07 at 15:13 +0800, Roland McGrath wrote:
> That looks reasonable to me, not being expert on the ia64 details.
> I rolled that into utrace-regset-ia64.patch in the 2.6.22 backport
> version.
>
> > patch is against latest utrace source (2.6.22 base + utrace patches)
>
> The latest utrace source is based on 2.6.23-rc2, and your patch does
> not
> apply there. TIF_NOTIFY_RESUME has been renamed to TIF_PERFMON_WORK.
> So you need to rename it back (or to something else) to overload it.
>
> If the gist of your patch here seems right to ia64 folks, then I'd
> suggest
> you do a patch adding ia64_sync_krbs to the upstream kernel. That
> would be
> the necessary prelude to doing the arch_ptrace_stop plan, which I can
> help
> ia64 folks with later.
Ok, this is the patch against 2.6.23-rc2
In ptrace case, user space RSE might be newer than kernel RSE. To avoid
stale RSE is used when return to userspace, this patch synchronize user
space RSE to kernel RSE.
Also, as TIF_ALLWORK_MASK bits are limited, TIF_NOTIFY_RESUME is
overrided.
Signed-off-by: Bibo Mao<bibo.mao@intel.com>
Signed-off-by: Shaohua Li<shaohua.li@intel.com>
===============================
arch/ia64/kernel/perfmon.c | 21 ++--------------
arch/ia64/kernel/process.c | 14 +++++++++++
arch/ia64/kernel/ptrace.c | 52 +++++++++++++++++++++++++++++++++++++++++
include/asm-ia64/ptrace.h | 1
include/asm-ia64/thread_info.h | 11 ++++++--
5 files changed, 78 insertions(+), 21 deletions(-)
Index: 2.6.23-rc2/arch/ia64/kernel/process.c
=================================--- 2.6.23-rc2.orig/arch/ia64/kernel/process.c 2007-08-04 10:49:55.000000000 +0800
+++ 2.6.23-rc2/arch/ia64/kernel/process.c 2007-08-08 09:27:18.000000000 +0800
@@ -154,6 +154,17 @@ show_regs (struct pt_regs *regs)
show_stack(NULL, NULL);
}
+void tsk_clear_notify_resume(struct task_struct *tsk)
+{
+#ifdef CONFIG_PERFMON
+ if (tsk->thread.pfm_needs_checking)
+ return;
+#endif
+ if (test_ti_thread_flag(task_thread_info(tsk), TIF_RESTORE_RSE))
+ return;
+ clear_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME);
+}
+
void
do_notify_resume_user (sigset_t *unused, struct sigscratch *scr, long in_syscall)
{
@@ -172,6 +183,9 @@ do_notify_resume_user (sigset_t *unused,
/* deal with pending signal delivery */
if (test_thread_flag(TIF_SIGPENDING)||test_thread_flag(TIF_RESTORE_SIGMASK))
ia64_do_signal(scr, in_syscall);
+ /* copy user rbs to kernel rbs */
+ if (unlikely(test_thread_flag(TIF_RESTORE_RSE)))
+ ia64_sync_krbs(current);
}
static int pal_halt = 1;
Index: 2.6.23-rc2/arch/ia64/kernel/ptrace.c
=================================--- 2.6.23-rc2.orig/arch/ia64/kernel/ptrace.c 2007-08-08 09:00:28.000000000 +0800
+++ 2.6.23-rc2/arch/ia64/kernel/ptrace.c 2007-08-08 09:27:18.000000000 +0800
@@ -554,6 +554,25 @@ ia64_sync_user_rbs (struct task_struct *
return 0;
}
+long
+ia64_sync_kernel_rbs (struct task_struct *child, struct switch_stack *sw,
+ unsigned long user_rbs_start, unsigned long user_rbs_end)
+{
+ unsigned long addr, val;
+ long ret;
+
+ /* now copy word for word from user rbs to kernel rbs: */
+ for (addr = user_rbs_start; addr < user_rbs_end; addr += 8) {
+ if (access_process_vm(child, addr, &val, sizeof(val), 0)
+ != sizeof(val))
+ return -EIO;
+ ret = ia64_poke(child, sw, user_rbs_end, addr, val);
+ if (ret < 0)
+ return ret;
+ }
+ return 0;
+}
+
/*
* Write f32-f127 back to task->thread.fph if it has been modified.
*/
@@ -728,6 +747,10 @@ syscall_trace_enter (long arg0, long arg
if (test_thread_flag(TIF_SYSCALL_TRACE))
tracehook_report_syscall(®s, 0);
+ /* copy user rbs to kernel rbs */
+ if (test_thread_flag(TIF_RESTORE_RSE))
+ ia64_sync_krbs(current);
+
if (unlikely(current->audit_context)) {
long syscall;
int arch;
@@ -764,6 +787,10 @@ syscall_trace_leave (long arg0, long arg
if (test_thread_flag(TIF_SYSCALL_TRACE))
tracehook_report_syscall(®s, 1);
+ /* copy user rbs to kernel rbs */
+ if (test_thread_flag(TIF_RESTORE_RSE))
+ ia64_sync_krbs(current);
+
if (test_thread_flag(TIF_SINGLESTEP)) {
force_sig(SIGTRAP, current); /* XXX */
tracehook_report_syscall_step(®s);
@@ -1416,9 +1443,34 @@ gpregs_writeback(struct task_struct *tar
const struct utrace_regset *regset,
int now)
{
+ if (test_and_set_tsk_thread_flag(target, TIF_RESTORE_RSE))
+ return 0;
+ tsk_set_notify_resume(target);
return do_regset_call(do_gpregs_writeback, target, regset, 0, 0, NULL, NULL);
}
+static void do_gpregs_readback(struct unw_frame_info *info, void *arg)
+{
+ struct pt_regs *pt;
+ utrace_getset_t *dst = arg;
+ unsigned long urbs_end;
+
+ if (unw_unwind_to_user(info) < 0)
+ return;
+ pt = task_pt_regs(dst->target);
+ urbs_end = ia64_get_user_rbs_end(dst->target, pt, NULL);
+ dst->ret = ia64_sync_kernel_rbs(dst->target, info->sw, pt->ar_bspstore, urbs_end);
+}
+/*
+ * This is called to read back the register backing store.
+ */
+long ia64_sync_krbs(struct task_struct *target)
+{
+ clear_tsk_thread_flag(target, TIF_RESTORE_RSE);
+ tsk_clear_notify_resume(target);
+ return do_regset_call(do_gpregs_readback, target, NULL, 0, 0, NULL, NULL);
+}
+
static int
fpregs_active(struct task_struct *target, const struct utrace_regset *regset)
{
Index: 2.6.23-rc2/include/asm-ia64/ptrace.h
=================================--- 2.6.23-rc2.orig/include/asm-ia64/ptrace.h 2007-08-04 10:49:55.000000000 +0800
+++ 2.6.23-rc2/include/asm-ia64/ptrace.h 2007-08-08 09:27:18.000000000 +0800
@@ -292,6 +292,7 @@ struct switch_stack {
unsigned long, long);
extern void ia64_flush_fph (struct task_struct *);
extern void ia64_sync_fph (struct task_struct *);
+ extern long ia64_sync_krbs(struct task_struct *);
extern long ia64_sync_user_rbs (struct task_struct *, struct switch_stack *,
unsigned long, unsigned long);
Index: 2.6.23-rc2/include/asm-ia64/thread_info.h
=================================--- 2.6.23-rc2.orig/include/asm-ia64/thread_info.h 2007-08-04 10:49:55.000000000 +0800
+++ 2.6.23-rc2/include/asm-ia64/thread_info.h 2007-08-08 09:35:08.000000000 +0800
@@ -71,6 +71,9 @@ struct thread_info {
#define alloc_task_struct() ((struct task_struct *)__get_free_pages(GFP_KERNEL | __GFP_COMP, KERNEL_STACK_SIZE_ORDER))
#define free_task_struct(tsk) free_pages((unsigned long) (tsk), KERNEL_STACK_SIZE_ORDER)
+#define tsk_set_notify_resume(tsk) \
+ set_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME)
+extern void tsk_clear_notify_resume(struct task_struct *tsk);
#endif /* !__ASSEMBLY */
/*
@@ -85,28 +88,30 @@ struct thread_info {
#define TIF_SYSCALL_AUDIT 3 /* syscall auditing active */
#define TIF_SINGLESTEP 4 /* restore singlestep on return to user mode */
#define TIF_RESTORE_SIGMASK 5 /* restore signal mask in do_signal() */
-#define TIF_PERFMON_WORK 6 /* work for pfm_handle_work() */
+#define TIF_NOTIFY_RESUME 6 /* resumption notification requested */
#define TIF_POLLING_NRFLAG 16 /* true if poll_idle() is polling TIF_NEED_RESCHED */
#define TIF_MEMDIE 17
#define TIF_MCA_INIT 18 /* this task is processing MCA or INIT */
#define TIF_DB_DISABLED 19 /* debug trap disabled for fsyscall */
#define TIF_FREEZE 20 /* is freezing for suspend */
+#define TIF_RESTORE_RSE 21 /* task need RSE synchronization */
#define _TIF_SYSCALL_TRACE (1 << TIF_SYSCALL_TRACE)
#define _TIF_SYSCALL_AUDIT (1 << TIF_SYSCALL_AUDIT)
#define _TIF_SINGLESTEP (1 << TIF_SINGLESTEP)
#define _TIF_SYSCALL_TRACEAUDIT (_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT|_TIF_SINGLESTEP)
#define _TIF_RESTORE_SIGMASK (1 << TIF_RESTORE_SIGMASK)
-#define _TIF_PERFMON_WORK (1 << TIF_PERFMON_WORK)
+#define _TIF_NOTIFY_RESUME (1 << TIF_NOTIFY_RESUME)
#define _TIF_SIGPENDING (1 << TIF_SIGPENDING)
#define _TIF_NEED_RESCHED (1 << TIF_NEED_RESCHED)
#define _TIF_POLLING_NRFLAG (1 << TIF_POLLING_NRFLAG)
#define _TIF_MCA_INIT (1 << TIF_MCA_INIT)
#define _TIF_DB_DISABLED (1 << TIF_DB_DISABLED)
#define _TIF_FREEZE (1 << TIF_FREEZE)
+#define _TIF_RESTORE_RSE (1 << TIF_RESTORE_RSE)
/* "work to do on user-return" bits */
-#define TIF_ALLWORK_MASK (_TIF_SIGPENDING|_TIF_PERFMON_WORK|_TIF_SYSCALL_AUDIT|\
+#define TIF_ALLWORK_MASK (_TIF_SIGPENDING|_TIF_NOTIFY_RESUME|_TIF_SYSCALL_AUDIT|\
_TIF_NEED_RESCHED| _TIF_SYSCALL_TRACE|\
_TIF_RESTORE_SIGMASK)
/* like TIF_ALLWORK_BITS but sans TIF_SYSCALL_TRACE or TIF_SYSCALL_AUDIT */
Index: 2.6.23-rc2/arch/ia64/kernel/perfmon.c
=================================--- 2.6.23-rc2.orig/arch/ia64/kernel/perfmon.c 2007-08-04 10:49:55.000000000 +0800
+++ 2.6.23-rc2/arch/ia64/kernel/perfmon.c 2007-08-08 09:32:41.000000000 +0800
@@ -586,21 +586,6 @@ pfm_put_task(struct task_struct *task)
}
static inline void
-pfm_set_task_notify(struct task_struct *task)
-{
- struct thread_info *info;
-
- info = (struct thread_info *) ((char *) task + IA64_TASK_SIZE);
- set_bit(TIF_PERFMON_WORK, &info->flags);
-}
-
-static inline void
-pfm_clear_task_notify(void)
-{
- clear_thread_flag(TIF_PERFMON_WORK);
-}
-
-static inline void
pfm_reserve_page(unsigned long a)
{
SetPageReserved(vmalloc_to_page((void *)a));
@@ -3730,7 +3715,7 @@ pfm_restart(pfm_context_t *ctx, void *ar
PFM_SET_WORK_PENDING(task, 1);
- pfm_set_task_notify(task);
+ tsk_set_notify_resume(task);
/*
* XXX: send reschedule if task runs on another CPU
@@ -5087,7 +5072,7 @@ pfm_handle_work(void)
PFM_SET_WORK_PENDING(current, 0);
- pfm_clear_task_notify();
+ tsk_clear_notify_resume(current);
regs = task_pt_regs(current);
@@ -5455,7 +5440,7 @@ pfm_overflow_handler(struct task_struct
* when coming from ctxsw, current still points to the
* previous task, therefore we must work with task and not current.
*/
- pfm_set_task_notify(task);
+ tsk_set_notify_resume(task);
}
/*
* defer until state is changed (shorten spin window). the context is locked
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH]utrace: IA64 RSE bug
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
` (2 preceding siblings ...)
2007-08-08 2:30 ` Shaohua Li
@ 2007-08-08 23:10 ` Stephane Eranian
2007-08-09 2:35 ` Shaohua Li
2007-08-14 9:13 ` Roland McGrath
5 siblings, 0 replies; 7+ messages in thread
From: Stephane Eranian @ 2007-08-08 23:10 UTC (permalink / raw)
To: linux-ia64
Hi,
Well, looks like we need to resurect TIF_NOTIFY_RESUME now
that we do have some actual need for it. This implies that
I need to rework my perfmon new code base to take this into
account. I don't want to use pfm_needs_checking. So maybe
it is okay to use a higher order TIF bit for perfmon on IA-64
combined with TIF_NOTIFY_RESUME.
For the RSE part, I am not sure I understand the logic behind this
change. I think more explanantions maybe needed to calrify this
a bit more.
On Wed, Aug 08, 2007 at 10:30:37AM +0800, Shaohua Li wrote:
> On Tue, 2007-08-07 at 15:13 +0800, Roland McGrath wrote:
> > That looks reasonable to me, not being expert on the ia64 details.
> > I rolled that into utrace-regset-ia64.patch in the 2.6.22 backport
> > version.
> >
> > > patch is against latest utrace source (2.6.22 base + utrace patches)
> >
> > The latest utrace source is based on 2.6.23-rc2, and your patch does
> > not
> > apply there. TIF_NOTIFY_RESUME has been renamed to TIF_PERFMON_WORK.
> > So you need to rename it back (or to something else) to overload it.
> >
> > If the gist of your patch here seems right to ia64 folks, then I'd
> > suggest
> > you do a patch adding ia64_sync_krbs to the upstream kernel. That
> > would be
> > the necessary prelude to doing the arch_ptrace_stop plan, which I can
> > help
> > ia64 folks with later.
> Ok, this is the patch against 2.6.23-rc2
>
>
> In ptrace case, user space RSE might be newer than kernel RSE. To avoid
> stale RSE is used when return to userspace, this patch synchronize user
> space RSE to kernel RSE.
> Also, as TIF_ALLWORK_MASK bits are limited, TIF_NOTIFY_RESUME is
> overrided.
>
> Signed-off-by: Bibo Mao<bibo.mao@intel.com>
> Signed-off-by: Shaohua Li<shaohua.li@intel.com>
>
> ===============================
> arch/ia64/kernel/perfmon.c | 21 ++--------------
> arch/ia64/kernel/process.c | 14 +++++++++++
> arch/ia64/kernel/ptrace.c | 52 +++++++++++++++++++++++++++++++++++++++++
> include/asm-ia64/ptrace.h | 1
> include/asm-ia64/thread_info.h | 11 ++++++--
> 5 files changed, 78 insertions(+), 21 deletions(-)
>
> Index: 2.6.23-rc2/arch/ia64/kernel/process.c
> =================================> --- 2.6.23-rc2.orig/arch/ia64/kernel/process.c 2007-08-04 10:49:55.000000000 +0800
> +++ 2.6.23-rc2/arch/ia64/kernel/process.c 2007-08-08 09:27:18.000000000 +0800
> @@ -154,6 +154,17 @@ show_regs (struct pt_regs *regs)
> show_stack(NULL, NULL);
> }
>
> +void tsk_clear_notify_resume(struct task_struct *tsk)
> +{
> +#ifdef CONFIG_PERFMON
> + if (tsk->thread.pfm_needs_checking)
> + return;
> +#endif
> + if (test_ti_thread_flag(task_thread_info(tsk), TIF_RESTORE_RSE))
> + return;
> + clear_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME);
> +}
> +
> void
> do_notify_resume_user (sigset_t *unused, struct sigscratch *scr, long in_syscall)
> {
> @@ -172,6 +183,9 @@ do_notify_resume_user (sigset_t *unused,
> /* deal with pending signal delivery */
> if (test_thread_flag(TIF_SIGPENDING)||test_thread_flag(TIF_RESTORE_SIGMASK))
> ia64_do_signal(scr, in_syscall);
> + /* copy user rbs to kernel rbs */
> + if (unlikely(test_thread_flag(TIF_RESTORE_RSE)))
> + ia64_sync_krbs(current);
> }
>
> static int pal_halt = 1;
> Index: 2.6.23-rc2/arch/ia64/kernel/ptrace.c
> =================================> --- 2.6.23-rc2.orig/arch/ia64/kernel/ptrace.c 2007-08-08 09:00:28.000000000 +0800
> +++ 2.6.23-rc2/arch/ia64/kernel/ptrace.c 2007-08-08 09:27:18.000000000 +0800
> @@ -554,6 +554,25 @@ ia64_sync_user_rbs (struct task_struct *
> return 0;
> }
>
> +long
> +ia64_sync_kernel_rbs (struct task_struct *child, struct switch_stack *sw,
> + unsigned long user_rbs_start, unsigned long user_rbs_end)
> +{
> + unsigned long addr, val;
> + long ret;
> +
> + /* now copy word for word from user rbs to kernel rbs: */
> + for (addr = user_rbs_start; addr < user_rbs_end; addr += 8) {
> + if (access_process_vm(child, addr, &val, sizeof(val), 0)
> + != sizeof(val))
> + return -EIO;
> + ret = ia64_poke(child, sw, user_rbs_end, addr, val);
> + if (ret < 0)
> + return ret;
> + }
> + return 0;
> +}
> +
> /*
> * Write f32-f127 back to task->thread.fph if it has been modified.
> */
> @@ -728,6 +747,10 @@ syscall_trace_enter (long arg0, long arg
> if (test_thread_flag(TIF_SYSCALL_TRACE))
> tracehook_report_syscall(®s, 0);
>
> + /* copy user rbs to kernel rbs */
> + if (test_thread_flag(TIF_RESTORE_RSE))
> + ia64_sync_krbs(current);
> +
> if (unlikely(current->audit_context)) {
> long syscall;
> int arch;
> @@ -764,6 +787,10 @@ syscall_trace_leave (long arg0, long arg
> if (test_thread_flag(TIF_SYSCALL_TRACE))
> tracehook_report_syscall(®s, 1);
>
> + /* copy user rbs to kernel rbs */
> + if (test_thread_flag(TIF_RESTORE_RSE))
> + ia64_sync_krbs(current);
> +
> if (test_thread_flag(TIF_SINGLESTEP)) {
> force_sig(SIGTRAP, current); /* XXX */
> tracehook_report_syscall_step(®s);
> @@ -1416,9 +1443,34 @@ gpregs_writeback(struct task_struct *tar
> const struct utrace_regset *regset,
> int now)
> {
> + if (test_and_set_tsk_thread_flag(target, TIF_RESTORE_RSE))
> + return 0;
> + tsk_set_notify_resume(target);
> return do_regset_call(do_gpregs_writeback, target, regset, 0, 0, NULL, NULL);
> }
>
> +static void do_gpregs_readback(struct unw_frame_info *info, void *arg)
> +{
> + struct pt_regs *pt;
> + utrace_getset_t *dst = arg;
> + unsigned long urbs_end;
> +
> + if (unw_unwind_to_user(info) < 0)
> + return;
> + pt = task_pt_regs(dst->target);
> + urbs_end = ia64_get_user_rbs_end(dst->target, pt, NULL);
> + dst->ret = ia64_sync_kernel_rbs(dst->target, info->sw, pt->ar_bspstore, urbs_end);
> +}
> +/*
> + * This is called to read back the register backing store.
> + */
> +long ia64_sync_krbs(struct task_struct *target)
> +{
> + clear_tsk_thread_flag(target, TIF_RESTORE_RSE);
> + tsk_clear_notify_resume(target);
> + return do_regset_call(do_gpregs_readback, target, NULL, 0, 0, NULL, NULL);
> +}
> +
> static int
> fpregs_active(struct task_struct *target, const struct utrace_regset *regset)
> {
> Index: 2.6.23-rc2/include/asm-ia64/ptrace.h
> =================================> --- 2.6.23-rc2.orig/include/asm-ia64/ptrace.h 2007-08-04 10:49:55.000000000 +0800
> +++ 2.6.23-rc2/include/asm-ia64/ptrace.h 2007-08-08 09:27:18.000000000 +0800
> @@ -292,6 +292,7 @@ struct switch_stack {
> unsigned long, long);
> extern void ia64_flush_fph (struct task_struct *);
> extern void ia64_sync_fph (struct task_struct *);
> + extern long ia64_sync_krbs(struct task_struct *);
> extern long ia64_sync_user_rbs (struct task_struct *, struct switch_stack *,
> unsigned long, unsigned long);
>
> Index: 2.6.23-rc2/include/asm-ia64/thread_info.h
> =================================> --- 2.6.23-rc2.orig/include/asm-ia64/thread_info.h 2007-08-04 10:49:55.000000000 +0800
> +++ 2.6.23-rc2/include/asm-ia64/thread_info.h 2007-08-08 09:35:08.000000000 +0800
> @@ -71,6 +71,9 @@ struct thread_info {
> #define alloc_task_struct() ((struct task_struct *)__get_free_pages(GFP_KERNEL | __GFP_COMP, KERNEL_STACK_SIZE_ORDER))
> #define free_task_struct(tsk) free_pages((unsigned long) (tsk), KERNEL_STACK_SIZE_ORDER)
>
> +#define tsk_set_notify_resume(tsk) \
> + set_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME)
> +extern void tsk_clear_notify_resume(struct task_struct *tsk);
> #endif /* !__ASSEMBLY */
>
> /*
> @@ -85,28 +88,30 @@ struct thread_info {
> #define TIF_SYSCALL_AUDIT 3 /* syscall auditing active */
> #define TIF_SINGLESTEP 4 /* restore singlestep on return to user mode */
> #define TIF_RESTORE_SIGMASK 5 /* restore signal mask in do_signal() */
> -#define TIF_PERFMON_WORK 6 /* work for pfm_handle_work() */
> +#define TIF_NOTIFY_RESUME 6 /* resumption notification requested */
> #define TIF_POLLING_NRFLAG 16 /* true if poll_idle() is polling TIF_NEED_RESCHED */
> #define TIF_MEMDIE 17
> #define TIF_MCA_INIT 18 /* this task is processing MCA or INIT */
> #define TIF_DB_DISABLED 19 /* debug trap disabled for fsyscall */
> #define TIF_FREEZE 20 /* is freezing for suspend */
> +#define TIF_RESTORE_RSE 21 /* task need RSE synchronization */
>
> #define _TIF_SYSCALL_TRACE (1 << TIF_SYSCALL_TRACE)
> #define _TIF_SYSCALL_AUDIT (1 << TIF_SYSCALL_AUDIT)
> #define _TIF_SINGLESTEP (1 << TIF_SINGLESTEP)
> #define _TIF_SYSCALL_TRACEAUDIT (_TIF_SYSCALL_TRACE|_TIF_SYSCALL_AUDIT|_TIF_SINGLESTEP)
> #define _TIF_RESTORE_SIGMASK (1 << TIF_RESTORE_SIGMASK)
> -#define _TIF_PERFMON_WORK (1 << TIF_PERFMON_WORK)
> +#define _TIF_NOTIFY_RESUME (1 << TIF_NOTIFY_RESUME)
> #define _TIF_SIGPENDING (1 << TIF_SIGPENDING)
> #define _TIF_NEED_RESCHED (1 << TIF_NEED_RESCHED)
> #define _TIF_POLLING_NRFLAG (1 << TIF_POLLING_NRFLAG)
> #define _TIF_MCA_INIT (1 << TIF_MCA_INIT)
> #define _TIF_DB_DISABLED (1 << TIF_DB_DISABLED)
> #define _TIF_FREEZE (1 << TIF_FREEZE)
> +#define _TIF_RESTORE_RSE (1 << TIF_RESTORE_RSE)
>
> /* "work to do on user-return" bits */
> -#define TIF_ALLWORK_MASK (_TIF_SIGPENDING|_TIF_PERFMON_WORK|_TIF_SYSCALL_AUDIT|\
> +#define TIF_ALLWORK_MASK (_TIF_SIGPENDING|_TIF_NOTIFY_RESUME|_TIF_SYSCALL_AUDIT|\
> _TIF_NEED_RESCHED| _TIF_SYSCALL_TRACE|\
> _TIF_RESTORE_SIGMASK)
> /* like TIF_ALLWORK_BITS but sans TIF_SYSCALL_TRACE or TIF_SYSCALL_AUDIT */
> Index: 2.6.23-rc2/arch/ia64/kernel/perfmon.c
> =================================> --- 2.6.23-rc2.orig/arch/ia64/kernel/perfmon.c 2007-08-04 10:49:55.000000000 +0800
> +++ 2.6.23-rc2/arch/ia64/kernel/perfmon.c 2007-08-08 09:32:41.000000000 +0800
> @@ -586,21 +586,6 @@ pfm_put_task(struct task_struct *task)
> }
>
> static inline void
> -pfm_set_task_notify(struct task_struct *task)
> -{
> - struct thread_info *info;
> -
> - info = (struct thread_info *) ((char *) task + IA64_TASK_SIZE);
> - set_bit(TIF_PERFMON_WORK, &info->flags);
> -}
> -
> -static inline void
> -pfm_clear_task_notify(void)
> -{
> - clear_thread_flag(TIF_PERFMON_WORK);
> -}
> -
> -static inline void
> pfm_reserve_page(unsigned long a)
> {
> SetPageReserved(vmalloc_to_page((void *)a));
> @@ -3730,7 +3715,7 @@ pfm_restart(pfm_context_t *ctx, void *ar
>
> PFM_SET_WORK_PENDING(task, 1);
>
> - pfm_set_task_notify(task);
> + tsk_set_notify_resume(task);
>
> /*
> * XXX: send reschedule if task runs on another CPU
> @@ -5087,7 +5072,7 @@ pfm_handle_work(void)
>
> PFM_SET_WORK_PENDING(current, 0);
>
> - pfm_clear_task_notify();
> + tsk_clear_notify_resume(current);
>
> regs = task_pt_regs(current);
>
> @@ -5455,7 +5440,7 @@ pfm_overflow_handler(struct task_struct
> * when coming from ctxsw, current still points to the
> * previous task, therefore we must work with task and not current.
> */
> - pfm_set_task_notify(task);
> + tsk_set_notify_resume(task);
> }
> /*
> * defer until state is changed (shorten spin window). the context is locked
> -
> To unsubscribe from this list: send the line "unsubscribe linux-ia64" in
> the body of a message to majordomo@vger.kernel.org
> More majordomo info at http://vger.kernel.org/majordomo-info.html
--
-Stephane
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH]utrace: IA64 RSE bug
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
` (3 preceding siblings ...)
2007-08-08 23:10 ` Stephane Eranian
@ 2007-08-09 2:35 ` Shaohua Li
2007-08-14 9:13 ` Roland McGrath
5 siblings, 0 replies; 7+ messages in thread
From: Shaohua Li @ 2007-08-09 2:35 UTC (permalink / raw)
To: linux-ia64
On Thu, 2007-08-09 at 07:10 +0800, Stephane Eranian wrote:
> Well, looks like we need to resurect TIF_NOTIFY_RESUME now
> that we do have some actual need for it. This implies that
> I need to rework my perfmon new code base to take this into
> account. I don't want to use pfm_needs_checking. So maybe
> it is okay to use a higher order TIF bit for perfmon on IA-64
> combined with TIF_NOTIFY_RESUME.
Fine.
> For the RSE part, I am not sure I understand the logic behind this
> change. I think more explanantions maybe needed to calrify this
> a bit more.
Basically for a ptraced thread, the patch will copy user RSE to kernel
RSE every time the task will be switched to user space. The reason is
when the thread is stopped (ptraced), debugger might change thread's
user stack, and we must avoid the RSE stored in kernel to override user
stack (user space's RSE is newer in the case), so we copy user RSE to
kernel first and kernel will user the newer RSE to return to user. While
I said we do the synchronization when return to user space, there is an
exception, which is syscall trace enter. debugger might change some
syscall parameters in syscall trace enter, and kernel will use the
parameters, so we do an extra synchronization for the case.
Thanks,
Shaohua
>
> On Wed, Aug 08, 2007 at 10:30:37AM +0800, Shaohua Li wrote:
> > On Tue, 2007-08-07 at 15:13 +0800, Roland McGrath wrote:
> > > That looks reasonable to me, not being expert on the ia64 details.
> > > I rolled that into utrace-regset-ia64.patch in the 2.6.22 backport
> > > version.
> > >
> > > > patch is against latest utrace source (2.6.22 base + utrace
> patches)
> > >
> > > The latest utrace source is based on 2.6.23-rc2, and your patch
> does
> > > not
> > > apply there. TIF_NOTIFY_RESUME has been renamed to
> TIF_PERFMON_WORK.
> > > So you need to rename it back (or to something else) to overload
> it.
> > >
> > > If the gist of your patch here seems right to ia64 folks, then I'd
> > > suggest
> > > you do a patch adding ia64_sync_krbs to the upstream kernel. That
> > > would be
> > > the necessary prelude to doing the arch_ptrace_stop plan, which I
> can
> > > help
> > > ia64 folks with later.
> > Ok, this is the patch against 2.6.23-rc2
> >
> >
> > In ptrace case, user space RSE might be newer than kernel RSE. To
> avoid
> > stale RSE is used when return to userspace, this patch synchronize
> user
> > space RSE to kernel RSE.
> > Also, as TIF_ALLWORK_MASK bits are limited, TIF_NOTIFY_RESUME is
> > overrided.
> >
> > Signed-off-by: Bibo Mao<bibo.mao@intel.com>
> > Signed-off-by: Shaohua Li<shaohua.li@intel.com>
> >
> > ===============================
> > arch/ia64/kernel/perfmon.c | 21 ++--------------
> > arch/ia64/kernel/process.c | 14 +++++++++++
> > arch/ia64/kernel/ptrace.c | 52
> +++++++++++++++++++++++++++++++++++++++++
> > include/asm-ia64/ptrace.h | 1
> > include/asm-ia64/thread_info.h | 11 ++++++--
> > 5 files changed, 78 insertions(+), 21 deletions(-)
> >
> > Index: 2.6.23-rc2/arch/ia64/kernel/process.c
> > =================================> > --- 2.6.23-rc2.orig/arch/ia64/kernel/process.c 2007-08-04
> 10:49:55.000000000 +0800
> > +++ 2.6.23-rc2/arch/ia64/kernel/process.c 2007-08-08
> 09:27:18.000000000 +0800
> > @@ -154,6 +154,17 @@ show_regs (struct pt_regs *regs)
> > show_stack(NULL, NULL);
> > }
> >
> > +void tsk_clear_notify_resume(struct task_struct *tsk)
> > +{
> > +#ifdef CONFIG_PERFMON
> > + if (tsk->thread.pfm_needs_checking)
> > + return;
> > +#endif
> > + if (test_ti_thread_flag(task_thread_info(tsk),
> TIF_RESTORE_RSE))
> > + return;
> > + clear_ti_thread_flag(task_thread_info(tsk),
> TIF_NOTIFY_RESUME);
> > +}
> > +
> > void
> > do_notify_resume_user (sigset_t *unused, struct sigscratch *scr,
> long in_syscall)
> > {
> > @@ -172,6 +183,9 @@ do_notify_resume_user (sigset_t *unused,
> > /* deal with pending signal delivery */
> > if (test_thread_flag(TIF_SIGPENDING)||
> test_thread_flag(TIF_RESTORE_SIGMASK))
> > ia64_do_signal(scr, in_syscall);
> > + /* copy user rbs to kernel rbs */
> > + if (unlikely(test_thread_flag(TIF_RESTORE_RSE)))
> > + ia64_sync_krbs(current);
> > }
> >
> > static int pal_halt = 1;
> > Index: 2.6.23-rc2/arch/ia64/kernel/ptrace.c
> > =================================> > --- 2.6.23-rc2.orig/arch/ia64/kernel/ptrace.c 2007-08-08
> 09:00:28.000000000 +0800
> > +++ 2.6.23-rc2/arch/ia64/kernel/ptrace.c 2007-08-08
> 09:27:18.000000000 +0800
> > @@ -554,6 +554,25 @@ ia64_sync_user_rbs (struct task_struct *
> > return 0;
> > }
> >
> > +long
> > +ia64_sync_kernel_rbs (struct task_struct *child, struct
> switch_stack *sw,
> > + unsigned long user_rbs_start, unsigned long
> user_rbs_end)
> > +{
> > + unsigned long addr, val;
> > + long ret;
> > +
> > + /* now copy word for word from user rbs to kernel rbs: */
> > + for (addr = user_rbs_start; addr < user_rbs_end; addr += 8)
> {
> > + if (access_process_vm(child, addr, &val,
> sizeof(val), 0)
> > + != sizeof(val))
> > + return -EIO;
> > + ret = ia64_poke(child, sw, user_rbs_end, addr,
> val);
> > + if (ret < 0)
> > + return ret;
> > + }
> > + return 0;
> > +}
> > +
> > /*
> > * Write f32-f127 back to task->thread.fph if it has been modified.
> > */
> > @@ -728,6 +747,10 @@ syscall_trace_enter (long arg0, long arg
> > if (test_thread_flag(TIF_SYSCALL_TRACE))
> > tracehook_report_syscall(®s, 0);
> >
> > + /* copy user rbs to kernel rbs */
> > + if (test_thread_flag(TIF_RESTORE_RSE))
> > + ia64_sync_krbs(current);
> > +
> > if (unlikely(current->audit_context)) {
> > long syscall;
> > int arch;
> > @@ -764,6 +787,10 @@ syscall_trace_leave (long arg0, long arg
> > if (test_thread_flag(TIF_SYSCALL_TRACE))
> > tracehook_report_syscall(®s, 1);
> >
> > + /* copy user rbs to kernel rbs */
> > + if (test_thread_flag(TIF_RESTORE_RSE))
> > + ia64_sync_krbs(current);
> > +
> > if (test_thread_flag(TIF_SINGLESTEP)) {
> > force_sig(SIGTRAP, current); /* XXX */
> > tracehook_report_syscall_step(®s);
> > @@ -1416,9 +1443,34 @@ gpregs_writeback(struct task_struct *tar
> > const struct utrace_regset *regset,
> > int now)
> > {
> > + if (test_and_set_tsk_thread_flag(target, TIF_RESTORE_RSE))
> > + return 0;
> > + tsk_set_notify_resume(target);
> > return do_regset_call(do_gpregs_writeback, target, regset, 0,
> 0, NULL, NULL);
> > }
> >
> > +static void do_gpregs_readback(struct unw_frame_info *info, void
> *arg)
> > +{
> > + struct pt_regs *pt;
> > + utrace_getset_t *dst = arg;
> > + unsigned long urbs_end;
> > +
> > + if (unw_unwind_to_user(info) < 0)
> > + return;
> > + pt = task_pt_regs(dst->target);
> > + urbs_end = ia64_get_user_rbs_end(dst->target, pt, NULL);
> > + dst->ret = ia64_sync_kernel_rbs(dst->target, info->sw,
> pt->ar_bspstore, urbs_end);
> > +}
> > +/*
> > + * This is called to read back the register backing store.
> > + */
> > +long ia64_sync_krbs(struct task_struct *target)
> > +{
> > + clear_tsk_thread_flag(target, TIF_RESTORE_RSE);
> > + tsk_clear_notify_resume(target);
> > + return do_regset_call(do_gpregs_readback, target, NULL, 0, 0,
> NULL, NULL);
> > +}
> > +
> > static int
> > fpregs_active(struct task_struct *target, const struct
> utrace_regset *regset)
> > {
> > Index: 2.6.23-rc2/include/asm-ia64/ptrace.h
> > =================================> > --- 2.6.23-rc2.orig/include/asm-ia64/ptrace.h 2007-08-04
> 10:49:55.000000000 +0800
> > +++ 2.6.23-rc2/include/asm-ia64/ptrace.h 2007-08-08
> 09:27:18.000000000 +0800
> > @@ -292,6 +292,7 @@ struct switch_stack {
> > unsigned long, long);
> > extern void ia64_flush_fph (struct task_struct *);
> > extern void ia64_sync_fph (struct task_struct *);
> > + extern long ia64_sync_krbs(struct task_struct *);
> > extern long ia64_sync_user_rbs (struct task_struct *, struct
> switch_stack *,
> > unsigned long, unsigned long);
> >
> > Index: 2.6.23-rc2/include/asm-ia64/thread_info.h
> > =================================> > --- 2.6.23-rc2.orig/include/asm-ia64/thread_info.h 2007-08-04
> 10:49:55.000000000 +0800
> > +++ 2.6.23-rc2/include/asm-ia64/thread_info.h 2007-08-08
> 09:35:08.000000000 +0800
> > @@ -71,6 +71,9 @@ struct thread_info {
> > #define alloc_task_struct() ((struct task_struct
> *)__get_free_pages(GFP_KERNEL | __GFP_COMP, KERNEL_STACK_SIZE_ORDER))
> > #define free_task_struct(tsk) free_pages((unsigned long)
> (tsk), KERNEL_STACK_SIZE_ORDER)
> >
> > +#define tsk_set_notify_resume(tsk) \
> > + set_ti_thread_flag(task_thread_info(tsk), TIF_NOTIFY_RESUME)
> > +extern void tsk_clear_notify_resume(struct task_struct *tsk);
> > #endif /* !__ASSEMBLY */
> >
> > /*
> > @@ -85,28 +88,30 @@ struct thread_info {
> > #define TIF_SYSCALL_AUDIT 3 /* syscall auditing active */
> > #define TIF_SINGLESTEP 4 /* restore singlestep
> on return to user mode */
> > #define TIF_RESTORE_SIGMASK 5 /* restore signal mask in
> do_signal() */
> > -#define TIF_PERFMON_WORK 6 /* work for pfm_handle_work()
> */
> > +#define TIF_NOTIFY_RESUME 6 /* resumption notification
> requested */
> > #define TIF_POLLING_NRFLAG 16 /* true if poll_idle() is
> polling TIF_NEED_RESCHED */
> > #define TIF_MEMDIE 17
> > #define TIF_MCA_INIT 18 /* this task is processing MCA
> or INIT */
> > #define TIF_DB_DISABLED 19 /* debug trap disabled
> for fsyscall */
> > #define TIF_FREEZE 20 /* is freezing for suspend */
> > +#define TIF_RESTORE_RSE 21 /* task need RSE
> synchronization */
> >
> > #define _TIF_SYSCALL_TRACE (1 << TIF_SYSCALL_TRACE)
> > #define _TIF_SYSCALL_AUDIT (1 << TIF_SYSCALL_AUDIT)
> > #define _TIF_SINGLESTEP (1 << TIF_SINGLESTEP)
> > #define _TIF_SYSCALL_TRACEAUDIT (_TIF_SYSCALL_TRACE|
> _TIF_SYSCALL_AUDIT|_TIF_SINGLESTEP)
> > #define _TIF_RESTORE_SIGMASK (1 << TIF_RESTORE_SIGMASK)
> > -#define _TIF_PERFMON_WORK (1 << TIF_PERFMON_WORK)
> > +#define _TIF_NOTIFY_RESUME (1 << TIF_NOTIFY_RESUME)
> > #define _TIF_SIGPENDING (1 << TIF_SIGPENDING)
> > #define _TIF_NEED_RESCHED (1 << TIF_NEED_RESCHED)
> > #define _TIF_POLLING_NRFLAG (1 << TIF_POLLING_NRFLAG)
> > #define _TIF_MCA_INIT (1 << TIF_MCA_INIT)
> > #define _TIF_DB_DISABLED (1 << TIF_DB_DISABLED)
> > #define _TIF_FREEZE (1 << TIF_FREEZE)
> > +#define _TIF_RESTORE_RSE (1 << TIF_RESTORE_RSE)
> >
> > /* "work to do on user-return" bits */
> > -#define TIF_ALLWORK_MASK (_TIF_SIGPENDING|_TIF_PERFMON_WORK|
> _TIF_SYSCALL_AUDIT|\
> > +#define TIF_ALLWORK_MASK (_TIF_SIGPENDING|_TIF_NOTIFY_RESUME|
> _TIF_SYSCALL_AUDIT|\
> > _TIF_NEED_RESCHED|
> _TIF_SYSCALL_TRACE|\
> > _TIF_RESTORE_SIGMASK)
> > /* like TIF_ALLWORK_BITS but sans TIF_SYSCALL_TRACE or
> TIF_SYSCALL_AUDIT */
> > Index: 2.6.23-rc2/arch/ia64/kernel/perfmon.c
> > =================================> > --- 2.6.23-rc2.orig/arch/ia64/kernel/perfmon.c 2007-08-04
> 10:49:55.000000000 +0800
> > +++ 2.6.23-rc2/arch/ia64/kernel/perfmon.c 2007-08-08
> 09:32:41.000000000 +0800
> > @@ -586,21 +586,6 @@ pfm_put_task(struct task_struct *task)
> > }
> >
> > static inline void
> > -pfm_set_task_notify(struct task_struct *task)
> > -{
> > - struct thread_info *info;
> > -
> > - info = (struct thread_info *) ((char *) task +
> IA64_TASK_SIZE);
> > - set_bit(TIF_PERFMON_WORK, &info->flags);
> > -}
> > -
> > -static inline void
> > -pfm_clear_task_notify(void)
> > -{
> > - clear_thread_flag(TIF_PERFMON_WORK);
> > -}
> > -
> > -static inline void
> > pfm_reserve_page(unsigned long a)
> > {
> > SetPageReserved(vmalloc_to_page((void *)a));
> > @@ -3730,7 +3715,7 @@ pfm_restart(pfm_context_t *ctx, void *ar
> >
> > PFM_SET_WORK_PENDING(task, 1);
> >
> > - pfm_set_task_notify(task);
> > + tsk_set_notify_resume(task);
> >
> > /*
> > * XXX: send reschedule if task runs on another CPU
> > @@ -5087,7 +5072,7 @@ pfm_handle_work(void)
> >
> > PFM_SET_WORK_PENDING(current, 0);
> >
> > - pfm_clear_task_notify();
> > + tsk_clear_notify_resume(current);
> >
> > regs = task_pt_regs(current);
> >
> > @@ -5455,7 +5440,7 @@ pfm_overflow_handler(struct task_struct
> > * when coming from ctxsw, current still
> points to the
> > * previous task, therefore we must work with
> task and not current.
> > */
> > - pfm_set_task_notify(task);
> > + tsk_set_notify_resume(task);
> > }
> > /*
> > * defer until state is changed (shorten spin window).
> the context is locked
> > -
> > To unsubscribe from this list: send the line "unsubscribe
> linux-ia64" in
> > the body of a message to majordomo@vger.kernel.org
> > More majordomo info at http://vger.kernel.org/majordomo-info.html
>
> --
>
> -Stephane
>
>
^ permalink raw reply [flat|nested] 7+ messages in thread
* Re: [PATCH]utrace: IA64 RSE bug
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
` (4 preceding siblings ...)
2007-08-09 2:35 ` Shaohua Li
@ 2007-08-14 9:13 ` Roland McGrath
5 siblings, 0 replies; 7+ messages in thread
From: Roland McGrath @ 2007-08-14 9:13 UTC (permalink / raw)
To: linux-ia64
> > If the gist of your patch here seems right to ia64 folks, then I'd
> > suggest you do a patch adding ia64_sync_krbs to the upstream kernel.
> > That would be the necessary prelude to doing the arch_ptrace_stop plan,
> > which I can help ia64 folks with later.
> Ok, this is the patch against 2.6.23-rc2
That patch is for a kernel that has "tracehook" calls, which is not the
upstream kernel. If it's for 2.6.23-rc2+linux-2.6.23-rc2-utrace.patch,
that is not what was requested in the bit you just quoted.
To reiterate, I think ia64 folks should consider a version of your patch
for vanilla 2.6.23-rc3. It sounded like there was some agreement on
re-integrating the flag bit conflicts. The flag bit integration and the
meat of the patch is not particular to utrace. If you do the upstream
version of this patch and ia64 folks consider it reasonable, then it can go
into the vanilla ia64 kernel soon. Can you do that? As I said before,
that patch would be the precursor to the arch_ptrace_stop support that
makes more cleanup of the vanilla kernel's ia64 ptrace code possible.
(Since this would now be a patch for the vanilla ia64 kernel, it would be
misleading to keep it in a thread with "utrace" in the Subject: line.)
If the low-level parts of the RSE-vs-debugger scheme will be going into the
vanilla kernel, then I would much prefer to have that happen and then have
the utrace ia64 patch be relative to that.
Thanks,
Roland
^ permalink raw reply [flat|nested] 7+ messages in thread
end of thread, other threads:[~2007-08-14 9:13 UTC | newest]
Thread overview: 7+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2007-08-07 5:23 [PATCH]utrace: IA64 RSE bug Shaohua Li
2007-08-07 7:13 ` Roland McGrath
2007-08-07 21:55 ` Stephane Eranian
2007-08-08 2:30 ` Shaohua Li
2007-08-08 23:10 ` Stephane Eranian
2007-08-09 2:35 ` Shaohua Li
2007-08-14 9:13 ` Roland McGrath
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox