Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

THREAT-387 Sublime Security Rules #1356

Merged
merged 8 commits into from
Sep 25, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Pipfile
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ wrapt = "~=1.15"
[packages]
policyuniverse = "==1.5.1.20230817"
requests = "==2.31.0"
panther-analysis-tool = "~=0.52.2"
panther-analysis-tool = "~=0.53.0"
panther-detection-helpers = "==0.4.0"

[requires]
Expand Down
438 changes: 219 additions & 219 deletions Pipfile.lock

Large diffs are not rendered by default.

10 changes: 10 additions & 0 deletions global_helpers/panther_sublime_helpers.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,10 @@
def sublime_alert_context(event) -> dict:
context = {}
context["events_type"] = event.get("type", default="<TYPE_NOT_FOUND>")
context["users_emails"] = event.deep_get(
"created_by", "email_address", default="<EMAIL_NOT_FOUND>"
)
context["users_role"] = event.deep_get("created_by", "role", default="<ROLES_NOT_FOUND>")
context["request_ip"] = event.deep_get("data", "request", "ip", default="<IP_NOT_FOUND>")
context["request_path"] = event.deep_get("data", "request", "path", default="<PATH_NOT_FOUND>")
return context
5 changes: 5 additions & 0 deletions global_helpers/panther_sublime_helpers.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
AnalysisType: global
Filename: panther_sublime_helpers.py
GlobalID: "panther_sublime_helpers"
Description: >
Global helpers for Sublime detections
12 changes: 12 additions & 0 deletions packs/sublime.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
AnalysisType: pack
PackID: PantherManaged.Sublime
Description: Group of all Sublime Security detections
PackDefinition:
IDs:
- Sublime.Mailbox.Deactivated
- Sublime.Message.Flagged
- Sublime.Message.Source.Deleted.Or.Deactivated
- Sublime.Rules.Deleted.Or.Deactivated
# Globals used in these detections
- panther_sublime_helpers
DisplayName: "Panther Sublime Pack"
9 changes: 9 additions & 0 deletions rules/sublime_rules/sublime_mailboxes_deactivated.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,9 @@
from panther_sublime_helpers import sublime_alert_context


def rule(event):
return event.get("type") == "message_source.deactivate_mailboxes"


def alert_context(event):
return sublime_alert_context(event)
84 changes: 84 additions & 0 deletions rules/sublime_rules/sublime_mailboxes_deactivated.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
AnalysisType: rule
Description: A Sublime User disabled some mailbox(es).
DisplayName: "Sublime Mailbox Deactivated"
Enabled: true
Filename: sublime_mailboxes_deactivated.py
Runbook: Assess if this was done by the user for a valid business reason. Be vigilant to re-enable the mailboxes if it's in the best security interest for your organization's security posture.
Reference: https://docs.sublime.security/docs/add-message-source
Severity: Medium
DedupPeriodMinutes: 60
AlertTitle: Sublime message mailbox(es) were deactivated
LogTypes:
- Sublime.Audit
RuleID: "Sublime.Mailbox.Deactivated"
Threshold: 1
Reports:
MITRE ATT&CK:
- TA0005:T1562.001 # Impair Defenses: Disable or Modify Tools
Tests:
- ExpectedResult: false
Name: Other Events
Log:
nhakmiller marked this conversation as resolved.
Show resolved Hide resolved
{
"created_at": "2024-09-09 19:33:34.237078000",
"created_by": {
"active": true,
"created_at": "2024-08-28 22:05:15.715644000",
"email_address": "[email protected]",
"first_name": "John",
"google_oauth_user_id": "",
"id": "cd3aedfe-a61f-4e0e-ba30-14dcc7883316",
"is_enrolled": true,
"last_name": "Doe",
"microsoft_oauth_user_id": "",
"role": "admin",
"updated_at": "2024-08-28 22:05:15.715644000"
},
"data": {
"request": {
"authentication_method": "user_session",
"body": "{\"mailbox_ids\":[\"493c6e21-7787-419b-bada-7c4f50cbb932\"]}",
"id": "73444211-31af-42d8-99b4-34a139cf7d4a",
"ip": "1.2.3.4",
"method": "POST",
"path": "/v1/message-sources/febb5bf4-2ead-47b1-b467-0ac729bf6871/deactivate",
"query": { },
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/128.0.0.0 Safari/537.36"
}
},
"id": "084732e5-7704-4bbe-ab5a-77f1aa65a737",
"type": "message_source.deactivate"
}
- ExpectedResult: true
Name: Mailbox Deactivated
Log:
{
"created_at": "2024-09-09 19:33:34.237078000",
"created_by": {
"active": true,
"created_at": "2024-08-28 22:05:15.715644000",
"email_address": "[email protected]",
"first_name": "John",
"google_oauth_user_id": "",
"id": "cd3aedfe-a61f-4e0e-ba30-14dcc7883316",
"is_enrolled": true,
"last_name": "Doe",
"microsoft_oauth_user_id": "",
"role": "admin",
"updated_at": "2024-08-28 22:05:15.715644000"
},
"data": {
"request": {
"authentication_method": "user_session",
"body": "{\"mailbox_ids\":[\"493c6e21-7787-419b-bada-7c4f50cbb932\"]}",
"id": "73444211-31af-42d8-99b4-34a139cf7d4a",
"ip": "1.2.3.4",
"method": "POST",
"path": "/v1/message-sources/febb5bf4-2ead-47b1-b467-0ac729bf6871/deactivate",
"query": { },
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/128.0.0.0 Safari/537.36"
}
},
"id": "084732e5-7704-4bbe-ab5a-77f1aa65a737",
"type": "message_source.deactivate_mailboxes"
}
14 changes: 14 additions & 0 deletions rules/sublime_rules/sublime_message_flagged.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
def rule(event):
return event.get("type") == "message.flagged"


def alert_context(event):
flagged_rules = event.deep_walk("data", "flagged_rules", "name", default=["<UNKNOWN_NAMES>"])
return {
"flagged_rules": flagged_rules,
}


def title(event):
rule_count = len(event.deep_get("data", "flagged_rules", default=[]))
return f"Sublime flagged email message that matched {rule_count} Sublime rules"
69 changes: 69 additions & 0 deletions rules/sublime_rules/sublime_message_flagged.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
AnalysisType: rule
Description: Sublime flagged some messages as suspicious.
DisplayName: "Sublime Flagged an Email"
Enabled: true
Filename: sublime_message_flagged.py
# Runbook: Assess if this was done by the user for a valid business reason. Be vigilant to re-enable the mailboxes if it's in the best security interest for your organization's security posture.
# Reference: https://docs.sublime.security/docs/add-message-source
Severity: High
DedupPeriodMinutes: 60
LogTypes:
- Sublime.MessageEvent
RuleID: "Sublime.Message.Flagged"
Threshold: 1
Tests:
- ExpectedResult: true
Name: Message Flagged
Log:
{
"p_source_file": {
"aws_s3_bucket": "audit.log.export",
"aws_s3_key": "sublime_platform_message_events/2024/09/24/164544Z-FPXIFG.json"
},
"p_any_sha256_hashes": [
"fb8b46e3317ac7d5036c6b21517d363634293c6d4f6bf1b1e67548c80948a1c6"
],
"p_event_time": "2024-09-24 16:45:43.302769000",
"p_log_type": "Sublime.MessageEvent",
"p_parse_time": "2024-09-24 16:51:47.687095351",
"p_row_id": "a23385494d57dfbbbdcbe4fa218101",
"p_schema_version": 0,
"p_source_id": "7e2a59aa-687e-430e-ae4a-81d3c0163f52",
"p_source_label": "Sublime Real Logs",
"p_udm": {},
"created_at": "2024-09-24 16:45:43.302769000",
"data": {
"flagged_rules": [
{
"id": "b0ab266f-8a12-4020-b165-e97bb1aacc42",
"name": "Credential phishing: Engaging language and other indicators (untrusted sender)"
},
{
"id": "a014f82e-f2d7-4058-adb1-36fc086de0b8",
"name": "Attachment: HTML smuggling with unescape"
},
{
"id": "e4866908-60fe-46f0-866e-84d412627006",
"name": "Headers: Zimbra mailer from a non-supported OS version"
},
{
"id": "5a9dc2cd-39f5-4814-95df-aa7614cc8bdd",
"name": "Impersonation: Human Resources with link or attachment and engaging language"
},
{
"id": "7988f1f5-5c95-42c2-9140-ead5a975918e",
"name": "Request for Quote or Purchase (RFQ|RFP) with HTML smuggling attachment"
}
],
"message": {
"canonical_id": "fb8b46e3317ac7d5036c6b21517d363634293c6d4f6bf1b1e67548c80948a1c6",
"external_id": "b86b1e58-e9f8-4b55-8b54-1402f9f95e69",
"id": "019224ec-aba6-763d-bb2e-cd4cbd40a29f",
"mailbox": {
"id": "624c8394-4fe2-4ba0-bd2b-86d2e503c614"
},
"message_source_id": "91956379-c2f3-4c50-a410-3ba89fb8bc74"
}
},
"type": "message.flagged"
}
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
from panther_sublime_helpers import sublime_alert_context

SUSPICIOUS_EVENTS = [
"message_source.deactivate",
"message_source.delete",
]


def rule(event):
return event.get("type") in SUSPICIOUS_EVENTS


def alert_context(event):
return sublime_alert_context(event)
Original file line number Diff line number Diff line change
@@ -0,0 +1,84 @@
AnalysisType: rule
Description: A Sublime User disabled or deleted some message source(s).
DisplayName: "Sublime Message Source Deleted Or Deactivated"
Enabled: true
Filename: sublime_message_source_deleted_or_deactivated.py
Runbook: Assess if this was done by the user for a valid business reason. Be vigilant to re-enable the message source(s) if it's in the best security interest for your organization's security posture.
Reference: https://docs.sublime.security/docs/message-types
Severity: Medium
DedupPeriodMinutes: 60
AlertTitle: Sublime message source(s) were deleted or deactivated
LogTypes:
- Sublime.Audit
RuleID: "Sublime.Message.Source.Deleted.Or.Deactivated"
Threshold: 1
Reports:
MITRE ATT&CK:
- TA0005:T1562.001 # Impair Defenses: Disable or Modify Tools
Tests:
- ExpectedResult: true
Name: Message Source Deactivated
Log:
{
"created_at": "2024-09-09 19:33:34.237078000",
"created_by": {
"active": true,
"created_at": "2024-08-28 22:05:15.715644000",
"email_address": "[email protected]",
"first_name": "John",
"google_oauth_user_id": "",
"id": "cd3aedfe-a61f-4e0e-ba30-14dcc7883316",
"is_enrolled": true,
"last_name": "Doe",
"microsoft_oauth_user_id": "",
"role": "admin",
"updated_at": "2024-08-28 22:05:15.715644000"
},
"data": {
"request": {
"authentication_method": "user_session",
"body": "{\"mailbox_ids\":[\"493c6e21-7787-419b-bada-7c4f50cbb932\"]}",
"id": "73444211-31af-42d8-99b4-34a139cf7d4a",
"ip": "1.2.3.4",
"method": "POST",
"path": "/v1/message-sources/febb5bf4-2ead-47b1-b467-0ac729bf6871/deactivate",
"query": { },
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/128.0.0.0 Safari/537.36"
}
},
"id": "084732e5-7704-4bbe-ab5a-77f1aa65a737",
"type": "message_source.deactivate"
}
- ExpectedResult: false
Name: Other Events
Log:
{
"created_at": "2024-09-09 19:33:34.237078000",
"created_by": {
"active": true,
"created_at": "2024-08-28 22:05:15.715644000",
"email_address": "[email protected]",
"first_name": "John",
"google_oauth_user_id": "",
"id": "cd3aedfe-a61f-4e0e-ba30-14dcc7883316",
"is_enrolled": true,
"last_name": "Doe",
"microsoft_oauth_user_id": "",
"role": "admin",
"updated_at": "2024-08-28 22:05:15.715644000"
},
"data": {
"request": {
"authentication_method": "user_session",
"body": "{\"mailbox_ids\":[\"493c6e21-7787-419b-bada-7c4f50cbb932\"]}",
"id": "73444211-31af-42d8-99b4-34a139cf7d4a",
"ip": "1.2.3.4",
"method": "POST",
"path": "/v1/message-sources/febb5bf4-2ead-47b1-b467-0ac729bf6871/deactivate",
"query": { },
"user_agent": "Mozilla/5.0 (Macintosh; Intel Mac OS X 10_15_7) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/128.0.0.0 Safari/537.36"
}
},
"id": "084732e5-7704-4bbe-ab5a-77f1aa65a737",
"type": "rule.deactivate"
}
14 changes: 14 additions & 0 deletions rules/sublime_rules/sublime_rules_deleted_or_deactivated.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,14 @@
from panther_sublime_helpers import sublime_alert_context

SUSPICIOUS_EVENTS = [
"rules.delete",
"rules.deactivate",
]


def rule(event):
return event.get("type") in SUSPICIOUS_EVENTS


def alert_context(event):
return sublime_alert_context(event)
Loading
Loading