# GCP - AppEngine Privesc

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

## App Engine

Za više informacija o App Engine, pogledajte:

{{#ref}}
../gcp-services/gcp-app-engine-enum.md
{{#endref}}

### `appengine.applications.get`, `appengine.instances.get`, `appengine.instances.list`, `appengine.operations.get`, `appengine.operations.list`, `appengine.services.get`, `appengine.services.list`, `appengine.versions.create`, `appengine.versions.get`, `appengine.versions.list`, `cloudbuild.builds.get`,`iam.serviceAccounts.actAs`, `resourcemanager.projects.get`, `storage.objects.create`, `storage.objects.list`

To su potrebne dozvole za **deployovanje aplikacije koristeći `gcloud` cli**. Možda bi se **`get`** i **`list`** mogli **izbeći**.

Možete pronaći primere python koda na [https://github.com/GoogleCloudPlatform/python-docs-samples/tree/main/appengine](https://github.com/GoogleCloudPlatform/python-docs-samples/tree/main/appengine)

Podrazumevano, ime App servisa će biti **`default`**, i može postojati samo 1 instanca sa istim imenom.\
Da biste to promenili i kreirali drugu aplikaciju, u **`app.yaml`**, promenite vrednost korenskog ključa na nešto poput **`service: my-second-app`**
```bash
cd python-docs-samples/appengine/flexible/hello_world
gcloud app deploy #Upload and start application inside the folder
```
Dajte mu najmanje 10-15 minuta, ako ne uspe, pozovite **deploy another of times** i sačekajte nekoliko minuta.

> [!NOTE]
> **moguće je naznačiti Service Account koji će se koristiti**, ali podrazumevano se koristi App Engine podrazumevani SA.

URL aplikacije je nešto poput `https://<proj-name>.oa.r.appspot.com/` ili `https://<service_name>-dot-<proj-name>.oa.r.appspot.com`

### Ažurirajte ekvivalentne dozvole

Možda imate dovoljno dozvola da ažurirate AppEngine, ali ne i da kreirate novi. U tom slučaju, ovako možete ažurirati trenutni App Engine:
```bash
# Find the code of the App Engine in the buckets
gsutil ls

# Download code
mkdir /tmp/appengine2
cd /tmp/appengine2
## In this case it was found in this custom bucket but you could also use the
## buckets generated when the App Engine is created
gsutil cp gs://appengine-lab-1-gcp-labs-4t04m0i6-3a97003354979ef6/labs_appengine_1_premissions_privesc.zip .
unzip labs_appengine_1_premissions_privesc.zip

## Now modify the code..

## If you don't have an app.yaml, create one like:
cat >> app.yaml <<EOF
runtime: python312

entrypoint: gunicorn -b :\$PORT main:app

env_variables:
A_VARIABLE: "value"
EOF

# Deploy the changes
gcloud app deploy

# Update the SA if you need it (and if you have actas permissions)
gcloud app update --service-account=<sa>@$PROJECT_ID.iam.gserviceaccount.com
```
Ako ste **već kompromitovali AppEngine** i imate dozvolu **`appengine.applications.update`** i **actAs** nad servisnim nalogom koji možete koristiti, mogli biste da modifikujete servisni nalog koji koristi AppEngine sa:
```bash
gcloud app update --service-account=<sa>@$PROJECT_ID.iam.gserviceaccount.com
```
### `appengine.instances.enableDebug`, `appengine.instances.get`, `appengine.instances.list`, `appengine.operations.get`, `appengine.services.get`, `appengine.services.list`, `appengine.versions.get`, `appengine.versions.list`, `compute.projects.get`

Sa ovim dozvolama, moguće je **prijaviti se putem ssh u App Engine instancama** tipa **flexible** (ne standard). Neke od **`list`** i **`get`** dozvola **možda nisu zaista potrebne**.
```bash
gcloud app instances ssh --service <app-name> --version <version-id> <ID>
```
### `appengine.applications.update`, `appengine.operations.get`

Mislim da ovo samo menja pozadinsku SA koju će Google koristiti za postavljanje aplikacija, tako da ne mislim da možete iskoristiti ovo da ukradete servisni nalog.
```bash
gcloud app update --service-account=<sa_email>
```
### `appengine.versions.getFileContents`, `appengine.versions.update`

Nisam siguran kako da koristim ove dozvole ili da li su korisne (napominjem da kada promenite kod, nova verzija se kreira, tako da ne znam da li možete samo da ažurirate kod ili IAM ulogu jednog, ali pretpostavljam da biste trebali moći, možda menjajući kod unutar bucket-a??).

### Write Access over the buckets

Kao što je pomenuto, appengine verzije generišu neke podatke unutar bucket-a sa formatom imena: `staging.<project-id>.appspot.com`. Napominjem da nije moguće unapred preuzeti ovaj bucket jer GCP korisnici nisu ovlašćeni da generišu bucket-e koristeći naziv domena `appspot.com`.

Međutim, sa read & write pristupom ovom bucket-u, moguće je eskalirati privilegije na SA vezanu za AppEngine verziju praćenjem bucket-a i svaki put kada se izvrši promena, što je brže moguće modifikovati kod. Na ovaj način, kontejner koji se kreira iz ovog koda će **izvršiti backdoored kod**.

Za više informacija i **PoC proverite relevantne informacije sa ove stranice**:

{{#ref}}
gcp-storage-privesc.md
{{#endref}}

### Write Access over the Artifact Registry

Iako App Engine kreira docker slike unutar Artifact Registry. Testirano je da **čak i ako modifikujete sliku unutar ove usluge** i uklonite App Engine instancu (tako da se nova implementira) **izvršeni kod se ne menja**.\
Moguće je da izvođenjem **Race Condition napada kao sa bucket-ima može biti moguće prepisati izvršeni kod**, ali ovo nije testirano.

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