Repository navigation
slcan doesn't receive corresponding response after sending can message. #2060
Description
Activity
Hello,
I think there's a small misunderstanding here about how SLCAN ACK/NACK is supposed to work.
The protocol originated with LAWICEL's CAN232/CANUSB, and on those devices the ACK response to a send command does not mean "the frame was transmitted on the bus". It just means "your command parsed and was queued into the Tx buffer". The minimal implementation literally only checks command syntax. As far as I can tell, CANUSB works this way, and every custom SLCAN firmware I've come across follows the same convention — I've never seen one where ACK/NACK implies bus-level transmission.
Regards.
Based upon the implementation of CANUSB (socketcan specifically), I have used, they will report failure to transmit after the Tx buffer is full, eventually making it known to the higher level that there is some problem with the CAN bus. There is the same kind of queue/buffers in almost all implementations, i.e. we won't know when exactly the bus failed and will only report after the queue/buffer is full.
In the case of SLCAN, if the response is totally rejected, then all frames will be reported as success even if hundreds of transmissions fail, and the higher level will never know if the underlying CAN bus has some errors. There probably will be workarounds for this (rejecting serial messages until we can fully transmit through the bus), but if there is already a functionality that achieves the same, shouldn't we use that?
Based on the LAWICEL's documentation, there is a provision for ACK/NACK after transmission. Will there be problems if we expect a response after each transmission (won't the existing implementation support this)?
I am not arguing about the meaning of ACK/NACK; that will be dependent upon the CAN device itself, but totally ignoring the response will neither inform about full buffers/queues nor about the failed bus-level transmission.
Hello,
I agree that host-side failure detection would be helpful.
That said, in the LAWICEL protocol, device state — including bus errors and Tx buffer-full — is reported through the
Fcommand, which the host is expected to poll. So for a LAWICEL-compliant device, the correct model is ACK/NACK checking plusFpolling — they cover different failure modes. But neither is implemented inpython-can.What
python-canshould actually do here is a harder question. The LAWICEL protocol is one thing; the SLCAN ecosystem in the wild is another. Outside of LAWICEL's own devices, fully spec-compliant implementations are rare — many firmwares leave ACK/NACK and/orFunimplemented or stub them with fake replies. So strict spec enforcement at the library layer would help spec-compliant devices but not the bulk of devices in the field.Regards.
Describe the bug
While calling slcanBus.send, the corresponding response isn't read. This makes it report false success even on failed messages.
To Reproduce
Setup two can devices, both configured to send ack on successful can message receive. Disconnect the can wires after some time.
Expected behavior
Expected to receive ack when wire is connected (slcan should report successful transmission)
Expected to receive nack(bel) when wire is disconnected (slcan should report failed transmission)
Additional context
OS and version: Ubuntu 24.04.3 LTS
Python version: Python 3.11.14
python-can version: 4.6.1
python-can interface/s: slcan with custom slcan device (esp32s3)
Details
The following implementation solves that problem (introduces other ones)I know following are the errors in the provided solution:
Any solution i came up for these problems seemed patchy as best. So, expecting it to solve inside of python-can itself or provide a better solution than locking.