Branch data Line data Source code
1 : : /* SPDX-License-Identifier: BSD-3-Clause
2 : : * Copyright(c) 2001-2023 Intel Corporation
3 : : */
4 : :
5 : : #include "ice_common.h"
6 : :
7 : : #define GL_MNG_DEF_DEVID 0x000B611C
8 : :
9 : : /**
10 : : * ice_aq_read_nvm
11 : : * @hw: pointer to the HW struct
12 : : * @module_typeid: module pointer location in words from the NVM beginning
13 : : * @offset: byte offset from the module beginning
14 : : * @length: length of the section to be read (in bytes from the offset)
15 : : * @data: command buffer (size [bytes] = length)
16 : : * @last_command: tells if this is the last command in a series
17 : : * @read_shadow_ram: tell if this is a shadow RAM read
18 : : * @cd: pointer to command details structure or NULL
19 : : *
20 : : * Read the NVM using the admin queue commands (0x0701)
21 : : */
22 : : int
23 : 0 : ice_aq_read_nvm(struct ice_hw *hw, u16 module_typeid, u32 offset, u16 length,
24 : : void *data, bool last_command, bool read_shadow_ram,
25 : : struct ice_sq_cd *cd)
26 : : {
27 : : struct ice_aq_desc desc;
28 : : struct ice_aqc_nvm *cmd;
29 : :
30 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
31 : :
32 : : cmd = &desc.params.nvm;
33 : :
34 [ # # ]: 0 : if (offset > ICE_AQC_NVM_MAX_OFFSET)
35 : : return ICE_ERR_PARAM;
36 : :
37 : 0 : ice_fill_dflt_direct_cmd_desc(&desc, ice_aqc_opc_nvm_read);
38 : :
39 [ # # ]: 0 : if (!read_shadow_ram && module_typeid == ICE_AQC_NVM_START_POINT)
40 : 0 : cmd->cmd_flags |= ICE_AQC_NVM_FLASH_ONLY;
41 : :
42 : : /* If this is the last command in a series, set the proper flag. */
43 [ # # ]: 0 : if (last_command)
44 : 0 : cmd->cmd_flags |= ICE_AQC_NVM_LAST_CMD;
45 : 0 : cmd->module_typeid = CPU_TO_LE16(module_typeid);
46 : 0 : cmd->offset_low = CPU_TO_LE16(offset & 0xFFFF);
47 : 0 : cmd->offset_high = (offset >> 16) & 0xFF;
48 : 0 : cmd->length = CPU_TO_LE16(length);
49 : :
50 : 0 : return ice_aq_send_cmd(hw, &desc, data, length, cd);
51 : : }
52 : :
53 : : /**
54 : : * ice_read_flat_nvm - Read portion of NVM by flat offset
55 : : * @hw: pointer to the HW struct
56 : : * @offset: offset from beginning of NVM
57 : : * @length: (in) number of bytes to read; (out) number of bytes actually read
58 : : * @data: buffer to return data in (sized to fit the specified length)
59 : : * @read_shadow_ram: if true, read from shadow RAM instead of NVM
60 : : *
61 : : * Reads a portion of the NVM, as a flat memory space. This function correctly
62 : : * breaks read requests across Shadow RAM sectors and ensures that no single
63 : : * read request exceeds the maximum 4KB read for a single AdminQ command.
64 : : *
65 : : * Returns a status code on failure. Note that the data pointer may be
66 : : * partially updated if some reads succeed before a failure.
67 : : */
68 : : int
69 : 0 : ice_read_flat_nvm(struct ice_hw *hw, u32 offset, u32 *length, u8 *data,
70 : : bool read_shadow_ram)
71 : : {
72 : 0 : u32 inlen = *length;
73 : : u32 bytes_read = 0;
74 : : int retry_cnt = 0;
75 : : bool last_cmd;
76 : : int status;
77 : :
78 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
79 : :
80 : 0 : *length = 0;
81 : :
82 : : /* Verify the length of the read if this is for the Shadow RAM */
83 [ # # # # ]: 0 : if (read_shadow_ram && ((offset + inlen) > (hw->flash.sr_words * 2u))) {
84 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "NVM error: requested data is beyond Shadow RAM limit\n");
85 : 0 : return ICE_ERR_PARAM;
86 : : }
87 : :
88 : : do {
89 : : u32 read_size, sector_offset;
90 : :
91 : : /* ice_aq_read_nvm cannot read more than 4KB at a time.
92 : : * Additionally, a read from the Shadow RAM may not cross over
93 : : * a sector boundary. Conveniently, the sector size is also
94 : : * 4KB.
95 : : */
96 : 0 : sector_offset = offset % ICE_AQ_MAX_BUF_LEN;
97 : 0 : read_size = MIN_T(u32, ICE_AQ_MAX_BUF_LEN - sector_offset,
98 : : inlen - bytes_read);
99 : :
100 : 0 : last_cmd = !(bytes_read + read_size < inlen);
101 : :
102 : : /* ice_aq_read_nvm takes the length as a u16. Our read_size is
103 : : * calculated using a u32, but the ICE_AQ_MAX_BUF_LEN maximum
104 : : * size guarantees that it will fit within the 2 bytes.
105 : : */
106 : 0 : status = ice_aq_read_nvm(hw, ICE_AQC_NVM_START_POINT,
107 : : offset, (u16)read_size,
108 : 0 : data + bytes_read, last_cmd,
109 : : read_shadow_ram, NULL);
110 [ # # ]: 0 : if (status) {
111 [ # # # # ]: 0 : if (hw->adminq.sq_last_status != ICE_AQ_RC_EBUSY ||
112 : : retry_cnt > ICE_SQ_SEND_MAX_EXECUTE)
113 : : break;
114 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM,
115 : : "NVM read EBUSY error, retry %d\n",
116 : : retry_cnt + 1);
117 : 0 : ice_release_nvm(hw);
118 : 0 : msleep(ICE_SQ_SEND_DELAY_TIME_MS);
119 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
120 [ # # ]: 0 : if (status)
121 : : break;
122 : 0 : retry_cnt++;
123 : : } else {
124 : : bytes_read += read_size;
125 : 0 : offset += read_size;
126 : : retry_cnt = 0;
127 : : }
128 [ # # ]: 0 : } while (!last_cmd);
129 : :
130 : 0 : *length = bytes_read;
131 : 0 : return status;
132 : : }
133 : :
134 : : /**
135 : : * ice_read_sr_word_aq - Reads Shadow RAM via AQ
136 : : * @hw: pointer to the HW structure
137 : : * @offset: offset of the Shadow RAM word to read (0x000000 - 0x001FFF)
138 : : * @data: word read from the Shadow RAM
139 : : *
140 : : * Reads one 16 bit word from the Shadow RAM using ice_read_flat_nvm.
141 : : */
142 : 0 : static int ice_read_sr_word_aq(struct ice_hw *hw, u16 offset, u16 *data)
143 : : {
144 : 0 : u32 bytes = sizeof(u16);
145 : : __le16 data_local;
146 : : int status;
147 : :
148 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
149 : :
150 : : /* Note that ice_read_flat_nvm checks if the read is past the Shadow
151 : : * RAM size, and ensures we don't read across a Shadow RAM sector
152 : : * boundary
153 : : */
154 : 0 : status = ice_read_flat_nvm(hw, offset * sizeof(u16), &bytes,
155 : : (_FORCE_ u8 *)&data_local, true);
156 [ # # ]: 0 : if (status)
157 : : return status;
158 : :
159 : 0 : *data = LE16_TO_CPU(data_local);
160 : 0 : return 0;
161 : : }
162 : :
163 : : /**
164 : : * ice_read_sr_buf_aq - Reads Shadow RAM buf via AQ
165 : : * @hw: pointer to the HW structure
166 : : * @offset: offset of the Shadow RAM word to read (0x000000 - 0x001FFF)
167 : : * @words: (in) number of words to read; (out) number of words actually read
168 : : * @data: words read from the Shadow RAM
169 : : *
170 : : * Reads 16 bit words (data buf) from the Shadow RAM. Ownership of the NVM is
171 : : * taken before reading the buffer and later released.
172 : : */
173 : : static int
174 : 0 : ice_read_sr_buf_aq(struct ice_hw *hw, u16 offset, u16 *words, u16 *data)
175 : : {
176 : 0 : u32 bytes = *words * 2, i;
177 : : int status;
178 : :
179 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
180 : :
181 : : /* ice_read_flat_nvm takes into account the 4KB AdminQ and Shadow RAM
182 : : * sector restrictions necessary when reading from the NVM.
183 : : */
184 : 0 : status = ice_read_flat_nvm(hw, offset * 2, &bytes, (u8 *)data, true);
185 : :
186 : : /* Report the number of words successfully read */
187 : 0 : *words = (u16)(bytes / 2);
188 : :
189 : : /* Byte swap the words up to the amount we actually read */
190 : : for (i = 0; i < *words; i++)
191 : : data[i] = LE16_TO_CPU(((_FORCE_ __le16 *)data)[i]);
192 : :
193 : 0 : return status;
194 : : }
195 : :
196 : : /**
197 : : * ice_acquire_nvm - Generic request for acquiring the NVM ownership
198 : : * @hw: pointer to the HW structure
199 : : * @access: NVM access type (read or write)
200 : : *
201 : : * This function will request NVM ownership.
202 : : */
203 : 0 : int ice_acquire_nvm(struct ice_hw *hw, enum ice_aq_res_access_type access)
204 : : {
205 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
206 : :
207 [ # # ]: 0 : if (hw->flash.blank_nvm_mode)
208 : : return 0;
209 : :
210 : 0 : return ice_acquire_res(hw, ICE_NVM_RES_ID, access, ICE_NVM_TIMEOUT);
211 : : }
212 : :
213 : : /**
214 : : * ice_release_nvm - Generic request for releasing the NVM ownership
215 : : * @hw: pointer to the HW structure
216 : : *
217 : : * This function will release NVM ownership.
218 : : */
219 : 0 : void ice_release_nvm(struct ice_hw *hw)
220 : : {
221 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
222 : :
223 [ # # ]: 0 : if (hw->flash.blank_nvm_mode)
224 : : return;
225 : :
226 : 0 : ice_release_res(hw, ICE_NVM_RES_ID);
227 : : }
228 : :
229 : : /**
230 : : * ice_get_flash_bank_offset - Get offset into requested flash bank
231 : : * @hw: pointer to the HW structure
232 : : * @bank: whether to read from the active or inactive flash bank
233 : : * @module: the module to read from
234 : : *
235 : : * Based on the module, lookup the module offset from the beginning of the
236 : : * flash.
237 : : *
238 : : * Returns the flash offset. Note that a value of zero is invalid and must be
239 : : * treated as an error.
240 : : */
241 : 0 : static u32 ice_get_flash_bank_offset(struct ice_hw *hw, enum ice_bank_select bank, u16 module)
242 : : {
243 : : struct ice_bank_info *banks = &hw->flash.banks;
244 : : enum ice_flash_bank active_bank;
245 : : bool second_bank_active;
246 : : u32 offset, size;
247 : :
248 [ # # # # ]: 0 : switch (module) {
249 : 0 : case ICE_SR_1ST_NVM_BANK_PTR:
250 : 0 : offset = banks->nvm_ptr;
251 : 0 : size = banks->nvm_size;
252 : 0 : active_bank = banks->nvm_bank;
253 : 0 : break;
254 : 0 : case ICE_SR_1ST_OROM_BANK_PTR:
255 : 0 : offset = banks->orom_ptr;
256 : 0 : size = banks->orom_size;
257 : 0 : active_bank = banks->orom_bank;
258 : 0 : break;
259 : 0 : case ICE_SR_NETLIST_BANK_PTR:
260 : 0 : offset = banks->netlist_ptr;
261 : 0 : size = banks->netlist_size;
262 : 0 : active_bank = banks->netlist_bank;
263 : 0 : break;
264 : 0 : default:
265 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unexpected value for flash module: 0x%04x\n", module);
266 : : return 0;
267 : : }
268 : :
269 [ # # # ]: 0 : switch (active_bank) {
270 : : case ICE_1ST_FLASH_BANK:
271 : : second_bank_active = false;
272 : : break;
273 : 0 : case ICE_2ND_FLASH_BANK:
274 : : second_bank_active = true;
275 : 0 : break;
276 : 0 : default:
277 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unexpected value for active flash bank: %u\n",
278 : : active_bank);
279 : : return 0;
280 : : }
281 : :
282 : : /* The second flash bank is stored immediately following the first
283 : : * bank. Based on whether the 1st or 2nd bank is active, and whether
284 : : * we want the active or inactive bank, calculate the desired offset.
285 : : */
286 [ # # # ]: 0 : switch (bank) {
287 : 0 : case ICE_ACTIVE_FLASH_BANK:
288 [ # # ]: 0 : return offset + (second_bank_active ? size : 0);
289 : 0 : case ICE_INACTIVE_FLASH_BANK:
290 [ # # ]: 0 : return offset + (second_bank_active ? 0 : size);
291 : : }
292 : :
293 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unexpected value for flash bank selection: %u\n", bank);
294 : : return 0;
295 : : }
296 : :
297 : : /**
298 : : * ice_read_flash_module - Read a word from one of the main NVM modules
299 : : * @hw: pointer to the HW structure
300 : : * @bank: which bank of the module to read
301 : : * @module: the module to read
302 : : * @offset: the offset into the module in bytes
303 : : * @data: storage for the word read from the flash
304 : : * @length: bytes of data to read
305 : : *
306 : : * Read data from the specified flash module. The bank parameter indicates
307 : : * whether or not to read from the active bank or the inactive bank of that
308 : : * module.
309 : : *
310 : : * The word will be read using flat NVM access, and relies on the
311 : : * hw->flash.banks data being setup by ice_determine_active_flash_banks()
312 : : * during initialization.
313 : : */
314 : : static int
315 : 0 : ice_read_flash_module(struct ice_hw *hw, enum ice_bank_select bank, u16 module,
316 : : u32 offset, u8 *data, u32 length)
317 : : {
318 : : int status;
319 : : u32 start;
320 : :
321 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
322 : :
323 : 0 : start = ice_get_flash_bank_offset(hw, bank, module);
324 [ # # ]: 0 : if (!start) {
325 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unable to calculate flash bank offset for module 0x%04x\n",
326 : : module);
327 : 0 : return ICE_ERR_PARAM;
328 : : }
329 : :
330 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
331 [ # # ]: 0 : if (status)
332 : : return status;
333 : :
334 : 0 : status = ice_read_flat_nvm(hw, start + offset, &length, data, false);
335 : :
336 : 0 : ice_release_nvm(hw);
337 : :
338 : 0 : return status;
339 : : }
340 : :
341 : : /**
342 : : * ice_read_nvm_module - Read from the active main NVM module
343 : : * @hw: pointer to the HW structure
344 : : * @bank: whether to read from active or inactive NVM module
345 : : * @offset: offset into the NVM module to read, in words
346 : : * @data: storage for returned word value
347 : : *
348 : : * Read the specified word from the active NVM module. This includes the CSS
349 : : * header at the start of the NVM module.
350 : : */
351 : : static int
352 : : ice_read_nvm_module(struct ice_hw *hw, enum ice_bank_select bank, u32 offset, u16 *data)
353 : : {
354 : : __le16 data_local;
355 : : int status;
356 : :
357 : 0 : status = ice_read_flash_module(hw, bank, ICE_SR_1ST_NVM_BANK_PTR, offset * sizeof(u16),
358 : : (_FORCE_ u8 *)&data_local, sizeof(u16));
359 [ # # # # : 0 : if (!status)
# # # # #
# ]
360 : 0 : *data = LE16_TO_CPU(data_local);
361 : :
362 : : return status;
363 : : }
364 : :
365 : : /**
366 : : * ice_get_nvm_css_hdr_len - Read the CSS header length from the NVM CSS header
367 : : * @hw: pointer to the HW struct
368 : : * @bank: whether to read from the active or inactive flash bank
369 : : * @hdr_len: storage for header length in words
370 : : *
371 : : * Read the CSS header length from the NVM CSS header and add the Authentication
372 : : * header size, and then convert to words.
373 : : */
374 : : static int
375 : 0 : ice_get_nvm_css_hdr_len(struct ice_hw *hw, enum ice_bank_select bank,
376 : : u32 *hdr_len)
377 : : {
378 : : u16 hdr_len_l, hdr_len_h;
379 : : u32 hdr_len_dword;
380 : : int status;
381 : :
382 : : status = ice_read_nvm_module(hw, bank, ICE_NVM_CSS_HDR_LEN_L,
383 : : &hdr_len_l);
384 [ # # ]: 0 : if (status)
385 : : return status;
386 : :
387 : : status = ice_read_nvm_module(hw, bank, ICE_NVM_CSS_HDR_LEN_H,
388 : : &hdr_len_h);
389 [ # # ]: 0 : if (status)
390 : : return status;
391 : :
392 : : /* CSS header length is in DWORD, so convert to words and add
393 : : * authentication header size
394 : : */
395 : 0 : hdr_len_dword = hdr_len_h << 16 | hdr_len_l;
396 : 0 : *hdr_len = (hdr_len_dword * 2) + ICE_NVM_AUTH_HEADER_LEN;
397 : :
398 : 0 : return 0;
399 : : }
400 : :
401 : : /**
402 : : * ice_read_nvm_sr_copy - Read a word from the Shadow RAM copy in the NVM bank
403 : : * @hw: pointer to the HW structure
404 : : * @bank: whether to read from the active or inactive NVM module
405 : : * @offset: offset into the Shadow RAM copy to read, in words
406 : : * @data: storage for returned word value
407 : : *
408 : : * Read the specified word from the copy of the Shadow RAM found in the
409 : : * specified NVM module.
410 : : */
411 : : static int
412 : 0 : ice_read_nvm_sr_copy(struct ice_hw *hw, enum ice_bank_select bank, u32 offset, u16 *data)
413 : : {
414 : : u32 hdr_len;
415 : : int status;
416 : :
417 : 0 : status = ice_get_nvm_css_hdr_len(hw, bank, &hdr_len);
418 [ # # ]: 0 : if (status)
419 : : return status;
420 : :
421 : 0 : hdr_len = ROUND_UP(hdr_len, 32);
422 : :
423 : 0 : return ice_read_nvm_module(hw, bank, hdr_len + offset, data);
424 : : }
425 : :
426 : : /**
427 : : * ice_read_orom_module - Read from the active Option ROM module
428 : : * @hw: pointer to the HW structure
429 : : * @bank: whether to read from active or inactive OROM module
430 : : * @offset: offset into the OROM module to read, in words
431 : : * @data: storage for returned word value
432 : : *
433 : : * Read the specified word from the active Option ROM module of the flash.
434 : : * Note that unlike the NVM module, the CSS data is stored at the end of the
435 : : * module instead of at the beginning.
436 : : */
437 : : static int
438 : : ice_read_orom_module(struct ice_hw *hw, enum ice_bank_select bank, u32 offset, u16 *data)
439 : : {
440 : : __le16 data_local;
441 : : int status;
442 : :
443 : 0 : status = ice_read_flash_module(hw, bank, ICE_SR_1ST_OROM_BANK_PTR, offset * sizeof(u16),
444 : : (_FORCE_ u8 *)&data_local, sizeof(u16));
445 [ # # # # ]: 0 : if (!status)
446 : 0 : *data = LE16_TO_CPU(data_local);
447 : :
448 : : return status;
449 : : }
450 : :
451 : : /**
452 : : * ice_read_sr_word - Reads Shadow RAM word and acquire NVM if necessary
453 : : * @hw: pointer to the HW structure
454 : : * @offset: offset of the Shadow RAM word to read (0x000000 - 0x001FFF)
455 : : * @data: word read from the Shadow RAM
456 : : *
457 : : * Reads one 16 bit word from the Shadow RAM using the ice_read_sr_word_aq.
458 : : */
459 : 0 : int ice_read_sr_word(struct ice_hw *hw, u16 offset, u16 *data)
460 : : {
461 : : int status;
462 : :
463 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
464 [ # # ]: 0 : if (!status) {
465 : 0 : status = ice_read_sr_word_aq(hw, offset, data);
466 : 0 : ice_release_nvm(hw);
467 : : }
468 : :
469 : 0 : return status;
470 : : }
471 : :
472 : : #define check_add_overflow __builtin_add_overflow
473 : :
474 : : /**
475 : : * ice_get_pfa_module_tlv - Reads sub module TLV from NVM PFA
476 : : * @hw: pointer to hardware structure
477 : : * @module_tlv: pointer to module TLV to return
478 : : * @module_tlv_len: pointer to module TLV length to return
479 : : * @module_type: module type requested
480 : : *
481 : : * Finds the requested sub module TLV type from the Preserved Field
482 : : * Area (PFA) and returns the TLV pointer and length. The caller can
483 : : * use these to read the variable length TLV value.
484 : : */
485 : : int
486 : 0 : ice_get_pfa_module_tlv(struct ice_hw *hw, u16 *module_tlv, u16 *module_tlv_len,
487 : : u16 module_type)
488 : : {
489 : : u16 pfa_len, pfa_ptr, next_tlv, max_tlv;
490 : : int status;
491 : :
492 : 0 : status = ice_read_sr_word(hw, ICE_SR_PFA_PTR, &pfa_ptr);
493 [ # # ]: 0 : if (status) {
494 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Preserved Field Array pointer.\n");
495 : 0 : return status;
496 : : }
497 : 0 : status = ice_read_sr_word(hw, pfa_ptr, &pfa_len);
498 [ # # ]: 0 : if (status) {
499 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read PFA length.\n");
500 : 0 : return status;
501 : : }
502 : :
503 [ # # ]: 0 : if (check_add_overflow(pfa_ptr, (u16)(pfa_len - 1), &max_tlv)) {
504 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "PFA starts at offset %u. PFA length of %u caused 16-bit arithmetic overflow.\n",
505 : : pfa_ptr, pfa_len);
506 : 0 : return ICE_ERR_INVAL_SIZE;
507 : : }
508 : :
509 : : /* The Preserved Fields Area contains a sequence of TLVs which define
510 : : * its contents. The PFA length includes all of the TLVs, plus its
511 : : * initial length word itself, *and* one final word at the end of all
512 : : * of the TLVs.
513 : : *
514 : : * Starting with first TLV after PFA length, iterate through the list
515 : : * of TLVs to find the requested one.
516 : : */
517 : 0 : next_tlv = pfa_ptr + 1;
518 [ # # ]: 0 : while (next_tlv < max_tlv) {
519 : : u16 tlv_sub_module_type;
520 : : u16 tlv_len;
521 : :
522 : : /* Read TLV type */
523 : 0 : status = ice_read_sr_word(hw, (u16)next_tlv,
524 : : &tlv_sub_module_type);
525 [ # # ]: 0 : if (status) {
526 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read TLV type.\n");
527 : 0 : break;
528 : : }
529 : : /* Read TLV length */
530 : 0 : status = ice_read_sr_word(hw, (u16)(next_tlv + 1), &tlv_len);
531 [ # # ]: 0 : if (status) {
532 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read TLV length.\n");
533 : : break;
534 : : }
535 [ # # ]: 0 : if (tlv_sub_module_type == module_type) {
536 [ # # ]: 0 : if (tlv_len) {
537 : 0 : *module_tlv = (u16)next_tlv;
538 : 0 : *module_tlv_len = tlv_len;
539 : 0 : return 0;
540 : : }
541 : : return ICE_ERR_INVAL_SIZE;
542 : : }
543 : :
544 [ # # ]: 0 : if (check_add_overflow(next_tlv, (u16)2, &next_tlv) ||
545 [ # # ]: 0 : check_add_overflow(next_tlv, tlv_len, &next_tlv)) {
546 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "TLV of type %u and length 0x%04x caused 16-bit arithmetic overflow. The PFA starts at 0x%04x and has length of 0x%04x\n",
547 : : tlv_sub_module_type, tlv_len, pfa_ptr, pfa_len);
548 : 0 : return ICE_ERR_INVAL_SIZE;
549 : : }
550 : : }
551 : : /* Module does not exist */
552 : : return ICE_ERR_DOES_NOT_EXIST;
553 : : }
554 : :
555 : : /**
556 : : * ice_read_pba_string - Reads part number string from NVM
557 : : * @hw: pointer to hardware structure
558 : : * @pba_num: stores the part number string from the NVM
559 : : * @pba_num_size: part number string buffer length
560 : : *
561 : : * Reads the part number string from the NVM.
562 : : */
563 : 0 : int ice_read_pba_string(struct ice_hw *hw, u8 *pba_num, u32 pba_num_size)
564 : : {
565 : : u16 pba_tlv, pba_tlv_len;
566 : : u16 pba_word, pba_size;
567 : : int status;
568 : : u16 i;
569 : :
570 : 0 : status = ice_get_pfa_module_tlv(hw, &pba_tlv, &pba_tlv_len,
571 : : ICE_SR_PBA_BLOCK_PTR);
572 [ # # ]: 0 : if (status) {
573 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read PBA Block TLV.\n");
574 : 0 : return status;
575 : : }
576 : :
577 : : /* pba_size is the next word */
578 : 0 : status = ice_read_sr_word(hw, (pba_tlv + 2), &pba_size);
579 [ # # ]: 0 : if (status) {
580 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read PBA Section size.\n");
581 : 0 : return status;
582 : : }
583 : :
584 [ # # ]: 0 : if (pba_tlv_len < pba_size) {
585 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Invalid PBA Block TLV size.\n");
586 : 0 : return ICE_ERR_INVAL_SIZE;
587 : : }
588 : :
589 : : /* Subtract one to get PBA word count (PBA Size word is included in
590 : : * total size)
591 : : */
592 : 0 : pba_size--;
593 [ # # ]: 0 : if (pba_num_size < (((u32)pba_size * 2) + 1)) {
594 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Buffer too small for PBA data.\n");
595 : 0 : return ICE_ERR_PARAM;
596 : : }
597 : :
598 [ # # ]: 0 : for (i = 0; i < pba_size; i++) {
599 : 0 : status = ice_read_sr_word(hw, (pba_tlv + 2 + 1) + i, &pba_word);
600 [ # # ]: 0 : if (status) {
601 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read PBA Block word %d.\n", i);
602 : 0 : return status;
603 : : }
604 : :
605 : 0 : pba_num[(i * 2)] = (pba_word >> 8) & 0xFF;
606 : 0 : pba_num[(i * 2) + 1] = pba_word & 0xFF;
607 : : }
608 : 0 : pba_num[(pba_size * 2)] = '\0';
609 : :
610 : 0 : return status;
611 : : }
612 : :
613 : : /**
614 : : * ice_get_nvm_srev - Read the security revision from the NVM CSS header
615 : : * @hw: pointer to the HW struct
616 : : * @bank: whether to read from the active or inactive flash bank
617 : : * @srev: storage for security revision
618 : : *
619 : : * Read the security revision out of the CSS header of the active NVM module
620 : : * bank.
621 : : */
622 : 0 : static int ice_get_nvm_srev(struct ice_hw *hw, enum ice_bank_select bank, u32 *srev)
623 : : {
624 : : u16 srev_l, srev_h;
625 : : int status;
626 : :
627 : : status = ice_read_nvm_module(hw, bank, ICE_NVM_CSS_SREV_L, &srev_l);
628 [ # # ]: 0 : if (status)
629 : : return status;
630 : :
631 : : status = ice_read_nvm_module(hw, bank, ICE_NVM_CSS_SREV_H, &srev_h);
632 [ # # ]: 0 : if (status)
633 : : return status;
634 : :
635 : 0 : *srev = srev_h << 16 | srev_l;
636 : :
637 : 0 : return 0;
638 : : }
639 : :
640 : : /**
641 : : * ice_get_nvm_ver_info - Read NVM version information
642 : : * @hw: pointer to the HW struct
643 : : * @bank: whether to read from the active or inactive flash bank
644 : : * @nvm: pointer to NVM info structure
645 : : *
646 : : * Read the NVM EETRACK ID and map version of the main NVM image bank, filling
647 : : * in the NVM info structure.
648 : : */
649 : : static int
650 : 0 : ice_get_nvm_ver_info(struct ice_hw *hw, enum ice_bank_select bank, struct ice_nvm_info *nvm)
651 : : {
652 : : u16 eetrack_lo, eetrack_hi, ver;
653 : : int status;
654 : :
655 : 0 : status = ice_read_nvm_sr_copy(hw, bank, ICE_SR_NVM_DEV_STARTER_VER, &ver);
656 [ # # ]: 0 : if (status) {
657 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read DEV starter version.\n");
658 : 0 : return status;
659 : : }
660 : :
661 : 0 : nvm->major = (ver & ICE_NVM_VER_HI_MASK) >> ICE_NVM_VER_HI_SHIFT;
662 : 0 : nvm->minor = (ver & ICE_NVM_VER_LO_MASK) >> ICE_NVM_VER_LO_SHIFT;
663 : :
664 : 0 : status = ice_read_nvm_sr_copy(hw, bank, ICE_SR_NVM_EETRACK_LO, &eetrack_lo);
665 [ # # ]: 0 : if (status) {
666 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read EETRACK lo.\n");
667 : 0 : return status;
668 : : }
669 : 0 : status = ice_read_nvm_sr_copy(hw, bank, ICE_SR_NVM_EETRACK_HI, &eetrack_hi);
670 [ # # ]: 0 : if (status) {
671 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read EETRACK hi.\n");
672 : 0 : return status;
673 : : }
674 : :
675 : 0 : nvm->eetrack = (eetrack_hi << 16) | eetrack_lo;
676 : :
677 : 0 : status = ice_get_nvm_srev(hw, bank, &nvm->srev);
678 [ # # ]: 0 : if (status)
679 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read NVM security revision.\n");
680 : :
681 : : return 0;
682 : : }
683 : :
684 : : /**
685 : : * ice_get_inactive_nvm_ver - Read Option ROM version from the inactive bank
686 : : * @hw: pointer to the HW structure
687 : : * @nvm: storage for Option ROM version information
688 : : *
689 : : * Reads the NVM EETRACK ID, Map version, and security revision of the
690 : : * inactive NVM bank. Used to access version data for a pending update that
691 : : * has not yet been activated.
692 : : */
693 : 0 : int ice_get_inactive_nvm_ver(struct ice_hw *hw, struct ice_nvm_info *nvm)
694 : : {
695 : 0 : return ice_get_nvm_ver_info(hw, ICE_INACTIVE_FLASH_BANK, nvm);
696 : : }
697 : :
698 : : /**
699 : : * ice_get_orom_srev - Read the security revision from the OROM CSS header
700 : : * @hw: pointer to the HW struct
701 : : * @bank: whether to read from active or inactive flash module
702 : : * @srev: storage for security revision
703 : : *
704 : : * Read the security revision out of the CSS header of the active OROM module
705 : : * bank.
706 : : */
707 : 0 : static int ice_get_orom_srev(struct ice_hw *hw, enum ice_bank_select bank, u32 *srev)
708 : : {
709 : 0 : u32 orom_size_word = hw->flash.banks.orom_size / 2;
710 : : u16 srev_l, srev_h;
711 : : u32 css_start;
712 : : u32 hdr_len;
713 : : int status;
714 : :
715 : 0 : status = ice_get_nvm_css_hdr_len(hw, bank, &hdr_len);
716 [ # # ]: 0 : if (status)
717 : : return status;
718 : :
719 [ # # ]: 0 : if (orom_size_word < hdr_len) {
720 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unexpected Option ROM Size of %u\n",
721 : : hw->flash.banks.orom_size);
722 : 0 : return ICE_ERR_CFG;
723 : : }
724 : :
725 : : /* calculate how far into the Option ROM the CSS header starts. Note
726 : : * that ice_read_orom_module takes a word offset
727 : : */
728 : 0 : css_start = orom_size_word - hdr_len;
729 : 0 : status = ice_read_orom_module(hw, bank, css_start + ICE_NVM_CSS_SREV_L, &srev_l);
730 [ # # ]: 0 : if (status)
731 : : return status;
732 : :
733 : 0 : status = ice_read_orom_module(hw, bank, css_start + ICE_NVM_CSS_SREV_H, &srev_h);
734 [ # # ]: 0 : if (status)
735 : : return status;
736 : :
737 : 0 : *srev = srev_h << 16 | srev_l;
738 : :
739 : 0 : return 0;
740 : : }
741 : :
742 : : /**
743 : : * ice_get_orom_civd_data - Get the combo version information from Option ROM
744 : : * @hw: pointer to the HW struct
745 : : * @bank: whether to read from the active or inactive flash module
746 : : * @civd: storage for the Option ROM CIVD data.
747 : : *
748 : : * Searches through the Option ROM flash contents to locate the CIVD data for
749 : : * the image.
750 : : */
751 : : static int
752 : 0 : ice_get_orom_civd_data(struct ice_hw *hw, enum ice_bank_select bank,
753 : : struct ice_orom_civd_info *civd)
754 : : {
755 : : struct ice_orom_civd_info civd_data_section;
756 : : int status;
757 : : u32 offset;
758 : : u32 tmp;
759 : :
760 : : /* The CIVD section is located in the Option ROM aligned to 512 bytes.
761 : : * The first 4 bytes must contain the ASCII characters "$CIV".
762 : : * A simple modulo 256 sum of all of the bytes of the structure must
763 : : * equal 0.
764 : : *
765 : : * The exact location is unknown and varies between images but is
766 : : * usually somewhere in the middle of the bank. We need to scan the
767 : : * Option ROM bank to locate it.
768 : : *
769 : : */
770 : :
771 : : /* Scan the memory buffer to locate the CIVD data section */
772 [ # # ]: 0 : for (offset = 0; (offset + 512) <= hw->flash.banks.orom_size; offset += 512) {
773 : : u8 sum = 0, i;
774 : :
775 : 0 : status = ice_read_flash_module(hw, bank, ICE_SR_1ST_OROM_BANK_PTR,
776 : : offset, (u8 *)&tmp, sizeof(tmp));
777 [ # # ]: 0 : if (status) {
778 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unable to read Option ROM data\n");
779 : 0 : return status;
780 : : }
781 : :
782 : : /* Skip forward until we find a matching signature */
783 [ # # ]: 0 : if (memcmp("$CIV", &tmp, sizeof(tmp)) != 0)
784 : : continue;
785 : :
786 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Found CIVD section at offset %u\n",
787 : : offset);
788 : :
789 : 0 : status = ice_read_flash_module(hw, bank, ICE_SR_1ST_OROM_BANK_PTR,
790 : : offset, (u8 *)&civd_data_section,
791 : : sizeof(civd_data_section));
792 [ # # ]: 0 : if (status) {
793 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unable to read CIVD data\n");
794 : 0 : goto exit_error;
795 : : }
796 : :
797 : : /* Verify that the simple checksum is zero */
798 [ # # ]: 0 : for (i = 0; i < sizeof(civd_data_section); i++)
799 : 0 : sum += ((u8 *)&civd_data_section)[i];
800 : :
801 [ # # ]: 0 : if (sum) {
802 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Found CIVD data with invalid checksum of %u\n",
803 : : sum);
804 : : status = ICE_ERR_NVM;
805 : 0 : goto exit_error;
806 : : }
807 : :
808 : 0 : *civd = civd_data_section;
809 : :
810 : 0 : return 0;
811 : : }
812 : :
813 : : status = ICE_ERR_NVM;
814 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Unable to locate CIVD data within the Option ROM\n");
815 : :
816 : 0 : exit_error:
817 : : return status;
818 : : }
819 : :
820 : : /**
821 : : * ice_get_orom_ver_info - Read Option ROM version information
822 : : * @hw: pointer to the HW struct
823 : : * @bank: whether to read from the active or inactive flash module
824 : : * @orom: pointer to Option ROM info structure
825 : : *
826 : : * Read Option ROM version and security revision from the Option ROM flash
827 : : * section.
828 : : */
829 : : static int
830 : 0 : ice_get_orom_ver_info(struct ice_hw *hw, enum ice_bank_select bank, struct ice_orom_info *orom)
831 : : {
832 : : struct ice_orom_civd_info civd;
833 : : u32 combo_ver;
834 : : int status;
835 : :
836 : 0 : status = ice_get_orom_civd_data(hw, bank, &civd);
837 [ # # ]: 0 : if (status) {
838 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to locate valid Option ROM CIVD data\n");
839 : 0 : return status;
840 : : }
841 : :
842 : 0 : combo_ver = LE32_TO_CPU(civd.combo_ver);
843 : :
844 : 0 : orom->major = (u8)((combo_ver & ICE_OROM_VER_MASK) >> ICE_OROM_VER_SHIFT);
845 : 0 : orom->patch = (u8)(combo_ver & ICE_OROM_VER_PATCH_MASK);
846 : 0 : orom->build = (u16)((combo_ver & ICE_OROM_VER_BUILD_MASK) >> ICE_OROM_VER_BUILD_SHIFT);
847 : :
848 : 0 : status = ice_get_orom_srev(hw, bank, &orom->srev);
849 [ # # ]: 0 : if (status) {
850 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read Option ROM security revision.\n");
851 : 0 : return status;
852 : : }
853 : :
854 : : return 0;
855 : : }
856 : :
857 : : /**
858 : : * ice_get_inactive_orom_ver - Read Option ROM version from the inactive bank
859 : : * @hw: pointer to the HW structure
860 : : * @orom: storage for Option ROM version information
861 : : *
862 : : * Reads the Option ROM version and security revision data for the inactive
863 : : * section of flash. Used to access version data for a pending update that has
864 : : * not yet been activated.
865 : : */
866 : 0 : int ice_get_inactive_orom_ver(struct ice_hw *hw, struct ice_orom_info *orom)
867 : : {
868 : 0 : return ice_get_orom_ver_info(hw, ICE_INACTIVE_FLASH_BANK, orom);
869 : : }
870 : :
871 : : /**
872 : : * ice_discover_flash_size - Discover the available flash size
873 : : * @hw: pointer to the HW struct
874 : : *
875 : : * The device flash could be up to 16MB in size. However, it is possible that
876 : : * the actual size is smaller. Use bisection to determine the accessible size
877 : : * of flash memory.
878 : : */
879 : 0 : static int ice_discover_flash_size(struct ice_hw *hw)
880 : : {
881 : : u32 min_size = 0, max_size = ICE_AQC_NVM_MAX_OFFSET + 1;
882 : : int status;
883 : :
884 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
885 : :
886 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
887 [ # # ]: 0 : if (status)
888 : : return status;
889 : :
890 [ # # ]: 0 : while ((max_size - min_size) > 1) {
891 : 0 : u32 offset = (max_size + min_size) / 2;
892 : 0 : u32 len = 1;
893 : : u8 data;
894 : :
895 : 0 : status = ice_read_flat_nvm(hw, offset, &len, &data, false);
896 [ # # ]: 0 : if (status == ICE_ERR_AQ_ERROR &&
897 [ # # ]: 0 : hw->adminq.sq_last_status == ICE_AQ_RC_EINVAL) {
898 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "%s: New upper bound of %u bytes\n",
899 : : __func__, offset);
900 : : status = 0;
901 : : max_size = offset;
902 [ # # ]: 0 : } else if (!status) {
903 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "%s: New lower bound of %u bytes\n",
904 : : __func__, offset);
905 : : min_size = offset;
906 : : } else {
907 : : /* an unexpected error occurred */
908 : 0 : goto err_read_flat_nvm;
909 : : }
910 : : }
911 : :
912 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Predicted flash size is %u bytes\n", max_size);
913 : :
914 : 0 : hw->flash.flash_size = max_size;
915 : :
916 : 0 : err_read_flat_nvm:
917 : 0 : ice_release_nvm(hw);
918 : :
919 : 0 : return status;
920 : : }
921 : :
922 : : /**
923 : : * ice_read_sr_pointer - Read the value of a Shadow RAM pointer word
924 : : * @hw: pointer to the HW structure
925 : : * @offset: the word offset of the Shadow RAM word to read
926 : : * @pointer: pointer value read from Shadow RAM
927 : : *
928 : : * Read the given Shadow RAM word, and convert it to a pointer value specified
929 : : * in bytes. This function assumes the specified offset is a valid pointer
930 : : * word.
931 : : *
932 : : * Each pointer word specifies whether it is stored in word size or 4KB
933 : : * sector size by using the highest bit. The reported pointer value will be in
934 : : * bytes, intended for flat NVM reads.
935 : : */
936 : 0 : static int ice_read_sr_pointer(struct ice_hw *hw, u16 offset, u32 *pointer)
937 : : {
938 : : int status;
939 : : u16 value;
940 : :
941 : 0 : status = ice_read_sr_word(hw, offset, &value);
942 [ # # ]: 0 : if (status)
943 : : return status;
944 : :
945 : : /* Determine if the pointer is in 4KB or word units */
946 [ # # ]: 0 : if (value & ICE_SR_NVM_PTR_4KB_UNITS)
947 : 0 : *pointer = (value & ~ICE_SR_NVM_PTR_4KB_UNITS) * 4 * 1024;
948 : : else
949 : 0 : *pointer = value * 2;
950 : :
951 : : return 0;
952 : : }
953 : :
954 : : /**
955 : : * ice_read_sr_area_size - Read an area size from a Shadow RAM word
956 : : * @hw: pointer to the HW structure
957 : : * @offset: the word offset of the Shadow RAM to read
958 : : * @size: size value read from the Shadow RAM
959 : : *
960 : : * Read the given Shadow RAM word, and convert it to an area size value
961 : : * specified in bytes. This function assumes the specified offset is a valid
962 : : * area size word.
963 : : *
964 : : * Each area size word is specified in 4KB sector units. This function reports
965 : : * the size in bytes, intended for flat NVM reads.
966 : : */
967 : : static int ice_read_sr_area_size(struct ice_hw *hw, u16 offset, u32 *size)
968 : : {
969 : : int status;
970 : : u16 value;
971 : :
972 : 0 : status = ice_read_sr_word(hw, offset, &value);
973 [ # # # # : 0 : if (status)
# # ]
974 : : return status;
975 : :
976 : : /* Area sizes are always specified in 4KB units */
977 : 0 : *size = value * 4 * 1024;
978 : :
979 : : return 0;
980 : : }
981 : :
982 : : /**
983 : : * ice_determine_active_flash_banks - Discover active bank for each module
984 : : * @hw: pointer to the HW struct
985 : : *
986 : : * Read the Shadow RAM control word and determine which banks are active for
987 : : * the NVM, OROM, and Netlist modules. Also read and calculate the associated
988 : : * pointer and size. These values are then cached into the ice_flash_info
989 : : * structure for later use in order to calculate the correct offset to read
990 : : * from the active module.
991 : : */
992 : 0 : static int ice_determine_active_flash_banks(struct ice_hw *hw)
993 : : {
994 : : struct ice_bank_info *banks = &hw->flash.banks;
995 : : u16 ctrl_word;
996 : : int status;
997 : :
998 : 0 : status = ice_read_sr_word(hw, ICE_SR_NVM_CTRL_WORD, &ctrl_word);
999 [ # # ]: 0 : if (status) {
1000 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read the Shadow RAM control word\n");
1001 : 0 : return status;
1002 : : }
1003 : :
1004 : : /* Check that the control word indicates validity */
1005 [ # # ]: 0 : if ((ctrl_word & ICE_SR_CTRL_WORD_1_M) >> ICE_SR_CTRL_WORD_1_S != ICE_SR_CTRL_WORD_VALID) {
1006 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Shadow RAM control word is invalid\n");
1007 : 0 : return ICE_ERR_CFG;
1008 : : }
1009 : :
1010 [ # # ]: 0 : if (!(ctrl_word & ICE_SR_CTRL_WORD_NVM_BANK))
1011 : 0 : banks->nvm_bank = ICE_1ST_FLASH_BANK;
1012 : : else
1013 : 0 : banks->nvm_bank = ICE_2ND_FLASH_BANK;
1014 : :
1015 [ # # ]: 0 : if (!(ctrl_word & ICE_SR_CTRL_WORD_OROM_BANK))
1016 : 0 : banks->orom_bank = ICE_1ST_FLASH_BANK;
1017 : : else
1018 : 0 : banks->orom_bank = ICE_2ND_FLASH_BANK;
1019 : :
1020 [ # # ]: 0 : if (!(ctrl_word & ICE_SR_CTRL_WORD_NETLIST_BANK))
1021 : 0 : banks->netlist_bank = ICE_1ST_FLASH_BANK;
1022 : : else
1023 : 0 : banks->netlist_bank = ICE_2ND_FLASH_BANK;
1024 : :
1025 : 0 : status = ice_read_sr_pointer(hw, ICE_SR_1ST_NVM_BANK_PTR, &banks->nvm_ptr);
1026 [ # # ]: 0 : if (status) {
1027 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read NVM bank pointer\n");
1028 : 0 : return status;
1029 : : }
1030 : :
1031 : : status = ice_read_sr_area_size(hw, ICE_SR_NVM_BANK_SIZE, &banks->nvm_size);
1032 : : if (status) {
1033 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read NVM bank area size\n");
1034 : 0 : return status;
1035 : : }
1036 : :
1037 : 0 : status = ice_read_sr_pointer(hw, ICE_SR_1ST_OROM_BANK_PTR, &banks->orom_ptr);
1038 [ # # ]: 0 : if (status) {
1039 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read OROM bank pointer\n");
1040 : 0 : return status;
1041 : : }
1042 : :
1043 : : status = ice_read_sr_area_size(hw, ICE_SR_OROM_BANK_SIZE, &banks->orom_size);
1044 : : if (status) {
1045 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read OROM bank area size\n");
1046 : 0 : return status;
1047 : : }
1048 : :
1049 : 0 : status = ice_read_sr_pointer(hw, ICE_SR_NETLIST_BANK_PTR, &banks->netlist_ptr);
1050 [ # # ]: 0 : if (status) {
1051 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read Netlist bank pointer\n");
1052 : 0 : return status;
1053 : : }
1054 : :
1055 : : status = ice_read_sr_area_size(hw, ICE_SR_NETLIST_BANK_SIZE, &banks->netlist_size);
1056 : : if (status) {
1057 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to read Netlist bank area size\n");
1058 : 0 : return status;
1059 : : }
1060 : :
1061 : : return 0;
1062 : : }
1063 : :
1064 : : /**
1065 : : * ice_init_nvm - initializes NVM setting
1066 : : * @hw: pointer to the HW struct
1067 : : *
1068 : : * This function reads and populates NVM settings such as Shadow RAM size,
1069 : : * max_timeout, and blank_nvm_mode
1070 : : */
1071 : 0 : int ice_init_nvm(struct ice_hw *hw)
1072 : : {
1073 : : struct ice_flash_info *flash = &hw->flash;
1074 : : u32 fla, gens_stat;
1075 : : u8 sr_size;
1076 : : int status;
1077 : :
1078 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
1079 : :
1080 : : /* The SR size is stored regardless of the NVM programming mode
1081 : : * as the blank mode may be used in the factory line.
1082 : : */
1083 : 0 : gens_stat = rd32(hw, GLNVM_GENS);
1084 : 0 : sr_size = (gens_stat & GLNVM_GENS_SR_SIZE_M) >> GLNVM_GENS_SR_SIZE_S;
1085 : :
1086 : : /* Switching to words (sr_size contains power of 2) */
1087 : 0 : flash->sr_words = BIT(sr_size) * ICE_SR_WORDS_IN_1KB;
1088 : :
1089 : : /* Check if we are in the normal or blank NVM programming mode */
1090 : 0 : fla = rd32(hw, GLNVM_FLA);
1091 [ # # ]: 0 : if (fla & GLNVM_FLA_LOCKED_M) { /* Normal programming mode */
1092 : 0 : flash->blank_nvm_mode = false;
1093 : : } else {
1094 : : /* Blank programming mode */
1095 : 0 : flash->blank_nvm_mode = true;
1096 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "NVM init error: unsupported blank mode.\n");
1097 : 0 : return ICE_ERR_NVM_BLANK_MODE;
1098 : : }
1099 : :
1100 : 0 : status = ice_discover_flash_size(hw);
1101 [ # # ]: 0 : if (status) {
1102 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "NVM init error: failed to discover flash size.\n");
1103 : 0 : return status;
1104 : : }
1105 : :
1106 : 0 : status = ice_determine_active_flash_banks(hw);
1107 [ # # ]: 0 : if (status) {
1108 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "Failed to determine active flash banks.\n");
1109 : 0 : return status;
1110 : : }
1111 : :
1112 : 0 : status = ice_get_nvm_ver_info(hw, ICE_ACTIVE_FLASH_BANK, &flash->nvm);
1113 [ # # ]: 0 : if (status) {
1114 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read NVM info.\n");
1115 : 0 : return status;
1116 : : }
1117 : :
1118 : 0 : status = ice_get_orom_ver_info(hw, ICE_ACTIVE_FLASH_BANK, &flash->orom);
1119 [ # # ]: 0 : if (status)
1120 [ # # ]: 0 : ice_debug(hw, ICE_DBG_INIT, "Failed to read Option ROM info.\n");
1121 : :
1122 : : return 0;
1123 : : }
1124 : :
1125 : : /**
1126 : : * ice_read_sr_buf - Reads Shadow RAM buf and acquire lock if necessary
1127 : : * @hw: pointer to the HW structure
1128 : : * @offset: offset of the Shadow RAM word to read (0x000000 - 0x001FFF)
1129 : : * @words: (in) number of words to read; (out) number of words actually read
1130 : : * @data: words read from the Shadow RAM
1131 : : *
1132 : : * Reads 16 bit words (data buf) from the SR using the ice_read_nvm_buf_aq
1133 : : * method. The buf read is preceded by the NVM ownership take
1134 : : * and followed by the release.
1135 : : */
1136 : : int
1137 : 0 : ice_read_sr_buf(struct ice_hw *hw, u16 offset, u16 *words, u16 *data)
1138 : : {
1139 : : int status;
1140 : :
1141 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
1142 [ # # ]: 0 : if (!status) {
1143 : 0 : status = ice_read_sr_buf_aq(hw, offset, words, data);
1144 : 0 : ice_release_nvm(hw);
1145 : : }
1146 : :
1147 : 0 : return status;
1148 : : }
1149 : :
1150 : : /**
1151 : : * ice_nvm_validate_checksum
1152 : : * @hw: pointer to the HW struct
1153 : : *
1154 : : * Verify NVM PFA checksum validity (0x0706)
1155 : : */
1156 : 0 : int ice_nvm_validate_checksum(struct ice_hw *hw)
1157 : : {
1158 : : struct ice_aqc_nvm_checksum *cmd;
1159 : : struct ice_aq_desc desc;
1160 : : int status;
1161 : :
1162 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
1163 [ # # ]: 0 : if (status)
1164 : : return status;
1165 : :
1166 : : cmd = &desc.params.nvm_checksum;
1167 : :
1168 : 0 : ice_fill_dflt_direct_cmd_desc(&desc, ice_aqc_opc_nvm_checksum);
1169 : 0 : cmd->flags = ICE_AQC_NVM_CHECKSUM_VERIFY;
1170 : :
1171 : 0 : status = ice_aq_send_cmd(hw, &desc, NULL, 0, NULL);
1172 : 0 : ice_release_nvm(hw);
1173 : :
1174 [ # # ]: 0 : if (!status)
1175 [ # # ]: 0 : if (LE16_TO_CPU(cmd->checksum) != ICE_AQC_NVM_CHECKSUM_CORRECT)
1176 : : status = ICE_ERR_NVM_CHECKSUM;
1177 : :
1178 : : return status;
1179 : : }
1180 : :
1181 : : /**
1182 : : * ice_nvm_recalculate_checksum
1183 : : * @hw: pointer to the HW struct
1184 : : *
1185 : : * Recalculate NVM PFA checksum (0x0706)
1186 : : */
1187 : 0 : int ice_nvm_recalculate_checksum(struct ice_hw *hw)
1188 : : {
1189 : : struct ice_aqc_nvm_checksum *cmd;
1190 : : struct ice_aq_desc desc;
1191 : : int status;
1192 : :
1193 : 0 : status = ice_acquire_nvm(hw, ICE_RES_READ);
1194 [ # # ]: 0 : if (status)
1195 : : return status;
1196 : :
1197 : : cmd = &desc.params.nvm_checksum;
1198 : :
1199 : 0 : ice_fill_dflt_direct_cmd_desc(&desc, ice_aqc_opc_nvm_checksum);
1200 : 0 : cmd->flags = ICE_AQC_NVM_CHECKSUM_RECALC;
1201 : :
1202 : 0 : status = ice_aq_send_cmd(hw, &desc, NULL, 0, NULL);
1203 : :
1204 : 0 : ice_release_nvm(hw);
1205 : :
1206 : 0 : return status;
1207 : : }
1208 : :
1209 : : /**
1210 : : * ice_nvm_access_get_features - Return the NVM access features structure
1211 : : * @cmd: NVM access command to process
1212 : : * @data: storage for the driver NVM features
1213 : : *
1214 : : * Fill in the data section of the NVM access request with a copy of the NVM
1215 : : * features structure.
1216 : : */
1217 : : int
1218 : 0 : ice_nvm_access_get_features(struct ice_nvm_access_cmd *cmd,
1219 : : union ice_nvm_access_data *data)
1220 : : {
1221 : : /* The provided data_size must be at least as large as our NVM
1222 : : * features structure. A larger size should not be treated as an
1223 : : * error, to allow future extensions to the features structure to
1224 : : * work on older drivers.
1225 : : */
1226 [ # # ]: 0 : if (cmd->data_size < sizeof(struct ice_nvm_features))
1227 : : return ICE_ERR_NO_MEMORY;
1228 : :
1229 : : /* Initialize the data buffer to zeros */
1230 : 0 : ice_memset(data, 0, cmd->data_size, ICE_NONDMA_MEM);
1231 : :
1232 : : /* Fill in the features data */
1233 : 0 : data->drv_features.major = ICE_NVM_ACCESS_MAJOR_VER;
1234 : 0 : data->drv_features.minor = ICE_NVM_ACCESS_MINOR_VER;
1235 : 0 : data->drv_features.size = sizeof(struct ice_nvm_features);
1236 : 0 : data->drv_features.features[0] = ICE_NVM_FEATURES_0_REG_ACCESS;
1237 : :
1238 : 0 : return 0;
1239 : : }
1240 : :
1241 : : /**
1242 : : * ice_nvm_access_get_module - Helper function to read module value
1243 : : * @cmd: NVM access command structure
1244 : : *
1245 : : * Reads the module value out of the NVM access config field.
1246 : : */
1247 : 0 : u32 ice_nvm_access_get_module(struct ice_nvm_access_cmd *cmd)
1248 : : {
1249 : 0 : return ((cmd->config & ICE_NVM_CFG_MODULE_M) >> ICE_NVM_CFG_MODULE_S);
1250 : : }
1251 : :
1252 : : /**
1253 : : * ice_nvm_access_get_flags - Helper function to read flags value
1254 : : * @cmd: NVM access command structure
1255 : : *
1256 : : * Reads the flags value out of the NVM access config field.
1257 : : */
1258 : 0 : u32 ice_nvm_access_get_flags(struct ice_nvm_access_cmd *cmd)
1259 : : {
1260 : 0 : return ((cmd->config & ICE_NVM_CFG_FLAGS_M) >> ICE_NVM_CFG_FLAGS_S);
1261 : : }
1262 : :
1263 : : /**
1264 : : * ice_nvm_access_get_adapter - Helper function to read adapter info
1265 : : * @cmd: NVM access command structure
1266 : : *
1267 : : * Read the adapter info value out of the NVM access config field.
1268 : : */
1269 : 0 : u32 ice_nvm_access_get_adapter(struct ice_nvm_access_cmd *cmd)
1270 : : {
1271 : 0 : return ((cmd->config & ICE_NVM_CFG_ADAPTER_INFO_M) >>
1272 : : ICE_NVM_CFG_ADAPTER_INFO_S);
1273 : : }
1274 : :
1275 : : /**
1276 : : * ice_validate_nvm_rw_reg - Check than an NVM access request is valid
1277 : : * @cmd: NVM access command structure
1278 : : *
1279 : : * Validates that an NVM access structure is request to read or write a valid
1280 : : * register offset. First validates that the module and flags are correct, and
1281 : : * then ensures that the register offset is one of the accepted registers.
1282 : : */
1283 : : static int
1284 : 0 : ice_validate_nvm_rw_reg(struct ice_nvm_access_cmd *cmd)
1285 : : {
1286 : : u32 module, flags, offset;
1287 : : u16 i;
1288 : :
1289 : 0 : module = ice_nvm_access_get_module(cmd);
1290 : 0 : flags = ice_nvm_access_get_flags(cmd);
1291 : 0 : offset = cmd->offset;
1292 : :
1293 : : /* Make sure the module and flags indicate a read/write request */
1294 : 0 : if (module != ICE_NVM_REG_RW_MODULE ||
1295 [ # # ]: 0 : flags != ICE_NVM_REG_RW_FLAGS ||
1296 [ # # ]: 0 : cmd->data_size != FIELD_SIZEOF(union ice_nvm_access_data, regval))
1297 : : return ICE_ERR_PARAM;
1298 : :
1299 [ # # ]: 0 : switch (offset) {
1300 : : case GL_HICR:
1301 : : case GL_HICR_EN: /* Note, this register is read only */
1302 : : case GL_FWSTS:
1303 : : case GL_MNG_FWSM:
1304 : : case GLGEN_CSR_DEBUG_C:
1305 : : case GLGEN_RSTAT:
1306 : : case GLPCI_LBARCTRL:
1307 : : case GL_MNG_DEF_DEVID:
1308 : : case GLNVM_GENS:
1309 : : case GLNVM_FLA:
1310 : : case PF_FUNC_RID:
1311 : : return 0;
1312 : : default:
1313 : : break;
1314 : : }
1315 : :
1316 [ # # ]: 0 : for (i = 0; i <= GL_HIDA_MAX_INDEX; i++)
1317 [ # # ]: 0 : if (offset == (u32)GL_HIDA(i))
1318 : : return 0;
1319 : :
1320 [ # # ]: 0 : for (i = 0; i <= GL_HIBA_MAX_INDEX; i++)
1321 [ # # ]: 0 : if (offset == (u32)GL_HIBA(i))
1322 : : return 0;
1323 : :
1324 : : /* All other register offsets are not valid */
1325 : : return ICE_ERR_OUT_OF_RANGE;
1326 : : }
1327 : :
1328 : : /**
1329 : : * ice_nvm_access_read - Handle an NVM read request
1330 : : * @hw: pointer to the HW struct
1331 : : * @cmd: NVM access command to process
1332 : : * @data: storage for the register value read
1333 : : *
1334 : : * Process an NVM access request to read a register.
1335 : : */
1336 : : int
1337 : 0 : ice_nvm_access_read(struct ice_hw *hw, struct ice_nvm_access_cmd *cmd,
1338 : : union ice_nvm_access_data *data)
1339 : : {
1340 : : int status;
1341 : :
1342 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
1343 : :
1344 : : /* Always initialize the output data, even on failure */
1345 : 0 : ice_memset(data, 0, cmd->data_size, ICE_NONDMA_MEM);
1346 : :
1347 : : /* Make sure this is a valid read/write access request */
1348 : 0 : status = ice_validate_nvm_rw_reg(cmd);
1349 [ # # ]: 0 : if (status)
1350 : : return status;
1351 : :
1352 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "NVM access: reading register %08x\n",
1353 : : cmd->offset);
1354 : :
1355 : : /* Read the register and store the contents in the data field */
1356 : 0 : data->regval = rd32(hw, cmd->offset);
1357 : :
1358 : 0 : return 0;
1359 : : }
1360 : :
1361 : : /**
1362 : : * ice_nvm_access_write - Handle an NVM write request
1363 : : * @hw: pointer to the HW struct
1364 : : * @cmd: NVM access command to process
1365 : : * @data: NVM access data to write
1366 : : *
1367 : : * Process an NVM access request to write a register.
1368 : : */
1369 : : int
1370 : 0 : ice_nvm_access_write(struct ice_hw *hw, struct ice_nvm_access_cmd *cmd,
1371 : : union ice_nvm_access_data *data)
1372 : : {
1373 : : int status;
1374 : :
1375 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
1376 : :
1377 : : /* Make sure this is a valid read/write access request */
1378 : 0 : status = ice_validate_nvm_rw_reg(cmd);
1379 [ # # ]: 0 : if (status)
1380 : : return status;
1381 : :
1382 : : /* Reject requests to write to read-only registers */
1383 [ # # ]: 0 : if (hw->mac_type == ICE_MAC_E830) {
1384 [ # # ]: 0 : if (cmd->offset == E830_GL_HICR_EN)
1385 : : return ICE_ERR_OUT_OF_RANGE;
1386 : : } else {
1387 [ # # ]: 0 : if (cmd->offset == GL_HICR_EN)
1388 : : return ICE_ERR_OUT_OF_RANGE;
1389 : : }
1390 : :
1391 [ # # ]: 0 : if (cmd->offset == GLGEN_RSTAT)
1392 : : return ICE_ERR_OUT_OF_RANGE;
1393 : :
1394 [ # # ]: 0 : ice_debug(hw, ICE_DBG_NVM, "NVM access: writing register %08x with value %08x\n",
1395 : : cmd->offset, data->regval);
1396 : :
1397 : : /* Write the data field to the specified register */
1398 : 0 : wr32(hw, cmd->offset, data->regval);
1399 : :
1400 : 0 : return 0;
1401 : : }
1402 : :
1403 : : /**
1404 : : * ice_handle_nvm_access - Handle an NVM access request
1405 : : * @hw: pointer to the HW struct
1406 : : * @cmd: NVM access command info
1407 : : * @data: pointer to read or return data
1408 : : *
1409 : : * Process an NVM access request. Read the command structure information and
1410 : : * determine if it is valid. If not, report an error indicating the command
1411 : : * was invalid.
1412 : : *
1413 : : * For valid commands, perform the necessary function, copying the data into
1414 : : * the provided data buffer.
1415 : : */
1416 : : int
1417 : 0 : ice_handle_nvm_access(struct ice_hw *hw, struct ice_nvm_access_cmd *cmd,
1418 : : union ice_nvm_access_data *data)
1419 : : {
1420 : : u32 module, flags, adapter_info;
1421 : :
1422 [ # # ]: 0 : ice_debug(hw, ICE_DBG_TRACE, "%s\n", __func__);
1423 : :
1424 : : /* Extended flags are currently reserved and must be zero */
1425 [ # # ]: 0 : if ((cmd->config & ICE_NVM_CFG_EXT_FLAGS_M) != 0)
1426 : : return ICE_ERR_PARAM;
1427 : :
1428 : : /* Adapter info must match the HW device ID */
1429 : 0 : adapter_info = ice_nvm_access_get_adapter(cmd);
1430 [ # # ]: 0 : if (adapter_info != hw->device_id)
1431 : : return ICE_ERR_PARAM;
1432 : :
1433 [ # # # ]: 0 : switch (cmd->command) {
1434 : 0 : case ICE_NVM_CMD_READ:
1435 : 0 : module = ice_nvm_access_get_module(cmd);
1436 : 0 : flags = ice_nvm_access_get_flags(cmd);
1437 : :
1438 : : /* Getting the driver's NVM features structure shares the same
1439 : : * command type as reading a register. Read the config field
1440 : : * to determine if this is a request to get features.
1441 : : */
1442 : 0 : if (module == ICE_NVM_GET_FEATURES_MODULE &&
1443 [ # # ]: 0 : flags == ICE_NVM_GET_FEATURES_FLAGS &&
1444 [ # # ]: 0 : cmd->offset == 0)
1445 : 0 : return ice_nvm_access_get_features(cmd, data);
1446 : : else
1447 : 0 : return ice_nvm_access_read(hw, cmd, data);
1448 : 0 : case ICE_NVM_CMD_WRITE:
1449 : 0 : return ice_nvm_access_write(hw, cmd, data);
1450 : : default:
1451 : : return ICE_ERR_PARAM;
1452 : : }
1453 : : }
1454 : :
1455 : : /**
1456 : : * ice_nvm_sanitize_operate - Clear the user data
1457 : : * @hw: pointer to the HW struct
1458 : : *
1459 : : * Clear user data from NVM using AQ command (0x070C).
1460 : : *
1461 : : * Return: the exit code of the operation.
1462 : : */
1463 : 0 : s32 ice_nvm_sanitize_operate(struct ice_hw *hw)
1464 : : {
1465 : : s32 status;
1466 : : u8 values;
1467 : :
1468 : : u8 cmd_flags = ICE_AQ_NVM_SANITIZE_REQ_OPERATE |
1469 : : ICE_AQ_NVM_SANITIZE_OPERATE_SUBJECT_CLEAR;
1470 : :
1471 : 0 : status = ice_nvm_sanitize(hw, cmd_flags, &values);
1472 [ # # ]: 0 : if (status)
1473 : : return status;
1474 [ # # ]: 0 : if ((!(values & ICE_AQ_NVM_SANITIZE_OPERATE_HOST_CLEAN_DONE) &&
1475 [ # # ]: 0 : !(values & ICE_AQ_NVM_SANITIZE_OPERATE_BMC_CLEAN_DONE)) ||
1476 : : ((values & ICE_AQ_NVM_SANITIZE_OPERATE_HOST_CLEAN_DONE) &&
1477 [ # # ]: 0 : !(values & ICE_AQ_NVM_SANITIZE_OPERATE_HOST_CLEAN_SUCCESS)) ||
1478 : : ((values & ICE_AQ_NVM_SANITIZE_OPERATE_BMC_CLEAN_DONE) &&
1479 : : !(values & ICE_AQ_NVM_SANITIZE_OPERATE_BMC_CLEAN_SUCCESS)))
1480 : 0 : return ICE_ERR_AQ_ERROR;
1481 : :
1482 : : return ICE_SUCCESS;
1483 : : }
1484 : :
1485 : : /**
1486 : : * ice_nvm_sanitize - Sanitize NVM
1487 : : * @hw: pointer to the HW struct
1488 : : * @cmd_flags: flag to the ACI command
1489 : : * @values: values returned from the command
1490 : : *
1491 : : * Sanitize NVM using AQ command (0x070C).
1492 : : *
1493 : : * Return: the exit code of the operation.
1494 : : */
1495 : 0 : s32 ice_nvm_sanitize(struct ice_hw *hw, u8 cmd_flags, u8 *values)
1496 : : {
1497 : : struct ice_aqc_nvm_sanitization *cmd;
1498 : : struct ice_aq_desc desc;
1499 : : s32 status;
1500 : :
1501 : : cmd = &desc.params.sanitization;
1502 : 0 : ice_fill_dflt_direct_cmd_desc(&desc, ice_aqc_opc_nvm_sanitization);
1503 : 0 : cmd->cmd_flags = cmd_flags;
1504 : :
1505 : 0 : status = ice_aq_send_cmd(hw, &desc, NULL, 0, NULL);
1506 [ # # ]: 0 : if (values)
1507 : 0 : *values = cmd->values;
1508 : :
1509 : 0 : return status;
1510 : : }
|