diff --git a/cmd_parser.c b/cmd_parser.c index 86fa251..68a01f4 100644 --- a/cmd_parser.c +++ b/cmd_parser.c @@ -514,7 +514,7 @@ void cmd_parser(void) __banked } if (cmd_compare(0, "flash") && cmd_words_b[1] > 0 && cmd_buffer[cmd_words_b[1]] == 'e') { print_string("\nFLASH erase\n"); - flash_block_erase(0x20000); + flash_sector_erase(0x20000); } if (cmd_compare(0, "flash") && cmd_words_b[1] > 0 && cmd_buffer[cmd_words_b[1]] == 'w') { print_string("\nFLASH write\n"); diff --git a/rtl837x_flash.c b/rtl837x_flash.c index 566e25b..471116f 100644 --- a/rtl837x_flash.c +++ b/rtl837x_flash.c @@ -11,7 +11,16 @@ __xdata uint8_t dio_enabled; __xdata uint8_t markbuf[16]; extern __xdata uint16_t mpos; -#pragma codeseg BANK1 +// For the flash commands, see e.g. Windbond W25Q32JV datasheet +#define CMD_WRITE_STATUS 0x01 +#define CMD_PAGE_PROGRAM 0x02 +#define CMD_WRITE_ENABLE 0x06 +#define CMD_FREAD 0x0b +#define CMD_SECTOR_ERASE 0x20 +#define CMD_READ_SECURITY_REGS 0x48 +#define CMD_READ_UNIQUE_ID 0x4b +#define CMD_READ_JEDEC_ID 0x9f +#define CMD_FREAD_DIO 0xbb /* * Configure Memory Managed IO @@ -21,14 +30,14 @@ void flash_configure_mmio(void) // Set configuration for MMIO access by controller if (dio_enabled) { SFR_FLASH_MODEB = 0x18; - SFR_FLASH_CMD_R = 0xbb; // By default we read with Dual speed - SFR_FLASH_DUMMYCICLES = 4; + SFR_FLASH_CMD_R = CMD_FREAD_DIO; // By default we read with Dual speed + SFR_FLASH_DUMMYCYCLES = 4; return; } SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0xb; // By default we read with single speed - SFR_FLASH_DUMMYCICLES = 8; + SFR_FLASH_CMD_R = 0xb; // Default is Single IO + SFR_FLASH_DUMMYCYCLES = 8; } @@ -39,27 +48,26 @@ void flash_configure_mmio(void) * This configures fast single IO at 20.8 MHz when the CPU clock is at 20.8MHz * and 62.5MHz when the CPU clock is configured at 125MHz */ -void flash_init(uint8_t enable_dio) __banked +void flash_init(uint8_t enable_dio) { if (enable_dio) { - // Configure fast DIO via divider/DIO/SIOconfig = 4 and read-cmd being 0xbb (for mmio) SFR_FLASH_CONFIG = 9; // There may be a chip-select in here - SFR_FLASH_CONF_RCMD = 0xbb; + SFR_FLASH_CONF_RCMD = CMD_FREAD_DIO; SFR_FLASH_CONF_DIV = 4; } else { - // Configure fast read via divider = 8 and read-cmd being 0xb (for mmio) + // Configure fast read via divider = 8 and read-cmd being CMD_FREAD (for mmio) SFR_FLASH_CONFIG = 9; - SFR_FLASH_CONF_RCMD = 0xb; + SFR_FLASH_CONF_RCMD = CMD_FREAD; SFR_FLASH_CONF_DIV = 8; } // Test Controller Busy while(SFR_FLASH_EXEC_BUSY); // Write 0 to status register - SFR_FLASH_DUMMYCICLES = 8; + SFR_FLASH_DUMMYCYCLES = 8; SFR_FLASH_MODEB = 0; SFR_FLASH_TCONF = 0x19; - SFR_FLASH_CMD = 1; + SFR_FLASH_CMD = CMD_WRITE_STATUS; SFR_FLASH_DATA0 = 0; SFR_FLASH_EXEC_GO = 1; while(SFR_FLASH_EXEC_BUSY); @@ -86,14 +94,14 @@ uint8_t flash_read_status(void) } -void flash_read_uid(void) __banked +void flash_read_uid(void) { while (flash_read_status() & 0x1); // Set slow read mode for UID SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0x4b; - SFR_FLASH_DUMMYCICLES = 8; + SFR_FLASH_CMD_R = CMD_READ_UNIQUE_ID; + SFR_FLASH_DUMMYCYCLES = 8; // Transfer 4 bytes (command + 3 dummy bytes) SFR_FLASH_TCONF = 4; @@ -110,7 +118,7 @@ void flash_read_uid(void) __banked print_byte(SFR_FLASH_DATA24); SFR_FLASH_EXEC_GO = 1; - SFR_FLASH_DUMMYCICLES = 24; + SFR_FLASH_DUMMYCYCLES = 24; while(SFR_FLASH_EXEC_BUSY); print_byte(SFR_FLASH_DATA0); @@ -122,14 +130,14 @@ void flash_read_uid(void) __banked } -void flash_read_jedecid(void) __banked +void flash_read_jedecid(void) { while (flash_read_status() & 0x1); // Set read mode for JEDEC ID SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0x9f; - SFR_FLASH_DUMMYCICLES = 0; + SFR_FLASH_CMD_R = CMD_READ_JEDEC_ID; + SFR_FLASH_DUMMYCYCLES = 0; // Transfer 3 bytes back SFR_FLASH_TCONF = 0x13; @@ -144,12 +152,12 @@ void flash_read_jedecid(void) __banked // Reset slow read mode SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0xb; - SFR_FLASH_DUMMYCICLES = 8; + SFR_FLASH_CMD_R = CMD_FREAD; + SFR_FLASH_DUMMYCYCLES = 8; } -void flash_write_enable(void) __banked +void flash_write_enable(void) { short status; @@ -157,14 +165,16 @@ void flash_write_enable(void) __banked do { status = flash_read_status(); } while (status & 0x1); -// while (flash_read_status() & 0x1); SFR_FLASH_TCONF = 0x18; - SFR_FLASH_CMD = 6; -/* The following is explicitly set for SIO, is this necessary?: + SFR_FLASH_CMD = CMD_WRITE_ENABLE; + + /* The following makes sure that the PAGE_PROGRAM command, + * where the data to be written follows the command word directly + * works properly + */ SFR_FLASH_DUMMYCYCLES = 0; SFR_FLASH_MODEB = 0; -*/ SFR_FLASH_EXEC_GO = 1; // Wait for write status enabled @@ -174,7 +184,7 @@ void flash_write_enable(void) __banked } -void flash_dump(register uint32_t addr, register uint8_t len) __banked +void flash_dump(register uint32_t addr, register uint8_t len) { short status; do { @@ -185,12 +195,12 @@ void flash_dump(register uint32_t addr, register uint8_t len) __banked // Set fast read mode if (dio_enabled) { SFR_FLASH_MODEB = 0x18; - SFR_FLASH_CMD_R = 0xbb; - SFR_FLASH_DUMMYCICLES = 4; + SFR_FLASH_CMD_R = CMD_FREAD_DIO; + SFR_FLASH_DUMMYCYCLES = 4; } else { SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0xb; // Fast read - SFR_FLASH_DUMMYCICLES = 8; // Add 8 dummy clocks after read? + SFR_FLASH_CMD_R = CMD_FREAD; // Fast read + SFR_FLASH_DUMMYCYCLES = 8; // Add 8 dummy clocks after read? } // Read 4 bytes SFR_FLASH_TCONF = 4; @@ -222,7 +232,7 @@ void flash_dump(register uint32_t addr, register uint8_t len) __banked * Reads bulk data of length len from the flash memory starging at address src * and writes the data into a buffer pointed to by dst in XMEM */ -void flash_read_bulk(register __xdata uint8_t *dst, __xdata uint32_t src, register uint16_t len) __banked +void flash_read_bulk(register __xdata uint8_t *dst, __xdata uint32_t src, register uint16_t len) { short status; do { @@ -232,12 +242,12 @@ void flash_read_bulk(register __xdata uint8_t *dst, __xdata uint32_t src, regist // Set fast read mode if (dio_enabled) { SFR_FLASH_MODEB = 0x18; - SFR_FLASH_CMD_R = 0xbb; - SFR_FLASH_DUMMYCICLES = 4; + SFR_FLASH_CMD_R = CMD_FREAD_DIO; + SFR_FLASH_DUMMYCYCLES = 4; } else { SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0xb; // Fast read - SFR_FLASH_DUMMYCICLES = 8; // Add 8 dummy clocks after read? + SFR_FLASH_CMD_R = CMD_FREAD; // Fast read + SFR_FLASH_DUMMYCYCLES = 8; // Add 8 dummy clocks after read? } // Read 4 bytes SFR_FLASH_TCONF = 4; @@ -266,7 +276,7 @@ void flash_read_bulk(register __xdata uint8_t *dst, __xdata uint32_t src, regist } -void flash_find_mark(__xdata uint32_t src, register uint16_t len, __code uint8_t *mark) __banked +void flash_find_mark(__xdata uint32_t src, register uint16_t len, __code uint8_t *mark) { uint16_t status; do { @@ -276,12 +286,12 @@ void flash_find_mark(__xdata uint32_t src, register uint16_t len, __code uint8_t // Set fast read mode if (dio_enabled) { SFR_FLASH_MODEB = 0x18; - SFR_FLASH_CMD_R = 0xbb; - SFR_FLASH_DUMMYCICLES = 4; + SFR_FLASH_CMD_R = CMD_FREAD_DIO; + SFR_FLASH_DUMMYCYCLES = 4; } else { SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0xb; // Fast read - SFR_FLASH_DUMMYCICLES = 8; // Add 8 dummy clocks after read? + SFR_FLASH_CMD_R = CMD_FREAD; // Fast read + SFR_FLASH_DUMMYCYCLES = 8; // Add 8 dummy clocks after read? } uint8_t i = 0; @@ -348,14 +358,14 @@ void flash_find_mark(__xdata uint32_t src, register uint16_t len, __code uint8_t } -void flash_read_security(uint32_t addr, uint8_t len) __banked +void flash_read_security(uint32_t addr, uint8_t len) { while (flash_read_status() & 0x1); // Set slow read mode SFR_FLASH_MODEB = 0x0; - SFR_FLASH_CMD_R = 0x48; // read security register - SFR_FLASH_DUMMYCICLES = 8; // Add 8 dummy clocks as for fast read + SFR_FLASH_CMD_R = CMD_READ_SECURITY_REGS; // read security register + SFR_FLASH_DUMMYCYCLES = 8; // Add 8 dummy clocks as for fast read // Transfer 4 bytes (command + 3byte address) SFR_FLASH_TCONF = 4; @@ -384,11 +394,11 @@ void flash_read_security(uint32_t addr, uint8_t len) __banked } -void flash_block_erase(uint32_t addr) __banked +void flash_sector_erase(uint32_t addr) { flash_write_enable(); SFR_FLASH_TCONF = 8; - SFR_FLASH_CMD = 0x20; + SFR_FLASH_CMD = CMD_SECTOR_ERASE; SFR_FLASH_ADDR16 = addr >> 16; SFR_FLASH_ADDR8 = addr >> 8; @@ -402,14 +412,14 @@ void flash_block_erase(uint32_t addr) __banked } -void flash_write_bytes(__xdata uint32_t addr, __xdata uint8_t *ptr, uint16_t len) __banked +void flash_write_bytes(__xdata uint32_t addr, __xdata uint8_t *ptr, uint16_t len) { - static __xdata uint8_t exit_loop = 0; + uint8_t exit_loop = 0; while(1) { flash_write_enable(); - SFR_FLASH_CMD = 2; - SFR_FLASH_TCONF = 0x40 | 8 | 2; // Bytes written is is 4, 8 enables write, 0x2 is unkown + SFR_FLASH_CMD = CMD_PAGE_PROGRAM; + SFR_FLASH_TCONF = 0x40 | 8 | 4; // Bytes written is is 4, 8 enables write, 0x40 is unkown // Last transfer? if (len < 5) { SFR_FLASH_TCONF = 8 | len; diff --git a/rtl837x_flash.h b/rtl837x_flash.h index 8e44385..f891f97 100644 --- a/rtl837x_flash.h +++ b/rtl837x_flash.h @@ -1,14 +1,14 @@ #ifndef _RTL837X_FLASH_H_ #define _RTL837X_FLASH_H_ -void flash_init(uint8_t enable_dio) __banked; -void flash_read_uid(void) __banked; -void flash_write_enable(void)__banked ; -void flash_dump(register uint32_t addr, register uint8_t len) __banked; -void flash_read_jedecid(void) __banked; -void flash_read_security(uint32_t addr, uint8_t len)__banked ; -void flash_block_erase(uint32_t addr) __banked; -void flash_read_bulk(register __xdata uint8_t *dst, __xdata uint32_t src, register uint16_t len) __banked; -void flash_write_bytes(__xdata uint32_t addr, register __xdata uint8_t *ptr, register uint16_t len)__banked; -void flash_find_mark(__xdata uint32_t src, register uint16_t len, __code uint8_t *mark) __banked; +void flash_init(uint8_t enable_dio); +void flash_read_uid(void); +void flash_write_enable(void); +void flash_dump(register uint32_t addr, register uint8_t len); +void flash_read_jedecid(void); +void flash_read_security(uint32_t addr, uint8_t len); +void flash_sector_erase(uint32_t addr); +void flash_read_bulk(register __xdata uint8_t *dst, __xdata uint32_t src, register uint16_t len); +void flash_write_bytes(__xdata uint32_t addr, register __xdata uint8_t *ptr, register uint16_t len); +void flash_find_mark(__xdata uint32_t src, register uint16_t len, __code uint8_t *mark); #endif diff --git a/rtl837x_sfr.h b/rtl837x_sfr.h index 314ea33..9a99ac7 100644 --- a/rtl837x_sfr.h +++ b/rtl837x_sfr.h @@ -71,7 +71,7 @@ __sfr __at(0xbc) SFR_FLASH_CONFIG; __sfr __at(0x9b) SFR_FLASH_CONF_DIV; __sfr __at(0x9c) SFR_FLASH_CONF_RCMD; -__sfr __at(0x9d) SFR_FLASH_DUMMYCICLES; +__sfr __at(0x9d) SFR_FLASH_DUMMYCYCLES; __sfr __at(0x9a) SFR_FLASH_MODEB; __sfr __at(0x9e) SFR_FLASH_TCONF;