aboutsummaryrefslogtreecommitdiff
path: root/pcap-linux.c
diff options
context:
space:
mode:
authorGuy Harris <guy@alum.mit.edu>2016-08-18 11:44:32 -0700
committerGuy Harris <guy@alum.mit.edu>2016-08-18 11:44:32 -0700
commit6aa0f48883bf69a5c8fb09532ec47edfb9750ee7 (patch)
tree6361ca880787655f10b8c64d3df93dd7b800aafb /pcap-linux.c
parent18bf0f9560fcf0fdc331c8109990bf46d63941de (diff)
Have separate DLTs for big-endian and host-endian SocketCAN headers.
At least with some versions of the Linux kernel, you can capture on SocketCAN interfaces with a PF_PACKET socket and get packets with SocketCAN headers; that code doesn't special-case ARPHRD_CAN, so it leaves the CAN ID field in host byte order. In addition, the "capture CAN packets on a USB device" code wasn't putting that field into host byte order, either. So have separate DLT_/LINKTYPE_ types, one for packets with the CAN ID in big-endian byte order and one for packets with the CAN ID in host byte order. When reading LINKTYPE_CAN_SOCKETCAN_HOSTENDIAN files, swap the CAN ID field as necessary to put it into the byte order for the host reading the file rather than the byte order for the host that wrote the file.
Diffstat (limited to 'pcap-linux.c')
-rw-r--r--pcap-linux.c19
1 files changed, 18 insertions, 1 deletions
diff --git a/pcap-linux.c b/pcap-linux.c
index 4df339c2..a2ace7b7 100644
--- a/pcap-linux.c
+++ b/pcap-linux.c
@@ -2943,7 +2943,24 @@ static void map_arphrd_to_dlt(pcap_t *handle, int sock_fd, int arptype,
#define ARPHRD_CAN 280
#endif
case ARPHRD_CAN:
- handle->linktype = DLT_CAN_SOCKETCAN;
+ /*
+ * DLT_CAN_SOCKETCAN_BIGENDIAN is defined to have the
+ * can_id field of the pseudo-header in big-endian
+ * (network) byte order.
+ *
+ * The packets delivered to sockets have that field
+ * in host byte order.
+ *
+ * The code that implements it in packet-can-linux.c
+ * passes that field to htonl() to put it into network
+ * byte order.
+ *
+ * The code that reads from a PF_PACKET socket doesn't
+ * change the byte order of that field, so we define
+ * a new DLT_CAN_SOCKETCAN_HOSTENDIAN, where the can_id
+ * is in host byte order.
+ */
+ handle->linktype = DLT_CAN_SOCKETCAN_HOSTENDIAN;
break;
#ifndef ARPHRD_IEEE802_TR