1. 本次采用利爾達的CC3200模塊,CC3200主時鍾80M,內部沒有flash,必須外接SPI Flash。本次測試采用利爾達科技的CC3200的底板和模塊(左邊)。燒寫連接VCC, GND, RXD, TXD, SOP2, RST這6根線即可完成下載。串口下載的時候SOP2需要上拉,正常運行的時候SOP2留空。

2. 使用IAR工具打開工程,看下main代碼,其中VStartSimpleLinkSpawnTask這個函數搞不明白是什么?SimpleLink是TI注冊的一個商標,CC3200是CC3200SimpleLink™Wi-Fi
1 void main() 2 { 3 long lRetVal = -1; 4 // 板子初始化配置 5 BoardInit(); 6 // 引腳復用配置 7 PinMuxConfig(); 8 //初始化穿口 9 InitTerm(); 10 // 啟動SimpleLink Host 11 lRetVal = VStartSimpleLinkSpawnTask(SPAWN_TASK_PRIORITY); 12 if(lRetVal < 0) 13 { 14 ERR_PRINT(lRetVal); 15 LOOP_FOREVER(); 16 } 17 // 啟動 WlanAPMode 任務 18 lRetVal = osi_TaskCreate( WlanAPMode, \ 19 (const signed char*)"wireless LAN in AP mode", \ 20 OSI_STACK_SIZE, NULL, 1, NULL ); 21 if(lRetVal < 0) 22 { 23 ERR_PRINT(lRetVal); 24 LOOP_FOREVER(); 25 } 26 // 開始任務調度 27 osi_start(); 28 }
3. 深入第一個函數去看看做了什么,創建了一個隊列和一個任務,目前不知道這個任務是什么用途,其次2048的任務空間是從哪里分配的,作為棧的空間,任務切換的時候保存任務的當前環境變量。
1 OsiReturnVal_e VStartSimpleLinkSpawnTask(unsigned portBASE_TYPE uxPriority) 2 { 3 xSimpleLinkSpawnQueue = xQueueCreate( slQUEUE_SIZE, sizeof( tSimpleLinkSpawnMsg ) ); 4 if(0 == xSimpleLinkSpawnQueue) 5 { 6 return OSI_OPERATION_FAILED; 7 } 8 if(pdPASS == xTaskCreate( vSimpleLinkSpawnTask, ( portCHAR * ) "SLSPAWN",\ 9 (2048/sizeof( portSTACK_TYPE )), NULL, uxPriority, &xSimpleLinkSpawnTaskHndl )) 10 { 11 return OSI_OK; 12 } 13 return OSI_OPERATION_FAILED; 14 }
4. 延伸一個問題,任務里面的臨時變量和數據還有任務里面的malloc,是從任務創建時候分配的棧里面再分配的嗎?書上說是堆棧空間,malloc是從堆里分配的,2048/sizeof( portSTACK_TYPE )單位是字,4個字節,所以實際要乘以4的。
5. STM32有2個棧指針,MSP,PSP,一個是系統堆棧指針MSP,一個是任務堆棧指針PSP,任務堆棧用來做什么?保存局部變量,函數嵌套,任務切換的時候保存內核寄存器(保存在棧的高地址)和任務當前的狀態(局部變量保存在低地址)。堆棧大小應該怎么去計算。任務里面的局部變量是保存在任務的棧里面的。
6. 繼續看這個代碼,一直循環接收隊列,tSimpleLinkSpawnMsg Msg;這個應該是給wifi網絡處理器返回應用處理器的消息隊列。這個結構體有2個參數,一個函數和一個數據,都是通過隊列傳送的。
1 void vSimpleLinkSpawnTask(void *pvParameters) 2 { 3 tSimpleLinkSpawnMsg Msg; 4 portBASE_TYPE ret=pdFAIL; 5 for(;;) 6 { 7 ret = xQueueReceive( xSimpleLinkSpawnQueue, &Msg, portMAX_DELAY ); 8 if(ret == pdPASS) 9 { 10 Msg.pEntry(Msg.pValue); 11 } 12 } 13 }
7. 看下AP模式的設置代碼
void WlanAPMode( void *pvParameters ) { int iTestResult = 0; unsigned char ucDHCP; long lRetVal = -1; InitializeAppVariables(); //恢復成默認模式 lRetVal = ConfigureSimpleLinkToDefaultState(); if(lRetVal < 0) { if (DEVICE_NOT_IN_STATION_MODE == lRetVal) UART_PRINT("Failed to configure the device in its default state \n\r"); LOOP_FOREVER(); } UART_PRINT("Device is configured in default state \n\r"); //啟動網絡 lRetVal = sl_Start(NULL,NULL,NULL); if (lRetVal < 0) { UART_PRINT("Failed to start the device \n\r"); LOOP_FOREVER(); } UART_PRINT("Device started as STATION \n\r"); //配置成AP模式 if(lRetVal != ROLE_AP) { if(ConfigureMode(lRetVal) != ROLE_AP) { sl_Stop(SL_STOP_TIMEOUT); LOOP_FOREVER(); } } //AP模式下,是否獲取到自己的IP地址 while(!IS_IP_ACQUIRED(g_ulStatus)) { //looping till ip is acquired } unsigned char len = sizeof(SlNetCfgIpV4Args_t); SlNetCfgIpV4Args_t ipV4 = {0}; // 獲取網絡配置 lRetVal = sl_NetCfgGet(SL_IPV4_AP_P2P_GO_GET_INFO,&ucDHCP,&len, (unsigned char *)&ipV4); if (lRetVal < 0) { UART_PRINT("Failed to get network configuration \n\r"); LOOP_FOREVER(); } //等待STA設備連接,並給STA分配IP地址 while(!IS_IP_LEASED(g_ulStatus)) { } //和STA設備建立TCP連接 lRetVal = BsdTcpClient(PORT_NUM); if(lRetVal < 0) { UART_PRINT("TCP Client failed\n\r"); LOOP_FOREVER(); } while(1); }
查看下AP模式的設置函數
1 static int ConfigureMode(int iMode) 2 { 3 char pcSsidName[33] = "cc3200_tcptest"; 4 long lRetVal = -1; 5 6 //設置為AP模式 7 lRetVal = sl_WlanSetMode(ROLE_AP); 8 ASSERT_ON_ERROR(lRetVal); 9 //設置AP模式的SSID 10 lRetVal = sl_WlanSet(SL_WLAN_CFG_AP_ID, WLAN_AP_OPT_SSID, strlen(pcSsidName), 11 (unsigned char*)pcSsidName); 12 ASSERT_ON_ERROR(lRetVal); 13 14 UART_PRINT("Device is configured in AP mode\n\r"); 15 16 /* Restart Network processor */ 17 lRetVal = sl_Stop(SL_STOP_TIMEOUT); 18 19 // reset status bits 20 CLR_STATUS_BIT_ALL(g_ulStatus); 21 return sl_Start(NULL,NULL,NULL); 22 }
8. 這個工程包含了3個庫文件,其中simplelink.a比較特殊,在SDK中找個這個相關工程並打開。問題是sl_start究竟是啟動的什么?和wifi網絡處理器怎么通信的?
1 $PROJ_DIR$/../../../simplelink/ewarm/OS/Exe/simplelink.a 2 $PROJ_DIR$/../../../driverlib/ewarm/Release/Exe/driverlib.a 3 $PROJ_DIR$/../../../oslib/ewarm/free_rtos/Exe/free_rtos.a
9. 繼續下一步
1 _i16 sl_WlanSetMode(const _u8 mode) 2 { 3 _SlwlanSetModeMsg_u Msg; 4 Msg.Cmd.mode = mode; 5 VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlWlanSetModeCmdCtrl , &Msg, NULL)); 6 return (_i16)Msg.Rsp.status; 7 }
10. 研究下,應用處理器是怎么給wifi網絡處理器發數據的,不過以下可能有錯誤的
1 //以sl_WlanSet為例子,以下層層調用,最后通過SPI接口發出 2 第1步:sl_WlanSet 3 第2步:VERIFY_RET_OK(_SlDrvCmdOp((_SlCmdCtrl_t *)&_SlWlanSetModeCmdCtrl , &Msg, NULL)); 4 第3步:_SlDrvMsgWrite 5 第4步:NWP_IF_WRITE_CHECK 6 第5步:spi_Write 7 第6步:spi_Write_CPU
11. 用uniflash燒寫測試一下,不過下次要花時間研究下CC3200的內存分配了,涉及到串口升級,OTA升級等

12. 需要在電腦上建立一個tcp server測試一下,以前測試CC3200的TCP傳輸速度只有100KB每秒不知道原因,有機會要再次測試一下。
