Android驱动-霍尔摁键hall_sensor的实现
第一步移植.c文件
将修改好的hall_sensor.c文件放到input路径下
如 drivers/input/hall_sensor.c
第二步Kconfig配置
路径在 drivers/input/Kconfig
第三步Makefile配置
路径在:drivers/input/Makefile
第四步deconfig配置
路径arch/arm/configs/msm8937go_defconfig
第五步设备树配置
路径在arch/arm64/boot/dts/qcom/qm215-qrd.dtsi
第六步(如果上图注释中pinctrl需要配置则需要配置)
第七步 检查是否生效
adb shell 进入后 getevent 事件可以查看是否有设备生效
第八步 新增加hall_sensor.kl文件
新增方法,跳转到查看matrix_keypad.kl的增加
第九步 功能测试
翻盖看是否亮灭(注意是否有磁性)
还可以看cat proc/interrupts 中断是否有产生
hall_sensor.c代码
/*** Copyright (c) 2014-2015, The Linux Foundation. All rights reserved.** This program is free software; you can redistribute it and/or modify* it under the terms of the GNU General Public License version 2 and* only version 2 as published by the Free Software Foundation.** This program is distributed in the hope that it will be useful,* but WITHOUT ANY WARRANTY; without even the implied warranty of* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the* GNU General Public License for more details.**/#include <linux/err.h>
#include <linux/errno.h>
#include <linux/input.h>
#include <linux/irq.h>
#include <linux/gpio.h>
#include <linux/interrupt.h>
#include <linux/slab.h>
#include <linux/pm.h>
#include <linux/module.h>
#include <linux/of_gpio.h>
#include <linux/platform_device.h>#define LID_DEV_NAME "hall_sensor"
#define HALL_INPUT "/dev/input/hall_dev"struct hall_data {int gpio; /* device use gpio number */int irq; /* device request irq number */int active_low; /* gpio active high or low for valid value */bool wakeup; /* device can wakeup system or not */struct input_dev *hall_dev;struct device *dev;
};static irqreturn_t hall_interrupt_handler(int irq, void *dev)
{int value;struct hall_data *data = dev;value = (gpio_get_value_cansleep(data->gpio) ? 1 : 0) ^data->active_low;if (value) {//input_report_key(data->hall_dev, KEY_SLEEP, 1);//input_sync(data->hall_dev);//input_report_key(data->hall_dev, KEY_SLEEP, 0);//input_sync(data->hall_dev);input_report_key(data->hall_dev, FLIP, 0);input_sync(data->hall_dev);dev_info(&data->hall_dev->dev, "near\n");} else {//input_report_key(data->hall_dev, KEY_WAKEUP, 1);//input_sync(data->hall_dev);//input_report_key(data->hall_dev, KEY_WAKEUP, 0);//input_sync(data->hall_dev);input_report_key(data->hall_dev, FLIP, 1);input_sync(data->hall_dev);dev_info(&data->hall_dev->dev, "far\n");}//input_report_key(data->hall_dev, KEY_FLIP, 1);//input_sync(data->hall_dev);//input_report_key(data->hall_dev, KEY_FLIP, 0);input_sync(data->hall_dev);return IRQ_HANDLED;
}static int hall_input_init(struct platform_device *pdev,struct hall_data *data)
{int err = -1;data->hall_dev = devm_input_allocate_device(&pdev->dev);if (!data->hall_dev) {dev_err(&data->hall_dev->dev,"input device allocation failed\n");return -EINVAL;}data->hall_dev->name = LID_DEV_NAME;data->hall_dev->phys = HALL_INPUT;set_bit(EV_KEY, data->hall_dev->evbit);//set_bit(KEY_WAKEUP, data->hall_dev->keybit);//set_bit(KEY_SLEEP, data->hall_dev->keybit);set_bit(FLIP,data->hall_dev->keybit);err = input_register_device(data->hall_dev);if (err < 0) {dev_err(&data->hall_dev->dev,"unable to register input device %s\n",LID_DEV_NAME);return err;}return 0;
}#ifdef CONFIG_OF
static int hall_parse_dt(struct device *dev, struct hall_data *data)
{unsigned int tmp;struct device_node *np = dev->of_node;data->gpio = of_get_named_gpio_flags(dev->of_node,"linux,gpio-int", 0, &tmp);if (!gpio_is_valid(data->gpio)) {dev_err(dev, "hall gpio is not valid\n");return -EINVAL;}data->active_low = tmp & OF_GPIO_ACTIVE_LOW ? 0 : 1;data->wakeup = of_property_read_bool(np, "linux,wakeup");return 0;
}
#else
static int hall_parse_dt(struct device *dev, struct hall_data *data)
{return -EINVAL;
}
#endif// Begin: add by hyangde for hall status show on 220516
static ssize_t hall_status_show(struct device *dev, struct device_attribute *attr, char *buf)
{struct hall_data *pdata = dev_get_drvdata(dev);int value;value = (gpio_get_value_cansleep(pdata->gpio) ? 1 : 0) ^ pdata->active_low;return snprintf(buf, PAGE_SIZE, "%d\n", value);
}static DEVICE_ATTR(hall_status, 0664, hall_status_show, NULL);static struct attribute *hall_attrs[] = {&dev_attr_hall_status.attr,NULL,
};static struct attribute_group hall_attr_group = {.attrs = hall_attrs,
};
// End: add by hyangde for hall status show on 220516 static int hall_driver_probe(struct platform_device *dev)
{struct hall_data *data;int err = 0;int irq_flags;printk("guh hall probe start");dev_info(&dev->dev, "hall_driver probe\n");data = devm_kzalloc(&dev->dev, sizeof(struct hall_data), GFP_KERNEL);if (data == NULL) {err = -ENOMEM;dev_err(&dev->dev,"failed to allocate memory %d\n", err);goto exit;}data->dev = &dev->dev;dev_set_drvdata(&dev->dev, data);if (dev->dev.of_node) {err = hall_parse_dt(&dev->dev, data);if (err < 0) {dev_err(&dev->dev, "Failed to parse device tree\n");goto exit;}} else if (dev->dev.platform_data != NULL) {memcpy(data, dev->dev.platform_data, sizeof(*data));} else {dev_err(&dev->dev, "No valid platform data.\n");err = -ENODEV;goto exit;}err = hall_input_init(dev, data);if (err < 0) {dev_err(&dev->dev, "input init failed\n");goto exit;}if (!gpio_is_valid(data->gpio)) {dev_err(&dev->dev, "gpio is not valid\n");err = -EINVAL;goto free_gpio;}irq_flags = IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING| IRQF_ONESHOT;err = gpio_request_one(data->gpio, GPIOF_DIR_IN, "hall_sensor_irq");if (err) {dev_err(&dev->dev, "unable to request gpio %d\n", data->gpio);goto exit;}data->irq = gpio_to_irq(data->gpio);err = devm_request_threaded_irq(&dev->dev, data->irq, NULL,hall_interrupt_handler,irq_flags, "hall_sensor", data);if (err < 0) {dev_err(&dev->dev, "request irq failed : %d\n", data->irq);goto free_irq;}err = sysfs_create_group(&data->dev->kobj, &hall_attr_group);if (err) {printk(KERN_ERR "%s sysfs_create_group fail\n", __func__);return err;}device_init_wakeup(&dev->dev, data->wakeup);enable_irq_wake(data->irq);printk("guh hall probe end");return 0;free_irq:disable_irq_wake(data->irq);device_init_wakeup(&dev->dev, 0);
free_gpio:gpio_free(data->gpio);
exit:return err;
}static int hall_driver_remove(struct platform_device *dev)
{struct hall_data *data = dev_get_drvdata(&dev->dev);disable_irq_wake(data->irq);device_init_wakeup(&dev->dev, 0);if (data->gpio)gpio_free(data->gpio);return 0;
}static struct platform_device_id hall_id[] = {{LID_DEV_NAME, 0 },{ },
};#ifdef CONFIG_OF
static struct of_device_id hall_match_table[] = {{.compatible = "hall-switch", },{ },
};
#endifstatic struct platform_driver hall_driver = {.driver = {.name = LID_DEV_NAME,.owner = THIS_MODULE,.of_match_table = of_match_ptr(hall_match_table),},.probe = hall_driver_probe,.remove = hall_driver_remove,.id_table = hall_id,
};static int __init hall_init(void)
{return platform_driver_register(&hall_driver);
}static void __exit hall_exit(void)
{platform_driver_unregister(&hall_driver);
}module_init(hall_init);
module_exit(hall_exit);
MODULE_DESCRIPTION("Hall sensor driver");
MODULE_LICENSE("GPL v2");
Android驱动-霍尔摁键hall_sensor的实现相关推荐
- android power 按键,Android Framework层Power键关机流程(一,Power长按键操作处理)
一:Android处理Power按键长按操作 在Framework层中,Android4.x对Power键(KeyEvent.KEYCODE_POWER)的操作,我们从PhoneWindowManag ...
- android power键测试,Android Framework层Power键关机流程(一,Power长按键操作处理)...
一:Android处理Power按键长按操作 在Framework层中,Android4.x对Power键(KeyEvent.KEYCODE_POWER)的操作,我们从PhoneWindowManag ...
- 视频教程-Android驱动深度开发视频教程-驱动/内核开发
Android驱动深度开发视频教程 2003 年毕业于中国科学技术大学,电子专业.软件专业双学位.近10年嵌入式开发经验,曾ZTE公司负责Linux底层系统开发. 近5年作为特聘讲师在若干个有名的培训 ...
- 初入android驱动开发之字符设备(一)
大学毕业,初入公司,招进去的是android驱动开发工程师的岗位,那时候刚进去,首先学到的就是如何搭建kernel.android的编译环境,然后就是了解如何刷设备以及一些最基本的工具.如adb.fa ...
- Android驱动开发之Hello实例(基于高通msm8909)
点击打开链接 Android驱动开发之Hello实例: 驱动部分 modified: kernel/arch/arm/configs/msm8909-1gb_w100_hd720p-perf_de ...
- Android驱动开发之Hello实例
Android驱动开发之Hello实例: 驱动部分 modified: kernel/arch/arm/configs/msm8909-1gb_w100_hd720p-perf_defconfig ...
- android 布局适配虚拟键适配
今天,看到关于虚拟键盘的内容,于是记录一下. 如果是控件,可以直接使用Android:fitsSystemWindows="true"),但是如果是popwindow,那就必须获取 ...
- android底层按键监听,Android应用中Back键的监听及处理实例
MainActivity如下: package cn.testnbackpressed; import android.os.Bundle; import android.view.KeyEvent; ...
- Android应用中Back键的监听及处理
MainActivity如下: package cn.testnbackpressed; import android.os.Bundle; import android.view.KeyEvent; ...
最新文章
- php读取js验证码,PHP + JS 实现验证码功能
- python字符串,列表,字典的常用方法
- bzoj1601: [Usaco2008 Oct]灌水
- jQuery中的ready
- position定位——让人又爱又恨的属性
- python 列表比较不同物质的吸热能力_python列表里面根据一定的条件挑选元素
- 对多用户分时系统最重要_互联网搜索引擎:让你的产品在最显眼的位置摆摊
- seL4操作系统基础06:dataport interface与seL4SharedData connector
- RAC静默安装与DG搭建
- 计算机装调与维护报告,Vmware workstation在计算机装调与维护实训中的应用
- 终极算法【6】——贝叶斯学派
- 移动端产品比较分析:APP、小程序、H5
- 查看电脑ip地址的命令Linux,怎么用ipconfig命令查看自己电脑的IP地址
- 2月12日 模拟题 递推 题解
- VMware虚拟机在Windows10下不兼容解决办法
- 虚拟路由器冗余协议——VRRP
- Espresso环境搭建及其基本使用
- 双显示屏切单显时打不开关掉的显示屏上打开的软件的问题
- 关于spring boot自动注入出现Consider defining a bean of type ‘xxx‘ in your configuration问题解决方案
- 「C位观察」零信任:企业分布式安全管理架构 | C位
热门文章
- 使用POI操作Excel时new XSSFWorkbook ()报错java.lang.NoSuchMethodError解决方式
- 编程题:7-2 复数类的操作
- Linux 入门视频教程
- 同指数幂相减公式_同底指数加减运算法则
- 手把手教如何搭建一个百度网盘目录站点【保姆级】
- MySQL上机第一章,创建S,C,T,SC,TC表
- css溢出文本省略号
- Part 2: CHAPTER 9 Consistency and Consensus
- 论文阅读笔记《Robust Point Matching via Vector Field Consensus》
- 斗鱼主播查询易语言代码