read函数中wait_event_interruptible无法唤醒,求助。
问题简介:
1,CPU的一个GPIO口配置为中断响应功能(以确定该口可以配置为中断),高电平触发,该口连接功能芯片的的IRQ口,IRQ口平时为低电平,当有数据要发送给CPU时,IRQ变为高电平,然后CPU读取数据。
2,现在的问题是下面的read函数可以读取第一帧数据,但是之后再调用时会一直挂在wait_event_interruptible处,表现为wait_event_interruptible长时间没有退出。通过示波器观察,确实是有一个中断产生的,IRQ线有一个向高跳变。
求教大家,可能的原因和解决方法,非常感谢。
源码如下:
static ssize_t scull_dev_read(struct file *filp, char __user *buf,
size_t count, loff_t *offset)
{
struct scull_dev *scull_dev = filp->private_data;
char tmp[MAX_BUFFER_SIZE];
int ret;
mutex_lock(&scull_dev->read_mutex);
if (!gpio_get_value(scull_dev->irq_gpio)) {
if (filp->f_flags & O_NONBLOCK) {
ret = -EAGAIN;
goto fail;
}
scull_dev->irq_enabled = true;
enable_irq(scull_dev->client->irq);
ret = wait_event_interruptible(scull_dev->read_wq,
gpio_get_value(scull_dev->irq_gpio));
scull_disable_irq(scull_dev);
if (ret)
goto fail;
}
/* Read data */
ret = i2c_master_recv(scull_dev->client, tmp, count);
mutex_unlock(&scull_dev->read_mutex);
if (ret < 0) {
pr_err("%s: i2c_master_recv returned %d\n", __func__, ret);
return ret;
}
if (ret > count) {
pr_err("%s: received too many bytes from i2c (%d)\n",
__func__, ret);
return -EIO;
}
if (copy_to_user(buf, tmp, ret)) {
pr_warning("%s : failed to copy to user space\n", __func__);
return -EFAULT;
}
return ret;
fail:
mutex_unlock(&scull_dev->read_mutex);
return ret;
}