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

Merge branch 'timers-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip

Pull clocksource updates from Ingo Molnar:
"Misc clocksource/clockevent driver updates that came in a bit late but
are ready for v5.2"

* 'timers-urgent-for-linus' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip:
misc: atmel_tclib: Do not probe already used TCBs
clocksource/drivers/timer-atmel-tcb: Convert tc_clksrc_suspend|resume() to static
clocksource/drivers/tcb_clksrc: Rename the file for consistency
clocksource/drivers/timer-atmel-pit: Rework Kconfig option
clocksource/drivers/tcb_clksrc: Move Kconfig option
ARM: at91: Implement clocksource selection
clocksource/drivers/tcb_clksrc: Use tcb as sched_clock
clocksource/drivers/tcb_clksrc: Stop depending on atmel_tclib
ARM: at91: move SoC specific definitions to SoC folder
clocksource/drivers/timer-milbeaut: Cleanup common register accesses
clocksource/drivers/timer-milbeaut: Add shutdown function
clocksource/drivers/timer-milbeaut: Fix to enable one-shot timer
clocksource/drivers/tegra: Rework for compensation of suspend time
clocksource/drivers/sp804: Add COMPILE_TEST to CONFIG_ARM_TIMER_SP804
clocksource/drivers/sun4i: Add a compatible for suniv
dt-bindings: timer: Add Allwinner suniv timer

+205 -139
+3 -1
Documentation/devicetree/bindings/timer/allwinner,sun4i-timer.txt
··· 2 2 3 3 Required properties: 4 4 5 - - compatible : should be "allwinner,sun4i-a10-timer" 5 + - compatible : should be one of the following: 6 + "allwinner,sun4i-a10-timer" 7 + "allwinner,suniv-f1c100s-timer" 6 8 - reg : Specifies base physical address and size of the registers. 7 9 - interrupts : The interrupt of the first timer 8 10 - clocks: phandle to the source clock (usually a 24 MHz fixed clock)
+23
arch/arm/mach-at91/Kconfig
··· 104 104 AT91SAM9X35 105 105 AT91SAM9XE 106 106 107 + comment "Clocksource driver selection" 108 + 109 + config ATMEL_CLOCKSOURCE_PIT 110 + bool "Periodic Interval Timer (PIT) support" 111 + depends on SOC_AT91SAM9 || SOC_SAMA5 112 + default SOC_AT91SAM9 || SOC_SAMA5 113 + select ATMEL_PIT 114 + help 115 + Select this to get a clocksource based on the Atmel Periodic Interval 116 + Timer. It has a relatively low resolution and the TC Block clocksource 117 + should be preferred. 118 + 119 + config ATMEL_CLOCKSOURCE_TCB 120 + bool "Timer Counter Blocks (TCB) support" 121 + default SOC_AT91RM9200 || SOC_AT91SAM9 || SOC_SAMA5 122 + select ATMEL_TCB_CLKSRC 123 + help 124 + Select this to get a high precision clocksource based on a 125 + TC block with a 5+ MHz base clock rate. 126 + On platforms with 16-bit counters, two timer channels are combined 127 + to make a single 32-bit timer. 128 + It can also be used as a clock event device supporting oneshot mode. 129 + 107 130 config HAVE_AT91_UTMI 108 131 bool 109 132
+12 -2
drivers/clocksource/Kconfig
··· 387 387 This options enables support for the ARM global timer unit 388 388 389 389 config ARM_TIMER_SP804 390 - bool "Support for Dual Timer SP804 module" 390 + bool "Support for Dual Timer SP804 module" if COMPILE_TEST 391 391 depends on GENERIC_SCHED_CLOCK && CLKDEV_LOOKUP 392 392 select CLKSRC_MMIO 393 393 select TIMER_OF if OF ··· 407 407 This options enables support for the ARMv7M system timer unit 408 408 409 409 config ATMEL_PIT 410 + bool "Atmel PIT support" if COMPILE_TEST 411 + depends on HAS_IOMEM 410 412 select TIMER_OF if OF 411 - def_bool SOC_AT91SAM9 || SOC_SAMA5 413 + help 414 + Support for the Periodic Interval Timer found on Atmel SoCs. 412 415 413 416 config ATMEL_ST 414 417 bool "Atmel ST timer support" if COMPILE_TEST ··· 420 417 select MFD_SYSCON 421 418 help 422 419 Support for the Atmel ST timer. 420 + 421 + config ATMEL_TCB_CLKSRC 422 + bool "Atmel TC Block timer driver" if COMPILE_TEST 423 + depends on HAS_IOMEM 424 + select TIMER_OF if OF 425 + help 426 + Support for Timer Counter Blocks on Atmel SoCs. 423 427 424 428 config CLKSRC_EXYNOS_MCT 425 429 bool "Exynos multi core timer driver" if COMPILE_TEST
+1 -1
drivers/clocksource/Makefile
··· 3 3 obj-$(CONFIG_TIMER_PROBE) += timer-probe.o 4 4 obj-$(CONFIG_ATMEL_PIT) += timer-atmel-pit.o 5 5 obj-$(CONFIG_ATMEL_ST) += timer-atmel-st.o 6 - obj-$(CONFIG_ATMEL_TCB_CLKSRC) += tcb_clksrc.o 6 + obj-$(CONFIG_ATMEL_TCB_CLKSRC) += timer-atmel-tcb.o 7 7 obj-$(CONFIG_X86_PM_TIMER) += acpi_pm.o 8 8 obj-$(CONFIG_SCx200HR_TIMER) += scx200_hrt.o 9 9 obj-$(CONFIG_CS5535_CLOCK_EVENT_SRC) += timer-cs5535.o
+86 -42
drivers/clocksource/tcb_clksrc.c drivers/clocksource/timer-atmel-tcb.c
··· 9 9 #include <linux/err.h> 10 10 #include <linux/ioport.h> 11 11 #include <linux/io.h> 12 - #include <linux/platform_device.h> 12 + #include <linux/of_address.h> 13 + #include <linux/of_irq.h> 14 + #include <linux/sched_clock.h> 13 15 #include <linux/syscore_ops.h> 14 - #include <linux/atmel_tc.h> 16 + #include <soc/at91/atmel_tcb.h> 15 17 16 18 17 19 /* ··· 29 27 * - The third channel may be used to provide a 16-bit clockevent 30 28 * source, used in either periodic or oneshot mode. This runs 31 29 * at 32 KiHZ, and can handle delays of up to two seconds. 32 - * 33 - * A boot clocksource and clockevent source are also currently needed, 34 - * unless the relevant platforms (ARM/AT91, AVR32/AT32) are changed so 35 - * this code can be used when init_timers() is called, well before most 36 - * devices are set up. (Some low end AT91 parts, which can run uClinux, 37 - * have only the timers in one TC block... they currently don't support 38 - * the tclib code, because of that initialization issue.) 39 30 * 40 31 * REVISIT behavior during system suspend states... we should disable 41 32 * all clocks and save the power. Easily done for clockevent devices, ··· 107 112 } 108 113 109 114 static struct clocksource clksrc = { 110 - .name = "tcb_clksrc", 111 115 .rating = 200, 112 116 .read = tc_get_cycles, 113 117 .mask = CLOCKSOURCE_MASK(32), ··· 114 120 .suspend = tc_clksrc_suspend, 115 121 .resume = tc_clksrc_resume, 116 122 }; 123 + 124 + static u64 notrace tc_sched_clock_read(void) 125 + { 126 + return tc_get_cycles(&clksrc); 127 + } 128 + 129 + static u64 notrace tc_sched_clock_read32(void) 130 + { 131 + return tc_get_cycles32(&clksrc); 132 + } 117 133 118 134 #ifdef CONFIG_GENERIC_CLOCKEVENTS 119 135 ··· 218 214 219 215 static struct tc_clkevt_device clkevt = { 220 216 .clkevt = { 221 - .name = "tc_clkevt", 222 217 .features = CLOCK_EVT_FEAT_PERIODIC | 223 218 CLOCK_EVT_FEAT_ONESHOT, 224 219 /* Should be lower than at91rm9200's system timer */ ··· 333 330 writel(ATMEL_TC_SYNC, tcaddr + ATMEL_TC_BCR); 334 331 } 335 332 336 - static int __init tcb_clksrc_init(void) 337 - { 338 - static char bootinfo[] __initdata 339 - = KERN_DEBUG "%s: tc%d at %d.%03d MHz\n"; 333 + static const u8 atmel_tcb_divisors[5] = { 2, 8, 32, 128, 0, }; 340 334 341 - struct platform_device *pdev; 342 - struct atmel_tc *tc; 335 + static const struct of_device_id atmel_tcb_of_match[] = { 336 + { .compatible = "atmel,at91rm9200-tcb", .data = (void *)16, }, 337 + { .compatible = "atmel,at91sam9x5-tcb", .data = (void *)32, }, 338 + { /* sentinel */ } 339 + }; 340 + 341 + static int __init tcb_clksrc_init(struct device_node *node) 342 + { 343 + struct atmel_tc tc; 343 344 struct clk *t0_clk; 345 + const struct of_device_id *match; 346 + u64 (*tc_sched_clock)(void); 344 347 u32 rate, divided_rate = 0; 345 348 int best_divisor_idx = -1; 346 349 int clk32k_divisor_idx = -1; 350 + int bits; 347 351 int i; 348 352 int ret; 349 353 350 - tc = atmel_tc_alloc(CONFIG_ATMEL_TCB_CLKSRC_BLOCK); 351 - if (!tc) { 352 - pr_debug("can't alloc TC for clocksource\n"); 353 - return -ENODEV; 354 - } 355 - tcaddr = tc->regs; 356 - pdev = tc->pdev; 354 + /* Protect against multiple calls */ 355 + if (tcaddr) 356 + return 0; 357 357 358 - t0_clk = tc->clk[0]; 358 + tc.regs = of_iomap(node->parent, 0); 359 + if (!tc.regs) 360 + return -ENXIO; 361 + 362 + t0_clk = of_clk_get_by_name(node->parent, "t0_clk"); 363 + if (IS_ERR(t0_clk)) 364 + return PTR_ERR(t0_clk); 365 + 366 + tc.slow_clk = of_clk_get_by_name(node->parent, "slow_clk"); 367 + if (IS_ERR(tc.slow_clk)) 368 + return PTR_ERR(tc.slow_clk); 369 + 370 + tc.clk[0] = t0_clk; 371 + tc.clk[1] = of_clk_get_by_name(node->parent, "t1_clk"); 372 + if (IS_ERR(tc.clk[1])) 373 + tc.clk[1] = t0_clk; 374 + tc.clk[2] = of_clk_get_by_name(node->parent, "t2_clk"); 375 + if (IS_ERR(tc.clk[2])) 376 + tc.clk[2] = t0_clk; 377 + 378 + tc.irq[2] = of_irq_get(node->parent, 2); 379 + if (tc.irq[2] <= 0) { 380 + tc.irq[2] = of_irq_get(node->parent, 0); 381 + if (tc.irq[2] <= 0) 382 + return -EINVAL; 383 + } 384 + 385 + match = of_match_node(atmel_tcb_of_match, node->parent); 386 + bits = (uintptr_t)match->data; 387 + 388 + for (i = 0; i < ARRAY_SIZE(tc.irq); i++) 389 + writel(ATMEL_TC_ALL_IRQ, tc.regs + ATMEL_TC_REG(i, IDR)); 390 + 359 391 ret = clk_prepare_enable(t0_clk); 360 392 if (ret) { 361 393 pr_debug("can't enable T0 clk\n"); 362 - goto err_free_tc; 394 + return ret; 363 395 } 364 396 365 397 /* How fast will we be counting? Pick something over 5 MHz. */ 366 398 rate = (u32) clk_get_rate(t0_clk); 367 - for (i = 0; i < 5; i++) { 368 - unsigned divisor = atmel_tc_divisors[i]; 399 + for (i = 0; i < ARRAY_SIZE(atmel_tcb_divisors); i++) { 400 + unsigned divisor = atmel_tcb_divisors[i]; 369 401 unsigned tmp; 370 402 371 403 /* remember 32 KiHz clock for later */ ··· 419 381 best_divisor_idx = i; 420 382 } 421 383 422 - 423 - printk(bootinfo, clksrc.name, CONFIG_ATMEL_TCB_CLKSRC_BLOCK, 424 - divided_rate / 1000000, 384 + clksrc.name = kbasename(node->parent->full_name); 385 + clkevt.clkevt.name = kbasename(node->parent->full_name); 386 + pr_debug("%s at %d.%03d MHz\n", clksrc.name, divided_rate / 1000000, 425 387 ((divided_rate % 1000000) + 500) / 1000); 426 388 427 - if (tc->tcb_config && tc->tcb_config->counter_width == 32) { 389 + tcaddr = tc.regs; 390 + 391 + if (bits == 32) { 428 392 /* use apropriate function to read 32 bit counter */ 429 393 clksrc.read = tc_get_cycles32; 430 394 /* setup ony channel 0 */ 431 - tcb_setup_single_chan(tc, best_divisor_idx); 395 + tcb_setup_single_chan(&tc, best_divisor_idx); 396 + tc_sched_clock = tc_sched_clock_read32; 432 397 } else { 433 - /* tclib will give us three clocks no matter what the 398 + /* we have three clocks no matter what the 434 399 * underlying platform supports. 435 400 */ 436 - ret = clk_prepare_enable(tc->clk[1]); 401 + ret = clk_prepare_enable(tc.clk[1]); 437 402 if (ret) { 438 403 pr_debug("can't enable T1 clk\n"); 439 404 goto err_disable_t0; 440 405 } 441 406 /* setup both channel 0 & 1 */ 442 - tcb_setup_dual_chan(tc, best_divisor_idx); 407 + tcb_setup_dual_chan(&tc, best_divisor_idx); 408 + tc_sched_clock = tc_sched_clock_read; 443 409 } 444 410 445 411 /* and away we go! */ ··· 452 410 goto err_disable_t1; 453 411 454 412 /* channel 2: periodic and oneshot timer support */ 455 - ret = setup_clkevents(tc, clk32k_divisor_idx); 413 + ret = setup_clkevents(&tc, clk32k_divisor_idx); 456 414 if (ret) 457 415 goto err_unregister_clksrc; 416 + 417 + sched_clock_register(tc_sched_clock, 32, divided_rate); 458 418 459 419 return 0; 460 420 ··· 464 420 clocksource_unregister(&clksrc); 465 421 466 422 err_disable_t1: 467 - if (!tc->tcb_config || tc->tcb_config->counter_width != 32) 468 - clk_disable_unprepare(tc->clk[1]); 423 + if (bits != 32) 424 + clk_disable_unprepare(tc.clk[1]); 469 425 470 426 err_disable_t0: 471 427 clk_disable_unprepare(t0_clk); 472 428 473 - err_free_tc: 474 - atmel_tc_free(tc); 429 + tcaddr = NULL; 430 + 475 431 return ret; 476 432 } 477 - arch_initcall(tcb_clksrc_init); 433 + TIMER_OF_DECLARE(atmel_tcb_clksrc, "atmel,tcb-timer", tcb_clksrc_init);
+49 -21
drivers/clocksource/timer-milbeaut.c
··· 26 26 #define MLB_TMR_TMCSR_CSL_DIV2 0 27 27 #define MLB_TMR_DIV_CNT 2 28 28 29 - #define MLB_TMR_SRC_CH (1) 30 - #define MLB_TMR_EVT_CH (0) 29 + #define MLB_TMR_SRC_CH 1 30 + #define MLB_TMR_EVT_CH 0 31 31 32 32 #define MLB_TMR_SRC_CH_OFS (MLB_TMR_REGSZPCH * MLB_TMR_SRC_CH) 33 33 #define MLB_TMR_EVT_CH_OFS (MLB_TMR_REGSZPCH * MLB_TMR_EVT_CH) ··· 43 43 #define MLB_TMR_EVT_TMRLR2_OFS (MLB_TMR_EVT_CH_OFS + MLB_TMR_TMRLR2_OFS) 44 44 45 45 #define MLB_TIMER_RATING 500 46 + #define MLB_TIMER_ONESHOT 0 47 + #define MLB_TIMER_PERIODIC 1 46 48 47 49 static irqreturn_t mlb_timer_interrupt(int irq, void *dev_id) 48 50 { ··· 61 59 return IRQ_HANDLED; 62 60 } 63 61 62 + static void mlb_evt_timer_start(struct timer_of *to, bool periodic) 63 + { 64 + u32 val = MLB_TMR_TMCSR_CSL_DIV2; 65 + 66 + val |= MLB_TMR_TMCSR_CNTE | MLB_TMR_TMCSR_TRG | MLB_TMR_TMCSR_INTE; 67 + if (periodic) 68 + val |= MLB_TMR_TMCSR_RELD; 69 + writel_relaxed(val, timer_of_base(to) + MLB_TMR_EVT_TMCSR_OFS); 70 + } 71 + 72 + static void mlb_evt_timer_stop(struct timer_of *to) 73 + { 74 + u32 val = readl_relaxed(timer_of_base(to) + MLB_TMR_EVT_TMCSR_OFS); 75 + 76 + val &= ~MLB_TMR_TMCSR_CNTE; 77 + writel_relaxed(val, timer_of_base(to) + MLB_TMR_EVT_TMCSR_OFS); 78 + } 79 + 80 + static void mlb_evt_timer_register_count(struct timer_of *to, unsigned long cnt) 81 + { 82 + writel_relaxed(cnt, timer_of_base(to) + MLB_TMR_EVT_TMRLR1_OFS); 83 + } 84 + 64 85 static int mlb_set_state_periodic(struct clock_event_device *clk) 65 86 { 66 87 struct timer_of *to = to_timer_of(clk); 67 - u32 val = MLB_TMR_TMCSR_CSL_DIV2; 68 88 69 - writel_relaxed(val, timer_of_base(to) + MLB_TMR_EVT_TMCSR_OFS); 70 - 71 - writel_relaxed(to->of_clk.period, timer_of_base(to) + 72 - MLB_TMR_EVT_TMRLR1_OFS); 73 - val |= MLB_TMR_TMCSR_RELD | MLB_TMR_TMCSR_CNTE | 74 - MLB_TMR_TMCSR_TRG | MLB_TMR_TMCSR_INTE; 75 - writel_relaxed(val, timer_of_base(to) + MLB_TMR_EVT_TMCSR_OFS); 89 + mlb_evt_timer_stop(to); 90 + mlb_evt_timer_register_count(to, to->of_clk.period); 91 + mlb_evt_timer_start(to, MLB_TIMER_PERIODIC); 76 92 return 0; 77 93 } 78 94 79 95 static int mlb_set_state_oneshot(struct clock_event_device *clk) 80 96 { 81 97 struct timer_of *to = to_timer_of(clk); 82 - u32 val = MLB_TMR_TMCSR_CSL_DIV2; 83 98 84 - writel_relaxed(val, timer_of_base(to) + MLB_TMR_EVT_TMCSR_OFS); 99 + mlb_evt_timer_stop(to); 100 + mlb_evt_timer_start(to, MLB_TIMER_ONESHOT); 101 + return 0; 102 + } 103 + 104 + static int mlb_set_state_shutdown(struct clock_event_device *clk) 105 + { 106 + struct timer_of *to = to_timer_of(clk); 107 + 108 + mlb_evt_timer_stop(to); 85 109 return 0; 86 110 } 87 111 ··· 116 88 { 117 89 struct timer_of *to = to_timer_of(clk); 118 90 119 - writel_relaxed(event, timer_of_base(to) + MLB_TMR_EVT_TMRLR1_OFS); 120 - writel_relaxed(MLB_TMR_TMCSR_CSL_DIV2 | 121 - MLB_TMR_TMCSR_CNTE | MLB_TMR_TMCSR_INTE | 122 - MLB_TMR_TMCSR_TRG, timer_of_base(to) + 123 - MLB_TMR_EVT_TMCSR_OFS); 91 + mlb_evt_timer_stop(to); 92 + mlb_evt_timer_register_count(to, event); 93 + mlb_evt_timer_start(to, MLB_TIMER_ONESHOT); 124 94 return 0; 125 95 } 126 96 127 97 static int mlb_config_clock_source(struct timer_of *to) 128 98 { 129 - writel_relaxed(0, timer_of_base(to) + MLB_TMR_SRC_TMCSR_OFS); 130 - writel_relaxed(~0, timer_of_base(to) + MLB_TMR_SRC_TMR_OFS); 99 + u32 val = MLB_TMR_TMCSR_CSL_DIV2; 100 + 101 + writel_relaxed(val, timer_of_base(to) + MLB_TMR_SRC_TMCSR_OFS); 131 102 writel_relaxed(~0, timer_of_base(to) + MLB_TMR_SRC_TMRLR1_OFS); 132 103 writel_relaxed(~0, timer_of_base(to) + MLB_TMR_SRC_TMRLR2_OFS); 133 - writel_relaxed(BIT(4) | BIT(1) | BIT(0), timer_of_base(to) + 134 - MLB_TMR_SRC_TMCSR_OFS); 104 + val |= MLB_TMR_TMCSR_RELD | MLB_TMR_TMCSR_CNTE | MLB_TMR_TMCSR_TRG; 105 + writel_relaxed(val, timer_of_base(to) + MLB_TMR_SRC_TMCSR_OFS); 135 106 return 0; 136 107 } 137 108 ··· 150 123 .features = CLOCK_EVT_FEAT_DYNIRQ | CLOCK_EVT_FEAT_ONESHOT, 151 124 .set_state_oneshot = mlb_set_state_oneshot, 152 125 .set_state_periodic = mlb_set_state_periodic, 126 + .set_state_shutdown = mlb_set_state_shutdown, 153 127 .set_next_event = mlb_clkevt_next_event, 154 128 }, 155 129
+4 -1
drivers/clocksource/timer-sun4i.c
··· 186 186 */ 187 187 if (of_machine_is_compatible("allwinner,sun4i-a10") || 188 188 of_machine_is_compatible("allwinner,sun5i-a13") || 189 - of_machine_is_compatible("allwinner,sun5i-a10s")) 189 + of_machine_is_compatible("allwinner,sun5i-a10s") || 190 + of_machine_is_compatible("allwinner,suniv-f1c100s")) 190 191 sched_clock_register(sun4i_timer_sched_read, 32, 191 192 timer_of_rate(&to)); 192 193 ··· 218 217 return ret; 219 218 } 220 219 TIMER_OF_DECLARE(sun4i, "allwinner,sun4i-a10-timer", 220 + sun4i_timer_init); 221 + TIMER_OF_DECLARE(suniv, "allwinner,suniv-f1c100s-timer", 221 222 sun4i_timer_init);
+20 -43
drivers/clocksource/timer-tegra20.c
··· 60 60 static u32 usec_config; 61 61 static void __iomem *timer_reg_base; 62 62 #ifdef CONFIG_ARM 63 - static void __iomem *rtc_base; 64 - static struct timespec64 persistent_ts; 65 - static u64 persistent_ms, last_persistent_ms; 66 63 static struct delay_timer tegra_delay_timer; 67 64 #endif 68 65 ··· 196 199 return readl(timer_reg_base + TIMERUS_CNTR_1US); 197 200 } 198 201 202 + static struct timer_of suspend_rtc_to = { 203 + .flags = TIMER_OF_BASE | TIMER_OF_CLOCK, 204 + }; 205 + 199 206 /* 200 207 * tegra_rtc_read - Reads the Tegra RTC registers 201 208 * Care must be taken that this funciton is not called while the 202 209 * tegra_rtc driver could be executing to avoid race conditions 203 210 * on the RTC shadow register 204 211 */ 205 - static u64 tegra_rtc_read_ms(void) 212 + static u64 tegra_rtc_read_ms(struct clocksource *cs) 206 213 { 207 - u32 ms = readl(rtc_base + RTC_MILLISECONDS); 208 - u32 s = readl(rtc_base + RTC_SHADOW_SECONDS); 214 + u32 ms = readl(timer_of_base(&suspend_rtc_to) + RTC_MILLISECONDS); 215 + u32 s = readl(timer_of_base(&suspend_rtc_to) + RTC_SHADOW_SECONDS); 209 216 return (u64)s * MSEC_PER_SEC + ms; 210 217 } 211 218 212 - /* 213 - * tegra_read_persistent_clock64 - Return time from a persistent clock. 214 - * 215 - * Reads the time from a source which isn't disabled during PM, the 216 - * 32k sync timer. Convert the cycles elapsed since last read into 217 - * nsecs and adds to a monotonically increasing timespec64. 218 - * Care must be taken that this funciton is not called while the 219 - * tegra_rtc driver could be executing to avoid race conditions 220 - * on the RTC shadow register 221 - */ 222 - static void tegra_read_persistent_clock64(struct timespec64 *ts) 223 - { 224 - u64 delta; 225 - 226 - last_persistent_ms = persistent_ms; 227 - persistent_ms = tegra_rtc_read_ms(); 228 - delta = persistent_ms - last_persistent_ms; 229 - 230 - timespec64_add_ns(&persistent_ts, delta * NSEC_PER_MSEC); 231 - *ts = persistent_ts; 232 - } 219 + static struct clocksource suspend_rtc_clocksource = { 220 + .name = "tegra_suspend_timer", 221 + .rating = 200, 222 + .read = tegra_rtc_read_ms, 223 + .mask = CLOCKSOURCE_MASK(32), 224 + .flags = CLOCK_SOURCE_IS_CONTINUOUS | CLOCK_SOURCE_SUSPEND_NONSTOP, 225 + }; 233 226 #endif 234 227 235 228 static int tegra_timer_common_init(struct device_node *np, struct timer_of *to) ··· 372 385 373 386 static int __init tegra20_init_rtc(struct device_node *np) 374 387 { 375 - struct clk *clk; 388 + int ret; 376 389 377 - rtc_base = of_iomap(np, 0); 378 - if (!rtc_base) { 379 - pr_err("Can't map RTC registers\n"); 380 - return -ENXIO; 381 - } 390 + ret = timer_of_init(np, &suspend_rtc_to); 391 + if (ret) 392 + return ret; 382 393 383 - /* 384 - * rtc registers are used by read_persistent_clock, keep the rtc clock 385 - * enabled 386 - */ 387 - clk = of_clk_get(np, 0); 388 - if (IS_ERR(clk)) 389 - pr_warn("Unable to get rtc-tegra clock\n"); 390 - else 391 - clk_prepare_enable(clk); 394 + clocksource_register_hz(&suspend_rtc_clocksource, 1000); 392 395 393 - return register_persistent_clock(tegra_read_persistent_clock64); 396 + return 0; 394 397 } 395 398 TIMER_OF_DECLARE(tegra20_rtc, "nvidia,tegra20-rtc", tegra20_init_rtc); 396 399 #endif
-24
drivers/misc/Kconfig
··· 59 59 blocks found on many Atmel processors. This facilitates using 60 60 these blocks by different drivers despite processor differences. 61 61 62 - config ATMEL_TCB_CLKSRC 63 - bool "TC Block Clocksource" 64 - depends on ATMEL_TCLIB 65 - default y 66 - help 67 - Select this to get a high precision clocksource based on a 68 - TC block with a 5+ MHz base clock rate. Two timer channels 69 - are combined to make a single 32-bit timer. 70 - 71 - When GENERIC_CLOCKEVENTS is defined, the third timer channel 72 - may be used as a clock event device supporting oneshot mode 73 - (delays of up to two seconds) based on the 32 KiHz clock. 74 - 75 - config ATMEL_TCB_CLKSRC_BLOCK 76 - int 77 - depends on ATMEL_TCB_CLKSRC 78 - default 0 79 - range 0 1 80 - help 81 - Some chips provide more than one TC block, so you have the 82 - choice of which one to use for the clock framework. The other 83 - TC can be used for other purposes, such as PWM generation and 84 - interval timing. 85 - 86 62 config DUMMY_IRQ 87 63 tristate "Dummy IRQ handler" 88 64 default n
+4 -1
drivers/misc/atmel_tclib.c
··· 1 - #include <linux/atmel_tc.h> 2 1 #include <linux/clk.h> 3 2 #include <linux/err.h> 4 3 #include <linux/init.h> ··· 9 10 #include <linux/slab.h> 10 11 #include <linux/export.h> 11 12 #include <linux/of.h> 13 + #include <soc/at91/atmel_tcb.h> 12 14 13 15 /* 14 16 * This is a thin library to solve the problem of how to portably allocate ··· 110 110 int irq; 111 111 struct resource *r; 112 112 unsigned int i; 113 + 114 + if (of_get_child_count(pdev->dev.of_node)) 115 + return -EBUSY; 113 116 114 117 irq = platform_get_irq(pdev, 0); 115 118 if (irq < 0)
+1 -1
drivers/pwm/pwm-atmel-tcb.c
··· 17 17 #include <linux/ioport.h> 18 18 #include <linux/io.h> 19 19 #include <linux/platform_device.h> 20 - #include <linux/atmel_tc.h> 21 20 #include <linux/pwm.h> 22 21 #include <linux/of_device.h> 23 22 #include <linux/slab.h> 23 + #include <soc/at91/atmel_tcb.h> 24 24 25 25 #define NPWM 6 26 26
+2 -2
include/linux/atmel_tc.h include/soc/at91/atmel_tcb.h
··· 7 7 * (at your option) any later version. 8 8 */ 9 9 10 - #ifndef ATMEL_TC_H 11 - #define ATMEL_TC_H 10 + #ifndef __SOC_ATMEL_TCB_H 11 + #define __SOC_ATMEL_TCB_H 12 12 13 13 #include <linux/compiler.h> 14 14 #include <linux/list.h>