Original URL: http://www.cnblogs.com/lcw/p/3335505.html
Hal Overview
The following is based on android4.0.3, which corresponds to other lower versions of the code, which may vary, but substantially the same.
The Android HAL is designed to protect the intellectual property of some hardware providers in order to avoid Linux's GPL bondage.
The idea is to put the control hardware action into the Android HAL, and Linux driver just do some simple data interaction, and even the hardware register space directly mapped to user space. And Android is based on Aparch license, so hardware vendors can only provide binary code, so that Android is only an open platform, not an open source platform.
Because Android does not comply with the GPL, Greg Kroah-hartman removes the Andorid drive from Linux in the 2.6.33 kernel. The GPL and hardware vendors still have a rift that cannot be bridged. It's not easy for Android to deal with this problem.
To summarize,the main reasons for Android Hal exist are:
- Not all hardware devices have standard Linux kernel interfaces
- KERNEL driver relates to the copyright of the GPL. Some device manufacturers do not have the reason to expose hardware drivers, so they use HAL to bypass the GPL.
- For some hardware, an has some special needs
Android architecture
SOURCE Location
/hardware/libhardware_legacy/-The old schema, how to take the link library module
The structure of the/hardware/libhardware new schema, tuned to the HAL stub directory, is as follows:
/hardware/libhardware/hardware.c compiled into LIBHARDWARE.S placed/system/lib
the/hardware/libhardware/Include/hardware directory contains the following header files:
Hardware.h General Hardware Module header file
Copybit.h Copybit Module Header file
Gralloc.h Gralloc Module Header file
Lights.h Backlight Module Header file
Overlay.h Overlay Module Header file
Qemud.h Qemud Module Header file
Sensors.h Sensor Module Header file
Many hardware modules are defined in the/hardware/libhardware/modules directory
/hardware/msm7k
/hardware/qcom
/hardware/ti
/device/samsung
/device/moto each vendor platform-related HAL
These hardware modules are compiled into xxx.xxx.so, and the target location is the/SYSTEM/LIB/HW directory.
How the HAL layer is implemented
Hal currently has two architectures, the old HAL schema in the Libhardware_legacy directory, and the new HAL schema in the Libhardware directory.
The two frameworks are as follows:
Libhardware_legacy
Libhardware_legacy is to use the *.so file as a shared library, using the HAL module in the Runtime (JNI section) with direct function call. The driver is manipulated by means of a direct function call.
Of course, applications can also be done without JNI, and it is also a way to directly load *.so (Dlopen) to invoke symbols (symbol) in *.so.
All in all, without encapsulation, the upper layer can operate the hardware directly.
Libhardware
Now the Libhardware architecture, there is the taste of stubs.
The HAL stub is a proxy concept, and the stub is still in the form of a *.so file, but Hal has hidden the *.so.
The stub provides the operation function (operations) to the HAL, while the runtime is operations the specific module (stub) to the HAL and callback the operation functions.
This architecture, with the indirect function call, makes the HAL stub a containment relationship , that is, the HAL contains many stubs (proxies).
Runtime can obtain an action function as long as the description type, or module ID, is used.
For the current HAL, it can be assumed that Android defines the HAL layer structure framework and accesses the hardware through several interfaces to unify the calling method.
Jni
The implementation of the Android HAL is required via JNI (Java Native Interface).
Jni simply means that a Java program can invoke a dynamic-link library written in C/s + +, so that HAL can be written in C + + language and is more efficient.
Jni-> General hardware module, hardware module, core driver interface, specific: Jni->libhardware.so->xxx.xxx.so->kernel, specifically: Android In frameworks, Jni calls the hw_get_module function defined in hardware.c to get the hardware module, then calls the method in the hardware module, and the method in the hardware module directly calls the kernel interface to complete the related function.
Access HAL Mode
There are roughly two ways to access the HAL under Android.
After service invocation
The Android app can call the. So format JNI directly through the service.
After the manager invokes the service
The above two methods should be said to have the advantages and disadvantages of each:
The first method is simple and efficient, but not formal.
The second approach is more complex to implement, but more consistent with the current Android framework.
In the second approach, Ledmanager and Ledservice (Java) need to communicate through process communication in two processes.
In today's Android framework, both of these methods exist, for example, for lights, which calls JNI directly through Lightsservice, whereas for sensor, the middle is called JNI by Sensorsmanager.
Universal Hardware Module (libhardware.so)
In general, HAL Moudle needs to involve three key structures:
struct hw_module_t; struct Hw_module_methods_t;struct hw_device_t;
These three structures are defined in hardware.h (/hardware/libhardware/include/hardware/hardware.h).
header file mainly defines the general hardware module structure Body hw_module_t, declares the JNI call interface function Hw_get_module, hw_module_t.
Defined as follows:
View Code
As the note says, all HAL modules have a structure named Hal_module_info_sym, and this structure begins with hw_module_t, which is to inherit the hw_module_t structure.
such as Lights,sensor:
1 struct sensors_module_t 2 {3 struct hw_module_t common; 4 int (*get_sensors_list) (struct sensors_module_t* Modu Le, 5 struct sensor_t const** list); 6}; 7 8/* 9 * The lights Module10 */11 struct light_module_t hal_module_info_sym = {common: {Tag:hardwa re_module_tag,14 version_major:1,15 version_minor:0,16 id:lights_hardware_module_id,17 Name: "Lights module", Author: "Rockchip", Methods: &light_module_methods,20}21};22 struct sensors_module_t hal_module_info_sym = {. Common = {. Tag = hardware_module_tag,26. Versio N_major = 1,27. Version_minor = 0,28. id = sensors_hardware_module_id,29. Name = "Stingray Sensors Module ", author =" Motorola ", methods = &sensors_module_methods,32},33. Get_sensors_li st = Sensors__get_sensors_list34};
The more important thing in hw_module_t is that the hardware module method structure hw_module_methods_t is defined as follows:
typedef struct HW_MODULE_METHODS_T { /** Open a specific device */ int (*open) (const struct hw_module_t* module, c Onst char* ID, struct hw_device_t** device);} hw_module_methods_t;
This method is initialized when the hal_module_info_sym is defined. Currently, only one open method is defined in the structure, where the device structure body parameter hw_device_t is defined as follows:
1/** 2 * Every device data structure must begin with hw_device_t 3 * followed by module specific public methods and a Ttributes. 4 */5 6 typedef struct HW_DEVICE_T 7 {8/** tag must be initialized to Hardware_device_tag */9 uint32_t tag;1 0/** version number for hw_device_t */12 uint32_t version;13/** Reference to the module this device is longs to */15 structs hw_module_t* module;16/** padding reserved for the future use */18 uint32_t reserved[12]; /** Close This device */21 int (*close) (struct hw_device_t* device); hw_device_t;23 ice_t {+ struct hw_device_t common;27 int (*set_light) (struct light_device_t* dev,28 struct light_ state_t const* State),};30/**32 * Every device data structure must begin with Hw_device_t33 * followed by module Specific public methods and attributes.34 */35-struct sensors_poll_device_t notoginseng {hw_device_t common;39 Int (*activATE) (struct sensors_poll_device_t *dev,40 int handle, int enabled), int (*setdelay) (struct Sensors_poll_ device_t *dev,42 int handle, int64_t ns); int (*poll) (struct sensors_poll_device_t *dev,44 s ensors_event_t* data, int count); 45};
As the note says, each device's data structure must also start with hw_device_t .
The hw_get_module function is declared as follows:
int hw_get_module (const char *id, const struct hw_module_t **module);
"Turn" "Android" HAL Analysis