PyTorch and TorchScript Rules
Detects unsafe PyTorch checkpoint loading, TorchScript custom operators, and dynamic hub imports.
The TORCH rule family turns findings on this surface into actionable records with rule ID, severity, CWE, OWASP LLM mapping, owner, release decision, and retest command.
PyTorch checkpoints commonly wrap pickle data. TorchScript and hub workflows can also execute native or Python code outside the model graph.
Supported inputs
.pt.pth.ckpt.torchscripthubconf.py
Typical attack scenarios
- A checkpoint executes Python during torch.load.
- A TorchScript model references an unreviewed native custom operator.
- A hubconf.py file pulls code from an unpinned repository.
Detection logic
Sentinel ties TORCH evidence to reproducible signals such as file path, metadata, opcode, AST node, manifest field, dependency, or archive entry. The same signal should disappear when the finding is closed.
Triage
Do not read TORCH findings as scanner noise. Verify the evidence first, map the finding to a severity-based release decision, and then produce closure evidence with the same Sentinel command.
- Source: where did the file, manifest, prompt, archive, or dependency come from?
- Impact: code execution, data leakage, supply chain, or resource consumption?
- Control: allowlist, hash, sandbox, egress policy, or secret rotation?
- Evidence: does the same rule category return clean after the fix?
Remediation
Remediation should change the risk boundary, not merely silence the finding: remove executable formats, pin source or hash, narrow tool permissions, rotate secrets, or add runtime sandboxing.
CI policy
category: TORCH
fail_on:
- CRITICAL
- HIGH
ticket_on:
- MEDIUM
retest: "sentinel artifact ./models/ --rule TORCH"Rule index
| Rule ID | Severity | Title | CWE | Fix Hint |
|---|---|---|---|---|
| TORCH-LOAD-UNTRUSTED | CRITICAL | Untrusted torch.load Deserialization | CWE-502 | Load tensors, not executable Python objects. |
| TORCH-SCRIPT-CUSTOM-OP | HIGH | TorchScript Custom Operator | CWE-94CWE-829 | Review and sign custom operators before promotion. |
| TORCH-HUB-DYNAMIC-IMPORT | MEDIUM | Dynamic Torch Hub Import | CWE-829CWE-494 | Replace remote hub execution with pinned, vendored model code. |
TORCH-LOAD-UNTRUSTED — Untrusted torch.load Deserialization
CRITICAL| Rule ID | TORCH-LOAD-UNTRUSTED |
|---|---|
| Category | TORCH |
| Severity | CRITICAL |
| CWE | CWE-502 |
| OWASP LLM | LLM03 — Supply Chain |
| FP Risk | MEDIUM |
| Owner | AI/ML platform or model release owner |
| Release decision | Block release; do not promote the artifact or code path until it is isolated. |
Description
Flags code or artifacts that rely on torch.load for untrusted checkpoints without weights_only or an equivalent safe loader path.
Why it matters
PyTorch checkpoints commonly wrap pickle data. TorchScript and hub workflows can also execute native or Python code outside the model graph.
When it fires
Sentinel fires this rule in the TORCH category when it sees ast call expression torch.load(...) without weights_only=true or artifact metadata showing pickle-backed checkpoint loading.. The finding should be reported with reproducible evidence such as file name, metadata, opcode, AST node, or manifest field.
Evidence format
AST call expression torch.load(...) without weights_only=True or artifact metadata showing pickle-backed checkpoint loading.
Expected evidence
The report should include the affected file or manifest path, observed signal, rule ID, severity, owner, and retest command required for closure.
False-positive notes
False-positive probability is medium. Verify source, expected use, and owner first; add an allowlist if needed, but do not remove evidence from the report.
Triage
- Owner: AI/ML platform or model release owner.
- Decision: Block release; do not promote the artifact or code path until it is isolated.
- Evidence: AST call expression torch.load(...) without weights_only=True or artifact metadata showing pickle-backed checkpoint loading.
- Closure: sentinel artifact ./models/ --rule TORCH must return clean output.
How to fix
Use weights_only=True where supported, load signed state_dict files, and block arbitrary object checkpoint loading in CI.
CLI
sentinel artifact ./models/ --rule TORCHPolicy example
rules:
TORCH-LOAD-UNTRUSTED:
owner: "AI/ML platform or model release owner"
fail_on: ["CRITICAL", "HIGH"]
retest: "sentinel artifact ./models/ --rule TORCH"Expected output
TORCH-LOAD-UNTRUSTED CRITICAL
Untrusted torch.load Deserialization
Load tensors, not executable Python objects.Example
import torch
model = torch.load("checkpoint.pt")import torch
state = torch.load("weights.pt", weights_only=True)
model.load_state_dict(state)Related rules
- TORCH-SCRIPT-CUSTOM-OP: TorchScript Custom Operator
- TORCH-HUB-DYNAMIC-IMPORT: Dynamic Torch Hub Import
TORCH-SCRIPT-CUSTOM-OP — TorchScript Custom Operator
HIGH| Rule ID | TORCH-SCRIPT-CUSTOM-OP |
|---|---|
| Category | TORCH |
| Severity | HIGH |
| CWE | CWE-94CWE-829 |
| OWASP LLM | LLM03 — Supply Chain |
| FP Risk | MEDIUM |
| Owner | AI/ML platform or model release owner |
| Release decision | Treat as a release gate; remediation or explicit risk acceptance is required. |
Description
Detects TorchScript graphs or model metadata referencing custom native operators that can introduce unreviewed execution behavior.
Why it matters
PyTorch checkpoints commonly wrap pickle data. TorchScript and hub workflows can also execute native or Python code outside the model graph.
When it fires
Sentinel fires this rule in the TORCH category when it sees aten/custom namespace references, shared-library load hints, or operator names outside the expected torch allowlist.. The finding should be reported with reproducible evidence such as file name, metadata, opcode, AST node, or manifest field.
Evidence format
aten/custom namespace references, shared-library load hints, or operator names outside the expected torch allowlist.
Expected evidence
The report should include the affected file or manifest path, observed signal, rule ID, severity, owner, and retest command required for closure.
False-positive notes
False-positive probability is medium. Verify source, expected use, and owner first; add an allowlist if needed, but do not remove evidence from the report.
Triage
- Owner: AI/ML platform or model release owner.
- Decision: Treat as a release gate; remediation or explicit risk acceptance is required.
- Evidence: aten/custom namespace references, shared-library load hints, or operator names outside the expected torch allowlist.
- Closure: sentinel artifact ./models/ --rule TORCH must return clean output.
How to fix
Inventory the operator source, require signed native extensions, and load the model in a sandboxed environment.
CLI
sentinel artifact ./models/ --rule TORCHPolicy example
rules:
TORCH-SCRIPT-CUSTOM-OP:
owner: "AI/ML platform or model release owner"
fail_on: ["CRITICAL", "HIGH"]
retest: "sentinel artifact ./models/ --rule TORCH"Expected output
TORCH-SCRIPT-CUSTOM-OP HIGH
TorchScript Custom Operator
Review and sign custom operators before promotion.Example
import torch
model = torch.load("checkpoint.pt")import torch
state = torch.load("weights.pt", weights_only=True)
model.load_state_dict(state)Related rules
- TORCH-LOAD-UNTRUSTED: Untrusted torch.load Deserialization
- TORCH-HUB-DYNAMIC-IMPORT: Dynamic Torch Hub Import
TORCH-HUB-DYNAMIC-IMPORT — Dynamic Torch Hub Import
MEDIUM| Rule ID | TORCH-HUB-DYNAMIC-IMPORT |
|---|---|
| Category | TORCH |
| Severity | MEDIUM |
| CWE | CWE-829CWE-494 |
| OWASP LLM | LLM03 — Supply Chain |
| FP Risk | MEDIUM |
| Owner | AI/ML platform or model release owner |
| Release decision | Assign an owner, fix within the sprint, and attach the retest command to the issue. |
Description
Finds hub loading flows that fetch and import model code from mutable remote repositories.
Why it matters
PyTorch checkpoints commonly wrap pickle data. TorchScript and hub workflows can also execute native or Python code outside the model graph.
When it fires
Sentinel fires this rule in the TORCH category when it sees torch.hub.load with branch names, unpinned refs, or trust_repo bypasses.. The finding should be reported with reproducible evidence such as file name, metadata, opcode, AST node, or manifest field.
Evidence format
torch.hub.load with branch names, unpinned refs, or trust_repo bypasses.
Expected evidence
The report should include the affected file or manifest path, observed signal, rule ID, severity, owner, and retest command required for closure.
False-positive notes
False-positive probability is medium. Verify source, expected use, and owner first; add an allowlist if needed, but do not remove evidence from the report.
Triage
- Owner: AI/ML platform or model release owner.
- Decision: Assign an owner, fix within the sprint, and attach the retest command to the issue.
- Evidence: torch.hub.load with branch names, unpinned refs, or trust_repo bypasses.
- Closure: sentinel artifact ./models/ --rule TORCH must return clean output.
How to fix
Pin a commit SHA, mirror trusted code internally, and review hubconf.py before execution.
CLI
sentinel artifact ./models/ --rule TORCHPolicy example
rules:
TORCH-HUB-DYNAMIC-IMPORT:
owner: "AI/ML platform or model release owner"
fail_on: ["CRITICAL", "HIGH"]
retest: "sentinel artifact ./models/ --rule TORCH"Expected output
TORCH-HUB-DYNAMIC-IMPORT MEDIUM
Dynamic Torch Hub Import
Replace remote hub execution with pinned, vendored model code.Example
import torch
model = torch.load("checkpoint.pt")import torch
state = torch.load("weights.pt", weights_only=True)
model.load_state_dict(state)Related rules
- TORCH-LOAD-UNTRUSTED: Untrusted torch.load Deserialization
- TORCH-SCRIPT-CUSTOM-OP: TorchScript Custom Operator