一.alsps的初始化函数和重要结构体

epl2182_init //

Epl2182.c (kernel-3.10\drivers\misc\mediatek\alsps\epl2182-new)
    struct alsps_hw *hw = get_cust_alsps_hw(); //得到配置和硬件信息
        i2c_register_board_info(hw->i2c_num, &i2c_EPL2182, 1); //注册I2C信息
            list_add_tail(&devinfo->list, &__i2c_board_list); //加入到__i2c_board_list链表中
        alsps_driver_add(&epl2182_init_info); // alsps_local_init函数加入
            alsps_init_list[i] = obj; //加入到alsps_init_list[i] 数组中,以备后面用
 
alsps_local_init //这个函数在alsps核心调用,下面有分析
    get_cust_alsps_hw();  //得到配置和硬件信息
        epl2182_power(hw, 1); //上电
           //mtk专门的上电函数(pmic.c),很多模块都在用,if(hw->power_id != POWER_NONE_MACRO) 会进行上电操作,这里只是一个赋值操作power_on = on;
            hwPowerOn(hw->power_id, hw->power_vol, "EPL2182")
        i2c_add_driver(&epl2182_i2c_driver)  //I2C注册driver
 
i2c_driver 结构体:
static struct i2c_driver epl2182_i2c_driver =
{
    .probe      = epl2182_i2c_probe,
    .remove     = epl2182_i2c_remove,
    .detect     = epl2182_i2c_detect,
    .suspend    = epl2182_i2c_suspend,
    .resume     = epl2182_i2c_resume,
    .id_table   = epl2182_i2c_id,
    .driver = {
        .name           = EPL2182_DEV_NAME,
    },
};
 
 
 
二.I2C的alsps的probe函数
通过i2c_driver 与adapter的匹配调用epl2182_i2c_probe
epl2182_i2c_probe
    epl2182_get_addr(obj->hw, &obj->addr); //得到I2C的地址
    INIT_WORK(&obj->eint_work, epl2182_eint_work); //初始化中断工作任务
        epld = g_epl2182_ptr;   //得到epl2182私有数据
        elan_epl2182_I2C_Read(epld->client,REG_16,R_TWO_BYTE,0x02,read_data);  //i2c的读函数,读channel1,ps的数据
        elan_epl2182_I2C_Read(epld->client,REG_13,R_SINGLE_BYTE,0x01,read_data); //读取到PS的中断状态,0或者1
        ps_report_interrupt_data 
            ps_data_report(cxt->idev,value,3);
                input_report_rel(dev, EVENT_TYPE_PS_VALUE, (value+1));  //输入子系统上报数据
        input_report_rel(dev, EVENT_TYPE_PS_STATUS, status);
        input_sync(dev); 
    INIT_WORK(&obj->data_work, epl2182_check_ps_data);  //也是上报数据
    elan_epl2182_I2C_Write(client,REG_0,W_SINGLE_BYTE,0x02, EPL_S_SENSING_MODE); //把光照转换到电压的时间
    elan_epl2182_I2C_Write(client,REG_9,W_SINGLE_BYTE,0x02,EPL_INT_DISABLE); //把中断清零
    epl2182_init_client
        if(obj->hw->polling_mode_ps == 0) //这里是中断模式
        epl2182_setup_eint(client) //
            g_epl2182_ptr = obj;  //后面有用到epl2182的属性
        hw8k_init_device
            epl2182_i2c_client=client; //后面有用到
    misc_register(&epl2182_device) //注册混杂设备
    als_ctl.open_report_data= als_open_report_data;  //als_control的赋值
    als_ctl.enable_nodata = als_enable_nodata;
    als_ctl.set_delay  = als_set_delay;
 
 
混杂设备结构体:
static struct miscdevice epl2182_device =
{
    .minor = MISC_DYNAMIC_MINOR,
    .name = "als_ps",
    .fops = &epl2182_fops,
};
static struct file_operations epl2182_fops =
{
    .owner = THIS_MODULE,
    .open = epl2182_open,
    .release = epl2182_release,
    .unlocked_ioctl = epl2182_unlocked_ioctl,
};
 
 
 
三.alsps核心
在alsps.c中是alsp的上层部分,在epl2182_init之后调用
static struct platform_driver alsps_driver =
{
.probe      = alsps_probe,
.remove     = alsps_remove,    
.suspend    = alsps_suspend,
.resume     = alsps_resume,
.driver     = 
{
.name = ALSPS_PL_DEV_NAME,
        #ifdef CONFIG_OF
.of_match_table = alsps_of_match,
#endif
}
}; //平台driver结构体
 
alsps_init
    platform_driver_register(&alsps_driver) //注册平台驱动,在mt_devs.c中有平台device:platform_device alsps_sensor
        
alsps_probe  //匹配后调用它
    alsps_context_alloc_object
        alsps_context *obj = kzalloc(sizeof(*obj), GFP_KERNEL); //分配alsps_context 结构体,保存了很多属性
      
        初始化obj结构体,比如work的初始化:als_work_func,ps_work_func;定时器初始化,执行函数:als_poll,ps_poll分别执行schedule_work(&obj->report_als); schedule_work(&obj->report_ps);
        alsps_real_driver_init //初始化实际的alsps
            alsps_real_driver_init //
                alsps_init_list[i]->init(); //这就是具体alsps驱动注册的init函数,在这里调用了
    alsps_factory_device_init    //is_use_common_factory被设置为true,就会进行misc_register(&alsps_factory_device),这里不用。
    alsps_input_init //输入子系统的初始化,注册
        input_allocate_device
        input_register_device
    
 
 
四.应用读取sensor数据:
   als_store_active 和 ps_store_active启动sensor,然后上报数据,PS一般用中断,als一般用轮询!
 
 
 
五.Light sensor level和value的设置

[DESCRIPTION]
    Light sensor level和value的设置
[PLATFORM]
    MT6575 MT6577 MT6589
[SOLUTION]
    Als_level是从sensor读到的raw dataals_value是由als_level转换为上报android的值,以
ltr559为例:在cust_alsps.c中 :

该值要客制化,请联系sensor vender提供。

[DESCRIPTION]

  由于结构限制或者传感器本身原因,工厂模式下检测到ic出来的值变化不够明显,可检测的范围小等。导致自动背光效果不明显。

[SOLUTION]

      硬件上没有方法改动的话,建议合理的修改,cust_alsps.c中的.level和.value这2个数组的值,driver里处理数据的原理:
       从driver里传感器IC寄存器出来的数据是level值,根据此level值参照上述2个数组的对应关系,由level数组的下标取到.value数组的下标对应的值,然后上报value值给工厂模式和上层看到。

      所以需要您调cust_alsps.c里的那2个数组,如果是被遮挡而引起变化范围变小的话,应该是寄存器出来的level变小了,所以建议把cust-als.c里的level也相应的减小,value不变,则应该有所改善。多试几组减小.level的情况。

另外如果需要更细腻的背光等级,可以适当的把这2个数组加大,取值更连续一些。(这个映射还与android的value(LUX)--->255级背光的映射有关,也不是连续的)

请参考 frameworks\base\core\res\res\values\config.xml

六.兼容

当遇到两个sensor同一个i2c地址,只启用一个的时候,可以在注册的时候该一个地址,然后在probe中改回来就可以了。

 通过工程模式可以看到sensor的raw 打他,通过工厂测试模式可以看到所有senso人上报的数值。

 
 
七.工程测试模式中sensor的读取数据流程
    1.输入*987*0#进行测试,一般用于产线的测试
     epl2182_unlocked_ioctl   : 用的是poll(ps)
 
      2.*#*#3646633#*#*这样是可以读到sensor的原始数据,可以调试sensor是否有遮挡            
        epl2182_unlocked_ioctl 用的是poll
 
 
 
 
八.把ps改成轮询方式
   现在的机制是:
         1. PS单独开启的时候用中断;
          2.单独ALS是轮询
          3.PS与ALS一起开启的时候在als_get_data中轮询ALS,如果是中断模式还要轮询PS,因为轮询als的时候ps不会产生中断
 
   把PS也改下轮询:
         因为poll的时候会互相干扰,产生竞争,导致数据闪动,需要信号量来控制
        als_get_data
         mutex_lock(&epl2182_poll_mutex);
         ...............
         mutex_unlock(&epl2182_poll_mutex);
 
       ps_get_data
                       mutex_lock(&epl2182_poll_mutex);
                         ...............
                        mutex_unlock(&epl2182_poll_mutex);
 
     PS在打电话的时候不能休眠:加睡眠锁
       目前的driver架构是对于没有使用中断模式的距离传感器(cust_alsps.c .ps_polling=1)在驱动的i2c_probe里初始化一个wake lock,在Operate函数的ENABLE分支,如果是

enable的话就wake_lock(your_lock),disable的话就wake_unlock(your_lock)

 
 
 

Android ALSPS驱动分析的更多相关文章

  1. 【转】android电池(五):电池 充电IC(PM2301)驱动分析篇

    关键词:android 电池  电量计  PL2301任务初始化宏 power_supply 中断线程化 平台信息:内核:linux2.6/linux3.0系统:android/android4.0  ...

  2. 【转】android电池(四):电池 电量计(MAX17040)驱动分析篇

    关键词:android 电池  电量计  MAX17040 任务初始化宏 power_supply 平台信息:内核:linux2.6/linux3.0系统:android/android4.0 平台: ...

  3. Android USB驱动源码分析(-)

    Android USB驱动中,上层应用协议里最重要的一个文件是android/kernel/drivers/usb/gadget/android.c.这个文件实现USB的上层应用协议. 首先包含了一些 ...

  4. android电池(四):电池 电量计(MAX17040)驱动分析篇【转】

    本文转载自:http://blog.csdn.net/xubin341719/article/details/8969369 电池电量计,库仑计,用max17040这颗电量IC去计量电池电量,这种方法 ...

  5. Qualcomm Android display架构分析

    Android display架构分析(一) http://blog.csdn.net/BonderWu/archive/2010/08/12/5805961.aspx http://hi.baidu ...

  6. 高通Android display架构分析

    目录(?)[-] Kernel Space Display架构介绍 函数和数据结构介绍 函数和数据结构介绍 函数和数据结构介绍 数据流分析 初始化过程分析 User Space display接口 K ...

  7. s5k4ba摄像头驱动分析

    注释: 本驱动是基于S5PV310的,但是全天下的摄像头驱动都是采用V4L2,因此驱动框架流程基本差不多.其中fimc_init_camera()函数会回调.init函数,该函数主要就是通过IIC总线 ...

  8. Android源码分析(六)-----蓝牙Bluetooth源码目录分析

    一 :Bluetooth 的设置应用 packages\apps\Settings\src\com\android\settings\bluetooth* 蓝牙设置应用及设置参数,蓝牙状态,蓝牙设备等 ...

  9. Android源码分析(八)-----系统启动流程&IPC简述

    一 :系统启动流程图 从下往上依次启动linux kernel -->zygote-->SystemServer-->NativeService-->AndroidServic ...

随机推荐

  1. 2020年Java基础超高频面试题汇总(1.2W字详细解析)

    1. Java语言有哪些特点 (1)简单易学.有丰富的类库 (2)面向对象(Java最重要的特性,让程序耦合度更低,内聚性更高) (3)与平台无关性(JVM是Java跨平台使用的根本) (4)可靠安全 ...

  2. 字节跳动2020Java面经,你离高薪就只差一片面试题了

    前言 经历了惨痛的春招与秋招之后,也积攒了一些面经,希望能对大家有所帮助.由于字数限制需要答案的可以关注GZH[程序员空间] 免费领取完整版PDF 其他 什什么是幂等?什什么情况下需要考虑幂等?你怎么 ...

  3. Linux入门到放弃之六《磁盘和文件系统管理三》

    设置磁盘配额 对之前创建的逻辑卷设置磁盘配额,要求用户student对该逻辑卷 容量的软限制是:5G,硬限制是7G,文件个数软限制为:25个,硬限制为30个. (1)首先对/etc/fstab文件进行 ...

  4. java之集合容器(Collection,Map)

    首先我们要了解什么是集合? 正所谓容器,比如说杯子是装水的容器,衣柜是装衣服的容器,那么集合就是装数据的容器. 集合有什么特点呢? 1.集合长度是可变的 2.集合用来存储对象 集合和数组有什么区别呢? ...

  5. 010_Java基础语法

    目录 Java基础语法 注释 单行注释 // 多行注释 /* */ 文档注释 /** */ 标识符 关键字 标识符注意点 数据类型 强类型语言 弱类型语言 Java基础语法 注释 单行注释 // 多行 ...

  6. jmeter 使用总结

    安装和启动(mac) 下载jmeter安装包并解压,进入其bin目录,执行./jmeter.sh或sh jmeter,打开就会出现如下画面 Thread Group 新建线程组,如下图 需要设置的选项 ...

  7. 《Head First 设计模式》:与设计模式相处

    正文 一.设计原则 1.封装变化 找出应用中可能需要变化之处,把它们独立出来,不要和那些不需要变化的代码混在一起. 2.针对接口编程,不针对实现编程 "针对接口编程"真正的意思是& ...

  8. Lte Design Documentation之RRC

    RRC 特点 RRC模型在模拟器中提供以下功能 生成(在eNB中)和解释(在UE中)信息块(尤其是MIB和SIB1, SIB2) 初始化小区选择 RRC连接建立过程 RRC重新配置程序, 支持以下方式 ...

  9. c++11-17 模板核心知识(二)—— 类模板

    类模板声明.实现与使用 Class Instantiation 使用类模板的部分成员函数 Concept 友元 方式一 方式二 类模板的全特化 类模板的偏特化 多模板参数的偏特化 默认模板参数 Typ ...

  10. H5--自动刷新

    每30秒中刷新当前html页面: <meta http-equiv="refresh" content="30">