1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22 """
23 This module implements the fast module scanning
24
25 @author: AAron Walters and Brendan Dolan-Gavitt
26 @license: GNU General Public License 2.0 or later
27 @contact: awalters@volatilesystems.com,bdolangavitt@wesleyan.edu
28 @organization: Volatile Systems
29 """
30
31 from rekall.plugins.windows import common
32 from rekall_lib import utils
33
34
37 super(PoolScanModuleFast, self).__init__(**kwargs)
38 self.checks = [
39
40 ('PoolTagCheck', dict(
41 tag=self.profile.get_constant("MODULE_POOLTAG"))),
42
43
44
45
46
47
48
49
50 ('CheckPoolType', dict(
51 paged=True, non_paged=True, free=True)),
52
53 ('CheckPoolIndex', dict(value=0)),
54 ]
55
56
57 -class ModScan(common.PoolScannerPlugin):
100
101
103 """ Carve out threat objects using the pool tag """
105 super(PoolScanThreadFast, self).__init__(**kwargs)
106 self.checks = [
107 ('PoolTagCheck', dict(
108 tag=self.profile.get_constant("THREAD_POOLTAG"))),
109
110 ('CheckPoolSize', dict(min_size=self.profile.get_obj_size(
111 "_ETHREAD"))),
112
113 ('CheckPoolType', dict(
114 paged=True, non_paged=True, free=True)),
115
116 ('CheckPoolIndex', dict(value=0)),
117 ]
118
119
120 -class ThrdScan(common.PoolScannerPlugin):
121 """Scan physical memory for _ETHREAD objects"""
122
123 __name = "thrdscan"
124
125 table_header = [
126 dict(name="offset", style="address"),
127 dict(name="pid", width=6, align="r"),
128 dict(name="tid", width=6, align="r"),
129 dict(name="start", style="address"),
130 dict(name="create_time", width=24),
131 dict(name="exit_time", width=24),
132 dict(name="name", width=16),
133 dict(name="symbol"),
134 ]
135
136 scanner_defaults = dict(
137 scan_kernel_nonpaged_pool=True
138 )
139
140
142 with self.session.plugins.cc() as cc:
143 for run in self.generate_memory_ranges():
144 scanner = PoolScanThreadFast(
145 profile=self.profile, session=self.session,
146 address_space=run.address_space)
147
148 for pool_obj in scanner.scan(run.start, run.length):
149 thread = pool_obj.GetObject("Thread").Body.cast("_ETHREAD")
150 if not thread:
151 continue
152
153 if (thread.Cid.UniqueProcess.v() != 0 and
154 thread.StartAddress == 0):
155 continue
156
157 try:
158
159 if thread.Tcb.SuspendSemaphore.Header.Type != 0x05:
160 continue
161
162 if thread.KeyedWaitSemaphore.Header.Type != 0x05:
163 continue
164 except AttributeError:
165 pass
166
167
168 task = thread.Tcb.ApcState.Process.dereference_as(
169 "_EPROCESS", vm=self.session.kernel_address_space)
170
171
172
173 start_address = thread.Win32StartAddress.v()
174 if start_address < self.session.GetParameter(
175 "highest_usermode_address"):
176 if task != self.session.GetParameter("process_context"):
177 cc.SwitchProcessContext(task)
178
179 else:
180 cc.SwitchProcessContext()
181
182 yield (thread.obj_offset,
183 thread.Cid.UniqueProcess,
184 thread.Cid.UniqueThread,
185 thread.Win32StartAddress.v(),
186 thread.CreateTime,
187 thread.ExitTime,
188 task.ImageFileName,
189 utils.FormattedAddress(
190 self.session.address_resolver, start_address))
191