[PATCH] timer: fttmr010: return a previously deleted driver now ported to DM
Sergei Antonov
saproj at gmail.com
Mon Feb 13 18:34:36 CET 2023
The fttmr010 timer driver was deleted by
commit 29fc6f24926e ("ARM: remove a320evb board support")
The original source file was: arch/arm/cpu/arm920t/a320/timer.c
Return the driver to the codebase in a DM compatible form.
A platform using fttmr010 will be submitted later.
This hardware is described in the datasheet [1], starting from page 348.
According to the datasheet, there is a Revision Register at offset 0x3C,
which is not present in 'struct fttmr010'. Add it and debug() print
revision in probe function.
[1]
https://bitbucket.org/Kasreyn/mkrom-uc7112lx/src/master/documents/FIC8120_DS_v1.2.pdf
Signed-off-by: Sergei Antonov <saproj at gmail.com>
---
drivers/timer/Kconfig | 7 +++
drivers/timer/Makefile | 1 +
drivers/timer/fttmr010_timer.c | 92 ++++++++++++++++++++++++++++++++++
include/faraday/fttmr010.h | 1 +
4 files changed, 101 insertions(+)
create mode 100644 drivers/timer/fttmr010_timer.c
diff --git a/drivers/timer/Kconfig b/drivers/timer/Kconfig
index f32bd16227e3..915b2af160c1 100644
--- a/drivers/timer/Kconfig
+++ b/drivers/timer/Kconfig
@@ -145,6 +145,13 @@ config DESIGNWARE_APB_TIMER
Enables support for the Designware APB Timer driver. This timer is
present on Altera SoCFPGA SoCs.
+config FTTMR010_TIMER
+ bool "Faraday Technology timer support"
+ depends on TIMER
+ help
+ Select this to enable support for the timer found on
+ devices using Faraday Technology's IP.
+
config GXP_TIMER
bool "HPE GXP Timer"
depends on TIMER
diff --git a/drivers/timer/Makefile b/drivers/timer/Makefile
index 3c92113fc6fd..cdc20f5e946e 100644
--- a/drivers/timer/Makefile
+++ b/drivers/timer/Makefile
@@ -13,6 +13,7 @@ obj-$(CONFIG_$(SPL_)ATMEL_PIT_TIMER) += atmel_pit_timer.o
obj-$(CONFIG_$(SPL_)ATMEL_TCB_TIMER) += atmel_tcb_timer.o
obj-$(CONFIG_CADENCE_TTC_TIMER) += cadence-ttc.o
obj-$(CONFIG_DESIGNWARE_APB_TIMER) += dw-apb-timer.o
+obj-$(CONFIG_FTTMR010_TIMER) += fttmr010_timer.o
obj-$(CONFIG_GXP_TIMER) += gxp-timer.o
obj-$(CONFIG_MPC83XX_TIMER) += mpc83xx_timer.o
obj-$(CONFIG_NOMADIK_MTU_TIMER) += nomadik-mtu-timer.o
diff --git a/drivers/timer/fttmr010_timer.c b/drivers/timer/fttmr010_timer.c
new file mode 100644
index 000000000000..b6289e646109
--- /dev/null
+++ b/drivers/timer/fttmr010_timer.c
@@ -0,0 +1,92 @@
+// SPDX-License-Identifier: GPL-2.0+
+/*
+ * (C) Copyright 2009 Faraday Technology
+ * Po-Yu Chuang <ratbert at faraday-tech.com>
+ *
+ * 23/08/2022 Port to DM
+ */
+#include <common.h>
+#include <dm.h>
+#include <log.h>
+#include <timer.h>
+#include <asm/io.h>
+#include <dm/ofnode.h>
+#include <faraday/fttmr010.h>
+#include <asm/global_data.h>
+
+#define TIMER_LOAD_VAL 0xffffffff
+
+struct fttmr010_timer_priv {
+ struct fttmr010 __iomem *regs;
+};
+
+static u64 fttmr010_timer_get_count(struct udevice *dev)
+{
+ struct fttmr010_timer_priv *priv = dev_get_priv(dev);
+ struct fttmr010 *tmr = priv->regs;
+ u32 now = TIMER_LOAD_VAL - readl(&tmr->timer3_counter);
+
+ /* increment tbu if tbl has rolled over */
+ if (now < gd->arch.tbl)
+ gd->arch.tbu++;
+ gd->arch.tbl = now;
+
+ return ((u64)gd->arch.tbu << 32) | gd->arch.tbl;
+}
+
+static int fttmr010_timer_probe(struct udevice *dev)
+{
+ struct fttmr010_timer_priv *priv = dev_get_priv(dev);
+ struct fttmr010 *tmr;
+ unsigned int cr;
+
+ priv->regs = dev_read_addr_ptr(dev);
+ if (!priv->regs)
+ return -EINVAL;
+ tmr = priv->regs;
+
+ debug("Faraday FTTMR010 timer revision 0x%08X\n", readl(&tmr->revision));
+
+ /* disable timers */
+ writel(0, &tmr->cr);
+
+ /* setup timer */
+ writel(TIMER_LOAD_VAL, &tmr->timer3_load);
+ writel(TIMER_LOAD_VAL, &tmr->timer3_counter);
+ writel(0, &tmr->timer3_match1);
+ writel(0, &tmr->timer3_match2);
+
+ /* we don't want timer to issue interrupts */
+ writel(FTTMR010_TM3_MATCH1 |
+ FTTMR010_TM3_MATCH2 |
+ FTTMR010_TM3_OVERFLOW,
+ &tmr->interrupt_mask);
+
+ cr = readl(&tmr->cr);
+ cr |= FTTMR010_TM3_CLOCK; /* use external clock */
+ cr |= FTTMR010_TM3_ENABLE;
+ writel(cr, &tmr->cr);
+
+ gd->arch.tbl = 0;
+ gd->arch.tbu = 0;
+
+ return 0;
+}
+
+static const struct timer_ops fttmr010_timer_ops = {
+ .get_count = fttmr010_timer_get_count,
+};
+
+static const struct udevice_id fttmr010_timer_ids[] = {
+ { .compatible = "faraday,fttmr010-timer" },
+ {}
+};
+
+U_BOOT_DRIVER(fttmr010_timer) = {
+ .name = "fttmr010_timer",
+ .id = UCLASS_TIMER,
+ .of_match = fttmr010_timer_ids,
+ .priv_auto = sizeof(struct fttmr010_timer_priv),
+ .probe = fttmr010_timer_probe,
+ .ops = &fttmr010_timer_ops,
+};
diff --git a/include/faraday/fttmr010.h b/include/faraday/fttmr010.h
index ec1c9895f57c..5b1bef38c77d 100644
--- a/include/faraday/fttmr010.h
+++ b/include/faraday/fttmr010.h
@@ -26,6 +26,7 @@ struct fttmr010 {
unsigned int cr; /* 0x30 */
unsigned int interrupt_state; /* 0x34 */
unsigned int interrupt_mask; /* 0x38 */
+ unsigned int revision; /* 0x3c */
};
/*
--
2.34.1
More information about the U-Boot
mailing list