cancel
Showing results for 
Search instead for 
Did you mean: 

STM32H563 bootloader command over SPI

Dimlite
Associate II

Based on the information found in AN4286 rev 14, I am trying to command to bootloader to start executing the application.

The setup is a H573 and a H563 connected over SPI @ 0.5 MHz. The 573 operates as SPI master, and the 563 as a slave. I know that the HW is fine as I have no problem with the communication (application to application) when booth are configured with BOOT0 = 0.

Then I set BOOT0 = 1 on the 563, and tries the following code:

void BootloaderTest(void)
{
    clrEsbCsN;

    DelayUsBlocking(10);

    // Sync frame
    uart_printf("SEND SYNC 0x5A, RX: %.2X\r\n", SpiWriteEsb(0x5A));
    DelayUsBlocking(10);

    // Get ACK.
    if (GetAck())
    {
        // Send GO command.
        uart_printf("SEND SOF 0x5A, RX: %.2X\r\n", SpiWriteEsb(0x5A));
        DelayUsBlocking(10);

        uart_printf("SEND CMD GO 0x21, RX: %.2X\r\n", SpiWriteEsb(0x21));
        DelayUsBlocking(10);

        uart_printf("SEND CHKSUM, RX: %.2X\r\n", SpiWriteEsb(~0x21));   // single byte command, nothing to XOR.
        DelayUsBlocking(10);

        // Get ack of command.
        uart_printf("SEND 0x00, RX: %.2X\r\n", SpiWriteEsb(0x00));
        DelayUsBlocking(10);

        uart_printf("SEND 0x00, RX: %.2X\r\n", SpiWriteEsb(0x00));
        DelayUsBlocking(10);

        // TODO: check if we received 0x79.

        uart_printf("SEND 0x79, RX: %.2X\r\n", SpiWriteEsb(0x79));
        DelayUsBlocking(10);
    }


    DelayUsBlocking(10);

    setEsbCsN;
}

static bool GetAck(void)
{
    uart_printf("GET ACK\r\n");

    uart_printf("SEND 0x00, RX DUMMY: %.2X\r\n", SpiWriteEsb(0x00));
    DelayUsBlocking(10);

    uart_printf("WAIT FOR ACK OR NACK\r\n");

    do
    {
        uint8 ack = SpiWriteEsb(0xFF);

        uart_printf("SEND DUMMY, RX: %.2X\r\n", ack);
        DelayUsBlocking(10);

        if (ack == 0x79)
        {
            uart_printf("ACK RECEIVED!\r\n");
            uart_printf("SEND 0x79, RX DUMMY: %.2X\r\n", SpiWriteEsb(0x79));
            DelayUsBlocking(10);
            return true;
        }

        if (ack == 0x1F)
        {
            uart_printf("NACK RECEIVED!\r\n");
            return false;
        }

        uart_printf("Trying again.\r\n");

    } while (true);

    return false; // TODO: won't come here unless we limit the nbr of retries.
}

If we assume for now that the low level parts are fine (we can get back to this if needed), do you see any obvious flaws in the implementation with regard to how AN4286 describes it?

This is the output I get:

SEND SYNC 0x5A, RX: A5
GET ACK
SEND 0x00, RX DUMMY: A5
WAIT FOR ACK OR NACK
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: A5
Trying again.
SEND DUMMY, RX: 79
ACK RECEIVED!
SEND 0x79, RX DUMMY: A5
SEND SOF 0x5A, RX: A5
SEND CMD GO 0x21, RX: A5
SEND CHKSUM, RX: A5
SEND 0x00, RX: A5
SEND 0x00, RX: A5
SEND 0x79, RX: A5

The application is not started, and I know it is there because I flashed and tried it before setting BOOT0 = 1.

What is interesting is that next time I send the same command, this is what I get:

TCP: Get status
SEND SYNC 0x5A, RX: A5
GET ACK
SEND 0x00, RX DUMMY: A5
WAIT FOR ACK OR NACK
SEND DUMMY, RX: 1F
NACK RECEIVED!

I always get a NACK on every second attempt. If I were to try again, I would get the first sequence (many attempts for ack), and on the attempt after that I get a NACK etc.

Something is obviously affecting the internal statemachine in the bootloader, but something is missing here.

Thanks in advance.

 

0 REPLIES 0