In this essay, I will talk about how to write the service libraries.

  TIPS :

I won't discuss the name rules about HAL libraries, but it's quite important to our understanding.
You can check the source file :
android_source/hardware/libhardware/hardware.c
Or google with key word :
android hardware.c

  

  1、Android.mk

  In this file, it's important to write the LOCAL_SHARED_LIBRARIES and LOCAL_C_INCLUDE to assign the libraries for the service.

# Android.mk
LOCAL_PATH:= $(call my-dir)
include $(CLEAR_VARS) # [optional, user, eng]
# eng = required
# optinal = no install on target
LOCAL_MODULE_TAGS := eng # This is the target being built.
LOCAL_MODULE:= leds_hal_jni # Target install path.
LOCAL_MODULE_PATH := $(TARGET_OUT_SHARED_LIBRARIES) # All of the source files that we will compile.
LOCAL_SRC_FILES:= \
LedHalService.cpp # All of the shared libraries we link against.
LOCAL_SHARED_LIBRARIES := \
  libandroid_runtime \
  libcutils \
   libhardware \
   libhardware_legacy \
   libnativehelper \
   libsystem_server \
   libutils \
   libui \
   libsurfaceflinger_client # Also need the JNI headers.
LOCAL_C_INCLUDES += \
    $(JNI_H_INCLUDE) \
   hardware/leds_hal # Don't prelink this library. For more efficient code, you may want
# to add this library to the prelink map and set this to true.
LOCAL_PRELINK_MODULE := false include $(BUILD_SHARED_LIBRARY)

  2、LedHalService.cpp

  Acturely, this file is the JNI file. Load the hal libraries (Use the hw_get_module function in hardware.c) and offer the API to android applications.

  There are another methods array we should know is JNINativeMethod.

  According the the native method, we could name the JNI functions ourselves without the long JNI default name.

#include <stdlib.h>
#include <string.h>
#include <unistd.h>
#include <assert.h>
#include <jni.h> #include <leds_hal.h> struct leds_device_t *leds_device = NULL; static jboolean leds_setOn(JNIEnv *env, jobject thiz, jint led)
{
LOGI("Leds HAL JNI : leds_setOn() is invoked."); if (leds_device == NULL) {
LOGI("Leds HAL JNI : leds_device was not fetch correctly.");
return -;
} else {
return leds_device->set_on(leds_device, led);
}
} static jboolean leds_setOff(JNIEnv *env, jobject thiz, jint led)
{
LOGI("Leds HAL JNI : leds_setOff() is invoked."); if (leds_device == NULL) {
LOGI("Leds HAL JNI : leds_device was not fetch correctly.");
return -;
} else {
return leds_device->set_off(leds_device, led);
}
} static inline int leds_device_open(const struct hw_module_t* module,
struct leds_device_t** device)
{
return module->methods->open(module, LED_HARDWARE_MODULE_ID,
(struct hw_device_t**) device);
} static jboolean leds_init(JNIEnv *env, jclass clazz)
{
leds_module_t* module; LOGI(" >> finding HAL...");
LOGI("HAL id :"LED_HARDWARE_MODULE_ID); if (hw_get_module(LED_HARDWARE_MODULE_ID,
(const hw_module_t**) &module) == ) {
LOGI("LedService JNI : Led Stub found.");
if (leds_device_open(&module->hw_module,
&leds_device) == ) {
LOGI("LedService JNI : Got Stub operation.");
return ;
}
}
LOGE("LedService JNI : Get Stub operation failed.");
return -;
} static const JNINativeMethod methods[] = {
{ "_init", "()Z", (void *) leds_init },
{ "_set_on", "(I)Z", (void *) leds_setOn },
{ "_set_off", "(I)Z", (void *) leds_setOff },
}; int register_leds_hal(JNIEnv *env)
{
static const char* const kClassName = "mobile/android/leds/hal/service/LedHalService"; jclass clazz; clazz = env->FindClass(kClassName); if (clazz == NULL) {
LOGE("Can't find class %s.\n", kClassName);
return -;
} if (env->RegisterNatives(clazz, methods,
sizeof(methods)/sizeof(methods[]) != JNI_OK)) {
LOGE("Failed registing methods for %s.\n", kClassName);
return -;
} return ;
} jint JNI_OnLoad(JavaVM *vm, void *reserved)
{
JNIEnv *env = NULL; if (vm->GetEnv((void **) &env, JNI_VERSION_1_4) != JNI_OK) {
LOGE(" GetEnv failed!");
return -;
} register_leds_hal(env); return JNI_VERSION_1_4;
}

  The prototype of JNINativeMethod :

typedef struct {
const char* name;
const char* signature;
void* fnPtr;
} JNINativeMethod;

  TIPS :

In the LedHalService.cpp, we use #include <leds_hal.h> instead of #include "leds_hal.h", because of the Path was loaded in the Android.mk

  After compiling, we should push the file leds_jni.so to dir /system/lib/ in ok6410.

  Finaly, we write the Java program to call service library.

package mobile.android.leds.hal.service;
public class LedHalService {
private static LedHalService ledHalService; public static LedHalService getInstance() {
if (ledHalService == null)
return new LedHalService();
else
return ledHalService;
} private LedHalService() {
init();
} public boolean init() {
return _init();
} public boolean setOn(int led) {
return _set_on(led);
} public boolean setOff(int led) {
return _set_off(led);
} private native boolean _init();
private native boolean _set_on(int led);
private native boolean _set_off(int led); static {
System.load("/system/lib/leds_hal_jni.so");
}
}

  What's more, this is a Java file and we can't use it directly. We stiil need to create an apk to call its jar file.

package com.example.leds_haljni;

import mobile.android.leds.hal.service.LedHalService;
import android.os.Bundle;
import android.app.Activity;
import android.view.Menu;
import android.view.View;
import android.widget.CheckBox; public class MainActivity extends Activity {
private CheckBox[] cBox_leds = new CheckBox[4];
LedHalService ledHalService = LedHalService.getInstance(); @Override
protected void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.activity_main); cBox_leds[0] = (CheckBox) findViewById(R.id.checkBox_led1);
cBox_leds[1] = (CheckBox) findViewById(R.id.checkBox_led2);
cBox_leds[2] = (CheckBox) findViewById(R.id.checkBox_led3);
cBox_leds[3] = (CheckBox) findViewById(R.id.checkBox_led4);
} public void onClick_switch(View view) { for (int i = 0; i < 4; i ++) {
if (cBox_leds[i].isChecked()) {
ledHalService.setOn(i);
} else {
ledHalService.setOff(i);
}
}
} @Override
public boolean onCreateOptionsMenu(Menu menu) {
// Inflate the menu; this adds items to the action bar if it is present.
getMenuInflater().inflate(R.menu.main, menu);
return true;
} }

  Ok, here is the activity.xml and strings.xml :

  (1) activity_main.xml

<RelativeLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
android:paddingBottom="@dimen/activity_vertical_margin"
android:paddingLeft="@dimen/activity_horizontal_margin"
android:paddingRight="@dimen/activity_horizontal_margin"
android:paddingTop="@dimen/activity_vertical_margin"
tools:context=".MainActivity" > <TextView
android:id="@+id/textView1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@string/hal_hello" /> <CheckBox
android:id="@+id/checkBox_led1"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignLeft="@+id/textView1"
android:layout_below="@+id/textView1"
android:layout_marginTop="14dp"
android:text="@string/led1" /> <Button
android:id="@+id/button_led"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignBaseline="@+id/checkBox_led4"
android:layout_alignBottom="@+id/checkBox_led4"
android:layout_alignParentRight="true"
android:onClick="onClick_switch"
android:text="@string/button_led" /> <CheckBox
android:id="@+id/checkBox_led2"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignBaseline="@+id/checkBox_led1"
android:layout_alignBottom="@+id/checkBox_led1"
android:layout_alignRight="@+id/textView1"
android:layout_marginRight="26dp"
android:text="@string/led2" /> <CheckBox
android:id="@+id/checkBox_led3"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignBaseline="@+id/checkBox_led2"
android:layout_alignBottom="@+id/checkBox_led2"
android:layout_toRightOf="@+id/checkBox_led2"
android:text="@string/led3" /> <CheckBox
android:id="@+id/checkBox_led4"
android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:layout_alignBaseline="@+id/checkBox_led3"
android:layout_alignBottom="@+id/checkBox_led3"
android:layout_marginLeft="34dp"
android:layout_toRightOf="@+id/checkBox_led3"
android:text="@string/led4" /> </RelativeLayout>

  (2) strings.xml

<?xml version="1.0" encoding="utf-8"?>
<resources> <string name="app_name">ledshal</string>
<string name="action_settings">Settings</string>
<string name="hal_hello">This is a leds HAL application :</string>
<string name="led1">Led1</string>
<string name="led2">Led2</string>
<string name="led3">Led3</string>
<string name="led4">Led4</string>
<string name="button_led">Switch</string> </resources>

  That's all about the simple Led Hal.

ok6410 android driver(12)的更多相关文章

  1. ok6410 android driver(5)

    Test the android driver by JNI (Java Native Interface), In the third article, we know how to compile ...

  2. ok6410 android driver(11)

    This essay, I go to a deeply studying to android HAL device driver program. According to the android ...

  3. ok6410 android driver(9)

    In this essay, I will write the JNI to test our leds device. If you don't know how to create a jni p ...

  4. ok6410 android driver(8)

    In the past, we know how to create and run a simple character device driver on pc, goldfish and ok64 ...

  5. ok6410 android driver(3)

    This article discusses the Makefile and how to port the module to different platform (localhost and ...

  6. ok6410 android driver(10)

    From this essay, we go to a new discussion "Android Hardware Abstraction Layer". In this e ...

  7. ok6410 android driver(7)

    This article talk about how to test device driver on JNI. There are two ways to test the device driv ...

  8. ok6410 android driver(6)

    This is a short essay about the mistakes in compiling ok6410 android-2.3 source codes. If there is n ...

  9. ok6410 android driver(1)

    target system : Android (OK6410) host system : Debian Wheezy AMD64 1.Set up android system in ok6410 ...

随机推荐

  1. 怎么在阿里云服务器部署多个tomcat

    部署前准备: 1.到阿里云官网购买一台服务器 2.给阿里云服务器挂盘,阿里云有教程这里不讲解,自己看. Linux 系统挂载数据盘 视频:Linux服务器挂载数据盘 3.下载tomcat  http: ...

  2. Jquery Data Table插件

    <%@ page language="java" contentType="text/html; charset=UTF-8" pageEncoding= ...

  3. nexus中央仓库中发布自己的jar包

    1.后台上传 通过nexus后台上传第三方包: http://blog.csdn.net/huchunlinnk/article/details/17789175 上面上传的只能上传release版本 ...

  4. 面向.Net程序员的Sql版本管理

    代码版本管理基本上程序员们都知道 TFS GIT SVN等等 但是对于数据库版本管理 java程序员或许会了解一些 但是.Net程序员收获的资料应该不多. 特别是现在云概念使用越来越广的情况下,与应用 ...

  5. Excel的一些常用设置

    1. Freeze表头 (1) 下拉Worksheet的Pane,让该sheet有2个工作区,将该pane下拉到某一特定的行. (2)Window->Freeze Panes.此时会将pane智 ...

  6. SQL语句 - 基本查询

    select select_list [ into new_table ] from table_source [ where search_condition ] [ group by broup_ ...

  7. Promising Linking

    Future/Promise 执行逻辑 scala Future 有几个要点,第一个是 tryAwait 需要借助 CowndownLatch 实现,第二个是可以在 Promise 挂载回调函数 首先 ...

  8. FileZilla FTP Server 高级防火墙例外

    在防火墙中: 在“例外”中,添加端口21,TCP 添加端口50000,TCP (或添加一组端口,一个一个的也行,如果你在软件中选择的是50000-51000,而在这里只打开了50000的单个端口,登录 ...

  9. ctex moderncv版本更新--用latex写一个漂亮的简历

    我的电脑是win7系统32位,ctex版本是v2.9.2.164 full(http://www.ctex.org/CTeXDownload) 一直不太清楚moderncv里面类似\cventry这种 ...

  10. 打开 Mac OS X 隐藏的用户资源库文件夹的方法

    在较高版本的 Mac OS X 中,用户的资源库文件夹(/Users/username/Library)默认被系统隐藏了,从 Finder 窗口中不能直接打开. 但是通过下面这个方法可以快速打开用户资 ...