Hacktoberfest 2026: le issue che i maintainer hanno segnato per ottobre, aperte e adatte ai principianti. Sfoglia le issue Hacktoberfest

slcan doesn't receive corresponding response after sending can message.

Aperta
#2,060 3 commenti 0 reazioni 0 assegnatari Vedi su GitHub

Nessuno ha ancora preso questa issue.

Valutazione

Difficoltà
4/5
Tempo stimato
3-5 giorni
Idoneità per principianti
48/100
Tipo di issue
Bug
Chiarezza
Abbastanza chiara
Stato di attività
Tranquilla
Stack tecnologico
python
Ambito
networking

Direzione di ricerca

Inizia con can.interfaces.slcan.slcanBus.send e recv, quindi esamina le chiamate a _write e _read utilizzate dall’implementazione segnalata. Riproduci la configurazione con due dispositivi, con i cavi CAN collegati e scollegati, verificando le risposte alla trasmissione e il comportamento della ricezione concorrente. L’attività è completata quando gli invii riusciti riportano ACKs, gli invii non riusciti riportano BEL/NACK e le operazioni di invio/ricezione non entrano in competizione né si bloccano in modo errato.

Scritto dal modello di indicizzazione a partire dal testo della issue.

Descrizione

bug
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)

The following implementation solves that problem (introduces other ones)
import can
from can.interfaces.slcan import slcanBus
import threading


class SLCANBusWithErrorCheck(slcanBus):
    def __init__(self, *args, **kwargs):
        super().__init__(*args, **kwargs)
        self._tx_lock = threading.Lock()

    def send(self, msg, timeout=None):
        if timeout != self.serialPortOrig.write_timeout:
            self.serialPortOrig.write_timeout = timeout

        if msg.is_remote_frame:
            if msg.is_extended_id:
                sendStr = f"R{msg.arbitration_id:08X}{msg.dlc:d}"
            else:
                sendStr = f"r{msg.arbitration_id:03X}{msg.dlc:d}"
        else:
            if msg.is_extended_id:
                sendStr = f"T{msg.arbitration_id:08X}{msg.dlc:d}"
            else:
                sendStr = f"t{msg.arbitration_id:03X}{msg.dlc:d}"
            sendStr += msg.data.hex().upper()

        with self._tx_lock:
            # Drain any leftover bytes from a previous error before sending
            self.serialPortOrig.reset_input_buffer()
            self._buffer.clear()

            self._write(sendStr)
            response = self._read(timeout=max(timeout or 0, 2.0))

        if response is None:
            raise can.CanError("TX timeout - no response from adapter")
        if self._ERROR.decode() in response:
            raise can.CanError("TX failed - BEL received (no ACK on bus)")

    def recv(self, timeout=None):
        if self._tx_lock.locked():
            return None
        return super().recv(timeout=timeout)

I know following are the errors in the provided solution:

  • If we are mid receive, then any call to send can create race condition (clear the serial buffers mid receive)
  • the timeout logic is also incorrect (additional 2.0 second for timeout < 2.0 second, patch for some other problem)
  • Receive fails immediately if transmission is going on

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.

Lingua principale
Python
Stelle
1.6k
Fork
697
Metriche di merge delle PR
Nessuna PR unita negli ultimi 30g

Guida per i contributori

Apri la guida per i contributori

Come iniziare

  1. Leggi tutta la issue e poi la guida ai contributi del progetto.
  2. Commenta sulla issue per dire che te ne occupi tu — evita che due persone facciano lo stesso lavoro.
  3. Fai un fork del repository e lavora su un branch.
  4. Apri una pull request che faccia riferimento al numero della issue.

Altre issue di hardbyte/python-can

Tutte le issue di hardbyte/python-can

Issue simili

Altre issue su Python

Ricevi le nuove issue nella tua casella

Un breve riepilogo di issue GitHub adatte ai principianti.