From 7cdad67f3fa60d87471a82885cc3a07327446336 Mon Sep 17 00:00:00 2001 From: Matthew Kennedy Date: Fri, 19 Mar 2021 14:05:04 -0700 Subject: [PATCH] USB uses its own channel, add implementations for serial channels (#2472) * USB uses its own channel * revise channels * put serial ports in their own file * h7 uart incompatible for now * guard for sim --- firmware/console/binary/tunerstudio.mk | 1 + firmware/console/binary/tunerstudio_io.cpp | 34 ---------- firmware/console/binary/tunerstudio_io.h | 39 +++++++++-- .../console/binary/tunerstudio_io_serial.cpp | 66 +++++++++++++++++++ firmware/console/console_io.cpp | 11 ---- firmware/console/console_io.h | 2 - firmware/console/usb_console.cpp | 26 +++++++- .../ports/stm32/stm32h7/cfg/halconf.h | 2 +- 8 files changed, 126 insertions(+), 55 deletions(-) create mode 100644 firmware/console/binary/tunerstudio_io_serial.cpp diff --git a/firmware/console/binary/tunerstudio.mk b/firmware/console/binary/tunerstudio.mk index a68736b0c9..ad4bf5eff0 100644 --- a/firmware/console/binary/tunerstudio.mk +++ b/firmware/console/binary/tunerstudio.mk @@ -1,5 +1,6 @@ TUNERSTUDIO_SRC_CPP = $(PROJECT_DIR)/console/binary/tunerstudio_io.cpp \ + $(PROJECT_DIR)/console/binary/tunerstudio_io_serial.cpp \ $(PROJECT_DIR)/console/binary/ts_can_channel.cpp \ $(PROJECT_DIR)/console/binary/tunerstudio.cpp \ $(PROJECT_DIR)/console/binary/tunerstudio_commands.cpp \ diff --git a/firmware/console/binary/tunerstudio_io.cpp b/firmware/console/binary/tunerstudio_io.cpp index 113952f1b8..2e1d36a09c 100644 --- a/firmware/console/binary/tunerstudio_io.cpp +++ b/firmware/console/binary/tunerstudio_io.cpp @@ -277,37 +277,3 @@ bool ts_channel_s::isConfigured() const { #endif this->channel; } - -bool ts_channel_s::isReady() const { -#if EFI_USB_SERIAL - if (isUsbSerial(this->channel)) { - // TS uses USB when console uses serial - return is_usb_serial_ready(); - } -#endif /* EFI_USB_SERIAL */ - return true; -} - -#if EFI_PROD_CODE || EFI_SIMULATOR -void BaseChannelTsChannel::write(const uint8_t* buffer, size_t size) { - chnWriteTimeout(m_channel, buffer, size, BINARY_IO_TIMEOUT); -} - -size_t BaseChannelTsChannel::readTimeout(uint8_t* buffer, size_t size, int timeout) { - return chnReadTimeout(m_channel, buffer, size, timeout); -} - -void BaseChannelTsChannel::flush() { - // nop for this channel, writes automatically flush -} - -bool BaseChannelTsChannel::isReady() const { -#if EFI_USB_SERIAL -if (isUsbSerial(m_channel)) { - // TS uses USB when console uses serial - return is_usb_serial_ready(); - } -#endif /* EFI_USB_SERIAL */ - return true; -} -#endif // EFI_PROD_CODE || EFI_SIMULATOR diff --git a/firmware/console/binary/tunerstudio_io.h b/firmware/console/binary/tunerstudio_io.h index 18a2e056db..b84a63b8a7 100644 --- a/firmware/console/binary/tunerstudio_io.h +++ b/firmware/console/binary/tunerstudio_io.h @@ -62,7 +62,6 @@ struct BaseChannel; struct ts_channel_s : public TsChannelBase { void write(const uint8_t* buffer, size_t size) override; size_t readTimeout(uint8_t* buffer, size_t size, int timeout) override; - bool isReady() const override; bool isConfigured() const override; BaseChannel * channel = nullptr; @@ -72,18 +71,46 @@ struct ts_channel_s : public TsChannelBase { #endif // TS_UART_DMA_MODE }; -class BaseChannelTsChannel : public TsChannelBase { +// This class represents a channel for a physical async serial poart +class SerialTsChannelBase : public TsChannelBase { public: - BaseChannelTsChannel(BaseChannel* channel) : m_channel(channel) { } + // Open the serial port with the specified baud rate + virtual void start(uint32_t baud) = 0; +}; + +#if HAL_USE_SERIAL +// This class implements a ChibiOS Serial Driver +class SerialTsChannel : public SerialTsChannelBase { +public: + SerialTsChannel(SerialDriver& driver) : m_driver(&driver) { } + + void start(uint32_t baud) override; + void stop() override; void write(const uint8_t* buffer, size_t size) override; size_t readTimeout(uint8_t* buffer, size_t size, int timeout) override; - void flush() override; - bool isReady() const override; private: - BaseChannel* const m_channel; + SerialDriver* const m_driver; }; +#endif // HAL_USE_SERIAL + +#if HAL_USE_UART +// This class implements a ChibiOS UART Driver +class UartTsChannel : public SerialTsChannelBase { + UartTsChannel(UARTDriver& driver) : m_driver(&driver) { } + + void start(uint32_t baud) override; + void stop() override; + + void write(const uint8_t* buffer, size_t size) override; + size_t readTimeout(uint8_t* buffer, size_t size, int timeout) override; + +private: + UARTDriver* const m_driver; + UARTConfig m_config; +}; +#endif // HAL_USE_UART #define CRC_VALUE_SIZE 4 // todo: double-check this diff --git a/firmware/console/binary/tunerstudio_io_serial.cpp b/firmware/console/binary/tunerstudio_io_serial.cpp new file mode 100644 index 0000000000..482ea74821 --- /dev/null +++ b/firmware/console/binary/tunerstudio_io_serial.cpp @@ -0,0 +1,66 @@ +/** + * Implementation for hardware-serial TunerStudio ports + */ + +#include "tunerstudio_io.h" + +#if HAL_USE_SERIAL +void SerialTsChannel::start(uint32_t baud) { + SerialConfig cfg = { + #if EFI_PROD_CODE + .speed = baud, + .cr1 = 0, + .cr2 = USART_CR2_STOP1_BITS | USART_CR2_LINEN, + .cr3 = 0 + #endif // EFI_PROD_CODE + }; + + sdStart(m_driver, &cfg); +} + +void SerialTsChannel::stop() { + sdStop(m_driver); +} + +void SerialTsChannel::write(const uint8_t* buffer, size_t size) { + chnWriteTimeout(m_driver, buffer, size, BINARY_IO_TIMEOUT); +} + +size_t SerialTsChannel::readTimeout(uint8_t* buffer, size_t size, int timeout) { + return chnReadTimeout(m_driver, buffer, size, timeout); +} + +#endif // HAL_USE_SERIAL + +#if HAL_USE_UART +void UartTsChannel::start(uint32_t baud) { + m_config = { + .txend1_cb = NULL, + .txend2_cb = NULL, + .rxend_cb = NULL, + .rxchar_cb = NULL, + .rxerr_cb = NULL, + .timeout_cb = NULL, + .speed = baud, + .cr1 = 0, + .cr2 = 0/*USART_CR2_STOP1_BITS*/ | USART_CR2_LINEN, + .cr3 = 0, + .rxhalf_cb = NULL + }; + + uartStart(m_driver, &m_config); +} + +void UartTsChannel::stop() { + uartStop(m_driver); +} + +void UartTsChannel::write(const uint8_t* buffer, size_t size) { + uartSendTimeout(m_driver, &size, buffer, BINARY_IO_TIMEOUT); +} + +size_t UartTsChannel::readTimeout(uint8_t* buffer, size_t size, int timeout) { + uartReceiveTimeout(m_driver, &size, buffer, timeout); + return size; +} +#endif // HAL_USE_UART diff --git a/firmware/console/console_io.cpp b/firmware/console/console_io.cpp index 3202b676f8..867c7a8db9 100644 --- a/firmware/console/console_io.cpp +++ b/firmware/console/console_io.cpp @@ -160,17 +160,6 @@ ts_channel_s primaryChannel; #if EFI_PROD_CODE || EFI_EGT -#if HAL_USE_SERIAL_USB -extern SerialUSBDriver EFI_CONSOLE_USB_DEVICE; -#endif /* HAL_USE_SERIAL_USB */ - -bool isUsbSerial(BaseChannel * channel) { -#if HAL_USE_SERIAL_USB - return channel == (BaseChannel *) &EFI_CONSOLE_USB_DEVICE; -#else - return false; -#endif /* EFI_CONSOLE_USB_DEVICE */ -} BaseChannel * getConsoleChannel(void) { #if PRIMARY_UART_DMA_MODE if (primaryChannel.uartp != nullptr) { diff --git a/firmware/console/console_io.h b/firmware/console/console_io.h index 8c78f9b6e1..82a9ffc05e 100644 --- a/firmware/console/console_io.h +++ b/firmware/console/console_io.h @@ -28,8 +28,6 @@ void onDataArrived(void); #if EFI_PROD_CODE || EFI_SIMULATOR || EFI_EGT bool isCommandLineConsoleReady(void); -bool isUsbSerial(BaseChannel * channel); - BaseChannel * getConsoleChannel(void); #else diff --git a/firmware/console/usb_console.cpp b/firmware/console/usb_console.cpp index 7e75045c4b..7ceb63d823 100644 --- a/firmware/console/usb_console.cpp +++ b/firmware/console/usb_console.cpp @@ -11,7 +11,31 @@ static_assert(SERIAL_USB_BUFFERS_SIZE >= BLOCKING_FACTOR + 10); extern SerialUSBDriver EFI_CONSOLE_USB_DEVICE; -static BaseChannelTsChannel usbChannel((BaseChannel*)&EFI_CONSOLE_USB_DEVICE); + +class UsbChannel : public TsChannelBase { +public: + UsbChannel(SerialUSBDriver& driver) + : m_channel(reinterpret_cast(&driver)) + { + } + + bool isReady() const override { + return is_usb_serial_ready(); + } + + void write(const uint8_t* buffer, size_t size) override { + chnWriteTimeout(m_channel, buffer, size, BINARY_IO_TIMEOUT); + } + + size_t readTimeout(uint8_t* buffer, size_t size, int timeout) override { + return chnReadTimeout(m_channel, buffer, size, timeout); + } + +private: + BaseChannel* const m_channel; +}; + +static UsbChannel usbChannel(EFI_CONSOLE_USB_DEVICE); struct UsbThread : public TunerstudioThread { UsbThread() : TunerstudioThread("USB Console") { } diff --git a/firmware/hw_layer/ports/stm32/stm32h7/cfg/halconf.h b/firmware/hw_layer/ports/stm32/stm32h7/cfg/halconf.h index 05506323d7..c5f67a9e1b 100644 --- a/firmware/hw_layer/ports/stm32/stm32h7/cfg/halconf.h +++ b/firmware/hw_layer/ports/stm32/stm32h7/cfg/halconf.h @@ -123,7 +123,7 @@ * @brief Enables the UART subsystem. */ #if !defined(HAL_USE_UART) || defined(__DOXYGEN__) -#define HAL_USE_UART TRUE +#define HAL_USE_UART FALSE #endif /**