🔍 Static Analysis Report - 2026-08-11
Analysis Summary
- Tools Used: zizmor, poutine, actionlint, runner-guard, syft, grype, yamllint, shellcheck
- Total Findings: 1660
- Workflows Scanned: 284
- Workflows Affected (zizmor/runner-guard/shellcheck): 21
- Container Images Scanned (syft/grype): 10
Findings by Tool
| Tool |
Total |
Critical |
High |
Medium |
Low |
| zizmor (security) |
9 |
0 |
0 |
0 |
8 (note) + 1 (warning) |
| poutine (supply chain) |
0 |
- |
- |
- |
- |
| actionlint (linting) |
0 |
- |
- |
- |
- |
| runner-guard (taint analysis) |
25 |
0 |
14 |
11 |
0 |
| syft (SBOM inventory) |
3798 packages / 10 images |
- |
- |
- |
- |
| grype (container CVEs) |
1625 |
67 |
436 |
766 |
172 (+142 negligible, 42 unknown) |
| yamllint (yaml linting) |
0 |
- |
- |
- |
- |
| shellcheck (shell linting) |
1 |
- |
- |
- |
- |
Clustered Findings by Tool and Type
Zizmor Security Findings
| Issue Type |
Severity |
Count |
Affected Workflows |
| github_action_from_unverified_creator_used |
note |
8 |
dataflow-pr-discussion-dataset.lock.yml, hippo-embed.lock.yml, super-linter.lock.yml, smoke-codex.lock.yml, copilot-setup-steps.yml, daily-elixir-credo-snippet-audit.lock.yml, link-check.yml (×2) |
| pr_runs_on_self_hosted |
warning |
1 |
smoke-copilot-arm.lock.yml |
All 8 unverified_creator findings already carry a # zizmor: ignore[...] suppression comment in-repo — they are informational only.
Poutine Supply Chain Findings
No findings — poutine scanned all 284 files and reported 0 issues.
Actionlint Linting Issues
No findings — actionlint checked 284 workflows and reported 0 issues.
Syft SBOM Inventory
| Image |
Packages |
Affected Workflows |
| ghcr.io/github/serena-mcp-server:sha-891c160 |
2314 |
workflows using Serena MCP server |
| ghcr.io/github/gh-aw-firewall/agent:0.27.44 |
532 |
firewall-enabled agentic workflows |
| ghcr.io/github/gh-aw-firewall/cli-proxy:0.27.44 |
348 |
firewall-enabled agentic workflows |
| ghcr.io/github/gh-aw-mcpg:v0.4.9 |
288 |
workflows using the gh-aw MCP gateway |
| ghcr.io/github/gh-aw-firewall/api-proxy:0.27.44 |
193 |
firewall-enabled agentic workflows |
| ghcr.io/github/gh-aw-node |
177 |
Node-based agent runner steps |
| grafana/mcp-grafana:1.0.0-alpine |
178 |
workflows using the Grafana MCP server |
| node:lts-alpine |
165 |
Node-based agent runner steps |
| ghcr.io/github/gh-aw-firewall/squid:0.27.44 |
63 |
firewall-enabled agentic workflows |
| ghcr.io/github/github-mcp-server:v1.9.0 |
40 |
workflows using the GitHub MCP server |
Runner-Guard Taint Analysis Findings
Runner-Guard Score: not reported in this run's output (no Score/Grade summary line emitted).
| Rule ID |
Name |
Severity |
Count |
Affected Workflows |
| RGS-012 |
Secret Exfiltration via Outbound HTTP Request |
High |
10 |
daily-model-inventory.lock.yml (×4), daily-byok-ollama-test.lock.yml (×3), visual-regression-checker.lock.yml (×2), docs-noob-tester.lock.yml (×1) |
| RGS-005 |
Excessive Permissions on Untrusted Trigger |
Medium |
9 |
ai-moderator.lock.yml (×5), q.lock.yml (×3), agentic_commands.yml (×1) |
| RGS-018 |
Suspicious Payload Execution Pattern |
High |
4 |
daily-sentrux-report.lock.yml, daily-byok-ollama-test.lock.yml, daily-cli-performance.lock.yml, smoke-claude.lock.yml |
| RGS-019 |
Step Output Interpolated in run Block |
Medium |
2 |
windows-cli-integration.yml, error-message-lint.yml |
Issues created: 3 new issues for the top RGS-012 findings (see below) — capped at the max-3-per-run limit. RGS-018, RGS-005, and RGS-019 occurrences were not filed this run to stay within the cap; they are tracked in cache-memory for follow-up in a future scan.
Grype Container Vulnerability Findings
| Package |
Severity |
Count (top) |
Affected Images |
| golang-1.24-go / golang-1.24-src |
Mixed |
48 each |
serena-mcp-server |
| libexpat1 |
Mixed |
43 |
serena-mcp-server, gh-aw-firewall/agent |
| python3.13 / python3.13-minimal / libpython3.13-stdlib / libpython3.13-minimal |
Mixed |
37 each |
serena-mcp-server |
| nodejs / libnode115 / libnode-dev |
Mixed |
34 each |
serena-mcp-server |
| node@22.23.1 |
High |
2 (CVE-2026-56846, CVE-2026-56848) |
ghcr.io/github/gh-aw-firewall/agent:0.27.44 — fixes available (22.23.2 / 24.18.1 / 26.5.1) |
| libcurl3t64-gnutls, perl, libc6, bind9-libs |
Mixed |
~29-31 each |
serena-mcp-server, gh-aw-firewall/agent |
67 Critical and 436 High severity CVEs were reported in total across all 10 images — dominated by base-OS packages in serena-mcp-server (1117 findings) and gh-aw-firewall/agent (367 findings), both of which appear to be running on older Debian/Ubuntu base layers with outstanding OS patches.
Yamllint YAML Linting Findings
No findings — yamllint scanned 284 files and reported 0 issues.
Shellcheck Shell Linting Findings
| Code |
Count |
Affected Workflows |
| SC2015 |
1 |
daily-vulnhunter-scan.lock.yml (step: "Prepare VulnHunter bundle") — `A && B |
Top Priority Issues
1. Grype: node@22.23.1 High-severity CVEs in gh-aw-firewall/agent image
- Tool: grype
- Count: 2 (CVE-2026-56846, CVE-2026-56848)
- Severity: High
- Affected:
ghcr.io/github/gh-aw-firewall/agent:0.27.44
- Description: The Node.js runtime bundled in the firewall agent image is vulnerable to two High-severity CVEs.
- Impact: This image runs in every firewall-enabled agentic workflow, so a fix benefits the whole fleet with a single base-image bump.
- Reference: (nvd.nist.gov/redacted), (nvd.nist.gov/redacted)
- Fix: bump bundled Node to 22.23.2, 24.18.1, or 26.5.1.
2. Runner-Guard RGS-012: Secret Exfiltration via Outbound HTTP Request
- Tool: runner-guard
- Count: 10 (most common high-severity finding this scan)
- Severity: High
- Affected: daily-model-inventory.lock.yml, daily-byok-ollama-test.lock.yml, visual-regression-checker.lock.yml, docs-noob-tester.lock.yml
- Description:
run: blocks with outbound HTTP requests to non-GitHub domains in jobs with secrets access.
- Impact: High-confidence indicator of credential exfiltration risk if a job is ever compromised via injection; on manual review of the 3 filed instances, the flagged commands look like legitimate public-API/localhost/verified-install-script traffic, but each needs a suppression or scope reduction to close the loop.
- Reference: this rule doesn't publish a public docs URL; see finding description embedded in the filed issues.
3. Zizmor: pr_runs_on_self_hosted
- Tool: zizmor
- Count: 1
- Severity: Warning
- Affected: smoke-copilot-arm.lock.yml
- Description: A pull-request-triggered job runs on a self-hosted-class runner (
ubuntu-24.04-arm).
- Impact: Untrusted PR code executing on non-ephemeral or org-visible runners can persist state or pivot to other jobs.
- Reference: (woodruffw.github.io/redacted)
Fix Suggestion for RGS-012 (Secret Exfiltration via Outbound HTTP Request)
Issue: Outbound HTTP requests to non-GitHub domains from run: blocks in jobs with secrets access
Severity: High
Affected Workflows: 4 workflows, 10 occurrences
Prompt to Copilot Agent:
You are fixing a security finding identified by runner-guard (rule RGS-012: Secret Exfiltration via
Outbound HTTP Request).
Vulnerability: A `run:` block issues an outbound HTTP request (curl/wget/httpie/fetch/requests) to a
domain other than github.com, api.github.com, or ghcr.io, inside a job that has access to secrets or
publishing capabilities.
Why it matters: this is the primary pattern used by attackers to exfiltrate stolen GitHub Actions
secrets once they've achieved code execution (via expression injection, fork PR checkout, or a
compromised action). An HTTP POST to an attacker-controlled domain carrying env vars or tokens is the
most common exfiltration vector, so any external HTTP call in a secrets-bearing job context is
treated as suspicious until proven otherwise.
Required fix, per flagged step:
1. Read the full `run:` block and identify exactly what data is sent in the request (query params,
POST body, headers).
2. Confirm none of that data derives from `secrets.*`, `env.*` values sourced from secrets, or
tokens/credentials of any kind.
3. If the call is a plain GET against a public, read-only resource (e.g. a public API index or a
verified installer script) with no secret data leaving the runner:
- Add a narrow suppression comment directly above the step explaining why it's safe, e.g.:
`# runner-guard: ignore[RGS-012] - GET against public read-only API, no secrets in job context`
- Prefer moving the step to a job/workflow that truly has no secrets access, if feasible.
4. If the call could carry secret data, remove the external call, replace it with a github.com/
api.github.com/ghcr.io-scoped equivalent, or drop the job's secrets access so the two never
co-occur.
5. Where the destination is actually `localhost`/`127.0.0.1` (e.g. polling a locally-started dev
server), note this explicitly in the suppression comment — it's not exfiltration since traffic
never leaves the runner.
Example:
Before:
```yaml
- name: Predownload models.dev API index
run: |
curl -fsS (models.dev/redacted) -o "$OUT/api.json"
After (confirmed benign, public read-only endpoint, no secrets in this job's env):
- name: Predownload models.dev API index
# runner-guard: ignore[RGS-012] - GET against public read-only API index, no secrets in job context
run: |
curl -fsS (models.dev/redacted) -o "$OUT/api.json"
Please apply this review-and-suppress-or-fix workflow to all affected workflows:
.github/workflows/daily-model-inventory.lock.yml,
.github/workflows/daily-byok-ollama-test.lock.yml,
.github/workflows/visual-regression-checker.lock.yml,
.github/workflows/docs-noob-tester.lock.yml
(Note: these are compiled .lock.yml files — the fix must be made in the corresponding source .md
workflow definition and then the lockfile recompiled, not edited directly.)
### All Findings Details
<details>
<summary><b>Detailed Findings by Workflow</b></summary>
#### daily-model-inventory.lock.yml
- **RGS-012** × 4 (lines 497, 1099, 1269, 1336) — Secret Exfiltration via Outbound HTTP Request (High). Reviewed instance at line 497: `curl -fsS (models.dev/redacted) — public read-only API, likely false positive pending suppression.
#### daily-byok-ollama-test.lock.yml
- **RGS-012** × 3 (lines 488, 496, 501) — outbound curl to GitHub Releases (checksum-verified installer) and localhost Ollama service — likely false positive.
- **RGS-018** × 1 (line 474) — Suspicious Payload Execution Pattern.
#### visual-regression-checker.lock.yml
- **RGS-012** × 2 (lines 527, 894) — polling `/dev/tcp/127.0.0.1/4321` (local docs preview server started in the same job) — likely false positive.
#### docs-noob-tester.lock.yml
- **RGS-012** × 1 (line 574) — Secret Exfiltration via Outbound HTTP Request (High), not yet manually reviewed.
#### daily-sentrux-report.lock.yml
- **RGS-018** × 1 (line 514) — Suspicious Payload Execution Pattern (High), not yet manually reviewed.
#### daily-cli-performance.lock.yml
- **RGS-018** × 1 (line 854) — Suspicious Payload Execution Pattern (High), not yet manually reviewed.
#### smoke-claude.lock.yml
- **RGS-018** × 1 (line 1388) — Suspicious Payload Execution Pattern (High), not yet manually reviewed.
#### ai-moderator.lock.yml
- **RGS-005** × 5 (line 1, job-level) — Excessive Permissions on Untrusted Trigger (Medium).
#### q.lock.yml
- **RGS-005** × 3 (line 1, job-level) — Excessive Permissions on Untrusted Trigger (Medium).
#### agentic_commands.yml
- **RGS-005** × 1 (line 1, job-level) — Excessive Permissions on Untrusted Trigger (Medium).
#### windows-cli-integration.yml
- **RGS-019** × 1 (line 645) — Step Output Interpolated in run Block (Medium).
#### error-message-lint.yml
- **RGS-019** × 1 (line 54) — Step Output Interpolated in run Block (Medium).
#### zizmor findings (informational, all suppressed in-repo)
- dataflow-pr-discussion-dataset.lock.yml:537, hippo-embed.lock.yml:469, super-linter.lock.yml:1791, smoke-codex.lock.yml:2405, copilot-setup-steps.yml:42, daily-elixir-credo-snippet-audit.lock.yml:484, link-check.yml:37, link-check.yml:46 — `github_action_from_unverified_creator_used` (note).
- smoke-copilot-arm.lock.yml:498 — `pr_runs_on_self_hosted` (warning).
#### daily-vulnhunter-scan.lock.yml
- **SC2015** (line 29) — `A && B || C` is not if-then-else; C may run when A is true.
</details>
### Historical Trends
Prior static-analysis reports exist as GitHub issues (#51310 for 2026-08-08, #51520 for 2026-08-09, #51692 for 2026-08-10) but no structured JSON was cached from those runs, so this is the first scan with full JSON persistence in cache-memory.
- **Previous runner-guard issue**: #51309 — `RGS-012` in `ab-testing-advisor.lock.yml` (+58 others), filed 2026-08-08, now **closed**.
- **This scan's RGS-012 findings** are in different files (daily-model-inventory.lock.yml, daily-byok-ollama-test.lock.yml, visual-regression-checker.lock.yml, docs-noob-tester.lock.yml) — no recurrence of the previously-closed finding; these are new instances of the same rule.
- Baseline established today for `security-scans/2026-08-11.json`; future scans should show deltas against this file.
#### New Issues
All findings this scan are new relative to the (sparse) prior cached record — no earlier scan's structured data existed to compare against.
#### Resolved Issues
Not determinable this run (no prior structured data cached). Once a second scan runs, `trends.json` will support real deltas.
### Recommendations
1. **Immediate**: Bump the Node.js runtime in `ghcr.io/github/gh-aw-firewall/agent:0.27.44` past 22.23.2/24.18.1/26.5.1 to close 2 High CVEs affecting every firewall-enabled workflow; triage the 67 Critical grype findings in `serena-mcp-server` and `gh-aw-firewall/agent` base images.
2. **Short-term**: Review and either suppress-with-justification or remediate the 10 RGS-012 and 4 RGS-018 High-severity runner-guard findings; fix the SC2015 shellcheck finding in daily-vulnhunter-scan.lock.yml.
3. **Long-term**: Reduce write-permission scope on the 9 RGS-005 (`Excessive Permissions on Untrusted Trigger`) findings in ai-moderator.lock.yml, q.lock.yml, and agentic_commands.yml; consider a scheduled base-image refresh cadence to keep grype's CVE backlog from growing.
4. **Prevention**: Add runner-guard suppression-comment conventions (mirroring zizmor's `# zizmor: ignore[...]`) to workflow authoring guidelines so reviewed false positives don't re-surface every scan.
### Next Steps
- [ ] Bump Node runtime in gh-aw-firewall/agent image (CVE-2026-56846, CVE-2026-56848)
- [ ] Review/suppress or fix the 3 filed RGS-012 issues (daily-model-inventory, daily-byok-ollama-test, visual-regression-checker)
- [ ] Triage remaining RGS-012 (docs-noob-tester.lock.yml) and RGS-018 (×4) findings not yet filed
- [ ] Reduce RGS-005 permission scope in ai-moderator.lock.yml, q.lock.yml, agentic_commands.yml
- [ ] Fix SC2015 in daily-vulnhunter-scan.lock.yml
- [ ] Consider adding all eight tools' suppression/allowlist conventions to workflow creation guidelines
> Generated by [📊 Static Analysis Report](https://github.com/github/gh-aw/actions/runs/31460155227) · agent · 150.9 AIC · ⌖ 33.6 AIC · ⊞ 11K · [◷](https://github.com/search?q=repo%3Agithub%2Fgh-aw+is%3Aissue+%22gh-aw-workflow-call-id%3A+github%2Fgh-aw%2Fstatic-analysis-report%22&type=issues)
> - [x] expires <!-- gh-aw-expires: 2026-08-18T05:25:02.507Z --> on Aug 17, 2026, 9:25 PM UTC-08:00
<!-- gh-aw-agentic-workflow: Static Analysis Report, engine: claude, model: agent, id: 31460155227, workflow_id: static-analysis-report, run: https://github.com/github/gh-aw/actions/runs/31460155227 -->
<!-- gh-aw-workflow-id: static-analysis-report -->
<!-- gh-aw-workflow-call-id: github/gh-aw/static-analysis-report -->
🔍 Static Analysis Report - 2026-08-11
Analysis Summary
Findings by Tool
Clustered Findings by Tool and Type
Zizmor Security Findings
All 8
unverified_creatorfindings already carry a# zizmor: ignore[...]suppression comment in-repo — they are informational only.Poutine Supply Chain Findings
No findings — poutine scanned all 284 files and reported 0 issues.
Actionlint Linting Issues
No findings — actionlint checked 284 workflows and reported 0 issues.
Syft SBOM Inventory
Runner-Guard Taint Analysis Findings
Runner-Guard Score: not reported in this run's output (no
Score/Gradesummary line emitted).Issues created: 3 new issues for the top RGS-012 findings (see below) — capped at the max-3-per-run limit. RGS-018, RGS-005, and RGS-019 occurrences were not filed this run to stay within the cap; they are tracked in cache-memory for follow-up in a future scan.
Grype Container Vulnerability Findings
67 Critical and 436 High severity CVEs were reported in total across all 10 images — dominated by base-OS packages in
serena-mcp-server(1117 findings) andgh-aw-firewall/agent(367 findings), both of which appear to be running on older Debian/Ubuntu base layers with outstanding OS patches.Yamllint YAML Linting Findings
No findings — yamllint scanned 284 files and reported 0 issues.
Shellcheck Shell Linting Findings
Top Priority Issues
1. Grype: node@22.23.1 High-severity CVEs in gh-aw-firewall/agent image
ghcr.io/github/gh-aw-firewall/agent:0.27.442. Runner-Guard RGS-012: Secret Exfiltration via Outbound HTTP Request
run:blocks with outbound HTTP requests to non-GitHub domains in jobs with secrets access.3. Zizmor: pr_runs_on_self_hosted
ubuntu-24.04-arm).Fix Suggestion for RGS-012 (Secret Exfiltration via Outbound HTTP Request)
Issue: Outbound HTTP requests to non-GitHub domains from
run:blocks in jobs with secrets accessSeverity: High
Affected Workflows: 4 workflows, 10 occurrences
Prompt to Copilot Agent:
After (confirmed benign, public read-only endpoint, no secrets in this job's env):
Please apply this review-and-suppress-or-fix workflow to all affected workflows:
.github/workflows/daily-model-inventory.lock.yml,
.github/workflows/daily-byok-ollama-test.lock.yml,
.github/workflows/visual-regression-checker.lock.yml,
.github/workflows/docs-noob-tester.lock.yml
(Note: these are compiled
.lock.ymlfiles — the fix must be made in the corresponding source.mdworkflow definition and then the lockfile recompiled, not edited directly.)