scapy.contrib.automotive.doip

class scapy.contrib.automotive.doip.DoIP(_pkt, /, *, protocol_version=2, inverse_version=253, payload_type=0, payload_length=None, nack=0, vin=b'', logical_address=0, eid=b'', gid=b'', further_action=0, vin_gid_status=0, source_address=0, activation_type=0, logical_address_tester=0, logical_address_doip_entity=0, routing_activation_response=0, reserved_iso=0, reserved_oem=b'', diagnostic_power_mode=0, node_type=0, max_open_sockets=1, cur_open_sockets=0, max_data_size=0, target_address=0, ack_code=0, nack_code=0, previous_msg=b'')[source]

Bases: Packet

Implementation of the DoIP (ISO 13400) protocol. DoIP packets can be sent via UDP and TCP. Depending on the payload type, the correct connection need to be chosen:

Payload Type

Payload Type Name

Connection Kind

0x0000

Generic DoIP header negative acknowledge

UDP / TCP

0x0001

Vehicle Identification request message

UDP

0x0002

Vehicle identification request message with EID

UDP

0x0003

Vehicle identification request message with VIN

UDP

0x0004

Vehicle announcement message/vehicle identification response

UDP

0x0005

Routing activation request

TCP

0x0006

Routing activation response

TCP

0x0007

Alive Check request

TCP

0x0008

Alive Check response

TCP

0x4001

IP entity status request

UDP

0x4002

DoIP entity status response

UDP

0x4003

Diagnostic power mode information request

UDP

0x4004

Diagnostic power mode information response

UDP

0x8001

Diagnostic message

TCP

0x8002

Diagnostic message positive acknowledgement

TCP

0x8003

Diagnostic message negative acknowledgement

TCP

Example with UDP:
>>> socket = L3RawSocket(iface="eth0")
>>> resp = socket.sr1(IP(dst="169.254.117.238")/UDP(dport=13400)/DoIP(payload_type=1))
Example with TCP:
>>> socket = DoIPSocket("169.254.117.238")
>>> pkt = DoIP(payload_type=0x8001, source_address=0xe80, target_address=0x1000) / UDS() / UDS_RDBI(identifiers=[0x1000])
>>> resp = socket.sr1(pkt, timeout=1)
Example with UDS:
>>> socket = UDS_DoIPSocket("169.254.117.238")
>>> pkt = UDS() / UDS_RDBI(identifiers=[0x1000])
>>> resp = socket.sr1(pkt, timeout=1)
aliastypes = [<class 'scapy.contrib.automotive.doip.DoIP'>, <class 'scapy.packet.Packet'>]
answers(other: Packet) int[source]

DEV: true if self is an answer from other

extract_padding(s: bytes) Tuple[bytes, bytes | None][source]
fields_desc: ClassVar[List[Field[Any, Any] | _FieldContainer]] = [<XByteEnumField (DoIP).protocol_version>, <XByteEnumField (DoIP).inverse_version>, <XShortEnumField (DoIP).payload_type>, <IntField (DoIP).payload_length>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>, <scapy.fields.ConditionalField object>]
hashret() bytes[source]
payload_guess: List[Tuple[Dict[str, Any], Type[Packet]]] = [({'payload_type': 32769}, <class 'scapy.contrib.automotive.uds.UDS'>)]
payload_types = {0: 'Generic DoIP header NACK', 1: 'Vehicle identification request', 2: 'Vehicle identification request with EID', 3: 'Vehicle identification request with VIN', 4: 'Vehicle announcement message/vehicle identification response message', 5: 'Routing activation request', 6: 'Routing activation response', 7: 'Alive check request', 8: 'Alive check response', 16385: 'DoIP entity status request', 16386: 'DoIP entity status response', 16387: 'Diagnostic power mode information request', 16388: 'Diagnostic power mode information response', 32769: 'Diagnostic message', 32770: 'Diagnostic message ACK', 32771: 'Diagnostic message NACK'}
post_build(pkt: bytes, pay: bytes) bytes[source]

This will set the Field ‘payload_length’ to the correct value.

classmethod tcp_reassemble(data: bytes, metadata: Dict[str, Any], session: Dict[str, Any]) Packet | None[source]
class scapy.contrib.automotive.doip.DoIPSSLStreamSocket(sock: socket, basecls: Type[Packet] | None = None)[source]

Bases: StreamSocketPeekless

Custom SSLStreamSocket for DoIP communication.

recv(x: int | None = 65535, **kwargs: Any) Packet | None[source]
class scapy.contrib.automotive.doip.DoIPSocket(ip: str = '127.0.0.1', port: int = 13400, tls_port: int = 3496, activate_routing: bool = True, source_address: int = 3712, target_address: int = 0, activation_type: int = 0, reserved_oem: bytes = b'', force_tls: bool = False, context: SSLContext | None = None, doip_version: int = 2, enforce_doip_version: bool = False)[source]

Bases: DoIPSSLStreamSocket

Socket for DoIP communication. This sockets automatically sends a routing activation request as soon as a TCP or TLS connection is established.

Parameters:
  • ip – IP address of destination

  • port – destination port, usually 13400

  • tls_port – destination port for TLS connection, usually 3496

  • activate_routing – If true, routing activation request is automatically sent

  • source_address – DoIP source address

  • target_address – DoIP target address, this is automatically determined if routing activation request is sent

  • activation_type – This allows to set a different activation type for the routing activation request

  • reserved_oem – Optional parameter to set value for reserved_oem field of routing activation request

  • force_tls – Skip establishing of a TCP connection and directly try to connect via SSL/TLS

  • context – Optional ssl.SSLContext object for initialization of ssl socket connections.

  • doip_version – DoIP protocol version to use, default is 2 (ISO 13400-2012)

  • enforce_doip_version – If true, the protocol_version field in each DoIP packet to be sent, is always set to the value of doip_version.

Example

>>> socket = DoIPSocket("169.254.0.131")
>>> pkt = DoIP(payload_type=0x8001, source_address=0xe80, target_address=0x1000) / UDS() / UDS_RDBI(identifiers=[0x1000])
>>> resp = socket.sr1(pkt, timeout=1)
send(x: Packet) int[source]
class scapy.contrib.automotive.doip.UDS_DoIPSocket(ip: str = '127.0.0.1', port: int = 13400, tls_port: int = 3496, activate_routing: bool = True, source_address: int = 3712, target_address: int = 0, activation_type: int = 0, reserved_oem: bytes = b'', force_tls: bool = False, context: SSLContext | None = None, doip_version: int = 2, enforce_doip_version: bool = False)[source]

Bases: DoIPSocket

Application-Layer socket for DoIP endpoints. This socket takes care about the encapsulation of UDS packets into DoIP packets.

Example

>>> socket = UDS_DoIPSocket("169.254.117.238")
>>> pkt = UDS() / UDS_RDBI(identifiers=[0x1000])
>>> resp = socket.sr1(pkt, timeout=1)
recv(x: int | None = 65535, **kwargs: Any) Packet | None[source]
send(x: Packet | bytes) int[source]