1 // SPDX-License-Identifier: GPL-2.0-only
2 
3 /*
4  *	Hardware driver for NI Mite PCI interface chip,
5  *	adapted from COMEDI
6  *
7  *	Copyright (C) 1997-8 David A. Schleef
8  *	Copyright (C) 2002 Frank Mori Hess
9  *
10  *	The PCI-MIO E series driver was originally written by
11  *	Tomasz Motylewski <...>, and ported to comedi by ds.
12  *
13  *	References for specifications:
14  *
15  *	   321747b.pdf  Register Level Programmer Manual (obsolete)
16  *	   321747c.pdf  Register Level Programmer Manual (new)
17  *	   DAQ-STC reference manual
18  *
19  *	Other possibly relevant info:
20  *
21  *	   320517c.pdf  User manual (obsolete)
22  *	   320517f.pdf  User manual (new)
23  *	   320889a.pdf  delete
24  *	   320906c.pdf  maximum signal ratings
25  *	   321066a.pdf  about 16x
26  *	   321791a.pdf  discontinuation of at-mio-16e-10 rev. c
27  *	   321808a.pdf  about at-mio-16e-10 rev P
28  *	   321837a.pdf  discontinuation of at-mio-16de-10 rev d
29  *	   321838a.pdf  about at-mio-16de-10 rev N
30  */
31 
32 #include <linux/module.h>
33 #include <linux/kernel.h>
34 #include <linux/errno.h>
35 #include <linux/ioport.h>
36 #include <linux/delay.h>
37 #include <linux/mm.h>
38 #include <linux/interrupt.h>
39 #include <linux/pci.h>
40 #include <linux/io.h>
41 #include <linux/slab.h>
42 
43 #include "mite.h"
44 
45 #define PCI_MITE_SIZE		4096
46 #define PCI_DAQ_SIZE		4096
47 
48 struct mite_struct *mite_devices;
49 
50 #define TOP_OF_PAGE(x) ((x) | (~(PAGE_MASK)))
51 
mite_init(void)52 void mite_init(void)
53 {
54 	struct pci_dev *pcidev;
55 	struct mite_struct *mite;
56 
57 	for (pcidev = pci_get_device(PCI_VENDOR_ID_NATINST, PCI_ANY_ID, NULL);
58 		pcidev;
59 		pcidev = pci_get_device(PCI_VENDOR_ID_NATINST, PCI_ANY_ID, pcidev)) {
60 		mite = kzalloc(sizeof(*mite), GFP_KERNEL);
61 		if (!mite)
62 			return;
63 
64 		mite->pcidev = pcidev;
65 		pci_dev_get(mite->pcidev);
66 		mite->next = mite_devices;
67 		mite_devices = mite;
68 	}
69 }
70 
mite_setup(struct mite_struct * mite)71 int mite_setup(struct mite_struct *mite)
72 {
73 	u32 addr;
74 
75 	if (pci_enable_device(mite->pcidev)) {
76 		pr_err("mite: error enabling mite.\n");
77 		return -EIO;
78 	}
79 	pci_set_master(mite->pcidev);
80 	if (pci_request_regions(mite->pcidev, "mite")) {
81 		pr_err("mite: failed to request mite io regions.\n");
82 		return -EIO;
83 	}
84 	addr = pci_resource_start(mite->pcidev, 0);
85 	mite->mite_phys_addr = addr;
86 	mite->mite_io_addr = ioremap(addr, pci_resource_len(mite->pcidev, 0));
87 	if (!mite->mite_io_addr) {
88 		pr_err("mite: failed to remap mite io memory address.\n");
89 		return -ENOMEM;
90 	}
91 	pr_info("mite: 0x%08lx mapped to %p\n", mite->mite_phys_addr, mite->mite_io_addr);
92 	addr = pci_resource_start(mite->pcidev, 1);
93 	mite->daq_phys_addr = addr;
94 	mite->daq_io_addr = ioremap(mite->daq_phys_addr, pci_resource_len(mite->pcidev, 1));
95 	if (!mite->daq_io_addr)	{
96 		pr_err("mite: failed to remap daq io memory address.\n");
97 		return -ENOMEM;
98 	}
99 	pr_info("mite: daq: 0x%08lx mapped to %p\n", mite->daq_phys_addr, mite->daq_io_addr);
100 	writel(mite->daq_phys_addr | WENAB, mite->mite_io_addr + MITE_IODWBSR);
101 	mite->used = 1;
102 	return 0;
103 }
104 
mite_cleanup(void)105 void mite_cleanup(void)
106 {
107 	struct mite_struct *mite, *next;
108 
109 	for (mite = mite_devices; mite; mite = next) {
110 		next = mite->next;
111 		if (mite->pcidev)
112 			pci_dev_put(mite->pcidev);
113 		kfree(mite);
114 	}
115 }
116 
mite_unsetup(struct mite_struct * mite)117 void mite_unsetup(struct mite_struct *mite)
118 {
119 	if (!mite)
120 		return;
121 	if (mite->mite_io_addr)	{
122 		iounmap(mite->mite_io_addr);
123 		mite->mite_io_addr = NULL;
124 	}
125 	if (mite->daq_io_addr) {
126 		iounmap(mite->daq_io_addr);
127 		mite->daq_io_addr = NULL;
128 	}
129 	if (mite->mite_phys_addr) {
130 		pci_release_regions(mite->pcidev);
131 		pci_disable_device(mite->pcidev);
132 		mite->mite_phys_addr = 0;
133 	}
134 	mite->used = 0;
135 }
136 
mite_list_devices(void)137 void mite_list_devices(void)
138 {
139 	struct mite_struct *mite, *next;
140 
141 	pr_info("Available NI PCI device IDs:");
142 	if (mite_devices)
143 		for (mite = mite_devices; mite; mite = next) {
144 			next = mite->next;
145 			pr_info(" 0x%04x", mite_device_id(mite));
146 			if (mite->used)
147 				pr_info("(used)");
148 	}
149 	pr_info("\n");
150 }
151