Android4.1中 HAL的段错误

 1. 在 Android4.1 中,执行到 hardware.c 中的 load 方法时
static int load(const char *id,
        const char *path,
        const struct hw_module_t **pHmi)
{
    int status;
    void *handle;
    struct hw_module_t *hmi;


    /*
     * load the symbols resolving undefined symbols before
     * dlopen returns. Since RTLD_GLOBAL is not or'd in with
     * RTLD_NOW the external symbols will not be global
     */
    handle = dlopen(path, RTLD_NOW);
    if (handle == NULL) {
        char const *err_str = dlerror();
        ALOGE("load: module=%s\n%s", path, err_str?err_str:"unknown");
        status = -EINVAL;
        goto done;
    }


    /* Get the address of the struct hal_module_info. */
    const char *sym = HAL_MODULE_INFO_SYM_AS_STR;
    hmi = (struct hw_module_t *)dlsym(handle, sym);
    if (hmi == NULL) {
        ALOGE("load: couldn't find symbol %s", sym);
        status = -EINVAL;
        goto done;
    }


    /* Check that the id matches */
    if (strcmp(id, hmi->id) != 0) {
        ALOGE("load: id=%s != hmi->id=%s", id, hmi->id);
        status = -EINVAL;
        goto done;
    }


    hmi->dso = handle;


    /* success */
    status = 0;


    done:
    if (status != 0) {
        hmi = NULL;
        if (handle != NULL) {
            dlclose(handle);
            handle = NULL;
        }
    } else {
        ALOGV("loaded HAL id=%s path=%s hmi=%p handle=%p",
                id, path, *pHmi, handle);
    }


    *pHmi = hmi;


    return status;
}
  其中有这样一句话  hmi->dso = handle;// 这句话导致 了 crash 
  Android4.1 中修改了 bionic/linker 中的内容,添加了对 RELRO的支持。他将 const 变量 的内存地址映射为只读的,如果通过const变量的指针对const变量进行修改,那么就会出现段错误。 
  hmi 表示  的是 具体HAL模块中定义的 模块变量 HAL_MODULE_INFO_SYM,以 power 模块为例子
  struct power_module HAL_MODULE_INFO_SYM = {
    .common = {
        .tag = HARDWARE_MODULE_TAG,
        .module_api_version = POWER_MODULE_API_VERSION_0_2,
        .hal_api_version = HARDWARE_HAL_API_VERSION,
        .id = POWER_HARDWARE_MODULE_ID,
        .name = "Default Power HAL",
        .author = "The Android Open Source Project",
        .methods = &power_module_methods,
    },


    .init = power_init,
    .setInteractive = power_set_interactive,
    .powerHint = power_hint,
};
  那么 如果 HAL_MODULE_INFO_SYM 定义为 const,
const struct power_module HAL_MODULE_INFO_SYM = {
....
}
那么libhardware 在调用 power 模块的动态链接库的时候就会出现 段错误,解决的方案就是 将 HAL_MODULE_INFO_SYM 声明为 非 const 类型的。
2.出现这个问题的原因在于 Android4.1 在 bionic/linker 中添加了对 relro 的支持,在bionic/linker 中查看 log
commit 9ec0f03a0d0b17bbb94ac0b9fef6add28a133c3a
Author: Nick Kralevich <nnk@google.com>
Date:   Tue Feb 28 10:40:00 2012 -0800


    Add relro support
    
    Add support for PT_GNU_RELRO. This allows the static linker to
    indicate that certain regions of memory should be marked as
    "read-only" after dynamic linking is complete.
    
    See:
      * http://www.akkadia.org/drepper/nonselsec.pdf (section 6)
      * http://tk-blog.blogspot.com/2009/02/relro-not-so-well-known-memory.html
    
    Note that this change has no effect on Android right now, because
    we don't compile our code with relro enabled.
    
    Change-Id: I6541f8775367e8558b4388f7d105b1ae6e8f046b


 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值