# Store-XSS in error message of build-dependencies

Stored XSS in GitLab CI job dependency error message: a malicious job name with an iframe srcdoc payload executes when viewing job-test details.

- Payout: hidden
- Severity: high
- Program: GitLab
- Found by (vendor credit): yvvdwf
- Found by: yvvdwf
- Disclosed: 2020-12-01
- CVE: CVE-2020-13340
- Write-up quality: 7/10
- Original: https://hackerone.com/reports/950190
- Library page: https://bugbountylibrary.com/r/h1%3A950190
- Tags: area:web domain:web impact:integrity kind:bounty platform:hackerone sev:high tech:ci-cd tech:ruby technique:source-review vuln:xss

**Target:** GitLab CI/CD job details page (build_details_entity failure_message)
**Root cause:** The CI job name is interpolated into the dependencies failure_message, which is marked html_safe in build_details_entity.rb and rendered without sanitization.
**Steps:**
1. Create empty project and register a runner
2. Add `.gitlab-ci.yml` with a job named `test<iframe srcdoc='<script src=.../alert.js></script>'></iframe>` producing an artifact with `expire_in: 1 second`
3. Add `job-test` with `dependencies: ["<same malicious job name>"]`
4. Wait for jobs to finish so the artifact expires and dependency resolution fails
5. Open job-test details; the failure_message renders the iframe and fires the script
**How found:** Researcher noted the dependencies validation feature is enabled by default on self-managed instances and inspected build_details_entity.rb, finding failure_message marked html_safe; crafted a job name that flows into the error message.
**Exploitation:** Attacker with project write access commits a crafted .gitlab-ci.yml; when a victim (e.g. maintainer) views the failed job-test detail page, the stored iframe srcdoc executes attacker JS in the GitLab origin, enabling actions on the victim's behalf.
**Escalation:** Uses `<iframe srcdoc>` to bypass gitlab.com CSP (per referenced #831962), though gitlab.com disables dependency validation by default.
**Insight:** CI/CD error messages that echo user-controlled job/dependency names are a common stored-XSS sink; grep serializers for html_safe on failure_message fields and test job names with HTML payloads.

