riscv_timer.c 1.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354
  1. // SPDX-License-Identifier: GPL-2.0+
  2. /*
  3. * Copyright (C) 2020, Sean Anderson <seanga2@gmail.com>
  4. * Copyright (C) 2018, Bin Meng <bmeng.cn@gmail.com>
  5. * Copyright (C) 2018, Anup Patel <anup@brainfault.org>
  6. * Copyright (C) 2012 Regents of the University of California
  7. *
  8. * RISC-V architecturally-defined generic timer driver
  9. *
  10. * This driver provides generic timer support for S-mode U-Boot.
  11. */
  12. #include <common.h>
  13. #include <dm.h>
  14. #include <errno.h>
  15. #include <timer.h>
  16. #include <asm/csr.h>
  17. static u64 riscv_timer_get_count(struct udevice *dev)
  18. {
  19. __maybe_unused u32 hi, lo;
  20. if (IS_ENABLED(CONFIG_64BIT))
  21. return csr_read(CSR_TIME);
  22. do {
  23. hi = csr_read(CSR_TIMEH);
  24. lo = csr_read(CSR_TIME);
  25. } while (hi != csr_read(CSR_TIMEH));
  26. return ((u64)hi << 32) | lo;
  27. }
  28. static int riscv_timer_probe(struct udevice *dev)
  29. {
  30. struct timer_dev_priv *uc_priv = dev_get_uclass_priv(dev);
  31. /* clock frequency was passed from the cpu driver as driver data */
  32. uc_priv->clock_rate = dev->driver_data;
  33. return 0;
  34. }
  35. static const struct timer_ops riscv_timer_ops = {
  36. .get_count = riscv_timer_get_count,
  37. };
  38. U_BOOT_DRIVER(riscv_timer) = {
  39. .name = "riscv_timer",
  40. .id = UCLASS_TIMER,
  41. .probe = riscv_timer_probe,
  42. .ops = &riscv_timer_ops,
  43. .flags = DM_FLAG_PRE_RELOC,
  44. };