xref: /xnu-11215.1.10/tools/lldbmacros/net.py (revision 8d741a5de7ff4191bf97d57b9f54c2f6d4a15585)
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"""
5from xnu import *
6from utils import *
7from string import *
8from socket import *
9import tempfile
10
11import xnudefines
12from netdefines import *
13from routedefines import *
14from mbufdefines import *
15
16def GetDlilIfFlagsAsString(dlil_if_flags):
17    """ Return a formatted string description of the dlil interface flags
18    """
19    out_string = ""
20    flags = (unsigned)(dlil_if_flags & 0xffff)
21    i = 0
22    num = 1
23    while num <= flags:
24        if flags & num:
25            out_string += dlil_if_flags_strings[i] + ","
26        i += 1
27        num = num << 1
28    return out_string.rstrip(",")
29
30def GetIfFlagsAsString(if_flags):
31    """ Return a formatted string description of the interface flags
32    """
33    out_string = ""
34    flags = (unsigned)(if_flags & 0xffff)
35    i = 0
36    num = 1
37    while num <= flags:
38        if flags & num:
39            out_string += if_flags_strings[i] + ","
40        i += 1
41        num = num << 1
42    return out_string.rstrip(",")
43
44
45def ShowIfConfiguration(ifnet):
46    """ Display ifconfig-like output for the ifnet
47    """
48    iface = Cast(ifnet, 'ifnet *')
49    dlifnet = Cast(ifnet, 'dlil_ifnet *')
50    out_string = ""
51    format_string = "{0: <s}: flags={1: <x} <{2: <s}> index {3: <d} mtu {4: <d}"
52    if iface :
53        out_string += format_string.format(iface.if_xname, (iface.if_flags & 0xffff), GetIfFlagsAsString(iface.if_flags), iface.if_index, iface.if_data.ifi_mtu)
54        out_string += "\n\tdlil flags=" + hex(dlifnet.dl_if_flags)+ " <" + GetDlilIfFlagsAsString(dlifnet.dl_if_flags) + ">"
55        out_string += "\n\t(struct ifnet *)" + hex(ifnet)
56        if iface.if_snd and iface.if_snd.ifcq_len :
57            out_string += "\n\t" + str(iface.if_snd.ifcq_len)
58        if dlifnet.dl_if_inpstorage.dlth_pkts.qlen :
59            out_string += "\n\t" + str(dlifnet.dl_if_inpstorage.dlth_pkts.qlen)
60    print(out_string)
61
62def GetIfConfiguration(ifname):
63    """ Return ifnet structure corresponding to the ifname passed in
64    """
65    global kern
66    ifnets = kern.globals.ifnet_head
67    for ifnet in IterateTAILQ_HEAD(ifnets, "if_link") :
68        if str(ifnet.if_xname) == ifname :
69            return ifnet
70    return None
71
72# Macro: net_get_always_on_pktap
73@lldb_command('net_get_always_on_pktap')
74def NetGetAlwaysOnPktap(cmd_args=None):
75    """ Dump the always-on packet capture to /tmp/dump.pktap
76    """
77    for i in range(0, 10):
78        ifnet = GetIfConfiguration("pktap"+str(i))
79        if not ifnet:
80            continue
81        if ifnet.if_bpf == 0:
82            ifnet = None
83            continue
84        if ifnet.if_bpf.bif_dlist.bd_headdrop == 0:
85            ifnet = None
86            continue
87
88        break
89
90    if not ifnet:
91        print("Could not find a pktap interface")
92        return
93
94    bpf_d = ifnet.if_bpf.bif_dlist
95
96    f = tempfile.NamedTemporaryFile(prefix="dump-", suffix=".pktap", dir="/tmp/", mode="wb", delete=False)
97
98    err = lldb.SBError()
99
100    if bpf_d.bd_hbuf != 0:
101        addr = bpf_d.bd_hbuf[0].GetSBValue().GetLoadAddress()
102        hlen = (unsigned(bpf_d.bd_hlen)+(4-1))&~(4-1)
103        buf = LazyTarget.GetProcess().ReadMemory(addr, hlen, err)
104        if err.fail:
105            print("Error, getting sbuf")
106        f.write(buf)
107
108    addr = bpf_d.bd_sbuf[0].GetSBValue().GetLoadAddress()
109    slen = (unsigned(bpf_d.bd_slen)+(4-1))&~(4-1)
110    buf = LazyTarget.GetProcess().ReadMemory(addr, slen, err)
111    if err.fail:
112        print("Error, getting sbuf")
113    f.write(buf)
114
115    print(f.name)
116    f.close()
117# EndMacro: net_get_always_on_pktap
118
119# Macro: ifconfig
120@lldb_command('ifconfig')
121def ShowIfconfig(cmd_args=None) :
122    """ Display ifconfig-like output, and print the (struct ifnet *) pointers for further inspection
123    """
124    if cmd_args != None and len(cmd_args) > 0:
125        showall = 1
126    else:
127        showall = 0
128
129    ifnets = kern.globals.ifnet_head
130    for ifnet in IterateTAILQ_HEAD(ifnets, "if_link"):
131        ShowIfConfiguration(ifnet)
132        if (showall == 1):
133            print(GetIfaddrs(ifnet))
134# EndMacro: ifconfig
135
136#Macro: ifconfig_dlil
137@lldb_command('ifconfig_dlil')
138def ShowIfconfigDlil(cmd_args=None) :
139    """ Display ifconfig-like output for DLIL interface list, print (struct ifnet *) pointer and dlil info for further inspection
140    """
141    dlil_ifnets = kern.globals.dlil_ifnet_head
142    for dlil_ifnet in IterateTAILQ_HEAD(dlil_ifnets, "dl_if_link"):
143        ShowIfConfiguration(dlil_ifnet)
144        print(GetIfaddrs(Cast(dlil_ifnet, 'ifnet *')))
145# EndMacro: ifconfig_dlil
146
147def GetAddressAsStringColonHex(addr, count):
148    out_string = ""
149    i = 0
150    addr_format_string = "{0:02x}"
151    while (i < count):
152        if (i == 0):
153            out_string += addr_format_string.format(unsigned(addr[i]))[-2:]
154        else:
155            out_string += ":" + addr_format_string.format(unsigned(addr[i]))[-2:]
156        i += 1
157    return out_string
158
159def GetSocketAddrAsStringUnspec(sockaddr):
160    out_string = ""
161    out_string += GetAddressAsStringColonHex(sockaddr.sa_data, sockaddr.sa_len - 2)
162    return out_string
163
164def GetSocketAddrAsStringUnix(sockaddr):
165    sock_unix = Cast(sockaddr, 'sockaddr_un *')
166    if (sock_unix == 0):
167        return "(null)"
168    else:
169        if (len(str(sock_unix.sun_path)) > 0):
170            return str(sock_unix.sun_path)
171        else:
172            return "\"\""
173
174def GetInAddrAsString(ia):
175    out_string = ""
176    inaddr = Cast(ia, 'in_addr *')
177
178    packed_value = struct.pack('I', unsigned(ia.s_addr))
179    out_string = inet_ntoa(packed_value)
180    return out_string
181
182def GetIn6AddrAsString(ia):
183    addr_raw_string = ":".join(["{0:02x}{1:02x}".format(unsigned(ia[i]),
184        unsigned(ia[i+1])) for i in range(0, 16, 2)])
185    return inet_ntop(AF_INET6, inet_pton(AF_INET6, addr_raw_string))
186
187def GetSocketAddrAsStringInet(sockaddr):
188    sock_in = Cast(sockaddr, 'sockaddr_in *')
189    return GetInAddrAsString(addressof(sock_in.sin_addr))
190
191def GetSocketAddrAsStringInet6(sockaddr):
192    sock_in6 = Cast(sockaddr, 'sockaddr_in6 *')
193    return GetIn6AddrAsString(sock_in6.sin6_addr.__u6_addr.__u6_addr8)
194
195def GetSocketAddrAsStringLink(sockaddr):
196    sock_link = Cast(sockaddr, 'sockaddr_dl *')
197    if sock_link is None:
198        return "(null)"
199    else:
200        out_string = ""
201        if (sock_link.sdl_nlen == 0 and sock_link.sdl_alen == 0 and sock_link.sdl_slen == 0):
202            out_string = "link#" + str(int(sock_link.sdl_index))
203        else:
204            out_string += GetAddressAsStringColonHex(addressof(sock_link.sdl_data[sock_link.sdl_nlen]), sock_link.sdl_alen)
205    return out_string
206
207def GetSocketAddrAsStringAT(sockaddr):
208    out_string = ""
209    sock_addr = Cast(sockaddr, 'sockaddr *')
210    out_string += GetAddressAsStringColonHex(sockaddr.sa_data, sockaddr.sa_len - 2)
211    return out_string
212
213def GetSocketAddrAsString(sockaddr):
214    if sockaddr is None :
215        return "(null)"
216    out_string = ""
217    if (sockaddr.sa_family == 0):
218        out_string += "UNSPC "
219        GetSocketAddrAsStringUnspec(sockaddr)
220    elif (sockaddr.sa_family == 1):
221        out_string += "UNIX "
222        out_string += GetSocketAddrAsStringUnix(sockaddr)
223    elif (sockaddr.sa_family == 2):
224        out_string += "INET "
225        out_string += GetSocketAddrAsStringInet(sockaddr)
226    elif (sockaddr.sa_family == 30):
227        out_string += "INET6 "
228        out_string += GetSocketAddrAsStringInet6(sockaddr)
229    elif (sockaddr.sa_family == 18):
230        out_string += "LINK "
231        out_string += GetSocketAddrAsStringLink(sockaddr)
232    elif (sockaddr.sa_family == 16):
233        out_string += "ATLK "
234        out_string += GetSocketAddrAsStringAT(sockaddr)
235    else:
236        out_string += "FAM " + str(sockaddr.sa_family)
237        out_string += GetAddressAsStringColonHex(sockaddr.sa_data, sockaddr.sa_len)
238    return out_string
239
240# Macro: showifaddrs
241@lldb_command('showifaddrs')
242def ShowIfaddrs(cmd_args=None):
243    """ Show the (struct ifnet).if_addrhead list of addresses for the given ifp
244    """
245    if cmd_args != None and len(cmd_args) > 0 :
246        ifp = kern.GetValueFromAddress(cmd_args[0], 'ifnet *')
247        if not ifp:
248            print("Unknown value passed as argument.")
249            return
250        i = 1
251        for ifaddr in IterateTAILQ_HEAD(ifp.if_addrhead, "ifa_link"):
252            format_string = "\t{0: <d}: 0x{1: <x} {2: <s} [{3: <d}]"
253            print(format_string.format(i, ifaddr, GetSocketAddrAsString(ifaddr.ifa_addr), ifaddr.ifa_refcnt))
254            i += 1
255    else :
256        print("Missing argument 0 in user function.")
257# EndMacro: showifaddrs
258
259def GetIfaddrs(ifp):
260    out_string = ""
261    if (ifp != 0):
262        i = 1
263        for ifaddr in IterateTAILQ_HEAD(ifp.if_addrhead, "ifa_link"):
264            format_string = "\t{0: <d}: 0x{1: <x} {2: <s} [{3: <d}]"
265            out_string += format_string.format(i, ifaddr, GetSocketAddrAsString(ifaddr.ifa_addr), ifaddr.ifa_refcnt) + "\n"
266            i += 1
267    else:
268        out_string += "Missing argument 0 in user function."
269    return out_string
270
271
272def GetCapabilitiesAsString(flags):
273    """ Return a formatted string description of the interface flags
274    """
275    out_string = ""
276    i = 0
277    num = 1
278    while num <= flags:
279        if flags & num:
280            out_string += if_capenable_strings[i] + ","
281        i += 1
282        num = num << 1
283    return out_string.rstrip(",")
284
285def GetIfEflagsAsString(if_eflags):
286    """ Return a formatted string description of the interface extra flags
287    """
288    out_string = ""
289    flags = unsigned(if_eflags)
290    i = 0
291    num = 1
292    while num <= flags:
293        if flags & num:
294            out_string += if_eflags_strings[i] + ","
295        i += 1
296        num = num << 1
297    return out_string.rstrip(",")
298
299def GetIfXflagsAsString(if_xflags):
300    """ Return a formatted string description of the interface extended flags
301    """
302    out_string = ""
303    flags = unsigned(if_xflags)
304    i = 0
305    num = 1
306    while num <= flags:
307        if flags & num:
308            out_string += if_xflags_strings[i] + ","
309        i += 1
310        num = num << 1
311    return out_string.rstrip(",")
312
313def ShowDlilIfnetConfiguration(dlil_ifnet, show_all) :
314    """ Formatted display of dlil_ifnet structures
315    """
316    DLIF_INUSE = 0x1
317    DLIF_REUSE = 0x2
318
319    if dlil_ifnet is None :
320        return
321
322    dlil_iface = Cast(dlil_ifnet, 'dlil_ifnet *')
323    iface = Cast(dlil_ifnet, 'ifnet *')
324    out_string = ""
325    if (dlil_iface.dl_if_flags & DLIF_REUSE) :
326        out_string  += "*"
327    format_string = "{0: <s}: flags={1: <x} <{2: <s}> index {3: <d} mtu {4: <d}"
328    extended_flags_format_string = "\n\teflags={0: <x} <{1: <s}>"
329    extra_flags_format_string = "\n\txflags={0: <x} <{1: <s}>"
330    capenabled_format_string = "\n\toptions={0: <x} <{1: <s}>"
331    if (dlil_iface.dl_if_flags & DLIF_INUSE) :
332        out_string += format_string.format(iface.if_xname, (iface.if_flags & 0xffff), GetIfFlagsAsString(iface.if_flags), iface.if_index, iface.if_data.ifi_mtu)
333    else :
334        out_string += format_string.format("[" + str(iface.if_name) + str(int(iface.if_unit)) + "]", (iface.if_flags & 0xffff), GetIfFlagsAsString(iface.if_flags), iface.if_index, iface.if_data.ifi_mtu)
335    if (iface.if_eflags) :
336        out_string += extended_flags_format_string.format(iface.if_eflags, GetIfEflagsAsString(iface.if_eflags))
337    if (iface.if_xflags) :
338        out_string += extra_flags_format_string.format(iface.if_xflags, GetIfXflagsAsString(iface.if_xflags))
339    if (iface.if_capenable) :
340        out_string += capenabled_format_string.format(iface.if_capenable, GetCapabilitiesAsString(iface.if_capenable))
341    out_string += "\n\t(struct ifnet *)" + hex(dlil_ifnet) + "\n"
342    if show_all :
343        out_string += GetIfaddrs(iface)
344        out_string += "\n"
345    print(out_string)
346
347# Macro: showifnets
348@lldb_command('showifnets')
349def ShowIfnets(cmd_args=None) :
350    """ Display ifconfig-like output for all attached and detached interfaces
351    """
352    showall = 0
353    if cmd_args != None and len(cmd_args) > 0 :
354        showall = 1
355    dlil_ifnets = kern.globals.dlil_ifnet_head
356    for dlil_ifnet in IterateTAILQ_HEAD(dlil_ifnets, "dl_if_link"):
357        ShowDlilIfnetConfiguration(dlil_ifnet, showall)
358# EndMacro: showifnets
359
360# Macro: showifmultiaddrs
361@lldb_command('showifmultiaddrs')
362def ShowIfMultiAddrs(cmd_args=None) :
363    """ Show the list of multicast addresses for the given ifp
364    """
365    out_string = ""
366    if cmd_args != None and len(cmd_args) > 0 :
367        ifp = kern.GetValueFromAddress(cmd_args[0], 'ifnet *')
368        if not ifp:
369            print("Unknown value passed as argument.")
370            return
371        ifmulti = cast(ifp.if_multiaddrs.lh_first, 'ifmultiaddr *')
372        i = 0
373        while ifmulti != 0:
374            ifma_format_string = "\t{0: <d}: 0x{1: <x} "
375            out_string += (ifma_format_string.format(i + 1, ifmulti))
376            if (ifmulti.ifma_addr.sa_family == 2):
377                if (ifmulti.ifma_ll != 0):
378                    out_string += GetSocketAddrAsStringLink(ifmulti.ifma_ll.ifma_addr) + " "
379                out_string += GetSocketAddrAsStringInet(ifmulti.ifma_addr)
380            if (ifmulti.ifma_addr.sa_family == 30):
381                if (ifmulti.ifma_ll != 0):
382                    out_string += GetSocketAddrAsStringLink(ifmulti.ifma_ll.ifma_addr) + " "
383                out_string += GetSocketAddrAsStringInet6(ifmulti.ifma_addr) + " "
384            if (ifmulti.ifma_addr.sa_family == 18):
385                out_string += GetSocketAddrAsStringLink(ifmulti.ifma_addr) + " "
386            if (ifmulti.ifma_addr.sa_family == 0):
387                out_string += GetSocketAddrAsStringUnspec(ifmulti.ifma_addr) + " "
388            out_string += "[" + str(int(ifmulti.ifma_refcount)) + "]\n"
389            ifmulti = cast(ifmulti.ifma_link.le_next, 'ifmultiaddr *')
390            i += 1
391        print(out_string)
392    else :
393        print("Missing argument 0 in user function.")
394# EndMacro: showifmultiaddrs
395
396# Macro: showinmultiaddrs
397@lldb_command('showinmultiaddrs')
398def ShowInMultiAddrs(cmd_args=None) :
399    """ Show the contents of IPv4 multicast address records
400    """
401    out_string = ""
402    inmultihead = kern.globals.in_multihead
403    inmulti = cast(inmultihead.lh_first, 'in_multi *')
404    i = 0
405    while inmulti != 0:
406        ifp = inmulti.inm_ifp
407        inma_format_string = "\t{0: <d}: 0x{1: <x} "
408        out_string += inma_format_string.format(i + 1, inmulti) + " "
409        out_string += GetInAddrAsString(addressof(inmulti.inm_addr)) + " "
410        ifma_format_string = "(ifp 0x{0: <x} [{1: <s}] ifma {2: <x})"
411        out_string += ifma_format_string.format(ifp, ifp.if_xname, inmulti.inm_ifma) + "\n"
412        inmulti = cast(inmulti.inm_link.le_next, 'in_multi *')
413        i += 1
414    print(out_string)
415# EndMacro: showinmultiaddrs
416
417# Macro: showin6multiaddrs
418@lldb_command('showin6multiaddrs')
419def ShowIn6MultiAddrs(cmd_args=None) :
420    """ Show the contents of IPv6 multicast address records
421    """
422    out_string = ""
423    in6multihead = kern.globals.in6_multihead
424    in6multi = cast(in6multihead.lh_first, 'in6_multi *')
425    i = 0
426    while in6multi != 0:
427        ifp = in6multi.in6m_ifp
428        inma_format_string = "\t{0: <d}: 0x{1: <x} "
429        out_string += inma_format_string.format(i + 1, in6multi) + " "
430        out_string += GetIn6AddrAsString((in6multi.in6m_addr.__u6_addr.__u6_addr8)) + " "
431        ifma_format_string = "(ifp 0x{0: <x} [{1: <s}] ifma {2: <x})"
432        out_string += ifma_format_string.format(ifp, ifp.if_xname, in6multi.in6m_ifma) + "\n"
433        in6multi = cast(in6multi.in6m_entry.le_next, 'in6_multi *')
434        i += 1
435    print(out_string)
436# EndMacro: showin6multiaddrs
437
438def GetTcpState(tcpcb):
439    out_string = ""
440    tp = Cast(tcpcb, 'tcpcb *')
441    if (int(tp) != 0):
442        if tp.t_state == 0:
443            out_string += "CLOSED\t"
444        if tp.t_state == 1:
445            out_string += "LISTEN\t"
446        if tp.t_state == 2:
447            out_string += "SYN_SENT\t"
448        if tp.t_state == 3:
449            out_string += "SYN_RCVD\t"
450        if tp.t_state == 4:
451            out_string += "ESTABLISHED\t"
452        if tp.t_state == 5:
453            out_string += "CLOSE_WAIT\t"
454        if tp.t_state == 6:
455            out_string += "FIN_WAIT_1\t"
456        if tp.t_state == 7:
457            out_string += "CLOSING\t"
458        if tp.t_state == 8:
459            out_string += "LAST_ACK\t"
460        if tp.t_state == 9:
461            out_string += "FIN_WAIT_2\t"
462        if tp.t_state == 10:
463            out_string += "TIME_WAIT\t"
464    return out_string
465
466def GetSocketProtocolAsString(sock):
467    out_string = ""
468    inpcb = Cast(sock.so_pcb, 'inpcb *')
469    if sock.so_proto.pr_protocol == 6:
470        out_string += " TCP "
471        out_string += GetTcpState(inpcb.inp_ppcb)
472    if sock.so_proto.pr_protocol == 17:
473        out_string += " UDP "
474    if sock.so_proto.pr_protocol == 1:
475        out_string += " ICMP "
476    if sock.so_proto.pr_protocol == 254:
477        out_string += " DIVERT "
478    if sock.so_proto.pr_protocol == 255:
479        out_string += " RAW "
480    return out_string
481
482def GetInAddr4to6AsString(inaddr):
483    out_string = ""
484    if (inaddr is not None):
485        ia = Cast(inaddr, 'unsigned char *')
486        inaddr_format_string = "{0:d}:{1:d}:{2:d}:{3:d}"
487        out_string += inaddr_format_string.format(unsigned(ia[0]), unsigned(ia[1]), unsigned(ia[2]), unsigned(ia[3]))
488    return out_string
489
490def GetInPortAsString(port):
491    out_string = ""
492    port_string = Cast(port, 'char *')
493    port_unsigned = dereference(Cast(port, 'unsigned short *'))
494
495    if ((((port_unsigned & 0xff00) >> 8) == port_string[0])) and (((port_unsigned & 0x00ff) == port_string[1])):
496        out_string += ":" + str(int(port_unsigned))
497    else:
498        out_string += ":" + str(int(((port_unsigned & 0xff00) >> 8) | ((port_unsigned & 0x00ff) << 8)))
499
500    return out_string
501
502def GetIPv4SocketAsString(sock) :
503    out_string = ""
504    pcb = Cast(sock.so_pcb, 'inpcb *')
505    if (pcb == 0):
506        out_string += "inpcb: (null) "
507    else:
508        out_string += "inpcb: " + hex(pcb)
509        out_string += GetSocketProtocolAsString(sock)
510
511        out_string += GetInAddr4to6AsString(addressof(pcb.inp_dependladdr.inp46_local.ia46_addr4))
512        out_string += GetInPortAsString(addressof(pcb.inp_lport))
513        out_string += " -> "
514        out_string += GetInAddr4to6AsString(addressof(pcb.inp_dependfaddr.inp46_foreign.ia46_addr4))
515        out_string += GetInPortAsString(addressof(pcb.inp_fport))
516    return out_string
517
518def GetIPv6SocketAsString(sock) :
519    out_string = ""
520    pcb = Cast(sock.so_pcb, 'inpcb *')
521    if (pcb == 0):
522        out_string += "inpcb: (null) "
523    else:
524        out_string += "inpcb: " + hex(pcb) + " "
525        out_string += GetSocketProtocolAsString(sock)
526
527        out_string += GetIn6AddrAsString((pcb.inp_dependladdr.inp6_local.__u6_addr.__u6_addr8))
528        out_string += GetInPortAsString(addressof(pcb.inp_lport))
529        out_string += " -> "
530        out_string += GetIn6AddrAsString((pcb.inp_dependfaddr.inp6_foreign.__u6_addr.__u6_addr8))
531        out_string += GetInPortAsString(addressof(pcb.inp_fport))
532    return out_string
533
534def GetUnixDomainSocketAsString(sock) :
535    out_string = ""
536    pcb = Cast(sock.so_pcb, 'unpcb *')
537    if (pcb == 0):
538        out_string += "unpcb: (null) "
539    else:
540        out_string += "unpcb: " + hex(pcb)  + " "
541        out_string += "unp_vnode: " + hex(pcb.unp_vnode) + " "
542        out_string += "unp_conn: " + hex(pcb.unp_conn) + " "
543        out_string += "unp_addr: " + GetSocketAddrAsStringUnix(pcb.unp_addr)
544    return out_string
545
546def GetVsockSocketAsString(sock) :
547    out_string = ""
548    pcb = Cast(sock.so_pcb, 'vsockpcb *')
549    if (pcb == 0):
550        out_string += "vsockpcb: (null) "
551    else:
552        out_string += "vsockpcb: " + hex(pcb) + " "
553        out_string += str(pcb.local_address) + " "
554        out_string += str(pcb.remote_address)
555    return out_string
556
557def GetSocket(socket) :
558    """ Show the contents of a socket
559    """
560    so = kern.GetValueFromAddress(unsigned(socket), 'socket *')
561    if (so):
562        out_string = ""
563        sock_format_string = "so: 0x{0:<x} options 0x{1:<x} state 0x{2:<x}"
564        out_string += sock_format_string.format(so, so.so_options, so.so_state)
565        domain = so.so_proto.pr_domain
566        domain_name_format_string = " {0:<s} "
567        out_string += domain_name_format_string.format(domain.dom_name)
568        if (domain.dom_family == 1):
569            out_string += GetUnixDomainSocketAsString(so)
570        if (domain.dom_family == 2):
571            out_string += GetIPv4SocketAsString(so)
572        if (domain.dom_family == 30):
573            out_string += GetIPv6SocketAsString(so)
574        if (domain.dom_family == 40):
575            out_string += GetVsockSocketAsString(so)
576        out_string += " s=" + str(int(so.so_snd.sb_cc)) + " r=" + str(int(so.so_rcv.sb_cc)) + " usecnt=" + str(int(so.so_usecount))
577    else:
578        out_string += "(null)"
579    return out_string
580# EndMacro: showsocket
581
582
583# Macro: showsocket
584@lldb_command('showsocket')
585def ShowSocket(cmd_args=None) :
586    """ Show the contents of a socket
587    """
588    if cmd_args is None or len(cmd_args) == 0:
589            print("Missing argument 0 in user function.")
590            return
591    so = kern.GetValueFromAddress(cmd_args[0], 'socket *')
592    if (len(str(cmd_args[0])) > 0):
593        out_string = ""
594        sock_format_string = "so: 0x{0:<x} options 0x{1:<x} state 0x{2:<x}"
595        out_string += sock_format_string.format(so, so.so_options, so.so_state)
596        domain = so.so_proto.pr_domain
597        domain_name_format_string = " {0:<s} "
598        out_string += domain_name_format_string.format(domain.dom_name)
599        if (domain.dom_family == 1):
600            out_string += GetUnixDomainSocketAsString(so)
601        if (domain.dom_family == 2):
602            out_string += GetIPv4SocketAsString(so)
603        if (domain.dom_family == 30):
604            out_string += GetIPv6SocketAsString(so)
605        if (domain.dom_family == 40):
606            out_string += GetVsockSocketAsString(so)
607        print(out_string)
608    else:
609        print("Unknown value passed as argument.")
610        return
611# EndMacro: showsocket
612
613def GetProcSockets(proc, total_snd_cc, total_rcv_cc, total_sock_fd):
614    """ Given a proc_t pointer, display information about its sockets
615    """
616    out_string = ""
617
618    if proc is None:
619        out_string += "Unknown value passed as argument."
620    else:
621        snd_cc = 0
622        rcv_cc = 0
623        sock_fd_seen = 0
624        """struct  filedesc *"""
625        proc_filedesc = addressof(proc.p_fd)
626        """struct  fileproc **"""
627        proc_ofiles = proc_filedesc.fd_ofiles
628        """ high-water mark of fd_ofiles """
629        if proc_filedesc.fd_nfiles != 0:
630            for fd in range(0, unsigned(proc_filedesc.fd_afterlast)):
631                if (unsigned(proc_ofiles[fd]) != 0 and proc_ofiles[fd].fp_glob != 0):
632                        fg = proc_ofiles[fd].fp_glob
633                        fg_data = Cast(fg.fg_data, 'void *')
634                        if (int(fg.fg_ops.fo_type) == 2):
635                            if (proc_filedesc.fd_ofileflags[fd] & 4):
636                                out_string += "U: "
637                            else:
638                                out_string += " "
639                            out_string += "fd = " + str(fd) + " "
640                            if (fg_data != 0):
641                                out_string += GetSocket(fg_data)
642                                out_string += "\n"
643
644                                so = Cast(fg_data, 'socket *')
645                                snd_cc += int(so.so_snd.sb_cc)
646                                total_snd_cc[0] += int(so.so_snd.sb_cc)
647                                rcv_cc += int(so.so_rcv.sb_cc)
648                                total_rcv_cc[0] += int(so.so_rcv.sb_cc)
649                                sock_fd_seen += 1
650                            else:
651                                out_string += ""
652        out_string += "total sockets " + str(int(sock_fd_seen)) + " snd_cc " + str(int(snd_cc)) + " rcv_cc " + str(int(rcv_cc)) + "\n"
653        total_sock_fd[0] = sock_fd_seen
654    return out_string
655
656
657# Macro: showprocsockets
658@lldb_command('showprocsockets')
659def ShowProcSockets(cmd_args=None):
660    """ Given a proc_t pointer, display information about its sockets
661    """
662    total_snd_cc = [0]
663    total_rcv_cc = [0]
664    sock_fd_seen = [0]
665    out_string = ""
666    if cmd_args != None and len(cmd_args) > 0 :
667        proc = kern.GetValueFromAddress(cmd_args[0], 'proc *')
668
669        if not proc:
670            print("Unknown value passed as argument.")
671            return
672        else:
673            print(GetProcInfo(proc))
674            print(GetProcSockets(proc, total_snd_cc, total_rcv_cc, sock_fd_seen))
675    else:
676        print("Missing argument 0 in user function.")
677# EndMacro: showprocsockets
678
679# Macro: showallprocsockets
680@lldb_command('showallprocsockets')
681def ShowAllProcSockets(cmd_args=None):
682    """Display information about the sockets of all the processes
683    """
684    total_snd_cc = [0]
685    total_rcv_cc = [0]
686    for proc in kern.procs:
687        sock_fd_seen = [0]
688        out_str = ""
689        out_str += GetProcSockets(proc, total_snd_cc, total_rcv_cc, sock_fd_seen)
690        if sock_fd_seen[0] != 0:
691            print("================================================================================")
692            print(GetProcInfo(proc))
693            print(out_str)
694    print ("total_snd_cc: " + str(int(total_snd_cc[0])) + " total_rcv_cc: " + str(int(total_rcv_cc[0])) + "\n")
695# EndMacro: showallprocsockets
696
697
698def GetRtEntryPrDetailsAsString(rte):
699    out_string = ""
700    rt = Cast(rte, 'rtentry *')
701    dst = Cast(rt.rt_nodes[0].rn_u.rn_leaf.rn_Key, 'sockaddr *')
702    isv6 = 0
703    dst_string_format = "{0:<18s}"
704    if (dst.sa_family == AF_INET):
705        out_string += dst_string_format.format(GetSocketAddrAsStringInet(dst)) + " "
706    else:
707        if (dst.sa_family == AF_INET6):
708            out_string += dst_string_format.format(GetSocketAddrAsStringInet6(dst)) + " "
709            isv6 = 1
710        else:
711            if (dst.sa_family == AF_LINK):
712                out_string += dst_string_format.format(GetSocketAddrAsStringLink(dst))
713                if (isv6 == 1):
714                    out_string += "                       "
715                else:
716                    out_string += " "
717            else:
718                out_string += dst_string_format.format(GetSocketAddrAsStringUnspec(dst)) + " "
719
720    gw = Cast(rt.rt_gateway, 'sockaddr *')
721    if (gw.sa_family == AF_INET):
722        out_string += dst_string_format.format(GetSocketAddrAsStringInet(gw)) + " "
723    else:
724        if (gw.sa_family == 30):
725            out_string += dst_string_format.format(GetSocketAddrAsStringInet6(gw)) + " "
726            isv6 = 1
727        else:
728            if (gw.sa_family == 18):
729                out_string += dst_string_format.format(GetSocketAddrAsStringLink(gw)) + " "
730                if (isv6 == 1):
731                    out_string += "                       "
732                else:
733                    out_string += " "
734            else:
735                dst_string_format.format(GetSocketAddrAsStringUnspec(gw))
736
737    if (rt.rt_flags & RTF_WASCLONED):
738        if (kern.ptrsize == 8):
739            rt_flags_string_format = "0x{0:<16x}"
740            out_string += rt_flags_string_format.format(rt.rt_parent) + " "
741        else:
742            rt_flags_string_format = "0x{0:<8x}"
743            out_string += rt_flags_string_format.format(rt.rt_parent) + " "
744    else:
745        if (kern.ptrsize == 8):
746            out_string += "                   "
747        else:
748            out_string += "           "
749
750    rt_refcnt_rmx_string_format = "{0:<d} {1:>10d}  "
751    out_string += rt_refcnt_rmx_string_format.format(rt.rt_refcnt, rt.rt_rmx.rmx_pksent) + "   "
752
753    rtf_string_format = "{0:>s}"
754    if (rt.rt_flags & RTF_UP):
755        out_string += rtf_string_format.format("U")
756    if (rt.rt_flags & RTF_GATEWAY):
757        out_string += rtf_string_format.format("G")
758    if (rt.rt_flags & RTF_HOST):
759        out_string += rtf_string_format.format("H")
760    if (rt.rt_flags & RTF_REJECT):
761        out_string += rtf_string_format.format("R")
762    if (rt.rt_flags & RTF_DYNAMIC):
763        out_string += rtf_string_format.format("D")
764    if (rt.rt_flags & RTF_MODIFIED):
765        out_string += rtf_string_format.format("M")
766    if (rt.rt_flags & RTF_CLONING):
767        out_string += rtf_string_format.format("C")
768    if (rt.rt_flags & RTF_PRCLONING):
769        out_string += rtf_string_format.format("c")
770    if (rt.rt_flags & RTF_LLINFO):
771        out_string += rtf_string_format.format("L")
772    if (rt.rt_flags & RTF_STATIC):
773        out_string += rtf_string_format.format("S")
774    if (rt.rt_flags & RTF_PROTO1):
775        out_string += rtf_string_format.format("1")
776    if (rt.rt_flags & RTF_PROTO2):
777        out_string += rtf_string_format.format("2")
778    if (rt.rt_flags & RTF_PROTO3):
779        out_string += rtf_string_format.format("3")
780    if (rt.rt_flags & RTF_WASCLONED):
781        out_string += rtf_string_format.format("W")
782    if (rt.rt_flags & RTF_BROADCAST):
783        out_string += rtf_string_format.format("b")
784    if (rt.rt_flags & RTF_MULTICAST):
785        out_string += rtf_string_format.format("m")
786    if (rt.rt_flags & RTF_XRESOLVE):
787        out_string += rtf_string_format.format("X")
788    if (rt.rt_flags & RTF_BLACKHOLE):
789        out_string += rtf_string_format.format("B")
790    if (rt.rt_flags & RTF_IFSCOPE):
791        out_string += rtf_string_format.format("I")
792    if (rt.rt_flags & RTF_CONDEMNED):
793        out_string += rtf_string_format.format("Z")
794    if (rt.rt_flags & RTF_IFREF):
795        out_string += rtf_string_format.format("i")
796    if (rt.rt_flags & RTF_PROXY):
797        out_string += rtf_string_format.format("Y")
798    if (rt.rt_flags & RTF_ROUTER):
799        out_string += rtf_string_format.format("r")
800
801    out_string +=  "/"
802    out_string += str(rt.rt_ifp.if_name)
803    out_string += str(int(rt.rt_ifp.if_unit))
804    out_string += "\n"
805    return out_string
806
807
808RNF_ROOT = 2
809def GetRtTableAsString(rt_tables):
810    out_string = ""
811    rn = Cast(rt_tables.rnh_treetop, 'radix_node *')
812    rnh_cnt = rt_tables.rnh_cnt
813
814    while (rn.rn_bit >= 0):
815        rn = rn.rn_u.rn_node.rn_L
816
817    while 1:
818        base = Cast(rn, 'radix_node *')
819        while ((rn.rn_parent.rn_u.rn_node.rn_R == rn) and (rn.rn_flags & RNF_ROOT == 0)):
820            rn = rn.rn_parent
821        rn = rn.rn_parent.rn_u.rn_node.rn_R
822        while (rn.rn_bit >= 0):
823            rn = rn.rn_u.rn_node.rn_L
824        next_rn = rn
825        while (base != 0):
826            rn = base
827            base = rn.rn_u.rn_leaf.rn_Dupedkey
828            if ((rn.rn_flags & RNF_ROOT) == 0):
829                rt = Cast(rn, 'rtentry *')
830                if (kern.ptrsize == 8):
831                    rtentry_string_format = "0x{0:<18x}"
832                    out_string += rtentry_string_format.format(rt) + " "
833                else:
834                    rtentry_string_format = "0x{0:<10x}"
835                    out_string += rtentry_string_format.format(rt) + " "
836                out_string += GetRtEntryPrDetailsAsString(rt) + " "
837
838        rn = next_rn
839        if ((rn.rn_flags & RNF_ROOT) != 0):
840            break
841    return out_string
842
843def GetRtInetAsString():
844    rt_tables = kern.globals.rt_tables[2]
845    if (kern.ptrsize == 8):
846        rt_table_header_format_string = "{0:<18s} {1: <16s} {2:<20s} {3:<16s} {4:<8s} {5:<8s} {6:<8s}"
847        print(rt_table_header_format_string.format("rtentry", " dst", "gw", "parent", "Refs", "Use", "flags/if"))
848        print(rt_table_header_format_string.format("-" * 18, "-" * 16, "-" * 16, "-" * 16, "-" * 8, "-" * 8, "-" * 8))
849        print(GetRtTableAsString(rt_tables))
850    else:
851        rt_table_header_format_string = "{0:<8s} {1:<16s} {2:<18s} {3:<8s} {4:<8s} {5:<8s} {6:<8s}"
852        print(rt_table_header_format_string.format("rtentry", "dst", "gw", "parent", "Refs", "Use", "flags/if"))
853        print(rt_table_header_format_string.format("-" * 8, "-" * 16, "-" * 16, "-" * 8, "-" * 8, "-" * 8, "-" * 8))
854        print(GetRtTableAsString(rt_tables))
855
856def GetRtInet6AsString():
857    rt_tables = kern.globals.rt_tables[30]
858    if (kern.ptrsize == 8):
859        rt_table_header_format_string = "{0:<18s} {1: <16s} {2:<20s} {3:<16s} {4:<8s} {5:<8s} {6:<8s}"
860        print(rt_table_header_format_string.format("rtentry", " dst", "gw", "parent", "Refs", "Use", "flags/if"))
861        print(rt_table_header_format_string.format("-" * 18, "-" * 16, "-" * 16, "-" * 16, "-" * 8, "-" * 8, "-" * 8))
862        print(GetRtTableAsString(rt_tables))
863    else:
864        rt_table_header_format_string = "{0:<8s} {1:<16s} {2:<18s} {3:<8s} {4:<8s} {5:<8s} {6:<8s}"
865        print(rt_table_header_format_string.format("rtentry", "dst", "gw", "parent", "Refs", "Use", "flags/if"))
866        print(rt_table_header_format_string.format("-" * 8, "-" * 16, "-" * 18, "-" * 8, "-" * 8, "-" * 8, "-" * 8))
867        print(GetRtTableAsString(rt_tables))
868
869# Macro: show_rt_inet
870@lldb_command('show_rt_inet')
871def ShowRtInet(cmd_args=None):
872    """ Display the IPv4 routing table
873    """
874    print(GetRtInetAsString())
875# EndMacro: show_rt_inet
876
877# Macro: show_rt_inet6
878@lldb_command('show_rt_inet6')
879def ShowRtInet6(cmd_args=None):
880    """ Display the IPv6 routing table
881    """
882    print(GetRtInet6AsString())
883# EndMacro: show_rt_inet6
884
885# Macro: rtentry_showdbg
886@lldb_command('rtentry_showdbg')
887def ShowRtEntryDebug(cmd_args=None):
888    """ Print the debug information of a route entry
889    """
890    if cmd_args is None or len(cmd_args) == 0:
891            print("Missing argument 0 in user function.")
892            return
893    out_string = ""
894    cnt = 0
895    rtd = kern.GetValueFromAddress(cmd_args[0], 'rtentry_dbg *')
896    rtd_summary_format_string = "{0:s} {1:d}"
897    out_string += rtd_summary_format_string.format("Total holds : ", rtd.rtd_refhold_cnt) + "\n"
898    out_string += rtd_summary_format_string.format("Total releases : ", rtd.rtd_refrele_cnt) + "\n"
899
900    ix = 0
901    while (ix < CTRACE_STACK_SIZE):
902        kgm_pc = rtd.rtd_alloc.pc[ix]
903        if (kgm_pc != 0):
904            if (ix == 0):
905                out_string += "\nAlloc: (thread " + hex(rtd.rtd_alloc.th) + "):\n"
906            out_string += str(int(ix + 1)) + ": "
907            out_string += GetSourceInformationForAddress(kgm_pc)
908            out_string += "\n"
909        ix += 1
910
911    ix = 0
912    while (ix < CTRACE_STACK_SIZE):
913        kgm_pc = rtd.rtd_free.pc[ix]
914        if (kgm_pc != 0):
915            if (ix == 0):
916                out_string += "\nFree: (thread " + hex(rtd.rtd_free.th) + "):\n"
917            out_string += str(int(ix + 1)) + ": "
918            out_string += GetSourceInformationForAddress(kgm_pc)
919            out_string += "\n"
920        ix += 1
921
922    while (cnt < RTD_TRACE_HIST_SIZE):
923        ix = 0
924        while (ix < CTRACE_STACK_SIZE):
925            kgm_pc = rtd.rtd_refhold[cnt].pc[ix]
926            if (kgm_pc != 0):
927                if (ix == 0):
928                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(rtd.rtd_refhold[cnt].th) + "):\n"
929                out_string += str(int(ix + 1)) + ": "
930                out_string += GetSourceInformationForAddress(kgm_pc)
931                out_string += "\n"
932            ix += 1
933        cnt += 1
934
935    cnt = 0
936    while (cnt < RTD_TRACE_HIST_SIZE):
937        ix = 0
938        while (ix < CTRACE_STACK_SIZE):
939            kgm_pc = rtd.rtd_refrele[cnt].pc[ix]
940            if (kgm_pc != 0):
941                if (ix == 0):
942                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(rtd.rtd_refrele[cnt].th) + "):\n"
943                out_string += str(int(ix + 1)) + ": "
944                out_string += GetSourceInformationForAddress(kgm_pc)
945                out_string += "\n"
946            ix += 1
947        cnt += 1
948
949    out_string += "\nTotal locks : " + str(int(rtd.rtd_lock_cnt))
950    out_string += "\nTotal unlocks : " + str(int(rtd.rtd_unlock_cnt))
951
952    cnt = 0
953    while (cnt < RTD_TRACE_HIST_SIZE):
954        ix = 0
955        while (ix < CTRACE_STACK_SIZE):
956            kgm_pc = rtd.rtd_lock[cnt].pc[ix]
957            if (kgm_pc != 0):
958                if (ix == 0):
959                    out_string += "\nLock [" + str(int(cnt)) + "] (thread " + hex(rtd.rtd_lock[cnt].th) + "):\n"
960                out_string += str(int(ix + 1)) + ": "
961                out_string += GetSourceInformationForAddress(kgm_pc)
962                out_string += "\n"
963            ix += 1
964        cnt += 1
965
966    cnt = 0
967    while (cnt < RTD_TRACE_HIST_SIZE):
968        ix = 0
969        while (ix < CTRACE_STACK_SIZE):
970            kgm_pc = rtd.rtd_unlock[cnt].pc[ix]
971            if (kgm_pc != 0):
972                if (ix == 0):
973                    out_string += "\nUnlock [" + str(int(cnt)) + "] (thread " + hex(rtd.rtd_unlock[cnt].th) + "):\n"
974                out_string += str(int(ix + 1)) + ": "
975                out_string += GetSourceInformationForAddress(kgm_pc)
976                out_string += "\n"
977            ix += 1
978        cnt += 1
979
980    print(out_string)
981# EndMacro: rtentry_showdbg
982
983# Macro: inm_showdbg
984@lldb_command('inm_showdbg')
985def InmShowDebug(cmd_args=None):
986    """ Print the debug information of an IPv4 multicast address
987    """
988    if cmd_args is None or len(cmd_args) == 0:
989            print("Missing argument 0 in user function.")
990            return
991    out_string = ""
992    cnt = 0
993    inm = kern.GetValueFromAddress(cmd_args[0], 'in_multi_dbg *')
994    in_multi_summary_format_string = "{0:s} {1:d}"
995    out_string += in_multi_summary_format_string.format("Total holds : ", inm.inm_refhold_cnt)
996    out_string += in_multi_summary_format_string.format("Total releases : ", inm.inm_refrele_cnt)
997
998    while (cnt < INM_TRACE_HIST_SIZE):
999        ix = 0
1000        while (ix < CTRACE_STACK_SIZE):
1001            kgm_pc = inm.inm_refhold[cnt].pc[ix]
1002            if (kgm_pc != 0):
1003                if (ix == 0):
1004                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(inm.inm_refhold[cnt].th) + "):\n"
1005                out_string += str(int(ix + 1)) + ": "
1006                out_string += GetSourceInformationForAddress(kgm_pc)
1007                out_string += "\n"
1008            ix += 1
1009        cnt += 1
1010    cnt = 0
1011    while (cnt < INM_TRACE_HIST_SIZE):
1012        ix = 0
1013        while (ix < CTRACE_STACK_SIZE):
1014            kgm_pc = inm.inm_refrele[cnt].pc[ix]
1015            if (kgm_pc != 0):
1016                if (ix == 0):
1017                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(inm.inm_refrele[cnt].th) + "):\n"
1018                out_string += str(int(ix + 1)) + ": "
1019                out_string += GetSourceInformationForAddress(kgm_pc)
1020                out_string += "\n"
1021            ix += 1
1022        cnt += 1
1023    print(out_string)
1024# EndMacro: inm_showdbg
1025
1026# Macro: ifma_showdbg
1027@lldb_command('ifma_showdbg')
1028def IfmaShowDebug(cmd_args=None):
1029    """ Print the debug information of a link multicast address
1030    """
1031    if cmd_args is None or len(cmd_args) == 0:
1032            print("Missing argument 0 in user function.")
1033            return
1034    out_string = ""
1035    cnt = 0
1036    ifma = kern.GetValueFromAddress(cmd_args[0], 'ifmultiaddr_dbg *')
1037    link_multi_summary_format_string = "{0:s} {1:d}"
1038    out_string += link_multi_summary_format_string.format("Total holds : ", ifma.ifma_refhold_cnt) + "\n"
1039    out_string += link_multi_summary_format_string.format("Total releases : ", ifma.ifma_refrele_cnt) + "\n"
1040
1041    while (cnt < IFMA_TRACE_HIST_SIZE):
1042        ix = 0
1043        while (ix < CTRACE_STACK_SIZE):
1044            kgm_pc = ifma.ifma_refhold[cnt].pc[ix]
1045            if (kgm_pc != 0):
1046                if (ix == 0):
1047                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(ifma.ifma_refhold[cnt].th) + "):\n"
1048                out_string += str(int(ix + 1)) + ": "
1049                out_string += GetSourceInformationForAddress(kgm_pc)
1050                out_string += "\n"
1051            ix += 1
1052        cnt += 1
1053    cnt = 0
1054    while (cnt < IFMA_TRACE_HIST_SIZE):
1055        ix = 0
1056        while (ix < CTRACE_STACK_SIZE):
1057            kgm_pc = ifma.ifma_refrele[cnt].pc[ix]
1058            if (kgm_pc != 0):
1059                if (ix == 0):
1060                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(ifma.ifma_refrele[cnt].th) + "):\n"
1061                out_string += str(int(ix + 1)) + ": "
1062                out_string += GetSourceInformationForAddress(kgm_pc)
1063                out_string += "\n"
1064            ix += 1
1065        cnt += 1
1066    print(out_string)
1067# EndMacro: ifma_showdbg
1068
1069# Macro: ifpref_showdbg
1070@lldb_command('ifpref_showdbg')
1071def IfpRefShowDebug(cmd_args=None):
1072    """ Print the debug information of an interface ref count
1073    """
1074    if cmd_args is None or len(cmd_args) == 0:
1075            print("Missing argument 0 in user function.")
1076            return
1077    out_string = ""
1078    cnt = 0
1079    dl_if = kern.GetValueFromAddress(cmd_args[0], 'dlil_ifnet_dbg *')
1080    dl_if_summary_format_string = "{0:s} {1:d}"
1081    out_string +=  dl_if_summary_format_string.format("Total holds : ", dl_if.dldbg_if_refhold_cnt)
1082    out_string += dl_if_summary_format_string.format("Total releases : ", dl_if.dldbg_if_refrele_cnt)
1083
1084    while (cnt < IF_REF_TRACE_HIST_SIZE):
1085        ix = 0
1086        while (ix < CTRACE_STACK_SIZE):
1087            kgm_pc = dl_if.dldbg_if_refhold[cnt].pc[ix]
1088            if (kgm_pc != 0):
1089                if (ix == 0):
1090                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(dl_if.dldbg_if_refhold[cnt].th) + "):\n"
1091                out_string += str(int(ix + 1)) + ": "
1092                out_string += GetSourceInformationForAddress(kgm_pc)
1093                out_string += "\n"
1094            ix += 1
1095        cnt += 1
1096    cnt = 0
1097    while (cnt < IF_REF_TRACE_HIST_SIZE):
1098        ix = 0
1099        while (ix < CTRACE_STACK_SIZE):
1100            kgm_pc = dl_if.dldbg_if_refrele[cnt].pc[ix]
1101            if (kgm_pc != 0):
1102                if (ix == 0):
1103                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(dl_if.dldbg_if_refrele[cnt].th) + "):\n"
1104                out_string += str(int(ix + 1)) + ": "
1105                out_string += GetSourceInformationForAddress(kgm_pc)
1106                out_string += "\n"
1107            ix += 1
1108        cnt += 1
1109    print(out_string)
1110# EndMacro: ifpref_showdbg
1111
1112# Macro: ndpr_showdbg
1113@lldb_command('ndpr_showdbg')
1114def ndprShowDebug(cmd_args=None):
1115    """ Print the debug information of a nd_prefix structure
1116    """
1117    if cmd_args is None or len(cmd_args) == 0:
1118            print("Missing argument 0 in user function.")
1119            return
1120    out_string = ""
1121    cnt = 0
1122    ndpr = kern.GetValueFromAddress(cmd_args[0], 'nd_prefix_dbg *')
1123    ndpr_summary_format_string = "{0:s} {1:d}"
1124    out_string += ndpr_summary_format_string.format("Total holds : ", ndpr.ndpr_refhold_cnt)
1125    out_string += ndpr_summary_format_string.format("Total releases : ", ndpr.ndpr_refrele_cnt)
1126
1127    while (cnt < NDPR_TRACE_HIST_SIZE):
1128        ix = 0
1129        while (ix < CTRACE_STACK_SIZE):
1130            kgm_pc = ndpr.ndpr_refhold[cnt].pc[ix]
1131            if (kgm_pc != 0):
1132                if (ix == 0):
1133                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(ndpr.ndpr_refhold[cnt].th) + "):\n"
1134                out_string += str(int(ix + 1)) + ": "
1135                out_string += GetSourceInformationForAddress(kgm_pc)
1136                out_string += "\n"
1137            ix += 1
1138        cnt += 1
1139    cnt = 0
1140    while (cnt < NDPR_TRACE_HIST_SIZE):
1141        ix = 0
1142        while (ix < CTRACE_STACK_SIZE):
1143            kgm_pc = ndpr.ndpr_refrele[cnt].pc[ix]
1144            if (kgm_pc != 0):
1145                if (ix == 0):
1146                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(ndpr.ndpr_refrele[cnt].th) + "):\n"
1147                out_string += str(int(ix + 1)) + ": "
1148                out_string += GetSourceInformationForAddress(kgm_pc)
1149                out_string += "\n"
1150            ix += 1
1151        cnt += 1
1152    print(out_string)
1153# EndMacro: ndpr_showdbg
1154
1155# Macro: nddr_showdbg
1156@lldb_command('nddr_showdbg')
1157def nddrShowDebug(cmd_args=None):
1158    """ Print the debug information of a nd_defrouter structure
1159    """
1160    if cmd_args is None or len(cmd_args) == 0:
1161            print("Missing argument 0 in user function.")
1162            return
1163    out_string = ""
1164    cnt = 0
1165    nddr = kern.GetValueFromAddress(cmd_args[0], 'nd_defrouter_dbg *')
1166    nddr_summary_format_string = "{0:s} {1:d}"
1167    out_string += nddr_summary_format_string.format("Total holds : ", nddr.nddr_refhold_cnt)
1168    out_string += nddr_summary_format_string.format("Total releases : ", nddr.nddr_refrele_cnt)
1169
1170    while (cnt < NDDR_TRACE_HIST_SIZE):
1171        ix = 0
1172        while (ix < CTRACE_STACK_SIZE):
1173            kgm_pc = nddr.nddr_refhold[cnt].pc[ix]
1174            if (kgm_pc != 0):
1175                if (ix == 0):
1176                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(nddr.nddr_refhold[cnt].th) + "):\n"
1177                out_string += str(int(ix + 1)) + ": "
1178                out_string += GetSourceInformationForAddress(kgm_pc)
1179                out_string += "\n"
1180            ix += 1
1181        cnt += 1
1182    cnt = 0
1183    while (cnt < NDDR_TRACE_HIST_SIZE):
1184        ix = 0
1185        while (ix < CTRACE_STACK_SIZE):
1186            kgm_pc = nddr.nddr_refrele[cnt].pc[ix]
1187            if (kgm_pc != 0):
1188                if (ix == 0):
1189                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(nddr.nddr_refrele[cnt].th) + "):\n"
1190                out_string += str(int(ix + 1)) + ": "
1191                out_string += GetSourceInformationForAddress(kgm_pc)
1192                out_string += "\n"
1193            ix += 1
1194        cnt += 1
1195    print(out_string)
1196# EndMacro: nddr_showdbg
1197
1198# Macro: imo_showdbg
1199@lldb_command('imo_showdbg')
1200def IpmOptions(cmd_args=None):
1201    """ Print the debug information of a ip_moptions structure
1202    """
1203    if cmd_args is None or len(cmd_args) == 0:
1204            print("Missing argument 0 in user function.")
1205            return
1206    out_string = ""
1207    cnt = 0
1208    imo = kern.GetValueFromAddress(cmd_args[0], 'ip_moptions_dbg *')
1209    imo_summary_format_string = "{0:s} {1:d}"
1210    out_string += imo_summary_format_string.format("Total holds : ", imo.imo_refhold_cnt)
1211    out_string += imo_summary_format_string.format("Total releases : ", imo.imo_refrele_cnt)
1212
1213    while (cnt < IMO_TRACE_HIST_SIZE):
1214        ix = 0
1215        while (ix < CTRACE_STACK_SIZE):
1216            kgm_pc = imo.imo_refhold[cnt].pc[ix]
1217            if (kgm_pc != 0):
1218                if (ix == 0):
1219                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(imo.imo_refhold[cnt].th) + "):\n"
1220                out_string += str(int(ix + 1)) + ": "
1221                out_string += GetSourceInformationForAddress(kgm_pc)
1222                out_string += "\n"
1223            ix += 1
1224        cnt += 1
1225    cnt = 0
1226    while (cnt < IMO_TRACE_HIST_SIZE):
1227        ix = 0
1228        while (ix < CTRACE_STACK_SIZE):
1229            kgm_pc = imo.imo_refrele[cnt].pc[ix]
1230            if (kgm_pc != 0):
1231                if (ix == 0):
1232                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(imo.imo_refrele[cnt].th) + "):\n"
1233                out_string += str(int(ix + 1)) + ": "
1234                out_string += GetSourceInformationForAddress(kgm_pc)
1235                out_string += "\n"
1236            ix += 1
1237        cnt += 1
1238    print(out_string)
1239# EndMacro: imo_showdbg
1240
1241# Macro: im6o_showdbg
1242@lldb_command('im6o_showdbg')
1243def IpmOptions(cmd_args=None):
1244    """ Print the debug information of a ip6_moptions structure
1245    """
1246    if cmd_args is None or len(cmd_args) == 0:
1247            print("Missing argument 0 in user function.")
1248            return
1249    out_string = ""
1250    cnt = 0
1251    im6o = kern.GetValueFromAddress(cmd_args[0], 'ip6_moptions_dbg *')
1252    im6o_summary_format_string = "{0:s} {1:d}"
1253    out_string += im6o_summary_format_string.format("Total holds : ", im6o.im6o_refhold_cnt)
1254    out_string += im6o_summary_format_string.format("Total releases : ", im6o.im6o_refrele_cnt)
1255
1256    while (cnt < IM6O_TRACE_HIST_SIZE):
1257        ix = 0
1258        while (ix < CTRACE_STACK_SIZE):
1259            kgm_pc = im6o.im6o_refhold[cnt].pc[ix]
1260            if (kgm_pc != 0):
1261                if (ix == 0):
1262                    out_string += "\nHold [" + str(int(cnt)) + "] (thread " + hex(im6o.im6o_refhold[cnt].th) + "):\n"
1263                out_string += str(int(ix + 1)) + ": "
1264                out_string += GetSourceInformationForAddress(kgm_pc)
1265                out_string += "\n"
1266            ix += 1
1267        cnt += 1
1268    cnt = 0
1269    while (cnt < IM6O_TRACE_HIST_SIZE):
1270        ix = 0
1271        while (ix < CTRACE_STACK_SIZE):
1272            kgm_pc = im6o.im6o_refrele[cnt].pc[ix]
1273            if (kgm_pc != 0):
1274                if (ix == 0):
1275                    out_string += "\nRelease [" + str(int(cnt)) + "] (thread " + hex(im6o.im6o_refrele[cnt].th) + "):\n"
1276                out_string += str(int(ix + 1)) + ": "
1277                out_string += GetSourceInformationForAddress(kgm_pc)
1278                out_string += "\n"
1279            ix += 1
1280        cnt += 1
1281    print(out_string)
1282# EndMacro: im6o_showdbg
1283
1284# Macro: rtentry_trash
1285@lldb_command('rtentry_trash')
1286def RtEntryTrash(cmd_args=None):
1287    """ Walk the list of trash route entries
1288    """
1289    out_string = ""
1290    rt_trash_head = kern.globals.rttrash_head
1291    rtd = Cast(rt_trash_head.tqh_first, 'rtentry_dbg *')
1292    rt_trash_format_string = "{0:4d}: {1:x} {2:3d} {3:6d} {4:6d}"
1293    cnt = 0
1294    while (int(rtd) != 0):
1295        if (cnt == 0):
1296            if (kern.ptrsize == 8):
1297                print("                rtentry ref   hold   rele             dst    gw             parent flags/if\n")
1298                print("      ----------------- --- ------ ------ --------------- ----- ------------------ -----------\n")
1299            else:
1300                print("        rtentry ref   hold   rele             dst    gw     parent flags/if\n")
1301                print("      --------- --- ------ ------ --------------- ----- ---------- -----------\n")
1302        out_string += rt_trash_format_string.format(cnt, rtd, rtd.rtd_refhold_cnt - rtd.rtd_refrele_cnt, rtd.rtd_refhold_cnt, rtd.rtd_refrele_cnt) + "   "
1303        out_string += GetRtEntryPrDetailsAsString(rtd) + "\n"
1304        rtd = rtd.rtd_trash_link.tqe_next
1305        cnt += 1
1306    print(out_string)
1307# EndMacro: rtentry_trash
1308
1309# Macro: show_rtentry
1310@lldb_command('show_rtentry')
1311def ShRtEntry(cmd_args=None):
1312    """ Print rtentry.
1313    """
1314    out_string = ""
1315    rt = kern.GetValueFromAddress(cmd_args[0], 'rtentry *')
1316    out_string += GetRtEntryPrDetailsAsString(rt) + "\n"
1317    print(out_string)
1318# EndMacro: show_rtentry
1319
1320# Macro: inifa_trash
1321@lldb_command('inifa_trash')
1322def InIfaTrash(cmd_args=None):
1323    """ Walk the list of trash in_ifaddr entries
1324    """
1325    out_string = ""
1326    ifa_trash_head = kern.globals.inifa_trash_head
1327    ifa = Cast(ifa_trash_head.tqh_first, 'in_ifaddr_dbg *')
1328    inifa_trash_format_string = "{0:4d}: {1:x} {2:3d} {3:6d} {4:6d}"
1329    cnt = 0
1330    while (int(ifa) != 0):
1331        if (cnt == 0):
1332            if (kern.ptrsize == 8):
1333                print("                  in_ifa  ref   hold   rele")
1334                print("      ------------------  ---  ------  ----")
1335            else:
1336                print("          in_ifa  ref   hold   rele")
1337                print("      ----------  ---  ----- ------")
1338        out_string += inifa_trash_format_string.format(cnt + 1, ifa, ifa.inifa_refhold_cnt - ifa.inifa_refrele_cnt, ifa.inifa_refhold_cnt, ifa.inifa_refrele_cnt) + "   "
1339        out_string += GetSocketAddrAsStringInet(ifa.inifa.ia_ifa.ifa_addr) + "\n"
1340        ifa = ifa.inifa_trash_link.tqe_next
1341        cnt += 1
1342    print(out_string)
1343# EndMacro: inifa_trash
1344
1345# Macro: in6ifa_trash
1346@lldb_command('in6ifa_trash')
1347def In6IfaTrash(cmd_args=None):
1348    """ Walk the list of trash in6_ifaddr entries
1349    """
1350    out_string = ""
1351    in6ifa_trash_head = kern.globals.in6ifa_trash_head
1352    ifa = Cast(in6ifa_trash_head.tqh_first, 'in6_ifaddr_dbg *')
1353    in6ifa_trash_format_string = "{0:4d}: 0x{1:x} {2:3d} {3:6d} {4:6d}"
1354    cnt = 0
1355    while (int(ifa) != 0):
1356        if (cnt == 0):
1357            if (kern.ptrsize == 8):
1358                print("                 in6_ifa  ref   hold   rele")
1359                print("      ------------------  --- ------ ------")
1360            else:
1361                print("         in6_ifa  ref   hold   rele")
1362                print("      ----------  --- ------ ------")
1363        out_string += in6ifa_trash_format_string.format(cnt + 1, ifa, ifa.in6ifa_refhold_cnt - ifa.in6ifa_refrele_cnt, ifa.in6ifa_refhold_cnt, ifa.in6ifa_refrele_cnt) + "   "
1364        out_string += GetSocketAddrAsStringInet6(ifa.in6ifa.ia_ifa.ifa_addr) + "\n"
1365        ifa = ifa.in6ifa_trash_link.tqe_next
1366        cnt += 1
1367    print(out_string)
1368# EndMacro: in6ifa_trash
1369
1370# Macro: inm_trash
1371@lldb_command('inm_trash')
1372def InmTrash(cmd_args=None):
1373    """ Walk the list of trash in_multi entries
1374    """
1375    out_string = ""
1376    inm_trash_head = kern.globals.inm_trash_head
1377    inm = Cast(inm_trash_head.tqh_first, 'in_multi_dbg *')
1378    inm_trash_format_string = "{0:4d}: {1:x} {2:3d} {3:6d} {4:6d}"
1379    cnt = 0
1380    while (int(inm) != 0):
1381        if (cnt == 0):
1382            if (kern.ptrsize == 8):
1383                print("                     inm  ref   hold   rele")
1384                print("      ------------------  --- ------ ------")
1385            else:
1386                print("             inm  ref   hold   rele")
1387                print("      ----------  --- ------ ------")
1388        out_string += inm_trash_format_string.format(cnt + 1, inm, inm.inm_refhold_cnt - inm.inm_refrele_cnt, inm.inm_refhold_cnt, inm.inm_refrele_cnt) + "   "
1389        out_string += GetInAddrAsString(addressof(inm.inm.inm_addr)) + "\n"
1390        inm = inm.inm_trash_link.tqe_next
1391        cnt += 1
1392    print(out_string)
1393# EndMacro: inm_trash
1394
1395# Macro: in6m_trash
1396@lldb_command('in6m_trash')
1397def In6mTrash(cmd_args=None):
1398    """ Walk the list of trash in6_multi entries
1399    """
1400    out_string = ""
1401    in6m_trash_head = kern.globals.in6m_trash_head
1402    in6m = Cast(in6m_trash_head.tqh_first, 'in6_multi_dbg *')
1403    in6m_trash_format_string = "{0:4d}: {1:x} {2:3d} {3:6d} {4:6d}"
1404    cnt = 0
1405    while (int(in6m) != 0):
1406        if (cnt == 0):
1407            if (kern.ptrsize == 8):
1408                print("                    in6m  ref   hold   rele")
1409                print("      ------------------  --- ------ ------")
1410            else:
1411                print("            in6m  ref   hold   rele")
1412                print("      ----------  --- ------ ------")
1413        out_string += in6m_trash_format_string.format(cnt + 1, in6m, in6m.in6m_refhold_cnt - in6m.in6m_refrele_cnt, in6m.in6m_refhold_cnt, in6m.in6m_refrele_cnt) + "   "
1414        out_string += GetIn6AddrAsString(addressof(in6m.in6m.in6m_addr)) + "\n"
1415        in6m = in6m.in6m_trash_link.tqe_next
1416        cnt += 1
1417    print(out_string)
1418# EndMacro: in6m_trash
1419
1420# Macro: ifma_trash
1421@lldb_command('ifma_trash')
1422def IfmaTrash(cmd_args=None):
1423    """ Walk the list of trash ifmultiaddr entries
1424    """
1425    out_string = ""
1426    ifma_trash_head = kern.globals.ifma_trash_head
1427    ifma = Cast(ifma_trash_head.tqh_first, 'ifmultiaddr_dbg *')
1428    ifma_trash_format_string = "{0:4d}: {1:x} {2:3d} {3:6d} {4:6d}"
1429    cnt = 0
1430    while (int(ifma) != 0):
1431        if (cnt == 0):
1432            if (kern.ptrsize == 8):
1433                print("                    ifma  ref   hold   rele")
1434                print("      ------------------  --- ------ ------")
1435            else:
1436                print("            ifma  ref   hold   rele")
1437                print("      ----------  --- ------ ------")
1438        out_string += ifma_trash_format_string.format(cnt + 1, ifma, ifma.ifma_refhold_cnt - ifma.ifma_refrele_cnt, ifma.ifma_refhold_cnt, ifma.ifma_refrele_cnt) + "   "
1439        out_string += GetSocketAddrAsString(ifma.ifma.ifma_addr) + "\n"
1440        out_string += " @ " + ifma.ifma.ifma_ifp.if_xname
1441        ifma = ifma.ifma_trash_link.tqe_next
1442        cnt += 1
1443    print(out_string)
1444# EndMacro: ifma_trash
1445
1446def GetInPcb(pcb, proto):
1447    out_string = ""
1448    out_string += hex(pcb)
1449
1450    if (proto == IPPROTO_TCP):
1451        out_string +=  " tcp"
1452    elif (proto == IPPROTO_UDP):
1453        out_string += " udp"
1454    elif (proto == IPPROTO_RAW):
1455        out_string += " raw"
1456    else:
1457        out_string += str(proto) +  "."
1458
1459    if (pcb.inp_vflag & INP_IPV4):
1460        out_string += "4 "
1461    if (pcb.inp_vflag & INP_IPV6):
1462        out_string += "6 "
1463
1464    if (pcb.inp_vflag & INP_IPV4):
1465        out_string += "                                       "
1466        out_string += GetInAddrAsString(addressof(pcb.inp_dependladdr.inp46_local.ia46_addr4))
1467    else:
1468        out_string += "  "
1469        out_string += GetIn6AddrAsString((pcb.inp_dependladdr.inp6_local.__u6_addr.__u6_addr8))
1470
1471    out_string += " "
1472    out_string += Getntohs(pcb.inp_lport)
1473    out_string += " "
1474
1475    if (pcb.inp_vflag & INP_IPV4):
1476        out_string += "                                 "
1477        out_string += GetInAddrAsString(addressof(pcb.inp_dependfaddr.inp46_foreign.ia46_addr4))
1478    else:
1479        out_string += GetIn6AddrAsString((pcb.inp_dependfaddr.inp6_foreign.__u6_addr.__u6_addr8))
1480
1481    out_string += " "
1482    out_string += Getntohs(pcb.inp_fport)
1483    out_string += " "
1484
1485    if (proto == IPPROTO_TCP):
1486        out_string += GetTcpState(pcb.inp_ppcb)
1487
1488    out_string += "\n\t"
1489    if (pcb.inp_flags & INP_RECVOPTS):
1490        out_string += "recvopts "
1491    if (pcb.inp_flags & INP_RECVRETOPTS):
1492        out_string += "recvretopts "
1493    if (pcb.inp_flags & INP_RECVDSTADDR):
1494        out_string += "recvdstaddr "
1495    if (pcb.inp_flags & INP_HDRINCL):
1496        out_string += "hdrincl "
1497    if (pcb.inp_flags & INP_HIGHPORT):
1498        out_string += "highport "
1499    if (pcb.inp_flags & INP_LOWPORT):
1500        out_string += "lowport "
1501    if (pcb.inp_flags & INP_ANONPORT):
1502        out_string += "anonport "
1503    if (pcb.inp_flags & INP_RECVIF):
1504        out_string += "recvif "
1505    if (pcb.inp_flags & INP_MTUDISC):
1506        out_string += "mtudisc "
1507    if (pcb.inp_flags & INP_STRIPHDR):
1508        out_string += "striphdr "
1509    if (pcb.inp_flags & INP_RECV_ANYIF):
1510        out_string += "recv_anyif "
1511    if (pcb.inp_flags & INP_INADDR_ANY):
1512        out_string += "inaddr_any "
1513    if (pcb.inp_flags & INP_RECVTTL):
1514        out_string += "recvttl "
1515    if (pcb.inp_flags & INP_UDP_NOCKSUM):
1516        out_string += "nocksum "
1517    if (pcb.inp_flags & INP_BOUND_IF):
1518        out_string += "boundif "
1519    if (pcb.inp_flags & IN6P_IPV6_V6ONLY):
1520        out_string += "v6only "
1521    if (pcb.inp_flags & IN6P_PKTINFO):
1522        out_string += "pktinfo "
1523    if (pcb.inp_flags & IN6P_HOPLIMIT):
1524        out_string += "hoplimit "
1525    if (pcb.inp_flags & IN6P_HOPOPTS):
1526        out_string += "hopopts "
1527    if (pcb.inp_flags & IN6P_DSTOPTS):
1528        out_string += "dstopts "
1529    if (pcb.inp_flags & IN6P_RTHDR):
1530        out_string += "rthdr "
1531    if (pcb.inp_flags & IN6P_RTHDRDSTOPTS):
1532        out_string += "rthdrdstopts "
1533    if (pcb.inp_flags & IN6P_TCLASS):
1534        out_string += "rcv_tclass "
1535    if (pcb.inp_flags & IN6P_AUTOFLOWLABEL):
1536        out_string += "autoflowlabel "
1537    if (pcb.inp_flags & IN6P_BINDV6ONLY):
1538        out_string += "bindv6only "
1539    if (pcb.inp_flags & IN6P_RFC2292):
1540        out_string += "RFC2292 "
1541    if (pcb.inp_flags & IN6P_MTU):
1542        out_string += "rcv_pmtu "
1543    if (pcb.inp_flags & INP_PKTINFO):
1544        out_string += "pktinfo "
1545    if (pcb.inp_flags & INP_FLOW_SUSPENDED):
1546        out_string += "suspended "
1547    if (pcb.inp_flags & INP_NO_IFT_CELLULAR):
1548        out_string += "nocellular "
1549    if (pcb.inp_flags & INP_FLOW_CONTROLLED):
1550        out_string += "flowctld "
1551    if (pcb.inp_flags & INP_FC_FEEDBACK):
1552        out_string += "fcfeedback "
1553    if (pcb.inp_flags2 & INP2_TIMEWAIT):
1554        out_string += "timewait "
1555    if (pcb.inp_flags2 & INP2_IN_FCTREE):
1556        out_string += "in_fctree "
1557    if (pcb.inp_flags2 & INP2_WANT_APP_POLICY):
1558        out_string += "want_app_policy "
1559
1560    out_string += "\n\t"
1561    so = pcb.inp_socket
1562    if (so != 0):
1563        out_string += "so=" + str(so) + " s=" + str(int(so.so_snd.sb_cc)) + " r=" + str(int(so.so_rcv.sb_cc))
1564        if proto == IPPROTO_TCP :
1565            tcpcb = cast(pcb.inp_ppcb, 'tcpcb *')
1566            out_string += " reass=" + str(int(tcpcb.t_reassqlen))
1567
1568        out_string += " usecnt=" + str(int(so.so_usecount)) + ", "
1569
1570    if (pcb.inp_state == 0 or pcb.inp_state == INPCB_STATE_INUSE):
1571        out_string += "inuse"
1572    else:
1573        if (pcb.inp_state == INPCB_STATE_DEAD):
1574            out_string += "dead"
1575        else:
1576            out_string += "unknown (" + str(int(pcb.inp_state)) + ")"
1577
1578    return out_string
1579
1580def CalcMbufInList(mpkt, pkt_cnt, buf_byte_cnt, mbuf_cnt, mbuf_cluster_cnt):
1581    while (mpkt != 0):
1582        mp = mpkt
1583        if kern.globals.mb_uses_mcache == 1:
1584            mpkt = mp.m_hdr.mh_nextpkt
1585        else:
1586            mpkt = mp.M_hdr_common.M_hdr.mh_nextpkt
1587        pkt_cnt[0] +=1
1588        while (mp != 0):
1589            if kern.globals.mb_uses_mcache == 1:
1590                mnext = mp.m_hdr.mh_next
1591                mflags = mp.m_hdr.mh_flags
1592                mtype = mp.m_hdr.mh_type
1593            else:
1594                mnext = mp.M_hdr_common.M_hdr.mh_next
1595                mflags = mp.M_hdr_common.M_hdr.mh_flags
1596                mtype = mp.M_hdr_common.M_hdr.mh_type
1597            mbuf_cnt[0] += 1
1598            buf_byte_cnt[int(mtype)] += 256
1599            buf_byte_cnt[Mbuf_Type.MT_LAST] += 256
1600            if (mflags & 0x01):
1601                mbuf_cluster_cnt[0] += 1
1602                if kern.globals.mb_uses_mcache == 1:
1603                    extsize = mp.M_dat.MH.MH_dat.MH_ext.ext_size
1604                else:
1605                    extsize = mp.M_hdr_common.M_ext.ext_size
1606                buf_byte_cnt[int(mtype)] += extsize
1607                buf_byte_cnt[Mbuf_Type.MT_LAST] += extsize
1608            mp = mnext
1609
1610def CalcMbufInSB(so, snd_cc, snd_buf, rcv_cc, rcv_buf, snd_record_cnt, rcv_record_cnt, snd_mbuf_cnt, rcv_mbuf_cnt, snd_mbuf_cluster_cnt, rcv_mbuf_cluster_cnt):
1611    snd_cc[0] += so.so_snd.sb_cc
1612    mpkt = so.so_snd.sb_mb
1613    CalcMbufInList(mpkt, snd_record_cnt, snd_buf, snd_mbuf_cnt, snd_mbuf_cluster_cnt)
1614    rcv_cc[0] += so.so_rcv.sb_cc
1615    mpkt = so.so_rcv.sb_mb
1616    CalcMbufInList(mpkt, rcv_record_cnt, rcv_buf, rcv_mbuf_cnt, rcv_mbuf_cluster_cnt)
1617
1618# Macro: show_socket_sb_mbuf_usage
1619@lldb_command('show_socket_sb_mbuf_usage')
1620def ShowSocketSbMbufUsage(cmd_args=None):
1621    """ Display for a socket the mbuf usage of the send and receive socket buffers
1622    """
1623    if cmd_args is None or len(cmd_args) == 0:
1624            print("Missing argument 0 in user function.")
1625            return
1626    so = kern.GetValueFromAddress(cmd_args[0], 'socket *')
1627    out_string = ""
1628    if (so != 0):
1629        snd_mbuf_cnt = [0]
1630        snd_mbuf_cluster_cnt = [0]
1631        snd_record_cnt = [0]
1632        snd_cc = [0]
1633        snd_buf = [0] * (Mbuf_Type.MT_LAST + 1)
1634        rcv_mbuf_cnt = [0]
1635        rcv_mbuf_cluster_cnt = [0]
1636        rcv_record_cnt = [0]
1637        rcv_cc = [0]
1638        rcv_buf = [0] * (Mbuf_Type.MT_LAST + 1)
1639        total_mbuf_bytes = 0
1640        CalcMbufInSB(so, snd_cc, snd_buf, rcv_cc, rcv_buf, snd_record_cnt, rcv_record_cnt, snd_mbuf_cnt, rcv_mbuf_cnt, snd_mbuf_cluster_cnt, rcv_mbuf_cluster_cnt)
1641        out_string += "total send mbuf count: " + str(int(snd_mbuf_cnt[0])) + " receive mbuf count: " + str(int(rcv_mbuf_cnt[0])) + "\n"
1642        out_string += "total send mbuf cluster count: " + str(int(snd_mbuf_cluster_cnt[0])) + " receive mbuf cluster count: " + str(int(rcv_mbuf_cluster_cnt[0])) + "\n"
1643        out_string += "total send record count: " + str(int(snd_record_cnt[0])) + " receive record count: " + str(int(rcv_record_cnt[0])) + "\n"
1644        out_string += "total snd_cc (total bytes in send buffers): " + str(int(snd_cc[0])) + " rcv_cc (total bytes in receive buffers): " + str(int(rcv_cc[0])) + "\n"
1645        out_string += "total snd_buf bytes " + str(int(snd_buf[Mbuf_Type.MT_LAST])) + " rcv_buf bytes " + str(int(rcv_buf[Mbuf_Type.MT_LAST])) + "\n"
1646        for x in range(Mbuf_Type.MT_LAST):
1647            if (snd_buf[x] != 0 or rcv_buf[x] != 0):
1648                out_string += "total snd_buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(snd_buf[x])) + " total recv_buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(rcv_buf[x])) + "\n"
1649                total_mbuf_bytes += snd_buf[x] + rcv_buf[x]
1650    print(out_string)
1651# EndMacro:  show_socket_sb_mbuf_usage
1652
1653
1654def GetMptcpInfo():
1655    mptcp = kern.globals.mtcbinfo
1656
1657    mppcb = cast(mptcp.mppi_pcbs.tqh_first, 'mppcb *')
1658    pcbseen = 0
1659    reinject_cnt=[0]
1660    reinject_byte_cnt=[0] * (Mbuf_Type.MT_LAST + 1)
1661    reinject_mbuf_cnt=[0]
1662    reinject_mbuf_cluster_cnt=[0]
1663
1664    snd_mbuf_cnt = [0]
1665    snd_mbuf_cluster_cnt = [0]
1666    snd_record_cnt = [0]
1667    snd_cc = [0]
1668    snd_buf = [0] * (Mbuf_Type.MT_LAST + 1)
1669    rcv_mbuf_cnt = [0]
1670    rcv_mbuf_cluster_cnt = [0]
1671    rcv_record_cnt = [0]
1672    rcv_cc = [0]
1673    rcv_buf = [0] * (Mbuf_Type.MT_LAST + 1)
1674    total_mbuf_bytes = 0
1675    while mppcb != 0:
1676        mpte = mppcb.mpp_pcbe
1677        pcbseen += 1
1678        CalcMbufInList(mpte.mpte_reinjectq, reinject_cnt, reinject_byte_cnt, reinject_mbuf_cnt, reinject_mbuf_cluster_cnt)
1679
1680        socket = mppcb.mpp_socket
1681        if socket != 0:
1682            CalcMbufInSB(socket, snd_cc, snd_buf, rcv_cc, rcv_buf, snd_record_cnt, rcv_record_cnt, snd_mbuf_cnt, rcv_mbuf_cnt, snd_mbuf_cluster_cnt, rcv_mbuf_cluster_cnt)
1683
1684        mppcb = cast(mppcb.mpp_entry.tqe_next, 'mppcb *')
1685
1686    out_string = ""
1687    out_string += "total pcbs seen: " + str(int(pcbseen)) + "\n"
1688    out_string += "total reinject mbuf count: " + str(int(reinject_mbuf_cnt[0])) + "\n"
1689    out_string += "total reinject mbuf cluster count: " + str(int(reinject_mbuf_cluster_cnt[0])) + "\n"
1690    out_string += "total reinject record count: " + str(int(reinject_cnt[0])) + "\n"
1691    for x in range(Mbuf_Type.MT_LAST):
1692        if (reinject_byte_cnt[x] != 0):
1693            out_string += "total reinject bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(reinject_byte_cnt[x])) + "\n"
1694            total_mbuf_bytes += reinject_byte_cnt[x]
1695
1696
1697    out_string += "total send mbuf count: " + str(int(snd_mbuf_cnt[0])) + " receive mbuf count: " + str(int(rcv_mbuf_cnt[0])) + "\n"
1698    out_string += "total send mbuf cluster count: " + str(int(snd_mbuf_cluster_cnt[0])) + " receive mbuf cluster count: " + str(int(rcv_mbuf_cluster_cnt[0])) + "\n"
1699    out_string += "total send record count: " + str(int(snd_record_cnt[0])) + " receive record count: " + str(int(rcv_record_cnt[0])) + "\n"
1700    out_string += "total snd_cc (total bytes in send buffers): " + str(int(snd_cc[0])) + " rcv_cc (total bytes in receive buffers): " + str(int(rcv_cc[0])) + "\n"
1701    out_string += "total snd_buf bytes " + str(int(snd_buf[Mbuf_Type.MT_LAST])) + " rcv_buf bytes " + str(int(rcv_buf[Mbuf_Type.MT_LAST])) + "\n"
1702    for x in range(Mbuf_Type.MT_LAST):
1703        if (snd_buf[x] != 0 or rcv_buf[x] != 0):
1704            out_string += "total snd_buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(snd_buf[x])) + " total recv_buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(rcv_buf[x])) + "\n"
1705            total_mbuf_bytes += snd_buf[x] + rcv_buf[x]
1706
1707    out_string += "total mbuf bytes used by MPTCP: "+ str(total_mbuf_bytes) + "\n"
1708    print(out_string)
1709
1710def GetPcbInfo(pcbi, proto):
1711    tcp_reassqlen = [0]
1712    tcp_reassq_bytes = 0
1713    mbuf_reassq_cnt = [0]
1714    mbuf_reassq_bytes = [0] * (Mbuf_Type.MT_LAST + 1)
1715    mbuf_reassq_cluster = [0]
1716    out_string = ""
1717    snd_mbuf_cnt = [0]
1718    snd_mbuf_cluster_cnt = [0]
1719    snd_record_cnt = [0]
1720    snd_cc = [0]
1721    snd_buf = [0] * (Mbuf_Type.MT_LAST + 1)
1722    rcv_mbuf_cnt = [0]
1723    rcv_mbuf_cluster_cnt = [0]
1724    rcv_record_cnt = [0]
1725    rcv_cc = [0]
1726    rcv_buf = [0] * (Mbuf_Type.MT_LAST + 1)
1727    pcbseen = 0
1728    out_string += "lastport " + str(int(pcbi.ipi_lastport)) + " lastlow " + str(int(pcbi.ipi_lastlow)) + " lasthi " + str(int(pcbi.ipi_lasthi)) + "\n"
1729    out_string += "active pcb count is " + str(int(pcbi.ipi_count)) + "\n"
1730    hashsize = pcbi.ipi_hashmask + 1
1731    out_string += "hash size is " + str(int(hashsize)) + "\n"
1732    out_string += str(pcbi.ipi_hashbase) + " has the following inpcb(s):\n"
1733    if (kern.ptrsize == 8):
1734        out_string += "pcb                proto  source                                        port  destination                                 port\n"
1735    else:
1736        out_string += "pcb            proto  source           address  port  destination         address  port\n\n"
1737
1738    if proto == IPPROTO_RAW:
1739        head = cast(pcbi.ipi_listhead, 'inpcbhead *')
1740        pcb = cast(head.lh_first, 'inpcb *')
1741        while pcb != 0:
1742            pcbseen += 1
1743            out_string += GetInPcb(pcb, proto) + "\n"
1744            so = pcb.inp_socket
1745            if so != 0:
1746                CalcMbufInSB(so, snd_cc, snd_buf, rcv_cc, rcv_buf, snd_record_cnt, rcv_record_cnt, snd_mbuf_cnt, rcv_mbuf_cnt, snd_mbuf_cluster_cnt, rcv_mbuf_cluster_cnt)
1747            pcb = cast(pcb.inp_list.le_next, 'inpcb *')
1748    else:
1749        i = 0
1750        hashbase = pcbi.ipi_hashbase
1751        while (i < hashsize):
1752            head = hashbase[i]
1753            pcb = cast(head.lh_first, 'inpcb *')
1754            while pcb != 0:
1755                pcbseen += 1
1756                out_string += GetInPcb(pcb, proto) + "\n"
1757                so = pcb.inp_socket
1758                if so != 0:
1759                    CalcMbufInSB(so, snd_cc, snd_buf, rcv_cc, rcv_buf, snd_record_cnt, rcv_record_cnt, snd_mbuf_cnt, rcv_mbuf_cnt, snd_mbuf_cluster_cnt, rcv_mbuf_cluster_cnt)
1760                if proto == IPPROTO_TCP and pcb.inp_ppcb:
1761                    tcpcb = cast(pcb.inp_ppcb, 'tcpcb *')
1762                    reass_entry = cast(tcpcb.t_segq.lh_first, 'tseg_qent *')
1763                    curr_reass = 0
1764                    while reass_entry != 0:
1765                        CalcMbufInList(reass_entry.tqe_m, tcp_reassqlen, mbuf_reassq_bytes, mbuf_reassq_cnt, mbuf_reassq_cluster)
1766                        tcp_reassq_bytes += reass_entry.tqe_len
1767                        curr_reass += reass_entry.tqe_len
1768
1769                        reass_entry = reass_entry.tqe_q.le_next
1770
1771                pcb = cast(pcb.inp_hash.le_next, 'inpcb *')
1772            i += 1
1773
1774    out_string += "total pcbs seen: " + str(int(pcbseen)) + "\n"
1775    out_string += "total send mbuf count: " + str(int(snd_mbuf_cnt[0])) + " receive mbuf count: " + str(int(rcv_mbuf_cnt[0])) + "\n"
1776    out_string += "total send mbuf cluster count: " + str(int(snd_mbuf_cluster_cnt[0])) + " receive mbuf cluster count: " + str(int(rcv_mbuf_cluster_cnt[0])) + "\n"
1777    out_string += "total send record count: " + str(int(snd_record_cnt[0])) + " receive record count: " + str(int(rcv_record_cnt[0])) + "\n"
1778    out_string += "total snd_cc (total bytes in send buffers): " + str(int(snd_cc[0])) + " rcv_cc (total bytes in receive buffers): " + str(int(rcv_cc[0])) + "\n"
1779    out_string += "total snd_buf bytes " + str(int(snd_buf[Mbuf_Type.MT_LAST])) + " rcv_buf bytes " + str(int(rcv_buf[Mbuf_Type.MT_LAST])) + "\n"
1780    for x in range(Mbuf_Type.MT_LAST):
1781        if (snd_buf[x] != 0 or rcv_buf[x] != 0):
1782            out_string += "total snd_buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(snd_buf[x])) + " total recv_buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(rcv_buf[x])) + "\n"
1783    out_string += "port hash base is " + hex(pcbi.ipi_porthashbase) + "\n"
1784    if proto == IPPROTO_TCP:
1785        out_string += "TCP reassembly queue length: " + str(tcp_reassqlen[0]) + " TCP-payload bytes: " + str(tcp_reassq_bytes) + "\n"
1786
1787        for x in range(Mbuf_Type.MT_LAST):
1788            if mbuf_reassq_bytes[x] != 0:
1789                out_string += "total reassq bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(mbuf_reassq_bytes[x]) + "\n"
1790
1791    i = 0
1792    hashbase = pcbi.ipi_porthashbase
1793    while (i < hashsize):
1794        head = hashbase[i]
1795        pcb = cast(head.lh_first, 'inpcbport *')
1796        while pcb != 0:
1797            out_string += "\t"
1798            out_string += GetInPcbPort(pcb)
1799            out_string += "\n"
1800            pcb = cast(pcb.phd_hash.le_next, 'inpcbport *')
1801        i += 1
1802
1803    return out_string
1804
1805def GetInPcbPort(ppcb):
1806    out_string = ""
1807    out_string += hex(ppcb) + ": lport "
1808    out_string += Getntohs(ppcb.phd_port)
1809    return out_string
1810
1811
1812def Getntohs(port):
1813    out_string = ""
1814    #p = unsigned(int(port) & 0x0000ffff)
1815    p = ((port & 0x0000ff00) >> 8)
1816    p |= ((port & 0x000000ff) << 8)
1817    return str(p)
1818
1819
1820# Macro: mbuf_list_usage_summary
1821@lldb_command('mbuf_list_usage_summary')
1822def ShowMbufListUsageSummary(cmd_args=None):
1823    """ Print mbuf list usage summary
1824    """
1825    out_string = ""
1826    pkt_cnt = [0]
1827    buf_byte_cnt = [0] * (Mbuf_Type.MT_LAST + 1)
1828    mbuf_cnt = [0]
1829    mbuf_cluster_cnt = [0]
1830
1831    mpkt = kern.GetValueFromAddress(cmd_args[0], 'struct mbuf *')
1832    CalcMbufInList(mpkt, pkt_cnt, buf_byte_cnt, mbuf_cnt, mbuf_cluster_cnt)
1833
1834    out_string += "Total packet count is " + str(int(pkt_cnt[0])) + "\n"
1835    for x in range(Mbuf_Type.MT_LAST):
1836        if (buf_byte_cnt[x] != 0):
1837            out_string += "Total buf bytes of type " + Mbuf_Type.reverse_mapping[x] + " : " + str(int(buf_byte_cnt[x])) + "\n"
1838    out_string += "Total mbuf count " + str(int(mbuf_cnt[0])) + "\n"
1839    out_string += "Total mbuf cluster count " + str(int(mbuf_cluster_cnt[0])) + "\n"
1840    print(out_string)
1841
1842# Macro: show_kern_event_pcbinfo
1843def GetKernEventPcbInfo(kev_pcb_head):
1844    out_string = ""
1845    pcb = Cast(kev_pcb_head.lh_first, 'kern_event_pcb *')
1846    if (kern.ptrsize == 8):
1847        kev_pcb_format_string = "0x{0:<16x} {1:12d} {2:16d} {3:16d} {4:16d} {5:16d}"
1848        out_string += "  evp socket         vendor code      class filter      subclass filter     so_rcv.sb_cc      so_rcv.sb_mbcnt\n"
1849        out_string += "--------------       -----------      ------------      ---------------     ------------      ---------------\n"
1850    else:
1851        kev_pcb_format_string = "0x{0:<8x} {1:12d} {2:16d} {3:16d} {4:16d} {5:16d}"
1852        out_string += "evp socket       vendor code      class filter      subclass filter     so_rcv.sb_cc      so_rcv.sb_mbcnt\n"
1853        out_string += "----------       -----------      ------------      ---------------     ------------      ---------------\n"
1854    while (pcb != 0):
1855        out_string += kev_pcb_format_string.format(pcb.evp_socket, pcb.evp_vendor_code_filter, pcb.evp_class_filter, pcb.evp_subclass_filter, pcb.evp_socket.so_rcv.sb_cc, pcb.evp_socket.so_rcv.sb_mbcnt)
1856        out_string += "\n"
1857        pcb = pcb.evp_link.le_next
1858    return out_string
1859
1860@lldb_command('show_kern_event_pcbinfo')
1861def ShowKernEventPcbInfo(cmd_args=None):
1862    """ Display the list of Kernel Event protocol control block information
1863    """
1864    print(GetKernEventPcbInfo(addressof(kern.globals.kern_event_head)))
1865# EndMacro:  show_kern_event_pcbinfo
1866
1867# Macro: show_kern_control_pcbinfo
1868def GetKernControlPcbInfo(ctl_head):
1869    out_string = ""
1870    kctl = Cast(ctl_head.tqh_first, 'kctl *')
1871    if (kern.ptrsize == 8):
1872        kcb_format_string = "0x{0:<16x} {1:10d} {2:10d} {3:10d}\n"
1873    else:
1874        kcb_format_string = "0x{0:<8x} {1:10d} {2:10d} {3:10d}\n"
1875    while unsigned(kctl) != 0:
1876        kctl_name = "controller: " + str(kctl.name) + "\n"
1877        out_string += kctl_name
1878        kcb = Cast(kctl.kcb_head.tqh_first, 'ctl_cb *')
1879        if unsigned(kcb) != 0:
1880            if (kern.ptrsize == 8):
1881                out_string += "socket               usecount     snd_cc     rcv_cc\n"
1882                out_string += "------               --------     ------     ------\n"
1883            else:
1884                out_string += "socket       usecount     snd_cc     rcv_cc\n"
1885                out_string += "------       --------     ------     ------\n"
1886        while unsigned(kcb) != 0:
1887            so = Cast(kcb.so, 'socket *')
1888            snd_cc = so.so_snd.sb_cc
1889            rcv_cc = so.so_rcv.sb_cc
1890            out_string += kcb_format_string.format(kcb.so, kcb.usecount, snd_cc, rcv_cc)
1891            kcb = kcb.next.tqe_next
1892        out_string += "\n"
1893        kctl = kctl.next.tqe_next
1894    return out_string
1895
1896@lldb_command('show_kern_control_pcbinfo')
1897def ShowKernControlPcbInfo(cmd_args=None):
1898    """ Display the list of Kernel Control protocol control block information
1899    """
1900    print(GetKernControlPcbInfo(addressof(kern.globals.ctl_head)))
1901# EndMacro:  show_kern_control_pcbinfo
1902
1903# Macro: show_unix_domain_pcbinfo
1904def GetUnixDomainPCBAsString(unp, type) :
1905    out_string = ""
1906    pcb = Cast(unp, 'unpcb *')
1907    out_string += "unpcb: " + hex(pcb)  + " " + str(type)
1908    out_string += " unp_socket: " + hex(pcb.unp_socket)
1909    out_string += " unp_vnode: " + hex(pcb.unp_vnode)
1910    out_string += " unp_conn: " + hex(pcb.unp_conn)
1911    out_string += " unp_addr: " + GetSocketAddrAsStringUnix(pcb.unp_addr)
1912    out_string += " unp_gencnt: " + str(int(pcb.unp_gencnt))
1913    out_string += " unp_flags: " + hex(pcb.unp_flags)
1914    if pcb.unp_socket != 0:
1915        so = Cast(pcb.unp_socket, 'socket *')
1916        out_string += " s=" + str(int(so.so_snd.sb_cc)) + " r=" + str(int(so.so_rcv.sb_cc)) + " usecnt=" + str(int(so.so_usecount))
1917    return out_string
1918
1919def GetUnixDomainPcbInfo(unp_head, type):
1920    out_string = ""
1921    unp = Cast(unp_head.lh_first, 'unpcb *')
1922    while unsigned(unp) != 0:
1923        out_string += GetUnixDomainPCBAsString(unp, type)
1924        out_string += "\n"
1925        unp = unp.unp_link.le_next
1926    return out_string
1927
1928@lldb_command('show_unix_domain_pcbinfo')
1929def ShowUnixDomainPcbInfo(cmd_args=None):
1930    """ Display the list of unix domain pcb
1931    """
1932    print(GetUnixDomainPcbInfo(addressof(kern.globals.unp_dhead), "dgram"))
1933    print(GetUnixDomainPcbInfo(addressof(kern.globals.unp_shead), "stream"))
1934# EndMacro:  show_kern_control_pcbinfo
1935
1936# Macro: show_tcp_pcbinfo
1937@lldb_command('show_tcp_pcbinfo')
1938def ShowTcpPcbInfo(cmd_args=None):
1939    """ Display the list of TCP protocol control block information
1940    """
1941    print(GetPcbInfo(addressof(kern.globals.tcbinfo), IPPROTO_TCP))
1942# EndMacro:  show_tcp_pcbinfo
1943
1944# Macro: show_udp_pcbinfo
1945@lldb_command('show_udp_pcbinfo')
1946def ShowUdpPcbInfo(cmd_args=None):
1947    """ Display the list of UDP protocol control block information
1948    """
1949    print(GetPcbInfo(addressof(kern.globals.udbinfo), IPPROTO_UDP))
1950# EndMacro:  show_udp_pcbinfo
1951
1952# Macro: show_rip_pcbinfo
1953@lldb_command('show_rip_pcbinfo')
1954def ShowRipPcbInfo(cmd_args=None):
1955    """ Display the list of Raw IP protocol control block information
1956    """
1957    print(GetPcbInfo(addressof(kern.globals.ripcbinfo), IPPROTO_RAW))
1958# EndMacro:  show_rip_pcbinfo
1959
1960# Macro: show_mptcp_pcbinfo
1961@lldb_command('show_mptcp_pcbinfo')
1962def ShowMptcpPcbInfo(cmd_args=None):
1963    """ Display the list of MPTCP protocol control block information
1964    """
1965    GetMptcpInfo()
1966# EndMacro:  show_mptcp_pcbinfo
1967
1968# Macro: show_domains
1969@lldb_command('show_domains')
1970def ShowDomains(cmd_args=None):
1971    """ Display the list of the domains
1972    """
1973    out_string = ""
1974    domains = kern.globals.domains
1975    dp = Cast(domains.tqh_first, 'domain *')
1976    ifma_trash_format_string = "{0:4d}: {1:x} {2:3d} {3:6d} {4:6d}"
1977    cnt = 0
1978    while (dp != 0):
1979        out_string += "\"" + str(dp.dom_name) + "\"" + "[" + str(int(dp.dom_refs)) + " refs] domain " + hex(dp) + "\n"
1980        out_string += "    family:\t" + str(int(dp.dom_family)) + "\n"
1981        out_string += "    flags:0x\t" + str(int(dp.dom_flags)) + "\n"
1982        out_string += "    rtparams:\toff=" + str(int(dp.dom_rtoffset)) + ", maxrtkey=" + str(int(dp.dom_maxrtkey)) + "\n"
1983
1984        if (dp.dom_init):
1985            out_string += "    init:\t"
1986            out_string += GetSourceInformationForAddress(dp.dom_init) + "\n"
1987        if (dp.dom_externalize):
1988            out_string += "    externalize:\t"
1989            out_string += GetSourceInformationForAddress(dp.dom_externalize) + "\n"
1990        if (dp.dom_dispose):
1991            out_string += "    dispose:\t"
1992            out_string += GetSourceInformationForAddress(dp.dom_dispose) + "\n"
1993        if (dp.dom_rtattach):
1994            out_string += "    rtattach:\t"
1995            out_string += GetSourceInformationForAddress(dp.dom_rtattach) + "\n"
1996        if (dp.dom_old):
1997            out_string += "    old:\t"
1998            out_string += GetSourceInformationForAddress(dp.dom_old) + "\n"
1999
2000        pr = Cast(dp.dom_protosw.tqh_first, 'protosw *')
2001        while pr != 0:
2002            pru = pr.pr_usrreqs
2003            out_string += "\ttype " + str(int(pr.pr_type)) + ", protocol " + str(int(pr.pr_protocol)) + ", protosw " + hex(pr) + "\n"
2004            out_string += "\t    flags:0x\t" + hex(pr.pr_flags) + "\n"
2005            if (pr.pr_input):
2006                out_string += "\t    input:\t"
2007                out_string += GetSourceInformationForAddress(pr.pr_input) + "\n"
2008            if (pr.pr_output):
2009                out_string += "\t    output:\t"
2010                out_string += GetSourceInformationForAddress(pr.pr_output) + "\n"
2011            if (pr.pr_ctlinput):
2012                out_string += "\t    ctlinput:\t"
2013                out_string += GetSourceInformationForAddress(pr.pr_ctlinput) + "\n"
2014            if (pr.pr_ctloutput):
2015                out_string += "\t    ctloutput:\t"
2016                out_string += GetSourceInformationForAddress(pr.pr_ctloutput) + "\n"
2017            if (pr.pr_init):
2018                out_string += "\t    init:\t"
2019                out_string += GetSourceInformationForAddress(pr.pr_init) + "\n"
2020            if (pr.pr_drain):
2021                out_string += "\t    drain:\t"
2022                out_string += GetSourceInformationForAddress(pr.pr_drain) + "\n"
2023            if (pr.pr_sysctl):
2024                out_string += "\t    sysctl:\t"
2025                out_string += GetSourceInformationForAddress(pr.pr_sysctl) + "\n"
2026            if (pr.pr_lock):
2027                out_string += "\t    lock:\t"
2028                out_string += GetSourceInformationForAddress(pr.pr_lock) + "\n"
2029            if (pr.pr_unlock):
2030                out_string += "\t    unlock:\t"
2031                out_string += GetSourceInformationForAddress(pr.pr_unlock) + "\n"
2032            if (pr.pr_getlock):
2033                out_string += "\t    getlock:\t"
2034                out_string += GetSourceInformationForAddress(pr.pr_getlock) + "\n"
2035            if (pr.pr_old):
2036                out_string += "\t    old:\t"
2037                out_string += GetSourceInformationForAddress(pr.pr_old) + "\n"
2038
2039            out_string += "\t    pru_flags:0x\t" + hex(pru.pru_flags) + "\n"
2040            out_string += "\t    abort:\t"
2041            out_string += GetSourceInformationForAddress(pru.pru_abort) + "\n"
2042            out_string += "\t    accept:\t"
2043            out_string += GetSourceInformationForAddress(pru.pru_accept) + "\n"
2044            out_string += "\t    attach:\t"
2045            out_string += GetSourceInformationForAddress(pru.pru_attach) + "\n"
2046            out_string += "\t    bind:\t"
2047            out_string += GetSourceInformationForAddress(pru.pru_bind) + "\n"
2048            out_string += "\t    connect:\t"
2049            out_string += GetSourceInformationForAddress(pru.pru_connect) + "\n"
2050            out_string += "\t    connect2:\t"
2051            out_string += GetSourceInformationForAddress(pru.pru_connect2) + "\n"
2052            out_string += "\t    connectx:\t"
2053            out_string += GetSourceInformationForAddress(pru.pru_connectx) + "\n"
2054            out_string += "\t    control:\t"
2055            out_string += GetSourceInformationForAddress(pru.pru_control) + "\n"
2056            out_string += "\t    detach:\t"
2057            out_string += GetSourceInformationForAddress(pru.pru_detach) + "\n"
2058            out_string += "\t    disconnect:\t"
2059            out_string += GetSourceInformationForAddress(pru.pru_disconnect) + "\n"
2060            out_string += "\t    listen:\t"
2061            out_string += GetSourceInformationForAddress(pru.pru_listen) + "\n"
2062            out_string += "\t    peeraddr:\t"
2063            out_string += GetSourceInformationForAddress(pru.pru_peeraddr) + "\n"
2064            out_string += "\t    rcvd:\t"
2065            out_string += GetSourceInformationForAddress(pru.pru_rcvd) + "\n"
2066            out_string += "\t    rcvoob:\t"
2067            out_string += GetSourceInformationForAddress(pru.pru_rcvoob) + "\n"
2068            out_string += "\t    send:\t"
2069            out_string += GetSourceInformationForAddress(pru.pru_send) + "\n"
2070            out_string += "\t    sense:\t"
2071            out_string += GetSourceInformationForAddress(pru.pru_sense) + "\n"
2072            out_string += "\t    shutdown:\t"
2073            out_string += GetSourceInformationForAddress(pru.pru_shutdown) + "\n"
2074            out_string += "\t    sockaddr:\t"
2075            out_string += GetSourceInformationForAddress(pru.pru_sockaddr) + "\n"
2076            out_string += "\t    sopoll:\t"
2077            out_string += GetSourceInformationForAddress(pru.pru_sopoll) + "\n"
2078            out_string += "\t    soreceive:\t"
2079            out_string += GetSourceInformationForAddress(pru.pru_soreceive) + "\n"
2080            out_string += "\t    sosend:\t"
2081            out_string += GetSourceInformationForAddress(pru.pru_sosend) + "\n"
2082            pr = pr.pr_entry.tqe_next
2083        dp = dp.dom_entry.tqe_next
2084
2085        print(out_string)
2086# EndMacro: show_domains
2087
2088# Macro: tcp_count_rxt_segments
2089@lldb_command('tcp_count_rxt_segments')
2090def TCPCountRxtSegments(cmd_args=None):
2091    """ Size of the t_rxt_segments chain
2092    """
2093    if not cmd_args:
2094        raise ArgumentError("Missing argument 0 in user function.")
2095
2096    tp = kern.GetValueFromAddress(cmd_args[0], 'tcpcb *')
2097    rxseg = cast(tp.t_rxt_segments.slh_first, 'tcp_rxt_seg *')
2098    cnt = 0
2099    while rxseg != 0:
2100        cnt += 1
2101        rxseg = rxseg.rx_link.sle_next
2102        if (cnt % 1000 == 0):
2103            print(" running count: {:d}".format(cnt))
2104    print(" total count: {:d}".format(cnt))
2105# EndMacro: tcp_count_rxt_segments
2106
2107# Macro: tcp_walk_rxt_segments
2108@lldb_command('tcp_walk_rxt_segments')
2109def TCPWalkRxtSegments(cmd_args=None):
2110    """ Walk the t_rxt_segments chain
2111    """
2112    if not cmd_args:
2113        raise ArgumentError("Missing argument 0 in user function.")
2114
2115    tp = kern.GetValueFromAddress(cmd_args[0], 'tcpcb *')
2116    rxseg = cast(tp.t_rxt_segments.slh_first, 'tcp_rxt_seg *')
2117    cnt = 0
2118    while rxseg != 0:
2119        cnt += 1
2120        rxseg = rxseg.rx_link.sle_next
2121        if (cnt % 1000 == 0):
2122            print(" running count: {:d}".format(cnt))
2123    print(" total count: {:d}".format(cnt))
2124    rxseg = cast(tp.t_rxt_segments.slh_first, 'tcp_rxt_seg *')
2125    cnt = 0
2126    while rxseg != 0:
2127        cnt += 1
2128        out_string = ""
2129        span = rxseg.rx_end - rxseg.rx_start
2130        rxseg_format = "{0:4d} 0x{1:x} rx_start 0x{2:x} rx_end 0x{3:x} rx_count {4:4d} rx_flags 0x{5:x} span {6:d}"
2131        out_string += rxseg_format.format(cnt, rxseg, rxseg.rx_start, rxseg.rx_end, rxseg.rx_count, rxseg.rx_flags, abs(span))
2132        print(out_string)
2133        rxseg = rxseg.rx_link.sle_next
2134# EndMacro: tcp_walk_rxt_segments
2135