FreeCalypso > hg > fc-selenite
diff src/cs/drivers/drv_app/ffs/board/drv.c @ 134:7d50d8d13711
FFS code sync with Magnetite + gcc version fix
This change brings the new flash autodetection for FC and Pirelli targets
from Magnetite, and should also fix the gcc version for C1xx and gtamodem
targets, which were previously broken because they used TI's original
flash autodetect code (which operates at address 0) while the boot ROM
is mapped there.
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Tue, 11 Dec 2018 08:43:25 +0000 |
parents | 4484ab3f6ab3 |
children | 7409b22cac61 |
line wrap: on
line diff
--- a/src/cs/drivers/drv_app/ffs/board/drv.c Mon Nov 19 07:19:05 2018 +0000 +++ b/src/cs/drivers/drv_app/ffs/board/drv.c Tue Dec 11 08:43:25 2018 +0000 @@ -12,6 +12,8 @@ #include "ffs.cfg" #endif +#include "fc-target.cfg" + #include "ffs/ffs.h" #include "ffs/board/drv.h" #include "ffs/board/ffstrace.h" @@ -979,6 +981,56 @@ // The function should be copied and executed from RAM! void ffsdrv_device_id_read(uint16 *manufact, uint16 *device) { +#if defined(CONFIG_TARGET_FCFAM) || defined(CONFIG_TARGET_PIRELLI) || \ + defined(__GNUC__) + /* + * This new FreeCalypso version of the device ID read function + * should work for all current targets, but we are being conservative + * and only enabling it for those targets for which it is required, + * i.e., where TI's original version does not work. + * + * Selenite change: for the gcc version we need to use this new + * autodetect code for all targets, TI's original version won't work + * because we run with the Calypso boot ROM at 0. + */ + + int addr, half, base, i; + + /* + * We operate at a non-zero erase block boundary so that this ID read + * operation will still work in our newer FreeCalypso environments + * where we have the Calypso boot ROM mapped at 0. + */ + base = 0x40000; + + /* + * muckery similar to TI's original to avoid literal pool loads, + * but we produce and use 0xAAA and 0x554 offsets instead of TI's + * original 0xAAAA and 0x5555. + */ + for (i = 0, addr = 0; i < 3; i++) + addr = addr << 4 | 0xA; + half = (addr >> 1) & ~1; + + FLASH_WRITE_HALFWORD (base + addr, 0xAA); + FLASH_WRITE_HALFWORD (base + half, 0x55); + FLASH_WRITE_HALFWORD (base + addr, 0x90); // Intel/AMD read id command + + *manufact = FLASH_READ_HALFWORD (base + 0); // flash a0 = 0 + *device = FLASH_READ_HALFWORD (base + 2); // flash a0 = 1 + + // Read extended id + device[1] = FLASH_READ_HALFWORD (base + (0xE << 1)); + device[2] = FLASH_READ_HALFWORD (base + (0xF << 1)); + FLASH_WRITE_HALFWORD (base, 0xFF); // Intel read-array command + + // AMD devices do not need the two unlock cycles but SST devices do, + // even though the SST datasheets states otherwise ;-) + FLASH_WRITE_HALFWORD (base + addr, 0xAA); + FLASH_WRITE_HALFWORD (base + half, 0x55); + FLASH_WRITE_HALFWORD (base + addr, 0xF0); // AMD read-array/reset command +#else + /* TI's original version */ int addr, i; // This silly looking code has one purpose; to set addr = 0xAAAA. It is @@ -1005,6 +1057,7 @@ FLASH_WRITE_HALFWORD (addr, 0xAA); FLASH_WRITE_HALFWORD (addr >> 1, 0x55); FLASH_WRITE_HALFWORD (addr, 0xF0); // AMD read-array/reset command +#endif } // Copy ffsdrv_device_id_read() function code to RAM. The only known way to @@ -1121,6 +1174,34 @@ return 0; } +#if defined(CONFIG_TARGET_PIRELLI) || defined(CONFIG_TARGET_FCFAM) + +#ifdef CONFIG_TARGET_FCFAM +#define FLASH2_BASE_ADDR 0x01800000 +#elif defined(CONFIG_TARGET_PIRELLI) +#define FLASH2_BASE_ADDR 0x02000000 +#endif + +int ffsdrv_is_new_spansion_flash(void) +{ + uint16 cfi_hi, cfi_lo, cfi_ver; + + /* CFI query */ + FLASH_WRITE_HALFWORD(FLASH2_BASE_ADDR + 0xAAA, 0x98); + cfi_hi = FLASH_READ_HALFWORD(FLASH2_BASE_ADDR + 0x86); + cfi_lo = FLASH_READ_HALFWORD(FLASH2_BASE_ADDR + 0x88); + cfi_ver = (cfi_hi << 8) | (cfi_lo & 0xFF); + + /* return to read array mode */ + FLASH_WRITE_HALFWORD(FLASH2_BASE_ADDR + 0xAAA, 0xF0); + + if (cfi_ver >= 0x3134) + return 1; + else + return 0; +} +#endif + #else // (TARGET == 0) void ffsdrv_device_id_read(uint16 *manufact, uint16 *device) {} @@ -1278,7 +1359,7 @@ if (ffs_flash_manufact == 0 && ffs_flash_device == 0) { #if (TARGET == 1) - char detect_code[80]; + char detect_code[0x80]; typedef (*pf_t)(uint16 *, uint16 *); pf_t myfp; uint16 device_id[3]; @@ -1299,6 +1380,10 @@ device_id[0] == 0x227E) { // This is a multi-id device dev.device = (device_id[1] << 8) | (device_id[2] & 0xFF); + #if defined(CONFIG_TARGET_PIRELLI) || defined(CONFIG_TARGET_FCFAM) + if (device_id[1] == 0x2221 && device_id[2] == 0x2200) + dev.device += ffsdrv_is_new_spansion_flash(); + #endif } else dev.device = device_id[0];