Linux注册GPIO中断函数注册gpio 25上升沿和下降沿中断函数,⽤于检测休眠唤醒信号。
DTS
quec,quectel-low-consume{
compatible = "quec,quectel-low-consume";
notify_gpio = <&tlmm_pinmux 11 0>; /* which gpio can be controlled by ioctl to notify mcu */
wakeup_gpio = <&tlmm_pinmux 25 0>; /* wakeup pin */
pinctrl-names = "default", "sleep", "wakeup_default"; /* status pin: module sleep indication gpio42 */
pinctrl-0 = <&sleep_ind_active>;
pinctrl-1 = <&sleep_ind_sleep>;
pinctrl-2 = <&wakeup_in_default>; /* wakeup pin default state */
status = "okay"; /* disable by default */
};
wakeup_in_default: wakeup_in_default {
config {
pins = "gpio25";
drive-strength = <2>;
bias-pull-up;
};
};
sleep_ind_active: sleep_ind_active {
mux {
pins = "gpio11";
function = "gpio";
};
config {
pins = "gpio11";
drive-strength = <2>;
bias-disable;
output-low;
};
};
sleep_ind_sleep: sleep_ind_sleep {
mux {
pins = "gpio11";
function = "gpio";
};
config {
pins = "gpio11";
drive-strength = <2>;
bias-disable;
output-high;
};
};
代码
static int notify_gpio = 0;
static int sleep_gpio = 0;
static int wakeup_gpio = 0;
static int wakeup_irq = 0;
static int quectel_low_consume_probe(struct platform_device *pdev)
{
gpio_data = devm_kzalloc(&pdev->dev,
sizeof(struct gpio_pinctrl_info),
GFP_KERNEL);
wakeup_gpio = of_get_named_gpio(pdev->dev.of_node, "wakeup_gpio", 0);
if(quectel_wakeup_init() < 0)
{
printk("[gale] %s: init wakeup gpio fail\n", __func__);
goto err_wakeup_init;
}
notify_gpio = of_get_named_gpio(pdev->dev.of_node, "notify_gpio", 0);
if((ret = gpio_init()) < 0)
{
printk("[gale] %s: notify pin init failed\n", __func__);
goto err_gpio_init;
}
static int quectel_wakeup_init(void)
{
int err;
err = gpio_request(wakeup_gpio, "wakeup_in");
if (err < 0)
{
printk("[gale] %s: request gpio: %d error: %d\n", __func__, wakeup_gpio, err);
goto err_gpio_request;
}
err = gpio_direction_input(wakeup_gpio);
if (err < 0)
{
printk("[gale] %s: set gpio direction input (%d) fail\n", __func__, wakeup_gpio);
goto err_gpio_to_irq;
}
err = gpio_to_irq(wakeup_gpio);
linux下的sleep函数printk("[gale] %s: gpio to irq: %d : %d\n", __func__, wakeup_gpio, err);
if (err < 0)
{
printk("[gale] %s: gpio to irq: %d error: %d\n", __func__, wakeup_gpio, err);
goto err_gpio_to_irq;
}
wakeup_irq = err; //中断号
err = request_any_context_irq(wakeup_irq, quectel_wakeup_irq_func, \
IRQF_TRIGGER_RISING | IRQF_TRIGGER_FALLING, "quectel_wakeup_in", NULL); if (err < 0)
{
printk("[gale] %s: Can't get %d IRQ for wakeup_in: %d\n", __func__, wakeup_irq, err); goto err_gpio_free_irq;
}
中断回调函数,判断对应的⾼低电平执⾏对应动作。
#define LOW_VALUE 0
#define HIGH_VALUE 1
static irqreturn_t quectel_wakeup_irq_func(void)
{
int value = gpio_get_value(wakeup_gpio);
if(value == LOW_VALUE)
{
strcpy(edge, "falling");
kill_fasync(&gpio_async, SIGIO, POLL_IN);
printk(KERN_ERR "eason LOW_VALUE\n");
}
else if(value == HIGH_VALUE)
{
strcpy(edge, "rising");
kill_fasync(&gpio_async, SIGIO, POLL_IN );
printk(KERN_ERR "eason HIGH_VALUE\n");
}
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论