Flash/LPC2000: Add support for LPC11(x)xx, LPC13xx

LPC11(x)xx and LPC13xx devices are mostly compatible with the lpc1700
variant of the LPC2000 driver, but use a fixed flash sector size of 4KB.

Change-Id: I033515f4ff6bc61d3b9babd27096f78c99cea927
Signed-off-by: Cosmin Gorgovan <cosmin@linux-geek.org>
Reviewed-on: http://openocd.zylin.com/2071
Tested-by: jenkins
Reviewed-by: Paul Fertser <fercerpav@gmail.com>
__archive__
Cosmin Gorgovan 2014-03-29 19:20:08 +00:00 committed by Andreas Fritiofson
parent 7bcf1d838d
commit 99d440cbba
2 changed files with 46 additions and 4 deletions

View File

@ -5173,9 +5173,10 @@ supported.}
@end deffn
@deffn {Flash Driver} lpc2000
Most members of the LPC1700, LPC1800, LPC2000 and LPC4300 microcontroller
families from NXP include internal flash and use Cortex-M3 (LPC1700, LPC1800),
Cortex-M4 (LPC4300) or ARM7TDMI (LPC2000) cores.
All members of the LPC11(x)00 and LPC1300 microcontroller families and most members
of the LPC1700, LPC1800, LPC2000 and LPC4300 microcontroller families from NXP
include internal flash and use Cortex-M0 (LPC11(x)00), Cortex-M3 (LPC1300, LPC1700,
LPC1800), Cortex-M4 (LPC4300) or ARM7TDMI (LPC2000) cores.
@quotation Note
There are LPC2000 devices which are not supported by the @var{lpc2000}
@ -5192,8 +5193,9 @@ which must appear in the following order:
@option{lpc2000_v1} (older LPC21xx and LPC22xx)
@option{lpc2000_v2} (LPC213x, LPC214x, LPC210[123], LPC23xx and LPC24xx)
@option{lpc1700} (LPC175x and LPC176x)
or @option{lpc4300} - available also as @option{lpc1800} alias (LPC18x[2357] and
@option{lpc4300} - available also as @option{lpc1800} alias (LPC18x[2357] and
LPC43x[2357])
or @option{lpc1100} (LPC11(x)xx and LPC13xx)
@item @var{clock_kHz} ... the frequency, in kiloHertz,
at which the core is running
@item @option{calc_checksum} ... optional (but you probably want to provide this!),

View File

@ -65,6 +65,16 @@
*
* lpc800:
* - 810 | 1 | 2 (tested with LPC810/LPC812)
*
* lpc1100:
* - 11xx
* - 11Axx
* - 11Cxx
* - 11Dxx
* - 11Exx
* - 11Uxx (tested with LPC11U34)
* - 131x
* - 134x
*/
typedef enum {
@ -73,6 +83,7 @@ typedef enum {
lpc1700,
lpc4300,
lpc800,
lpc1100,
} lpc2000_variant;
struct lpc2000_flash_bank {
@ -329,6 +340,25 @@ static int lpc2000_build_sector_list(struct flash_bank *bank)
bank->sectors[i].is_protected = 1;
}
} else if (lpc2000_info->variant == lpc1100) {
if ((bank->size % (4 * 1024)) != 0) {
LOG_ERROR("BUG: unknown bank->size encountered,\nLPC1100 flash size must be a multiple of 4096");
exit(-1);
}
lpc2000_info->cmd51_max_buffer = 512; /* smallest MCU in the series, LPC1110, has 1 kB of SRAM */
bank->num_sectors = bank->size / 4096;
bank->sectors = malloc(sizeof(struct flash_sector) * bank->num_sectors);
for (int i = 0; i < bank->num_sectors; i++) {
bank->sectors[i].offset = offset;
/* all sectors are 4kB-sized */
bank->sectors[i].size = 4 * 1024;
offset += bank->sectors[i].size;
bank->sectors[i].is_erased = -1;
bank->sectors[i].is_protected = 1;
}
} else {
LOG_ERROR("BUG: unknown lpc2000_info->variant encountered");
exit(-1);
@ -360,6 +390,7 @@ static int lpc2000_iap_working_area_init(struct flash_bank *bank, struct working
/* write IAP code to working area */
switch (lpc2000_info->variant) {
case lpc800:
case lpc1100:
case lpc1700:
case lpc4300:
target_buffer_set_u32(target, jump_gate, ARMV4_5_T_BX(12));
@ -397,6 +428,7 @@ static int lpc2000_iap_call(struct flash_bank *bank, struct working_area *iap_wo
switch (lpc2000_info->variant) {
case lpc800:
case lpc1100:
case lpc1700:
armv7m_info.common_magic = ARMV7M_COMMON_MAGIC;
armv7m_info.core_mode = ARM_MODE_THREAD;
@ -448,6 +480,7 @@ static int lpc2000_iap_call(struct flash_bank *bank, struct working_area *iap_wo
switch (lpc2000_info->variant) {
case lpc800:
case lpc1100:
case lpc1700:
case lpc4300:
/* IAP stack */
@ -601,6 +634,13 @@ FLASH_BANK_COMMAND_HANDLER(lpc2000_flash_bank_command)
lpc2000_info->cmd51_can_8192b = 0;
lpc2000_info->checksum_vector = 7;
lpc2000_info->iap_max_stack = 148;
} else if (strcmp(CMD_ARGV[6], "lpc1100") == 0) {
lpc2000_info->variant = lpc1100;
lpc2000_info->cmd51_dst_boundary = 256;
lpc2000_info->cmd51_can_256b = 1;
lpc2000_info->cmd51_can_8192b = 0;
lpc2000_info->checksum_vector = 7;
lpc2000_info->iap_max_stack = 128;
} else {
LOG_ERROR("unknown LPC2000 variant: %s", CMD_ARGV[6]);
free(lpc2000_info);