【问题标题】:UART, can receive but not submitUART,可以接收但不能提交
【发布时间】:2022-01-07 07:25:52
【问题描述】:

我有一个 ESP32-S2 和一个外部单元,它连接到 Serial2(引脚 16/17 和引脚 8 上的 CTS)。 可以使用内置的 USB->UART 控制器访问外部单元,我可以手动打开终端并提交 HEX 命令。 现在,我断开 USB 并通过 ESP32 运行所有通信。传输命令需要 CTS。该单元还每 30 秒报告一次,给出读数。到目前为止,一切顺利。

问题是,该装置没有响应来自 ESP-32 的命令。正如您在下面看到的,它等待 10 秒,然后以两种不同的方式触发命令 (0x09 0x00),这应该会触发几乎立即的响应。

我在 COM4(ESP32)上打开了 RealTerm 以监控通信。 10 秒后,我看到命令正在发送 - 但没有返回任何答案。由于单元返回读数,我认为这与单元不知道何时接收命令有关(CTS 问题)。

有什么建议吗?

#include "driver/uart.h"
#include <HardwareSerial.h>
 
#define RXD2 16
#define TXD2 17
#define CTS 8
#define BUF_SIZE (1024)
 
void setup() {
 
  Serial.begin(115200);
  init_uart();
  Serial2.begin(115200, SERIAL_8N1, RXD2, TXD2); // To peripheral      
 
  delay(10000);
 
  // Send hex code 09 00 to Serial2. The loop-function should then show an answer and display something like 59 24 FF FF 1A FF FF BD FF FF 1D FF FF BF FF FF BE 00 12 25 FF FF B3 FF FF A3 FF FF 82 FF FF D4 FF FF 78 FF FF F0
  byte message[] = {0x09,0x00};
  Serial2.write(message, sizeof(message));

  // Another test
  uart_write_bytes(uart_num, (const char*)message, sizeof(message));
}
 
void loop() {
    if (Serial2.available()) {
      // Communication works - peridically receiving something like 52 12 00 12 00 09 00 20 00 08 00 00 68 F8 00 00 00 00 00 00
      Serial.print(Serial2.readString());
    }
}
 
void init_uart() {
    const uart_port_t uart_num = UART_NUM_2;
    uart_config_t uart_config = {
        .baud_rate = 115200,
        .data_bits = UART_DATA_8_BITS,
        .parity    = UART_PARITY_DISABLE,
        .stop_bits = UART_STOP_BITS_1,
        .flow_ctrl = UART_HW_FLOWCTRL_CTS
    };
   
    //ESP_ERROR_CHECK(uart_param_config(uart_num, &uart_config));
   
    uart_param_config(UART_NUM_2, &uart_config);
    uart_set_pin(UART_NUM_2,UART_PIN_NO_CHANGE, UART_PIN_NO_CHANGE,UART_PIN_NO_CHANGE,UART_PIN_NO_CHANGE);
    uart_driver_install(UART_NUM_2, BUF_SIZE * 2, 0, 0, NULL, 0);
}

【问题讨论】:

  • 也许尝试将CTS 引脚传递给uart_set_pin() 函数,而不是使用UART_PIN_NO_CHANGE
  • 我试过了,但没有任何区别。但是,我连接了示波器并监控了 ESP32 的 CTR 和 CTS 引脚以及 TX 引脚并发现了问题……虽然我还没有确定如何解决它。请求已发送(我可以在示波器上看到数据),但由于未知原因,微控制器从未发送 RTS。 ESP 侧的 RTS 连接到外部单元侧的 CTS。
  • 但是,我注意到一件有趣的事情:根据 Espressif 数据表,U2RTS 默认设置为 GPIO7……但是使用此引脚时 ESP 会不断重启。在另一个网站上,声明不推荐使用 GPIO6-11,因为它们连接到集成的 SPI 闪存。我尝试将 RTS 设置为 GPIO18,但没有成功。一旦我得到它的工作,我会更新这篇文章。

标签: arduino arduino-esp32


【解决方案1】:

现在可以了。

我最初无法理解与 UART 通信的两种不同方法。

在下面,您可以看到 Serial2.begin、Serial.write 等已消失,而我使用 uart_ 命令 - uart_write_bytesuart_read_bytes 等等。

流控制也可以完美运行,但我不得不将它重新映射到另一个 GPIO(我选择了 GPIO19),因为我在某个地方读到我应该不理会 GPIO6-11。根据数据表,UART2 的默认 CTS 是 GPIO8,但是这个引脚导致 ESP32 不断重启。

CTR 引脚被忽略并连接 CTS 到 CTS,如图所示 here

#include "driver/uart.h"
#include <HardwareSerial.h>

#define ECHO_TEST_TXD  (GPIO_NUM_17)
#define ECHO_TEST_RXD  (GPIO_NUM_16)
#define ECHO_TEST_RTS  (UART_PIN_NO_CHANGE)
//#define ECHO_TEST_CTS  (UART_PIN_NO_CHANGE)
#define ECHO_TEST_CTS  (GPIO_NUM_19)  

#define BUF_SIZE (1024)

unsigned long previousMillis = 0;
unsigned int interval = 45000;

byte message[] = {0x09, 0x00};

const uart_port_t uart_num = UART_NUM_2;

void setup() {

  Serial.begin(115200);
  
  uart_config_t uart_config = {
      .baud_rate = 115200,
      .data_bits = UART_DATA_8_BITS,
      .parity    = UART_PARITY_DISABLE,
      .stop_bits = UART_STOP_BITS_1,
      .flow_ctrl = UART_HW_FLOWCTRL_CTS // Enable flow-control
  };
    
  uart_param_config(UART_NUM_2, &uart_config);
  //uart_set_line_inverse(UART_NUM_2, UART_INVERSE_CTS); // The CTS-pin on the DCE is active high, so we invert the signal
  uart_set_pin(UART_NUM_2, ECHO_TEST_TXD, ECHO_TEST_RXD, ECHO_TEST_RTS, ECHO_TEST_CTS);
  uart_driver_install(UART_NUM_2, BUF_SIZE * 2, 0, 0, NULL, 0);
  
  delay(3000);
}

void loop() {
  unsigned long currentMillis = millis();
  if (currentMillis - previousMillis >= interval) {
    previousMillis = currentMillis;
        
    // Send hex code 09 00 to UART every 45th second. 
    // The loop-function should return an answer, display something like 59 24 FF FF 1A FF FF BD FF FF 1D FF FF BF FF FF BE 00 12 25 FF FF B3 FF FF A3 FF FF 82 FF FF D4 FF FF 78 FF FF F0
    uart_write_bytes(uart_num, (const char*)message, sizeof(message));
  }

  // Read data from UART.
  uint8_t data[128];
  int length = 0;
  ESP_ERROR_CHECK(uart_get_buffered_data_len(uart_num, (size_t*)&length));
  length = uart_read_bytes(uart_num, data, length, 100);
  if (length > 0) {
    for (int i=0; i<length; i++) {
      Serial.write(data[i]);
    }
  } 
}

在这里,您可以看到通讯。黄色是数据,蓝色是CTS

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2011-05-28
    • 2017-09-16
    • 1970-01-01
    • 1970-01-01
    • 2018-06-20
    相关资源
    最近更新 更多