1 /*
2 * CDDL HEADER START
3 *
4 * The contents of this file are subject to the terms of the
5 * Common Development and Distribution License (the "License").
6 * You may not use this file except in compliance with the License.
7 *
8 * You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
9 * or http://www.opensolaris.org/os/licensing.
10 * See the License for the specific language governing permissions
11 * and limitations under the License.
12 *
13 * When distributing Covered Code, include this CDDL HEADER in each
14 * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
15 * If applicable, add the following below this CDDL HEADER, with the
16 * fields enclosed by brackets "[]" replaced with your own identifying
17 * information: Portions Copyright [yyyy] [name of copyright owner]
18 *
19 * CDDL HEADER END
20 */
21
22 /*
23 * Copyright 2010 QLogic Corporation. All rights reserved.
24 * Use is subject to license terms.
25 */
26
27 #pragma ident "Copyright 2010 QLogic Corporation; ql_nx.c"
28
29 /*
30 * ISP2xxx Solaris Fibre Channel Adapter (FCA) driver source file.
31 *
32 * ***********************************************************************
33 * * **
34 * * NOTICE **
35 * * COPYRIGHT (C) 1996-2010 QLOGIC CORPORATION **
36 * * ALL RIGHTS RESERVED **
37 * * **
38 * ***********************************************************************
39 *
40 */
41
42 #include <ql_apps.h>
43 #include <ql_api.h>
44 #include <ql_debug.h>
45 #include <ql_mbx.h>
46 #include <ql_nx.h>
47
48 /*
49 * Local Function Prototypes.
50 */
51 static void *ql_8021_pci_base_offsetfset(ql_adapter_state_t *, uint64_t);
52 static void ql_crb_addr_transform_setup(ql_adapter_state_t *);
53 static void ql_8021_pci_set_crbwindow_2M(ql_adapter_state_t *, uint64_t *);
54 static void ql_8021_wr_32(ql_adapter_state_t *, uint64_t, uint32_t);
55 static void ql_8021_rd_32(ql_adapter_state_t *, uint64_t, uint32_t *);
56 static int ql_8021_crb_win_lock(ql_adapter_state_t *);
57 static void ql_8021_crb_win_unlock(ql_adapter_state_t *);
58 static int ql_8021_pci_get_crb_addr_2M(ql_adapter_state_t *, uint64_t *);
59 static uint32_t ql_8021_pci_mem_bound_check(ql_adapter_state_t *, uint64_t,
60 uint32_t);
61 static uint64_t ql_8021_pci_set_window(ql_adapter_state_t *, uint64_t);
62 static int ql_8021_pci_is_same_window(ql_adapter_state_t *, uint64_t);
63 static int ql_8021_pci_mem_read_direct(ql_adapter_state_t *, uint64_t, void *,
64 uint32_t);
65 static int ql_8021_pci_mem_write_direct(ql_adapter_state_t *, uint64_t, void *,
66 uint32_t);
67 static int ql_8021_pci_mem_read_2M(ql_adapter_state_t *, uint64_t, void *,
68 uint32_t);
69 static int ql_8021_pci_mem_write_2M(ql_adapter_state_t *, uint64_t, void *,
70 uint32_t);
71 static uint32_t ql_8021_decode_crb_addr(ql_adapter_state_t *, uint32_t);
72 static int ql_8021_rom_lock(ql_adapter_state_t *);
73 static void ql_8021_rom_unlock(ql_adapter_state_t *);
74 static int ql_8021_wait_rom_done(ql_adapter_state_t *);
75 static int ql_8021_wait_flash_done(ql_adapter_state_t *);
76 static int ql_8021_do_rom_fast_read(ql_adapter_state_t *, uint32_t, uint32_t *);
77 static int ql_8021_rom_fast_read(ql_adapter_state_t *, uint32_t, uint32_t *);
78 static int ql_8021_do_rom_write(ql_adapter_state_t *, uint32_t, uint32_t);
79 static int ql_8021_do_rom_erase(ql_adapter_state_t *, uint32_t);
80 static int ql_8021_phantom_init(ql_adapter_state_t *);
81 static int ql_8021_pinit_from_rom(ql_adapter_state_t *);
82 static int ql_8021_load_from_flash(ql_adapter_state_t *);
83 static int ql_8021_load_firmware(ql_adapter_state_t *);
84 static int ql_8021_reset_hw(ql_adapter_state_t *, int);
85 static int ql_8021_init_p3p(ql_adapter_state_t *);
86 static int ql_8021_hw_lock(ql_adapter_state_t *, uint32_t);
87 static void ql_8021_hw_unlock(ql_adapter_state_t *);
88 static void ql_8021_need_reset_handler(ql_adapter_state_t *);
89
90 /*
91 * Local Data.
92 */
93 static uint32_t crb_addr_xform[MAX_CRB_XFORM];
94 static int crb_table_initialized = 0;
95 static int pci_set_window_warning_count = 0;
96
97 static struct legacy_intr_set legacy_intr[] = NX_LEGACY_INTR_CONFIG;
98
99 static crb_128M_2M_block_map_t crb_128M_2M_map[64] = {
100 {{{0, 0, 0, 0}}}, /* 0: PCI */
101 {{{1, 0x0100000, 0x0102000, 0x120000}, /* 1: PCIE */
102 {1, 0x0110000, 0x0120000, 0x130000},
103 {1, 0x0120000, 0x0122000, 0x124000},
104 {1, 0x0130000, 0x0132000, 0x126000},
105 {1, 0x0140000, 0x0142000, 0x128000},
106 {1, 0x0150000, 0x0152000, 0x12a000},
107 {1, 0x0160000, 0x0170000, 0x110000},
108 {1, 0x0170000, 0x0172000, 0x12e000},
109 {0, 0x0000000, 0x0000000, 0x000000},
110 {0, 0x0000000, 0x0000000, 0x000000},
111 {0, 0x0000000, 0x0000000, 0x000000},
112 {0, 0x0000000, 0x0000000, 0x000000},
113 {0, 0x0000000, 0x0000000, 0x000000},
114 {0, 0x0000000, 0x0000000, 0x000000},
115 {1, 0x01e0000, 0x01e0800, 0x122000},
116 {0, 0x0000000, 0x0000000, 0x000000}}},
117 {{{1, 0x0200000, 0x0210000, 0x180000}}}, /* 2: MN */
118 {{{0, 0, 0, 0}}}, /* 3: */
119 {{{1, 0x0400000, 0x0401000, 0x169000}}}, /* 4: P2NR1 */
120 {{{1, 0x0500000, 0x0510000, 0x140000}}}, /* 5: SRE */
121 {{{1, 0x0600000, 0x0610000, 0x1c0000}}}, /* 6: NIU */
122 {{{1, 0x0700000, 0x0704000, 0x1b8000}}}, /* 7: QM */
123 {{{1, 0x0800000, 0x0802000, 0x170000}, /* 8: SQM0 */
124 {0, 0x0000000, 0x0000000, 0x000000},
125 {0, 0x0000000, 0x0000000, 0x000000},
126 {0, 0x0000000, 0x0000000, 0x000000},
127 {0, 0x0000000, 0x0000000, 0x000000},
128 {0, 0x0000000, 0x0000000, 0x000000},
129 {0, 0x0000000, 0x0000000, 0x000000},
130 {0, 0x0000000, 0x0000000, 0x000000},
131 {0, 0x0000000, 0x0000000, 0x000000},
132 {0, 0x0000000, 0x0000000, 0x000000},
133 {0, 0x0000000, 0x0000000, 0x000000},
134 {0, 0x0000000, 0x0000000, 0x000000},
135 {0, 0x0000000, 0x0000000, 0x000000},
136 {0, 0x0000000, 0x0000000, 0x000000},
137 {0, 0x0000000, 0x0000000, 0x000000},
138 {1, 0x08f0000, 0x08f2000, 0x172000}}},
139 {{{1, 0x0900000, 0x0902000, 0x174000}, /* 9: SQM1 */
140 {0, 0x0000000, 0x0000000, 0x000000},
141 {0, 0x0000000, 0x0000000, 0x000000},
142 {0, 0x0000000, 0x0000000, 0x000000},
143 {0, 0x0000000, 0x0000000, 0x000000},
144 {0, 0x0000000, 0x0000000, 0x000000},
145 {0, 0x0000000, 0x0000000, 0x000000},
146 {0, 0x0000000, 0x0000000, 0x000000},
147 {0, 0x0000000, 0x0000000, 0x000000},
148 {0, 0x0000000, 0x0000000, 0x000000},
149 {0, 0x0000000, 0x0000000, 0x000000},
150 {0, 0x0000000, 0x0000000, 0x000000},
151 {0, 0x0000000, 0x0000000, 0x000000},
152 {0, 0x0000000, 0x0000000, 0x000000},
153 {0, 0x0000000, 0x0000000, 0x000000},
154 {1, 0x09f0000, 0x09f2000, 0x176000}}},
155 {{{0, 0x0a00000, 0x0a02000, 0x178000}, /* 10: SQM2 */
156 {0, 0x0000000, 0x0000000, 0x000000},
157 {0, 0x0000000, 0x0000000, 0x000000},
158 {0, 0x0000000, 0x0000000, 0x000000},
159 {0, 0x0000000, 0x0000000, 0x000000},
160 {0, 0x0000000, 0x0000000, 0x000000},
161 {0, 0x0000000, 0x0000000, 0x000000},
162 {0, 0x0000000, 0x0000000, 0x000000},
163 {0, 0x0000000, 0x0000000, 0x000000},
164 {0, 0x0000000, 0x0000000, 0x000000},
165 {0, 0x0000000, 0x0000000, 0x000000},
166 {0, 0x0000000, 0x0000000, 0x000000},
167 {0, 0x0000000, 0x0000000, 0x000000},
168 {0, 0x0000000, 0x0000000, 0x000000},
169 {0, 0x0000000, 0x0000000, 0x000000},
170 {1, 0x0af0000, 0x0af2000, 0x17a000}}},
171 {{{0, 0x0b00000, 0x0b02000, 0x17c000}, /* 11: SQM3 */
172 {0, 0x0000000, 0x0000000, 0x000000},
173 {0, 0x0000000, 0x0000000, 0x000000},
174 {0, 0x0000000, 0x0000000, 0x000000},
175 {0, 0x0000000, 0x0000000, 0x000000},
176 {0, 0x0000000, 0x0000000, 0x000000},
177 {0, 0x0000000, 0x0000000, 0x000000},
178 {0, 0x0000000, 0x0000000, 0x000000},
179 {0, 0x0000000, 0x0000000, 0x000000},
180 {0, 0x0000000, 0x0000000, 0x000000},
181 {0, 0x0000000, 0x0000000, 0x000000},
182 {0, 0x0000000, 0x0000000, 0x000000},
183 {0, 0x0000000, 0x0000000, 0x000000},
184 {0, 0x0000000, 0x0000000, 0x000000},
185 {0, 0x0000000, 0x0000000, 0x000000},
186 {1, 0x0bf0000, 0x0bf2000, 0x17e000}}},
187 {{{1, 0x0c00000, 0x0c04000, 0x1d4000}}}, /* 12: I2Q */
188 {{{1, 0x0d00000, 0x0d04000, 0x1a4000}}}, /* 13: TMR */
189 {{{1, 0x0e00000, 0x0e04000, 0x1a0000}}}, /* 14: ROMUSB */
190 {{{1, 0x0f00000, 0x0f01000, 0x164000}}}, /* 15: PEG4 */
191 {{{0, 0x1000000, 0x1004000, 0x1a8000}}}, /* 16: XDMA */
192 {{{1, 0x1100000, 0x1101000, 0x160000}}}, /* 17: PEG0 */
193 {{{1, 0x1200000, 0x1201000, 0x161000}}}, /* 18: PEG1 */
194 {{{1, 0x1300000, 0x1301000, 0x162000}}}, /* 19: PEG2 */
195 {{{1, 0x1400000, 0x1401000, 0x163000}}}, /* 20: PEG3 */
196 {{{1, 0x1500000, 0x1501000, 0x165000}}}, /* 21: P2ND */
197 {{{1, 0x1600000, 0x1601000, 0x166000}}}, /* 22: P2NI */
198 {{{0, 0, 0, 0}}}, /* 23: */
199 {{{0, 0, 0, 0}}}, /* 24: */
200 {{{0, 0, 0, 0}}}, /* 25: */
201 {{{0, 0, 0, 0}}}, /* 26: */
202 {{{0, 0, 0, 0}}}, /* 27: */
203 {{{0, 0, 0, 0}}}, /* 28: */
204 {{{1, 0x1d00000, 0x1d10000, 0x190000}}}, /* 29: MS */
205 {{{1, 0x1e00000, 0x1e01000, 0x16a000}}}, /* 30: P2NR2 */
206 {{{1, 0x1f00000, 0x1f10000, 0x150000}}}, /* 31: EPG */
207 {{{0}}}, /* 32: PCI */
208 {{{1, 0x2100000, 0x2102000, 0x120000}, /* 33: PCIE */
209 {1, 0x2110000, 0x2120000, 0x130000},
210 {1, 0x2120000, 0x2122000, 0x124000},
211 {1, 0x2130000, 0x2132000, 0x126000},
212 {1, 0x2140000, 0x2142000, 0x128000},
213 {1, 0x2150000, 0x2152000, 0x12a000},
214 {1, 0x2160000, 0x2170000, 0x110000},
215 {1, 0x2170000, 0x2172000, 0x12e000},
216 {0, 0x0000000, 0x0000000, 0x000000},
217 {0, 0x0000000, 0x0000000, 0x000000},
218 {0, 0x0000000, 0x0000000, 0x000000},
219 {0, 0x0000000, 0x0000000, 0x000000},
220 {0, 0x0000000, 0x0000000, 0x000000},
221 {0, 0x0000000, 0x0000000, 0x000000},
222 {0, 0x0000000, 0x0000000, 0x000000},
223 {0, 0x0000000, 0x0000000, 0x000000}}},
224 {{{1, 0x2200000, 0x2204000, 0x1b0000}}}, /* 34: CAM */
225 {{{0}}}, /* 35: */
226 {{{0}}}, /* 36: */
227 {{{0}}}, /* 37: */
228 {{{0}}}, /* 38: */
229 {{{0}}}, /* 39: */
230 {{{1, 0x2800000, 0x2804000, 0x1a4000}}}, /* 40: TMR */
231 {{{1, 0x2900000, 0x2901000, 0x16b000}}}, /* 41: P2NR3 */
232 {{{1, 0x2a00000, 0x2a00400, 0x1ac400}}}, /* 42: RPMX1 */
233 {{{1, 0x2b00000, 0x2b00400, 0x1ac800}}}, /* 43: RPMX2 */
234 {{{1, 0x2c00000, 0x2c00400, 0x1acc00}}}, /* 44: RPMX3 */
235 {{{1, 0x2d00000, 0x2d00400, 0x1ad000}}}, /* 45: RPMX4 */
236 {{{1, 0x2e00000, 0x2e00400, 0x1ad400}}}, /* 46: RPMX5 */
237 {{{1, 0x2f00000, 0x2f00400, 0x1ad800}}}, /* 47: RPMX6 */
238 {{{1, 0x3000000, 0x3000400, 0x1adc00}}}, /* 48: RPMX7 */
239 {{{0, 0x3100000, 0x3104000, 0x1a8000}}}, /* 49: XDMA */
240 {{{1, 0x3200000, 0x3204000, 0x1d4000}}}, /* 50: I2Q */
241 {{{1, 0x3300000, 0x3304000, 0x1a0000}}}, /* 51: ROMUSB */
242 {{{0}}}, /* 52: */
243 {{{1, 0x3500000, 0x3500400, 0x1ac000}}}, /* 53: RPMX0 */
244 {{{1, 0x3600000, 0x3600400, 0x1ae000}}}, /* 54: RPMX8 */
245 {{{1, 0x3700000, 0x3700400, 0x1ae400}}}, /* 55: RPMX9 */
246 {{{1, 0x3800000, 0x3804000, 0x1d0000}}}, /* 56: OCM0 */
247 {{{1, 0x3900000, 0x3904000, 0x1b4000}}}, /* 57: CRYPTO */
248 {{{1, 0x3a00000, 0x3a04000, 0x1d8000}}}, /* 58: SMB */
249 {{{0}}}, /* 59: I2C0 */
250 {{{0}}}, /* 60: I2C1 */
251 {{{1, 0x3d00000, 0x3d04000, 0x1dc000}}}, /* 61: LPC */
252 {{{1, 0x3e00000, 0x3e01000, 0x167000}}}, /* 62: P2NC */
253 {{{1, 0x3f00000, 0x3f01000, 0x168000}}} /* 63: P2NR0 */
254 };
255
256 /*
257 * top 12 bits of crb internal address (hub, agent)
258 */
259 static uint32_t crb_hub_agt[64] = {
260 0,
261 UNM_HW_CRB_HUB_AGT_ADR_PS,
262 UNM_HW_CRB_HUB_AGT_ADR_MN,
263 UNM_HW_CRB_HUB_AGT_ADR_MS,
264 0,
265 UNM_HW_CRB_HUB_AGT_ADR_SRE,
266 UNM_HW_CRB_HUB_AGT_ADR_NIU,
267 UNM_HW_CRB_HUB_AGT_ADR_QMN,
268 UNM_HW_CRB_HUB_AGT_ADR_SQN0,
269 UNM_HW_CRB_HUB_AGT_ADR_SQN1,
270 UNM_HW_CRB_HUB_AGT_ADR_SQN2,
271 UNM_HW_CRB_HUB_AGT_ADR_SQN3,
272 UNM_HW_CRB_HUB_AGT_ADR_I2Q,
273 UNM_HW_CRB_HUB_AGT_ADR_TIMR,
274 UNM_HW_CRB_HUB_AGT_ADR_ROMUSB,
275 UNM_HW_CRB_HUB_AGT_ADR_PGN4,
276 UNM_HW_CRB_HUB_AGT_ADR_XDMA,
277 UNM_HW_CRB_HUB_AGT_ADR_PGN0,
278 UNM_HW_CRB_HUB_AGT_ADR_PGN1,
279 UNM_HW_CRB_HUB_AGT_ADR_PGN2,
280 UNM_HW_CRB_HUB_AGT_ADR_PGN3,
281 UNM_HW_CRB_HUB_AGT_ADR_PGND,
282 UNM_HW_CRB_HUB_AGT_ADR_PGNI,
283 UNM_HW_CRB_HUB_AGT_ADR_PGS0,
284 UNM_HW_CRB_HUB_AGT_ADR_PGS1,
285 UNM_HW_CRB_HUB_AGT_ADR_PGS2,
286 UNM_HW_CRB_HUB_AGT_ADR_PGS3,
287 0,
288 UNM_HW_CRB_HUB_AGT_ADR_PGSI,
289 UNM_HW_CRB_HUB_AGT_ADR_SN,
290 0,
291 UNM_HW_CRB_HUB_AGT_ADR_EG,
292 0,
293 UNM_HW_CRB_HUB_AGT_ADR_PS,
294 UNM_HW_CRB_HUB_AGT_ADR_CAM,
295 0,
296 0,
297 0,
298 0,
299 0,
300 UNM_HW_CRB_HUB_AGT_ADR_TIMR,
301 0,
302 UNM_HW_CRB_HUB_AGT_ADR_RPMX1,
303 UNM_HW_CRB_HUB_AGT_ADR_RPMX2,
304 UNM_HW_CRB_HUB_AGT_ADR_RPMX3,
305 UNM_HW_CRB_HUB_AGT_ADR_RPMX4,
306 UNM_HW_CRB_HUB_AGT_ADR_RPMX5,
307 UNM_HW_CRB_HUB_AGT_ADR_RPMX6,
308 UNM_HW_CRB_HUB_AGT_ADR_RPMX7,
309 UNM_HW_CRB_HUB_AGT_ADR_XDMA,
310 UNM_HW_CRB_HUB_AGT_ADR_I2Q,
311 UNM_HW_CRB_HUB_AGT_ADR_ROMUSB,
312 0,
313 UNM_HW_CRB_HUB_AGT_ADR_RPMX0,
314 UNM_HW_CRB_HUB_AGT_ADR_RPMX8,
315 UNM_HW_CRB_HUB_AGT_ADR_RPMX9,
316 UNM_HW_CRB_HUB_AGT_ADR_OCM0,
317 0,
318 UNM_HW_CRB_HUB_AGT_ADR_SMB,
319 UNM_HW_CRB_HUB_AGT_ADR_I2C0,
320 UNM_HW_CRB_HUB_AGT_ADR_I2C1,
321 0,
322 UNM_HW_CRB_HUB_AGT_ADR_PGNC,
323 0,
324 };
325
326 static void *
ql_8021_pci_base_offsetfset(ql_adapter_state_t * ha,uint64_t off)327 ql_8021_pci_base_offsetfset(ql_adapter_state_t *ha, uint64_t off)
328 {
329 if ((off < ha->first_page_group_end) &&
330 (off >= ha->first_page_group_start)) {
331 return ((void *)(ha->nx_pcibase + off));
332 }
333
334 return (NULL);
335 }
336
337 /* ARGSUSED */
338 static void
ql_crb_addr_transform_setup(ql_adapter_state_t * ha)339 ql_crb_addr_transform_setup(ql_adapter_state_t *ha)
340 {
341 crb_addr_transform(XDMA);
342 crb_addr_transform(TIMR);
343 crb_addr_transform(SRE);
344 crb_addr_transform(SQN3);
345 crb_addr_transform(SQN2);
346 crb_addr_transform(SQN1);
347 crb_addr_transform(SQN0);
348 crb_addr_transform(SQS3);
349 crb_addr_transform(SQS2);
350 crb_addr_transform(SQS1);
351 crb_addr_transform(SQS0);
352 crb_addr_transform(RPMX7);
353 crb_addr_transform(RPMX6);
354 crb_addr_transform(RPMX5);
355 crb_addr_transform(RPMX4);
356 crb_addr_transform(RPMX3);
357 crb_addr_transform(RPMX2);
358 crb_addr_transform(RPMX1);
359 crb_addr_transform(RPMX0);
360 crb_addr_transform(ROMUSB);
361 crb_addr_transform(SN);
362 crb_addr_transform(QMN);
363 crb_addr_transform(QMS);
364 crb_addr_transform(PGNI);
365 crb_addr_transform(PGND);
366 crb_addr_transform(PGN3);
367 crb_addr_transform(PGN2);
368 crb_addr_transform(PGN1);
369 crb_addr_transform(PGN0);
370 crb_addr_transform(PGSI);
371 crb_addr_transform(PGSD);
372 crb_addr_transform(PGS3);
373 crb_addr_transform(PGS2);
374 crb_addr_transform(PGS1);
375 crb_addr_transform(PGS0);
376 crb_addr_transform(PS);
377 crb_addr_transform(PH);
378 crb_addr_transform(NIU);
379 crb_addr_transform(I2Q);
380 crb_addr_transform(EG);
381 crb_addr_transform(MN);
382 crb_addr_transform(MS);
383 crb_addr_transform(CAS2);
384 crb_addr_transform(CAS1);
385 crb_addr_transform(CAS0);
386 crb_addr_transform(CAM);
387 crb_addr_transform(C2C1);
388 crb_addr_transform(C2C0);
389 crb_addr_transform(SMB);
390 crb_addr_transform(OCM0);
391 /*
392 * Used only in P3 just define it for P2 also.
393 */
394 crb_addr_transform(I2C0);
395
396 crb_table_initialized = 1;
397 }
398
399 /*
400 * In: 'off' is offset from CRB space in 128M pci map
401 * Out: 'off' is 2M pci map addr
402 * side effect: lock crb window
403 */
404 static void
ql_8021_pci_set_crbwindow_2M(ql_adapter_state_t * ha,uint64_t * off)405 ql_8021_pci_set_crbwindow_2M(ql_adapter_state_t *ha, uint64_t *off)
406 {
407 uint32_t win_read;
408
409 ha->crb_win = (uint32_t)CRB_HI(*off);
410 WRT_REG_DWORD(ha, CRB_WINDOW_2M + ha->nx_pcibase, ha->crb_win);
411
412 /*
413 * Read back value to make sure write has gone through before trying
414 * to use it.
415 */
416 win_read = RD_REG_DWORD(ha, CRB_WINDOW_2M + ha->nx_pcibase);
417 if (win_read != ha->crb_win) {
418 EL(ha, "Written crbwin (0x%x) != Read crbwin (0x%x), "
419 "off=0x%llx\n", ha->crb_win, win_read, *off);
420 }
421 *off = (*off & MASK(16)) + CRB_INDIRECT_2M + (uintptr_t)ha->nx_pcibase;
422 }
423
424 static void
ql_8021_wr_32(ql_adapter_state_t * ha,uint64_t off,uint32_t data)425 ql_8021_wr_32(ql_adapter_state_t *ha, uint64_t off, uint32_t data)
426 {
427 int rv;
428
429 rv = ql_8021_pci_get_crb_addr_2M(ha, &off);
430 if (rv == -1) {
431 cmn_err(CE_PANIC, "ql_8021_wr_32, ql_8021_pci_get_crb_addr_"
432 "2M=-1\n");
433 }
434 if (rv == 1) {
435 (void) ql_8021_crb_win_lock(ha);
436 ql_8021_pci_set_crbwindow_2M(ha, &off);
437 }
438
439 WRT_REG_DWORD(ha, (uintptr_t)off, data);
440
441 if (rv == 1) {
442 ql_8021_crb_win_unlock(ha);
443 }
444 }
445
446 static void
ql_8021_rd_32(ql_adapter_state_t * ha,uint64_t off,uint32_t * data)447 ql_8021_rd_32(ql_adapter_state_t *ha, uint64_t off, uint32_t *data)
448 {
449 int rv;
450 uint32_t n;
451
452 rv = ql_8021_pci_get_crb_addr_2M(ha, &off);
453 if (rv == -1) {
454 cmn_err(CE_PANIC, "ql_8021_rd_32, ql_8021_pci_get_crb_addr_"
455 "2M=-1\n");
456 }
457
458 if (rv == 1) {
459 (void) ql_8021_crb_win_lock(ha);
460 ql_8021_pci_set_crbwindow_2M(ha, &off);
461 }
462 n = RD_REG_DWORD(ha, (uintptr_t)off);
463
464 if (data != NULL) {
465 *data = n;
466 }
467
468 if (rv == 1) {
469 ql_8021_crb_win_unlock(ha);
470 }
471 }
472
473 static int
ql_8021_crb_win_lock(ql_adapter_state_t * ha)474 ql_8021_crb_win_lock(ql_adapter_state_t *ha)
475 {
476 uint32_t done = 0, timeout = 0;
477
478 while (!done) {
479 /* acquire semaphore3 from PCI HW block */
480 ql_8021_rd_32(ha, UNM_PCIE_REG(PCIE_SEM7_LOCK), &done);
481 if (done == 1) {
482 break;
483 }
484 if (timeout >= CRB_WIN_LOCK_TIMEOUT) {
485 EL(ha, "timeout\n");
486 return (-1);
487 }
488 timeout++;
489
490 /* Yield CPU */
491 delay(1);
492 }
493 ql_8021_wr_32(ha, UNM_CRB_WIN_LOCK_ID, ha->function_number);
494
495 return (0);
496 }
497
498 static void
ql_8021_crb_win_unlock(ql_adapter_state_t * ha)499 ql_8021_crb_win_unlock(ql_adapter_state_t *ha)
500 {
501 ql_8021_rd_32(ha, UNM_PCIE_REG(PCIE_SEM7_UNLOCK), NULL);
502 }
503
504 static int
ql_8021_pci_get_crb_addr_2M(ql_adapter_state_t * ha,uint64_t * off)505 ql_8021_pci_get_crb_addr_2M(ql_adapter_state_t *ha, uint64_t *off)
506 {
507 crb_128M_2M_sub_block_map_t *m;
508
509 if (*off >= UNM_CRB_MAX) {
510 EL(ha, "%llx >= %llx\n", *off, UNM_CRB_MAX);
511 return (-1);
512 }
513
514 if (*off >= UNM_PCI_CAMQM && (*off < UNM_PCI_CAMQM_2M_END)) {
515 *off = (*off - UNM_PCI_CAMQM) + UNM_PCI_CAMQM_2M_BASE +
516 (uintptr_t)ha->nx_pcibase;
517 return (0);
518 }
519
520 if (*off < UNM_PCI_CRBSPACE) {
521 EL(ha, "%llx < %llx\n", *off, UNM_PCI_CRBSPACE);
522 return (-1);
523 }
524
525 *off -= UNM_PCI_CRBSPACE;
526 /*
527 * Try direct map
528 */
529
530 m = &crb_128M_2M_map[CRB_BLK(*off)].sub_block[CRB_SUBBLK(*off)];
531
532 if (m->valid && ((uint64_t)m->start_128M <= *off) &&
533 ((uint64_t)m->end_128M > *off)) {
534 *off = (uint64_t)(*off + m->start_2M - m->start_128M +
535 (uintptr_t)ha->nx_pcibase);
536 return (0);
537 }
538
539 /*
540 * Not in direct map, use crb window
541 */
542 return (1);
543 }
544
545 /*
546 * check memory access boundary.
547 * used by test agent. support ddr access only for now
548 */
549 /* ARGSUSED */
550 static uint32_t
ql_8021_pci_mem_bound_check(ql_adapter_state_t * ha,uint64_t addr,uint32_t size)551 ql_8021_pci_mem_bound_check(ql_adapter_state_t *ha, uint64_t addr,
552 uint32_t size)
553 {
554 /*LINTED suspicious 0 comparison*/
555 if (!QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_DDR_NET,
556 UNM_ADDR_DDR_NET_MAX) ||
557 /*LINTED suspicious 0 comparison*/
558 !QL_8021_ADDR_IN_RANGE(addr + size - 1, UNM_ADDR_DDR_NET,
559 UNM_ADDR_DDR_NET_MAX) ||
560 ((size != 1) && (size != 2) && (size != 4) && (size != 8))) {
561 return (0);
562 }
563
564 return (1);
565 }
566
567 static uint64_t
ql_8021_pci_set_window(ql_adapter_state_t * ha,uint64_t addr)568 ql_8021_pci_set_window(ql_adapter_state_t *ha, uint64_t addr)
569 {
570 uint32_t window, win_read;
571
572 /*LINTED suspicious 0 comparison*/
573 if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_DDR_NET,
574 UNM_ADDR_DDR_NET_MAX)) {
575 /* DDR network side */
576 window = (uint32_t)MN_WIN(addr);
577 ha->ddr_mn_window = window;
578 ql_8021_wr_32(ha, ha->mn_win_crb | UNM_PCI_CRBSPACE, window);
579 ql_8021_rd_32(ha, ha->mn_win_crb | UNM_PCI_CRBSPACE,
580 &win_read);
581 if ((win_read << 17) != window) {
582 EL(ha, "Warning, Written MNwin (0x%x) != Read MNwin "
583 "(0x%x)\n", window, win_read);
584 }
585 addr = GET_MEM_OFFS_2M(addr) + UNM_PCI_DDR_NET;
586 } else if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_OCM0,
587 UNM_ADDR_OCM0_MAX)) {
588 uint32_t temp1;
589
590 if ((addr & 0x00ff800) == 0xff800) {
591 /* if bits 19:18&17:11 are on */
592 EL(ha, "QM access not handled\n");
593 addr = -1UL;
594 }
595
596 window = (uint32_t)OCM_WIN(addr);
597 ha->ddr_mn_window = window;
598 ql_8021_wr_32(ha, ha->mn_win_crb | UNM_PCI_CRBSPACE, window);
599 ql_8021_rd_32(ha, ha->mn_win_crb | UNM_PCI_CRBSPACE,
600 &win_read);
601 temp1 = ((window & 0x1FF) << 7) |
602 ((window & 0x0FFFE0000) >> 17);
603 if (win_read != temp1) {
604 EL(ha, "Written OCMwin (0x%x) != Read OCMwin (0x%x)\n",
605 temp1, win_read);
606 }
607 addr = GET_MEM_OFFS_2M(addr) + UNM_PCI_OCM0_2M;
608 } else if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_QDR_NET,
609 NX_P3_ADDR_QDR_NET_MAX)) {
610 /* QDR network side */
611 window = (uint32_t)MS_WIN(addr);
612 ha->qdr_sn_window = window;
613 ql_8021_wr_32(ha, ha->mn_win_crb | UNM_PCI_CRBSPACE, window);
614 ql_8021_rd_32(ha, ha->mn_win_crb | UNM_PCI_CRBSPACE,
615 &win_read);
616 if (win_read != window) {
617 EL(ha, "Written MSwin (0x%x) != Read MSwin (0x%x)\n",
618 window, win_read);
619 }
620 addr = GET_MEM_OFFS_2M(addr) + UNM_PCI_QDR_NET;
621 } else {
622 /*
623 * peg gdb frequently accesses memory that doesn't exist,
624 * this limits the chit chat so debugging isn't slowed down.
625 */
626 if ((pci_set_window_warning_count++ < 8) ||
627 (pci_set_window_warning_count % 64 == 0)) {
628 EL(ha, "Unknown address range\n");
629 }
630 addr = -1UL;
631 }
632
633 return (addr);
634 }
635
636 /* check if address is in the same windows as the previous access */
637 static int
ql_8021_pci_is_same_window(ql_adapter_state_t * ha,uint64_t addr)638 ql_8021_pci_is_same_window(ql_adapter_state_t *ha, uint64_t addr)
639 {
640 uint32_t window;
641 uint64_t qdr_max;
642
643 qdr_max = NX_P3_ADDR_QDR_NET_MAX;
644
645 /*LINTED suspicious 0 comparison*/
646 if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_DDR_NET,
647 UNM_ADDR_DDR_NET_MAX)) {
648 /* DDR network side */
649 EL(ha, "DDR network side\n");
650 return (0); /* MN access can not come here */
651 } else if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_OCM0,
652 UNM_ADDR_OCM0_MAX)) {
653 return (1);
654 } else if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_OCM1,
655 UNM_ADDR_OCM1_MAX)) {
656 return (1);
657 } else if (QL_8021_ADDR_IN_RANGE(addr, UNM_ADDR_QDR_NET, qdr_max)) {
658 /* QDR network side */
659 window = (uint32_t)(((addr - UNM_ADDR_QDR_NET) >> 22) & 0x3f);
660 if (ha->qdr_sn_window == window) {
661 return (1);
662 }
663 }
664
665 return (0);
666 }
667
668 static int
ql_8021_pci_mem_read_direct(ql_adapter_state_t * ha,uint64_t off,void * data,uint32_t size)669 ql_8021_pci_mem_read_direct(ql_adapter_state_t *ha, uint64_t off, void *data,
670 uint32_t size)
671 {
672 void *addr;
673 int ret = 0;
674 uint64_t start;
675
676 /*
677 * If attempting to access unknown address or straddle hw windows,
678 * do not access.
679 */
680 if (((start = ql_8021_pci_set_window(ha, off)) == -1UL) ||
681 (ql_8021_pci_is_same_window(ha, off + size - 1) == 0)) {
682 EL(ha, "out of bound pci memory access. offset is 0x%llx\n",
683 off);
684 return (-1);
685 }
686
687 addr = ql_8021_pci_base_offsetfset(ha, start);
688 if (!addr) {
689 addr = (void *)((uint8_t *)ha->nx_pcibase + start);
690 }
691
692 switch (size) {
693 case 1:
694 *(uint8_t *)data = RD_REG_BYTE(ha, addr);
695 break;
696 case 2:
697 *(uint16_t *)data = RD_REG_WORD(ha, addr);
698 break;
699 case 4:
700 *(uint32_t *)data = RD_REG_DWORD(ha, addr);
701 break;
702 case 8:
703 *(uint64_t *)data = RD_REG_DDWORD(ha, addr);
704 break;
705 default:
706 EL(ha, "invalid size=%x\n", size);
707 ret = -1;
708 break;
709 }
710
711 return (ret);
712 }
713
714 static int
ql_8021_pci_mem_write_direct(ql_adapter_state_t * ha,uint64_t off,void * data,uint32_t size)715 ql_8021_pci_mem_write_direct(ql_adapter_state_t *ha, uint64_t off, void *data,
716 uint32_t size)
717 {
718 void *addr;
719 int ret = 0;
720 uint64_t start;
721
722 /*
723 * If attempting to access unknown address or straddle hw windows,
724 * do not access.
725 */
726 if (((start = ql_8021_pci_set_window(ha, off)) == -1UL) ||
727 (ql_8021_pci_is_same_window(ha, off + size -1) == 0)) {
728 EL(ha, "out of bound pci memory access. offset is 0x%llx\n",
729 off);
730 return (-1);
731 }
732
733 addr = ql_8021_pci_base_offsetfset(ha, start);
734 if (!addr) {
735 addr = (void *)((uint8_t *)ha->nx_pcibase + start);
736 }
737
738 switch (size) {
739 case 1:
740 WRT_REG_BYTE(ha, addr, *(uint8_t *)data);
741 break;
742 case 2:
743 WRT_REG_WORD(ha, addr, *(uint16_t *)data);
744 break;
745 case 4:
746 WRT_REG_DWORD(ha, addr, *(uint32_t *)data);
747 break;
748 case 8:
749 WRT_REG_DDWORD(ha, addr, *(uint64_t *)data);
750 break;
751 default:
752 EL(ha, "invalid size=%x\n", size);
753 ret = -1;
754 break;
755 }
756
757 return (ret);
758 }
759
760 static int
ql_8021_pci_mem_read_2M(ql_adapter_state_t * ha,uint64_t off,void * data,uint32_t size)761 ql_8021_pci_mem_read_2M(ql_adapter_state_t *ha, uint64_t off, void *data,
762 uint32_t size)
763 {
764 int j = 0;
765 uint32_t i, temp, sz[2], loop, shift_amount;
766 uint64_t start, end, k;
767 uint64_t off8, off0[2], val, mem_crb, word[2] = {0, 0};
768
769 /*
770 * If not MN, go check for MS or invalid.
771 */
772
773 if (off >= UNM_ADDR_QDR_NET && off <= NX_P3_ADDR_QDR_NET_MAX) {
774 mem_crb = UNM_CRB_QDR_NET;
775 } else {
776 mem_crb = UNM_CRB_DDR_NET;
777 if (ql_8021_pci_mem_bound_check(ha, off, size) == 0) {
778 return (ql_8021_pci_mem_read_direct(ha, off, data,
779 size));
780 }
781 }
782
783 if (NX_IS_REVISION_P3PLUS(ha->rev_id)) {
784 off8 = off & 0xfffffff0;
785 off0[0] = off & 0xf;
786 sz[0] = (uint32_t)(((uint64_t)size < (16 - off0[0])) ? size :
787 (16 - off0[0]));
788 shift_amount = 4;
789 } else {
790 off8 = off & 0xfffffff8;
791 off0[0] = off & 0x7;
792 sz[0] = (uint32_t)(((uint64_t)size < (8 - off0[0])) ? size :
793 (8 - off0[0]));
794 shift_amount = 3;
795 }
796 loop = (uint32_t)(((off0[0] + size - 1) >> shift_amount) + 1);
797 off0[1] = 0;
798 sz[1] = size - sz[0];
799
800 /*
801 * don't lock here - write_wx gets the lock if each time
802 * write_lock_irqsave(&adapter->adapter_lock, flags);
803 * netxen_nic_pci_change_crbwindow_128M(adapter, 0);
804 */
805
806 for (i = 0; i < loop; i++) {
807 temp = (uint32_t)(off8 + (i << shift_amount));
808 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_ADDR_LO, temp);
809 temp = 0;
810 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_ADDR_HI, temp);
811 temp = MIU_TA_CTL_ENABLE;
812 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_CTRL, temp);
813 temp = MIU_TA_CTL_START | MIU_TA_CTL_ENABLE;
814 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_CTRL, temp);
815
816 for (j = 0; j < MAX_CTL_CHECK; j++) {
817 ql_8021_rd_32(ha, mem_crb + MIU_TEST_AGT_CTRL, &temp);
818 if ((temp & MIU_TA_CTL_BUSY) == 0) {
819 break;
820 }
821 }
822
823 if (j >= MAX_CTL_CHECK) {
824 EL(ha, "failed to read through agent\n");
825 break;
826 }
827
828 start = off0[i] >> 2;
829 end = (off0[i] + sz[i] - 1) >> 2;
830 for (k = start; k <= end; k++) {
831 ql_8021_rd_32(ha, mem_crb + MIU_TEST_AGT_RDDATA(k),
832 &temp);
833 word[i] |= ((uint64_t)temp << (32 * (k & 1)));
834 }
835 }
836
837 /*
838 * netxen_nic_pci_change_crbwindow_128M(adapter, 1);
839 * write_unlock_irqrestore(&adapter->adapter_lock, flags);
840 */
841
842 if (j >= MAX_CTL_CHECK) {
843 return (-1);
844 }
845
846 if ((off0[0] & 7) == 0) {
847 val = word[0];
848 } else {
849 val = ((word[0] >> (off0[0] * 8)) & (~(~0ULL << (sz[0] * 8)))) |
850 ((word[1] & (~(~0ULL << (sz[1] * 8)))) << (sz[0] * 8));
851 }
852
853 switch (size) {
854 case 1:
855 *(uint8_t *)data = (uint8_t)val;
856 break;
857 case 2:
858 *(uint16_t *)data = (uint16_t)val;
859 break;
860 case 4:
861 *(uint32_t *)data = (uint32_t)val;
862 break;
863 case 8:
864 *(uint64_t *)data = val;
865 break;
866 }
867
868 return (0);
869 }
870
871 static int
ql_8021_pci_mem_write_2M(ql_adapter_state_t * ha,uint64_t off,void * data,uint32_t size)872 ql_8021_pci_mem_write_2M(ql_adapter_state_t *ha, uint64_t off, void *data,
873 uint32_t size)
874 {
875 int j, ret = 0;
876 uint32_t i, temp, loop, sz[2];
877 uint32_t scale, shift_amount, p3p, startword;
878 uint64_t off8, off0, mem_crb, tmpw, word[2] = {0, 0};
879
880 /*
881 * If not MN, go check for MS or invalid.
882 */
883 if (off >= UNM_ADDR_QDR_NET && off <= NX_P3_ADDR_QDR_NET_MAX) {
884 mem_crb = UNM_CRB_QDR_NET;
885 } else {
886 mem_crb = UNM_CRB_DDR_NET;
887 if (ql_8021_pci_mem_bound_check(ha, off, size) == 0) {
888 return (ql_8021_pci_mem_write_direct(ha, off, data,
889 size));
890 }
891 }
892
893 off0 = off & 0x7;
894 sz[0] = (uint32_t)(((uint64_t)size < (8 - off0)) ? size : (8 - off0));
895 sz[1] = size - sz[0];
896
897 if (NX_IS_REVISION_P3PLUS(ha->rev_id)) {
898 off8 = off & 0xfffffff0;
899 loop = (uint32_t)((((off & 0xf) + size - 1) >> 4) + 1);
900 shift_amount = 4;
901 scale = 2;
902 p3p = 1;
903 startword = (uint32_t)((off & 0xf) / 8);
904 } else {
905 off8 = off & 0xfffffff8;
906 loop = (uint32_t)(((off0 + size - 1) >> 3) + 1);
907 shift_amount = 3;
908 scale = 1;
909 p3p = 0;
910 startword = 0;
911 }
912
913 if (p3p || (size != 8) || (off0 != 0)) {
914 for (i = 0; i < loop; i++) {
915 if (ql_8021_pci_mem_read_2M(ha, off8 +
916 (i << shift_amount), &word[i * scale], 8)) {
917 EL(ha, "8021_pci_mem_read_2M != 0\n");
918 return (-1);
919 }
920 }
921 }
922
923 switch (size) {
924 case 1:
925 tmpw = (uint64_t)(*((uint8_t *)data));
926 break;
927 case 2:
928 tmpw = (uint64_t)(*((uint16_t *)data));
929 break;
930 case 4:
931 tmpw = (uint64_t)(*((uint32_t *)data));
932 break;
933 case 8:
934 default:
935 tmpw = *((uint64_t *)data);
936 break;
937 }
938
939 if (p3p) {
940 if (sz[0] == 8) {
941 word[startword] = tmpw;
942 } else {
943 word[startword] &= ~((~(~0ULL << (sz[0] * 8))) <<
944 (off0 * 8));
945 word[startword] |= tmpw << (off0 * 8);
946 }
947 if (sz[1] != 0) {
948 word[startword+1] &= ~(~0ULL << (sz[1] * 8));
949 word[startword+1] |= tmpw >> (sz[0] * 8);
950 }
951 } else {
952 word[startword] &= ~((~(~0ULL << (sz[0] * 8))) << (off0 * 8));
953 word[startword] |= tmpw << (off0 * 8);
954
955 if (loop == 2) {
956 word[1] &= ~(~0ULL << (sz[1] * 8));
957 word[1] |= tmpw >> (sz[0] * 8);
958 }
959 }
960
961 /*
962 * don't lock here - write_wx gets the lock if each time
963 * write_lock_irqsave(&adapter->adapter_lock, flags);
964 * netxen_nic_pci_change_crbwindow_128M(adapter, 0);
965 */
966
967 for (i = 0; i < loop; i++) {
968 temp = (uint32_t)(off8 + (i << shift_amount));
969 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_ADDR_LO, temp);
970 temp = 0;
971 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_ADDR_HI, temp);
972 temp = (uint32_t)(word[i * scale] & 0xffffffff);
973 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_WRDATA_LO, temp);
974 temp = (uint32_t)((word[i * scale] >> 32) & 0xffffffff);
975 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_WRDATA_HI, temp);
976 if (p3p) {
977 temp = (uint32_t)(word[i * scale + 1] & 0xffffffff);
978 ql_8021_wr_32(ha,
979 mem_crb + MIU_TEST_AGT_WRDATA_UPPER_LO, temp);
980 temp = (uint32_t)((word[i * scale + 1] >> 32) &
981 0xffffffff);
982 ql_8021_wr_32(ha,
983 mem_crb + MIU_TEST_AGT_WRDATA_UPPER_HI, temp);
984 }
985 temp = MIU_TA_CTL_ENABLE | MIU_TA_CTL_WRITE;
986 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_CTRL, temp);
987 temp = MIU_TA_CTL_START | MIU_TA_CTL_ENABLE | MIU_TA_CTL_WRITE;
988 ql_8021_wr_32(ha, mem_crb + MIU_TEST_AGT_CTRL, temp);
989
990 for (j = 0; j < MAX_CTL_CHECK; j++) {
991 ql_8021_rd_32(ha, mem_crb + MIU_TEST_AGT_CTRL, &temp);
992 if ((temp & MIU_TA_CTL_BUSY) == 0)
993 break;
994 }
995
996 if (j >= MAX_CTL_CHECK) {
997 EL(ha, "failed to write through agent\n");
998 ret = -1;
999 break;
1000 }
1001 }
1002
1003 return (ret);
1004 }
1005
1006 static uint32_t
ql_8021_decode_crb_addr(ql_adapter_state_t * ha,uint32_t addr)1007 ql_8021_decode_crb_addr(ql_adapter_state_t *ha, uint32_t addr)
1008 {
1009 int i;
1010 uint32_t base_addr, offset, pci_base;
1011
1012 if (!crb_table_initialized) {
1013 ql_crb_addr_transform_setup(ha);
1014 }
1015
1016 pci_base = ADDR_ERROR;
1017 base_addr = addr & 0xfff00000;
1018 offset = addr & 0x000fffff;
1019
1020 for (i = 0; i < MAX_CRB_XFORM; i++) {
1021 if (crb_addr_xform[i] == base_addr) {
1022 pci_base = i << 20;
1023 break;
1024 }
1025 }
1026 if (pci_base == ADDR_ERROR) {
1027 return (pci_base);
1028 } else {
1029 return (pci_base + offset);
1030 }
1031 }
1032
1033 static int
ql_8021_hw_lock(ql_adapter_state_t * ha,uint32_t timer)1034 ql_8021_hw_lock(ql_adapter_state_t *ha, uint32_t timer)
1035 {
1036 uint32_t done = 0, timeout = 0;
1037
1038 while (!done) {
1039 /* acquire semaphore5 from PCI HW block */
1040 ql_8021_rd_32(ha, UNM_PCIE_REG(PCIE_SEM5_LOCK), &done);
1041 if (done == 1) {
1042 break;
1043 }
1044 if (timeout >= timer) {
1045 EL(ha, "timeout\n");
1046 return (-1);
1047 }
1048 timeout++;
1049
1050 /*
1051 * Yield CPU
1052 */
1053 delay(1);
1054 }
1055
1056 return (0);
1057 }
1058
1059 static void
ql_8021_hw_unlock(ql_adapter_state_t * ha)1060 ql_8021_hw_unlock(ql_adapter_state_t *ha)
1061 {
1062 ql_8021_rd_32(ha, UNM_PCIE_REG(PCIE_SEM5_UNLOCK), NULL);
1063 }
1064
1065 static int
ql_8021_rom_lock(ql_adapter_state_t * ha)1066 ql_8021_rom_lock(ql_adapter_state_t *ha)
1067 {
1068 uint32_t done = 0, timeout = 0;
1069
1070 while (!done) {
1071 /* acquire semaphore2 from PCI HW block */
1072 ql_8021_rd_32(ha, UNM_PCIE_REG(PCIE_SEM2_LOCK), &done);
1073 if (done == 1) {
1074 break;
1075 }
1076 if (timeout >= ROM_LOCK_TIMEOUT) {
1077 EL(ha, "timeout\n");
1078 return (-1);
1079 }
1080 timeout++;
1081
1082 /*
1083 * Yield CPU
1084 */
1085 delay(1);
1086 }
1087 ql_8021_wr_32(ha, UNM_ROM_LOCK_ID, ROM_LOCK_DRIVER);
1088
1089 return (0);
1090 }
1091
1092 static void
ql_8021_rom_unlock(ql_adapter_state_t * ha)1093 ql_8021_rom_unlock(ql_adapter_state_t *ha)
1094 {
1095 ql_8021_rd_32(ha, UNM_PCIE_REG(PCIE_SEM2_UNLOCK), NULL);
1096 }
1097
1098 static int
ql_8021_wait_rom_done(ql_adapter_state_t * ha)1099 ql_8021_wait_rom_done(ql_adapter_state_t *ha)
1100 {
1101 uint32_t timeout = 0, done = 0;
1102
1103 while (done == 0) {
1104 ql_8021_rd_32(ha, UNM_ROMUSB_GLB_STATUS, &done);
1105 done &= 2;
1106 timeout++;
1107 if (timeout >= ROM_MAX_TIMEOUT) {
1108 EL(ha, "Timeout reached waiting for rom done\n");
1109 return (-1);
1110 }
1111 }
1112
1113 return (0);
1114 }
1115
1116 static int
ql_8021_wait_flash_done(ql_adapter_state_t * ha)1117 ql_8021_wait_flash_done(ql_adapter_state_t *ha)
1118 {
1119 clock_t timer;
1120 uint32_t status;
1121
1122 for (timer = 30 * drv_usectohz(1000000); timer; timer--) {
1123 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 0);
1124 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1125 UNM_ROMUSB_ROM_RDSR_INSTR);
1126 if (ql_8021_wait_rom_done(ha)) {
1127 EL(ha, "Error waiting for rom done2\n");
1128 return (-1);
1129 }
1130
1131 /* Get status. */
1132 ql_8021_rd_32(ha, UNM_ROMUSB_ROM_RDATA, &status);
1133 if (!(status & BIT_0)) {
1134 return (0);
1135 }
1136 delay(1);
1137 }
1138
1139 EL(ha, "timeout status=%x\n", status);
1140 return (-1);
1141 }
1142
1143 static int
ql_8021_do_rom_fast_read(ql_adapter_state_t * ha,uint32_t addr,uint32_t * valp)1144 ql_8021_do_rom_fast_read(ql_adapter_state_t *ha, uint32_t addr, uint32_t *valp)
1145 {
1146 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ADDRESS, addr);
1147 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_DUMMY_BYTE_CNT, 0);
1148 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 3);
1149 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1150 UNM_ROMUSB_ROM_FAST_RD_INSTR);
1151 if (ql_8021_wait_rom_done(ha)) {
1152 EL(ha, "Error waiting for rom done\n");
1153 return (-1);
1154 }
1155 /* reset abyte_cnt and dummy_byte_cnt */
1156 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_DUMMY_BYTE_CNT, 0);
1157 drv_usecwait(10);
1158 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 0);
1159
1160 ql_8021_rd_32(ha, UNM_ROMUSB_ROM_RDATA, valp);
1161
1162 return (0);
1163 }
1164
1165 int
ql_8021_rom_fast_read(ql_adapter_state_t * ha,uint32_t addr,uint32_t * valp)1166 ql_8021_rom_fast_read(ql_adapter_state_t *ha, uint32_t addr, uint32_t *valp)
1167 {
1168 int ret, loops = 0;
1169
1170 while ((ql_8021_rom_lock(ha) != 0) && (loops < 50000)) {
1171 drv_usecwait(100);
1172 loops++;
1173 }
1174 if (loops >= 50000) {
1175 EL(ha, "rom_lock failed\n");
1176 return (-1);
1177 }
1178 ret = ql_8021_do_rom_fast_read(ha, addr, valp);
1179 ql_8021_rom_unlock(ha);
1180
1181 return (ret);
1182 }
1183
1184 static int
ql_8021_do_rom_write(ql_adapter_state_t * ha,uint32_t addr,uint32_t data)1185 ql_8021_do_rom_write(ql_adapter_state_t *ha, uint32_t addr, uint32_t data)
1186 {
1187 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 0);
1188 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1189 UNM_ROMUSB_ROM_WREN_INSTR);
1190 if (ql_8021_wait_rom_done(ha)) {
1191 EL(ha, "Error waiting for rom done\n");
1192 return (-1);
1193 }
1194
1195 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_WDATA, data);
1196 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ADDRESS, addr);
1197 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 3);
1198 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1199 UNM_ROMUSB_ROM_PP_INSTR);
1200 if (ql_8021_wait_rom_done(ha)) {
1201 EL(ha, "Error waiting for rom done1\n");
1202 return (-1);
1203 }
1204
1205 if (ql_8021_wait_flash_done(ha)) {
1206 EL(ha, "Error waiting for flash done\n");
1207 return (-1);
1208 }
1209
1210 return (0);
1211 }
1212
1213 static int
ql_8021_do_rom_erase(ql_adapter_state_t * ha,uint32_t addr)1214 ql_8021_do_rom_erase(ql_adapter_state_t *ha, uint32_t addr)
1215 {
1216 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 0);
1217 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1218 UNM_ROMUSB_ROM_WREN_INSTR);
1219 if (ql_8021_wait_rom_done(ha)) {
1220 EL(ha, "Error waiting for rom done\n");
1221 return (-1);
1222 }
1223
1224 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ADDRESS, addr);
1225 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 3);
1226 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1227 UNM_ROMUSB_ROM_SE_INSTR);
1228 if (ql_8021_wait_rom_done(ha)) {
1229 EL(ha, "Error waiting for rom done1\n");
1230 return (-1);
1231 }
1232
1233 if (ql_8021_wait_flash_done(ha)) {
1234 EL(ha, "Error waiting for flash done\n");
1235 return (-1);
1236 }
1237
1238 return (0);
1239 }
1240
1241 int
ql_8021_rom_read(ql_adapter_state_t * ha,uint32_t addr,uint32_t * bp)1242 ql_8021_rom_read(ql_adapter_state_t *ha, uint32_t addr, uint32_t *bp)
1243 {
1244 int ret;
1245
1246 ret = ql_8021_rom_fast_read(ha, addr << 2, bp) == 0 ? QL_SUCCESS :
1247 QL_FUNCTION_FAILED;
1248
1249 return (ret);
1250 }
1251
1252 int
ql_8021_rom_write(ql_adapter_state_t * ha,uint32_t addr,uint32_t data)1253 ql_8021_rom_write(ql_adapter_state_t *ha, uint32_t addr, uint32_t data)
1254 {
1255 int ret, loops = 0;
1256
1257 while ((ql_8021_rom_lock(ha) != 0) && (loops < 50000)) {
1258 drv_usecwait(100);
1259 loops++;
1260 }
1261 if (loops >= 50000) {
1262 EL(ha, "rom_lock failed\n");
1263 ret = QL_FUNCTION_TIMEOUT;
1264 } else {
1265 ret = ql_8021_do_rom_write(ha, addr << 2, data) == 0 ?
1266 QL_SUCCESS : QL_FUNCTION_FAILED;
1267 ql_8021_rom_unlock(ha);
1268 }
1269
1270 return (ret);
1271 }
1272
1273 int
ql_8021_rom_erase(ql_adapter_state_t * ha,uint32_t addr)1274 ql_8021_rom_erase(ql_adapter_state_t *ha, uint32_t addr)
1275 {
1276 int ret, loops = 0;
1277
1278 while ((ql_8021_rom_lock(ha) != 0) && (loops < 50000)) {
1279 drv_usecwait(100);
1280 loops++;
1281 }
1282 if (loops >= 50000) {
1283 EL(ha, "rom_lock failed\n");
1284 ret = QL_FUNCTION_TIMEOUT;
1285 } else {
1286 ret = ql_8021_do_rom_erase(ha, addr << 2) == 0 ? QL_SUCCESS :
1287 QL_FUNCTION_FAILED;
1288 ql_8021_rom_unlock(ha);
1289 }
1290
1291 return (ret);
1292 }
1293
1294 int
ql_8021_rom_wrsr(ql_adapter_state_t * ha,uint32_t data)1295 ql_8021_rom_wrsr(ql_adapter_state_t *ha, uint32_t data)
1296 {
1297 int ret = QL_SUCCESS, loops = 0;
1298
1299 while ((ql_8021_rom_lock(ha) != 0) && (loops < 50000)) {
1300 drv_usecwait(100);
1301 loops++;
1302 }
1303 if (loops >= 50000) {
1304 EL(ha, "rom_lock failed\n");
1305 ret = QL_FUNCTION_TIMEOUT;
1306 } else {
1307 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 0);
1308 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1309 UNM_ROMUSB_ROM_WREN_INSTR);
1310 if (ql_8021_wait_rom_done(ha)) {
1311 EL(ha, "Error waiting for rom done\n");
1312 ret = QL_FUNCTION_FAILED;
1313 } else {
1314 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_WDATA, data);
1315 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_ABYTE_CNT, 0);
1316 ql_8021_wr_32(ha, UNM_ROMUSB_ROM_INSTR_OPCODE,
1317 UNM_ROMUSB_ROM_WRSR_INSTR);
1318 if (ql_8021_wait_rom_done(ha)) {
1319 EL(ha, "Error waiting for rom done1\n");
1320 ret = QL_FUNCTION_FAILED;
1321 } else if (ql_8021_wait_flash_done(ha)) {
1322 EL(ha, "Error waiting for flash done\n");
1323 ret = QL_FUNCTION_FAILED;
1324 }
1325 }
1326 ql_8021_rom_unlock(ha);
1327 }
1328
1329 return (ret);
1330 }
1331
1332 static int
ql_8021_phantom_init(ql_adapter_state_t * ha)1333 ql_8021_phantom_init(ql_adapter_state_t *ha)
1334 {
1335 uint32_t val = 0, err = 0;
1336 int retries = 60;
1337
1338 do {
1339 ql_8021_rd_32(ha, CRB_CMDPEG_STATE, &val);
1340
1341 switch (val) {
1342 case PHAN_INITIALIZE_COMPLETE:
1343 case PHAN_INITIALIZE_ACK:
1344 EL(ha, "success=%xh\n", val);
1345 return (0);
1346 case PHAN_INITIALIZE_FAILED:
1347 EL(ha, "PHAN_INITIALIZE_FAILED\n");
1348 err = 1;
1349 break;
1350 default:
1351 break;
1352 }
1353
1354 if (err) {
1355 break;
1356 }
1357 /* 500 msec wait */
1358 delay(50);
1359
1360 } while (--retries);
1361
1362 if (!err) {
1363 ql_8021_wr_32(ha, CRB_CMDPEG_STATE, PHAN_INITIALIZE_FAILED);
1364 }
1365
1366 EL(ha, "firmware init failed=%x\n", val);
1367 return (-1);
1368 }
1369
1370 static int
ql_8021_pinit_from_rom(ql_adapter_state_t * ha)1371 ql_8021_pinit_from_rom(ql_adapter_state_t *ha)
1372 {
1373 int init_delay = 0;
1374 struct crb_addr_pair *buf;
1375 uint32_t offset, off, i, n, addr, val;
1376
1377 /* Grab the lock so that no one can read flash when we reset the chip */
1378 (void) ql_8021_rom_lock(ha);
1379 ql_8021_wr_32(ha, UNM_ROMUSB_GLB_SW_RESET, 0xffffffff);
1380 /* Just in case it was held when we reset the chip */
1381 ql_8021_rom_unlock(ha);
1382
1383 if (ql_8021_rom_fast_read(ha, 0, &n) != 0 || n != 0xcafecafe ||
1384 ql_8021_rom_fast_read(ha, 4, &n) != 0) {
1385 EL(ha, "ERROR Reading crb_init area: n: %08x\n", n);
1386 return (-1);
1387 }
1388 offset = n & 0xffff;
1389 n = (n >> 16) & 0xffff;
1390 if (n >= 1024) {
1391 EL(ha, "n=0x%x Error! NetXen card flash not initialized\n", n);
1392 return (-1);
1393 }
1394
1395 buf = kmem_zalloc(n * sizeof (struct crb_addr_pair), KM_SLEEP);
1396 if (buf == NULL) {
1397 EL(ha, "Unable to zalloc memory\n");
1398 return (-1);
1399 }
1400
1401 for (i = 0; i < n; i++) {
1402 if (ql_8021_rom_fast_read(ha, 8 * i + 4 * offset, &val) != 0 ||
1403 ql_8021_rom_fast_read(ha, 8 * i + 4 * offset + 4, &addr) !=
1404 0) {
1405 kmem_free(buf, n * sizeof (struct crb_addr_pair));
1406 EL(ha, "ql_8021_rom_fast_read != 0 to zalloc memory\n");
1407 return (-1);
1408 }
1409
1410 buf[i].addr = addr;
1411 buf[i].data = val;
1412 }
1413
1414 for (i = 0; i < n; i++) {
1415 off = ql_8021_decode_crb_addr(ha, buf[i].addr);
1416 if (off == ADDR_ERROR) {
1417 EL(ha, "Err: Unknown addr: 0x%lx\n", buf[i].addr);
1418 continue;
1419 }
1420 off += UNM_PCI_CRBSPACE;
1421
1422 if (off & 1) {
1423 continue;
1424 }
1425
1426 /* skipping cold reboot MAGIC */
1427 if (off == UNM_RAM_COLD_BOOT) {
1428 continue;
1429 }
1430 if (off == (UNM_CRB_I2C0 + 0x1c)) {
1431 continue;
1432 }
1433 /* do not reset PCI */
1434 if (off == (ROMUSB_GLB + 0xbc)) {
1435 continue;
1436 }
1437 if (off == (ROMUSB_GLB + 0xa8)) {
1438 continue;
1439 }
1440 if (off == (ROMUSB_GLB + 0xc8)) { /* core clock */
1441 continue;
1442 }
1443 if (off == (ROMUSB_GLB + 0x24)) { /* MN clock */
1444 continue;
1445 }
1446 if (off == (ROMUSB_GLB + 0x1c)) { /* MS clock */
1447 continue;
1448 }
1449 if ((off & 0x0ff00000) == UNM_CRB_DDR_NET) {
1450 continue;
1451 }
1452 if (off == (UNM_CRB_PEG_NET_1 + 0x18) &&
1453 !NX_IS_REVISION_P3PLUS(ha->rev_id)) {
1454 buf[i].data = 0x1020;
1455 }
1456 /* skip the function enable register */
1457 if (off == UNM_PCIE_REG(PCIE_SETUP_FUNCTION)) {
1458 continue;
1459 }
1460 if (off == UNM_PCIE_REG(PCIE_SETUP_FUNCTION2)) {
1461 continue;
1462 }
1463 if ((off & 0x0ff00000) == UNM_CRB_SMB) {
1464 continue;
1465 }
1466
1467 /* After writing this register, HW needs time for CRB */
1468 /* to quiet down (else crb_window returns 0xffffffff) */
1469 init_delay = 1;
1470 if (off == UNM_ROMUSB_GLB_SW_RESET) {
1471 init_delay = 100; /* Sleep 1000 msecs */
1472 }
1473
1474 ql_8021_wr_32(ha, off, buf[i].data);
1475
1476 delay(init_delay);
1477 }
1478 kmem_free(buf, n * sizeof (struct crb_addr_pair));
1479
1480 /* disable_peg_cache_all */
1481
1482 /* p2dn replyCount */
1483 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_D + 0xec, 0x1e);
1484 /* disable_peg_cache 0 */
1485 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_D + 0x4c, 8);
1486 /* disable_peg_cache 1 */
1487 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_I + 0x4c, 8);
1488
1489 /* peg_clr_all */
1490 /* peg_clr 0 */
1491 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_0 + 0x8, 0);
1492 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_0 + 0xc, 0);
1493 /* peg_clr 1 */
1494 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_1 + 0x8, 0);
1495 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_1 + 0xc, 0);
1496 /* peg_clr 2 */
1497 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_2 + 0x8, 0);
1498 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_2 + 0xc, 0);
1499 /* peg_clr 3 */
1500 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_3 + 0x8, 0);
1501 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_3 + 0xc, 0);
1502
1503 return (0);
1504 }
1505
1506 static int
ql_8021_load_from_flash(ql_adapter_state_t * ha)1507 ql_8021_load_from_flash(ql_adapter_state_t *ha)
1508 {
1509 int i;
1510 uint32_t flashaddr, memaddr;
1511 uint32_t high, low, size;
1512 uint64_t data;
1513
1514 size = ha->bootloader_size / 2;
1515 flashaddr = ha->bootloader_addr << 2;
1516 memaddr = BOOTLD_START;
1517
1518 for (i = 0; i < size; i++) {
1519 if ((ql_8021_rom_fast_read(ha, flashaddr, &low)) ||
1520 (ql_8021_rom_fast_read(ha, flashaddr + 4, &high))) {
1521 EL(ha, "ql_8021_rom_fast_read != 0\n");
1522 return (-1);
1523 }
1524 data = ((uint64_t)high << 32) | low;
1525 (void) ql_8021_pci_mem_write_2M(ha, memaddr, &data, 8);
1526 flashaddr += 8;
1527 memaddr += 8;
1528 }
1529
1530 size = ha->flash_fw_size / 2;
1531 flashaddr = ha->flash_fw_addr << 2;
1532 memaddr = IMAGE_START;
1533
1534 for (i = 0; i < size; i++) {
1535 if ((ql_8021_rom_fast_read(ha, flashaddr, &low)) ||
1536 (ql_8021_rom_fast_read(ha, flashaddr + 4, &high))) {
1537 EL(ha, "ql_8021_rom_fast_read3 != 0\n");
1538 return (-1);
1539 }
1540 data = ((uint64_t)high << 32) | low;
1541 (void) ql_8021_pci_mem_write_2M(ha, memaddr, &data, 8);
1542 flashaddr += 8;
1543 memaddr += 8;
1544 }
1545
1546 return (0);
1547 }
1548
1549 static int
ql_8021_load_firmware(ql_adapter_state_t * ha)1550 ql_8021_load_firmware(ql_adapter_state_t *ha)
1551 {
1552 uint64_t data;
1553 uint32_t i, flashaddr, size;
1554 uint8_t *bp, n, *dp;
1555
1556 bp = (uint8_t *)(ha->risc_fw[0].code);
1557 dp = (uint8_t *)&size;
1558 for (n = 0; n < 4; n++) {
1559 dp[n] = *bp++;
1560 }
1561 LITTLE_ENDIAN_32(&size);
1562 EL(ha, "signature=%x\n", size);
1563
1564 size = (IMAGE_START - BOOTLD_START) / 8;
1565
1566 bp = (uint8_t *)(ha->risc_fw[0].code + BOOTLD_START);
1567 flashaddr = BOOTLD_START;
1568
1569 dp = (uint8_t *)&data;
1570 for (i = 0; i < size; i++) {
1571 for (n = 0; n < 8; n++) {
1572 dp[n] = *bp++;
1573 }
1574 LITTLE_ENDIAN_64(&data);
1575 (void) ql_8021_pci_mem_write_2M(ha, flashaddr, &data, 8);
1576 flashaddr += 8;
1577 }
1578
1579 bp = (uint8_t *)(ha->risc_fw[0].code + FW_SIZE_OFFSET);
1580 dp = (uint8_t *)&size;
1581 for (n = 0; n < 4; n++) {
1582 dp[n] = *bp++;
1583 }
1584 LITTLE_ENDIAN_32(&size);
1585 EL(ha, "IMAGE_START size=%llx\n", size);
1586 size = (size + 7) / 8;
1587
1588 bp = (uint8_t *)(ha->risc_fw[0].code + IMAGE_START);
1589 flashaddr = IMAGE_START;
1590
1591 dp = (uint8_t *)&data;
1592 for (i = 0; i < size; i++) {
1593 for (n = 0; n < 8; n++) {
1594 dp[n] = *bp++;
1595 }
1596 LITTLE_ENDIAN_64(&data);
1597 (void) ql_8021_pci_mem_write_2M(ha, flashaddr, &data, 8);
1598 flashaddr += 8;
1599 }
1600
1601 return (0);
1602 }
1603
1604 static int
ql_8021_init_p3p(ql_adapter_state_t * ha)1605 ql_8021_init_p3p(ql_adapter_state_t *ha)
1606 {
1607 uint32_t data;
1608
1609 /* ??? */
1610 ql_8021_wr_32(ha, UNM_PORT_MODE_ADDR, UNM_PORT_MODE_AUTO_NEG);
1611 delay(drv_usectohz(1000000));
1612
1613 /* CAM RAM Cold Boot Register */
1614 ql_8021_rd_32(ha, UNM_RAM_COLD_BOOT, &data);
1615 if (data == 0x55555555) {
1616 ql_8021_rd_32(ha, UNM_ROMUSB_GLB_SW_RESET, &data);
1617 if (data != 0x80000f) {
1618 EL(ha, "CRB_UNM_GLB_SW_RST=%x exit\n", data);
1619 return (-1);
1620 }
1621 ql_8021_wr_32(ha, UNM_RAM_COLD_BOOT, 0);
1622 }
1623 ql_8021_rd_32(ha, UNM_ROMUSB_GLB_PEGTUNE_DONE, &data);
1624 data |= 1;
1625 ql_8021_wr_32(ha, UNM_ROMUSB_GLB_PEGTUNE_DONE, data);
1626
1627 /*
1628 * ???
1629 * data = ha->pci_bus_addr | BIT_31;
1630 * ql_8021_wr_32(ha, UNM_BUS_DEV_NO, data);
1631 */
1632
1633 return (0);
1634 }
1635
1636 /* ARGSUSED */
1637 void
ql_8021_reset_chip(ql_adapter_state_t * ha)1638 ql_8021_reset_chip(ql_adapter_state_t *ha)
1639 {
1640 /*
1641 * Disable interrupts does not work on a per function bases
1642 * leave them enabled
1643 */
1644 ql_8021_enable_intrs(ha);
1645
1646 ADAPTER_STATE_LOCK(ha);
1647 ha->flags |= INTERRUPTS_ENABLED;
1648 ADAPTER_STATE_UNLOCK(ha);
1649
1650 (void) ql_stop_firmware(ha);
1651 }
1652
1653 static int
ql_8021_reset_hw(ql_adapter_state_t * ha,int type)1654 ql_8021_reset_hw(ql_adapter_state_t *ha, int type)
1655 {
1656 int ret;
1657 uint32_t rst;
1658
1659 /* scrub dma mask expansion register */
1660 ql_8021_wr_32(ha, CRB_DMA_SHIFT, 0x55555555);
1661
1662 /* Overwrite stale initialization register values */
1663 ql_8021_wr_32(ha, CRB_CMDPEG_STATE, 0);
1664 ql_8021_wr_32(ha, CRB_RCVPEG_STATE, 0);
1665 ql_8021_wr_32(ha, UNM_PEG_HALT_STATUS1, 0);
1666 ql_8021_wr_32(ha, UNM_PEG_HALT_STATUS2, 0);
1667
1668 (void) ql_8021_pinit_from_rom(ha);
1669 delay(1);
1670
1671 /* Bring QM and CAMRAM out of reset */
1672 ql_8021_rd_32(ha, UNM_ROMUSB_GLB_SW_RESET, &rst);
1673 rst &= ~((1 << 28) | (1 << 24));
1674 ql_8021_wr_32(ha, UNM_ROMUSB_GLB_SW_RESET, rst);
1675
1676 switch (type) {
1677 case 0:
1678 ret = ql_8021_init_p3p(ha);
1679 break;
1680 case 1:
1681 ret = ql_8021_load_from_flash(ha);
1682 break;
1683 case 2:
1684 ret = ql_8021_load_firmware(ha);
1685 break;
1686 }
1687 delay(1);
1688
1689 ql_8021_wr_32(ha, UNM_CRB_PEG_NET_0 + 0x18, 0x1020);
1690 ql_8021_wr_32(ha, UNM_ROMUSB_GLB_SW_RESET, 0x80001e);
1691
1692 if (ret) {
1693 EL(ha, "type=%d, ret=%d\n", type, ret);
1694 } else {
1695 ret = ql_8021_phantom_init(ha);
1696 }
1697 return (ret);
1698 }
1699
1700 int
ql_8021_load_risc(ql_adapter_state_t * ha)1701 ql_8021_load_risc(ql_adapter_state_t *ha)
1702 {
1703 int rv = 0;
1704 static int ql_8021_fw_loaded = 0;
1705
1706 GLOBAL_HW_LOCK();
1707 if (!ql_8021_fw_loaded) {
1708 if (ha->risc_fw[0].code) {
1709 EL(ha, "from driver\n");
1710 rv = ql_8021_reset_hw(ha, 2);
1711 } else {
1712 /*
1713 * BIOS method
1714 * ql_8021_reset_hw(ha, 0)
1715 */
1716 EL(ha, "from flash\n");
1717 rv = ql_8021_reset_hw(ha, 1);
1718 }
1719 if (rv == 0) {
1720 ql_8021_fw_loaded = 1;
1721
1722 ql_8021_wr_32(ha, CRB_DMA_SHIFT, 0x55555555);
1723 ql_8021_wr_32(ha, UNM_PEG_HALT_STATUS1, 0x0);
1724 ql_8021_wr_32(ha, UNM_PEG_HALT_STATUS2, 0x0);
1725
1726 GLOBAL_HW_UNLOCK();
1727
1728 ADAPTER_STATE_LOCK(ha);
1729 ha->flags &= ~INTERRUPTS_ENABLED;
1730 ADAPTER_STATE_UNLOCK(ha);
1731
1732 (void) ql_8021_enable_intrs(ha);
1733
1734 ADAPTER_STATE_LOCK(ha);
1735 ha->flags |= INTERRUPTS_ENABLED;
1736 ADAPTER_STATE_UNLOCK(ha);
1737 } else {
1738 GLOBAL_HW_UNLOCK();
1739 }
1740 } else {
1741 GLOBAL_HW_UNLOCK();
1742 EL(ha, "Firmware loaded by other function\n");
1743 }
1744
1745 if (rv == 0) {
1746 ql_8021_rd_32(ha, UNM_FW_VERSION_MAJOR, &ha->fw_major_version);
1747 ql_8021_rd_32(ha, UNM_FW_VERSION_MINOR, &ha->fw_minor_version);
1748 ql_8021_rd_32(ha, UNM_FW_VERSION_SUB, &ha->fw_subminor_version);
1749 EL(ha, "fw v%d.%02d.%02d\n", ha->fw_major_version,
1750 ha->fw_minor_version, ha->fw_subminor_version);
1751 } else {
1752 EL(ha, "status = -1\n");
1753 return (QL_FUNCTION_FAILED);
1754 }
1755
1756 return (QL_SUCCESS);
1757 }
1758
1759 void
ql_8021_clr_hw_intr(ql_adapter_state_t * ha)1760 ql_8021_clr_hw_intr(ql_adapter_state_t *ha)
1761 {
1762 ql_8021_wr_32(ha, ha->nx_legacy_intr.tgt_status_reg, 0xffffffff);
1763 ql_8021_rd_32(ha, ISR_INT_VECTOR, NULL);
1764 ql_8021_rd_32(ha, ISR_INT_VECTOR, NULL);
1765 }
1766
1767 void
ql_8021_clr_fw_intr(ql_adapter_state_t * ha)1768 ql_8021_clr_fw_intr(ql_adapter_state_t *ha)
1769 {
1770 WRT32_IO_REG(ha, nx_risc_int, 0);
1771 ql_8021_wr_32(ha, ha->nx_legacy_intr.tgt_status_reg, 0xfbff);
1772 }
1773
1774 void
ql_8021_enable_intrs(ql_adapter_state_t * ha)1775 ql_8021_enable_intrs(ql_adapter_state_t *ha)
1776 {
1777 GLOBAL_HW_LOCK();
1778 ql_8021_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0xfbff);
1779 GLOBAL_HW_UNLOCK();
1780 (void) ql_toggle_interrupt(ha, 1);
1781 }
1782
1783 void
ql_8021_disable_intrs(ql_adapter_state_t * ha)1784 ql_8021_disable_intrs(ql_adapter_state_t *ha)
1785 {
1786 (void) ql_toggle_interrupt(ha, 0);
1787 GLOBAL_HW_LOCK();
1788 ql_8021_wr_32(ha, ha->nx_legacy_intr.tgt_mask_reg, 0x0400);
1789 GLOBAL_HW_UNLOCK();
1790 }
1791
1792 void
ql_8021_update_crb_int_ptr(ql_adapter_state_t * ha)1793 ql_8021_update_crb_int_ptr(ql_adapter_state_t *ha)
1794 {
1795 struct legacy_intr_set *nx_legacy_intr;
1796
1797 ha->qdr_sn_window = (uint32_t)-1;
1798 ha->ddr_mn_window = (uint32_t)-1;
1799 nx_legacy_intr = &legacy_intr[ha->function_number];
1800
1801 ha->nx_legacy_intr.int_vec_bit = nx_legacy_intr->int_vec_bit;
1802 ha->nx_legacy_intr.tgt_status_reg = nx_legacy_intr->tgt_status_reg;
1803 ha->nx_legacy_intr.tgt_mask_reg = nx_legacy_intr->tgt_mask_reg;
1804 ha->nx_legacy_intr.pci_int_reg = nx_legacy_intr->pci_int_reg;
1805 }
1806
1807 void
ql_8021_set_drv_active(ql_adapter_state_t * ha)1808 ql_8021_set_drv_active(ql_adapter_state_t *ha)
1809 {
1810 uint32_t val;
1811
1812 if (ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT)) {
1813 return;
1814 }
1815
1816 ql_8021_rd_32(ha, CRB_DRV_ACTIVE, &val);
1817 if (val == 0xffffffff) {
1818 val = (1 << (ha->function_number * 4));
1819 } else {
1820 val |= (1 << (ha->function_number * 4));
1821 }
1822 ql_8021_wr_32(ha, CRB_DRV_ACTIVE, val);
1823
1824 ql_8021_hw_unlock(ha);
1825 }
1826
1827 void
ql_8021_clr_drv_active(ql_adapter_state_t * ha)1828 ql_8021_clr_drv_active(ql_adapter_state_t *ha)
1829 {
1830 uint32_t val;
1831
1832 if (ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT)) {
1833 return;
1834 }
1835
1836 ql_8021_rd_32(ha, CRB_DRV_ACTIVE, &val);
1837 val &= ~(1 << (ha->function_number * 4));
1838 ql_8021_wr_32(ha, CRB_DRV_ACTIVE, val);
1839
1840 ql_8021_hw_unlock(ha);
1841 }
1842
1843 static void
ql_8021_need_reset_handler(ql_adapter_state_t * ha)1844 ql_8021_need_reset_handler(ql_adapter_state_t *ha)
1845 {
1846 uint32_t drv_state, drv_active;
1847 clock_t timer;
1848
1849 (void) ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT);
1850
1851 ql_8021_rd_32(ha, CRB_DRV_STATE, &drv_state);
1852 drv_state |= (1 << (ha->function_number * 4));
1853 ql_8021_wr_32(ha, CRB_DRV_STATE, drv_state);
1854
1855 ql_8021_rd_32(ha, CRB_DRV_ACTIVE, &drv_active);
1856
1857 ql_8021_hw_unlock(ha);
1858
1859 for (timer = 30; timer && drv_state != drv_active; timer--) {
1860 delay(100);
1861
1862 (void) ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT);
1863 ql_8021_rd_32(ha, CRB_DRV_STATE, &drv_state);
1864 ql_8021_rd_32(ha, CRB_DRV_ACTIVE, &drv_active);
1865 ql_8021_hw_unlock(ha);
1866 }
1867 }
1868
1869 uint32_t
ql_8021_idc_handler(ql_adapter_state_t * ha)1870 ql_8021_idc_handler(ql_adapter_state_t *ha)
1871 {
1872 uint32_t dev_state, drv_state, rval;
1873 clock_t timer;
1874 ql_mbx_data_t mr;
1875 boolean_t stalled = B_FALSE, lock = B_FALSE;
1876
1877 /* wait for 30 seconds for device to go ready */
1878 timer = 30;
1879 while (timer) {
1880 if (lock == B_FALSE) {
1881 (void) ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT);
1882 lock = B_TRUE;
1883 }
1884 ql_8021_rd_32(ha, CRB_DEV_STATE, &dev_state);
1885
1886 switch (dev_state) {
1887 case 0xffffffff:
1888 case NX_DEV_COLD:
1889 EL(ha, "dev_state=NX_DEV_COLD\n");
1890 rval = NX_DEV_COLD;
1891 ql_8021_wr_32(ha, CRB_DEV_STATE, NX_DEV_INITIALIZING);
1892 ql_8021_wr_32(ha, CRB_DRV_IDC_VERSION, NX_IDC_VERSION);
1893 (void) ql_8021_hw_unlock(ha);
1894 if (ql_get_fw_version(ha, &mr, 2) == QL_SUCCESS &&
1895 (mr.mb[1] | mr.mb[2] | mr.mb[3])) {
1896 ql_8021_rd_32(ha, UNM_FW_VERSION_MAJOR,
1897 &ha->fw_major_version);
1898 ql_8021_rd_32(ha, UNM_FW_VERSION_MINOR,
1899 &ha->fw_minor_version);
1900 ql_8021_rd_32(ha, UNM_FW_VERSION_SUB,
1901 &ha->fw_subminor_version);
1902 rval = NX_DEV_READY;
1903 } else if (ql_8021_load_risc(ha) == QL_SUCCESS) {
1904 rval = NX_DEV_READY;
1905 }
1906 (void) ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT);
1907 ql_8021_wr_32(ha, CRB_DEV_STATE, rval);
1908 break;
1909 case NX_DEV_READY:
1910 rval = NX_DEV_READY;
1911 timer = 0;
1912 break;
1913 case NX_DEV_FAILED:
1914 EL(ha, "dev_state=NX_DEV_FAILED\n");
1915 rval = NX_DEV_FAILED;
1916 timer = 0;
1917 break;
1918
1919 case NX_DEV_NEED_RESET:
1920 EL(ha, "dev_state=NX_DEV_NEED_RESET\n");
1921 rval = NX_DEV_NEED_RESET;
1922 (void) ql_8021_hw_unlock(ha);
1923 lock = B_FALSE;
1924 if (ql_stall_driver(ha, 0) == QL_SUCCESS) {
1925 stalled = B_TRUE;
1926 ql_8021_need_reset_handler(ha);
1927 }
1928 break;
1929
1930 case NX_DEV_NEED_QUIESCENT:
1931 EL(ha, "dev_state=NX_DEV_NEED_QUIESCENT\n");
1932 (void) ql_8021_hw_unlock(ha);
1933 lock = B_FALSE;
1934 rval = ql_stall_driver(ha, 0);
1935 if (rval == QL_SUCCESS) {
1936 stalled = B_TRUE;
1937 (void) ql_8021_hw_lock(ha, IDC_LOCK_TIMEOUT);
1938 lock = B_TRUE;
1939 ql_8021_rd_32(ha, CRB_DRV_STATE, &drv_state);
1940 drv_state |=
1941 (2 << (ha->function_number * 4));
1942 ql_8021_wr_32(ha, CRB_DRV_STATE, drv_state);
1943 }
1944 break;
1945
1946 case NX_DEV_INITIALIZING:
1947 EL(ha, "dev_state=NX_DEV_INITIALIZING\n");
1948 break;
1949 case NX_DEV_QUIESCENT:
1950 EL(ha, "dev_state=NX_DEV_QUIESCENT\n");
1951 break;
1952 default:
1953 EL(ha, "dev_state=%x, default\n", dev_state);
1954 break;
1955 }
1956 if (lock == B_TRUE) {
1957 (void) ql_8021_hw_unlock(ha);
1958 lock = B_FALSE;
1959 }
1960
1961 if (timer) {
1962 delay(100);
1963 timer--;
1964 }
1965 }
1966
1967 if (stalled) {
1968 ql_restart_driver(ha);
1969 }
1970 return (rval);
1971 }
1972