1f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du/* 2f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * Watchdog driver for CSR SiRFprimaII and SiRFatlasVI 3f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * 4f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * Copyright (c) 2013 Cambridge Silicon Radio Limited, a CSR plc group company. 5f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * 6f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * Licensed under GPLv2 or later. 7f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du */ 8f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 9f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/module.h> 10f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/watchdog.h> 11f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/platform_device.h> 12f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/moduleparam.h> 13f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/of.h> 14f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/io.h> 15f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#include <linux/uaccess.h> 16f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 17b0df38dd3554d47fcfd5c1183951c2fe7dd07edaUwe Kleine-König#define CLOCK_FREQ 1000000 18b0df38dd3554d47fcfd5c1183951c2fe7dd07edaUwe Kleine-König 19f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_COUNTER_LO 0x0000 20f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_MATCH_0 0x0008 21f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_INT_EN 0x0024 22f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_WATCHDOG_EN 0x0028 23f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_LATCH 0x0030 24f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_LATCHED_LO 0x0034 25f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 26f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_TIMER_WDT_INDEX 5 27f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 28f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_WDT_MIN_TIMEOUT 30 /* 30 secs */ 29f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_WDT_MAX_TIMEOUT (10 * 60) /* 10 mins */ 30f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define SIRFSOC_WDT_DEFAULT_TIMEOUT 30 /* 30 secs */ 31f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 32f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic unsigned int timeout = SIRFSOC_WDT_DEFAULT_TIMEOUT; 33f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic bool nowayout = WATCHDOG_NOWAYOUT; 34f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 35f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dumodule_param(timeout, uint, 0); 36f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dumodule_param(nowayout, bool, 0); 37f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 38f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_PARM_DESC(timeout, "Default watchdog timeout (in seconds)"); 39f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_PARM_DESC(nowayout, "Watchdog cannot be stopped once started (default=" 40f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du __MODULE_STRING(WATCHDOG_NOWAYOUT) ")"); 41f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 42f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic unsigned int sirfsoc_wdt_gettimeleft(struct watchdog_device *wdd) 43f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 44f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du u32 counter, match; 45f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du void __iomem *wdt_base; 46f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du int time_left; 47f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 48f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du wdt_base = watchdog_get_drvdata(wdd); 49f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du counter = readl(wdt_base + SIRFSOC_TIMER_COUNTER_LO); 50f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du match = readl(wdt_base + 51f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du SIRFSOC_TIMER_MATCH_0 + (SIRFSOC_TIMER_WDT_INDEX << 2)); 52f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 53f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du time_left = match - counter; 54f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 55b0df38dd3554d47fcfd5c1183951c2fe7dd07edaUwe Kleine-König return time_left / CLOCK_FREQ; 56f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 57f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 58f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_updatetimeout(struct watchdog_device *wdd) 59f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 60f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du u32 counter, timeout_ticks; 61f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du void __iomem *wdt_base; 62f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 63b0df38dd3554d47fcfd5c1183951c2fe7dd07edaUwe Kleine-König timeout_ticks = wdd->timeout * CLOCK_FREQ; 64f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du wdt_base = watchdog_get_drvdata(wdd); 65f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 66f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du /* Enable the latch before reading the LATCH_LO register */ 67f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du writel(1, wdt_base + SIRFSOC_TIMER_LATCH); 68f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 69f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du /* Set the TO value */ 70f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du counter = readl(wdt_base + SIRFSOC_TIMER_LATCHED_LO); 71f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 72f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du counter += timeout_ticks; 73f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 74f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du writel(counter, wdt_base + 75f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du SIRFSOC_TIMER_MATCH_0 + (SIRFSOC_TIMER_WDT_INDEX << 2)); 76f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 77f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 78f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 79f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 80f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_enable(struct watchdog_device *wdd) 81f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 82f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du void __iomem *wdt_base = watchdog_get_drvdata(wdd); 83f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du sirfsoc_wdt_updatetimeout(wdd); 84f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 85f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du /* 86f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * NOTE: If interrupt is not enabled 87f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * then WD-Reset doesn't get generated at all. 88f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du */ 89f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du writel(readl(wdt_base + SIRFSOC_TIMER_INT_EN) 90f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du | (1 << SIRFSOC_TIMER_WDT_INDEX), 91f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du wdt_base + SIRFSOC_TIMER_INT_EN); 92f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du writel(1, wdt_base + SIRFSOC_TIMER_WATCHDOG_EN); 93f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 94f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 95f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 96f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 97f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_disable(struct watchdog_device *wdd) 98f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 99f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du void __iomem *wdt_base = watchdog_get_drvdata(wdd); 100f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 101f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du writel(0, wdt_base + SIRFSOC_TIMER_WATCHDOG_EN); 102f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du writel(readl(wdt_base + SIRFSOC_TIMER_INT_EN) 103f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du & (~(1 << SIRFSOC_TIMER_WDT_INDEX)), 104f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du wdt_base + SIRFSOC_TIMER_INT_EN); 105f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 106f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 107f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 108f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 109f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_settimeout(struct watchdog_device *wdd, unsigned int to) 110f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 111f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du wdd->timeout = to; 112f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du sirfsoc_wdt_updatetimeout(wdd); 113f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 114f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 115f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 116f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 117f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#define OPTIONS (WDIOF_SETTIMEOUT | WDIOF_KEEPALIVEPING | WDIOF_MAGICCLOSE) 118f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 119f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic const struct watchdog_info sirfsoc_wdt_ident = { 120f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .options = OPTIONS, 121f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .firmware_version = 0, 122f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .identity = "SiRFSOC Watchdog", 123f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du}; 124f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 125f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic struct watchdog_ops sirfsoc_wdt_ops = { 126f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .owner = THIS_MODULE, 127f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .start = sirfsoc_wdt_enable, 128f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .stop = sirfsoc_wdt_disable, 129f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .get_timeleft = sirfsoc_wdt_gettimeleft, 130f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .ping = sirfsoc_wdt_updatetimeout, 131f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .set_timeout = sirfsoc_wdt_settimeout, 132f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du}; 133f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 134f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic struct watchdog_device sirfsoc_wdd = { 135f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .info = &sirfsoc_wdt_ident, 136f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .ops = &sirfsoc_wdt_ops, 137f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .timeout = SIRFSOC_WDT_DEFAULT_TIMEOUT, 138f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .min_timeout = SIRFSOC_WDT_MIN_TIMEOUT, 139f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .max_timeout = SIRFSOC_WDT_MAX_TIMEOUT, 140f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du}; 141f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 142f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_probe(struct platform_device *pdev) 143f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 144f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du struct resource *res; 145f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du int ret; 146f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du void __iomem *base; 147f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 148f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du res = platform_get_resource(pdev, IORESOURCE_MEM, 0); 149f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du base = devm_ioremap_resource(&pdev->dev, res); 150f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du if (IS_ERR(base)) 151f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return PTR_ERR(base); 152f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 153f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du watchdog_set_drvdata(&sirfsoc_wdd, base); 154f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 155f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du watchdog_init_timeout(&sirfsoc_wdd, timeout, &pdev->dev); 156f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du watchdog_set_nowayout(&sirfsoc_wdd, nowayout); 157f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 158f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du ret = watchdog_register_device(&sirfsoc_wdd); 159f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du if (ret) 160f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return ret; 161f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 162f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du platform_set_drvdata(pdev, &sirfsoc_wdd); 163f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 164f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 165f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 166f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 167f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic void sirfsoc_wdt_shutdown(struct platform_device *pdev) 168f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 169f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du struct watchdog_device *wdd = platform_get_drvdata(pdev); 170f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 171f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du sirfsoc_wdt_disable(wdd); 172f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 173f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 174f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_remove(struct platform_device *pdev) 175f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 176f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du sirfsoc_wdt_shutdown(pdev); 177f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 178f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 179f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 180f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#ifdef CONFIG_PM_SLEEP 181f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_suspend(struct device *dev) 182f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 183f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 184f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 185f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 186f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic int sirfsoc_wdt_resume(struct device *dev) 187f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du{ 188f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du struct watchdog_device *wdd = dev_get_drvdata(dev); 189f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 190f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du /* 191f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * NOTE: Since timer controller registers settings are saved 192f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * and restored back by the timer-prima2.c, so we need not 193f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du * update WD settings except refreshing timeout. 194f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du */ 195f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du sirfsoc_wdt_updatetimeout(wdd); 196f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 197f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du return 0; 198f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du} 199f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du#endif 200f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 201f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic SIMPLE_DEV_PM_OPS(sirfsoc_wdt_pm_ops, 202f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du sirfsoc_wdt_suspend, sirfsoc_wdt_resume); 203f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 204f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic const struct of_device_id sirfsoc_wdt_of_match[] = { 205f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du { .compatible = "sirf,prima2-tick"}, 206f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du {}, 207f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du}; 208f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_DEVICE_TABLE(of, sirfsoc_wdt_of_match); 209f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 210f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dustatic struct platform_driver sirfsoc_wdt_driver = { 211f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .driver = { 212f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .name = "sirfsoc-wdt", 213f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .owner = THIS_MODULE, 214f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .pm = &sirfsoc_wdt_pm_ops, 21515edd9eedd61ac7be53d63ffa6a7208d4479ceceSachin Kamat .of_match_table = sirfsoc_wdt_of_match, 216f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du }, 217f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .probe = sirfsoc_wdt_probe, 218f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .remove = sirfsoc_wdt_remove, 219f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du .shutdown = sirfsoc_wdt_shutdown, 220f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du}; 221f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Dumodule_platform_driver(sirfsoc_wdt_driver); 222f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong Du 223f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_DESCRIPTION("SiRF SoC watchdog driver"); 224f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_AUTHOR("Xianglong Du <Xianglong.Du@csr.com>"); 225f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_LICENSE("GPL v2"); 226f0fcbdbf202e2be36c8eb6d1f5c01f95805777deXianglong DuMODULE_ALIAS("platform:sirfsoc-wdt"); 227