Detection rules › Kusto

High-Risk Cross-Cloud User Impersonation

Severity
medium
Time window
1d
Group by
IPAddress, RiskEventTypes, RiskEventTypes_V2, SourceIpAddress, UserPrincipalName, signInTime
Source
github.com/Azure/Azure-Sentinel

This detection focuses on identifying high-risk cross-cloud activities and sign-in anomalies that may indicate potential security threats. The query starts by analyzing Microsoft Entra ID Signin Logs to pinpoint instances where specific applications, risk levels, and result types align. It then correlates this information with relevant AWS CloudTrail events to identify activities across Azure and AWS environments.

MITRE ATT&CK coverage

Telemetry coverage

PlatformRecord / event type
AWSCloudTrail event AddUserToGroup: Adds an IAM user to the specified IAM group, granting the user the permissions attached to that group.
AWSCloudTrail event CreateAccessKey: Creates a new AWS access key pair (access key ID and secret access key) for the specified IAM user.
AWSCloudTrail event CreateGroup: Creates a new IAM group to which IAM users can be added to share a common set of permissions.
AWSCloudTrail event CreateRole: Creates a new IAM role with a specified trust policy, defining which principals can assume the role.
AWSCloudTrail event CreateUser: Creates a new IAM user in the AWS account with a specified user name.
AWSCloudTrail event CreateVirtualMFADevice: Creates a new virtual MFA device and returns the QR code seed for enrollment.
AWSCloudTrail event DeleteGroup: Deletes an IAM group, which must not have any users or attached policies before deletion.
AWSCloudTrail event DeleteLoginProfile: Deletes the password-based login profile for an IAM user, preventing console sign-in.
AWSCloudTrail event ChangePassword: Changes the password of the IAM user who is calling this operation.
AWSCloudTrail event CreateServiceSpecificCredential: Generates a set of credentials consisting of a user name and password that can be used to access the service specified in the request.
AWSCloudTrail event DeleteAccessKey: Deletes the access key pair associated with the specified IAM user.
AWSCloudTrail event DeleteGroupPolicy: Deletes the specified inline policy that is embedded in the specified IAM group.
AWSCloudTrail event DeleteRole: Deletes the specified role.
AWSCloudTrail event DeleteServiceSpecificCredential: Deletes the specified service-specific credential.
AWSCloudTrail event DeleteUser: Deletes the specified IAM user.
AWSCloudTrail event RemoveUserFromGroup: Removes the specified user from the specified group.
AWSCloudTrail event UploadServerCertificate: Uploads a server certificate entity for the Amazon Web Services account.
AWSCloudTrail event CreateGroup: Creates a group within the specified identity store.
AWSCloudTrail event CreateUser: Creates a user within the specified identity store.
AWSCloudTrail event DeleteGroup: Delete a group within an identity store given GroupId.
AWSCloudTrail event DeleteUser: Deletes a user within an identity store given UserId.
AWSCloudTrail event CreateUser: Creates a user in a Simple AD or Microsoft AD directory.
AWSCloudTrail event DeleteUser: Deletes the specified user from a Simple AD or Microsoft AD directory.
AWSCloudTrail event CreateGroup: Creates a group that can be used in WorkMail by calling the RegisterToWorkMail operation.
AWSCloudTrail event CreateOrganization: Creates a new WorkMail organization.
AWSCloudTrail event CreateUser: Creates a user who can be used in WorkMail by calling the RegisterToWorkMail operation.
AWSCloudTrail event DeleteGroup: Deletes a group from WorkMail.
AWSCloudTrail event DeleteUser: Deletes a user from WorkMail and all subsequent systems.
AWSCloudTrail event RegisterToWorkMail: Registers an existing and disabled user, group, or resource for WorkMail use by associating a mailbox and calendaring capabilities.
AWSCloudTrail event ResetPassword: Allows the administrator to reset the password for a user.
Entra IDSigninLogs sign-in event: Sign-in with an Identity Protection risk assessment
Entra IDSigninLogs sign-in event: Sign-in naming a target application

Rules detecting the same action

These rules filter on the same operation.

Rule body

id: f4a28082-2808-4783-9736-33c1ae117475
name: High-Risk Cross-Cloud User Impersonation 
description: |
    'This detection focuses on identifying high-risk cross-cloud activities and sign-in anomalies that may indicate potential security threats. The query starts by analyzing Microsoft Entra ID Signin Logs to pinpoint instances where specific applications, risk levels, and result types align. It then correlates this information with relevant AWS CloudTrail events to identify activities across Azure and AWS environments.'
severity: Medium
requiredDataConnectors:
  - connectorId: AWS
    dataTypes:
      - AWSCloudTrail
  - connectorId: AzureActiveDirectory
    dataTypes:
      - SigninLogs
queryFrequency: 1d
queryPeriod: 1d
triggerOperator: gt
triggerThreshold: 0
tactics:
  - PrivilegeEscalation
relevantTechniques:
  - T1134
  - T1078.002
  - T1078.004
query: |
  // Retrieve Azure AD SigninLogs within the last day
  SigninLogs 
  // Filter for specific AppDisplayNames, ResultType, and Risk Levels
  | where AppDisplayName in ("Azure Portal", "ADFS Trust", "Microsoft Azure PowerShell")
      and RiskLevelAggregated == "high"
      and RiskLevelDuringSignIn == "high"
  // Summarize AppDisplayNames by relevant attributes
  | extend Result = iff(ResultType == 0, "Successful Signin", "Failed Signin")
  | summarize make_set(AppDisplayName)
      by
      IPAddress,
      signInTime=TimeGenerated,
      UserPrincipalName,
      RiskEventTypes,
      RiskEventTypes_V2
  // Inner join with AWS CloudTrail events
  | join kind=inner (
      AWSCloudTrail
      | where isempty(ErrorMessage)
      | where EventSource in ("iam.amazonaws.com", "identitystore.amazonaws.com", "workmail.amazonaws.com", "workdocs.amazonaws.com")
      // List of AWS event names
      | where EventName in~ ("CreateRole", "DeleteRole", "CreateUser", "CreateAccessKey", "DeleteAccessKey", "CreateGroup", "AddUserToGroup", "ChangePassword", "DeleteGroup", "DeleteUser", "RemoveUserFromGroup", "CreateVirtualMFADevice", "DeleteLoginProfile", "CreateOrganization", "SetDefaultMailDomain", "SetMailUserDetails", "CreateMailUser", "ResetPassword", "RegisterToWorkMail", "DisableMailUsers", "EnableMailUsers", "DeleteServiceSpecificCredential", "CreateServiceSpecificCredential", "UpdateAccountEmailAddress", "DeleteGroupPolicy", "UploadServerCertificate")  
      // Summarize relevant attributes
      | summarize make_set(RequestParameters), make_set(ResponseElements)
          by
          SourceIpAddress,
          UserIdentityArn,
          UserIdentityType,
          EventName,
          EventTime=TimeGenerated,
          EventSource
      )
      on $left.IPAddress == $right.SourceIpAddress  
  // Calculate time difference in hours between AWS event and Azure sign-in
  | extend timedef = datetime_diff("hour", EventTime, signInTime)
  // Filter for time differences within a certain range
  | where timedef between (0 .. 8)
entityMappings:
  - entityType: IP
    fieldMappings:
      - identifier: Address
        columnName: SourceIpAddress
customDetails:
   AwsUser: UserIdentityArn
   RiskEventTypes: RiskEventTypes
   AzureUser: UserPrincipalName
   AWSEventName: EventName
kind: Scheduled
version: 1.0.1

Stages and Predicates

Stage 1: source

SigninLogs

Stage 2: where

| where AppDisplayName in ("Azure Portal", "ADFS Trust", "Microsoft Azure PowerShell")
    and RiskLevelAggregated == "high"
    and RiskLevelDuringSignIn == "high"

Stage 3: extend

| extend Result = iff(ResultType == 0, "Successful Signin", "Failed Signin")
Result =
ifResultType == 0"Successful Signin"
else"Failed Signin"

Stage 4: summarize

| summarize make_set(AppDisplayName)
    by
    IPAddress,
    signInTime=TimeGenerated,
    UserPrincipalName,
    RiskEventTypes,
    RiskEventTypes_V2

Stage 5: join

| join kind=inner (
    AWSCloudTrail
    | where isempty(ErrorMessage)
    | where EventSource in ("iam.amazonaws.com", "identitystore.amazonaws.com", "workmail.amazonaws.com", "workdocs.amazonaws.com")
    | where EventName in~ ("CreateRole", "DeleteRole", "CreateUser", "CreateAccessKey", "DeleteAccessKey", "CreateGroup", "AddUserToGroup", "ChangePassword", "DeleteGroup", "DeleteUser", "RemoveUserFromGroup", "CreateVirtualMFADevice", "DeleteLoginProfile", "CreateOrganization", "SetDefaultMailDomain", "SetMailUserDetails", "CreateMailUser", "ResetPassword", "RegisterToWorkMail", "DisableMailUsers", "EnableMailUsers", "DeleteServiceSpecificCredential", "CreateServiceSpecificCredential", "UpdateAccountEmailAddress", "DeleteGroupPolicy", "UploadServerCertificate")  
    | summarize make_set(RequestParameters), make_set(ResponseElements)
        by
        SourceIpAddress,
        UserIdentityArn,
        UserIdentityType,
        EventName,
        EventTime=TimeGenerated,
        EventSource
    )
    on $left.IPAddress == $right.SourceIpAddress

Stage 6: extend

| extend timedef = datetime_diff("hour", EventTime, signInTime)

Stage 7: where

| where timedef between (0 .. 8)

Indicators

These rows show field, operator, and value matches.

FieldKindValuesSearch
AppDisplayNamein
  • ADFS Trust
  • Azure Portal
  • Microsoft Azure PowerShell
field:"Application" kind:in
ErrorMessageis_null
  • (no value, null check)
field:"aws::errorMessage" kind:is_null
EventNamein
  • AddUserToGroup
  • ChangePassword
  • CreateAccessKey
  • CreateGroup
  • CreateMailUser
  • CreateOrganization
  • CreateRole
  • CreateServiceSpecificCredential
  • CreateUser
  • CreateVirtualMFADevice
  • DeleteAccessKey
  • DeleteGroup
  • DeleteGroupPolicy
  • DeleteLoginProfile
  • DeleteRole
  • DeleteServiceSpecificCredential
  • DeleteUser
  • DisableMailUsers
  • EnableMailUsers
  • RegisterToWorkMail
  • RemoveUserFromGroup
  • ResetPassword
  • SetDefaultMailDomain
  • SetMailUserDetails
  • UpdateAccountEmailAddress
  • UploadServerCertificate
field:"aws::eventName" kind:in
EventSourcein
  • iam.amazonaws.com
  • identitystore.amazonaws.com
  • workdocs.amazonaws.com
  • workmail.amazonaws.com
field:"aws::eventSource" kind:in
RiskLevelAggregatedeq
  • high
field:"RiskLevelAggregated" kind:eq value:"high"
RiskLevelDuringSignIneq
  • high
field:"RiskLevelDuringSignIn" kind:eq value:"high"
timedefge
  • 0
field:"timedef" kind:ge value:"0"
timedefle
  • 8
field:"timedef" kind:le value:"8"

Output fields

These fields are emitted when the rule matches.

FieldSource
IPAddresssummarize
RiskEventTypessummarize
RiskEventTypes_V2summarize
UserPrincipalNamesummarize
signInTimesummarize
timedefextend