]> Pileus Git - ~andy/linux/blob - drivers/staging/sbe-2t3e3/io.c
Merge branch 'perf-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel...
[~andy/linux] / drivers / staging / sbe-2t3e3 / io.c
1 /*
2  * SBE 2T3E3 synchronous serial card driver for Linux
3  *
4  * Copyright (C) 2009-2010 Krzysztof Halasa <khc@pm.waw.pl>
5  *
6  * This program is free software; you can redistribute it and/or modify it
7  * under the terms of version 2 of the GNU General Public License
8  * as published by the Free Software Foundation.
9  *
10  * This code is based on a driver written by SBE Inc.
11  */
12
13 #include <linux/ip.h>
14 #include "2t3e3.h"
15 #include "ctrl.h"
16
17 /* All access to registers done via the 21143 on port 0 must be
18  * protected via the card->bootrom_lock. */
19
20 /* priviate define to be used here only - must be protected by card->bootrom_lock */
21 #define cpld_write_nolock(channel, reg, val)                    \
22         bootrom_write((channel), CPLD_MAP_REG(reg, channel), val)
23
24 u32 cpld_read(struct channel *channel, u32 reg)
25 {
26         unsigned long flags;
27         u32 val;
28
29         spin_lock_irqsave(&channel->card->bootrom_lock, flags);
30         val = bootrom_read((channel), CPLD_MAP_REG(reg, channel));
31         spin_unlock_irqrestore(&channel->card->bootrom_lock, flags);
32         return val;
33 }
34
35 /****************************************
36  * Access via BootROM port
37  ****************************************/
38
39 u32 bootrom_read(struct channel *channel, u32 reg)
40 {
41         unsigned long addr = channel->card->bootrom_addr;
42         u32 result;
43
44         /* select BootROM address */
45         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_PROGRAMMING_ADDRESS, reg & 0x3FFFF);
46
47         /* select reading from BootROM */
48         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
49                  SBE_2T3E3_21143_VAL_READ_OPERATION |
50                  SBE_2T3E3_21143_VAL_BOOT_ROM_SELECT);
51
52         udelay(2); /* 20 PCI cycles */
53
54         /* read from BootROM */
55         result = dc_read(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT) & 0xff;
56
57         /* reset CSR9 */
58         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT, 0);
59
60         return result;
61 }
62
63 void bootrom_write(struct channel *channel, u32 reg, u32 val)
64 {
65         unsigned long addr = channel->card->bootrom_addr;
66
67         /* select BootROM address */
68         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_PROGRAMMING_ADDRESS, reg & 0x3FFFF);
69
70         /* select writting to BootROM */
71         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
72                  SBE_2T3E3_21143_VAL_WRITE_OPERATION |
73                  SBE_2T3E3_21143_VAL_BOOT_ROM_SELECT |
74                  (val & 0xff));
75
76         udelay(2); /* 20 PCI cycles */
77
78         /* reset CSR9 */
79         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT, 0);
80 }
81
82
83 /****************************************
84  * Access via Serial I/O port
85  ****************************************/
86
87 static u32 serialrom_read_bit(struct channel *channel)
88 {
89         unsigned long addr = channel->card->bootrom_addr;
90         u32 bit;
91
92         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
93                  SBE_2T3E3_21143_VAL_READ_OPERATION |
94                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
95                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CLOCK |
96                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);   /* clock high */
97
98         bit = (dc_read(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT) &
99                SBE_2T3E3_21143_VAL_SERIAL_ROM_DATA_OUT) > 0 ? 1 : 0;
100
101         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
102                  SBE_2T3E3_21143_VAL_READ_OPERATION |
103                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
104                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);   /* clock low */
105
106         return bit;
107 }
108
109 static void serialrom_write_bit(struct channel *channel, u32 bit)
110 {
111         unsigned long addr = channel->card->bootrom_addr;
112         u32 lastbit = -1;
113
114         bit &= 1;
115
116         if (bit != lastbit) {
117                 dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
118                          SBE_2T3E3_21143_VAL_WRITE_OPERATION |
119                          SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
120                          SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT |
121                          (bit << 2)); /* clock low */
122
123                 lastbit = bit;
124         }
125
126         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
127                  SBE_2T3E3_21143_VAL_WRITE_OPERATION |
128                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
129                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CLOCK |
130                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT |
131                  (bit << 2)); /* clock high */
132
133         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
134                  SBE_2T3E3_21143_VAL_WRITE_OPERATION |
135                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
136                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT |
137                  (bit << 2)); /* clock low */
138 }
139
140 /****************************************
141  * Access to SerialROM (eeprom)
142  ****************************************/
143
144 u32 t3e3_eeprom_read_word(struct channel *channel, u32 address)
145 {
146         unsigned long addr = channel->card->bootrom_addr;
147         u32 i, val;
148         unsigned long flags;
149
150         address &= 0x3f;
151
152         spin_lock_irqsave(&channel->card->bootrom_lock, flags);
153
154         /* select correct Serial Chip */
155         cpld_write_nolock(channel, SBE_2T3E3_CPLD_REG_SERIAL_CHIP_SELECT,
156                           SBE_2T3E3_CPLD_VAL_EEPROM_SELECT);
157
158         /* select reading from Serial I/O Bus */
159         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
160                  SBE_2T3E3_21143_VAL_READ_OPERATION |
161                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
162                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);        /* clock low */
163
164         /* select read operation */
165         serialrom_write_bit(channel, 0);
166         serialrom_write_bit(channel, 1);
167         serialrom_write_bit(channel, 1);
168         serialrom_write_bit(channel, 0);
169
170         for (i = 0x20; i; i >>= 1)
171                 serialrom_write_bit(channel, address & i ? 1 : 0);
172
173         val = 0;
174         for (i = 0x8000; i; i >>= 1)
175                 val |= (serialrom_read_bit(channel) ? i : 0);
176
177         /* Reset 21143's CSR9 */
178         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
179                  SBE_2T3E3_21143_VAL_READ_OPERATION |
180                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
181                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);        /* clock low */
182         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT, 0);
183
184         /* Unselect Serial Chip */
185         cpld_write_nolock(channel, SBE_2T3E3_CPLD_REG_SERIAL_CHIP_SELECT, 0);
186
187         spin_unlock_irqrestore(&channel->card->bootrom_lock, flags);
188
189         return ntohs(val);
190 }
191
192
193 /****************************************
194  * Access to Framer
195  ****************************************/
196
197 u32 exar7250_read(struct channel *channel, u32 reg)
198 {
199         u32 result;
200         unsigned long flags;
201
202 #if 0
203         switch (reg) {
204         case SBE_2T3E3_FRAMER_REG_OPERATING_MODE:
205                 return channel->framer_regs[reg];
206                 break;
207         default:
208         }
209 #endif
210
211         spin_lock_irqsave(&channel->card->bootrom_lock, flags);
212
213         result = bootrom_read(channel, cpld_reg_map[SBE_2T3E3_CPLD_REG_FRAMER_BASE_ADDRESS]
214                               [channel->h.slot] + (t3e3_framer_reg_map[reg] << 2));
215
216         spin_unlock_irqrestore(&channel->card->bootrom_lock, flags);
217
218         return result;
219 }
220
221 void exar7250_write(struct channel *channel, u32 reg, u32 val)
222 {
223         unsigned long flags;
224
225         val &= 0xff;
226         channel->framer_regs[reg] = val;
227
228         spin_lock_irqsave(&channel->card->bootrom_lock, flags);
229
230         bootrom_write(channel, cpld_reg_map[SBE_2T3E3_CPLD_REG_FRAMER_BASE_ADDRESS]
231                       [channel->h.slot] + (t3e3_framer_reg_map[reg] << 2), val);
232
233         spin_unlock_irqrestore(&channel->card->bootrom_lock, flags);
234 }
235
236
237 /****************************************
238  * Access to LIU
239  ****************************************/
240
241 u32 exar7300_read(struct channel *channel, u32 reg)
242 {
243         unsigned long addr = channel->card->bootrom_addr, flags;
244         u32 i, val;
245
246 #if 0
247         switch (reg) {
248         case SBE_2T3E3_LIU_REG_REG1:
249         case SBE_2T3E3_LIU_REG_REG2:
250         case SBE_2T3E3_LIU_REG_REG3:
251         case SBE_2T3E3_LIU_REG_REG4:
252                 return channel->liu_regs[reg];
253                 break;
254         default:
255         }
256 #endif
257
258         /* select correct Serial Chip */
259
260         spin_lock_irqsave(&channel->card->bootrom_lock, flags);
261
262         cpld_write_nolock(channel, SBE_2T3E3_CPLD_REG_SERIAL_CHIP_SELECT,
263                           cpld_val_map[SBE_2T3E3_CPLD_VAL_LIU_SELECT][channel->h.slot]);
264
265         /* select reading from Serial I/O Bus */
266         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
267                  SBE_2T3E3_21143_VAL_READ_OPERATION |
268                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
269                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);   /* clock low */
270
271         /* select read operation */
272         serialrom_write_bit(channel, 1);
273
274         /* Exar7300 register address is 4 bit long */
275         reg = t3e3_liu_reg_map[reg];
276         for (i = 0; i < 4; i++, reg >>= 1) /* 4 bits of SerialROM address */
277                 serialrom_write_bit(channel, reg & 1);
278         for (i = 0; i < 3; i++) /* remaining 3 bits of SerialROM address */
279                 serialrom_write_bit(channel, 0);
280
281         val = 0; /* Exar7300 register value is 5 bit long */
282         for (i = 0; i < 8; i++) /* 8 bits of SerialROM value */
283                 val += (serialrom_read_bit(channel) << i);
284
285         /* Reset 21143's CSR9 */
286         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
287                  SBE_2T3E3_21143_VAL_READ_OPERATION |
288                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
289                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);   /* clock low */
290         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT, 0);
291
292         /* Unselect Serial Chip */
293         cpld_write_nolock(channel, SBE_2T3E3_CPLD_REG_SERIAL_CHIP_SELECT, 0);
294
295         spin_unlock_irqrestore(&channel->card->bootrom_lock, flags);
296
297         return val;
298 }
299
300 void exar7300_write(struct channel *channel, u32 reg, u32 val)
301 {
302         unsigned long addr = channel->card->bootrom_addr, flags;
303         u32 i;
304
305         channel->liu_regs[reg] = val;
306
307         /* select correct Serial Chip */
308
309         spin_lock_irqsave(&channel->card->bootrom_lock, flags);
310
311         cpld_write_nolock(channel, SBE_2T3E3_CPLD_REG_SERIAL_CHIP_SELECT,
312                           cpld_val_map[SBE_2T3E3_CPLD_VAL_LIU_SELECT][channel->h.slot]);
313
314         /* select writting to Serial I/O Bus */
315         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
316                  SBE_2T3E3_21143_VAL_WRITE_OPERATION |
317                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
318                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);   /* clock low */
319
320         /* select write operation */
321         serialrom_write_bit(channel, 0);
322
323         /* Exar7300 register address is 4 bit long */
324         reg = t3e3_liu_reg_map[reg];
325         for (i = 0; i < 4; i++) {       /* 4 bits */
326                 serialrom_write_bit(channel, reg & 1);
327                 reg >>= 1;
328         }
329         for (i = 0; i < 3; i++) /* remaining 3 bits of SerialROM address */
330                 serialrom_write_bit(channel, 0);
331
332         /* Exar7300 register value is 5 bit long */
333         for (i = 0; i < 5; i++) {
334                 serialrom_write_bit(channel, val & 1);
335                 val >>= 1;
336         }
337         for (i = 0; i < 3; i++) /* remaining 3 bits of SerialROM value */
338                 serialrom_write_bit(channel, 0);
339
340         /* Reset 21143_CSR9 */
341         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT,
342                  SBE_2T3E3_21143_VAL_WRITE_OPERATION |
343                  SBE_2T3E3_21143_VAL_SERIAL_ROM_SELECT |
344                  SBE_2T3E3_21143_VAL_SERIAL_ROM_CHIP_SELECT);   /* clock low */
345         dc_write(addr, SBE_2T3E3_21143_REG_BOOT_ROM_SERIAL_ROM_AND_MII_MANAGEMENT, 0);
346
347         /* Unselect Serial Chip */
348         cpld_write_nolock(channel, SBE_2T3E3_CPLD_REG_SERIAL_CHIP_SELECT, 0);
349
350         spin_unlock_irqrestore(&channel->card->bootrom_lock, flags);
351 }