]> git.kernelconcepts.de Git - karo-tx-uboot.git/blob - board/mousse/pci.c
ARM: highbank: use default prompt
[karo-tx-uboot.git] / board / mousse / pci.c
1 /*
2  *
3  * (C) Copyright 2000
4  * Wolfgang Denk, DENX Software Engineering, wd@denx.de.
5  *
6  * (C) Copyright 2001
7  * James Dougherty (jfd@cs.stanford.edu)
8  *
9  * SPDX-License-Identifier:     GPL-2.0+
10  */
11
12 /*
13  * PCI Configuration space access support for MPC824x/MPC107 PCI Bridge
14  */
15 #include <common.h>
16 #include <mpc824x.h>
17 #include <pci.h>
18
19 #include "mousse.h"
20
21 /*
22  * Promise ATA/66 support.
23  */
24 #define XFER_PIO_4      0x0C    /* 0000|1100 */
25 #define XFER_PIO_3      0x0B    /* 0000|1011 */
26 #define XFER_PIO_2      0x0A    /* 0000|1010 */
27 #define XFER_PIO_1      0x09    /* 0000|1001 */
28 #define XFER_PIO_0      0x08    /* 0000|1000 */
29 #define XFER_PIO_SLOW   0x00    /* 0000|0000 */
30
31 /* Promise Regs */
32 #define REG_A           0x01
33 #define REG_B           0x02
34 #define REG_C           0x04
35 #define REG_D           0x08
36
37 void
38 pdc202xx_decode_registers (unsigned char registers, unsigned char value)
39 {
40         unsigned char   bit = 0, bit1 = 0, bit2 = 0;
41         switch(registers) {
42                 case REG_A:
43                         bit2 = 0;
44                         printf("  A Register ");
45                         if (value & 0x80) printf("SYNC_IN ");
46                         if (value & 0x40) printf("ERRDY_EN ");
47                         if (value & 0x20) printf("IORDY_EN ");
48                         if (value & 0x10) printf("PREFETCH_EN ");
49                         if (value & 0x08) { printf("PA3 ");bit2 |= 0x08; }
50                         if (value & 0x04) { printf("PA2 ");bit2 |= 0x04; }
51                         if (value & 0x02) { printf("PA1 ");bit2 |= 0x02; }
52                         if (value & 0x01) { printf("PA0 ");bit2 |= 0x01; }
53                         printf("PIO(A) = %d ", bit2);
54                         break;
55                 case REG_B:
56                         bit1 = 0;bit2 = 0;
57                         printf("  B Register ");
58                         if (value & 0x80) { printf("MB2 ");bit1 |= 0x80; }
59                         if (value & 0x40) { printf("MB1 ");bit1 |= 0x40; }
60                         if (value & 0x20) { printf("MB0 ");bit1 |= 0x20; }
61                         printf("DMA(B) = %d ", bit1 >> 5);
62                         if (value & 0x10) printf("PIO_FORCED/PB4 ");
63                         if (value & 0x08) { printf("PB3 ");bit2 |= 0x08; }
64                         if (value & 0x04) { printf("PB2 ");bit2 |= 0x04; }
65                         if (value & 0x02) { printf("PB1 ");bit2 |= 0x02; }
66                         if (value & 0x01) { printf("PB0 ");bit2 |= 0x01; }
67                         printf("PIO(B) = %d ", bit2);
68                         break;
69                 case REG_C:
70                         bit2 = 0;
71                         printf("  C Register ");
72                         if (value & 0x80) printf("DMARQp ");
73                         if (value & 0x40) printf("IORDYp ");
74                         if (value & 0x20) printf("DMAR_EN ");
75                         if (value & 0x10) printf("DMAW_EN ");
76
77                         if (value & 0x08) { printf("MC3 ");bit2 |= 0x08; }
78                         if (value & 0x04) { printf("MC2 ");bit2 |= 0x04; }
79                         if (value & 0x02) { printf("MC1 ");bit2 |= 0x02; }
80                         if (value & 0x01) { printf("MC0 ");bit2 |= 0x01; }
81                         printf("DMA(C) = %d ", bit2);
82                         break;
83                 case REG_D:
84                         printf("  D Register ");
85                         break;
86                 default:
87                         return;
88         }
89         printf("\n        %s ", (registers & REG_D) ? "DP" :
90                                 (registers & REG_C) ? "CP" :
91                                 (registers & REG_B) ? "BP" :
92                                 (registers & REG_A) ? "AP" : "ERROR");
93         for (bit=128;bit>0;bit/=2)
94                 printf("%s", (value & bit) ? "1" : "0");
95         printf("\n");
96 }
97
98 /*
99  * Promise ATA/66 Support: configure Promise ATA66 card in specified mode.
100  */
101 int
102 pdc202xx_tune_chipset (pci_dev_t dev, int drive, unsigned char speed)
103 {
104         unsigned short          drive_conf;
105         int                     err = 0;
106         unsigned char                   drive_pci, AP, BP, CP, DP;
107         unsigned char                   TA = 0, TB = 0;
108
109         switch (drive) {
110                 case 0: drive_pci = 0x60; break;
111                 case 1: drive_pci = 0x64; break;
112                 case 2: drive_pci = 0x68; break;
113                 case 3: drive_pci = 0x6c; break;
114                 default: return -1;
115         }
116
117         pci_read_config_word(dev, drive_pci, &drive_conf);
118         pci_read_config_byte(dev, (drive_pci), &AP);
119         pci_read_config_byte(dev, (drive_pci)|0x01, &BP);
120         pci_read_config_byte(dev, (drive_pci)|0x02, &CP);
121         pci_read_config_byte(dev, (drive_pci)|0x03, &DP);
122
123         if ((AP & 0x0F) || (BP & 0x07)) {
124           /* clear PIO modes of lower 8421 bits of A Register */
125           pci_write_config_byte(dev, (drive_pci), AP & ~0x0F);
126           pci_read_config_byte(dev, (drive_pci), &AP);
127
128           /* clear PIO modes of lower 421 bits of B Register */
129           pci_write_config_byte(dev, (drive_pci)|0x01, BP & ~0x07);
130           pci_read_config_byte(dev, (drive_pci)|0x01, &BP);
131
132           pci_read_config_byte(dev, (drive_pci), &AP);
133           pci_read_config_byte(dev, (drive_pci)|0x01, &BP);
134         }
135
136         pci_read_config_byte(dev, (drive_pci), &AP);
137         pci_read_config_byte(dev, (drive_pci)|0x01, &BP);
138         pci_read_config_byte(dev, (drive_pci)|0x02, &CP);
139
140         switch(speed) {
141                 case XFER_PIO_4:        TA = 0x01; TB = 0x04; break;
142                 case XFER_PIO_3:        TA = 0x02; TB = 0x06; break;
143                 case XFER_PIO_2:        TA = 0x03; TB = 0x08; break;
144                 case XFER_PIO_1:        TA = 0x05; TB = 0x0C; break;
145                 case XFER_PIO_0:
146                 default:                TA = 0x09; TB = 0x13; break;
147         }
148
149         pci_write_config_byte(dev, (drive_pci), AP|TA);
150         pci_write_config_byte(dev, (drive_pci)|0x01, BP|TB);
151
152         pci_read_config_byte(dev, (drive_pci), &AP);
153         pci_read_config_byte(dev, (drive_pci)|0x01, &BP);
154         pci_read_config_byte(dev, (drive_pci)|0x02, &CP);
155         pci_read_config_byte(dev, (drive_pci)|0x03, &DP);
156
157
158 #ifdef PDC202XX_DEBUG
159         pdc202xx_decode_registers(REG_A, AP);
160         pdc202xx_decode_registers(REG_B, BP);
161         pdc202xx_decode_registers(REG_C, CP);
162         pdc202xx_decode_registers(REG_D, DP);
163 #endif
164         return err;
165 }
166 /*
167  * Show/Init PCI devices on the specified bus number.
168  */
169
170 void pci_mousse_fixup_irq(struct pci_controller *hose, pci_dev_t dev)
171 {
172         unsigned int line;
173
174         switch(PCI_DEV(dev)) {
175         case 0x0d:
176                 line = 0x00000101;
177                 break;
178
179         case 0x0e:
180         default:
181                 line = 0x00000303;
182                 break;
183         }
184
185         pci_write_config_dword(dev, PCI_INTERRUPT_LINE, line);
186 }
187
188 void pci_mousse_setup_pdc202xx(struct pci_controller *hose, pci_dev_t dev,
189                                struct pci_config_table *_)
190 {
191         unsigned short vendorId;
192         unsigned int mbar0, cmd;
193         int bar, a;
194
195         pci_read_config_word(dev, PCI_VENDOR_ID, &vendorId);
196
197         if(vendorId == PCI_VENDOR_ID_PROMISE || vendorId == PCI_VENDOR_ID_CMD){
198                 /* PDC 202xx card is handled differently, it is a bootable
199                  * device and needs all 5 MBAR's configured
200                  */
201                 for(bar = 0; bar < 5; bar++){
202                         pci_read_config_dword(dev, PCI_BASE_ADDRESS_0+bar*4, &mbar0);
203                         pci_write_config_dword(dev, PCI_BASE_ADDRESS_0+bar*4, ~0);
204                         pci_read_config_dword(dev, PCI_BASE_ADDRESS_0+bar*4, &mbar0);
205 #ifdef DEBUG
206                         printf("  ATA_bar[%d] = %dbytes\n", bar,
207                                ~(mbar0 & PCI_BASE_ADDRESS_MEM_MASK) + 1);
208 #endif
209                 }
210
211                 /* Program all BAR's */
212                 pci_write_config_dword(dev, PCI_BASE_ADDRESS_0, PROMISE_MBAR0);
213                 pci_write_config_dword(dev, PCI_BASE_ADDRESS_1, PROMISE_MBAR1);
214                 pci_write_config_dword(dev, PCI_BASE_ADDRESS_2, PROMISE_MBAR2);
215                 pci_write_config_dword(dev, PCI_BASE_ADDRESS_3, PROMISE_MBAR3);
216                 pci_write_config_dword(dev, PCI_BASE_ADDRESS_4, PROMISE_MBAR4);
217                 pci_write_config_dword(dev, PCI_BASE_ADDRESS_5, PROMISE_MBAR5);
218
219                 for(bar = 0; bar < 5; bar++){
220                         pci_read_config_dword(dev, PCI_BASE_ADDRESS_0+bar*4, &mbar0);
221 #ifdef DEBUG
222                         printf("  ATA_bar[%d]@0x%x\n", bar, mbar0);
223 #endif
224                 }
225
226                 /* Enable ROM Expansion base */
227                 pci_write_config_dword(dev, PCI_ROM_ADDRESS, PROMISE_MBAR5|1);
228
229                 /* Io enable, Memory enable, master enable */
230                 pci_read_config_dword(dev, PCI_COMMAND, &cmd);
231                 cmd &= ~0xffff0000;
232                 cmd |= PCI_COMMAND_MASTER | PCI_COMMAND_MEMORY | PCI_COMMAND_IO;
233                 pci_write_config_dword(dev, PCI_COMMAND, cmd);
234
235                 /* Breath some life into the controller */
236                 for( a = 0; a < 4; a++)
237                         pdc202xx_tune_chipset(dev, a, XFER_PIO_0);
238         }
239 }
240
241 static struct pci_config_table pci_sandpoint_config_table[] = {
242         { PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, 0x00, 0x0e, 0x00,
243           pci_mousse_setup_pdc202xx },
244 #ifndef CONFIG_PCI_PNP
245         { PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, 0x00, 0x0d, 0x00,
246           pci_cfgfunc_config_device, {PCI_ENET_IOADDR,
247                                       PCI_ENET_MEMADDR,
248                                       PCI_COMMAND_MEMORY |
249                                       PCI_COMMAND_MASTER}},
250         { PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID, PCI_ANY_ID,
251           pci_cfgfunc_config_device, {PCI_SLOT_IOADDR,
252                                       PCI_SLOT_MEMADDR,
253                                       PCI_COMMAND_MEMORY |
254                                       PCI_COMMAND_MASTER}},
255 #endif
256         { }
257 };
258
259 struct pci_controller hose = {
260         config_table: pci_sandpoint_config_table,
261         fixup_irq: pci_mousse_fixup_irq,
262 };
263
264 void pci_init_board(void)
265 {
266         pci_mpc824x_init(&hose);
267 }