打印

STM32L151CBT6 为什么只能下载烧写一次程序

[复制链接]
7112|4
手机看帖
扫描二维码
随时随地手机跟帖
跳转到指定楼层
楼主
关聿|  楼主 | 2011-12-21 15:29 | 只看该作者 回帖奖励 |倒序浏览 |阅读模式
请教各位高手,
STM32L151CBT6   为什么只能下载烧写一次程序,
焊了2块线路板,换了3次CPU,仿真器用的是J-LINK.
每次只能是第一次烧程序可以写入,PA8输出系统时钟 SYSCLK,可以用示波器看到正确配置的时钟输出,然后就再也写不进程序了。
程序只先写了一部分,很简单,如下,
急啊!!!!!!!!

int main(void)
{
  RCC_GetClocksFreq(&RCC_Clocks);
  SysTick_Config(RCC_Clocks.HCLK_Frequency / 2000);  

  init_used_pin();  // 初始化管脚  
  while (1)
  {  DZ_LED_1;
     POWER_LED_1;
     Delay_us(20000);  // 延时us
     POWER_LED_0;
     DZ_LED_0;     
  }
}

void init_used_pin(void)  // 初始化管脚
{  GPIO_InitTypeDef GPIO_InitStructure;
      
   RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOA, ENABLE);   // 使能GPIOA 时钟
   RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOB, ENABLE);   // 使能GPIOB 时钟
   
   GPIO_InitStructure.GPIO_Pin = GPIO_Pin_All;  // 指定管脚
   GPIO_InitStructure.GPIO_Speed = GPIO_Speed_400KHz;  // 管脚输出的速度:400KHz
   GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;  // 管脚工作模式:输出
   GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; // 推挽方式输出 还是 集电极开路方式输出
   GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;  // 输入时上(下)拉状态:上拉
   
        ////////  PA所有管脚   开漏输出  ///////////
   GPIO_Init(GPIOA, &GPIO_InitStructure);
   GPIO_ResetBits(GPIOA, GPIO_Pin_All);
       ////////  PB所有管脚   开漏输出  ///////////
   GPIO_Init(GPIOB, &GPIO_InitStructure);
   GPIO_ResetBits(GPIOB, GPIO_Pin_All);
   
    ///  Output the system clock on MCO pin (PA.08)  ///
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_8;
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_40MHz;
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AF;
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP;
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;  
  GPIO_Init(GPIOA, &GPIO_InitStructure);
  RCC_MCOConfig(RCC_MCOSource_SYSCLK, RCC_MCODiv_1);  // MCO输出系统时钟 SYSCLK
  
      ///  电源指示LED(PA4), 动作LED(PA3)  ///
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_3 | GPIO_Pin_4; // 指定管脚
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_400KHz;  // 管脚输出的速度:400KHz
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;  // 管脚工作模式:输出
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; // 推挽方式输出
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;   // 输入时上(下)拉状态:上拉
  GPIO_Init(GPIOA, &GPIO_InitStructure);
  
      ///  电压信号(模拟量)输入:PA6  ///
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6; // 指定管脚
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_40MHz;  // 管脚输出的速度:40MHz
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_AN;   // 管脚工作模式:模拟输入
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; // 推挽方式输出
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_NOPULL; // 输入时上(下)拉状态:既不上拉,也不下拉
  GPIO_Init(GPIOA, &GPIO_InitStructure);
  
      ///  驱动光耦动作 PB6  ///
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_6; // 指定管脚
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_400KHz;  // 管脚输出的速度:400KHz
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;  // 管脚工作模式:输出
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; // 推挽方式输出
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;   // 输入时上(下)拉状态:上拉
  GPIO_Init(GPIOB, &GPIO_InitStructure);
  
      ///  1S输入(PB14), 2S输入(PB12), 3S输入(PB13)  ///
  GPIO_InitStructure.GPIO_Pin = GPIO_Pin_12 | GPIO_Pin_13 | GPIO_Pin_14; // 指定管脚
  GPIO_InitStructure.GPIO_Speed = GPIO_Speed_400KHz;  // 管脚输出的速度:400KHz
  GPIO_InitStructure.GPIO_Mode = GPIO_Mode_IN;  // 管脚工作模式:输入
  GPIO_InitStructure.GPIO_OType = GPIO_OType_PP; // 推挽方式输出
  GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;   // 输入时上(下)拉状态:上拉
  GPIO_Init(GPIOB, &GPIO_InitStructure);
}


我是直接copy 模板STM32L1xx_StdPeriph_Template的
时钟配置由STM32L1xx_Clock_Configuration_V1.0.0.excel生成的
void SystemInit (void)
{
  /*!< Set MSION bit */
  RCC->CR |= (uint32_t)0x00000100;
  /*!< Reset SW[1:0], HPRE[3:0], PPRE1[2:0], PPRE2[2:0], MCOSEL[2:0] and MCOPRE[2:0] bits */
  RCC->CFGR &= (uint32_t)0x88FFC00C;
  
  /*!< Reset HSION, HSEON, CSSON and PLLON bits */
  RCC->CR &= (uint32_t)0xEEFEFFFE;
  /*!< Reset HSEBYP bit */
  RCC->CR &= (uint32_t)0xFFFBFFFF;
  /*!< Reset PLLSRC, PLLMUL[3:0] and PLLDIV[1:0] bits */
  RCC->CFGR &= (uint32_t)0xFF02FFFF;
  /*!< Disable all interrupts */
  RCC->CIR = 0x00000000;
   
  /* Configure the System clock frequency, AHB/APBx prescalers and Flash settings */
  SetSysClock();
#ifdef VECT_TAB_SRAM
  SCB->VTOR = SRAM_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal SRAM. */
#else
  SCB->VTOR = FLASH_BASE | VECT_TAB_OFFSET; /* Vector Table Relocation in Internal FLASH. */
#endif
}

static void SetSysClock(void)
{
  __IO uint32_t StartUpCounter = 0, HSIStatus = 0;
  
  /* SYSCLK, HCLK, PCLK2 and PCLK1 configuration ---------------------------*/
  /* Enable HSI */
  RCC->CR |= ((uint32_t)RCC_CR_HSION);

  /* Wait till HSI is ready and if Time out is reached exit */
  do
  {
    HSIStatus = RCC->CR & RCC_CR_HSIRDY;
  } while((HSIStatus == 0) && (StartUpCounter != HSI_STARTUP_TIMEOUT));
  if ((RCC->CR & RCC_CR_HSIRDY) != RESET)
  {
    HSIStatus = (uint32_t)0x01;
  }
  else
  {
    HSIStatus = (uint32_t)0x00;
  }
   
  if (HSIStatus == (uint32_t)0x01)
  {
    /* Flash 0 wait state */
    FLASH->ACR &= ~FLASH_ACR_LATENCY;
   
    /* Disable Prefetch Buffer */
    FLASH->ACR &= ~FLASH_ACR_PRFTEN;
    /* Disable 64-bit access */
    FLASH->ACR &= ~FLASH_ACR_ACC64;
   
    /* Power enable */
    RCC->APB1ENR |= RCC_APB1ENR_PWREN;
  
    /* Select the Voltage Range 1 (1.8 V) */
    PWR->CR = PWR_CR_VOS_0;
  
  
    /* Wait Until the Voltage Regulator is ready */
    while((PWR->CSR & PWR_CSR_VOSF) != RESET)
    {
    }
      
    /* HCLK = SYSCLK /4*/
    RCC->CFGR |= (uint32_t)RCC_CFGR_HPRE_DIV4;
    /* PCLK2 = HCLK /1*/
    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE2_DIV1;
   
    /* PCLK1 = HCLK /1*/
    RCC->CFGR |= (uint32_t)RCC_CFGR_PPRE1_DIV1;
   
    /* Select HSI as system clock source */
    RCC->CFGR &= (uint32_t)((uint32_t)~(RCC_CFGR_SW));
    RCC->CFGR |= (uint32_t)RCC_CFGR_SW_HSI;
    /* Wait till HSI is used as system clock source */
    while ((RCC->CFGR & (uint32_t)RCC_CFGR_SWS) != (uint32_t)RCC_CFGR_SWS_HSI)
    {
    }
  }
  else
  {
    /* If HSI fails to start-up, the application will have wrong clock
       configuration. User can add here some code to deal with this error */
  }
}
沙发
关聿|  楼主 | 2011-12-21 16:32 | 只看该作者
补充:
  仿真器连不上,提示如下
  Wed Dec 21 16:29:33 2011: Fatal error: Failed to get CPU status after 4 retries   Session aborted!

Wed Dec 21 16:29:33 2011: Failed to load flash loader: C:\Program Files\IAR Systems\Embedded Workbench 5.4\arm\config\flashloader\ST\FlashSTM32L15xxxRAM16K.out

Wed Dec 21 16:29:33 2011: Failed to load flash loader: C:\Program Files\IAR Systems\Embedded Workbench 5.4\arm\config\flashloader\ST\FlashSTM32L15xxB.flash

使用特权

评论回复
板凳
nikita-fuck| | 2011-12-22 11:01 | 只看该作者
头一次听说你的情况。搞过152CBT6

使用特权

评论回复
地板
关聿|  楼主 | 2011-12-24 09:22 | 只看该作者
原因查明,为了防止干扰,把多余的管脚置为输出状态,在程序运行初始,在函数 void init_used_pin(void)   里,把管脚置为  集电极开路输出,其中包括了PA15,PA13,PA14,PB3(分别是TDI,TMS,TCK,TO)
故JATG口没法用了,也就连不上仿真器了,
所以第一次可以烧入程序,以后就再也连不上了。
不过我很奇怪,在STM32F系列的芯片里,我也是这样做的,但是不影响仿真调试的。STM32L系列就是不行?????

void init_used_pin(void)  // 初始化管脚
{  GPIO_InitTypeDef GPIO_InitStructure;
      
   RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOA, ENABLE);   // 使能GPIOA 时钟
   RCC_AHBPeriphClockCmd(RCC_AHBPeriph_GPIOB, ENABLE);   // 使能GPIOB 时钟
   
   GPIO_InitStructure.GPIO_Pin = GPIO_Pin_All;  // 指定管脚
   GPIO_InitStructure.GPIO_Speed = GPIO_Speed_400KHz;  // 管脚输出的速度:400KHz
   GPIO_InitStructure.GPIO_Mode = GPIO_Mode_OUT;  // 管脚工作模式:输出
   GPIO_InitStructure.GPIO_OType = GPIO_OType_OD; // 推挽方式输出 还是 集电极开路方式输出
   GPIO_InitStructure.GPIO_PuPd = GPIO_PuPd_UP;  // 输入时上(下)拉状态:上拉
   
        ////////  PA所有管脚   开漏输出  ///////////
   GPIO_Init(GPIOA, &GPIO_InitStructure);
   GPIO_ResetBits(GPIOA, GPIO_Pin_All);
       ////////  PB所有管脚   开漏输出  ///////////
   GPIO_Init(GPIOB, &GPIO_InitStructure);
   GPIO_ResetBits(GPIOB, GPIO_Pin_All);

使用特权

评论回复
5
dngd2008| | 2011-12-25 10:35 | 只看该作者
不会吧?你的样片应该没问题吧?如有需要,可联系我,QQ:275527307

使用特权

评论回复
发新帖 我要提问
您需要登录后才可以回帖 登录 | 注册

本版积分规则

20

主题

46

帖子

0

粉丝