Android启动过程中执行一个C语言的应用程序或者执行shell脚本
一、Android启动过程中去对系统做一些设置,如修改某些文件夹的属性和文件的权限,可在init.rc中增加service执行shell脚本,从而可在shell脚本中完成大部分操作。或者也可以执行c语言应用程序。
二、实际测试
1、在init.xxxx.rc中增加执行脚本的service,把service设为class main,则在启动class类的serive自动启动init-setup的service。
1.1 开机执行脚本
service init-setup /system/bin/rootandwakelock.sh
class main
user root
group root
oneshot
seclabel u:r:init:s0
1.2 开机执行C可执行程序
service check_hdmiin_signal /system/bin/check_hdmiin_signal
class main
user root
group root
oneshot
seclabel u:r:init:s0
1.3 如果想在开机完成后执行shell脚本,可如下设置:
service init-setup /system/bin/rootandwakelock.sh
user root
group root
disabled
oneshot
seclabel u:r:init:s0
on property:sys.boot_completed=1
start init-setup
1.4 各参数解释:
Android 服务名称规则invalid service name 限制16字符以内
user root 和 group root 意思是使用 root 权限。
seclabel u:r:init:s0 这句的具体含义大概是设置init进程的安全上下文,不加这个会提示没有权限:service does not have a SELinux domain defined。
disabled是不自动执行,得另外start。
oneshot说明的是该操作只会执行一次,并不像其他带有 restart 指令的 service 一样当被 kill 调之后会重新调起。如果你希望被kill掉之后重新调起,那就不写.
我这里的测试代码如下图
2、在Android下编写和编译c程序生存两个可执行文件。
2.1 auto_run.c的代码
#include <stdio.h>
#include <android/log.h>
#define LOG "ffmpegDemo-jni" // 这个是自定义的LOG的标识
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG,LOG,__VA_ARGS__) // 定义LOGD类型
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO,LOG,__VA_ARGS__) // 定义LOGI类型
#define LOGW(...) __android_log_print(ANDROID_LOG_WARN,LOG,__VA_ARGS__) // 定义LOGW类型
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR,LOG,__VA_ARGS__) // 定义LOGE类型
#define LOGF(...) __android_log_print(ANDROID_LOG_FATAL,LOG,__VA_ARGS__) // 定义LOGF类型
int main(void)
{
int i=0;
//signal(SIGCHLD, SIG_IGN);
//daemon(0, 0);//fork 强制后台运行!
// for(i = 0; i < 10; i++)
system("touch /data/new_file.txt");
while(1)
{
sleep(1);
printf("auto run demo! number=%d\n",i);
LOGF("auto run demo! number=%d\n",i);
i+=8;
// LOGI("Calls=%d,Valid=%d",10,11);
}
return 0;
}
2.2 Android.mk的代码
LOCAL_PATH := $(call my-dir)
include $(CLEAR_VARS)
LOCAL_MODULE_TAGS := optional
LOCAL_MODULE := auto_run
LOCAL_SRC_FILES := $(call all-subdir-c-files)
LOCAL_SHARED_LIBRARIES := \
liblog \
libcutils
include $(BUILD_EXECUTABLE)
2.3 rootandwakelock.sh脚本如下,里面是执行另外一个c可执行程序auto_run_script。
2.4 auto_run_script.c代码如下
#include <stdio.h>
#include <android/log.h>
#define LOG "ffmpegDemo-jni" // 这个是自定义的LOG的标识
#define LOGD(...) __android_log_print(ANDROID_LOG_DEBUG,LOG,__VA_ARGS__) // 定义LOGD类型
#define LOGI(...) __android_log_print(ANDROID_LOG_INFO,LOG,__VA_ARGS__) // 定义LOGI类型
#define LOGW(...) __android_log_print(ANDROID_LOG_WARN,LOG,__VA_ARGS__) // 定义LOGW类型
#define LOGE(...) __android_log_print(ANDROID_LOG_ERROR,LOG,__VA_ARGS__) // 定义LOGE类型
#define LOGF(...) __android_log_print(ANDROID_LOG_FATAL,LOG,__VA_ARGS__) // 定义LOGF类型
int main(void)
{
int i=0;
//signal(SIGCHLD, SIG_IGN);
//daemon(0, 0);//fork 强制后台运行!
// for(i = 0; i < 10; i++)
system("touch /data/new_file.txt");
while(1)
{
sleep(1);
printf("auto run demo! number=%d\n",i);
LOGF("\nscript auto run demo! number=%d\n",i);
i+=1;
// LOGI("Calls=%d,Valid=%d",10,11);
}
return 0;
}
2.5 在Android下编译成可执行文件auto_run和auto_run_script。
3、打包固件运行,打开一个cmd窗口adb logcat查看打印信息,打开另外一个窗口setprop变量来start和stop进程。通过打印信息可以看出来开机后执行auto_run程序和运行rootandwakelock.sh。
三、kill 该进程后之后会重新调起例子,没有oneshot。
service gwdtservice /system/bin/giada_watchdog
user root
group root
disabled
seclabel u:r:init:s0