Merge with /pub/scm/linux/kernel/git/torvalds/linux-2.6.git
[linux-2.6] / arch / mips / pci / pci-ocelot.c
1 /*
2  * BRIEF MODULE DESCRIPTION
3  * Galileo Evaluation Boards PCI support.
4  *
5  * The general-purpose functions to read/write and configure the GT64120A's
6  * PCI registers (function names start with pci0 or pci1) are either direct
7  * copies of functions written by Galileo Technology, or are modifications
8  * of their functions to work with Linux 2.4 vs Linux 2.2.  These functions
9  * are Copyright - Galileo Technology.
10  *
11  * Other functions are derived from other MIPS PCI implementations, or were
12  * written by RidgeRun, Inc,  Copyright (C) 2000 RidgeRun, Inc.
13  *   glonnon@ridgerun.com, skranz@ridgerun.com, stevej@ridgerun.com
14  *
15  * Copyright 2001 MontaVista Software Inc.
16  * Author: Jun Sun, jsun@mvista.com or jsun@junsun.net
17  *
18  *  This program is free software; you can redistribute  it and/or modify it
19  *  under  the terms of  the GNU General  Public License as published by the
20  *  Free Software Foundation;  either version 2 of the  License, or (at your
21  *  option) any later version.
22  *
23  *  THIS  SOFTWARE  IS PROVIDED   ``AS  IS'' AND   ANY  EXPRESS OR IMPLIED
24  *  WARRANTIES,   INCLUDING, BUT NOT  LIMITED  TO, THE IMPLIED WARRANTIES OF
25  *  MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.  IN
26  *  NO  EVENT  SHALL   THE AUTHOR  BE    LIABLE FOR ANY   DIRECT, INDIRECT,
27  *  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT
28  *  NOT LIMITED   TO, PROCUREMENT OF  SUBSTITUTE GOODS  OR SERVICES; LOSS OF
29  *  USE, DATA,  OR PROFITS; OR  BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
30  *  ANY THEORY OF LIABILITY, WHETHER IN  CONTRACT, STRICT LIABILITY, OR TORT
31  *  (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
32  *  THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
33  *
34  *  You should have received a copy of the  GNU General Public License along
35  *  with this program; if not, write  to the Free Software Foundation, Inc.,
36  *  675 Mass Ave, Cambridge, MA 02139, USA.
37  */
38 #include <linux/init.h>
39 #include <linux/types.h>
40 #include <linux/pci.h>
41 #include <linux/kernel.h>
42 #include <linux/slab.h>
43 #include <linux/cache.h>
44 #include <asm/pci.h>
45 #include <asm/io.h>
46 #include <asm/gt64120.h>
47
48 static inline unsigned int pci0ReadConfigReg(unsigned int offset)
49 {
50         unsigned int DataForRegCf8;
51         unsigned int data;
52
53         DataForRegCf8 = ((PCI_SLOT(device->devfn) << 11) |
54                          (PCI_FUNC(device->devfn) << 8) |
55                          (offset & ~0x3)) | 0x80000000;
56         GT_WRITE(GT_PCI0_CFGADDR_OFS, DataForRegCf8);
57         GT_READ(GT_PCI0_CFGDATA_OFS, &data);
58
59         return data;
60 }
61
62 static inline void pci0WriteConfigReg(unsigned int offset, unsigned int data)
63 {
64         unsigned int DataForRegCf8;
65
66         DataForRegCf8 = ((PCI_SLOT(device->devfn) << 11) |
67                          (PCI_FUNC(device->devfn) << 8) |
68                          (offset & ~0x3)) | 0x80000000;
69         GT_WRITE(GT_PCI0_CFGADDR_OFS, DataForRegCf8);
70         GT_WRITE(GT_PCI0_CFGDATA_OFS, data);
71 }
72
73 static struct resource ocelot_mem_resource = {
74         start   = GT_PCI_MEM_BASE;
75         end     = GT_PCI_MEM_BASE + GT_PCI_MEM_BASE - 1;
76 };
77
78 static struct resource ocelot_io_resource = {
79         start   = GT_PCI_IO_BASE;
80         end     = GT_PCI_IO_BASE + GT_PCI_IO_SIZE - 1;
81 };
82
83 static struct pci_controller ocelot_pci_controller = {
84         .pci_ops        = gt64120_pci_ops;
85         .mem_resource   = &ocelot_mem_resource;
86         .io_resource    = &ocelot_io_resource;
87 };
88
89 static int __init ocelot_pcibios_init(void)
90 {
91         u32 tmp;
92
93         GT_READ(GT_PCI0_CMD_OFS, &tmp);
94         GT_READ(GT_PCI0_BARE_OFS, &tmp);
95
96         /*
97          * You have to enable bus mastering to configure any other
98          * card on the bus.
99          */
100         tmp = pci0ReadConfigReg(PCI_COMMAND);
101         tmp |= PCI_COMMAND_MEMORY | PCI_COMMAND_MASTER | PCI_COMMAND_SERR;
102         pci0WriteConfigReg(PCI_COMMAND, tmp);
103
104         register_pci_controller(&ocelot_pci_controller);
105 }
106
107 arch_initcall(ocelot_pcibios_init);