Safeguard
AI Security•

How do I find model files hiding in repos and artifact stores?

List model weight files by extension across repos, buckets and registries, then check the format. Pickle based files can run code when loaded. Steps.

Safeguard Security Team
4 min read

Search repos, object storage and artifact registries for common model file extensions, then record each file's format, source and owner. Pay first attention to pickle based formats, because loading them can execute code. Files that were downloaded from a public hub and never reviewed are the usual shadow AI finding.

Why model files count as shadow dependencies

A model file is code-adjacent data your application loads at runtime. It came from somewhere, someone chose it, and it will change how your product behaves. If nobody wrote that down, it is a dependency with no record.

Hugging Face's security documentation explains the sharpest risk. Pickle is a widely used serialization format in machine learning, and it is the default format for PyTorch model weights. Loading a pickle can run arbitrary code, so the documentation advises loading models only from users and organizations you trust. It also describes safetensors as a simpler serialization format intended to avoid this.

OWASP adds that published models carry no strong provenance guarantees and that static inspection of a model offers little assurance, which is why recording origin and hashes matters.

Step 1: list candidate files

Start with extensions. These are common, not exhaustive, so check what your own teams use:

ExtensionUsually means
.pkl, .picklePython pickle, can execute code on load
.pt, .pth, .binOften PyTorch weights, frequently pickle based
.safetensorsSafetensors weights
.ggufA quantized model format used by local runners
.onnxONNX model
.h5, .kerasKeras models

Search each repo, including history, since a file removed last month may still be in the object store. Large files often live outside git, so also list your object storage buckets, container images and artifact registries.

git ls-files | grep -E '\.(pkl|pickle|pt|pth|bin|safetensors|gguf|onnx|h5|keras)$'

Step 2: look for load calls

A file in a bucket matters only if something loads it. Search code for model loading calls and for downloads from a model hub, and note the model identifier each one uses. A model identifier in code is an inventory entry even when no file is committed.

Step 3: record the minimum

For each model, record:

  1. Name and version or revision.
  2. Where it came from (public hub, internal training, a vendor).
  3. File format.
  4. A hash of the file.
  5. Who owns it and which service loads it.
  6. License, as noted by its source.

A one-page intake record keeps this consistent. See a one page model intake record.

Step 4: reduce the risky formats

Where you can choose, prefer formats that do not execute code on load. Where you cannot, load only from sources you trust, pin the revision, and keep the hash. Hugging Face notes that its Hub pickle scan is not foolproof, so treat a scan result as one input, not a clearance. For a deeper look, see can you sign pickle files with HMAC for internal model handoffs.

Quick check

Is a .bin file always a pickle?

No. The extension is a hint, not proof. Check the loader that reads it and the format documentation of its source.

Do models called over an API need this?

They need an inventory entry too, but there is no file to find. See do you need an AI BOM entry for a model you only call through an API.

Safeguard offers asset discovery and SBOM and dependency scanning, and you can try a free scan at gold.safeguard.sh/scan.

Sources

Last reviewed: 19 October 2026.

Never miss an update

Weekly insights on software supply chain security, delivered to your inbox.

Self-healing security runs on Safeguard.

Your first fix PR is minutes away.

No sales call required, even your agent can complete the purchase over MCP.