Skip to main content
Associate II
June 15, 2026
Question

How to flash .elf through CAN in spc58ec80e5 in autodevkit studio

  • June 15, 2026
  • 5 replies
  • 61 views

How tp flash the .elf through CAN , i’m using SPC58EC80E5 and working on Autodevkit studio. 

5 replies

SRomeo
ST Employee
June 29, 2026

Hi, you cannot. Use the supported way instead. (Jtag/USB)
Best regards
Simone

Pooja1Author
Associate II
June 30, 2026

IN FIELDS i’m not allowed to use Jtag i have only connection with CAN so using that how to implement the Bootloader concept.

SRomeo
ST Employee
June 30, 2026

If you are in the Automotive industry, you should already know that exists companies in charge of Bootloader development, (obviously under payment). Moreover, you usually need a vendor-specific Bootloader utility for flashing. 

AutoDevKit Studio does not include any SPC58x bootloader natively.
We cannot grant any support on this.
Best regards,
Simone
AEK_Team
 

Pooja1Author
Associate II
July 8, 2026

Hii SRomeo, 

 

What should i do now, i’m using Autodevkitstudio SPC58EC80E5, The bootloader program im using is given below

/* ── 1. includes ── */
#include "components.h"
#include "can_lld.h"
#include "can_lld_cfg.h"
#include "pal.h"
#include "osal.h"
#include "ivor_cfg.h"
#include "ssd_c55.h"
#include <string.h>


/* ── 2. defines ── */
#define APP_FLASH_BASE          0x01000000UL
#define APP_IMAGE_MAX_SIZE      (128UL * 1024UL)
#define BLOCK_SIZE_BYTES        (128UL * 1024UL)
#define BOOT_ENTRY_TIMEOUT_MS   3000U
#define RXQ_DEPTH               16U
#define CANID_START_TRANSFER    0x700U
#define CANID_DATA_FRAME        0x701U
#define CANID_END_TRANSFER      0x702U
#define CANID_ACK               0x710U
#define CANID_NACK              0x711U
#define ACK_START_OK            0x01U
#define ACK_DATA_OK             0x02U
#define ACK_TRANSFER_COMPLETE   0x03U
#define ACK_FLASH_OK            0x04U
#define NACK_SIZE_INVALID       0x81U
#define NACK_SIZE_MISMATCH      0x82U
#define NACK_CRC_FAIL           0x83U
#define NACK_FLASH_FAIL         0x84U
#define NACK_OVERFLOW           0x85U
#define ACK_BOOT_READY          0x05U
#define UPDATE_SW_PORT PORT_C

#define UPDATE_SW_PAD 14U


/* ── 3. types ── */
typedef enum {
    BOOT_IDLE, BOOT_RECEIVING, BOOT_ERASING,
    BOOT_PROGRAMMING, BOOT_VERIFYING, BOOT_DONE
} BootState;

typedef struct {
    uint32_t id;
    uint8_t  dlc;
    uint8_t  data[8];
} RxFrame;

/* ── 4. file-scope variables ── */
SSD_CONFIG ssdConfig = {
    C55_REG_BASE, MAIN_ARRAY_BASE,
    {0,0,0}, {0,0,0}, {0,0,0}, 0,
    UTEST_ARRAY_BASE, TRUE, C55_PROGRAMMABLE_SIZE, FALSE
};
CONTEXT_DATA pgmCtxData, eraseCtxData, pvCtxData;
static CONTEXT_DATA dummyCtxData;
static uint8_t          app_image_buf[APP_IMAGE_MAX_SIZE];
static volatile RxFrame rxq[RXQ_DEPTH];
static volatile uint8_t rxq_head        = 0U;
static volatile uint8_t rxq_tail        = 0U;
static BootState        boot_state      = BOOT_IDLE;
static uint32_t         rx_total_size   = 0U;
static uint32_t         rx_received     = 0U;
static uint32_t         last_activity_tick = 0U;
static uint8_t flash_initialized = 0U;

/* ── 5. forward declarations ← MUST BE HERE, before any function that calls them ── */
static uint32_t CRC32_Compute(const uint8_t *data, uint32_t length);
static void __attribute__((section(".ram_func"), noinline))
CAN_SendResponse(uint32_t can_id, uint8_t reason, uint32_t info);
static uint32_t __attribute__((section(".ram_func"), noinline))
Flash_EraseAndProgram(void);
volatile uint32_t g_fault_dear = 0U;
volatile uint32_t g_fault_esr  = 0U;
volatile uint32_t g_fault_srr0 = 0U;
volatile uint32_t g_fault_srr1 = 0U;

volatile uint32_t g_fault1_srr0 = 0U; volatile uint32_t g_fault1_srr1 = 0U;
void ivor1_callback(uint32_t srr0, uint32_t srr1) {
    g_fault1_srr0 = srr0; g_fault1_srr1 = srr1;
    while (1) { }
}


/* ── 6. RX callback ── */
void mcanconf_Bootloader_CANRxCallback(uint32_t msgbuf, CANRxFrame crfp)
{
    uint8_t i;
    uint8_t next;
    (void)msgbuf;

    next = (uint8_t)((rxq_head + 1U) % RXQ_DEPTH);
    if (next == rxq_tail) return;

    rxq[rxq_head].id  = crfp.ID;
    rxq[rxq_head].dlc = crfp.DLC;
    for (i = 0U; i < crfp.DLC; i++) {
        rxq[rxq_head].data[i] = crfp.data8[i];
    }
    rxq_head = next;
}

/* ── 7. queue processor ── */
static void CAN_Process_RxQueue(void)
{
    while (rxq_tail != rxq_head)
    {
        uint8_t  i;
        RxFrame  f;

        f.id  = rxq[rxq_tail].id;
        f.dlc = rxq[rxq_tail].dlc;
        for (i = 0U; i < f.dlc; i++) {
            f.data[i] = rxq[rxq_tail].data[i];
        }
        rxq_tail = (uint8_t)((rxq_tail + 1U) % RXQ_DEPTH);

        last_activity_tick = osalThreadGetMilliseconds();

        switch (f.id)
        {
            case CANID_START_TRANSFER:
            {
                uint32_t announced;
                if (f.dlc < 4U) {
                    CAN_SendResponse(CANID_NACK, NACK_SIZE_INVALID, 0U);
                    break;
                }
                announced =
                    (uint32_t)f.data[0]         |
                    ((uint32_t)f.data[1] << 8U)  |
                    ((uint32_t)f.data[2] << 16U) |
                    ((uint32_t)f.data[3] << 24U);

                if (announced == 0U || announced > APP_IMAGE_MAX_SIZE) {
                    CAN_SendResponse(CANID_NACK, NACK_SIZE_INVALID, announced);
                    boot_state = BOOT_IDLE;
                    break;
                }
                rx_total_size = announced;
                rx_received   = 0U;
                boot_state    = BOOT_RECEIVING;
                CAN_SendResponse(CANID_ACK, ACK_START_OK, rx_total_size);
                break;
            }

            case CANID_DATA_FRAME:
            {
                uint8_t payload_len;
                if (boot_state != BOOT_RECEIVING) {
                    CAN_SendResponse(CANID_NACK, NACK_OVERFLOW, rx_received);
                    break;
                }
                if (f.dlc < 2U) break;

                payload_len = f.dlc - 1U;
                if ((rx_received + payload_len) > APP_IMAGE_MAX_SIZE) {
                    CAN_SendResponse(CANID_NACK, NACK_OVERFLOW, rx_received);
                    boot_state = BOOT_IDLE;
                    break;
                }
                for (i = 0U; i < payload_len; i++) {
                    app_image_buf[rx_received + i] = f.data[1U + i];
                }
                rx_received += payload_len;

                if (rx_received > 0U && (rx_received % (32U * 7U)) == 0U) {
                    CAN_SendResponse(CANID_ACK, ACK_DATA_OK, rx_received);
                }
                break;
            }

            case CANID_END_TRANSFER:
            {
                uint32_t host_crc;
                uint32_t local_crc;   /* ← declared at top of case block, not at file scope */

                if (rx_received != rx_total_size) {
                    CAN_SendResponse(CANID_NACK, NACK_SIZE_MISMATCH, rx_received);
                    boot_state = BOOT_IDLE;
                    break;
                }
                if (f.dlc < 4U) {
                    CAN_SendResponse(CANID_NACK, NACK_CRC_FAIL, 0U);
                    boot_state = BOOT_IDLE;
                    break;
                }
                host_crc =
                    (uint32_t)f.data[0]         |
                    ((uint32_t)f.data[1] << 8U)  |
                    ((uint32_t)f.data[2] << 16U) |
                    ((uint32_t)f.data[3] << 24U);

                local_crc = CRC32_Compute(app_image_buf, rx_received);

                if (local_crc != host_crc) {
                    CAN_SendResponse(CANID_NACK, NACK_CRC_FAIL, local_crc);
                    boot_state = BOOT_IDLE;
                    break;
                }
                CAN_SendResponse(CANID_ACK, ACK_TRANSFER_COMPLETE, rx_received);
                boot_state = BOOT_ERASING;
                break;
            }

            default:
                break;
        }
    }
}

/* ── 8. CRC32 ── */
static uint32_t CRC32_Compute(const uint8_t *data, uint32_t length)
{
    uint32_t crc = 0xFFFFFFFFUL;
    uint32_t i;
    uint8_t  bit;

    for (i = 0U; i < length; i++) {
        crc ^= (uint32_t)data[i];
        for (bit = 0U; bit < 8U; bit++) {
            if ((crc & 1UL) != 0UL) {
                crc = (crc >> 1U) ^ 0xEDB88320UL;
            } else {
                crc >>= 1U;
            }
        }
    }
    return crc ^ 0xFFFFFFFFUL;
}

/* ── 9. TX helper ── */
static void __attribute__((section(".ram_func"), noinline))
CAN_SendResponse(uint32_t can_id, uint8_t reason, uint32_t info)
{
    CANTxFrame txf;
    uint32_t   result;
    uint8_t    retry;

    txf.OPERATION = 0U;
    txf.RTR       = 0U;
    txf.IDE       = 0U;
    txf.ID        = can_id;
    txf.DLC       = 5U;
    txf.data8[0]  = reason;
    txf.data8[1]  = (uint8_t)((info)        & 0xFFU);
    txf.data8[2]  = (uint8_t)((info >> 8U)  & 0xFFU);
    txf.data8[3]  = (uint8_t)((info >> 16U) & 0xFFU);
    txf.data8[4]  = (uint8_t)((info >> 24U) & 0xFFU);

    for (retry = 0U; retry < 20U; retry++)
    {
        result = can_lld_transmit(&CAND10, 0, &txf);
        if (result == CAN_MSG_OK) {
            return;
        }
        osalThreadDelayMilliseconds(2U);
    }
}
/* ── 10. Flash ── */
#define FLASH_OP_TIMEOUT_MS   5000U


static uint32_t __attribute__((section(".ram_func"), noinline))
Flash_EraseAndProgram(void)
{
    uint32_t returnCode;
    NLARGE_BLOCK_SEL nLargeBlockSelect;
    uint32_t opResult;

    if (rx_received == 0U || rx_received > APP_IMAGE_MAX_SIZE) {
        CAN_SendResponse(CANID_NACK, NACK_FLASH_FAIL, rx_received);
        return 0U;
    }

    if (!flash_initialized) {
        returnCode = FlashInit(&ssdConfig);
        if (returnCode != C55_OK) {
            CAN_SendResponse(CANID_NACK, 0xF1U, returnCode);
            return 0U;
        }
        flash_initialized = 1U;
    }

    returnCode = SetLock(&ssdConfig, C55_BLOCK_LARGE_FIRST, UNLOCK_ALL_BLOCKS);

    nLargeBlockSelect.firstLargeBlockSelect  = (1U << 0);
    nLargeBlockSelect.secondLargeBlockSelect = 0U;

    /* ── Disable interrupts for the entire erase+program window.
         No ISR may fire while flash is busy — its code may live in flash
         and cause a Machine Check on fetch. ── */
    irqIsrDisable();

    returnCode = FlashErase(&ssdConfig, C55_ERASE_MAIN,
                            0U, 0U, 0U, nLargeBlockSelect);
    if (returnCode != C55_OK) {
        irqIsrEnable();
        CAN_SendResponse(CANID_NACK, 0xF2U, returnCode);
        return 0U;
    }

    opResult = C55_OK;
    while (C55_INPROGRESS == FlashCheckStatus(&ssdConfig,
           C55_MODE_OP_ERASE, &opResult, &dummyCtxData)) { }

    if (opResult != C55_OK) {
        irqIsrEnable();
        CAN_SendResponse(CANID_NACK, 0xF3U, opResult);
        return 0U;
    }

    returnCode = FlashProgram(&ssdConfig, FALSE,
                              APP_FLASH_BASE,
                              rx_received,
                              (uint32_t)app_image_buf,
                              &pgmCtxData);
    if (returnCode != C55_OK) {
        irqIsrEnable();
        CAN_SendResponse(CANID_NACK, 0xF4U, returnCode);
        return 0U;
    }

    opResult = C55_OK;
    while (C55_INPROGRESS == FlashCheckStatus(&ssdConfig,
           C55_MODE_OP_PROGRAM, &opResult, &pgmCtxData)) { }

    irqIsrEnable();   /* ── re-enable now that flash is fully idle ── */

    if (opResult != C55_OK) {
        CAN_SendResponse(CANID_NACK, 0xF5U, opResult);
        return 0U;
    }

    return 1U;
}
/* ───────────────────────── Jump ───────────────────────── */
static void Jump_To_Application(void)
{
    typedef void (*tAppEntry)(void);
    irqIsrDisable();
    ((tAppEntry)(APP_FLASH_BASE + 0x0CUL))();
}


/* ── 12. main ── */
/* ── 12. main ── */
int main(void)
{
    {
            extern uint32_t _ram_func_start;
            extern uint32_t _ram_func_end;
            extern uint32_t _ram_func_load;
            uint32_t *src = &_ram_func_load;
            uint32_t *dst = &_ram_func_start;
            while (dst < &_ram_func_end) {
                *dst++ = *src++;
            }
        }

    pgmCtxData.pReqCompletionFn = FlashProgram;

    componentsInit();
    irqIsrEnable();

    pal_setgroupmode(UPDATE_SW_PORT, PAL_PORT_BIT(UPDATE_SW_PAD),
                     PAL_MODE_INPUT | PAL_SPC5_WPUE);
    pal_setgroupmode(PORT_E, PAL_PORT_BIT(15U), PAL_MODE_OUTPUT);
           pal_setpad(PORT_E, 15U);
    pal_setgroupmode(PORT_G, PAL_PORT_BIT(12U), PAL_MODE_OUTPUT);   /* NEW: bus-off indicator */
    pal_setgroupmode(PORT_H, PAL_PORT_BIT(2U), PAL_MODE_OUTPUT);   /* NEW: error-passive indicator */
    can_lld_start(&CAND10, &can_config_mcanconf);
    osalThreadDelayMilliseconds(50U);

    if (pal_readpad(UPDATE_SW_PORT, UPDATE_SW_PAD) == PAL_LOW)
    {
        uint32_t now;
        uint32_t last_ready_tx_tick;

        boot_state         = BOOT_RECEIVING;
        last_activity_tick = osalThreadGetMilliseconds();

        /* first ready broadcast immediately */
        CAN_SendResponse(CANID_ACK, ACK_BOOT_READY, 0U);
        last_ready_tx_tick = osalThreadGetMilliseconds();

        while (boot_state != BOOT_DONE)
        {
            CAN_Process_RxQueue();

            now = osalThreadGetMilliseconds();

            /* Still waiting for host to send START_TRANSFER -> keep pinging every 500ms,
               do NOT time out here; wait as long as needed for the GUI to respond. */
            if ((boot_state == BOOT_RECEIVING) && (rx_total_size == 0U))
            {
                if ((now - last_ready_tx_tick) >= 500U)
                {
                    CAN_SendResponse(CANID_ACK, ACK_BOOT_READY, 0U);
                    last_ready_tx_tick = now;
                }
            }
            /* Transfer has started (rx_total_size != 0) -> now apply the inactivity
               timeout, so a stalled/dropped transfer doesn't hang forever. */
            else if ((boot_state == BOOT_RECEIVING) && (rx_total_size != 0U))
            {
                if ((now - last_activity_tick) > BOOT_ENTRY_TIMEOUT_MS)
                {
                    break; /* stalled mid-transfer -> fall through to Jump_To_Application */
                }
            }

            if (boot_state == BOOT_ERASING)
            {
                g_fault1_srr0 = 0xDEADBEEFU;
                g_fault1_srr1 = 0xDEADBEEFU;

                uint32_t flash_result = Flash_EraseAndProgram();


                if (flash_result != 0U)
                {
                    CAN_SendResponse(CANID_ACK, ACK_FLASH_OK, rx_total_size);
                    boot_state = BOOT_DONE;
                }
                else
                {
                    CAN_SendResponse(CANID_NACK, NACK_FLASH_FAIL, 0U);
                    boot_state = BOOT_IDLE;
                    last_activity_tick = osalThreadGetMilliseconds();
                }
            }
        }
    }

    can_lld_stop(&CAND10);
    Jump_To_Application();
    while (1) { }
}
check this and also i added .ld file (application.ld is generating file but i include user.ld file check the file content given below)

/****************************************************************************
*
* Copyright © 2016-2019 STMicroelectronics - All Rights Reserved
*
* This software is licensed under SLA0098 terms that can be found in the
* DM00779817_1_0.pdf file in the licenses directory of this software product.

* THIS SOFTWARE IS DISTRIBUTED "AS IS," AND ALL WARRANTIES ARE DISCLAIMED, 
* INCLUDING MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.
*
*****************************************************************************/

/*
 * This file is automatically generated and can be overwritten, do no change
 * this file manually.
 */

/*
 * SPC58ECxx memory setup.
 */

__irq_stack_size__            = 0;
__process_stack_size__        = 4096;
__core0_irq_stack_size__      = 0;
__core0_process_stack_size__  = 2048;

MEMORY
{
    hsmflash    : org = 0x0060C000, len = 144k
    dataflash   : org = 0x00800000, len = 128k
    flash       : org = 0x00FC0000, len = 192k 
    ram         : org = 0x400A8000, len = 512k - 128k
    dram0       : org = 0x50800000, len = 64k
    dram2       : org = 0x52800000, len = 64k
}

ENTRY(_reset_address2)

/*
 * Derived constants.
 */
__flash_size__          = LENGTH(flash);
__flash_start__         = ORIGIN(flash);
__flash_end__           = ORIGIN(flash) + LENGTH(flash);

__ram_size__            = LENGTH(ram);
__ram_start__           = ORIGIN(ram);
__ram_end__             = ORIGIN(ram) + LENGTH(ram);

__dram0_size__          = LENGTH(dram0);
__dram0_start__         = ORIGIN(dram0);
__dram0_end__           = ORIGIN(dram0) + LENGTH(dram0);

__dram2_size__          = LENGTH(dram2);
__dram2_start__         = ORIGIN(dram2);
__dram2_end__           = ORIGIN(dram2) + LENGTH(dram2);


SECTIONS
{
    . = ORIGIN(flash);
    .boot0 : ALIGN(16) SUBALIGN(16)
    {
        KEEP(*(.boot))
        KEEP(*(.handlers))
        KEEP(*(.crt0))
    } > flash
    .boot1 : ALIGN(16) SUBALIGN(16)
    {
        . = ALIGN(0x100);
        __ivpr0_base__ = .;
        KEEP(*(.core0_ivors))
        . = ALIGN(0x100);
        __ivpr2_base__ = .;
        KEEP(*(.core2_ivors))
        . = ALIGN(0x1000);
        KEEP(*(.vectors))
    } > flash
    constructors : ALIGN(4) SUBALIGN(4)
    {
        PROVIDE(__init_array_start = .);
        KEEP(*(SORT(.init_array.*)))
        KEEP(*(.init_array))
        PROVIDE(__init_array_end = .);
    } > flash
    destructors : ALIGN(4) SUBALIGN(4)
    {
        PROVIDE(__fini_array_start = .);
        KEEP(*(.fini_array))
        KEEP(*(SORT(.fini_array.*)))
        PROVIDE(__fini_array_end = .);
    } > flash

    /* ── RAM functions — placed BEFORE .text so these sections are
       claimed here first and not duplicated in flash ── */
.ram_func : ALIGN(16)
{
    _ram_func_start = .;

    *(.ram_func)
    *(.ram_func*)

    *c55_freegcc.a:SetLock.o(.text .text.* .text_vle .text_vle.*)
    *c55_freegcc.a:FlashProgram.o(.text .text.* .text_vle .text_vle.*)
    *c55_freegcc.a:FlashInit.o(.text .text.* .text_vle .text_vle.*)
    *c55_freegcc.a:FlashErase.o(.text .text.* .text_vle .text_vle.*)
    *c55_freegcc.a:FlashCheckStatus.o(.text .text.* .text_vle .text_vle.*)

    /* constant data used by the driver — must also be reachable while flash is busy */
    *c55_freegcc.a:SetLock.o(.rodata .rodata.*)
    *c55_freegcc.a:FlashProgram.o(.rodata .rodata.*)
    *c55_freegcc.a:FlashInit.o(.rodata .rodata.*)
    *c55_freegcc.a:FlashErase.o(.rodata .rodata.*)
    *c55_freegcc.a:FlashCheckStatus.o(.rodata .rodata.*)

    . = ALIGN(4);
    _ram_func_end = .;
} > ram AT > flash

    _ram_func_load = LOADADDR(.ram_func);

    .text_vle : ALIGN(16) SUBALIGN(16)
    {
        *(.text_vle)
        *(.text_vle.*)
        *(.gnu.linkonce.t_vle.*)
    } > flash
    .text : ALIGN(16) SUBALIGN(16)
    {
        *(.text)
        *(.text.*)
        *(.gnu.linkonce.t.*)
    } > flash
    .rodata : ALIGN(16) SUBALIGN(16)
    {
        *(.glue_7t)
        *(.glue_7)
        *(.gcc*)
        *(.rodata)
        *(.rodata.*)
        *(.rodata1)
    } > flash
    .sdata2 : ALIGN(16) SUBALIGN(16)
    {
        __sdata2_start__ = . + 0x8000;
        *(.sdata2)
        *(.sdata2.*)
        *(.gnu.linkonce.s2.*)
        *(.sbss2)
        *(.sbss2.*)
        *(.gnu.linkonce.sb2.*)
    } > flash
    .eh_frame_hdr :
    {
        *(.eh_frame_hdr)
    } > flash
    .eh_frame : ONLY_IF_RO
    {
        *(.eh_frame)
    } > flash
    .romdata : ALIGN(16) SUBALIGN(16)
    {
        __romdata_start__ = .;
    } > flash
    .core0_stacks : ALIGN(16) SUBALIGN(16)
    {
        . = ALIGN(8);
        __core0_irq_stack_base__ = .;
        . += __core0_irq_stack_size__;
        . = ALIGN(8);
        __core0_irq_stack_end__ = .;
        __core0_process_stack_base__ = .;
        __core0_main_thread_stack_base__ = .;
        . += __core0_process_stack_size__;
        . = ALIGN(8);
        __core0_process_stack_end__ = .;
        __core0_main_thread_stack_end__ = .;
    } > dram0
    .core2_stacks : ALIGN(16) SUBALIGN(16)
    {
        . = ALIGN(8);
        __irq_stack_base__ = .;
        . += __irq_stack_size__;
        . = ALIGN(8);
        __irq_stack_end__ = .;
        __process_stack_base__ = .;
        __main_thread_stack_base__ = .;
        . += __process_stack_size__;
        . = ALIGN(8);
        __process_stack_end__ = .;
        __main_thread_stack_end__ = .;
    } > dram2
    .data : AT(__romdata_start__)
    {
        . = ALIGN(4);
        __data_start__ = .;
        *(.data)
        *(.data.*)
        *(.gnu.linkonce.d.*)
    } > ram
    .sdata :
    {
        . = ALIGN(4);
        __sdata_start__ = . + 0x8000;
        *(.sdata)
        *(.sdata.*)
        *(.gnu.linkonce.s.*)
        __data_end__ = .;
    } > ram
    .sbss :
    {
        __bss_start__ = .;
        *(.sbss)
        *(.sbss.*)
        *(.gnu.linkonce.sb.*)
        *(.scommon)
    } > ram
    .bss :
    {
        *(.bss)
        *(.bss.*)
        *(.gnu.linkonce.b.*)
        *(COMMON)
        __bss_end__ = .;
    } > ram
    __heap_base__   = __bss_end__;
    __heap_end__    = __ram_end__;
}

 

and i’m transmitting .bin file using GUI, it showing the file data are transmitted but flashing is failing 


TX CAN : t70143BFFFFFF
TX (14): 74 37 30 31 34 33 42 46 46 46 46 46 46 0D

Firmware Transfer Complete
Total Bytes Sent = 70304

====================================
Sending END Frame
CRC = 46E58380
====================================

TX CAN : t70248083E546
TX (14): 74 37 30 32 34 38 30 38 33 45 35 34 36 0D
RX (16): 74 37 31 30 35 30 33 41 30 31 32 30 31 30 30 0D  | t710503A0120100.

RX CAN ID : 710
RX DLC    : 5
RX DATA   : 03 A0 12 01 00

Received CAN ID : 710

ACK Reason : 0x03
Info       : 70304
CRC Verified
Transfer Complete ACK Received
Waiting for Flash Programming...
ACK Timeout
Flash Programming Failed
Firmware Download Failed
Press any key to continue . . .

 

 

please help me to do it properly , how to work on this..

 

SRomeo
ST Employee
July 8, 2026

Hi pooja,
The one you posted is an IA generated content.
It won’t work.

You need a third parties professional to deliver (under payment) a working bootloader.

We cannot give any support on this.
Best regards,
Simone
AEK_Team

Pooja1Author
Associate II
July 10, 2026

Hii SRomeo,

What should i do now ?

Which is that third party professional bootloader how can i use that ?

I’m using SPC58EC80E5 and working in autodevkit Studio not SPC58STUDIO, how to use that third party bootloader , how to buy that one , and wt are the logics i should create, please give the code how to use it, and explain how to load the .bin file through CAN without using JTAG.