2
0

imx6_src.c 8.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298
  1. /*
  2. * IMX6 System Reset Controller
  3. *
  4. * Copyright (c) 2015 Jean-Christophe Dubois <jcd@tribudubois.net>
  5. *
  6. * This work is licensed under the terms of the GNU GPL, version 2 or later.
  7. * See the COPYING file in the top-level directory.
  8. *
  9. */
  10. #include "qemu/osdep.h"
  11. #include "hw/misc/imx6_src.h"
  12. #include "migration/vmstate.h"
  13. #include "qemu/bitops.h"
  14. #include "qemu/log.h"
  15. #include "qemu/main-loop.h"
  16. #include "qemu/module.h"
  17. #include "target/arm/arm-powerctl.h"
  18. #include "hw/core/cpu.h"
  19. #include "trace.h"
  20. static const char *imx6_src_reg_name(uint32_t reg)
  21. {
  22. static char unknown[20];
  23. switch (reg) {
  24. case SRC_SCR:
  25. return "SRC_SCR";
  26. case SRC_SBMR1:
  27. return "SRC_SBMR1";
  28. case SRC_SRSR:
  29. return "SRC_SRSR";
  30. case SRC_SISR:
  31. return "SRC_SISR";
  32. case SRC_SIMR:
  33. return "SRC_SIMR";
  34. case SRC_SBMR2:
  35. return "SRC_SBMR2";
  36. case SRC_GPR1:
  37. return "SRC_GPR1";
  38. case SRC_GPR2:
  39. return "SRC_GPR2";
  40. case SRC_GPR3:
  41. return "SRC_GPR3";
  42. case SRC_GPR4:
  43. return "SRC_GPR4";
  44. case SRC_GPR5:
  45. return "SRC_GPR5";
  46. case SRC_GPR6:
  47. return "SRC_GPR6";
  48. case SRC_GPR7:
  49. return "SRC_GPR7";
  50. case SRC_GPR8:
  51. return "SRC_GPR8";
  52. case SRC_GPR9:
  53. return "SRC_GPR9";
  54. case SRC_GPR10:
  55. return "SRC_GPR10";
  56. default:
  57. snprintf(unknown, sizeof(unknown), "%u ?", reg);
  58. return unknown;
  59. }
  60. }
  61. static const VMStateDescription vmstate_imx6_src = {
  62. .name = TYPE_IMX6_SRC,
  63. .version_id = 1,
  64. .minimum_version_id = 1,
  65. .fields = (const VMStateField[]) {
  66. VMSTATE_UINT32_ARRAY(regs, IMX6SRCState, SRC_MAX),
  67. VMSTATE_END_OF_LIST()
  68. },
  69. };
  70. static void imx6_src_reset(DeviceState *dev)
  71. {
  72. IMX6SRCState *s = IMX6_SRC(dev);
  73. trace_imx6_src_reset();
  74. memset(s->regs, 0, sizeof(s->regs));
  75. /* Set reset values */
  76. s->regs[SRC_SCR] = 0x521;
  77. s->regs[SRC_SRSR] = 0x1;
  78. s->regs[SRC_SIMR] = 0x1F;
  79. }
  80. static uint64_t imx6_src_read(void *opaque, hwaddr offset, unsigned size)
  81. {
  82. uint32_t value = 0;
  83. IMX6SRCState *s = (IMX6SRCState *)opaque;
  84. uint32_t index = offset >> 2;
  85. if (index < SRC_MAX) {
  86. value = s->regs[index];
  87. } else {
  88. qemu_log_mask(LOG_GUEST_ERROR, "[%s]%s: Bad register at offset 0x%"
  89. HWADDR_PRIx "\n", TYPE_IMX6_SRC, __func__, offset);
  90. }
  91. trace_imx6_src_read(imx6_src_reg_name(index), value);
  92. return value;
  93. }
  94. /* The reset is asynchronous so we need to defer clearing the reset
  95. * bit until the work is completed.
  96. */
  97. struct SRCSCRResetInfo {
  98. IMX6SRCState *s;
  99. int reset_bit;
  100. };
  101. static void imx6_clear_reset_bit(CPUState *cpu, run_on_cpu_data data)
  102. {
  103. struct SRCSCRResetInfo *ri = data.host_ptr;
  104. IMX6SRCState *s = ri->s;
  105. assert(bql_locked());
  106. s->regs[SRC_SCR] = deposit32(s->regs[SRC_SCR], ri->reset_bit, 1, 0);
  107. trace_imx6_clear_reset_bit(imx6_src_reg_name(SRC_SCR), s->regs[SRC_SCR]);
  108. g_free(ri);
  109. }
  110. static void imx6_defer_clear_reset_bit(int cpuid,
  111. IMX6SRCState *s,
  112. unsigned long reset_shift)
  113. {
  114. struct SRCSCRResetInfo *ri;
  115. CPUState *cpu = arm_get_cpu_by_id(cpuid);
  116. if (!cpu) {
  117. return;
  118. }
  119. ri = g_new(struct SRCSCRResetInfo, 1);
  120. ri->s = s;
  121. ri->reset_bit = reset_shift;
  122. async_run_on_cpu(cpu, imx6_clear_reset_bit, RUN_ON_CPU_HOST_PTR(ri));
  123. }
  124. static void imx6_src_write(void *opaque, hwaddr offset, uint64_t value,
  125. unsigned size)
  126. {
  127. IMX6SRCState *s = (IMX6SRCState *)opaque;
  128. uint32_t index = offset >> 2;
  129. unsigned long change_mask;
  130. unsigned long current_value = value;
  131. if (index >= SRC_MAX) {
  132. qemu_log_mask(LOG_GUEST_ERROR, "[%s]%s: Bad register at offset 0x%"
  133. HWADDR_PRIx "\n", TYPE_IMX6_SRC, __func__, offset);
  134. return;
  135. }
  136. trace_imx6_src_write(imx6_src_reg_name(index), value);
  137. change_mask = s->regs[index] ^ (uint32_t)current_value;
  138. switch (index) {
  139. case SRC_SCR:
  140. /*
  141. * On real hardware when the system reset controller starts a
  142. * secondary CPU it runs through some boot ROM code which reads
  143. * the SRC_GPRX registers controlling the start address and branches
  144. * to it.
  145. * Here we are taking a short cut and branching directly to the
  146. * requested address (we don't want to run the boot ROM code inside
  147. * QEMU)
  148. */
  149. if (EXTRACT(change_mask, CORE3_ENABLE)) {
  150. if (EXTRACT(current_value, CORE3_ENABLE)) {
  151. /* CORE 3 is brought up */
  152. arm_set_cpu_on(3, s->regs[SRC_GPR7], s->regs[SRC_GPR8],
  153. 3, false);
  154. } else {
  155. /* CORE 3 is shut down */
  156. arm_set_cpu_off(3);
  157. }
  158. /* We clear the reset bits as the processor changed state */
  159. imx6_defer_clear_reset_bit(3, s, CORE3_RST_SHIFT);
  160. clear_bit(CORE3_RST_SHIFT, &change_mask);
  161. }
  162. if (EXTRACT(change_mask, CORE2_ENABLE)) {
  163. if (EXTRACT(current_value, CORE2_ENABLE)) {
  164. /* CORE 2 is brought up */
  165. arm_set_cpu_on(2, s->regs[SRC_GPR5], s->regs[SRC_GPR6],
  166. 3, false);
  167. } else {
  168. /* CORE 2 is shut down */
  169. arm_set_cpu_off(2);
  170. }
  171. /* We clear the reset bits as the processor changed state */
  172. imx6_defer_clear_reset_bit(2, s, CORE2_RST_SHIFT);
  173. clear_bit(CORE2_RST_SHIFT, &change_mask);
  174. }
  175. if (EXTRACT(change_mask, CORE1_ENABLE)) {
  176. if (EXTRACT(current_value, CORE1_ENABLE)) {
  177. /* CORE 1 is brought up */
  178. arm_set_cpu_on(1, s->regs[SRC_GPR3], s->regs[SRC_GPR4],
  179. 3, false);
  180. } else {
  181. /* CORE 1 is shut down */
  182. arm_set_cpu_off(1);
  183. }
  184. /* We clear the reset bits as the processor changed state */
  185. imx6_defer_clear_reset_bit(1, s, CORE1_RST_SHIFT);
  186. clear_bit(CORE1_RST_SHIFT, &change_mask);
  187. }
  188. if (EXTRACT(change_mask, CORE0_RST)) {
  189. arm_reset_cpu(0);
  190. imx6_defer_clear_reset_bit(0, s, CORE0_RST_SHIFT);
  191. }
  192. if (EXTRACT(change_mask, CORE1_RST)) {
  193. arm_reset_cpu(1);
  194. imx6_defer_clear_reset_bit(1, s, CORE1_RST_SHIFT);
  195. }
  196. if (EXTRACT(change_mask, CORE2_RST)) {
  197. arm_reset_cpu(2);
  198. imx6_defer_clear_reset_bit(2, s, CORE2_RST_SHIFT);
  199. }
  200. if (EXTRACT(change_mask, CORE3_RST)) {
  201. arm_reset_cpu(3);
  202. imx6_defer_clear_reset_bit(3, s, CORE3_RST_SHIFT);
  203. }
  204. if (EXTRACT(change_mask, SW_IPU2_RST)) {
  205. /* We pretend the IPU2 is reset */
  206. clear_bit(SW_IPU2_RST_SHIFT, &current_value);
  207. }
  208. if (EXTRACT(change_mask, SW_IPU1_RST)) {
  209. /* We pretend the IPU1 is reset */
  210. clear_bit(SW_IPU1_RST_SHIFT, &current_value);
  211. }
  212. s->regs[index] = current_value;
  213. break;
  214. default:
  215. s->regs[index] = current_value;
  216. break;
  217. }
  218. }
  219. static const struct MemoryRegionOps imx6_src_ops = {
  220. .read = imx6_src_read,
  221. .write = imx6_src_write,
  222. .endianness = DEVICE_NATIVE_ENDIAN,
  223. .valid = {
  224. /*
  225. * Our device would not work correctly if the guest was doing
  226. * unaligned access. This might not be a limitation on the real
  227. * device but in practice there is no reason for a guest to access
  228. * this device unaligned.
  229. */
  230. .min_access_size = 4,
  231. .max_access_size = 4,
  232. .unaligned = false,
  233. },
  234. };
  235. static void imx6_src_realize(DeviceState *dev, Error **errp)
  236. {
  237. IMX6SRCState *s = IMX6_SRC(dev);
  238. memory_region_init_io(&s->iomem, OBJECT(dev), &imx6_src_ops, s,
  239. TYPE_IMX6_SRC, 0x1000);
  240. sysbus_init_mmio(SYS_BUS_DEVICE(dev), &s->iomem);
  241. }
  242. static void imx6_src_class_init(ObjectClass *klass, void *data)
  243. {
  244. DeviceClass *dc = DEVICE_CLASS(klass);
  245. dc->realize = imx6_src_realize;
  246. device_class_set_legacy_reset(dc, imx6_src_reset);
  247. dc->vmsd = &vmstate_imx6_src;
  248. dc->desc = "i.MX6 System Reset Controller";
  249. }
  250. static const TypeInfo imx6_src_info = {
  251. .name = TYPE_IMX6_SRC,
  252. .parent = TYPE_SYS_BUS_DEVICE,
  253. .instance_size = sizeof(IMX6SRCState),
  254. .class_init = imx6_src_class_init,
  255. };
  256. static void imx6_src_register_types(void)
  257. {
  258. type_register_static(&imx6_src_info);
  259. }
  260. type_init(imx6_src_register_types)