functions/Tenant/Search-HawkTenantEXOAuditLog.ps1
Function Search-HawkTenantEXOAuditLog { <# .SYNOPSIS Searches the admin audit logs for possible bad actor activities .DESCRIPTION Searches the Exchange admin audkit logs for a number of possible bad actor activies. * New inbox rules * Changes to user forwarding configurations * Changes to user mailbox permissions * Granting of impersonation rights .OUTPUTS File: Simple_New_InboxRule.csv Path: \ Description: cmdlets to create any new inbox rules in a simple to read format File: New_InboxRules.xml Path: \XML Description: Search results for any new inbox rules in CLI XML format File: _Investigate_Simple_New_InboxRule.csv Path: \ Description: cmdlets to create inbox rules that forward or delete email in a simple format File: _Investigate_New_InboxRules.xml Path: \XML Description: Search results for newly created inbox rules that forward or delete email in CLI XML File: _Investigate_New_InboxRules.txt Path: \ Description: Search results of newly created inbox rules that forward or delete email File: Simple_Forwarding_Changes.csv Path: \ Description: cmdlets that change forwarding settings in a simple to read format File: Forwarding_Changes.xml Path: \XML Description: Search results for cmdlets that change forwarding settings in CLI XML File: Forwarding_Recipients.csv Path: \ Description: List of unique Email addresses that were setup to recieve email via forwarding File: Simple_Mailbox_Permissions.csv Path: \ Description: Cmdlets that add permissions to users in a simple to read format File: Mailbox_Permissions.xml Path: \XML Description: Search results for cmdlets that change permissions in CLI XML File: _Investigate_Impersonation_Roles.csv Path: \ Description: List all users with impersonation rights if we find more than the default of one File: _Investigate_Impersonation_Roles.csv Path: \XML Description: List all users with impersonation rights if we find more than the default of one as CLI XML File: Impersonation_Rights.csv Path: \ Description: List all users with impersonation rights if we only find the default one File: Impersonation_Rights.csv Path: \XML Description: List all users with impersonation rights if we only find the default one as CLI XML .EXAMPLE Search-HawkTenantEXOAuditLog Searches the tenant audit logs looking for changes that could have been made in the tenant. #> Test-EXOConnection Send-AIEvent -Event "CmdRun" Out-LogFile "Searching EXO Audit Logs" -Action Out-LogFile "Searching Entire Admin Audit Log for Specific cmdlets" #Make sure our values are null $TenantInboxRules = $Null $TenantSetInboxRules = $Null $TenantRemoveInboxRules = $Null # Search for the creation of ANY inbox rules Out-LogFile "Searching for ALL Inbox Rules Created in the Shell" -action [array]$TenantInboxRules = Search-UnifiedAuditLog -RecordType ExchangeAdmin -Operations New-InboxRule -StartDate $Hawk.StartDate -EndDate $Hawk.EndDate # If we found anything report it and log it if ($TenantInboxRules.count -gt 0) { Out-LogFile ("Found " + $TenantInboxRules.count + " Inbox Rule(s) created from PowerShell") $TenantInboxRules | Get-SimpleAdminAuditLog | Out-MultipleFileType -fileprefix "Simple_New_InboxRule" -csv -json $TenantInboxRules | Out-MultipleFileType -fileprefix "New_InboxRules" -csv -json } # Search for the Modification of ANY inbox rules Out-LogFile "Searching for ALL Inbox Rules Modified in the Shell" -action [array]$TenantSetInboxRules = Search-AdminAuditLog -Cmdlets Set-InboxRule -StartDate $Hawk.StartDate -EndDate $Hawk.EndDate # If we found anything report it and log it if ($TenantSetInboxRules.count -gt 0) { Out-LogFile ("Found " + $TenantSetInboxRules.count + " Inbox Rule(s) created from PowerShell") $TenantSetInboxRules | Get-SimpleAdminAuditLog | Out-MultipleFileType -fileprefix "Simple_Set_InboxRule" -csv -json $TenantSetInboxRules | Out-MultipleFileType -fileprefix "Set_InboxRules" -csv -json } # Search for the Modification of ANY inbox rules Out-LogFile "Searching for ALL Inbox Rules Removed in the Shell" -action [array]$TenantRemoveInboxRules = Search-AdminAuditLog -Cmdlets Remove-InboxRule -StartDate $Hawk.StartDate -EndDate $Hawk.EndDate # If we found anything report it and log it if ($TenantRemoveInboxRules.count -gt 0) { Out-LogFile ("Found " + $TenantRemoveInboxRules.count + " Inbox Rule(s) created from PowerShell") $TenantRemoveInboxRules | Get-SimpleAdminAuditLog | Out-MultipleFileType -fileprefix "Simple_Remove_InboxRule" -csv -json $TenantRemoveInboxRules | Out-MultipleFileType -fileprefix "Remove_InboxRules" -csv -json } # Searching for interesting inbox rules Out-LogFile "Searching for Interesting Inbox Rules Created in the Shell" -action [array]$InvestigateInboxRules = Search-AdminAuditLog -StartDate $Hawk.StartDate -EndDate $Hawk.EndDate -cmdlets New-InboxRule -Parameters ForwardTo, ForwardAsAttachmentTo, RedirectTo, DeleteMessage # if we found a rule report it and output it to the _Investigate files if ($InvestigateInboxRules.count -gt 0) { Out-LogFile ("Found " + $InvestigateInboxRules.count + " Inbox Rules that should be investigated further.") -notice $InvestigateInboxRules | Get-SimpleAdminAuditLog | Out-MultipleFileType -fileprefix "_Investigate_Simple_New_InboxRule" -csv -json -Notice $InvestigateInboxRules | Out-MultipleFileType -fileprefix "_Investigate_New_InboxRules" -xml -txt -Notice } # Look for changes to user forwarding Out-LogFile "Searching for user Forwarding Changes" -action [array]$TenantForwardingChanges = Search-AdminAuditLog -Cmdlets Set-Mailbox -Parameters ForwardingAddress, ForwardingSMTPAddress -StartDate $Hawk.StartDate -EndDate $Hawk.EndDate if ($TenantForwardingChanges.count -gt 0) { Out-LogFile ("Found " + $TenantForwardingChanges.count + " Change(s) to user Email Forwarding") -notice $TenantForwardingChanges | Get-SimpleAdminAuditLog | Out-MultipleFileType -FilePrefix "Simple_Forwarding_Changes" -csv -json -Notice $TenantForwardingChanges | Out-MultipleFileType -FilePrefix "Forwarding_Changes" -xml -Notice # Make sure our output array is null [array]$Output = $null # Checking if addresses were added or removed # If added compile a list Foreach ($Change in $TenantForwardingChanges) { # Get the user object modified $user = ($Change.CmdletParameters | Where-Object ($_.name -eq "Identity")).value # Check the ForwardingSMTPAddresses first if ([string]::IsNullOrEmpty(($Change.CmdletParameters | Where-Object { $_.name -eq "ForwardingSMTPAddress" }).value)) { } # If not null then push the email address into $output else { [array]$Output = $Output + ($Change.CmdletParameters | Where-Object { $_.name -eq "ForwardingSMTPAddress" }) | Select-Object -Property @{Name = "UserModified"; Expression = { $user } }, @{Name = "TargetSMTPAddress"; Expression = { $_.value.split(":")[1] } } } # Check ForwardingAddress if ([string]::IsNullOrEmpty(($Change.CmdletParameters | Where-Object { $_.name -eq "ForwardingAddress" }).value)) { } else { # Here we get back a recipient object in EXO not an SMTP address # So we need to go track down the recipient object $recipient = Get-EXORecipient (($Change.CmdletParameters | Where-Object { $_.name -eq "ForwardingAddress" }).value) -ErrorAction SilentlyContinue # If we can't resolve the recipient we need to log that if ($null -eq $recipient) { Out-LogFile ("Unable to resolve forwarding Target Recipient " + ($Change.CmdletParameters | Where-Object { $_.name -eq "ForwardingAddress" })) -notice } # If we can resolve it then we need to push the address the mail was being set to into $output else { # Determine the type of recipient and handle as needed to get out the SMTP address Switch ($recipient.RecipientType) { # For mailcontact we needed the external email address MailContact { [array]$Output += $recipient | Select-Object -Property @{Name = "UserModified"; Expression = { $user } }; @{Name = "TargetSMTPAddress"; Expression = { $_.ExternalEmailAddress.split(":")[1] } } } # For all others I believe primary will work Default { [array]$Output += $recipient | Select-Object -Property @{Name = "UserModified"; Expression = { $user } }; @{Name = "TargetSMTPAddress"; Expression = { $_.PrimarySmtpAddress } } } } } } } # Output our email address user modified pairs Out-logfile ("Found " + $Output.count + " email addresses set to be forwarded mail") -notice $Output | Out-MultipleFileType -FilePrefix "Forwarding_Recipients" -csv -json -Notice } # Look for changes to mailbox permissions Out-LogFile "Searching for Mailbox Permissions Changes" -Action [array]$TenantMailboxPermissionChanges = Search-AdminAuditLog -StartDate $Hawk.StartDate -EndDate $Hawk.EndDate -cmdlets Add-MailboxPermission if ($TenantMailboxPermissionChanges.count -gt 0) { Out-LogFile ("Found " + $TenantMailboxPermissionChanges.count + " changes to mailbox permissions") $TenantMailboxPermissionChanges | Get-SimpleAdminAuditLog | Out-MultipleFileType -fileprefix "Simple_Mailbox_Permissions" -csv -json $TenantMailboxPermissionChanges | Out-MultipleFileType -fileprefix "Mailbox_Permissions" -xml ## TODO: Possibly check who was added with permissions and see how old their accounts are } # Look for change to impersonation access Out-LogFile "Searching Impersonation Access" -action [array]$TenantImpersonatingRoles = Get-ManagementRoleEntry "*\Impersonate-ExchangeUser" if ($TenantImpersonatingRoles.count -gt 1) { Out-LogFile ("Found " + $TenantImpersonatingRoles.count + " Impersonation Roles. Default is 1") -notice $TenantImpersonatingRoles | Out-MultipleFileType -fileprefix "_Investigate_Impersonation_Roles" -csv -json -xml -Notice } elseif ($TenantImpersonatingRoles.count -eq 0) { } else { $TenantImpersonatingRoles | Out-MultipleFileType -fileprefix "Impersonation_Roles" -csv -json -xml } $Output = $null # Search all impersonation roles for users that have access foreach ($Role in $TenantImpersonatingRoles) { [array]$Output += Get-ManagementRoleAssignment -Role $Role.role -GetEffectiveUsers -Delegating:$false } if ($Output.count -gt 1) { Out-LogFile ("Found " + $Output.count + " Users/Groups with Impersonation rights. Default is 1") -notice $Output | Out-MultipleFileType -fileprefix "Impersonation_Rights" -csv -json -xml $Output | Out-MultipleFileType -fileprefix "_Investigate_Impersonation_Rights" -csv -json -xml -Notice } elseif ($Output.count -eq 1) { Out-LogFile ("Found default number of Impersonation users") $Output | Out-MultipleFileType -fileprefix "Impersonation_Rights" -csv -json -xml } else { } } |