diff options
Diffstat (limited to 'drivers/rtc/rtc-r9701.c')
| -rw-r--r-- | drivers/rtc/rtc-r9701.c | 61 | 
1 files changed, 35 insertions, 26 deletions
diff --git a/drivers/rtc/rtc-r9701.c b/drivers/rtc/rtc-r9701.c index 9beba49c3c5..feeedbd8200 100644 --- a/drivers/rtc/rtc-r9701.c +++ b/drivers/rtc/rtc-r9701.c @@ -119,34 +119,53 @@ static const struct rtc_class_ops r9701_rtc_ops = {  	.set_time	= r9701_set_datetime,  }; -static int __devinit r9701_probe(struct spi_device *spi) +static int r9701_probe(struct spi_device *spi)  {  	struct rtc_device *rtc; +	struct rtc_time dt;  	unsigned char tmp;  	int res; -	rtc = rtc_device_register("r9701", -				&spi->dev, &r9701_rtc_ops, THIS_MODULE); -	if (IS_ERR(rtc)) -		return PTR_ERR(rtc); - -	dev_set_drvdata(&spi->dev, rtc); -  	tmp = R100CNT;  	res = read_regs(&spi->dev, &tmp, 1);  	if (res || tmp != 0x20) { -		rtc_device_unregister(rtc); -		return res; +		dev_err(&spi->dev, "cannot read RTC register\n"); +		return -ENODEV;  	} +	/* +	 * The device seems to be present. Now check if the registers +	 * contain invalid values. If so, try to write a default date: +	 * 2000/1/1 00:00:00 +	 */ +	if (r9701_get_datetime(&spi->dev, &dt)) { +		dev_info(&spi->dev, "trying to repair invalid date/time\n"); +		dt.tm_sec  = 0; +		dt.tm_min  = 0; +		dt.tm_hour = 0; +		dt.tm_mday = 1; +		dt.tm_mon  = 0; +		dt.tm_year = 100; + +		if (r9701_set_datetime(&spi->dev, &dt) || +				r9701_get_datetime(&spi->dev, &dt)) { +			dev_err(&spi->dev, "cannot repair RTC register\n"); +			return -ENODEV; +		} +	} + +	rtc = devm_rtc_device_register(&spi->dev, "r9701", +				&r9701_rtc_ops, THIS_MODULE); +	if (IS_ERR(rtc)) +		return PTR_ERR(rtc); + +	spi_set_drvdata(spi, rtc); +  	return 0;  } -static int __devexit r9701_remove(struct spi_device *spi) +static int r9701_remove(struct spi_device *spi)  { -	struct rtc_device *rtc = dev_get_drvdata(&spi->dev); - -	rtc_device_unregister(rtc);  	return 0;  } @@ -156,20 +175,10 @@ static struct spi_driver r9701_driver = {  		.owner	= THIS_MODULE,  	},  	.probe	= r9701_probe, -	.remove = __devexit_p(r9701_remove), +	.remove = r9701_remove,  }; -static __init int r9701_init(void) -{ -	return spi_register_driver(&r9701_driver); -} -module_init(r9701_init); - -static __exit void r9701_exit(void) -{ -	spi_unregister_driver(&r9701_driver); -} -module_exit(r9701_exit); +module_spi_driver(r9701_driver);  MODULE_DESCRIPTION("r9701 spi RTC driver");  MODULE_AUTHOR("Magnus Damm <damm@opensource.se>");  | 
