Port Scan
Id | b2c5907b-1040-4692-9802-9946031017e8 |
Rulename | Port Scan |
Description | Identifies a source IP scanning multiple open ports on Azure Firewall. This can indicate malicious scanning of ports by an attacker, trying to reveal open ports in the organization that can be compromised for initial access. Configurable Parameters: - Port scan time - the time range to look for multiple ports scanned. Default is set to 30 seconds. - Minimum different ports threshold - alert only if more than this number of ports scanned. Default is set to 100. |
Severity | Medium |
Tactics | Discovery |
Techniques | T1046 |
Required data connectors | AzureFirewall |
Kind | Scheduled |
Query frequency | 1d |
Query period | 1d |
Trigger threshold | 1 |
Trigger operator | gt |
Source Uri | https://github.com/Azure/Azure-Sentinel/blob/master/Solutions/Azure Firewall/Analytic Rules/Azure Firewall - Port Scan.yaml |
Version | 1.1.2 |
Arm template | b2c5907b-1040-4692-9802-9946031017e8.json |
let MinimumDifferentPortsThreshold = 100;
let BinTime = 30s;
union isfuzzy=true(
AZFWApplicationRule
| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn
| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold),
(AZFWNetworkRule
| extend Fqdn = DestinationIp
| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn
| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold),
(AzureDiagnostics
| where OperationName == "AzureFirewallApplicationRuleLog" or OperationName == "AzureFirewallNetworkRuleLog"
| parse msg_s with * "from " SourceIp ":" SourcePort:int " to " Fqdn ":" DestinationPort:int *
| where isnotempty(Fqdn) and isnotempty(SourceIp)
| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn
| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold)
relevantTechniques:
- T1046
name: Port Scan
requiredDataConnectors:
- dataTypes:
- AzureDiagnostics
- AZFWApplicationRule
- AZFWNetworkRule
connectorId: AzureFirewall
entityMappings:
- fieldMappings:
- identifier: Address
columnName: SourceIp
entityType: IP
- fieldMappings:
- identifier: Url
columnName: Fqdn
entityType: URL
triggerThreshold: 1
id: b2c5907b-1040-4692-9802-9946031017e8
tactics:
- Discovery
version: 1.1.2
OriginalUri: https://github.com/Azure/Azure-Sentinel/blob/master/Solutions/Azure Firewall/Analytic Rules/Azure Firewall - Port Scan.yaml
queryPeriod: 1d
kind: Scheduled
queryFrequency: 1d
severity: Medium
status: Available
description: |
'Identifies a source IP scanning multiple open ports on Azure Firewall. This can indicate malicious scanning of ports by an attacker, trying to reveal open ports in the organization that can be compromised for initial access.
Configurable Parameters:
- Port scan time - the time range to look for multiple ports scanned. Default is set to 30 seconds.
- Minimum different ports threshold - alert only if more than this number of ports scanned. Default is set to 100.'
query: |
let MinimumDifferentPortsThreshold = 100;
let BinTime = 30s;
union isfuzzy=true(
AZFWApplicationRule
| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn
| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold),
(AZFWNetworkRule
| extend Fqdn = DestinationIp
| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn
| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold),
(AzureDiagnostics
| where OperationName == "AzureFirewallApplicationRuleLog" or OperationName == "AzureFirewallNetworkRuleLog"
| parse msg_s with * "from " SourceIp ":" SourcePort:int " to " Fqdn ":" DestinationPort:int *
| where isnotempty(Fqdn) and isnotempty(SourceIp)
| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn
| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold)
triggerOperator: gt
{
"$schema": "https://schema.management.azure.com/schemas/2019-04-01/deploymentTemplate.json#",
"contentVersion": "1.0.0.0",
"parameters": {
"workspace": {
"type": "String"
}
},
"resources": [
{
"apiVersion": "2024-01-01-preview",
"id": "[concat(resourceId('Microsoft.OperationalInsights/workspaces/providers', parameters('workspace'), 'Microsoft.SecurityInsights'),'/alertRules/b2c5907b-1040-4692-9802-9946031017e8')]",
"kind": "Scheduled",
"name": "[concat(parameters('workspace'),'/Microsoft.SecurityInsights/b2c5907b-1040-4692-9802-9946031017e8')]",
"properties": {
"alertRuleTemplateName": "b2c5907b-1040-4692-9802-9946031017e8",
"customDetails": null,
"description": "'Identifies a source IP scanning multiple open ports on Azure Firewall. This can indicate malicious scanning of ports by an attacker, trying to reveal open ports in the organization that can be compromised for initial access.\n\nConfigurable Parameters:\n\n- Port scan time - the time range to look for multiple ports scanned. Default is set to 30 seconds.\n- Minimum different ports threshold - alert only if more than this number of ports scanned. Default is set to 100.'\n",
"displayName": "Port Scan",
"enabled": true,
"entityMappings": [
{
"entityType": "IP",
"fieldMappings": [
{
"columnName": "SourceIp",
"identifier": "Address"
}
]
},
{
"entityType": "URL",
"fieldMappings": [
{
"columnName": "Fqdn",
"identifier": "Url"
}
]
}
],
"OriginalUri": "https://github.com/Azure/Azure-Sentinel/blob/master/Solutions/Azure Firewall/Analytic Rules/Azure Firewall - Port Scan.yaml",
"query": "let MinimumDifferentPortsThreshold = 100;\nlet BinTime = 30s;\nunion isfuzzy=true(\nAZFWApplicationRule\n| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn\n| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold),\n(AZFWNetworkRule\n| extend Fqdn = DestinationIp\n| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn\n| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold),\n(AzureDiagnostics\n| where OperationName == \"AzureFirewallApplicationRuleLog\" or OperationName == \"AzureFirewallNetworkRuleLog\"\n| parse msg_s with * \"from \" SourceIp \":\" SourcePort:int \" to \" Fqdn \":\" DestinationPort:int *\n| where isnotempty(Fqdn) and isnotempty(SourceIp)\n| summarize AlertTimedCountPortsInBinTime = dcount(DestinationPort) by SourceIp, bin(TimeGenerated, BinTime), Fqdn\n| where AlertTimedCountPortsInBinTime > MinimumDifferentPortsThreshold)\n",
"queryFrequency": "P1D",
"queryPeriod": "P1D",
"severity": "Medium",
"status": "Available",
"subTechniques": [],
"suppressionDuration": "PT1H",
"suppressionEnabled": false,
"tactics": [
"Discovery"
],
"techniques": [
"T1046"
],
"templateVersion": "1.1.2",
"triggerOperator": "GreaterThan",
"triggerThreshold": 1
},
"type": "Microsoft.OperationalInsights/workspaces/providers/alertRules"
}
]
}