Author: markj
Date: Mon Jun 23 01:10:56 2014
New Revision: 267759
URL: http://svnweb.freebsd.org/changeset/base/267759

Log:
  Fix a couple of bugs on amd64 when fetching probe arguments beyond the
  first five for probes entered through a UD fault (i.e. FBT probes).
  
  Specifically, handle the fact that dtrace_invop_callsite must be
  16 byte-aligned and thus may not immediately follow the call to
  dtrace_invop() in dtrace_invop_start(). Also fetch register arguments and
  the stack pointer through a struct trapframe instead of a struct reg.
  
  PR:           191260
  Submitted by: luke...@gmail.com
  MFC after:    3 weeks

Modified:
  head/sys/cddl/dev/dtrace/amd64/dtrace_isa.c

Modified: head/sys/cddl/dev/dtrace/amd64/dtrace_isa.c
==============================================================================
--- head/sys/cddl/dev/dtrace/amd64/dtrace_isa.c Mon Jun 23 00:54:56 2014        
(r267758)
+++ head/sys/cddl/dev/dtrace/amd64/dtrace_isa.c Mon Jun 23 01:10:56 2014        
(r267759)
@@ -349,7 +349,8 @@ dtrace_getarg(int arg, int aframes)
        for (i = 1; i <= aframes; i++) {
                fp = fp->f_frame;
 
-               if (fp->f_retaddr == (long)dtrace_invop_callsite) {
+               if (P2ROUNDUP(fp->f_retaddr, 16) ==
+                   (long)dtrace_invop_callsite) {
                        /*
                         * In the case of amd64, we will use the pointer to the
                         * regs structure that was pushed when we took the
@@ -363,33 +364,33 @@ dtrace_getarg(int arg, int aframes)
                         * we're seeking is passed in regsiters, we can just
                         * load it directly.
                         */
-                       struct reg *rp = (struct reg *)((uintptr_t)&fp[1] +
-                           sizeof (uintptr_t));
+                       struct trapframe *tf =
+                           (struct trapframe *)((uintptr_t)&fp[1]);
 
                        if (arg <= inreg) {
                                switch (arg) {
                                case 0:
-                                       stack = (uintptr_t *)&rp->r_rdi;
+                                       stack = (uintptr_t *)&tf->tf_rdi;
                                        break;
                                case 1:
-                                       stack = (uintptr_t *)&rp->r_rsi;
+                                       stack = (uintptr_t *)&tf->tf_rsi;
                                        break;
                                case 2:
-                                       stack = (uintptr_t *)&rp->r_rdx;
+                                       stack = (uintptr_t *)&tf->tf_rdx;
                                        break;
                                case 3:
-                                       stack = (uintptr_t *)&rp->r_rcx;
+                                       stack = (uintptr_t *)&tf->tf_rcx;
                                        break;
                                case 4:
-                                       stack = (uintptr_t *)&rp->r_r8;
+                                       stack = (uintptr_t *)&tf->tf_r8;
                                        break;
                                case 5:
-                                       stack = (uintptr_t *)&rp->r_r9;
+                                       stack = (uintptr_t *)&tf->tf_r9;
                                        break;
                                }
                                arg = 0;
                        } else {
-                               stack = (uintptr_t *)(rp->r_rsp);
+                               stack = (uintptr_t *)(tf->tf_rsp);
                                arg -= inreg;
                        }
                        goto load;
_______________________________________________
svn-src-head@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-head
To unsubscribe, send any mail to "svn-src-head-unsubscr...@freebsd.org"

Reply via email to