属性是 Android 系统的一大特色,它用来进行系统配置,模块,组件间的通讯。这篇文章主要是聊一下 Android property 的应用和工作原理以及一些常用的系统属性。
属性配置文件
在主板系统上,属性文件分别是:
- /default.prop -- 对应编译系统 out 目录下的 …/root/default.prop
- /system/build.prop -- 对应编译系统 out 目录下 …/system/build.prop
- /data/property -- 这个目录下,是 persist 开头的可读写的属性。
属性的规则
- 以 ”ro.” 开头的属性,一旦设置,就不能再被改变;非 “ro.” 开头的属性值可以被修改。
- 以 ”net.” 开头的属性,会被当作 DNS 属性,属于特殊属性,不要随便使用。
- 以 “persist.” 开头的属性,会保存到 /data/property/ 下面,它是可以保存的;其它属性修改后,值不能保存,重启后无效。
API
Java 层:
java API 主要是在系统预置 apk 和 framework 里面使用,它没有拉出来作为应用的 API。
import android.os.SystemProperties;
set(String key, String val)
String get(String key, String def)
int getInt(String key, int def)
long getLong(String key, long def)
boolean getBoolean(String key, boolean def)
c 层:
#include "cutils/properties.h"
int property_get(const char *key, char *value, const char *default_value);
int8_t property_get_bool(const char *key, int8_t default_value);
int64_t property_get_int64(const char *key, int64_t default_value);
int32_t property_get_int32(const char *key, int32_t default_value);
int property_get(const char *key, char *value, const char *default_value)
int property_set(const char *key, const char *value);
bool 类型的有效值
- true: “1”, “true”, “y”, “yes”, “on”
- false: “0”, “false”, “n”, “no”, “off”
有效的数字字符串
- 符号字符: ‘+’ 或者 ‘-‘
- ‘0’ 前缀表示是 8 进制数字
- 0x / 0X 前缀表示是 16 进制数字
一些有用的系统属性
ro.secure=0 -- 启用 root 帐户; 为 1,则是关闭 root 帐号。
ro.debuggable=1 -- 启用 adb
user 版本软件的配置是:
ro.secure=1
ro.debuggable=0
ro.HOME_APP_ADJ = 1 -- 加速 launcher, 强制把 launcher 加载到内存。
设置 DNS,如 8.8.8.8
net.dns1=8.8.8.8
net.ppp0.dns1=8.8.8.8
net.wlan0.dns1=8.8.8.8
net.eth0.dns1=8.8.8.8
dalvik.vm.usejit = true | false -- enable/disable JIT。
dalvik.vm.checkjni = true -- 启动 JNI 检查,调试用。
dalvik.vm.jniopts = forcecopy -- JNI 检查数组越界。
添加属性
1: device.mk 可以使用 PRODUCT_PROPERTY_OVERRIDES,如果该属性不存在,会追加到文件中。如:
PRODUCT_PROPERTY_OVERRIDES += ro.adb.secure=0
2: 可以添加到 build/tools/buildinfo.sh,如:
echo “ro.product.IME.default=xxx.inputmethod.pinyin/.PinyinIME”
build 的时候,先 rm out/…../system/build.prop,不然,改动可能无效。
也可以直接用 root 登录文件系统,remount /system,然后修改 /system/build.prop 文件,重启即可生效。
具体实现
是典型的 policy/function 分层结构,”/system/core/init/property_service.c” 提供 policy,“/bionic /libc/bionic/system_properties.c” 提供 function。
init 进程初始化过程中,在 property_service.c 加载所有的属性文件 (‘load_all_props()’),然后,创建一个 unix domain socket (/dev/socket/property_service) 来监听客户的请求(‘start_property_service’),init 初始化结束后,进入轮循状态(for(;;)),通过 poll 函数得到 socket 文件事件,最后在 ”handle_property_set_fd()” 来处理客户请求。
system_properties.c 根据属性名,用 ‘ . ‘ 区分各个节点,用二插树来保存属性数据。
/bionic/libc/include/sys/_system_properties.h
#define PROP_PATH_RAMDISK_DEFAULT “/default.prop”
#define PROP_PATH_SYSTEM_BUILD “/system/build.prop”
#define PROP_PATH_SYSTEM_DEFAULT “/system/default.prop”
#define PROP_PATH_VENDOR_BUILD “/vendor/build.prop”
#define PROP_PATH_LOCAL_OVERRIDE “/data/local.prop”
system_properties.c
__system_property_add
__system_property_get
__system_property_set
__system_property_update
权限配置
AN4: property_service.c property_perms[]
AN5: external/sepolic/property_contexts
欢迎大家来我的网站交流: 般若程序蝉