platform.c 4.2 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189
  1. /* SPDX-License-Identifier: BSD-2-Clause */
  2. /*
  3. * Copyright (C) 2019 FORTH-ICS/CARV
  4. * Panagiotis Peristerakis <perister@ics.forth.gr>
  5. */
  6. #include <sbi/riscv_asm.h>
  7. #include <sbi/riscv_encoding.h>
  8. #include <sbi/riscv_io.h>
  9. #include <sbi/sbi_console.h>
  10. #include <sbi/sbi_const.h>
  11. #include <sbi/sbi_hart.h>
  12. #include <sbi/sbi_platform.h>
  13. #include <sbi_utils/fdt/fdt_helper.h>
  14. #include <sbi_utils/fdt/fdt_fixup.h>
  15. #include <sbi_utils/ipi/aclint_mswi.h>
  16. #include <sbi_utils/irqchip/plic.h>
  17. #include <sbi_utils/serial/uart8250.h>
  18. #include <sbi_utils/timer/aclint_mtimer.h>
  19. #define ARIANE_UART_ADDR 0x10000000
  20. #define ARIANE_UART_FREQ 50000000
  21. #define ARIANE_UART_BAUDRATE 115200
  22. #define ARIANE_UART_REG_SHIFT 2
  23. #define ARIANE_UART_REG_WIDTH 4
  24. #define ARIANE_UART_REG_OFFSET 0
  25. #define ARIANE_PLIC_ADDR 0xc000000
  26. #define ARIANE_PLIC_NUM_SOURCES 3
  27. #define ARIANE_HART_COUNT 1
  28. #define ARIANE_CLINT_ADDR 0x2000000
  29. #define ARIANE_ACLINT_MTIMER_FREQ 1000000
  30. #define ARIANE_ACLINT_MSWI_ADDR (ARIANE_CLINT_ADDR + \
  31. CLINT_MSWI_OFFSET)
  32. #define ARIANE_ACLINT_MTIMER_ADDR (ARIANE_CLINT_ADDR + \
  33. CLINT_MTIMER_OFFSET)
  34. static struct plic_data plic = {
  35. .addr = ARIANE_PLIC_ADDR,
  36. .num_src = ARIANE_PLIC_NUM_SOURCES,
  37. };
  38. static struct aclint_mswi_data mswi = {
  39. .addr = ARIANE_ACLINT_MSWI_ADDR,
  40. .size = ACLINT_MSWI_SIZE,
  41. .first_hartid = 0,
  42. .hart_count = ARIANE_HART_COUNT,
  43. };
  44. static struct aclint_mtimer_data mtimer = {
  45. .mtime_freq = ARIANE_ACLINT_MTIMER_FREQ,
  46. .mtime_addr = ARIANE_ACLINT_MTIMER_ADDR +
  47. ACLINT_DEFAULT_MTIME_OFFSET,
  48. .mtime_size = ACLINT_DEFAULT_MTIME_SIZE,
  49. .mtimecmp_addr = ARIANE_ACLINT_MTIMER_ADDR +
  50. ACLINT_DEFAULT_MTIMECMP_OFFSET,
  51. .mtimecmp_size = ACLINT_DEFAULT_MTIMECMP_SIZE,
  52. .first_hartid = 0,
  53. .hart_count = ARIANE_HART_COUNT,
  54. .has_64bit_mmio = true,
  55. };
  56. /*
  57. * Ariane platform early initialization.
  58. */
  59. static int ariane_early_init(bool cold_boot)
  60. {
  61. /* For now nothing to do. */
  62. return 0;
  63. }
  64. /*
  65. * Ariane platform final initialization.
  66. */
  67. static int ariane_final_init(bool cold_boot)
  68. {
  69. void *fdt;
  70. if (!cold_boot)
  71. return 0;
  72. fdt = fdt_get_address();
  73. fdt_fixups(fdt);
  74. return 0;
  75. }
  76. /*
  77. * Initialize the ariane console.
  78. */
  79. static int ariane_console_init(void)
  80. {
  81. return uart8250_init(ARIANE_UART_ADDR,
  82. ARIANE_UART_FREQ,
  83. ARIANE_UART_BAUDRATE,
  84. ARIANE_UART_REG_SHIFT,
  85. ARIANE_UART_REG_WIDTH,
  86. ARIANE_UART_REG_OFFSET);
  87. }
  88. static int plic_ariane_warm_irqchip_init(int m_cntx_id, int s_cntx_id)
  89. {
  90. int ret;
  91. /* By default, enable all IRQs for M-mode of target HART */
  92. if (m_cntx_id > -1) {
  93. ret = plic_context_init(&plic, m_cntx_id, true, 0x1);
  94. if (ret)
  95. return ret;
  96. }
  97. /* Enable all IRQs for S-mode of target HART */
  98. if (s_cntx_id > -1) {
  99. ret = plic_context_init(&plic, s_cntx_id, true, 0x0);
  100. if (ret)
  101. return ret;
  102. }
  103. return 0;
  104. }
  105. /*
  106. * Initialize the ariane interrupt controller for current HART.
  107. */
  108. static int ariane_irqchip_init(bool cold_boot)
  109. {
  110. u32 hartid = current_hartid();
  111. int ret;
  112. if (cold_boot) {
  113. ret = plic_cold_irqchip_init(&plic);
  114. if (ret)
  115. return ret;
  116. }
  117. return plic_ariane_warm_irqchip_init(2 * hartid, 2 * hartid + 1);
  118. }
  119. /*
  120. * Initialize IPI for current HART.
  121. */
  122. static int ariane_ipi_init(bool cold_boot)
  123. {
  124. int ret;
  125. if (cold_boot) {
  126. ret = aclint_mswi_cold_init(&mswi);
  127. if (ret)
  128. return ret;
  129. }
  130. return aclint_mswi_warm_init();
  131. }
  132. /*
  133. * Initialize ariane timer for current HART.
  134. */
  135. static int ariane_timer_init(bool cold_boot)
  136. {
  137. int ret;
  138. if (cold_boot) {
  139. ret = aclint_mtimer_cold_init(&mtimer, NULL);
  140. if (ret)
  141. return ret;
  142. }
  143. return aclint_mtimer_warm_init();
  144. }
  145. /*
  146. * Platform descriptor.
  147. */
  148. const struct sbi_platform_operations platform_ops = {
  149. .early_init = ariane_early_init,
  150. .final_init = ariane_final_init,
  151. .console_init = ariane_console_init,
  152. .irqchip_init = ariane_irqchip_init,
  153. .ipi_init = ariane_ipi_init,
  154. .timer_init = ariane_timer_init,
  155. };
  156. const struct sbi_platform platform = {
  157. .opensbi_version = OPENSBI_VERSION,
  158. .platform_version = SBI_PLATFORM_VERSION(0x0, 0x01),
  159. .name = "ARIANE RISC-V",
  160. .features = SBI_PLATFORM_DEFAULT_FEATURES,
  161. .hart_count = ARIANE_HART_COUNT,
  162. .hart_stack_size = SBI_PLATFORM_DEFAULT_HART_STACK_SIZE,
  163. .platform_ops_addr = (unsigned long)&platform_ops
  164. };