Layer 01 · Before it runs · portcullis

What was it
allowed to do?

Your agent obeys more than your prompt. It obeys the plugins you installed, the skills in your repo, the MCP servers you connected, and any instruction text sitting inside them. A manifest tells you a name and a description. It does not tell you that a "read-only" tool writes files, or that a comment three folders down tells the agent to post your environment to a URL.

Portcullis reads that layer as data and reports what it found, with the exact file and line for every signal. Then it signs a receipt, so "we reviewed this" becomes something you can show rather than something you say.

A wrought-iron portcullis grille raked by a single hard light.

In detail

How it
works.

What it readsClaude Code plugins, Agent Skills, MCP servers — manifests, code, and the prose an agent will read as instructions
How it reads itRead-only, one buffer per file, symlinks flagged and never followed, traversal never leaves the target root
Rule familiesinstruction-injection (INJ) · exfiltration (EXF) · dangerous-capability (CAP) · manifest-mismatch (MAN/PKG)
What it emitsA findings report citing rule id, file and line — plus a signed vetting receipt
Fails on--fail-on high for a gate you can put in CI
It never executes what it is scanning.

That is the whole design, and it is enforced rather than intended. The test suite runs every scan in a child process where child_process and dynamic loading of any target path throw before scanner code loads; a companion preload makes every network surface throw. Hostile fixtures still scan to completion, which proves the no-execute and no-network properties behaviourally instead of by grep. A static check forbids the entire exec and network surface anywhere in src/.

Straight answers

What this
does not prove.

Stated here, at full size, rather than in a footnote. Every tool in the stack carries its own ceiling, and they are not the same ceiling.

Signals, with a citation not a verdict on the author

A finding says “this pattern can exfiltrate data,” never “this author is malicious.” Many of these patterns have entirely ordinary explanations — a build tool legitimately shells out. The manifest never tells you which; portcullis makes the pattern visible so a person can decide.

The scan ran not that the package is safe

The receipt attests that this scanner, at this version, examined these exact bytes. A clean result is reported as “no signals matched by this scanner’s current rules” — which is not a statement that no risk is present.

Run it

Free,
and local.

scan a packageportcullis ./some-plugin
gate a marketplace intakeportcullis ./a-marketplace-checkout --fail-on high
re-check a receipt someone handed youportcullis --verify portcullis-out/receipt.json

Everything above runs on your machine with no account and no network call. Checking an artifact is free permanently — see what we actually charge for.

The agent will act either way.

The only question is whether anything survives it that a stranger can check.