Abnormal Port to Protocol
| Id | 826f930c-2f25-4508-8e75-a95b809a4e15 |
| Rulename | Abnormal Port to Protocol |
| Description | Identifies communication for well known protocol over a non-standard port based on learning period activity. This can indicate malicious communication (C2) or exfiltration by attackers trying to communicate over known ports (22:SSH, 80:HTTP) but dont use the known protocol headers to match the port number. Configurable Parameters: - Learning period time - learning period for protocol learning in days. Default is set to 7. |
| Severity | Medium |
| Tactics | Exfiltration CommandAndControl |
| Techniques | T1041 T1571 |
| Required data connectors | AzureFirewall |
| Kind | Scheduled |
| Query frequency | 1h |
| Query period | 8d |
| Trigger threshold | 1 |
| Trigger operator | gt |
| Source Uri | https://github.com/Azure/Azure-Sentinel/blob/master/Solutions/Azure Firewall/Analytic Rules/Azure Firewall - Abnormal Port to Protocol.yaml |
| Version | 1.1.3 |
| Arm template | 826f930c-2f25-4508-8e75-a95b809a4e15.json |
let LearningPeriod = 7d;
let RunTime = 1h;
let StartLearningPeriod = LearningPeriod + RunTime;
let DetectionWindowStart = ago(RunTime);
let LearningPortToProtocol1 = (AzureDiagnostics
| where OperationName == "AzureFirewallApplicationRuleLog"
| where TimeGenerated between (ago(StartLearningPeriod) .. ago(RunTime))
| extend msg_s= column_ifexists('msg_s',Message)
| parse msg_s with Protocol " request from " SourceIp ":" SourcePort:int " to " Fqdn ":" DestinationPort:int "." *
| where isnotempty(DestinationPort)
| summarize LearningTimeCount = count() by LearningTimeDstPort = DestinationPort, LearningTimeProtocol = Protocol, SourceIp, Fqdn);
let LearningPortToProtocol2 = (AZFWNetworkRule
| where TimeGenerated between (ago(StartLearningPeriod) .. ago(RunTime))
| where isnotempty(DestinationPort)
| extend Fqdn = DestinationIp
| summarize LearningTimeCount = count() by LearningTimeDstPort = DestinationPort, LearningTimeProtocol = Protocol, SourceIp, Fqdn);
let LearningPortToProtocol3 = (AZFWApplicationRule
| where TimeGenerated between (ago(StartLearningPeriod) .. ago(RunTime))
| where isnotempty(DestinationPort)
| summarize LearningTimeCount = count() by LearningTimeDstPort = DestinationPort, LearningTimeProtocol = Protocol, SourceIp, Fqdn);
let AlertTimePortToProtocol1 = (AzureDiagnostics
| where TimeGenerated between (DetectionWindowStart .. now())
| where OperationName == "AzureFirewallApplicationRuleLog"
| extend msg_s= column_ifexists('msg_s',Message)
| parse msg_s with Protocol " request from " SourceIp ":" SourcePort " to " Fqdn ":" DestinationPort:int "." *
| where isnotempty(DestinationPort)
| summarize AlertTimeCount = count() by AlertTimeDstPort = DestinationPort, AlertTimeProtocol = Protocol);
let AlertTimePortToProtocol2 = (AZFWNetworkRule
| where TimeGenerated between (DetectionWindowStart .. now())
| where isnotempty(DestinationPort)
| extend Fqdn = DestinationIp
| summarize AlertTimeCount = count() by AlertTimeDstPort = DestinationPort, AlertTimeProtocol = Protocol);
let AlertTimePortToProtocol3 = (AZFWApplicationRule
| where TimeGenerated between (DetectionWindowStart .. now())
| where isnotempty(DestinationPort)
| summarize AlertTimeCount = count() by AlertTimeDstPort = DestinationPort, AlertTimeProtocol = Protocol);
(union isfuzzy=true
(AlertTimePortToProtocol1
| join kind=leftouter (LearningPortToProtocol1) on $left.AlertTimeDstPort == $right.LearningTimeDstPort
| where LearningTimeProtocol != AlertTimeProtocol),
(AlertTimePortToProtocol2
| join kind=leftouter (LearningPortToProtocol2) on $left.AlertTimeDstPort == $right.LearningTimeDstPort
| where LearningTimeProtocol != AlertTimeProtocol),
(AlertTimePortToProtocol3
| join kind=leftouter (LearningPortToProtocol3) on $left.AlertTimeDstPort == $right.LearningTimeDstPort
| where LearningTimeProtocol != AlertTimeProtocol))
tactics:
- Exfiltration
- CommandAndControl
triggerOperator: gt
queryPeriod: 8d
queryFrequency: 1h
requiredDataConnectors:
- dataTypes:
- AzureDiagnostics
- AZFWApplicationRule
- AZFWNetworkRule
connectorId: AzureFirewall
status: Available
id: 826f930c-2f25-4508-8e75-a95b809a4e15
relevantTechniques:
- T1041
- T1571
triggerThreshold: 1
kind: Scheduled
entityMappings:
- fieldMappings:
- identifier: Address
columnName: SourceIp
entityType: IP
- fieldMappings:
- identifier: Url
columnName: Fqdn
entityType: URL
query: |
let LearningPeriod = 7d;
let RunTime = 1h;
let StartLearningPeriod = LearningPeriod + RunTime;
let DetectionWindowStart = ago(RunTime);
let LearningPortToProtocol1 = (AzureDiagnostics
| where OperationName == "AzureFirewallApplicationRuleLog"
| where TimeGenerated between (ago(StartLearningPeriod) .. ago(RunTime))
| extend msg_s= column_ifexists('msg_s',Message)
| parse msg_s with Protocol " request from " SourceIp ":" SourcePort:int " to " Fqdn ":" DestinationPort:int "." *
| where isnotempty(DestinationPort)
| summarize LearningTimeCount = count() by LearningTimeDstPort = DestinationPort, LearningTimeProtocol = Protocol, SourceIp, Fqdn);
let LearningPortToProtocol2 = (AZFWNetworkRule
| where TimeGenerated between (ago(StartLearningPeriod) .. ago(RunTime))
| where isnotempty(DestinationPort)
| extend Fqdn = DestinationIp
| summarize LearningTimeCount = count() by LearningTimeDstPort = DestinationPort, LearningTimeProtocol = Protocol, SourceIp, Fqdn);
let LearningPortToProtocol3 = (AZFWApplicationRule
| where TimeGenerated between (ago(StartLearningPeriod) .. ago(RunTime))
| where isnotempty(DestinationPort)
| summarize LearningTimeCount = count() by LearningTimeDstPort = DestinationPort, LearningTimeProtocol = Protocol, SourceIp, Fqdn);
let AlertTimePortToProtocol1 = (AzureDiagnostics
| where TimeGenerated between (DetectionWindowStart .. now())
| where OperationName == "AzureFirewallApplicationRuleLog"
| extend msg_s= column_ifexists('msg_s',Message)
| parse msg_s with Protocol " request from " SourceIp ":" SourcePort " to " Fqdn ":" DestinationPort:int "." *
| where isnotempty(DestinationPort)
| summarize AlertTimeCount = count() by AlertTimeDstPort = DestinationPort, AlertTimeProtocol = Protocol);
let AlertTimePortToProtocol2 = (AZFWNetworkRule
| where TimeGenerated between (DetectionWindowStart .. now())
| where isnotempty(DestinationPort)
| extend Fqdn = DestinationIp
| summarize AlertTimeCount = count() by AlertTimeDstPort = DestinationPort, AlertTimeProtocol = Protocol);
let AlertTimePortToProtocol3 = (AZFWApplicationRule
| where TimeGenerated between (DetectionWindowStart .. now())
| where isnotempty(DestinationPort)
| summarize AlertTimeCount = count() by AlertTimeDstPort = DestinationPort, AlertTimeProtocol = Protocol);
(union isfuzzy=true
(AlertTimePortToProtocol1
| join kind=leftouter (LearningPortToProtocol1) on $left.AlertTimeDstPort == $right.LearningTimeDstPort
| where LearningTimeProtocol != AlertTimeProtocol),
(AlertTimePortToProtocol2
| join kind=leftouter (LearningPortToProtocol2) on $left.AlertTimeDstPort == $right.LearningTimeDstPort
| where LearningTimeProtocol != AlertTimeProtocol),
(AlertTimePortToProtocol3
| join kind=leftouter (LearningPortToProtocol3) on $left.AlertTimeDstPort == $right.LearningTimeDstPort
| where LearningTimeProtocol != AlertTimeProtocol))
OriginalUri: https://github.com/Azure/Azure-Sentinel/blob/master/Solutions/Azure Firewall/Analytic Rules/Azure Firewall - Abnormal Port to Protocol.yaml
name: Abnormal Port to Protocol
version: 1.1.3
severity: Medium
description: |
'Identifies communication for well known protocol over a non-standard port based on learning period activity. This can indicate malicious communication (C2) or exfiltration by attackers trying to communicate over known ports (22:SSH, 80:HTTP) but dont use the known protocol headers to match the port number.
Configurable Parameters:
- Learning period time - learning period for protocol learning in days. Default is set to 7.'