一执行FLASH->ACR |= (uint32_t)FLASH_ACR_LATENCY_2就HardFault了?

[复制链接]
8189|18
 楼主| ounie 发表于 2010-9-1 23:15 | 显示全部楼层 |阅读模式
本想将程序在flash中调试,因为之前一直在内部sram运行。
跳线啊,一些ROM/RAM地址啊 其他设置都弄好后 开始调试啦。结果发现一执行到FLASH->ACR |= (uint32_t)FLASH_ACR_LATENCY_2就HardFault了
这句在system_stm32f10x.c文件的static void SetSysClockTo72(void)函数里面,我用的3.3的库。
后面我把这三句话FLASH->ACR |= FLASH_ACR_PRFTBE;
    FLASH->ACR &= (uint32_t)((uint32_t)~FLASH_ACR_LATENCY);
    FLASH->ACR |= (uint32_t)FLASH_ACR_LATENCY_2;
改为了FLASH->ACR= (uint32_t)(FLASH_ACR_PRFTBE|FLASH_ACR_LATENCY_2);就没有任何fault了。程序完全正常了!我看了,上面写法不同,但寄存器最终结果还是一样的,但是库函数那种就fault了
MDK调试下看到,USG_FAULT那个寄存器里面UNDEFINSTR置位1了,HARD_FAULT里面FORCED置位1了
 楼主| ounie 发表于 2010-9-1 23:17 | 显示全部楼层
晕 可以上图片啊 之前不知道啊
1.jpg
lut1lut 发表于 2010-9-2 09:34 | 显示全部楼层
执行的这句话是设置flash的等待周期。
0:(0, 24MHz]
1: (24MHz, 48MHz]
2:(48Mhz, 72MHz]

如果你此时cpu本身的运算速度和设置后的不符合,就会hard fault。
 楼主| ounie 发表于 2010-9-2 09:39 | 显示全部楼层
CPU系统时钟设置对的啊 这个时钟频率和等待周期的对应关系我知道的
FLASH->ACR |= FLASH_ACR_PRFTBE;
FLASH->ACR &= (uint32_t)((uint32_t)~FLASH_ACR_LATENCY);
FLASH->ACR |= (uint32_t)FLASH_ACR_LATENCY_2;
改为了FLASH->ACR= (uint32_t)(FLASH_ACR_PRFTBE|FLASH_ACR_LATENCY_2);
就好了 其实对ACR的设置值,两种方法最终是一样的,但是结果是库函数那样搞 第3句执行完就HardFault了。我自己写的就没有HardFault了
 楼主| ounie 发表于 2010-9-2 09:42 | 显示全部楼层
本帖最后由 ounie 于 2010-9-2 09:43 编辑

static void SetSysClockTo72(void)
{
  __IO uint32_t StartUpCounter = 0, HSEStatus = 0;
  
  /* SYSCLK, HCLK, PCLK2 and PCLK1 configuration ---------------------------*/   
  /* Enable HSE */   
  RCC->CR |= ((uint32_t)RCC_CR_HSEON);

  /* Wait till HSE is ready and if Time out is reached exit */
  do
  {
    HSEStatus = RCC->CR & RCC_CR_HSERDY;
    StartUpCounter++;  
  } while((HSEStatus == 0) && (StartUpCounter != HSEStartUp_TimeOut));

  if ((RCC->CR & RCC_CR_HSERDY) != RESET)
  {
    HSEStatus = (uint32_t)0x01;
  }
  else
  {
    HSEStatus = (uint32_t)0x00;
  }  

  if (HSEStatus == (uint32_t)0x01)
  {
    /* Enable Prefetch Buffer */
    FLASH->ACR |= FLASH_ACR_PRFTBE;

    /* Flash 2 wait state */
    FLASH->ACR &= (uint32_t)((uint32_t)~FLASH_ACR_LATENCY);
    FLASH->ACR |= (uint32_t)FLASH_ACR_LATENCY_2;
   


    /* HCLK = SYSCLK */
    RCC->CFGR |= (uint32_t)RCC_CFGR_HPRE_DIV1;
      
    /* PCLK2 = HCLK */
    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE2_DIV1;
   
    /* PCLK1 = HCLK */
    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE1_DIV2;
.............以下函数内容省略
香水城 发表于 2010-9-2 09:50 | 显示全部楼层
请检查一下编译出来的汇编代码,是否有误。
 楼主| ounie 发表于 2010-9-2 13:07 | 显示全部楼层
按库函数的那三句话编译出来的
   904:     FLASH->ACR |= FLASH_ACR_PRFTBE;
   905:  
   906:     /* Flash 2 wait state */
0x08001370 4A4A      LDR      r2,[pc,#296]  ; @0x0800149C
0x08001372 6812      LDR      r2,[r2,#0x00]
0x08001374 F0420210  ORR      r2,r2,#0x10
0x08001378 4B48      LDR      r3,[pc,#288]  ; @0x0800149C
0x0800137A 601A      STR      r2,[r3,#0x00]
   907:     FLASH->ACR &= (uint32_t)((uint32_t)~FLASH_ACR_LATENCY);
0x0800137C 461A      MOV      r2,r3
0x0800137E 6812      LDR      r2,[r2,#0x00]
0x08001380 F0220203  BIC      r2,r2,#0x03
0x08001384 601A      STR      r2,[r3,#0x00]
   908:     FLASH->ACR |= (uint32_t)FLASH_ACR_LATENCY_2;
   909:  
   910:         /* HCLK = SYSCLK */
0x08001386 461A      MOV      r2,r3
0x08001388 6812      LDR      r2,[r2,#0x00]
0x0800138A F0420202  ORR      r2,r2,#0x02
0x0800138E 601A      STR      r2,[r3,#0x00]
/*------------------------------------------------------------------------------*/
我自己写的编译出来:
   903:     FLASH->ACR= (uint32_t)(FLASH_ACR_PRFTBE|FLASH_ACR_LATENCY_2);
   904:  
   905:         /* HCLK = SYSCLK */
0x08001370 2212      MOVS     r2,#0x12
0x08001372 4B43      LDR      r3,[pc,#268]  ; @0x08001480
0x08001374 601A      STR      r2,[r3,#0x00]
/*----------------------------------------------------------------------------------*/
我自己写的编译出来似乎。。。。不过我自己写的就没有HardFault。库函数就HardFault了啊
香水城 发表于 2010-9-2 13:48 | 显示全部楼层
请在库函数编译出来代码的最后一行放一个断点,看看r2的内容:
    0x0800138E 601A      STR      r2,[r3,#0x00]
 楼主| ounie 发表于 2010-9-2 14:18 | 显示全部楼层
R2是0x00000012
 楼主| ounie 发表于 2010-9-2 14:25 | 显示全部楼层
R2的值此时对应ACR寄存器的值?似乎是FLASH的ACR寄存器PRFTBS置0了,就是说预取缓冲区关闭了?
 楼主| ounie 发表于 2010-9-2 14:26 | 显示全部楼层
呵呵 手头没的硬件现在 软件仿真看到的结果 不知道会不会和实际用J-LINK在板子上跑,数值由偏差
香水城 发表于 2010-9-2 16:42 | 显示全部楼层
呵呵 手头没的硬件现在 软件仿真看到的结果 不知道会不会和实际用J-LINK在板子上跑,数值由偏差
ounie 发表于 2010-9-2 14:26


软件仿真?早说呢!
 楼主| ounie 发表于 2010-9-2 20:08 | 显示全部楼层
硬件仿真 r2是0x00000032啊
执行完0x0800138E 601A      STR      r2,[r3,#0x00] 就HardFault了
 楼主| ounie 发表于 2010-9-2 20:12 | 显示全部楼层
额 我自己写的FLASH->ACR= (uint32_t)(FLASH_ACR_PRFTBE|FLASH_ACR_LATENCY_2);
硬件仿真 r2是0x00000012
看来 快要知道为什么了
 楼主| ounie 发表于 2010-9-2 20:36 | 显示全部楼层
就是一个ACR寄存器里面,PRFTBS预取缓冲区状态 值不同。看文档,这是个只读寄存器啊??
参考的PM0042 即STM32F10XXX闪存编程中文版
 楼主| ounie 发表于 2010-9-3 10:39 | 显示全部楼层
香水城 发表于 2010-9-3 11:04 | 显示全部楼层
请不要用软件仿真,直接硬件上运行,我测试过,没有问题,别人也都没有发现这种问题。
 楼主| ounie 发表于 2010-9-3 11:38 | 显示全部楼层
是硬件啊 板子+JLINK
我也是很奇快怎么会有这个问题 所以发帖看其他人是不是有遇到过 共同探讨哈
panwenxiao 发表于 2014-4-23 16:16 | 显示全部楼层
FLASH->ACR= (uint32_t)(FLASH_ACR_PRFTBE|FLASH_ACR_LATENCY_2)是什么个意思,没看太明白,求大神指教。
您需要登录后才可以回帖 登录 | 注册

本版积分规则

0

主题

41

帖子

1

粉丝
快速回复 在线客服 返回列表 返回顶部