mirror of
https://git.codelinaro.org/clo/qsdk/oss/boot/u-boot-2016.git
synced 2025-12-10 07:44:53 +01:00
sf: Update sf to support all sizes of flashes
Updated the spi_flash framework to handle all sizes of flashes using bank/extd addr reg facility The current implementation in spi_flash supports 3-byte address mode due to this up to 16Mbytes amount of flash is able to access for those flashes which has an actual size of > 16MB. As most of the flashes introduces a bank/extd address registers for accessing the flashes in 16Mbytes of banks if the flash size is > 16Mbytes, this new scheme will add the bank selection feature for performing write/erase operations on all flashes. Signed-off-by: Jagannadha Sutradharudu Teki <jaganna@xilinx.com> Reviewed-by: Simon Glass <sjg@chromium.org>
This commit is contained in:
parent
e612ddf593
commit
e3ff9d51ec
1 changed files with 26 additions and 13 deletions
|
|
@ -74,11 +74,9 @@ int spi_flash_cmd_write_multi(struct spi_flash *flash, u32 offset,
|
||||||
unsigned long page_addr, byte_addr, page_size;
|
unsigned long page_addr, byte_addr, page_size;
|
||||||
size_t chunk_len, actual;
|
size_t chunk_len, actual;
|
||||||
int ret;
|
int ret;
|
||||||
u8 cmd[4];
|
u8 cmd[4], bank_sel;
|
||||||
|
|
||||||
page_size = flash->page_size;
|
page_size = flash->page_size;
|
||||||
page_addr = offset / page_size;
|
|
||||||
byte_addr = offset % page_size;
|
|
||||||
|
|
||||||
ret = spi_claim_bus(flash->spi);
|
ret = spi_claim_bus(flash->spi);
|
||||||
if (ret) {
|
if (ret) {
|
||||||
|
|
@ -88,6 +86,16 @@ int spi_flash_cmd_write_multi(struct spi_flash *flash, u32 offset,
|
||||||
|
|
||||||
cmd[0] = CMD_PAGE_PROGRAM;
|
cmd[0] = CMD_PAGE_PROGRAM;
|
||||||
for (actual = 0; actual < len; actual += chunk_len) {
|
for (actual = 0; actual < len; actual += chunk_len) {
|
||||||
|
bank_sel = offset / SPI_FLASH_16MB_BOUN;
|
||||||
|
|
||||||
|
ret = spi_flash_cmd_bankaddr_write(flash, bank_sel);
|
||||||
|
if (ret) {
|
||||||
|
debug("SF: fail to set bank%d\n", bank_sel);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
|
page_addr = offset / page_size;
|
||||||
|
byte_addr = offset % page_size;
|
||||||
chunk_len = min(len - actual, page_size - byte_addr);
|
chunk_len = min(len - actual, page_size - byte_addr);
|
||||||
|
|
||||||
if (flash->spi->max_write_size)
|
if (flash->spi->max_write_size)
|
||||||
|
|
@ -117,11 +125,7 @@ int spi_flash_cmd_write_multi(struct spi_flash *flash, u32 offset,
|
||||||
if (ret)
|
if (ret)
|
||||||
break;
|
break;
|
||||||
|
|
||||||
byte_addr += chunk_len;
|
offset += chunk_len;
|
||||||
if (byte_addr == page_size) {
|
|
||||||
page_addr++;
|
|
||||||
byte_addr = 0;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
spi_release_bus(flash->spi);
|
spi_release_bus(flash->spi);
|
||||||
|
|
@ -204,9 +208,9 @@ int spi_flash_cmd_wait_ready(struct spi_flash *flash, unsigned long timeout)
|
||||||
|
|
||||||
int spi_flash_cmd_erase(struct spi_flash *flash, u32 offset, size_t len)
|
int spi_flash_cmd_erase(struct spi_flash *flash, u32 offset, size_t len)
|
||||||
{
|
{
|
||||||
u32 end, erase_size;
|
u32 erase_size;
|
||||||
int ret;
|
int ret;
|
||||||
u8 cmd[4];
|
u8 cmd[4], bank_sel;
|
||||||
|
|
||||||
erase_size = flash->sector_size;
|
erase_size = flash->sector_size;
|
||||||
if (offset % erase_size || len % erase_size) {
|
if (offset % erase_size || len % erase_size) {
|
||||||
|
|
@ -224,11 +228,17 @@ int spi_flash_cmd_erase(struct spi_flash *flash, u32 offset, size_t len)
|
||||||
cmd[0] = CMD_ERASE_4K;
|
cmd[0] = CMD_ERASE_4K;
|
||||||
else
|
else
|
||||||
cmd[0] = CMD_ERASE_64K;
|
cmd[0] = CMD_ERASE_64K;
|
||||||
end = offset + len;
|
|
||||||
|
|
||||||
while (offset < end) {
|
while (len) {
|
||||||
|
bank_sel = offset / SPI_FLASH_16MB_BOUN;
|
||||||
|
|
||||||
|
ret = spi_flash_cmd_bankaddr_write(flash, bank_sel);
|
||||||
|
if (ret) {
|
||||||
|
debug("SF: fail to set bank%d\n", bank_sel);
|
||||||
|
return ret;
|
||||||
|
}
|
||||||
|
|
||||||
spi_flash_addr(offset, cmd);
|
spi_flash_addr(offset, cmd);
|
||||||
offset += erase_size;
|
|
||||||
|
|
||||||
debug("SF: erase %2x %2x %2x %2x (%x)\n", cmd[0], cmd[1],
|
debug("SF: erase %2x %2x %2x %2x (%x)\n", cmd[0], cmd[1],
|
||||||
cmd[2], cmd[3], offset);
|
cmd[2], cmd[3], offset);
|
||||||
|
|
@ -244,6 +254,9 @@ int spi_flash_cmd_erase(struct spi_flash *flash, u32 offset, size_t len)
|
||||||
ret = spi_flash_cmd_wait_ready(flash, SPI_FLASH_PAGE_ERASE_TIMEOUT);
|
ret = spi_flash_cmd_wait_ready(flash, SPI_FLASH_PAGE_ERASE_TIMEOUT);
|
||||||
if (ret)
|
if (ret)
|
||||||
goto out;
|
goto out;
|
||||||
|
|
||||||
|
offset += erase_size;
|
||||||
|
len -= erase_size;
|
||||||
}
|
}
|
||||||
|
|
||||||
out:
|
out:
|
||||||
|
|
|
||||||
Loading…
Add table
Reference in a new issue