android HAL接口的編碼小結

定義一個module
struct xxx_module_t  {
     hw_module_t common;
     xxx,這裏的主要是一些在未open時就可以操作該模塊的ops接口,有時候可以不填充
}

struct xxx_mdoule HAL_MODULE_INFO_SYM =
{
     填充該結構體,以填充hw_module_t爲主
}//所有的hal模塊的名字都一樣,該結構在編譯時會轉爲一個hmi的描述符,供load對應的so時的使用。同時load的id要與hw_module_t相一致。

其中hw_module_t 的methods一般需要指定並實現一個open的接口,如下所示:
typedef struct hw_module_methods_t {
    /** Open a specific device */
    int (*open)(const struct hw_module_t* module, const char* id,
            struct hw_device_t** device);
} hw_module_methods_t;


一般在open後需要返回一個模塊需要用到的設備xxx_device_t接口,一般結構如下,需要注意的是多重封裝時,也需要確保hw_device_t 位於返回首地址即可:
typedef struct xxx_device_t {
     hw_device_t common;
     xxx各種可操作device的ops函數。
     
}
或則
class xxx_xxxx_t: public struct xxx_device_t{
     xxx_xxx_t();
}

在構造函數中xxx_xxxx_t()
{
     完成對xxx_device_t 的初始化包括common和各種framework層需要的ops
}

hw_device_t的結構體定義:
typedef struct hw_device_t {
 
    uint32_t tag;
    uint32_t version;
    struct hw_module_t* module;
    uint32_t reserved[12];
    int (*close)(struct hw_device_t* device);

} hw_device_t;

綜上所述,HAL是通過struct xxx_device_t這個結構體向上層提供接口的.

即:接口包含在struct xxx_device_t這個結構體內。

而具體執行是通過struct xxx_module_t HAL_MODULE_INFO_SYM這個結構體變量的函數列表成員下的open函數來返回給上層的.

附加:
之所以將HAL所有的模塊命名爲HAL_MODULE_INFO_SYM原因在於該名字會被替換爲一個宏名HMI,即最終編譯器對每一個模塊的CPP進行組合生產so庫時,內部是由一個HMI的符號表存在的。而這個符號表再load module時會首先進行dlsym的操作,其中明確規定要查找的符號入口爲“HMI”,這就要求當前模塊必須含有這個符號名。也就要求每一個HAL庫要確保自己的名字是HAL_MODULE_INFO_SYM因爲只有這個名字纔會被替換爲HMI後編譯進入SO文件中,從而被load出HMI的入口即hw_module_t.
發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章