Linux kernel mirror (for testing) git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git
kernel os linux
1
fork

Configure Feed

Select the types of activity you want to include in your feed.

Merge tag 'timers-core-2022-08-01' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull timer updates from Thomas Gleixner:
"Timers, timekeeping and related drivers update:

Core:

- Make wait_event_hrtimeout() aware of RT/DL tasks

New drivers:

- R-Car Gen4 timer

- Tegra186 timer

- Mediatek MT6795 CPUXGPT timer

Updates:

- Rework suspend/resume handling in timer drivers so it
takes inactive clocks into account.

- The usual device tree compatible add ons

- Small fixed and cleanups all over the place"

* tag 'timers-core-2022-08-01' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: (24 commits)
wait: Fix __wait_event_hrtimeout for RT/DL tasks
clocksource/drivers/sun5i: Remove unnecessary (void*) conversions
dt-bindings: timer: allwinner,sun4i-a10-timer: Add D1 compatible
dt-bindings: timer: ingenic,tcu: use absolute path to other schema
clocksource/drivers/sun4i: Remove unnecessary (void*) conversions
dt-bindings: timer: renesas,cmt: Fix R-Car Gen4 fall-out
clocksource/drivers/tegra186: Put Kconfig option 'tristate' to 'bool'
clocksource/drivers/timer-ti-dm: Make driver selection bool for TI K3
clocksource/drivers/timer-ti-dm: Add compatible for am6 SoCs
clocksource/drivers/timer-ti-dm: Make timer selectable for ARCH_K3
clocksource/drivers/timer-ti-dm: Move inline functions to driver for am6
clocksource/drivers/sh_cmt: Add R-Car Gen4 support
dt-bindings: timer: renesas,cmt: R-Car V3U is R-Car Gen4
dt-bindings: timer: renesas,cmt: Add r8a779f0 and generic Gen4 CMT support
clocksource/drivers/timer-microchip-pit64b: Fix compilation warnings
clocksource/drivers/timer-microchip-pit64b: Use mchp_pit64b_{suspend, resume}
clocksource/drivers/timer-microchip-pit64b: Remove suspend/resume ops for ce
thermal/drivers/rcar_gen3_thermal: Add r8a779f0 support
clocksource/drivers/timer-mediatek: Implement CPUXGPT timers
dt-bindings: timer: mediatek: Add CPUX System Timer and MT6795 compatible
...

+901 -198
+1
Documentation/devicetree/bindings/timer/allwinner,sun4i-a10-timer.yaml
··· 20 20 - allwinner,suniv-f1c100s-timer 21 21 - items: 22 22 - enum: 23 + - allwinner,sun20i-d1-timer 23 24 - allwinner,sun50i-a64-timer 24 25 - allwinner,sun50i-h6-timer 25 26 - allwinner,sun50i-h616-timer
+2 -2
Documentation/devicetree/bindings/timer/ingenic,tcu.yaml
··· 113 113 patternProperties: 114 114 "^watchdog@[a-f0-9]+$": 115 115 type: object 116 - $ref: ../watchdog/watchdog.yaml# 116 + $ref: /schemas/watchdog/watchdog.yaml# 117 117 properties: 118 118 compatible: 119 119 oneOf: ··· 145 145 146 146 "^pwm@[a-f0-9]+$": 147 147 type: object 148 - $ref: ../pwm/pwm.yaml# 148 + $ref: /schemas/pwm/pwm.yaml# 149 149 properties: 150 150 compatible: 151 151 oneOf:
+5 -1
Documentation/devicetree/bindings/timer/mediatek,mtk-timer.txt
··· 1 1 MediaTek Timers 2 2 --------------- 3 3 4 - MediaTek SoCs have two different timers on different platforms, 4 + MediaTek SoCs have different timers on different platforms, 5 + - CPUX (ARM/ARM64 System Timer) 5 6 - GPT (General Purpose Timer) 6 7 - SYST (System Timer) 7 8 ··· 29 28 * "mediatek,mt8195-timer" for MT8195 compatible timers (SYST) 30 29 * "mediatek,mt7629-timer" for MT7629 compatible timers (SYST) 31 30 * "mediatek,mt6765-timer" for MT6765 and all above compatible timers (SYST) 31 + 32 + For those SoCs that use CPUX 33 + * "mediatek,mt6795-systimer" for MT6795 compatible timers (CPUX) 32 34 33 35 - reg: Should contain location and length for timer register. 34 36 - clocks: Should contain system clock.
+14 -2
Documentation/devicetree/bindings/timer/renesas,cmt.yaml
··· 80 80 - renesas,r8a77980-cmt0 # 32-bit CMT0 on R-Car V3H 81 81 - renesas,r8a77990-cmt0 # 32-bit CMT0 on R-Car E3 82 82 - renesas,r8a77995-cmt0 # 32-bit CMT0 on R-Car D3 83 - - renesas,r8a779a0-cmt0 # 32-bit CMT0 on R-Car V3U 84 83 - const: renesas,rcar-gen3-cmt0 # 32-bit CMT0 on R-Car Gen3 and RZ/G2 85 84 86 85 - items: ··· 96 97 - renesas,r8a77980-cmt1 # 48-bit CMT on R-Car V3H 97 98 - renesas,r8a77990-cmt1 # 48-bit CMT on R-Car E3 98 99 - renesas,r8a77995-cmt1 # 48-bit CMT on R-Car D3 99 - - renesas,r8a779a0-cmt1 # 48-bit CMT on R-Car V3U 100 100 - const: renesas,rcar-gen3-cmt1 # 48-bit CMT on R-Car Gen3 and RZ/G2 101 + 102 + - items: 103 + - enum: 104 + - renesas,r8a779a0-cmt0 # 32-bit CMT0 on R-Car V3U 105 + - renesas,r8a779f0-cmt0 # 32-bit CMT0 on R-Car S4-8 106 + - const: renesas,rcar-gen4-cmt0 # 32-bit CMT0 on R-Car Gen4 107 + 108 + - items: 109 + - enum: 110 + - renesas,r8a779a0-cmt1 # 48-bit CMT on R-Car V3U 111 + - renesas,r8a779f0-cmt1 # 48-bit CMT on R-Car S4-8 112 + - const: renesas,rcar-gen4-cmt1 # 48-bit CMT on R-Car Gen4 101 113 102 114 reg: 103 115 maxItems: 1 ··· 145 135 enum: 146 136 - renesas,rcar-gen2-cmt0 147 137 - renesas,rcar-gen3-cmt0 138 + - renesas,rcar-gen4-cmt0 148 139 then: 149 140 properties: 150 141 interrupts: ··· 159 148 enum: 160 149 - renesas,rcar-gen2-cmt1 161 150 - renesas,rcar-gen3-cmt1 151 + - renesas,rcar-gen4-cmt1 162 152 then: 163 153 properties: 164 154 interrupts:
+58
Documentation/devicetree/bindings/timer/st,nomadik-mtu.yaml
··· 1 + # SPDX-License-Identifier: (GPL-2.0 OR BSD-2-Clause) 2 + # Copyright 2022 Linaro Ltd. 3 + %YAML 1.2 4 + --- 5 + $id: "http://devicetree.org/schemas/timer/st,nomadik-mtu.yaml#" 6 + $schema: "http://devicetree.org/meta-schemas/core.yaml#" 7 + 8 + title: ST Microelectronics Nomadik Multi-Timer Unit MTU Timer 9 + 10 + maintainers: 11 + - Linus Walleij <linus.walleij@linaro.org> 12 + 13 + description: This timer is found in the ST Microelectronics Nomadik 14 + SoCs STn8800, STn8810 and STn8815 as well as in ST-Ericsson DB8500. 15 + 16 + properties: 17 + compatible: 18 + items: 19 + - const: st,nomadik-mtu 20 + 21 + reg: 22 + maxItems: 1 23 + 24 + interrupts: 25 + maxItems: 1 26 + 27 + clocks: 28 + description: The first clock named TIMCLK clocks the actual timers and 29 + the second clock clocks the digital interface to the interconnect. 30 + maxItems: 2 31 + 32 + clock-names: 33 + items: 34 + - const: timclk 35 + - const: apb_pclk 36 + 37 + required: 38 + - compatible 39 + - reg 40 + - interrupts 41 + - clocks 42 + - clock-names 43 + 44 + additionalProperties: false 45 + 46 + examples: 47 + - | 48 + #include <dt-bindings/interrupt-controller/irq.h> 49 + #include <dt-bindings/interrupt-controller/arm-gic.h> 50 + #include <dt-bindings/mfd/dbx500-prcmu.h> 51 + timer@a03c6000 { 52 + compatible = "st,nomadik-mtu"; 53 + reg = <0xa03c6000 0x1000>; 54 + interrupts = <GIC_SPI 4 IRQ_TYPE_LEVEL_HIGH>; 55 + 56 + clocks = <&prcmu_clk PRCMU_TIMCLK>, <&prcc_pclk 6 6>; 57 + clock-names = "timclk", "apb_pclk"; 58 + };
+2
arch/arm/mach-omap2/Kconfig
··· 105 105 select MACH_OMAP_GENERIC 106 106 select MEMORY 107 107 select MFD_SYSCON 108 + select OMAP_DM_SYSTIMER 108 109 select OMAP_DM_TIMER 109 110 select OMAP_GPMC 110 111 select PINCTRL ··· 210 209 bool "OMAP2420 support" 211 210 depends on ARCH_OMAP2 212 211 default y 212 + select OMAP_DM_SYSTIMER 213 213 select OMAP_DM_TIMER 214 214 select SOC_HAS_OMAP2_SDRC 215 215
+17 -2
drivers/clocksource/Kconfig
··· 22 22 config I8253_LOCK 23 23 bool 24 24 25 - config OMAP_DM_TIMER 25 + config OMAP_DM_SYSTIMER 26 26 bool 27 27 select TIMER_OF 28 28 ··· 55 55 depends on HAS_IOMEM 56 56 help 57 57 Enables the support for the digicolor timer driver. 58 + 59 + config OMAP_DM_TIMER 60 + bool "OMAP dual-mode timer driver" if ARCH_K3 || COMPILE_TEST 61 + default y if ARCH_K3 62 + select TIMER_OF 63 + help 64 + Enables the support for the TI dual-mode timer driver. 58 65 59 66 config DW_APB_TIMER 60 67 bool "DW APB timer driver" if COMPILE_TEST ··· 156 149 depends on ARCH_TEGRA || COMPILE_TEST 157 150 help 158 151 Enables support for the Tegra driver. 152 + 153 + config TEGRA186_TIMER 154 + bool "NVIDIA Tegra186 timer driver" 155 + depends on ARCH_TEGRA || COMPILE_TEST 156 + depends on WATCHDOG && WATCHDOG_CORE 157 + help 158 + Enables support for the timers and watchdogs found on NVIDIA 159 + Tegra186 and later SoCs. 159 160 160 161 config VT8500_TIMER 161 162 bool "VT8500 timer driver" if COMPILE_TEST ··· 382 367 depends on ARM_GLOBAL_TIMER 383 368 help 384 369 When the ARM global timer initializes, its current rate is declared 385 - to the kernel and maintained forever. Should it's parent clock 370 + to the kernel and maintained forever. Should its parent clock 386 371 change, the driver tries to fix the timer's internal prescaler. 387 372 On some machs (i.e. Zynq) the initial prescaler value thus poses 388 373 bounds about how much the parent clock is allowed to decrease or
+2 -1
drivers/clocksource/Makefile
··· 18 18 obj-$(CONFIG_DAVINCI_TIMER) += timer-davinci.o 19 19 obj-$(CONFIG_DIGICOLOR_TIMER) += timer-digicolor.o 20 20 obj-$(CONFIG_OMAP_DM_TIMER) += timer-ti-dm.o 21 - obj-$(CONFIG_OMAP_DM_TIMER) += timer-ti-dm-systimer.o 21 + obj-$(CONFIG_OMAP_DM_SYSTIMER) += timer-ti-dm-systimer.o 22 22 obj-$(CONFIG_DW_APB_TIMER) += dw_apb_timer.o 23 23 obj-$(CONFIG_DW_APB_TIMER_OF) += dw_apb_timer_of.o 24 24 obj-$(CONFIG_FTTMR010_TIMER) += timer-fttmr010.o ··· 36 36 obj-$(CONFIG_SUN5I_HSTIMER) += timer-sun5i.o 37 37 obj-$(CONFIG_MESON6_TIMER) += timer-meson6.o 38 38 obj-$(CONFIG_TEGRA_TIMER) += timer-tegra.o 39 + obj-$(CONFIG_TEGRA186_TIMER) += timer-tegra186.o 39 40 obj-$(CONFIG_VT8500_TIMER) += timer-vt8500.o 40 41 obj-$(CONFIG_NSPIRE_TIMER) += timer-zevio.o 41 42 obj-$(CONFIG_BCM_KONA_TIMER) += bcm_kona_timer.o
+8
drivers/clocksource/sh_cmt.c
··· 981 981 .compatible = "renesas,rcar-gen3-cmt1", 982 982 .data = &sh_cmt_info[SH_CMT1_RCAR_GEN2] 983 983 }, 984 + { 985 + .compatible = "renesas,rcar-gen4-cmt0", 986 + .data = &sh_cmt_info[SH_CMT0_RCAR_GEN2] 987 + }, 988 + { 989 + .compatible = "renesas,rcar-gen4-cmt1", 990 + .data = &sh_cmt_info[SH_CMT1_RCAR_GEN2] 991 + }, 984 992 { } 985 993 }; 986 994 MODULE_DEVICE_TABLE(of, sh_cmt_of_table);
+114
drivers/clocksource/timer-mediatek.c
··· 22 22 23 23 #define TIMER_SYNC_TICKS (3) 24 24 25 + /* cpux mcusys wrapper */ 26 + #define CPUX_CON_REG 0x0 27 + #define CPUX_IDX_REG 0x4 28 + 29 + /* cpux */ 30 + #define CPUX_IDX_GLOBAL_CTRL 0x0 31 + #define CPUX_ENABLE BIT(0) 32 + #define CPUX_CLK_DIV_MASK GENMASK(10, 8) 33 + #define CPUX_CLK_DIV1 BIT(8) 34 + #define CPUX_CLK_DIV2 BIT(9) 35 + #define CPUX_CLK_DIV4 BIT(10) 36 + #define CPUX_IDX_GLOBAL_IRQ 0x30 37 + 25 38 /* gpt */ 26 39 #define GPT_IRQ_EN_REG 0x00 27 40 #define GPT_IRQ_ENABLE(val) BIT((val) - 1) ··· 84 71 #define SYST_CON_IRQ_CLR BIT(4) 85 72 86 73 static void __iomem *gpt_sched_reg __read_mostly; 74 + 75 + static u32 mtk_cpux_readl(u32 reg_idx, struct timer_of *to) 76 + { 77 + writel(reg_idx, timer_of_base(to) + CPUX_IDX_REG); 78 + return readl(timer_of_base(to) + CPUX_CON_REG); 79 + } 80 + 81 + static void mtk_cpux_writel(u32 val, u32 reg_idx, struct timer_of *to) 82 + { 83 + writel(reg_idx, timer_of_base(to) + CPUX_IDX_REG); 84 + writel(val, timer_of_base(to) + CPUX_CON_REG); 85 + } 86 + 87 + static void mtk_cpux_set_irq(struct timer_of *to, bool enable) 88 + { 89 + const unsigned long *irq_mask = cpumask_bits(cpu_possible_mask); 90 + u32 val; 91 + 92 + val = mtk_cpux_readl(CPUX_IDX_GLOBAL_IRQ, to); 93 + 94 + if (enable) 95 + val |= *irq_mask; 96 + else 97 + val &= ~(*irq_mask); 98 + 99 + mtk_cpux_writel(val, CPUX_IDX_GLOBAL_IRQ, to); 100 + } 101 + 102 + static int mtk_cpux_clkevt_shutdown(struct clock_event_device *clkevt) 103 + { 104 + /* Clear any irq */ 105 + mtk_cpux_set_irq(to_timer_of(clkevt), false); 106 + 107 + /* 108 + * Disabling CPUXGPT timer will crash the platform, especially 109 + * if Trusted Firmware is using it (usually, for sleep states), 110 + * so we only mask the IRQ and call it a day. 111 + */ 112 + return 0; 113 + } 114 + 115 + static int mtk_cpux_clkevt_resume(struct clock_event_device *clkevt) 116 + { 117 + mtk_cpux_set_irq(to_timer_of(clkevt), true); 118 + return 0; 119 + } 87 120 88 121 static void mtk_syst_ack_irq(struct timer_of *to) 89 122 { ··· 340 281 }, 341 282 }; 342 283 284 + static int __init mtk_cpux_init(struct device_node *node) 285 + { 286 + static struct timer_of to_cpux; 287 + u32 freq, val; 288 + int ret; 289 + 290 + /* 291 + * There are per-cpu interrupts for the CPUX General Purpose Timer 292 + * but since this timer feeds the AArch64 System Timer we can rely 293 + * on the CPU timer PPIs as well, so we don't declare TIMER_OF_IRQ. 294 + */ 295 + to_cpux.flags = TIMER_OF_BASE | TIMER_OF_CLOCK; 296 + to_cpux.clkevt.name = "mtk-cpuxgpt"; 297 + to_cpux.clkevt.rating = 10; 298 + to_cpux.clkevt.cpumask = cpu_possible_mask; 299 + to_cpux.clkevt.set_state_shutdown = mtk_cpux_clkevt_shutdown; 300 + to_cpux.clkevt.tick_resume = mtk_cpux_clkevt_resume; 301 + 302 + /* If this fails, bad things are about to happen... */ 303 + ret = timer_of_init(node, &to_cpux); 304 + if (ret) { 305 + WARN(1, "Cannot start CPUX timers.\n"); 306 + return ret; 307 + } 308 + 309 + /* 310 + * Check if we're given a clock with the right frequency for this 311 + * timer, otherwise warn but keep going with the setup anyway, as 312 + * that makes it possible to still boot the kernel, even though 313 + * it may not work correctly (random lockups, etc). 314 + * The reason behind this is that having an early UART may not be 315 + * possible for everyone and this gives a chance to retrieve kmsg 316 + * for eventual debugging even on consumer devices. 317 + */ 318 + freq = timer_of_rate(&to_cpux); 319 + if (freq > 13000000) 320 + WARN(1, "Requested unsupported timer frequency %u\n", freq); 321 + 322 + /* Clock input is 26MHz, set DIV2 to achieve 13MHz clock */ 323 + val = mtk_cpux_readl(CPUX_IDX_GLOBAL_CTRL, &to_cpux); 324 + val &= ~CPUX_CLK_DIV_MASK; 325 + val |= CPUX_CLK_DIV2; 326 + mtk_cpux_writel(val, CPUX_IDX_GLOBAL_CTRL, &to_cpux); 327 + 328 + /* Enable all CPUXGPT timers */ 329 + val = mtk_cpux_readl(CPUX_IDX_GLOBAL_CTRL, &to_cpux); 330 + mtk_cpux_writel(val | CPUX_ENABLE, CPUX_IDX_GLOBAL_CTRL, &to_cpux); 331 + 332 + clockevents_config_and_register(&to_cpux.clkevt, timer_of_rate(&to_cpux), 333 + TIMER_SYNC_TICKS, 0xffffffff); 334 + 335 + return 0; 336 + } 337 + 343 338 static int __init mtk_syst_init(struct device_node *node) 344 339 { 345 340 int ret; ··· 452 339 } 453 340 TIMER_OF_DECLARE(mtk_mt6577, "mediatek,mt6577-timer", mtk_gpt_init); 454 341 TIMER_OF_DECLARE(mtk_mt6765, "mediatek,mt6765-timer", mtk_syst_init); 342 + TIMER_OF_DECLARE(mtk_mt6795, "mediatek,mt6795-systimer", mtk_cpux_init);
+30 -40
drivers/clocksource/timer-microchip-pit64b.c
··· 61 61 }; 62 62 63 63 /** 64 - * mchp_pit64b_clkevt - PIT64B clockevent data structure 64 + * struct mchp_pit64b_clkevt - PIT64B clockevent data structure 65 65 * @timer: PIT64B timer 66 66 * @clkevt: clockevent 67 67 */ ··· 75 75 struct mchp_pit64b_clkevt, clkevt)) 76 76 77 77 /** 78 - * mchp_pit64b_clksrc - PIT64B clocksource data structure 78 + * struct mchp_pit64b_clksrc - PIT64B clocksource data structure 79 79 * @timer: PIT64B timer 80 80 * @clksrc: clocksource 81 81 */ ··· 173 173 { 174 174 struct mchp_pit64b_timer *timer = clkevt_to_mchp_pit64b_timer(cedev); 175 175 176 - writel_relaxed(MCHP_PIT64B_CR_SWRST, timer->base + MCHP_PIT64B_CR); 176 + if (!clockevent_state_detached(cedev)) 177 + mchp_pit64b_suspend(timer); 177 178 178 179 return 0; 179 180 } ··· 183 182 { 184 183 struct mchp_pit64b_timer *timer = clkevt_to_mchp_pit64b_timer(cedev); 185 184 185 + if (clockevent_state_shutdown(cedev)) 186 + mchp_pit64b_resume(timer); 187 + 186 188 mchp_pit64b_reset(timer, mchp_pit64b_ce_cycles, MCHP_PIT64B_MR_CONT, 189 + MCHP_PIT64B_IER_PERIOD); 190 + 191 + return 0; 192 + } 193 + 194 + static int mchp_pit64b_clkevt_set_oneshot(struct clock_event_device *cedev) 195 + { 196 + struct mchp_pit64b_timer *timer = clkevt_to_mchp_pit64b_timer(cedev); 197 + 198 + if (clockevent_state_shutdown(cedev)) 199 + mchp_pit64b_resume(timer); 200 + 201 + mchp_pit64b_reset(timer, mchp_pit64b_ce_cycles, MCHP_PIT64B_MR_ONE_SHOT, 187 202 MCHP_PIT64B_IER_PERIOD); 188 203 189 204 return 0; ··· 214 197 MCHP_PIT64B_IER_PERIOD); 215 198 216 199 return 0; 217 - } 218 - 219 - static void mchp_pit64b_clkevt_suspend(struct clock_event_device *cedev) 220 - { 221 - struct mchp_pit64b_timer *timer = clkevt_to_mchp_pit64b_timer(cedev); 222 - 223 - mchp_pit64b_suspend(timer); 224 - } 225 - 226 - static void mchp_pit64b_clkevt_resume(struct clock_event_device *cedev) 227 - { 228 - struct mchp_pit64b_timer *timer = clkevt_to_mchp_pit64b_timer(cedev); 229 - 230 - mchp_pit64b_resume(timer); 231 200 } 232 201 233 202 static irqreturn_t mchp_pit64b_interrupt(int irq, void *dev_id) ··· 245 242 } 246 243 247 244 /** 248 - * mchp_pit64b_init_mode - prepare PIT64B mode register value to be used at 249 - * runtime; this includes prescaler and SGCLK bit 245 + * mchp_pit64b_init_mode() - prepare PIT64B mode register value to be used at 246 + * runtime; this includes prescaler and SGCLK bit 247 + * @timer: pointer to pit64b timer to init 248 + * @max_rate: maximum rate that timer's clock could use 250 249 * 251 250 * PIT64B timer may be fed by gclk or pclk. When gclk is used its rate has to 252 251 * be at least 3 times lower that pclk's rate. pclk rate is fixed, gclk rate ··· 346 341 if (!cs) 347 342 return -ENOMEM; 348 343 344 + mchp_pit64b_resume(timer); 349 345 mchp_pit64b_reset(timer, ULLONG_MAX, MCHP_PIT64B_MR_CONT, 0); 350 346 351 347 mchp_pit64b_cs_base = timer->base; ··· 368 362 pr_debug("clksrc: Failed to register PIT64B clocksource!\n"); 369 363 370 364 /* Stop timer. */ 371 - writel_relaxed(MCHP_PIT64B_CR_SWRST, 372 - timer->base + MCHP_PIT64B_CR); 365 + mchp_pit64b_suspend(timer); 373 366 kfree(cs); 374 367 375 368 return ret; ··· 400 395 ce->clkevt.rating = 150; 401 396 ce->clkevt.set_state_shutdown = mchp_pit64b_clkevt_shutdown; 402 397 ce->clkevt.set_state_periodic = mchp_pit64b_clkevt_set_periodic; 398 + ce->clkevt.set_state_oneshot = mchp_pit64b_clkevt_set_oneshot; 403 399 ce->clkevt.set_next_event = mchp_pit64b_clkevt_set_next_event; 404 - ce->clkevt.suspend = mchp_pit64b_clkevt_suspend; 405 - ce->clkevt.resume = mchp_pit64b_clkevt_resume; 406 400 ce->clkevt.cpumask = cpumask_of(0); 407 401 ce->clkevt.irq = irq; 408 402 ··· 452 448 if (ret) 453 449 goto irq_unmap; 454 450 455 - ret = clk_prepare_enable(timer.pclk); 456 - if (ret) 457 - goto irq_unmap; 458 - 459 - if (timer.mode & MCHP_PIT64B_MR_SGCLK) { 460 - ret = clk_prepare_enable(timer.gclk); 461 - if (ret) 462 - goto pclk_unprepare; 463 - 451 + if (timer.mode & MCHP_PIT64B_MR_SGCLK) 464 452 clk_rate = clk_get_rate(timer.gclk); 465 - } else { 453 + else 466 454 clk_rate = clk_get_rate(timer.pclk); 467 - } 468 455 clk_rate = clk_rate / (MCHP_PIT64B_MODE_TO_PRES(timer.mode) + 1); 469 456 470 457 if (clkevt) ··· 464 469 ret = mchp_pit64b_init_clksrc(&timer, clk_rate); 465 470 466 471 if (ret) 467 - goto gclk_unprepare; 472 + goto irq_unmap; 468 473 469 474 return 0; 470 475 471 - gclk_unprepare: 472 - if (timer.mode & MCHP_PIT64B_MR_SGCLK) 473 - clk_disable_unprepare(timer.gclk); 474 - pclk_unprepare: 475 - clk_disable_unprepare(timer.pclk); 476 476 irq_unmap: 477 477 irq_dispose_mapping(irq); 478 478 io_unmap:
+1 -1
drivers/clocksource/timer-sun4i.c
··· 128 128 129 129 static irqreturn_t sun4i_timer_interrupt(int irq, void *dev_id) 130 130 { 131 - struct clock_event_device *evt = (struct clock_event_device *)dev_id; 131 + struct clock_event_device *evt = dev_id; 132 132 struct timer_of *to = to_timer_of(evt); 133 133 134 134 sun4i_timer_clear_interrupt(timer_of_base(to));
+1 -1
drivers/clocksource/timer-sun5i.c
··· 142 142 143 143 static irqreturn_t sun5i_timer_interrupt(int irq, void *dev_id) 144 144 { 145 - struct sun5i_timer_clkevt *ce = (struct sun5i_timer_clkevt *)dev_id; 145 + struct sun5i_timer_clkevt *ce = dev_id; 146 146 147 147 writel(0x1, ce->timer.base + TIMER_IRQ_ST_REG); 148 148 ce->clkevt.event_handler(&ce->clkevt);
+514
drivers/clocksource/timer-tegra186.c
··· 1 + // SPDX-License-Identifier: GPL-2.0-only 2 + /* 3 + * Copyright (c) 2019-2020 NVIDIA Corporation. All rights reserved. 4 + */ 5 + 6 + #include <linux/clocksource.h> 7 + #include <linux/module.h> 8 + #include <linux/interrupt.h> 9 + #include <linux/io.h> 10 + #include <linux/of.h> 11 + #include <linux/of_device.h> 12 + #include <linux/platform_device.h> 13 + #include <linux/pm.h> 14 + #include <linux/watchdog.h> 15 + 16 + /* shared registers */ 17 + #define TKETSC0 0x000 18 + #define TKETSC1 0x004 19 + #define TKEUSEC 0x008 20 + #define TKEOSC 0x00c 21 + 22 + #define TKEIE(x) (0x100 + ((x) * 4)) 23 + #define TKEIE_WDT_MASK(x, y) ((y) << (16 + 4 * (x))) 24 + 25 + /* timer registers */ 26 + #define TMRCR 0x000 27 + #define TMRCR_ENABLE BIT(31) 28 + #define TMRCR_PERIODIC BIT(30) 29 + #define TMRCR_PTV(x) ((x) & 0x0fffffff) 30 + 31 + #define TMRSR 0x004 32 + #define TMRSR_INTR_CLR BIT(30) 33 + 34 + #define TMRCSSR 0x008 35 + #define TMRCSSR_SRC_USEC (0 << 0) 36 + 37 + /* watchdog registers */ 38 + #define WDTCR 0x000 39 + #define WDTCR_SYSTEM_POR_RESET_ENABLE BIT(16) 40 + #define WDTCR_SYSTEM_DEBUG_RESET_ENABLE BIT(15) 41 + #define WDTCR_REMOTE_INT_ENABLE BIT(14) 42 + #define WDTCR_LOCAL_FIQ_ENABLE BIT(13) 43 + #define WDTCR_LOCAL_INT_ENABLE BIT(12) 44 + #define WDTCR_PERIOD_MASK (0xff << 4) 45 + #define WDTCR_PERIOD(x) (((x) & 0xff) << 4) 46 + #define WDTCR_TIMER_SOURCE_MASK 0xf 47 + #define WDTCR_TIMER_SOURCE(x) ((x) & 0xf) 48 + 49 + #define WDTCMDR 0x008 50 + #define WDTCMDR_DISABLE_COUNTER BIT(1) 51 + #define WDTCMDR_START_COUNTER BIT(0) 52 + 53 + #define WDTUR 0x00c 54 + #define WDTUR_UNLOCK_PATTERN 0x0000c45a 55 + 56 + struct tegra186_timer_soc { 57 + unsigned int num_timers; 58 + unsigned int num_wdts; 59 + }; 60 + 61 + struct tegra186_tmr { 62 + struct tegra186_timer *parent; 63 + void __iomem *regs; 64 + unsigned int index; 65 + unsigned int hwirq; 66 + }; 67 + 68 + struct tegra186_wdt { 69 + struct watchdog_device base; 70 + 71 + void __iomem *regs; 72 + unsigned int index; 73 + bool locked; 74 + 75 + struct tegra186_tmr *tmr; 76 + }; 77 + 78 + static inline struct tegra186_wdt *to_tegra186_wdt(struct watchdog_device *wdd) 79 + { 80 + return container_of(wdd, struct tegra186_wdt, base); 81 + } 82 + 83 + struct tegra186_timer { 84 + const struct tegra186_timer_soc *soc; 85 + struct device *dev; 86 + void __iomem *regs; 87 + 88 + struct tegra186_wdt *wdt; 89 + struct clocksource usec; 90 + struct clocksource tsc; 91 + struct clocksource osc; 92 + }; 93 + 94 + static void tmr_writel(struct tegra186_tmr *tmr, u32 value, unsigned int offset) 95 + { 96 + writel_relaxed(value, tmr->regs + offset); 97 + } 98 + 99 + static void wdt_writel(struct tegra186_wdt *wdt, u32 value, unsigned int offset) 100 + { 101 + writel_relaxed(value, wdt->regs + offset); 102 + } 103 + 104 + static u32 wdt_readl(struct tegra186_wdt *wdt, unsigned int offset) 105 + { 106 + return readl_relaxed(wdt->regs + offset); 107 + } 108 + 109 + static struct tegra186_tmr *tegra186_tmr_create(struct tegra186_timer *tegra, 110 + unsigned int index) 111 + { 112 + unsigned int offset = 0x10000 + index * 0x10000; 113 + struct tegra186_tmr *tmr; 114 + 115 + tmr = devm_kzalloc(tegra->dev, sizeof(*tmr), GFP_KERNEL); 116 + if (!tmr) 117 + return ERR_PTR(-ENOMEM); 118 + 119 + tmr->parent = tegra; 120 + tmr->regs = tegra->regs + offset; 121 + tmr->index = index; 122 + tmr->hwirq = 0; 123 + 124 + return tmr; 125 + } 126 + 127 + static const struct watchdog_info tegra186_wdt_info = { 128 + .options = WDIOF_SETTIMEOUT | WDIOF_MAGICCLOSE | WDIOF_KEEPALIVEPING, 129 + .identity = "NVIDIA Tegra186 WDT", 130 + }; 131 + 132 + static void tegra186_wdt_disable(struct tegra186_wdt *wdt) 133 + { 134 + /* unlock and disable the watchdog */ 135 + wdt_writel(wdt, WDTUR_UNLOCK_PATTERN, WDTUR); 136 + wdt_writel(wdt, WDTCMDR_DISABLE_COUNTER, WDTCMDR); 137 + 138 + /* disable timer */ 139 + tmr_writel(wdt->tmr, 0, TMRCR); 140 + } 141 + 142 + static void tegra186_wdt_enable(struct tegra186_wdt *wdt) 143 + { 144 + struct tegra186_timer *tegra = wdt->tmr->parent; 145 + u32 value; 146 + 147 + /* unmask hardware IRQ, this may have been lost across powergate */ 148 + value = TKEIE_WDT_MASK(wdt->index, 1); 149 + writel(value, tegra->regs + TKEIE(wdt->tmr->hwirq)); 150 + 151 + /* clear interrupt */ 152 + tmr_writel(wdt->tmr, TMRSR_INTR_CLR, TMRSR); 153 + 154 + /* select microsecond source */ 155 + tmr_writel(wdt->tmr, TMRCSSR_SRC_USEC, TMRCSSR); 156 + 157 + /* configure timer (system reset happens on the fifth expiration) */ 158 + value = TMRCR_PTV(wdt->base.timeout * USEC_PER_SEC / 5) | 159 + TMRCR_PERIODIC | TMRCR_ENABLE; 160 + tmr_writel(wdt->tmr, value, TMRCR); 161 + 162 + if (!wdt->locked) { 163 + value = wdt_readl(wdt, WDTCR); 164 + 165 + /* select the proper timer source */ 166 + value &= ~WDTCR_TIMER_SOURCE_MASK; 167 + value |= WDTCR_TIMER_SOURCE(wdt->tmr->index); 168 + 169 + /* single timer period since that's already configured */ 170 + value &= ~WDTCR_PERIOD_MASK; 171 + value |= WDTCR_PERIOD(1); 172 + 173 + /* enable local interrupt for WDT petting */ 174 + value |= WDTCR_LOCAL_INT_ENABLE; 175 + 176 + /* enable local FIQ and remote interrupt for debug dump */ 177 + if (0) 178 + value |= WDTCR_REMOTE_INT_ENABLE | 179 + WDTCR_LOCAL_FIQ_ENABLE; 180 + 181 + /* enable system debug reset (doesn't properly reboot) */ 182 + if (0) 183 + value |= WDTCR_SYSTEM_DEBUG_RESET_ENABLE; 184 + 185 + /* enable system POR reset */ 186 + value |= WDTCR_SYSTEM_POR_RESET_ENABLE; 187 + 188 + wdt_writel(wdt, value, WDTCR); 189 + } 190 + 191 + wdt_writel(wdt, WDTCMDR_START_COUNTER, WDTCMDR); 192 + } 193 + 194 + static int tegra186_wdt_start(struct watchdog_device *wdd) 195 + { 196 + struct tegra186_wdt *wdt = to_tegra186_wdt(wdd); 197 + 198 + tegra186_wdt_enable(wdt); 199 + 200 + return 0; 201 + } 202 + 203 + static int tegra186_wdt_stop(struct watchdog_device *wdd) 204 + { 205 + struct tegra186_wdt *wdt = to_tegra186_wdt(wdd); 206 + 207 + tegra186_wdt_disable(wdt); 208 + 209 + return 0; 210 + } 211 + 212 + static int tegra186_wdt_ping(struct watchdog_device *wdd) 213 + { 214 + struct tegra186_wdt *wdt = to_tegra186_wdt(wdd); 215 + 216 + tegra186_wdt_disable(wdt); 217 + tegra186_wdt_enable(wdt); 218 + 219 + return 0; 220 + } 221 + 222 + static int tegra186_wdt_set_timeout(struct watchdog_device *wdd, 223 + unsigned int timeout) 224 + { 225 + struct tegra186_wdt *wdt = to_tegra186_wdt(wdd); 226 + 227 + if (watchdog_active(&wdt->base)) 228 + tegra186_wdt_disable(wdt); 229 + 230 + wdt->base.timeout = timeout; 231 + 232 + if (watchdog_active(&wdt->base)) 233 + tegra186_wdt_enable(wdt); 234 + 235 + return 0; 236 + } 237 + 238 + static const struct watchdog_ops tegra186_wdt_ops = { 239 + .owner = THIS_MODULE, 240 + .start = tegra186_wdt_start, 241 + .stop = tegra186_wdt_stop, 242 + .ping = tegra186_wdt_ping, 243 + .set_timeout = tegra186_wdt_set_timeout, 244 + }; 245 + 246 + static struct tegra186_wdt *tegra186_wdt_create(struct tegra186_timer *tegra, 247 + unsigned int index) 248 + { 249 + unsigned int offset = 0x10000, source; 250 + struct tegra186_wdt *wdt; 251 + u32 value; 252 + int err; 253 + 254 + offset += tegra->soc->num_timers * 0x10000 + index * 0x10000; 255 + 256 + wdt = devm_kzalloc(tegra->dev, sizeof(*wdt), GFP_KERNEL); 257 + if (!wdt) 258 + return ERR_PTR(-ENOMEM); 259 + 260 + wdt->regs = tegra->regs + offset; 261 + wdt->index = index; 262 + 263 + /* read the watchdog configuration since it might be locked down */ 264 + value = wdt_readl(wdt, WDTCR); 265 + 266 + if (value & WDTCR_LOCAL_INT_ENABLE) 267 + wdt->locked = true; 268 + 269 + source = value & WDTCR_TIMER_SOURCE_MASK; 270 + 271 + wdt->tmr = tegra186_tmr_create(tegra, source); 272 + if (IS_ERR(wdt->tmr)) 273 + return ERR_CAST(wdt->tmr); 274 + 275 + wdt->base.info = &tegra186_wdt_info; 276 + wdt->base.ops = &tegra186_wdt_ops; 277 + wdt->base.min_timeout = 1; 278 + wdt->base.max_timeout = 255; 279 + wdt->base.parent = tegra->dev; 280 + 281 + err = watchdog_init_timeout(&wdt->base, 5, tegra->dev); 282 + if (err < 0) { 283 + dev_err(tegra->dev, "failed to initialize timeout: %d\n", err); 284 + return ERR_PTR(err); 285 + } 286 + 287 + err = devm_watchdog_register_device(tegra->dev, &wdt->base); 288 + if (err < 0) { 289 + dev_err(tegra->dev, "failed to register WDT: %d\n", err); 290 + return ERR_PTR(err); 291 + } 292 + 293 + return wdt; 294 + } 295 + 296 + static u64 tegra186_timer_tsc_read(struct clocksource *cs) 297 + { 298 + struct tegra186_timer *tegra = container_of(cs, struct tegra186_timer, 299 + tsc); 300 + u32 hi, lo, ss; 301 + 302 + hi = readl_relaxed(tegra->regs + TKETSC1); 303 + 304 + /* 305 + * The 56-bit value of the TSC is spread across two registers that are 306 + * not synchronized. In order to read them atomically, ensure that the 307 + * high 24 bits match before and after reading the low 32 bits. 308 + */ 309 + do { 310 + /* snapshot the high 24 bits */ 311 + ss = hi; 312 + 313 + lo = readl_relaxed(tegra->regs + TKETSC0); 314 + hi = readl_relaxed(tegra->regs + TKETSC1); 315 + } while (hi != ss); 316 + 317 + return (u64)hi << 32 | lo; 318 + } 319 + 320 + static int tegra186_timer_tsc_init(struct tegra186_timer *tegra) 321 + { 322 + tegra->tsc.name = "tsc"; 323 + tegra->tsc.rating = 300; 324 + tegra->tsc.read = tegra186_timer_tsc_read; 325 + tegra->tsc.mask = CLOCKSOURCE_MASK(56); 326 + tegra->tsc.flags = CLOCK_SOURCE_IS_CONTINUOUS; 327 + 328 + return clocksource_register_hz(&tegra->tsc, 31250000); 329 + } 330 + 331 + static u64 tegra186_timer_osc_read(struct clocksource *cs) 332 + { 333 + struct tegra186_timer *tegra = container_of(cs, struct tegra186_timer, 334 + osc); 335 + 336 + return readl_relaxed(tegra->regs + TKEOSC); 337 + } 338 + 339 + static int tegra186_timer_osc_init(struct tegra186_timer *tegra) 340 + { 341 + tegra->osc.name = "osc"; 342 + tegra->osc.rating = 300; 343 + tegra->osc.read = tegra186_timer_osc_read; 344 + tegra->osc.mask = CLOCKSOURCE_MASK(32); 345 + tegra->osc.flags = CLOCK_SOURCE_IS_CONTINUOUS; 346 + 347 + return clocksource_register_hz(&tegra->osc, 38400000); 348 + } 349 + 350 + static u64 tegra186_timer_usec_read(struct clocksource *cs) 351 + { 352 + struct tegra186_timer *tegra = container_of(cs, struct tegra186_timer, 353 + usec); 354 + 355 + return readl_relaxed(tegra->regs + TKEUSEC); 356 + } 357 + 358 + static int tegra186_timer_usec_init(struct tegra186_timer *tegra) 359 + { 360 + tegra->usec.name = "usec"; 361 + tegra->usec.rating = 300; 362 + tegra->usec.read = tegra186_timer_usec_read; 363 + tegra->usec.mask = CLOCKSOURCE_MASK(32); 364 + tegra->usec.flags = CLOCK_SOURCE_IS_CONTINUOUS; 365 + 366 + return clocksource_register_hz(&tegra->usec, USEC_PER_SEC); 367 + } 368 + 369 + static irqreturn_t tegra186_timer_irq(int irq, void *data) 370 + { 371 + struct tegra186_timer *tegra = data; 372 + 373 + if (watchdog_active(&tegra->wdt->base)) { 374 + tegra186_wdt_disable(tegra->wdt); 375 + tegra186_wdt_enable(tegra->wdt); 376 + } 377 + 378 + return IRQ_HANDLED; 379 + } 380 + 381 + static int tegra186_timer_probe(struct platform_device *pdev) 382 + { 383 + struct device *dev = &pdev->dev; 384 + struct tegra186_timer *tegra; 385 + unsigned int irq; 386 + int err; 387 + 388 + tegra = devm_kzalloc(dev, sizeof(*tegra), GFP_KERNEL); 389 + if (!tegra) 390 + return -ENOMEM; 391 + 392 + tegra->soc = of_device_get_match_data(dev); 393 + dev_set_drvdata(dev, tegra); 394 + tegra->dev = dev; 395 + 396 + tegra->regs = devm_platform_ioremap_resource(pdev, 0); 397 + if (IS_ERR(tegra->regs)) 398 + return PTR_ERR(tegra->regs); 399 + 400 + err = platform_get_irq(pdev, 0); 401 + if (err < 0) 402 + return err; 403 + 404 + irq = err; 405 + 406 + /* create a watchdog using a preconfigured timer */ 407 + tegra->wdt = tegra186_wdt_create(tegra, 0); 408 + if (IS_ERR(tegra->wdt)) { 409 + err = PTR_ERR(tegra->wdt); 410 + dev_err(dev, "failed to create WDT: %d\n", err); 411 + return err; 412 + } 413 + 414 + err = tegra186_timer_tsc_init(tegra); 415 + if (err < 0) { 416 + dev_err(dev, "failed to register TSC counter: %d\n", err); 417 + return err; 418 + } 419 + 420 + err = tegra186_timer_osc_init(tegra); 421 + if (err < 0) { 422 + dev_err(dev, "failed to register OSC counter: %d\n", err); 423 + goto unregister_tsc; 424 + } 425 + 426 + err = tegra186_timer_usec_init(tegra); 427 + if (err < 0) { 428 + dev_err(dev, "failed to register USEC counter: %d\n", err); 429 + goto unregister_osc; 430 + } 431 + 432 + err = devm_request_irq(dev, irq, tegra186_timer_irq, 0, 433 + "tegra186-timer", tegra); 434 + if (err < 0) { 435 + dev_err(dev, "failed to request IRQ#%u: %d\n", irq, err); 436 + goto unregister_usec; 437 + } 438 + 439 + return 0; 440 + 441 + unregister_usec: 442 + clocksource_unregister(&tegra->usec); 443 + unregister_osc: 444 + clocksource_unregister(&tegra->osc); 445 + unregister_tsc: 446 + clocksource_unregister(&tegra->tsc); 447 + return err; 448 + } 449 + 450 + static int tegra186_timer_remove(struct platform_device *pdev) 451 + { 452 + struct tegra186_timer *tegra = platform_get_drvdata(pdev); 453 + 454 + clocksource_unregister(&tegra->usec); 455 + clocksource_unregister(&tegra->osc); 456 + clocksource_unregister(&tegra->tsc); 457 + 458 + return 0; 459 + } 460 + 461 + static int __maybe_unused tegra186_timer_suspend(struct device *dev) 462 + { 463 + struct tegra186_timer *tegra = dev_get_drvdata(dev); 464 + 465 + if (watchdog_active(&tegra->wdt->base)) 466 + tegra186_wdt_disable(tegra->wdt); 467 + 468 + return 0; 469 + } 470 + 471 + static int __maybe_unused tegra186_timer_resume(struct device *dev) 472 + { 473 + struct tegra186_timer *tegra = dev_get_drvdata(dev); 474 + 475 + if (watchdog_active(&tegra->wdt->base)) 476 + tegra186_wdt_enable(tegra->wdt); 477 + 478 + return 0; 479 + } 480 + 481 + static SIMPLE_DEV_PM_OPS(tegra186_timer_pm_ops, tegra186_timer_suspend, 482 + tegra186_timer_resume); 483 + 484 + static const struct tegra186_timer_soc tegra186_timer = { 485 + .num_timers = 10, 486 + .num_wdts = 3, 487 + }; 488 + 489 + static const struct tegra186_timer_soc tegra234_timer = { 490 + .num_timers = 16, 491 + .num_wdts = 3, 492 + }; 493 + 494 + static const struct of_device_id tegra186_timer_of_match[] = { 495 + { .compatible = "nvidia,tegra186-timer", .data = &tegra186_timer }, 496 + { .compatible = "nvidia,tegra234-timer", .data = &tegra234_timer }, 497 + { } 498 + }; 499 + MODULE_DEVICE_TABLE(of, tegra186_timer_of_match); 500 + 501 + static struct platform_driver tegra186_wdt_driver = { 502 + .driver = { 503 + .name = "tegra186-timer", 504 + .pm = &tegra186_timer_pm_ops, 505 + .of_match_table = tegra186_timer_of_match, 506 + }, 507 + .probe = tegra186_timer_probe, 508 + .remove = tegra186_timer_remove, 509 + }; 510 + module_platform_driver(tegra186_wdt_driver); 511 + 512 + MODULE_AUTHOR("Thierry Reding <treding@nvidia.com>"); 513 + MODULE_DESCRIPTION("NVIDIA Tegra186 timers driver"); 514 + MODULE_LICENSE("GPL v2");
+123
drivers/clocksource/timer-ti-dm.c
··· 44 44 REQUEST_BY_NODE, 45 45 }; 46 46 47 + static inline u32 __omap_dm_timer_read(struct omap_dm_timer *timer, u32 reg, 48 + int posted) 49 + { 50 + if (posted) 51 + while (readl_relaxed(timer->pend) & (reg >> WPSHIFT)) 52 + cpu_relax(); 53 + 54 + return readl_relaxed(timer->func_base + (reg & 0xff)); 55 + } 56 + 57 + static inline void __omap_dm_timer_write(struct omap_dm_timer *timer, 58 + u32 reg, u32 val, int posted) 59 + { 60 + if (posted) 61 + while (readl_relaxed(timer->pend) & (reg >> WPSHIFT)) 62 + cpu_relax(); 63 + 64 + writel_relaxed(val, timer->func_base + (reg & 0xff)); 65 + } 66 + 67 + static inline void __omap_dm_timer_init_regs(struct omap_dm_timer *timer) 68 + { 69 + u32 tidr; 70 + 71 + /* Assume v1 ip if bits [31:16] are zero */ 72 + tidr = readl_relaxed(timer->io_base); 73 + if (!(tidr >> 16)) { 74 + timer->revision = 1; 75 + timer->irq_stat = timer->io_base + OMAP_TIMER_V1_STAT_OFFSET; 76 + timer->irq_ena = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET; 77 + timer->irq_dis = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET; 78 + timer->pend = timer->io_base + _OMAP_TIMER_WRITE_PEND_OFFSET; 79 + timer->func_base = timer->io_base; 80 + } else { 81 + timer->revision = 2; 82 + timer->irq_stat = timer->io_base + OMAP_TIMER_V2_IRQSTATUS; 83 + timer->irq_ena = timer->io_base + OMAP_TIMER_V2_IRQENABLE_SET; 84 + timer->irq_dis = timer->io_base + OMAP_TIMER_V2_IRQENABLE_CLR; 85 + timer->pend = timer->io_base + 86 + _OMAP_TIMER_WRITE_PEND_OFFSET + 87 + OMAP_TIMER_V2_FUNC_OFFSET; 88 + timer->func_base = timer->io_base + OMAP_TIMER_V2_FUNC_OFFSET; 89 + } 90 + } 91 + 92 + /* 93 + * __omap_dm_timer_enable_posted - enables write posted mode 94 + * @timer: pointer to timer instance handle 95 + * 96 + * Enables the write posted mode for the timer. When posted mode is enabled 97 + * writes to certain timer registers are immediately acknowledged by the 98 + * internal bus and hence prevents stalling the CPU waiting for the write to 99 + * complete. Enabling this feature can improve performance for writing to the 100 + * timer registers. 101 + */ 102 + static inline void __omap_dm_timer_enable_posted(struct omap_dm_timer *timer) 103 + { 104 + if (timer->posted) 105 + return; 106 + 107 + if (timer->errata & OMAP_TIMER_ERRATA_I103_I767) { 108 + timer->posted = OMAP_TIMER_NONPOSTED; 109 + __omap_dm_timer_write(timer, OMAP_TIMER_IF_CTRL_REG, 0, 0); 110 + return; 111 + } 112 + 113 + __omap_dm_timer_write(timer, OMAP_TIMER_IF_CTRL_REG, 114 + OMAP_TIMER_CTRL_POSTED, 0); 115 + timer->context.tsicr = OMAP_TIMER_CTRL_POSTED; 116 + timer->posted = OMAP_TIMER_POSTED; 117 + } 118 + 119 + static inline void __omap_dm_timer_stop(struct omap_dm_timer *timer, 120 + int posted, unsigned long rate) 121 + { 122 + u32 l; 123 + 124 + l = __omap_dm_timer_read(timer, OMAP_TIMER_CTRL_REG, posted); 125 + if (l & OMAP_TIMER_CTRL_ST) { 126 + l &= ~0x1; 127 + __omap_dm_timer_write(timer, OMAP_TIMER_CTRL_REG, l, posted); 128 + #ifdef CONFIG_ARCH_OMAP2PLUS 129 + /* Readback to make sure write has completed */ 130 + __omap_dm_timer_read(timer, OMAP_TIMER_CTRL_REG, posted); 131 + /* 132 + * Wait for functional clock period x 3.5 to make sure that 133 + * timer is stopped 134 + */ 135 + udelay(3500000 / rate + 1); 136 + #endif 137 + } 138 + 139 + /* Ack possibly pending interrupt */ 140 + writel_relaxed(OMAP_TIMER_INT_OVERFLOW, timer->irq_stat); 141 + } 142 + 143 + static inline void __omap_dm_timer_int_enable(struct omap_dm_timer *timer, 144 + unsigned int value) 145 + { 146 + writel_relaxed(value, timer->irq_ena); 147 + __omap_dm_timer_write(timer, OMAP_TIMER_WAKEUP_EN_REG, value, 0); 148 + } 149 + 150 + static inline unsigned int 151 + __omap_dm_timer_read_counter(struct omap_dm_timer *timer, int posted) 152 + { 153 + return __omap_dm_timer_read(timer, OMAP_TIMER_COUNTER_REG, posted); 154 + } 155 + 156 + static inline void __omap_dm_timer_write_status(struct omap_dm_timer *timer, 157 + unsigned int value) 158 + { 159 + writel_relaxed(value, timer->irq_stat); 160 + } 161 + 47 162 /** 48 163 * omap_dm_timer_read_reg - read timer registers in posted and non-posted mode 49 164 * @timer: timer pointer over which read operation to perform ··· 1036 921 .timer_ops = &dmtimer_ops, 1037 922 }; 1038 923 924 + static const struct dmtimer_platform_data am6_pdata = { 925 + .timer_ops = &dmtimer_ops, 926 + }; 927 + 1039 928 static const struct of_device_id omap_timer_match[] = { 1040 929 { 1041 930 .compatible = "ti,omap2420-timer", ··· 1067 948 { 1068 949 .compatible = "ti,dm816-timer", 1069 950 .data = &omap3plus_pdata, 951 + }, 952 + { 953 + .compatible = "ti,am654-timer", 954 + .data = &am6_pdata, 1070 955 }, 1071 956 {}, 1072 957 };
+4
drivers/thermal/rcar_gen3_thermal.c
··· 399 399 .compatible = "renesas,r8a779a0-thermal", 400 400 .data = &rcar_gen3_ths_tj_1, 401 401 }, 402 + { 403 + .compatible = "renesas,r8a779f0-thermal", 404 + .data = &rcar_gen3_ths_tj_1, 405 + }, 402 406 {}, 403 407 }; 404 408 MODULE_DEVICE_TABLE(of, rcar_gen3_thermal_dt_ids);
-144
include/clocksource/timer-ti-dm.h
··· 247 247 #define OMAP_TIMER_TICK_INT_MASK_COUNT_REG \ 248 248 (_OMAP_TIMER_TICK_INT_MASK_COUNT_OFFSET | (WP_TOWR << WPSHIFT)) 249 249 250 - /* 251 - * The below are inlined to optimize code size for system timers. Other code 252 - * should not need these at all. 253 - */ 254 - #if defined(CONFIG_ARCH_OMAP1) || defined(CONFIG_ARCH_OMAP2PLUS) 255 - static inline u32 __omap_dm_timer_read(struct omap_dm_timer *timer, u32 reg, 256 - int posted) 257 - { 258 - if (posted) 259 - while (readl_relaxed(timer->pend) & (reg >> WPSHIFT)) 260 - cpu_relax(); 261 - 262 - return readl_relaxed(timer->func_base + (reg & 0xff)); 263 - } 264 - 265 - static inline void __omap_dm_timer_write(struct omap_dm_timer *timer, 266 - u32 reg, u32 val, int posted) 267 - { 268 - if (posted) 269 - while (readl_relaxed(timer->pend) & (reg >> WPSHIFT)) 270 - cpu_relax(); 271 - 272 - writel_relaxed(val, timer->func_base + (reg & 0xff)); 273 - } 274 - 275 - static inline void __omap_dm_timer_init_regs(struct omap_dm_timer *timer) 276 - { 277 - u32 tidr; 278 - 279 - /* Assume v1 ip if bits [31:16] are zero */ 280 - tidr = readl_relaxed(timer->io_base); 281 - if (!(tidr >> 16)) { 282 - timer->revision = 1; 283 - timer->irq_stat = timer->io_base + OMAP_TIMER_V1_STAT_OFFSET; 284 - timer->irq_ena = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET; 285 - timer->irq_dis = timer->io_base + OMAP_TIMER_V1_INT_EN_OFFSET; 286 - timer->pend = timer->io_base + _OMAP_TIMER_WRITE_PEND_OFFSET; 287 - timer->func_base = timer->io_base; 288 - } else { 289 - timer->revision = 2; 290 - timer->irq_stat = timer->io_base + OMAP_TIMER_V2_IRQSTATUS; 291 - timer->irq_ena = timer->io_base + OMAP_TIMER_V2_IRQENABLE_SET; 292 - timer->irq_dis = timer->io_base + OMAP_TIMER_V2_IRQENABLE_CLR; 293 - timer->pend = timer->io_base + 294 - _OMAP_TIMER_WRITE_PEND_OFFSET + 295 - OMAP_TIMER_V2_FUNC_OFFSET; 296 - timer->func_base = timer->io_base + OMAP_TIMER_V2_FUNC_OFFSET; 297 - } 298 - } 299 - 300 - /* 301 - * __omap_dm_timer_enable_posted - enables write posted mode 302 - * @timer: pointer to timer instance handle 303 - * 304 - * Enables the write posted mode for the timer. When posted mode is enabled 305 - * writes to certain timer registers are immediately acknowledged by the 306 - * internal bus and hence prevents stalling the CPU waiting for the write to 307 - * complete. Enabling this feature can improve performance for writing to the 308 - * timer registers. 309 - */ 310 - static inline void __omap_dm_timer_enable_posted(struct omap_dm_timer *timer) 311 - { 312 - if (timer->posted) 313 - return; 314 - 315 - if (timer->errata & OMAP_TIMER_ERRATA_I103_I767) { 316 - timer->posted = OMAP_TIMER_NONPOSTED; 317 - __omap_dm_timer_write(timer, OMAP_TIMER_IF_CTRL_REG, 0, 0); 318 - return; 319 - } 320 - 321 - __omap_dm_timer_write(timer, OMAP_TIMER_IF_CTRL_REG, 322 - OMAP_TIMER_CTRL_POSTED, 0); 323 - timer->context.tsicr = OMAP_TIMER_CTRL_POSTED; 324 - timer->posted = OMAP_TIMER_POSTED; 325 - } 326 - 327 - /** 328 - * __omap_dm_timer_override_errata - override errata flags for a timer 329 - * @timer: pointer to timer handle 330 - * @errata: errata flags to be ignored 331 - * 332 - * For a given timer, override a timer errata by clearing the flags 333 - * specified by the errata argument. A specific erratum should only be 334 - * overridden for a timer if the timer is used in such a way the erratum 335 - * has no impact. 336 - */ 337 - static inline void __omap_dm_timer_override_errata(struct omap_dm_timer *timer, 338 - u32 errata) 339 - { 340 - timer->errata &= ~errata; 341 - } 342 - 343 - static inline void __omap_dm_timer_stop(struct omap_dm_timer *timer, 344 - int posted, unsigned long rate) 345 - { 346 - u32 l; 347 - 348 - l = __omap_dm_timer_read(timer, OMAP_TIMER_CTRL_REG, posted); 349 - if (l & OMAP_TIMER_CTRL_ST) { 350 - l &= ~0x1; 351 - __omap_dm_timer_write(timer, OMAP_TIMER_CTRL_REG, l, posted); 352 - #ifdef CONFIG_ARCH_OMAP2PLUS 353 - /* Readback to make sure write has completed */ 354 - __omap_dm_timer_read(timer, OMAP_TIMER_CTRL_REG, posted); 355 - /* 356 - * Wait for functional clock period x 3.5 to make sure that 357 - * timer is stopped 358 - */ 359 - udelay(3500000 / rate + 1); 360 - #endif 361 - } 362 - 363 - /* Ack possibly pending interrupt */ 364 - writel_relaxed(OMAP_TIMER_INT_OVERFLOW, timer->irq_stat); 365 - } 366 - 367 - static inline void __omap_dm_timer_load_start(struct omap_dm_timer *timer, 368 - u32 ctrl, unsigned int load, 369 - int posted) 370 - { 371 - __omap_dm_timer_write(timer, OMAP_TIMER_COUNTER_REG, load, posted); 372 - __omap_dm_timer_write(timer, OMAP_TIMER_CTRL_REG, ctrl, posted); 373 - } 374 - 375 - static inline void __omap_dm_timer_int_enable(struct omap_dm_timer *timer, 376 - unsigned int value) 377 - { 378 - writel_relaxed(value, timer->irq_ena); 379 - __omap_dm_timer_write(timer, OMAP_TIMER_WAKEUP_EN_REG, value, 0); 380 - } 381 - 382 - static inline unsigned int 383 - __omap_dm_timer_read_counter(struct omap_dm_timer *timer, int posted) 384 - { 385 - return __omap_dm_timer_read(timer, OMAP_TIMER_COUNTER_REG, posted); 386 - } 387 - 388 - static inline void __omap_dm_timer_write_status(struct omap_dm_timer *timer, 389 - unsigned int value) 390 - { 391 - writel_relaxed(value, timer->irq_stat); 392 - } 393 - #endif /* CONFIG_ARCH_OMAP1 || CONFIG_ARCH_OMAP2PLUS */ 394 250 #endif /* __CLOCKSOURCE_DMTIMER_H */
+5 -4
include/linux/wait.h
··· 544 544 \ 545 545 hrtimer_init_sleeper_on_stack(&__t, CLOCK_MONOTONIC, \ 546 546 HRTIMER_MODE_REL); \ 547 - if ((timeout) != KTIME_MAX) \ 548 - hrtimer_start_range_ns(&__t.timer, timeout, \ 549 - current->timer_slack_ns, \ 550 - HRTIMER_MODE_REL); \ 547 + if ((timeout) != KTIME_MAX) { \ 548 + hrtimer_set_expires_range_ns(&__t.timer, timeout, \ 549 + current->timer_slack_ns); \ 550 + hrtimer_sleeper_start_expires(&__t, HRTIMER_MODE_REL); \ 551 + } \ 551 552 \ 552 553 __ret = ___wait_event(wq_head, condition, state, 0, 0, \ 553 554 if (!__t.task) { \