This is the mail archive of the
systemtap@sourceware.org
mailing list for the systemtap project.
Re: systemtap ARM port status
On Mon, Jun 04, 2007 at 10:35:47AM -0400, Martin Hunt wrote:
On Sat, 2007-06-02 at 09:11 -0500, Quentin Barnes wrote:
On Fri, Jun 01, 2007 at 10:29:37PM -0500, Quentin Barnes wrote:
[...]
>So I think all I have to do to properly port the deref() macro
>for ARM is to copy the ARM's __{get|put}_user_asm_{byte|half|word}()
>macros to loc2c-runtime.h, rename them to the _stp_* variety, and
>have them use the "ldrb", "strb", "ldr", and "str" instructions.
Overnight testing revealed that works. Attached is the ARM version
that seems to do the right thing:
Sorry I was unable to respond to this sooner; I was out on Friday.
Do you want me to check this latest version in, or are you still
testing?
The 20070602 testsuite is still running with this patch, but it's
made it through the critical parts now. The patch below should
bring the runtime up to fully operational with ARM (at least as far
as I'm currently aware!). Please inspect it over carefully and
check it in if it is acceptable.
Martin
Quentin
Index: systemtap-20070602/runtime/stack-arm.c
===================================================================
--- systemtap-20070602/runtime/stack-arm.c (.../vendor/usr/src) (revision 214)
+++ systemtap-20070602/runtime/stack-arm.c (.../branches/kprobes/usr/src) (revision 214)
@@ -59,7 +59,7 @@ static void __stp_stack_print (struct pt
_stp_symbol_print((unsigned long)pc);
_stp_print_char('\n');
} else {
- _stp_printf("%08lx ", pc);
+ _stp_printf("%08lx ", (unsigned long)pc);
}
/* Sanity check the next_fp. */
Index: systemtap-20070602/runtime/loc2c-runtime.h
===================================================================
--- systemtap-20070602/runtime/loc2c-runtime.h (.../vendor/usr/src) (revision 214)
+++ systemtap-20070602/runtime/loc2c-runtime.h (.../branches/kprobes/usr/src) (revision 214)
@@ -303,14 +303,118 @@
#elif defined (__arm__)
+#define __stp_get_user_asm_byte(x,addr,err) \
+ __asm__ __volatile__( \
+ "1: ldrb %1,[%2],#0\n" \
+ "2:\n" \
+ " .section .fixup,\"ax\"\n" \
+ " .align 2\n" \
+ "3: mov %0, %3\n" \
+ " mov %1, #0\n" \
+ " b 2b\n" \
+ " .previous\n" \
+ " .section __ex_table,\"a\"\n" \
+ " .align 3\n" \
+ " .long 1b, 3b\n" \
+ " .previous" \
+ : "+r" (err), "=&r" (x) \
+ : "r" (addr), "i" (-EFAULT) \
+ : "cc")
+
+#ifndef __ARMEB__
+#define __stp_get_user_asm_half(x,__gu_addr,err) \
+({ \
+ unsigned long __b1, __b2; \
+ __stp_get_user_asm_byte(__b1, __gu_addr, err); \
+ __stp_get_user_asm_byte(__b2, __gu_addr + 1, err); \
+ (x) = __b1 | (__b2 << 8); \
+})
+#else
+#define __stp_get_user_asm_half(x,__gu_addr,err) \
+({ \
+ unsigned long __b1, __b2; \
+ __stp_get_user_asm_byte(__b1, __gu_addr, err); \
+ __stp_get_user_asm_byte(__b2, __gu_addr + 1, err); \
+ (x) = (__b1 << 8) | __b2; \
+})
+#endif
+
+#define __stp_get_user_asm_word(x,addr,err) \
+ __asm__ __volatile__( \
+ "1: ldr %1,[%2],#0\n" \
+ "2:\n" \
+ " .section .fixup,\"ax\"\n" \
+ " .align 2\n" \
+ "3: mov %0, %3\n" \
+ " mov %1, #0\n" \
+ " b 2b\n" \
+ " .previous\n" \
+ " .section __ex_table,\"a\"\n" \
+ " .align 3\n" \
+ " .long 1b, 3b\n" \
+ " .previous" \
+ : "+r" (err), "=&r" (x) \
+ : "r" (addr), "i" (-EFAULT) \
+ : "cc")
+
+#define __stp_put_user_asm_byte(x,__pu_addr,err) \
+ __asm__ __volatile__( \
+ "1: strb %1,[%2],#0\n" \
+ "2:\n" \
+ " .section .fixup,\"ax\"\n" \
+ " .align 2\n" \
+ "3: mov %0, %3\n" \
+ " b 2b\n" \
+ " .previous\n" \
+ " .section __ex_table,\"a\"\n" \
+ " .align 3\n" \
+ " .long 1b, 3b\n" \
+ " .previous" \
+ : "+r" (err) \
+ : "r" (x), "r" (__pu_addr), "i" (-EFAULT) \
+ : "cc")
+
+#ifndef __ARMEB__
+#define __stp_put_user_asm_half(x,__pu_addr,err) \
+({ \
+ unsigned long __temp = (unsigned long)(x); \
+ __stp_put_user_asm_byte(__temp, __pu_addr, err); \
+ __stp_put_user_asm_byte(__temp >> 8, __pu_addr + 1, err); \
+})
+#else
+#define __stp_put_user_asm_half(x,__pu_addr,err) \
+({ \
+ unsigned long __temp = (unsigned long)(x); \
+ __stp_put_user_asm_byte(__temp >> 8, __pu_addr, err); \
+ __stp_put_user_asm_byte(__temp, __pu_addr + 1, err); \
+})
+#endif
+
+#define __stp_put_user_asm_word(x,__pu_addr,err) \
+ __asm__ __volatile__( \
+ "1: str %1,[%2],#0\n" \
+ "2:\n" \
+ " .section .fixup,\"ax\"\n" \
+ " .align 2\n" \
+ "3: mov %0, %3\n" \
+ " b 2b\n" \
+ " .previous\n" \
+ " .section __ex_table,\"a\"\n" \
+ " .align 3\n" \
+ " .long 1b, 3b\n" \
+ " .previous" \
+ : "+r" (err) \
+ : "r" (x), "r" (__pu_addr), "i" (-EFAULT) \
+ : "cc")
+
#define deref(size, addr) \
({ \
int _bad = 0; \
intptr_t _v=0; \
switch (size){ \
- case 1: __get_user_asm_byte(_v, addr, _bad); break; \
- case 2: __get_user_asm_half(_v, addr, _bad); break; \
- case 4: __get_user_asm_word(_v, addr, _bad); break; \
+ case 1: __stp_get_user_asm_byte(_v, addr, _bad); break; \
+ case 2: __stp_get_user_asm_half(_v, addr, _bad); break; \
+ case 4: __stp_get_user_asm_word(_v, addr, _bad); break; \
default: __get_user_bad(); break; \
} \
if (_bad) \
@@ -322,10 +426,10 @@
({ \
int _bad=0; \
switch (size){ \
- case 1: __put_user_asm_byte(value, addr, _bad); break; \
- case 2: __put_user_asm_half(value, addr, _bad); break; \
- case 4: __put_user_asm_word(value, addr, _bad); break; \
- case 8: __put_user_asm_dword(value, addr, _bad); break; \
+ case 1: __stp_put_user_asm_byte(value, addr, _bad); break; \
+ case 2: __stp_put_user_asm_half(value, addr, _bad); break; \
+ case 4: __stp_put_user_asm_word(value, addr, _bad); break; \
+ case 8: __stp_put_user_asm_dword(value, addr, _bad); break; \
default: __put_user_bad(); break; \
} \
if (_bad) \
Index: systemtap-20070602/runtime/regs.c
===================================================================
--- systemtap-20070602/runtime/regs.c (.../vendor/usr/src) (revision 214)
+++ systemtap-20070602/runtime/regs.c (.../branches/kprobes/usr/src) (revision 214)
@@ -47,6 +47,8 @@ unsigned long _stp_ret_addr (struct pt_r
return regs->b0;
#elif defined (__s390__) || defined (__s390x__)
return regs->gprs[14];
+#elif defined (__arm__)
+ return regs->ARM_r0;
#else
#error Unimplemented architecture
#endif
Index: systemtap-20070602/tapset/errno.stp
===================================================================
--- systemtap-20070602/tapset/errno.stp (.../vendor/usr/src) (revision 214)
+++ systemtap-20070602/tapset/errno.stp (.../branches/kprobes/usr/src) (revision 214)
@@ -370,6 +370,8 @@ function returnstr:string (returnp:long)
ret = CONTEXT->regs->u_regs[UREG_RETPC];
#elif defined (__s390x__)
ret = CONTEXT->regs->gprs[2];
+#elif defined (__arm__)
+ ret = CONTEXT->regs->ARM_r0;
#else
goto no_ret;
#endif