linux驱动杂项设备类misc

misc(杂项设备类) 
 
struct miscdevice  {
int minor; // 次设备号
const char *name; // 设备名
const struct file_operations *fops; // 操作方法
struct list_head list;
struct device *parent; // 私有指针
struct device *this_device; // 指向自己的指针
const char *nodename;
mode_t mode;

};


extern int misc_register(struct miscdevice * misc);
extern int misc_deregister(struct miscdevice *misc);

实例:

misc.c

#include <linux/kernel.h>
#include <linux/module.h>
#include <linux/fs.h>
#include <linux/kdev_t.h>
#include <linux/cdev.h>
#include <asm/uaccess.h>
#include <linux/device.h>
#include <linux/platform_device.h>
#include <linux/ioport.h>
#include <linux/io.h>
#include <linux/delay.h>
#include <linux/miscdevice.h>

#define LED_ON	0
#define LED_OFF 1

struct resource *ptr = NULL;
unsigned long *gpj2con = NULL;

int led_open(struct inode *inode, struct file *file)
{
	printk("led init ....\n");
	int val;
	/* led init */
	val = ioread32(gpj2con);
	val &=~(0xF<<0);
	val |=(0x1<<0);
	iowrite32(val,gpj2con);

	val = ioread32(gpj2con+1);
	val |=(0x1<<0);
	iowrite32(val,gpj2con+1);
	printk("debug_001\n");
	
	return 0;
}

int led_close(struct inode *inode, struct file *file)
{
	printk("led close ....\n");
	
	return 0;
}

void led_on()
{
	int val;
	val = ioread32(gpj2con+1);
	val &=~(0x1<<0);
	iowrite32(val,gpj2con+1);	
}

void led_off()
{
	int val;
	val = ioread32(gpj2con+1);
	val |=(0x1<<0);
	iowrite32(val,gpj2con+1);	
}

int led_ioctl(struct inode *inode,struct file *file,int cmd,int arg)
{
	switch(cmd){
		case LED_ON:
			led_on();
			break;
		case LED_OFF:
			led_off();
			break;
	}
}

struct file_operations led_fops = {
	.open 		= led_open,
	.release 	= led_close,
	.ioctl		= led_ioctl,
};


struct miscdevice led_miscdev ={
	.minor 	= 138,
	.name 	= "led-misc",
	.fops 	= &led_fops,
};

int led_platdev_probe(struct platform_device *pdev)
{
	printk("led driver entry>>>>>>>\n");
	
	int val;
	int phys_addr = pdev->resource[0].start;  // =0xe0200280
	
	ptr = request_mem_region(phys_addr,0x1000,"led-drv");
	if(ptr == NULL)
	{
		printk("request_mem_region\n");
		return -1;
	}
	
	gpj2con = (unsigned long*)ioremap(phys_addr,0x1000);
	if(gpj2con == NULL)
	{
		printk("ioremap fail\n");
		return -1;
	}

	val = misc_register(&led_miscdev);
	if(val < 0)
	{
		printk("misc register fail\n");
		return -1;
	}
	
	return 0;
}

int led_platdev_remove(struct platform_device *pdev)
{
	misc_deregister(&led_miscdev);
	iounmap(gpj2con);
	release_mem_region(0xe0200280,0x1000);
}

struct platform_driver led_platdrv ={
	.driver = {
		.name 	= "led-dev-drv",
	},
	.probe 	= led_platdev_probe, 
	.remove = led_platdev_remove,
};

int __init led_platdrv_init()
{
	printk("led plat drv init \n");
	platform_driver_register(&led_platdrv);	
	return 0;
}

void __exit led_platdrv_exit()
{
	printk("usb drv mouse exit \n");
	platform_driver_unregister(&led_platdrv);
}


module_init(led_platdrv_init);
module_exit(led_platdrv_exit);

MODULE_LICENSE("xx");
MODULE_AUTHOR("xx");
MODULE_DESCRIPTION("xx..");
加载这个杂项类设备驱动,在对应的杂项类cat /sys/class/misc也可以看到创建的。

需要上一篇的insmod dev.c和应用程序测试。
这样你也可以比较上一篇的pdrv.c的设备类。

类都帮我们创建好了设备节点,所以可以直接./app运行测试。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值