Skip to content

Read the strace, not the man page.

Linux is taught as a list of commands, which is why people who have used it for a decade still cannot say what fork gives the child, why their container takes ten seconds to stop, or what D state means. The commands are the interface. The contract is underneath, and the contract is what breaks.

Correct C. Passes the test that runs it once.
int fd = open("/var/log/app.log", O_RDONLY);
if (fork() == 0) { read(fd, buf, 4096); _exit(0); }
openat(AT_FDCWD, "/var/log/app.log", O_RDONLY) = 3
clone(flags=CLONE_CHILD_CLEARTID|SIGCHLD) = 4127
[pid 4127] read(3, "...", 4096) = 4096
[pid 4126] lseek(3, 0, SEEK_CUR) = 4096

The parent never read a byte and its offset is four kilobytes in. The defect is not in the syntax — it is in the fact that a descriptor table, an open file description and an inode are three different things, and fork copies only the first of them. None of that is visible without a model of the kernel underneath. So there is one here.

Eight tracks

  • Processes

    What exactly does the child get?

  • Descriptors

    Which of the three levels is this bug in?

  • Signals

    When is this delivered, and what does it interrupt?

  • PID 1 and lifecycle

    Why does your container take ten seconds to stop?

  • Identity and permission

    Who does the kernel think you are?

  • /proc and observability

    What is this process actually doing?

  • Namespaces and cgroups

    What is a container, before any container tooling exists?

  • Reading what was generated

    What will the kernel do with this?

Everything you do here stays in this browser.Part of liter8.sh