If the socket sndbuf is full, we fail to send a packet. This should
actually happen less often for UDP than it does for TCP because of the
lack of back pressure from the peer, but it's still a fairly normal
condition and needs to be handled properly.
The correct handling is basically to do nothing and wait for the jam to
clear, unless it's been *so* long that DPD has caused us to think the
peer is dead, or we need a rekey (which we do be reconnecting the
transport channel). The ka_stalled_action() function exists specifically
to handle this case, and returns one of KA_NONE, KA_DPD_DEAD or KA_REKEY.
There's no ponit in it returning KA_DPD or KA_KEEPALIVE like the normal
keepalive_action() does because the point here is that we *can't* send
anything at the moment anyway.
The problem here is that the PPP mainloop doesn't handle those three
cases correctly, and KA_REKEY and KA_NONE were just falling through to
end up at the fatal error condition for a *short* write, which should
never happen. I went too far when commenting out the cut and pasted
mainloop to create ppp_mainloop.
Fix KA_REKEY to do a reconnect, and KA_NONE to just return work_done
as it should.
Fixes: a47406b43 ("add support for PPP-based protocols")
Signed-off-by: David Woodhouse <dwmw2@infradead.org>
case KA_DPD_DEAD:
goto peer_dead;
case KA_REKEY:
-// goto do_rekey;
+ goto do_reconnect;
case KA_NONE:
-// return work_done;
+ return work_done;
default:
- /* This should never happen */
+ /* This can never happen because ka_stalled_action()
+ * always returns one of the above. */
;
}
}