I am trying to re-invoke the USB ISP bootloader using the IAP method on the LPCXpresso5411x.
As stated in LPC51U68-Reinvoke-ISP-in-USB-Mode-is-not-working the IAP_ReinvokeISP() method is broken in two ways:
- The ispType parameter (=2 for USB) is handled incorrectly (at least for this chip)
- Calling __disable_irq(); before IAP breaks the USB bootloader
Apparently there are some prerequisites for the USB bootloader to operate property, but I cannot find any documentation on this:
- The main clock must be configured as 48MHz from FRO?
- IRQs must not be disabled?
- ...?
So when using a clock setup with 48MHz FRO as main and manually calling the IAP entry point, the USB bootloader indeed works as expected.
However, setting up a higher clock rate for my main application and switching back to 48MHz before making the IAP call doesn't work for me. The USB device is not responsive from the perspective of the OS.
[[noreturn]] int main() {
BOARD_InitBootPins();
BOARD_BootClock98MHz(); // <- this line breaks the USB bootloader
BOARD_BootClock48MHz();
fixed_IAP_Reinvoke_ISP_USB();
The BOARD_BootClockX methods are created using the IDE clock tool:
void BOARD_BootClock98MHz(void)
{
#ifndef SDK_SECONDARY_CORE
/*!< Set up the clock sources */
/*!< Set up FRO */
POWER_DisablePD(kPDRUNCFG_PD_FRO_EN); /*!< Ensure FRO is on */
CLOCK_SetupFROClocking(12000000U); /*!< Set up FRO to the 12 MHz, just for sure */
CLOCK_AttachClk(kFRO12M_to_MAIN_CLK); /*!< Switch to FRO 12MHz first to ensure we can change voltage without accidentally
being below the voltage for current speed */
POWER_SetVoltageForFreq(96000000U); /*!< Set voltage for the one of the fastest clock outputs: System clock output */
CLOCK_SetFLASHAccessCyclesForFreq(96000000U); /*!< Set FLASH wait states for core */
CLOCK_SetupFROClocking(96000000U); /*!< Set up high frequency FRO output to selected frequency */
/*!< Set up dividers */
CLOCK_SetClkDiv(kCLOCK_DivAhbClk, 1U, false); /*!< Set AHBCLKDIV divider to value 1 */
/*!< Set up clock selectors - Attach clocks to the peripheries */
CLOCK_AttachClk(kFRO_HF_to_MAIN_CLK); /*!< Switch MAIN_CLK to FRO_HF */
/*< Set SystemCoreClock variable. */
SystemCoreClock = BOARD_BOOTCLOCK98MHZ_CORE_CLOCK;
#endif
}
So the question is, are there any other particular system states that must be enabled/disabled/reset for the USB bootloader to operate properly?