Attachment: PDF with a suspicious string and single URL
Detects single-page PDF attachments containing suspicious language such as 'View Document' or 'View PDF' along with exactly one URL, commonly used in credential theft attacks.
Sublime rule (View on GitHub)
1name: "Attachment: PDF with a suspicious string and single URL"
2description: "Detects single-page PDF attachments containing suspicious language such as 'View Document' or 'View PDF' along with exactly one URL, commonly used in credential theft attacks."
3type: "rule"
4severity: "high"
5source: |
6 type.inbound
7 and any(attachments,
8 .file_type == "pdf"
9 and (
10 //
11 // This rule makes use of a beta feature and is subject to change without notice
12 // using the beta feature in custom rules is not suggested until it has been formally released
13 //
14 // a single page pdf
15 beta.parse_exif(.).page_count == 1
16 // in some cases the pdf might have an invalid xref table
17 // so we can instead use the number of pages in the pdf scanner
18 or (
19 beta.parse_exif(.).page_count == 0
20 and any(beta.parse_exif(.).fields,
21 .key == "Warning" and .value == "Invalid xref table"
22 )
23 and length(filter(file.explode(.),
24 strings.istarts_with(.file_name, 'pdf_2_png_')
25 )
26 ) == 1
27 )
28 )
29 and any(file.explode(.),
30 // the pdf contains specific suspicious wording
31 // these are exact matches when split on new lines extracted from the text of the PDF from the scanPDF scanner
32 any(.scan.strings.strings,
33 regex.icontains(.,
34 // action!
35 '^\s*(?:view documents?|view pdf|view presentation|preview new docusign|Download Secure PDF|VIEW DOCUMENT HERE|ACCESS DOCUMENT|REVIEW NEW SECURE DOCUMENT|OPEN SECURE VIEWER|DOWNLOAD RFP DOCUMENT|View Dashboard here|ACCESS SECURE DOCUMENTS|VIEW PROPOSAL DOCUMENTS|ACCESS / VIEW PROPOSAL DOCUMENT|Review & Sign Document|Open PDF|Access Document\(s\)|(?:P?RE)?VIEW SHARED DOCUMENT|New Secured Document|ACCESS SECURE RFP PORTAL|Please Review and Sign|Review and Validate|SECURE DOCUMENT|Open Document|View Details|Q!_Compensation/Salary Amendments\.pptx|PREVIEW DOCUMENT HERE|Download Tax Details Below:|Review and Sign Document|Review Document|Open Encrypted|OPEN DOCUMENT HERE|Click to read message|CLICK HERE TO VIEW DOCUMENTS|VIEW FULL DOCUMENT HERE|View Full Proposal)\s*$',
36 // "secure fax"
37 'View Secure Fax',
38 // more fake errors
39 'It seems there was an issue opening the document. Please view it online.',
40 // fake adobe update
41 'Update Adobe Viewer',
42 // fake sharepoint wording
43 'Learn more about messages protected by Microsoft',
44 // fake encryption crap
45 'This document is protected by 256-bit encryption.',
46 // sent you a document
47 '.*sent you a \S+ to review(?:\s*(?:and|&)\s*sign)$',
48 '^You received a \S+ to review and sign$',
49 // docusign
50 '\s*DocuSign Contract Under Review\s*',
51 'DOCUMENT PREVIEW',
52 'PREVIEW DOCUMENT',
53 'VIEW REMITTANCE COPY HERE',
54 'shared a file with you',
55 '(?:check your personal|view your) forecast',
56 'full new state pension',
57 'UN1TED STATES',
58 'view secure documents'
59 )
60 )
61 // fake error messages
62 or (
63 'Error' in~ .scan.strings.strings
64 and any(.scan.strings.strings,
65 regex.icontains(., '^\s*(?:View Video)\s*$')
66 )
67 )
68 // really terse PDF with link
69 or (
70 length(.scan.strings.strings) == 1
71 and 'Some additional information here' in~ .scan.strings.strings
72 )
73 )
74 and any(file.explode(.),
75 .depth == 0
76 and (
77 length(filter(.scan.url.urls,
78 // remove mailto: links
79 not strings.istarts_with(.url, 'mailto:')
80 and not strings.istarts_with(.url, 'email:')
81 // remove links found in exiftool output producer/creator
82 and not any([
83 ..scan.exiftool.producer,
84 ..scan.exiftool.creator
85 ],
86 . is not null
87 and strings.icontains(.,
88 ..domain.domain
89 )
90 )
91 and not .domain.root_domain in ('pdf-tools.com')
92 and not .url in (
93 'https://gamma.app/?utm_source=made-with-gamma'
94 )
95 )
96 ) == 1
97 or
98 // there is only one unique domain
99 (
100 length(distinct(filter(.scan.url.urls,
101 // remove mailto: links
102 not strings.istarts_with(.url,
103 'mailto:'
104 )
105 and not strings.istarts_with(.url,
106 'email:'
107 )
108 // remove links found in exiftool output producer/creator
109 and not any([
110 ..scan.exiftool.producer,
111 ..scan.exiftool.creator
112 ],
113 . is not null
114 and strings.icontains(.,
115 ..domain.domain
116 )
117 )
118 and not .domain.root_domain in (
119 'pdf-tools.com'
120 )
121 and not .url in (
122 'https://gamma.app/?utm_source=made-with-gamma'
123 )
124 ),
125 .domain.domain
126 )
127 ) == 1
128 // all of them are in self_service
129 and all(distinct(filter(.scan.url.urls,
130 // remove mailto: links
131 not strings.istarts_with(.url,
132 'mailto:'
133 )
134 and not strings.istarts_with(.url,
135 'email:'
136 )
137 // remove links found in exiftool output producer/creator
138 and not any([
139 ..scan.exiftool.producer,
140 ..scan.exiftool.creator
141 ],
142 . is not null
143 and strings.icontains(.,
144 ..domain.domain
145 )
146 )
147 and not .domain.root_domain in (
148 'pdf-tools.com'
149 )
150 and not .url in (
151 'https://gamma.app/?utm_source=made-with-gamma'
152 )
153 ),
154 .domain.domain
155 ),
156 .domain.domain in $self_service_creation_platform_domains
157 or .domain.root_domain in $self_service_creation_platform_domains
158 )
159 )
160 )
161 )
162 )
163attack_types:
164 - "Credential Phishing"
165tactics_and_techniques:
166 - "PDF"
167 - "Social engineering"
168 - "Evasion"
169detection_methods:
170 - "Content analysis"
171 - "File analysis"
172 - "URL analysis"
173 - "Exif analysis"
174id: "3bdbb7ad-ca08-546a-ac20-309bef95779a"