1+ name : " Brand impersonation: Sharepoint"
2+ description : |
3+ Body, attached images or pdf contains a Sharepoint logo. The message contains a link and credential theft language.
4+ type : " rule"
5+ severity : " high"
6+ source : |
7+ type.inbound
8+ and length(body.links) > 0
9+ and (
10+ any(attachments,
11+ (.file_type in $file_types_images or .file_type == "pdf")
12+ and any(ml.logo_detect(.).brands, .name == "Microsoft SharePoint")
13+ )
14+ or any(ml.logo_detect(file.message_screenshot()).brands,
15+ .name == "Microsoft SharePoint"
16+ )
17+ or strings.istarts_with(strings.replace_confusables(body.current_thread.text),
18+ "Sharepoint"
19+ )
20+ or regex.icontains(body.html.raw,
21+ '<img.*(title=|alt=).share.*src=""'
22+ ) // broken Sharepoint logo
23+ or (
24+ strings.icontains(strings.replace_confusables(body.plain.raw), "SharePoint")
25+ // message body references file deletion
26+ and regex.icontains(body.plain.raw,
27+ '(expired )?file\s(was|has been|will be|scheduled (for|to be))\s?delet(ed|ion)'
28+ )
29+ )
30+ )
31+ and (
32+ (
33+ any(ml.nlu_classifier(body.current_thread.text).intents,
34+ .name == "cred_theft" and .confidence == "high"
35+ )
36+ //
37+ // This rule makes use of a beta feature and is subject to change without notice
38+ // using the beta feature in custom rules is not suggested until it has been formally released
39+ //
40+ or any(ml.nlu_classifier(beta.ocr(file.message_screenshot()).text).intents,
41+ .name == "cred_theft" and .confidence == "high"
42+ )
43+ )
44+ or any(ml.nlu_classifier(body.current_thread.text).entities,
45+ .name == "urgency" and strings.ilike(.text, "*encrypted*")
46+ )
47+ or any(body.links,
48+ regex.imatch(.display_text,
49+ '(?:re)?view (?:(?:&|and) (?:e([[:punct:]]|\s)?)?sign )?(?:complete )?(?:document|file)'
50+ )
51+ )
52+ )
53+ and not (
54+ (
55+ (
56+ strings.istarts_with(subject.subject, "RE:")
57+ or strings.istarts_with(subject.subject, "R:")
58+ or strings.istarts_with(subject.subject, "ODG:")
59+ or strings.istarts_with(subject.subject, "答复:")
60+ or strings.istarts_with(subject.subject, "AW:")
61+ or strings.istarts_with(subject.subject, "TR:")
62+ or strings.istarts_with(subject.subject, "FWD:")
63+ or regex.imatch(subject.subject, '(\[[^\]]+\]\s?){0,3}(re|fwd?)\s?:')
64+ or regex.imatch(subject.subject,
65+ '^\[?(EXT|EXTERNAL)\]?[: ]\s*(RE|FWD?|FW|AW|TR|ODG|答复):.*'
66+ )
67+ )
68+ and (
69+ (length(headers.references) > 0 or headers.in_reply_to is not null)
70+ // ensure that there are actual threads
71+ and (
72+ length(body.previous_threads) > 0
73+ or (length(body.html.display_text) - length(body.current_thread.text)) > 200
74+ )
75+ )
76+ )
77+ )
78+ and (
79+ profile.by_sender_email().prevalence != 'common'
80+ or not profile.by_sender_email().solicited
81+ or profile.by_sender().any_messages_malicious_or_spam
82+ )
83+ and not profile.by_sender().any_messages_benign
84+
85+ // negate highly trusted sender domains unless they fail DMARC authentication
86+ and (
87+ (
88+ sender.email.domain.root_domain in $high_trust_sender_root_domains
89+ and not headers.auth_summary.dmarc.pass
90+ )
91+ or sender.email.domain.root_domain not in $high_trust_sender_root_domains
92+ )
93+
94+ // negate sharepoint file share
95+ and not (
96+ // based on the message id format
97+ (
98+ (
99+ strings.starts_with(headers.message_id, '<Share-')
100+ and strings.ends_with(headers.message_id, '@odspnotify>')
101+ )
102+ or // negate legitimate access request to file
103+ (
104+ strings.starts_with(headers.message_id, '<Sharing')
105+ and strings.ends_with(headers.message_id, '@odspnotify>')
106+ )
107+ // deal with Google thinking the message ID is "broke"
108+ or (
109+ strings.icontains(headers.message_id, 'SMTPIN_ADDED_BROKEN')
110+ and any(headers.hops,
111+ any(.fields,
112+ .name == "X-Google-Original-Message-ID"
113+ and strings.starts_with(.value, '<Share-')
114+ and strings.ends_with(.value, '@odspnotify>')
115+ )
116+ )
117+ )
118+ )
119+ // all of the "action" links are sharepoint/ms
120+ and all(filter(body.links,
121+ strings.icontains(subject.subject, .display_text)
122+ or .display_text == "Open"
123+ ),
124+ .href_url.domain.root_domain in ("sharepoint.com")
125+ or (
126+ .href_url.domain.tld == "ms"
127+ // Microsoft does not own the .ms TLD, this checks to ensure it is one of their domains
128+ and (
129+ network.whois(.href_url.domain).registrant_company == "Microsoft Corporation"
130+ or strings.ilike(network.whois(.href_url.domain).registrar_name,
131+ "*MarkMonitor*",
132+ "*CSC Corporate*",
133+ "*com laude*"
134+ )
135+ )
136+ )
137+ )
138+ )
139+ attack_types :
140+ - " Credential Phishing"
141+ tactics_and_techniques :
142+ - " Impersonation: Brand"
143+ - " Social engineering"
144+ detection_methods :
145+ - " Computer Vision"
146+ - " Content analysis"
147+ - " File analysis"
148+ - " Natural Language Understanding"
149+ - " Sender analysis"
150+ id : " fd6068f1-8c02-5f9b-a6e1-1292d7b59536"
151+ og_id : " 284b1b70-8daa-5adf-9df8-15d4c6b5ead9"
152+ testing_pr : 3724
153+ testing_sha : 7ab74a78174293954773ebb20a5ae3ca03ec2fe0
0 commit comments