⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 uio_cif.c

📁 linux 内核源代码
💻 C
字号:
/* * UIO Hilscher CIF card driver * * (C) 2007 Hans J. Koch <hjk@linutronix.de> * Original code (C) 2005 Benedikt Spranger <b.spranger@linutronix.de> * * Licensed under GPL version 2 only. * */#include <linux/device.h>#include <linux/module.h>#include <linux/pci.h>#include <linux/uio_driver.h>#include <asm/io.h>#ifndef PCI_DEVICE_ID_PLX_9030#define PCI_DEVICE_ID_PLX_9030	0x9030#endif#define PLX9030_INTCSR		0x4C#define INTSCR_INT1_ENABLE	0x01#define INTSCR_INT1_STATUS	0x04#define INT1_ENABLED_AND_ACTIVE	(INTSCR_INT1_ENABLE | INTSCR_INT1_STATUS)#define PCI_SUBVENDOR_ID_PEP	0x1518#define CIF_SUBDEVICE_PROFIBUS	0x430#define CIF_SUBDEVICE_DEVICENET	0x432static irqreturn_t hilscher_handler(int irq, struct uio_info *dev_info){	void __iomem *plx_intscr = dev_info->mem[0].internal_addr					+ PLX9030_INTCSR;	if ((ioread8(plx_intscr) & INT1_ENABLED_AND_ACTIVE)	    != INT1_ENABLED_AND_ACTIVE)		return IRQ_NONE;	/* Disable interrupt */	iowrite8(ioread8(plx_intscr) & ~INTSCR_INT1_ENABLE, plx_intscr);	return IRQ_HANDLED;}static int __devinit hilscher_pci_probe(struct pci_dev *dev,					const struct pci_device_id *id){	struct uio_info *info;	info = kzalloc(sizeof(struct uio_info), GFP_KERNEL);	if (!info)		return -ENOMEM;	if (pci_enable_device(dev))		goto out_free;	if (pci_request_regions(dev, "hilscher"))		goto out_disable;	info->mem[0].addr = pci_resource_start(dev, 0);	if (!info->mem[0].addr)		goto out_release;	info->mem[0].internal_addr = ioremap(pci_resource_start(dev, 0),					     pci_resource_len(dev, 0));	if (!info->mem[0].internal_addr)		goto out_release;	info->mem[0].size = pci_resource_len(dev, 0);	info->mem[0].memtype = UIO_MEM_PHYS;	info->mem[1].addr = pci_resource_start(dev, 2);	info->mem[1].size = pci_resource_len(dev, 2);	info->mem[1].memtype = UIO_MEM_PHYS;	switch (id->subdevice) {		case CIF_SUBDEVICE_PROFIBUS:			info->name = "CIF_Profibus";			break;		case CIF_SUBDEVICE_DEVICENET:			info->name = "CIF_Devicenet";			break;		default:			info->name = "CIF_???";	}	info->version = "0.0.1";	info->irq = dev->irq;	info->irq_flags = IRQF_DISABLED | IRQF_SHARED;	info->handler = hilscher_handler;	if (uio_register_device(&dev->dev, info))		goto out_unmap;	pci_set_drvdata(dev, info);	return 0;out_unmap:	iounmap(info->mem[0].internal_addr);out_release:	pci_release_regions(dev);out_disable:	pci_disable_device(dev);out_free:	kfree (info);	return -ENODEV;}static void hilscher_pci_remove(struct pci_dev *dev){	struct uio_info *info = pci_get_drvdata(dev);	uio_unregister_device(info);	pci_release_regions(dev);	pci_disable_device(dev);	pci_set_drvdata(dev, NULL);	iounmap(info->mem[0].internal_addr);	kfree (info);}static struct pci_device_id hilscher_pci_ids[] = {	{		.vendor =	PCI_VENDOR_ID_PLX,		.device =	PCI_DEVICE_ID_PLX_9030,		.subvendor =	PCI_SUBVENDOR_ID_PEP,		.subdevice =	CIF_SUBDEVICE_PROFIBUS,	},	{		.vendor =	PCI_VENDOR_ID_PLX,		.device =	PCI_DEVICE_ID_PLX_9030,		.subvendor =	PCI_SUBVENDOR_ID_PEP,		.subdevice =	CIF_SUBDEVICE_DEVICENET,	},	{ 0, }};static struct pci_driver hilscher_pci_driver = {	.name = "hilscher",	.id_table = hilscher_pci_ids,	.probe = hilscher_pci_probe,	.remove = hilscher_pci_remove,};static int __init hilscher_init_module(void){	return pci_register_driver(&hilscher_pci_driver);}static void __exit hilscher_exit_module(void){	pci_unregister_driver(&hilscher_pci_driver);}module_init(hilscher_init_module);module_exit(hilscher_exit_module);MODULE_LICENSE("GPL v2");MODULE_AUTHOR("Hans J. Koch, Benedikt Spranger");

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -