gitlab.com/Raven-IO/raven-delve@v1.22.4/pkg/proc/native/ptrace_freebsd_amd64.go (about) 1 package native 2 3 /* 4 #include <sys/types.h> 5 #include <sys/ptrace.h> 6 */ 7 import "C" 8 9 import ( 10 "fmt" 11 "unsafe" 12 13 "gitlab.com/Raven-IO/raven-delve/pkg/proc/amd64util" 14 ) 15 16 var ( 17 xsaveLen int 18 xsaveErr error 19 ) 20 21 func ptraceGetXsaveLen(tid int) (int, error) { 22 var info C.struct_ptrace_xstate_info 23 ret, err := C.ptrace(C.PT_GETXSTATE_INFO, C.pid_t(tid), C.caddr_t(unsafe.Pointer(&info)), C.int(unsafe.Sizeof(info))) 24 if ret == 0 { 25 xsaveLen = int(info.xsave_len) 26 } else { 27 xsaveLen, xsaveErr = -1, err 28 return xsaveLen, fmt.Errorf("failed to get xstate info: %v", err) 29 } 30 return xsaveLen, nil 31 } 32 33 func ptraceXsaveLen(tid int) (int, error) { 34 if xsaveLen > 0 { 35 return xsaveLen, nil 36 } 37 if xsaveLen < 0 { 38 return xsaveLen, fmt.Errorf("failed to get xstate info: %v", xsaveErr) 39 } 40 return ptraceGetXsaveLen(tid) 41 } 42 43 // ptraceGetXsave gets the X86 XSAVE data for the given tid. 44 func ptraceGetXsave(tid int) ([]byte, error) { 45 len, err := ptraceXsaveLen(tid) 46 if err != nil { 47 return nil, err 48 } 49 xsaveBuf := make([]byte, len) 50 ret, err := C.ptrace(C.PT_GETXSTATE, C.pid_t(tid), C.caddr_t(unsafe.Pointer(&xsaveBuf[0])), C.int(len)) 51 if ret != 0 { 52 return nil, fmt.Errorf("failed to get xstate: %v", err) 53 } 54 return xsaveBuf, nil 55 } 56 57 // ptraceSetXsave sets the X86 XSAVE data for the given tid. 58 func ptraceSetXsave(tid int, xsaveBuf []byte) error { 59 ret, err := C.ptrace(C.PT_SETXSTATE, C.pid_t(tid), C.caddr_t(unsafe.Pointer(&xsaveBuf[0])), C.int(len(xsaveBuf))) 60 if ret != 0 { 61 return fmt.Errorf("failed to set xstate: %v", err) 62 } 63 return nil 64 } 65 66 func ptraceGetRegset(id int) (*amd64util.AMD64Xstate, error) { 67 var regset amd64util.AMD64Xstate 68 ret, err := C.ptrace(C.PT_GETFPREGS, C.pid_t(id), C.caddr_t(unsafe.Pointer(®set.AMD64PtraceFpRegs)), C.int(0)) 69 if ret != 0 { 70 return nil, fmt.Errorf("failed to get FP registers: %v", err) 71 } 72 regset.Xsave, err = ptraceGetXsave(id) 73 if err != nil { 74 return nil, err 75 } 76 err = amd64util.AMD64XstateRead(regset.Xsave, false, ®set) 77 return ®set, err 78 } 79 80 func ptraceSetRegset(id int, regset *amd64util.AMD64Xstate) error { 81 ret, err := C.ptrace(C.PT_SETFPREGS, C.pid_t(id), C.caddr_t(unsafe.Pointer(®set.AMD64PtraceFpRegs)), C.int(0)) 82 if ret != 0 { 83 return fmt.Errorf("failed to set FP registers: %v", err) 84 } 85 if regset.Xsave != nil { 86 return ptraceSetXsave(id, regset.Xsave) 87 } 88 return nil 89 }