Files
mukul975 27c6414ca5 Add folder anatomy (scripts/agent.py + references/api-reference.md) for 648 cybersecurity skills
Complete skill folder anatomy across all cybersecurity skills:
- scripts/agent.py: 80-150 line Python agents using real libraries (impacket,
  boto3, azure-mgmt-*, kubernetes, pefile, yara, scapy, shodan, stix2, etc.)
- references/api-reference.md: real API documentation with method signatures
- LICENSE: MIT license for all skill folders
2026-03-10 21:02:12 +01:00

174 lines
6.8 KiB
Python

#!/usr/bin/env python3
"""
Kubernetes Pod Privilege Escalation Detection Agent
Audits Kubernetes pods for privilege escalation risks including privileged
containers, host namespace access, and dangerous capabilities.
Authorized security monitoring use only.
"""
import argparse
import json
import sys
from datetime import datetime, timezone
from kubernetes import client, config
DANGEROUS_CAPABILITIES = [
"SYS_ADMIN", "SYS_PTRACE", "NET_ADMIN", "NET_RAW",
"DAC_OVERRIDE", "SETUID", "SETGID", "SYS_RAWIO",
]
def load_k8s_config(kubeconfig=None, in_cluster=False):
"""Load Kubernetes configuration."""
if in_cluster:
config.load_incluster_config()
else:
config.load_kube_config(config_file=kubeconfig)
def audit_pod_security(namespace=None):
"""Audit pods for privilege escalation vectors."""
v1 = client.CoreV1Api()
if namespace:
pods = v1.list_namespaced_pod(namespace)
else:
pods = v1.list_pod_for_all_namespaces()
findings = []
for pod in pods.items:
pod_name = pod.metadata.name
pod_ns = pod.metadata.namespace
for container in (pod.spec.containers or []):
sc = container.security_context
if not sc:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"container": container.name,
"issue": "no_security_context",
"severity": "medium",
"detail": "Container has no security context defined",
})
continue
if sc.privileged:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"container": container.name,
"issue": "privileged_container",
"severity": "critical",
"detail": "Container runs in privileged mode",
})
if sc.allow_privilege_escalation is not False:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"container": container.name,
"issue": "allow_privilege_escalation",
"severity": "high",
"detail": "allowPrivilegeEscalation is not explicitly set to false",
})
if sc.run_as_user == 0 or (sc.run_as_non_root is not True and not sc.run_as_user):
findings.append({
"pod": pod_name, "namespace": pod_ns,
"container": container.name,
"issue": "runs_as_root",
"severity": "high",
"detail": "Container may run as root",
})
if sc.capabilities and sc.capabilities.add:
dangerous = [c for c in sc.capabilities.add if c in DANGEROUS_CAPABILITIES]
if dangerous:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"container": container.name,
"issue": "dangerous_capabilities",
"severity": "high",
"detail": f"Dangerous capabilities: {dangerous}",
})
spec = pod.spec
if spec.host_pid:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"issue": "host_pid_namespace", "severity": "critical",
"detail": "Pod shares host PID namespace",
})
if spec.host_network:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"issue": "host_network", "severity": "high",
"detail": "Pod shares host network namespace",
})
if spec.host_ipc:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"issue": "host_ipc", "severity": "high",
"detail": "Pod shares host IPC namespace",
})
for vol in (spec.volumes or []):
if vol.host_path:
findings.append({
"pod": pod_name, "namespace": pod_ns,
"issue": "host_path_volume",
"severity": "high",
"detail": f"hostPath volume: {vol.host_path.path}",
})
return findings
def audit_rbac_escalation(namespace=None):
"""Check RBAC for privilege escalation paths."""
rbac = client.RbacAuthorizationV1Api()
findings = []
if namespace:
bindings = rbac.list_namespaced_role_binding(namespace)
else:
bindings = rbac.list_cluster_role_binding()
for binding in bindings.items:
role_ref = binding.role_ref
if role_ref.name in ("cluster-admin", "admin", "edit"):
for subject in (binding.subjects or []):
if subject.kind == "ServiceAccount":
findings.append({
"binding": binding.metadata.name,
"role": role_ref.name,
"subject": f"{subject.namespace}/{subject.name}",
"issue": "overprivileged_service_account",
"severity": "high",
"detail": f"ServiceAccount bound to {role_ref.name}",
})
return findings
def generate_report(pod_findings, rbac_findings):
"""Generate Kubernetes privilege escalation report."""
all_findings = pod_findings + rbac_findings
return {
"report_title": "Kubernetes Privilege Escalation Detection",
"generated_at": datetime.now(timezone.utc).isoformat(),
"total_findings": len(all_findings),
"critical": len([f for f in all_findings if f.get("severity") == "critical"]),
"high": len([f for f in all_findings if f.get("severity") == "high"]),
"pod_findings": pod_findings,
"rbac_findings": rbac_findings,
}
if __name__ == "__main__":
parser = argparse.ArgumentParser(description="Detect K8s pod privilege escalation")
parser.add_argument("--namespace", "-n", help="Kubernetes namespace to audit")
parser.add_argument("--kubeconfig", help="Path to kubeconfig file")
parser.add_argument("--in-cluster", action="store_true", help="Use in-cluster config")
parser.add_argument("--output", default="k8s_privesc_audit.json", help="Output file")
args = parser.parse_args()
load_k8s_config(args.kubeconfig, args.in_cluster)
print("[*] Auditing pod security contexts...")
pod_findings = audit_pod_security(args.namespace)
print("[*] Auditing RBAC bindings...")
rbac_findings = audit_rbac_escalation(args.namespace)
report = generate_report(pod_findings, rbac_findings)
with open(args.output, "w") as f:
json.dump(report, f, indent=2)
print(json.dumps(report, indent=2))