EEPROM_24Cxx_Remap.h 12.5 KB
Newer Older
时昊's avatar
时昊 committed
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230


#ifndef   _EEPROM_24CXX_REMAP_H_
#define   _EEPROM_24CXX_REMAP_H_



/***************************************************************************************************************************
1.存储器地址重映射

因为单次写入的最大长度为一页(Page),所以重映射以页(Page)为单位,EEPROM存储器的空间被划分为四等份,形成一个有N(N = 总页数 / 4)行
4列的页(Page)矩阵

Page  ^                    Physical                    Physical                    Physical                    Physical
Row   |                    Address                     Address                     Address                     Address
      |                     
      |   +---------------+ MC/4-1    +---------------+ 2MC/4-1   +---------------+ 3MC/4-1   +---------------+  MC-1
T/4-1 |   | Page (T/4-1)  |           | Page (2T/4-1) |           | Page (3T/4-1) |           |  Page (T-1)   |
      |   +---------------+           +---------------+           +---------------+           +---------------+
  :   |   |       :       |           |       :       |           |       :       |           |       :       |
  :   |   |       :       |           |       :       |           |       :       |           |       :       |
  :   |   |       :       |           |       :       |           |       :       |           |       :       |
      |   +---------------+           +---------------+           +---------------+           +---------------+
  1   |   |    Page (1)   |           | Page (T/4+1)  |           | Page (2T/4+1) |           | Page (3T/4+1) |
      |   +---------------+           +---------------+           +---------------+           +---------------+
  0   |   |    Page (0)   |           |  Page (T/4)   |           |  Page (2T/4)  |           |  Page (3T/4)  |
      |   +---------------+   0       +---------------+   MC/4    +---------------+  2MC/4    +---------------+  3MC/4
      +------------------------------------------------------------------------------------------------------------------>
                  0                           1                           2                           3           Page Col

* MC = Memory Capacity  存储器容量
* T  = Total pages      总页数

2.数据类型

因数据的安全性等级不同,设置三种数据存储类型:

 - HiRel     高可靠性数据存储.该存储类型的数据存取单元由数据字节和校验字节组成,其中校验字节为数据字节按位取反产生.在进行数据
             存储时,每个数据存取单元会在页矩阵的同一行(Row)的第1、2、3列(Col)各存储一次,第0列为保留页不使用.在进行数据读取时,
             读出的每个数据存取单元中的数据字节会使用同一单元中的校验字节进行校验,当有数据校验失败时, 仍然有存储于其他位置数
             据单元作为备份,从而保证了数据存储的可靠性.
             提高可靠性的另一个途径是页矩阵同一行(Row)中的不同列(Col)其物理地址并不连续而是分散于EEPROM之中的,当EEPROM遭受外
             界干扰而丢失了某一区块的数据时,虽然存储于该区域的数据存取单元将会一同丢失,但存储于其他区域的未受影响的数据单元
             则仍可以保证数据可以顺利被读取.
             
 - ExtLife   扩展寿命的数据存储.EEPROM的擦写周期约为 1,000,000 次,对于某些需要频繁擦写的数据,这一周期数也许并不能满足擦写次数
             的要求.扩展寿命的数据存储则是将其数据存取单元滚动地存储于页矩阵的3行(Row)4列(Col)的12个不同的位置上,从而将寿命延
             长了12倍,达到 12,000,000 次擦写.这种存储类型的数据存取单元分为三部分,第一部分为16位的滚动计数器,第二部分为数据字
             节,第三部分为16位的数据字节的Checksum.每次存储数据时,新的数据将会滚动存储于数据所属页矩阵区域中的一个新的位置上,
             同时,保存的滚动计数器将会加1.读取数据时,于数据所属页矩阵区域中的所有的滚动计数器将都被读取,根据滚动计数器的值判
             断哪一个数据存储单元中包含的是最新的数据.
             扩展寿命的数据存储仍然可以保证较高的数据可靠性,存储数据时,会同时计算数据字节的Checksum一并存储,读出数据时使用该
             CheckSum对读出的数据字节进行校验,如果校验失败,则读取前一次存储的数据,直至数据被读出.另一方面,与高可靠性数据存储
             相同,数据存取单元分散于EEPROM中存储,而避免了外界干扰造成的数据意外丢失.
             
 - Normal    普通数据存储.用于存储一般性的数据,这种存储方式的安全性依赖EEPROM自身的可靠性,用于存放一般性的数据
 
 3.数据分布
 
 +-------------------+-------+------------+------------+------------+------------+
 |     Data Type     |  Row  |   Col 0    |   Col 1    |   Col 2    |   Col 3    |
 +-------------------+-------+------------+------------+------------+------------+
 |                   | T/4-1 | NPage(M-4) | NPage(M-3) | NPage(M-2) | NPage(M-1) |
 |                   +-------+------------+------------+------------+------------+
 |                   |   :   |     :      |     :      |     :      |     :      |
 |                   |   :   |     :      |     :      |     :      |     :      |
 |      Normal       +-------+------------+------------+------------+------------+
 |                   |  N+1  |  NPage(4)  |  NPage(5)  |  NPage(6)  |  NPage(7)  |
 |                   +-------+------------+------------+------------+------------+
 |                   |   N   |  NPage(0)  |  NPage(1)  |  NPage(2)  |  NPage(3)  |
 +---------+---------+-------+------------+------------+------------+------------+
 |         |    :    |   :   |     :      |     :      |     :      |     :      |
 |         |    :    |   :   |     :      |     :      |     :      |     :      |
 |         +---------+-------+------------+------------+------------+------------+
 |         |         |  E+5  |  EPage(8)  |  EPage(9)  |  EPage(10) |  EPage(11) |
 |         |         +-------+------------+------------+------------+------------+
 |         | EData 1 |  E+4  |  EPage(4)  |  EPage(5)  |  EPage(6)  |  EPage(7)  |
 |         |         +-------+------------+------------+------------+------------+
 | ExtLife |         |  E+3  |  EPage(0)  |  EPage(1)  |  EPage(2)  |  EPage(3)  |
 |         +---------+-------+------------+------------+------------+------------+
 |         |         |  E+2  |  EPage(8)  |  EPage(9)  |  EPage(10) |  EPage(11) |
 |         |         +-------+------------+------------+------------+------------+
 |         | EData 0 |  E+1  |  EPage(4)  |  EPage(5)  |  EPage(6)  |  EPage(7)  |
 |         |         +-------+------------+------------+------------+------------+
 |         |         |   E   |  EPage(0)  |  EPage(1)  |  EPage(2)  |  EPage(3)  |
 +---------+---------+-------+------------+------------+------------+------------+
 |         |    :    |   :   |     :      |     :      |     :      |     :      |
 |         |    :    |   :   |     :      |     :      |     :      |     :      |
 |         +---------+-------+------------+------------+------------+------------+
 | HiRel   | HData 1 |   1   |   Rsvd.    |  HPage(0)  |  HPage(1)  |  HPage(2)  |
 |         +---------+-------+------------+------------+------------+------------+
 |         | HData 0 |   0   |   Rsvd.    |  HPage(0)  |  HPage(1)  |  HPage(2)  |
 +---------+---------+-------+------------+------------+------------+------------+
 
 * T     = Total pages                总页数
 * M     = Total Normal Data pages    普通数据存储总页数
 * N     = Start row of Normal Data   普通数据存储起始行
 * NPage = Normal Data page           普通数据存储页
 * E     = Start row of ExtLife Data  扩展寿命的数据存储起始行
 * EPage = ExtLife Data page          扩展寿命的数据存储页
 * EData = ExtLife Data               扩展寿命的数据
 * HPage = HiRel Data page            高可靠性数据存储页
 * HData = HiRel Data                 高可靠性数据
 
***************************************************************************************************************************/

/***************************************************************************************************************************
存储器配置
***************************************************************************************************************************/
#define   EEPPROM_HIREL_DATA_NUM                  2              //高可靠性数据总数
#define   EEPPROM_EXTLIFE_DATA_NUM                0              //扩展寿命的数据总数

#define   EEPPROM_DATA_BUFFER_SIZE                64//32

#define   EEPPROM_DEVICE_ADDR                     0              //存储器的硬件地址

/***************************************************************************************************************************
参数预处理
***************************************************************************************************************************/
/*** 存储器全局 ***/
#define   EEPPROM_TOTAL_ROW_NUM                   (EEPROM_TOTAL_PAGE_NUM / 4)

/*** 高可靠性数据 ***/
#define   EEPPROM_HIREL_DATA_MAX_LEN              (EEPROM_PAGE_SIZE / 2)

/*** 扩展寿命的数据 ***/
#define   EEPPROM_EXTLIFE_DATA_ROW_OFFSEET        EEPPROM_HIREL_DATA_NUM
#define   EEPPROM_EXTLIFE_DATA_MAX_LEN            (EEPROM_PAGE_SIZE - 4)

/*** 普通数据 ***/
#define   EEPPROM_DATA_ROW_OFFSEET                (EEPPROM_HIREL_DATA_NUM + EEPPROM_EXTLIFE_DATA_NUM * 3)
#define   EEPPROM_DATA_TOTAL_PAGE_NUM             ((EEPPROM_TOTAL_ROW_NUM - EEPPROM_DATA_ROW_OFFSEET) * 4)
#define   EEPPROM_DATA_MAX_ADDR                   (EEPROM_PAGE_SIZE * EEPPROM_DATA_TOTAL_PAGE_NUM - 1)

/***************************************************************************************************************************
数据类型
***************************************************************************************************************************/
#define   EEPROM_HIREL_DATA_TYPE                  0
#define   EEPROM_EXTLIFE_DATA_TYPE                1
#define   EEPROM_NORMAL_DATA_TYPE                 2

/***************************************************************************************************************************
数据状态
***************************************************************************************************************************/
typedef enum
{
  EEPROM_DATA_OK = 0,
  EEPROM_DATA_PARTIAL_LOST,
  EEPROM_DATA_LOST,
  EEPROM_DATA_ADDR_ERR,
  EEPROM_DATA_LEN_ERR,
  EEPROM_DATA_RW_FAIL,
  EEPROM_MEMORY_BUSY,
  EEPROM_MEMORY_ABSENT,
}EEPROMAccessStatusEnum;       

/***************************************************************************************************************************
数据存取控制                               
********************* ******************************************************************************************************/
#if (EEPPROM_DATA_BUFFER_SIZE < EEPROM_PAGE_SIZE)
  
  typedef struct
  {                                        
    uint8_t   Type;
    uint8_t   Data[EEPROM_PAGE_SIZE];
    uint16_t  DataLen;
    uint8_t   Row;
    uint8_t   Col;
    uint8_t   Offset;
    uint8_t   Retry;
    uint8_t   WrLen;
    uint16_t  WrCnt;
    uint8_t   Busy;
    EEPROMAccessStatusEnum  Result;
  }EEPROMDataWrCtrlStruct;
  
#else
  
  typedef struct
  {
    uint8_t   Type;
    uint8_t   Data[EEPPROM_DATA_BUFFER_SIZE];
    uint16_t  DataLen;
    uint8_t   Row;
    uint8_t   Col;
    uint8_t   Offset;
    uint8_t   Retry;
    uint8_t   WrLen;
    uint16_t  WrCnt;
    uint8_t   Busy;
    EEPROMAccessStatusEnum  Result;
  }EEPROMDataWrCtrlStruct;

#endif


EXTERN  EEPROMDataWrCtrlStruct      EEPROMDataWrCtrl;

/***************************************************************************************************************************
函数声明
***************************************************************************************************************************/
/*** 外部函数 ***/
EEPROMAccessStatusEnum EEPROM_Data_Write(uint8_t Type, uint16_t Addr, uint8_t *pData, uint8_t Len);
EEPROMAccessStatusEnum EEPROM_Get_Data_Write_Status(void);
EEPROMAccessStatusEnum EEPROM_Startup_Data_Read(uint8_t Type, uint16_t Addr, uint8_t *pData, uint8_t Len);
void    EEPROM_Access_Service(void);

/**************************************************************************************************************************/
/*** HiRel类型数据读写 ***/
EEPROMAccessStatusEnum EEPROM_HiRel_Data_Write(uint16_t Addr, uint8_t *pData, uint8_t Len);
EEPROMAccessStatusEnum EEPROM_Startup_HiRel_Data_Read(uint16_t Addr, uint8_t *pData, uint8_t Len);
EEPROMAccessStatusEnum EEPROM_Startup_HiRel_Page_Read(uint8_t Row, uint8_t Col, uint8_t *pData, uint8_t Len);
uint8_t EEPROM_HiRel_Data_Check(uint8_t *pData, uint8_t Len);
void    EEPROM_HiRel_Data_Write_Service(void);

/*** ExtLife类型数据读写 ***/

/*** Normal类型数据读写 ***/
EEPROMAccessStatusEnum EEPROM_Normal_Data_Write(uint16_t Addr, uint8_t *pData, uint16_t Len);
EEPROMAccessStatusEnum EEPROM_Startup_Normal_Data_Read(uint16_t Addr, uint8_t *pData, uint8_t Len);
void    EEPROM_Normal_Data_Write_Service(void);

/*** 共用字符串处理 ***/
void    EEPROM_Copy_Data(uint8_t *pDstData, uint8_t *pSrcData, uint8_t Len);
uint8_t EEPROM_Compare_Data(uint8_t *pDstData, uint8_t *pSrcData, uint8_t Len);




#endif