From 4d19d72f605f40356c8763b90c899618cbe64082 Mon Sep 17 00:00:00 2001 From: "google-labs-jules[bot]" <161369871+google-labs-jules[bot]@users.noreply.github.com> Date: Mon, 8 Jun 2026 17:34:15 +0000 Subject: [PATCH] =?UTF-8?q?=F0=9F=9B=A1=EF=B8=8F=20Sentinel:=20[CRITICAL]?= =?UTF-8?q?=20Fix=20arbitrary=20code=20execution=20vulnerability=20in=20AS?= =?UTF-8?q?T=20evaluation?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Co-authored-by: bashandbone <89049923+bashandbone@users.noreply.github.com> --- .jules/sentinel.md | 5 +++++ src/codeweaver/core/di/container.py | 25 +++++++++++++++++++++++++ 2 files changed, 30 insertions(+) diff --git a/.jules/sentinel.md b/.jules/sentinel.md index 1959a5253..a2b90a415 100644 --- a/.jules/sentinel.md +++ b/.jules/sentinel.md @@ -4,3 +4,8 @@ **Vulnerability:** Found an unused `_attempt_import` function in `src/codeweaver/server/mcp/server.py` that dynamically imports a module directly from unvalidated configuration (`import_module(mw.rsplit(".", 1)[0])`), leading to potential arbitrary code execution. **Learning:** Functions that perform dynamic imports should not be left around in the codebase if they are unused, especially if they are designed to take unvalidated strings as input. **Prevention:** Avoid dynamic imports based on configuration or inputs without strict whitelisting. Use tools like `semgrep` with python security rules to actively catch these patterns. + +## 2026-04-21 - Restrict arbitrary Call nodes in AST dynamic evaluation +**Vulnerability:** The type validation logic using `ast.parse(type_str, mode="eval")` allowed generic `ast.Call` nodes to pass. Even though standard Python literal types were blocked, any accessible callable within the execution environment's scope could be arbitrarily executed, leading to a critical Arbitrary Code Execution (ACE) vulnerability during type resolution. +**Learning:** Permitting generic `ast.Call` nodes in type validation allows unauthorized function execution. Allowed AST nodes must be restricted to their expected forms and specific callable identifiers (e.g., `Depends`, `Field`) must be hardcoded or whitelisted. +**Prevention:** Explicitly restrict allowed callables in the `TypeValidator` to a predefined whitelist instead of broadly allowing the `ast.Call` class. Implement rigorous AST node visitation checks that explicitly validate both `node.func.id` and `node.func.attr`. diff --git a/src/codeweaver/core/di/container.py b/src/codeweaver/core/di/container.py index 7cd68ce98..b71296394 100644 --- a/src/codeweaver/core/di/container.py +++ b/src/codeweaver/core/di/container.py @@ -136,6 +136,31 @@ def generic_visit(self, node: ast.AST) -> None: if isinstance(node, ast.Attribute) and node.attr.startswith("__"): raise TypeError(f"Forbidden dunder attribute: {node.attr}") + # Restricting generic ast.Call nodes prevents arbitrary code execution vulnerabilities + # by only permitting safe, expected callables. + if isinstance(node, ast.Call): + # Check if the callable is one of the explicitly allowed functions + is_allowed = False + if (isinstance(node.func, ast.Name) and node.func.id in { + "Depends", + "depends", + "Field", + "PrivateAttr", + "Tag", + "Parameter", + }) or (isinstance(node.func, ast.Attribute) and node.func.attr in { + "Depends", + "depends", + "Field", + "PrivateAttr", + "Tag", + "Parameter", + }): + is_allowed = True + + if not is_allowed: + raise TypeError("Forbidden function call in type string.") + super().generic_visit(node) try: