HAL层概述

名称: HAL, Hardware Abstracting Layer,中文名字:硬件抽象层。

作用:对Linux内核驱动程序的封装,向上提供接口,屏蔽低层的实现细节。向上衔接Android Runtime和Framework,向下衔接驱动程序

产生原因:利益,竞争

Android代码结构中,HAL层的内容主要集中在Hardware目录中,结合之前讲解Camera模块的时候提到的

system/lib/hw/camera.$(TARGET_BOARD_PLATFORM).so

HAL层的内容集成在动态库中,然后CameraService通过这个So访问其中的内容。

如何访问?

void CameraService::onFirstRef()

hw_get_module(CAMERA_HARDWARE_MODULE_ID, (const hw_module_t **)&rawModule)

每一个独立的HAL层的so,有一个与其对应的Id

#define CAMERA_HARDWARE_MODULE_ID “camera”

定义在hardware/libhardware/include/hardware/camera_common.h

又或者

system/lib/hw/audio.primary.$(TARGET_BOARD_PLATFORM)

frameworks/av/services/audioflinger/AudioFlinger.cpp

rc = hw_get_module_by_class(AUDIO_HARDWARE_MODULE_ID, if_name, &mod);

#define AUDIO_HARDWARE_MODULE_ID “audio”

定义在

hardware/libhardware/include/hardware/audio.h

当然这里只是举个例子,Audio需要加载的模块不止这一个。

基本上每一个模块对应一个So,命名方式也是比较相似,xxx.$(TARGET_BOARD_PLATFORM),存放路径

system/lib/hw

system/lib64/hw

hw_get_module ->hw_get_module_by_class

定义在hardware/libhardware/include/hardware/hardware.h

实现在hardware/libhardware/hardware.c

int hw_get_module(const char *id, const struct hw_module_t **module)
{
return hw_get_module_by_class(id, NULL, module);
}
……
int hw_get_module_by_class(const char *class_id, const char *inst,
const struct hw_module_t **module)
{
int i = 0;
char prop[PATH_MAX] = {0};
char path[PATH_MAX] = {0};
char name[PATH_MAX] = {0};
char prop_name[PATH_MAX] = {0}; if (inst)//如果inst不为空,name= class_id.inst
snprintf(name, PATH_MAX, "%s.%s", class_id, inst);
else //如果为空的话,name = class_id
strlcpy(name, class_id, PATH_MAX); //判断是否有配置项定义了对应的Hal层
snprintf(prop_name, sizeof(prop_name), "ro.hardware.%s", name);
if (property_get(prop_name, prop, NULL) > 0) {
if (hw_module_exists(path, sizeof(path), name, prop) == 0) {//若存在则跳转
goto found;
}
} //循环查找ro.hardware,ro.product.board,ro.board.platform,ro.arch
for (i=0 ; i<HAL_VARIANT_KEYS_COUNT; i++) {
if (property_get(variant_keys[i], prop, NULL) == 0) {
continue;
}
if (hw_module_exists(path, sizeof(path), name, prop) == 0) {
goto found;
}
} /* Nothing found, try the default */
if (hw_module_exists(path, sizeof(path), name, "default") == 0) {
goto found;
} return -ENOENT; found:
/* load the module, if this fails, we're doomed, and we should not try
* to load a different variant. */
return load(class_id, path, module);
}

再看看hw_module_exists这个方法

static int hw_module_exists(char *path, size_t path_len, const char *name,
const char *subname)
{
//拼凑HAL so库的名字 /vendor/lib/hw/name.subname.so或者/vendor/lib64/hw/name.subname.so
snprintf(path, path_len, "%s/%s.%s.so",
HAL_LIBRARY_PATH2, name, subname);
if (access(path, R_OK) == 0)
return 0;
//拼凑HAL so库的名字 /system/lib/hw/name.subname.so或者/system/lib64/hw/name.subname.so
snprintf(path, path_len, "%s/%s.%s.so",
HAL_LIBRARY_PATH1, name, subname);
if (access(path, R_OK) == 0)
return 0; return -ENOENT;
}

以audio其中的一个so为例,在源码中找一个芯片平台高通msm8974

system/lib/hw/audio.primary.msm8974.so

顺着以上的代码很好理解,当然这个msm8974必然是可以用过循环的那几个配置项其中的一个获取,否则就是

system/lib/hw/audio.promary.default.so

如何加载

以上代码跳转到found之后

return load(class_id, path, module);

static int load(const char *id,
const char *path,
const struct hw_module_t **pHmi)
{
…… //打开so,获取句柄
handle = dlopen(path, RTLD_NOW);
…… /* Get the address of the struct hal_module_info. */
//获取地址空间的入口
const char *sym = HAL_MODULE_INFO_SYM_AS_STR;
hmi = (struct hw_module_t *)dlsym(handle, sym);
……
…… hmi->dso = handle;
……
*pHmi = hmi; //赋值给传入参数
……
}

最后上层拿到的就是hw_module_t *

然后通过这个入口操作库中的内容,并且每一个HAL模块在定义自己的结构的时候也是需要按照一定的规范来执行。这个留着明天再写吧……

<Android HAL 之路> HAL 简介的更多相关文章

  1. 【Android】Sensor框架HAL层解读

    Android sensor构建 Android4.1 系统内置对传感器的支持达13种,他们分别是:加速度传感器(accelerometer).磁力传感器(magnetic field).方向传感器( ...

  2. Android 11(R) Power HAL AIDL简析 -- 基本接口

    Android 11(R) Power HAL AIDL将分三篇文章来介绍: Android 11(R) Power HAL AIDL简析 -- 基本接口 Android 11(R) Power HA ...

  3. <Android Framework 之路>Android5.1 Camera Framework(一)

    Android5.0 Camera Framework 简介 CameraService启动 CameraService是在MediaServer启动过程中进行的 main_mediaserver.c ...

  4. Android进阶之路(2)-详解MVP

    ### MVP简介 >MVP 全称:Model-View-Presenter :MVP 是从经典的模式MVC演变而来,它们的基本思想有相通的[地方](https://baike.baidu.co ...

  5. Android高薪之路-Android程序员面试宝典

    Android高薪之路-Android程序员面试宝典

  6. Android学习之路——简易版微信为例(一)

    这是“Android学习之路”系列文章的开篇,可能会让大家有些失望——这篇文章中我们不介绍简易版微信的实现(不过不是标题党哦,我会在后续博文中一步步实现这个应用程序的).这里主要是和广大园友们聊聊一个 ...

  7. 小猪的Android入门之路 Day 3 - part 3

    小猪的Android入门之路 Day 3 - part 3 各种UI组件的学习 Part 3 本节引言: 在前面两个部分中我们对Android中一些比較经常使用的基本组件进行了一个了解, part 1 ...

  8. 小猪的Android入门之路 Day 7 part 2

    小猪的Android入门之路 Day 7 part 2 Android的数据存储与訪问之--SharedPreferences(保存偏好參数) ---转载请注明出处:coder-pig 本节引言: 在 ...

  9. 小猪的Android入门之路 day 1

    小猪的Android入门之路 Day 1 Android相关背景与开发环境的搭建 ------转载请注明出处:coder-pig 本节引言: 随着社会经济的发展,移动互联网的越来越热,手机APP开发显 ...

随机推荐

  1. c# namespace不能和class的name 相同

    比如namespace A, 内部Class A, 那么调用class A的方法只能通过A.A.XXX来访问. 或者说实例化一个class A,  A a = new A(); // compile ...

  2. JSP的优势 和劣势 与php的比较

    一 jsp的 优势 与劣势 由于JSP页面的内置脚本语言是基于Java编程语言的,而且所有的JSP页面都被编译成为Java Servlet,JSP页面就具有Java技术的所有好处,包括健壮的存储管理和 ...

  3. vmware ubuntu14.04 忘记密码

    重置root密码 启动系统,一直点击esc键盘,出现如下界面,选择Advanced options for Ubuntu 按回车键确认: 选择recovery mode,按 e : 到 linux / ...

  4. jquery中attr() & prop() 的区别与其实现方法

    $(function(){ $('#check').attr('checked'); // undefind ???一头雾水 }) 在jquery中 attr 本来就是用来设置或者获取属性的,可是上面 ...

  5. vmware 虚拟网卡配置

    VMware虚拟机进阶:[1]网卡配置 1. 可以在下面这个图中看到几种网络设置模式,一直以来我们都喜欢用桥接模式和NAT模式,因为这两种模式是最符合一般人上网设置的模式,下面我们就一种种介绍个大家 ...

  6. Jsoncpp写“鱘”的json数据,报错。

    最近在用Json::FastWriter生成json数据时,发现一个问题.含有“鱘”字的json字段会多出一个斜杠,不知道是不是编码的问题. C++要使用JSON来解析数据,一般采用jsoncpp. ...

  7. redis win系统安装并设置开机自启

    安装包下载网址 :https://github.com/MSOpenTech/redis/releases 找到最新发布的安装包进行下载 下载完后解压到c盘 打开cmd,并进到redis里面 cd C ...

  8. Java基础--基本规则、语法

    一.关键字.保留字.标识符.常量.变量 1.关键字:使用某种语言赋予特殊含义的单词. 2.保留字:没有赋予特殊含义,但以后可能会使用的单词. 3.标识符:自定义的单词,以数字.字母.下划线以及$符组成 ...

  9. 监控数组与foreach绑定-Knockout.js

    html: <h2>Your seat reservations</h2> <table>    <thead>  <tr>         ...

  10. GYM 101933E(记忆化搜索)

    用每个人的血量作为状态去搜索T飞,考虑题解中更好的搜索方式:每种血量有多少个人作为状态.这样会减去很多重复的状态,因为只要乘一下就得到了所有相同情况的和. 虽然我不会算,但是直观感受起来复杂度比较优秀 ...