Spam: Fake photo share
Message contains pretexting language about sharing photos ("found these photos and thought you'd like them", "remember these photos?") and a link with a newly registered domain. Fake threads and plain text bodies have been seen in the wild, indicating active evasion techniques.
Sublime rule (View on GitHub)
1name: "Spam: Fake photo share"
2description: 'Message contains pretexting language about sharing photos ("found these photos and thought you''d like them", "remember these photos?") and a link with a newly registered domain. Fake threads and plain text bodies have been seen in the wild, indicating active evasion techniques.'
3type: "rule"
4severity: "low"
5source: |
6 type.inbound
7 and length(attachments) == 0
8 and (
9 (
10 (
11 (
12 (length(body.plain.raw) < 500 and length(body.current_thread.text) == 0)
13 or (
14 length(body.html.display_text) < 500
15 and length(body.current_thread.text) == 0
16 )
17 or length(body.current_thread.text) < 500
18 or any(map(filter(ml.nlu_classifier(body.current_thread.text).entities,
19 .name == "disclaimer"
20 ),
21 .text
22 ),
23 (length(body.current_thread.text) - length(.)) < 500
24 )
25 )
26 and (
27 strings.ilike(subject.subject,
28 "*picture*",
29 "*photo*",
30 "*image*",
31 "*sad news*",
32 "*sad announcement*",
33 "*sad update*",
34 "*new pics*",
35 "*Reunion*",
36 "*planing*",
37 "*back memories*",
38 "*any memories*",
39 "*old memories*",
40 "*evoke memories*",
41 "*bittersweet memories*"
42 )
43 or regex.icontains(subject.base, 'pics?\s*\(\d{1,2}\)')
44 )
45 )
46 or (
47 (
48 (
49 length(body.html.display_text) < 500
50 and length(body.current_thread.text) == 0
51 )
52 and strings.ilike(body.html.display_text,
53 "*picture*",
54 "*photo*",
55 "*image*",
56 "*sad news*",
57 "*sad announcement*",
58 "*sad update*",
59 "*new pics*",
60 "*back memories*",
61 "*any memories*",
62 "*old memories*",
63 "*evoke memories*",
64 "*bittersweet memories*"
65 )
66 )
67 or (
68 (length(body.plain.raw) < 500 and length(body.current_thread.text) == 0)
69 and strings.ilike(body.plain.raw,
70 "*picture*",
71 "*photo*",
72 "*image*",
73 "*sad news*",
74 "*sad announcement*",
75 "*sad update*",
76 "*new pics*",
77 "*back memories*",
78 "*any memories*",
79 "*old memories*",
80 "*evoke memories*",
81 "*bittersweet memories*"
82 )
83 and not strings.icontains(body.plain.raw, "[cid:image")
84 )
85 or (
86 length(body.current_thread.text) < 500
87 and strings.ilike(body.current_thread.text,
88 "*picture*",
89 "*photo*",
90 "*image*",
91 "*sad news*",
92 "*sad announcement*",
93 "*sad update*",
94 "*new pics*",
95 "*back memories*",
96 "*any memories*",
97 "*old memories*",
98 "*evoke memories*",
99 "*bittersweet memories*"
100 )
101 )
102 )
103 or (
104 body.plain.raw is not null
105 and body.html.display_text is null
106 and (
107 length(body.current_thread.text) == 0
108 or (
109 length(body.current_thread.text) < 500
110 // fake forward indicator in the plain text body
111 and (
112 regex.contains(body.plain.raw,
113 'On (Sunday|Monday|Tuesday|Wednesday|Thursday|Friday|Saturday).{0,50} wrote'
114 )
115 or strings.icontains(body.plain.raw, 'Original Message')
116 )
117 and not regex.contains(body.current_thread.text,
118 'On (Sunday|Monday|Tuesday|Wednesday|Thursday|Friday|Saturday).{0,50} wrote'
119 )
120 and not strings.icontains(body.current_thread.text,
121 'Original Message'
122 )
123 and not any(headers.hops, any(.fields, .name == "Resent-From"))
124 )
125 )
126 and strings.ilike(body.plain.raw,
127 "*picture*",
128 "*photo*",
129 "*image*",
130 "*sad news*",
131 "*sad announcement*",
132 "*sad update*",
133 "*pics*",
134 "*back memories*",
135 "*any memories*",
136 "*old memories*",
137 "*evoke memories*",
138 "*bittersweet memories*"
139 )
140 and not strings.istarts_with(body.plain.raw, "[cid:image")
141 and strings.icontains(subject.subject, sender.display_name)
142 )
143 or (
144 strings.icontains(subject.subject, sender.display_name)
145 and sender.email.domain.root_domain in $free_email_providers
146 and length(body.links) == 2
147 and length(filter(body.links, .display_text == "h")) == 1
148 and length(filter(body.links, .display_url.scheme == "ttp")) == 1
149 )
150 )
151 and length(body.links) < 5
152 and any(body.links,
153 (
154 (
155 network.whois(.href_url.domain).days_old < 30
156 or network.whois(.display_url.domain).days_old < 30
157 or not network.whois(.href_url.domain).found
158 or network.whois(.href_url.domain).found is null
159 )
160 and .href_url.domain.root_domain != sender.email.domain.root_domain
161 )
162 or (
163 length(.display_text) == 1
164 and .href_url.domain.root_domain in ("facebook.com", "youtube.com")
165 )
166 or (
167 // random 5-6 character subdomain
168 regex.icontains(.href_url.domain.domain,
169 '^[a-z]{5,6}\.[a-z]{5,}\.[a-z]+'
170 )
171 // subdomain contains 3+ consecutive consonants
172 and regex.icontains(.href_url.domain.domain,
173 '^[a-z]*[b-df-hj-np-tv-z]{3,}[a-z]*\.'
174 )
175 and network.whois(.href_url.domain).days_old < 365
176 )
177 )
178 )
179 and (
180 (
181 (length(headers.references) > 0 or headers.in_reply_to is null)
182 and not (
183 (
184 strings.istarts_with(subject.subject, "RE:")
185 or strings.istarts_with(subject.subject, "R:")
186 or strings.istarts_with(subject.subject, "ODG:")
187 or strings.istarts_with(subject.subject, "答复:")
188 or strings.istarts_with(subject.subject, "AW:")
189 or strings.istarts_with(subject.subject, "TR:")
190 or strings.istarts_with(subject.subject, "FWD:")
191 or regex.imatch(subject.subject, '(\[[^\]]+\]\s?){0,3}(re|fwd?)\s?:')
192 )
193 )
194 )
195 or length(headers.references) == 0
196 )
197 // negate highly trusted sender domains unless they fail DMARC authentication
198 and (
199 (
200 sender.email.domain.root_domain in $high_trust_sender_root_domains
201 and not headers.auth_summary.dmarc.pass
202 )
203 or sender.email.domain.root_domain not in $high_trust_sender_root_domains
204 )
205attack_types:
206 - "Spam"
207tactics_and_techniques:
208 - "Evasion"
209 - "Social engineering"
210detection_methods:
211 - "Content analysis"
212 - "Sender analysis"
213 - "URL analysis"
214 - "Whois"
215id: "eb086f7d-3ad7-52cd-8e16-3ce08726b9ea"