~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

TOMOYO Linux Cross Reference
Linux/arch/mips/vr41xx/common/vrc4173.c

Version: ~ [ linux-5.1-rc1 ] ~ [ linux-5.0.3 ] ~ [ linux-4.20.17 ] ~ [ linux-4.19.30 ] ~ [ linux-4.18.20 ] ~ [ linux-4.17.19 ] ~ [ linux-4.16.18 ] ~ [ linux-4.15.18 ] ~ [ linux-4.14.107 ] ~ [ linux-4.13.16 ] ~ [ linux-4.12.14 ] ~ [ linux-4.11.12 ] ~ [ linux-4.10.17 ] ~ [ linux-4.9.164 ] ~ [ linux-4.8.17 ] ~ [ linux-4.7.10 ] ~ [ linux-4.6.7 ] ~ [ linux-4.5.7 ] ~ [ linux-4.4.176 ] ~ [ linux-4.3.6 ] ~ [ linux-4.2.8 ] ~ [ linux-4.1.52 ] ~ [ linux-4.0.9 ] ~ [ linux-3.19.8 ] ~ [ linux-3.18.136 ] ~ [ linux-3.17.8 ] ~ [ linux-3.16.63 ] ~ [ linux-3.15.10 ] ~ [ linux-3.14.79 ] ~ [ linux-3.13.11 ] ~ [ linux-3.12.74 ] ~ [ linux-3.11.10 ] ~ [ linux-3.10.108 ] ~ [ linux-3.9.11 ] ~ [ linux-3.8.13 ] ~ [ linux-3.7.10 ] ~ [ linux-3.6.11 ] ~ [ linux-3.5.7 ] ~ [ linux-3.4.113 ] ~ [ linux-3.3.8 ] ~ [ linux-3.2.102 ] ~ [ linux-3.1.10 ] ~ [ linux-3.0.101 ] ~ [ linux-2.6.39.4 ] ~ [ linux-2.6.38.8 ] ~ [ linux-2.6.37.6 ] ~ [ linux-2.6.36.4 ] ~ [ linux-2.6.35.14 ] ~ [ linux-2.6.34.15 ] ~ [ linux-2.6.33.20 ] ~ [ linux-2.6.32.71 ] ~ [ linux-2.6.0 ] ~ [ linux-2.4.37.11 ] ~ [ unix-v6-master ] ~ [ ccs-tools-1.8.5 ] ~ [ policy-sample ] ~
Architecture: ~ [ i386 ] ~ [ alpha ] ~ [ m68k ] ~ [ mips ] ~ [ ppc ] ~ [ sparc ] ~ [ sparc64 ] ~

  1 /*
  2  * FILE NAME
  3  *      drivers/char/vrc4173.c
  4  * 
  5  * BRIEF MODULE DESCRIPTION
  6  *      NEC VRC4173 driver for NEC VR4122/VR4131.
  7  *
  8  * Author: Yoichi Yuasa
  9  *         yyuasa@mvista.com or source@mvista.com
 10  *
 11  * Copyright 2001,2002 MontaVista Software Inc.
 12  *
 13  *  This program is free software; you can redistribute it and/or modify it
 14  *  under the terms of the GNU General Public License as published by the
 15  *  Free Software Foundation; either version 2 of the License, or (at your
 16  *  option) any later version.
 17  *
 18  *  THIS SOFTWARE IS PROVIDED ``AS IS'' AND ANY EXPRESS OR IMPLIED
 19  *  WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 20  *  MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
 21  *  IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT,
 22  *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
 23  *  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
 24  *  OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
 25  *  ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR
 26  *  TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE
 27  *  USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 28  *
 29  *  You should have received a copy of the GNU General Public License along
 30  *  with this program; if not, write to the Free Software Foundation, Inc.,
 31  *  675 Mass Ave, Cambridge, MA 02139, USA.
 32  */
 33 #include <linux/config.h>
 34 #include <linux/init.h>
 35 #include <linux/module.h>
 36 #include <linux/interrupt.h>
 37 #include <linux/irq.h>
 38 #include <linux/pci.h>
 39 #include <linux/types.h>
 40 
 41 #include <asm/vr41xx/vr41xx.h>
 42 #include <asm/vr41xx/vrc4173.h>
 43 
 44 MODULE_DESCRIPTION("NEC VRC4173 driver for NEC VR4122/4131");
 45 MODULE_AUTHOR("Yoichi Yuasa <yyuasa@mvista.com>");
 46 MODULE_LICENSE("GPL");
 47 
 48 #define VRC4173_CMUCLKMSK       0x040
 49 #define VRC4173_CMUSRST         0x042
 50 
 51 #define VRC4173_SELECTREG       0x09e
 52 
 53 #define VRC4173_SYSINT1REG      0x060
 54 #define VRC4173_MSYSINT1REG     0x06c
 55 
 56 static struct pci_device_id vrc4173_table[] = {
 57         {PCI_VENDOR_ID_NEC, PCI_DEVICE_ID_NEC_VRC4173, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0},
 58         {0, }
 59 };
 60 
 61 unsigned long vrc4173_io_offset = 0;
 62 
 63 EXPORT_SYMBOL(vrc4173_io_offset);
 64 
 65 static u16 vrc4173_cmuclkmsk;
 66 static int vrc4173_initialized;
 67 
 68 void vrc4173_clock_supply(u16 mask)
 69 {
 70         if (vrc4173_initialized) {
 71                 vrc4173_cmuclkmsk |= mask;
 72                 vrc4173_outw(vrc4173_cmuclkmsk, VRC4173_CMUCLKMSK);
 73         }
 74 }
 75 
 76 void vrc4173_clock_mask(u16 mask)
 77 {
 78         if (vrc4173_initialized) {
 79                 vrc4173_cmuclkmsk &= ~mask;
 80                 vrc4173_outw(vrc4173_cmuclkmsk, VRC4173_CMUCLKMSK);
 81         }
 82 }
 83 
 84 static inline void vrc4173_cmu_init(void)
 85 {
 86         vrc4173_cmuclkmsk = vrc4173_inw(VRC4173_CMUCLKMSK);
 87 }
 88 
 89 EXPORT_SYMBOL(vrc4173_clock_supply);
 90 EXPORT_SYMBOL(vrc4173_clock_mask);
 91 
 92 void vrc4173_select_function(int func)
 93 {
 94         u16 val;
 95 
 96         if (vrc4173_initialized) {
 97                 val = vrc4173_inw(VRC4173_SELECTREG);
 98                 switch(func) {
 99                 case PS2CH1_SELECT:
100                         val |= 0x0004;
101                         break;
102                 case PS2CH2_SELECT:
103                         val |= 0x0002;
104                         break;
105                 case TOUCHPANEL_SELECT:
106                         val &= 0x0007;
107                         break;
108                 case KIU8_SELECT:
109                         val &= 0x000e;
110                         break;
111                 case KIU10_SELECT:
112                         val &= 0x000c;
113                         break;
114                 case KIU12_SELECT:
115                         val &= 0x0008;
116                         break;
117                 case GPIO_SELECT:
118                         val |= 0x0008;
119                         break;
120                 }
121                 vrc4173_outw(val, VRC4173_SELECTREG);
122         }
123 }
124 
125 EXPORT_SYMBOL(vrc4173_select_function);
126 
127 static void enable_vrc4173_irq(unsigned int irq)
128 {
129         u16 val;
130 
131         val = vrc4173_inw(VRC4173_MSYSINT1REG);
132         val |= (u16)1 << (irq - VRC4173_IRQ_BASE);
133         vrc4173_outw(val, VRC4173_MSYSINT1REG);
134 }
135 
136 static void disable_vrc4173_irq(unsigned int irq)
137 {
138         u16 val;
139 
140         val = vrc4173_inw(VRC4173_MSYSINT1REG);
141         val &= ~((u16)1 << (irq - VRC4173_IRQ_BASE));
142         vrc4173_outw(val, VRC4173_MSYSINT1REG);
143 }
144 
145 static unsigned int startup_vrc4173_irq(unsigned int irq)
146 {
147         enable_vrc4173_irq(irq);
148         return 0; /* never anything pending */
149 }
150 
151 #define shutdown_vrc4173_irq    disable_vrc4173_irq
152 #define ack_vrc4173_irq         disable_vrc4173_irq
153 
154 static void end_vrc4173_irq(unsigned int irq)
155 {
156         if (!(irq_desc[irq].status & (IRQ_DISABLED | IRQ_INPROGRESS)))
157                 enable_vrc4173_irq(irq);
158 }
159 
160 static struct hw_interrupt_type vrc4173_irq_type = {
161         "VRC4173",
162         startup_vrc4173_irq,
163         shutdown_vrc4173_irq,
164         enable_vrc4173_irq,
165         disable_vrc4173_irq,
166         ack_vrc4173_irq,
167         end_vrc4173_irq,
168         NULL
169 };
170 
171 static int vrc4173_get_irq_number(int irq)
172 {
173         u16 status, mask;
174         int i;
175 
176         status = vrc4173_inw(VRC4173_SYSINT1REG);
177         mask = vrc4173_inw(VRC4173_MSYSINT1REG);
178 
179         status &= mask;
180         if (status) {
181                 for (i = 0; i < 16; i++)
182                         if (status & (0x0001 << i))
183                                 return VRC4173_IRQ_BASE + i;
184         }
185 
186         return -EINVAL;
187 }
188 
189 static inline void vrc4173_icu_init(int cascade_irq)
190 {
191         int i;
192 
193         if (cascade_irq < GIU_IRQ(0) || cascade_irq > GIU_IRQ(15))
194                 return;
195         
196         vrc4173_outw(0, VRC4173_MSYSINT1REG);
197 
198         vr41xx_set_irq_trigger(cascade_irq - GIU_IRQ(0), TRIGGER_LEVEL, SIGNAL_THROUGH);
199         vr41xx_set_irq_level(cascade_irq - GIU_IRQ(0), LEVEL_LOW);
200 
201         for (i = VRC4173_IRQ_BASE; i <= VRC4173_IRQ_LAST; i++)
202                 irq_desc[i].handler = &vrc4173_irq_type;
203 }
204 
205 static int __devinit vrc4173_probe(struct pci_dev *pdev,
206                                    const struct pci_device_id *ent)
207 {
208         unsigned long start, flags;
209         int err;
210 
211         if ((err = pci_enable_device(pdev)) < 0) {
212                 printk(KERN_ERR "vrc4173: failed to enable device -- err=%d\n", err);
213                 return err;
214         }
215 
216         pci_set_master(pdev);
217 
218         start = pci_resource_start(pdev, 0);
219         if (!start) {
220                 printk(KERN_ERR "vrc4173:No PCI I/O resources, aborting\n");
221                 return -ENODEV;
222         }
223 
224         if (!start || (((flags = pci_resource_flags(pdev, 0)) & IORESOURCE_IO) == 0)) {
225                 printk(KERN_ERR "vrc4173: No PCI I/O resources, aborting\n");
226                 return -ENODEV;
227         }
228 
229         if ((err = pci_request_regions(pdev, "NEC VRC4173")) < 0) {
230                 printk(KERN_ERR "vrc4173: PCI resources are busy, aborting\n");
231                 return err;
232         }
233 
234         set_vrc4173_io_offset(start);
235 
236         vrc4173_cmu_init();
237 
238         vrc4173_icu_init(pdev->irq);
239 
240         if ((err = vr41xx_cascade_irq(pdev->irq, vrc4173_get_irq_number)) < 0) {
241                 printk(KERN_ERR
242                        "vrc4173: IRQ resource %d is busy, aborting\n", pdev->irq);
243                 return err;
244         }
245 
246         printk(KERN_INFO
247                "NEC VRC4173 at 0x%#08lx, IRQ is cascaded to %d\n", start, pdev->irq);
248 
249         return 0;
250 }
251 
252 static struct pci_driver vrc4173_driver = {
253         .name           = "NEC VRC4173",
254         .probe          = vrc4173_probe,
255         .remove         = NULL,
256         .id_table       = vrc4173_table,
257 };
258 
259 static int __devinit vrc4173_init(void)
260 {
261         int err;
262 
263         if ((err = pci_module_init(&vrc4173_driver)) < 0)
264                 return err;
265 
266         vrc4173_initialized = 1;
267 
268         return 0;
269 }
270 
271 static void __devexit vrc4173_exit(void)
272 {
273         vrc4173_initialized = 0;
274 
275         pci_unregister_driver(&vrc4173_driver);
276 }
277 
278 module_init(vrc4173_init);
279 module_exit(vrc4173_exit);
280 

~ [ source navigation ] ~ [ diff markup ] ~ [ identifier search ] ~

kernel.org | git.kernel.org | LWN.net | Project Home | Wiki (Japanese) | Wiki (English) | SVN repository | Mail admin

Linux® is a registered trademark of Linus Torvalds in the United States and other countries.
TOMOYO® is a registered trademark of NTT DATA CORPORATION.

osdn.jp