实现相应的JNI部分已经sever部分
此次实现主要涉及的修改两个目录的文件 hardware,以及framework。
一、修改hardware目录:
由于平台原因,使用的主要是hardwarelibhardware_legacy 目录下的文件,接口为老的接口,不同于老罗使用的相关,自己写代码可以参考vibrator 马达的实现。
添加头文件hardwarelibhardware_legacyincludehardware_legacywelcome.h
#ifndef _ANDROID_WELCOME_INTERFACE_H_ #define _ANDROID_WELCOME_INTERFACE_H_ #if 1 #if __cplusplus extern "C" { #endif // 定义模块ID //#define WELCOME_HARDWARE_MODULE_ID "welcome" //硬件接口结构体 int set_val(const char *sysfs_path,int val); int get_val(const char *sysfs_path,int* val); #if __cplusplus } // extern "C" #endif #endif #endif //__ANDROID_WELCOME_INTERFACE_H__
2、添加相应的实现文件hardwarelibhardware_legacy
2.1 在此目录先新建welcome 目录用于统一管理本次hal层代码,并添加相关Android.mk 文件添加编译规则
LOCAL_SRC_FILES += welcome/welcome.c
2.2 添加实现文件welcome.c
#define LOG_TAG "welcomeStub" #include <hardware/hardware.h> #include <hardware_legacy/welcome.h> #include <fcntl.h> #include <stdlib.h> #include <string.h> #include <errno.h> #include <cutils/log.h> #include <cutils/atomic.h> #define DEVICE_NAME "/dev/welcomf" #define MODULE_AUTHOR "atlas_li@126.com" //设备访问接口 int welcome_set_val(char *sysfs_path,int val); int welcome_get_val(char *sysfs_path,int* val); //设备打开和关闭接口 int welcome_device_open(const struct hw_module_t* module,const char* name, struct hw_device_t** device){ return 0; } int welcome_device_close(struct hw_device_t* device){ return 0; } //设备访问接口 int set_val(const char *sysfs_path,int val){ int fd; if((fd = open(DEVICE_NAME,O_RDWR)) == -1){ ALOGE("Welcome Staub : failed to open %s .%m",DEVICE_NAME); return -EFAULT; } ALOGI("Welcome Stub: set value %d to device.",val); write(fd,&val,sizeof(val)); close(fd); return 0; } int get_val(const char *sysfs_path,int* val){ int fd; if((fd = open(DEVICE_NAME,O_RDWR)) == -1){ ALOGE("Welcome Staub : failed to open %s .%m",DEVICE_NAME); return -EFAULT; } if(!val){ ALOGE("Welcome Stube: error val pointer"); return -EFAULT; } read(fd,val,sizeof(*val)); ALOGI("Welcome Stub: get value %d from device",*val); close(fd); return 0; }
此部分耗时比较常,按老罗的方式,添加会导致手机不能正常开机一直停留在开机动画过程,故借鉴此平台的马达实现部分对代码进行修改。
2.3 将相应的代码合入到对应的库文件中修改hardwarelibhardware_legacyAndroid.mk 添加对应模块welcome
legacy_modules := power uevent vibrator wifi qemu qemu_tracing welcome
二、修改framework部分
此部分主要包含以下几个部分的实现:实现相应的JNI文件,实现相应的aidl文件,实现相关的server文件,配置相关文件让jni与server正常工作
1、实现相应的JNI文件: frameworksaseservicescorejni
1.1、使用相应的jni文件:com_android_server_WelcomeService.cpp
/* * Copyright (C) 2009 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #if 1 #define LOG_TAG "WelcomeService" #include "jni.h" #include "JNIHelp.h" #include "android_runtime/AndroidRuntime.h" #include <utils/misc.h> #include <utils/Log.h> #include <hardware_legacy/welcome.h> #include <stdio.h> namespace android { const char* DEVICE_PATH ="/dev/welcomf" ; // 通过硬件抽象层定义的硬件访问接口设置硬件寄存器val的值 static void welcome_setVal(JNIEnv *env, jobject clazz,jint value){ int val = value; ALOGI("Welcome JNI: set value %d to device.",val); set_val(DEVICE_PATH,val); } //通过硬件抽象定义的硬件访问接口读取硬件寄存器val 值 static jint welcome_getVal(JNIEnv *env, jobject clazz){ int val = 0; get_val(DEVICE_PATH,&val); ALOGI("Welcome JNI: get value %d from device.",val); return val; } //通过硬件抽象层定义的硬件模块打开接口打开硬件设备 vib 在hardware h文件中 /*static inline int welcome_device_open(const hw_module_t* module,struct welcome_device_t** device){ return module->methods->open(module,WELCOME_HARDWARE_MODULE_ID,(struct hw_device_t**)device); }*/ //通过硬件模块ID 来加载指定的在硬件模块并打开硬件 static jboolean welcome_init(JNIEnv *env, jobject clazz){ ALOGI("Welcome JNI :initializing...... "); return 0; } //JNI 方法表 static JNINativeMethod method_table[] = { // {"init_native","()Z",(void *)welcome_init}, {"setVal_native","(I)V",(void *)welcome_setVal}, {"getVal_native","()I",(void *)welcome_getVal}, }; //JNI 注册 int register_android_server_WelcomeService(JNIEnv *env){ return jniRegisterNativeMethods(env,"com/android/server/WelcomeService",method_table,NELEM(method_table)); } };//namespace android #endif
1.2、修改编译规则,让jni参与编译,已经调用
1.2.1、修改该目录下的Android.mk 文件 在LOCAL_SRC_FILES += 增加一行
LOCAL_SRC_FILES +=
.................
$(LOCAL_REL_DIR)/com_android_server_WelcomeService.cpp
1.2.2、添加相关调用,修改同目录下的:onload.cpp
首先在namespace android增加register_android_server_WelcomeService函数声明:
namespace android {
..............................................................................................
int register_android_server_WelcomeService(JNIEnv *env);
在JNI_onLoad增加register_android_server_HelloService函数调用:
extern "C" jint JNI_onLoad(JavaVM* vm, void* reserved){
.................................................................................................
register_android_server_WelcomeService(env);
2、实现相应的aidl文件
.1、frameworksasecorejavaandroidosIWelcomeService.aidl
/** * Copyright (c) 2007, The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package android.os; /** {@hide} */ interface IWelcomeService { void setVal(int val); int getVal(); }
2.2、添加入编译规则 frameworksaseAndroid.mk
LOCAL_SRC_FILES +=
..........
core/java/android/os/IWelcomeService.aidl
3、实现相关的server文件
3.1、实现相应的server文件:frameworksaseservicescorejavacomandroidserverWelcomeService.java
/* * Copyright (C) 2008 The Android Open Source Project * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ package com.android.server; //import android.app.AppOpsManager; //import android.content.BroadcastReceiver; import android.content.Context; import android.os.IWelcomeService; import com.android.server.SystemService; import android.app.Service; import android.util.Slog; public class WelcomeService extends IWelcomeService.Stub{ private static final String TAG = "WelcomeService"; WelcomeService(){ // super(context); // init_native(); } public void setVal(int val){ setVal_native(val); } public int getVal(){ return getVal_native(); } // private static native boolean init_native(); native static void setVal_native(int val); native static int getVal_native(); }
3.2、将相应的server添加到系统server中:frameworksaseservicesjavacomandroidserverSystemServer.java
在ServerThread::run函数中增加加载HelloService的代码:
@Override
public void run() {
....................................................................................
try{ Slog.i(TAG, "Welcome Service"); ServiceManager.addService("welcome",new WelcomeService()); }catch(Throwable e){ Slog.e(TAG,"Failure starting Welcome Service",e); }
三、编译,打包下载
至此jni部分 实现完成,打包下载,看看能否正常开机,能正常开机没有异常,则成功了一半。