1 /*****************************************************************************
3 (c) Cambridge Silicon Radio Limited 2012
4 All rights reserved and confidential information of CSR
6 Refer to LICENSE.txt included with this source for details
9 *****************************************************************************/
12 * ---------------------------------------------------------------------------
13 * FILE: csr_wifi_hip_download.c
16 * Routines for downloading firmware to UniFi.
18 * ---------------------------------------------------------------------------
20 #include "csr_wifi_hip_unifi.h"
21 #include "csr_wifi_hip_unifiversion.h"
22 #include "csr_wifi_hip_card.h"
23 #include "csr_wifi_hip_xbv.h"
25 #undef CSR_WIFI_IGNORE_PATCH_VERSION_MISMATCH
27 static CsrResult do_patch_download(card_t *card, void *dlpriv,
28 xbv1_t *pfwinfo, CsrUint32 boot_ctrl_addr);
30 static CsrResult do_patch_convert_download(card_t *card,
31 void *dlpriv, xbv1_t *pfwinfo);
34 * ---------------------------------------------------------------------------
37 * Find the offset of the appropriate object in the SLUT of a card
40 * card Pointer to card struct
41 * psym Pointer to symbol object.
43 * obj will be set up by this function
44 * pslut Pointer to SLUT address, if 0xffffffff then it must be
47 * CSR_RESULT_SUCCESS on success
49 * CSR_WIFI_HIP_RESULT_NOT_FOUND if not found
50 * ---------------------------------------------------------------------------
52 static CsrResult _find_in_slut(card_t *card, symbol_t *psym, CsrUint32 *pslut)
54 CsrUint32 slut_address;
59 /* Get SLUT address */
60 if (*pslut == 0xffffffff)
62 r = card_wait_for_firmware_to_start(card, &slut_address);
63 if (r == CSR_WIFI_HIP_RESULT_NO_DEVICE)
67 if (r != CSR_RESULT_SUCCESS)
69 unifi_error(card->ospriv, "Firmware hasn't started\n");
73 *pslut = slut_address;
76 * Firmware has started so set the SDIO bus clock to the initial speed,
77 * faster than UNIFI_SDIO_CLOCK_SAFE_HZ, to speed up the f/w download.
79 csrResult = CsrSdioMaxBusClockFrequencySet(card->sdio_if, UNIFI_SDIO_CLOCK_INIT_HZ);
80 if (csrResult != CSR_RESULT_SUCCESS)
82 r = ConvertCsrSdioToCsrHipResult(card, csrResult);
86 card->sdio_clock_speed = UNIFI_SDIO_CLOCK_INIT_HZ;
90 slut_address = *pslut; /* Use previously discovered address */
92 unifi_trace(card->ospriv, UDBG4, "SLUT addr: 0x%lX\n", slut_address);
95 * Check the SLUT fingerprint.
96 * The slut_address is a generic pointer so we must use unifi_card_read16().
98 unifi_trace(card->ospriv, UDBG4, "Looking for SLUT finger print\n");
100 r = unifi_card_read16(card, slut_address, &finger_print);
101 if (r == CSR_WIFI_HIP_RESULT_NO_DEVICE)
105 if (r != CSR_RESULT_SUCCESS)
107 unifi_error(card->ospriv, "Failed to read SLUT finger print\n");
112 if (finger_print != SLUT_FINGERPRINT)
114 unifi_error(card->ospriv, "Failed to find SLUT fingerprint\n");
115 func_exit_r(CSR_RESULT_FAILURE);
116 return CSR_RESULT_FAILURE;
119 /* Symbol table starts imedately after the fingerprint */
127 r = unifi_card_read16(card, slut_address, &id);
128 if (r != CSR_RESULT_SUCCESS)
135 if (id == CSR_SLT_END)
137 /* End of table reached: not found */
138 r = CSR_WIFI_HIP_RESULT_RANGE;
142 r = unifi_read32(card, slut_address, &obj);
143 if (r != CSR_RESULT_SUCCESS)
150 unifi_trace(card->ospriv, UDBG3, " found SLUT id %02d.%08lx\n", id, obj);
152 r = CSR_WIFI_HIP_RESULT_NOT_FOUND;
153 /* Found search term? */
156 unifi_trace(card->ospriv, UDBG1, " matched SLUT id %02d.%08lx\n", id, obj);
158 r = CSR_RESULT_SUCCESS;
169 * ---------------------------------------------------------------------------
170 * do_patch_convert_download
172 * Download the given firmware image to the UniFi, converting from FWDL
173 * to PTDL XBV format.
176 * card Pointer to card struct
177 * dlpriv Pointer to source firmware image
178 * fwinfo Pointer to source firmware info struct
181 * CSR_RESULT_SUCCESS on success, CSR error code on error
184 * ---------------------------------------------------------------------------
186 static CsrResult do_patch_convert_download(card_t *card, void *dlpriv, xbv1_t *pfwinfo)
189 CsrUint32 slut_base = 0xffffffff;
194 /* Reset the chip to guarantee that the ROM loader is running */
195 r = unifi_init(card);
196 if (r != CSR_RESULT_SUCCESS)
198 unifi_error(card->ospriv,
199 "do_patch_convert_download: failed to re-init UniFi\n");
203 /* If no unifi_helper is running, the firmware version must be read */
204 if (card->build_id == 0)
207 sym.id = CSR_SLT_BUILD_ID_NUMBER;
208 sym.obj = 0; /* To be updated by _find_in_slut() */
210 unifi_trace(card->ospriv, UDBG1, "Need f/w version\n");
212 /* Find chip build id entry in SLUT */
213 r = _find_in_slut(card, &sym, &slut_base);
214 if (r != CSR_RESULT_SUCCESS)
216 unifi_error(card->ospriv, "Failed to find CSR_SLT_BUILD_ID_NUMBER\n");
217 return CSR_RESULT_FAILURE;
220 /* Read running f/w version */
221 r = unifi_read32(card, sym.obj, &ver);
222 if (r == CSR_WIFI_HIP_RESULT_NO_DEVICE)
226 if (r != CSR_RESULT_SUCCESS)
228 unifi_error(card->ospriv, "Failed to read f/w id\n");
229 return CSR_RESULT_FAILURE;
231 card->build_id = ver;
234 /* Convert the ptest firmware to a patch against the running firmware */
235 pfw = xbv_to_patch(card, unifi_fw_read, dlpriv, pfwinfo, &psize);
238 unifi_error(card->ospriv, "Failed to convert f/w to patch");
239 return CSR_WIFI_HIP_RESULT_NO_MEMORY;
244 sym.id = CSR_SLT_BOOT_LOADER_CONTROL;
245 sym.obj = 0; /* To be updated by _find_in_slut() */
247 /* Find boot loader control entry in SLUT */
248 r = _find_in_slut(card, &sym, &slut_base);
249 if (r != CSR_RESULT_SUCCESS)
251 unifi_error(card->ospriv, "Failed to find BOOT_LOADER_CONTROL\n");
252 return CSR_RESULT_FAILURE;
255 r = unifi_set_host_state(card, UNIFI_HOST_STATE_AWAKE);
256 if (r != CSR_RESULT_SUCCESS)
258 unifi_error(card->ospriv, "Failed to wake UniFi\n");
261 /* Get a dlpriv for the patch buffer so that unifi_fw_read() can
264 desc = unifi_fw_open_buffer(card->ospriv, pfw, psize);
267 return CSR_WIFI_HIP_RESULT_NO_MEMORY;
270 /* Download the patch */
271 unifi_info(card->ospriv, "Downloading converted f/w as patch\n");
272 r = unifi_dl_patch(card, desc, sym.obj);
274 unifi_fw_close_buffer(card->ospriv, desc);
276 if (r != CSR_RESULT_SUCCESS)
278 unifi_error(card->ospriv, "Converted patch download failed\n");
284 unifi_trace(card->ospriv, UDBG1, "Converted patch downloaded\n");
287 /* This command starts the firmware */
288 r = unifi_do_loader_op(card, sym.obj + 6, UNIFI_BOOT_LOADER_RESTART);
289 if (r != CSR_RESULT_SUCCESS)
291 unifi_error(card->ospriv, "Failed to write loader restart cmd\n");
301 * ---------------------------------------------------------------------------
304 * Download the given firmware image to the UniFi.
307 * card Pointer to card struct
308 * dlpriv A context pointer from the calling function to be
309 * passed when calling unifi_fw_read().
312 * CSR_RESULT_SUCCESS on success,
313 * CSR_WIFI_HIP_RESULT_NO_MEMORY memory allocation failed
314 * CSR_WIFI_HIP_RESULT_INVALID_VALUE error in XBV file
315 * CSR_RESULT_FAILURE SDIO error
318 * Stops and resets the chip, does the download and runs the new
320 * ---------------------------------------------------------------------------
322 CsrResult unifi_dl_firmware(card_t *card, void *dlpriv)
329 fwinfo = CsrMemAlloc(sizeof(xbv1_t));
332 unifi_error(card->ospriv, "Failed to allocate memory for firmware\n");
333 return CSR_WIFI_HIP_RESULT_NO_MEMORY;
337 * Scan the firmware file to find the TLVs we are interested in.
339 * - check we support the file format version in VERF
340 * - SLTP Symbol Lookup Table Pointer
341 * - FWDL firmware download segments
342 * - FWOV firmware overlay segment
343 * - VMEQ Register probe tests to verify matching h/w
345 r = xbv1_parse(card, unifi_fw_read, dlpriv, fwinfo);
346 if (r != CSR_RESULT_SUCCESS || fwinfo->mode != xbv_firmware)
348 unifi_error(card->ospriv, "File type is %s, expected firmware.\n",
349 fwinfo->mode == xbv_patch?"patch" : "unknown");
351 return CSR_WIFI_HIP_RESULT_INVALID_VALUE;
354 /* UF6xxx doesn't accept firmware, only patches. Therefore we convert
355 * the file to patch format with version numbers matching the current
356 * running firmware, and then download via the patch mechanism.
357 * The sole purpose of this is to support production test firmware across
358 * different ROM releases, the test firmware being provided in non-patch
361 if (card->chip_id > SDIO_CARD_ID_UNIFI_2)
363 unifi_info(card->ospriv, "Must convert f/w to patch format\n");
364 r = do_patch_convert_download(card, dlpriv, fwinfo);
368 /* Older UniFi chips allowed firmware to be directly loaded onto the
369 * chip, which is no longer supported.
371 unifi_error(card->ospriv, "Only patch downloading supported\n");
372 r = CSR_WIFI_HIP_RESULT_INVALID_VALUE;
378 } /* unifi_dl_firmware() */
382 * ---------------------------------------------------------------------------
385 * Load the given patch set into UniFi.
388 * card Pointer to card struct
389 * dlpriv The os specific handle to the firmware file.
390 * boot_ctrl The address of the boot loader control structure.
393 * CSR_RESULT_SUCCESS on success,
394 * CSR_WIFI_HIP_RESULT_NO_MEMORY memory allocation failed
395 * CSR_WIFI_HIP_RESULT_INVALID_VALUE error in XBV file
396 * CSR_RESULT_FAILURE SDIO error
399 * This ends up telling UniFi to restart.
400 * ---------------------------------------------------------------------------
402 CsrResult unifi_dl_patch(card_t *card, void *dlpriv, CsrUint32 boot_ctrl)
409 unifi_info(card->ospriv, "unifi_dl_patch %p %08x\n", dlpriv, boot_ctrl);
411 fwinfo = CsrMemAlloc(sizeof(xbv1_t));
414 unifi_error(card->ospriv, "Failed to allocate memory for patches\n");
416 return CSR_WIFI_HIP_RESULT_NO_MEMORY;
420 * Scan the firmware file to find the TLVs we are interested in.
422 * - check we support the file format version in VERF
423 * - FWID The build ID of the ROM that we can patch
424 * - PTDL patch download segments
426 r = xbv1_parse(card, unifi_fw_read, dlpriv, fwinfo);
427 if (r != CSR_RESULT_SUCCESS || fwinfo->mode != xbv_patch)
430 unifi_error(card->ospriv, "Failed to read in patch file\n");
432 return CSR_WIFI_HIP_RESULT_INVALID_VALUE;
436 * We have to check the build id read from the SLUT against that
437 * for the patch file. They have to match exactly.
438 * "card->build_id" == XBV1.PTCH.FWID
440 if (card->build_id != fwinfo->build_id)
442 unifi_error(card->ospriv, "Wrong patch file for chip (chip = %lu, file = %lu)\n",
443 card->build_id, fwinfo->build_id);
445 #ifndef CSR_WIFI_IGNORE_PATCH_VERSION_MISMATCH
447 return CSR_WIFI_HIP_RESULT_INVALID_VALUE;
451 return CSR_RESULT_SUCCESS;
455 r = do_patch_download(card, dlpriv, fwinfo, boot_ctrl);
456 if (r != CSR_RESULT_SUCCESS)
458 unifi_error(card->ospriv, "Failed to patch image\n");
465 } /* unifi_dl_patch() */
468 void* unifi_dl_fw_read_start(card_t *card, s8 is_fw)
470 card_info_t card_info;
472 unifi_card_info(card, &card_info);
473 unifi_trace(card->ospriv, UDBG5,
474 "id=%d, ver=0x%x, fw_build=%u, fw_hip=0x%x, block_size=%d\n",
475 card_info.chip_id, card_info.chip_version,
476 card_info.fw_build, card_info.fw_hip_version,
477 card_info.sdio_block_size);
479 return unifi_fw_read_start(card->ospriv, is_fw, &card_info);
484 * ---------------------------------------------------------------------------
485 * safe_read_shared_location
487 * Read a shared memory location repeatedly until we get two readings
491 * card Pointer to card context struct.
492 * unifi_addr UniFi shared-data-memory address to access.
493 * pdata Pointer to a byte variable for the value read.
497 * CSR_RESULT_SUCCESS on success, CSR error code on failure
498 * ---------------------------------------------------------------------------
500 static CsrResult safe_read_shared_location(card_t *card, CsrUint32 address, u8 *pdata)
508 r = unifi_read_8_or_16(card, address, &b);
509 if (r != CSR_RESULT_SUCCESS)
516 r = unifi_read_8_or_16(card, address, &b2);
517 if (r != CSR_RESULT_SUCCESS)
522 /* When we have a stable value, return it */
526 return CSR_RESULT_SUCCESS;
532 return CSR_RESULT_FAILURE;
533 } /* safe_read_shared_location() */
537 * ---------------------------------------------------------------------------
540 * Send a loader / boot_loader command to the UniFi and wait for
544 * card Pointer to card context struct.
545 * op_addr The address of the loader operation control word.
546 * opcode The operation to perform.
549 * CSR_RESULT_SUCCESS on success
550 * CSR_RESULT_FAILURE SDIO error or SDIO/XAP timeout
551 * ---------------------------------------------------------------------------
555 * Ideally instead of sleeping, we want to busy wait.
556 * Currently there is no framework API to do this. When it becomes available,
557 * we can use it to busy wait using usecs
559 #define OPERATION_TIMEOUT_LOOPS (100) /* when OPERATION_TIMEOUT_DELAY==1, (500) otherwise */
560 #define OPERATION_TIMEOUT_DELAY 1 /* msec, or 200usecs */
562 CsrResult unifi_do_loader_op(card_t *card, CsrUint32 op_addr, u8 opcode)
567 unifi_trace(card->ospriv, UDBG4, "Loader cmd 0x%0x -> 0x%08x\n", opcode, op_addr);
569 /* Set the Operation command byte to the opcode */
570 r = unifi_write_8_or_16(card, op_addr, opcode);
571 if (r != CSR_RESULT_SUCCESS)
573 unifi_error(card->ospriv, "Failed to write loader copy command\n");
577 /* Wait for Operation command byte to be Idle */
578 /* Typically takes ~100us */
580 r = CSR_RESULT_SUCCESS;
586 * Read the memory location until two successive reads give
590 r = safe_read_shared_location(card, op_addr, &op);
591 if (r != CSR_RESULT_SUCCESS)
593 unifi_error(card->ospriv, "Failed to read loader status\n");
597 if (op == UNIFI_LOADER_IDLE)
605 unifi_error(card->ospriv, "Error reported by loader: 0x%X\n", op);
606 r = CSR_RESULT_FAILURE;
610 /* Allow 500us timeout */
611 if (++op_retries >= OPERATION_TIMEOUT_LOOPS)
613 unifi_error(card->ospriv, "Timeout waiting for loader to ack transfer\n");
614 /* Stop XAPs to aid post-mortem */
615 r = unifi_card_stop_processor(card, UNIFI_PROC_BOTH);
616 if (r != CSR_RESULT_SUCCESS)
618 unifi_error(card->ospriv, "Failed to stop UniFi processors\n");
622 r = CSR_RESULT_FAILURE;
626 CsrThreadSleep(OPERATION_TIMEOUT_DELAY);
627 } /* Loop exits with r != CSR_RESULT_SUCCESS on error */
630 } /* unifi_do_loader_op() */
634 * ---------------------------------------------------------------------------
637 * Copy a patch block from userland to the UniFi.
638 * This function reads data, 2K at a time, from userland and writes
642 * card A pointer to the card structure
643 * dlpriv The os specific handle for the firmware file
644 * ptdl A pointer ot the PTDL block
645 * handle The buffer handle to use for the xfer
646 * op_addr The address of the loader operation control word
649 * Number of bytes sent (Positive) or negative value indicating
651 * CSR_WIFI_HIP_RESULT_NO_MEMORY memory allocation failed
652 * CSR_WIFI_HIP_RESULT_INVALID_VALUE error in XBV file
653 * CSR_RESULT_FAILURE SDIO error
654 * ---------------------------------------------------------------------------
656 static CsrResult send_ptdl_to_unifi(card_t *card, void *dlpriv,
657 const struct PTDL *ptdl, CsrUint32 handle,
665 const u16 buf_size = 2 * 1024;
667 offset = ptdl->dl_offset;
668 data_len = ptdl->dl_size;
670 if (data_len > buf_size)
672 unifi_error(card->ospriv, "PTDL block is too large (%u)\n",
674 return CSR_WIFI_HIP_RESULT_INVALID_VALUE;
677 buf = CsrMemAllocDma(buf_size);
680 unifi_error(card->ospriv, "Failed to allocate transfer buffer for firmware download\n");
681 return CSR_WIFI_HIP_RESULT_NO_MEMORY;
684 r = CSR_RESULT_SUCCESS;
686 if (unifi_fw_read(card->ospriv, dlpriv, offset, buf, data_len) != data_len)
688 unifi_error(card->ospriv, "Failed to read from file\n");
692 /* We can always round these if the host wants to */
693 if (card->sdio_io_block_pad)
695 write_len = (data_len + (card->sdio_io_block_size - 1)) &
696 ~(card->sdio_io_block_size - 1);
698 /* Zero out the rest of the buffer (This isn't needed, but it
699 * makes debugging things later much easier). */
700 CsrMemSet(buf + data_len, 0, write_len - data_len);
704 write_len = data_len;
707 r = unifi_bulk_rw_noretry(card, handle, buf, write_len, UNIFI_SDIO_WRITE);
708 if (r != CSR_RESULT_SUCCESS)
710 unifi_error(card->ospriv, "CMD53 failed writing %d bytes to handle %ld\n",
716 * Can change the order of things to overlap read from file
719 r = unifi_do_loader_op(card, op_addr, UNIFI_BOOT_LOADER_PATCH);
725 if (r != CSR_RESULT_SUCCESS && r != CSR_WIFI_HIP_RESULT_NO_DEVICE)
727 unifi_error(card->ospriv, "Failed to copy block of %u bytes to UniFi\n",
732 } /* send_ptdl_to_unifi() */
736 * ---------------------------------------------------------------------------
739 * This function downloads a set of patches to UniFi and then
740 * causes it to restart.
743 * card Pointer to card struct.
744 * dlpriv A context pointer from the calling function to be
745 * used when reading the XBV file. This can be NULL
746 * in which case not patches are applied.
747 * pfwinfo Pointer to a fwinfo struct describing the f/w
749 * boot_ctrl_addr The address of the boot loader control structure.
752 * 0 on success, or an error code
753 * CSR_WIFI_HIP_RESULT_INVALID_VALUE for a bad laoader version number
754 * ---------------------------------------------------------------------------
756 static CsrResult do_patch_download(card_t *card, void *dlpriv, xbv1_t *pfwinfo, CsrUint32 boot_ctrl_addr)
762 CsrUint32 total_bytes;
765 * Read info from the SDIO Loader Control Data Structure
767 /* Check the loader version */
768 r = unifi_card_read16(card, boot_ctrl_addr, &loader_version);
769 if (r != CSR_RESULT_SUCCESS)
771 unifi_error(card->ospriv, "Patch download: Failed to read loader version\n");
774 unifi_trace(card->ospriv, UDBG2, "Patch download: boot loader version 0x%04X\n", loader_version);
775 switch (loader_version)
781 unifi_error(card->ospriv, "Patch loader version (0x%04X) is not supported by this driver\n",
783 return CSR_WIFI_HIP_RESULT_INVALID_VALUE;
786 /* Retrieve the handle to use with CMD53 */
787 r = unifi_card_read16(card, boot_ctrl_addr + 4, &handle);
788 if (r != CSR_RESULT_SUCCESS)
790 unifi_error(card->ospriv, "Patch download: Failed to read loader handle\n");
794 /* Set the mask of LEDs to flash */
795 if (card->loader_led_mask)
797 r = unifi_card_write16(card, boot_ctrl_addr + 2,
798 (u16)card->loader_led_mask);
799 if (r != CSR_RESULT_SUCCESS)
801 unifi_error(card->ospriv, "Patch download: Failed to write LED mask\n");
808 /* Copy download data to UniFi memory */
809 for (i = 0; i < pfwinfo->num_ptdl; i++)
811 unifi_trace(card->ospriv, UDBG3, "Patch download: %d Downloading for %d from offset %d\n",
813 pfwinfo->ptdl[i].dl_size,
814 pfwinfo->ptdl[i].dl_offset);
816 r = send_ptdl_to_unifi(card, dlpriv, &pfwinfo->ptdl[i],
817 handle, boot_ctrl_addr + 6);
818 if (r == CSR_WIFI_HIP_RESULT_NO_DEVICE)
822 if (r != CSR_RESULT_SUCCESS)
824 unifi_error(card->ospriv, "Patch failed after %u bytes\n",
828 total_bytes += pfwinfo->ptdl[i].dl_size;
831 return CSR_RESULT_SUCCESS;
832 } /* do_patch_download() */