]> git.saurik.com Git - apple/xnu.git/blob - tools/lldbmacros/mbufs.py
xnu-7195.81.3.tar.gz
[apple/xnu.git] / tools / lldbmacros / mbufs.py
1
2 """ Please make sure you read the README COMPLETELY BEFORE reading anything below.
3 It is very critical that you read coding guidelines in Section E in README file.
4 """
5
6 from xnu import *
7 from utils import *
8
9 from mbufdefines import *
10 import xnudefines
11
12 # Macro: mbuf_stat
13 @lldb_command('mbuf_stat')
14 def MBufStat(cmd_args=None):
15 """ Print extended mbuf allocator statistics.
16 """
17 hdr_format = "{0: <16s} {1: >8s} {2: >8s} {3: ^16s} {4: >8s} {5: >12s} {6: >8s} {7: >8s} {8: >8s} {9: >8s}"
18 print hdr_format.format('class', 'total', 'cached', 'uncached', 'inuse', 'failed', 'waiter', 'notified', 'purge', 'max')
19 print hdr_format.format('name', 'objs', 'objs', 'objs/slabs', 'objs', 'alloc count', 'count', 'count', 'count', 'objs')
20 print hdr_format.format('-'*16, '-'*8, '-'*8, '-'*16, '-'*8, '-'*12, '-'*8, '-'*8, '-'*8, '-'*8)
21 entry_format = "{0: <16s} {1: >8d} {2: >8d} {3:>7d} / {4:<6d} {5: >8d} {6: >12d} {7: >8d} {8: >8d} {9: >8d} {10: >8d}"
22 num_items = sizeof(kern.globals.mbuf_table) / sizeof(kern.globals.mbuf_table[0])
23 ncpus = int(kern.globals.ncpu)
24 for i in range(num_items):
25 mbuf = kern.globals.mbuf_table[i]
26 mcs = Cast(mbuf.mtbl_stats, 'mb_class_stat_t *')
27 mc = mbuf.mtbl_cache
28 total = 0
29 total += int(mc.mc_full.bl_total) * int(mc.mc_cpu[0].cc_bktsize)
30 ccp_arr = mc.mc_cpu
31 for i in range(ncpus):
32 ccp = ccp_arr[i]
33 if int(ccp.cc_objs) > 0:
34 total += int(ccp.cc_objs)
35 if int(ccp.cc_pobjs) > 0:
36 total += int(ccp.cc_pobjs)
37 print entry_format.format(mcs.mbcl_cname, mcs.mbcl_total, total,
38 mcs.mbcl_infree, mcs.mbcl_slab_cnt,
39 (mcs.mbcl_total - total - mcs.mbcl_infree),
40 mcs.mbcl_fail_cnt, mbuf.mtbl_cache.mc_waiter_cnt,
41 mcs.mbcl_notified, mcs.mbcl_purge_cnt,
42 mbuf.mtbl_maxlimit
43 )
44 # EndMacro: mbuf_stat
45
46 # Macro: mbuf_walkpkt
47 @lldb_command('mbuf_walkpkt')
48 def MbufWalkPacket(cmd_args=None):
49 """ Walk the mbuf packet chain (m_nextpkt)
50 """
51 if not cmd_args:
52 raise ArgumentError("Missing argument 0 in user function.")
53
54 mp = kern.GetValueFromAddress(cmd_args[0], 'mbuf *')
55 cnt = 1
56 tot = 0
57 while (mp):
58 out_string = ""
59 mbuf_walk_packet_format = "{0:4d} 0x{1:x} [len {2:4d}, type {3:2d}, "
60 out_string += mbuf_walk_packet_format.format(cnt, mp, mp.m_hdr.mh_len, mp.m_hdr.mh_type)
61 if (kern.globals.mclaudit != 0):
62 out_string += GetMbufBuf2Mca(mp) + ", "
63 tot = tot + mp.m_hdr.mh_len
64 out_string += "total " + str(tot) + "]"
65 print out_string
66 mp = mp.m_hdr.mh_nextpkt
67 cnt += 1
68 # EndMacro: mbuf_walkpkt
69
70 # Macro: mbuf_walk
71 @lldb_command('mbuf_walk')
72 def MbufWalk(cmd_args=None):
73 """ Walk the mbuf chain (m_next)
74 """
75 mp = kern.GetValueFromAddress(cmd_args[0], 'mbuf *')
76 cnt = 1
77 tot = 0
78 while (mp):
79 out_string = ""
80 mbuf_walk_format = "{0:4d} 0x{1:x} [len {2:4d}, type {3:2d}, "
81 out_string += mbuf_walk_format.format(cnt, mp, mp.m_hdr.mh_len, mp.m_hdr.mh_type)
82 if (kern.globals.mclaudit != 0):
83 out_string += GetMbufBuf2Mca(mp) + ", "
84 tot = tot + mp.m_hdr.mh_len
85 out_string += "total " + str(tot) + "]"
86 print out_string
87 mp = mp.m_hdr.mh_next
88 cnt += 1
89 # EndMacro: mbuf_walk
90
91 # Macro: mbuf_buf2slab
92 @lldb_command('mbuf_buf2slab')
93 def MbufBuf2Slab(cmd_args=None):
94 """ Given an mbuf object, find its corresponding slab address
95 """
96 if not cmd_args:
97 raise ArgumentError("Missing argument 0 in user function.")
98
99 m = kern.GetValueFromAddress(cmd_args[0], 'mbuf *')
100 slab = GetMbufSlab(m)
101 if (kern.ptrsize == 8):
102 mbuf_slab_format = "0x{0:<16x}"
103 print mbuf_slab_format.format(slab)
104 else:
105 mbuf_slab_format = "0x{0:<8x}"
106 print mbuf_slab_format.format(slab)
107 # EndMacro: mbuf_buf2slab
108
109 # Macro: mbuf_buf2mca
110 @lldb_command('mbuf_buf2mca')
111 def MbufBuf2Mca(cmd_args=None):
112 """ Find the mcache audit structure of the corresponding mbuf
113 """
114 m = kern.GetValueFromAddress(cmd_args[0], 'mbuf *')
115 print GetMbufBuf2Mca(m)
116 return
117 # EndMacro: mbuf_buf2mca
118
119 # Macro: mbuf_slabs
120 @lldb_command('mbuf_slabs')
121 def MbufSlabs(cmd_args=None):
122 """ Print all slabs in the group
123 """
124
125 out_string = ""
126 if not cmd_args:
127 raise ArgumentError("Invalid arguments passed.")
128
129 slg = kern.GetValueFromAddress(cmd_args[0], 'mcl_slabg_t *')
130 x = 0
131
132 if (kern.ptrsize == 8):
133 slabs_string_format = "{0:>4d}: 0x{1:16x} 0x{2:16x} 0x{3:16x} {4:4s} {5:20d} {6:3d} {7:3d} {8:3d} {9:3d} {10:>6s} "
134 out_string += "slot slab next obj mca tstamp C R N size flags\n"
135 out_string += "---- ------------------ ------------------ ------------------ ------------------ ---------- -- -- -- ------ -----\n"
136 else:
137 slabs_string_format = "{0:>4d}: 0x{1:8x} 0x{2:8x} 0x{3:8x} {4:4s} {5:20d} {6:3d} {7:3d} {8:3d} {9:3d} {10:>6s} "
138 out_string += "slot slab next obj mca tstamp C R N size flags\n"
139 out_string += "---- ---------- ---------- ---------- ---------- ---------- -- -- -- ------ -----\n"
140
141 mbutl = cast(kern.globals.mbutl, 'unsigned char *')
142 nslabspmb = int((1 << MBSHIFT) >> unsigned(kern.globals.page_shift))
143 while x < nslabspmb:
144 sl = addressof(slg.slg_slab[x])
145 mca = 0
146 obj = sl.sl_base
147 ts = 0
148
149 if (kern.globals.mclaudit != 0):
150 mca = GetMbufMcaPtr(obj, sl.sl_class)
151 trn = (mca.mca_next_trn + unsigned(kern.globals.mca_trn_max) - 1) % unsigned(kern.globals.mca_trn_max)
152 ts = mca.mca_trns[trn].mca_tstamp
153
154 out_string += slabs_string_format.format((x + 1), sl, sl.sl_next, obj, hex(mca), int(ts), int(sl.sl_class), int(sl.sl_refcnt), int(sl.sl_chunks), int(sl.sl_len), hex(sl.sl_flags))
155
156 if (sl.sl_flags != 0):
157 out_string += "<"
158 if sl.sl_flags & SLF_MAPPED:
159 out_string += "mapped"
160 if sl.sl_flags & SLF_PARTIAL:
161 out_string += ",partial"
162 if sl.sl_flags & SLF_DETACHED:
163 out_string += ",detached"
164 out_string += ">"
165 out_string += "\n"
166
167 if sl.sl_chunks > 1:
168 z = 1
169 c = sl.sl_len/sl.sl_chunks
170
171 while z < sl.sl_chunks:
172 obj = sl.sl_base + (c * z)
173 mca = 0
174 ts = 0
175
176 if (kern.globals.mclaudit != 0):
177 mca = GetMbufMcaPtr(obj, sl.sl_class)
178 trn = (mca.mca_next_trn + unsigned(kern.globals.mca_trn_max) - 1) % unsigned(kern.globals.mca_trn_max)
179 ts = mca.mca_trns[trn].mca_tstamp
180
181 if (kern.ptrsize == 8):
182 out_string += " " + hex(obj) + " " + hex(mca) + " " + str(unsigned(ts)) + "\n"
183 else:
184 out_string += " " + hex(obj) + " " + hex(mca) + " " + str(unsigned(ts)) + "\n"
185
186 z += 1
187 x += 1
188 print out_string
189 # EndMacro: mbuf_slabs
190
191 # Macro: mbuf_slabstbl
192 @lldb_command('mbuf_slabstbl')
193 def MbufSlabsTbl(cmd_args=None):
194 """ Print slabs table
195 """
196 out_string = ""
197 x = 0
198
199 if (kern.ptrsize == 8):
200 out_string += "slot slabg slabs range\n"
201 out_string += "---- ------------------ -------------------------------------------\n"
202 else:
203 out_string += "slot slabg slabs range\n"
204 out_string += "---- ---------- ---------------------------\n"
205
206 slabstbl = kern.globals.slabstbl
207 slabs_table_blank_string_format = "{0:>3d}: - \n"
208 nslabspmb = int(((1 << MBSHIFT) >> unsigned(kern.globals.page_shift)))
209 while (x < unsigned(kern.globals.maxslabgrp)):
210 slg = slabstbl[x]
211 if (slg == 0):
212 out_string += slabs_table_blank_string_format.format(x+1)
213 else:
214 if (kern.ptrsize == 8):
215 slabs_table_string_format = "{0:>3d}: 0x{1:16x} [ 0x{2:16x} - 0x{3:16x} ]\n"
216 out_string += slabs_table_string_format.format(x+1, slg, addressof(slg.slg_slab[0]), addressof(slg.slg_slab[nslabspmb-1]))
217 else:
218 slabs_table_string_format = "{0:>3d}: 0x{1:8x} [ 0x{2:8x} - 0x{3:8x} ]\n"
219 out_string += slabs_table_string_format.format(x+1, slg, addressof(slg.slg_slab[0]), addressof(slg.slg_slab[nslabspmb-1]))
220
221 x += 1
222 print out_string
223 # EndMacro: mbuf_slabstbl
224
225 def GetMbufMcaPtr(m, cl):
226 pgshift = int(kern.globals.page_shift)
227 ix = int((m - Cast(kern.globals.mbutl, 'char *')) >> pgshift)
228 page_addr = (Cast(kern.globals.mbutl, 'char *') + (ix << pgshift))
229
230 if (int(cl) == 0):
231 midx = int((m - page_addr) >> 8)
232 mca = kern.globals.mclaudit[ix].cl_audit[midx]
233 elif (int(cl) == 1):
234 midx = int((m - page_addr) >> 11)
235 mca = kern.globals.mclaudit[ix].cl_audit[midx]
236 elif (int(cl) == 2):
237 midx = int((m - page_addr) >> 12)
238 mca = kern.globals.mclaudit[ix].cl_audit[midx]
239 else:
240 mca = kern.globals.mclaudit[ix].cl_audit[0]
241 return Cast(mca, 'mcache_audit_t *')
242
243 def GetMbufSlab(m):
244 pgshift = int(kern.globals.page_shift)
245 gix = int((Cast(m, 'char *') - Cast(kern.globals.mbutl, 'char *')) >> MBSHIFT)
246 slabstbl = kern.globals.slabstbl
247 ix = int((Cast(m, 'char *') - Cast(slabstbl[gix].slg_slab[0].sl_base, 'char *')) >> pgshift)
248 return addressof(slabstbl[gix].slg_slab[ix])
249
250 def GetMbufBuf2Mca(m):
251 sl = GetMbufSlab(m)
252 mca = GetMbufMcaPtr(m, sl.sl_class)
253 return str(mca)
254
255 def GetMbufWalkAllSlabs(show_a, show_f, show_tr):
256 out_string = ""
257
258 kern.globals.slabstbl[0]
259
260 x = 0
261 total = 0
262 total_a = 0
263 total_f = 0
264
265 if (show_a and not(show_f)):
266 out_string += "Searching only for active... \n"
267 if (not(show_a) and show_f):
268 out_string += "Searching only for inactive... \n"
269 if (show_a and show_f):
270 out_string += "Displaying all... \n"
271
272 if (kern.ptrsize == 8):
273 show_mca_string_format = "{0:>4s} {1:>4s} {2:>16s} {3:>16s} {4:>16} {5:>12s} {6:12s}"
274 out_string += show_mca_string_format.format("slot", "idx", "slab address", "mca address", "obj address", "type", "allocation state\n")
275 else:
276 show_mca_string_format = "{0:4s} {1:4s} {2:8s} {3:8s} {4:8} {5:12s} {6:12s}"
277 out_string += show_mca_string_format.format("slot", "idx", "slab address", "mca address", "obj address", "type", "allocation state\n")
278
279 nslabspmb = unsigned((1 << MBSHIFT) >> unsigned(kern.globals.page_shift))
280 while (x < unsigned(kern.globals.slabgrp)):
281 slg = kern.globals.slabstbl[x]
282 y = 0
283 stop = 0
284 while ((y < nslabspmb) and (stop == 0)):
285 sl = addressof(slg.slg_slab[y])
286 base = sl.sl_base
287 mca = GetMbufMcaPtr(base, sl.sl_class)
288 first = 1
289
290 while ((Cast(mca, 'int') != 0) and (unsigned(mca.mca_addr) != 0)):
291 printmca = 0
292 if (mca.mca_uflags & (MB_INUSE | MB_COMP_INUSE)):
293 total_a = total_a + 1
294 printmca = show_a
295 else:
296 total_f = total_f + 1
297 printmca = show_f
298
299 if (printmca != 0):
300 if (first == 1):
301 if (kern.ptrsize == 8):
302 mca_string_format = "{0:4d} {1:4d} 0x{2:16x} "
303 out_string += mca_string_format.format(x, y, sl)
304 else:
305 mca_string_format = "{0:4d} {1:4d} 0x{02:8x} "
306 out_string += mca_string_format.format(x, y, sl)
307 else:
308 if (kern.ptrsize == 8):
309 out_string += " "
310 else:
311 out_string += " "
312
313 if (kern.ptrsize == 8):
314 mca_string_format = "0x{0:16x} 0x{1:16x}"
315 out_string += mca_string_format.format(mca, mca.mca_addr)
316 else:
317 mca_string_format = "0x{0:8x} 0x{1:8x}"
318 out_string += mca_string_format.format(mca, mca.mca_addr)
319
320 out_string += GetMbufMcaCtype(mca, 0)
321
322 if (mca.mca_uflags & (MB_INUSE | MB_COMP_INUSE)):
323 out_string += "active "
324 else:
325 out_string += " freed "
326 if (first == 1):
327 first = 0
328 out_string += "\n"
329 total = total + 1
330
331 if (show_tr != 0):
332 if (mca.mca_next_trn == 0):
333 trn = 1
334 else:
335 trn = 0
336 out_string += "Transaction " + str(int(trn)) + " at " + str(int(mca.mca_trns[int(trn)].mca_tstamp)) + " by thread: 0x" + str(hex(mca.mca_trns[int(trn)].mca_thread)) + ":\n"
337 cnt = 0
338 while (cnt < mca.mca_trns[int(trn)].mca_depth):
339 kgm_pc = mca.mca_trns[int(trn)].mca_stack[int(cnt)]
340 out_string += str(int(cnt) + 1) + " "
341 out_string += GetPc(kgm_pc)
342 cnt += 1
343
344 print out_string
345 out_string = ""
346 mca = mca.mca_next
347
348 y += 1
349 if (slg.slg_slab[int(y)].sl_base == 0):
350 stop = 1
351 x += 1
352
353 if (total and show_a and show_f):
354 out_string += "total objects = " + str(int(total)) + "\n"
355 out_string += "active/unfreed objects = " + str(int(total_a)) + "\n"
356 out_string += "freed/in_cache objects = " + str(int(total_f)) + "\n"
357
358 return out_string
359
360 def GetMbufMcaCtype(mca, vopt):
361 cp = mca.mca_cache
362 mca_class = unsigned(cp.mc_private)
363 csize = unsigned(kern.globals.mbuf_table[mca_class].mtbl_stats.mbcl_size)
364 done = 0
365 out_string = " "
366 if (csize == MSIZE):
367 if (vopt):
368 out_string += "M (mbuf) "
369 else:
370 out_string += "M "
371 return out_string
372 if (csize == MCLBYTES):
373 if (vopt):
374 out_string += "CL (2K cluster) "
375 else:
376 out_string += "CL "
377 return out_string
378 if (csize == MBIGCLBYTES):
379 if (vopt):
380 out_string += "BCL (4K cluster) "
381 else:
382 out_string += "BCL "
383 return out_string
384 if (csize == M16KCLBYTES):
385 if (vopt):
386 out_string += "JCL (16K cluster) "
387 else:
388 out_string += "JCL "
389 return out_string
390
391 if (csize == (MSIZE + MCLBYTES)):
392 if (mca.mca_uflags & MB_SCVALID):
393 if (mca.mca_uptr):
394 out_string += "M+CL "
395 if vopt:
396 out_string += "(paired mbuf, 2K cluster) "
397 else:
398 out_string += "M-CL "
399 if vopt:
400 out_string += "(unpaired mbuf, 2K cluster) "
401 else:
402 if (mca.mca_uptr):
403 out_string += "CL+M "
404 if vopt:
405 out_string += "(paired 2K cluster, mbuf) "
406 else:
407 out_string += "CL-M "
408 if vopt:
409 out_string += "(unpaired 2K cluster, mbuf) "
410 return out_string
411
412 if (csize == (MSIZE + MBIGCLBYTES)):
413 if (mca.mca_uflags & MB_SCVALID):
414 if (mca.mca_uptr):
415 out_string += "M+BCL "
416 if vopt:
417 out_string += "(paired mbuf, 4K cluster) "
418 else:
419 out_string += "M-BCL "
420 if vopt:
421 out_string += "(unpaired mbuf, 4K cluster) "
422 else:
423 if (mca.mca_uptr):
424 out_string += "BCL+M "
425 if vopt:
426 out_string += "(paired 4K cluster, mbuf) "
427 else:
428 out_string += "BCL-m "
429 if vopt:
430 out_string += "(unpaired 4K cluster, mbuf) "
431 return out_string
432
433 if (csize == (MSIZE + M16KCLBYTES)):
434 if (mca.mca_uflags & MB_SCVALID):
435 if (mca.mca_uptr):
436 out_string += "M+BCL "
437 if vopt:
438 out_string += "(paired mbuf, 4K cluster) "
439 else:
440 out_string += "M-BCL "
441 if vopt:
442 out_string += "(unpaired mbuf, 4K cluster) "
443 else:
444 if (mca.mca_uptr):
445 out_string += "BCL+M "
446 if vopt:
447 out_string += "(paired 4K cluster, mbuf) "
448 else:
449 out_string += "BCL-m "
450 if vopt:
451 out_string += "(unpaired 4K cluster, mbuf) "
452 return out_string
453
454 out_string += "unknown: " + cp.mc_name
455 return out_string
456
457 kgm_pkmod = 0
458 kgm_pkmodst = 0
459 kgm_pkmoden = 0
460
461 def GetPointerAsString(kgm_pc):
462 if (kern.ptrsize == 8):
463 pointer_format_string = "0x{0:<16x} "
464 else:
465 pointer_format_string = "0x{0:<8x} "
466 return pointer_format_string.format(kgm_pc)
467
468 def GetPc(kgm_pc):
469 out_string = GetSourceInformationForAddress(unsigned(kgm_pc)) + "\n"
470 return out_string
471
472
473 # Macro: mbuf_showactive
474 @lldb_command('mbuf_showactive')
475 def MbufShowActive(cmd_args=None):
476 """ Print all active/in-use mbuf objects
477 """
478 if cmd_args:
479 print GetMbufWalkAllSlabs(1, 0, cmd_args[0])
480 else:
481 print GetMbufWalkAllSlabs(1, 0, 0)
482 # EndMacro: mbuf_showactive
483
484
485 # Macro: mbuf_showinactive
486 @lldb_command('mbuf_showinactive')
487 def MbufShowInactive(cmd_args=None):
488 """ Print all freed/in-cache mbuf objects
489 """
490 print GetMbufWalkAllSlabs(0, 1, 0)
491 # EndMacro: mbuf_showinactive
492
493
494 # Macro: mbuf_showmca
495 @lldb_command('mbuf_showmca')
496 def MbufShowMca(cmd_args=None):
497 """ Print the contents of an mbuf mcache audit structure
498 """
499 out_string = ""
500 pgshift = unsigned(kern.globals.page_shift)
501 if cmd_args:
502 mca = kern.GetValueFromAddress(cmd_args[0], 'mcache_audit_t *')
503 cp = mca.mca_cache
504 out_string += "object type:\t"
505 out_string += GetMbufMcaCtype(mca, 1)
506 out_string += "\nControlling mcache :\t" + hex(mca.mca_cache) + " (" + str(cp.mc_name) + ")\n"
507 if (mca.mca_uflags & MB_SCVALID):
508 mbutl = Cast(kern.globals.mbutl, 'unsigned char *')
509 ix = (mca.mca_addr - mbutl) >> pgshift
510 clbase = mbutl + (ix << pgshift)
511 mclidx = (mca.mca_addr - clbase) >> 8
512 out_string += "mbuf obj :\t\t" + hex(mca.mca_addr) + "\n"
513 out_string += "mbuf index :\t\t" + str(mclidx + 1) + " (out of 16) in cluster base " + hex(clbase) + "\n"
514 if (int(mca.mca_uptr) != 0):
515 peer_mca = cast(mca.mca_uptr, 'mcache_audit_t *')
516 out_string += "paired cluster obj :\t" + hex(peer_mca.mca_addr) + " (mca " + hex(peer_mca) + ")\n"
517 out_string += "saved contents :\t" + hex(mca.mca_contents) + " (" + str(int(mca.mca_contents_size)) + " bytes)\n"
518 else:
519 out_string += "cluster obj :\t\t" + hex(mca.mca_addr) + "\n"
520 if (mca.mca_uptr != 0):
521 peer_mca = cast(mca.mca_uptr, 'mcache_audit_t *')
522 out_string += "paired mbuf obj :\t" + hex(peer_mca.mca_addr) + " (mca " + hex(peer_mca) + ")\n"
523
524 for idx in range(unsigned(kern.globals.mca_trn_max), 0, -1):
525 trn = (mca.mca_next_trn + idx - 1) % unsigned(kern.globals.mca_trn_max)
526 out_string += "transaction {:d} (tstamp {:d}, thread 0x{:x}):\n".format(trn, mca.mca_trns[trn].mca_tstamp, mca.mca_trns[trn].mca_thread)
527 cnt = 0
528 while (cnt < mca.mca_trns[trn].mca_depth):
529 kgm_pc = mca.mca_trns[trn].mca_stack[cnt]
530 out_string += " " + str(cnt + 1) + ". "
531 out_string += GetPc(kgm_pc)
532 cnt += 1
533
534 msc = cast(mca.mca_contents, 'mcl_saved_contents_t *')
535 msa = addressof(msc.sc_scratch)
536 if (mca.mca_uflags & MB_SCVALID):
537 if (msa.msa_depth > 0):
538 out_string += "Recent scratch transaction (tstamp {:d}, thread 0x{:x}):\n".format(msa.msa_tstamp, msa.msa_thread)
539 cnt = 0
540 while (cnt < msa.msa_depth):
541 kgm_pc = msa.msa_stack[cnt]
542 out_string += " " + str(cnt + 1) + ". "
543 out_string += GetPc(kgm_pc)
544 cnt += 1
545
546 if (msa.msa_pdepth > 0):
547 out_string += "previous scratch transaction (tstamp {:d}, thread 0x{:x}):\n".format(msa.msa_ptstamp, msa.msa_pthread)
548 if (msa):
549 cnt = 0
550 while (cnt < msa.msa_pdepth):
551 kgm_pc = msa.msa_pstack[cnt]
552 out_string += " " + str(cnt + 1) + ". "
553 out_string += GetPc(kgm_pc)
554 cnt += 1
555 else:
556 out_string += "Missing argument 0 in user function."
557
558 print out_string
559 # EndMacro: mbuf_showmca
560
561
562 # Macro: mbuf_showall
563 @lldb_command('mbuf_showall')
564 def MbufShowAll(cmd_args=None):
565 """ Print all mbuf objects
566 """
567 print GetMbufWalkAllSlabs(1, 1, 1)
568 # EndMacro: mbuf_showall
569
570 # Macro: mbuf_countchain
571 @lldb_command('mbuf_countchain')
572 def MbufCountChain(cmd_args=None):
573 """ Count the length of an mbuf chain
574 """
575 if not cmd_args:
576 raise ArgumentError("Missing argument 0 in user function.")
577
578 mp = kern.GetValueFromAddress(cmd_args[0], 'mbuf *')
579
580 pkt = 0
581 nxt = 0
582
583 while (mp):
584 pkt = pkt + 1
585 mn = mp.m_hdr.mh_next
586 while (mn):
587 nxt = nxt + 1
588 mn = mn.m_hdr.mh_next
589
590 mp = mp.m_hdr.mh_nextpkt
591
592 if (((pkt + nxt) % 50) == 0):
593 print " ..." + str(pkt_nxt)
594
595 print "Total: " + str(pkt + nxt) + " (via m_next: " + str(nxt) + ")"
596 # EndMacro: mbuf_countchain
597
598
599
600 # Macro: mbuf_topleak
601 @lldb_command('mbuf_topleak')
602 def MbufTopLeak(cmd_args=None):
603 """ Print the top suspected mbuf leakers
604 """
605 topcnt = 0
606 if (int(len(cmd_args)) > 0 and int(cmd_args[0]) < 5):
607 maxcnt = cmd_args[0]
608 else:
609 maxcnt = 5
610 while (topcnt < maxcnt):
611 print GetMbufTraceLeak(kern.globals.mleak_top_trace[topcnt])
612 topcnt += 1
613
614 # EndMacro: mbuf_topleak
615
616 def GetMbufTraceLeak(trace):
617 out_string = ""
618 if (trace.allocs != 0):
619 out_string += hex(trace) + ":" + str(trace.allocs) + " outstanding allocs\n"
620 out_string += "Backtrace saved " + str(trace.depth) + " deep\n"
621 if (trace.depth != 0):
622 cnt = 0
623 while (cnt < trace.depth):
624 out_string += str(cnt + 1) + ": "
625 out_string += GetPc(trace.addr[cnt])
626 out_string += "\n"
627 cnt += 1
628 return out_string
629
630 @lldb_command('mbuf_largefailures')
631 def MbufLargeFailures(cmd_args=None):
632 """ Print the largest allocation failures
633 """
634 topcnt = 0
635 if (int(len(cmd_args)) > 0 and int(cmd_args[0]) < 5):
636 maxcnt = cmd_args[0]
637 else:
638 maxcnt = 5
639 while (topcnt < maxcnt):
640 trace = kern.globals.mtracelarge_table[topcnt]
641 if (trace.size == 0):
642 topcnt += 1
643 continue
644 print str(trace.size)
645 if (trace.depth != 0):
646 cnt = 0
647 while (cnt < trace.depth):
648 print str(cnt + 1) + ": " + GetPc(trace.addr[cnt])
649 cnt += 1
650 topcnt += 1
651
652
653 # Macro: mbuf_traceleak
654 @lldb_command('mbuf_traceleak')
655 def MbufTraceLeak(cmd_args=None):
656 """ Print the leak information for a given leak address
657 Given an mbuf leak trace (mtrace) structure address, print out the
658 stored information with that trace
659 syntax: (lldb) mbuf_traceleak <addr>
660 """
661 if not cmd_args:
662 raise ArgumentError("Missing argument 0 in user function.")
663
664 trace = kern.GetValueFromAddress(cmd_args[0], 'mtrace *')
665 print GetMbufTraceLeak(trace)
666 # EndMacro: mbuf_traceleak
667
668
669 # Macro: mcache_walkobj
670 @lldb_command('mcache_walkobj')
671 def McacheWalkObject(cmd_args=None):
672 """ Given a mcache object address, walk its obj_next pointer
673 """
674 if not cmd_args:
675 raise ArgumentError("Missing argument 0 in user function.")
676
677 out_string = ""
678 p = kern.GetValueFromAddress(cmd_args[0], 'mcache_obj_t *')
679 cnt = 1
680 total = 0
681 while (p):
682 mcache_object_format = "{0:>4d}: 0x{1:>16x}"
683 out_string += mcache_object_format.format(cnt, p) + "\n"
684 p = p.obj_next
685 cnt += 1
686 print out_string
687 # EndMacro: mcache_walkobj
688
689 # Macro: mcache_stat
690 @lldb_command('mcache_stat')
691 def McacheStat(cmd_args=None):
692 """ Print all mcaches in the system.
693 """
694 head = kern.globals.mcache_head
695 out_string = ""
696 mc = cast(head.lh_first, 'mcache *')
697 if (kern.ptrsize == 8):
698 mcache_stat_format_string = "{0:<24s} {1:>8s} {2:>20s} {3:>5s} {4:>5s} {5:>20s} {6:>30s} {7:>18s}"
699 else:
700 mcache_stat_format_string = "{0:<24s} {1:>8s} {2:>12s} {3:>5s} {4:>5s} {5:>12s} {6:>30s} {7:>18s}"
701
702 if (kern.ptrsize == 8):
703 mcache_stat_data_format_string = "{0:<24s} {1:>12s} {2:>20s} {3:>5s} {4:>5s} {5:>22s} {6:>12d} {7:>8d} {8:>8d} {9:>18d}"
704 else:
705 mcache_stat_data_format_string = "{0:<24s} {1:>12s} {2:>12s} {3:>5s} {4:>5s} {5:>14s} {6:>12d} {7:>8d} {8:>8d} {9:>18d}"
706
707 out_string += mcache_stat_format_string.format("cache name", "cache state", "cache addr", "buf size", "buf align", "backing zone", "wait nowait failed", "bufs incache")
708 out_string += "\n"
709
710 ncpu = int(kern.globals.ncpu)
711 while mc != 0:
712 bktsize = mc.mc_cpu[0].cc_bktsize
713 cache_state = ""
714 if (mc.mc_flags & MCF_NOCPUCACHE):
715 cache_state = "disabled"
716 else:
717 if (bktsize == 0):
718 cache_state = " offline"
719 else:
720 cache_state = " online"
721 if (mc.mc_slab_zone != 0):
722 backing_zone = mc.mc_slab_zone
723 else:
724 if (kern.ptrsize == 8):
725 backing_zone = " custom"
726 else:
727 backing_zone = " custom"
728
729 total = 0
730 total += mc.mc_full.bl_total * bktsize
731 n = 0
732 while(n < ncpu):
733 ccp = mc.mc_cpu[n]
734 if (ccp.cc_objs > 0):
735 total += ccp.cc_objs
736 if (ccp.cc_pobjs > 0):
737 total += ccp.cc_pobjs
738 n += 1
739 ccp += 1
740
741 out_string += mcache_stat_data_format_string.format(mc.mc_name, cache_state, hex(mc), str(int(mc.mc_bufsize)), str(int(mc.mc_align)), hex(mc.mc_slab_zone), int(mc.mc_wretry_cnt), int(mc.mc_nwretry_cnt), int(mc.mc_nwfail_cnt), total)
742 out_string += "\n"
743 mc = cast(mc.mc_list.le_next, 'mcache *')
744 print out_string
745 # EndMacro: mcache_stat
746
747 # Macro: mcache_showcache
748 @lldb_command('mcache_showcache')
749 def McacheShowCache(cmd_args=None):
750 """Display the number of objects in cache.
751 """
752 out_string = ""
753 cp = kern.GetValueFromAddress(cmd_args[0], 'mcache_t *')
754 bktsize = cp.mc_cpu[0].cc_bktsize
755 cnt = 0
756 total = 0
757 mcache_cache_format = "{0:<4d} {1:>8d} {2:>8d} {3:>8d}"
758 out_string += "Showing cache " + str(cp.mc_name) + " :\n\n"
759 out_string += " CPU cc_objs cc_pobjs total\n"
760 out_string += "---- ------- -------- --------\n"
761 ncpu = int(kern.globals.ncpu)
762 while (cnt < ncpu):
763 ccp = cp.mc_cpu[cnt]
764 objs = ccp.cc_objs
765 if (objs <= 0):
766 objs = 0
767 pobjs = ccp.cc_pobjs
768 if (pobjs <= 0):
769 pobjs = 0
770 tot_cpu = objs + pobjs
771 total += tot_cpu
772 out_string += mcache_cache_format.format(cnt, objs, pobjs, tot_cpu)
773 out_string += "\n"
774 cnt += 1
775
776 out_string += " ========\n"
777 out_string += " " + str(total) + "\n\n"
778 total += cp.mc_full.bl_total * bktsize
779
780 out_string += "Total # of full buckets (" + str(int(bktsize)) + " objs/bkt):\t" + str(int(cp.mc_full.bl_total)) + "\n"
781 out_string += "Total # of objects cached:\t\t" + str(total) + "\n"
782 print out_string
783 # EndMacro: mcache_showcache
784
785 # Macro: mbuf_wdlog
786 @lldb_command('mbuf_wdlog')
787 def McacheShowCache(cmd_args=None):
788 """Display the watchdog log
789 """
790 lldb_run_command('settings set max-string-summary-length 4096')
791 print('%s' % lldb_run_command('p/s mbwdog_logging').replace("\\n","\n"))
792 # EndMacro: mbuf_wdlog