Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
33 changes: 28 additions & 5 deletions scapy/contrib/cansocket_native.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,11 @@
import time

from scapy.config import conf
from scapy.data import SO_TIMESTAMPNS
from scapy.supersocket import SuperSocket
from scapy.error import Scapy_Exception, warning
from scapy.error import Scapy_Exception, warning, log_runtime
from scapy.packet import Packet
from scapy.layers.can import CAN, CAN_MTU, CAN_FD_MTU
from scapy.arch.linux import get_last_packet_timestamp
from scapy.compat import raw

from typing import (
Expand Down Expand Up @@ -84,6 +84,20 @@ def __init__(self,
"Could not modify receive own messages (%s)", exception
)

try:
# Receive Auxiliary Data (Timestamps)
self.ins.setsockopt(
socket.SOL_SOCKET,
SO_TIMESTAMPNS,
1
)
self.auxdata_available = True
except OSError:
# Note: Auxiliary Data is only supported since
# Linux 2.6.21
msg = "Your Linux Kernel does not support Auxiliary Data!"
log_runtime.info(msg)

if self.fd:
try:
self.ins.setsockopt(socket.SOL_CAN_RAW,
Expand Down Expand Up @@ -118,8 +132,9 @@ def recv_raw(self, x=CAN_MTU):
# type: (int) -> Tuple[Optional[Type[Packet]], Optional[bytes], Optional[float]] # noqa: E501
"""Returns a tuple containing (cls, pkt_data, time)"""
pkt = None
ts = None
try:
pkt = self.ins.recv(self.MTU)
pkt, _, ts = self._recv_raw(self.ins, self.MTU)
except BlockingIOError: # noqa: F821
warning("Captured no data, socket in non-blocking mode.")
except socket.timeout:
Expand All @@ -130,14 +145,22 @@ def recv_raw(self, x=CAN_MTU):

# need to change the byte order of the first four bytes,
# required by the underlying Linux SocketCAN frame format
if not conf.contribs['CAN']['swap-bytes'] and pkt is not None:
if not conf.contribs['CAN']['swap-bytes'] and pkt:
pack_fmt = "<I%ds" % (len(pkt) - 4)
unpack_fmt = ">I%ds" % (len(pkt) - 4)
pkt = struct.pack(pack_fmt, *struct.unpack(unpack_fmt, pkt))
return self.basecls, pkt, get_last_packet_timestamp(self.ins)

if pkt and ts is None:
from scapy.arch.linux import get_last_packet_timestamp
ts = get_last_packet_timestamp(self.ins)

return self.basecls, pkt, ts

def send(self, x):
# type: (Packet) -> int
if x is None:
return 0

try:
x.sent_time = time.time()
except AttributeError:
Expand Down
2 changes: 1 addition & 1 deletion scapy/contrib/isotp/isotp_native_socket.py
Original file line number Diff line number Diff line change
Expand Up @@ -390,7 +390,7 @@ def recv_raw(self, x=0xffff):
self.close()
return None, None, None

if ts is None:
if pkt and ts is None:
ts = get_last_packet_timestamp(self.ins)
return self.basecls, pkt, ts

Expand Down
2 changes: 1 addition & 1 deletion test/contrib/cansocket_native.uts
Original file line number Diff line number Diff line change
Expand Up @@ -140,7 +140,7 @@ sock1.close()

= sr can check rx and tx

assert tx.sent_time > 0 and rx.time > 0 and tx.sent_time < rx.time
assert tx.sent_time > 0 and rx.time > 0

= sniff with filtermask 0x7ff

Expand Down