print-null.c revision 98527
1/* 2 * Copyright (c) 1991, 1993, 1994, 1995, 1996, 1997 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 * $FreeBSD: head/contrib/tcpdump/print-null.c 98527 2002-06-21 00:49:02Z fenner $ 22 */ 23 24#ifndef lint 25static const char rcsid[] = 26 "@(#) $Header: /tcpdump/master/tcpdump/print-null.c,v 1.41 2001/07/05 18:54:15 guy Exp $ (LBL)"; 27#endif 28 29#ifdef HAVE_CONFIG_H 30#include "config.h" 31#endif 32 33#include <sys/param.h> 34#include <sys/time.h> 35#include <sys/socket.h> 36#include <sys/file.h> 37#include <sys/ioctl.h> 38 39struct mbuf; 40struct rtentry; 41 42#include <netinet/in.h> 43 44#include <pcap.h> 45#include <stdio.h> 46#include <string.h> 47 48#include "interface.h" 49#include "addrtoname.h" 50 51#include "ip.h" 52#ifdef INET6 53#include "ip6.h" 54#endif 55 56#ifndef AF_NS 57#define AF_NS 6 /* XEROX NS protocols */ 58#endif 59 60/* 61 * The DLT_NULL packet header is 4 bytes long. It contains a host-byte-order 62 * 32-bit integer that specifies the family, e.g. AF_INET. 63 * 64 * Note here that "host" refers to the host on which the packets were 65 * captured; that isn't necessarily *this* host. 66 * 67 * The OpenBSD DLT_LOOP packet header is the same, except that the integer 68 * is in network byte order. 69 */ 70#define NULL_HDRLEN 4 71 72static void 73null_print(u_int family, u_int length) 74{ 75 if (nflag) 76 printf("AF %u ", family); 77 else { 78 switch (family) { 79 80 case AF_INET: 81 printf("ip "); 82 break; 83 84#ifdef INET6 85 case AF_INET6: 86 printf("ip6 "); 87 break; 88#endif 89 90 case AF_NS: 91 printf("ns "); 92 break; 93 94 default: 95 printf("AF %u ", family); 96 break; 97 } 98 } 99 printf("%d: ", length); 100} 101 102/* 103 * Byte-swap a 32-bit number. 104 * ("htonl()" or "ntohl()" won't work - we want to byte-swap even on 105 * big-endian platforms.) 106 */ 107#define SWAPLONG(y) \ 108((((y)&0xff)<<24) | (((y)&0xff00)<<8) | (((y)&0xff0000)>>8) | (((y)>>24)&0xff)) 109 110void 111null_if_print(u_char *user, const struct pcap_pkthdr *h, const u_char *p) 112{ 113 u_int length = h->len; 114 u_int caplen = h->caplen; 115 const struct ip *ip; 116 u_int family; 117 118 ++infodelay; 119 ts_print(&h->ts); 120 121 memcpy((char *)&family, (char *)p, sizeof(family)); 122 123 /* 124 * This isn't necessarily in our host byte order; if this is 125 * a DLT_LOOP capture, it's in network byte order, and if 126 * this is a DLT_NULL capture from a machine with the opposite 127 * byte-order, it's in the opposite byte order from ours. 128 * 129 * If the upper 16 bits aren't all zero, assume it's byte-swapped. 130 */ 131 if ((family & 0xFFFF0000) != 0) 132 family = SWAPLONG(family); 133 134 /* 135 * Some printers want to get back at the link level addresses, 136 * and/or check that they're not walking off the end of the packet. 137 * Rather than pass them all the way down, we set these globals. 138 */ 139 packetp = p; 140 snapend = p + caplen; 141 142 length -= NULL_HDRLEN; 143 144 ip = (struct ip *)(p + NULL_HDRLEN); 145 146 if (eflag) 147 null_print(family, length); 148 149 switch (IP_V(ip)) { 150 case 4: 151 ip_print((const u_char *)ip, length); 152 break; 153#ifdef INET6 154 case 6: 155 ip6_print((const u_char *)ip, length); 156 break; 157#endif /* INET6 */ 158 default: 159 printf("ip v%d", IP_V(ip)); 160 break; 161 } 162 163 if (xflag) 164 default_print((const u_char *)ip, caplen - NULL_HDRLEN); 165 putchar('\n'); 166 --infodelay; 167 if (infoprint) 168 info(0); 169} 170 171