fixes UART pin detach on end() (#7402)
This commit is contained in:
parent
d3ccd2a961
commit
2cebee4a40
4 changed files with 64 additions and 8 deletions
|
|
@ -145,6 +145,10 @@ _eventTask(NULL)
|
|||
#if !CONFIG_DISABLE_HAL_LOCKS
|
||||
,_lock(NULL)
|
||||
#endif
|
||||
,_rxPin(-1)
|
||||
,_txPin(-1)
|
||||
,_ctsPin(-1)
|
||||
,_rtsPin(-1)
|
||||
{
|
||||
#if !CONFIG_DISABLE_HAL_LOCKS
|
||||
if(_lock == NULL){
|
||||
|
|
@ -384,7 +388,8 @@ void HardwareSerial::begin(unsigned long baud, uint32_t config, int8_t rxPin, in
|
|||
|
||||
// Set UART RX timeout
|
||||
uartSetRxTimeout(_uart, _rxTimeout);
|
||||
|
||||
_rxPin = rxPin;
|
||||
_txPin = txPin;
|
||||
HSERIAL_MUTEX_UNLOCK();
|
||||
}
|
||||
|
||||
|
|
@ -403,6 +408,8 @@ void HardwareSerial::end(bool fullyTerminate)
|
|||
if (uartGetDebug() == _uart_nr) {
|
||||
uartSetDebug(0);
|
||||
}
|
||||
uartDetachPins(_uart, _rxPin, _txPin, _ctsPin, _rtsPin);
|
||||
_rxPin = _txPin = _ctsPin = _rtsPin = -1;
|
||||
}
|
||||
delay(10);
|
||||
uartEnd(_uart);
|
||||
|
|
@ -507,10 +514,19 @@ void HardwareSerial::setRxInvert(bool invert)
|
|||
void HardwareSerial::setPins(int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin)
|
||||
{
|
||||
if(_uart == NULL) {
|
||||
log_e("setPins() shall be called after begin() - nothing done");
|
||||
log_e("setPins() shall be called after begin() - nothing done\n");
|
||||
return;
|
||||
}
|
||||
uartSetPins(_uart, rxPin, txPin, ctsPin, rtsPin);
|
||||
|
||||
// uartSetPins() checks if pins are valid for each function and for the SoC
|
||||
if (uartSetPins(_uart, rxPin, txPin, ctsPin, rtsPin)) {
|
||||
_txPin = _txPin >= 0 ? txPin : _txPin;
|
||||
_rxPin = _rxPin >= 0 ? rxPin : _rxPin;
|
||||
_rtsPin = _rtsPin >= 0 ? rtsPin : _rtsPin;
|
||||
_ctsPin = _ctsPin >= 0 ? ctsPin : _ctsPin;
|
||||
} else {
|
||||
log_e("Error when setting Serial port Pins. Invalid Pin.\n");
|
||||
}
|
||||
}
|
||||
|
||||
// Enables or disables Hardware Flow Control using RTS and/or CTS pins (must use setAllPins() before)
|
||||
|
|
|
|||
|
|
@ -176,6 +176,7 @@ protected:
|
|||
#if !CONFIG_DISABLE_HAL_LOCKS
|
||||
SemaphoreHandle_t _lock;
|
||||
#endif
|
||||
int8_t _rxPin, _txPin, _ctsPin, _rtsPin;
|
||||
|
||||
void _createEventTask(void *args);
|
||||
void _destroyEventTask(void);
|
||||
|
|
|
|||
|
|
@ -23,6 +23,9 @@
|
|||
#include "soc/soc_caps.h"
|
||||
#include "soc/uart_struct.h"
|
||||
|
||||
#include "hal/gpio_hal.h"
|
||||
#include "esp_rom_gpio.h"
|
||||
|
||||
static int s_uart_debug_nr = 0;
|
||||
|
||||
struct uart_struct_t {
|
||||
|
|
@ -69,6 +72,40 @@ static uart_t _uart_bus_array[] = {
|
|||
|
||||
#endif
|
||||
|
||||
// IDF UART has no detach function. As consequence, after ending a UART, the previous pins continue
|
||||
// to work as RX/TX. It can be verified by changing the UART pins and writing to the UART. Output can
|
||||
// be seen in the previous pins and new pins as well.
|
||||
// Valid pin UART_PIN_NO_CHANGE is defined to (-1)
|
||||
// Negative Pin Number will keep it unmodified, thus this function can detach individual pins
|
||||
void uartDetachPins(uart_t* uart, int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin)
|
||||
{
|
||||
if(uart == NULL) {
|
||||
return;
|
||||
}
|
||||
|
||||
UART_MUTEX_LOCK();
|
||||
if (txPin >= 0) {
|
||||
gpio_hal_iomux_func_sel(GPIO_PIN_MUX_REG[txPin], PIN_FUNC_GPIO);
|
||||
esp_rom_gpio_connect_out_signal(txPin, SIG_GPIO_OUT_IDX, false, false);
|
||||
}
|
||||
|
||||
if (rxPin >= 0) {
|
||||
gpio_hal_iomux_func_sel(GPIO_PIN_MUX_REG[rxPin], PIN_FUNC_GPIO);
|
||||
esp_rom_gpio_connect_in_signal(GPIO_FUNC_IN_LOW, UART_PERIPH_SIGNAL(uart->num, SOC_UART_RX_PIN_IDX), false);
|
||||
}
|
||||
|
||||
if (rtsPin >= 0) {
|
||||
gpio_hal_iomux_func_sel(GPIO_PIN_MUX_REG[rtsPin], PIN_FUNC_GPIO);
|
||||
esp_rom_gpio_connect_out_signal(rtsPin, SIG_GPIO_OUT_IDX, false, false);
|
||||
}
|
||||
|
||||
if (ctsPin >= 0) {
|
||||
gpio_hal_iomux_func_sel(GPIO_PIN_MUX_REG[ctsPin], PIN_FUNC_GPIO);
|
||||
esp_rom_gpio_connect_in_signal(GPIO_FUNC_IN_LOW, UART_PERIPH_SIGNAL(uart->num, SOC_UART_CTS_PIN_IDX), false);
|
||||
}
|
||||
UART_MUTEX_UNLOCK();
|
||||
}
|
||||
|
||||
// solves issue https://github.com/espressif/arduino-esp32/issues/6032
|
||||
// baudrate must be multiplied when CPU Frequency is lower than APB 80MHz
|
||||
uint32_t _get_effective_baudrate(uint32_t baudrate)
|
||||
|
|
@ -108,15 +145,16 @@ bool uartIsDriverInstalled(uart_t* uart)
|
|||
|
||||
// Valid pin UART_PIN_NO_CHANGE is defined to (-1)
|
||||
// Negative Pin Number will keep it unmodified, thus this function can set individual pins
|
||||
void uartSetPins(uart_t* uart, int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin)
|
||||
bool uartSetPins(uart_t* uart, int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin)
|
||||
{
|
||||
if(uart == NULL) {
|
||||
return;
|
||||
return false;
|
||||
}
|
||||
UART_MUTEX_LOCK();
|
||||
// IDF uart_set_pin() will issue necessary Error Message and take care of all GPIO Number validation.
|
||||
uart_set_pin(uart->num, txPin, rxPin, rtsPin, ctsPin);
|
||||
bool retCode = uart_set_pin(uart->num, txPin, rxPin, rtsPin, ctsPin) == ESP_OK;
|
||||
UART_MUTEX_UNLOCK();
|
||||
return retCode;
|
||||
}
|
||||
|
||||
//
|
||||
|
|
|
|||
|
|
@ -91,8 +91,9 @@ int uartGetDebug();
|
|||
|
||||
bool uartIsDriverInstalled(uart_t* uart);
|
||||
|
||||
// Negative Pin Number will keep it unmodified, thus this function can set individual pins
|
||||
void uartSetPins(uart_t* uart, int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin);
|
||||
// Negative Pin Number will keep it unmodified, thus this function can set/reset individual pins
|
||||
bool uartSetPins(uart_t* uart, int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin);
|
||||
void uartDetachPins(uart_t* uart, int8_t rxPin, int8_t txPin, int8_t ctsPin, int8_t rtsPin);
|
||||
|
||||
// Enables or disables HW Flow Control function -- needs also to set CTS and/or RTS pins
|
||||
void uartSetHwFlowCtrlMode(uart_t *uart, uint8_t mode, uint8_t threshold);
|
||||
|
|
|
|||
Loading…
Reference in a new issue