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 | |
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, from: pcidev)) { |
60 | mite = kzalloc(sizeof(*mite), GFP_KERNEL); |
61 | if (!mite) |
62 | return; |
63 | |
64 | mite->pcidev = pcidev; |
65 | pci_dev_get(dev: mite->pcidev); |
66 | mite->next = mite_devices; |
67 | mite_devices = mite; |
68 | } |
69 | } |
70 | |
71 | int mite_setup(struct mite_struct *mite) |
72 | { |
73 | u32 addr; |
74 | |
75 | if (pci_enable_device(dev: mite->pcidev)) { |
76 | pr_err("mite: error enabling mite.\n" ); |
77 | return -EIO; |
78 | } |
79 | pci_set_master(dev: 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(offset: 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 | addr = pci_resource_start(mite->pcidev, 1); |
92 | mite->daq_phys_addr = addr; |
93 | mite->daq_io_addr = ioremap(offset: mite->daq_phys_addr, pci_resource_len(mite->pcidev, 1)); |
94 | if (!mite->daq_io_addr) { |
95 | pr_err("mite: failed to remap daq io memory address.\n" ); |
96 | return -ENOMEM; |
97 | } |
98 | writel(val: mite->daq_phys_addr | WENAB, addr: mite->mite_io_addr + MITE_IODWBSR); |
99 | mite->used = 1; |
100 | return 0; |
101 | } |
102 | |
103 | void mite_cleanup(void) |
104 | { |
105 | struct mite_struct *mite, *next; |
106 | |
107 | for (mite = mite_devices; mite; mite = next) { |
108 | next = mite->next; |
109 | if (mite->pcidev) |
110 | pci_dev_put(dev: mite->pcidev); |
111 | kfree(objp: mite); |
112 | } |
113 | } |
114 | |
115 | void mite_unsetup(struct mite_struct *mite) |
116 | { |
117 | if (!mite) |
118 | return; |
119 | if (mite->mite_io_addr) { |
120 | iounmap(addr: mite->mite_io_addr); |
121 | mite->mite_io_addr = NULL; |
122 | } |
123 | if (mite->daq_io_addr) { |
124 | iounmap(addr: mite->daq_io_addr); |
125 | mite->daq_io_addr = NULL; |
126 | } |
127 | if (mite->mite_phys_addr) { |
128 | pci_release_regions(mite->pcidev); |
129 | pci_disable_device(dev: mite->pcidev); |
130 | mite->mite_phys_addr = 0; |
131 | } |
132 | mite->used = 0; |
133 | } |
134 | |