# AWS - S3 Enum non authentifié

{{#include ../../../banners/hacktricks-training.md}}

## S3 Buckets Publics

Un bucket est considéré comme **“public”** si **tout utilisateur peut lister le contenu** du bucket, et **“privé”** si le contenu du bucket peut **être listé ou écrit uniquement par certains utilisateurs**.

Les entreprises peuvent avoir des **permissions de buckets mal configurées** donnant accès soit à tout, soit à tous les utilisateurs authentifiés dans AWS dans n'importe quel compte (donc à n'importe qui). Notez que même avec de telles mauvaises configurations, certaines actions peuvent ne pas être possibles car les buckets peuvent avoir leurs propres listes de contrôle d'accès (ACL).

**Découvrez les mauvaises configurations AWS-S3 ici :** [**http://flaws.cloud**](http://flaws.cloud/) **et** [**http://flaws2.cloud/**](http://flaws2.cloud)

### Trouver des Buckets AWS

Différentes méthodes pour trouver quand une page web utilise AWS pour stocker certaines ressources :

#### Énumération & OSINT :

- Utiliser le plugin de navigateur **wappalyzer**
- Utiliser burp (**spidering** le web) ou en naviguant manuellement à travers la page, toutes les **ressources** **chargées** seront sauvegardées dans l'historique.
- **Vérifiez les ressources** dans des domaines comme :

```
http://s3.amazonaws.com/[bucket_name]/
http://[bucket_name].s3.amazonaws.com/
```

- Vérifiez les **CNAMES** car `resources.domain.com` pourrait avoir le CNAME `bucket.s3.amazonaws.com`
- Vérifiez [https://buckets.grayhatwarfare.com](https://buckets.grayhatwarfare.com/), un site avec déjà des **buckets ouverts découverts**.
- Le **nom du bucket** et le **nom de domaine du bucket** doivent être **les mêmes.**
- **flaws.cloud** est en **IP** 52.92.181.107 et si vous y allez, cela vous redirige vers [https://aws.amazon.com/s3/](https://aws.amazon.com/s3/). De plus, `dig -x 52.92.181.107` donne `s3-website-us-west-2.amazonaws.com`.
- Pour vérifier qu'il s'agit d'un bucket, vous pouvez également **visiter** [https://flaws.cloud.s3.amazonaws.com/](https://flaws.cloud.s3.amazonaws.com/).

#### Brute-Force

Vous pouvez trouver des buckets en **brute-forçant des noms** liés à l'entreprise que vous testez :

- [https://github.com/sa7mon/S3Scanner](https://github.com/sa7mon/S3Scanner)
- [https://github.com/clario-tech/s3-inspector](https://github.com/clario-tech/s3-inspector)
- [https://github.com/jordanpotti/AWSBucketDump](https://github.com/jordanpotti/AWSBucketDump) (Contient une liste avec des noms de buckets potentiels)
- [https://github.com/fellchase/flumberboozle/tree/master/flumberbuckets](https://github.com/fellchase/flumberboozle/tree/master/flumberbuckets)
- [https://github.com/smaranchand/bucky](https://github.com/smaranchand/bucky)
- [https://github.com/tomdev/teh_s3_bucketeers](https://github.com/tomdev/teh_s3_bucketeers)
- [https://github.com/RhinoSecurityLabs/Security-Research/tree/master/tools/aws-pentest-tools/s3](https://github.com/RhinoSecurityLabs/Security-Research/tree/master/tools/aws-pentest-tools/s3)
- [https://github.com/Eilonh/s3crets_scanner](https://github.com/Eilonh/s3crets_scanner)
- [https://github.com/belane/CloudHunter](https://github.com/belane/CloudHunter)

<pre class="language-bash"><code class="lang-bash"># Générer une liste de mots pour créer des permutations
curl -s https://raw.githubusercontent.com/cujanovic/goaltdns/master/words.txt > /tmp/words-s3.txt.temp
curl -s https://raw.githubusercontent.com/jordanpotti/AWSBucketDump/master/BucketNames.txt >>/tmp/words-s3.txt.temp
cat /tmp/words-s3.txt.temp | sort -u > /tmp/words-s3.txt

# Générer une liste de mots basée sur les domaines et sous-domaines à tester
## Écrire ces domaines et sous-domaines dans subdomains.txt
cat subdomains.txt > /tmp/words-hosts-s3.txt
cat subdomains.txt | tr "." "-" >> /tmp/words-hosts-s3.txt
cat subdomains.txt | tr "." "\n" | sort -u >> /tmp/words-hosts-s3.txt

# Créer des permutations basées sur une liste avec les domaines et sous-domaines à attaquer
goaltdns -l /tmp/words-hosts-s3.txt -w /tmp/words-s3.txt -o /tmp/final-words-s3.txt.temp
## L'outil précédent est spécialisé dans la création de permutations pour les sous-domaines, filtrons cette liste
<strong>### Supprimer les lignes se terminant par "."
</strong>cat /tmp/final-words-s3.txt.temp | grep -Ev "\.$" > /tmp/final-words-s3.txt.temp2
### Créer une liste sans TLD
cat /tmp/final-words-s3.txt.temp2 | sed -E 's/\.[a-zA-Z0-9]+$//' > /tmp/final-words-s3.txt.temp3
### Créer une liste sans points
cat /tmp/final-words-s3.txt.temp3 | tr -d "." > /tmp/final-words-s3.txt.temp4http://phantom.s3.amazonaws.com/
### Créer une liste sans tirets
cat /tmp/final-words-s3.txt.temp3 | tr "." "-" > /tmp/final-words-s3.txt.temp5

## Générer la liste de mots finale
cat /tmp/final-words-s3.txt.temp2 /tmp/final-words-s3.txt.temp3 /tmp/final-words-s3.txt.temp4 /tmp/final-words-s3.txt.temp5 | grep -v -- "-\." | awk '{print tolower($0)}' | sort -u > /tmp/final-words-s3.txt

## Appeler s3scanner
s3scanner --threads 100 scan --buckets-file /tmp/final-words-s3.txt  | grep bucket_exists
</code></pre>

#### Loot S3 Buckets

Étant donné des buckets S3 ouverts, [**BucketLoot**](https://github.com/redhuntlabs/BucketLoot) peut automatiquement **chercher des informations intéressantes**.

### Trouver la Région

Vous pouvez trouver toutes les régions prises en charge par AWS dans [**https://docs.aws.amazon.com/general/latest/gr/s3.html**](https://docs.aws.amazon.com/general/latest/gr/s3.html)

#### Par DNS

Vous pouvez obtenir la région d'un bucket avec un **`dig`** et **`nslookup`** en effectuant une **demande DNS de l'IP découverte** :
```bash
dig flaws.cloud
;; ANSWER SECTION:
flaws.cloud.    5    IN    A    52.218.192.11

nslookup 52.218.192.11
Non-authoritative answer:
11.192.218.52.in-addr.arpa name = s3-website-us-west-2.amazonaws.com.
```
Vérifiez que le domaine résolu contient le mot "website".\
Vous pouvez accéder au site web statique en allant à : `flaws.cloud.s3-website-us-west-2.amazonaws.com`\
ou vous pouvez accéder au bucket en visitant : `flaws.cloud.s3-us-west-2.amazonaws.com`

#### En essayant

Si vous essayez d'accéder à un bucket, mais dans le **nom de domaine vous spécifiez une autre région** (par exemple, le bucket est dans `bucket.s3.amazonaws.com` mais vous essayez d'accéder à `bucket.s3-website-us-west-2.amazonaws.com`, alors vous serez **indiqué vers l'emplacement correct** :

![](<../../../images/image (106).png>)

### Énumération du bucket

Pour tester l'ouverture du bucket, un utilisateur peut simplement entrer l'URL dans son navigateur web. Un bucket privé répondra par "Accès refusé". Un bucket public listera les 1 000 premiers objets qui ont été stockés.

Ouvert à tous :

![](<../../../images/image (201).png>)

Privé :

![](<../../../images/image (83).png>)

Vous pouvez également vérifier cela avec le cli :
```bash
#Use --no-sign-request for check Everyones permissions
#Use --profile <PROFILE_NAME> to indicate the AWS profile(keys) that youwant to use: Check for "Any Authenticated AWS User" permissions
#--recursive if you want list recursivelyls
#Opcionally you can select the region if you now it
aws s3 ls s3://flaws.cloud/ [--no-sign-request] [--profile <PROFILE_NAME>] [ --recursive] [--region us-west-2]
```
Si le bucket n'a pas de nom de domaine, lors de la tentative de l'énumérer, **mettez uniquement le nom du bucket** et non l'ensemble du domaine AWSs3. Exemple : `s3://<BUCKETNAME>`

### Modèle d'URL publique
```
https://{user_provided}.s3.amazonaws.com
```
### Obtenir l'ID de compte à partir d'un Bucket public

Il est possible de déterminer un compte AWS en tirant parti de la nouvelle **`S3:ResourceAccount`** **clé de condition de politique**. Cette condition **restreint l'accès en fonction du bucket S3** dans lequel se trouve un compte (d'autres politiques basées sur le compte restreignent en fonction du compte dans lequel se trouve le principal demandeur).\
Et parce que la politique peut contenir des **caractères génériques**, il est possible de trouver le numéro de compte **un chiffre à la fois**.

Cet outil automatise le processus :
```bash
# Installation
pipx install s3-account-search
pip install s3-account-search
# With a bucket
s3-account-search arn:aws:iam::123456789012:role/s3_read s3://my-bucket
# With an object
s3-account-search arn:aws:iam::123456789012:role/s3_read s3://my-bucket/path/to/object.ext
```
Cette technique fonctionne également avec les URL de l'API Gateway, les URL Lambda, les ensembles de données Data Exchange et même pour obtenir la valeur des tags (si vous connaissez la clé du tag). Vous pouvez trouver plus d'informations dans la [**recherche originale**](https://blog.plerion.com/conditional-love-for-aws-metadata-enumeration/) et l'outil [**conditional-love**](https://github.com/plerionhq/conditional-love/) pour automatiser cette exploitation.

### Confirmer qu'un bucket appartient à un compte AWS

Comme expliqué dans [**cet article de blog**](https://blog.plerion.com/things-you-wish-you-didnt-need-to-know-about-s3/)**, si vous avez les permissions pour lister un bucket**, il est possible de confirmer un accountID auquel le bucket appartient en envoyant une requête comme :
```bash
curl -X GET "[bucketname].amazonaws.com/" \
-H "x-amz-expected-bucket-owner: [correct-account-id]"

<?xml version="1.0" encoding="UTF-8"?>
<ListBucketResult xmlns="http://s3.amazonaws.com/doc/2006-03-01/">...</ListBucketResult>
```
Si l'erreur est un "Accès refusé", cela signifie que l'ID de compte était incorrect.

### Utilisation des e-mails pour l'énumération du compte root

Comme expliqué dans [**cet article de blog**](https://blog.plerion.com/things-you-wish-you-didnt-need-to-know-about-s3/), il est possible de vérifier si une adresse e-mail est liée à un compte AWS en **essayant d'accorder des permissions à une e-mail** sur un bucket S3 via des ACL. Si cela ne déclenche pas d'erreur, cela signifie que l'e-mail est un utilisateur root d'un compte AWS :
```python
s3_client.put_bucket_acl(
Bucket=bucket_name,
AccessControlPolicy={
'Grants': [
{
'Grantee': {
'EmailAddress': 'some@emailtotest.com',
'Type': 'AmazonCustomerByEmail',
},
'Permission': 'READ'
},
],
'Owner': {
'DisplayName': 'Whatever',
'ID': 'c3d78ab5093a9ab8a5184de715d409c2ab5a0e2da66f08c2f6cc5c0bdeadbeef'
}
}
)
```
## Références

- [https://www.youtube.com/watch?v=8ZXRw4Ry3mQ](https://www.youtube.com/watch?v=8ZXRw4Ry3mQ)
- [https://cloudar.be/awsblog/finding-the-account-id-of-any-public-s3-bucket/](https://cloudar.be/awsblog/finding-the-account-id-of-any-public-s3-bucket/)

{{#include ../../../banners/hacktricks-training.md}}
