{
  "module": "DD-16 — ZeroClaw: The Rust Microkernel Harness",
  "course": "Harness Engineering Master Course",
  "version": "1.0.0",
  "duration_minutes": 30,
  "total_questions": 15,
  "bloom_distribution": {
    "target": "20% recall / 40% application / 40% analysis",
    "actual": { "recall": 3, "application": 6, "analysis": 6 }
  },
  "passing_score_percent": 70,
  "questions": [
    {
      "id": "Q01",
      "bloom": "recall",
      "type": "multiple_choice",
      "prompt": "Per ADR-002, what does the ZeroClaw kernel depend on?",
      "options": [
        "Concrete provider implementations behind feature flags",
        "Only the zeroclaw-api traits (ModelProvider, Channel, Tool, Memory, Observer, RuntimeAdapter, Peripheral) — never concrete impls",
        "A vendor-specific adapter layer compiled into zeroclaw-runtime",
        "A plugin registry that dynamically loads shared objects at startup"
      ],
      "answer_index": 1,
      "rationale": "ADR-002 is trait-driven extensibility: the kernel depends ONLY on zeroclaw-api traits, never on concrete implementations. Adding a provider/channel/tool is a trait impl wired through a factory — not a core patch. This is the cleanest separation of concerns in the roster."
    },
    {
      "id": "Q02",
      "bloom": "recall",
      "type": "multiple_choice",
      "prompt": "Which lists the 6 layers of ZeroClaw's safety model in correct order (outer to inner)?",
      "options": [
        "OS sandbox, channel pairing, tool receipts, autonomy level, workspace boundary, shell policy",
        "Channel pairing, autonomy level, workspace boundary, shell policy, OS sandbox, tool receipts",
        "Workspace boundary, shell policy, tool receipts, channel pairing, autonomy level, OS sandbox",
        "Autonomy level, tool receipts, OS sandbox, channel pairing, shell policy, workspace boundary"
      ],
      "answer_index": 1,
      "rationale": "The correct order is: (1) channel pairing/access control, (2) autonomy level, (3) workspace boundary + path rules, (4) shell command policy, (5) OS-level sandbox, (6) tool receipts. Each layer is independently defeatable but the default ships all six on."
    },
    {
      "id": "Q03",
      "bloom": "recall",
      "type": "multiple_choice",
      "prompt": "What is ZeroClaw's rubric score and where does it score highest?",
      "options": [
        "34/60, highest on Module 6 Permission/Safety (5/5)",
        "34/60, highest on Module 3 Context Management (5/5)",
        "28/60, highest on Module 9 Verification (5/5)",
        "41/60, highest on Module 1 Loop (5/5)"
      ],
      "answer_index": 0,
      "rationale": "ZeroClaw scores 34/60. It scores highest on Module 6 (Permission/Safety) at 5/5 — the 6-layer model is the deepest in the thin-harness category. It loses on Module 3 (Context) at 2/5."
    },
    {
      "id": "Q04",
      "bloom": "application",
      "type": "multiple_choice",
      "prompt": "A tool call attempts to read /etc/passwd. The autonomy level is 'supervised' and workspace_only is true. Which layer blocks it, and why?",
      "options": [
        "Layer 2 (autonomy level): file_read is risk-classified as high-risk, so it is blocked",
        "Layer 3 (workspace boundary): /etc/passwd is outside the workspace, and workspace_only confines reads",
        "Layer 4 (shell policy): /etc is on the forbidden_commands list",
        "Layer 6 (tool receipts): no receipt exists for /etc/passwd, so the read is rejected"
      ],
      "answer_index": 1,
      "rationale": "Layer 3 (workspace boundary + path rules) blocks it. workspace_only confines reads/writes to the workspace; /etc/passwd is outside. forbidden_paths would also independently block /etc. Layer 2 classifies tools by risk; layer 4 applies to shell commands; layer 6 receipts are computed AFTER a successful call."
    },
    {
      "id": "Q05",
      "bloom": "application",
      "type": "multiple_choice",
      "prompt": "You are adding a new LLM vendor to ZeroClaw. Which sequence correctly follows the trait-driven pattern?",
      "options": [
        "Patch zeroclaw-runtime to import the vendor SDK, add a switch statement, recompile",
        "Write a ModelProvider trait impl, register it in the provider factory, add a Cargo feature flag, reference by name in zeroclaw.toml",
        "Write a shell script that wraps the vendor API, register it as a tool, call it from the loop",
        "Fork zeroclaw-api, add a vendor-specific trait, merge back into the kernel"
      ],
      "answer_index": 1,
      "rationale": "The trait-driven pattern: implement the trait, register in the factory, feature-flag it, reference by name. No core patch, no provider-specific code in the kernel. This is why 25+ provider slots scale without bloat."
    },
    {
      "id": "Q06",
      "bloom": "application",
      "type": "multiple_choice",
      "prompt": "You want to prevent the agent from EVER writing to ~/.ssh. Which ZeroClaw mechanism is the correct one to configure?",
      "options": [
        "Layer 2 autonomy level set to readonly",
        "Layer 3 forbidden_paths including ~/.ssh",
        "Layer 4 forbidden_commands including ssh",
        "Layer 6 tool receipts disabled for ssh writes"
      ],
      "answer_index": 1,
      "rationale": "Layer 3 (workspace boundary + path rules) with forbidden_paths is the correct mechanism. forbidden_paths always blocks specified paths (like /etc, /sys, ~/.ssh) regardless of anything else. Layer 4 governs shell commands, not file paths; layer 2 governs tool risk; layer 6 is a detection mechanism, not a prevention gate."
    },
    {
      "id": "Q07",
      "bloom": "application",
      "type": "multiple_choice",
      "prompt": "An indirect injection arrives inside a tool output in ZeroClaw. Under the explicit-only memory design, what happens to it?",
      "options": [
        "It is automatically persisted to durable memory and influences all future turns",
        "It can influence the current turn but cannot persist to durable memory unless the agent explicitly calls memory_store",
        "It is blocked by layer 1 (channel pairing) because it came from a tool output",
        "It triggers the outbound leak detector and is quarantined"
      ],
      "answer_index": 1,
      "rationale": "Under explicit-only memory, prompt context, tool output, files, and logs are NOT durable memory by default. The injection can influence the current turn but cannot persist itself silently — it would need an explicit memory_store call, which the security cascade inspects. This is the security property that differs from Hermes's free-writes design."
    },
    {
      "id": "Q08",
      "bloom": "application",
      "type": "multiple_choice",
      "prompt": "You need a per-call routing setup: reasoning on Claude, cheap chat on Ollama. Which ZeroClaw mechanism do you use?",
      "options": [
        "The compatible.rs OpenAI-compatible shim",
        "The router.rs per-call model routing",
        "The reliable.rs retry/key-rotation wrapper",
        "The peripheral trait for multi-model dispatch"
      ],
      "answer_index": 1,
      "rationale": "router.rs enables per-call model routing — reasoning on one model, cheap chat on another. reliable.rs provides retry/backoff/API-key rotation. compatible.rs is the OpenAI-compatible shim for vendors that speak that protocol. The Peripheral trait is for hardware devices, not model routing."
    },
    {
      "id": "Q09",
      "bloom": "application",
      "type": "multiple_choice",
      "prompt": "Your deployment needs a security gate where high-risk tool calls are routed to a separate approver channel before execution. Which ZeroClaw feature does this?",
      "options": [
        "The tool-receipt system with ephemeral keys",
        "Approval routing redirected to an approver channel with fail-closed semantics",
        "The OS-level sandbox auto-detection",
        "The minimal-prompt philosophy configured per-channel"
      ],
      "answer_index": 1,
      "rationale": "Approval routing can redirect to a separate approver channel with fail-closed semantics. This composes with the 6-layer cascade — it is one of the extra gates ZeroClaw ships alongside OTP gating, emergency stop, and the outbound leak detector."
    },
    {
      "id": "Q10",
      "bloom": "analysis",
      "type": "multiple_choice",
      "prompt": "Why is the shell command policy implemented BEFORE the shell executes, rather than detected in an audit log afterward?",
      "options": [
        "Because audit logs are expensive to store and slow to query",
        "Because detect-after-exec is too late — the command has already run; blocking at the policy gate is the correct layer for shell injection defense",
        "Because the model cannot read audit logs, so it would not learn from blocks",
        "Because OS-level sandboxes (layer 5) make audit logs redundant"
      ],
      "answer_index": 1,
      "rationale": "Detect-after-exec is too late — the command has already run by the time the audit log records it. Blocking at the policy gate (the allowed_commands allowlist, pattern-matched before exec) is the correct layer for shell injection defense. This is defense-in-depth applied at the right layer."
    },
    {
      "id": "Q11",
      "bloom": "analysis",
      "type": "multiple_choice",
      "prompt": "A reviewer claims 'ZeroClaw is a thin harness, so it must be a small codebase.' What is the correct response?",
      "options": [
        "Agree — thin harnesses are always under 50k LOC by definition",
        "Correct the misreading: ZeroClaw is thin by PHILOSOPHY (single binary, no telemetry, no hidden prompts) but medium-thick by IMPLEMENTATION (~700-800k Rust LOC, 1015 files); RFC #5574 is closing the gap",
        "Agree — the ~700k LOC count includes test fixtures, so the real number is small",
        "Correct the misreading: ZeroClaw is actually thick by philosophy and thin by implementation"
      ],
      "answer_index": 1,
      "rationale": "This is the thickness-paradox anti-pattern. 'Thin' is a design INTENT (single binary, no telemetry, no SaaS, no hidden prompts), not a LOC count. The as-built artifact is ~700-800k Rust LOC across 1015 files. RFC #5574 (microkernel refactor) is closing the gap by factoring functionality behind feature flags."
    },
    {
      "id": "Q12",
      "bloom": "analysis",
      "type": "multiple_choice",
      "prompt": "A forensics team wants to use ZeroClaw's tool receipts to prove, to a third party, what a session did after it ended. Why does this not work today?",
      "options": [
        "Because receipts are only generated for failed tool calls, not successful ones",
        "Because receipts use ephemeral keys — they are an in-context integrity signal, not yet a chained/durable audit log; they cannot prove anything to a third party after the session ends",
        "Because the model can forge receipts by computing its own HMAC-SHA256",
        "Because receipts are stored in memory only and are never fed back into the conversation"
      ],
      "answer_index": 1,
      "rationale": "The limitation: receipts use ephemeral keys. They defend against fabricated-tool-claim attacks within the current session (the receipt is in-context evidence), but they are NOT yet a chained, cross-signed, durable audit log. They cannot prove anything to a third party after the session ends. Making them durable is fix #2 on the architect's list. The harness computes receipts, so the model cannot forge them."
    },
    {
      "id": "Q13",
      "bloom": "analysis",
      "type": "multiple_choice",
      "prompt": "Compare ZeroClaw's explicit-only memory to Hermes's model-initiated free writes (DD-08). What is the trade?",
      "options": [
        "ZeroClaw optimizes for compounding capability; Hermes optimizes for a smaller poisoning surface",
        "ZeroClaw trades compounding capability for a smaller poisoning surface; Hermes trades a smaller poisoning surface for compounding capability (self-evolving skills)",
        "Both designs make the same trade; the difference is implementation language only",
        "ZeroClaw uses free writes; Hermes uses explicit-only memory"
      ],
      "answer_index": 1,
      "rationale": "The trade is capability vs. security. ZeroClaw's explicit-only memory (the agent must call memory_store explicitly) trades compounding capability for a smaller poisoning surface — an indirect injection cannot silently persist itself. Hermes's model-initiated free writes enable compounding capability (self-evolving skills) but create a larger poisoning surface. Both are defensible; the choice depends on deployment priorities."
    },
    {
      "id": "Q14",
      "bloom": "analysis",
      "type": "multiple_choice",
      "prompt": "Why does the security check run BETWEEN the model emitting a tool_call and the tool executing — rather than as a pre-filter on user input or a post-hoc audit?",
      "options": [
        "Because pre-filters are too fast and would slow down the loop",
        "Because a benign-looking user input can produce a dangerous tool call after model processing; and a post-hoc audit is too late since the command has run. The model-emit-to-tool-exec boundary is the one place every model-emitted action must pass through",
        "Because the security layer cannot inspect user input for technical reasons",
        "Because post-hoc audits require more memory than the runtime can allocate"
      ],
      "answer_index": 1,
      "rationale": "The placement is load-bearing. A pre-filter on input misses the case where benign input produces a dangerous tool call after the model processes it. A post-hoc audit detects after the command has already run — too late. The model-emit-to-tool-exec boundary is the one place every model-emitted action must pass through, and a block there surfaces as ToolResult::Err the model can react to (not a silent failure)."
    },
    {
      "id": "Q15",
      "bloom": "analysis",
      "type": "multiple_choice",
      "prompt": "The model claims 'the file says X' to justify an egress tool call, but no file_read receipt exists. What does this demonstrate, and how does ZeroClaw's layer 6 address it?",
      "options": [
        "It demonstrates a channel-pairing bypass; layer 6 cannot address it because receipts are only for shell commands",
        "It demonstrates the fabricated-tool-claim attack (Module 11); layer 6 (HMAC-SHA256 receipts over successful tool calls) provides in-context evidence that no file_read occurred, allowing the harness to flag the fabrication",
        "It demonstrates an OS-sandbox escape; layer 6 addresses it by re-running the file_read inside a fresh sandbox",
        "It demonstrates a workspace-boundary violation; layer 6 addresses it by adding /tmp/X to forbidden_paths"
      ],
      "answer_index": 1,
      "rationale": "This is the fabricated-tool-claim attack from Module 11. The model fabricates a tool result to justify a downstream action. Layer 6 (HMAC-SHA256 receipts over successful tool calls, fed back into the conversation) provides in-context evidence: if no receipt exists for the claimed file_read, the harness can flag the fabrication. The model cannot credibly claim a tool returned data it did not. Caveat: ephemeral keys mean this is an integrity signal, not a durable audit log."
    }
  ]
}
