From 1e766a04c723e003c001c0f1a4f301aef026a75e Mon Sep 17 00:00:00 2001 From: Ovidiu Panait Date: Wed, 12 Oct 2022 08:36:54 +0300 Subject: timer-uclass: add timer_get_ops() macro Align timer uclass with the other subsystems and provide a timer_get_ops() convenience macro. Using this instead of the generic device_get_ops() also prevents -Wdiscarded-qualifiers warnings when used with non-const variables. Signed-off-by: Ovidiu Panait Reviewed-by: Simon Glass Link: https://lore.kernel.org/r/20221012053656.1492457-1-ovpanait@gmail.com Signed-off-by: Michal Simek --- drivers/timer/timer-uclass.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/timer') diff --git a/drivers/timer/timer-uclass.c b/drivers/timer/timer-uclass.c index cbc36476987..bdc77b38223 100644 --- a/drivers/timer/timer-uclass.c +++ b/drivers/timer/timer-uclass.c @@ -32,7 +32,7 @@ DECLARE_GLOBAL_DATA_PTR; int notrace timer_get_count(struct udevice *dev, u64 *count) { - const struct timer_ops *ops = device_get_ops(dev); + struct timer_ops *ops = timer_get_ops(dev); if (!ops->get_count) return -ENOSYS; -- cgit v1.2.3 From 8272d4cb897ca15eef2f39afe488f6731312e5c2 Mon Sep 17 00:00:00 2001 From: Ovidiu Panait Date: Wed, 12 Oct 2022 08:36:55 +0300 Subject: timer-uclass: relocate ops pointers for CONFIG_NEEDS_MANUAL_RELOC Relocate timer_ops pointers when CONFIG_NEEDS_MANUAL_RELOC is enabled. The (gd->flags & GD_FLG_RELOC) check was added to make sure the reloc_done logic works for drivers that use DM_FLAG_PRE_RELOC. Signed-off-by: Ovidiu Panait Reviewed-by: Simon Glass Link: https://lore.kernel.org/r/20221012053656.1492457-2-ovpanait@gmail.com Signed-off-by: Michal Simek --- drivers/timer/timer-uclass.c | 14 ++++++++++++++ 1 file changed, 14 insertions(+) (limited to 'drivers/timer') diff --git a/drivers/timer/timer-uclass.c b/drivers/timer/timer-uclass.c index bdc77b38223..bb719792135 100644 --- a/drivers/timer/timer-uclass.c +++ b/drivers/timer/timer-uclass.c @@ -18,6 +18,7 @@ #include #include #include +#include DECLARE_GLOBAL_DATA_PTR; @@ -50,6 +51,19 @@ unsigned long notrace timer_get_rate(struct udevice *dev) static int timer_pre_probe(struct udevice *dev) { + if (IS_ENABLED(CONFIG_NEEDS_MANUAL_RELOC) && + (gd->flags & GD_FLG_RELOC)) { + struct timer_ops *ops = timer_get_ops(dev); + static int reloc_done; + + if (!reloc_done) { + if (ops->get_count) + MANUAL_RELOC(ops->get_count); + + reloc_done++; + } + } + if (CONFIG_IS_ENABLED(OF_REAL)) { struct timer_dev_priv *uc_priv = dev_get_uclass_priv(dev); struct clk timer_clk; -- cgit v1.2.3 From b34bc22bd9921547246c117fb95eb58bedaceff5 Mon Sep 17 00:00:00 2001 From: Ovidiu Panait Date: Wed, 12 Oct 2022 08:36:56 +0300 Subject: timer: xilinx-timer: use timer_conv_64() to fix timer wrap around Current xilinx_timer_get_count() implementation does not take into account the periodic 32-bit wrap arounds, as it directly returns the 32-bit counter register value. The roll-overs cause problems in the upper timer layers, as generic timer code expects an incrementing 64-bit value from get_count() to work correctly. Add the missing 64-bit up-conversion to fix random hangs/delays in __udelay(). Fixes: a36d86720f ("microblaze: Convert axi timer to DM driver") Signed-off-by: Ovidiu Panait Reviewed-by: Michal Simek Link: https://lore.kernel.org/r/20221012053656.1492457-3-ovpanait@gmail.com Signed-off-by: Michal Simek --- drivers/timer/xilinx-timer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'drivers/timer') diff --git a/drivers/timer/xilinx-timer.c b/drivers/timer/xilinx-timer.c index 75b4473b639..172fd9f9296 100644 --- a/drivers/timer/xilinx-timer.c +++ b/drivers/timer/xilinx-timer.c @@ -40,7 +40,7 @@ static u64 xilinx_timer_get_count(struct udevice *dev) regmap_read(priv->regs, TIMER_COUNTER_OFFSET, &value); - return value; + return timer_conv_64(value); } static int xilinx_timer_probe(struct udevice *dev) -- cgit v1.2.3