From b92d21bd3198b60e241d9fc43815d30ca6fd203b Mon Sep 17 00:00:00 2001 From: Jacob Dahl <37091262+dakejahl@users.noreply.github.com> Date: Fri, 12 Dec 2025 09:31:33 -0900 Subject: [PATCH] serial: add txSpaceAvailable function (#26069) * serial: add txSpaceAvailable function * serial: txSpaceAvailable and bytesAvailable fixups --- platforms/common/Serial.cpp | 5 ++++ .../include/px4_platform_common/Serial.hpp | 1 + platforms/nuttx/src/px4/common/SerialImpl.cpp | 26 ++++++++++++++++++- .../src/px4/common/include/SerialImpl.hpp | 1 + platforms/posix/include/SerialImpl.hpp | 1 + platforms/posix/src/px4/common/SerialImpl.cpp | 21 ++++++++++++++- platforms/qurt/include/SerialImpl.hpp | 1 + platforms/qurt/src/px4/SerialImpl.cpp | 21 ++++++++++++++- 8 files changed, 74 insertions(+), 3 deletions(-) diff --git a/platforms/common/Serial.cpp b/platforms/common/Serial.cpp index 748dcba9b2..a129fe2492 100644 --- a/platforms/common/Serial.cpp +++ b/platforms/common/Serial.cpp @@ -74,6 +74,11 @@ ssize_t Serial::bytesAvailable() return _impl.bytesAvailable(); } +ssize_t Serial::txSpaceAvailable() +{ + return _impl.txSpaceAvailable(); +} + ssize_t Serial::read(uint8_t *buffer, size_t buffer_size) { return _impl.read(buffer, buffer_size); diff --git a/platforms/common/include/px4_platform_common/Serial.hpp b/platforms/common/include/px4_platform_common/Serial.hpp index 983834ccf6..bf14035a5e 100644 --- a/platforms/common/include/px4_platform_common/Serial.hpp +++ b/platforms/common/include/px4_platform_common/Serial.hpp @@ -62,6 +62,7 @@ public: bool close(); ssize_t bytesAvailable(); + ssize_t txSpaceAvailable(); ssize_t read(uint8_t *buffer, size_t buffer_size); ssize_t readAtLeast(uint8_t *buffer, size_t buffer_size, size_t character_count = 1, uint32_t timeout_ms = 0); diff --git a/platforms/nuttx/src/px4/common/SerialImpl.cpp b/platforms/nuttx/src/px4/common/SerialImpl.cpp index f8968e4881..9bee2ddf23 100644 --- a/platforms/nuttx/src/px4/common/SerialImpl.cpp +++ b/platforms/nuttx/src/px4/common/SerialImpl.cpp @@ -293,12 +293,36 @@ ssize_t SerialImpl::bytesAvailable() { if (!_open) { PX4_ERR("Device not open!"); + errno = EBADF; return -1; } ssize_t bytes_available = 0; int ret = ioctl(_serial_fd, FIONREAD, &bytes_available); - return ret >= 0 ? bytes_available : 0; + + if (ret < 0) { + return -1; + } + + return bytes_available; +} + +ssize_t SerialImpl::txSpaceAvailable() +{ + if (!_open) { + PX4_ERR("Device not open!"); + errno = EBADF; + return -1; + } + + ssize_t space_available = 0; + int ret = ioctl(_serial_fd, FIONSPACE, &space_available); + + if (ret < 0) { + return -1; + } + + return space_available; } ssize_t SerialImpl::read(uint8_t *buffer, size_t buffer_size) diff --git a/platforms/nuttx/src/px4/common/include/SerialImpl.hpp b/platforms/nuttx/src/px4/common/include/SerialImpl.hpp index 82e4ddd29d..32c549ad6e 100644 --- a/platforms/nuttx/src/px4/common/include/SerialImpl.hpp +++ b/platforms/nuttx/src/px4/common/include/SerialImpl.hpp @@ -60,6 +60,7 @@ public: bool close(); ssize_t bytesAvailable(); + ssize_t txSpaceAvailable(); ssize_t read(uint8_t *buffer, size_t buffer_size); ssize_t readAtLeast(uint8_t *buffer, size_t buffer_size, size_t character_count = 1, uint32_t timeout_us = 0); diff --git a/platforms/posix/include/SerialImpl.hpp b/platforms/posix/include/SerialImpl.hpp index 82e4ddd29d..32c549ad6e 100644 --- a/platforms/posix/include/SerialImpl.hpp +++ b/platforms/posix/include/SerialImpl.hpp @@ -60,6 +60,7 @@ public: bool close(); ssize_t bytesAvailable(); + ssize_t txSpaceAvailable(); ssize_t read(uint8_t *buffer, size_t buffer_size); ssize_t readAtLeast(uint8_t *buffer, size_t buffer_size, size_t character_count = 1, uint32_t timeout_us = 0); diff --git a/platforms/posix/src/px4/common/SerialImpl.cpp b/platforms/posix/src/px4/common/SerialImpl.cpp index cb12b6919d..4859832829 100644 --- a/platforms/posix/src/px4/common/SerialImpl.cpp +++ b/platforms/posix/src/px4/common/SerialImpl.cpp @@ -281,12 +281,31 @@ ssize_t SerialImpl::bytesAvailable() { if (!_open) { PX4_ERR("Device not open!"); + errno = EBADF; return -1; } ssize_t bytes_available = 0; int ret = ioctl(_serial_fd, FIONREAD, &bytes_available); - return ret >= 0 ? bytes_available : 0; + + if (ret < 0) { + return -1; + } + + return bytes_available; +} + +ssize_t SerialImpl::txSpaceAvailable() +{ + if (!_open) { + PX4_ERR("Device not open!"); + errno = EBADF; + return -1; + } + + // POSIX/Linux doesn't have a direct equivalent to NuttX's FIONSPACE + errno = ENOSYS; + return -1; } ssize_t SerialImpl::read(uint8_t *buffer, size_t buffer_size) diff --git a/platforms/qurt/include/SerialImpl.hpp b/platforms/qurt/include/SerialImpl.hpp index c7739429ef..09797a33f7 100644 --- a/platforms/qurt/include/SerialImpl.hpp +++ b/platforms/qurt/include/SerialImpl.hpp @@ -59,6 +59,7 @@ public: bool close(); ssize_t bytesAvailable(); + ssize_t txSpaceAvailable(); ssize_t read(uint8_t *buffer, size_t buffer_size); ssize_t readAtLeast(uint8_t *buffer, size_t buffer_size, size_t character_count = 1, uint32_t timeout_us = 0); diff --git a/platforms/qurt/src/px4/SerialImpl.cpp b/platforms/qurt/src/px4/SerialImpl.cpp index 5c31be9a5c..c7d78baffe 100644 --- a/platforms/qurt/src/px4/SerialImpl.cpp +++ b/platforms/qurt/src/px4/SerialImpl.cpp @@ -156,14 +156,33 @@ ssize_t SerialImpl::bytesAvailable() { if (!_open) { PX4_ERR("Device not open!"); + errno = EBADF; return -1; } uint32_t rx_bytes = 0; - (void) fc_uart_rx_available(_serial_fd, &rx_bytes); + int ret = fc_uart_rx_available(_serial_fd, &rx_bytes); + + if (ret < 0) { + return -1; + } + return (ssize_t) rx_bytes; } +ssize_t SerialImpl::txSpaceAvailable() +{ + if (!_open) { + PX4_ERR("Device not open!"); + errno = EBADF; + return -1; + } + + // QURT doesn't have a direct equivalent to NuttX's FIONSPACE + errno = ENOSYS; + return -1; +} + ssize_t SerialImpl::read(uint8_t *buffer, size_t buffer_size) { if (!_open) {