If retry timeout is equal for all systems and/or sockets, it will collide at some point. In this case, one sender will always have a chance to send some thing and make the CAN queue full, the other one will always get -ENOBUS response. Even if we would implement a scheduler for local system, we can't solve same problem for multiple identical systems on same bus. Since the protocol has no other way to avoid this kind of collisions, we can use random number for retry timer and reduce probability of colliding retries. Signed-off-by: Oleksij Rempel <o.rempel@xxxxxxxxxxxxxx> --- net/can/j1939/transport.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/net/can/j1939/transport.c b/net/can/j1939/transport.c index e47eff502b6f..0d2b1998d111 100644 --- a/net/can/j1939/transport.c +++ b/net/can/j1939/transport.c @@ -116,7 +116,6 @@ enum j1939_xtp_abort { }; static unsigned int j1939_tp_block = 255; -static unsigned int j1939_tp_retry_ms = 20; static unsigned int j1939_tp_packet_delay; static unsigned int j1939_tp_padding = 1; @@ -854,7 +853,8 @@ static enum hrtimer_restart j1939_tp_txtimer(struct hrtimer *hrtimer) ret = j1939_tp_txnext(session); if (ret < 0) - j1939_tp_schedule_txtimer(session, j1939_tp_retry_ms ?: 20); + j1939_tp_schedule_txtimer(session, 10 + prandom_u32_max(16)); + j1939_session_put(session); return HRTIMER_NORESTART; -- 2.20.1