Repository navigation
fix(agent-hypervisor): prevent path traversal and prefix collision in session isolation - #4356
Vardhman Gupta (Kaap10) wants to merge 3 commits into
Conversation
… session isolation Normalize paths using posixpath.normpath and enforce directory hierarchy containment in SessionScope.is_path_allowed. Add regression tests covering relative segment breakouts, sibling directory prefix collisions, nested subdirectories, and granted cross-session boundaries. Fixes microsoft#4355 Signed-off-by: Vardhman Gupta <[email protected]>
|
Azure Pipelines: There may be pipelines that require an authorized user to comment /azp run to run. |
PR Review Summary
Verdict: AI review comments are untrusted advisory output. The summary reports workflow-generated completion status only, not model-authored pass/fail claims. |
|
🔴 Contributor Check: HIGH
Automated check by AGT Contributor Check. |
MohammadHaroonAbuomar
left a comment
There was a problem hiding this comment.
- Thank you for the report and the fix. I verified both bugs on main and confirmed the fix closes them: traversal through
..and sibling-prefix collisions are denied, nested paths and the exact directory are still allowed, the granted-session path gets the same containment check, and three of the four new tests fail on main and pass here. The hypervisor suite passes locally (667 passed).
Three things before I can approve:
-
Scope widening through the session or granted id.
_is_path_containednormalizes the base directory as well as the target, so an id containing..or/now widens the scope instead of matching nothing. I reproduced it on this head:SessionScope(session_id="..", agent_did=..., base_path="/var/agt/sessions")has working directory/var/agt/sessions/..andis_path_allowed("/var/agt/secret")returns True (main returns False);session_id="s/../other"allows/var/agt/sessions/other/x; andgrant_cross_session_access("s1", "..")under READ_COMMITTED grants every sibling session. Ids come from the control plane rather than the agent, but the change turns a formerly inert misconfiguration into a wide grant. Please either require the normalized working and granted directories to sit strictly insideposixpath.normpath(self.base_path), or reject ids that contain/or equal.or..increate_scopeandgrant_access, and add a test for each case. -
PR template. Please use the repository template for the description: Type of Change, Package(s) Affected, Testing and Checklist sections, and the AI Assistance and IP attestations (with a note on any AI tools used).
-
CHANGELOG. Please add an entry to the root
CHANGELOG.mdunder## [Unreleased]>### Fixed, in the style of the existing Hypervisor entries, naming both bugs and the two behaviour changes that come with the fix: a relativebase_pathand the session parent directory (.../session-1/..) are now denied.
Optional: run ruff format on tests/test_session_isolation.py (three create_scope(...) lines exceed 100 columns), and a docstring note that the check is a string containment test and does not resolve symlinks would help future readers.
The gated CI workflows for first-time contributors need a maintainer to approve them before they run; that is not on you.
…entifiers Reject traversal identifiers in create_scope and grant_access, ensure working directories remain strictly inside base_path, add CHANGELOG entry, and expand regression tests. Addresses review on microsoft#4356. Signed-off-by: Vardhman Gupta <[email protected]>
|
Hi MohammadHaroonAbuomar, Thanks for the review!
All 26 isolation tests and Section 11 conformance tests pass locally, with |
All three asks are addressed on 9aec40d. I re-ran my probe against this head: a session id of '..' or 's/../other' and an empty id are denied, create_scope and grant_access reject such ids, grant_cross_session_access returns False for them, and the normal cases (traversal denied, sibling prefix denied, nested and exact paths allowed) are unchanged. The description now follows the template with attestations, and the changelog entry names both bugs and the behaviour changes. Hypervisor suite passes locally (670 passed), ruff check and ruff format are clean. Nothing left to fix. The gated CI workflows for first-time contributors still need a maintainer to approve them; once they run green I will approve and merge.
|
Gentle reminder when you have a moment - could you please approve and trigger the gated CI workflows for this PR so they can run? Everything is ready to go. Thanks! |
|
Thanks for the reminder. Gated CI runs on a first contribution are approved by a maintainer by hand; I have flagged this one and will come back once they have run. |
|
Hi MohammadHaroonAbuomar liamcrumm, Checking in gently to see if someone could please approve the gated CI workflows for this PR when you have a moment. Also, please let me know if it's alright for me to pick up and work on another issue in the meantime, or if you prefer I wait until this PR is merged first. Thanks for your time and guidance! |
|
Vardhman Gupta (@Kaap10) thanks for the patience. The gated runs on a first contribution need a maintainer with the right permission, and this one is in the queue; I will make sure it is not forgotten. Please do pick up another issue in the meantime, no need to wait on this one. |
Related Issue
Fixes #4355
Type of Change
Package(s) Affected
Core & runtime:
Governance & security:
Platform & tooling:
CLI plugins:
Shared / other:
Testing
Unit Testing
tests/test_session_isolation.py:test_path_traversal_with_relative_segments_denied: verifies..traversal escapes (/var/agt/sessions/session-1/../session-2/data.jsonand.../../../etc/passwd) are denied.test_sibling_prefix_collision_denied: verifies sibling prefix collision attempts (session-1-extra,session-10) are denied.test_nested_subdirectories_allowed: verifies authorized paths within own working directory remain allowed.test_granted_session_relative_traversal_denied: verifies traversal outside granted cross-session scope is denied.test_scope_widening_via_traversal_session_id_denied: verifiessession_id=".."andsession_id="s/../other"cannot widen access to parent directory or other scopes.test_create_scope_invalid_session_ids_rejected: verifiescreate_scoperaisesValueErroron traversal/slash identifiers (..,.,s/../other,foo/bar,"").test_grant_access_invalid_session_ids_rejected: verifiesgrant_cross_session_accessreturnsFalseandSessionScope.grant_accessraisesValueErroron invalid session identifiers.tests/test_spec_hypervisor_conformance.pySection 11 session isolation conformance tests pass.Manual Testing
Checklist
Attribution & Prior Art
Prior art / related projects (if any):
None
AI Assistance
If AI tools materially shaped this change, briefly note what was used:
Antigravity for implementation assistance and review response — all code, tests, and diffs reviewed and verified by author.
IP, Patents, and Licensing