An 12384
An 12384
Contents
1 Abstract 1 Abstract................................................ 1
A simple Secondary Bootloader (SBL) software is designed in this application 2 Overview...............................................1
note. It can optionally load the new image from user UART terminal. The
3 Hardware platform based on
YModem file transfer protocol is used in this design to transfer the image file
LPC54608 MCU.................................. 1
from PC to the board. In-Application Programming (IAP) feature is used to
download the firmware's image to on-chip FLASH memory. The demo project 4 Software design................................... 3
is developed based on LPCXpresso54608 board and MCUXpresso SDK 5 Demonstration....................................15
Software Library.
2 Overview
SBL is a small piece of code immediately running after the hardware boot process. It works as the normal software, but only
dealing with some customized tasks before the user software, for example to do some previous configuration for the user system.
It exists like the normal bootloader which is kept in ROM and used to boot the system, but can execute the additional customized
booting task following the normal (first) bootloader. The Secondary Bootloader is still a part of software. So, it is more flexible than
the ROM bootloader which is stable and can not modified by customer.
In this application note, a simple SBL software is designed to optionally load the new image file from user UART terminal and
keep it in the on-chip flash memory for next run. Therefore, the design is also called UART Flashloader with IAP. The YModel
file transfer protocol is used in this design to send the binary image file from PC to the board. The demo project is developed
based on LPCXpresso54608 board and MCUXpresso SDK Software Library.
0x0000 0000 to 0x1FFF FFFF On-chip non-volatile memory 0x0000 0000-0x0007 FFFF Flash memory (512 KB)
Boot ROM 0x0300 0000-0x0300 FFFF Boot ROM with flash services
in a 64 KB space
SPI Flash Interface (SPIFI) 0x1000 0000-0x17FF FFFF SPIFI memory mapped
access space (128 MB)
0x2000 0000 to 0x3FFF FFFF SRAM bank 0x2000 0000-0x2002 7FFF SRAM bank (160 KB)
SRAM bit band alias 0x2200 0000-0x23FF FFFF SRAM bit band alias
addressing addressing (32 MB)
The 512-KB programmable FLASH is mapped to the address from start to 0x0007_FFFF, and the SRAM are mapped to three
parts:
• the 32 KB SRAMX from 0x0400_0000 to 0x0400_7FFF,
• the 160 KB normal SRAM from 0x2000_0000 to 0x2002_7FFF,
• the 8 KB USB SRAM from 0x4010_0000 to 0x4010_1FFC (not listed in Table 1. Flash memory summarization on page 1).
For the on-chip FLASH memory, it can be performed erase and write operations directly by the end-user application through the
IAP. Some IAP commands operate on sectors and specify sector numbers.The size of a sector is 32 KB (a normal size for an
erase operation) and the size of a page is 256 Byte (the minimal size for a write operation). One sector contains 128 pages. Sector
0 and page 0 are located at address 0x0000_0000. Table 2. Mapping between sector and address on page 2 descirbes the
mapping between sector number and address.
Sector number Sector size Page numbers Address range Total flash (including this
sector)
To erase and write the on-chip FLASH in user application code, NXP MCUXpresso SDK Software Library already provides the
IAP driver. The IAP driver would be used to handle the on-chip FLASH in this application demo.
In this application demo, the LPCXpresso54608 Board with the LPC54608J512BD208 chip is used to run the executable image
and verify the software.
4 Software design
SCB->VTOR = fwImageBaseAddr; /* The stack address is also the start address of vector. */
__set_MSP(fwStackVal); /* setup the stack address for MSP. */
__set_PSP(fwStackVal); /* setpu the stack address for PSP. */
firmwareFunc();
}
Keil IDE does not output the bin file directly, but the user command in Keil can be processed within the post build action:
On the User tab of the Options for Target dialog box, fill the command into the After Build/Rebuild section and check the box
to enable it, as shown in Figure 1. on page 4.
Do not forget to change the original generated image file's name with axf as post-fix in the Outputtab, as shown in Figure 2. on
page 5.
Then, once the project is built, an executable bin file is generated and updated automatically for every rebuild..
Taking the hello_world project as an example, its executable bin file is as shown in Figure 3. on page 6.
The SBL and user software are both running inside the MCU, so the arrangement of these two parts of software is necessary.
SBL starts following the chip hardware booting. Its code is placed from the address 0x0000_0000, so the chip can recognize and
boot it automatically by default. Then, to facilitate the operation to FLASH, a whole sector of 32 KB memory is reserved for the
SBL. All the other memory of FLASH is for the user firmware.
The arrangement of these address settings are defined in the demo code.
Keep the firmware version information in the unused vector items. Arm reserves 256 vectors for Cortex-M4's vector table with 1
KB memory space, but not all the 256 vectors are implemented for a specific chip. For the LPC54608 MCU, only 73 vectors are
used, while the tailing 652 Byte are spare in the vector table. In this application demo, the tailing 32 bytes are used to record the
file name of the user firmware.
Figure 4. on page 7 shows the binary image files generated from the SBL software and the modified hello_world demo project
in MCUXpresso SDK software library.
• The FLASH with the address lower than 0x0000_8000 is all 0xFF. The memory is just erased for SBL space but not used.
• The FLASH with the address beginning from 0x0000_8000 is for the user firmware.
• The FLASH with the address between 0x0000_8000 and 0x0000_8400 is for user firmware's vector table with the length of
1 KB. Only the front items are used as the exeception/interrupt function's entries. The memory for unused vectors is all
zero.
• The FLASH with the address between 0x0000_83E0 and 0x0000_8400 are the tailing 16 bytes in user firmware's vector
table. In this application demo, the memory is used to keep the firmware's file name. As shown in Figure 4. on page 7,
0x68, 0x65, 0x6C, 0x6C, 0x6F, 0x5F, 0x77, 0x6F, 0x72, 0x6C, 0x64, 0x5F, 0x30, 0x31, 0x30, 0x32, 0x2E, 0x62, 0x69, and
0x6E are just the ASICC codes for the string of hello_world_0102.bin.
The SBL project's memory mapping is similar to the normal project, which starts the image address from 0x0000_0000, and no
additional setting is needed. As the image of the user firmware project starts from 0x0000_8000 (sector 1), perform the following
steps to modify its linker configurations.
1. Update the linker file.
Add an address offset of m_bootloader_offset to reserve the space for bootloader, as shown in Figure 5. on page 8.
After the modifications, the user firmware's image may not be downloaded into the chip with the IDE's debug tool. It cannot be
debugged unless the 2nd bootloader exists inside the chip.
• If the 2nd bootloader is not ready yet, when entering the debug demo, the chip boots from the address of 0x0000_0000,
but the available code in current project starts from 0x0000_8000, so the chip can run to current firmware.
• If the 2nd bootloader is ready, the chip boots from the address of 0x0000_0000, the 2nd bootloader can help to jump to the
current firmware, and then the debugger can monitor the statement and catch the break point for the current project.
YModem is a general file transfer protocol for transferring files between PC and embedded system in the embedded development.
It is fast and high-efficient to transfer the file with CRC check to make sure the data is right. Also, the receiver sends the ACK to
the sender for next package when it is ready to catch that one, and the data stream is under control. It is a typical way to implement
the bootloader for MCU as well.
YMODEM-1K uses a block size of one kilobyte instead of the standard 128 bytes. 1 K-blocks is an option in the original YMODEM
standard, but this variant neglects the rest of the features, and is best described as a 1 k variant of XMODEM.
In this application demo, a YModem protocol component is created for general use cases. As this component is coded with a
pure C language, it can be easily ported to other embedded system.
In the YModem component, xymodem.h/xymodem.c files process the protocol interaction, and users implement the two functions
based on the specific hardware platform in the xymodem_port.c file.
• void XYModem_Uart_SendByte(unsigned char ch)
This function sends out a byte of unsigned char ch through the user USART channel. In the application demo code, this
function is implemented with the polling method to send out the character through the Terminal UART (USART0).
• int XYModem_Uart_RecvByteTimeout(unsigned char *ch)
This function receives a byte in an indicated time period (defined in the implementation but not as parameter). It returns 1 if
this function runs timeout with no available data received, returns 0 if the new available data received in time and the received
data is returned through pointer unsigned char * ch. In the application demo code, this receiving function is implemented
with the a hardware timer (RIT) a USART receiver working in interrupt mode and a ring FIFO to buffer the receiving data.
When using this function to read a data, the timer and the FIFO (connect to the receiver) are enabled together. Either for the
event that the timer runs timeout or there is any available received data in the FIFO, this function will return and tell the return
event.
In the xymodem_port.c file:
/*
* send byte "ch".
*/
void XYModem_Uart_SendByte(unsigned char ch)
{
Terminal_PutChar(ch);
}
/*
* return 1 if timeout without available received data.
* return 0 if data is available before timeout.
*/
int XYModem_Uart_RecvByteTimeout(unsigned char *ch)
{
return Terminal_GetCharTimeout(ch, 1000u) ? 0 : 1;
}
/* setup uart. */
USART_GetDefaultConfig(&usartConfigStruct);
usartConfigStruct.baudRate_Bps = baudrate;
usartConfigStruct.enableRx = true;
usartConfigStruct.enableTx = true;
usartConfigStruct.txWatermark = kUSART_TxFifo0;
usartConfigStruct.rxWatermark = kUSART_RxFifo1;
USART_Init(USART0, &usartConfigStruct, CLOCK_GetFreq(kCLOCK_Flexcomm0));
/* rx available interrupt. */
if (kUSART_RxFifoNotEmptyFlag == (kUSART_RxFifoNotEmptyFlag & flags) )
{
rxDat = USART_ReadByte(USART0);
if ( !RBUF_IsFull(&gAppTerUartRxFifoHandle) )
{
RBUF_PutDataIn(&gAppTerUartRxFifoHandle, rxDat);
}
}
USART_ClearStatusFlags(USART0, flags);
}
flags = RIT_GetStatusFlags(RIT);
bAppRitTimeout = true;
RIT_ClearStatusFlags(RIT, flags);
RIT_StopTimer(RIT); /* for one time trigger. */
}
Most terminal softwares integrate the YModem protocol, so there is no need to build a special desktop software for communicating
with MCU. In this application demo, the Tera Term software is used as the desktop terminal software on PC. Select File ->
Transfer -> YMODEM -> Send... to activate the window for transferring the given file, as shown in Figure 7. on page 13.
• status_t IAP_Compare(uint32_t dstAddr, uint32_t *srcAddr, uint32_t numOfBytes): to check whether the
FLASH is really written after the write operation.
In the demo code, SBL software knows the length of firmware image according to the first package of YModem transfer, erases
enough FLASH sectors for the coming image data, and then writes binary data to FLASH when receiving a new package.
gAppFwWriteImageLen = gAppModemStruct.filelen;
gAppFwWriteSectorStart = BOOT_FIRMWARE_BASE_ADDRESS / FSL_FEATURE_SYSCON_FLASH_SECTOR_SIZE_BYTES;
gAppFwWriteSectorCount = (gAppFwWriteImageLen + FSL_FEATURE_SYSCON_FLASH_SECTOR_SIZE_BYTES-1) /
FSL_FEATURE_SYSCON_FLASH_SECTOR_SIZE_BYTES;
if (gAppModemStruct.cur_num == 1u) /* the first package would include the firmware info. */
{
/* copy the file name of firmware into the image. */
strcpy( (char *)(gAppModemStruct.buf+BOOT_FIRMWARE_INFO_OFFSET), (char
*)gAppModemStruct.filename);
}
if (errIAP != kStatus_IAP_Success)
{
err = 10;
}
Considering the package is error and will be re-sent from the host, though the auto-creasing mode is simpler, the SBL uses the
package index to get the writing sector index and the address instead.
Prepare the sector before the write operation, and Compare or Check the written data from FLASH after the write operation.
5 Demonstration
The SBL project and the modifed hello_world and rit_example demo projects from MCUXpresso SDK software library are
packed alone with this application note. The projects are originally developed with Keil IDE, but can be easily ported to other IAR
IDE like MCUXpresso IDE or IAR IDE. The demo projects are originally verified on the LPCXpresso54608 board. The following
introduces how to run the demo.
1. Connect the board debug port to PC with a USB cable.
2. Prepare the user firmware's binary image file.
• Any existing project for LPC54608 is OK to be a base project. In this application note, the hello_world demo is
used as it is considerted as the simplest demo project in the software library and the rit_example demo is used as
it enables the interrupt event.
• Change their linker configurations by following the guide in Compiler link configuration on page 8.
• Add the user command for generating the binary image file.
• Build the project and get the binary image file.
3. Download the SBL project.
• Build the SBL project and download it through IDE. Other downloading way, like debug operation or command line
tool, is available.
4. Launch the YModem to download the image.
• Execute the Tera Term to open the UART port to LPCXpresso54608 with 115200 baudrate, no parity, 1 stop bit.
• Reset the board, and a question is printed to the UART terminal. The SBL will wait for the input for about five
seconds, as shown in Figure 8. on page 16.
— For no input, it jumps to the per-downloaded user firmware automatically.
— For input n, it jumps to the pre-downloaded user firmware immediately.
— For input y, it starts the YModem communication immediately and wait to get a new firmware image file.
• Send the prepared user firmware image file using the YModem tool of Tera Term, by following the guide in PC:
Send file through YModem as host on page 12. Then the progress bar appears in the dialog window, as shown in
Figure 10. on page 17.
You can try to download another prepared firmware (for example, using rit_example.bin) to see whether the new firmware can
be executed. Of course, it works.
While NXP has implemented advanced security features, all products may be subject to
unidentified vulnerabilities. Customers are responsible for the design and operation of their
applications and products to reduce the effect of these vulnerabilities on customer’s applications
and products, and NXP accepts no liability for any vulnerability that is discovered. Customers
should implement appropriate design and operating safeguards to minimize the risks associated
with their applications and products.
NXP, the NXP logo, NXP SECURE CONNECTIONS FOR A SMARTER WORLD, COOLFLUX,
EMBRACE, GREENCHIP, HITAG, I2C BUS, ICODE, JCOP, LIFE VIBES, MIFARE, MIFARE
CLASSIC, MIFARE DESFire, MIFARE PLUS, MIFARE FLEX, MANTIS, MIFARE ULTRALIGHT,
MIFARE4MOBILE, MIGLO, NTAG, ROADLINK, SMARTLX, SMARTMX, STARPLUG, TOPFET,
TRENCHMOS, UCODE, Freescale, the Freescale logo, AltiVec, C‑5, CodeTEST, CodeWarrior,
ColdFire, ColdFire+, C‑Ware, the Energy Efficient Solutions logo, Kinetis, Layerscape, MagniV,
mobileGT, PEG, PowerQUICC, Processor Expert, QorIQ, QorIQ Qonverge, Ready Play,
SafeAssure, the SafeAssure logo, StarCore, Symphony, VortiQa, Vybrid, Airfast, BeeKit,
BeeStack, CoreNet, Flexis, MXC, Platform in a Package, QUICC Engine, SMARTMOS, Tower,
TurboLink, and UMEMS are trademarks of NXP B.V. All other product or service names are the
property of their respective owners. AMBA, Arm, Arm7, Arm7TDMI, Arm9, Arm11, Artisan,
big.LITTLE, Cordio, CoreLink, CoreSight, Cortex, DesignStart, DynamIQ, Jazelle, Keil, Mali,
Mbed, Mbed Enabled, NEON, POP, RealView, SecurCore, Socrates, Thumb, TrustZone, ULINK,
ULINK2, ULINK-ME, ULINK-PLUS, ULINKpro, µVision, Versatile are trademarks or registered
trademarks of Arm Limited (or its subsidiaries) in the US and/or elsewhere. The related
technology may be protected by any or all of patents, copyrights, designs and trade secrets. All
rights reserved. Oracle and Java are registered trademarks of Oracle and/or its affiliates. The
Power Architecture and Power.org word marks and the Power and Power.org logos and related
marks are trademarks and service marks licensed by Power.org.