Просмотр исходного кода

1、完善soft SD drv_uart 差hard_flash

zhuts 1 неделя назад
Родитель
Сommit
e4e3022077

+ 30 - 15
controller_yy_app/hardware/hard_hdma_int.c

@@ -1,32 +1,47 @@
 #include "hard_hdma_int.h"
 #include "hpm_dma_drv.h"
 #include "board.h"
-volatile bool uart1_tx_dma_done;
-volatile bool uart2_tx_dma_done;
-volatile bool uart3_tx_dma_done;
-volatile bool uart4_tx_dma_done;
-volatile bool uart5_tx_dma_done;
-volatile bool uart6_tx_dma_done;
-
+volatile bool uart1_tx_dma_done = true;
+volatile bool uart2_tx_dma_done = true;
+volatile bool uart3_tx_dma_done = true;
+volatile bool uart4_tx_dma_done = true;
+volatile bool uart5_tx_dma_done = true;
+volatile bool uart6_tx_dma_done = true;
 
 
+extern struct _uart_config _u1_config;
+extern struct _uart_config _u4_config;
+extern void uart_tx_dma_isr_callback(struct _uart_config *config);
 /*--------------------------------------------------------------------------*/
 /* DMA 发送完成中断服务程序                                                */
 /*--------------------------------------------------------------------------*/
 SDK_DECLARE_EXT_ISR_M(IRQn_HDMA, dma_isr)
 void dma_isr(void)
 {   
-    volatile hpm_stat_t stat_tx_chn;
-    stat_tx_chn = dma_check_transfer_status(SBUS_UART2_DMA_CONTROLLER, SBUS_UART2_TX_DMA_CH);
-    if (stat_tx_chn & DMA_CHANNEL_STATUS_TC) { 
-        uart2_tx_dma_done = true;
-    }
+    //volatile hpm_stat_t stat_tx_chn;
+    //stat_tx_chn = dma_check_transfer_status(SBUS_UART2_DMA_CONTROLLER, SBUS_UART2_TX_DMA_CH);
+    //if (stat_tx_chn & DMA_CHANNEL_STATUS_TC) { 
+    //    uart2_tx_dma_done = true;
+    //}
 
-    stat_tx_chn = dma_check_transfer_status(IMU_UART3_DMA_CONTROLLER, IMU_UART3_TX_DMA_CH);
-    if (stat_tx_chn & DMA_CHANNEL_STATUS_TC) {
-        uart3_tx_dma_done = true;
+    //stat_tx_chn = dma_check_transfer_status(IMU_UART3_DMA_CONTROLLER, IMU_UART3_TX_DMA_CH);
+    //if (stat_tx_chn & DMA_CHANNEL_STATUS_TC) {
+    //    uart3_tx_dma_done = true;
+    //    uart_tx_dma_isr_callback(&_u3_config); // 串口3 DMA发送中断回调
 
+    //}
+    volatile hpm_stat_t stat_tx_chn = dma_check_transfer_status(HPM_HDMA, 0);
+    
+    if (stat_tx_chn & DMA_CHANNEL_STATUS_TC) {
+      
+        uart1_tx_dma_done = true;
+        uart_tx_dma_isr_callback(&_u1_config);
     }
 
+        if (stat_tx_chn & DMA_CHANNEL_STATUS_TC) {
+      
+        uart4_tx_dma_done = true;
+        uart_tx_dma_isr_callback(&_u4_config);
+    }
 
 }

+ 3 - 3
controller_yy_app/hardware/hard_imu_uart3.c

@@ -231,7 +231,7 @@ bool usart3_tx_isbusy(void)
 extern void recv_imu_data_hookfunction(const uint8_t *pbuffer,
                                        uint32_t rx_length);
 
-
+#ifndef UART_DRV_TEST
 
 SDK_DECLARE_EXT_ISR_M(IMU_UART3_IRQ, uart3_isr)
 void uart3_isr(void)
@@ -265,7 +265,7 @@ void uart3_isr(void)
 
 }
 
-
+#endif
 /* uart dma rx_irq  tx_dma demo 2026/03/14 pass*/
 #ifdef UART3_TEST
 
@@ -277,7 +277,7 @@ void imu_uart3_test(void)
   while(1)
   {
       // c++;
-      board_delay_ms(500);
+      // board_delay_ms(500);
       if(rec_succ)
       {
         rec_succ = false;

+ 3 - 1
controller_yy_app/hardware/hard_inc/hard_sdio_sd.h

@@ -1,6 +1,8 @@
 // 使用官方的SDMMC例程包
 #ifndef  __HARD_SDIO_SD_H
 #define  __HARD_SDIO_SD_H
-
+#include "hpm_sdmmc_sd.h"
+#include "ff.h"
+#include "diskio.h"
 
 #endif

+ 560 - 163
controller_yy_app/software/drv_usart.c

@@ -1,82 +1,12 @@
 #include "board.h"
 #include "hard_hdma_int.h"
-#include "hpm_uart_drv.h"
-#include "hpm_dmamux_drv.h"
-#include "hpm_dma_drv.h"
-#include "hpm_gpio_drv.h"
+#include "my_board.h"
 #include "hpm_clock_drv.h"
+#include "drv_usart.h"
 #include "rkfifo.h"
+#include "test.h"
 #include <string.h>
 
-/* ========== 配置宏定义 ========== */
-#ifndef UART_RX_FIFO_BUFFER_LEN
-#define UART_RX_FIFO_BUFFER_LEN    256
-#endif
-
-#ifndef UART_TX_FIFO_BUFFER_LEN
-#define UART_TX_FIFO_BUFFER_LEN    256
-#endif
-
-#ifndef UART_TX_DMA_BUFFER_LEN
-#define UART_TX_DMA_BUFFER_LEN     1024
-#endif
-
-/* ========== 外部DMA完成标志声明 ========== */
-extern bool uart1_tx_dma_done;
-extern bool uart2_tx_dma_done;
-extern bool uart3_tx_dma_done;
-extern bool uart4_tx_dma_done;
-extern bool uart5_tx_dma_done;
-extern bool uart6_tx_dma_done;
-
-/* ========== 结构体定义 ========== */
-struct _uart_config {
-    UART_Type *uart_base;           /* UART基地址 */
-    uart_intr_enable_t uart_irq_mask; /* UART中断掩码 */
-    uint8_t uart_irq_num;           /* 中断号 */ 
-    
-    /* GPIO配置 */
-    uint8_t tx_port;                /* TX端口: 0-9 (GPIOA-GPIOJ) */
-    uint8_t tx_pin;                 /* TX引脚 */
-    uint8_t rx_port;                /* RX端口 */
-    uint8_t rx_pin;                 /* RX引脚 */
-    uint8_t tx_af;                  /* TX复用功能 */
-    uint8_t rx_af;                  /* RX复用功能 */
-    
-    /* DMA配置 */
-    DMA_Type *dma_base;             /* DMA控制器基地址 */
-    DMAMUX_Type *dma_mux_base;      /* DMA MUX */
-    uint8_t dma_enable;             /* DMA 使能 (修正拼写) */
-    uint8_t dma_channel;            /* DMA通道 */
-    uint8_t dma_irq_num;            /* DMA中断号 */
-    uint8_t dma_request;            /* DMA请求源 */
-    
-    /* 缓冲区 */
-    uint8_t *tx_fifo_buff;          /* TX FIFO缓冲区 */
-    uint32_t tx_fifo_buff_size;     /* TX FIFO大小 */
-    uint8_t *rx_fifo_buff;          /* RX FIFO缓冲区 */
-    uint32_t rx_fifo_buff_size;     /* RX FIFO大小 */
-    
-    /* DMA缓冲区 */
-    uint8_t *dma_tx_buff;           /* DMA发送缓冲区 */
-    uint32_t dma_tx_buff_size;      /* DMA发送缓冲区大小 */
-    
-    /* 内部使用 */
-    rkfifo_t tx_fifo;               /* TX FIFO */
-    rkfifo_t rx_fifo;               /* RX FIFO */
-    volatile uint8_t dma_busy;      /* DMA发送忙标志 */
-};
-
-struct _uart_ops {
-    int (*init)(struct _uart_config *config, uint32_t baudrate);
-    uint32_t (*read)(struct _uart_config *config, void *data, uint32_t len);
-    uint32_t (*write)(struct _uart_config *config, const void *data, uint32_t len);
-};
-
-struct _uart_device {
-    struct _uart_config *config;
-    struct _uart_ops *ops;
-};
 
 /* ========== 辅助函数:获取DMA完成标志指针 ========== */
 static bool* _get_dma_done_flag(UART_Type *uart_base)
@@ -131,11 +61,11 @@ static void _uart_clock_enable(UART_Type *uart_base)
 static void _dma_clock_enable(DMA_Type *dma_base)
 {
     /* HDMA 时钟来源于系统总线时钟(AHB),已默认使能 */
-    (void)dma_base;
+    // clock_add_to_group(clock_hdma, 0);   
 }
 
 /* ========== GPIO配置 ========== */
-static void _uart_gpio_config(UART_Type *uart_base)
+static void _uart_gpio_config(UART_Type *uart_base) // 根据实际引脚配置
 {
     if (uart_base == HPM_UART1) {
         HPM_IOC->PAD[IOC_PAD_PA02].FUNC_CTL = IOC_PA02_FUNC_CTL_UART1_TXD;
@@ -171,9 +101,7 @@ static int _uart_config(struct _uart_config *config, uint32_t baudrate)
     _uart_gpio_config(config->uart_base);
     
     /* 获取UART时钟频率 */
-    if (config->uart_base == HPM_UART0) {
-        uart_clock_freq = clock_get_frequency(clock_uart0);
-    } else if (config->uart_base == HPM_UART1) {
+    if (config->uart_base == HPM_UART1) {
         uart_clock_freq = clock_get_frequency(clock_uart1);
     } else if (config->uart_base == HPM_UART2) {
         uart_clock_freq = clock_get_frequency(clock_uart2);
@@ -185,9 +113,7 @@ static int _uart_config(struct _uart_config *config, uint32_t baudrate)
         uart_clock_freq = clock_get_frequency(clock_uart5);
     } else if (config->uart_base == HPM_UART6) {
         uart_clock_freq = clock_get_frequency(clock_uart6);
-    } else if (config->uart_base == HPM_UART7) {
-        uart_clock_freq = clock_get_frequency(clock_uart7);
-    }
+    } 
     
     /* 配置UART */
     uart_default_config(config->uart_base, &uart_cfg);
@@ -223,7 +149,6 @@ static int _uart_dma_config(struct _uart_config *config)
                   DMA_SOC_CHN_TO_DMAMUX_CHN(config->dma_base, config->dma_channel), 
                   config->dma_request, 
                   true);
-    
     /* 配置 TX 握手参数 */
     dma_default_handshake_config(config->dma_base, &handshake_config);
     handshake_config.ch_index = config->dma_channel;
@@ -252,7 +177,9 @@ static void _uart_nvic_config(struct _uart_config *config)
     
     /* 使能DMA中断 */
     if (config->dma_enable) {
+
         intc_m_enable_irq_with_priority(config->dma_irq_num, 1);
+        printf("DMA interrupt enabled for channel %d\n", config->dma_channel);
     }
 }
 
@@ -274,60 +201,32 @@ int _uart_init(struct _uart_config *config, uint32_t baudrate)
     /* 配置中断 */
     _uart_nvic_config(config);
     
-    config->dma_busy = 0;
     
     return 0;
 }
 
-/**
- * @brief 获取串口发送是否忙碌
- */
-bool usart_tx_isbusy(struct _uart_config *config)
-{   
-    bool *dma_done_flag = _get_dma_done_flag(config->uart_base);
-    
-    if (dma_done_flag) {
-        return !(*dma_done_flag);
-    }
-    
-    return false;
-}
 
+uint8_t TX_BUFF[256]={'0','1','3'};
 void open_usart_dma_tx(struct _uart_config *config, uint32_t len)
 {
     dma_handshake_config_t handshake_config;
-    bool *dma_done_flag = _get_dma_done_flag(config->uart_base);
-    
-    /* 等待上次发送完成 */
-    uint32_t timeout = 1000000;
-    while (usart_tx_isbusy(config) && timeout--) {
-        __asm("nop");
-    }
-    
-    if (timeout == 0) {
-        /* 超时处理,复位DMA */
-        dma_abort_channel(config->dma_base, config->dma_channel);
-        if (dma_done_flag) {
-            *dma_done_flag = true;
-        }
-    }
-    
-    /* 清除DMA完成标志 */
-    if (dma_done_flag) {
-        *dma_done_flag = false;
-    }
-    
+
     /* 重新配置 TX 传输大小 */
     dma_default_handshake_config(config->dma_base, &handshake_config);
-    handshake_config.ch_index = config->dma_channel;
-    handshake_config.dst = (uint32_t)&config->uart_base->THR;
+    handshake_config.ch_index =  config->dma_channel;
+    handshake_config.dst =  (uint32_t)&(config->uart_base->THR);
     handshake_config.dst_fixed = true;
-    handshake_config.src = core_local_mem_to_sys_address(0, (uint32_t)config->dma_tx_buff);
+    handshake_config.src = core_local_mem_to_sys_address(0,(uint32_t)config->dma_tx_buff);
     handshake_config.src_fixed = false;
     handshake_config.data_width = DMA_TRANSFER_WIDTH_BYTE;
     handshake_config.size_in_byte = len;
     
-    dma_setup_handshake(config->dma_base, &handshake_config, true);
+   hpm_stat_t stat = dma_setup_handshake(config->dma_base, &handshake_config, true);
+   if(stat != status_success)
+   {
+      printf("uart dma tx config error\r\n");
+   }
+
 }
 
 /* ========== UART发送数据(DMA方式) ========== */
@@ -341,16 +240,11 @@ static uint32_t uart_tx_data(struct _uart_config *config, const void *data, uint
     ret = rkfifo_in(&config->tx_fifo, data, len);
     
     if (config->dma_tx_buff != NULL && config->dma_enable) {
-        /* DMA方式发送 */
-        if (!config->dma_busy) {
-            /* DMA空闲,立即发送 */
-            uint32_t count = rkfifo_out(&config->tx_fifo, 
-                                        config->dma_tx_buff, 
-                                        config->dma_tx_buff_size);
-            if (count > 0) {
-                open_usart_dma_tx(config, count);
-                config->dma_busy = 1;
-            }
+       
+        uint32_t count = rkfifo_out(&config->tx_fifo, config->dma_tx_buff, config->dma_tx_buff_size);
+        if (count > 0) {
+            open_usart_dma_tx(config, count);
+     
         }
     }
     
@@ -393,16 +287,8 @@ void uart_isr_callback(struct _uart_config *config)
 
 /* ========== DMA发送完成中断处理 ========== */
 void uart_tx_dma_isr_callback(struct _uart_config *config)
-{
-    bool *dma_done_flag = _get_dma_done_flag(config->uart_base);
-    
-    /* 设置DMA完成标志 */
-    if (dma_done_flag) {
-        *dma_done_flag = true;
-    }
-    
-    config->dma_busy = 0;
-    
+{ 
+  
     rkfifo_t *tx_fifo = &config->tx_fifo;
     uint8_t *dma_buff = config->dma_tx_buff;
     uint32_t dma_buff_size = config->dma_tx_buff_size;
@@ -410,29 +296,29 @@ void uart_tx_dma_isr_callback(struct _uart_config *config)
     
     if (count > 0) {
         open_usart_dma_tx(config, count);
-        config->dma_busy = 1;
+       
     }
 }
 
 /* ========== UART1 配置 ========== */
 #ifdef DRV_USING_UART1
-
-static uint8_t u1_rx_fifo_buff[UART_RX_FIFO_BUFFER_LEN];
-static uint8_t u1_tx_fifo_buff[UART_TX_FIFO_BUFFER_LEN];
-static uint8_t u1_dma_tx_buff[UART_TX_DMA_BUFFER_LEN];
+// ATTR_PLACE_AT_NONCACHEABLE这个一定不要忘记加 
+static ATTR_PLACE_AT_NONCACHEABLE uint8_t u1_rx_fifo_buff[UART1_RX_FIFO_BUFFER_LEN];
+static ATTR_PLACE_AT_NONCACHEABLE uint8_t u1_tx_fifo_buff[UART1_TX_FIFO_BUFFER_LEN];
+static ATTR_PLACE_AT_NONCACHEABLE uint8_t u1_dma_tx_buff[UART1_TX_DMA_BUFFER_LEN];
 
 struct _uart_config _u1_config = {
-    .uart_base = HPM_UART1,              /* 修正:应该是UART1 */
-    .uart_irq_mask = uart_intr_rx_rdy | uart_intr_rx_timeout,  /* 添加中断掩码 */
-    .uart_irq_num = IRQn_UART1,          /* 修正:IRQn_UART1 */
+    .uart_base = HPM_UART1,            
+    .uart_irq_mask = uart_intr_rx_data_avail_or_timeout,  /* 添加中断掩码 */
+    .uart_irq_num = IRQn_UART1,          
     
     /* DMA配置 */
-    .dma_base = HPM_DMA0,
-    .dma_mux_base = HPM_DMAMUX0,
-    .dma_enable = 1,                     /* 修正拼写 */
+    .dma_base = HPM_HDMA,
+    .dma_mux_base = HPM_DMAMUX,
+    .dma_enable = 1,                   
     .dma_channel = 0,
-    .dma_irq_num = IRQn_DMA0_CH0,
-    .dma_request = DMA_REQUEST_UART1_TX, /* 修正:UART1_TX */
+    .dma_irq_num = IRQn_HDMA,
+    .dma_request = HPM_DMA_SRC_UART1_TX, 
     
     /* FIFO缓冲区 */
     .tx_fifo_buff = u1_tx_fifo_buff,
@@ -450,7 +336,7 @@ static uint32_t u1_write_data(const void *data, uint32_t len)
     return uart_tx_data(&_u1_config, data, len);
 }
 
-static uint32_t u1_read_data(void *data, uint32_t len)
+static uint32_t u1_read_data( void *data, uint32_t len)
 {
     return uart_rx_data(&_u1_config, data, len);
 }
@@ -470,20 +356,81 @@ static struct _uart_device uart1 = {
     .config = &_u1_config,
     .ops = &_u1_ops,
 };
-
 /* UART1中断处理函数 */
-void uart1_irq_handler(void)
+SDK_DECLARE_EXT_ISR_M(IRQn_UART1, uart1_isr)
+void uart1_isr(void)
+{
+   uart_isr_callback(&_u1_config);
+}
+
+#endif
+
+#ifdef DRV_USING_UART4
+// ATTR_PLACE_AT_NONCACHEABLE这个一定不要忘记加 
+static ATTR_PLACE_AT_NONCACHEABLE uint8_t u4_rx_fifo_buff[UART4_RX_FIFO_BUFFER_LEN];
+static ATTR_PLACE_AT_NONCACHEABLE uint8_t u4_tx_fifo_buff[UART4_TX_FIFO_BUFFER_LEN];
+static ATTR_PLACE_AT_NONCACHEABLE uint8_t u4_dma_tx_buff[UART4_TX_DMA_BUFFER_LEN];
+
+struct _uart_config _u4_config = {
+    .uart_base = HPM_UART4,            
+    .uart_irq_mask = uart_intr_rx_data_avail_or_timeout,  /* 添加中断掩码 */
+    .uart_irq_num = IRQn_UART4,          
+    
+    /* DMA配置 */
+    .dma_base = HPM_HDMA,
+    .dma_mux_base = HPM_DMAMUX,
+    .dma_enable = 1,                   
+    .dma_channel = 0,
+    .dma_irq_num = IRQn_HDMA,
+    .dma_request = HPM_DMA_SRC_UART4_TX, 
+    
+    /* FIFO缓冲区 */
+    .tx_fifo_buff = u4_tx_fifo_buff,
+    .tx_fifo_buff_size = sizeof(u4_tx_fifo_buff),
+    .rx_fifo_buff = u4_rx_fifo_buff,
+    .rx_fifo_buff_size = sizeof(u4_rx_fifo_buff),
+    
+    /* DMA缓冲区 */
+    .dma_tx_buff = u4_dma_tx_buff,
+    .dma_tx_buff_size = sizeof(u4_dma_tx_buff),
+};
+
+static uint32_t u4_write_data(const void *data, uint32_t len)
+{
+    return uart_tx_data(&_u4_config, data, len);
+}
+
+static uint32_t u4_read_data( void *data, uint32_t len)
 {
-    uart_isr_callback(&_u1_config);
+    return uart_rx_data(&_u4_config, data, len);
 }
 
-/* DMA0通道0中断处理函数 */
-void dma0_ch0_irq_handler(void)
+static int u4_init(uint32_t baudrate)
+{
+    return _uart_init(&_u4_config, baudrate);
+}
+
+static struct _uart_ops _u4_ops = {
+    .init = u4_init,
+    .read = u4_read_data,
+    .write = u4_write_data,
+};
+
+static struct _uart_device uart4 = {
+    .config = &_u4_config,
+    .ops = &_u4_ops,
+};
+
+/* UART4中断处理函数 */
+SDK_DECLARE_EXT_ISR_M(IRQn_UART4, uart4_isr)
+void uart4_isr(void)
 {
-    uart_tx_dma_isr_callback(&_u1_config);
+   uart_isr_callback(&_u4_config);
 }
 
-#endif /* DRV_USING_UART1 */
+
+
+#endif /* DRV_USING_UART4 */
 
 /* ========== UART查找函数 ========== */
 struct _uart_device *uart_find(const char *name)
@@ -517,4 +464,454 @@ struct _uart_device *uart_find(const char *name)
     }
     
     return uart;
-}
+}
+
+// 通用串口驱动测试例程 20260323 pass
+#ifdef UART_DRV_TEST
+
+/* uart_test.c
+ * UART驱动测试例程
+ * 测试功能:发送测试、接收测试、回环测试、DMA传输测试
+ */
+
+#include "board.h"
+#include "my_board.h"
+#include "drv_usart.h"
+#include <stdio.h>
+#include <string.h>
+
+/* ========== 测试配置 ========== */
+#define TEST_UART_NAME     "uart3"      /* 测试的UART名称 */
+#define TEST_BAUDRATE      115200       /* 波特率 */
+#define TEST_BUFFER_SIZE   256          /* 测试缓冲区大小 */
+#define TEST_LOOP_COUNT    10           /* 回环测试次数 */
+
+/* 测试标志 */
+static uint32_t test_pass_count = 0;
+static uint32_t test_fail_count = 0;
+
+/* ========== 辅助函数 ========== */
+
+/**
+ * @brief 打印测试结果
+ */
+static void print_test_result(const char *test_name, bool passed)
+{
+    if (passed) {
+        printf("[PASS] %s\n", test_name);
+        test_pass_count++;
+    } else {
+        printf("[FAIL] %s\n", test_name);
+        test_fail_count++;
+    }
+}
+
+/**
+ * @brief 打印测试汇总
+ */
+static void print_test_summary(void)
+{
+    printf("\n========== Test Summary ==========\n");
+    printf("Total Tests: %d\n", test_pass_count + test_fail_count);
+    printf("Passed: %d\n", test_pass_count);
+    printf("Failed: %d\n", test_fail_count);
+    printf("==================================\n");
+    
+    if (test_fail_count == 0) {
+        printf("All tests PASSED!\n");
+    } else {
+        printf("Some tests FAILED!\n");
+    }
+}
+
+/**
+ * @brief 延迟函数(毫秒)
+ */
+static void delay_ms(uint32_t ms)
+{
+   board_delay_ms(ms);
+}
+
+/**
+ * @brief 生成测试数据
+ */
+static void generate_test_data(uint8_t *buffer, uint32_t len, uint8_t pattern)
+{
+    for (uint32_t i = 0; i < len; i++) {
+        buffer[i] = pattern+i;
+    }
+   
+}
+
+/**
+ * @brief 验证数据是否正确
+ */
+static bool verify_test_data(uint8_t *buffer, uint32_t len, uint8_t pattern)
+{
+    for (uint32_t i = 0; i < len; i++) {
+        if (buffer[i] != (pattern + i)) {
+            printf("Data mismatch at pos %d: expected 0x%02X, got 0x%02X\n", 
+                   i, pattern + i, buffer[i]);
+            return false;
+        }
+    }
+    return true;
+}
+
+/* ========== 测试用例 ========== */
+
+/**
+ * @brief 测试1:UART初始化
+ */
+static void test_uart_init(struct _uart_device *uart_dev)
+{
+    printf("\n--- Test 1: UART Init ---\n");
+    
+    if (uart_dev == NULL) {
+        printf("UART device not found!\n");
+        print_test_result("UART Init", false);
+        return;
+    }
+    
+    int ret = uart_dev->ops->init( TEST_BAUDRATE);
+    if (ret == 0) {
+        printf("UART initialized successfully at %d baud\n", TEST_BAUDRATE);
+        print_test_result("UART Init", true);
+    } else {
+        printf("UART init failed with code: %d\n", ret);
+        print_test_result("UART Init", false);
+    }
+}
+
+/**
+ * @brief 测试2:单字节发送和接收(回环测试)
+ * 需要将TX和RX引脚短接
+ */
+static void test_single_byte_loopback(struct _uart_device *uart_dev)
+{
+    printf("\n--- Test 2: Single Byte Loopback ---\n");
+    printf("NOTE: Please short TX and RX pins for this test!\n");
+    
+    delay_ms(100);  /* 等待用户准备 */
+    
+    uint8_t test_byte = 0x5A;
+    uint8_t recv_byte = 0;
+    uint32_t timeout = 10000;
+    
+    /* 发送数据 */
+    uint32_t sent = uart_dev->ops->write( &test_byte, 1);
+    if (sent != 1) {
+        printf("Failed to send byte\n");
+        print_test_result("Single Byte Loopback", false);
+        return;
+    }
+    printf("Sent: 0x%02X\n", test_byte);
+    
+    /* 等待接收 */
+    while (timeout--) {
+        uint32_t received = uart_dev->ops->read( &recv_byte, 1);
+        if (received == 1) {
+            break;
+        }
+        delay_ms(1);
+    }
+    
+    if (timeout == 0) {
+        printf("Timeout waiting for data\n");
+        print_test_result("Single Byte Loopback", false);
+        return;
+    }
+    
+    printf("Received: 0x%02X\n", recv_byte);
+    
+    if (test_byte == recv_byte) {
+        print_test_result("Single Byte Loopback", true);
+    } else {
+        printf("Data mismatch!\n");
+        print_test_result("Single Byte Loopback", false);
+    }
+}
+
+/**
+ * @brief 测试3:多字节发送和接收(回环测试)
+ */
+static void test_multi_byte_loopback(struct _uart_device *uart_dev)
+{
+    printf("\n--- Test 3: Multi-Byte Loopback ---\n");
+    
+    uint8_t tx_buffer[64];
+    uint8_t rx_buffer[64];
+    uint32_t test_len = 64;
+    
+    /* 生成测试数据 */
+    generate_test_data(tx_buffer, test_len, 0x40);
+    memset(rx_buffer, 0, test_len);
+    
+    /* 发送数据 */
+    uint32_t sent = uart_dev->ops->write( tx_buffer, test_len);
+    if (sent != test_len) {
+        printf("Failed to send data: sent %d, expected %d\n", sent, test_len);
+        print_test_result("Multi-Byte Loopback", false);
+        return;
+    }
+    printf("Sent %d bytes\n", sent);
+    
+    /* 等待接收完成 */
+    uint32_t total_received = 0;
+    uint32_t timeout = 100000;
+    
+    while (total_received < test_len && timeout--) {
+        uint32_t received = uart_dev->ops->read(
+                                                 &rx_buffer[total_received], 
+                                                 test_len - total_received);
+        if (received > 0) {
+            total_received += received;
+        }
+        delay_ms(1);
+    }
+    
+    if (timeout == 0) {
+        printf("Timeout: received %d/%d bytes\n", total_received, test_len);
+        print_test_result("Multi-Byte Loopback", false);
+        return;
+    }
+    
+    printf("Received %d bytes\n", total_received);
+    
+    /* 验证数据 */
+    if (verify_test_data(rx_buffer, test_len, 0x40)) {
+        print_test_result("Multi-Byte Loopback", true);
+    } else {
+        print_test_result("Multi-Byte Loopback", false);
+    }
+}
+
+/**
+ * @brief 测试4:DMA发送测试
+ */
+static void test_dma_transmit(struct _uart_device *uart_dev)
+{
+    printf("\n--- Test 4: DMA Transmit Test ---\n");
+    
+    /* 检查是否支持DMA */
+    if (!uart_dev->config->dma_enable || uart_dev->config->dma_tx_buff == NULL) {
+        printf("DMA not enabled for this UART\n");
+        print_test_result("DMA Transmit", false);
+        return;
+    }
+    
+    uint8_t tx_buffer[256];
+    uint32_t test_len = 256;
+    
+    generate_test_data(tx_buffer, test_len, 0x30);
+    tx_buffer[255] = 0;
+     //printf("%s\r\n", tx_buffer);
+    /* 通过DMA发送 */
+    //  uart_send_data(HPM_UART3, tx_buffer, 128);
+    uint32_t sent = uart_dev->ops->write( tx_buffer, test_len);
+    
+    if (sent != test_len) {
+        printf("DMA send failed: sent %d, expected %d\n", sent, test_len);
+        print_test_result("DMA Transmit", false);
+        return;
+    }
+    
+    printf("DMA sent %d bytes\n", sent);
+    
+    
+    printf("DMA transfer completed\n");
+    print_test_result("DMA Transmit", true);
+}
+
+/**
+ * @brief 测试5:压力测试 - 连续发送接收
+ */
+static void test_stress_loopback(struct _uart_device *uart_dev)
+{
+    printf("\n--- Test 5: Stress Test (Continuous Loopback) ---\n");
+    
+    uint8_t tx_buffer[32];
+    uint8_t rx_buffer[32];
+    uint32_t total_tests = TEST_LOOP_COUNT;
+    uint32_t pass_tests = 0;
+    
+    for (uint32_t i = 0; i < total_tests; i++) {
+        uint8_t pattern = (uint8_t)(0x10 + i);
+        uint32_t test_len = 16 + (i % 16);  /* 可变长度测试 */
+        
+        generate_test_data(tx_buffer, test_len, pattern);
+        memset(rx_buffer, 0, test_len);
+        
+        /* 发送 */
+        uint32_t sent = uart_dev->ops->write( tx_buffer, test_len);
+        if (sent != test_len) {
+            printf("Test %d: Send failed\n", i);
+            continue;
+        }
+        
+        /* 接收 */
+        uint32_t total_received = 0;
+        uint32_t timeout = 10000;
+        
+        while (total_received < test_len && timeout--) {
+            uint32_t received = uart_dev->ops->read(
+                                                     &rx_buffer[total_received],
+                                                     test_len - total_received);
+            if (received > 0) {
+                total_received += received;
+            }
+            delay_ms(1);
+        }
+        
+        if (total_received != test_len) {
+            printf("Test %d: Received %d/%d bytes\n", i, total_received, test_len);
+            continue;
+        }
+        
+        /* 验证 */
+        if (verify_test_data(rx_buffer, test_len, pattern)) {
+            pass_tests++;
+        } else {
+            printf("Test %d: Data verification failed\n", i);
+        }
+        
+        delay_ms(10);  /* 测试间隔 */
+    }
+    
+    printf("Stress test: %d/%d passed\n", pass_tests, total_tests);
+    print_test_result("Stress Test", (pass_tests == total_tests));
+}
+
+/**
+ * @brief 测试6:波特率准确性测试
+ */
+static void test_baudrate_accuracy(struct _uart_device *uart_dev)
+{
+    printf("\n--- Test 6: Baudrate Accuracy Test ---\n");
+    
+    /* 发送一串特定字符,在接收端验证 */
+    const char *test_string = "Hello UART! 1234567890\r\n";
+    uint32_t test_len = strlen(test_string);
+    char rx_buffer[128];
+    
+    printf("Sending: %s", test_string);
+    
+    uint32_t sent = uart_dev->ops->write(test_string, test_len);
+    if (sent != test_len) {
+        print_test_result("Baudrate Accuracy", false);
+        return;
+    }
+    
+    /* 等待接收 */
+    uint32_t total_received = 0;
+    uint32_t timeout = 50000;
+    
+    while (total_received < test_len && timeout--) {
+        uint32_t received = uart_dev->ops->read(
+                                                 &rx_buffer[total_received],
+                                                 test_len - total_received);
+        if (received > 0) {
+            total_received += received;
+        }
+        delay_ms(1);
+    }
+    
+    if (total_received != test_len) {
+        printf("Received %d/%d bytes\n", total_received, test_len);
+        print_test_result("Baudrate Accuracy", false);
+        return;
+    }
+    
+    rx_buffer[total_received] = '\0';
+    printf("Received: %s", rx_buffer);
+    
+    if (memcmp(test_string, rx_buffer, test_len) == 0) {
+        print_test_result("Baudrate Accuracy", true);
+    } else {
+        printf("Data mismatch!\n");
+        print_test_result("Baudrate Accuracy", false);
+    }
+}
+
+/* ========== 主测试函数 ========== */
+
+/**
+ * @brief UART测试主函数
+ * @param test_mode 测试模式:
+ *        0 - 完整测试(需要TX/RX短接)
+ *        1 - 仅发送测试(不需要短接)
+ */
+int uart_test_main(int test_mode)
+{
+    struct _uart_device *uart_dev = NULL;
+    
+    printf("\n");
+    printf("========================================\n");
+    printf("       UART Driver Test Suite\n");
+    printf("========================================\n");
+    printf("Testing UART: %s\n", TEST_UART_NAME);
+    printf("Baudrate: %d\n", TEST_BAUDRATE);
+    printf("Test Mode: %s\n", test_mode == 0 ? "Full (Loopback)" : "Transmit Only");
+    printf("========================================\n");
+    
+    /* 查找UART设备 */
+    uart_dev = uart_find(TEST_UART_NAME);
+    if (uart_dev == NULL) {
+        printf("Error: UART device '%s' not found!\n", TEST_UART_NAME);
+        return -1;
+    }
+    printf("UART device found\n");
+    
+    /* 重置测试计数器 */
+    test_pass_count = 0;
+    test_fail_count = 0;
+    
+    /* 执行测试 */
+    test_uart_init(uart_dev);
+    
+    if (test_mode == 0) {
+        /* 完整测试模式 - 需要TX/RX短接 */
+        test_single_byte_loopback(uart_dev);
+        test_multi_byte_loopback(uart_dev);
+        test_stress_loopback(uart_dev);
+        test_baudrate_accuracy(uart_dev);
+    }
+    
+    /* DMA测试(无论是否回环都可以测试) */
+    test_dma_transmit(uart_dev);
+    
+    /* 打印测试结果 */
+    print_test_summary();
+    
+    return (test_fail_count == 0) ? 0 : -1;
+}
+
+/**
+ * @brief 简单的打印测试(用于验证基本功能)
+ */
+int uart_simple_print_test(void)
+{
+    struct _uart_device *uart_dev = NULL;
+    const char *message = "Hello from UART test!\r\n";
+    
+    uart_dev = uart_find(TEST_UART_NAME);
+    if (uart_dev == NULL) {
+        printf("UART device not found!\n");
+        return -1;
+    }
+    
+    /* 初始化UART */
+    if (uart_dev->ops->init( TEST_BAUDRATE) != 0) {
+        printf("UART init failed!\n");
+        return -1;
+    }
+    
+    printf("UART initialized, sending test message...\n");
+    
+    /* 发送测试消息 */
+    uint32_t sent = uart_dev->ops->write(message, strlen(message));
+    printf("Sent %d bytes: %s", sent, message);
+    
+    return 0;
+}
+#endif

+ 43 - 46
controller_yy_app/software/soft_inc/drv_usart.h

@@ -2,57 +2,54 @@
 #define __DRV_USART_H__
 
 #include "rkfifo.h"
+#include "hpm_uart_drv.h"
+#include "hpm_dmamux_drv.h"
+#include "hpm_dma_drv.h"
 #include "stdint.h"
-#if 0
-
-
-struct stm32_uart_config
-{
-    USART_TypeDef *uartx;
-    GPIO_TypeDef *_tx_port;
-    GPIO_TypeDef *_rx_port;
-    uint8_t _uart_irq_channel;
-    uint16_t _tx_pin;
-    uint16_t _rx_pin;
-
-    uint8_t *_dma_tx_buff;
-    uint32_t _dma_tx_buff_size;
-    uint8_t *_dma_rx_buff;
-    uint32_t _dma_rx_buff_size;
-
-    DMA_Stream_TypeDef *_tx_dma;
-    uint32_t _tx_dma_channel;
-    uint32_t _tx_dma_tcif;
-    uint32_t _tx_dma_teif;
-    uint8_t _tx_dma_irq_channel;
-
-    DMA_Stream_TypeDef *_rx_dma;
-    uint32_t _rx_dma_channel;
-    uint32_t _rx_dma_tcif;
-    uint32_t _rx_dma_teif;
-    uint8_t _rx_dma_irq_channel;
-
-    rkfifo_t _rx_fifo;
-    uint8_t *_rx_fifo_buff;
-    uint32_t _rx_fifo_buff_size;
-    rkfifo_t _tx_fifo;
-    uint8_t *_tx_fifo_buff;
-    uint32_t _tx_fifo_buff_size;
+
+/* ========== 结构体定义 ========== */
+struct _uart_config {
+    UART_Type *uart_base;           /* UART基地址 */
+    uart_intr_enable_t uart_irq_mask; /* UART中断掩码 */
+    uint8_t uart_irq_num;           /* 中断号 */ 
+   
+    /* DMA配置 */
+    DMA_Type *dma_base;             /* DMA控制器基地址 */
+    DMAMUX_Type *dma_mux_base;      /* DMA MUX */
+    uint8_t dma_enable;             /* DMA 使能  */
+    uint8_t dma_channel;            /* DMA通道 */
+    uint8_t dma_irq_num;            /* DMA中断号 */
+    uint8_t dma_request;            /* DMA请求源 */
+    
+    /* 缓冲区 */
+    uint8_t *tx_fifo_buff;          /* TX FIFO缓冲区 */
+    uint32_t tx_fifo_buff_size;     /* TX FIFO大小 */
+    uint8_t *rx_fifo_buff;          /* RX FIFO缓冲区 */
+    uint32_t rx_fifo_buff_size;     /* RX FIFO大小 */
+    
+    /* DMA缓冲区 */
+    uint8_t *dma_tx_buff;           /* DMA发送缓冲区 */
+    uint32_t dma_tx_buff_size;      /* DMA发送缓冲区大小 */
+    
+    /* 内部使用 */
+    rkfifo_t tx_fifo;               /* TX FIFO */
+    rkfifo_t rx_fifo;               /* RX FIFO */
+
 };
 
-struct stm32_uart_ops
-{
-    int (*init)(uint32_t bps);
-    uint32_t (*write)(const void *pdata, uint32_t len);
-    uint32_t (*read)(void *pdata, uint32_t len);
+struct _uart_ops {
+    int (*init)(uint32_t baudrate);
+    uint32_t (*read)(void *data, uint32_t len);
+    uint32_t (*write)(const void *data, uint32_t len);
 };
 
-struct stm32_uart
-{
-    struct stm32_uart_ops *ops;
-    struct stm32_uart_config *_config;
+struct _uart_device {
+    struct _uart_config *config;
+    struct _uart_ops *ops;
 };
+struct _uart_device *uart_find(const char *name);
 
-struct stm32_uart *uart_find(const char *name);
-#endif
+
+extern int uart_test_main(int test_mode);
 #endif
+

+ 2 - 2
controller_yy_app/software/soft_inc/my_board.h

@@ -1,5 +1,5 @@
-#ifndef __BOARD_H__
-#define __BOARD_H__
+#ifndef __MYBOARD_H__
+#define __MYBOARD_H__
 
 #define DRV_USING_UART1
 #define UART1_TX_USING_DMA

+ 1 - 1
controller_yy_app/software/soft_inc/soft_gs.h

@@ -33,7 +33,7 @@ struct GCS_Link
     uint32_t link_lost_time_us;
     uint32_t last_check_time_us;
 
-    struct stm32_uart *uart;
+    struct _uart_device *uart;
 
     uint8_t msg_pack_buffer[512];
 

+ 2 - 0
controller_yy_app/software/soft_inc/soft_sdcard.h

@@ -18,4 +18,6 @@ uint8_t sdcard_initok(void);
 
 void sdcard_inital(uint8_t init_type);
 
+void main_test_demo(void);
+
 #endif

+ 1 - 2
controller_yy_app/software/soft_port_uart4.c

@@ -10,11 +10,10 @@
 #include "soft_imu.h"
 #include "soft_time.h"
 #include "soft_usharpradar.h"
-#include "stm32f4xx.h"
 #include "string.h"
 #include "ver_config.h"
 
-struct stm32_uart *payload_uart = NULL;
+struct _uart_device *payload_uart = NULL;
 
 // 选择串口 4 设备
 Port4PayloadType port4_payload_type = PORT4_PAYLOAD_NONE;

+ 678 - 89
controller_yy_app/software/soft_sdcard.c

@@ -1,3 +1,4 @@
+#include "board.h"
 #include "soft_sdcard.h"
 #include "ff.h"
 #include "hard_sdio_sd.h"
@@ -7,6 +8,8 @@
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
+#include "test.h"
+
 // 掉hpm的sd fatfs库
 /*
 //==========================连续写入测试=============================
@@ -26,12 +29,12 @@ WriteBuffer字节  写入速度    写固定字节数             写大数据
 
 
 */
-#if 0
 /**
  ******************************************************************************
  *                              定义变量
  ******************************************************************************
  */
+#if 1
 FATFS fs;                /* FatFs文件系统对象 */
 FIL fnew_data, fnew_log; /* 文件对象 */
 FRESULT res_sd;          /* 文件操作结果 */
@@ -46,18 +49,119 @@ DIR posdir;
 FILINFO fno;
 
 int file_num = 0;
-
+const TCHAR driver_num_buf[3] = { DEV_SD + '0', ':', '/' };
 // FATFS文件名不区分大小写。默认大写。
 const char *logpath = "LOG";
 const char *pospath = "POS";
 
 static uint8_t _sd_init_ok = 0;
 
+const char *show_error_string(FRESULT fresult);
+
+static FRESULT sd_mount_fs(void);
+
+static FRESULT sd_mkfs(void);
+
 uint8_t sdcard_initok(void)
 {
     return _sd_init_ok;
 }
+static FRESULT sd_mount_fs(void)
+{
+    FRESULT fresult = f_mount(&fs, driver_num_buf, 1);
+    if (fresult == FR_OK) {
+        printf("SD card has been mounted successfully\n");
+    } else {
+        printf("Failed to mount SD card, cause: %s\n", show_error_string(fresult));
+    }
+
+    fresult = f_chdrive(driver_num_buf);
+    return fresult;
+}
 
+static FRESULT sd_mkfs(void)
+{
+    printf("Formatting the SD card, depending on the SD card capacity, the formatting process may take a long time\n");
+    FRESULT fresult = f_mkfs(driver_num_buf, NULL, work, sizeof(work));
+    if (fresult != FR_OK) {
+        printf("Making File system failed, cause: %s\n", show_error_string(fresult));
+    } else {
+        printf("Making file system is successful\n");
+    }
+
+    return fresult;
+}
+const char *show_error_string(FRESULT fresult)
+{
+    const char *result_str;
+
+    switch (fresult) {
+    case FR_OK:
+        result_str = "succeeded";
+        break;
+    case FR_DISK_ERR:
+        result_str = "A hard error occurred in the low level disk I/O level";
+        break;
+    case FR_INT_ERR:
+        result_str = "Assertion failed";
+        break;
+    case FR_NOT_READY:
+        result_str = "The physical drive cannot work";
+        break;
+    case FR_NO_FILE:
+        result_str = "Could not find the file";
+        break;
+    case FR_NO_PATH:
+        result_str = "Could not find the path";
+        break;
+    case FR_INVALID_NAME:
+        result_str = "Tha path name format is invalid";
+        break;
+    case FR_DENIED:
+        result_str = "Access denied due to prohibited access or directory full";
+        break;
+    case FR_EXIST:
+        result_str = "Access denied due to prohibited access";
+        break;
+    case FR_INVALID_OBJECT:
+        result_str = "The file/directory object is invalid";
+        break;
+    case FR_WRITE_PROTECTED:
+        result_str = "The physical drive is write protected";
+        break;
+    case FR_INVALID_DRIVE:
+        result_str = "The logical driver number is invalid";
+        break;
+    case FR_NOT_ENABLED:
+        result_str = "The volume has no work area";
+        break;
+    case FR_NO_FILESYSTEM:
+        result_str = "There is no valid FAT volume";
+        break;
+    case FR_MKFS_ABORTED:
+        result_str = "THe f_mkfs() aborted due to any problem";
+        break;
+    case FR_TIMEOUT:
+        result_str = "Could not get a grant to access the volume within defined period";
+        break;
+    case FR_LOCKED:
+        result_str = "The operation is rejected according to the file sharing policy";
+        break;
+    case FR_NOT_ENOUGH_CORE:
+        result_str = "LFN working buffer could not be allocated";
+        break;
+    case FR_TOO_MANY_OPEN_FILES:
+        result_str = "Number of open files > FF_FS_LOCK";
+        break;
+    case FR_INVALID_PARAMETER:
+        result_str = "Given parameter is invalid";
+        break;
+    default:
+        result_str = "Unknown error";
+        break;
+    }
+    return result_str;
+}
 /**
  * @brief 初始化 SD 卡
  * @param init_type
@@ -65,91 +169,576 @@ uint8_t sdcard_initok(void)
  */
 void sdcard_inital(uint8_t init_type)
 {
-    //while ((SD_Init())) // 检测不到SD卡
-    //{
-    //    printf("SD CARD ERR \n");
-    //    delay_ms(600);
-    //}
-
-    //SDIO_NvicConfig();
-
-    //// SDIO方式挂载文件系统,文件系统挂载时会对SDIO设备初始化
-    //res_sd = f_mount(&fs, "", 1);
-
-    ///*----------------------- 格式化测试 ---------------------------*/
-    ///* 如果没有文件系统就格式化创建创建文件系统 */
-    //if (res_sd == FR_NO_FILESYSTEM || init_type == 1)
-    //{
-    //    /* 格式化 */
-    //    res_sd = f_mkfs("", FM_ANY, 0, work, sizeof(work));
-
-    //    if (res_sd == FR_OK)
-    //    {
-    //        /* 格式化后,先取消挂载 */
-    //        res_sd = f_mount(NULL, "", 1);
-    //        /* 重新挂载	*/
-    //        res_sd = f_mount(&fs, "", 1);
-    //    }
-    //    else
-    //    {
-    //        // 格式化失败。》》
-    //        printf("sd card format fail!\n");
-    //        while (1)
-    //            ;
-    //    }
-    //}
-    //else if (res_sd != FR_OK)
-    //{
-    //    // SD卡挂载文件系统失败,可能原因:SD卡初始化不成功。\r\n");
-    //    printf("sd card mount fail!\n");
-    //    while (1)
-    //        ;
-    //}
-    //else
-    //{
-    //    // 文件系统挂载成功,可以进行读写测试\r\n");
-    //}
-
-    //// 创建文件夹
-    //res_sd = f_mkdir(logpath);
-    //res_sd = f_mkdir(pospath);
-
-    //// 检查是否存在LOG文件
-    //f_open(&fnew_data, "LOG/LOG_FLY.DAT", FA_CREATE_NEW);
-    //f_close(&fnew_data);
-
-    //DWORD nclst;
-    //unsigned long free_size = 0;
-    //FATFS *fs_p = &fs;
-    //// 检查剩余容量
-    //res_sd = f_getfree("", &nclst, &fs_p);
-    //free_size = nclst * fs_p->csize / 2;
-
-    //// 打开log文件夹, 读下一个的文件
-    //res_sd = f_opendir(&logdir, logpath);
-    //res_sd = f_readdir(&logdir, &fno);
-    //// 如果剩余容量小于96MB, 删除部分数据文件, 防止写满
-    //while (free_size < 96 * 1024)
-    //{
-    //    if (fno.fname[0] != 'L')
-    //    {
-    //        char datafile_path[20] = "";
-    //        // 拼接文件路径
-    //        strcat(datafile_path, logpath);
-    //        strcat(datafile_path, "/");
-    //        strcat(datafile_path, fno.fname);
-    //        // 删除一个文件
-    //        f_unlink(datafile_path);
-    //    }
-    //    // 再读一下剩余的容量是否够用
-    //    res_sd = f_getfree("", &nclst, &fs_p);
-    //    free_size = nclst * fs_p->csize / 2;
-    //    // 读下一个文件
-    //    res_sd = f_readdir(&logdir, &fno);
-    //}
-
-    //_sd_init_ok = 1;
-    //// 关闭文件夹
-    //res_sd = f_closedir(&logdir);
+    bool need_init_filesystem = true;
+    DSTATUS dstatus = disk_status(DEV_SD);
+    printf("sd state is %d\r\n", dstatus); // 找到SD卡
+    if (dstatus == STA_NODISK) {
+        printf("No disk in the SD slot, please insert an SD card...\n");
+        do {
+            dstatus = disk_status(DEV_SD);
+        } while (dstatus == STA_NODISK);
+        board_delay_ms(100);
+        printf("Detected SD card, re-initialize the filesystem...\n");
+        need_init_filesystem = true;
+    }
+    dstatus = disk_initialize(DEV_SD);
+    if (dstatus != RES_OK) {
+        printf("Failed to initialize SD disk\n");
+    }
+     if (need_init_filesystem) {
+            res_sd = sd_mount_fs();
+            if (res_sd == FR_NO_FILESYSTEM ||  init_type == 1) {
+                printf("There is no File system available, making file system...\n");
+                res_sd = sd_mkfs();
+                if (res_sd != FR_OK) {
+                    printf("Failed to make filesystem, cause:%s\n", show_error_string(res_sd));
+                } else {
+                    need_init_filesystem = false;
+                }
+            }
+        }
+    
+    
+    // 创建文件夹
+    res_sd = f_mkdir(logpath);
+    if (res_sd != FR_OK && res_sd != FR_EXIST) {
+        printf("Failed to create LOG directory, cause: %d\n", res_sd);
+    }
+    
+    res_sd = f_mkdir(pospath);
+    if (res_sd != FR_OK && res_sd != FR_EXIST) {
+        printf("Failed to create POS directory, cause: %d\n", res_sd);
+    }
+    
+    // 检查是否存在LOG文件
+    res_sd = f_open(&fnew_data, "LOG/LOG_FLY.DAT", FA_CREATE_NEW);
+    if (res_sd == FR_OK) {
+        f_close(&fnew_data);
+        printf("LOG_FLY.DAT file created\n");
+    } else if (res_sd == FR_EXIST) {
+        printf("LOG_FLY.DAT file already exists\n");
+    } else {
+        printf("Failed to create LOG_FLY.DAT, cause: %d\n", res_sd);
+    }
+    
+    DWORD nclst;
+    unsigned long free_size = 0;
+    FATFS *fs_p = &fs;
+    
+    // 检查剩余容量
+    res_sd = f_getfree(driver_num_buf, &nclst, &fs_p);
+    if (res_sd == FR_OK) {
+        free_size = nclst * fs_p->csize / 2;  /* 单位:KB */
+        printf("Free space: %lu KB\n", free_size);
+    } else {
+        printf("Failed to get free space, cause: %d\n", res_sd);
+    }
+    
+    // 打开log文件夹, 读下一个的文件
+    res_sd = f_opendir(&logdir, logpath);
+    if (res_sd == FR_OK) {
+        res_sd = f_readdir(&logdir, &fno);
+        
+        // 如果剩余容量小于96MB, 删除部分数据文件, 防止写满
+        while (free_size < 96 * 1024 && res_sd == FR_OK && fno.fname[0] != 0)
+        {
+            // 跳过目录和LOG_FLY.DAT文件
+            if (fno.fname[0] != 'L' && !(fno.fattrib & AM_DIR))
+            {
+                char datafile_path[50] = {0};
+                // 拼接文件路径
+                strcat(datafile_path, logpath);
+                strcat(datafile_path, "/");
+                strcat(datafile_path, fno.fname);
+                // 删除一个文件
+                printf("Deleting old file: %s\n", datafile_path);
+                f_unlink(datafile_path);
+                
+                // 再读一下剩余的容量是否够用
+                res_sd = f_getfree("", &nclst, &fs_p);
+                if (res_sd == FR_OK) {
+                    free_size = nclst * fs_p->csize / 2;
+                    printf("Free space now: %lu KB\n", free_size);
+                }
+            }
+            // 读下一个文件
+            res_sd = f_readdir(&logdir, &fno);
+        }
+        
+        // 关闭文件夹
+        res_sd = f_closedir(&logdir);
+    } else {
+        printf("Failed to open LOG directory, cause: %d\n", res_sd);
+    }
+    
+    _sd_init_ok = 1;
+    printf("SD card initialization completed!\n");
 }
-#endif
+#endif
+#ifdef SOFT_SD_TEST
+// 测试代码 - 注意:这里不再重复包含头文件,因为上面已经包含了
+
+// 测试配置
+#define TEST_FILE_NAME      "test_speed.bin"
+#define TEST_BUFFER_SIZE    4096    // 测试缓冲区大小
+#define TEST_DATA_SIZE      (2 * 1024 * 1024)  // 测试数据大小 2MB
+#define TEST_ITERATIONS     10      // 测试次数
+
+// 测试结果结构体
+typedef struct {
+    uint32_t buffer_size;       // 缓冲区大小
+    uint32_t total_bytes;       // 总写入字节数
+    uint32_t total_time_us;     // 总耗时(微秒)
+    uint32_t avg_time_per_write_us; // 平均每次写入耗时
+    float speed_kb_per_sec;     // 写入速度(KB/s)
+} test_result_t;
+
+// 函数声明
+void sd_speed_test(void);
+void sd_continuous_write_test(void);
+void sd_random_write_test(void);
+void sd_large_block_test(void);
+void sd_integrity_test(void);
+void sd_run_tests(void);
+int sd_write_data(const char *filename, const uint8_t *data, uint32_t size);
+void main_test_demo(void);
+
+/**
+ * @brief 测试SD卡写入速度
+ */
+void sd_speed_test(void)
+{
+    if (!sdcard_initok()) {
+        printf("SD card not initialized!\n");
+        return;
+    }
+    
+    printf("\n========== SD Card Speed Test ==========\n");
+    
+    // 测试1: 连续写入测试
+    sd_continuous_write_test();
+    
+    // 测试2: 随机写入测试(模拟实际记录场景)
+    sd_random_write_test();
+    
+    // 测试3: 不同缓冲区大小测试
+    sd_large_block_test();
+}
+
+/**
+ * @brief 连续写入测试
+ */
+void sd_continuous_write_test(void)
+{
+    test_result_t result;
+    FIL test_file;
+    UINT bytes_written;
+    uint32_t start_time, end_time;
+    uint8_t *buffer;
+    
+    printf("\n--- Continuous Write Test ---\n");
+    
+    // 分配测试缓冲区
+    buffer = (uint8_t *)malloc(TEST_BUFFER_SIZE);
+    if (buffer == NULL) {
+        printf("Failed to allocate buffer!\n");
+        return;
+    }
+    
+    // 填充测试数据
+    for (uint32_t i = 0; i < TEST_BUFFER_SIZE; i++) {
+        buffer[i] = i & 0xFF;
+    }
+    
+    // 创建测试文件
+    FRESULT res = f_open(&test_file, TEST_FILE_NAME, FA_WRITE | FA_CREATE_ALWAYS);
+    if (res != FR_OK) {
+        printf("Failed to create test file! Error: %d\n", res);
+        free(buffer);
+        return;
+    }
+    
+    // 开始测试
+    start_time = micros();
+    
+    uint32_t remaining = TEST_DATA_SIZE;
+    uint32_t write_count = 0;
+    
+    while (remaining > 0) {
+        uint32_t write_size = (remaining > TEST_BUFFER_SIZE) ? TEST_BUFFER_SIZE : remaining;
+        res = f_write(&test_file, buffer, write_size, &bytes_written);
+        if (res != FR_OK || bytes_written != write_size) {
+            printf("Write failed! Error: %d, Written: %d\n", res, bytes_written);
+            break;
+        }
+        remaining -= bytes_written;
+        write_count++;
+    }
+    
+    end_time = micros();
+    
+    // 关闭文件
+    f_close(&test_file);
+    
+    // 计算结果
+    result.buffer_size = TEST_BUFFER_SIZE;
+    result.total_bytes = TEST_DATA_SIZE;
+    result.total_time_us = end_time - start_time;
+    result.avg_time_per_write_us = result.total_time_us / write_count;
+    result.speed_kb_per_sec = (float)(TEST_DATA_SIZE) / 1024.0f / (result.total_time_us / 1000000.0f);
+    
+    printf("Continuous Write Test Results:\n");
+    printf("  Buffer size: %d bytes\n", result.buffer_size);
+    printf("  Total data: %d bytes (%.2f MB)\n", result.total_bytes, result.total_bytes / (1024.0f * 1024.0f));
+    printf("  Write count: %d\n", write_count);
+    printf("  Total time: %d us (%.2f ms)\n", result.total_time_us, result.total_time_us / 1000.0f);
+    printf("  Avg time per write: %d us\n", result.avg_time_per_write_us);
+    printf("  Speed: %.2f KB/s (%.2f MB/s)\n", result.speed_kb_per_sec, result.speed_kb_per_sec / 1024.0f);
+    
+    free(buffer);
+}
+
+/**
+ * @brief 随机写入测试(模拟实际记录场景)
+ */
+void sd_random_write_test(void)
+{
+    test_result_t result;
+    FIL test_file;
+    UINT bytes_written;
+    uint32_t start_time, end_time;
+    uint8_t *buffer;
+    
+    printf("\n--- Random Write Test (Simulating Real Recording) ---\n");
+    
+    // 分配测试缓冲区
+    buffer = (uint8_t *)malloc(512);  // 模拟实际记录时的512字节数据包
+    if (buffer == NULL) {
+        printf("Failed to allocate buffer!\n");
+        return;
+    }
+    
+    // 填充测试数据
+    for (uint32_t i = 0; i < 512; i++) {
+        buffer[i] = i & 0xFF;
+    }
+    
+    // 创建测试文件
+    FRESULT res = f_open(&test_file, "random_test.bin", FA_WRITE | FA_CREATE_ALWAYS);
+    if (res != FR_OK) {
+        printf("Failed to create test file! Error: %d\n", res);
+        free(buffer);
+        return;
+    }
+    
+    // 测试不同写入大小的性能
+    uint32_t test_sizes[] = {512, 1024, 2048, 4096};
+    int test_count = sizeof(test_sizes) / sizeof(test_sizes[0]);
+    
+    for (int t = 0; t < test_count; t++) {
+        uint32_t write_size = test_sizes[t];
+        uint32_t total_data = 2 * 1024 * 1024;  // 2MB
+        uint32_t write_count = total_data / write_size;
+        
+        printf("\n  Testing write size: %d bytes\n", write_size);
+        
+        // 重新定位文件开头
+        f_lseek(&test_file, 0);
+        
+        start_time = micros();
+        
+        for (uint32_t i = 0; i < write_count; i++) {
+            res = f_write(&test_file, buffer, write_size, &bytes_written);
+            if (res != FR_OK || bytes_written != write_size) {
+                printf("    Write failed at %d! Error: %d\n", i, res);
+                break;
+            }
+        }
+        
+        end_time = micros();
+        
+        result.buffer_size = write_size;
+        result.total_bytes = total_data;
+        result.total_time_us = end_time - start_time;
+        result.avg_time_per_write_us = result.total_time_us / write_count;
+        result.speed_kb_per_sec = (float)(total_data) / 1024.0f / (result.total_time_us / 1000000.0f);
+        
+        printf("    Total time: %d us (%.2f ms)\n", result.total_time_us, result.total_time_us / 1000.0f);
+        printf("    Avg time per write: %d us\n", result.avg_time_per_write_us);
+        printf("    Speed: %.2f KB/s (%.2f MB/s)\n", result.speed_kb_per_sec, result.speed_kb_per_sec / 1024.0f);
+    }
+    
+    // 关闭文件
+    f_close(&test_file);
+    free(buffer);
+}
+
+/**
+ * @brief 大数据块写入测试
+ */
+void sd_large_block_test(void)
+{
+    FIL test_file;
+    UINT bytes_written;
+    uint32_t start_time, end_time;
+    uint8_t *buffer;
+    
+    printf("\n--- Large Block Write Test ---\n");
+    
+    // 测试不同缓冲区大小
+    uint32_t buffer_sizes[] = {512, 1024, 2048, 4096, 8192};
+    int test_count = sizeof(buffer_sizes) / sizeof(buffer_sizes[0]);
+    
+    for (int t = 0; t < test_count; t++) {
+        uint32_t buffer_size = buffer_sizes[t];
+        
+        // 分配测试缓冲区
+        buffer = (uint8_t *)malloc(buffer_size);
+        if (buffer == NULL) {
+            printf("Failed to allocate buffer size %d!\n", buffer_size);
+            continue;
+        }
+        
+        // 填充测试数据
+        for (uint32_t i = 0; i < buffer_size; i++) {
+            buffer[i] = i & 0xFF;
+        }
+        
+        // 创建测试文件
+        FRESULT res = f_open(&test_file, "large_block_test.bin", FA_WRITE | FA_CREATE_ALWAYS);
+        if (res != FR_OK) {
+            printf("Failed to create test file! Error: %d\n", res);
+            free(buffer);
+            continue;
+        }
+        
+        uint32_t total_data = 2 * 1024 * 1024;  // 2MB
+        uint32_t write_count = total_data / buffer_size;
+        
+        start_time = micros();
+        
+        for (uint32_t i = 0; i < write_count; i++) {
+            res = f_write(&test_file, buffer, buffer_size, &bytes_written);
+            if (res != FR_OK || bytes_written != buffer_size) {
+                printf("  Write failed at %d! Error: %d\n", i, res);
+                break;
+            }
+        }
+        
+        end_time = micros();
+        
+        // 关闭文件
+        f_close(&test_file);
+        
+        uint32_t total_time_us = end_time - start_time;
+        float speed_kb_per_sec = (float)(total_data) / 1024.0f / (total_time_us / 1000000.0f);
+        
+        printf("  Buffer size: %5d bytes -> Total time: %6d us (%.2f ms) -> Speed: %.2f KB/s (%.2f MB/s)\n", 
+               buffer_size, total_time_us, total_time_us / 1000.0f, 
+               speed_kb_per_sec, speed_kb_per_sec / 1024.0f);
+        
+        free(buffer);
+        
+        // 删除测试文件
+        f_unlink("large_block_test.bin");
+    }
+}
+
+/**
+ * @brief 测试文件写入并验证数据完整性
+ */
+void sd_integrity_test(void)
+{
+    FIL test_file;
+    UINT bytes_written, bytes_read;
+    uint32_t start_time, end_time;
+    uint8_t *write_buffer, *read_buffer;
+    uint32_t test_size = 1024 ;  // 1MB测试数据
+    
+    printf("\n--- Data Integrity Test ---\n");
+    
+    if (!sdcard_initok()) {
+        printf("SD card not initialized!\n");
+        return;
+    }
+    
+    // 分配缓冲区
+    write_buffer = (uint8_t *)malloc(test_size);
+    read_buffer = (uint8_t *)malloc(test_size);
+    if (write_buffer == NULL || read_buffer == NULL) {
+        printf("Failed to allocate buffers!\n");
+        if (write_buffer) free(write_buffer);
+        if (read_buffer) free(read_buffer);
+        return;
+    }
+    
+    // 填充测试数据(使用特定的模式)
+    for (uint32_t i = 0; i < test_size; i++) {
+        write_buffer[i] = i & 0xFF;
+    }
+    
+    // 写入测试
+    FRESULT res = f_open(&test_file, "integrity_test.bin", FA_WRITE | FA_CREATE_ALWAYS);
+    if (res != FR_OK) {
+        printf("Failed to create test file! Error: %d\n", res);
+        goto cleanup;
+    }
+    
+    start_time = micros();
+    res = f_write(&test_file, write_buffer, test_size, &bytes_written);
+    end_time = micros();
+    
+    if (res != FR_OK || bytes_written != test_size) {
+        printf("Write failed! Error: %d, Written: %d\n", res, bytes_written);
+        f_close(&test_file);
+        goto cleanup;
+    }
+    
+    printf("Write completed: %d bytes in %d us (%.2f KB/s)\n", 
+           bytes_written, end_time - start_time,
+           (float)bytes_written / 1024.0f / ((end_time - start_time) / 1000000.0f));
+    
+    f_close(&test_file);
+    
+    // 读取测试
+    res = f_open(&test_file, "integrity_test.bin", FA_READ);
+    if (res != FR_OK) {
+        printf("Failed to open test file for reading! Error: %d\n", res);
+        goto cleanup;
+    }
+    
+    start_time = micros();
+    res = f_read(&test_file, read_buffer, test_size, &bytes_read);
+    end_time = micros();
+    
+    if (res != FR_OK || bytes_read != test_size) {
+        printf("Read failed! Error: %d, Read: %d\n", res, bytes_read);
+        f_close(&test_file);
+        goto cleanup;
+    }
+    
+    printf("Read completed: %d bytes in %d us (%.2f KB/s)\n", 
+           bytes_read, end_time - start_time,
+           (float)bytes_read / 1024.0f / ((end_time - start_time) / 1000000.0f));
+    
+    f_close(&test_file);
+    
+    // 验证数据完整性
+    printf("Verifying data integrity...\n");
+    int error_count = 0;
+    for (uint32_t i = 0; i < test_size; i++) {
+        if (write_buffer[i] != read_buffer[i]) {
+            if (error_count < 10) {  // 只显示前10个错误
+                printf("Data mismatch at offset %d: expected 0x%02X, got 0x%02X\n", 
+                       i, write_buffer[i], read_buffer[i]);
+            }
+            error_count++;
+        }
+    }
+    
+    if (error_count == 0) {
+        printf("Data integrity test PASSED! All %d bytes verified.\n", test_size);
+    } else {
+        printf("Data integrity test FAILED! %d errors found.\n", error_count);
+    }
+    
+    // 删除测试文件
+    f_unlink("integrity_test.bin");
+    
+cleanup:
+    free(write_buffer);
+    free(read_buffer);
+}
+
+/**
+ * @brief 主测试函数,可以在主循环中调用
+ */
+void sd_run_tests(void)
+{
+    printf("\n");
+    printf("****************************************\n");
+    printf("*      SD Card Performance Test       *\n");
+    printf("****************************************\n");
+    
+    // 运行各种测试
+    sd_speed_test();
+    sd_integrity_test();
+    
+    printf("\n========== All Tests Completed ==========\n");
+}
+
+/**
+ * @brief 简单的文件写入测试(用于实际应用)
+ * @param filename 文件名
+ * @param data 数据指针
+ * @param size 数据大小
+ * @return 0:成功, -1:失败
+ */
+int sd_write_data(const char *filename, const uint8_t *data, uint32_t size)
+{
+    FIL file;
+    UINT bytes_written;
+    uint32_t start_time, end_time;
+    
+    if (!sdcard_initok()) {
+        printf("SD card not ready!\n");
+        return -1;
+    }
+    
+    // 打开或创建文件
+    FRESULT res = f_open(&file, filename, FA_WRITE | FA_OPEN_ALWAYS);
+    if (res != FR_OK) {
+        printf("Failed to open file %s! Error: %d\n", filename, res);
+        return -1;
+    }
+    
+    // 移动到文件末尾
+    f_lseek(&file, f_size(&file));
+    
+    // 写入数据
+    start_time = micros();
+    res = f_write(&file, data, size, &bytes_written);
+    end_time = micros();
+    
+    if (res != FR_OK || bytes_written != size) {
+        printf("Write failed! Error: %d, Written: %d\n", res, bytes_written);
+        f_close(&file);
+        return -1;
+    }
+    
+    printf("Written %d bytes to %s in %d us (%.2f KB/s)\n", 
+           bytes_written, filename, end_time - start_time,
+           (float)bytes_written / 1024.0f / ((end_time - start_time) / 1000000.0f));
+    
+    f_close(&file);
+    return 0;
+}
+#include "hard_system_delay.h"
+/**
+ * @brief 测试主函数
+ */
+void main_test_demo(void)
+{
+    // 先初始化SD卡
+    sdcard_inital(0);
+    system_time_initial();
+    if (sdcard_initok()) {
+        // 运行性能测试
+        sd_run_tests();
+        
+        // 示例:写入实际数据
+        uint8_t test_data[512];
+        for (int i = 0; i < 512; i++) {
+            test_data[i] = i & 0xFF;
+        }
+        
+        // 写入到LOG目录下的测试文件
+        sd_write_data("LOG/test_data.dat", test_data, sizeof(test_data));
+        
+        printf("\nAll tests completed. You can now use the SD card for your application.\n");
+    } else {
+        printf("SD card initialization failed!\n");
+    }
+}
+
+#endif /* SOFT_SD_TEST */

+ 2 - 0
controller_yy_app/user_src/inc/test.h

@@ -17,4 +17,6 @@
 #define UART2_TX_TEST // SBUS TX 测试
 // #define SD_TEST // SD TEST
 #define GD25Q16_TEST  // SPI-FLASH 测试
+#define UART_DRV_TEST 
+#define SOFT_SD_TEST
 #endif

+ 11 - 9
controller_yy_app/user_src/main.c

@@ -4,7 +4,7 @@
  * SPDX-License-Identifier: BSD-3-Clause
  *
  */
-#if 0
+#if 1
 #include <stdio.h>
 #include "board.h"
 
@@ -12,7 +12,7 @@
 #ifdef TEST_EN
 #include "bsp_V8M_YY_led.h"
 #include "bsp_V8M_YY_pwm.h"
- #include "bsp_V8M_YY_adc.h"
+#include "bsp_V8M_YY_adc.h"
 #include "hard_system.h"
 #include "hard_system_time.h"
 #include "hard_system_delay.h"
@@ -22,6 +22,8 @@
 #include "hard_can.h"
 #include "hard_sbus_out.h"
 #include "hard_flash_gd25q16.h"
+#include "drv_usart.h"
+#include "soft_sdcard.h"
 #include "main.h"
 #include "hpm_math.h"
 #endif
@@ -67,15 +69,15 @@ static void test_hard(void)
     // uart2_sbus_test();
     // system_test();
     // sbus_uart2_out_test();
-    test_gd25q16_quick();
-    gd25q16_cs_high();
+    // test_gd25q16_quick();
+    main_test_demo();
     while(1)
     {
       theta += PI*0.1;
       sin_theta = hpm_dsp_sin_f32(theta);
-    
+      //uart_test_main(0);
       board_delay_ms(200);
-      printf("sin theta is %f\r\n", sin_theta);
+      //printf("sin theta is %f\r\n", sin_theta);
     }
      
 }
@@ -87,8 +89,8 @@ int main(void)
     sin_theta = hpm_dsp_sin_f32(theta);
     
    
-    printf("hello world %f\n", i);
-    printf("sin theta is %f\r\n", sin_theta);
+    //printf("hello world %f\n", i);
+    //printf("sin theta is %f\r\n", sin_theta);
 
     test_hard();
     return 0;
@@ -96,7 +98,7 @@ int main(void)
 // DMA 最大4k
 
 #endif
-#if 1
+#if 0
 /*
  * Copyright (c) 2021 HPMicro
  *

+ 3 - 3
controller_yy_app_controller_yy_board_flash_sdram_xip_debug/segger_embedded_studio/controlware_yy_app.emProject

@@ -378,7 +378,7 @@
           <configuration
             Name="Common"
             build_object_file_name="$(IntDir)/drv_usart.c$(OBJ)" />
-          <configuration Name="Debug" build_exclude_from_build="Yes" />
+          <configuration Name="Debug" build_exclude_from_build="No" />
         </file>
         <file file_name="..\..\controller_yy_app\software\my_crc.c">
           <configuration
@@ -424,7 +424,7 @@
           <configuration
             Name="Common"
             build_object_file_name="$(IntDir)/soft_gs.c$(OBJ)" />
-          <configuration Name="Debug" build_exclude_from_build="Yes" />
+          <configuration Name="Debug" build_exclude_from_build="No" />
         </file>
         <file file_name="..\..\controller_yy_app\software\soft_imu.c">
           <configuration
@@ -445,7 +445,7 @@
           <configuration
             Name="Common"
             build_object_file_name="$(IntDir)/soft_port_uart4.c$(OBJ)" />
-          <configuration Name="Debug" build_exclude_from_build="Yes" />
+          <configuration Name="Debug" build_exclude_from_build="No" />
         </file>
         <file file_name="..\..\controller_yy_app\software\soft_rc_input.c">
           <configuration

+ 50 - 41
controller_yy_app_controller_yy_board_flash_sdram_xip_debug/segger_embedded_studio/controlware_yy_app.emSession

@@ -7,7 +7,7 @@
   <FrameBufferWindow width="0" keepAspectRatio="0" zoomToFitWindow="0" showGrid="0" addressSpace="" format="0" height="0" autoEvaluate="0" scaleFactor="1" refreshPeriod="0" name="controlware_yy_app - controller_yy_board_Debug" addressText="" accessByDisplayWidth="0"/>
  </FrameBuffer>
  <Memory1>
-  <MemoryWindow addressSpace="" dataSize="1" autoEvaluate="0" viewMode="0" viewType="4" addressOrder="0" columnsText="" refreshPeriod="0" name="controlware_yy_app - controller_yy_board_Debug" sizeText="" addressText=""/>
+  <MemoryWindow addressSpace="" dataSize="1" autoEvaluate="0" viewMode="0" viewType="4" addressOrder="0" columnsText="" refreshPeriod="0" name="controlware_yy_app - controller_yy_board_Debug" sizeText="sizeof((*_u3_config.dma_tx_buff))" addressText="0x40000250"/>
  </Memory1>
  <Memory2>
   <MemoryWindow addressSpace="" dataSize="1" autoEvaluate="0" viewMode="0" viewType="4" addressOrder="0" columnsText="" refreshPeriod="0" name="controlware_yy_app - controller_yy_board_Debug" sizeText="" addressText=""/>
@@ -22,13 +22,15 @@
   <ProjectSessionItem path="controlware_yy_app"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application"/>
+  <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;controlware"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;hardware"/>
+  <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;remote_controller"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;software"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;user_src"/>
+  <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;v8"/>
+  <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;application;v8;v8m"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;boards"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;boards;controller_yy_board"/>
-  <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;soc"/>
-  <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;soc;HPM6700"/>
   <ProjectSessionItem path="controlware_yy_app;controlware_yy_app - controller_yy_board;utils"/>
  </Project>
  <Register1>
@@ -51,7 +53,11 @@
  </TraceWindow>
  <Watch1>
   <Watches active="1" update="Never">
-   <Watchpoint expression="buf" name="buf" radix="16" linenumber="222" filename="../../controller_yy_app/hardware/hard_flash_gd25q16.c"/>
+   <Watchpoint expression="u3_rx_fifo_buff" name="u3_rx_fifo_buff" radix="-1" linenumber="370" filename="../../controller_yy_app/software/drv_usart.c"/>
+   <Watchpoint expression="tx_buffer" name="tx_buffer" radix="-1" linenumber="707" filename="../../controller_yy_app/software/drv_usart.c"/>
+   <Watchpoint expression="u3_dma_tx_buff" name="u3_dma_tx_buff" radix="-1" linenumber="372" filename="../../controller_yy_app/software/drv_usart.c"/>
+   <Watchpoint expression="_u3_config" name="_u3_config" radix="-1" linenumber="374" filename="../../controller_yy_app/software/drv_usart.c"/>
+   <Watchpoint expression="u3_tx_fifo_buff" name="u3_tx_fifo_buff" radix="-1" linenumber="371" filename="../../controller_yy_app/software/drv_usart.c"/>
   </Watches>
  </Watch1>
  <Watch2>
@@ -64,43 +70,46 @@
   <Watches active="0" update="Never"/>
  </Watch4>
  <Files>
-  <SessionOpenFile windowGroup="DockEditLeft" x="23" y="298" useTextEdit="1" folds0="82" path="../../controller_yy_app/software/drv_usart.c" left="0" selected="1" top="330" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="45" y="434" useTextEdit="1" path="../../controller_yy_app/hardware/hard_flash_gd25q16.c" left="0" top="438" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="19" y="72" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_flash_gd25q16.h" left="0" top="49" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="138" useTextEdit="1" path="../../controller_yy_app/user_src/main.c" left="0" top="124" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="25" y="8" useTextEdit="1" path="../../controller_yy_app/hardware/hard_sdio_sd.c" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_sdio_sd.h" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="30" y="446" useTextEdit="1" path="../../controller_yy_board/board.c" left="0" top="853" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="39" y="18" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/boot/hpm_bootheader.c" left="0" top="14" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="12" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/boot/hpm_bootheader.h" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/software/soft_gs.c" left="0" top="6" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="25" y="21" useTextEdit="1" path="../../controller_yy_app/hardware/hard_hdma_int.c" left="0" top="9" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/inc/hpm_uart_drv.h" left="0" top="687" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="169" useTextEdit="1" folds0="126" path="../../controller_yy_app/hardware/hard_imu_uart3.c" left="0" top="128" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="42" y="485" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/hpm_clock_drv.c" left="0" top="472" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="14" y="191" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/hpm_clock_drv.h" left="0" top="173" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="2" y="31" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/ip/hpm_dma_regs.h" left="0" top="5" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="145" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/ip/hpm_uart_regs.h" left="0" top="133" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="8" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/src/hpm_gpio_drv.c" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="40" y="272" useTextEdit="1" path="../../../../../../tool/HPM6750_tool/include/stdint.h" left="0" top="260" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/inc/hpm_gpio_drv.h" left="0" top="370" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="326" useTextEdit="1" path="../../controller_yy_board/board.h" left="0" top="314" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="34" y="17" useTextEdit="1" path="../../controller_yy_board/pinmux.c" left="0" top="12" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="5" y="26" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/src/hpm_uart_drv.c" left="0" top="2" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="38" y="36" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_hdma_int.h" left="0" top="24" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="200" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/hpm_interrupt.h" left="0" top="188" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="5" y="61" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/src/hpm_dma_drv.c" left="0" top="52" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="44" y="59" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/inc/hpm_dmamux_drv.h" left="0" top="47" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="17" y="123" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/hpm_soc.h" left="0" top="113" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="13" y="187" useTextEdit="1" path="../../controller_yy_app/software/rkfifo.c" left="0" top="128" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/toolchains/gcc/start.S" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/toolchains/gcc/initfini.c" left="0" top="62" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="25" y="22" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/toolchains/reset.c" left="0" top="162" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/system.c" left="0" top="32" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/utils/hpm_crc32.c" left="0" top="4" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/utils/hpm_ffssi.c" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/utils/hpm_swap.c" left="0" top="0" codecName="Default"/>
-  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="46" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/hpm_soc_irq.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="33" y="369" useTextEdit="1" folds0="12,31,68,92,172,233,255,261,498,512" path="../../controller_yy_app/software/drv_usart.c" left="0" selected="1" top="208" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="36" y="15" useTextEdit="1" path="../../controller_yy_app/software/soft_inc/my_board.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="26" y="47" useTextEdit="1" path="../../controller_yy_app/hardware/hard_imu_uart3.c" left="0" top="33" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="20" useTextEdit="1" path="../../controller_yy_app/user_src/inc/test.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="19" y="237" useTextEdit="1" path="../../controller_yy_app/user_src/main.c" left="0" top="210" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="13" y="36" useTextEdit="1" path="../../controller_yy_app/hardware/hard_hdma_int.c" left="0" top="19" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="19" y="45" useTextEdit="1" path="../../controller_yy_app/software/soft_inc/drv_usart.h" left="0" top="28" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="4" y="91" useTextEdit="1" path="../../controller_yy_app/software/rkfifo.c" left="0" top="78" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/software/debug_printf.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="27" y="8" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_hdma_int.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="100" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/hpm_soc_irq.h" left="0" top="86" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="70" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/inc/hpm_csr_drv.h" left="0" top="69" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="119" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/soc/HPM6700/HPM6750/toolchains/reset.c" left="0" top="103" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="245" useTextEdit="1" path="D:/sdk_env/sdk_env-v1.8.0/hpm_sdk/drivers/src/hpm_uart_drv.c" left="0" top="229" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="21" y="46" useTextEdit="1" path="../../controller_yy_app/software/soft_gs.c" left="0" top="42" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="23" y="35" useTextEdit="1" path="../../controller_yy_app/software/soft_inc/soft_gs.h" left="0" top="19" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="12" y="17" useTextEdit="1" path="../../controller_yy_app/software/soft_port_uart4.c" left="0" top="2" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="18" y="165" useTextEdit="1" folds0="94" path="../../controller_yy_app/software/soft_sdcard.c" left="0" top="139" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="19" y="5" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_sdio_sd.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="38" y="25" useTextEdit="1" path="../../controller_yy_app/middleware/fatfs/src/portable/diskio.h" left="0" top="15" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="3603" useTextEdit="1" path="../../controller_yy_app/middleware/fatfs/src/common/ff.c" left="0" top="3588" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="13" y="94" useTextEdit="1" path="../../controller_yy_app/middleware/fatfs/src/common/ff.h" left="0" top="82" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="115" useTextEdit="1" path="../../controller_yy_app/middleware/fatfs/src/portable/diskio.c" left="0" top="115" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/middleware/fatfs/src/portable/sdxc/hpm_sdmmc_disk.c" left="0" top="249" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="19" y="20" useTextEdit="1" path="../../controller_yy_app/software/soft_inc/soft_sdcard.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="8" y="199" useTextEdit="1" path="../../controller_yy_app/middleware/fatfs/src/common/ffconf.h" left="0" top="187" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="24" y="6" useTextEdit="1" path="../../controller_yy_app/software/soft_time.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_system.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/hardware/hard_inc/hard_system_delay.h" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/software/soft_can.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/software/soft_can_yy.c" left="0" top="21" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="55" y="258" useTextEdit="1" folds0="135" path="../../controller_yy_app/controlware/data_save.c" left="0" top="258" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/hardware/hard_flash_at45db.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/hardware/hard_flash_gd25q16.c" left="0" top="417" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/v8/v8m/bsp_V8M_flash.c" left="0" top="141" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/v8/v8m/bsp_V8M_adc.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/v8/v8m/bsp_V8M_GPIO_photo.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/v8/v8m/bsp_V8M_led.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/v8/v8m/bsp_V8M_pwm.c" left="0" top="0" codecName="Default"/>
+  <SessionOpenFile windowGroup="DockEditLeft" x="0" y="0" useTextEdit="1" path="../../controller_yy_app/hardware/hard_can.c" left="0" top="199" codecName="Default"/>
  </Files>
  <EMStudioWindow activeProject="controlware_yy_app - controller_yy_board" fileDialogDefaultFilter="*.c" autoConnectTarget="GDB Server" buildConfiguration="Debug" sessionSettings="" debugSearchFileMap="" fileDialogInitialDirectory="" debugSearchPath="" autoConnectCapabilities="1343"/>
 </session>

+ 1 - 0
踩坑.md

@@ -0,0 +1 @@
+1、需要DMA搬运的数据一定要加前缀 ATTR_PLACE_AT_NONCACHEABLE