diff --git a/u-boot/board/ar7240/carambola2/flash.c b/u-boot/board/ar7240/carambola2/flash.c index 5e407d1468..38b3bb4059 100644 --- a/u-boot/board/ar7240/carambola2/flash.c +++ b/u-boot/board/ar7240/carambola2/flash.c @@ -2,27 +2,3 @@ #include #include #include - -/* - * sets up flash_info and returns size of FLASH (bytes) - */ -unsigned long -flash_get_geom (flash_info_t *flash_info) -{ - int i; - - /* XXX this is hardcoded until we figure out how to read flash id */ - - flash_info->flash_id = FLASH_M25P64; - flash_info->size = CFG_FLASH_SIZE; /* bytes */ - flash_info->sector_count = flash_info->size/CFG_FLASH_SECTOR_SIZE; - - for (i = 0; i < flash_info->sector_count; i++) { - flash_info->start[i] = CFG_FLASH_BASE + (i * CFG_FLASH_SECTOR_SIZE); - flash_info->protect[i] = 0; - } - - debug ("flash size %d, sector count = %d\n", flash_info->size, flash_info->sector_count); - return (flash_info->size); - -} diff --git a/u-boot/board/ar7240/common/ar7240_flash.c b/u-boot/board/ar7240/common/ar7240_flash.c index 076e18bde8..23aca3eff4 100644 --- a/u-boot/board/ar7240/common/ar7240_flash.c +++ b/u-boot/board/ar7240/common/ar7240_flash.c @@ -14,6 +14,18 @@ flash_info_t flash_info[CFG_MAX_FLASH_BANKS]; #undef display #define display(x) ; +#define SIZE_INBYTES_4MBYTES (4 * 1024 * 1024) +#define SIZE_INBYTES_8MBYTES (2 * SIZE_INBYTES_4MBYTES) +#define SIZE_INBYTES_16MBYTES (2 * SIZE_INBYTES_8MBYTES) + +#define SIZE_INBYTES_4KBYTES (4 * 1024) +#define SIZE_INBYTES_64KBYTES (16 * SIZE_INBYTES_4KBYTES) + +#ifndef DEFAULT_FLASH_SIZE_IN_MB +#error "DEFAULT_FLASH_SIZE_IN_MB not defined!" +#endif + + /* * statics */ @@ -24,26 +36,34 @@ static void ar7240_spi_write_page(uint32_t addr, uint8_t * data, int len); #endif static void ar7240_spi_sector_erase(uint32_t addr); -static u32 -ath_spi_read_id(void) +static ulong read_id(void) { - u32 rd = 0x777777; + unsigned int flashid = 0; + ar7240_reg_wr_nf(AR7240_SPI_FS, 1); ar7240_reg_wr_nf(AR7240_SPI_WRITE, AR7240_SPI_CS_DIS); - ar7240_spi_bit_banger(AR7240_SPI_CMD_RDID); - ar7240_spi_delay_8(); - ar7240_spi_delay_8(); - ar7240_spi_delay_8(); - ar7240_spi_go(); - rd = ar7240_reg_rd(AR7240_SPI_RD_STATUS); + ar7240_spi_bit_banger(0x9F); - debug("Flash Manuf Id 0x%x, DeviceId0 0x%x, DeviceId1 0x%x\n", - (rd >> 16) & 0xff, (rd >> 8) & 0xff, (rd >> 0) & 0xff); - return rd; + ar7240_spi_delay_8(); + ar7240_spi_delay_8(); + ar7240_spi_delay_8(); + ar7240_spi_delay_8(); + + flashid = ar7240_reg_rd(AR7240_SPI_RD_STATUS); + + /* + * We have 3 bytes: + * - manufacture ID (1b) + * - product ID (2b) + */ + flashid = flashid >> 8; + + ar7240_spi_done(); + + return((ulong)flashid); } - #ifdef ATH_SST_FLASH void ar7240_spi_flash_unblock(void) { @@ -55,25 +75,157 @@ void ar7240_spi_flash_unblock(void) } #endif +static void flash_set_geom(int size, int sector_count, int sector_size){ + int i; + flash_info_t *info = &flash_info[0]; + + info->size = size; + info->sector_count = sector_count; + info->sector_size = sector_size; + + for(i = 0; i < info->sector_count; i++){ + info->start[i] = CFG_FLASH_BASE + (i * info->sector_size); + } +} + unsigned long flash_init(void) { -#ifndef CONFIG_WASP -#ifdef ATH_SST_FLASH - ar7240_reg_wr_nf(AR7240_SPI_CLOCK, 0x3); - ar7240_spi_flash_unblock(); - ar7240_reg_wr(AR7240_SPI_FS, 0); -#else - ar7240_reg_wr_nf(AR7240_SPI_CLOCK, 0x43); -#endif -#endif - ar7240_reg_rmw_set(AR7240_SPI_FS, 1); - ath_spi_read_id(); - ar7240_reg_rmw_clear(AR7240_SPI_FS, 1); + flash_info_t *info; - /* - * hook into board specific code to fill flash_info - */ - return (flash_get_geom(&flash_info[0])); + info = &flash_info[0]; + + // spi flash clock + ar7240_reg_wr(AR7240_SPI_FS, 0x01); + + ar7240_reg_wr(AR7240_SPI_CLOCK, 0x43); + + ar7240_reg_wr(AR7240_SPI_FS, 0x0); + + // get flash id + info->flash_id = read_id(); + + puts("FLASH: "); + + // fill flash info based on JEDEC ID + switch(info->flash_id) { + /* + * 4M flash chips + */ + case 0x010215: // tested + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("Spansion S25FL032P (4 MB)"); + break; + + case 0x1F4700: + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("Atmel AT25DF321 (4 MB)"); + break; + + case 0x1C3016: // tested + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("EON EN25Q32 (4 MB)"); + break; + + case 0x1C3116: // tested + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("EON EN25F32 (4 MB)"); + break; + + case 0x202016: + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("Micron M25P32 (4 MB)"); + break; + + case 0xEF4016: + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("Winbond W25Q32 (4 MB)"); + break; + + case 0xC22016: + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("Macronix MX25L320 (4 MB)"); + break; + + /* + * 8M flash chips + */ + case 0x010216: + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("Spansion S25FL064P (8 MB)"); + break; + + case 0x1F4800: + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("Atmel AT25DF641 (8 MB)"); + break; + + case 0x1C3017: // tested + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("EON EN25Q64 (8 MB)"); + break; + + case 0x202017: + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("Micron M25P64 (8 MB)"); + break; + + case 0xEF4017: // tested + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("Winbond W25Q64 (8 MB)"); + break; + + case 0xC22017: // tested + case 0xC22617: + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("Macronix MX25L64 (8 MB)"); + break; + + /* + * 16M flash chips + */ + case 0xEF4018: // tested + flash_set_geom(SIZE_INBYTES_16MBYTES, 256, SIZE_INBYTES_64KBYTES); + puts("Winbond W25Q128 (16 MB)"); + break; + + case 0xC22018: + case 0xC22618: + flash_set_geom(SIZE_INBYTES_16MBYTES, 256, SIZE_INBYTES_64KBYTES); + puts("Macronix MX25L128 (16 MB)"); + break; + + case 0x012018: + flash_set_geom(SIZE_INBYTES_16MBYTES, 256, SIZE_INBYTES_64KBYTES); + puts("Spansion S25FL127S (16 MB)"); + break; + + case 0x20BA18: + flash_set_geom(SIZE_INBYTES_16MBYTES, 256, SIZE_INBYTES_64KBYTES); + puts("Micron N25Q128 (16 MB)"); + break; + + /* + * Unknown flash + */ + default: +#if (DEFAULT_FLASH_SIZE_IN_MB == 4) + flash_set_geom(SIZE_INBYTES_4MBYTES, 64, SIZE_INBYTES_64KBYTES); + puts("Unknown type (using only 4 MB)\n"); +#elif (DEFAULT_FLASH_SIZE_IN_MB == 8) + flash_set_geom(SIZE_INBYTES_8MBYTES, 128, SIZE_INBYTES_64KBYTES); + puts("Unknown type (using only 8 MB)\n"); +#elif (DEFAULT_FLASH_SIZE_IN_MB == 16) + flash_set_geom(SIZE_INBYTES_16MBYTES, 256, SIZE_INBYTES_64KBYTES); + puts("Unknown type (using only 16 MB)\n"); +#endif + printf("\nPlease, send request to add support\nfor your FLASH - JEDEC ID: 0x%06lX\n", info->flash_id); + info->flash_id = FLASH_CUSTOM; + break; + } + + puts("\n"); + + return(info->size); } void @@ -103,7 +255,7 @@ flash_erase(flash_info_t *info, int s_first, int s_last) show_activity(3); #endif #if defined(CONFIG_HW_WATCHDOG) || defined(CONFIG_WATCHDOG) - WATCHDOG_RESET(); + WATCHDOG_RESET(); #endif #endif diff --git a/u-boot/board/ar7240/common/ar7240_flash.h b/u-boot/board/ar7240/common/ar7240_flash.h index de6aae7acf..f3f88ebb00 100644 --- a/u-boot/board/ar7240/common/ar7240_flash.h +++ b/u-boot/board/ar7240/common/ar7240_flash.h @@ -59,6 +59,6 @@ #define ar7240_spi_delay_8() ar7240_spi_bit_banger(0) #define ar7240_spi_done() ar7240_reg_wr_nf(AR7240_SPI_FS, 0) -extern unsigned long flash_get_geom (flash_info_t *flash_info); +extern unsigned long flash_get_geom (flash_info_t *flash_info, u32 flashid); #endif /*_FLASH_H*/ diff --git a/u-boot/common/cmd_setmac.c b/u-boot/common/cmd_setmac.c index 17916829ef..e2b4168c81 100644 --- a/u-boot/common/cmd_setmac.c +++ b/u-boot/common/cmd_setmac.c @@ -22,7 +22,10 @@ */ #include +#include +#include #include +#include #ifdef CFG_CMD_SETMAC @@ -113,25 +116,29 @@ static int backup_calibration(u8 *buffer) { int rc = -1; + ulong sector_size = flash_info[0].sector_size; + ushort cal_sector = flash_info[0].sector_count -1; + u8 *board_cal = (u8 *) (KSEG1ADDR(AR7240_SPI_BASE) + cal_sector * flash_info[0].sector_size); + /* read */ - memcpy(buffer, (void *)BOARDCAL, CFG_FLASH_SECTOR_SIZE); + memcpy(buffer, (void *)board_cal, sector_size); /* erase */ - rc = flash_erase(flash_info, CAL_SECTOR-1, CAL_SECTOR-1); + rc = flash_erase(flash_info, cal_sector-1, cal_sector-1); if (rc) { printf("Backup failed because flash erase failed! rc %d\n", rc); return 1; } - /* cp */ - rc = write_buff(flash_info, buffer, BOARDCAL-CFG_FLASH_SECTOR_SIZE, CFG_FLASH_SECTOR_SIZE); + /* writing into flash - we use the mapped flash as source */ + rc = write_buff(flash_info, buffer, board_cal - sector_size, sector_size); if (rc) { printf("Backup failed because write to flash failed! rc %d\n", rc); return 1; } /* compare */ - if (memcmp(buffer, (void *)BOARDCAL-CFG_FLASH_SECTOR_SIZE, CFG_FLASH_SECTOR_SIZE)) { + if (memcmp(buffer, (void *)board_cal - sector_size, sector_size)) { printf("Backup failed. Read back different value!\n"); return 1; } @@ -144,8 +151,12 @@ int write_mac(u8 *buffer, u8 macs[ARRAY_SIZE(mac_location)][ETH_ALEN]) int i; int rc; + ulong sector_size = flash_info[0].sector_size; + ushort cal_sector = flash_info[0].sector_count -1; + u8 *board_cal = (u8 *) (KSEG1ADDR(AR7240_SPI_BASE) + cal_sector * flash_info[0].sector_size); + /* read */ - memcpy(buffer, (void *)BOARDCAL, CFG_FLASH_SECTOR_SIZE); + memcpy(buffer, (void *)board_cal, sector_size); /* set macs */ for(i=0; i [..] or set_mac [..] nobackup @@ -210,26 +225,42 @@ int do_setmac(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) } } + buffer = malloc(sector_size); + if (!buffer) { + printf("Could not allocate memory"); + return CMD_RET_FAILURE; + } + if (do_backup) { if (backup_calibration(buffer)) { - printf("Backup failed to the sector before calibration. Not updating calibration sector!"); - return CMD_RET_FAILURE; + printf("Backup failed to the sector before calibration.\n" + "Not updating calibration sector!\n"); + rc = CMD_RET_FAILURE; + goto out; } } if (!write_mac(buffer, macs)) { - return CMD_RET_FAILURE; + rc = CMD_RET_FAILURE; + goto out; } - return CMD_RET_SUCCESS; + rc = CMD_RET_SUCCESS; +out: + free(buffer); + return rc; } int do_showmac(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) { int i = 0; - u8 buffer[CFG_FLASH_SECTOR_SIZE]; + u8 *buffer; u8 *mac; - memcpy(buffer, (void *)BOARDCAL, CFG_FLASH_SECTOR_SIZE); + ushort cal_sector = flash_info[0].sector_count -1; + u8 *board_cal = (u8 *) (KSEG1ADDR(AR7240_SPI_BASE) + cal_sector * flash_info[0].sector_size); + + /* using mapped spi memory */ + buffer = (void *)board_cal; for (i=0; i < ARRAY_SIZE(mac_location); i++) { mac = buffer + mac_location[i]; @@ -242,10 +273,13 @@ int do_showmac(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) int do_setserial(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) { - u8 buffer[CFG_FLASH_SECTOR_SIZE]; + u8 *buffer; int32_t *serial; int32_t serial_number; int rc; + ulong sector_size = flash_info[0].sector_size; + ushort cal_sector = flash_info[0].sector_count -1; + u8 *board_cal = KSEG1ADDR(AR7240_SPI_BASE) + cal_sector * flash_info[0].sector_size; if (argc != 2) return CMD_RET_FAILURE; @@ -256,37 +290,51 @@ int do_setserial(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) return CMD_RET_FAILURE; } + buffer = malloc(sector_size); + if (!buffer) { + printf("Could not allocate memory"); + return CMD_RET_FAILURE; + } + /* read */ - memcpy(buffer, (void *)BOARDCAL, CFG_FLASH_SECTOR_SIZE); + memcpy(buffer, (void *)board_cal, sector_size); /* set serial number */ serial = (int32_t *) (buffer + SERIAL_LOCATION); *serial = serial_number; /* erase */ - rc = flash_erase(flash_info, CAL_SECTOR, CAL_SECTOR); + rc = flash_erase(flash_info, cal_sector, cal_sector); if (rc) { printf("Write serial failed because flash_erase failed! rc %d\n", rc); - return 1; + rc = CMD_RET_SUCCESS; + goto out; } /* write */ - rc = write_buff(flash_info, buffer, BOARDCAL, CFG_FLASH_SECTOR_SIZE); + rc = write_buff(flash_info, buffer, board_cal, sector_size); if (rc) { printf("Write serial failed because write_buff failed! rc %d\n", rc); - return 1; + rc = CMD_RET_FAILURE; + goto out; } printf("Set serial to %d\n", serial_number); + rc = CMD_RET_SUCCESS; - return CMD_RET_SUCCESS; +out: + free(buffer); + return rc; } int do_showserial(cmd_tbl_t *cmdtp, int flag, int argc, char *argv[]) { - u8 buffer[CFG_FLASH_SECTOR_SIZE]; + ulong sector_size = flash_info[0].sector_size; + ushort cal_sector = flash_info[0].sector_count -1; + u8 *board_cal = KSEG1ADDR(AR7240_SPI_BASE) + cal_sector * flash_info[0].sector_size; + u8 *buffer = board_cal; + int32_t *serial; - memcpy(buffer, (void *)BOARDCAL, CFG_FLASH_SECTOR_SIZE); serial = (int32_t *) (buffer + SERIAL_LOCATION); printf("serial %d\n", *serial); diff --git a/u-boot/include/configs/ap1.h b/u-boot/include/configs/ap1.h index 6573794703..99ec89e86a 100644 --- a/u-boot/include/configs/ap1.h +++ b/u-boot/include/configs/ap1.h @@ -21,11 +21,8 @@ * FLASH and environment organization *----------------------------------------------------------------------- */ - -#define CFG_MAX_FLASH_BANKS 1 -#define CFG_MAX_FLASH_SECT 256 -#define CFG_FLASH_SECTOR_SIZE (64*1024) -#define CFG_FLASH_SIZE 0x01000000 + +#define DEFAULT_FLASH_SIZE_IN_MB 16 #define BOARDCAL 0x9fff0000 diff --git a/u-boot/include/configs/ap2.h b/u-boot/include/configs/ap2.h index 63c2c6384c..e554892c92 100644 --- a/u-boot/include/configs/ap2.h +++ b/u-boot/include/configs/ap2.h @@ -22,10 +22,7 @@ *----------------------------------------------------------------------- */ -#define CFG_MAX_FLASH_BANKS 1 -#define CFG_MAX_FLASH_SECT 128 -#define CFG_FLASH_SECTOR_SIZE (64*1024) -#define CFG_FLASH_SIZE 0x00800000 +#define DEFAULT_FLASH_SIZE_IN_MB 16 #define BOARDCAL 0x9f7f0000 diff --git a/u-boot/include/configs/carambola2.h b/u-boot/include/configs/carambola2.h index 00fde6086c..0580d82e91 100644 --- a/u-boot/include/configs/carambola2.h +++ b/u-boot/include/configs/carambola2.h @@ -22,10 +22,7 @@ *----------------------------------------------------------------------- */ -#define CFG_MAX_FLASH_BANKS 1 -#define CFG_MAX_FLASH_SECT 256 -#define CFG_FLASH_SECTOR_SIZE (64*1024) -#define CFG_FLASH_SIZE 0x01000000 +#define DEFAULT_FLASH_SIZE_IN_MB 16 #define BOARDCAL 0x9fff0000 diff --git a/u-boot/include/configs/common.h b/u-boot/include/configs/common.h index ff6329ade9..54e908018e 100644 --- a/u-boot/include/configs/common.h +++ b/u-boot/include/configs/common.h @@ -5,6 +5,9 @@ * We boot from this flash */ #define CFG_FLASH_BASE 0x9f000000 +#define CFG_MAX_FLASH_SECT 4096 +#define CFG_MAX_FLASH_BANKS 1 +#define CFG_MAX_FLASH_SECT 256 #define CFG_CMD_SETMAC diff --git a/u-boot/include/configs/jb02v2-cb2.h b/u-boot/include/configs/jb02v2-cb2.h index 1c2a8ec562..3236501119 100644 --- a/u-boot/include/configs/jb02v2-cb2.h +++ b/u-boot/include/configs/jb02v2-cb2.h @@ -21,11 +21,8 @@ * FLASH and environment organization *----------------------------------------------------------------------- */ - -#define CFG_MAX_FLASH_BANKS 1 -#define CFG_MAX_FLASH_SECT 256 -#define CFG_FLASH_SECTOR_SIZE (64*1024) -#define CFG_FLASH_SIZE 0x01000000 + +#define DEFAULT_FLASH_SIZE_IN_MB 16 #define BOARDCAL 0x9fff0000 diff --git a/u-boot/include/configs/jb02v3-skw.h b/u-boot/include/configs/jb02v3-skw.h index f516ec7974..397a49390c 100644 --- a/u-boot/include/configs/jb02v3-skw.h +++ b/u-boot/include/configs/jb02v3-skw.h @@ -22,10 +22,7 @@ *----------------------------------------------------------------------- */ -#define CFG_MAX_FLASH_BANKS 1 -#define CFG_MAX_FLASH_SECT 256 -#define CFG_FLASH_SECTOR_SIZE (64*1024) -#define CFG_FLASH_SIZE 0x01000000 +#define DEFAULT_FLASH_SIZE_IN_MB 16 #define BOARDCAL 0x9fff0000 diff --git a/u-boot/include/flash.h b/u-boot/include/flash.h index 11285b4866..6921ab4114 100644 --- a/u-boot/include/flash.h +++ b/u-boot/include/flash.h @@ -31,6 +31,7 @@ typedef struct { ulong size; /* total bank size in bytes */ + ulong sector_size; /* size of erase unit in bytes */ ushort sector_count; /* number of erase units */ ulong flash_id; /* combined device & manufacturer code */ ulong start[CFG_MAX_FLASH_SECT]; /* physical sector start addresses */ @@ -418,6 +419,7 @@ extern void flash_read_factory_serial(flash_info_t * info, void * buffer, int of #define FLASH_M25P64 0x00F2 +#define FLASH_CUSTOM 0x1111 #define FLASH_UNKNOWN 0xFFFF /* unknown flash type */