编程驱动的差异

STM8L001和STM8L101系列单片机片上的EEPROM的驱动方式和STM8L05X或STM8L15X系列单片机的驱动方式存在差异,由两组单片机的参考手册中的内存结构图可获知:

  • STM8L001系列单片机,内部EEPROM包含在MAIN FLASH上,不能按常规的EEPROM解锁MASS密钥进行解锁;
  • STM8L001组驱动内部EEPROM时,进行写保护的解锁的时候,应该解锁的是FLASH的MASS密钥(往**FLASH_PUKR寄存器写入0x56,0xAE**),而非EEPROM的密钥(往FLASH_DUKR寄存器写入0xAE,0x56);
  • STM8L15X系列单片机,内部EEPROM独立于MAIN FLASH,可按常规的EEPROM解锁MASS密钥进行解锁
  • STM8L15X组驱动内部EEPROM时,进行写保护的解锁的时候,按常规的EEPROM解锁MASS密钥进行解锁即可。

image.png
图1 STM8L001/101系列单片机内存分配图
image.png
图2 STM8L05X/15X系列单片机内存分配图

遗留问题

  • STM8L001芯片执行EEPROM的block写入操作,会出现重启现象,原因暂不明确;STM8L15x芯片无此现象;
  • STM8L001芯片执行eeprom写入操作时,推荐直接调用FLASH_ProgramByte(add,data)函数接口单字节写入:

    1. /*******************************************************************************
    2. **函数名称:void EEPROM_Block_Write(u16 start_address, u8 block_Num, u16 *Data)
    3. **功能描述:向EEPROM中固定地址写入一个或多个64字节(1个block)数据
    4. **入口参数:
    5. start_address : EEPROM块首地址
    6. block_Num : 读取的block数量
    7. *Data : 存储数据的数组
    8. **输出:无
    9. *******************************************************************************/
    10. void EEPROM_Block_Write(u16 start_address, u8 block_Num, u16 *Data)
    11. {
    12. u8 DataH = 0;
    13. u8 DataL = 0;
    14. u16 add = 0;
    15. add = start_address;
    16. FLASH_DeInit();
    17. /* Define flash programming Time*/
    18. FLASH_SetProgrammingTime(FLASH_ProgramTime_Standard);
    19. //STM8L001EEPROM需要擦写FLASH,非EEPROM
    20. FLASH_Unlock(FLASH_MemType_Program);
    21. /* Wait until Flash Program area unlocked flag is set*/
    22. while (FLASH_GetFlagStatus(FLASH_FLAG_PUL) == RESET)
    23. {
    24. }
    25. //test
    26. /* for (u16 i = 0; i < IRBUFSIZE; i++)
    27. {
    28. if (i == 100)
    29. {
    30. dataBuf[i] = 0xfffd;
    31. }
    32. else
    33. {
    34. dataBuf[i] = newval++;
    35. }
    36. } */
    37. for (u16 i = 0; i < (FLASH_BLOCK_SIZE * block_Num); i++)
    38. {
    39. // 大端模式,低位地址存高位数据
    40. DataH = (u8)(Data[i] >> 8);
    41. FLASH_ProgramByte(add, DataH);
    42. /* Wait until End of programming flag is set*/
    43. while (FLASH_GetFlagStatus(FLASH_FLAG_EOP) == RESET)
    44. {
    45. }
    46. add++;
    47. DataL = (u8)Data[i];
    48. FLASH_ProgramByte(add, DataL);
    49. add++;
    50. /* Wait until End of programming flag is set*/
    51. while (FLASH_GetFlagStatus(FLASH_FLAG_EOP) == RESET)
    52. {
    53. }
    54. if (Data[i] == 0xFFFD) //读到结束字符,则停止再写入数据
    55. {
    56. break;
    57. }
    58. }
    59. /* lock flash data eeprom memory */
    60. FLASH_Lock(FLASH_MemType_Program);
    61. LED_Normal_Flash(); //写入完成反馈
    62. }
  • STM8L001芯片读取eeprom的数据时,调用FLASH_ReadByte(add)函数接口单字节读取数据:

    1. /*******************************************************************************
    2. **函数名称:void EEPROM_Block_Read(u16 start_address, u8 block_Num, u16 *Data)
    3. **功能描述:向EEPROM中固定地址读出1个或多个64个字节(1个block)数据
    4. **入口参数:
    5. start_address : EEPROM块首地址
    6. block_Num : 读取的block数量
    7. *Data : 存储数据的数组
    8. **输出:无
    9. *******************************************************************************/
    10. void EEPROM_Block_Read(u16 start_address, u8 block_Num, u16 *Data)
    11. {
    12. u16 DataL = 0;
    13. u16 DataH = 0;
    14. u16 add = 0;
    15. add = start_address;
    16. // test
    17. /* for (u16 i = 0; i < IRBUFSIZE; i++)
    18. {
    19. dataBuf[i] = 0;
    20. } */
    21. for (u16 i = 0; i < (FLASH_BLOCK_SIZE * block_Num); i++)
    22. {
    23. // 大端模式,低位地址存高位数据
    24. DataH = FLASH_ReadByte(add);
    25. add++;
    26. delay_ms(1);
    27. DataL = FLASH_ReadByte(add);
    28. add++;
    29. delay_ms(1);
    30. Data[i] = (DataH << 8) | DataL;
    31. if (Data[i] == 0xFFFD) //读到结束字符,则停止再读取数据
    32. {
    33. break;
    34. }
    35. }
    36. }