Home | History | Annotate | Download | only in tcpdump
      1 /*
      2  * Oracle
      3  */
      4 #ifdef HAVE_CONFIG_H
      5 #include "config.h"
      6 #endif
      7 
      8 #include <tcpdump-stdinc.h>
      9 
     10 #include <stdio.h>
     11 #include <pcap.h>
     12 
     13 #include "netdissect.h"
     14 #include "interface.h"
     15 #include "extract.h"
     16 #include "ppi.h"
     17 
     18 #ifdef DLT_PPI
     19 
     20 static inline void
     21 ppi_header_print(struct netdissect_options *ndo, const u_char *bp, u_int length)
     22 {
     23 	const ppi_header_t *hdr;
     24 	u_int32_t dlt;
     25 	u_int16_t len;
     26 
     27 	hdr = (const ppi_header_t *)bp;
     28 
     29 	len = EXTRACT_16BITS(&hdr->ppi_len);
     30 	dlt = EXTRACT_32BITS(&hdr->ppi_dlt);
     31 
     32 	if (!ndo->ndo_qflag) {
     33 		ND_PRINT((ndo,", V.%d DLT %s (%d) len %d", hdr->ppi_ver,
     34 			  pcap_datalink_val_to_name(dlt), dlt,
     35                           len));
     36         } else {
     37 		ND_PRINT((ndo,", %s", pcap_datalink_val_to_name(dlt)));
     38         }
     39 
     40 	ND_PRINT((ndo, ", length %u: ", length));
     41 }
     42 
     43 static void
     44 ppi_print(struct netdissect_options *ndo,
     45                const struct pcap_pkthdr *h, const u_char *p)
     46 {
     47 	if_ndo_printer ndo_printer;
     48         if_printer printer;
     49 	ppi_header_t *hdr;
     50 	u_int caplen = h->caplen;
     51 	u_int length = h->len;
     52 	u_int32_t dlt;
     53 
     54 	if (caplen < sizeof(ppi_header_t)) {
     55 		ND_PRINT((ndo, "[|ppi]"));
     56 		return;
     57 	}
     58 	hdr = (ppi_header_t *)p;
     59 	dlt = EXTRACT_32BITS(&hdr->ppi_dlt);
     60 
     61 	if (ndo->ndo_eflag)
     62 		ppi_header_print(ndo, p, length);
     63 
     64 	length -= sizeof(ppi_header_t);
     65 	caplen -= sizeof(ppi_header_t);
     66 	p += sizeof(ppi_header_t);
     67 
     68 	if ((printer = lookup_printer(dlt)) != NULL) {
     69 		printer(h, p);
     70 	} else if ((ndo_printer = lookup_ndo_printer(dlt)) != NULL) {
     71 		ndo_printer(ndo, h, p);
     72 	} else {
     73 		if (!ndo->ndo_eflag)
     74 			ppi_header_print(ndo, (u_char *)hdr,
     75 					length + sizeof(ppi_header_t));
     76 
     77 		if (!ndo->ndo_suppress_default_print)
     78 			ndo->ndo_default_print(ndo, p, caplen);
     79 	}
     80 }
     81 
     82 /*
     83  * This is the top level routine of the printer.  'p' points
     84  * to the ether header of the packet, 'h->ts' is the timestamp,
     85  * 'h->len' is the length of the packet off the wire, and 'h->caplen'
     86  * is the number of bytes actually captured.
     87  */
     88 u_int
     89 ppi_if_print(struct netdissect_options *ndo,
     90                const struct pcap_pkthdr *h, const u_char *p)
     91 {
     92 	ppi_print(ndo, h, p);
     93 
     94 	return (sizeof(ppi_header_t));
     95 }
     96 
     97 /*
     98  * Local Variables:
     99  * c-style: whitesmith
    100  * c-basic-offset: 8
    101  * End:
    102  */
    103 
    104 #endif /* DLT_PPI */
    105