Lines Matching +full:static +full:- +full:enable
1 // SPDX-License-Identifier: GPL-2.0+
3 * rtc-ab-b5ze-s3 - Driver for Abracon AB-RTCMC-32.768Khz-B5ZE-S3
10 * https://www.abracon.com/realtimeclock/AB-RTCMC-32.768kHz-B5ZE-S3-Application-Manual.pdf
12 * This work is based on ISL12057 driver (drivers/rtc/rtc-isl12057.c).
24 #define DRV_NAME "rtc-ab-b5ze-s3"
28 #define ABB5ZES3_REG_CTRL1_CIE BIT(0) /* Pulse interrupt enable */
29 #define ABB5ZES3_REG_CTRL1_AIE BIT(1) /* Alarm interrupt enable */
30 #define ABB5ZES3_REG_CTRL1_SIE BIT(2) /* Second interrupt enable */
33 #define ABB5ZES3_REG_CTRL1_STOP BIT(5) /* RTC circuit enable */
37 #define ABB5ZES3_REG_CTRL2_CTBIE BIT(0) /* Countdown timer B int. enable */
38 #define ABB5ZES3_REG_CTRL2_CTAIE BIT(1) /* Countdown timer A int. enable */
39 #define ABB5ZES3_REG_CTRL2_WTAIE BIT(2) /* Watchdog timer A int. enable */
52 #define ABB5ZES3_REG_CTRL3_BSIE BIT(1) /* Battery switchover int. enable */
53 #define ABB5ZES3_REG_CTRL3_BLIE BIT(0) /* Battery low int. enable */
70 /* Alarm section (enable bits are all active low) */
71 #define ABB5ZES3_REG_ALRM_MN 0x0A /* Alarm - minute register */
72 #define ABB5ZES3_REG_ALRM_MN_AE BIT(7) /* Minute enable */
73 #define ABB5ZES3_REG_ALRM_HR 0x0B /* Alarm - hours register */
74 #define ABB5ZES3_REG_ALRM_HR_AE BIT(7) /* Hour enable */
75 #define ABB5ZES3_REG_ALRM_DT 0x0C /* Alarm - date register */
76 #define ABB5ZES3_REG_ALRM_DT_AE BIT(7) /* Date (day of the month) enable */
77 #define ABB5ZES3_REG_ALRM_DW 0x0D /* Alarm - day of the week reg. */
78 #define ABB5ZES3_REG_ALRM_DW_AE BIT(7) /* Day of the week enable */
93 #define ABB5ZES3_REG_TIM_CLK_TAC1 BIT(2) /* Timer A: - 01 : countdown */
94 #define ABB5ZES3_REG_TIM_CLK_TAC0 BIT(1) /* - 10 : timer */
95 #define ABB5ZES3_REG_TIM_CLK_TBC BIT(0) /* Timer B enable */
133 static int abb5zes3_i2c_validate_chip(struct regmap *regmap) in abb5zes3_i2c_validate_chip()
136 static const u8 mask[ABB5ZES3_MEM_MAP_LEN] = { 0x00, 0x00, 0x10, 0x00, in abb5zes3_i2c_validate_chip()
149 return -ENODEV; in abb5zes3_i2c_validate_chip()
156 static int _abb5zes3_rtc_clear_alarm(struct device *dev) in _abb5zes3_rtc_clear_alarm()
161 ret = regmap_update_bits(data->regmap, ABB5ZES3_REG_CTRL2, in _abb5zes3_rtc_clear_alarm()
169 /* Enable or disable alarm (i.e. alarm interrupt generation) */
170 static int _abb5zes3_rtc_update_alarm(struct device *dev, bool enable) in _abb5zes3_rtc_update_alarm() argument
175 ret = regmap_update_bits(data->regmap, ABB5ZES3_REG_CTRL1, in _abb5zes3_rtc_update_alarm()
177 enable ? ABB5ZES3_REG_CTRL1_AIE : 0); in _abb5zes3_rtc_update_alarm()
185 /* Enable or disable timer (watchdog timer A interrupt generation) */
186 static int _abb5zes3_rtc_update_timer(struct device *dev, bool enable) in _abb5zes3_rtc_update_timer() argument
191 ret = regmap_update_bits(data->regmap, ABB5ZES3_REG_CTRL2, in _abb5zes3_rtc_update_timer()
193 enable ? ABB5ZES3_REG_CTRL2_WTAIE : 0); in _abb5zes3_rtc_update_timer()
205 static int _abb5zes3_rtc_read_time(struct device *dev, struct rtc_time *tm) in _abb5zes3_rtc_read_time()
217 ret = regmap_bulk_read(data->regmap, ABB5ZES3_REG_CTRL1, regs, in _abb5zes3_rtc_read_time()
227 return -ENODATA; in _abb5zes3_rtc_read_time()
229 tm->tm_sec = bcd2bin(regs[ABB5ZES3_REG_RTC_SC] & 0x7F); in _abb5zes3_rtc_read_time()
230 tm->tm_min = bcd2bin(regs[ABB5ZES3_REG_RTC_MN]); in _abb5zes3_rtc_read_time()
233 tm->tm_hour = bcd2bin(regs[ABB5ZES3_REG_RTC_HR] & 0x1f); in _abb5zes3_rtc_read_time()
235 tm->tm_hour += 12; in _abb5zes3_rtc_read_time()
237 tm->tm_hour = bcd2bin(regs[ABB5ZES3_REG_RTC_HR]); in _abb5zes3_rtc_read_time()
240 tm->tm_mday = bcd2bin(regs[ABB5ZES3_REG_RTC_DT]); in _abb5zes3_rtc_read_time()
241 tm->tm_wday = bcd2bin(regs[ABB5ZES3_REG_RTC_DW]); in _abb5zes3_rtc_read_time()
242 tm->tm_mon = bcd2bin(regs[ABB5ZES3_REG_RTC_MO]) - 1; /* starts at 1 */ in _abb5zes3_rtc_read_time()
243 tm->tm_year = bcd2bin(regs[ABB5ZES3_REG_RTC_YR]) + 100; in _abb5zes3_rtc_read_time()
248 static int abb5zes3_rtc_set_time(struct device *dev, struct rtc_time *tm) in abb5zes3_rtc_set_time()
254 regs[ABB5ZES3_REG_RTC_SC] = bin2bcd(tm->tm_sec); /* MSB=0 clears OSC */ in abb5zes3_rtc_set_time()
255 regs[ABB5ZES3_REG_RTC_MN] = bin2bcd(tm->tm_min); in abb5zes3_rtc_set_time()
256 regs[ABB5ZES3_REG_RTC_HR] = bin2bcd(tm->tm_hour); /* 24-hour format */ in abb5zes3_rtc_set_time()
257 regs[ABB5ZES3_REG_RTC_DT] = bin2bcd(tm->tm_mday); in abb5zes3_rtc_set_time()
258 regs[ABB5ZES3_REG_RTC_DW] = bin2bcd(tm->tm_wday); in abb5zes3_rtc_set_time()
259 regs[ABB5ZES3_REG_RTC_MO] = bin2bcd(tm->tm_mon + 1); in abb5zes3_rtc_set_time()
260 regs[ABB5ZES3_REG_RTC_YR] = bin2bcd(tm->tm_year - 100); in abb5zes3_rtc_set_time()
262 ret = regmap_bulk_write(data->regmap, ABB5ZES3_REG_RTC_SC, in abb5zes3_rtc_set_time()
273 static inline void sec_to_timer_a(u8 secs, u8 *taq, u8 *timer_a) in sec_to_timer_a()
283 static inline int sec_from_timer_a(u8 *secs, u8 taq, u8 timer_a) in sec_from_timer_a()
286 return -EINVAL; in sec_from_timer_a()
297 static int _abb5zes3_rtc_read_timer(struct device *dev, in _abb5zes3_rtc_read_timer()
301 struct rtc_time rtc_tm, *alarm_tm = &alarm->time; in _abb5zes3_rtc_read_timer()
313 ret = regmap_bulk_read(data->regmap, ABB5ZES3_REG_TIM_CLK, regs, in _abb5zes3_rtc_read_timer()
337 ret = regmap_read(data->regmap, ABB5ZES3_REG_CTRL2, ®); in _abb5zes3_rtc_read_timer()
344 alarm->enabled = !!(reg & ABB5ZES3_REG_CTRL2_WTAIE); in _abb5zes3_rtc_read_timer()
350 static int _abb5zes3_rtc_read_alarm(struct device *dev, in _abb5zes3_rtc_read_alarm()
354 struct rtc_time rtc_tm, *alarm_tm = &alarm->time; in _abb5zes3_rtc_read_alarm()
360 ret = regmap_bulk_read(data->regmap, ABB5ZES3_REG_ALRM_MN, regs, in _abb5zes3_rtc_read_alarm()
368 alarm_tm->tm_sec = 0; in _abb5zes3_rtc_read_alarm()
369 alarm_tm->tm_min = bcd2bin(regs[0] & 0x7f); in _abb5zes3_rtc_read_alarm()
370 alarm_tm->tm_hour = bcd2bin(regs[1] & 0x3f); in _abb5zes3_rtc_read_alarm()
371 alarm_tm->tm_mday = bcd2bin(regs[2] & 0x3f); in _abb5zes3_rtc_read_alarm()
372 alarm_tm->tm_wday = -1; in _abb5zes3_rtc_read_alarm()
383 alarm_tm->tm_year = rtc_tm.tm_year; in _abb5zes3_rtc_read_alarm()
384 alarm_tm->tm_mon = rtc_tm.tm_mon; in _abb5zes3_rtc_read_alarm()
390 if (alarm_tm->tm_mon == 11) { in _abb5zes3_rtc_read_alarm()
391 alarm_tm->tm_mon = 0; in _abb5zes3_rtc_read_alarm()
392 alarm_tm->tm_year += 1; in _abb5zes3_rtc_read_alarm()
394 alarm_tm->tm_mon += 1; in _abb5zes3_rtc_read_alarm()
398 ret = regmap_read(data->regmap, ABB5ZES3_REG_CTRL1, ®); in _abb5zes3_rtc_read_alarm()
405 alarm->enabled = !!(reg & ABB5ZES3_REG_CTRL1_AIE); in _abb5zes3_rtc_read_alarm()
419 static int abb5zes3_rtc_read_alarm(struct device *dev, struct rtc_wkalrm *alarm) in abb5zes3_rtc_read_alarm()
424 if (data->timer_alarm) in abb5zes3_rtc_read_alarm()
437 static int _abb5zes3_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *alarm) in _abb5zes3_rtc_set_alarm()
440 struct rtc_time *alarm_tm = &alarm->time; in _abb5zes3_rtc_set_alarm()
443 int ret, enable = 1; in _abb5zes3_rtc_set_alarm() local
445 if (!alarm->enabled) { in _abb5zes3_rtc_set_alarm()
446 enable = 0; in _abb5zes3_rtc_set_alarm()
473 return -EINVAL; in _abb5zes3_rtc_set_alarm()
481 regs[0] = bin2bcd(alarm_tm->tm_min) & 0x7f; in _abb5zes3_rtc_set_alarm()
482 regs[1] = bin2bcd(alarm_tm->tm_hour) & 0x3f; in _abb5zes3_rtc_set_alarm()
483 regs[2] = bin2bcd(alarm_tm->tm_mday) & 0x3f; in _abb5zes3_rtc_set_alarm()
486 ret = regmap_bulk_write(data->regmap, ABB5ZES3_REG_ALRM_MN, regs, in _abb5zes3_rtc_set_alarm()
495 data->timer_alarm = 0; in _abb5zes3_rtc_set_alarm()
497 /* Enable or disable alarm interrupt generation */ in _abb5zes3_rtc_set_alarm()
498 return _abb5zes3_rtc_update_alarm(dev, enable); in _abb5zes3_rtc_set_alarm()
505 static int _abb5zes3_rtc_set_timer(struct device *dev, struct rtc_wkalrm *alarm, in _abb5zes3_rtc_set_timer()
515 ret = regmap_bulk_write(data->regmap, ABB5ZES3_REG_TIMA_CLK, regs, in _abb5zes3_rtc_set_timer()
523 ret = regmap_update_bits(data->regmap, ABB5ZES3_REG_TIM_CLK, in _abb5zes3_rtc_set_timer()
529 data->timer_alarm = 1; in _abb5zes3_rtc_set_timer()
531 /* Enable or disable timer interrupt generation */ in _abb5zes3_rtc_set_timer()
532 return _abb5zes3_rtc_update_timer(dev, alarm->enabled); in _abb5zes3_rtc_set_timer()
541 static int abb5zes3_rtc_set_alarm(struct device *dev, struct rtc_wkalrm *alarm) in abb5zes3_rtc_set_alarm()
544 struct rtc_time *alarm_tm = &alarm->time; in abb5zes3_rtc_set_alarm()
570 data->timer_alarm = 0; in abb5zes3_rtc_set_alarm()
576 if ((alarm_secs > rtc_secs) && ((alarm_secs - rtc_secs) <= 240)) in abb5zes3_rtc_set_alarm()
578 alarm_secs - rtc_secs); in abb5zes3_rtc_set_alarm()
589 /* Enable or disable battery low irq generation */
590 static inline int _abb5zes3_rtc_battery_low_irq_enable(struct regmap *regmap, in _abb5zes3_rtc_battery_low_irq_enable()
591 bool enable) in _abb5zes3_rtc_battery_low_irq_enable() argument
595 enable ? ABB5ZES3_REG_CTRL3_BLIE : 0); in _abb5zes3_rtc_battery_low_irq_enable()
599 * Check current RTC status and enable/disable what needs to be. Return 0 if
602 static int abb5zes3_rtc_check_setup(struct device *dev) in abb5zes3_rtc_check_setup()
605 struct regmap *regmap = data->regmap; in abb5zes3_rtc_check_setup()
636 * we set all alarm enable bits to disable current alarm setting. in abb5zes3_rtc_check_setup()
660 * WTAF is read-only and cleared automatically by reading the register. in abb5zes3_rtc_check_setup()
674 * Enable battery low detection function and battery switchover function in abb5zes3_rtc_check_setup()
715 data->battery_low = reg & ABB5ZES3_REG_CTRL3_BLF; in abb5zes3_rtc_check_setup()
716 if (data->battery_low) { in abb5zes3_rtc_check_setup()
728 static int abb5zes3_rtc_alarm_irq_enable(struct device *dev, in abb5zes3_rtc_alarm_irq_enable()
729 unsigned int enable) in abb5zes3_rtc_alarm_irq_enable() argument
734 if (rtc_data->irq) { in abb5zes3_rtc_alarm_irq_enable()
735 if (rtc_data->timer_alarm) in abb5zes3_rtc_alarm_irq_enable()
736 ret = _abb5zes3_rtc_update_timer(dev, enable); in abb5zes3_rtc_alarm_irq_enable()
738 ret = _abb5zes3_rtc_update_alarm(dev, enable); in abb5zes3_rtc_alarm_irq_enable()
744 static irqreturn_t _abb5zes3_rtc_interrupt(int irq, void *data) in _abb5zes3_rtc_interrupt()
747 struct device *dev = &client->dev; in _abb5zes3_rtc_interrupt()
749 struct rtc_device *rtc = rtc_data->rtc; in _abb5zes3_rtc_interrupt()
753 ret = regmap_bulk_read(rtc_data->regmap, 0, regs, in _abb5zes3_rtc_interrupt()
769 _abb5zes3_rtc_battery_low_irq_enable(rtc_data->regmap, false); in _abb5zes3_rtc_interrupt()
799 rtc_data->timer_alarm = 0; in _abb5zes3_rtc_interrupt()
807 static const struct rtc_class_ops rtc_ops = {
815 static const struct regmap_config abb5zes3_rtc_regmap_config = {
820 static int abb5zes3_probe(struct i2c_client *client, in abb5zes3_probe()
824 struct device *dev = &client->dev; in abb5zes3_probe()
828 if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C | in abb5zes3_probe()
831 return -ENODEV; in abb5zes3_probe()
847 return -ENOMEM; in abb5zes3_probe()
849 data->regmap = regmap; in abb5zes3_probe()
856 data->rtc = devm_rtc_allocate_device(dev); in abb5zes3_probe()
857 ret = PTR_ERR_OR_ZERO(data->rtc); in abb5zes3_probe()
864 if (client->irq > 0) { in abb5zes3_probe()
865 ret = devm_request_threaded_irq(dev, client->irq, NULL, in abb5zes3_probe()
871 data->irq = client->irq; in abb5zes3_probe()
873 client->irq); in abb5zes3_probe()
876 __func__, client->irq, ret); in abb5zes3_probe()
881 data->rtc->ops = &rtc_ops; in abb5zes3_probe()
882 data->rtc->range_min = RTC_TIMESTAMP_BEGIN_2000; in abb5zes3_probe()
883 data->rtc->range_max = RTC_TIMESTAMP_END_2099; in abb5zes3_probe()
885 /* Enable battery low detection interrupt if battery not already low */ in abb5zes3_probe()
886 if (!data->battery_low && data->irq) { in abb5zes3_probe()
895 ret = rtc_register_device(data->rtc); in abb5zes3_probe()
898 if (ret && data->irq) in abb5zes3_probe()
904 static int abb5zes3_rtc_suspend(struct device *dev) in abb5zes3_rtc_suspend()
909 return enable_irq_wake(rtc_data->irq); in abb5zes3_rtc_suspend()
914 static int abb5zes3_rtc_resume(struct device *dev) in abb5zes3_rtc_resume()
919 return disable_irq_wake(rtc_data->irq); in abb5zes3_rtc_resume()
925 static SIMPLE_DEV_PM_OPS(abb5zes3_rtc_pm_ops, abb5zes3_rtc_suspend,
929 static const struct of_device_id abb5zes3_dt_match[] = {
936 static const struct i2c_device_id abb5zes3_id[] = {
942 static struct i2c_driver abb5zes3_driver = {
954 MODULE_DESCRIPTION("Abracon AB-RTCMC-32.768kHz-B5ZE-S3 RTC/Alarm driver");