Improve UART locking and fallback read logic
Refactored XT211Uart to handle cases where the lock is not initialized, preventing null dereference. Added fallback to base read_array for non-hardware UARTs in read_array_quick_, improving compatibility with BLE-backed UARTs.uart_fix
parent
81b71206a6
commit
ce199326a1
|
|
@ -85,13 +85,19 @@ class XT211Uart final : public uart::ESP8266UartComponent {
|
|||
class XT211Uart final : public uart::IDFUARTComponent {
|
||||
public:
|
||||
XT211Uart(uart::IDFUARTComponent &uart)
|
||||
: uart_(uart), iuart_num_(uart.*(&XT211Uart::uart_num_)), ilock_(uart.*(&XT211Uart::lock_)) {}
|
||||
: uart_(uart), iuart_num_(uart.*(&XT211Uart::uart_num_)) {}
|
||||
|
||||
// Reconfigure baudrate
|
||||
void update_baudrate(uint32_t baudrate) {
|
||||
xSemaphoreTake(ilock_, portMAX_DELAY);
|
||||
uart_set_baudrate(iuart_num_, baudrate);
|
||||
xSemaphoreGive(ilock_);
|
||||
auto &lock = uart_.*(&XT211Uart::lock_);
|
||||
if (lock != nullptr) {
|
||||
xSemaphoreTake(lock, portMAX_DELAY);
|
||||
uart_set_baudrate(iuart_num_, baudrate);
|
||||
xSemaphoreGive(lock);
|
||||
} else {
|
||||
// Lock not initialized yet, just set baudrate without locking
|
||||
uart_set_baudrate(iuart_num_, baudrate);
|
||||
}
|
||||
}
|
||||
|
||||
bool read_one_byte(uint8_t *data) { return read_array_quick_(data, 1); }
|
||||
|
|
@ -115,23 +121,40 @@ class XT211Uart final : public uart::IDFUARTComponent {
|
|||
size_t length_to_read = len;
|
||||
if (!this->check_read_timeout_quick_(len))
|
||||
return false;
|
||||
xSemaphoreTake(this->ilock_, portMAX_DELAY);
|
||||
|
||||
auto &lock = uart_.*(&XT211Uart::lock_);
|
||||
bool locked = false;
|
||||
if (lock != nullptr) {
|
||||
xSemaphoreTake(lock, portMAX_DELAY);
|
||||
locked = true;
|
||||
}
|
||||
|
||||
if (this->has_peek_) {
|
||||
length_to_read--;
|
||||
*data = this->peek_byte_;
|
||||
data++;
|
||||
this->has_peek_ = false;
|
||||
}
|
||||
if (length_to_read > 0)
|
||||
uart_read_bytes(this->iuart_num_, data, length_to_read, 20 / portTICK_PERIOD_MS);
|
||||
xSemaphoreGive(this->ilock_);
|
||||
if (length_to_read > 0) {
|
||||
// If no valid hardware UART, fall back to base read_array (e.g., BLE-backed UART)
|
||||
if (this->iuart_num_ < UART_NUM_0 || this->iuart_num_ >= UART_NUM_MAX) {
|
||||
if (!uart_.read_array(data, length_to_read)) {
|
||||
return false;
|
||||
}
|
||||
} else {
|
||||
uart_read_bytes(this->iuart_num_, data, length_to_read, 20 / portTICK_PERIOD_MS);
|
||||
}
|
||||
}
|
||||
|
||||
if (locked) {
|
||||
xSemaphoreGive(lock);
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
uart::IDFUARTComponent &uart_;
|
||||
uart_port_t iuart_num_;
|
||||
SemaphoreHandle_t &ilock_;
|
||||
};
|
||||
#endif
|
||||
|
||||
|
|
|
|||
Loading…
Reference in New Issue