修改spi读取方式,增加独立线程读取
authorhcj <1224667075@qq.com>
Thu, 4 Dec 2025 11:22:06 +0000 (19:22 +0800)
committerhcj <1224667075@qq.com>
Thu, 4 Dec 2025 11:22:06 +0000 (19:22 +0800)
code/sdk/zhihui/utils/custom_spi.c
code/sdk/zhihui/utils/custom_utils_at_cmd.c

index 25aefb8..e0b88d3 100644 (file)
 #include "pinctrl.h"
 #include "errcode.h"
 #include "los_base.h"
+#include "los_sem.h"
 #include "tcxo.h"
 #include <stdint.h>
+#include <string.h>
 #include "spi.h"
 #include "custom_spi.h"
+#include "custom_utils.h"
 
 static int total_cnt = 0;
 static uint8_t g_rx_buffer[1024] = {0};
+
+/* SPI read thread and semaphore */
+static UINT32 g_spi_sem_id = 0;
+static uint32_t g_spi_thread_handle = 0;
+static volatile uint8_t g_spi_thread_running = 0;
+
+#define USE_EXTEND_MEM 1
+
+/**
+ * @brief SPI read thread function
+ * Wait for semaphore and call custom_spi_read when triggered
+ */
+static void spi_read_thread_entry(void *arg)
+{
+    UNUSED(arg);
+    
+    printf("SPI read thread started\n");
+    
+    while (g_spi_thread_running) {
+        // Wait for semaphore (blocking)
+        UINT32 ret = LOS_SemPend(g_spi_sem_id, LOS_WAIT_FOREVER);
+        if (ret != LOS_OK) {
+            printf("LOS_SemPend failed: 0x%x\n", ret);
+            break;
+        }
+        
+        // Check if thread should still run
+        if (!g_spi_thread_running) {
+            break;
+        }
+        
+        // Execute SPI read
+        custom_spi_read();
+    }
+    
+    printf("SPI read thread exited\n");
+}
 void custom_spi_read(void)
 {
     spi_xfer_data_t spi_data = {0};
@@ -135,10 +175,75 @@ void custom_spi_init(void)
         printf("uapi_gpio_register_isr_func failed: 0x%x\n", ret);
         return;
     }
+    
+    // Initialize semaphore (initial count = 0)
+    UINT32 sem_ret = LOS_SemCreate(0, &g_spi_sem_id);
+    if (sem_ret != LOS_OK) {
+        printf("SPI semaphore create failed: 0x%x\n", sem_ret);
+        return;
+    }
+    printf("SPI semaphore created: 0x%x\n", g_spi_sem_id);
+    
+    // Create SPI read thread
+    g_spi_thread_running = 1;
+    app_task_definition_ext_t task_cfg = {0};
+    task_cfg.attr.name = "spi_read_task";
+    task_cfg.attr.stack_size = 0x2000;  // 8KB stack
+    task_cfg.attr.priority = TASK_PRIORITY_APP;  // Use TASK_PRIORITY_APP (17)
+    task_cfg.func = spi_read_thread_entry;
+    task_cfg.task_handle = &g_spi_thread_handle;
+    task_cfg.create_queue_handle = NULL;
+    task_cfg.use_mem = USE_EXTEND_MEM;
+    task_cfg.inst_args = NULL;
+    
+    errcode_t task_ret = uapi_create_osThread_custom_with_args(&task_cfg);
+    if (task_ret != ERRCODE_SUCC) {
+        printf("SPI read thread create failed: 0x%x\n", task_ret);
+        g_spi_thread_running = 0;
+        LOS_SemDelete(g_spi_sem_id);
+        g_spi_sem_id = 0;
+        return;
+    }
+    printf("SPI read thread created: 0x%x\n", g_spi_thread_handle);
 }
 
 void custom_spi_deinit(void)
 {
+    // Stop SPI read thread
+    if (g_spi_thread_running) {
+        g_spi_thread_running = 0;
+        
+        // Post semaphore to wake up thread if it's waiting
+        if (g_spi_sem_id != 0) {
+            LOS_SemPost(g_spi_sem_id);
+        }
+        
+        // Wait a bit for thread to exit
+        LOS_Msleep(100);
+        
+        // Terminate thread
+        if (g_spi_thread_handle != 0) {
+            errcode_t ret = uapi_terminate_thread((void *)g_spi_thread_handle);
+            if (ret != ERRCODE_SUCC) {
+                printf("SPI read thread terminate failed: 0x%x\n", ret);
+            } else {
+                printf("SPI read thread terminated\n");
+            }
+            g_spi_thread_handle = 0;
+        }
+    }
+    
+    // Delete semaphore
+    if (g_spi_sem_id != 0) {
+        UINT32 ret = LOS_SemDelete(g_spi_sem_id);
+        if (ret != LOS_OK) {
+            printf("SPI semaphore delete failed: 0x%x\n", ret);
+        } else {
+            printf("SPI semaphore deleted\n");
+        }
+        g_spi_sem_id = 0;
+    }
+    
     uapi_spi_deinit(SPI_BUS_1);
     uapi_pin_set_ie(S_MGPIO23,HAL_PIO_IE_DISABLE);
     errcode_t ret = uapi_gpio_unregister_isr_func(S_MGPIO23);
@@ -151,8 +256,15 @@ void custom_spi_deinit(void)
 
 void custom_spi_rx_callback(pin_t pin, uintptr_t param)
 {
-    // printf("custom_spi_rx_callback %d 0x%X\n",pin,param);
+    UNUSED(param);
+    printf("custom_spi_rx_callback %d 0x%X\n",pin,param);
     uapi_gpio_clear_interrupt(pin);
 
-    // do_custom_cmd_service_check_msg(CUSTOM_CMD_MSG_SPI_READ,NULL,0);
+    // Post semaphore to trigger SPI read in thread
+    if (g_spi_sem_id != 0 && g_spi_thread_running) {
+        UINT32 ret = LOS_SemPost(g_spi_sem_id);
+        if (ret != LOS_OK) {
+            printf("LOS_SemPost failed in callback: 0x%x\n", ret);
+        }
+    }
 }
index f283b8d..68ea253 100644 (file)
@@ -57,6 +57,8 @@
 /* Include spi_protocol_test.h for protocol test functions */
 /* Note: spi_protocol_test.h is in utilscpp directory, need to check include path */
 #include "../utilscpp/spi_protocol_test.h"
+/* Include custom_spi.h for SPI init/deinit test functions */
+#include "custom_spi.h"
 
 #define ARRAY_COUNT(array) (sizeof(array) / sizeof(array[0]))
 #define CUSTOM_UTILS_MAX_ARGC            8
@@ -2189,6 +2191,40 @@ static uint32_t custom_spi1_rx_stat(uint8_t *para, uint32_t paraLen, char *strCo
     return ERRCODE_SUCC;
 }
 
+/**
+ * @brief AT^SPIINIT - Initialize SPI1
+ * Usage: AT^SPIINIT
+ */
+static uint32_t custom_spi_init_test(uint8_t *para, uint32_t paraLen, char *strCommonCmd)
+{
+    UNUSED(para);
+    UNUSED(paraLen);
+    UNUSED(strCommonCmd);
+    
+    wstp_print("AT^SPIINIT: Initializing SPI1...\n");
+    custom_spi_init();
+    wstp_print("AT^SPIINIT: SPI1 initialized successfully\n");
+    
+    return ERRCODE_SUCC;
+}
+
+/**
+ * @brief AT^SPIDEINIT - Deinitialize SPI1
+ * Usage: AT^SPIDEINIT
+ */
+static uint32_t custom_spi_deinit_test(uint8_t *para, uint32_t paraLen, char *strCommonCmd)
+{
+    UNUSED(para);
+    UNUSED(paraLen);
+    UNUSED(strCommonCmd);
+    
+    wstp_print("AT^SPIDEINIT: Deinitializing SPI1...\n");
+    custom_spi_deinit();
+    wstp_print("AT^SPIDEINIT: SPI1 deinitialized successfully\n");
+    
+    return ERRCODE_SUCC;
+}
+
 static const at_cmd_table_t g_custom_utils_cmd[] = {
     { (char *)"AT^CUSTOM_SN",      custom_utils_setsn, (char *)"123456789ABCDEF2345678" },
     { (char *)"AT^CUSTOM_SN_REQ",  custom_utils_getsn, (char *)" " },
@@ -2301,6 +2337,10 @@ static const at_cmd_table_t g_custom_utils_cmd[] = {
     { (char *)"AT^SPI1RXSTART",   custom_spi1_rx_start, (char *)" " },
     { (char *)"AT^SPI1RXSTOP",    custom_spi1_rx_stop, (char *)" " },
     { (char *)"AT^SPI1RXSTAT",    custom_spi1_rx_stat, (char *)" " },
+    
+    /* SPI1 init/deinit test AT commands */
+    { (char *)"AT^SPIINIT",       custom_spi_init_test, (char *)" " },
+    { (char *)"AT^SPIDEINIT",     custom_spi_deinit_test, (char *)" " },
 };