summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMalfurious <m@lfurio.us>2023-09-29 18:48:41 -0400
committerMalfurious <m@lfurio.us>2024-04-24 13:31:08 -0400
commitcca59c4d757c99df14978d1778b6be562dd886cd (patch)
tree5a9b8ba802f1e2acbfe35cc504a0c0f0dad19215
parentf9584d0417ed8d3fc72d9dcb297b1738fef2d00c (diff)
downloadmisplays-cca59c4d757c99df14978d1778b6be562dd886cd.tar.gz
misplays-cca59c4d757c99df14978d1778b6be562dd886cd.zip
Workaround SIGSTOP on child process startup
The debugger design prefers to use PTRACE_SEIZE instead of PTRACE_ATTACH, due to the simpler thread control semantics that are available. However, to utilize the same featureset for forked processes, we can no longer use PTRACE_TRACEME to guarantee that the child becomes a tracee before it execs into the target program. Manually raising SIGSTOP to act as a synchronization point is problematic for a couple reasons: - We need to detect whether the special SIGSTOP was or was not yet encountered by the time our debugger module attaches and interrupts the thread. This complicates the dance of input controls to ensure we are at the exec (and nowhere else) when the real user takes over the controls. - The injection of an extra signal circumvents the benefits we hope to leverage by using the PTRACE_SEIZE semantics. We can no longer assume that all incoming signals are genuine. For the time being, sleep in the newly forked child for the scheduler delay period. This is not bullet-proof, but tends to allow the debugger module enough time to actually seize the thread before anything interesting happens. At this point a single dbg_cont() will cause the child to arrive and stop at the user's exec. Signed-off-by: Malfurious <m@lfurio.us>
-rw-r--r--debugger.c3
-rw-r--r--misplays.c7
2 files changed, 8 insertions, 2 deletions
diff --git a/debugger.c b/debugger.c
index 572231c..d016076 100644
--- a/debugger.c
+++ b/debugger.c
@@ -17,7 +17,8 @@
static const int PTRACE_OPTIONS =
PTRACE_O_TRACECLONE |
- PTRACE_O_TRACEEXIT |
+ //PTRACE_O_TRACEEXIT |
+ PTRACE_O_TRACEEXEC |
PTRACE_O_TRACESYSGOOD;
static int detect_breakpoint(struct thread *th) {
diff --git a/misplays.c b/misplays.c
index da15a30..2f0ce8f 100644
--- a/misplays.c
+++ b/misplays.c
@@ -27,9 +27,10 @@ static pid_t dofork(char **argv, struct console *cons) {
}
if (pid == 0) {
+ usleep(100000);
console_configslave(cons);
close_range(STDERR_FILENO+1, ~0U, CLOSE_RANGE_UNSHARE);
- raise(SIGSTOP); // ptrace(PTRACE_TRACEME, 0, NULL, NULL);
+ //raise(SIGSTOP); // ptrace(PTRACE_TRACEME, 0, NULL, NULL);
execvp(argv[0], argv);
exit(EXIT_FAILURE);
}
@@ -209,6 +210,10 @@ int main(int argc, char **argv) {
list_insert(processes.end, proc);
th = proc->threads.head;
+ if (child) {
+ dbg_cont(th, PTRACE_CONT);
+ }
+
cursinit();
left = newpan(0, 0, 0, 0);
right = newpan(0, 0, 0, 0);