1
HAL程序必须要一个HAL-MODULE-INFO——SYM(hw_module_t)变量,有了这个才能被Android系统调用。类似于(C函数的main()和linux驱动程序的init()函数)
2 HAL编程是三个关键结构体:
struct hw_module_t; (HAL模块 中)
struct hw_module_methods_t; (入口函数 小)
struct hw_device_t; (HAL设备 大)
这几个数据结构是在Android工作目录/hardware/libhardware/include/hardware/hardware.h文件中定义.
3 源程序
3.1 leds_hal.h
#include <hardware/hardware.h>
#include <fcntl.h>
#include <cutils/log.h>
struct led_module_t
{
struct hw_module_t hw_module;
};
struct led_control_device_t
{
struct hw_device_t hw_device;
int (*set_on)(struct led_control_device_t *dev, int32_t led);
int (*set_off)(struct led_control_device_t *dev, int32_t led);
};
#define LED_HARDWARE_MODULE_ID "led_hal"
3.2 leds_hal.c
#include "leds_hal.h"
int dev_file = 0;
int led_on(struct led_control_device_t *dev, int32_t led)
{
return ioctl(dev_file, 1, led);
}
int led_off(struct led_control_device_t *dev, int32_t led)
{
return ioctl(dev_file, 0, led);
}
int led_device_close(struct hw_device_t* device)
{
struct led_control_device_t* ctx = (struct led_control_device_t*) device;
if (ctx)
{
free(ctx);
}
close(dev_file);
return 0;
}
static int led_device_open(const struct hw_module_t* module, const char* name,
struct hw_device_t** device)
{
struct led_control_device_t *dev;
dev = (struct led_control_device_t *) malloc(sizeof(*dev));
memset(dev, 0, sizeof(*dev));
dev->hw_device.tag = HARDWARE_DEVICE_TAG;
dev->hw_device.version = 0;
dev->hw_device.module = (struct hw_module_t*) module;
dev->hw_device.close = led_device_close;
dev->set_on = led_on;
dev->set_off = led_off;
//*device = &dev->hw_device;
*device = (hw_device_t*)dev;
dev_file = open("/dev/leds", O_RDWR);
if (dev_file < 0)
{
LOGI("LED Stub: open /dev/leds fail.");
}
else
{
LOGI("LED Stub: open /dev/leds success .");
}
//leds_init_gpm();
return 0;
}
static struct hw_module_methods_t led_module_methods =
{ open: led_device_open };
struct led_module_t HAL_MODULE_INFO_SYM =
{ hw_module:
{ tag: HARDWARE_MODULE_TAG, version_major: 1, version_minor: 0, id
: LED_HARDWARE_MODULE_ID,
name: "Sample LED HAL Stub",
author: "Lining",
methods: &led_module_methods,
}
};
4 Android.mk文件与分析
第一步:
HAL模块属于android系统的一部分,HAL需要很多的Android的头文件和共享库,采用办法如下:建立链接
ln -s /root/drivers/ch09/leds_hal/ /working/android2.3.4_src/hardware/leds_hal
第二步 采用mm命令编译
Android.mk文件如下:
LOCAL_PATH := $(call my-dir) //返回当前路径
include $(CLEAR_VARS) //清楚...变量
LOCAL_PRELINK_MODULE := false
LOCAL_MODULE_PATH := $(TARGET_OUT_SHARED_LIBRARIES)/hw
//编译出来的.so文件存放地方
LOCAL_SHARED_LIBRARIES := liblog //本次编译要链接动态库文件liblog.so文件
LOCAL_SRC_FILES := leds_hal.c
LOCAL_MODULE :=led_hal.default //编译生成led_hal.default.so
LOCAL_MODULE_TAGS := eng
include $(BUILD_SHARED_LIBRARY) //编译器负责
第三步:把生成的led_hal.default.so传入开发板的/system/lib/hw中。