硬汉嵌入式论坛

 找回密码
 立即注册
查看: 1007|回复: 5
收起左侧

[求助]V6开发板跳转系统BootLoader失败

[复制链接]

11

主题

104

回帖

137

积分

初级会员

积分
137
发表于 2022-9-30 09:36:52 | 显示全部楼层 |阅读模式
开发环境:win10专业版
IDE:mdk5.37.0.0

软件是通过STM32CUBEMX生成的最小测试系统,方便测试这个问题。

MCU资源用到了TIM9(1000ms)/USART1(软件中未开启接收中断,只用了输出功能)/PB6(Output)/PC13(Input)。

实测发现,软件无法从APP跳转到系统BootLoader,其表现就是按下KEY2后串口反复打印system start,同时PB6引脚上的灯(自己焊接的)还是会1s周期闪烁,这是系统在不断复位。如果成功跳转的话,串口将不会有任何输出,灯也不会闪烁。


根据ST官网如下链接,已经试了-O0/-O1两种优化等级,还是无法将软件保持在BootLoader。
IAP bootloader not jumping to the application address. (st.com)
application jump to system memory bootloader

有没有道友遇到过这个问题呢?

testBoot.7z

429.14 KB, 下载次数: 9

源代码包

回复

使用道具 举报

1万

主题

6万

回帖

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
106590
QQ
发表于 2022-9-30 11:07:43 | 显示全部楼层
意思是boot向app跳转正常,而app像boot跳转不正常? 这种情况在app里面直接调用systemreset函数就行了,就重新从boot开始运行了。不知道是否满足楼主的需求。
回复

使用道具 举报

11

主题

104

回帖

137

积分

初级会员

积分
137
 楼主| 发表于 2022-9-30 11:17:36 | 显示全部楼层
eric2013 发表于 2022-9-30 11:07
意思是boot向app跳转正常,而app像boot跳转不正常? 这种情况在app里面直接调用systemreset函数就行了,就 ...

不是呢,我是根据咱们的例程《V6-009_基于系统bootloader的USB接口方式IAP升级(USB DFU)》,在做从App跳转到系统BootLoader的实验,结果发现一运行跳转代码系统就复位了。
回复

使用道具 举报

11

主题

104

回帖

137

积分

初级会员

积分
137
 楼主| 发表于 2022-9-30 16:13:07 | 显示全部楼层
自己发的问题自己回复下解决方案。
现在发现将全局中断开启这句关掉,代码优化开-O1就能正常跳转,但是代码优化设置成O0就不行。这个现象我无法理解,这么小的代码量堆栈也不会超啊。有谁知道吗?
[C] 纯文本查看 复制代码
static void JumpToBootloader(void)
{
    uint32_t i = 0;
    void (*SysMemBootJump)(void);        /* 声明一个函数指针 */
    __IO uint32_t BootAddr = 0x1FFF0000; /* STM32F4的系统BootLoader地址 */

    /* 关闭全局中断 */
    DISABLE_INT();

    /* 关闭滴答定时器,复位到默认值 */
    SysTick->CTRL = 0;
    SysTick->LOAD = 0;
    SysTick->VAL = 0;

    /* 设置所有时钟到默认状态,使用HSI时钟 */
    HAL_RCC_DeInit();

    /* 关闭所有中断,清除所有中断挂起标志 */
    for (i = 0; i < 8; i++)
    {
        NVIC->ICER[i]=0xFFFFFFFF;
        NVIC->ICPR[i]=0xFFFFFFFF;
    }

    //注释掉这句就行了
//    /* 使能全局中断 */
//    ENABLE_INT();

    /* 设置重映射到系统Flash */
    __HAL_SYSCFG_REMAPMEMORY_SYSTEMFLASH();

    /* 跳转到系统BootLoader,首地址是MSP,地址+4是复位中断服务程序地址 */
    SysMemBootJump = (void (*)(void)) (*((uint32_t *) (BootAddr + 4)));

    /* 设置朱堆栈指针 */
    __set_MSP(*(uint32_t *)BootAddr);

    /* 在RTOS工程,这条语句很重要,设置为特权级模式,使用MSP指针 */
    __set_CONTROL(0);

    /* 跳转到系统BootLoader */
    SysMemBootJump();

    /* 跳转成功的话,不会执行到这里,用户可以在这里添加代码 */
    while (1)
    {

    }
}
回复

使用道具 举报

1万

主题

6万

回帖

10万

积分

管理员

Rank: 9Rank: 9Rank: 9

积分
106590
QQ
发表于 2022-10-1 00:29:12 | 显示全部楼层
笔记本的自嘲 发表于 2022-9-30 16:13
自己发的问题自己回复下解决方案。
现在发现将全局中断开启这句关掉,代码优化开-O1就能正常跳转,但是代 ...

特别注意,函数
HAL_RCC_DeInit();

要放在下面函数的前面,因为这个HAL_RCC_DeInit会再次开启滴答定时器。

SysTick->CTRL = 0;
SysTick->LOAD = 0;
SysTick->VAL = 0;
回复

使用道具 举报

11

主题

104

回帖

137

积分

初级会员

积分
137
 楼主| 发表于 2022-10-1 18:40:47 | 显示全部楼层
eric2013 发表于 2022-10-1 00:29
特别注意,函数
HAL_RCC_DeInit();

有效果,但是无法连接programmer,翻了以前的帖子,买了个FT232再试下,谢谢老大,国庆快乐鸭
回复

使用道具 举报

您需要登录后才可以回帖 登录 | 立即注册

本版积分规则

QQ|小黑屋|Archiver|手机版|硬汉嵌入式论坛

GMT+8, 2024-4-26 04:01 , Processed in 0.191823 second(s), 28 queries .

Powered by Discuz! X3.4 Licensed

Copyright © 2001-2023, Tencent Cloud.

快速回复 返回顶部 返回列表