Skip to content

Commit

Permalink
Merge tag 'timers-core-2022-10-05' of git://git.kernel.org/pub/scm/li…
Browse files Browse the repository at this point in the history
…nux/kernel/git/tip/tip

Pull timer updates from Thomas Gleixner:
 "A boring time, timekeeping, timers update:

   - No core code changes

   - No new clocksource/event driver

   - Cleanup of the TI DM clocksource/event driver

   - The usual set of device tree binding updates

   - Small improvement, fixes and cleanups all over the place"

* tag 'timers-core-2022-10-05' of git://git.kernel.org/pub/scm/linux/kernel/git/tip/tip: (22 commits)
  clocksource/drivers/arm_arch_timer: Fix CNTPCT_LO and CNTVCT_LO value
  clocksource/drivers/imx-sysctr: handle nxp,no-divider property
  dt-bindings: timer: nxp,sysctr-timer: add nxp,no-divider property
  clocksource/drivers/timer-ti-dm: Get clock in probe with devm_clk_get()
  clocksource/drivers/timer-ti-dm: Add flag to detect omap1
  clocksource/drivers/timer-ti-dm: Move struct omap_dm_timer fields to driver
  clocksource/drivers/timer-ti-dm: Use runtime PM directly and check errors
  clocksource/drivers/timer-ti-dm: Move private defines to the driver
  clocksource/drivers/timer-ti-dm: Simplify register access further
  clocksource/drivers/timer-ti-dm: Simplify register writes with dmtimer_write()
  clocksource/drivers/timer-ti-dm: Simplify register reads with dmtimer_read()
  clocksource/drivers/timer-ti-dm: Drop unused functions
  clocksource/drivers/timer-gxp: Add missing error handling in gxp_timer_probe
  clocksource/drivers/arm_arch_timer: Fix handling of ARM erratum 858921
  clocksource/drivers/exynos_mct: Enable building on ARTPEC
  clocksource/drivers/exynos_mct: Support local-timers property
  clocksource/drivers/exynos_mct: Support frc-shared property
  dt-bindings: timer: exynos4210-mct: Add ARTPEC-8 MCT support
  clocksource/drivers/sun4i: Add definition of clear interrupt
  clocksource/drivers/renesas-ostm: Add support for RZ/V2L SoC
  ...
  • Loading branch information
torvalds committed Oct 10, 2022
2 parents 7f6dcff + 6cb5ce1 commit 55be608
Show file tree
Hide file tree
Showing 13 changed files with 553 additions and 381 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ Required properties:
For those SoCs that use SYST
* "mediatek,mt8183-timer" for MT8183 compatible timers (SYST)
* "mediatek,mt8186-timer" for MT8186 compatible timers (SYST)
* "mediatek,mt8188-timer" for MT8188 compatible timers (SYST)
* "mediatek,mt8192-timer" for MT8192 compatible timers (SYST)
* "mediatek,mt8195-timer" for MT8195 compatible timers (SYST)
* "mediatek,mt7629-timer" for MT7629 compatible timers (SYST)
Expand Down
4 changes: 4 additions & 0 deletions Documentation/devicetree/bindings/timer/nxp,sysctr-timer.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,10 @@ properties:
clock-names:
const: per

nxp,no-divider:
description: if present, means there is no internal base clk divider.
type: boolean

required:
- compatible
- reg
Expand Down
1 change: 1 addition & 0 deletions Documentation/devicetree/bindings/timer/renesas,tmu.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,7 @@ properties:
- renesas,tmu-r8a77990 # R-Car E3
- renesas,tmu-r8a77995 # R-Car D3
- renesas,tmu-r8a779a0 # R-Car V3U
- renesas,tmu-r8a779f0 # R-Car S4-8
- const: renesas,tmu

reg:
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -25,6 +25,7 @@ properties:
- samsung,exynos4412-mct
- items:
- enum:
- axis,artpec8-mct
- samsung,exynos3250-mct
- samsung,exynos5250-mct
- samsung,exynos5260-mct
Expand All @@ -45,6 +46,19 @@ properties:
reg:
maxItems: 1

samsung,frc-shared:
type: boolean
description: |
Indicates that the hardware requires that this processor share the
free-running counter with a different (main) processor.
samsung,local-timers:
$ref: /schemas/types.yaml#/definitions/uint32-array
minItems: 1
maxItems: 16
description: |
List of indices of local timers usable from this processor.
interrupts:
description: |
Interrupts should be put in specific order. This is, the local timer
Expand Down Expand Up @@ -74,6 +88,17 @@ required:
- reg

allOf:
- if:
not:
properties:
compatible:
contains:
enum:
- axis,artpec8-mct
then:
properties:
samsung,local-timers: false
samsung,frc-shared: false
- if:
properties:
compatible:
Expand Down Expand Up @@ -101,6 +126,7 @@ allOf:
compatible:
contains:
enum:
- axis,artpec8-mct
- samsung,exynos5260-mct
- samsung,exynos5420-mct
- samsung,exynos5433-mct
Expand Down
2 changes: 1 addition & 1 deletion drivers/clocksource/Kconfig
Original file line number Diff line number Diff line change
Expand Up @@ -434,7 +434,7 @@ config ATMEL_TCB_CLKSRC
config CLKSRC_EXYNOS_MCT
bool "Exynos multi core timer driver" if COMPILE_TEST
depends on ARM || ARM64
depends on ARCH_EXYNOS || COMPILE_TEST
depends on ARCH_ARTPEC || ARCH_EXYNOS || COMPILE_TEST
help
Support for Multi Core Timer controller on Exynos SoCs.

Expand Down
6 changes: 4 additions & 2 deletions drivers/clocksource/arm_arch_timer.c
Original file line number Diff line number Diff line change
Expand Up @@ -44,8 +44,8 @@
#define CNTACR_RWVT BIT(4)
#define CNTACR_RWPT BIT(5)

#define CNTVCT_LO 0x00
#define CNTPCT_LO 0x08
#define CNTPCT_LO 0x00
#define CNTVCT_LO 0x08
#define CNTFRQ 0x10
#define CNTP_CVAL_LO 0x20
#define CNTP_CTL 0x2c
Expand Down Expand Up @@ -473,6 +473,8 @@ static const struct arch_timer_erratum_workaround ool_workarounds[] = {
.desc = "ARM erratum 858921",
.read_cntpct_el0 = arm64_858921_read_cntpct_el0,
.read_cntvct_el0 = arm64_858921_read_cntvct_el0,
.set_next_event_phys = erratum_set_next_event_phys,
.set_next_event_virt = erratum_set_next_event_virt,
},
#endif
#ifdef CONFIG_SUN50I_ERRATUM_UNKNOWN1
Expand Down
83 changes: 74 additions & 9 deletions drivers/clocksource/exynos_mct.c
Original file line number Diff line number Diff line change
Expand Up @@ -33,7 +33,7 @@
#define EXYNOS4_MCT_G_INT_ENB EXYNOS4_MCTREG(0x248)
#define EXYNOS4_MCT_G_WSTAT EXYNOS4_MCTREG(0x24C)
#define _EXYNOS4_MCT_L_BASE EXYNOS4_MCTREG(0x300)
#define EXYNOS4_MCT_L_BASE(x) (_EXYNOS4_MCT_L_BASE + (0x100 * x))
#define EXYNOS4_MCT_L_BASE(x) (_EXYNOS4_MCT_L_BASE + (0x100 * (x)))
#define EXYNOS4_MCT_L_MASK (0xffffff00)

#define MCT_L_TCNTB_OFFSET (0x00)
Expand Down Expand Up @@ -66,6 +66,8 @@
#define MCT_L0_IRQ 4
/* Max number of IRQ as per DT binding document */
#define MCT_NR_IRQS 20
/* Max number of local timers */
#define MCT_NR_LOCAL (MCT_NR_IRQS - MCT_L0_IRQ)

enum {
MCT_INT_SPI,
Expand Down Expand Up @@ -233,9 +235,16 @@ static cycles_t exynos4_read_current_timer(void)
}
#endif

static int __init exynos4_clocksource_init(void)
static int __init exynos4_clocksource_init(bool frc_shared)
{
exynos4_mct_frc_start();
/*
* When the frc is shared, the main processer should have already
* turned it on and we shouldn't be writing to TCON.
*/
if (frc_shared)
mct_frc.resume = NULL;
else
exynos4_mct_frc_start();

#if defined(CONFIG_ARM)
exynos4_delay_timer.read_current_timer = &exynos4_read_current_timer;
Expand Down Expand Up @@ -449,7 +458,6 @@ static int exynos4_mct_starting_cpu(unsigned int cpu)
per_cpu_ptr(&percpu_mct_tick, cpu);
struct clock_event_device *evt = &mevt->evt;

mevt->base = EXYNOS4_MCT_L_BASE(cpu);
snprintf(mevt->name, sizeof(mevt->name), "mct_tick%d", cpu);

evt->name = mevt->name;
Expand Down Expand Up @@ -520,8 +528,17 @@ static int __init exynos4_timer_resources(struct device_node *np)
return 0;
}

/**
* exynos4_timer_interrupts - initialize MCT interrupts
* @np: device node for MCT
* @int_type: interrupt type, MCT_INT_PPI or MCT_INT_SPI
* @local_idx: array mapping CPU numbers to local timer indices
* @nr_local: size of @local_idx array
*/
static int __init exynos4_timer_interrupts(struct device_node *np,
unsigned int int_type)
unsigned int int_type,
const u32 *local_idx,
size_t nr_local)
{
int nr_irqs, i, err, cpu;

Expand Down Expand Up @@ -554,13 +571,21 @@ static int __init exynos4_timer_interrupts(struct device_node *np,
} else {
for_each_possible_cpu(cpu) {
int mct_irq;
unsigned int irq_idx;
struct mct_clock_event_device *pcpu_mevt =
per_cpu_ptr(&percpu_mct_tick, cpu);

if (cpu >= nr_local) {
err = -EINVAL;
goto out_irq;
}

irq_idx = MCT_L0_IRQ + local_idx[cpu];

pcpu_mevt->evt.irq = -1;
if (MCT_L0_IRQ + cpu >= ARRAY_SIZE(mct_irqs))
if (irq_idx >= ARRAY_SIZE(mct_irqs))
break;
mct_irq = mct_irqs[MCT_L0_IRQ + cpu];
mct_irq = mct_irqs[irq_idx];

irq_set_status_flags(mct_irq, IRQ_NOAUTOEN);
if (request_irq(mct_irq,
Expand All @@ -576,6 +601,17 @@ static int __init exynos4_timer_interrupts(struct device_node *np,
}
}

for_each_possible_cpu(cpu) {
struct mct_clock_event_device *mevt = per_cpu_ptr(&percpu_mct_tick, cpu);

if (cpu >= nr_local) {
err = -EINVAL;
goto out_irq;
}

mevt->base = EXYNOS4_MCT_L_BASE(local_idx[cpu]);
}

/* Install hotplug callbacks which configure the timer on this CPU */
err = cpuhp_setup_state(CPUHP_AP_EXYNOS4_MCT_TIMER_STARTING,
"clockevents/exynos4/mct_timer:starting",
Expand Down Expand Up @@ -605,20 +641,49 @@ static int __init exynos4_timer_interrupts(struct device_node *np,

static int __init mct_init_dt(struct device_node *np, unsigned int int_type)
{
bool frc_shared = of_property_read_bool(np, "samsung,frc-shared");
u32 local_idx[MCT_NR_LOCAL] = {0};
int nr_local;
int ret;

nr_local = of_property_count_u32_elems(np, "samsung,local-timers");
if (nr_local == 0)
return -EINVAL;
if (nr_local > 0) {
if (nr_local > ARRAY_SIZE(local_idx))
return -EINVAL;

ret = of_property_read_u32_array(np, "samsung,local-timers",
local_idx, nr_local);
if (ret)
return ret;
} else {
int i;

nr_local = ARRAY_SIZE(local_idx);
for (i = 0; i < nr_local; i++)
local_idx[i] = i;
}

ret = exynos4_timer_resources(np);
if (ret)
return ret;

ret = exynos4_timer_interrupts(np, int_type);
ret = exynos4_timer_interrupts(np, int_type, local_idx, nr_local);
if (ret)
return ret;

ret = exynos4_clocksource_init();
ret = exynos4_clocksource_init(frc_shared);
if (ret)
return ret;

/*
* When the FRC is shared with a main processor, this secondary
* processor cannot use the global comparator.
*/
if (frc_shared)
return ret;

return exynos4_clockevent_init();
}

Expand Down
2 changes: 1 addition & 1 deletion drivers/clocksource/renesas-ostm.c
Original file line number Diff line number Diff line change
Expand Up @@ -224,7 +224,7 @@ static int __init ostm_init(struct device_node *np)

TIMER_OF_DECLARE(ostm, "renesas,ostm", ostm_init);

#ifdef CONFIG_ARCH_R9A07G044
#ifdef CONFIG_ARCH_RZG2L
static int __init ostm_probe(struct platform_device *pdev)
{
struct device *dev = &pdev->dev;
Expand Down
7 changes: 6 additions & 1 deletion drivers/clocksource/timer-gxp.c
Original file line number Diff line number Diff line change
Expand Up @@ -171,6 +171,7 @@ static int gxp_timer_probe(struct platform_device *pdev)
{
struct platform_device *gxp_watchdog_device;
struct device *dev = &pdev->dev;
int ret;

if (!gxp_timer) {
pr_err("Gxp Timer not initialized, cannot create watchdog");
Expand All @@ -187,7 +188,11 @@ static int gxp_timer_probe(struct platform_device *pdev)
gxp_watchdog_device->dev.platform_data = gxp_timer->counter;
gxp_watchdog_device->dev.parent = dev;

return platform_device_add(gxp_watchdog_device);
ret = platform_device_add(gxp_watchdog_device);
if (ret)
platform_device_put(gxp_watchdog_device);

return ret;
}

static const struct of_device_id gxp_timer_of_match[] = {
Expand Down
6 changes: 4 additions & 2 deletions drivers/clocksource/timer-imx-sysctr.c
Original file line number Diff line number Diff line change
Expand Up @@ -134,8 +134,10 @@ static int __init sysctr_timer_init(struct device_node *np)
if (ret)
return ret;

/* system counter clock is divided by 3 internally */
to_sysctr.of_clk.rate /= SYS_CTR_CLK_DIV;
if (!of_property_read_bool(np, "nxp,no-divider")) {
/* system counter clock is divided by 3 internally */
to_sysctr.of_clk.rate /= SYS_CTR_CLK_DIV;
}

sys_ctr_base = timer_of_base(&to_sysctr);
cmpcr = readl(sys_ctr_base + CMPCR);
Expand Down
3 changes: 2 additions & 1 deletion drivers/clocksource/timer-sun4i.c
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,7 @@
#define TIMER_IRQ_EN_REG 0x00
#define TIMER_IRQ_EN(val) BIT(val)
#define TIMER_IRQ_ST_REG 0x04
#define TIMER_IRQ_CLEAR(val) BIT(val)
#define TIMER_CTL_REG(val) (0x10 * val + 0x10)
#define TIMER_CTL_ENABLE BIT(0)
#define TIMER_CTL_RELOAD BIT(1)
Expand Down Expand Up @@ -123,7 +124,7 @@ static int sun4i_clkevt_next_event(unsigned long evt,

static void sun4i_timer_clear_interrupt(void __iomem *base)
{
writel(TIMER_IRQ_EN(0), base + TIMER_IRQ_ST_REG);
writel(TIMER_IRQ_CLEAR(0), base + TIMER_IRQ_ST_REG);
}

static irqreturn_t sun4i_timer_interrupt(int irq, void *dev_id)
Expand Down
Loading

0 comments on commit 55be608

Please sign in to comment.