Debug without blowing efuses / setting efuses from J-Link?

キャンセル
次の結果を表示 
表示  限定  | 次の代わりに検索 
もしかして: 

Debug without blowing efuses / setting efuses from J-Link?

ソリューションへジャンプ
3,075件の閲覧回数
nplayle
Contributor I

Hi, 

 

We have a custom board using an RT1064. Both BOOT_MODE[1:0] are floating, which per the reference manual should result in defaulting to the efuse pins. 

We have an issue where I cannot debug a program loaded via J-Link. When I pause the debugger, I get various addresses around 0x21aadc which is in the internal ROM. My best guess is that since we have not yet programmed the efuses and BT_FUSE_SEL = 0, that the device is booting directly to the serial downloader. 

This is rather problematic. We are using USB2 and the LPUART1 is being used as ADC pins, so we cannot access the serial config tool. 

I have also tried setting the PC via the J link to the start of internal flash, but that (somewhat predictably) didn't work, likely due to the initialization in the ROM code. 

I've done a bit of searching, and other members who managed to work around this have been able to get a program running somehow, maybe via internal loader or external jumpers:

https://community.nxp.com/t5/i-MX-RT/How-to-burn-BT-FUSE-SEL-on-RT1050/m-p/809577

And other people have had the same issue of not being able to debug:

https://community.nxp.com/t5/i-MX-RT/How-to-Enable-Debugging-for-i-MX-RT1064-SIP-4M-Flash-Memory/m-p...

Is there no way to debug without these fuses set if BOOT_MODE[1:0] are floating?

Is there any way to burn the fuses via debugger?

Right now, the workarounds I see are as follows:

1. Hack out the ADC pins and temporarily use them as a UART to allow booting MFGTool to program the efuses

2. I've got access to BOOT_MODE1 which should allow me to boot to internal boot, then hopefully run a program. 

Neither of those seem very nice to me. Is there really no way to burn via JLink? 

Thanks

0 件の賞賛
返信
1 解決策
3,041件の閲覧回数
mjbcswitzerland
Specialist V

Hi

If you link code to RAM it will be loaded there and the debugger will set up the stack pointer and start address so that it can run without passing through the ROM Loader.

The flash config is supplied by the startup code (either application when standalone or boot loader when the product supports field and OTA updating) and needs to be in the correct form to be recognised by the ROM loader otherwise it will not start that code.

Debuggers are very sensitive working with the i.MX RT parts and not everything works perfectly, especially when not working with very standard programs that are doing things exactly as the designers foresaw (sometimes breakpoints need to be set only after connection otherwise they will be missed). With trial and error techniques can be worked out that give reasonable results - I have found IAR behavior the most reliable with regards to debugging.

Regards

Mark

 

元の投稿で解決策を見る

5 返答(返信)
3,069件の閲覧回数
nplayle
Contributor I

As a bit of an update to add some more info, I've continued on with the following:

  • Changed BOOT_MODE1 to pull up. 
  • Changed other pulls on the BOOT_CFG lines. 

I now have the following:

  • BOOT_MODE[1:0] = 0b10 (internal boot)
  • BOOT_CFG1 = 0x0
  • BOOT_CFG2 = 0x0

I've verified the above with the debuggeR:

nplayle_0-1618286573618.png

 

Unfortunately, I'm still getting stuck when debugging in the 0x218390 region... This varies, but it still seems like it's in serial loader mode somehow? 

nplayle_1-1618286622660.png

 

This doesn't 100% make sense to me... what else am I missing? 

0 件の賞賛
返信
3,064件の閲覧回数
mjbcswitzerland
Specialist V

Hi

If you can connect via JTAG you can load a program to  RAM that can program eFuses.

Regards

Mark
[uTasker project developer for Kinetis and i.MX RT]
Contact me by personal message or on the uTasker web site to discuss professional training, solutions to problems or rapid product development requirements

For professionals searching for faster, problem-free Kinetis and i.MX RT 10xx developments the uTasker project holds the key: https://www.utasker.com/iMX/RT1064.html

0 件の賞賛
返信
3,058件の閲覧回数
nplayle
Contributor I

Thanks, would that be done just by linking the program to run from RAM? How do you get the MCU to skip over the ROM code at the start? 

 

In any case, I've made some more progress. I was never able to find where the configuration of the internal flash took place and assumed the tool did it automatically. When I looked closer at the demo projects I noticed that there was a file that looked like it configured the flash:

const flexspi_nor_config_t qspiflash_config = {
    .memConfig =
        {
            .tag              = FLEXSPI_CFG_BLK_TAG,
            .version          = FLEXSPI_CFG_BLK_VERSION,
            .readSampleClksrc=kFlexSPIReadSampleClk_LoopbackFromDqsPad,
            .csHoldTime       = 3u,
            .csSetupTime      = 3u,
            .sflashPadType    = kSerialFlash_4Pads,
            .serialClkFreq    = kFlexSpiSerialClk_100MHz,
            .sflashA1Size     = 4u * 1024u * 1024u,
            .lookupTable =
                {
                    // Read LUTs
                    FLEXSPI_LUT_SEQ(CMD_SDR, FLEXSPI_1PAD, 0xEB, RADDR_SDR, FLEXSPI_4PAD, 0x18),
                    FLEXSPI_LUT_SEQ(DUMMY_SDR, FLEXSPI_4PAD, 0x06, READ_SDR, FLEXSPI_4PAD, 0x04),
                },
        },
    .pageSize           = 256u,
    .sectorSize         = 4u * 1024u,
    .blockSize          = 64u * 1024u,
    .isUniformBlockSize = false,
};

When I included that I can get my hello world to run fine, sometimes. 

Now I seem to have an interesting problem where I need to run the debug configuration twice to get an update. The first click erases flash and then ends up in the serial loader ROM region, the second run is able to program flash and executes the hello world, but seems to skip over all the breakpoints I have set in main. 

0 件の賞賛
返信
3,042件の閲覧回数
mjbcswitzerland
Specialist V

Hi

If you link code to RAM it will be loaded there and the debugger will set up the stack pointer and start address so that it can run without passing through the ROM Loader.

The flash config is supplied by the startup code (either application when standalone or boot loader when the product supports field and OTA updating) and needs to be in the correct form to be recognised by the ROM loader otherwise it will not start that code.

Debuggers are very sensitive working with the i.MX RT parts and not everything works perfectly, especially when not working with very standard programs that are doing things exactly as the designers foresaw (sometimes breakpoints need to be set only after connection otherwise they will be missed). With trial and error techniques can be worked out that give reasonable results - I have found IAR behavior the most reliable with regards to debugging.

Regards

Mark

 

3,023件の閲覧回数
nplayle
Contributor I

Thanks, 

 

Using the above and the code from my initially linked post I was able to get the application running in RAM via J-Link and used the following code to set the fuses to internal boot and burn the BT_SEL flags:

void burn_fuses(void)
{
	if (!(SRC->SBMR2 & SRC_SBMR2_BT_FUSE_SEL_MASK))
	{
		// Assumes ipg_clk = 132MHz
		// WAIT+1/ipg_clk >= 150ns, 24 = 189ns
		// RELAX+1/ipg_clk >= 100ns, 20 = 151.5ns
		// STROBE_PROG --> tpgm = ((STROBE_PROG +1) - 2x (RELAX_PROG+1))/ipg_clk = 10000us, 1340 = 10us
		// STROBE_READ --> trd = ((STROBE_READ+1) - 2x (RELAX_PROG+1))/ipg_clk > 45ns, STROBE_READ+1/ipg_clk > 75ns =
	    int timing = OCOTP_TIMING_STROBE_PROG(1340) | OCOTP_TIMING_RELAX(20) | OCOTP_TIMING_STROBE_READ(50) |OCOTP_TIMING_WAIT(24); //ipg_clk=132MHz, Calculation described at Chapter 42.3.3 OTP Read/Write Timing Parameters
	    OCOTP->TIMING = timing;
	    while ((OCOTP->CTRL & (1<<OCOTP_CTRL_BUSY_SHIFT)) || (OCOTP->CTRL & (1<<OCOTP_CTRL_ERROR_SHIFT))); //Check that HW_OCOTP_CTRL[BUSY] and HW_OCOTP_CTRL[ERROR]are clear
	    int ocotp_ctrl = OCOTP->CTRL;
	    ocotp_ctrl &= ~OCOTP_CTRL_ADDR_MASK;
	    ocotp_ctrl|= OCOTP_CTRL_ADDR(6);
	    ocotp_ctrl &= ~OCOTP_CTRL_WR_UNLOCK_MASK ;
	    ocotp_ctrl|= OCOTP_CTRL_WR_UNLOCK(0x3E77);
	    OCOTP->CTRL = ocotp_ctrl; //Write ADDR and unlock
	    OCOTP->DATA = (long)((1<<4)|(1<<16));//burn BT_FUSE_SEL (1<<4) and FORCE_INTERNAL_BOOT (1<<16)
	}
}
0 件の賞賛
返信