1 // SPDX-License-Identifier: GPL-2.0 2 /* 3 * Renesas RZ/G2L WDT Watchdog Driver 4 * 5 * Copyright (C) 2021 Renesas Electronics Corporation 6 */ 7 #include <linux/bitops.h> 8 #include <linux/clk.h> 9 #include <linux/delay.h> 10 #include <linux/io.h> 11 #include <linux/iopoll.h> 12 #include <linux/kernel.h> 13 #include <linux/module.h> 14 #include <linux/of.h> 15 #include <linux/platform_device.h> 16 #include <linux/pm_runtime.h> 17 #include <linux/reset.h> 18 #include <linux/units.h> 19 #include <linux/watchdog.h> 20 21 #define WDTCNT 0x00 22 #define WDTSET 0x04 23 #define WDTTIM 0x08 24 #define WDTINT 0x0C 25 #define PECR 0x10 26 #define PEEN 0x14 27 #define WDTCNT_WDTEN BIT(0) 28 #define WDTINT_INTDISP BIT(0) 29 #define PEEN_FORCE BIT(0) 30 31 #define WDT_DEFAULT_TIMEOUT 60U 32 33 /* Setting period time register only 12 bit set in WDTSET[31:20] */ 34 #define WDTSET_COUNTER_MASK (0xFFF00000) 35 #define WDTSET_COUNTER_VAL(f) ((f) << 20) 36 37 #define F2CYCLE_NSEC(f) (1000000000 / (f)) 38 39 #define RZV2M_A_NSEC 730 40 41 static bool nowayout = WATCHDOG_NOWAYOUT; 42 module_param(nowayout, bool, 0); 43 MODULE_PARM_DESC(nowayout, "Watchdog cannot be stopped once started (default=" 44 __MODULE_STRING(WATCHDOG_NOWAYOUT) ")"); 45 46 enum rz_wdt_type { 47 WDT_RZG2L, 48 WDT_RZV2M, 49 }; 50 51 struct rzg2l_wdt_priv { 52 void __iomem *base; 53 struct watchdog_device wdev; 54 struct reset_control *rstc; 55 unsigned long osc_clk_rate; 56 unsigned long delay; 57 unsigned long minimum_assertion_period; 58 struct clk *pclk; 59 struct clk *osc_clk; 60 enum rz_wdt_type devtype; 61 }; 62 63 static int rzg2l_wdt_reset(struct rzg2l_wdt_priv *priv) 64 { 65 int err, status; 66 67 if (priv->devtype == WDT_RZV2M) { 68 /* WDT needs TYPE-B reset control */ 69 err = reset_control_assert(priv->rstc); 70 if (err) 71 return err; 72 ndelay(priv->minimum_assertion_period); 73 err = reset_control_deassert(priv->rstc); 74 if (err) 75 return err; 76 err = read_poll_timeout(reset_control_status, status, 77 status != 1, 0, 1000, false, 78 priv->rstc); 79 } else { 80 err = reset_control_reset(priv->rstc); 81 } 82 83 return err; 84 } 85 86 static void rzg2l_wdt_wait_delay(struct rzg2l_wdt_priv *priv) 87 { 88 /* delay timer when change the setting register */ 89 ndelay(priv->delay); 90 } 91 92 static u32 rzg2l_wdt_get_cycle_usec(unsigned long cycle, u32 wdttime) 93 { 94 u64 timer_cycle_us = 1024 * 1024ULL * (wdttime + 1) * MICRO; 95 96 return div64_ul(timer_cycle_us, cycle); 97 } 98 99 static void rzg2l_wdt_write(struct rzg2l_wdt_priv *priv, u32 val, unsigned int reg) 100 { 101 if (reg == WDTSET) 102 val &= WDTSET_COUNTER_MASK; 103 104 writel_relaxed(val, priv->base + reg); 105 /* Registers other than the WDTINT is always synchronized with WDT_CLK */ 106 if (reg != WDTINT) 107 rzg2l_wdt_wait_delay(priv); 108 } 109 110 static void rzg2l_wdt_init_timeout(struct watchdog_device *wdev) 111 { 112 struct rzg2l_wdt_priv *priv = watchdog_get_drvdata(wdev); 113 u32 time_out; 114 115 /* Clear Lapsed Time Register and clear Interrupt */ 116 rzg2l_wdt_write(priv, WDTINT_INTDISP, WDTINT); 117 /* 2 consecutive overflow cycle needed to trigger reset */ 118 time_out = (wdev->timeout * (MICRO / 2)) / 119 rzg2l_wdt_get_cycle_usec(priv->osc_clk_rate, 0); 120 rzg2l_wdt_write(priv, WDTSET_COUNTER_VAL(time_out), WDTSET); 121 } 122 123 static int rzg2l_wdt_start(struct watchdog_device *wdev) 124 { 125 struct rzg2l_wdt_priv *priv = watchdog_get_drvdata(wdev); 126 int ret; 127 128 ret = pm_runtime_resume_and_get(wdev->parent); 129 if (ret) 130 return ret; 131 132 /* Initialize time out */ 133 rzg2l_wdt_init_timeout(wdev); 134 135 /* Initialize watchdog counter register */ 136 rzg2l_wdt_write(priv, 0, WDTTIM); 137 138 /* Enable watchdog timer*/ 139 rzg2l_wdt_write(priv, WDTCNT_WDTEN, WDTCNT); 140 141 return 0; 142 } 143 144 static int rzg2l_wdt_stop(struct watchdog_device *wdev) 145 { 146 struct rzg2l_wdt_priv *priv = watchdog_get_drvdata(wdev); 147 int ret; 148 149 rzg2l_wdt_reset(priv); 150 151 ret = pm_runtime_put(wdev->parent); 152 if (ret < 0) 153 return ret; 154 155 return 0; 156 } 157 158 static int rzg2l_wdt_set_timeout(struct watchdog_device *wdev, unsigned int timeout) 159 { 160 int ret = 0; 161 162 wdev->timeout = timeout; 163 164 /* 165 * If the watchdog is active, reset the module for updating the WDTSET 166 * register by calling rzg2l_wdt_stop() (which internally calls reset_control_reset() 167 * to reset the module) so that it is updated with new timeout values. 168 */ 169 if (watchdog_active(wdev)) { 170 ret = rzg2l_wdt_stop(wdev); 171 if (ret) 172 return ret; 173 174 ret = rzg2l_wdt_start(wdev); 175 } 176 177 return ret; 178 } 179 180 static int rzg2l_wdt_restart(struct watchdog_device *wdev, 181 unsigned long action, void *data) 182 { 183 struct rzg2l_wdt_priv *priv = watchdog_get_drvdata(wdev); 184 185 clk_prepare_enable(priv->pclk); 186 clk_prepare_enable(priv->osc_clk); 187 188 if (priv->devtype == WDT_RZG2L) { 189 /* Generate Reset (WDTRSTB) Signal on parity error */ 190 rzg2l_wdt_write(priv, 0, PECR); 191 192 /* Force parity error */ 193 rzg2l_wdt_write(priv, PEEN_FORCE, PEEN); 194 } else { 195 /* RZ/V2M doesn't have parity error registers */ 196 rzg2l_wdt_reset(priv); 197 198 wdev->timeout = 0; 199 200 /* Initialize time out */ 201 rzg2l_wdt_init_timeout(wdev); 202 203 /* Initialize watchdog counter register */ 204 rzg2l_wdt_write(priv, 0, WDTTIM); 205 206 /* Enable watchdog timer*/ 207 rzg2l_wdt_write(priv, WDTCNT_WDTEN, WDTCNT); 208 209 /* Wait 2 consecutive overflow cycles for reset */ 210 mdelay(DIV_ROUND_UP(2 * 0xFFFFF * 1000, priv->osc_clk_rate)); 211 } 212 213 return 0; 214 } 215 216 static const struct watchdog_info rzg2l_wdt_ident = { 217 .options = WDIOF_MAGICCLOSE | WDIOF_KEEPALIVEPING | WDIOF_SETTIMEOUT, 218 .identity = "Renesas RZ/G2L WDT Watchdog", 219 }; 220 221 static int rzg2l_wdt_ping(struct watchdog_device *wdev) 222 { 223 struct rzg2l_wdt_priv *priv = watchdog_get_drvdata(wdev); 224 225 rzg2l_wdt_write(priv, WDTINT_INTDISP, WDTINT); 226 227 return 0; 228 } 229 230 static const struct watchdog_ops rzg2l_wdt_ops = { 231 .owner = THIS_MODULE, 232 .start = rzg2l_wdt_start, 233 .stop = rzg2l_wdt_stop, 234 .ping = rzg2l_wdt_ping, 235 .set_timeout = rzg2l_wdt_set_timeout, 236 .restart = rzg2l_wdt_restart, 237 }; 238 239 static void rzg2l_wdt_reset_assert_pm_disable(void *data) 240 { 241 struct watchdog_device *wdev = data; 242 struct rzg2l_wdt_priv *priv = watchdog_get_drvdata(wdev); 243 244 pm_runtime_disable(wdev->parent); 245 reset_control_assert(priv->rstc); 246 } 247 248 static int rzg2l_wdt_probe(struct platform_device *pdev) 249 { 250 struct device *dev = &pdev->dev; 251 struct rzg2l_wdt_priv *priv; 252 unsigned long pclk_rate; 253 int ret; 254 255 priv = devm_kzalloc(dev, sizeof(*priv), GFP_KERNEL); 256 if (!priv) 257 return -ENOMEM; 258 259 priv->base = devm_platform_ioremap_resource(pdev, 0); 260 if (IS_ERR(priv->base)) 261 return PTR_ERR(priv->base); 262 263 /* Get watchdog main clock */ 264 priv->osc_clk = devm_clk_get(&pdev->dev, "oscclk"); 265 if (IS_ERR(priv->osc_clk)) 266 return dev_err_probe(&pdev->dev, PTR_ERR(priv->osc_clk), "no oscclk"); 267 268 priv->osc_clk_rate = clk_get_rate(priv->osc_clk); 269 if (!priv->osc_clk_rate) 270 return dev_err_probe(&pdev->dev, -EINVAL, "oscclk rate is 0"); 271 272 /* Get Peripheral clock */ 273 priv->pclk = devm_clk_get(&pdev->dev, "pclk"); 274 if (IS_ERR(priv->pclk)) 275 return dev_err_probe(&pdev->dev, PTR_ERR(priv->pclk), "no pclk"); 276 277 pclk_rate = clk_get_rate(priv->pclk); 278 if (!pclk_rate) 279 return dev_err_probe(&pdev->dev, -EINVAL, "pclk rate is 0"); 280 281 priv->delay = F2CYCLE_NSEC(priv->osc_clk_rate) * 6 + F2CYCLE_NSEC(pclk_rate) * 9; 282 283 priv->rstc = devm_reset_control_get_exclusive(&pdev->dev, NULL); 284 if (IS_ERR(priv->rstc)) 285 return dev_err_probe(&pdev->dev, PTR_ERR(priv->rstc), 286 "failed to get cpg reset"); 287 288 ret = reset_control_deassert(priv->rstc); 289 if (ret) 290 return dev_err_probe(dev, ret, "failed to deassert"); 291 292 priv->devtype = (uintptr_t)of_device_get_match_data(dev); 293 294 if (priv->devtype == WDT_RZV2M) { 295 priv->minimum_assertion_period = RZV2M_A_NSEC + 296 3 * F2CYCLE_NSEC(pclk_rate) + 5 * 297 max(F2CYCLE_NSEC(priv->osc_clk_rate), 298 F2CYCLE_NSEC(pclk_rate)); 299 } 300 301 pm_runtime_enable(&pdev->dev); 302 303 priv->wdev.info = &rzg2l_wdt_ident; 304 priv->wdev.ops = &rzg2l_wdt_ops; 305 priv->wdev.parent = dev; 306 priv->wdev.min_timeout = 1; 307 priv->wdev.max_timeout = rzg2l_wdt_get_cycle_usec(priv->osc_clk_rate, 0xfff) / 308 USEC_PER_SEC; 309 priv->wdev.timeout = WDT_DEFAULT_TIMEOUT; 310 311 watchdog_set_drvdata(&priv->wdev, priv); 312 ret = devm_add_action_or_reset(&pdev->dev, 313 rzg2l_wdt_reset_assert_pm_disable, 314 &priv->wdev); 315 if (ret < 0) 316 return ret; 317 318 watchdog_set_nowayout(&priv->wdev, nowayout); 319 watchdog_stop_on_unregister(&priv->wdev); 320 321 ret = watchdog_init_timeout(&priv->wdev, 0, dev); 322 if (ret) 323 dev_warn(dev, "Specified timeout invalid, using default"); 324 325 return devm_watchdog_register_device(&pdev->dev, &priv->wdev); 326 } 327 328 static const struct of_device_id rzg2l_wdt_ids[] = { 329 { .compatible = "renesas,rzg2l-wdt", .data = (void *)WDT_RZG2L }, 330 { .compatible = "renesas,rzv2m-wdt", .data = (void *)WDT_RZV2M }, 331 { /* sentinel */ } 332 }; 333 MODULE_DEVICE_TABLE(of, rzg2l_wdt_ids); 334 335 static struct platform_driver rzg2l_wdt_driver = { 336 .driver = { 337 .name = "rzg2l_wdt", 338 .of_match_table = rzg2l_wdt_ids, 339 }, 340 .probe = rzg2l_wdt_probe, 341 }; 342 module_platform_driver(rzg2l_wdt_driver); 343 344 MODULE_DESCRIPTION("Renesas RZ/G2L WDT Watchdog Driver"); 345 MODULE_AUTHOR("Biju Das <biju.das.jz@bp.renesas.com>"); 346 MODULE_LICENSE("GPL v2"); 347