1 /* QLogic qed NIC Driver
2 * Copyright (c) 2015 QLogic Corporation
4 * This software is available under the terms of the GNU General Public License
5 * (GPL) Version 2, available from the file COPYING in the main directory of
9 #include <linux/types.h>
11 #include <linux/delay.h>
12 #include <linux/errno.h>
13 #include <linux/kernel.h>
14 #include <linux/slab.h>
15 #include <linux/string.h>
19 #include "qed_init_ops.h"
20 #include "qed_reg_addr.h"
21 #include "qed_sriov.h"
23 #define QED_INIT_MAX_POLL_COUNT 100
24 #define QED_INIT_POLL_PERIOD_US 500
26 static u32 pxp_global_win
[] = {
29 0x1c02, /* win 2: addr=0x1c02000, size=4096 bytes */
30 0x1c80, /* win 3: addr=0x1c80000, size=4096 bytes */
31 0x1d00, /* win 4: addr=0x1d00000, size=4096 bytes */
32 0x1d01, /* win 5: addr=0x1d01000, size=4096 bytes */
33 0x1d80, /* win 6: addr=0x1d80000, size=4096 bytes */
34 0x1d81, /* win 7: addr=0x1d81000, size=4096 bytes */
35 0x1d82, /* win 8: addr=0x1d82000, size=4096 bytes */
36 0x1e00, /* win 9: addr=0x1e00000, size=4096 bytes */
37 0x1e80, /* win 10: addr=0x1e80000, size=4096 bytes */
38 0x1f00, /* win 11: addr=0x1f00000, size=4096 bytes */
48 void qed_init_iro_array(struct qed_dev
*cdev
)
50 cdev
->iro_arr
= iro_arr
;
53 /* Runtime configuration helpers */
54 void qed_init_clear_rt_data(struct qed_hwfn
*p_hwfn
)
58 for (i
= 0; i
< RUNTIME_ARRAY_SIZE
; i
++)
59 p_hwfn
->rt_data
.b_valid
[i
] = false;
62 void qed_init_store_rt_reg(struct qed_hwfn
*p_hwfn
,
66 p_hwfn
->rt_data
.init_val
[rt_offset
] = val
;
67 p_hwfn
->rt_data
.b_valid
[rt_offset
] = true;
70 void qed_init_store_rt_agg(struct qed_hwfn
*p_hwfn
,
71 u32 rt_offset
, u32
*p_val
,
76 for (i
= 0; i
< size
/ sizeof(u32
); i
++) {
77 p_hwfn
->rt_data
.init_val
[rt_offset
+ i
] = p_val
[i
];
78 p_hwfn
->rt_data
.b_valid
[rt_offset
+ i
] = true;
82 static int qed_init_rt(struct qed_hwfn
*p_hwfn
,
83 struct qed_ptt
*p_ptt
,
89 u32
*p_init_val
= &p_hwfn
->rt_data
.init_val
[rt_offset
];
90 bool *p_valid
= &p_hwfn
->rt_data
.b_valid
[rt_offset
];
94 /* Since not all RT entries are initialized, go over the RT and
95 * for each segment of initialized values use DMA.
97 for (i
= 0; i
< size
; i
++) {
101 /* In case there isn't any wide-bus configuration here,
102 * simply write the data instead of using dmae.
105 qed_wr(p_hwfn
, p_ptt
, addr
+ (i
<< 2),
110 /* Start of a new segment */
111 for (segment
= 1; i
+ segment
< size
; segment
++)
112 if (!p_valid
[i
+ segment
])
115 rc
= qed_dmae_host2grc(p_hwfn
, p_ptt
,
116 (uintptr_t)(p_init_val
+ i
),
117 addr
+ (i
<< 2), segment
, 0);
121 /* Jump over the entire segment, including invalid entry */
128 int qed_init_alloc(struct qed_hwfn
*p_hwfn
)
130 struct qed_rt_data
*rt_data
= &p_hwfn
->rt_data
;
132 if (IS_VF(p_hwfn
->cdev
))
135 rt_data
->b_valid
= kzalloc(sizeof(bool) * RUNTIME_ARRAY_SIZE
,
137 if (!rt_data
->b_valid
)
140 rt_data
->init_val
= kzalloc(sizeof(u32
) * RUNTIME_ARRAY_SIZE
,
142 if (!rt_data
->init_val
) {
143 kfree(rt_data
->b_valid
);
150 void qed_init_free(struct qed_hwfn
*p_hwfn
)
152 kfree(p_hwfn
->rt_data
.init_val
);
153 kfree(p_hwfn
->rt_data
.b_valid
);
156 static int qed_init_array_dmae(struct qed_hwfn
*p_hwfn
,
157 struct qed_ptt
*p_ptt
,
159 u32 dmae_data_offset
,
167 /* Perform DMAE only for lengthy enough sections or for wide-bus */
168 if (!b_can_dmae
|| (!b_must_dmae
&& (size
< 16))) {
169 const u32
*data
= buf
+ dmae_data_offset
;
172 for (i
= 0; i
< size
; i
++)
173 qed_wr(p_hwfn
, p_ptt
, addr
+ (i
<< 2), data
[i
]);
175 rc
= qed_dmae_host2grc(p_hwfn
, p_ptt
,
176 (uintptr_t)(buf
+ dmae_data_offset
),
183 static int qed_init_fill_dmae(struct qed_hwfn
*p_hwfn
,
184 struct qed_ptt
*p_ptt
,
189 static u32 zero_buffer
[DMAE_MAX_RW_SIZE
];
191 memset(zero_buffer
, 0, sizeof(u32
) * DMAE_MAX_RW_SIZE
);
193 /* invoke the DMAE virtual/physical buffer API with
194 * 1. DMAE init channel
196 * 3. p_hwfb->temp_data,
200 return qed_dmae_host2grc(p_hwfn
, p_ptt
,
201 (uintptr_t)(&zero_buffer
[0]),
203 QED_DMAE_FLAG_RW_REPL_SRC
);
206 static void qed_init_fill(struct qed_hwfn
*p_hwfn
,
207 struct qed_ptt
*p_ptt
,
214 for (i
= 0; i
< fill_count
; i
++, addr
+= sizeof(u32
))
215 qed_wr(p_hwfn
, p_ptt
, addr
, fill
);
218 static int qed_init_cmd_array(struct qed_hwfn
*p_hwfn
,
219 struct qed_ptt
*p_ptt
,
220 struct init_write_op
*cmd
,
224 u32 data
= le32_to_cpu(cmd
->data
);
225 u32 addr
= GET_FIELD(data
, INIT_WRITE_OP_ADDRESS
) << 2;
226 u32 dmae_array_offset
= le32_to_cpu(cmd
->args
.array_offset
);
227 u32 offset
, output_len
, input_len
, max_size
;
228 struct qed_dev
*cdev
= p_hwfn
->cdev
;
229 union init_array_hdr
*hdr
;
230 const u32
*array_data
;
234 array_data
= cdev
->fw_data
->arr_data
;
236 hdr
= (union init_array_hdr
*)(array_data
+
238 data
= le32_to_cpu(hdr
->raw
.data
);
239 switch (GET_FIELD(data
, INIT_ARRAY_RAW_HDR_TYPE
)) {
240 case INIT_ARR_ZIPPED
:
241 offset
= dmae_array_offset
+ 1;
242 input_len
= GET_FIELD(data
,
243 INIT_ARRAY_ZIPPED_HDR_ZIPPED_SIZE
);
244 max_size
= MAX_ZIPPED_SIZE
* 4;
245 memset(p_hwfn
->unzip_buf
, 0, max_size
);
247 output_len
= qed_unzip_data(p_hwfn
, input_len
,
248 (u8
*)&array_data
[offset
],
249 max_size
, (u8
*)p_hwfn
->unzip_buf
);
251 rc
= qed_init_array_dmae(p_hwfn
, p_ptt
, addr
, 0,
254 b_must_dmae
, b_can_dmae
);
256 DP_NOTICE(p_hwfn
, "Failed to unzip dmae data\n");
260 case INIT_ARR_PATTERN
:
262 u32 repeats
= GET_FIELD(data
,
263 INIT_ARRAY_PATTERN_HDR_REPETITIONS
);
266 size
= GET_FIELD(data
, INIT_ARRAY_PATTERN_HDR_PATTERN_SIZE
);
268 for (i
= 0; i
< repeats
; i
++, addr
+= size
<< 2) {
269 rc
= qed_init_array_dmae(p_hwfn
, p_ptt
, addr
,
270 dmae_array_offset
+ 1,
272 b_must_dmae
, b_can_dmae
);
278 case INIT_ARR_STANDARD
:
279 size
= GET_FIELD(data
, INIT_ARRAY_STANDARD_HDR_SIZE
);
280 rc
= qed_init_array_dmae(p_hwfn
, p_ptt
, addr
,
281 dmae_array_offset
+ 1,
283 b_must_dmae
, b_can_dmae
);
290 /* init_ops write command */
291 static int qed_init_cmd_wr(struct qed_hwfn
*p_hwfn
,
292 struct qed_ptt
*p_ptt
,
293 struct init_write_op
*cmd
,
296 u32 data
= le32_to_cpu(cmd
->data
);
297 u32 addr
= GET_FIELD(data
, INIT_WRITE_OP_ADDRESS
) << 2;
298 bool b_must_dmae
= GET_FIELD(data
, INIT_WRITE_OP_WIDE_BUS
);
299 union init_write_args
*arg
= &cmd
->args
;
303 if (b_must_dmae
&& !b_can_dmae
) {
305 "Need to write to %08x for Wide-bus but DMAE isn't allowed\n",
310 switch (GET_FIELD(data
, INIT_WRITE_OP_SOURCE
)) {
311 case INIT_SRC_INLINE
:
312 qed_wr(p_hwfn
, p_ptt
, addr
,
313 le32_to_cpu(arg
->inline_val
));
317 (b_can_dmae
&& (le32_to_cpu(arg
->zeros_count
) >= 64)))
318 rc
= qed_init_fill_dmae(p_hwfn
, p_ptt
, addr
, 0,
319 le32_to_cpu(arg
->zeros_count
));
321 qed_init_fill(p_hwfn
, p_ptt
, addr
, 0,
322 le32_to_cpu(arg
->zeros_count
));
325 rc
= qed_init_cmd_array(p_hwfn
, p_ptt
, cmd
,
326 b_must_dmae
, b_can_dmae
);
328 case INIT_SRC_RUNTIME
:
329 qed_init_rt(p_hwfn
, p_ptt
, addr
,
330 le16_to_cpu(arg
->runtime
.offset
),
331 le16_to_cpu(arg
->runtime
.size
),
339 static inline bool comp_eq(u32 val
, u32 expected_val
)
341 return val
== expected_val
;
344 static inline bool comp_and(u32 val
, u32 expected_val
)
346 return (val
& expected_val
) == expected_val
;
349 static inline bool comp_or(u32 val
, u32 expected_val
)
351 return (val
| expected_val
) > 0;
354 /* init_ops read/poll commands */
355 static void qed_init_cmd_rd(struct qed_hwfn
*p_hwfn
,
356 struct qed_ptt
*p_ptt
,
357 struct init_read_op
*cmd
)
359 bool (*comp_check
)(u32 val
, u32 expected_val
);
360 u32 delay
= QED_INIT_POLL_PERIOD_US
, val
;
361 u32 data
, addr
, poll
;
364 data
= le32_to_cpu(cmd
->op_data
);
365 addr
= GET_FIELD(data
, INIT_READ_OP_ADDRESS
) << 2;
366 poll
= GET_FIELD(data
, INIT_READ_OP_POLL_TYPE
);
369 val
= qed_rd(p_hwfn
, p_ptt
, addr
);
371 if (poll
== INIT_POLL_NONE
)
376 comp_check
= comp_eq
;
379 comp_check
= comp_or
;
382 comp_check
= comp_and
;
385 DP_ERR(p_hwfn
, "Invalid poll comparison type %08x\n",
390 data
= le32_to_cpu(cmd
->expected_val
);
392 i
< QED_INIT_MAX_POLL_COUNT
&& !comp_check(val
, data
);
395 val
= qed_rd(p_hwfn
, p_ptt
, addr
);
398 if (i
== QED_INIT_MAX_POLL_COUNT
) {
400 "Timeout when polling reg: 0x%08x [ Waiting-for: %08x Got: %08x (comparsion %08x)]\n",
401 addr
, le32_to_cpu(cmd
->expected_val
),
402 val
, le32_to_cpu(cmd
->op_data
));
406 /* init_ops callbacks entry point */
407 static void qed_init_cmd_cb(struct qed_hwfn
*p_hwfn
,
408 struct qed_ptt
*p_ptt
,
409 struct init_callback_op
*p_cmd
)
411 DP_NOTICE(p_hwfn
, "Currently init values have no need of callbacks\n");
414 static u8
qed_init_cmd_mode_match(struct qed_hwfn
*p_hwfn
,
418 struct qed_dev
*cdev
= p_hwfn
->cdev
;
419 const u8
*modes_tree_buf
;
420 u8 arg1
, arg2
, tree_val
;
422 modes_tree_buf
= cdev
->fw_data
->modes_tree_buf
;
423 tree_val
= modes_tree_buf
[(*offset
)++];
425 case INIT_MODE_OP_NOT
:
426 return qed_init_cmd_mode_match(p_hwfn
, offset
, modes
) ^ 1;
427 case INIT_MODE_OP_OR
:
428 arg1
= qed_init_cmd_mode_match(p_hwfn
, offset
, modes
);
429 arg2
= qed_init_cmd_mode_match(p_hwfn
, offset
, modes
);
431 case INIT_MODE_OP_AND
:
432 arg1
= qed_init_cmd_mode_match(p_hwfn
, offset
, modes
);
433 arg2
= qed_init_cmd_mode_match(p_hwfn
, offset
, modes
);
436 tree_val
-= MAX_INIT_MODE_OPS
;
437 return (modes
& (1 << tree_val
)) ? 1 : 0;
441 static u32
qed_init_cmd_mode(struct qed_hwfn
*p_hwfn
,
442 struct init_if_mode_op
*p_cmd
,
445 u16 offset
= le16_to_cpu(p_cmd
->modes_buf_offset
);
447 if (qed_init_cmd_mode_match(p_hwfn
, &offset
, modes
))
450 return GET_FIELD(le32_to_cpu(p_cmd
->op_data
),
451 INIT_IF_MODE_OP_CMD_OFFSET
);
454 static u32
qed_init_cmd_phase(struct qed_hwfn
*p_hwfn
,
455 struct init_if_phase_op
*p_cmd
,
459 u32 data
= le32_to_cpu(p_cmd
->phase_data
);
460 u32 op_data
= le32_to_cpu(p_cmd
->op_data
);
462 if (!(GET_FIELD(data
, INIT_IF_PHASE_OP_PHASE
) == phase
&&
463 (GET_FIELD(data
, INIT_IF_PHASE_OP_PHASE_ID
) == ANY_PHASE_ID
||
464 GET_FIELD(data
, INIT_IF_PHASE_OP_PHASE_ID
) == phase_id
)))
465 return GET_FIELD(op_data
, INIT_IF_PHASE_OP_CMD_OFFSET
);
470 int qed_init_run(struct qed_hwfn
*p_hwfn
,
471 struct qed_ptt
*p_ptt
,
476 struct qed_dev
*cdev
= p_hwfn
->cdev
;
477 u32 cmd_num
, num_init_ops
;
478 union init_op
*init_ops
;
482 num_init_ops
= cdev
->fw_data
->init_ops_size
;
483 init_ops
= cdev
->fw_data
->init_ops
;
485 p_hwfn
->unzip_buf
= kzalloc(MAX_ZIPPED_SIZE
* 4, GFP_ATOMIC
);
486 if (!p_hwfn
->unzip_buf
) {
487 DP_NOTICE(p_hwfn
, "Failed to allocate unzip buffer\n");
491 for (cmd_num
= 0; cmd_num
< num_init_ops
; cmd_num
++) {
492 union init_op
*cmd
= &init_ops
[cmd_num
];
493 u32 data
= le32_to_cpu(cmd
->raw
.op_data
);
495 switch (GET_FIELD(data
, INIT_CALLBACK_OP_OP
)) {
497 rc
= qed_init_cmd_wr(p_hwfn
, p_ptt
, &cmd
->write
,
501 qed_init_cmd_rd(p_hwfn
, p_ptt
, &cmd
->read
);
503 case INIT_OP_IF_MODE
:
504 cmd_num
+= qed_init_cmd_mode(p_hwfn
, &cmd
->if_mode
,
507 case INIT_OP_IF_PHASE
:
508 cmd_num
+= qed_init_cmd_phase(p_hwfn
, &cmd
->if_phase
,
510 b_dmae
= GET_FIELD(data
, INIT_IF_PHASE_OP_DMAE_ENABLE
);
513 /* qed_init_run is always invoked from
516 udelay(le32_to_cpu(cmd
->delay
.delay
));
519 case INIT_OP_CALLBACK
:
520 qed_init_cmd_cb(p_hwfn
, p_ptt
, &cmd
->callback
);
528 kfree(p_hwfn
->unzip_buf
);
532 void qed_gtt_init(struct qed_hwfn
*p_hwfn
)
537 /* Set the global windows */
538 gtt_base
= PXP_PF_WINDOW_ADMIN_START
+ PXP_PF_WINDOW_ADMIN_GLOBAL_START
;
540 for (i
= 0; i
< ARRAY_SIZE(pxp_global_win
); i
++)
541 if (pxp_global_win
[i
])
542 REG_WR(p_hwfn
, gtt_base
+ i
* PXP_GLOBAL_ENTRY_SIZE
,
546 int qed_init_fw_data(struct qed_dev
*cdev
, const u8
*data
)
548 struct qed_fw_data
*fw
= cdev
->fw_data
;
549 struct bin_buffer_hdr
*buf_hdr
;
553 DP_NOTICE(cdev
, "Invalid fw data\n");
557 /* First Dword contains metadata and should be skipped */
558 buf_hdr
= (struct bin_buffer_hdr
*)(data
+ sizeof(u32
));
560 offset
= buf_hdr
[BIN_BUF_FW_VER_INFO
].offset
;
561 fw
->fw_ver_info
= (struct fw_ver_info
*)(data
+ offset
);
563 offset
= buf_hdr
[BIN_BUF_INIT_CMD
].offset
;
564 fw
->init_ops
= (union init_op
*)(data
+ offset
);
566 offset
= buf_hdr
[BIN_BUF_INIT_VAL
].offset
;
567 fw
->arr_data
= (u32
*)(data
+ offset
);
569 offset
= buf_hdr
[BIN_BUF_INIT_MODE_TREE
].offset
;
570 fw
->modes_tree_buf
= (u8
*)(data
+ offset
);
571 len
= buf_hdr
[BIN_BUF_INIT_CMD
].length
;
572 fw
->init_ops_size
= len
/ sizeof(struct init_raw_op
);