DF-5833 / dripper.c
/* * dripper.c -- DF-5833 rig: pre-forked drip driver. * * Waits for the eater's "ready" file (floor reached; the victim will * release its workers within ~100 ms), sleeps past the drain + crash + * prelude + DRYRUN, then drives the drip sequence into the eater's * fifo. NEVER forks -- all syscalls (access/open/write) survive the * memory-pressure window. * * usage: dripper <readyfile> <fifo> */ #include <sys/types.h> #include <fcntl.h> #include <stdio.h> #include <unistd.h> #include <string.h> int main(int argc, char **argv) { const char *gofile = argv[1]; const char *fifo = argv[2]; char buf[64]; int fd, i, n; if (argc < 3) return (1); /* wait for the eater's ready marker (no forks; access() only) */ while (access(gofile, F_OK) != 0) usleep(5000); /* Timeline (relative to ready): * +100ms victim releases workers (drain begins) * +700ms victim crashes; dumper enters sigexit * +700ms.. dumper prelude (expand_name/vn_open/..., ~30 fresh * pages) crawls on vm_wait; workers are parked in * their in-flight lwp_create (~4-8 fresh pages each) * +850ms open the fifo * +900ms.. small staged drips: the prelude (~30 pages) completes * FIRST, then the 16 workers (~80 pages) insert AFTER * the DRYRUN note walk, and the dumper's huge * core-header alloc (hundreds of pages) completes LAST. * This ordering is what lands the lwp_create insertions * between the DRYRUN sizing pass and the WRITE pass. */ usleep(1100000); fd = open(fifo, O_WRONLY); if (fd < 0) return (2); usleep(50000); /* ONE big burst timed INSIDE the [DRYRUN, WRITE] window: the * dumper's huge core-header kmalloc completes, AND every parked * in-flight lwp_create completes at the same instant -- dozens of * worker threads then race the single dumper for p_token and * their RB-tree insertions land BEFORE the WRITE note walk. */ n = snprintf(buf, sizeof(buf), "D 4194304\n"); write(fd, buf, n); usleep(150000); for (i = 0; i < 24; i++) { n = snprintf(buf, sizeof(buf), "D 65536\n"); write(fd, buf, n); usleep(80000); } n = snprintf(buf, sizeof(buf), "D 4194304\n"); write(fd, buf, n); usleep(300000); n = snprintf(buf, sizeof(buf), "D 67108864\n"); write(fd, buf, n); close(fd); return (0); } |