fix(mux): 修复MUX半帧丢失与发送路径静默失败

This commit is contained in:
2026-04-18 18:48:38 +08:00
parent a0b27d34a0
commit 495fbe4298
4 changed files with 225 additions and 78 deletions
+95 -36
View File
@@ -66,7 +66,9 @@ static void App_RouteMuxUartTraffic(void);
static void App_RouteTcpTraffic(void);
static void StackGuard_Init(void);
static void StackGuard_Check(void);
static void App_SendToUart(uint8_t uart_index, uint8_t src_id, uint8_t dst_mask, const uint8_t *data, uint16_t len);
static bool App_SendToUart(uint8_t uart_index, uint8_t src_id, uint8_t dst_mask, const uint8_t *data, uint16_t len);
static bool App_SendTcpServerPayload(uint8_t instance, const uint8_t *data, uint16_t len);
static bool App_SendTcpClientPayload(uint8_t instance, const uint8_t *data, uint16_t len);
/* USER CODE END PFP */
/* Private user code ---------------------------------------------------------*/
@@ -261,19 +263,33 @@ static void App_Init(void)
}
}
static void App_SendToUart(uint8_t uart_index, uint8_t src_id, uint8_t dst_mask, const uint8_t *data, uint16_t len)
static bool App_SendTcpServerPayload(uint8_t instance, const uint8_t *data, uint16_t len)
{
return tcp_server_send(instance, data, len) == (int)len;
}
static bool App_SendTcpClientPayload(uint8_t instance, const uint8_t *data, uint16_t len)
{
return tcp_client_send(instance, data, len) == (int)len;
}
static bool App_SendToUart(uint8_t uart_index, uint8_t src_id, uint8_t dst_mask, const uint8_t *data, uint16_t len)
{
const device_config_t *cfg = config_get();
uart_channel_t channel = (uart_index == LINK_UART_U1) ? UART_CHANNEL_U1 : UART_CHANNEL_U0;
uint16_t written;
if (cfg->mux_mode == MUX_MODE_FRAME) {
uint8_t frame[APP_ROUTE_BUFFER_SIZE + 6u];
uint16_t frame_len = 0u;
if (uart_mux_encode_frame(src_id, dst_mask, data, len, frame, &frame_len, sizeof(frame))) {
(void)uart_trans_write(channel, frame, frame_len);
written = uart_trans_write(channel, frame, frame_len);
return written == frame_len;
}
return false;
} else {
(void)uart_trans_write(channel, data, len);
written = uart_trans_write(channel, data, len);
return written == len;
}
}
@@ -286,11 +302,13 @@ static void App_RouteTcpTraffic(void)
int rc = tcp_server_recv(i, buffer, sizeof(buffer));
if (rc > 0) {
uint8_t link_index = (i == 0u) ? CONFIG_LINK_S1 : CONFIG_LINK_S2;
App_SendToUart(cfg->links[link_index].uart,
config_link_index_to_endpoint(link_index),
config_uart_index_to_endpoint(cfg->links[link_index].uart),
buffer,
(uint16_t)rc);
if (!App_SendToUart(cfg->links[link_index].uart,
config_link_index_to_endpoint(link_index),
config_uart_index_to_endpoint(cfg->links[link_index].uart),
buffer,
(uint16_t)rc)) {
return;
}
}
}
@@ -298,11 +316,13 @@ static void App_RouteTcpTraffic(void)
int rc = tcp_client_recv(i, buffer, sizeof(buffer));
if (rc > 0) {
uint8_t link_index = (i == 0u) ? CONFIG_LINK_C1 : CONFIG_LINK_C2;
App_SendToUart(cfg->links[link_index].uart,
config_link_index_to_endpoint(link_index),
config_uart_index_to_endpoint(cfg->links[link_index].uart),
buffer,
(uint16_t)rc);
if (!App_SendToUart(cfg->links[link_index].uart,
config_link_index_to_endpoint(link_index),
config_uart_index_to_endpoint(cfg->links[link_index].uart),
buffer,
(uint16_t)rc)) {
return;
}
}
}
}
@@ -315,37 +335,57 @@ static void App_RouteRawUartTraffic(void)
len = uart_trans_read(UART_CHANNEL_U0, buffer, sizeof(buffer));
if (len > 0u) {
bool routed_ok = true;
for (uint8_t i = 0; i < CONFIG_LINK_COUNT; ++i) {
bool sent = true;
if (cfg->links[i].enabled == 0u || cfg->links[i].uart != LINK_UART_U0) {
continue;
}
if (i == CONFIG_LINK_S1) {
(void)tcp_server_send(0u, buffer, len);
sent = App_SendTcpServerPayload(0u, buffer, len);
} else if (i == CONFIG_LINK_S2) {
(void)tcp_server_send(1u, buffer, len);
sent = App_SendTcpServerPayload(1u, buffer, len);
} else if (i == CONFIG_LINK_C1) {
(void)tcp_client_send(0u, buffer, len);
sent = App_SendTcpClientPayload(0u, buffer, len);
} else if (i == CONFIG_LINK_C2) {
(void)tcp_client_send(1u, buffer, len);
sent = App_SendTcpClientPayload(1u, buffer, len);
}
if (!sent) {
routed_ok = false;
}
}
if (!routed_ok) {
return;
}
}
len = uart_trans_read(UART_CHANNEL_U1, buffer, sizeof(buffer));
if (len > 0u) {
bool routed_ok = true;
for (uint8_t i = 0; i < CONFIG_LINK_COUNT; ++i) {
bool sent = true;
if (cfg->links[i].enabled == 0u || cfg->links[i].uart != LINK_UART_U1) {
continue;
}
if (i == CONFIG_LINK_S1) {
(void)tcp_server_send(0u, buffer, len);
sent = App_SendTcpServerPayload(0u, buffer, len);
} else if (i == CONFIG_LINK_S2) {
(void)tcp_server_send(1u, buffer, len);
sent = App_SendTcpServerPayload(1u, buffer, len);
} else if (i == CONFIG_LINK_C1) {
(void)tcp_client_send(0u, buffer, len);
sent = App_SendTcpClientPayload(0u, buffer, len);
} else if (i == CONFIG_LINK_C2) {
(void)tcp_client_send(1u, buffer, len);
sent = App_SendTcpClientPayload(1u, buffer, len);
}
if (!sent) {
routed_ok = false;
}
}
if (!routed_ok) {
return;
}
}
}
@@ -354,6 +394,7 @@ static void App_RouteMuxUartTraffic(void)
{
uart_mux_frame_t frame;
const device_config_t *cfg = config_get();
bool routed_ok;
while (uart_mux_try_extract_frame(UART_CHANNEL_U0, &frame)) {
#if defined(DEBUG) && (DEBUG != 0)
@@ -366,33 +407,42 @@ static void App_RouteMuxUartTraffic(void)
uint16_t response_len = (uint16_t)strlen(response_text);
uint16_t frame_len = 0u;
if (uart_mux_encode_frame(config_uart_index_to_endpoint(LINK_UART_U0), 0u, (const uint8_t *)response_text, response_len, g_mux_response_frame, &frame_len, sizeof(g_mux_response_frame))) {
(void)uart_trans_write(UART_CHANNEL_U0, g_mux_response_frame, frame_len);
if (uart_trans_write(UART_CHANNEL_U0, g_mux_response_frame, frame_len) != frame_len) {
return;
}
}
if (result == AT_NEED_REBOOT) {
static const char hint[] = "Note: Use AT+SAVE then AT+RESET to apply changes\r\n";
response_len = (uint16_t)strlen(hint);
if (uart_mux_encode_frame(config_uart_index_to_endpoint(LINK_UART_U0), 0u, (const uint8_t *)hint, response_len, g_mux_response_frame, &frame_len, sizeof(g_mux_response_frame))) {
(void)uart_trans_write(UART_CHANNEL_U0, g_mux_response_frame, frame_len);
if (uart_trans_write(UART_CHANNEL_U0, g_mux_response_frame, frame_len) != frame_len) {
return;
}
}
}
}
continue;
}
routed_ok = true;
if ((frame.dst_mask & ENDPOINT_S1) != 0u) {
(void)tcp_server_send(0u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpServerPayload(0u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_S2) != 0u) {
(void)tcp_server_send(1u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpServerPayload(1u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_C1) != 0u) {
(void)tcp_client_send(0u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpClientPayload(0u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_C2) != 0u) {
(void)tcp_client_send(1u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpClientPayload(1u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_UART3) != 0u && cfg->links[CONFIG_LINK_S2].uart == LINK_UART_U1) {
App_SendToUart(LINK_UART_U1, frame.src_id, ENDPOINT_UART3, frame.payload, frame.payload_len);
routed_ok = App_SendToUart(LINK_UART_U1, frame.src_id, ENDPOINT_UART3, frame.payload, frame.payload_len) && routed_ok;
}
if (!routed_ok) {
return;
}
}
@@ -407,33 +457,42 @@ static void App_RouteMuxUartTraffic(void)
uint16_t response_len = (uint16_t)strlen(response_text);
uint16_t frame_len = 0u;
if (uart_mux_encode_frame(config_uart_index_to_endpoint(LINK_UART_U1), 0u, (const uint8_t *)response_text, response_len, g_mux_response_frame, &frame_len, sizeof(g_mux_response_frame))) {
(void)uart_trans_write(UART_CHANNEL_U1, g_mux_response_frame, frame_len);
if (uart_trans_write(UART_CHANNEL_U1, g_mux_response_frame, frame_len) != frame_len) {
return;
}
}
if (result == AT_NEED_REBOOT) {
static const char hint[] = "Note: Use AT+SAVE then AT+RESET to apply changes\r\n";
response_len = (uint16_t)strlen(hint);
if (uart_mux_encode_frame(config_uart_index_to_endpoint(LINK_UART_U1), 0u, (const uint8_t *)hint, response_len, g_mux_response_frame, &frame_len, sizeof(g_mux_response_frame))) {
(void)uart_trans_write(UART_CHANNEL_U1, g_mux_response_frame, frame_len);
if (uart_trans_write(UART_CHANNEL_U1, g_mux_response_frame, frame_len) != frame_len) {
return;
}
}
}
}
continue;
}
routed_ok = true;
if ((frame.dst_mask & ENDPOINT_S1) != 0u) {
(void)tcp_server_send(0u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpServerPayload(0u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_S2) != 0u) {
(void)tcp_server_send(1u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpServerPayload(1u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_C1) != 0u) {
(void)tcp_client_send(0u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpClientPayload(0u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_C2) != 0u) {
(void)tcp_client_send(1u, frame.payload, frame.payload_len);
routed_ok = App_SendTcpClientPayload(1u, frame.payload, frame.payload_len) && routed_ok;
}
if ((frame.dst_mask & ENDPOINT_UART2) != 0u) {
App_SendToUart(LINK_UART_U0, frame.src_id, ENDPOINT_UART2, frame.payload, frame.payload_len);
routed_ok = App_SendToUart(LINK_UART_U0, frame.src_id, ENDPOINT_UART2, frame.payload, frame.payload_len) && routed_ok;
}
if (!routed_ok) {
return;
}
}
}