fix(model_conversion): use weights_only=True in OptimizationConverter (CWE-502)#98
Open
sebastiondev wants to merge 1 commit into
Open
Conversation
… (CWE-502) OptimizationConverter.convert/validate/get_metadata call torch.load() without passing weights_only. On PyTorch < 2.6 the default was weights_only=False, which pickle-deserializes the input file and executes any __reduce__ payload it contains. The repo pins only torch>=2.0.0, so this reaches RCE on any 2.0.x–2.5.x runtime whenever the checkpoint path is not fully trusted (e.g., a downloaded snapshot, a shared model registry, an uploaded checkpoint, or a pipeline stage consuming a converter's output). Route all three call sites through a small _safe_torch_load() helper that passes weights_only=True explicitly. This restricts unpickling to tensor/storage/primitive types on every supported torch version and refuses arbitrary class instances at load time. No API changes.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
What does this PR do?
Fixes an insecure deserialization (CWE-502) vulnerability in
multimind/model_conversion/optimization.py. TheOptimizationConverterclass loaded PyTorch checkpoints viatorch.load(model_path)in three places (convert,validate,get_metadata) without passingweights_only=True. On PyTorch < 2.6 — which is permitted by the SDK'storch>=2.0.0pin —torch.loaddefaults to full pickle deserialization, so a crafted.ptfile executes arbitrary Python (RCE) the moment it is opened.All three call sites now route through a small helper,
_safe_torch_load, which passesweights_only=Trueexplicitly. This restricts unpickling to an allow-list of tensor / storage / primitive types and rejects__reduce__-based payloads, independent of the user's installed torch version.Vulnerability summary
multimind/model_conversion/optimization.py—OptimizationConverter.convert,.validate,.get_metadatamodel_pathtoOptimizationConverter— e.g. checkpoints pulled from a shared model registry, user-uploaded files in a pipeline, or a downloaded pretrained modelFix rationale
weights_only=Trueis the upstream-recommended mitigation (see PyTorch security advisory GHSA-pg7h-5qx3-wjr3 and thetorch.loaddocs).torch>=2.0.0pin to>=2.6, because that would be a breaking change for users on older Python / CUDA combinations. Passing the flag explicitly gives safe behaviour on every supported torch version.Proof of concept
Reproduces on any environment with
torch<2.6installed (e.g.pip install "torch==2.5.1"):After the fix, the same call raises
pickle.UnpicklingError: Weights only load failed ... GLOBAL posix.system is forbidden, no file is created, andvalidatereturnsFalsevia its existingexcept Exceptionguard.convertandget_metadatasimilarly refuse the payload instead of executing it.Testing
torch==2.5.1against the pre-fix code (marker file created).UnpicklingErrorontorch==2.5.1andtorch==2.2.2.state_dictcheckpoint (torch.save(model.state_dict(), ...)) still succeeds through_safe_torch_load.git diff --statshows a single file changed, +21/-3 — no unrelated edits.Adversarial review
Before submitting we tried to disprove the finding. The pinned range
torch>=2.0.0inrequirements.txtreally does allow vulnerable versions (2.0–2.5), andtorch.load'sweights_onlydefault isFalseon all of them; upgrading torch alone is not a mitigation the SDK can rely on. There is no sanitisation betweenmodel_pathandtorch.load, andvalidate'sexcept Exceptionswallows the unpickling error but only after pickle has already executed the payload, so it does not prevent RCE. We also checked thatOptimizationConverteris part of the public conversion API (exposed viamultimind.model_conversion) and reachable from user-supplied paths, not just internal fixtures.Checklist
Discovered by the Sebastion AI GitHub App.