aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/rtc/rtc-rx8025.c
diff options
context:
space:
mode:
authorAlexandre Belloni <alexandre.belloni@free-electrons.com>2015-07-26 04:13:31 -0400
committerAlexandre Belloni <alexandre.belloni@free-electrons.com>2015-09-05 07:19:11 -0400
commit6f0a8cfebb898b88fb0d934d7a44a6d4c98d5285 (patch)
treee79796b8ed107ffde4647337e51ec4dcf3c33ebb /drivers/rtc/rtc-rx8025.c
parent2e10e74df72ff0f8ea65eb1ee6e39ed8278a91bf (diff)
rtc: rx8025: don't reset the time
Stop setting the time to epoch when it is invalid. The proper way to handle that is to return an error when it is invalid instead of returning an incorrect value. Signed-off-by: Alexandre Belloni <alexandre.belloni@free-electrons.com>
Diffstat (limited to 'drivers/rtc/rtc-rx8025.c')
-rw-r--r--drivers/rtc/rtc-rx8025.c38
1 files changed, 22 insertions, 16 deletions
diff --git a/drivers/rtc/rtc-rx8025.c b/drivers/rtc/rtc-rx8025.c
index 771558602409..d158a640299e 100644
--- a/drivers/rtc/rtc-rx8025.c
+++ b/drivers/rtc/rtc-rx8025.c
@@ -166,9 +166,23 @@ out:
166static int rx8025_get_time(struct device *dev, struct rtc_time *dt) 166static int rx8025_get_time(struct device *dev, struct rtc_time *dt)
167{ 167{
168 struct rx8025_data *rx8025 = dev_get_drvdata(dev); 168 struct rx8025_data *rx8025 = dev_get_drvdata(dev);
169 u8 date[7]; 169 u8 date[7], ctrl;
170 int err; 170 int err;
171 171
172 err = rx8025_read_reg(rx8025->client, RX8025_REG_CTRL2, &ctrl);
173 if (err)
174 return err;
175
176 if (ctrl & RX8025_BIT_CTRL2_PON) {
177 dev_warn(dev, "power-on reset detected, date is invalid\n");
178 return -EINVAL;
179 }
180
181 if (!(ctrl & RX8025_BIT_CTRL2_XST)) {
182 dev_warn(dev, "crystal stopped, date is invalid\n");
183 return -EINVAL;
184 }
185
172 err = rx8025_read_regs(rx8025->client, RX8025_REG_SEC, 7, date); 186 err = rx8025_read_regs(rx8025->client, RX8025_REG_SEC, 7, date);
173 if (err) 187 if (err)
174 return err; 188 return err;
@@ -230,7 +244,7 @@ static int rx8025_set_time(struct device *dev, struct rtc_time *dt)
230 return rx8025_write_regs(rx8025->client, RX8025_REG_SEC, 7, date); 244 return rx8025_write_regs(rx8025->client, RX8025_REG_SEC, 7, date);
231} 245}
232 246
233static int rx8025_init_client(struct i2c_client *client, int *need_reset) 247static int rx8025_init_client(struct i2c_client *client)
234{ 248{
235 struct rx8025_data *rx8025 = i2c_get_clientdata(client); 249 struct rx8025_data *rx8025 = i2c_get_clientdata(client);
236 u8 ctrl[2], ctrl2; 250 u8 ctrl[2], ctrl2;
@@ -247,19 +261,19 @@ static int rx8025_init_client(struct i2c_client *client, int *need_reset)
247 if (ctrl[1] & RX8025_BIT_CTRL2_PON) { 261 if (ctrl[1] & RX8025_BIT_CTRL2_PON) {
248 dev_warn(&client->dev, "power-on reset was detected, " 262 dev_warn(&client->dev, "power-on reset was detected, "
249 "you may have to readjust the clock\n"); 263 "you may have to readjust the clock\n");
250 *need_reset = 1; 264 need_clear = 1;
251 } 265 }
252 266
253 if (ctrl[1] & RX8025_BIT_CTRL2_VDET) { 267 if (ctrl[1] & RX8025_BIT_CTRL2_VDET) {
254 dev_warn(&client->dev, "a power voltage drop was detected, " 268 dev_warn(&client->dev, "a power voltage drop was detected, "
255 "you may have to readjust the clock\n"); 269 "you may have to readjust the clock\n");
256 *need_reset = 1; 270 need_clear = 1;
257 } 271 }
258 272
259 if (!(ctrl[1] & RX8025_BIT_CTRL2_XST)) { 273 if (!(ctrl[1] & RX8025_BIT_CTRL2_XST)) {
260 dev_warn(&client->dev, "Oscillation stop was detected," 274 dev_warn(&client->dev, "Oscillation stop was detected,"
261 "you may have to readjust the clock\n"); 275 "you may have to readjust the clock\n");
262 *need_reset = 1; 276 need_clear = 1;
263 } 277 }
264 278
265 if (ctrl[1] & (RX8025_BIT_CTRL2_DAFG | RX8025_BIT_CTRL2_WAFG)) { 279 if (ctrl[1] & (RX8025_BIT_CTRL2_DAFG | RX8025_BIT_CTRL2_WAFG)) {
@@ -270,7 +284,7 @@ static int rx8025_init_client(struct i2c_client *client, int *need_reset)
270 if (!(ctrl[1] & RX8025_BIT_CTRL2_CTFG)) 284 if (!(ctrl[1] & RX8025_BIT_CTRL2_CTFG))
271 need_clear = 1; 285 need_clear = 1;
272 286
273 if (*need_reset || need_clear) { 287 if (need_clear) {
274 ctrl2 = ctrl[0]; 288 ctrl2 = ctrl[0];
275 ctrl2 &= ~(RX8025_BIT_CTRL2_PON | RX8025_BIT_CTRL2_VDET | 289 ctrl2 &= ~(RX8025_BIT_CTRL2_PON | RX8025_BIT_CTRL2_VDET |
276 RX8025_BIT_CTRL2_CTFG | RX8025_BIT_CTRL2_WAFG | 290 RX8025_BIT_CTRL2_CTFG | RX8025_BIT_CTRL2_WAFG |
@@ -508,7 +522,7 @@ static int rx8025_probe(struct i2c_client *client,
508{ 522{
509 struct i2c_adapter *adapter = to_i2c_adapter(client->dev.parent); 523 struct i2c_adapter *adapter = to_i2c_adapter(client->dev.parent);
510 struct rx8025_data *rx8025; 524 struct rx8025_data *rx8025;
511 int err = 0, need_reset = 0; 525 int err = 0;
512 526
513 if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA 527 if (!i2c_check_functionality(adapter, I2C_FUNC_SMBUS_BYTE_DATA
514 | I2C_FUNC_SMBUS_I2C_BLOCK)) { 528 | I2C_FUNC_SMBUS_I2C_BLOCK)) {
@@ -525,18 +539,10 @@ static int rx8025_probe(struct i2c_client *client,
525 rx8025->client = client; 539 rx8025->client = client;
526 i2c_set_clientdata(client, rx8025); 540 i2c_set_clientdata(client, rx8025);
527 541
528 err = rx8025_init_client(client, &need_reset); 542 err = rx8025_init_client(client);
529 if (err) 543 if (err)
530 return err; 544 return err;
531 545
532 if (need_reset) {
533 struct rtc_time tm;
534 dev_info(&client->dev,
535 "bad conditions detected, resetting date\n");
536 rtc_time_to_tm(0, &tm); /* 1970/1/1 */
537 rx8025_set_time(&client->dev, &tm);
538 }
539
540 rx8025->rtc = devm_rtc_device_register(&client->dev, client->name, 546 rx8025->rtc = devm_rtc_device_register(&client->dev, client->name,
541 &rx8025_rtc_ops, THIS_MODULE); 547 &rx8025_rtc_ops, THIS_MODULE);
542 if (IS_ERR(rx8025->rtc)) { 548 if (IS_ERR(rx8025->rtc)) {