xref: /dragonfly/test/debug/wildcardinfo.c (revision 030b3383)
1 /*
2  * WILDCARDINFO.C
3  *
4  * cc -I/usr/src/sys wildcardinfo.c -o /usr/local/bin/wildcardinfo -lkvm
5  *
6  * wildcardinfo
7  *
8  * Dump the tcbinfo[] array and wildcard hash table for each cpu.
9  *
10  * Copyright (c) 2004 The DragonFly Project.  All rights reserved.
11  *
12  * This code is derived from software contributed to The DragonFly Project
13  * by Matthew Dillon <dillon@backplane.com>
14  *
15  * Redistribution and use in source and binary forms, with or without
16  * modification, are permitted provided that the following conditions
17  * are met:
18  *
19  * 1. Redistributions of source code must retain the above copyright
20  *    notice, this list of conditions and the following disclaimer.
21  * 2. Redistributions in binary form must reproduce the above copyright
22  *    notice, this list of conditions and the following disclaimer in
23  *    the documentation and/or other materials provided with the
24  *    distribution.
25  * 3. Neither the name of The DragonFly Project nor the names of its
26  *    contributors may be used to endorse or promote products derived
27  *    from this software without specific, prior written permission.
28  *
29  * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
30  * ``AS IS'' AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
31  * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
32  * FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN NO EVENT SHALL THE
33  * COPYRIGHT HOLDERS OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
34  * INCIDENTAL, SPECIAL, EXEMPLARY OR CONSEQUENTIAL DAMAGES (INCLUDING,
35  * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
36  * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
37  * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
38  * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
39  * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
40  * SUCH DAMAGE.
41  *
42  * $DragonFly: src/test/debug/wildcardinfo.c,v 1.1 2005/04/05 02:49:15 dillon Exp $
43  */
44 
45 #define _KERNEL_STRUCTURES_
46 #include <sys/param.h>
47 #include <sys/user.h>
48 #include <sys/malloc.h>
49 #include <sys/signalvar.h>
50 #include <sys/socket.h>
51 #include <sys/socketvar.h>
52 #include <net/route.h>
53 #include <net/if.h>
54 #include <net/if_var.h>
55 #include <net/netisr.h>
56 #include <netinet/in_systm.h>
57 #include <netinet/in.h>
58 #include <netinet/ip.h>
59 #include <netinet/in_pcb.h>
60 #include <netinet/in_var.h>
61 #include <arpa/inet.h>
62 
63 #include <stdio.h>
64 #include <stdlib.h>
65 #include <string.h>
66 #include <fcntl.h>
67 #include <kvm.h>
68 #include <nlist.h>
69 #include <getopt.h>
70 
71 struct nlist Nl[] = {
72     { "_ncpus" },
73     { "_tcbinfo" },
74     { NULL }
75 };
76 
77 static void dumptcb(kvm_t *kd, intptr_t tcbinfo);
78 static void dumpinpcontainerhead(kvm_t *kd, int index, void *kptr);
79 static void kkread(kvm_t *kd, u_long addr, void *buf, size_t nbytes);
80 
81 int
82 main(int ac, char **av)
83 {
84     kvm_t *kd;
85     int i;
86     int ch;
87     int ncpus;
88     const char *corefile = NULL;
89     const char *sysfile = NULL;
90 
91     while ((ch = getopt(ac, av, "M:N:")) != -1) {
92 	switch(ch) {
93 	case 'M':
94 	    corefile = optarg;
95 	    break;
96 	case 'N':
97 	    sysfile = optarg;
98 	    break;
99 	default:
100 	    fprintf(stderr, "%s [-M core] [-N system]\n", av[0]);
101 	    exit(1);
102 	}
103     }
104 
105     if ((kd = kvm_open(sysfile, corefile, NULL, O_RDONLY, "kvm:")) == NULL) {
106 	perror("kvm_open");
107 	exit(1);
108     }
109     if (kvm_nlist(kd, Nl) != 0) {
110 	perror("kvm_nlist");
111 	exit(1);
112     }
113     kkread(kd, Nl[0].n_value, &ncpus, sizeof(ncpus));
114     for (i = 0; i < ncpus; ++i) {
115 	printf("CPU %d\n", i);
116 	dumptcb(kd, (intptr_t)Nl[1].n_value + i * sizeof(struct inpcbinfo));
117     }
118     return(0);
119 }
120 
121 static
122 void
123 dumptcb(kvm_t *kd, intptr_t tcbaddr)
124 {
125     struct inpcbinfo info;
126     struct inpcbportinfo pinfo;
127     int i;
128 
129     kkread(kd, tcbaddr, &info, sizeof(info));
130     kkread(kd, (intptr_t)info.portinfo, &pinfo, sizeof(pinfo));
131     printf("    hashbase %p\n", info.hashbase);
132     printf("    hashmask %ld\n", info.hashmask);
133     printf("    porthashbase %p\n", pinfo.porthashbase);
134     printf("    porthashmask %lu\n", pinfo.porthashmask);
135     printf("    wildcardhashbase %p\n", info.wildcardhashbase);
136     printf("    wildcardhashmask %lu\n", info.wildcardhashmask);
137     printf("    lastport %d\n", (int)pinfo.lastport);
138     printf("    lastlow %d\n", (int)pinfo.lastlow);
139     printf("    lasthi %d\n", (int)pinfo.lasthi);
140     printf("    ipi_size %zu\n", info.ipi_size);
141     printf("    ipi_count %d\n", (int)info.ipi_count);
142     printf("    ipi_gencnt %lld\n", (long long)info.ipi_gencnt);
143     printf("    cpu %d\n", info.cpu);
144     for (i = 0; i <= info.wildcardhashmask; ++i)
145 	dumpinpcontainerhead(kd, i, info.wildcardhashbase + i);
146 }
147 
148 static
149 void
150 dumpinpcontainerhead(kvm_t *kd, int index, void *kptr)
151 {
152     struct inpcontainerhead head;
153     struct inpcontainer node;
154     struct inpcb pcb;
155 
156     kkread(kd, (intptr_t)kptr, &head, sizeof(head));
157     if (head.lh_first == NULL)
158 	return;
159     printf("\tinpcontainer list at index %d {\n", index);
160     for (kptr = head.lh_first; kptr; kptr = node.ic_list.le_next)  {
161 	kkread(kd, (intptr_t)kptr, &node, sizeof(node));
162 	printf("\t    inpcontainer %p inpcb %p", kptr, node.ic_inp);
163 	if (node.ic_inp) {
164 		printf(" {\n");
165 		kkread(kd, (intptr_t)node.ic_inp, &pcb, sizeof(pcb));
166 		printf("\t\tlocal %s:%d foreign %s:%d\n",
167 			inet_ntoa(pcb.inp_inc.inc_laddr),
168 			ntohs(pcb.inp_inc.inc_lport),
169 			inet_ntoa(pcb.inp_inc.inc_faddr),
170 			ntohs(pcb.inp_inc.inc_fport));
171 		printf("\t    }");
172 	}
173 	printf("\n");
174     }
175     printf("\t}\n");
176 }
177 
178 static void
179 kkread(kvm_t *kd, u_long addr, void *buf, size_t nbytes)
180 {
181     if (kvm_read(kd, addr, buf, nbytes) != nbytes) {
182         perror("kvm_read");
183         exit(1);
184     }
185 }
186 
187