PTRACE(2)

NAME
ptrace - process trace

SYNOPSIS
#include <signal.h>
#include <sys/ptrace.h>
#include <sys/wait.h>

ptrace(request, pid, addr, data [ , addr2 ] )
enum ptracereq request;
int pid;
char *addr;
int data;
char *addr2;

DESCRIPTION

ptrace() provides a means by which a process may control the execution of another process, and examine and change its core image. Its primary use is for the implementation of breakpoint debugging. There are five arguments whose interpretation depends on the request argument. Generally, pid is the process ID of the traced process. A process being traced behaves normally until it encounters some signal whether internally generated like “illegal instruction” or externally generated like “interrupt”. See sigvec(2) for the list. Then the traced process enters a stopped state and the tracing process is notified using wait(2V). When the traced process is in the stopped state, its core image can be examined and modified using ptrace(). If desired, another ptrace() request can then cause the traced process either to terminate or to continue, possibly ignoring the signal.

Note: several different values of the request argument can make ptrace() return data values — since -1 is a possibly legitimate value, to differentiate between -1 as a legitimate value and -1 as an error code, you should clear the errno global error code before doing a ptrace() call, and then check the value of errno afterwards.

The value of the request argument determines the precise action of the call:

PTRACE_TRACEME
    This request is the only one used by the traced process; it declares that the process is to be traced by its parent. All the other arguments are ignored. Peculiar results will ensue if the parent does not expect to trace the child.

PTRACE_PEEKTEXT
PTRACE_PEEKDATA
    The word in the traced process's address space at addr is returned. If the instruction and data spaces are separate (for example, historically on a PDP-11), request PTRACE_PEEKTEXT indicates instruction space while PTRACE_PEEKDATA indicates data space. Otherwise, either request may be used, with equal results; addr must be a multiple of 4 on a Sun-4 system. The child must be stopped. The input data and addr2 are ignored.

PTRACE_PEEKUSER
    The word of the system's per-process data area corresponding to addr is returned. addr must be a valid offset within the kernel's per-process data pages. This space contains the registers and other information about the process; its layout corresponds to the user structure in the system (see <sys/user.h>).

PTRACE_POKETEXT
PTRACE_POKEDATA
    The given data are written at the word in the process's address space corresponding to addr. addr must be a multiple of 4 on a Sun-4 system. No useful value is returned. If the instruction and data spaces are separate, request PTRACE_PEEKTEXT indicates instruction space while PTRACE_PEEKDATA indicates data space. The PTRACE_POKETEXT request must be used to write into a process's text space even if the instruction and data spaces are not separate.

PTRACE_POKEUSER
    The process's system data are written, as it is read with request PTRACE_PEEKUSER. Only a few locations can be written in this way: the general registers, the floating point and status registers, and certain bits of the processor status word.

PTRACE_CONT
    The data argument is taken as a signal number and the child's execution continues at location addr as if it had incurred that signal. Normally the signal number will be either 0 to indicate that the signal that caused the stop should be ignored, or that value fetched out of the process's image indicating which signal caused the stop. If addr is (int *)1 then execution continues from where it stopped. addr must be a multiple of 4 on a Sun-4 system.

PTRACE_KILL
    The traced process terminates, with the same consequences as exit(2V).

PTRACE_SINGLESTEP
    Execution continues as in request PTRACE_CONT; however, as soon as possible after execution of at least one instruction, execution stops again. The signal number from the stop is SIGTRAP. On Sun-3 and Sun386i systems, the status register T-bit is used and just one instruction is executed. This is part of the mechanism for implementing breakpoints. On a Sun-4 system this will return an error since there is no hardware assist for this feature. Instead, the user should insert breakpoint traps in the debugged program with PTRACE_POKETEXT.

PTRACE_ATTACH
    Attach to the process identified by the pid argument and begin tracing it. PTRACE_ATTACH causes a SIGSTOP to be sent to process pid. Process pid does not have to be a child of the requestor, but the requestor must have permission to send process pid a signal and the effective user IDs of the requesting process and process pid must match.

PTRACE_DETACH
    Detach the process being traced. Process pid is no longer being traced and continues its execution. The data argument is taken as a signal number and the process continues at location addr as if it had incurred that signal.

PTRACE_GETREGS
    The traced process's registers are returned in a structure pointed to by the addr argument. The registers include the general purpose registers, the program counter and the program status word. The ``regs'' structure defined in <machine/reg.h> describes the data that are returned.

PTRACE_SETREGS
    The traced process's registers are written from a structure pointed to by the addr argument. The registers include the general purpose registers, the program counter and the program status word. The ``regs'' structure defined in reg.h describes the data that are set.

PTRACE_GETFPREGS
    (Sun-3, Sun-4 and Sun386i systems only) The traced process's FPP status is returned in a structure pointed to by the addr argument. The status includes the 68881 (80387 on Sun386i systems) floating point registers and the control, status, and instruction address registers. The ``fp_status'' structure defined in reg. describes the data that are returned. The fp_state structure defined in <machine/fp.h> describes the data that are returned on a Sun386i system.

PTRACE_SETFPREGS
    (Sun-3, Sun-4 and Sun386i systems only) The traced process's FPP status is written from a structure pointed to by the addr argument. The status includes the FPP floating point registers and the control, status, and instruction address registers. The ``fp_status'' structure defined in reg.h describes the data that are set. The ``fp_state'' structure defined in fp.h describes the data that are returned on a Sun386i system.

PTRACE_GETFPAREGS
    (a Sun-3 system with FPA only) The traced process's FPA registers are returned in a structure pointed to by the addr argument. The ``fpa_regs'' structure defined in reg.h describes the data that are returned.

PTRACE_SETFPAREGS
    (a Sun-3 system with FPA only) The traced process's FPA registers are written from a structure pointed to by the addr argument. The “fpa_regs” structure defined in reg.h describes the data that are set.

PTRACE_READTEXT
PTRACE_READDATA
    Read data from the address space of the traced process. If the instruction and data spaces are separate, request PTRACE_READTEXT indicates instruction space while PTRACE_READDATA indicates data space. The addr argument is the address within the traced process from where the data are read, the data argument is the number of bytes to read, and the addr2 argument is the address within the requesting process where the data are written.

PTRACE_WRITETEXT
PTRACE_WRITEDATA
    Write data into the address space of the traced process. If the instruction and data spaces are separate, request PTRACE_READTEXT indicates instruction space while PTRACE_READDATA indicates data space. The addr argument is the address within the traced process where the data are written, the data argument is the number of bytes to write, and the addr2 argument is the address within the requesting process from where the data are read.

PTRACE_SETWRBKPT
    (Sun386i systems only) Set a write breakpoint at location addr in the process being traced. Whenever a write is directed to this location a breakpoint will occur and a SIGTRAP signal will be sent to the process. The data argument specifies which debug register should be used for the address of the breakpoint and must be in the range 0 through 3, inclusive. The addr2 argument specifies the length of the operand in bytes, and must be one of 1, 2, or 4.

PTRACE_SETACBKPT
    (Sun386i systems only) Set an access breakpoint at location addr in the process being traced. When location addr is read or written a breakpoint will occur and the process will be sent a SIGTRAP signal. The data argument specifies which debug register should be used for the address of the breakpoint and must be in the range 0 through 3, inclusive. The addr2 argument specifies the length of the operand in bytes, and must be one of 1, 2, or 4.

PTRACE_CLRBKPT
    (Sun386i systems only) Clears all break points set with PTRACE_SETACBKPT or PTRACE_SETWRBKPT.

PTRACE_SYSCALL
    Execution continues as in request PTRACE_CONT; until the process makes a system call. The process receives a SIGTRAP signal and stops. At this point the arguments to the system call may be inspected in the process user structure using the PTRACE_PEEKUSER request. The system call number is available in place of the 8th argument. Continuing with another PTRACE_SYSCALL will stop the process again at the completion of the system call. At this point the result of the system call and error value may be inspected in the process user structure.

PTRACE_DUMPCORE
    Dumps a core image of the traced process to a file. The name of the file is obtained from the addr argument.

As indicated, these calls (except for requests PTRACE_TRACEME, PTRACE_ATTACH and PTRACE_DETACH) can be used only when the subject process has stopped. The wait() call is used to determine when a process stops; in such a case the “termination” status returned by wait() has the value WSTOPPED to indicate a stop rather than genuine termination.

To forestall possible fraud, ptrace() inhibits the setUID and setGID facilities on subsequent execve(2V) calls. If a traced process calls execve(), it will stop before executing the first instruction of the new image, showing signal SIGTRAP.

On the Sun, “word” also means a 32-bit integer.

RETURN VALUES

On success, the value returned by ptrace() depends on request as follows:

    PTRACE_PEEKTEXT
    PTRACE_PEEKDATA
        The word in the traced process's address space at addr.

    PTRACE_PEEKUSER
        The word of the system's per-process data area corresponding to addr.

On failure, these requests return -1 and set errno to indicate the error.

For all other values of request, ptrace() returns:

0   on success.

-1  on failure and sets errno to indicate the error.

ERRORS

EIO The request code is invalid.

    The given signal number is invalid.

    The specified address is out of bounds.

EPERM
    The specified process cannot be traced.

ESRCH
    The specified process does not exist.

    request requires process pid to be traced by the current process and stopped, and process pid is not being traced by the current process.

    request requires process pid to be traced by the current process and stopped, and process pid is not stopped.

SEE ALSO
adb(1), intro(2), ioctl(2), sigvec(2), wait(2V)

BUGS

ptrace() is unique and arcane; it should be replaced with a special file which can be opened and read and written. The control functions could then be implemented with ioctl(2) calls on this file. This would be simpler to understand and have much higher performance.

The requests PTRACE_TRACEME through PTRACE_SINGLESTEP are standard UNIX system ptrace() requests. The requests PTRACE_ATTACH through PTRACE_DUMPCORE and the fifth argument, addr2, are unique to SunOS.

The request PTRACE_TRACEME should be able to specify signals which are to be treated normally and not cause a stop. In this way, for example, programs with simulated floating point (which use “illegal instruction” signals at a very high rate) could be efficiently debugged.

The error indication, -1, is a legitimate function value; errno, (see intro(2)), can be used to clarify what it means.