1 /* 2 * Copyright (c) 1994, 1995, 1996 3 * The Regents of the University of California. All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that: (1) source code distributions 7 * retain the above copyright notice and this paragraph in its entirety, (2) 8 * distributions including binary code include the above copyright notice and 9 * this paragraph in its entirety in the documentation or other materials 10 * provided with the distribution, and (3) all advertising materials mentioning 11 * features or use of this software display the following acknowledgement: 12 * ``This product includes software developed by the University of California, 13 * Lawrence Berkeley Laboratory and its contributors.'' Neither the name of 14 * the University nor the names of its contributors may be used to endorse 15 * or promote products derived from this software without specific prior 16 * written permission. 17 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED 18 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF 19 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE. 20 * 21 * Format and print Novell IPX packets. 22 * Contributed by Brad Parker (brad@fcr.com). 23 */ 24 25 #ifndef lint 26 static const char rcsid[] = 27 "@(#) $Header: print-ipx.c,v 1.19 96/12/10 23:23:52 leres Exp $"; 28 #endif 29 30 #include <sys/param.h> 31 #include <sys/time.h> 32 #include <sys/socket.h> 33 34 #include <netinet/in.h> 35 #include <netinet/in_systm.h> 36 #include <netinet/ip.h> 37 #include <netinet/ip_var.h> 38 #include <netinet/udp.h> 39 #include <netinet/udp_var.h> 40 #include <netinet/tcp.h> 41 #include <netinet/tcpip.h> 42 43 #ifdef __STDC__ 44 #include <stdlib.h> 45 #endif 46 #include <stdio.h> 47 #include <string.h> 48 49 #include "interface.h" 50 #include "addrtoname.h" 51 #include "ipx.h" 52 #include "extract.h" 53 54 55 static const char *ipxaddr_string(u_int32_t, const u_char *); 56 void ipx_decode(const struct ipxHdr *, const u_char *, u_int); 57 void ipx_sap_print(const u_short *, u_int); 58 void ipx_rip_print(const u_short *, u_int); 59 60 /* 61 * Print IPX datagram packets. 62 */ 63 void 64 ipx_print(const u_char *p, u_int length) 65 { 66 const struct ipxHdr *ipx = (const struct ipxHdr *)p; 67 68 TCHECK(ipx->srcSkt); 69 (void)printf("%s.%x > ", 70 ipxaddr_string(EXTRACT_32BITS(ipx->srcNet), ipx->srcNode), 71 EXTRACT_16BITS(&ipx->srcSkt)); 72 73 (void)printf("%s.%x:", 74 ipxaddr_string(EXTRACT_32BITS(ipx->dstNet), ipx->dstNode), 75 EXTRACT_16BITS(&ipx->dstSkt)); 76 77 /* take length from ipx header */ 78 TCHECK(ipx->length); 79 length = EXTRACT_16BITS(&ipx->length); 80 81 ipx_decode(ipx, (u_char *)ipx + ipxSize, length - ipxSize); 82 return; 83 trunc: 84 printf("[|ipx %d]", length); 85 } 86 87 static const char * 88 ipxaddr_string(u_int32_t net, const u_char *node) 89 { 90 static char line[256]; 91 92 sprintf(line, "%x.%02x:%02x:%02x:%02x:%02x:%02x", 93 net, node[0], node[1], node[2], node[3], node[4], node[5]); 94 95 return line; 96 } 97 98 void 99 ipx_decode(const struct ipxHdr *ipx, const u_char *datap, u_int length) 100 { 101 register u_short dstSkt; 102 103 dstSkt = EXTRACT_16BITS(&ipx->dstSkt); 104 switch (dstSkt) { 105 case IPX_SKT_NCP: 106 (void)printf(" ipx-ncp %d", length); 107 break; 108 case IPX_SKT_SAP: 109 ipx_sap_print((u_short *)datap, length); 110 break; 111 case IPX_SKT_RIP: 112 ipx_rip_print((u_short *)datap, length); 113 break; 114 case IPX_SKT_NETBIOS: 115 (void)printf(" ipx-netbios %d", length); 116 break; 117 case IPX_SKT_DIAGNOSTICS: 118 (void)printf(" ipx-diags %d", length); 119 break; 120 default: 121 (void)printf(" ipx-#%x %d", dstSkt, length); 122 break; 123 } 124 } 125 126 void 127 ipx_sap_print(const u_short *ipx, u_int length) 128 { 129 int command, i; 130 131 TCHECK(ipx[0]); 132 command = EXTRACT_16BITS(ipx); 133 ipx++; 134 length -= 2; 135 136 switch (command) { 137 case 1: 138 case 3: 139 if (command == 1) 140 (void)printf("ipx-sap-req"); 141 else 142 (void)printf("ipx-sap-nearest-req"); 143 144 if (length > 0) { 145 TCHECK(ipx[1]); 146 (void)printf(" %x '", EXTRACT_16BITS(&ipx[0])); 147 fn_print((u_char *)&ipx[1], (u_char *)&ipx[1] + 48); 148 putchar('\''); 149 } 150 break; 151 152 case 2: 153 case 4: 154 if (command == 2) 155 (void)printf("ipx-sap-resp"); 156 else 157 (void)printf("ipx-sap-nearest-resp"); 158 159 for (i = 0; i < 8 && length > 0; i++) { 160 TCHECK2(ipx[27], 1); 161 (void)printf(" %x '", EXTRACT_16BITS(&ipx[0])); 162 fn_print((u_char *)&ipx[1], (u_char *)&ipx[1] + 48); 163 printf("' addr %s", 164 ipxaddr_string(EXTRACT_32BITS(&ipx[25]), (u_char *)&ipx[27])); 165 ipx += 32; 166 length -= 64; 167 } 168 break; 169 default: 170 (void)printf("ipx-sap-?%x", command); 171 break; 172 } 173 return; 174 trunc: 175 printf("[|ipx %d]", length); 176 } 177 178 void 179 ipx_rip_print(const u_short *ipx, u_int length) 180 { 181 int command, i; 182 183 TCHECK(ipx[0]); 184 command = EXTRACT_16BITS(ipx); 185 ipx++; 186 length -= 2; 187 188 switch (command) { 189 case 1: 190 (void)printf("ipx-rip-req"); 191 if (length > 0) { 192 TCHECK(ipx[3]); 193 (void)printf(" %x/%d.%d", EXTRACT_32BITS(&ipx[0]), 194 EXTRACT_16BITS(&ipx[2]), EXTRACT_16BITS(&ipx[3])); 195 } 196 break; 197 case 2: 198 (void)printf("ipx-rip-resp"); 199 for (i = 0; i < 50 && length > 0; i++) { 200 TCHECK(ipx[3]); 201 (void)printf(" %x/%d.%d", EXTRACT_32BITS(&ipx[0]), 202 EXTRACT_16BITS(&ipx[2]), EXTRACT_16BITS(&ipx[3])); 203 204 ipx += 4; 205 length -= 8; 206 } 207 break; 208 default: 209 (void)printf("ipx-rip-?%x", command); 210 } 211 return; 212 trunc: 213 printf("[|ipx %d]", length); 214 } 215 216