PCF8653 RTC时钟模块时间异常问题修复
1.问题描述:
时间设置到2020-01-01 00:00:00之前,时间不能跳到2020-01-01 00:00:00;
https://www.nxp.com.cn/docs/zh/data-sheet/PCF8563.pdf
1 #include "stdio.h" 2 #include "lib_i2c.h" 3 //============================================================================== 4 // 5 // DEFINES 6 // 7 //============================================================================== 8 9 #define I2C_ADDR (0xA2>>1) 10 11 //============================================================================== 12 // 13 // EXTERNAL VARIABLES REFERENCE 14 // 15 //============================================================================== 16 17 //============================================================================== 18 // 19 // EXTERNAL FUNCTION PROTOTYPES 20 // 21 //============================================================================== 22 23 //============================================================================== 24 // 25 // VARIABLES 26 // 27 //============================================================================== 28 29 //============================================================================== 30 // 31 // FUNCTIONS 32 // 33 //============================================================================== 34 s32 gm_pcf8563_check() 35 { 36 s32 REG0,REG1,REG2; 37 REG0 = gm_i2c_read(I2C_ADDR,0x02); 38 REG1 = gm_i2c_read(I2C_ADDR,0x03); 39 REG2 = gm_i2c_read(I2C_ADDR,0x04); 40 printf("0:%d,1:%d,2:%d\n",REG0,REG1,REG2); 41 if((REG0 < 0) || (REG1 < 0) || (REG2 < 0) || (REG0 == 0xFF) || (REG1 == 0xFF) || (REG2 == 0xFF)) 42 { 43 printf("pcf8563 not exist\n"); 44 return -1; 45 } 46 else 47 { 48 printf("pcf8563 exist\n"); 49 return 0; 50 } 51 } 52 53 54 s32 gm_pcf8563_gettime(u32 *year, u32 *mon, u32 *mday, 55 u32 *hour, u32 *min, u32 *sec) 56 { 57 #if 1 58 struct i2c_msg msgs[2]; 59 unsigned char tmp[2], tmp2[7]; 60 61 tmp[0] = 0x2 & 0xFF; 62 msgs[0].addr = I2C_ADDR; 63 msgs[0].flags = 0; 64 msgs[0].len = 1; 65 msgs[0].buf = tmp; 66 67 tmp2[0] = 0; 68 msgs[1].addr = I2C_ADDR; 69 msgs[1].flags = 1; 70 msgs[1].len = 7; 71 msgs[1].buf = tmp2; 72 73 if (gm_i2c_transfer(msgs, 2) != 2){ 74 printf("PCF8563 Get Fail\n"); 75 return FAIL; 76 } 77 #if 0 78 { 79 int i; 80 printf("\n\n"); 81 for(i=0; i<7; i++){ 82 printf("%d, ", tmp2[i]); 83 } 84 printf("\n\n"); 85 } 86 #endif 87 *sec = (u32)(((tmp2[0]>>4)&0x7)*10 + (tmp2[0]&0x0F)); 88 *min = (u32)(((tmp2[1]>>4)&0x7)*10 + (tmp2[1]&0x0F)); 89 *hour = (u32)(((tmp2[2]>>4)&0x3)*10 + (tmp2[2]&0x0F)); 90 *mday = (u32)(((tmp2[3]>>4)&0x3)*10 + (tmp2[3]&0x0F)); 91 *mon = (u32)(((tmp2[5]>>4)&0x1)*10 + (tmp2[5]&0x0F) + ((tmp2[5]&BIT7)? 1 : 0)); 92 *year = (u32)(((tmp2[6]>>4)&0xF)*10 + (tmp2[6]&0x0F)) + 2000; 93 printf("hi,gm_pcf8563_gettime:%04d/%02d/%02d, %02d:%02d:%02d\n", *year, *mon, *mday, *hour, *min, *sec); 94 return SUCCESS; 95 96 #else 97 s32 value; 98 99 //lib_I2C_SetAddressMode(I2C_ADDR_MODE_8BIT); 100 101 if ((value = gm_i2c_read(I2C_ADDR, 0x02)) < 0) 102 { 103 goto pcf8563_get_fail; 104 } 105 else 106 { 107 *sec = (int)(((value>>4)&0x7)*10 + (value&0x0F)); 108 } 109 110 if ((value = gm_i2c_read(I2C_ADDR, 0x03)) < 0) 111 { 112 goto pcf8563_get_fail; 113 } 114 else 115 { 116 *min = (int)(((value>>4)&0x7)*10 + (value&0x0F)); 117 } 118 119 if ((value = gm_i2c_read(I2C_ADDR, 0x04)) < 0) 120 { 121 goto pcf8563_get_fail; 122 } 123 else 124 { 125 *hour = (int)(((value>>4)&0x3)*10 + (value&0x0F)); 126 } 127 128 if ((value = gm_i2c_read(I2C_ADDR, 0x05)) < 0) 129 { 130 goto pcf8563_get_fail; 131 } 132 else 133 { 134 *mday = (int)(((value>>4)&0x3)*10 + (value&0x0F)); 135 } 136 137 if ((value = gm_i2c_read(I2C_ADDR, 0x07)) < 0) 138 { 139 goto pcf8563_get_fail; 140 } 141 else 142 { 143 *mon = (int)(((value>>4)&0x1)*10 + (value&0x0F) + ((value&BIT7)? 1 : 0)); 144 } 145 146 if ((value = gm_i2c_read(I2C_ADDR, 0x08)) < 0) 147 { 148 goto pcf8563_get_fail; 149 } 150 else 151 { 152 *year = (int)(((value>>4)&0xF)*10 + (value&0x0F)) + 1900; /* years since 1900 */ 153 } 154 155 printf("gm_pcf8563_gettime: %d-%d-%d %d:%d:%d\n", *year, *mon, *mday, *hour, *min, *sec); 156 157 return SUCCESS; 158 159 pcf8563_get_fail: 160 printf("PCF8563 Get Fail\n"); 161 return FAIL; 162 #endif 163 } 164 165 s32 gm_pcf8563_settime(u32 year, u32 mon, u32 mday, 166 u32 hour, u32 min, u32 sec) 167 { 168 if (year < 2000 || year > 2100 || mon > 12 || mday > 31 || //steven 20130410 169 hour > 23 || min > 59 || sec > 59) 170 { 171 return FAIL; 172 } 173 else 174 { 175 //lib_I2C_SetAddressMode(I2C_ADDR_MODE_8BIT); 176 177 if (gm_i2c_write(I2C_ADDR, 0x02, (((sec/10)&0x7)<<4)|((sec%10)&0xF)) < 0) 178 { 179 goto pcf8563_set_fail; 180 } 181 182 if (gm_i2c_write(I2C_ADDR, 0x03, (((min/10)&0x7)<<4)|((min%10)&0xF)) < 0) 183 { 184 goto pcf8563_set_fail; 185 } 186 187 if (gm_i2c_write(I2C_ADDR, 0x04, (((hour/10)&0x3)<<4)|((hour%10)&0xF)) < 0) 188 { 189 goto pcf8563_set_fail; 190 } 191 192 if (gm_i2c_write(I2C_ADDR, 0x05, (((mday/10)&0x3)<<4)|((mday%10)&0xF)) < 0) 193 { 194 goto pcf8563_set_fail; 195 } 196 197 if (gm_i2c_write(I2C_ADDR, 0x07, (((mon/10)&0x1)<<4)|((mon%10)&0xF)) < 0) 198 { 199 goto pcf8563_set_fail; 200 } 201 202 if (gm_i2c_write(I2C_ADDR, 0x08, ((((year-2000)/10)&0xF)<<4)|(((year-2000)%10)&0xF)) < 0) 203 { 204 goto pcf8563_set_fail; 205 } 206 } 207 printf("\n\n\ngm_pcf8563_settime22:%04d/%02d/%02d, %02d:%02d:%02d\n\n\n\n", year, mon, mday, hour, min, sec); 208 return SUCCESS; 209 210 pcf8563_set_fail: 211 printf("PCF8563 Set Fail\n"); 212 return FAIL; 213 }