Index: lib/libc/sys/ptrace.2 =================================================================== --- lib/libc/sys/ptrace.2 +++ lib/libc/sys/ptrace.2 @@ -2,7 +2,7 @@ .\" $NetBSD: ptrace.2,v 1.2 1995/02/27 12:35:37 cgd Exp $ .\" .\" This file is in the public domain. -.Dd July 15, 2019 +.Dd April 10, 2021 .Dt PTRACE 2 .Os .Sh NAME @@ -807,6 +807,20 @@ The .Fa data argument is ignored. +.It Dv PT_COREDUMP +This request creates a coredump for the stopped program. +.Fa addr +argument specifies a pointer to a +.Vt "struct ptrace_coredump" , +which is defined as follows: +.Bd -literal +struct ptrace_coredump { + TODO; +}; +.Ed +.Pp +The size of the structmust be passed in +.Fa data . .El .Sh ARM MACHINE-SPECIFIC REQUESTS .Bl -tag -width "Dv PT_SETVFPREGS" Index: sys/kern/sys_process.c =================================================================== --- sys/kern/sys_process.c +++ sys/kern/sys_process.c @@ -51,6 +51,8 @@ #include #include #include +#include +#include #include @@ -446,6 +448,33 @@ return (error); } +static int +ptrace_coredump(struct thread *tracer, struct thread *tracee, + struct ptrace_coredump *pc) +{ + int error; + struct file *fp; + struct vnode *vp; + struct proc *p = tracee->td_proc; + + if (p->p_sysent->sv_coredump == NULL) + return (ENOSYS); + + error = getvnode(tracer, pc->pc_fd, &cap_write_rights, &fp); + if (error != 0) + return (error); + + vp = fp->f_vnode; + /* do not try writing to non-regular files */ + if (vp->v_type != VREG) + return (EFAULT); + + error = p->p_sysent->sv_coredump(tracee, vp, OFF_MAX, 0); + + fdrop(fp, tracer); + return (error); +} + /* * Process debugging system call. */ @@ -469,6 +498,7 @@ struct ptrace_io_desc piod; struct ptrace_lwpinfo pl; struct ptrace_vm_entry pve; + struct ptrace_coredump pc; struct dbreg dbreg; struct fpreg fpreg; struct reg reg; @@ -519,6 +549,12 @@ case PT_VM_ENTRY: error = copyin(uap->addr, &r.pve, sizeof(r.pve)); break; + case PT_COREDUMP: + if (uap->data != sizeof(r.pc)) + error = EINVAL; + else + error = copyin(uap->addr, &r.pc, uap->data); + break; default: addr = uap->addr; break; @@ -1299,6 +1335,12 @@ PROC_LOCK(p); break; + case PT_COREDUMP: + PROC_UNLOCK(p); + error = ptrace_coredump(td, td2, addr); + PROC_LOCK(p); + break; + default: #ifdef __HAVE_PTRACE_MACHDEP if (req >= PT_FIRSTMACH) { Index: sys/sys/ptrace.h =================================================================== --- sys/sys/ptrace.h +++ sys/sys/ptrace.h @@ -74,6 +74,8 @@ #define PT_GET_SC_ARGS 27 /* fetch syscall args */ #define PT_GET_SC_RET 28 /* fetch syscall results */ +#define PT_COREDUMP 29 /* create a coredump */ + #define PT_GETREGS 33 /* get general-purpose registers */ #define PT_SETREGS 34 /* set general-purpose registers */ #define PT_GETFPREGS 35 /* get floating-point registers */ @@ -176,6 +178,11 @@ char *pve_path; /* Path name of object. */ }; +/* Argument structure for PT_COREDUMP. */ +struct ptrace_coredump { + int pc_fd; /* File descriptor to write dump to. */ +}; + #ifdef _KERNEL int ptrace_set_pc(struct thread *_td, unsigned long _addr);