]> git.saurik.com Git - apple/network_cmds.git/blob - tcpdump.tproj/print-isoclns.c
cea4a7e3f4ff80165d1896ea47c95db175d4f246
[apple/network_cmds.git] / tcpdump.tproj / print-isoclns.c
1 /*
2 * Copyright (c) 1999 Apple Computer, Inc. All rights reserved.
3 *
4 * @APPLE_LICENSE_HEADER_START@
5 *
6 * "Portions Copyright (c) 1999 Apple Computer, Inc. All Rights
7 * Reserved. This file contains Original Code and/or Modifications of
8 * Original Code as defined in and that are subject to the Apple Public
9 * Source License Version 1.0 (the 'License'). You may not use this file
10 * except in compliance with the License. Please obtain a copy of the
11 * License at http://www.apple.com/publicsource and read it before using
12 * this file.
13 *
14 * The Original Code and all software distributed under the License are
15 * distributed on an 'AS IS' basis, WITHOUT WARRANTY OF ANY KIND, EITHER
16 * EXPRESS OR IMPLIED, AND APPLE HEREBY DISCLAIMS ALL SUCH WARRANTIES,
17 * INCLUDING WITHOUT LIMITATION, ANY WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT. Please see the
19 * License for the specific language governing rights and limitations
20 * under the License."
21 *
22 * @APPLE_LICENSE_HEADER_END@
23 */
24 /*
25 * Copyright (c) 1992, 1993, 1994, 1995, 1996
26 * The Regents of the University of California. All rights reserved.
27 *
28 * Redistribution and use in source and binary forms, with or without
29 * modification, are permitted provided that: (1) source code distributions
30 * retain the above copyright notice and this paragraph in its entirety, (2)
31 * distributions including binary code include the above copyright notice and
32 * this paragraph in its entirety in the documentation or other materials
33 * provided with the distribution, and (3) all advertising materials mentioning
34 * features or use of this software display the following acknowledgement:
35 * ``This product includes software developed by the University of California,
36 * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of
37 * the University nor the names of its contributors may be used to endorse
38 * or promote products derived from this software without specific prior
39 * written permission.
40 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
41 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
42 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
43 *
44 * Original code by Matt Thomas, Digital Equipment Corporation
45 */
46
47 #ifndef lint
48 static const char rcsid[] =
49 "@(#) $Header: /cvs/Darwin/Commands/NeXT/network_cmds/tcpdump.tproj/print-isoclns.c,v 1.1.1.1 1999/05/02 03:58:34 wsanchez Exp $ (LBL)";
50 #endif
51
52 #include <sys/types.h>
53 #include <sys/time.h>
54 #include <sys/socket.h>
55
56 #if __STDC__
57 struct mbuf;
58 struct rtentry;
59 #endif
60 #include <net/if.h>
61
62 #include <netinet/in.h>
63 #include <netinet/if_ether.h>
64
65 #include <stdio.h>
66
67 #include "interface.h"
68 #include "addrtoname.h"
69 #include "ethertype.h"
70
71 #define CLNS 129
72 #define ESIS 130
73 #define ISIS 131
74 #define NULLNS 0
75
76 static int osi_cksum(const u_char *, u_int, const u_char *, u_char *, u_char *);
77 static void esis_print(const u_char *, u_int);
78
79 void
80 isoclns_print(const u_char *p, u_int length, u_int caplen,
81 const u_char *esrc, const u_char *edst)
82 {
83 if (caplen < 1) {
84 printf("[|iso-clns] ");
85 if (!eflag)
86 printf("%s > %s",
87 etheraddr_string(esrc),
88 etheraddr_string(edst));
89 return;
90 }
91
92 switch (*p) {
93
94 case CLNS:
95 /* esis_print(&p, &length); */
96 printf("iso-clns");
97 if (!eflag)
98 (void)printf(" %s > %s",
99 etheraddr_string(esrc),
100 etheraddr_string(edst));
101 break;
102
103 case ESIS:
104 printf("iso-esis");
105 if (!eflag)
106 (void)printf(" %s > %s",
107 etheraddr_string(esrc),
108 etheraddr_string(edst));
109 esis_print(p, length);
110 return;
111
112 case ISIS:
113 printf("iso-isis");
114 if (!eflag)
115 (void)printf(" %s > %s",
116 etheraddr_string(esrc),
117 etheraddr_string(edst));
118 /* isis_print(&p, &length); */
119 (void)printf(" len=%d ", length);
120 if (caplen > 1)
121 default_print_unaligned(p, caplen);
122 break;
123
124 case NULLNS:
125 printf("iso-nullns");
126 if (!eflag)
127 (void)printf(" %s > %s",
128 etheraddr_string(esrc),
129 etheraddr_string(edst));
130 break;
131
132 default:
133 printf("iso-clns %02x", p[0]);
134 if (!eflag)
135 (void)printf(" %s > %s",
136 etheraddr_string(esrc),
137 etheraddr_string(edst));
138 (void)printf(" len=%d ", length);
139 if (caplen > 1)
140 default_print_unaligned(p, caplen);
141 break;
142 }
143 }
144
145 #define ESIS_REDIRECT 6
146 #define ESIS_ESH 2
147 #define ESIS_ISH 4
148
149 struct esis_hdr {
150 u_char version;
151 u_char reserved;
152 u_char type;
153 u_char tmo[2];
154 u_char cksum[2];
155 };
156
157 static void
158 esis_print(const u_char *p, u_int length)
159 {
160 const u_char *ep;
161 int li = p[1];
162 const struct esis_hdr *eh = (const struct esis_hdr *) &p[2];
163 u_char cksum[2];
164 u_char off[2];
165
166 if (length == 2) {
167 if (qflag)
168 printf(" bad pkt!");
169 else
170 printf(" no header at all!");
171 return;
172 }
173 ep = p + li;
174 if (li > length) {
175 if (qflag)
176 printf(" bad pkt!");
177 else
178 printf(" LI(%d) > PDU size (%d)!", li, length);
179 return;
180 }
181 if (li < sizeof(struct esis_hdr) + 2) {
182 if (qflag)
183 printf(" bad pkt!");
184 else {
185 printf(" too short for esis header %d:", li);
186 while (--length >= 0)
187 printf("%02X", *p++);
188 }
189 return;
190 }
191 switch (eh->type & 0x1f) {
192
193 case ESIS_REDIRECT:
194 printf(" redirect");
195 break;
196
197 case ESIS_ESH:
198 printf(" esh");
199 break;
200
201 case ESIS_ISH:
202 printf(" ish");
203 break;
204
205 default:
206 printf(" type %d", eh->type & 0x1f);
207 break;
208 }
209 off[0] = eh->cksum[0];
210 off[1] = eh->cksum[1];
211 if (vflag && osi_cksum(p, li, eh->cksum, cksum, off)) {
212 printf(" bad cksum (got %02x%02x want %02x%02x)",
213 eh->cksum[1], eh->cksum[0], cksum[1], cksum[0]);
214 return;
215 }
216 if (eh->version != 1) {
217 printf(" unsupported version %d", eh->version);
218 return;
219 }
220 p += sizeof(*eh) + 2;
221 li -= sizeof(*eh) + 2; /* protoid * li */
222
223 switch (eh->type & 0x1f) {
224 case ESIS_REDIRECT: {
225 const u_char *dst, *snpa, *is;
226
227 dst = p; p += *p + 1;
228 if (p > snapend)
229 return;
230 printf(" %s", isonsap_string(dst));
231 snpa = p; p += *p + 1;
232 is = p; p += *p + 1;
233 if (p > snapend)
234 return;
235 if (p > ep) {
236 printf(" [bad li]");
237 return;
238 }
239 if (is[0] == 0)
240 printf(" > %s", etheraddr_string(&snpa[1]));
241 else
242 printf(" > %s", isonsap_string(is));
243 li = ep - p;
244 break;
245 }
246 #if 0
247 case ESIS_ESH:
248 printf(" esh");
249 break;
250 #endif
251 case ESIS_ISH: {
252 const u_char *is;
253
254 is = p; p += *p + 1;
255 if (p > ep) {
256 printf(" [bad li]");
257 return;
258 }
259 if (p > snapend)
260 return;
261 printf(" %s", isonsap_string(is));
262 li = ep - p;
263 break;
264 }
265
266 default:
267 (void)printf(" len=%d", length);
268 if (length && p < snapend) {
269 length = snapend - p;
270 default_print(p, length);
271 }
272 return;
273 }
274 if (vflag)
275 while (p < ep && li) {
276 int op, opli;
277 const u_char *q;
278
279 if (snapend - p < 2)
280 return;
281 if (li < 2) {
282 printf(" bad opts/li");
283 return;
284 }
285 op = *p++;
286 opli = *p++;
287 li -= 2;
288 if (opli > li) {
289 printf(" opt (%d) too long", op);
290 return;
291 }
292 li -= opli;
293 q = p;
294 p += opli;
295 if (snapend < p)
296 return;
297 if (op == 198 && opli == 2) {
298 printf(" tmo=%d", q[0] * 256 + q[1]);
299 continue;
300 }
301 printf (" %d:<", op);
302 while (--opli >= 0)
303 printf("%02x", *q++);
304 printf (">");
305 }
306 }
307
308 static int
309 osi_cksum(register const u_char *p, register u_int len,
310 const u_char *toff, u_char *cksum, u_char *off)
311 {
312 int x, y, f = (len - ((toff - p) + 1));
313 int32_t c0 = 0, c1 = 0;
314
315 if ((cksum[0] = off[0]) == 0 && (cksum[1] = off[1]) == 0)
316 return 0;
317
318 off[0] = off[1] = 0;
319 while (--len >= 0) {
320 c0 += *p++;
321 c1 += c0;
322 c0 %= 255;
323 c1 %= 255;
324 }
325 x = (c0 * f - c1);
326 if (x < 0)
327 x = 255 - (-x % 255);
328 else
329 x %= 255;
330 y = -1 * (x + c0);
331 if (y < 0)
332 y = 255 - (-y % 255);
333 else
334 y %= 255;
335
336 off[0] = x;
337 off[1] = y;
338
339 return (off[0] != cksum[0] || off[1] != cksum[1]);
340 }