IT数码 购物 网址 头条 软件 日历 阅读 图书馆
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
图片批量下载器
↓批量下载图片,美女图库↓
图片自动播放器
↓图片自动播放器↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁
 
   -> 移动开发 -> [Android驱动] 高通 Q PNP Flash LED驱动 及上层调用的流程 -> 正文阅读

[移动开发][Android驱动] 高通 Q PNP Flash LED驱动 及上层调用的流程

直白的记录一下,翻译的文件来自kernel:

kernel/documentation/devicetree/bindings/leds/leds-qpnp-flash.txt

---------------

QPNP (Qualcomm Technologies Plug N Play) Flash LED,

用于在相机sensor拍照时,背景比较暗时能拍出更好的图片。

它是高通平台上PMIC的一部分。PMIC通过SPMI连接到主机处理器。

(也就是说,这玩意就是高通平台的闪光灯和手电筒驱动)

-----------

dsti节点:? ? ? ?

compatible :? ? ? ? "qcom, qpnp-flash-led"

qcom, startup-dly:   delay before flashing after flash excuted(value: 10, 32, 64 ,128us)

qcom, thermal-derate-threshold: thermal threshold for derate, (80,100摄氏度这种)

--------------------------
Example:
    qcom,leds@d300 {
        compatible = "qcom,qpnp-flash-led";
        status = "okay";
        reg = <0xd300 0x100>;
        label = "flash";
        qcom,headroom = <500>;
        qcom,startup-dly = <128>;
        qcom,clamp-curr = <200>;
        qcom,pmic-charger-support;
        qcom,self-check-enabled;
        qcom,thermal-derate-enabled;
        qcom,thermal-derate-threshold = <80>;
        qcom,thermal-derate-rate = "4_PERCENT";
        qcom,current-ramp-enabled;
        qcom,ramp_up_step = "27US";
        qcom,ramp_dn_step = "27US";
        qcom,vph-pwr-droop-enabled;
        qcom,vph-pwr-droop-threshold = <3200>;
        qcom,vph-pwr-droop-debounce-time = <10>;
        qcom,headroom-sense-ch0-enabled;
        qcom,headroom-sense-ch1-enabled;

        pm8226_flash0: qcom,flash_0 {
            label = "flash";
            qcom,led-name = "led:flash_0";
            qcom,default-led-trigger =
                    "flash0_trigger";
            qcom,max-current = <1000>;
            qcom,duration = <1280>;
            qcom,id = <0>;
            qcom,current = <625>;
            boost-supply = <&pm8226_chg_boost>;
        };

        pm8226_torch: qcom,torch_0 {
            label = "torch";
            qcom,led-name = "led:torch_0";
            qcom,default-led-trigger =
                    "torch0_trigger";
            boost-supply = <&pm8226_chg_boost>;
            qcom,max-current = <200>;
            qcom,id = <0>;
            qcom,current = <120>;
            boost-voltage-max = <3600000>;
        };
    };

-----------------

驱动:

? ? ? ? spmi_driver_register(&qpnp_flash_led_driver);

(spmi:连接soc的集成电源控制器和电源管理IC)

结构体是struct qpnp_flash_led {
       struct spmi_device;
       struct flash_led_platform_data *pdata;
       
       //flash_node_data结构记录了一些灯的控制参数

       struct flash_node_data *flash_node;                
       struct power_supply    *battery_psy;
       struct muxtext         flash_led_lock;
       int num_leds;
       u16 base;
       u8  peripheral_type;
}

记录一下驱动代码的结构:

spmi_driver_register(&qpnp_flash_led_driver);        //注册驱动,匹配device, 进入probe
               |
qpnp_flash_led_probe(struct spmi_device *spmi)
               |
                --- a. 申请qpnp_flash_led空间

                ----b. qpnp_flash_led_parse_common_dt(led, node)    //解析dtsi

                ----c. 申请flash_node_data实例的空间,初始化填充dtsi里面的参数
                       初始化了两个函数指针成员
                                brightness_set = qpnp_flash_led_brightness_set
                                brightness_get = qpnp_flash_led_brightness_get
                
                ---d. INIT_WORK(&led->flash_node[i].work, qpnp_flash_led_work);

                ---e. led_class_dev_register(&spmi->dev, &led->flash_node[i]->dev);

                ---f. 然后是dtsli解析第二层的节点,区分是闪光灯还是手电筒的
                       qpnp_flash_led_parse_each_led_dt(led, &led->flash_node[i])

                 ---g. 分别创建了文件节点
                        sysfs_create_file(&led->flash_node[i].cdev.dev->kobj, &qpnp_flash_led_attrs[j].attr);

-------------
驱动就是这个架子

    主要的函数就是 static void qpnp_flash_led_work(struct work_struct *work);

    这个里面的if...else判断了手电筒和闪光灯,功能函数是通过qpnp_ledmasked_write来操作的,该函数可以通过地址等参数来设置灯使能以及亮度。

函数:
    //kernel/driver/leds/leds-qpnp-flash.c
    static int qpnp_led_masked_write(struct spmi_device *spmi_dev, u16 addr, u8 mask, u8 val);    
    

---------------------driver end----------------------

那么上层应用是怎么个调用的呢 ?

App里面打开手电筒就是

        private CameraManger manager;
        manager = (Cameramanager)getSystemService(Context.CAMERA_SERVICE);
        manager.setTorchMode("0", true);

--------
流程:

    manager.setTorchMode
            |
    cameraManager.seTorchMode   //frameworks/base/core/java/android/hardware/camera2/CameraManager.java      
            |
    cameraService.setTorchMode(cameraId, enabled, mTorchClientBinder) //frameworks/base/core/java/android/hardware/camera2/CameraManager.java  
            |
    CameraService:setTorchMode(const String& cameraId, bool enabled, const sp<IBinder>& clienBinder)        //frameworks/av/services/camera/libcameraservice/CameraService.cpp
            |
        err = mFlashlight->setTorchMode(id, enabled);        //mFlashlight = new CameraFlashlight(*mModule, *this);
            |
    CameraFlashlight::setTorchMode(const String8& cameraId, bool enabled)        //frameworks/av/services/camera/libcameraservice/CameraFlashlight.cpp
            |
        res = mFlashControl->setTorchMode(cameraId, enabled);        // mFlashControl = new ModuleFlashControl(*mCameraModule, *mCallbacks);
            |
        mCameraModule->setTorchMode(cameraId.toString, enabled);
            |
    CameraModule::setTorchMode(const char* camera_id, bool enable);    //frameworks/av/services/camera/libcameraservice/common/CameraModule.cpp
            |
        res = mModule->set_torch_mode(cameraid, enable);    //Camera_module_t 
            |
            |
    终 于 到 HAL 层 了 
            |
 迷了还在看,怎么在hardware里看不到set_torch_mode原型 ??      

晚上全局搜了,很奇怪没搜到。。。按道理有个c文件里面gpio_device_t的结构赋值这个函数指针啊。。。。。。。先记录一下

?

  移动开发 最新文章
Vue3装载axios和element-ui
android adb cmd
【xcode】Xcode常用快捷键与技巧
Android开发中的线程池使用
Java 和 Android 的 Base64
Android 测试文字编码格式
微信小程序支付
安卓权限记录
知乎之自动养号
【Android Jetpack】DataStore
上一篇文章      下一篇文章      查看所有文章
加:2021-08-26 12:13:18  更:2021-08-26 12:14:48 
 
开发: C++知识库 Java知识库 JavaScript Python PHP知识库 人工智能 区块链 大数据 移动开发 嵌入式 开发工具 数据结构与算法 开发测试 游戏开发 网络协议 系统运维
教程: HTML教程 CSS教程 JavaScript教程 Go语言教程 JQuery教程 VUE教程 VUE3教程 Bootstrap教程 SQL数据库教程 C语言教程 C++教程 Java教程 Python教程 Python3教程 C#教程
数码: 电脑 笔记本 显卡 显示器 固态硬盘 硬盘 耳机 手机 iphone vivo oppo 小米 华为 单反 装机 图拉丁

360图书馆 购物 三丰科技 阅读网 日历 万年历 2025年3日历 -2025/3/4 15:34:01-

图片自动播放器
↓图片自动播放器↓
TxT小说阅读器
↓语音阅读,小说下载,古典文学↓
一键清除垃圾
↓轻轻一点,清除系统垃圾↓
图片批量下载器
↓批量下载图片,美女图库↓
  网站联系: qq:121756557 email:121756557@qq.com  IT数码