3 onps棧移植說明——添加網卡( 三 )

其中buddy_alloc()函數在功能上與c語言的標準庫函數malloc()完全相同,都是動態分配一塊指定大小的內存給調用者使用,使用完畢后再由用戶通過buddy_free()函數釋放 。這兩個函數由協議棧的內存管理(mmu)模塊提供 。ethernet_put_packet()函數需要重點解釋一下 。這個函數由協議棧提供 。它完成的工作非常重要,它在網卡接收函數與協議棧以太網接收線程thread_ethernet_ii_recv()之間搭建了一個數據流通的“橋” 。接收函數收到報文后按照協議棧要求,將報文封裝成ST_SLINKEDLIST_NODE類型的鏈表節點,然后傳遞給ethernet_put_packet()函數 。該函數將立即把傳遞過來的節點掛載到由協議棧管理的以太網接收鏈表的尾部,然后投遞一個“有新報文到達”的信號量 。前文提到的以太網接收線程thread_ethernet_ii_recv()會輪詢等待這個信號量 。一旦信號到達 , 接收線程將立即讀取鏈表并取出報文交給協議棧處理 。
至此,ethernet網卡相關的移植工作完成 。
4.2 ppp撥號網卡在Linux系統,2g/4g/5g模塊作為一個通訊終端,驅動層會把它當作一個tty設備來看待 。Linux下ppp棧也是圍繞著操作一個標準的tty設備來實現底層通訊邏輯的 。至于如何操作這個ppp撥號終端進行實際的數據收發tty層并不關心 。所以,協議棧完全借鑒了這個成功的設計思想,在底層驅動與撥號終端之間增加了一個tty層,將具體的設備操作與上層的業務邏輯進行了剝離 。ppp撥號網卡的的移植工作其實就是完成tty層到底層驅動的封裝工作 。協議棧利用句柄來唯一的標識一個tty設備 。在os_datatype.h文件中定義了這個句柄類型:
#if SUPPORT_PPPtypedef INT HTTY;//* tty終端句柄#define INVALID_HTTY -1 //* 無效的tty終端句柄#endif這個句柄類型非常重要,所有與tty操作相關的函數都要用到這個句柄類型 。tty層要完成的驅動封裝工作涉及的函數原型定義依然是在os_adapter.h文件中:
#if SUPPORT_PPP//* 打開 tty 設備 , 返回 tty 設備句柄,參數 pszTTYName 指定要打開的 tty 設備的名稱OS_ADAPTER_EXT HTTY os_open_tty(const CHAR *pszTTYName);//* 關閉 tty 設備,參數 hTTY 為要關閉的 tty 設備的句柄OS_ADAPTER_EXT void os_close_tty(HTTY hTTY);//* 向 hTTY 指定的 tty 設備發送數據,返回實際發送的數據長度//*hTTY:設備句柄//*pubData:指針 , 指向要發送的數據的指針//* nDataLen:要發送的數據長度//* 返回值為實際發送的字節數OS_ADAPTER_EXT INT os_tty_send(HTTY hTTY, UCHAR *pubData, INT nDataLen);//* 從參數 hTTY 指定的 tty 設備等待接收數據,阻塞型//*hTTY:設備句柄//*pubRcvBuf:指針,指向數據接收緩沖區的指針,用于保存收到的數據//* nRcvBufLen:接收緩沖區的長度//*nWaitSecs:等待的時長,單位:秒 。0 一直等待;直至收到數據或報錯 , 大于 0 , 等待指定秒數;小于 0,不支持//* 返回值為實際收到的數據長度,單位:字節OS_ADAPTER_EXT INT os_tty_recv(HTTY hTTY, UCHAR *pubRcvBuf, INT nRcvBufLen, INT nWaitSecs); //* 復位 tty 設備 , 這個函數名稱體現了2g/4g/5g模塊作為tty設備的特殊性,其功能從本質上看就是一個 modem,modem 設備出現通訊//* 故障時 , 最好的修復故障的方式就是直接復位,復位可以修復絕大部分的因軟件問題產生的故障OS_ADAPTER_EXT void os_modem_reset(HTTY hTTY);#endif依據上述函數的原型定義及功能說明 , 我們在os_adapter.c文件編碼實現它們,相關偽代碼實現如下:
#if SUPPORT_PPPHTTY os_open_tty(const CHAR *pszTTYName){//* 如果你的系統存在多個ppp撥號終端,那么pszTTYName參數用于區分打開哪個串口//* 在這里添加串口打開代碼將連接撥號終端的串口打開…………//* 如果目標系統只有一個撥號終端,那么這里返回的tty句柄x值為0 , 如果目標系統存在多個模塊,這里需要你根據參數//* pszTTYName指定的名稱來區分是哪個設備,并據此返回不同的tty句柄,句柄值x應從0開始自增 , 步長為1return x;}void os_close_tty(HTTY hTTY){//* 在這里添加串口關閉代碼,關閉哪個串口的依據是tty設備句柄hTTY……}INT os_tty_send(HTTY hTTY, UCHAR *pubData, INT nDataLen){//* 在這里添加數據發送代碼,其實就是調用對應的串口驅動函數發送數據到撥號終端 , 如果存在多個tty設備,請依據參數hTTY來//* 確定需要調用哪個串口驅動函數發送數據,返回值為實際發送的字節數……}INT os_tty_recv(HTTY hTTY, UCHAR *pubRcvBuf, INT nRcvBufLen, INT nWaitSecs){//* 同上 , 在這里添加數據讀取代碼,其實就是調用對應的串口驅動函數從撥號終端讀取數據 , 如果存在多個tty設備,請依據參數hTTY來//* 確定需要調用哪個串口驅動函數讀取數據,返回值為實際讀取到的字節數……}void os_modem_reset(HTTY hTTY){//* 在這里添加撥號終端的復位代碼,如果你的目標板不支持軟件復位模塊,可以省略這一步//* 復位模塊的目的是解決絕大部分的因軟件問題產生的故障……}#endif

推薦閱讀