From: Nathael Pajani Date: Mon, 21 May 2012 17:13:32 +0000 (+0200) Subject: Adding flash_target support to prog X-Git-Tag: v1.0~16 X-Git-Url: http://git.techno-innov.fr/?a=commitdiff_plain;h=7e4cf16a5cda702df67635896e1e46c5bee9975c;p=soft%2Ftools%2Flpctools Adding flash_target support to prog --- diff --git a/prog_commands.c b/prog_commands.c index 0184321..5a268e6 100644 --- a/prog_commands.c +++ b/prog_commands.c @@ -14,7 +14,7 @@ #include /* printf, snprintf */ #include #include -#include /* strncmp */ +#include /* strncmp, memset */ #include #include @@ -151,10 +151,120 @@ int start_prog(struct part_desc* part) } +static unsigned int calc_write_size(unsigned int sector_size, unsigned int ram_buff_size) +{ + unsigned int write_size = 0; + + write_size = ((sector_size < ram_buff_size) ? sector_size : ram_buff_size); + /* According to section 21.5.7 of LPC11xx user's manual (UM10398), number of bytes + * written should be 256 | 512 | 1024 | 4096 */ + if (write_size >= 4096) { + write_size = 4096; + } else if (write_size >= 1024) { + write_size = 1024; + } else if (write_size >= 512) { + write_size = 512; + } else if (write_size >= 256) { + write_size = 256; + } else { + write_size = 0; + } + return write_size; +} + int flash_target(struct part_desc* part, char* filename, int check) { int ret = 0; + char* data = NULL; + int size = 0; + int i = 0, blocks = 0; + unsigned int write_size = 0; + unsigned int sector_size = (part->flash_size / part->flash_nb_sectors); + uint32_t ram_addr = (part->ram_base + part->ram_buff_offset); + + /** Sanity checks *********************************/ + /* RAM buffer address within RAM */ + if (ram_addr > (part->ram_base + part->ram_size)) { + printf("Invalid configuration, asked to use buffer out of RAM, aborting.\n"); + return -1; + } + /* Calc write block size */ + write_size = calc_write_size(sector_size, part->ram_buff_size); + if (write_size == 0) { + printf("Config error, I cannot flash using blocks of nul size !\nAborted.\n"); + return -2; + } + + /* Just make sure flash is erased */ + ret = erase_flash(part); + if (ret != 0) { + printf("Unable to erase device, aborting.\n"); + return -4; + } + + /* Allocate a buffer as big as the flash */ + data = malloc(part->flash_size); + if (data == NULL) { + printf("Unable to get a buffer to load the image!"); + return -5; + } + /* And fill the buffer with the image */ + size = isp_file_to_buff(data, part->flash_size, filename); + if (size <= 0){ + free(data); + return -6; + } + /* Fill unused buffer with 0's so we can flash blocks of data of "write_size" */ + memset(&data[size], 0, (part->flash_size - size)); + blocks = (size / write_size) + ((size % write_size) ? 1 : 0); + /* Gonna write out of flash ? */ + if ((blocks * write_size) > part->flash_size) { + printf("Config error, I cannot flash beyond end of flash !\n"); + printf("Flash size : %d, trying to flash %d blocks of %d bytes : %d\n", + part->flash_size, blocks, write_size, (blocks * write_size)); + free(data); + return -3; + } + printf("Flash size : %d, trying to flash %d blocks of %d bytes : %d\n", + part->flash_size, blocks, write_size, (blocks * write_size)); + + /* Now flash the device */ + printf("Writing started, %d blocks of %d bytes ...\n", blocks, write_size); + for (i=0; iflash_base + (i * write_size); + /* Prepare sector for writting (must be done before each write) */ + ret = isp_send_cmd_sectors("prepare-for-write", 'P', current_sector, current_sector, 1); + if (ret != 0) { + printf("Error (%d) when trying to prepare sector %d for erase operation!\n", ret, i); + free(data); + return ret; + } + /* Send data to RAM */ + ret = isp_send_buf_to_ram(&data[i * write_size], ram_addr, write_size); + if (ret != 0) { + printf("Unable to perform write-to-ram operation for block %d (block size: %d)\n", + i, write_size); + free(data); + return ret; + } + /* Copy from RAM to FLASH */ + ret = isp_send_cmd_address('C', flash_addr, ram_addr, write_size, "write_to_ram"); + if (ret != 0) { + printf("Unable to copy data to flash for block %d (block size: %d)\n", i, write_size); + free(data); + return ret; + } + } + + /* And check if asked */ + if (check == 1) { + free(data); + return 0; + } + + free(data); return ret; }