Page Menu
Home
FreeBSD
Search
Configure Global Search
Log In
Files
F139650851
D29691.id87799.diff
No One
Temporary
Actions
View File
Edit File
Delete File
View Transforms
Subscribe
Mute Notifications
Flag For Later
Award Token
Size
6 KB
Referenced Files
None
Subscribers
None
D29691.id87799.diff
View Options
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/subr_trap.c
===================================================================
--- sys/kern/subr_trap.c
+++ sys/kern/subr_trap.c
@@ -193,6 +193,40 @@
#endif
}
+static void
+ptrace_coredump(struct proc *p)
+{
+ struct thread *td;
+
+ td = curthread;
+
+ if ((p->p_flag2 & P2_COREDUMP) == 0)
+ return;
+ if (p->p_sysent->sv_coredump == NULL) {
+ p->p_coredump_error = ENOSYS;
+ return;
+ }
+
+ if ((p->p_flag & P_HADTHREADS) != 0) {
+ if (thread_single(p, SINGLE_BOUNDARY) != 0) {
+ p->p_coredump_error = EBUSY;
+ return;
+ }
+ }
+
+ struct vnode *vp = p->p_coredump_vn;
+ PROC_UNLOCK(p);
+ p->p_coredump_error =
+ p->p_sysent->sv_coredump(td, vp, p->p_coredump_limit, 0);
+ PROC_LOCK(p);
+
+ if ((p->p_flag & P_HADTHREADS) != 0)
+ thread_single_end(p, SINGLE_BOUNDARY);
+
+ p->p_flag2 &= ~P2_COREDUMP;
+ wakeup(p);
+}
+
/*
* Process an asynchronous software trap.
* This is relatively easy.
@@ -355,6 +389,12 @@
kern_sigprocmask(td, SIG_SETMASK, &td->td_oldsigmask, NULL, 0);
}
+ if ((p->p_flag2 & P2_COREDUMP) != 0) {
+ PROC_LOCK(p);
+ ptrace_coredump(p);
+ PROC_UNLOCK(p);
+ }
+
#ifdef RACCT
if (__predict_false(racct_enable && p->p_throttled != 0))
racct_proc_throttled(p);
Index: sys/kern/sys_process.c
===================================================================
--- sys/kern/sys_process.c
+++ sys/kern/sys_process.c
@@ -51,6 +51,8 @@
#include <sys/sx.h>
#include <sys/malloc.h>
#include <sys/signalvar.h>
+#include <sys/caprights.h>
+#include <sys/filedesc.h>
#include <machine/reg.h>
@@ -469,6 +471,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 +522,14 @@
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);
+ if (r.pc.pc_flags != 0)
+ error = EINVAL;
+ break;
default:
addr = uap->addr;
break;
@@ -611,6 +622,7 @@
struct ptrace_io_desc *piod = NULL;
struct ptrace_lwpinfo *pl;
struct ptrace_sc_ret *psr;
+ struct file *fp;
int error, num, tmp;
int proctree_locked = 0;
lwpid_t tid = 0, *buf;
@@ -635,6 +647,7 @@
case PT_SET_EVENT_MASK:
case PT_DETACH:
case PT_GET_SC_ARGS:
+ case PT_COREDUMP:
sx_xlock(&proctree_lock);
proctree_locked = 1;
break;
@@ -950,6 +963,11 @@
case PT_TO_SCX:
case PT_SYSCALL:
case PT_DETACH:
+ case PT_COREDUMP:
+ /* PT_COREDUMP does not pass signal in data. */
+ if (req == PT_COREDUMP)
+ data = 0;
+
/* Zero means do not send any signal */
if (data < 0 || data > _SIG_MAXSIG) {
error = EINVAL;
@@ -1003,6 +1021,30 @@
break;
}
break;
+ case PT_COREDUMP:
+ {
+ struct ptrace_coredump *pc = addr;
+ CTR2(KTR_PTRACE,
+ "PT_COREDUMP: pid %d, fd = %d",
+ p->p_pid, pc->pc_fd);
+
+ error = getvnode(td, pc->pc_fd, &cap_write_rights, &fp);
+ if (error != 0)
+ break;
+
+ /* Do not try writing to non-regular files. */
+ if (fp->f_vnode->v_type != VREG) {
+ error = EFAULT;
+ break;
+ }
+
+ p->p_coredump_vn = fp->f_vnode;
+ if (pc->pc_limit <= 0)
+ p->p_coredump_limit = OFF_MAX;
+ else
+ p->p_coredump_limit = pc->pc_limit;
+ break;
+ }
case PT_DETACH:
/*
* Clear P_TRACED before reparenting
@@ -1052,12 +1094,20 @@
break;
}
+ if (error != 0)
+ break;
+
sx_xunlock(&proctree_lock);
proctree_locked = 0;
sendsig:
MPASS(proctree_locked == 0);
+ if ((p->p_flag2 & P2_COREDUMP) != 0) {
+ /* XXXKIB do something reasonable */
+ }
+ p->p_flag2 |= P2_COREDUMP;
+
/*
* Clear the pending event for the thread that just
* reported its event (p_xthread). This may not be
@@ -1313,6 +1363,13 @@
}
out:
+ if (req == PT_COREDUMP) {
+ while ((p->p_flag2 & P2_COREDUMP) != 0)
+ msleep(p, &p->p_mtx, PPAUSE, "crdmp", 0);
+ fdrop(fp, td);
+ error = p->p_coredump_error;
+ }
+
/* Drop our hold on this process now that the request has completed. */
_PRELE(p);
fail:
Index: sys/sys/proc.h
===================================================================
--- sys/sys/proc.h
+++ sys/sys/proc.h
@@ -720,6 +720,9 @@
uint64_t p_prev_runtime; /* (c) Resource usage accounting. */
struct racct *p_racct; /* (b) Resource accounting. */
int p_throttled; /* (c) Flag for racct pcpu throttling */
+ struct vnode *p_coredump_vn; /* (c) vnode to write coredump to. */
+ off_t p_coredump_limit; /* (c) max coredump file size. */
+ int p_coredump_error; /* (c) coredump return value. */
/*
* An orphan is the child that has been re-parented to the
* debugger as a result of attaching to it. Need to keep
@@ -829,6 +832,7 @@
#define P2_STKGAP_DISABLE_EXEC 0x00001000 /* Stack gap disabled
after exec */
#define P2_ITSTOPPED 0x00002000
+#define P2_COREDUMP 0x00004000 /* Coredump request */
/* Flags protected by proctree_lock, kept in p_treeflags. */
#define P_TREE_ORPHANED 0x00000001 /* Reparented, on orphan list */
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,14 @@
char *pve_path; /* Path name of object. */
};
+/* Argument structure for PT_COREDUMP. */
+struct ptrace_coredump {
+ int pc_fd; /* File descriptor to write dump to. */
+ off_t pc_limit; /* Maximum size of the coredump,
+ 0 for no limit. */
+ uint32_t pc_flags; /* Flags (currently reserved). */
+};
+
#ifdef _KERNEL
int ptrace_set_pc(struct thread *_td, unsigned long _addr);
File Metadata
Details
Attached
Mime Type
text/plain
Expires
Mon, Dec 15, 2:34 PM (52 m, 35 s)
Storage Engine
blob
Storage Format
Raw Data
Storage Handle
26987612
Default Alt Text
D29691.id87799.diff (6 KB)
Attached To
Mode
D29691: ptrace: Add PT_COREDUMP request (WIP)
Attached
Detach File
Event Timeline
Log In to Comment