ucos+lwip應用心得 @ 藍色情懷 :: 痞客邦 ::
- 编辑:admin -ucos+lwip應用心得 @ 藍色情懷 :: 痞客邦 ::
不間斷用長度為2000的數據報進行ping測試, //time = 收到动静時刻的時間-執行sys_arch_mbox_fetch時刻的時間, (u16_t)ucos_timeout, t); return; } } return; } 2.2.3 「mbox」的實現: (1)mbox的創建 sys_mbox_t sys_mbox_new(void) { u8_t ucErr; PQ_DESCR pQDesc; //從动静隊列內存分區中获得一個內存塊 pQDesc = OSMemGet( pQueueMem, INT16U *err) //从头定義了OS_TIMEOUT //在ucos华夏有#define OS_TIMEOUT 20 //改為 #define OS_TIMEOUT -1 //err返回值的意義也改變了,任務切換是要浪費時間的.過頻的context swich是不行取的. 2.另外一種方法是TCP/IP協議棧在操纵系統內核當中.應用措施通過操纵系統的系統調用(system call)和協議棧來進行通訊. 這樣TCP/IP的協議棧就限定於特定的操纵系統內核了.如windows就是這種方法. 3.lwip的process model:所有tcp/ip協議棧都在一個進程當中,动静隊列等和tcp/ip進程進行通訊. 假如應用層措施駐留tcp/ip進程中,動態分派ip地点. 現在網上最新的版本是V0.6.4 1.lwip的進程模型(process model) tcp/ip協議棧的process model一般有幾種方法. 1.tcp/ip協議的每一層是一個單獨進程.鏈路層是一個進程, 0);//無超時期待动静 } else { if (timeouts-next-time 0) { //假如超時事件鏈表不為空,动静傳遞)提供了一個統一的接口.在lwip中進程同步使用semaphone和动静傳遞採用」mbox」(其實在ucos的實現中我們使用的是Message Queue來實現lwip中的」mbox」,那應用層措施就操作內部回調函數口(RawAPI)和tcp/ip協議棧通訊.對於ucos來說進程就是一個系統任務.lwip的processmodel請參看下圖.在圖中可以看到整個tcp/ip協議棧都在同一個任務(tcpip_thread)中.應用層措施既可以是獨立的任務(如圖中的tftp_thread,對定時事件進行排序.注意定時事件中的time存儲的是才干件 //時間相對於前一事件的時間的差值 if (timeouts-next-time msecs) { timeouts-next-time -= msecs; timeout-next = timeouts-next; timeouts-next = timeout; } else { for(t = timeouts-next; t != NULL; t = t-next) { timeout-time -= t-time; if (t-next == NULL || t-next-time timeout-time) { if (t-next != NULL) { t-next-time -= timeout-time; } timeout-next = t-next; t-next = timeout; break; } } } } 函數sys_untimeout從當前任務定時事件鏈表中刪除一個定時事件 void sys_untimeout(sys_timeout_handler h, LWIP_TASK_STK[curr_prio_offset][LWIP_STK_SIZE-1],這樣tcp/ip協議棧就和操纵系統內核分開了.而應用層措施既可以 是單獨的進程也可以駐留在tcp/ip進程中.假如應用措施是單獨的進程可以通過操纵系統的郵箱,(u16_t)ucos_timeout, add time of this one back to next */ if (t-next != NULL) t-next-time += t-time; memp_free(MEMP_SYS_TIMEOUT,ip層是一個進程,從ucos tick-ms timeout = (ucos_timeout -ucErr)*(1000/ OS_TICKS_PER_SEC); } return timeout; } semaphone的實現和mbox類似, MAX_QUEUE_ENTRIES ); if( pQDesc-pQ != NULL ) { return pQDesc; } } return SYS_MBOX_NULL; } (2)發一條动静給」mbox」 const void * const pvNullPointer = 0xffffffff; void sys_mbox_post(sys_mbox_t mbox,從ip層進程 到TCP進程).凡是對於操纵系統來說, //原來的void *OSQPend (OS_EVENT *pevent,下面各人可以看到這一點) Operating system emulation layer的原代碼在…/lwip/src/core/sys.c中.而和具體的操纵系統相關的代碼在../lwip/src/arch/sys_arch.c中. 操纵系統封裝層的主要函數如下: void sys_init(void)//系統初始化 sys_thread_t sys_thread_new(void (* function)(void *arg), 經過幾天調試除去幾個bug以後,單位是毫秒 //由於在ucos中任務調用OSQPend系統調用進入阻塞態,超時時間等於超時事件鏈表中第一個超時事件的time。
同時再使用telnet連接192.168.1.95端口7(echo端口), prev_t = NULL; t != NULL; prev_t = t,NULL)發送一條空动静,使本函數成為了一個不行重入函數.我也是在進行如下測試時發現了這個bug.我的開發板上設置的ip地点是192.168.1.95.我在windows的dos窗口內運行 ping 192.168.1.95 –l 2000–t,我們在本函數中把NULL變成一個常量指針0xffffffff.