1 // SPDX-License-Identifier: GPL-2.0+
3 * Renesas RZ/N1 Real Time Clock interface for Linux
6 * - 2014 Renesas Electronics Europe Limited
7 * - 2022 Schneider Electric
10 * - Michel Pollet <buserror@gmail.com>
11 * - Miquel Raynal <miquel.raynal@bootlin.com>
14 #include <linux/bcd.h>
15 #include <linux/init.h>
16 #include <linux/iopoll.h>
17 #include <linux/module.h>
18 #include <linux/mod_devicetable.h>
19 #include <linux/platform_device.h>
20 #include <linux/pm_runtime.h>
21 #include <linux/rtc.h>
23 #define RZN1_RTC_CTL0 0x00
24 #define RZN1_RTC_CTL0_SLSB_SUBU 0
25 #define RZN1_RTC_CTL0_SLSB_SCMP BIT(4)
26 #define RZN1_RTC_CTL0_AMPM BIT(5)
27 #define RZN1_RTC_CTL0_CE BIT(7)
29 #define RZN1_RTC_CTL1 0x04
30 #define RZN1_RTC_CTL1_ALME BIT(4)
32 #define RZN1_RTC_CTL2 0x08
33 #define RZN1_RTC_CTL2_WAIT BIT(0)
34 #define RZN1_RTC_CTL2_WST BIT(1)
35 #define RZN1_RTC_CTL2_WUST BIT(5)
36 #define RZN1_RTC_CTL2_STOPPED (RZN1_RTC_CTL2_WAIT | RZN1_RTC_CTL2_WST)
38 #define RZN1_RTC_TIME 0x30
39 #define RZN1_RTC_TIME_MIN_SHIFT 8
40 #define RZN1_RTC_TIME_HOUR_SHIFT 16
41 #define RZN1_RTC_CAL 0x34
42 #define RZN1_RTC_CAL_DAY_SHIFT 8
43 #define RZN1_RTC_CAL_MON_SHIFT 16
44 #define RZN1_RTC_CAL_YEAR_SHIFT 24
46 #define RZN1_RTC_SUBU 0x38
47 #define RZN1_RTC_SUBU_DEV BIT(7)
48 #define RZN1_RTC_SUBU_DECR BIT(6)
50 #define RZN1_RTC_ALM 0x40
51 #define RZN1_RTC_ALH 0x44
52 #define RZN1_RTC_ALW 0x48
54 #define RZN1_RTC_SECC 0x4c
55 #define RZN1_RTC_TIMEC 0x68
56 #define RZN1_RTC_CALC 0x6c
59 struct rtc_device
*rtcdev
;
63 static void rzn1_rtc_get_time_snapshot(struct rzn1_rtc
*rtc
, struct rtc_time
*tm
)
67 val
= readl(rtc
->base
+ RZN1_RTC_TIMEC
);
68 tm
->tm_sec
= bcd2bin(val
);
69 tm
->tm_min
= bcd2bin(val
>> RZN1_RTC_TIME_MIN_SHIFT
);
70 tm
->tm_hour
= bcd2bin(val
>> RZN1_RTC_TIME_HOUR_SHIFT
);
72 val
= readl(rtc
->base
+ RZN1_RTC_CALC
);
73 tm
->tm_wday
= val
& 0x0f;
74 tm
->tm_mday
= bcd2bin(val
>> RZN1_RTC_CAL_DAY_SHIFT
);
75 tm
->tm_mon
= bcd2bin(val
>> RZN1_RTC_CAL_MON_SHIFT
) - 1;
76 tm
->tm_year
= bcd2bin(val
>> RZN1_RTC_CAL_YEAR_SHIFT
) + 100;
79 static int rzn1_rtc_read_time(struct device
*dev
, struct rtc_time
*tm
)
81 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
85 * The RTC was not started or is stopped and thus does not carry the
88 val
= readl(rtc
->base
+ RZN1_RTC_CTL2
);
89 if (val
& RZN1_RTC_CTL2_STOPPED
)
92 rzn1_rtc_get_time_snapshot(rtc
, tm
);
93 secs
= readl(rtc
->base
+ RZN1_RTC_SECC
);
94 if (tm
->tm_sec
!= bcd2bin(secs
))
95 rzn1_rtc_get_time_snapshot(rtc
, tm
);
100 static int rzn1_rtc_set_time(struct device
*dev
, struct rtc_time
*tm
)
102 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
106 val
= readl(rtc
->base
+ RZN1_RTC_CTL2
);
107 if (!(val
& RZN1_RTC_CTL2_STOPPED
)) {
108 /* Hold the counter if it was counting up */
109 writel(RZN1_RTC_CTL2_WAIT
, rtc
->base
+ RZN1_RTC_CTL2
);
111 /* Wait for the counter to stop: two 32k clock cycles */
112 usleep_range(61, 100);
113 ret
= readl_poll_timeout(rtc
->base
+ RZN1_RTC_CTL2
, val
,
114 val
& RZN1_RTC_CTL2_WST
, 0, 100);
119 val
= bin2bcd(tm
->tm_sec
);
120 val
|= bin2bcd(tm
->tm_min
) << RZN1_RTC_TIME_MIN_SHIFT
;
121 val
|= bin2bcd(tm
->tm_hour
) << RZN1_RTC_TIME_HOUR_SHIFT
;
122 writel(val
, rtc
->base
+ RZN1_RTC_TIME
);
125 val
|= bin2bcd(tm
->tm_mday
) << RZN1_RTC_CAL_DAY_SHIFT
;
126 val
|= bin2bcd(tm
->tm_mon
+ 1) << RZN1_RTC_CAL_MON_SHIFT
;
127 val
|= bin2bcd(tm
->tm_year
- 100) << RZN1_RTC_CAL_YEAR_SHIFT
;
128 writel(val
, rtc
->base
+ RZN1_RTC_CAL
);
130 writel(0, rtc
->base
+ RZN1_RTC_CTL2
);
135 static irqreturn_t
rzn1_rtc_alarm_irq(int irq
, void *dev_id
)
137 struct rzn1_rtc
*rtc
= dev_id
;
139 rtc_update_irq(rtc
->rtcdev
, 1, RTC_AF
| RTC_IRQF
);
144 static int rzn1_rtc_alarm_irq_enable(struct device
*dev
, unsigned int enable
)
146 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
147 u32 ctl1
= readl(rtc
->base
+ RZN1_RTC_CTL1
);
150 ctl1
|= RZN1_RTC_CTL1_ALME
;
152 ctl1
&= ~RZN1_RTC_CTL1_ALME
;
154 writel(ctl1
, rtc
->base
+ RZN1_RTC_CTL1
);
159 static int rzn1_rtc_read_alarm(struct device
*dev
, struct rtc_wkalrm
*alrm
)
161 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
162 struct rtc_time
*tm
= &alrm
->time
;
163 unsigned int min
, hour
, wday
, delta_days
;
168 ret
= rzn1_rtc_read_time(dev
, tm
);
172 min
= readl(rtc
->base
+ RZN1_RTC_ALM
);
173 hour
= readl(rtc
->base
+ RZN1_RTC_ALH
);
174 wday
= readl(rtc
->base
+ RZN1_RTC_ALW
);
177 tm
->tm_min
= bcd2bin(min
);
178 tm
->tm_hour
= bcd2bin(hour
);
179 delta_days
= ((fls(wday
) - 1) - tm
->tm_wday
+ 7) % 7;
180 tm
->tm_wday
= fls(wday
) - 1;
183 alarm
= rtc_tm_to_time64(tm
) + (delta_days
* 86400);
184 rtc_time64_to_tm(alarm
, tm
);
187 ctl1
= readl(rtc
->base
+ RZN1_RTC_CTL1
);
188 alrm
->enabled
= !!(ctl1
& RZN1_RTC_CTL1_ALME
);
193 static int rzn1_rtc_set_alarm(struct device
*dev
, struct rtc_wkalrm
*alrm
)
195 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
196 struct rtc_time
*tm
= &alrm
->time
, tm_now
;
197 unsigned long alarm
, farest
;
198 unsigned int days_ahead
, wday
;
201 ret
= rzn1_rtc_read_time(dev
, &tm_now
);
205 /* We cannot set alarms more than one week ahead */
206 farest
= rtc_tm_to_time64(&tm_now
) + rtc
->rtcdev
->alarm_offset_max
;
207 alarm
= rtc_tm_to_time64(tm
);
208 if (time_after(alarm
, farest
))
211 /* Convert alarm day into week day */
212 days_ahead
= tm
->tm_mday
- tm_now
.tm_mday
;
213 wday
= (tm_now
.tm_wday
+ days_ahead
) % 7;
215 writel(bin2bcd(tm
->tm_min
), rtc
->base
+ RZN1_RTC_ALM
);
216 writel(bin2bcd(tm
->tm_hour
), rtc
->base
+ RZN1_RTC_ALH
);
217 writel(BIT(wday
), rtc
->base
+ RZN1_RTC_ALW
);
219 rzn1_rtc_alarm_irq_enable(dev
, alrm
->enabled
);
224 static int rzn1_rtc_read_offset(struct device
*dev
, long *offset
)
226 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
227 unsigned int ppb_per_step
;
231 val
= readl(rtc
->base
+ RZN1_RTC_SUBU
);
232 ppb_per_step
= val
& RZN1_RTC_SUBU_DEV
? 1017 : 3051;
233 subtract
= val
& RZN1_RTC_SUBU_DECR
;
239 *offset
= -(((~val
) & 0x3F) + 1) * ppb_per_step
;
241 *offset
= (val
- 1) * ppb_per_step
;
246 static int rzn1_rtc_set_offset(struct device
*dev
, long offset
)
248 struct rzn1_rtc
*rtc
= dev_get_drvdata(dev
);
249 int stepsh
, stepsl
, steps
;
254 * Check which resolution mode (every 20 or 60s) can be used.
255 * Between 2 and 124 clock pulses can be added or substracted.
257 * In 20s mode, the minimum resolution is 2 / (32768 * 20) which is
258 * close to 3051 ppb. In 60s mode, the resolution is closer to 1017.
260 stepsh
= DIV_ROUND_CLOSEST(offset
, 1017);
261 stepsl
= DIV_ROUND_CLOSEST(offset
, 3051);
263 if (stepsh
>= -0x3E && stepsh
<= 0x3E) {
264 /* 1017 ppb per step */
266 subu
|= RZN1_RTC_SUBU_DEV
;
267 } else if (stepsl
>= -0x3E && stepsl
<= 0x3E) {
268 /* 3051 ppb per step */
280 subu
|= RZN1_RTC_SUBU_DECR
;
281 subu
|= (~(-steps
- 1)) & 0x3F;
284 ret
= readl_poll_timeout(rtc
->base
+ RZN1_RTC_CTL2
, ctl2
,
285 !(ctl2
& RZN1_RTC_CTL2_WUST
), 100, 2000000);
289 writel(subu
, rtc
->base
+ RZN1_RTC_SUBU
);
294 static const struct rtc_class_ops rzn1_rtc_ops
= {
295 .read_time
= rzn1_rtc_read_time
,
296 .set_time
= rzn1_rtc_set_time
,
297 .read_alarm
= rzn1_rtc_read_alarm
,
298 .set_alarm
= rzn1_rtc_set_alarm
,
299 .alarm_irq_enable
= rzn1_rtc_alarm_irq_enable
,
300 .read_offset
= rzn1_rtc_read_offset
,
301 .set_offset
= rzn1_rtc_set_offset
,
304 static int rzn1_rtc_probe(struct platform_device
*pdev
)
306 struct rzn1_rtc
*rtc
;
310 rtc
= devm_kzalloc(&pdev
->dev
, sizeof(*rtc
), GFP_KERNEL
);
314 platform_set_drvdata(pdev
, rtc
);
316 rtc
->base
= devm_platform_ioremap_resource(pdev
, 0);
317 if (IS_ERR(rtc
->base
))
318 return dev_err_probe(&pdev
->dev
, PTR_ERR(rtc
->base
), "Missing reg\n");
320 alarm_irq
= platform_get_irq(pdev
, 0);
324 rtc
->rtcdev
= devm_rtc_allocate_device(&pdev
->dev
);
325 if (IS_ERR(rtc
->rtcdev
))
326 return PTR_ERR(rtc
->rtcdev
);
328 rtc
->rtcdev
->range_min
= RTC_TIMESTAMP_BEGIN_2000
;
329 rtc
->rtcdev
->range_max
= RTC_TIMESTAMP_END_2099
;
330 rtc
->rtcdev
->alarm_offset_max
= 7 * 86400;
331 rtc
->rtcdev
->ops
= &rzn1_rtc_ops
;
332 set_bit(RTC_FEATURE_ALARM_RES_MINUTE
, rtc
->rtcdev
->features
);
333 clear_bit(RTC_FEATURE_UPDATE_INTERRUPT
, rtc
->rtcdev
->features
);
335 ret
= devm_pm_runtime_enable(&pdev
->dev
);
338 ret
= pm_runtime_resume_and_get(&pdev
->dev
);
343 * Ensure the clock counter is enabled.
344 * Set 24-hour mode and possible oscillator offset compensation in SUBU mode.
346 writel(RZN1_RTC_CTL0_CE
| RZN1_RTC_CTL0_AMPM
| RZN1_RTC_CTL0_SLSB_SUBU
,
347 rtc
->base
+ RZN1_RTC_CTL0
);
349 /* Disable all interrupts */
350 writel(0, rtc
->base
+ RZN1_RTC_CTL1
);
352 ret
= devm_request_irq(&pdev
->dev
, alarm_irq
, rzn1_rtc_alarm_irq
, 0,
353 dev_name(&pdev
->dev
), rtc
);
355 dev_err(&pdev
->dev
, "RTC timer interrupt not available\n");
359 ret
= devm_rtc_register_device(rtc
->rtcdev
);
366 pm_runtime_put(&pdev
->dev
);
371 static void rzn1_rtc_remove(struct platform_device
*pdev
)
373 pm_runtime_put(&pdev
->dev
);
376 static const struct of_device_id rzn1_rtc_of_match
[] = {
377 { .compatible
= "renesas,rzn1-rtc" },
380 MODULE_DEVICE_TABLE(of
, rzn1_rtc_of_match
);
382 static struct platform_driver rzn1_rtc_driver
= {
383 .probe
= rzn1_rtc_probe
,
384 .remove
= rzn1_rtc_remove
,
387 .of_match_table
= rzn1_rtc_of_match
,
390 module_platform_driver(rzn1_rtc_driver
);
392 MODULE_AUTHOR("Michel Pollet <buserror@gmail.com>");
393 MODULE_AUTHOR("Miquel Raynal <miquel.raynal@bootlin.com");
394 MODULE_DESCRIPTION("RZ/N1 RTC driver");
395 MODULE_LICENSE("GPL");