? Zstack協(xié)議棧依靠協(xié)議棧內(nèi)部的OS(即OSAL)才能運行起來,OSAL提供的服務和管理包括:信息管理、任務同步、時間管理、中斷管理、任務管理、內(nèi)存管理、電源管理以及非易失存儲管理。
1. 信息管理API
? 信息管理API為任務和處理單元之間的信息交換提供了一種具有不同處理環(huán)境的機制(例如,在一個控制循環(huán)中調(diào)用中斷服務常規(guī)程序或函數(shù))。這個API中國的函數(shù)可以使任務分配或回收信息緩沖區(qū),給其他任務發(fā)送任務信息以及接受回復信息。
1.1 osal_msg_allocate()
? 這個函數(shù)被一個任務調(diào)用去分配一個信息緩沖,這個任務/函數(shù)將填充這個信息并且調(diào)用osal_msg_send()發(fā)送消息到另一個任務中。函數(shù)原型如下:
????uint8?*osal_msg_allocate(?uint16?len?);
? 參數(shù)描述:
??? len是信息的長度。
? 返回值:返回值是指向一個信息分配的緩沖區(qū)的指針。一個空值的返回表明信息分配操作失敗。
1.2 osal_msg_deallocate()
? 這個函數(shù)用來回收一個信息緩沖區(qū),在完成處理一個接受信息后這個函數(shù)被一個任務(或處理機單元)低啊用。函數(shù)原型如下:
????uint8?osal_msg_deallocate(byte?*msg_ptr);
? 參數(shù)描述:
msg_ptr是指向必須回收的信息緩沖的指針。
? 返回值:返回值指示了操作的結果。
ZSUCCESS:分配成功;
INVALID_MSG_POINTER:無效的信息指針;
MSG_BUFFER_NOT_AVAIL:緩沖區(qū)隊列。
1.3 osal_msg_send()
? 這個函數(shù)的功能是被一個任務調(diào)用,給另一個任務或者處理單元發(fā)送命令或數(shù)據(jù)信息。函數(shù)原型如下:
????uint8?osal_msg_send(?byte?destination_task?,?byte?*msg_ptr);
? 參數(shù)描述:
destination_task是接收信息任務的ID。
msg_ptr是指向必須包含信息的緩沖區(qū)的指針。msg_ptr必須執(zhí)行osal_msg_allocate()分配的一個有效緩沖區(qū)。
? 返回值:返回值是一個字節(jié),表明操作的結果。
ZSUCCESS:分配成功;
INVALID_MSG_POINTER:無效的信息指針;
INVALID_TASK:destination_task是無效的。
1.4 osal_msg_receive()
? 此函數(shù)被一個任務調(diào)用來檢索一條已經(jīng)收到的命令信息。調(diào)用osal_msg_receive()處理信息后,必須回收信息緩沖區(qū)。函數(shù)原型如下:
????uint8?*osal_msg_receive(?byte?task_id);
? 參數(shù)描述:task_id是調(diào)用任務(信息指定的)的標識符。
? 返回值:返回值是一個指向包含該信息的緩沖區(qū)的指針,如果沒有已接收的信息,返回值為空(NULL)。
2. 任務同步API
? 任務同步API使得任務等待事件發(fā)送,并在等待期間返回控制。這個API中的函數(shù)可以用來為一個任務設置事件,無論設置了什么事件都通知任務。
? 通過osal_set_event()這個函數(shù)調(diào)用,為一個任務設置事件的標志。其函數(shù)原型如下:
????uint8?osal_set_event(?byte?task_id?,?UINT16?event_flag?);
? 參數(shù)描述:
task_id是設置事件的任務的標識符。
event_flag是兩個字節(jié)的位圖且每個位詳述了一個事件。這僅有一個系統(tǒng)事件(SYS_EVENT_MSG),其余事件/位都是通過接收任務來規(guī)定的。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
INVALID_TASK:無效事件;
3. 定時器管理API
? 定時器管理API使Zstack內(nèi)部的任務和外部的應用層任務都可以使用定時器。API提供了啟動和停止一個定時器的功能,這個定時器可設定遞增的一毫秒。
3.1 osal_start_timer()
? 啟動一個定時器時調(diào)用此函數(shù)。當定時器終止時,給定的事件位將設置。這個事件通過osal_start_timer()函數(shù)調(diào)用,將在任務中設置。函數(shù)原型如下:
????uint8?osal_start_timer(?UINT16?event_id?,?UINT16?timeout_value);
? 參數(shù)描述:
event_id是用戶確定事件的ID。當定時器終止時,該事件將被觸發(fā)。
timeout_value指定時器事件設置之前的時長(以毫秒為單位)。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
NO_TIMER_AVAILABLE:沒有能夠啟動定時器;
3.2 osal_start_timerEx() ? 類似于osal_start_timer(),增加了taskID參數(shù)。允許訪問這個調(diào)用程序為另一個任務設置定時器。函數(shù)原型如下:
????uint8?osal_start_timerEx(?byte?taskID?,?UINT16?event_id?,?UINT16?timerout_value?);
? 參數(shù)描述:
taskID是定時器終止時,獲取該事件任務的ID。
event_id是用戶確定事件的ID。當定時器終止時,該事件將被觸發(fā)。
timeout_value指定時器事件設置之前的時長(以毫秒為單位)。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
NO_TIMER_AVAILABLE:沒有能夠啟動定時器;
3.3 osal_stop_timer()
??? 此函數(shù)用來停止一個已啟動的定時器,如果成功,函數(shù)將取消定時器并阻止設置調(diào)用程序中與定時器有關的時間。使用osal_stop_timer()函數(shù),意味著調(diào)用osal_stop_timer()的任務中定時器正在運行。函數(shù)原型如下:
????uint8?osal_stop_timer(?UINT16?event_id?);
? 參數(shù)描述:
event_id是要停止的計時器的標識符。
? 返回值:返回值指示操作的結果。
ZSUCCESS:關閉定時器成功;
INVALID_EVENT_ID:無效事件;
3.3 osal_stop_timerEx() ? 此函數(shù)功能是在不同的任務中中止定時器的,與osal_stop_timer()函數(shù)類似,只是指明了任務ID。函數(shù)原型如下:
????uint8?osal_stop_timerEx(?byte?task_id?,?UINT16?event_id?);
? 參數(shù)描述:
task_id:停止定時器所在的任務ID。
event_id:要停止的計時器的標識符。
? 返回值:返回值指示操作的結果。
ZSUCCESS:關閉定時器成功;
INVALID_EVENT_ID:無效事件;
3.5 osal_GetSystemClock()
? 此函數(shù)功能為讀取系統(tǒng)時鐘。函數(shù)原型如下:
????uint8?osal_GetSystemClock(?void?);
? 返回值為以毫秒為單位的系統(tǒng)時鐘。
4. 中斷管理API
? 中斷管理API可以使一個任務與外部中斷互相交流。API中的函數(shù)允許和每個中斷去聯(lián)絡一個具體的服務流程。中斷可以啟用或禁用,在服務例程內(nèi)部,可以為其他任務設置事件。
4.1 osal_int_enable()
? 此函數(shù)的功能是啟用一個中斷,中斷一旦啟用將調(diào)用與該中斷相聯(lián)系的服務例程。函數(shù)原型如下:
????uint8?osal_int_enable(?byte?interrupt_id?);
? 參數(shù)描述:
interrupt_id:指明要啟用的中斷。
? 返回值:返回值指示操作的結果。
ZSUCCESS:開啟中斷成功;
INVALID_INTERRUPT_ID:無效中斷;
4.2 osal_int_disable()
? 此函數(shù)的功能是禁用一個中斷,當禁用一個中斷時,與該中斷相聯(lián)系的服務例程將不被調(diào)用。函數(shù)原型如下:
????uint8?osal_int_enable(?byte?interrupt_id?);
? 參數(shù)描述:
interrupt_id:指明要禁用的中斷。
? 返回值:返回值指示操作的結果。
ZSUCCESS:關閉中斷成功;
INVALID_INTERRUPT_ID:無效中斷;
5. 任務管理API
? 在OSAL系統(tǒng)中,API常用語添加和管理任務。每個任務由初始化函數(shù)和時間處理函數(shù)組成。
5.1 osal_init_system()
? 此函數(shù)功能為初始化OSAL系統(tǒng)。在使用任何其他OSAL函數(shù)之前必須先調(diào)用此函數(shù)啟動OSAL系統(tǒng)。函數(shù)原型為:
????uint8?osal_init_system(?void?);
? 參數(shù)描述:
無。
? 返回值:返回值指示操作的結果。
ZSUCCESS:初始OSAL系統(tǒng)成功;
5.2 osal_start_system()
? 此函數(shù)是任務系統(tǒng)中的主循環(huán)函數(shù)。它將仔細檢查所有的任務事件,并且為含有該事件的任務調(diào)用任務事件處理函數(shù)。如果有特定任務事件,這個函數(shù)將為該任務調(diào)用事件處理例程來處理事件。相應任務的事件處理例程一次處理一個事件。一個事件被處理后,剩余事件將等待下一次循環(huán)。如果沒有時間,這個函數(shù)時處理器程序處于睡眠模式。函數(shù)原型為:
????uint8?osal_start_system(?void?);
? 參數(shù)描述:
無。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
6. 內(nèi)存管理API
? 內(nèi)存管理API代表一個簡單的內(nèi)存分配系統(tǒng)。這些函數(shù)允許動態(tài)存儲內(nèi)存分配。
6.1 osal_mem_alloc()
? 此函數(shù)是一個內(nèi)存分配函數(shù),如果分配內(nèi)存成功,返回一個指向緩沖區(qū)的指針。函數(shù)原型如下:
????void?*osal_mem_alloc(?uint16?size?);
? 參數(shù)描述:
size:要求的緩沖區(qū)字節(jié)數(shù)值。
? 返回值:
指向新分配的緩沖區(qū)的空指針(應指向目的緩沖類型)。
如果沒有足夠的內(nèi)存可分配,將返回NULL指針。
6.2 osal_mem_free()
? 此函數(shù)用于釋放存儲空間,便于被釋放的存儲空間的再次使用,僅在內(nèi)存已經(jīng)通過調(diào)用osal_mem_alloc()被分配后才有效。函數(shù)原型如下:
????void?osal_mem_free(?void?*ptr?);
參數(shù)描述:
ptr:指向要釋放的緩沖區(qū)的指針。這個緩沖區(qū)必須在之前調(diào)用osal_mem_alloc()已被分配,為以前分配的空間。
? 返回值:
???????????? 無。
7. 電源管理API
? 當安全關閉接收器或外部硬件時,電源管理API為應用程序或任務提供了告知OSAL的方法,使處理器轉(zhuǎn)入睡眠狀態(tài)。
? 電源管理API有2個函數(shù):osal_pwrmgr_device()和osal_pwrmgr_task_state()。第一個函數(shù)時設置設備的模式;第二個為電源狀態(tài)管理。
7.1 osal_pwrmgr_device()
? 當升高電源或需要改變電源時(例如:電池支持的協(xié)調(diào)器),這個函數(shù)應有中心控制實體(比如ZDO)調(diào)用。函數(shù)原型如下:
????void?osal_pwrmgr_device(?byte?pwrmgr_device);
? 參數(shù)描述:
pwrmgr_device:改變和設置電源的節(jié)省模式。
PWRMGR_ALWAYS_ON:沒有省電模式,設備可能使用主電源供電。
PWRMGR_BATTERY:打開省電模式。
? 返回值:
???????????? 無。
7.2 osal_pwrmgr_task_state()
? 每個任務都將調(diào)用此函數(shù)。此函數(shù)的功能是用來表決是否需要OSAL電源保護或推遲電源保護。當一個任務被創(chuàng)建時,默認情況下電源狀態(tài)設置為保護模式。如果該任務一直想保護電源,就不必調(diào)用該函數(shù)。函數(shù)原型如下:
????void?osal_pwrmgr_task_state(?bytetask_id?,?byte?state);
? 參數(shù)描述:
state:改變一個任務的電源狀態(tài)。
PWRMGR_CONSERVE:打開省電模式,所有事件必須允許。事件初始化時,此狀態(tài)位默認狀態(tài)。
PWRMGR_HOLD:關閉省電模式。
? 返回值:
???????????? ZSUCCESS:成功。
INVALID_TASK:無效事件。
8.非易失性存儲管理API
? 非易失性存儲器API為應用程序提供了一種吧信息永久保存到設備內(nèi)存的方法。它還能用于把Zigbee規(guī)范要求的某些項目永久保存到協(xié)議棧。NV函數(shù)的功能是讀寫任意數(shù)據(jù)類型的用戶自定義項目,比如結構體和數(shù)組。用戶能通過設置合適的偏移和長度來讀寫一個整體的項目或元素。API獨立于NV存儲介質(zhì),并且能用于實現(xiàn)閃存或EEPROM。
? 每個易失性的項目都僅有一個ID,當一些ID由?;蚱脚_保留或運用時,應用程序中有特定的一系列ID值。加入應用程序創(chuàng)建自己的易失性項目,它必須從應用范圍的值內(nèi)選擇一個標識符。如表所示:
值 使用者 0x0000 保留 0x0001-0x0020 操作系統(tǒng)抽象層 0x0021-0x0040 網(wǎng)絡層 0x0041-0x0060 應用支持子層 0x0061-0x0080 安全 0x0081-0x00A0 Zigbee設備對象 0x00A1-0x0200 保留 0x0201-0x0FFF 應用程序 0x1000-0xFFFF 保留 ? 運用API時需要注意以下幾個方面:
有一些模塊化調(diào)用函數(shù),操作系統(tǒng)可能需要較短的時間來完成(例如幾毫秒的時間),尤其是對NV寫入操作。
盡量不要頻繁地執(zhí)行NV寫入操作。
結構體中一個或多個NV項目改變,尤其是從一個Zstack版本升級至另一個版本時,必須擦除和重新初始化NV內(nèi)存。否則,修改NV項目的讀寫操作將失敗,或產(chǎn)生錯誤結果。
8.1 osal_nv_item_init()
? 此函數(shù)用于初始化NV項目,用于檢查存在的NV的項目。如果不存在,它將通過這個函數(shù)去創(chuàng)建或初始化。假如存在,再調(diào)用osal_nv_read()或osal_nv_write()之前,每個項目都應調(diào)用此函數(shù)。函數(shù)原型如下:
????uint8?osal_nv_item_init(?uint16?id?,?uint16?len?,?void?*buf);
? 參數(shù)描述:
id:用戶自定義項的ID。
len:項目字節(jié)長度。
*buf:初始化數(shù)據(jù)指針。如沒初始化數(shù)據(jù),則設置為空。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
NV_ITEM_UNINIT:對象沒初始化;
NV_OPER_FAILED:操作失敗。
8.2 osal_nv_read()
? 此函數(shù)用于從NV中讀出數(shù)據(jù),用于從NV中帶用偏移的索引指向的項目中讀出整個項目或一個元素,讀出數(shù)據(jù)復制到*buf中。函數(shù)原型如下:
????uint8?osal_nv_read(?uint16?id?,?uint16?offset?,uint16?len?,?void?*buf);
? 參數(shù)描述:
id:用戶自定義項的ID。
offset:以字節(jié)為單位到項目的存儲偏移量
len:項目字節(jié)長度。
*buf:數(shù)據(jù)讀取到緩沖區(qū)。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
NV_ITEM_UNINIT:對象沒初始化;
NV_OPER_FAILED:操作失敗。
8.3 osal_nv_write()
? 此函數(shù)用于寫入數(shù)據(jù)到NV中,用于從NV中帶用偏移的索引指向的項目中寫入整到整個NV項目中。函數(shù)原型如下:
????uint8?osal_nv_write(?uint16?id?,?uint16?offset?,uint16?len?,?void?*buf);
? 參數(shù)描述:
id:用戶自定義項的ID。
offset:以字節(jié)為單位到項目的存儲偏移量
len:項目字節(jié)長度。
*buf:數(shù)據(jù)寫入到緩沖區(qū)。
? 返回值:返回值指示操作的結果。
ZSUCCESS:成功;
NV_ITEM_UNINIT:對象沒初始化;
NV_OPER_FAILED:操作失敗。
8.4 osal_offsetof()
? 此函數(shù)用于計算一個結構體內(nèi)元素的偏移量,以字節(jié)為單位。用它來計算NV API函數(shù)使用的參數(shù)的偏移量。函數(shù)原型如下:
????uint8?osal_offsetof(?type?,?member);
? 參數(shù)描述:
????????????? type:結構體類型。
???????????? member:結構體成員
? 返回值:
??????????? 無。