{"slug": "mini-shai-hulud-tanstack-mistral-ai-supply-chain-audit-script", "title": "Mini Shai-Hulud / TanStack + Mistral AI supply-chain audit script", "summary": "A developer has released an open-source supply-chain audit script, \"Mini Shai-Hulud,\" designed to detect the TanStack Router and Mistral AI supply-chain attacks. The bash script checks for specific SHA hashes, malicious commits, and known command-and-control infrastructure associated with the incidents. It scans project directories and lockfiles for indicators of compromise, including trojanized tarballs and persistence mechanisms.", "body_md": "| #!/usr/bin/env bash | |\n| # | |\n| # Mini Shai-Hulud / TanStack + Mistral AI supply-chain audit script | |\n| # | |\n| # chmod +x tanstack_mistral_audit_public.sh | |\n| # ./tanstack_mistral_audit_public.sh | |\n| # sudo ./tanstack_mistral_audit_public.sh | |\n| # ./tanstack_mistral_audit_public.sh /path/to/project /tmp | |\n| set -uo pipefail | |\n| RED='' | |\n| GREEN='' | |\n| YELLOW='' | |\n| NC='' | |\n| if [[ -t 1 && -z \"${NO_COLOR:-}\" ]]; then | |\n| RED=$'\\033[0;31m' | |\n| GREEN=$'\\033[0;32m' | |\n| YELLOW=$'\\033[1;33m' | |\n| NC=$'\\033[0m' | |\n| fi | |\n| SCRIPT_VERSION=\"2026-05-12-public\" | |\n| ROUTER_INIT_SHA=\"ab4fcadaec49c03278063dd269ea5eef82d24f2124a8e15d7b90f2fa8601266c\" | |\n| TANSTACK_RUNNER_SHA=\"2ec78d556d696e208927cc503d48e4b5eb56b31abc2870c2ed2e98d6be27fc96\" | |\n| TANSTACK_SETUP_PACKAGE_SHA=\"7c12d8614c624c70d6dd6fc2ee289332474abaa38f70ebe2cdef064923ca3a9b\" | |\n| SETUP_MJS_SHA=\"2258284d65f63829bd67eaba01ef6f1ada2f593f9bbe41678b2df360bd90d3df\" | |\n| TANSTACK_TROJANIZED_TARBALL_SHA=\"1e8538c6e0563d50da0f2e097e979ebd5294ce1defe01d0b9fe361ba3bed1898\" | |\n| MALICIOUS_COMMIT=\"79ac49eedf774dd4b0cfa308722bc463cfe5885c\" | |\n| MALICIOUS_SETUP_SPEC=\"github:tanstack/router#${MALICIOUS_COMMIT}\" | |\n| SESSION_RECIPIENT_ID=\"05f9e609d79eed391015e11380dee4b5c9ead0b6e2e7f0134e6e51767a87323026\" | |\n| PYPI_MISTRAL_C2=\"83.142.209.194\" | |\n| PYPI_MISTRAL_ENV_MARKER=\"MISTRAL_INIT\" | |\n| PYPI_PAYLOAD_DOMAIN=\"git-tanstack.com\" | |\n| PYPI_PAYLOAD_URL_PATH=\"tmp/transformers.pyz\" | |\n| PYPI_SECOND_STAGE=\"transformers.pyz\" | |\n| PYPI_SECOND_STAGE_ABS=\"/tmp/transformers.pyz\" | |\n| PYPI_PERSISTENCE_SCRIPT=\"pgmonitor.py\" | |\n| PYPI_PERSISTENCE_SERVICE=\"pgsql-monitor.service\" | |\n| GUARDRAILS_AI_0101_SDIST_SHA=\"8491b17dc16f31c27f290b3b1e0f2e8866cc775828590e90376ecfb0cc1f8d9c\" | |\n| GUARDRAILS_AI_0101_WHEEL_SHA=\"b76c800a685c0376a668170b000ba1e5a5ac7daeb714a6af97eac2d31d9a8dbc\" | |\n| MISTRALAI_246_WHEEL_SHA=\"6dbaa43bf2f3c0d3cddbca74967e952da563fb974c1ef9d4ecbb2e58e41fe81b\" | |\n| MISTRALAI_246_STAGE1_INIT_SHA=\"2a314ea8be337e1ca9ec833ed13ed854d9fd38bce0a519cf288f3bec8d9e6f30\" | |\n| MISTRALAI_246_TRANSFORMERS_PYZ_SHA=\"eab7964658dd6ad28cb581d979837cfbf4690c582e0c507e965060defbb89d1b\" | |\n| MISTRALAI_246_STAGE2_MAIN_SHA=\"59811e589b0caa202e63a07c61129d58443fe8911545fdb3ed9264f8628d68e5\" | |\n| MISTRALAI_246_STAGE2_AGGREGATE_SHA=\"eeee34f2db5cb3eb5e5877c93e2250d44128c470d24fad38885bbfdab452de09\" | |\n| MISTRALAI_246_STAGE2_CONFIG_SHA=\"714152c0489c3d8d9196305efa12a6850e5d460ab62ff3be91caf3fb852ec793\" | |\n| MISTRALAI_246_STAGE2_ENTRYPOINT_SHA=\"e9d0fefa8efc50e4fa9a84375780bef9590dfd60968757a35158ba0d45e265b1\" | |\n| MISTRALAI_246_STAGE2_ROULETTE_SHA=\"5774ad8f2594f6f1c34cdfb2511dc4728db7b5f4089765600d6c74a353de69a3\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_AWS_SHA=\"03cdeb175f6f3d79aeca171841f83d10fff83143b2bc61a22c15f1ccfe484f27\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_AZURE_SHA=\"3e0f0fbf089adc0255775cb65b2e8dfc18028bb288376080d7a90a2448b00e92\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_FILESYSTEM_SHA=\"50d88c81cac859cb0f446a30229b64336ef4f682a1ed12e1f4cfa03758d57042\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_GCP_SHA=\"4c37f2239888b689d67a193bbd7864d33641c9343574412470b4f882aefbff5c\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_KUBERNETES_SHA=\"ed81603bb88d8060deb46b474a515d49bb71ca0832a3f6d854b4b886bff25842\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_PASSWORDS_SHA=\"630333cc3950387605ad09a528506053e4ff36cee08547b8424958d742a5eac7\" | |\n| MISTRALAI_246_STAGE2_COLLECTORS_VAULT_SHA=\"0eb70f94b82aa24ae8f69d6644f17ca1173b1318a0d30af142d8f76a5175aa49\" | |\n| MISTRALAI_246_STAGE2_UTILITIES_AWS_SIGNER_SHA=\"3b48fb6375ca66dba4b38c001a635b53a4e9ebee233a4ff3ac6352674f4ddc38\" | |\n| MISTRALAI_246_STAGE2_UTILITIES_CRYPTO_SHA=\"831d54a730b2a141ed97ce7a892cec9066c29c9f4094ad6d2ba3e92af97edb51\" | |\n| INCLUDE_LOCKFILE_SCAN=\"${INCLUDE_LOCKFILE_SCAN:-true}\" | |\n| EXIT_ON_MEDIUM=\"${EXIT_ON_MEDIUM:-false}\" | |\n| PRINT_FINDING_LIMIT=\"${PRINT_FINDING_LIMIT:-200}\" | |\n| FD_THREADS=\"${FD_THREADS:-1}\" | |\n| SCAN_ROOTS=() | |\n| FILES_SCANNED=0 | |\n| LOCKFILES_SCANNED=0 | |\n| FILE_FINDER='' | |\n| if command -v fdfind >/dev/null 2>&1; then | |\n| FILE_FINDER='fdfind' | |\n| elif command -v fd >/dev/null 2>&1; then | |\n| FILE_FINDER='fd' | |\n| fi | |\n| ISSUES_FILE=\"$(mktemp \"${TMPDIR:-/tmp}/tanstack_mistral_audit.XXXXXX\")\" || exit 2 | |\n| trap 'rm -f \"$ISSUES_FILE\"' EXIT | |\n| sanitize_field() { | |\n| printf '%s' \"${1:-}\" | tr '\\t\\n\\r' ' ' | cut -c 1-1200 | |\n| } | |\n| print_header() { | |\n| printf '\\n%s=== %s ===%s\\n' \"$YELLOW\" \"$1\" \"$NC\" | |\n| } | |\n| print_clean() { | |\n| printf '%s[+] CLEAN:%s %s\\n' \"$GREEN\" \"$NC\" \"$1\" | |\n| } | |\n| print_warning() { | |\n| printf '%s[?] WARNING:%s %s\\n' \"$YELLOW\" \"$NC\" \"$1\" | |\n| } | |\n| add_issue() { | |\n| printf '%s\\t%s\\t%s\\t%s\\n' \\ | |\n| \"$(sanitize_field \"$1\")\" \\ | |\n| \"$(sanitize_field \"$2\")\" \\ | |\n| \"$(sanitize_field \"$3\")\" \\ | |\n| \"$(sanitize_field \"$4\")\" >> \"$ISSUES_FILE\" | |\n| } | |\n| issue_count() { | |\n| wc -l < \"$ISSUES_FILE\" | tr -d ' ' | |\n| } | |\n| count_severity() { | |\n| local severity=\"$1\" | |\n| awk -F '\\t' -v s=\"$severity\" '$1 == s { c++ } END { print c + 0 }' \"$ISSUES_FILE\" | |\n| } | |\n| actionable_count() { | |\n| awk -F '\\t' '$1 == \"CRITICAL\" || $1 == \"HIGH\" { c++ } END { print c + 0 }' \"$ISSUES_FILE\" | |\n| } | |\n| medium_count() { | |\n| count_severity \"MEDIUM\" | |\n| } | |\n| path_is_under() { | |\n| local child=\"$1\" | |\n| local parent=\"$2\" | |\n| [[ \"$child\" == \"$parent\" ]] && return 0 | |\n| if [[ \"$parent\" == \"/\" ]]; then | |\n| [[ \"$child\" == /* ]] | |\n| return | |\n| fi | |\n| [[ \"$child\" == \"$parent\"/* ]] | |\n| } | |\n| add_scan_root() { | |\n| local candidate=\"$1\" | |\n| local resolved existing | |\n| local kept=() | |\n| [[ -d \"$candidate\" ]] || { | |\n| print_warning \"Skipping missing directory: $candidate\" | |\n| return | |\n| } | |\n| resolved=\"$(cd \"$candidate\" 2>/dev/null && pwd -P)\" || { | |\n| print_warning \"Skipping unreadable directory: $candidate\" | |\n| return | |\n| } | |\n| if [[ \"${#SCAN_ROOTS[@]}\" -gt 0 ]]; then | |\n| for existing in \"${SCAN_ROOTS[@]}\"; do | |\n| if path_is_under \"$resolved\" \"$existing\"; then | |\n| return | |\n| fi | |\n| if ! path_is_under \"$existing\" \"$resolved\"; then | |\n| kept+=(\"$existing\") | |\n| fi | |\n| done | |\n| fi | |\n| if [[ \"${#kept[@]}\" -gt 0 ]]; then | |\n| SCAN_ROOTS=(\"${kept[@]}\" \"$resolved\") | |\n| else | |\n| SCAN_ROOTS=(\"$resolved\") | |\n| fi | |\n| } | |\n| add_scan_root_if_exists() { | |\n| [[ -d \"$1\" ]] && add_scan_root \"$1\" | |\n| } | |\n| add_global_package_roots() { | |\n| local path | |\n| for path in \\ | |\n| /usr/local/lib/node_modules \\ | |\n| /usr/lib/node_modules \\ | |\n| /opt/homebrew/lib/node_modules \\ | |\n| /Library/Python/*/site-packages \\ | |\n| /opt/homebrew/lib/python*/site-packages \\ | |\n| /usr/local/lib/python*/site-packages \\ | |\n| /usr/local/lib/python*/dist-packages \\ | |\n| /usr/lib/python*/site-packages \\ | |\n| /usr/lib/python*/dist-packages \\ | |\n| /opt/*/venv/lib/python*/site-packages \\ | |\n| /opt/*/.venv/lib/python*/site-packages \\ | |\n| /srv/*/venv/lib/python*/site-packages \\ | |\n| /srv/*/.venv/lib/python*/site-packages; do | |\n| add_scan_root_if_exists \"$path\" | |\n| done | |\n| } | |\n| add_default_scan_roots() { | |\n| local cwd os uid | |\n| cwd=\"$(pwd -P 2>/dev/null || pwd)\" | |\n| os=\"$(uname -s 2>/dev/null || printf unknown)\" | |\n| uid=\"$(id -u 2>/dev/null || printf 1)\" | |\n| if [[ \"$uid\" == \"0\" ]]; then | |\n| if [[ \"$os\" == \"Darwin\" ]]; then | |\n| add_scan_root_if_exists /Users | |\n| add_scan_root_if_exists /var/root | |\n| add_scan_root_if_exists /usr/local/lib/node_modules | |\n| add_scan_root_if_exists /opt/homebrew/lib/node_modules | |\n| else | |\n| add_scan_root_if_exists /home | |\n| add_scan_root_if_exists /root | |\n| fi | |\n| [[ -n \"${HOME:-}\" && \"$HOME\" != \"/\" ]] && add_scan_root_if_exists \"$HOME\" | |\n| else | |\n| [[ -n \"${HOME:-}\" && \"$HOME\" != \"/\" ]] && add_scan_root_if_exists \"$HOME\" | |\n| fi | |\n| case \"$cwd\" in | |\n| /|/private|/System|/Library|/Applications|/usr|/usr/local|/opt|/opt/homebrew) ;; | |\n| *) add_scan_root_if_exists \"$cwd\" ;; | |\n| esac | |\n| add_scan_root_if_exists /tmp | |\n| add_scan_root_if_exists /var/tmp | |\n| add_scan_root_if_exists /private/tmp | |\n| add_scan_root_if_exists /private/var/tmp | |\n| add_global_package_roots | |\n| } | |\n| hash_file() { | |\n| if command -v sha256sum >/dev/null 2>&1; then | |\n| sha256sum \"$1\" 2>/dev/null | awk '{print $1}' | |\n| elif command -v shasum >/dev/null 2>&1; then | |\n| shasum -a 256 \"$1\" 2>/dev/null | awk '{print $1}' | |\n| elif command -v openssl >/dev/null 2>&1; then | |\n| openssl dgst -sha256 \"$1\" 2>/dev/null | awk '{print $NF}' | |\n| else | |\n| printf 'sha256-unavailable' | |\n| fi | |\n| } | |\n| file_has() { | |\n| grep -Fq -- \"$2\" \"$1\" 2>/dev/null | |\n| } | |\n| file_has_regex() { | |\n| grep -Eq -- \"$2\" \"$1\" 2>/dev/null | |\n| } | |\n| json_get_string() { | |\n| local file=\"$1\" | |\n| local key=\"$2\" | |\n| sed -nE \"s/.*\\\"${key}\\\"[[:space:]]*:[[:space:]]*\\\"([^\\\"]*)\\\".*/\\1/p\" \"$file\" 2>/dev/null | head -n 1 | |\n| } | |\n| file_has_pkg_version_nearby() { | |\n| local file=\"$1\" | |\n| local package_ere=\"$2\" | |\n| local version_ere=\"$3\" | |\n| awk -v pkg=\"$package_ere\" -v ver=\"$version_ere\" ' | |\n| BEGIN { found = 0 } | |\n| $0 ~ pkg { | |\n| if ($0 ~ ver) { found = 1; exit } | |\n| for (i = 0; i < 18 && (getline line) > 0; i++) { | |\n| if (line ~ ver) { found = 1; exit } | |\n| if (line ~ pkg && line ~ ver) { found = 1; exit } | |\n| } | |\n| } | |\n| END { exit(found ? 0 : 1) } | |\n| ' \"$file\" 2>/dev/null | |\n| } | |\n| file_has_any_malware_marker() { | |\n| local file=\"$1\" | |\n| [[ -f \"$file\" ]] || return 1 | |\n| file_has \"$file\" \"filev2.getsession.org\" || | |\n| file_has \"$file\" \"api.masscan.cloud\" || | |\n| file_has \"$file\" \"git-tanstack.com\" || | |\n| file_has \"$file\" \"seed1.getsession.org\" || | |\n| file_has \"$file\" \"seed2.getsession.org\" || | |\n| file_has \"$file\" \"seed3.getsession.org\" || | |\n| file_has \"$file\" \"$SESSION_RECIPIENT_ID\" || | |\n| file_has \"$file\" \"IfYouRevokeThisTokenItWillWipeTheComputerOfTheOwner\" || | |\n| file_has \"$file\" \"svksjrhjkcejg\" || | |\n| file_has \"$file\" \"EveryBoiWeBuildIsAWormyBoi\" || | |\n| file_has \"$file\" \"A Mini Shai-Hulud has Appeared\" || | |\n| file_has \"$file\" \"Shai-Hulud: Here We Go Again\" || | |\n| file_has \"$file\" \"PUSH UR T3MPRR\" || | |\n| file_has \"$file\" \"bun run tanstack_runner.js\" || | |\n| file_has \"$file\" \"$MALICIOUS_SETUP_SPEC\" || | |\n| { file_has \"$file\" \"@tanstack/setup\" && file_has \"$file\" \"$MALICIOUS_COMMIT\"; } | |\n| } | |\n| pypi_loader_is_malicious() { | |\n| local file=\"$1\" | |\n| [[ -f \"$file\" ]] || return 1 | |\n| { file_has \"$file\" \"$PYPI_MISTRAL_ENV_MARKER\" && \\ | |\n| { file_has \"$file\" \"$PYPI_MISTRAL_C2\" || file_has \"$file\" \"$PYPI_SECOND_STAGE\" || file_has \"$file\" \"$PYPI_PAYLOAD_DOMAIN\"; }; } || | |\n| { file_has \"$file\" \"$PYPI_MISTRAL_C2\" && file_has \"$file\" \"$PYPI_SECOND_STAGE\"; } || | |\n| { file_has \"$file\" \"$PYPI_PAYLOAD_DOMAIN\" && file_has \"$file\" \"$PYPI_SECOND_STAGE\"; } || | |\n| { file_has \"$file\" \"$PYPI_SECOND_STAGE_ABS\" && \\ | |\n| { file_has \"$file\" \"subprocess\" || file_has \"$file\" \"Popen\" || file_has \"$file\" \"curl\" || file_has \"$file\" \"urlopen\"; }; } | |\n| } | |\n| pypi_payload_is_malicious() { | |\n| local file=\"$1\" | |\n| [[ -f \"$file\" ]] || return 1 | |\n| { file_has \"$file\" \"$PYPI_MISTRAL_ENV_MARKER\" && \\ | |\n| { file_has \"$file\" \"$PYPI_MISTRAL_C2\" || file_has \"$file\" \"$PYPI_SECOND_STAGE\" || file_has \"$file\" \"$PYPI_PAYLOAD_DOMAIN\"; }; } || | |\n| { file_has \"$file\" \"$PYPI_MISTRAL_C2\" && \\ | |\n| { file_has \"$file\" \"$PYPI_SECOND_STAGE\" || file_has \"$file\" \"$PYPI_PERSISTENCE_SCRIPT\" || file_has \"$file\" \"$PYPI_PERSISTENCE_SERVICE\" || file_has \"$file\" \"PUSH UR T3MPRR\"; }; } || | |\n| { file_has \"$file\" \"$PYPI_PAYLOAD_DOMAIN\" && file_has \"$file\" \"$PYPI_SECOND_STAGE\"; } || | |\n| { file_has \"$file\" \"$PYPI_SECOND_STAGE\" && file_has \"$file\" \"$PYPI_PERSISTENCE_SCRIPT\" && file_has \"$file\" \"$PYPI_PERSISTENCE_SERVICE\"; } || | |\n| { file_has \"$file\" \"FIRESCALE\" && file_has \"$file\" \"$PYPI_MISTRAL_C2\"; } || | |\n| { file_has \"$file\" \"PUSH UR T3MPRR\" && file_has \"$file\" \"RunForCover.mp3\"; } | |\n| } | |\n| pypi_service_points_to_monitor() { | |\n| local file=\"$1\" | |\n| [[ -f \"$file\" ]] || return 1 | |\n| file_has \"$file\" \"$PYPI_PERSISTENCE_SCRIPT\" && \\ | |\n| { file_has \"$file\" \"$PYPI_PERSISTENCE_SERVICE\" || file_has \"$file\" \"ExecStart\" || file_has \"$file\" \"systemd\"; } | |\n| } | |\n| pypi_metadata_compromised_package() { | |\n| local file=\"$1\" | |\n| [[ -f \"$file\" ]] || return 1 | |\n| if file_has \"$file\" \"Name: mistralai\" && file_has \"$file\" \"Version: 2.4.6\"; then | |\n| printf 'mistralai==2.4.6' | |\n| return 0 | |\n| fi | |\n| if file_has \"$file\" \"Name: guardrails-ai\" && file_has \"$file\" \"Version: 0.10.1\"; then | |\n| printf 'guardrails-ai==0.10.1' | |\n| return 0 | |\n| fi | |\n| return 1 | |\n| } | |\n| node_metadata_compromised_package() { | |\n| local file=\"$1\" | |\n| local name version | |\n| [[ -f \"$file\" ]] || return 1 | |\n| name=\"$(json_get_string \"$file\" name)\" | |\n| version=\"$(json_get_string \"$file\" version)\" | |\n| case \"${name}:${version}\" in | |\n| '@mistralai/mistralai:2.2.2'|'@mistralai/mistralai:2.2.3'|'@mistralai/mistralai:2.2.4'|'@mistralai/mistralai-azure:1.7.1'|'@mistralai/mistralai-azure:1.7.2'|'@mistralai/mistralai-azure:1.7.3'|'@mistralai/mistralai-gcp:1.7.1'|'@mistralai/mistralai-gcp:1.7.2'|'@mistralai/mistralai-gcp:1.7.3') | |\n| printf '%s@%s' \"$name\" \"$version\" | |\n| return 0 | |\n| ;; | |\n| esac | |\n| return 1 | |\n| } | |\n| exposure_marker_for_depfile() { | |\n| local file=\"$1\" | |\n| [[ -f \"$file\" ]] || return 1 | |\n| if file_has_pkg_version_nearby \"$file\" '@mistralai/mistralai-azure([^A-Za-z0-9_.-]|$)' '1[.]7[.][123]'; then | |\n| printf '@mistralai/mistralai-azure affected version marker' | |\n| return 0 | |\n| fi | |\n| if file_has_pkg_version_nearby \"$file\" '@mistralai/mistralai-gcp([^A-Za-z0-9_.-]|$)' '1[.]7[.][123]'; then | |\n| printf '@mistralai/mistralai-gcp affected version marker' | |\n| return 0 | |\n| fi | |\n| if file_has_pkg_version_nearby \"$file\" '@mistralai/mistralai([^A-Za-z0-9_.-]|$)' '2[.]2[.][234]'; then | |\n| printf '@mistralai/mistralai affected version marker' | |\n| return 0 | |\n| fi | |\n| if file_has_pkg_version_nearby \"$file\" '(^|[^A-Za-z0-9_./@-])mistralai([^A-Za-z0-9_./-]|$)' '2[.]4[.]6' || \\ | |\n| file_has_regex \"$file\" '(^|[^A-Za-z0-9_./@-])mistralai([^A-Za-z0-9_./-]|[[:space:]])+([^#\\r\\n]*)2[.]4[.]6'; then | |\n| printf 'mistralai==2.4.6 marker' | |\n| return 0 | |\n| fi | |\n| if file_has_pkg_version_nearby \"$file\" '(^|[^A-Za-z0-9_.-])guardrails-ai([^A-Za-z0-9_.-]|$)' '0[.]10[.]1' || \\ | |\n| file_has_pkg_version_nearby \"$file\" '(^|[^A-Za-z0-9_.-])guardrails_ai([^A-Za-z0-9_.-]|$)' '0[.]10[.]1' || \\ | |\n| file_has_regex \"$file\" '(^|[^A-Za-z0-9_.-])guardrails[-_]ai([^A-Za-z0-9_.-]|[[:space:]])+([^#\\r\\n]*)0[.]10[.]1'; then | |\n| printf 'guardrails-ai==0.10.1 marker' | |\n| return 0 | |\n| fi | |\n| return 1 | |\n| } | |\n| file_hash_is_known_malicious() { | |\n| local file=\"$1\" | |\n| local digest | |\n| digest=\"$(hash_file \"$file\")\" | |\n| case \"$digest\" in | |\n| \"$ROUTER_INIT_SHA\"|\"$TANSTACK_RUNNER_SHA\"|\"$TANSTACK_SETUP_PACKAGE_SHA\"|\"$SETUP_MJS_SHA\"|\"$TANSTACK_TROJANIZED_TARBALL_SHA\"|\"$GUARDRAILS_AI_0101_SDIST_SHA\"|\"$GUARDRAILS_AI_0101_WHEEL_SHA\"|\"$MISTRALAI_246_WHEEL_SHA\"|\"$MISTRALAI_246_STAGE1_INIT_SHA\"|\"$MISTRALAI_246_TRANSFORMERS_PYZ_SHA\"|\"$MISTRALAI_246_STAGE2_MAIN_SHA\"|\"$MISTRALAI_246_STAGE2_AGGREGATE_SHA\"|\"$MISTRALAI_246_STAGE2_CONFIG_SHA\"|\"$MISTRALAI_246_STAGE2_ENTRYPOINT_SHA\"|\"$MISTRALAI_246_STAGE2_ROULETTE_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_AWS_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_AZURE_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_FILESYSTEM_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_GCP_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_KUBERNETES_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_PASSWORDS_SHA\"|\"$MISTRALAI_246_STAGE2_COLLECTORS_VAULT_SHA\"|\"$MISTRALAI_246_STAGE2_UTILITIES_AWS_SIGNER_SHA\"|\"$MISTRALAI_246_STAGE2_UTILITIES_CRYPTO_SHA\") | |\n| printf '%s' \"$digest\" | |\n| return 0 | |\n| ;; | |\n| esac | |\n| return 1 | |\n| } | |\n| installed_package_has_malicious_setup() { | |\n| local package_json=\"$1\" | |\n| [[ \"$package_json\" == */node_modules/*/package.json ]] || return 1 | |\n| file_has \"$package_json\" '\"@tanstack/setup\"' && file_has \"$package_json\" \"$MALICIOUS_SETUP_SPEC\" | |\n| } | |\n| lockfile_has_malicious_setup() { | |\n| local lockfile=\"$1\" | |\n| file_has \"$lockfile\" \"@tanstack/setup\" && file_has \"$lockfile\" \"$MALICIOUS_COMMIT\" | |\n| } | |\n| persistence_script_is_malicious() { | |\n| local file=\"$1\" | |\n| local digest | |\n| [[ -f \"$file\" ]] || return 1 | |\n| if digest=\"$(file_hash_is_known_malicious \"$file\")\"; then | |\n| return 0 | |\n| fi | |\n| file_has_any_malware_marker \"$file\" | |\n| } | |\n| find_candidate_files() { | |\n| local root=\"$1\" | |\n| if [[ -n \"$FILE_FINDER\" ]]; then | |\n| \"$FILE_FINDER\" -0 -j \"$FD_THREADS\" -H -I -t f \\ | |\n| -E .git \\ | |\n| -E .hg \\ | |\n| -E .svn \\ | |\n| -E target \\ | |\n| -E .cache \\ | |\n| -E node_modules/.cache \\ | |\n| -E .pnpm-store \\ | |\n| -E .yarn/cache \\ | |\n| -E .Trash \\ | |\n| -E Library/Caches \\ | |\n| -E Library/Developer/Xcode/DerivedData \\ | |\n| -p '(^|/)(router_init\\.js|tanstack_runner\\.js|router_runtime\\.js|node_modules/.*/package\\.json|mistralai/client/__init__\\.py|guardrails/__init__\\.py|mistralai-2\\.4\\.6\\.dist-info/METADATA|guardrails[_-]ai-0\\.10\\.1\\.dist-info/METADATA|mistralai-2\\.4\\.6(-py3-none-any\\.whl|\\.tar\\.gz)|guardrails_ai-0\\.10\\.1(-py3-none-any\\.whl|\\.tar\\.gz)|transformers\\.pyz|pgmonitor\\.py|pgsql-monitor\\.service|__main__\\.py|aggregate\\.py|config\\.py|entrypoint\\.py|roulette\\.py|collectors/(aws|azure|filesystem|gcp|kubernetes|passwords|vault)\\.py|utilities/(aws_signer|crypto)\\.py|\\.claude/(settings\\.json|router_runtime\\.js|setup\\.mjs)|\\.vscode/(tasks\\.json|setup\\.mjs)|gh-token-monitor\\.service|com\\.user\\.gh-token-monitor\\.plist|gh-token-monitor\\.sh|\\.config/gh-token-monitor/token|\\.github/workflows/codeql_analysis\\.ya?ml)$' \\ | |\n| \"$root\" 2>/dev/null | |\n| return | |\n| fi | |\n| find \"$root\" \\ | |\n| \\( \\ | |\n| -path '*/.git' -o \\ | |\n| -path '*/.hg' -o \\ | |\n| -path '*/.svn' -o \\ | |\n| -path '*/target' -o \\ | |\n| -path '*/.cache' -o \\ | |\n| -path '*/node_modules/.cache' -o \\ | |\n| -path '*/.pnpm-store' -o \\ | |\n| -path '*/.yarn/cache' -o \\ | |\n| -path '*/.Trash' -o \\ | |\n| -path '*/Library/Caches' -o \\ | |\n| -path '*/Library/Developer/Xcode/DerivedData' \\ | |\n| \\) -prune -o \\ | |\n| -type f \\( \\ | |\n| -name 'router_init.js' -o \\ | |\n| -name 'tanstack_runner.js' -o \\ | |\n| -name 'router_runtime.js' -o \\ | |\n| -path '*/node_modules/*/package.json' -o \\ | |\n| -path '*/mistralai/client/__init__.py' -o \\ | |\n| -path '*/guardrails/__init__.py' -o \\ | |\n| -path '*/mistralai-2.4.6.dist-info/METADATA' -o \\ | |\n| -path '*/guardrails_ai-0.10.1.dist-info/METADATA' -o \\ | |\n| -path '*/guardrails-ai-0.10.1.dist-info/METADATA' -o \\ | |\n| -name 'mistralai-2.4.6-py3-none-any.whl' -o \\ | |\n| -name 'mistralai-2.4.6.tar.gz' -o \\ | |\n| -name 'guardrails_ai-0.10.1-py3-none-any.whl' -o \\ | |\n| -name 'guardrails_ai-0.10.1.tar.gz' -o \\ | |\n| -name 'transformers.pyz' -o \\ | |\n| -name 'pgmonitor.py' -o \\ | |\n| -name 'pgsql-monitor.service' -o \\ | |\n| -name '__main__.py' -o \\ | |\n| -name 'aggregate.py' -o \\ | |\n| -name 'config.py' -o \\ | |\n| -name 'entrypoint.py' -o \\ | |\n| -name 'roulette.py' -o \\ | |\n| -path '*/collectors/aws.py' -o \\ | |\n| -path '*/collectors/azure.py' -o \\ | |\n| -path '*/collectors/filesystem.py' -o \\ | |\n| -path '*/collectors/gcp.py' -o \\ | |\n| -path '*/collectors/kubernetes.py' -o \\ | |\n| -path '*/collectors/passwords.py' -o \\ | |\n| -path '*/collectors/vault.py' -o \\ | |\n| -path '*/utilities/aws_signer.py' -o \\ | |\n| -path '*/utilities/crypto.py' -o \\ | |\n| -path '*/.claude/settings.json' -o \\ | |\n| -path '*/.claude/router_runtime.js' -o \\ | |\n| -path '*/.claude/setup.mjs' -o \\ | |\n| -path '*/.vscode/tasks.json' -o \\ | |\n| -path '*/.vscode/setup.mjs' -o \\ | |\n| -name 'gh-token-monitor.service' -o \\ | |\n| -name 'com.user.gh-token-monitor.plist' -o \\ | |\n| -name 'gh-token-monitor.sh' -o \\ | |\n| -path '*/.config/gh-token-monitor/token' -o \\ | |\n| -path '*/.github/workflows/codeql_analysis.yml' -o \\ | |\n| -path '*/.github/workflows/codeql_analysis.yaml' \\ | |\n| \\) -print0 2>/dev/null | |\n| } | |\n| find_exposure_files() { | |\n| local root=\"$1\" | |\n| if [[ -n \"$FILE_FINDER\" ]]; then | |\n| \"$FILE_FINDER\" -0 -j \"$FD_THREADS\" -H -I -t f \\ | |\n| -E .git \\ | |\n| -E .hg \\ | |\n| -E .svn \\ | |\n| -E target \\ | |\n| -E .cache \\ | |\n| -E node_modules \\ | |\n| -E .pnpm-store \\ | |\n| -E .yarn/cache \\ | |\n| -E .Trash \\ | |\n| -E Library/Caches \\ | |\n| -E Library/Developer/Xcode/DerivedData \\ | |\n| -p '(^|/)(package\\.json|package-lock\\.json|npm-shrinkwrap\\.json|pnpm-lock\\.yaml|yarn\\.lock|requirements.*\\.txt|pyproject\\.toml|uv\\.lock|poetry\\.lock|Pipfile|Pipfile\\.lock|pdm\\.lock|environment\\.ya?ml)$' \\ | |\n| \"$root\" 2>/dev/null | |\n| return | |\n| fi | |\n| find \"$root\" \\ | |\n| \\( \\ | |\n| -path '*/.git' -o \\ | |\n| -path '*/.hg' -o \\ | |\n| -path '*/.svn' -o \\ | |\n| -path '*/target' -o \\ | |\n| -path '*/.cache' -o \\ | |\n| -path '*/node_modules' -o \\ | |\n| -path '*/.pnpm-store' -o \\ | |\n| -path '*/.yarn/cache' -o \\ | |\n| -path '*/.Trash' -o \\ | |\n| -path '*/Library/Caches' -o \\ | |\n| -path '*/Library/Developer/Xcode/DerivedData' \\ | |\n| \\) -prune -o \\ | |\n| -type f \\( \\ | |\n| -name 'package.json' -o \\ | |\n| -name 'package-lock.json' -o \\ | |\n| -name 'npm-shrinkwrap.json' -o \\ | |\n| -name 'pnpm-lock.yaml' -o \\ | |\n| -name 'yarn.lock' -o \\ | |\n| -name 'requirements*.txt' -o \\ | |\n| -name 'pyproject.toml' -o \\ | |\n| -name 'uv.lock' -o \\ | |\n| -name 'poetry.lock' -o \\ | |\n| -name 'Pipfile' -o \\ | |\n| -name 'Pipfile.lock' -o \\ | |\n| -name 'pdm.lock' -o \\ | |\n| -name 'environment.yml' -o \\ | |\n| -name 'environment.yaml' \\ | |\n| \\) -print0 2>/dev/null | |\n| } | |\n| scan_candidate_files() { | |\n| print_header \"Checking confirmed filesystem indicators\" | |\n| local before root file digest basename project_root setup_file setup_file2 pypi_package npm_package | |\n| before=\"$(issue_count)\" | |\n| for root in \"${SCAN_ROOTS[@]}\"; do | |\n| while IFS= read -r -d '' file; do | |\n| FILES_SCANNED=$((FILES_SCANNED + 1)) | |\n| basename=\"$(basename \"$file\")\" | |\n| case \"$file\" in | |\n| */router_init.js|*/tanstack_runner.js|*/router_runtime.js|*/.claude/setup.mjs|*/.vscode/setup.mjs) | |\n| if digest=\"$(file_hash_is_known_malicious \"$file\")\"; then | |\n| add_issue \"CRITICAL\" \"known malicious payload hash\" \"$file\" \"sha256=$digest\" | |\n| continue | |\n| fi | |\n| if file_has_any_malware_marker \"$file\"; then | |\n| add_issue \"CRITICAL\" \"malicious payload marker\" \"$file\" \"high-confidence Mini Shai-Hulud marker found\" | |\n| continue | |\n| fi | |\n| if [[ \"$basename\" == \"router_init.js\" ]]; then | |\n| setup_file=\"$(dirname \"$file\")/package.json\" | |\n| if installed_package_has_malicious_setup \"$setup_file\"; then | |\n| add_issue \"CRITICAL\" \"infected installed package artifact\" \"$file\" \"router_init.js next to exact malicious @tanstack/setup dependency\" | |\n| fi | |\n| fi | |\n| ;; | |\n| */mistralai/client/__init__.py) | |\n| if pypi_loader_is_malicious \"$file\"; then | |\n| add_issue \"CRITICAL\" \"compromised PyPI mistralai loader\" \"$file\" \"import-time loader references ${PYPI_MISTRAL_ENV_MARKER}/${PYPI_MISTRAL_C2}/${PYPI_SECOND_STAGE}\" | |\n| fi | |\n| ;; | |\n| */guardrails/__init__.py) | |\n| if pypi_loader_is_malicious \"$file\"; then | |\n| add_issue \"CRITICAL\" \"compromised PyPI guardrails-ai loader\" \"$file\" \"import-time loader references ${PYPI_PAYLOAD_DOMAIN}/${PYPI_SECOND_STAGE}\" | |\n| fi | |\n| ;; | |\n| */__main__.py|*/aggregate.py|*/config.py|*/entrypoint.py|*/roulette.py|*/collectors/aws.py|*/collectors/azure.py|*/collectors/filesystem.py|*/collectors/gcp.py|*/collectors/kubernetes.py|*/collectors/passwords.py|*/collectors/vault.py|*/utilities/aws_signer.py|*/utilities/crypto.py) | |\n| if digest=\"$(file_hash_is_known_malicious \"$file\")\"; then | |\n| add_issue \"CRITICAL\" \"known malicious extracted PyPI payload hash\" \"$file\" \"sha256=$digest\" | |\n| fi | |\n| ;; | |\n| */mistralai-2.4.6.dist-info/METADATA|*/guardrails_ai-0.10.1.dist-info/METADATA|*/guardrails-ai-0.10.1.dist-info/METADATA) | |\n| if pypi_package=\"$(pypi_metadata_compromised_package \"$file\")\"; then | |\n| add_issue \"HIGH\" \"installed compromised PyPI package version\" \"$file\" \"$pypi_package installed; verify whether it was imported or used on this host\" | |\n| fi | |\n| ;; | |\n| */mistralai-2.4.6-py3-none-any.whl|*/mistralai-2.4.6.tar.gz|*/guardrails_ai-0.10.1-py3-none-any.whl|*/guardrails_ai-0.10.1.tar.gz) | |\n| if digest=\"$(file_hash_is_known_malicious \"$file\")\"; then | |\n| add_issue \"HIGH\" \"known compromised PyPI package archive hash\" \"$file\" \"sha256=$digest\" | |\n| fi | |\n| ;; | |\n| */transformers.pyz) | |\n| if digest=\"$(file_hash_is_known_malicious \"$file\")\"; then | |\n| add_issue \"CRITICAL\" \"known malicious PyPI second-stage hash\" \"$file\" \"sha256=$digest\" | |\n| continue | |\n| fi | |\n| if pypi_payload_is_malicious \"$file\"; then | |\n| add_issue \"CRITICAL\" \"PyPI second-stage payload\" \"$file\" \"Mini Shai-Hulud PyPI payload markers found\" | |\n| fi | |\n| ;; | |\n| */pgmonitor.py) | |\n| if pypi_payload_is_malicious \"$file\"; then | |\n| add_issue \"CRITICAL\" \"PyPI persistence payload\" \"$file\" \"Mini Shai-Hulud PyPI persistence markers found\" | |\n| fi | |\n| ;; | |\n| */pgsql-monitor.service) | |\n| if pypi_service_points_to_monitor \"$file\"; then | |\n| add_issue \"CRITICAL\" \"PyPI systemd persistence artifact\" \"$file\" \"pgsql-monitor service points to pgmonitor.py\" | |\n| fi | |\n| ;; | |\n| */node_modules/*/package.json) | |\n| if installed_package_has_malicious_setup \"$file\"; then | |\n| add_issue \"CRITICAL\" \"infected installed package marker\" \"$file\" \"exact malicious @tanstack/setup dependency found in node_modules package.json\" | |\n| continue | |\n| fi | |\n| if npm_package=\"$(node_metadata_compromised_package \"$file\")\"; then | |\n| add_issue \"HIGH\" \"installed compromised npm package version\" \"$file\" \"$npm_package installed; treat this install environment as exposed\" | |\n| continue | |\n| fi | |\n| case \"$file\" in | |\n| */node_modules/@tanstack/setup/package.json|*/node_modules/.pnpm/*/node_modules/@tanstack/setup/package.json) | |\n| if digest=\"$(file_hash_is_known_malicious \"$file\")\"; then | |\n| add_issue \"CRITICAL\" \"known malicious @tanstack/setup manifest hash\" \"$file\" \"sha256=$digest\" | |\n| fi | |\n| ;; | |\n| esac | |\n| ;; | |\n| */.claude/settings.json) | |\n| project_root=\"$(dirname \"$(dirname \"$file\")\")\" | |\n| setup_file=\"$project_root/.claude/setup.mjs\" | |\n| setup_file2=\"$project_root/.vscode/setup.mjs\" | |\n| if { file_has \"$file\" \"hooks\" || file_has \"$file\" \"SessionStart\"; } && \\ | |\n| { file_has \"$file\" \"router_runtime.js\" || file_has \"$file\" \"setup.mjs\" || file_has \"$file\" \".vscode/setup.mjs\" || file_has \"$file\" \".claude/setup.mjs\"; }; then | |\n| if persistence_script_is_malicious \"$setup_file\" || persistence_script_is_malicious \"$setup_file2\" || file_has_any_malware_marker \"$file\"; then | |\n| add_issue \"CRITICAL\" \"Claude Code persistence hook\" \"$file\" \"hook references malicious setup/router runtime payload\" | |\n| fi | |\n| fi | |\n| ;; | |\n| */.vscode/tasks.json) | |\n| project_root=\"$(dirname \"$(dirname \"$file\")\")\" | |\n| setup_file=\"$project_root/.vscode/setup.mjs\" | |\n| setup_file2=\"$project_root/.claude/setup.mjs\" | |\n| if { file_has \"$file\" \"folderOpen\" || file_has \"$file\" \"runOn\" || file_has \"$file\" \"setup.mjs\"; } && \\ | |\n| { file_has \"$file\" \"setup.mjs\" || file_has \"$file\" \"router_runtime.js\" || file_has \"$file\" \".claude/setup.mjs\" || file_has \"$file\" \".vscode/setup.mjs\"; }; then | |\n| if persistence_script_is_malicious \"$setup_file\" || persistence_script_is_malicious \"$setup_file2\" || file_has_any_malware_marker \"$file\"; then | |\n| add_issue \"CRITICAL\" \"VS Code persistence task\" \"$file\" \"task references malicious setup/router runtime payload\" | |\n| fi | |\n| fi | |\n| ;; | |\n| */gh-token-monitor.service|*/com.user.gh-token-monitor.plist) | |\n| if file_has \"$file\" \"gh-token-monitor\" && \\ | |\n| { file_has \"$file\" \".config/gh-token-monitor\" || file_has \"$file\" \".local/bin/gh-token-monitor.sh\" || file_has \"$file\" \"gh-token-monitor.sh\" || file_has \"$file\" \"api.github.com/user\"; }; then | |\n| add_issue \"CRITICAL\" \"service persistence artifact\" \"$file\" \"gh-token-monitor service/LaunchAgent points to malware token monitor\" | |\n| fi | |\n| ;; | |\n| */gh-token-monitor.sh) | |\n| if file_has \"$file\" \"GH_TOKEN\" && \\ | |\n| { file_has \"$file\" \"api.github.com/user\" || file_has \"$file\" \".config/gh-token-monitor/token\" || file_has \"$file\" \"IfYouRevokeThisTokenItWillWipeTheComputerOfTheOwner\" || file_has \"$file\" \"rm -rf\"; }; then | |\n| add_issue \"CRITICAL\" \"service persistence artifact\" \"$file\" \"gh-token-monitor script contains token monitor/wiper markers\" | |\n| fi | |\n| ;; | |\n| */.config/gh-token-monitor/token) | |\n| if [[ -s \"$file\" ]]; then | |\n| add_issue \"CRITICAL\" \"service persistence token store\" \"$file\" \"non-empty gh-token-monitor token store\" | |\n| fi | |\n| ;; | |\n| */.github/workflows/codeql_analysis.yml|*/.github/workflows/codeql_analysis.yaml) | |\n| if file_has \"$file\" \"toJSON(secrets)\" && \\ | |\n| { file_has \"$file\" \"api.masscan.cloud\" || file_has \"$file\" \"filev2.getsession.org\" || file_has \"$file\" \"format-results\" || file_has \"$file\" \"CodeQL Analysis\"; }; then | |\n| add_issue \"CRITICAL\" \"secret-exfiltration workflow\" \"$file\" \"workflow serializes GitHub secrets\" | |\n| fi | |\n| ;; | |\n| esac | |\n| done < <(find_candidate_files \"$root\") | |\n| done | |\n| if [[ \"$(issue_count)\" == \"$before\" ]]; then | |\n| print_clean \"No confirmed filesystem indicators found.\" | |\n| fi | |\n| } | |\n| scan_lockfiles_for_exposure() { | |\n| [[ \"$INCLUDE_LOCKFILE_SCAN\" == \"true\" ]] || return 0 | |\n| print_header \"Checking dependency and lockfile exposure markers\" | |\n| local before root file marker | |\n| before=\"$(issue_count)\" | |\n| for root in \"${SCAN_ROOTS[@]}\"; do | |\n| while IFS= read -r -d '' file; do | |\n| LOCKFILES_SCANNED=$((LOCKFILES_SCANNED + 1)) | |\n| if lockfile_has_malicious_setup \"$file\"; then | |\n| add_issue \"MEDIUM\" \"lockfile exposure marker\" \"$file\" \"exact malicious @tanstack/setup commit appears in dependency file; verify whether install scripts ran on this host\" | |\n| continue | |\n| fi | |\n| if marker=\"$(exposure_marker_for_depfile \"$file\")\"; then | |\n| add_issue \"MEDIUM\" \"dependency exposure marker\" \"$file\" \"$marker; verify whether this resolved/installed on this host\" | |\n| fi | |\n| done < <(find_exposure_files \"$root\") | |\n| done | |\n| if [[ \"$(issue_count)\" == \"$before\" ]]; then | |\n| print_clean \"No dependency or lockfile exposure markers found.\" | |\n| fi | |\n| } | |\n| scan_system_persistence_paths() { | |\n| print_header \"Checking confirmed system persistence paths\" | |\n| local before file | |\n| before=\"$(issue_count)\" | |\n| for file in \\ | |\n| /Library/LaunchAgents/com.user.gh-token-monitor.plist \\ | |\n| /Library/LaunchDaemons/com.user.gh-token-monitor.plist \\ | |\n| /var/root/Library/LaunchAgents/com.user.gh-token-monitor.plist \\ | |\n| /etc/systemd/system/gh-token-monitor.service \\ | |\n| /etc/systemd/system/pgsql-monitor.service \\ | |\n| /lib/systemd/system/gh-token-monitor.service \\ | |\n| /lib/systemd/system/pgsql-monitor.service \\ | |\n| /usr/lib/systemd/system/gh-token-monitor.service \\ | |\n| /usr/lib/systemd/system/pgsql-monitor.service; do | |\n| if [[ -e \"$file\" ]] && file_has \"$file\" \"gh-token-monitor\" && \\ | |\n| { file_has \"$file\" \".config/gh-token-monitor\" || file_has \"$file\" \".local/bin/gh-token-monitor.sh\" || file_has \"$file\" \"gh-token-monitor.sh\" || file_has \"$file\" \"api.github.com/user\"; }; then | |\n| add_issue \"CRITICAL\" \"system persistence artifact\" \"$file\" \"gh-token-monitor service/LaunchAgent points to malware token monitor\" | |\n| continue | |\n| fi | |\n| if [[ -e \"$file\" ]] && pypi_service_points_to_monitor \"$file\"; then | |\n| add_issue \"CRITICAL\" \"PyPI system persistence artifact\" \"$file\" \"pgsql-monitor service points to pgmonitor.py\" | |\n| fi | |\n| done | |\n| if [[ \"$(issue_count)\" == \"$before\" ]]; then | |\n| print_clean \"No confirmed system persistence paths found.\" | |\n| fi | |\n| } | |\n| scan_processes() { | |\n| print_header \"Checking running process command lines\" | |\n| local before pid cmd | |\n| before=\"$(issue_count)\" | |\n| while read -r pid cmd; do | |\n| [[ -n \"$pid\" ]] || continue | |\n| [[ -n \"${cmd:-}\" ]] || continue | |\n| [[ \"$pid\" == \"$$\" ]] && continue | |\n| case \"$cmd\" in | |\n| *tanstack_mistral_audit_public*.sh*|*tanstack_audit_public.sh*|*mini-shai-hulud-ioc-scanner*) continue ;; | |\n| find\\ *|*/find\\ *|fd\\ *|*/fd\\ *|fdfind\\ *|*/fdfind\\ *|rg\\ *|*/rg\\ *|grep\\ *|*/grep\\ *) continue ;; | |\n| *' find '*|*' fd '*|*' fdfind '*|*' rg '*|*' grep '*) continue ;; | |\n| esac | |\n| case \"$cmd\" in | |\n| *'bun run tanstack_runner.js'*|*'tanstack_runner.js'*|*'router_runtime.js'*|*'filev2.getsession.org'*|*'api.masscan.cloud'*|*'git-tanstack.com'*|*'IfYouRevokeThisTokenItWillWipeTheComputerOfTheOwner'*|*'gh-token-monitor'*|*'83.142.209.194'*|*'/tmp/transformers.pyz'*|*'/private/tmp/transformers.pyz'*|*'/var/tmp/transformers.pyz'*|*'/private/var/tmp/transformers.pyz'*) | |\n| add_issue \"HIGH\" \"running process command-line indicator\" \"pid=$pid\" \"$cmd\" | |\n| ;; | |\n| esac | |\n| done < <(ps -axo pid=,command= 2>/dev/null || true) | |\n| if [[ \"$(issue_count)\" == \"$before\" ]]; then | |\n| print_clean \"No running process command-line indicators found.\" | |\n| fi | |\n| } | |\n| scan_process_environments() { | |\n| [[ \"$(uname -s 2>/dev/null || printf unknown)\" == \"Linux\" ]] || return 0 | |\n| print_header \"Checking Linux process environments\" | |\n| local before envfile pid cmd | |\n| before=\"$(issue_count)\" | |\n| for envfile in /proc/[0-9]*/environ; do | |\n| [[ -r \"$envfile\" ]] || continue | |\n| if tr '\\0' '\\n' < \"$envfile\" 2>/dev/null | grep -Fq \"${PYPI_MISTRAL_ENV_MARKER}=1\"; then | |\n| pid=\"${envfile#/proc/}\" | |\n| pid=\"${pid%/environ}\" | |\n| cmd=\"$(tr '\\0' ' ' < \"/proc/$pid/cmdline\" 2>/dev/null | cut -c 1-240)\" | |\n| add_issue \"HIGH\" \"running process environment indicator\" \"pid=$pid\" \"${PYPI_MISTRAL_ENV_MARKER}=1 ${cmd:+cmd=$cmd}\" | |\n| fi | |\n| done | |\n| if [[ \"$(issue_count)\" == \"$before\" ]]; then | |\n| print_clean \"No Linux process environment indicators found.\" | |\n| fi | |\n| } | |\n| scan_network_connections() { | |\n| print_header \"Checking active network indicators\" | |\n| local before output | |\n| before=\"$(issue_count)\" | |\n| output='' | |\n| if command -v lsof >/dev/null 2>&1; then | |\n| output=\"$(lsof -nP -iTCP -iUDP 2>/dev/null | grep -F \"$PYPI_MISTRAL_C2\" | head -n 5 || true)\" | |\n| elif command -v ss >/dev/null 2>&1; then | |\n| output=\"$(ss -tunap 2>/dev/null | grep -F \"$PYPI_MISTRAL_C2\" | head -n 5 || true)\" | |\n| elif command -v netstat >/dev/null 2>&1; then | |\n| output=\"$(netstat -anv 2>/dev/null | grep -F \"$PYPI_MISTRAL_C2\" | head -n 5 || true)\" | |\n| else | |\n| print_warning \"No supported network inspection tool found (lsof/ss/netstat); skipped active connection check.\" | |\n| return 0 | |\n| fi | |\n| if [[ -n \"$output\" ]]; then | |\n| add_issue \"HIGH\" \"active network indicator\" \"$PYPI_MISTRAL_C2\" \"$output\" | |\n| fi | |\n| if [[ \"$(issue_count)\" == \"$before\" ]]; then | |\n| print_clean \"No active network indicators found.\" | |\n| fi | |\n| } | |\n| print_summary() { | |\n| local count actionable medium severity category path detail i | |\n| count=\"$(issue_count)\" | |\n| actionable=\"$(actionable_count)\" | |\n| medium=\"$(medium_count)\" | |\n| printf '\\n%s----------------------------------------%s\\n' \"$YELLOW\" \"$NC\" | |\n| printf 'Files inspected: %s\\n' \"$FILES_SCANNED\" | |\n| if [[ \"$INCLUDE_LOCKFILE_SCAN\" == \"true\" ]]; then | |\n| printf 'Dependency/lockfiles inspected: %s\\n' \"$LOCKFILES_SCANNED\" | |\n| fi | |\n| if [[ \"$count\" -eq 0 ]]; then | |\n| printf '%sAUDIT COMPLETE: No issues detected.%s\\n' \"$GREEN\" \"$NC\" | |\n| return | |\n| fi | |\n| printf '%sAUDIT COMPLETE: %s finding(s) detected (%s actionable, %s medium exposure).%s\\n' \"$RED\" \"$count\" \"$actionable\" \"$medium\" \"$NC\" | |\n| printf '\\nFindings:\\n' | |\n| i=0 | |\n| while IFS=$'\\t' read -r severity category path detail; do | |\n| i=$((i + 1)) | |\n| [[ \"$i\" -le \"$PRINT_FINDING_LIMIT\" ]] || continue | |\n| printf ' [%s] %s: %s -- %s\\n' \"$severity\" \"$category\" \"$path\" \"$detail\" | |\n| done < \"$ISSUES_FILE\" | |\n| if [[ \"$count\" -gt \"$PRINT_FINDING_LIMIT\" ]]; then | |\n| printf ' ... %s more finding(s) suppressed; set PRINT_FINDING_LIMIT to increase.\\n' \"$((count - PRINT_FINDING_LIMIT))\" | |\n| fi | |\n| if [[ \"$medium\" -gt 0 && \"$actionable\" -eq 0 ]]; then | |\n| printf '\\nNote: MEDIUM dependency/lockfile findings are exposure evidence, not proof of active persistence or current process execution. Confirm whether install/import scripts ran on this host before treating it as actively infected.\\n' | |\n| fi | |\n| } | |\n| usage() { | |\n| cat <<USAGE | |\n| Usage: $(basename \"$0\") [--exposure|--include-lockfiles] [--no-exposure] [DIR ...] | |\n| Run without arguments to scan likely local locations. Pass one or more directories | |\n| to scan only those paths. | |\n| Environment: | |\n| INCLUDE_LOCKFILE_SCAN=true Scan dependency and lockfiles for affected TanStack/Mistral/PyPI versions. Default: true. | |\n| EXIT_ON_MEDIUM=true Exit non-zero for MEDIUM exposure-only findings. Default: false. | |\n| FD_THREADS=1 Threads used by fd/fdfind when available. | |\n| PRINT_FINDING_LIMIT=200 Max findings printed to stdout. | |\n| USAGE | |\n| } | |\n| main() { | |\n| local root | |\n| while [[ \"$#\" -gt 0 ]]; do | |\n| case \"$1\" in | |\n| --help|-h) | |\n| usage | |\n| exit 0 | |\n| ;; | |\n| --include-lockfiles|--exposure) | |\n| INCLUDE_LOCKFILE_SCAN=true | |\n| shift | |\n| ;; | |\n| --no-exposure) | |\n| INCLUDE_LOCKFILE_SCAN=false | |\n| shift | |\n| ;; | |\n| --*) | |\n| printf 'Unknown option: %s\\n' \"$1\" >&2 | |\n| usage >&2 | |\n| exit 2 | |\n| ;; | |\n| *) | |\n| add_scan_root \"$1\" | |\n| shift | |\n| ;; | |\n| esac | |\n| done | |\n| [[ \"${#SCAN_ROOTS[@]}\" -eq 0 ]] && add_default_scan_roots | |\n| if [[ \"${#SCAN_ROOTS[@]}\" -eq 0 ]]; then | |\n| printf 'No valid scan roots provided.\\n' >&2 | |\n| exit 2 | |\n| fi | |\n| printf '%s----------------------------------------%s\\n' \"$YELLOW\" \"$NC\" | |\n| printf '%s Mini Shai-Hulud / TanStack + Mistral AI Audit%s\\n' \"$YELLOW\" \"$NC\" | |\n| printf '%s----------------------------------------%s\\n' \"$YELLOW\" \"$NC\" | |\n| printf 'Version: %s\\n' \"$SCRIPT_VERSION\" | |\n| if [[ -n \"$FILE_FINDER\" ]]; then | |\n| printf 'File search: %s (threads=%s)\\n' \"$FILE_FINDER\" \"$FD_THREADS\" | |\n| else | |\n| printf 'File search: find\\n' | |\n| fi | |\n| printf 'Dependency/lockfile exposure scan: %s\\n' \"$INCLUDE_LOCKFILE_SCAN\" | |\n| printf 'Scan roots:\\n' | |\n| for root in \"${SCAN_ROOTS[@]}\"; do | |\n| printf ' - %s\\n' \"$root\" | |\n| done | |\n| scan_candidate_files | |\n| scan_system_persistence_paths | |\n| scan_processes | |\n| scan_process_environments | |\n| scan_network_connections | |\n| scan_lockfiles_for_exposure | |\n| print_summary | |\n| if [[ \"$(actionable_count)\" -gt 0 ]]; then | |\n| exit 1 | |\n| fi | |\n| if [[ \"$EXIT_ON_MEDIUM\" == \"true\" && \"$(medium_count)\" -gt 0 ]]; then | |\n| exit 1 | |\n| fi | |\n| exit 0 | |\n| } | |\n| main \"$@\" |", "url": "https://wpnews.pro/news/mini-shai-hulud-tanstack-mistral-ai-supply-chain-audit-script", "canonical_source": "https://gist.github.com/beowolx2/a3ceeb18d1f1cec977d5cc6eaf41c96a", "published_at": "2026-05-12 13:55:14+00:00", "updated_at": "2026-06-07 01:13:11.815122+00:00", "lang": "en", "topics": ["ai-safety", "ai-infrastructure", "ai-tools", "mlops", "ai-ethics"], "entities": ["TanStack", "Mistral AI", "Shai-Hulud", "PyPI"], "alternates": {"html": "https://wpnews.pro/news/mini-shai-hulud-tanstack-mistral-ai-supply-chain-audit-script", "markdown": "https://wpnews.pro/news/mini-shai-hulud-tanstack-mistral-ai-supply-chain-audit-script.md", "text": "https://wpnews.pro/news/mini-shai-hulud-tanstack-mistral-ai-supply-chain-audit-script.txt", "jsonld": "https://wpnews.pro/news/mini-shai-hulud-tanstack-mistral-ai-supply-chain-audit-script.jsonld"}}