读书人

帮小弟我看看小弟我的中断处理函数为啥

发布时间: 2013-01-01 14:04:18 作者: rapoo

帮我看看我的中断处理函数为啥进不去呢?
帮我看看我的中断处理函数为啥进不去呢?中断能申请成功,cat /proc/interrupts下有usr_gpio,为啥read_interrupt直接进不去,printk("int the read_interrupt\n");这句话直接打印不出来。哪个哥帮看下,小弟感激不敬啊~~~~~~~
~o_o~


#include <linux/miscdevice.h>
#include <linux/delay.h>
#include <linux/interrupt.h>
#include <linux/workqueue.h>
#include <linux/sched.h>
#include <mach/hardware.h>
#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/init.h>
#include <linux/mm.h>
#include <linux/fs.h>
#include <linux/types.h>
#include <linux/delay.h>
#include <linux/moduleparam.h>
#include <linux/slab.h>
#include <linux/errno.h>
#include <linux/ioctl.h>
#include <linux/cdev.h>
#include <linux/string.h>
#include <linux/list.h>
#include <linux/pci.h>
#include <linux/irq.h>

#include <asm/uaccess.h>
#include <asm/atomic.h>
#include <asm/unistd.h>
#include <asm/irq.h>

#include <mach/map.h>
#include <mach/regs-clock.h>
#include <mach/regs-gpio.h>
#include <mach/gpio.h>

#include <plat/gpio-cfg.h>
#include <mach/gpio-bank-e.h>

#define DEVICE_NAME "usr_gpio"

//#define S3C_GPIO_SFN(0) (S3C_GPIO_SPECIAL(0))//输入
//#define S3C_GPIO_SFN(1) (S3C_GPIO_SPECIAL(1))//输出
//#define S3C_GPIO_SFN(3) (S3C_GPIO_SPECIAL(1))//中断

#define GPIO_INPUT_0 S3C64XX_GPF(10)
#define GPIO_OUTPUT_0 S3C64XX_GPK(5)
#define GPIO_INNUM 1
#define GPIO_OUTNUM 1

short temp;
irqreturn_t gpio_irq = 53;
struct workqueue_struct *gpio_queue;
struct work_struct gpio_wq;
void goio_do_work(unsigned long data);

static unsigned long input_table[] = {
GPIO_INPUT_0

};

static unsigned long output_table[] = {
GPIO_OUTPUT_0
};

//中断处理底半部
void gpio_do_work(unsigned long data)
{
int i, val;
for (i = 0; i < GPIO_INNUM; i++)
{
val = gpio_get_value(input_table[i]);
temp |= ((val&0x1) << i);
}
}

static int gpio_input_init(void)
{
int ret = 0, i = 0;
for (i = 0; i < GPIO_INNUM; i++)
{
if (gpio_is_valid(input_table[i]) == -EINVAL)
{
printk("ERROR, GPIO used for input port is using by other devices !");
break;
}
//设置上拉
s3c_gpio_setpull(input_table[i], S3C_GPIO_PULL_DOWN);
//设置为中断
s3c_gpio_cfgpin(input_table[i], S3C_GPIO_SFN(3));
}

return ret;
}

static int gpio_output_init(void)
{
int ret = 0, i = 0;
for (i = 0; i < GPIO_OUTNUM; i++)
{
if (gpio_is_valid(output_table[i]) == -EINVAL)
{
printk("ERROR, GPIO used for output port is using by other devices !");
break;
}
//设置上拉
s3c_gpio_setpull(output_table[i], S3C_GPIO_PULL_UP);
//设置为输出
s3c_gpio_cfgpin(output_table[i], S3C_GPIO_SFN(1));


//设置引脚电平状态
gpio_set_value(output_table[i], 1);
}

return ret;
}

ssize_t gpio_read(struct file *filp, char __user *buf, size_t count, loff_t *f_pos)
{
unsigned long n;
count = sizeof(temp);
printk("temp=%d\n", temp);
n = copy_to_user(&temp, buf, count);
if (n != 0)
{
printk("ERROR, copy to usr error!\n");
return n;
}
else
return count;
}

ssize_t gpio_write(struct file *filp, const char __user *buf, size_t count, loff_t *f_pos)
{
int i = 0;
printk("%d\n", buf[0]);
for (i = 0; i < GPIO_OUTNUM; i++)
{
if(((buf[0]>>i)&0x1)== 1)
gpio_set_value(output_table[i], 1);
if(((buf[0]>>i)&0x1) == 0)
gpio_set_value(output_table[i], 0);
}
return 0;
}

//中断处理顶半部
irqreturn_t read_interrupt(int irq, void *dev_id)
{
printk("int the read_interrupt\n");
queue_work(gpio_queue, &gpio_wq);

return IRQ_HANDLED;
}

static struct file_operations dev_fops = {
.owner = THIS_MODULE,
.read=gpio_read,
.write=gpio_write,

};

static struct miscdevice misc = {
.minor = MISC_DYNAMIC_MINOR,
.name = DEVICE_NAME,
.fops = &dev_fops
};

//设备驱动模块加载函数
static int __init dev_init(void)
{
int ret, result;



//初始化输入输出引脚
gpio_input_init();
gpio_output_init();

//注册混杂设备结构体
ret = misc_register(&misc);
if (ret < 0)
{
printk("ERROR, misc_register error");
return ret;
}

set_irq_type(gpio_irq,IRQF_TRIGGER_RISING);//设置中断触发方式IRQ_TYPE_EDGE_RISING

enable_irq(gpio_irq);
//申请设备中断
result = request_irq(gpio_irq, read_interrupt, IRQF_DISABLED, DEVICE_NAME, NULL);
if (result < 0)
{
printk("IRQ %d cannot be requested.", gpio_irq);
goto gpio_irq_err;
}
gpio_queue = create_workqueue("gpio_queue");
//初始化工作队列
INIT_WORK(&gpio_wq, (void *)gpio_do_work);

printk(DEVICE_NAME"\t initialized\n");

return ret;

gpio_irq_err:
free_irq(gpio_irq, read_interrupt);
return ret;
}

//设备驱动模块卸载函数
static void __exit dev_exit(void)
{
//注销混杂设备结构体
misc_deregister(&misc);
//释放中断
disable_irq(gpio_irq);
free_irq(gpio_irq, read_interrupt);
destroy_workqueue(gpio_queue);
}

module_init(dev_init);
module_exit(dev_exit);
MODULE_LICENSE("GPL");
MODULE_AUTHOR("CAIHUI.");




#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <sys/ioctl.h>
#include <sys/ioctl.h>
#include <sys/types.h>
#include <fcntl.h>
#include <sys/stat.h>

int main(int argc, char **argv)
{
int pin_state;
int pin_no;
int fd;
char n;
unsigned int bytes = 0;

fd = open("/dev/usr_gpio", O_RDWR);


if (fd < 0)
{
perror("open device /dev/usr_gpio");
exit(1);
}

bytes = read(fd, &n, 1);
printf("%d\n", n);
//ioctl(fd, 0, 0);

close(fd);

return 0;
}




CC = arm-linux-gcc
obj-m := gpio_drv.o
PWD := $(shell pwd)
KDIR := /home/huicai/new-work/linux-2.6.38
default:
$(MAKE) -C $(KDIR) M=$(PWD) modules
clean:
$(MAKE) -C $(KDIR) M=$(PWD) clean

[解决办法]
你只是应用层打开这个设备,没有对这个GPIO口进行电平变化操作。要上升沿才能触发中断的。
[解决办法]
你确定你的中断号是对的吗?
[解决办法]
我用你的代码试了下 申请53号中断也没什么错 加载成功了 但是读设备时copy_to_user函数出错 s3c_gpio_cfgpin(input_table[i], S3C_GPIO_SFN(0))改成这样了还是一样的错 可能是引脚配置有问题

读书人网 >驱动开发

热点推荐