Cloud Pentesting (GCP)#
Initial Access & Reconnaissance#
Authentication Methods#
gcloud CLI Authentication (Current Standard):#
# Installation verification
gcloud version
# Update to latest version
gcloud components update
# USER AUTHENTICATION METHODS:
# Method 1: Interactive browser authentication (OAuth 2.0)
gcloud auth login
# Method 2: Device code flow (for headless/restricted environments)
gcloud auth login --no-launch-browser
# Follow the displayed URL and enter code
# Method 3: Application Default Credentials (ADC)
gcloud auth application-default login
# Used by client libraries and SDKs
# SERVICE ACCOUNT AUTHENTICATION:
# Method 4: Service account key file
gcloud auth activate-service-account --key-file=/path/to/key.json
# Method 5: Service account impersonation
gcloud auth activate-service-account SERVICE_ACCOUNT@PROJECT.iam.gserviceaccount.com \
--key-file=/path/to/key.json
# WORKLOAD IDENTITY (Modern Kubernetes authentication)
# Automatically configured for GKE workloads
# No explicit authentication needed from within cluster
# VERIFY AUTHENTICATION:
# Check current authenticated account
gcloud auth list
# Show active account details
gcloud config list
# Get current project
gcloud config get-value project
# Get access token (for API calls)
gcloud auth print-access-token
# Get identity token (for authenticated services)
gcloud auth print-identity-token
# SET CONFIGURATION:
# Set active project
gcloud config set project PROJECT_ID
# Set default region/zone
gcloud config set compute/region us-central1
gcloud config set compute/zone us-central1-a
# Create named configuration (multiple accounts)
gcloud config configurations create red-team-config
gcloud config configurations activate red-team-config
# OPSEC: OAuth authentication generates logs in Workspace if using Google Workspace
# Service account authentication is common for automation (less suspicious)
# ADC is used by applications (blends with normal app traffic)
Credential Storage & Security:#
# Credential locations:
# Linux/macOS: ~/.config/gcloud/
# Windows: %APPDATA%\gcloud\
# Key files:
# - credentials.db: Access tokens (SQLite database)
# - application_default_credentials.json: ADC tokens
# - legacy_credentials/: Older credential format
# - access_tokens.db: Cached access tokens
# View stored credentials
cat ~/.config/gcloud/credentials.db | strings | grep -i token
# Application Default Credentials location
cat ~/.config/gcloud/application_default_credentials.json
# Extract access token manually
sqlite3 ~/.config/gcloud/credentials.db "SELECT * FROM credentials;"
# OPSEC: Credential files contain refresh tokens (long-lived)
# Stealing credentials.db provides persistent access
# ADC credentials often have broad permissions
Service Account Key Management:#
# Service account keys are JSON files containing private keys
# NEVER commit to version control (common mistake)
# Example service account key structure:
{
"type": "service_account",
"project_id": "project-id",
"private_key_id": "key-id",
"private_key": "-----BEGIN PRIVATE KEY-----\n...",
"client_email": "sa-name@project-id.iam.gserviceaccount.com",
"client_id": "1234567890",
"auth_uri": "https://accounts.google.com/o/oauth2/auth",
"token_uri": "https://oauth2.googleapis.com/token",
"auth_provider_x509_cert_url": "https://www.googleapis.com/oauth2/v1/certs"
}
# Authenticate with service account key
gcloud auth activate-service-account --key-file=sa-key.json
# OPSEC: Service account keys are powerful and often over-permissioned
# Look for keys in:
# - Git repositories (.git/config, commit history)
# - Cloud Storage buckets
# - Application source code
# - CI/CD pipelines
# - Developer workstations
# - Docker images / container registries
GCP - Project Discovery & IAM Enumeration#
Project and Organization Discovery#
Organization Enumeration:
bash
# List accessible organizations (requires specific permissions)
gcloud organizations list
# Get organization details
gcloud organizations describe ORGANIZATION_ID
# Get organization IAM policy (requires resourcemanager.organizations.getIamPolicy)
gcloud organizations get-iam-policy ORGANIZATION_ID
# List folders in organization (hierarchical structure)
gcloud resource-manager folders list --organization=ORGANIZATION_ID
# Get folder IAM policy
gcloud resource-manager folders get-iam-policy FOLDER_ID
# OPSEC: Organization-level access is rare
# Most users only see project-level resources
# Organization visibility indicates privileged access or misconfig
Project Enumeration:
bash
# List all accessible projects
gcloud projects list
# Get detailed project information
gcloud projects describe PROJECT_ID
# Get project number (sometimes needed for APIs)
gcloud projects describe PROJECT_ID --format="value(projectNumber)"
# Get project IAM policy
gcloud projects get-iam-policy PROJECT_ID
# Format output for easier parsing
gcloud projects get-iam-policy PROJECT_ID --format=json > project-iam.json
# Filter for specific roles
gcloud projects get-iam-policy PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.role:roles/owner"
# List billing accounts associated with projects
gcloud billing projects describe PROJECT_ID
# Check if billing is enabled (disabled projects have limited functionality)
gcloud billing projects describe PROJECT_ID --format="value(billingEnabled)"
# Enumerate project metadata
gcloud compute project-info describe --project=PROJECT_ID
# Get project-wide SSH keys
gcloud compute project-info describe --project=PROJECT_ID \
--format="value(commonInstanceMetadata.items[0].value)"
# OPSEC: Project enumeration is normal for developers/admins
# Focus on projects with production-sounding names
# Billing-enabled projects are active targets
Active Project Context:
bash
# Set active project for subsequent commands
gcloud config set project PROJECT_ID
# Verify current project
gcloud config get-value project
# Quick project switching
export PROJECT_ID="target-project-id"
gcloud config set project $PROJECT_ID
# Use project flag in individual commands (alternative to setting default)
gcloud compute instances list --project=PROJECT_ID
# OPSEC: Project switching generates minimal logs
# All subsequent API calls tied to active project
IAM Enumeration Strategy#
Service Account Discovery & Analysis:
bash
# List all service accounts in project
gcloud iam service-accounts list --project=PROJECT_ID
# Get specific service account details
gcloud iam service-accounts describe SA_EMAIL --project=PROJECT_ID
# List keys for service account (key metadata, not actual keys)
gcloud iam service-accounts keys list \
--iam-account=SA_EMAIL \
--project=PROJECT_ID
# Check when keys were created (look for old/stale keys)
gcloud iam service-accounts keys list \
--iam-account=SA_EMAIL \
--project=PROJECT_ID \
--format="table(name,validAfterTime,validBeforeTime)"
# Get service account IAM policy (who can impersonate it)
gcloud iam service-accounts get-iam-policy SA_EMAIL --project=PROJECT_ID
# Critical: Check for overly permissive impersonation
gcloud iam service-accounts get-iam-policy SA_EMAIL \
--project=PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.role:roles/iam.serviceAccountUser OR bindings.role:roles/iam.serviceAccountTokenCreator"
# Find service accounts that can be impersonated by current user
for sa in $(gcloud iam service-accounts list --format="value(email)"); do
echo "Checking: $sa"
gcloud iam service-accounts get-iam-policy $sa \
--flatten="bindings[].members" \
--filter="bindings.members:user:$(gcloud config get-value account)" 2>/dev/null && \
echo " [+] Can interact with: $sa"
done
# PRIVILEGE ESCALATION: Create new key for service account (if you have permissions)
gcloud iam service-accounts keys create key.json \
--iam-account=SA_EMAIL \
--project=PROJECT_ID
# Use the newly created key
gcloud auth activate-service-account --key-file=key.json
# OPSEC: Service account key creation is logged
# Old service accounts with keys may be forgotten/unmonitored
# Default service accounts (compute, app engine) often over-permissioned
Role Analysis:
bash
# List all predefined roles
gcloud iam roles list
# Filter roles by name pattern
gcloud iam roles list --filter="name:*admin*"
# Get detailed role permissions
gcloud iam roles describe roles/owner
# List custom roles in project
gcloud iam roles list --project=PROJECT_ID
# Get custom role definition
gcloud iam roles describe ROLE_ID --project=PROJECT_ID
# Find dangerous permissions in custom roles
gcloud iam roles describe ROLE_ID --project=PROJECT_ID | \
grep -E "iam.serviceAccountKeys.create|iam.serviceAccounts.actAs|compute.instances.setMetadata"
# List all roles at organization level
gcloud iam roles list --organization=ORGANIZATION_ID
# OPSEC: Role enumeration is read-only and common
# Focus on custom roles (may have privilege escalation paths)
# Look for wildcard permissions: "resourcemanager.*", "iam.*", "compute.*"
IAM Policy Analysis (Critical for Privilege Escalation):
bash
# PROJECT-LEVEL IAM:
# Get complete project IAM policy
gcloud projects get-iam-policy PROJECT_ID --format=json
# Find all users with Owner role
gcloud projects get-iam-policy PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.role:roles/owner" \
--format="table(bindings.members)"
# Find all users with Editor role
gcloud projects get-iam-policy PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.role:roles/editor"
# Find service accounts with elevated privileges
gcloud projects get-iam-policy PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.members:serviceAccount:*" \
--format="table(bindings.role,bindings.members)"
# Check for allUsers or allAuthenticatedUsers (public access)
gcloud projects get-iam-policy PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.members:allUsers OR bindings.members:allAuthenticatedUsers"
# RESOURCE-LEVEL IAM:
# Get IAM policy for specific Compute Engine instance
gcloud compute instances get-iam-policy INSTANCE_NAME \
--zone=ZONE \
--project=PROJECT_ID
# Get IAM policy for Cloud Storage bucket
gsutil iam get gs://BUCKET_NAME
# Get IAM policy for Cloud Function
gcloud functions get-iam-policy FUNCTION_NAME --region=REGION
# Get IAM policy for Cloud Run service
gcloud run services get-iam-policy SERVICE_NAME --region=REGION
# CONDITIONAL IAM BINDINGS (modern feature):
# Check for condition-based access (time-based, attribute-based)
gcloud projects get-iam-policy PROJECT_ID --format=json | \
jq '.bindings[] | select(.condition != null)'
# OPSEC: IAM policy enumeration is normal administrative activity
# Extensive enumeration may trigger rate limits
# Focus on high-value roles: Owner, Editor, Service Account Admin
Impersonation and ActAs Permissions:
bash
# SERVICE ACCOUNT IMPERSONATION (Major Privilege Escalation Path):
# Check if you can impersonate service accounts
# Required permission: iam.serviceAccounts.actAs or iam.serviceAccounts.getAccessToken
# Test impersonation
gcloud iam service-accounts get-access-token SA_EMAIL
# If successful, use impersonated service account for operations
gcloud compute instances list \
--impersonate-service-account=SA_EMAIL \
--project=PROJECT_ID
# Generate access token as impersonated service account
gcloud auth print-access-token \
--impersonate-service-account=SA_EMAIL
# Run command as impersonated service account
gcloud projects get-iam-policy PROJECT_ID \
--impersonate-service-account=SA_EMAIL
# Chain impersonation (if SA1 can impersonate SA2)
gcloud compute instances list \
--impersonate-service-account=SA2_EMAIL \
--impersonate-service-account=SA1_EMAIL
# OPSEC: Impersonation is logged as the impersonated identity
# Audit logs show both impersonator and impersonated account
# Common in CI/CD pipelines and automation
Workload Identity Federation (Modern GCP Feature):
bash
# Workload Identity Federation allows external identities (AWS, Azure, GitHub)
# to authenticate to GCP without service account keys
# List Workload Identity Pools
gcloud iam workload-identity-pools list \
--location=global \
--project=PROJECT_ID
# Describe Workload Identity Pool
gcloud iam workload-identity-pools describe POOL_ID \
--location=global \
--project=PROJECT_ID
# List Workload Identity Providers
gcloud iam workload-identity-pools providers list \
--workload-identity-pool=POOL_ID \
--location=global \
--project=PROJECT_ID
# Get provider configuration
gcloud iam workload-identity-pools providers describe PROVIDER_ID \
--workload-identity-pool=POOL_ID \
--location=global \
--project=PROJECT_ID
# ATTACK VECTOR: If you control external identity (GitHub Actions, AWS role)
# You may be able to authenticate to GCP via Workload Identity Federation
# OPSEC: Workload Identity Federation is newer and may be less monitored
# Common in multi-cloud environments
# Check attribute conditions (may have weak validation)
IAM Recommender (Find Over-Privileged Accounts):
bash
# IAM Recommender suggests removing unused permissions
# Useful for attackers to identify valuable permissions
# List IAM recommendations
gcloud recommender recommendations list \
--project=PROJECT_ID \
--location=global \
--recommender=google.iam.policy.Recommender
# Get specific recommendation
gcloud recommender recommendations describe RECOMMENDATION_ID \
--project=PROJECT_ID \
--location=global \
--recommender=google.iam.policy.Recommender
# Insights show actual permission usage
gcloud recommender insights list \
--project=PROJECT_ID \
--location=global \
--insight-type=google.iam.policy.Insight
# OPSEC: Recommender data shows which permissions are actively used
# Unused permissions may indicate test accounts or over-provisioning
# Actively used permissions are likely required for operations
Policy Troubleshooter (Understand Permission Denials):
bash
# Policy Troubleshooter explains why access was granted/denied
# Useful for understanding privilege escalation paths
# Check if user has specific permission on resource
gcloud policy-troubleshoot iam \
--resource-name="//cloudresourcemanager.googleapis.com/projects/PROJECT_ID" \
--permission="resourcemanager.projects.setIamPolicy" \
--principal-email="user@example.com"
# OPSEC: Policy troubleshooter queries are logged
# Reveals which permissions you're testing
# Use sparingly to avoid detection
Asset Inventory (Comprehensive Resource Enumeration):
bash
# Cloud Asset Inventory provides unified view of all resources
# Requires cloudasset.assets.* permissions
# Search all assets in project
gcloud asset search-all-resources \
--scope=projects/PROJECT_ID \
--asset-types="*"
# Search for specific asset types
gcloud asset search-all-resources \
--scope=projects/PROJECT_ID \
--asset-types="compute.googleapis.com/Instance,storage.googleapis.com/Bucket"
# Search IAM policies across all resources
gcloud asset search-all-iam-policies \
--scope=projects/PROJECT_ID \
--query="policy:roles/owner"
# Find resources accessible by specific user
gcloud asset search-all-iam-policies \
--scope=projects/PROJECT_ID \
--query="policy:user:target@example.com"
# Export full asset inventory
gcloud asset export \
--project=PROJECT_ID \
--content-type=resource \
--output-path=gs://BUCKET/assets.json
# OPSEC: Asset API provides comprehensive view
# Single API for all resource types
# Requires elevated permissions but extremely valuable
Admin Activity Audit Log Analysis:
bash
# Audit logs reveal who has what permissions based on actual usage
# Requires logging.logEntries.list permission
# List recent admin activities
gcloud logging read "protoPayload.methodName=~SetIamPolicy" \
--project=PROJECT_ID \
--limit=50 \
--format=json
# Find recent service account key creations
gcloud logging read 'protoPayload.methodName="google.iam.admin.v1.CreateServiceAccountKey"' \
--project=PROJECT_ID \
--limit=20
# Find recent compute instance creations
gcloud logging read 'resource.type="gce_instance" AND protoPayload.methodName="v1.compute.instances.insert"' \
--project=PROJECT_ID \
--limit=20
# Find authentication events
gcloud logging read 'protoPayload.serviceName="iamcredentials.googleapis.com"' \
--project=PROJECT_ID \
--limit=50
# OPSEC: Log queries are themselves logged (meta-logging)
# Use filters to reduce noise
# Large log queries may trigger alerts
Enumerate Enabled APIs:
bash
# List enabled APIs and services in project
gcloud services list --enabled --project=PROJECT_ID
# Check if specific API is enabled
gcloud services list --enabled --filter="name:compute.googleapis.com" --project=PROJECT_ID
# Common high-value APIs to check:
# - compute.googleapis.com (Compute Engine)
# - storage-api.googleapis.com (Cloud Storage)
# - iam.googleapis.com (IAM)
# - cloudkms.googleapis.com (Key Management)
# - sqladmin.googleapis.com (Cloud SQL)
# - container.googleapis.com (GKE)
# PRIVILEGE ESCALATION: Enable APIs (if you have permissions)
gcloud services enable compute.googleapis.com --project=PROJECT_ID
# OPSEC: Enabled APIs indicate which services are in use
# Disabled APIs limit attack surface
# Enabling APIs generates logs and may trigger alerts
Quick Privilege Check Script:
bash
#!/bin/bash
# GCP Quick Privilege Enumeration
# Usage: ./gcp-priv-check.sh PROJECT_ID
PROJECT_ID=$1
echo "[*] GCP Privilege Enumeration for $PROJECT_ID"
echo ""
echo "[+] Current Identity:"
gcloud config get-value account
echo ""
echo "[+] Current Project:"
gcloud config get-value project
echo ""
echo "[+] Testing High-Value Permissions:"
# Test Owner role
echo -n " - resourcemanager.projects.setIamPolicy (Owner): "
gcloud projects get-iam-policy $PROJECT_ID &>/dev/null && echo "YES" || echo "NO"
# Test service account key creation
echo -n " - iam.serviceAccountKeys.create: "
gcloud iam service-accounts keys list --iam-account=test@$PROJECT_ID.iam.gserviceaccount.com &>/dev/null && echo "YES" || echo "NO"
# Test compute instance creation
echo -n " - compute.instances.create: "
gcloud compute instances list --project=$PROJECT_ID &>/dev/null && echo "YES (list)" || echo "NO"
# Test storage bucket access
echo -n " - storage.buckets.list: "
gsutil ls -p $PROJECT_ID &>/dev/null && echo "YES" || echo "NO"
# Test service account impersonation
echo ""
echo "[+] Checking Service Account Impersonation:"
for sa in $(gcloud iam service-accounts list --format="value(email)" --project=$PROJECT_ID 2>/dev/null); do
if gcloud iam service-accounts get-access-token $sa &>/dev/null; then
echo " [!] Can impersonate: $sa"
fi
done
echo ""
echo "[+] High-Privilege Service Accounts:"
gcloud projects get-iam-policy $PROJECT_ID \
--flatten="bindings[].members" \
--filter="bindings.role:roles/owner OR bindings.role:roles/editor" \
--format="table(bindings.role,bindings.members)" 2>/dev/null | grep serviceAccount
echo ""
echo "[+] Enabled APIs:"
gcloud services list --enabled --project=$PROJECT_ID --format="value(config.name)" | head -10
echo ""
echo "[*] Enumeration Complete"
Make script executable and run:#
chmod +x gcp-priv-check.sh
./gcp-priv-check.sh my-project-id