1 '''
2 The envi.memcanvas module is the home of the base MemoryRenderer object and
3 MemoryCanvas objects.
4 '''
5
6 import sys
7 import traceback
8
9 import envi
10 import envi.memory as e_mem
11 import envi.resolver as e_resolv
12
14 """
15 A top level object for all memory renderers
16 """
17
19 """
20 If there is a symbolic name for the current va, print it...
21 """
22 sym = mcanv.syms.getSymByAddr(va)
23 if sym != None:
24 mcanv.addVaText("%s:\n" % repr(sym), va)
25
29
31 for b in bytes:
32 val = ord(b)
33 bstr = "%.2x" % val
34 if val < 0x20 or val > 0x7e:
35 b = "."
36 mcanv.addNameText(b, bstr)
37
39 """
40 Render one "unit" and return the size you ate.
41 mcanv will be a MemoryCanvas extender and va
42 is the virtual address you are expected to render.
43 """
44 raise Exception("Implement render!")
45
47 """
48 A memory canvas is a place where the textual representation
49 of memory will be displayed. The methods implemented here show
50 how a memory canvas which simply prints would be implemented.
51 """
53 if syms == None:
54 syms = e_resolv.SymbolResolver()
55 self.mem = mem
56 self.syms = syms
57 self.currend = None
58 self.renderers = {}
59 self._canv_scrolled = False
60 self._canv_navcallback = None
61
62
63 self._canv_beginva = None
64 self._canv_endva = None
65 self._canv_rendvas = []
66
69
73
75 '''
76 Set a navigation "callback" that will be called with
77 a memory expression as it's first argument anytime the
78 canvas recieves user input which desires nav...
79 '''
80 self._canv_navcallback = callback
81
83 self.renderers[name] = rend
84 self.currend = rend
85
88
93
95 rend = self.renderers.get(name)
96 if rend == None:
97 raise Exception("Unknown renderer: %s" % name)
98 self.currend = rend
99
101 """
102 Retrieve a non-named tag (doesn't highlight or do
103 anything particularly special, but allows color
104 by typename).
105 """
106 return None
107
114
116 """
117 Retrieve a tag object suitable for showing that the text
118 added with this tag should link through to the specified
119 virtual address in the memory canvas.
120 """
121 return None
122
123 - def addText(self, text, tag=None):
124 """
125 Add text to the canvas with a specified tag.
126
127 NOTE: Implementors should probably check _canv_scrolled to
128 decide if they should scroll to the end of the view...
129 """
130 sys.stdout.write(text.encode(sys.stdout.encoding,'replace'))
131
132 - def addNameText(self, text, name=None, typename=None):
133 if name == None:
134 name = text
135 tag = self.getNameTag(name, typename=typename)
136 self.addText(text, tag=tag)
137
138 - def addVaText(self, text, va):
139 tag = self.getVaTag(va)
140 self.addText(text, tag=tag)
141
142 - def render(self, va, size, rend=None):
143 raise Exception('Depricated! use renderMemory!')
144
147
150
153
156
159
161 raise Exception('Default canvas cant update!')
162
165
167 raise Exception('Default canvas cant append!')
168
171
173 raise Exception('Default canvas cant prepend!')
174
177
179 '''
180 Returns true if any part of the current render overlaps
181 with the specified region.
182 '''
183 if self._canv_beginva == None:
184 return False
185
186 if self._canv_endva == None:
187 return False
188
189 if va > self._canv_endva:
190 return False
191
192 if maxva < self._canv_beginva:
193 return False
194
195 return True
196
198
199 maxva = va + size
200 if not self._isRendered(va, maxva):
201 return
202
203
204 iend = None
205 ibegin = None
206 for i,(rendva,rendsize) in enumerate(self._canv_rendvas):
207
208 if ibegin == None and va <= rendva:
209 ibegin = i
210
211 if iend == None and maxva <= rendva:
212 iend = i
213
214 if ibegin != None and iend != None:
215 break
216
217 saved_last = self._canv_rendvas[iend:]
218 saved_first = self._canv_rendvas[:ibegin]
219 updatedvas = self._canv_rendvas[ibegin:iend]
220
221
222
223
224
225
226
227
228 startva = updatedvas[0][0]
229 endva = self._canv_endva
230 if saved_last:
231 endva = saved_last[0][0]
232
233 newrendvas = []
234
235 self._beginUpdateVas(updatedvas)
236 try:
237
238 while startva < endva:
239 self._beginRenderVa(startva)
240 rsize = self.currend.render(self, startva)
241 newrendvas.append((startva,rsize))
242 self._endRenderVa(startva)
243 startva += rsize
244
245 except Exception, e:
246 s = traceback.format_exc()
247 self.addText("\nException At %s: %s\n" % (hex(va),s))
248
249 self._canv_rendvas = saved_first + newrendvas + saved_last
250
251 self._endUpdateVas()
252
254 firstva, firstsize = self._canv_rendvas[0]
255
256 va = firstva - size
257
258 self._beginRenderPrepend()
259
260 savedrendvas = self._canv_rendvas
261 self._canv_rendvas = []
262 self._canv_beginva = va
263
264 rend = self.currend
265
266 try:
267
268 while va < firstva:
269 self._beginRenderVa(va)
270 rsize = rend.render(self, va)
271 self._canv_rendvas.append((va,rsize))
272 self._endRenderVa(va)
273 va += rsize
274
275 self._canv_rendvas.extend(savedrendvas)
276
277 except Exception, e:
278 s = traceback.format_exc()
279 self.addText("\nException At %s: %s\n" % (hex(va),s))
280
281 self._endRenderPrepend()
282
284 lastva, lastsize = self._canv_rendvas[-1]
285
286 va = lastva + lastsize
287
288 self._beginRenderAppend()
289
290 rend = self.currend
291 try:
292 maxva = va + size
293 while va < maxva:
294 self._beginRenderVa(va)
295 rsize = rend.render(self, va)
296 self._canv_rendvas.append((va,rsize))
297 self._endRenderVa(va)
298 va += rsize
299
300 self._canv_endva = maxva
301
302 except Exception, e:
303 s = traceback.format_exc()
304 self.addText("\nException At %s: %s\n" % (hex(va),s))
305
306 self._endRenderAppend()
307
309
310
311 if not self._canv_scrolled:
312 self.clearCanvas()
313
314 if rend == None:
315 rend = self.currend
316
317 self.currend = rend
318
319
320 self._canv_beginva = va
321 self._canv_endva = va + size
322 self._canv_rendvas = []
323
324
325 self._beginRenderMemory(va, size, rend)
326 try:
327 maxva = va + size
328 while va < maxva:
329 self._beginRenderVa(va)
330 rsize = rend.render(self, va)
331 self._canv_rendvas.append((va,rsize))
332 self._endRenderVa(va)
333 va += rsize
334
335 except Exception, e:
336 s = traceback.format_exc()
337 self.addText("\nException At %s: %s\n" % (hex(va),s))
338
339
340 self._endRenderMemory(va, size, rend)
341
343
347
348 - def addText(self, text, tag=None):
350
353