/*
 * Copyright 2009 Bert Vermeulen <bert@biot.com>
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that: (1) source code distributions
 * retain the above copyright notice and this paragraph in its entirety, (2)
 * distributions including binary code include the above copyright notice and
 * this paragraph in its entirety in the documentation or other materials
 * provided with the distribution, and (3) all advertising materials mentioning
 * features or use of this software display the following acknowledgement:
 * ``This product includes software developed by Paolo Abeni.''
 * The name of author may not be used to endorse or promote products derived
 * from this software without specific prior written permission.
 * THIS SOFTWARE IS PROVIDED ``AS IS'' AND WITHOUT ANY EXPRESS OR IMPLIED
 * WARRANTIES, INCLUDING, WITHOUT LIMITATION, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
 *
 * Support for USB packets
 *
 */

#define NETDISSECT_REWORKED
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include <tcpdump-stdinc.h>

#include "interface.h"


#if defined(HAVE_PCAP_USB_H) && defined(DLT_USB_LINUX)
#include <pcap/usb.h>

static const char tstr[] = "[|usb]";

/* returns direction: 1=inbound 2=outbound -1=invalid */
static int
get_direction(int transfer_type, int event_type)
{
	int direction;

	direction = -1;
	switch(transfer_type){
	case URB_BULK:
	case URB_CONTROL:
	case URB_ISOCHRONOUS:
		switch(event_type)
		{
		case URB_SUBMIT:
			direction = 2;
			break;
		case URB_COMPLETE:
		case URB_ERROR:
			direction = 1;
			break;
		default:
			direction = -1;
		}
		break;
	case URB_INTERRUPT:
		switch(event_type)
		{
		case URB_SUBMIT:
			direction = 1;
			break;
		case URB_COMPLETE:
		case URB_ERROR:
			direction = 2;
			break;
		default:
			direction = -1;
		}
		break;
	 default:
		direction = -1;
	}

	return direction;
}

static void
usb_header_print(netdissect_options *ndo, const pcap_usb_header *uh)
{
	int direction;

	switch(uh->transfer_type)
	{
		case URB_ISOCHRONOUS:
			ND_PRINT((ndo, "ISOCHRONOUS"));
			break;
		case URB_INTERRUPT:
			ND_PRINT((ndo, "INTERRUPT"));
			break;
		case URB_CONTROL:
			ND_PRINT((ndo, "CONTROL"));
			break;
		case URB_BULK:
			ND_PRINT((ndo, "BULK"));
			break;
		default:
			ND_PRINT((ndo, " ?"));
	}

	switch(uh->event_type)
	{
		case URB_SUBMIT:
			ND_PRINT((ndo, " SUBMIT"));
			break;
		case URB_COMPLETE:
			ND_PRINT((ndo, " COMPLETE"));
			break;
		case URB_ERROR:
			ND_PRINT((ndo, " ERROR"));
			break;
		default:
			ND_PRINT((ndo, " ?"));
	}

	direction = get_direction(uh->transfer_type, uh->event_type);
	if(direction == 1)
		ND_PRINT((ndo, " from"));
	else if(direction == 2)
		ND_PRINT((ndo, " to"));
	ND_PRINT((ndo, " %d:%d:%d", uh->bus_id, uh->device_address, uh->endpoint_number & 0x7f));
}

/*
 * This is the top level routine of the printer for captures with a
 * 48-byte header.
 *
 * 'p' points to the header of the packet, 'h->ts' is the timestamp,
 * 'h->len' is the length of the packet off the wire, and 'h->caplen'
 * is the number of bytes actually captured.
 */
u_int
usb_linux_48_byte_print(netdissect_options *ndo, const struct pcap_pkthdr *h,
                        register const u_char *p)
{
	if (h->caplen < sizeof(pcap_usb_header)) {
		ND_PRINT((ndo, "%s", tstr));
		return(sizeof(pcap_usb_header));
	}

	usb_header_print(ndo, (const pcap_usb_header *) p);

	return(sizeof(pcap_usb_header));
}

#ifdef DLT_USB_LINUX_MMAPPED
/*
 * This is the top level routine of the printer for captures with a
 * 64-byte header.
 *
 * 'p' points to the header of the packet, 'h->ts' is the timestamp,
 * 'h->len' is the length of the packet off the wire, and 'h->caplen'
 * is the number of bytes actually captured.
 */
u_int
usb_linux_64_byte_print(netdissect_options *ndo, const struct pcap_pkthdr *h,
                        register const u_char *p)
{
	if (h->caplen < sizeof(pcap_usb_header_mmapped)) {
		ND_PRINT((ndo, "%s", tstr));
		return(sizeof(pcap_usb_header_mmapped));
	}

	usb_header_print(ndo, (const pcap_usb_header *) p);

	return(sizeof(pcap_usb_header_mmapped));
}
#endif /* DLT_USB_LINUX_MMAPPED */

#endif /* defined(HAVE_PCAP_USB_H) && defined(DLT_USB_LINUX) */

