Skip to content

Cloud IAM Privilege Escalation: Attack Paths Defenders Must Know

Identity and Access Management is the new perimeter. With traditional network boundaries dissolved across multi-cloud environments, IAM misconfigurations have become the primary initial access vector in cloud breaches. Industry reports consistently show that over 75% of cloud security incidents involve IAM misconfigurations or excessive permissions, and the average organization has more than 40% of its cloud identities carrying unused privileged access. Attackers know this — and they are building tooling specifically to enumerate and exploit IAM weaknesses at scale.

This post maps the most critical privilege escalation paths across AWS, Azure, and GCP, provides detection queries for each, and offers a cross-cloud defense playbook that SOC teams can implement immediately.


AWS Privilege Escalation Paths

AWS IAM's flexibility is also its greatest risk surface. The combination of managed policies, inline policies, resource-based policies, and service-linked roles creates a permission model where dangerous escalation paths are easy to create and hard to spot.

1. iam:PassRole + lambda:CreateFunction

An attacker with iam:PassRole and lambda:CreateFunction permissions can create a Lambda function that assumes a high-privilege execution role. The attacker passes an administrator-level role to the function, deploys code that performs privileged actions (creating new IAM users, exfiltrating secrets from Secrets Manager), and invokes it. The Lambda service assumes the role on the attacker's behalf — bypassing the attacker's own limited permissions entirely.

Synthetic example — attacker creates a privileged Lambda from 198.51.100.23:

aws lambda create-function \
  --function-name exfil-func \
  --runtime python3.11 \
  --role arn:aws:iam::123456789012:role/AdminLambdaRole \
  --handler index.handler \
  --zip-file fileb://payload.zip \
  --region us-east-1

Defensive Takeaway

Restrict iam:PassRole to specific role ARNs using conditions. Never grant iam:PassRole with Resource: "*". Monitor CreateFunction API calls where the execution role carries administrative permissions.

2. iam:CreatePolicyVersion

A principal with iam:CreatePolicyVersion can create a new version of any customer-managed policy and set it as the default — effectively rewriting their own permissions to "Effect": "Allow", "Action": "*", "Resource": "*". This is a direct path to full account compromise without needing any other permission.

3. sts:AssumeRole Chaining

Cross-account trust relationships create transitive escalation paths. An attacker who compromises a role in Account A that is trusted by a privileged role in Account B can chain sts:AssumeRole calls to pivot across accounts. In complex multi-account environments, a chain of three or four hops can bridge from a low-privilege development account to a production administrator role.

AWS Detection — CloudTrail Queries

AWSCloudTrail
| where EventName in ("CreateFunction20150331", "CreatePolicyVersion",
    "AssumeRole", "PassRole")
| extend UserIdentity = tostring(parse_json(UserIdentityArn))
| extend SourceIP = SourceIpAddress
| where SourceIP !startswith "10." and SourceIP !startswith "172.16."
| project TimeGenerated, EventName, UserIdentity, SourceIP,
          RequestParameters
| sort by TimeGenerated desc
index=aws sourcetype=aws:cloudtrail
    eventName IN ("CreateFunction20150331", "CreatePolicyVersion",
    "AssumeRole", "PassRole")
| eval src_ip=sourceIPAddress
| where NOT cidrmatch("10.0.0.0/8", src_ip)
    AND NOT cidrmatch("172.16.0.0/12", src_ip)
| table _time eventName userIdentity.arn src_ip requestParameters
| sort -_time

Azure Privilege Escalation Paths

Azure's identity model spans Entra ID (formerly Azure AD), Azure RBAC, and resource-level access controls. The interaction between these layers creates escalation opportunities that are unique to the Microsoft ecosystem.

1. Entra ID Role Activation Abuse

Privileged Identity Management (PIM) allows just-in-time role activation — but if an attacker compromises an account that is eligible for a Global Administrator or Privileged Role Administrator assignment, they can self-activate the role. If PIM approval is not enforced or if the approver account is also compromised, the attacker gains permanent administrative control over the entire tenant.

2. Managed Identity Token Theft

Azure Managed Identities expose tokens via the Instance Metadata Service (IMDS) at http://169.254.169.254/metadata/identity/oauth2/token. An attacker with code execution on a VM or App Service can steal the managed identity's access token and use it from any location to access Azure resources — Storage Accounts, Key Vaults, SQL databases — at whatever privilege level the managed identity holds.

Synthetic example — token theft from compromised VM at 192.0.2.45:

curl -s -H "Metadata: true" \
  "http://169.254.169.254/metadata/identity/oauth2/token?api-version=2018-02-01&resource=https://management.azure.com/" \
  | jq '.access_token'

3. Subscription-Level Role Assignment

A principal with Microsoft.Authorization/roleAssignments/write at the subscription scope can assign themselves or any other identity the Owner or Contributor role on the entire subscription. This single permission escalates from limited resource access to full subscription control.

Azure Detection — Activity Log Queries

AzureActivity
| where OperationNameValue in (
    "Microsoft.Authorization/roleAssignments/write",
    "Microsoft.Authorization/elevateAccess/action")
| extend CallerIP = CallerIpAddress
| extend TargetRole = tostring(parse_json(Properties).requestbody)
| project TimeGenerated, Caller, CallerIP, OperationNameValue,
          TargetRole, SubscriptionId
| sort by TimeGenerated desc
index=azure sourcetype=azure:activity
    operationName IN (
    "Microsoft.Authorization/roleAssignments/write",
    "Microsoft.Authorization/elevateAccess/action")
| table _time caller callerIpAddress operationName
        properties.requestbody subscriptionId
| sort -_time

GCP Privilege Escalation Paths

Google Cloud Platform's IAM model uses a resource hierarchy (Organization → Folder → Project) with policy inheritance. Escalation paths often exploit the inheritance model or the permissive default behavior of service accounts.

1. setIamPolicy Abuse

A principal with resourcemanager.projects.setIamPolicy can modify the IAM policy on a project to grant themselves (or any other identity) the roles/owner role. This is the GCP equivalent of Azure's role assignment write — a single permission that unlocks full project control.

2. Service Account Key Creation

A principal with iam.serviceAccountKeys.create can generate a new key for any service account they have access to. If that service account holds elevated privileges (e.g., roles/editor or custom roles with broad permissions), the attacker now has persistent, credential-based access that survives the compromise of the original identity. Service account keys do not expire by default and are frequently overlooked in access reviews.

Synthetic example — key creation for privileged SA:

gcloud iam service-accounts keys create /tmp/sa-key.json \
  --iam-account=admin-sa@project-example.iam.gserviceaccount.com

3. Organization-Level Access

Principals with resourcemanager.organizations.setIamPolicy can modify IAM bindings at the organization level. Because GCP policies inherit downward, granting roles/owner at the organization scope gives full control over every folder, project, and resource in the entire GCP organization — a single API call to total compromise.

GCP Detection — Cloud Audit Log Queries

GCPAuditLogs
| where MethodName in ("SetIamPolicy",
    "google.iam.admin.v1.CreateServiceAccountKey")
| extend CallerIP = tostring(RequestMetadata.callerIp)
| extend PrincipalEmail = AuthenticationInfo.principalEmail
| where CallerIP != "192.168.0.0/16"
| project Timestamp, PrincipalEmail, CallerIP, MethodName,
          ResourceName
| sort by Timestamp desc
index=gcp sourcetype=gcp:audit
    methodName IN ("SetIamPolicy",
    "google.iam.admin.v1.CreateServiceAccountKey")
| table _time authenticationInfo.principalEmail
        requestMetadata.callerIp methodName resourceName
| sort -_time

Cross-Cloud Defense Playbook

IAM privilege escalation follows similar patterns regardless of cloud provider. The following checklist applies universally.

Least Privilege Audit Checklist

  1. Enumerate all identities with escalation-capable permissionsiam:PassRole, iam:CreatePolicyVersion, roleAssignments/write, setIamPolicy, and serviceAccountKeys.create are the critical ones. Remove them from every identity that does not have an explicit, documented business justification.
  2. Eliminate wildcard resource permissions — Any policy granting Action: "*" or Resource: "*" is an escalation waiting to happen. Replace with resource-specific ARNs, scopes, or resource names.
  3. Audit cross-account and cross-project trust relationships — Map every trust chain. Identify transitive paths that bridge from low-privilege to high-privilege environments. Remove unused trust relationships immediately.
  4. Enforce MFA and approval workflows on privileged role activation — AWS STS conditions, Azure PIM approval gates, and GCP Access Approval must be mandatory for any administrative action.
  5. Rotate and reduce service account credentials — Delete unused service account keys (GCP), rotate access keys (AWS), and prefer workload identity federation or managed identities over long-lived credentials everywhere possible.

IAM Policy Guardrails

Guardrail AWS Azure GCP
Deny wildcard admin SCP: Deny iam:* except breakglass Azure Policy: deny Owner assignment Org Policy: restrict roles/owner grants
Enforce MFA on privilege STS condition aws:MultiFactorAuthPresent PIM: require MFA on activation Access Approval + BeyondCorp
Block credential creation SCP: deny CreateAccessKey Conditional Access: block legacy auth Org Policy: disable SA key creation
Limit blast radius Permission boundaries per account Management group scoping Folder-level IAM boundaries

Monitoring Recommendations

  • Forward all IAM-related API calls to your SIEM with less than 5 minutes of latency
  • Build correlation rules that detect permission changes followed by high-privilege actions within a 15-minute window
  • Alert on any IAM change originating from an IP address outside your known corporate ranges (use RFC 5737 test ranges 192.0.2.0/24, 198.51.100.0/24, 203.0.113.0/24 for lab exercises)
  • Track service account and managed identity usage patterns — alert on first-time resource access or geographic anomalies

ATT&CK Technique Mapping

Technique ID Cloud IAM Relevance
Valid Accounts: Cloud Accounts T1078.004 Compromised IAM credentials used for initial access and lateral movement
Account Manipulation: Additional Cloud Roles T1098.003 Attacker assigns elevated roles to compromised or attacker-controlled identities
Abuse Elevation Control Mechanism T1548 Exploiting IAM permission gaps to escalate from limited to administrative access

These techniques are consistently observed in cloud intrusion campaigns. Mapping your detection coverage against them ensures your SOC can identify IAM-based escalation at every stage of the kill chain.


Next Steps


Level Up Your Cloud Security Skills

Cloud IAM security is a top-tier skill for SOC analysts, cloud engineers, and penetration testers. Industry certifications like AWS Certified Security — Specialty, AZ-500 (Azure Security Engineer), and Google Professional Cloud Security Engineer validate your ability to identify and remediate the escalation paths covered in this post. Pair certification study with hands-on practice in our Lab 8 and Lab 13 environments to build real detection and response muscle memory.