mirror of
https://github.com/leonvanzyl/autocoder.git
synced 2026-01-30 06:12:06 +00:00
security: validate all pkill patterns for BSD compatibility
pkill on BSD systems accepts multiple pattern operands. Previous code only validated args[-1], allowing disallowed processes to slip through when combined with allowed ones (e.g., "pkill node sshd" would only check "sshd"). Now validates every non-flag argument to ensure no disallowed process can be targeted. Added tests for multiple pattern scenarios. Addresses CodeRabbit feedback on PR #101. Co-Authored-By: Claude Opus 4.5 <noreply@anthropic.com>
This commit is contained in:
18
security.py
18
security.py
@@ -273,15 +273,17 @@ def validate_pkill_command(
|
|||||||
if not args:
|
if not args:
|
||||||
return False, "pkill requires a process name"
|
return False, "pkill requires a process name"
|
||||||
|
|
||||||
# The target is typically the last non-flag argument
|
# Validate every non-flag argument (pkill accepts multiple patterns on BSD)
|
||||||
target = args[-1]
|
# This defensively ensures no disallowed process can be targeted
|
||||||
|
targets = []
|
||||||
|
for arg in args:
|
||||||
|
# For -f flag (full command line match), take the first word as process name
|
||||||
|
# e.g., "pkill -f 'node server.js'" -> target is "node server.js", process is "node"
|
||||||
|
t = arg.split()[0] if " " in arg else arg
|
||||||
|
targets.append(t)
|
||||||
|
|
||||||
# For -f flag (full command line match), extract the first word as process name
|
disallowed = [t for t in targets if t not in allowed_process_names]
|
||||||
# e.g., "pkill -f 'node server.js'" -> target is "node server.js", process is "node"
|
if not disallowed:
|
||||||
if " " in target:
|
|
||||||
target = target.split()[0]
|
|
||||||
|
|
||||||
if target in allowed_process_names:
|
|
||||||
return True, ""
|
return True, ""
|
||||||
return False, f"pkill only allowed for processes: {sorted(allowed_process_names)}"
|
return False, f"pkill only allowed for processes: {sorted(allowed_process_names)}"
|
||||||
|
|
||||||
|
|||||||
@@ -876,6 +876,34 @@ pkill_processes:
|
|||||||
print(" FAIL: Process name with space should be rejected")
|
print(" FAIL: Process name with space should be rejected")
|
||||||
failed += 1
|
failed += 1
|
||||||
|
|
||||||
|
# Test 12: Multiple patterns - all must be allowed (BSD behavior)
|
||||||
|
# On BSD, "pkill node sshd" would kill both, so we must validate all patterns
|
||||||
|
allowed, reason = validate_pkill_command("pkill node npm")
|
||||||
|
if allowed:
|
||||||
|
print(" PASS: Multiple allowed patterns accepted")
|
||||||
|
passed += 1
|
||||||
|
else:
|
||||||
|
print(f" FAIL: Multiple allowed patterns should be accepted: {reason}")
|
||||||
|
failed += 1
|
||||||
|
|
||||||
|
# Test 13: Multiple patterns - block if any is disallowed
|
||||||
|
allowed, reason = validate_pkill_command("pkill node sshd")
|
||||||
|
if not allowed:
|
||||||
|
print(" PASS: Multiple patterns blocked when one is disallowed")
|
||||||
|
passed += 1
|
||||||
|
else:
|
||||||
|
print(" FAIL: Should block when any pattern is disallowed")
|
||||||
|
failed += 1
|
||||||
|
|
||||||
|
# Test 14: Multiple patterns - only first allowed, second disallowed
|
||||||
|
allowed, reason = validate_pkill_command("pkill npm python")
|
||||||
|
if not allowed:
|
||||||
|
print(" PASS: Multiple patterns blocked (first allowed, second not)")
|
||||||
|
passed += 1
|
||||||
|
else:
|
||||||
|
print(" FAIL: Should block when second pattern is disallowed")
|
||||||
|
failed += 1
|
||||||
|
|
||||||
return passed, failed
|
return passed, failed
|
||||||
|
|
||||||
|
|
||||||
|
|||||||
Reference in New Issue
Block a user