主题 : 最近搞了个最简单的驱动,可是就是没办法工作,高手们帮忙看下 复制链接 | 浏览器收藏 | 打印
级别: 新手上路
UID: 63069
精华: 0
发帖: 3
金钱: 15 两
威望: 3 点
综合积分: 6 分
注册时间: 2012-02-13
最后登录: 2012-05-05
楼主  发表于: 2012-05-05 18:13

 最近搞了个最简单的驱动,可是就是没办法工作,高手们帮忙看下

我把我现在的问题说一下,请高人指点下。

我用#insmod uart.ko 装载程序;
用#cat /proc/devices 看一下驱动程序的主设备号为:
252 uart

创建设备节点#mknod /dev/uart c 252 0

之后运行应用程序,得到输出结果是:
open start!  
open error: -1

可是我很迷惑是哪里出了差错;请高手指点迷津。

下面是我的驱动源程序:

#define rMPLLCON (*(volatile unsigned *)0x7E00F010)
#define rCLKDIVN (*(volatile unsigned *)0X7E00F020)  

#define rGPFCON (*(volatile unsigned *)(0x7F0080A0))
#define rGPFDAT (*(volatile unsigned *)(0x7F0080A4))
#define rGPFPUD (*(volatile unsigned *)(0x7F0080A8))


#include<linux/module.h>
#include<linux/version.h>
#include<linux/init.h>
#include<linux/fs.h>
#include<linux/cdev.h>
#include<linux/kernel.h>
#include<linux/stat.h>
#include<linux/errno.h>
#include<linux/kdev_t.h>
#include<linux/types.h>

#define NAME "uart"
MODULE_LICENSE("Dual BSD/GPL");
static dev_t uart_minor=0;
static dev_t uart_major=0;
void delay(void);

struct cdev *my_cdev;
static int uart_release(struct inode *inode, struct file *filp);
static int uart_ioctl(struct file * filp, unsigned int cmd, unsigned long arg);
static int uart_open(struct inode * inode, struct file *filp);

struct file_operations uart_fops =
{
.owner = THIS_MODULE,
.unlocked_ioctl = uart_ioctl,
.open = uart_open,
.release = uart_release,

};
static int uart_ioctl(struct file * filp, unsigned int cmd, unsigned long arg)
{
//int data = arg;
switch(cmd)
{

case 0:
rGPFDAT = (rGPFDAT & ~(0xfU<<14)) | (0x3<<14);
delay();break;
case 1:
rGPFDAT = (rGPFDAT & ~(0xfu<<14));
delay();
break;
}
return 0;
}

static int uart_release(struct inode *inode, struct file *filp)
{
return 0;
}

static int uart_open(struct inode * inode, struct file *filp)
{
rGPFCON = (rGPFCON & ~(0x0fU<<28))|(0x5U<<28);
rGPFPUD = (rGPFPUD & ~(0x0fU<<28))|(0xaU<<28);

return 0;
}

static int __init uart_init()
{
int result = 0, i;
dev_t dev = MKDEV(uart_major,0);
i =register_chrdev_region(dev,1,NAME);
if(i<0)
{
printk(KERN_ALERT "alloc char dev region!");
result = alloc_chrdev_region(&dev,0,1,NAME);
uart_major = MAJOR(dev);
uart_minor = MINOR(dev);
if(result<0)
return result;
}
my_cdev = cdev_alloc();
int err,devno = MKDEV(uart_major, uart_minor);

cdev_init(my_cdev,&uart_fops);
my_cdev->owner = THIS_MODULE;
my_cdev->ops = &uart_fops;

err = cdev_add(my_cdev,devno,1);
if(err)
printk(KERN_NOTICE "Error %d adding uart\n",err);
printk(KERN_ALERT "init OK!\n");
return 0;
}

static int __exit uart_exit()
{
cdev_del(my_cdev);
unregister_chrdev_region(MKDEV(uart_major,0),1);
printk(KERN_ALERT "UART removed!\n");
return 0;
}
void delay(void)
{
unsigned int k;
  for(k = 0; k < 2000000; k++);
}
module_exit(uart_exit);
module_init(uart_init);

我的makefile如下:
obj-m := uart.o
KERNELDIR := /home/linux-2.6.38
PWD := $(shell pwd)

modules :
$(MAKE) -C $(KERNELDIR) M=$(PWD) modules

modules_install :
$(MAKE) -C $(KERNELDIR) M=$(PWD) modules_install
.PHONY:clean
clean:
rm -f *.o *.ko *.mod.c *symvers *order


下面是我写的应用程序:
#include<stdlib.h>
#include<stdio.h>
#include<fcntl.h>
int main()
{
int fd;
int loop,num;
printf("open start!\n");
fd = open("/dev/uart",O_RDWR);
if(fd < 0) {
printf("open error: %d\n",fd);
return 0;
}
printf("open OK!\n");
loop = 0;
while(loop < 10) {
ioctl(fd,1,1);
sleep(1);
ioctl(fd,1,2);
loop++;
}
close(fd);
exit(0);
}
级别: 侠客
UID: 24708
精华: 0
发帖: 94
金钱: 480 两
威望: 96 点
综合积分: 188 分
注册时间: 2010-07-13
最后登录: 2023-04-23
1楼  发表于: 2012-05-08 10:09
把open函数只return 0看