azure-nsg-join-action-escalation

Principal with join/action on an NSG they control can re-associate (replace) the NSG on a target subnet or NIC, bypassing the original NSG's security rules. This is an NSG-specific escalation primitive that does not decompose into generic can-control or credential chains.

derived azure emits CanModifyConfiguration

match (effective permission)

{ "action": "Microsoft.Network/networkSecurityGroups/join/action", "scope_type": "resource|resourceGroup|subscription" }

emit

source typeIdentity
target typeFirewall
source<principal>
target<NSG node (Firewall)>
permissionsMicrosoft.Network/networkSecurityGroups/join/action
conditionsiam_permission deny_assignment
state logicACTIVE if the principal's effective permission at the NSG scope includes join/action and no deny assignment covers it; BLOCKED if a deny assignment covers join/action at the NSG, RG, or subscription scope. This capability is CONDITIONAL: it requires the principal to also control a permissive NSG (CanModifyConfiguration on that NSG), which is the actual foothold enabling subnet-level firewall bypass. The edge represents the association capability; the blast radius materializes when combined with NSG rule control.

Narrative

{principal.name} can associate/re-associate NSG {target.name} with subnets and network interfaces (Microsoft.Network/networkSecurityGroups/join/action). If the principal controls a permissive NSG, they can replace a production subnet's NSG, effectively overriding all existing firewall protections on that subnet.

Raw rule rules/derived/azure/nsg.yaml

id: azure-nsg-join-action-escalation
emits: CanModifyConfiguration
description: Principal with join/action on an NSG they control can re-associate (replace) the NSG on a
  target subnet or NIC, bypassing the original NSG's security rules. This is an NSG-specific escalation
  primitive that does not decompose into generic can-control or credential chains.
applies_to:
- azure
match_effective_permission:
  action: Microsoft.Network/networkSecurityGroups/join/action
  scope_type: resource|resourceGroup|subscription
emit:
  source_type: Identity
  target_type: Firewall
  source: <principal>
  target: <NSG node (Firewall)>
  permissions:
  - Microsoft.Network/networkSecurityGroups/join/action
  conditions:
  - iam_permission
  - deny_assignment
  state_logic: 'ACTIVE if the principal''s effective permission at the NSG scope includes join/action
    and no deny assignment covers it; BLOCKED if a deny assignment covers join/action at the NSG, RG,
    or subscription scope. This capability is CONDITIONAL: it requires the principal to also control a
    permissive NSG (CanModifyConfiguration on that NSG), which is the actual foothold enabling subnet-level
    firewall bypass. The edge represents the association capability; the blast radius materializes when
    combined with NSG rule control.'
  confidence: 0.88
  derived_from:
  - '<RBAC effective permission: join/action at NSG scope>'
  false_positive_note: "join/action alone is not a full compromise path; it represents the ability to\
    \ associate the NSG with subnets/NICs. The attacker must also control (or have CanModifyConfiguration\
    \ on) a permissive NSG to exploit this. This rule emits a CanModifyConfiguration edge capturing the\
    \ NSG-level capability; downstream rules (attack-path linchpins) compose this with attacker-controlled\
    \ NSG facts to infer subnet-level compromise. A deny assignment blocking join/action \u2192 BLOCKED."
  narrative: '{principal.name} can associate/re-associate NSG {target.name} with subnets and network interfaces
    (Microsoft.Network/networkSecurityGroups/join/action). If the principal controls a permissive NSG,
    they can replace a production subnet''s NSG, effectively overriding all existing firewall protections
    on that subnet.'
move · open · esc close