Merge PR #3214: companion USB connection and flow control
Preserve the newer terminal and mOTA passthrough paths while adding real USB client detection and whole-frame transmit pacing.
This commit is contained in:
commit
a92215fd07
3 files changed
+75
-4
No files matched your search
@@ -66,7 +66,8 @@ void ArduinoSerialInterface::disable() {
|
||||
resetReceiveState();
|
||||
}
|
||||
|
||||
bool ArduinoSerialInterface::isConnected() const {
|
||||
bool ArduinoSerialInterface::isConnected() const {
|
||||
if (_conn_check) return _conn_check();
|
||||
return true; // no way of knowing, so assume yes
|
||||
}
|
||||
|
||||
@@ -75,6 +76,12 @@ bool ArduinoSerialInterface::isReadBusy() const {
|
||||
}
|
||||
|
||||
bool ArduinoSerialInterface::isWriteBusy() const {
|
||||
if (_passthroughMode) return false;
|
||||
if (_flow_ctl && isConnected()) {
|
||||
return const_cast<Stream*>(_serial)->availableForWrite() < (int)(MAX_FRAME_SIZE + 3);
|
||||
}
|
||||
// while nobody drains the port the TX buffer stays full, so never report
|
||||
// busy in that case: it would stall the paced streams on all interfaces
|
||||
return false;
|
||||
}
|
||||
|
||||
@@ -84,6 +91,17 @@ size_t ArduinoSerialInterface::writeFrame(const uint8_t src[], size_t len) {
|
||||
return 0;
|
||||
}
|
||||
if (_passthroughMode) return len;
|
||||
if (_flow_ctl) {
|
||||
if (!isConnected()) {
|
||||
return len; // nobody is listening, drop instead of filling the TX buffer
|
||||
}
|
||||
if (_serial->availableForWrite() < (int)(len + 3)) {
|
||||
// a short write would tear the length prefixed framing, and as there is
|
||||
// neither a checksum nor a resync marker the receiver would stay out of
|
||||
// sync forever - so drop the whole frame instead
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t hdr[3];
|
||||
hdr[0] = '>';
|
||||
@@ -133,6 +151,7 @@ size_t ArduinoSerialInterface::checkRecvFrame(uint8_t dest[]) {
|
||||
if (_frame_len > MAX_FRAME_SIZE) _frame_len = MAX_FRAME_SIZE; // truncate
|
||||
memcpy(dest, rx_buf, _frame_len);
|
||||
_state = RECV_STATE_IDLE; // reset state, for next frame
|
||||
_last_frame_ms = millis(); // a real client is talking to us
|
||||
return _frame_len;
|
||||
}
|
||||
}
|
||||
|
||||
Reference in new issue
Block a user