gcp-pubsub-create-push-subscription-can-pass-identity

pubsub.subscriptions.create (or pubsub.subscriptions.update) + iam.serviceAccounts.actAs on a push SA allows creating a push subscription that delivers the SA's OIDC token to a push endpoint, attaching the SA's identity to the event source.

derived gcp emits CanPassIdentity

match

A conjunctive graph pattern. Variables (?x) bind node ids; every clause must hold.

{'match_effective_permission': {'action': 'pubsub.subscriptions.create', 'resource_type': 'google.pubsub.Topic'}} {'match_effective_permission': {'action': 'iam.serviceAccounts.actAs', 'resource_type': 'google.iam.ServiceAccount'}}

where

both permissions held by ?principal ?sa is the target of iam.serviceAccounts.actAs

emit

source typeIdentity
target typeServiceAccount
source<principal>
target<push service account>
permissionspubsub.subscriptions.create iam.serviceAccounts.actAs
conditionsiam_permission role_compatibility
state logicACTIVE when both pubsub.subscriptions.create (or pubsub.subscriptions.update) and iam.serviceAccounts.actAs on the target SA are effectively granted and no deny policy blocks. CONDITIONAL(role_compatibility) when the actAs scope or role compatibility to the push SA is not confirmed. BLOCKED by IAM deny on either permission or an org policy that restricts actAs usage.

Narrative

{principal.name} can create a Pub/Sub push subscription (pubsub.subscriptions.create) with pushConfig.oidcToken.serviceAccountEmail set to {sa.name} and holds iam.serviceAccounts.actAs on {sa.name}, enabling delivery of {sa.name}'s OIDC token to an attacker-controlled push endpoint for extraction and replay.

Raw rule rules/derived/gcp/pubsub.yaml

id: gcp-pubsub-create-push-subscription-can-pass-identity
emits: CanPassIdentity
description: pubsub.subscriptions.create (or pubsub.subscriptions.update) + iam.serviceAccounts.actAs
  on a push SA allows creating a push subscription that delivers the SA's OIDC token to a push endpoint,
  attaching the SA's identity to the event source.
match:
- match_effective_permission:
    action: pubsub.subscriptions.create
    resource_type: google.pubsub.Topic
- match_effective_permission:
    action: iam.serviceAccounts.actAs
    resource_type: google.iam.ServiceAccount
where:
- both permissions held by ?principal
- ?sa is the target of iam.serviceAccounts.actAs
emit:
  source_type: Identity
  target_type: ServiceAccount
  source: <principal>
  target: <push service account>
  permissions:
  - pubsub.subscriptions.create
  - iam.serviceAccounts.actAs
  conditions:
  - iam_permission
  - role_compatibility
  state_logic: ACTIVE when both pubsub.subscriptions.create (or pubsub.subscriptions.update) and iam.serviceAccounts.actAs
    on the target SA are effectively granted and no deny policy blocks. CONDITIONAL(role_compatibility)
    when the actAs scope or role compatibility to the push SA is not confirmed. BLOCKED by IAM deny on
    either permission or an org policy that restricts actAs usage.
  confidence: 0.85
  derived_from:
  - 'effective-permission: pubsub.subscriptions.create (or .update) on Topic'
  - 'effective-permission: iam.serviceAccounts.actAs on ServiceAccount'
  false_positive_note: "The Pub/Sub Service Agent (service-<project-number>@gcp-sa-pubsub.iam.gserviceaccount.com)\
    \ must also hold iam.serviceAccounts.actAs on the push SA at delivery time \u2014 if the Service Agent\
    \ binding is absent or revoked, push delivery fails even if the creator has actAs. Do not emit unless\
    \ both permissions are confirmed on the same principal. The CanPassIdentity edge feeds credential-chains\
    \ when combined with ExposesCredential(subscription \u2192 push SA) and CredentialsFor(token \u2192\
    \ push SA)."
  narrative: '{principal.name} can create a Pub/Sub push subscription (pubsub.subscriptions.create) with
    pushConfig.oidcToken.serviceAccountEmail set to {sa.name} and holds iam.serviceAccounts.actAs on {sa.name},
    enabling delivery of {sa.name}''s OIDC token to an attacker-controlled push endpoint for extraction
    and replay.'
move · open · esc close