summaryrefslogtreecommitdiff
path: root/9ns/docs/DESIGN.md
diff options
context:
space:
mode:
Diffstat (limited to '9ns/docs/DESIGN.md')
-rw-r--r--9ns/docs/DESIGN.md25
1 files changed, 25 insertions, 0 deletions
diff --git a/9ns/docs/DESIGN.md b/9ns/docs/DESIGN.md
index 1d66387..6b1b80c 100644
--- a/9ns/docs/DESIGN.md
+++ b/9ns/docs/DESIGN.md
@@ -114,6 +114,31 @@ posted name reaches that server's whole 9P tree, and nothing is connected
until something walks. XDG_RUNTIME_DIR unset is fatal before anything is
forked (the registry is not guessable; no `/tmp` fallback).
+A registry entry that is a **directory** is served the same way the root
+is: a synthetic directory (its node id under the reserved index
+`synth_index`, the slot in the low bits) listing the real directory's
+entries, dialing the sockets found inside on walk and recursing into
+further directories — up to `max_synth_depth` (8) levels, bounded by
+`max_synth_dirs` (64) synthetic nodes per 9ns process. This is how
+multi-service providers organize themselves (zmx posts its sessions
+under `zmx/<name>`), the plan9port `mntgen` shape: one tree, many
+mounts, each entry a mount point. Non-socket, non-directory entries
+inside a directory answer EIO on walk, exactly like a plain file in the
+registry itself; a directory's slots are freed when the kernel forgets
+the dentry.
+
+A synthetic node's slot comes back through FORGET, and the kernel sends
+most of them as `BATCH_FORGET`, whose header `nodeid` is 0 and whose
+body carries one `(nodeid, nlookup)` per forgotten node — for any mix of
+owners. The dispatcher therefore cannot route a batch by its header the
+way it routes every other request: `distributeForgets` unpacks the body
+and hands each entry to its owner (synthetic root, synthetic
+subdirectory or per-mount bridge). Routing the batch whole instead loses
+every entry in it, so the 64 slots leak and a subdirectory served once
+answers EIO forever. The forgets themselves arrive on the kernel's
+schedule, not at `close`, so a slot may take a moment to return; a
+listing that needs one meanwhile answers EIO rather than waiting.
+
```
program 9ns parent
in new userns │