上两篇《修改启动代码&重写向量表》《SRAM初始化&设置NVIC中断表偏移》文章中,我们设置了中断向量表,初始化了RAM,并重设了向量表的地址,本篇文章是相对重要的一篇,我们将设置芯片时钟。

   1、新建CortexM3.h头文件

   在.\DeviceCode\Targets\Native\CortexM3目录中新建 CortexM3.h文件,并编写如下代码:

   
   
   
   
  1. #ifndef _CORTEXM3_H_  
  2.  
  3. #define _CORTEXM3_H_1  
  4.  
  5.    
  6.  
  7. #include   
  8.  
  9.    
  10.  
  11. typedef volatile unsigned long  VU32;  
  12.  
  13. typedef volatile unsigned short VU16;  
  14.  
  15. typedef volatile unsigned char  VU8;  
  16.  
  17.    
  18.  
  19. extern "C" 
  20.  
  21. {  
  22.  
  23.     void BootstrapCode_Clocks();  
  24.  
  25. }  
  26.  
  27.    
  28.  
  29. /*------------------------ Reset and Clock Control ---------------------------*/ 
  30.  
  31. struct CortexM3_RCC  
  32.  
  33. {  
  34.  
  35.     static const UINT32 c_Base = 0x40021000;  
  36.  
  37.       
  38.  
  39.     static const    UINT8 FLAG_HSIRDY = ((UINT8)0x20);  
  40.  
  41.     static const    UINT8 FLAG_HSERDY = ((UINT8)0x31);  
  42.  
  43.    
  44.  
  45.     /****/ volatile UINT32  CR;  
  46.  
  47.     static const    UINT32  CR_HSEBYP_Reset = ((UINT32)0xFFFBFFFF);  
  48.  
  49.     static const    UINT32  CR_HSEBYP_Set = ((UINT32)0x00040000);  
  50.  
  51.     static const    UINT32  CR_HSEON_Reset = ((UINT32)0xFFFEFFFF);  
  52.  
  53.     static const    UINT32  CR_HSEON_Set = ((UINT32)0x00010000);  
  54.  
  55.     static const    UINT32  CR_HSITRIM_Mask = ((UINT32)0xFFFFFF07);  
  56.  
  57.    
  58.  
  59.     /****/ volatile UINT32  CFGR;  
  60.  
  61.     static const    UINT32  CFGR_SYSCLK_Div1 = ((UINT32)0x00000000);  
  62.  
  63.     static const    UINT32  CFGR_SYSCLK_Div2 = ((UINT32)0x00000080);  
  64.  
  65.     static const    UINT32  CFGR_SYSCLK_Div4 = ((UINT32)0x00000090);  
  66.  
  67.     static const    UINT32  CFGR_SYSCLK_Div8 = ((UINT32)0x000000A0);  
  68.  
  69.     static const    UINT32  CFGR_SYSCLK_Div16 = ((UINT32)0x000000B0);  
  70.  
  71.     static const    UINT32  CFGR_HCLK_Div1 = ((UINT32)0x00000000);  
  72.  
  73.     static const    UINT32  CFGR_HCLK_Div2 = ((UINT32)0x00000400);  
  74.  
  75.     static const    UINT32  CFGR_HCLK_Div4 = ((UINT32)0x00000500);  
  76.  
  77.        
  78.  
  79.     // 省略部分代码 .....  
  80.  
  81.       
  82.  
  83.     /****/ volatile UINT32  APB1RSTR;  
  84.  
  85.     /****/ volatile UINT32  AHBENR;  
  86.  
  87.     /****/ volatile UINT32  BDCR;  
  88.  
  89.     /****/ volatile UINT32  CSR;  
  90.  
  91.    
  92.  
  93.     static void Initialize();  
  94.  
  95.     static bool GetFlagStatus(UINT8 Flag);  
  96.  
  97. };  
  98.  
  99.    
  100.  
  101. struct CortexM3  
  102.  
  103. {  
  104.  
  105.     static CortexM3_RCC  & RCC()   { return *(CortexM3_RCC *)(size_t)(CortexM3_RCC::c_Base); }  
  106.  
  107. };  
  108.  
  109.    
  110.  
  111. #endif // _CORTEXM3_H_1  
  112.  

 

 

   2、编写BootStrap代码

   我们从.\DeviceCode\Drivers\Stubs\Processor\stubs_bootstrap目录到.\DeviceCode\Targets\Native\CortexM3\DeviceCode,并修改目录的名字为BootStrap,下一步我们在BootStrap.cpp文件编写如下代码:

   

   
   
   
   
  1. #include   
  2.  
  3. #include "..\CortexM3.h"  
  4.  
  5.    
  6.  
  7. //--//  
  8.  
  9.    
  10.  
  11. #pragma arm section code = "SectionForBootstrapOperations"  
  12.  
  13.    
  14.  
  15. void __section(SectionForBootstrapOperations) CortexM3_RCC::Initialize (void)  
  16.  
  17. {  
  18.  
  19.          CortexM3_RCC &RCC = CortexM3::RCC();  
  20.  
  21.    
  22.  
  23.         // RCC system reset(for debug purpose)  
  24.  
  25.          /* Set HSION bit */ 
  26.  
  27.          RCC.CR |= (UINT32)0x00000001;  
  28.  
  29.    
  30.  
  31.          /* Reset SW[1:0], HPRE[3:0], PPRE1[2:0], PPRE2[2:0], ADCPRE[1:0] and MCO[2:0] bits */ 
  32.  
  33.          RCC.CFGR &= (UINT32)0xF8FF0000;  
  34.  
  35.    
  36.  
  37.          /* Reset HSEON, CSSON and PLLON bits */ 
  38.  
  39.          RCC.CR &= (UINT32)0xFEF6FFFF;  
  40.  
  41.    
  42.  
  43.          // 省略部分代码 .....  
  44.  
  45.      
  46.  
  47.          /* Enable GPIOA, GPIOB, GPIOF, GPIOG and AFIO clocks */ 
  48.  
  49.          RCC.APB2ENR |= CortexM3_RCC::APB2RSTR_GPIOA | CortexM3_RCC::APB2RSTR_GPIOB | CortexM3_RCC::APB2RSTR_GPIOF |CortexM3_RCC::APB2RSTR_GPIOG |CortexM3_RCC::APB2RSTR_AFIO;  
  50.  
  51. }  
  52.  
  53.    
  54.  
  55. bool __section(SectionForBootstrapOperations)  CortexM3_RCC::GetFlagStatus(UINT8 Flag)  
  56.  
  57. {  
  58.  
  59.          UINT32 tmp = 0;  
  60.  
  61.          UINT32 statusreg = 0;  
  62.  
  63.          CortexM3_RCC &RCC = CortexM3::RCC();  
  64.  
  65.    
  66.  
  67.          /* Get the RCC register index */ 
  68.  
  69.          tmp = Flag >> 5;  
  70.  
  71.          if (tmp == 1)               /* The flag to check is in CR register */ 
  72.  
  73.          {  
  74.  
  75.                    statusreg = RCC.CR;  
  76.  
  77.          }  
  78.  
  79.          else if (tmp == 2)          /* The flag to check is in BDCR register */ 
  80.  
  81.          {  
  82.  
  83.                    statusreg = RCC.BDCR;  
  84.  
  85.          }  
  86.  
  87.          else                       /* The flag to check is in CSR register */ 
  88.  
  89.          {  
  90.  
  91.                    statusreg = RCC.CSR;  
  92.  
  93.          }  
  94.  
  95.    
  96.  
  97.          /* Get the flag position */ 
  98.  
  99.          tmp = Flag & ((UINT8)0x1F);  
  100.  
  101.          return ((statusreg & ((UINT32)1 << tmp)) != 0);  
  102.  
  103. }  
  104.  
  105.    
  106.  
  107.    
  108.  
  109. void __section(SectionForBootstrapOperations) BootstrapCode_Clocks()  
  110.  
  111. {  
  112.  
  113.      CortexM3_RCC::Initialize();  
  114.  
  115. }  
  116.  
  117.    
  118.  
  119. extern "C" 
  120.  
  121. {  
  122.  
  123.    
  124.  
  125. void __section(SectionForBootstrapOperations) BootstrapCode()  
  126.  
  127. {  
  128.  
  129.           BootstrapCode_Clocks();  
  130.  
  131. }  
  132.  
  133.    
  134.  
  135. }  
  136.  
  137.    
  138.  
  139. #pragma arm section code  
  140.  
  141.    
  142.  

  3、修改.\Solutions\STM3210E\NativeSample\NativeSample.proj文件

   在NativeSample.proj文件中作如下修改: 

 

  

   
   
   
   
  1. <ItemGroup> 
  2.  
  3.     <RequiredProjects Include="$(SPOCLIENT)\DeviceCode\Targets\Native\CortexM3\DeviceCode\stubs_bootstrap\dotNetMF.proj" /> 
  4.  
  5.     <DriverLibs Include="cpu_bootstrap_stubs.$(LIB_EXT)" /> 
  6.  
  7.   ItemGroup> 
  8.  

  修改为:

 

   
   
   
   
  1. <ItemGroup> 
  2.  
  3.    <RequiredProjects Include="$(SPOCLIENT)\DeviceCode\Targets\Native\CortexM3\DeviceCode\BootStrap\dotNetMF.proj" /> 
  4.  
  5.    <DriverLibs Include="BootStrap.$(LIB_EXT)" /> 
  6.  
  7.  ItemGroup> 

 

  4、编译修改并调试运行,我想这次会有很大的成就感,因为LED闪烁的节奏明显的加快了,我们的CPU在高速运行了!

 

       即将过去的2010年的前三天,对我来说是辛苦的三天,平均每天工作16个小时以上,不仅编写了相关代码,还写了以上六篇文章。希望我的这些努力能点燃.Net Micro Framework爱好者心中的热情,动起手来一起移植.Net Micro Framework,其实这对自己的嵌入式开发功力的提高也大有裨益。明天就要上班了,我将又回到开发Wifi相关接口的工作上来,后续的文章我想只有到下周末才能相见了,到那时我们将编写串口驱动,系统的一些调试信息将可以通过串口传输给PC机上的串口调试程序,这一步将是关键的一步,非常值得的期待,希望我能顺利完成这步工作!