HvApi.cs 8.9 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329
  1. using System;
  2. using System.Runtime.InteropServices;
  3. using System.Runtime.Versioning;
  4. namespace Ryujinx.Cpu.AppleHv
  5. {
  6. struct HvVcpuExitException
  7. {
  8. #pragma warning disable CS0649 // Field is never assigned to
  9. public ulong Syndrome;
  10. public ulong VirtualAddress;
  11. public ulong PhysicalAddress;
  12. #pragma warning restore CS0649
  13. }
  14. enum HvExitReason : uint
  15. {
  16. Canceled,
  17. Exception,
  18. VTimerActivated,
  19. Unknown,
  20. }
  21. struct HvVcpuExit
  22. {
  23. #pragma warning disable CS0649 // Field is never assigned to
  24. public HvExitReason Reason;
  25. public HvVcpuExitException Exception;
  26. #pragma warning restore CS0649
  27. }
  28. enum HvReg : uint
  29. {
  30. X0,
  31. X1,
  32. X2,
  33. X3,
  34. X4,
  35. X5,
  36. X6,
  37. X7,
  38. X8,
  39. X9,
  40. X10,
  41. X11,
  42. X12,
  43. X13,
  44. X14,
  45. X15,
  46. X16,
  47. X17,
  48. X18,
  49. X19,
  50. X20,
  51. X21,
  52. X22,
  53. X23,
  54. X24,
  55. X25,
  56. X26,
  57. X27,
  58. X28,
  59. X29,
  60. FP = X29,
  61. X30,
  62. LR = X30,
  63. PC,
  64. FPCR,
  65. FPSR,
  66. CPSR,
  67. }
  68. enum HvSimdFPReg : uint
  69. {
  70. Q0,
  71. Q1,
  72. Q2,
  73. Q3,
  74. Q4,
  75. Q5,
  76. Q6,
  77. Q7,
  78. Q8,
  79. Q9,
  80. Q10,
  81. Q11,
  82. Q12,
  83. Q13,
  84. Q14,
  85. Q15,
  86. Q16,
  87. Q17,
  88. Q18,
  89. Q19,
  90. Q20,
  91. Q21,
  92. Q22,
  93. Q23,
  94. Q24,
  95. Q25,
  96. Q26,
  97. Q27,
  98. Q28,
  99. Q29,
  100. Q30,
  101. Q31,
  102. }
  103. enum HvSysReg : ushort
  104. {
  105. DBGBVR0_EL1 = 0x8004,
  106. DBGBCR0_EL1 = 0x8005,
  107. DBGWVR0_EL1 = 0x8006,
  108. DBGWCR0_EL1 = 0x8007,
  109. DBGBVR1_EL1 = 0x800c,
  110. DBGBCR1_EL1 = 0x800d,
  111. DBGWVR1_EL1 = 0x800e,
  112. DBGWCR1_EL1 = 0x800f,
  113. MDCCINT_EL1 = 0x8010,
  114. MDSCR_EL1 = 0x8012,
  115. DBGBVR2_EL1 = 0x8014,
  116. DBGBCR2_EL1 = 0x8015,
  117. DBGWVR2_EL1 = 0x8016,
  118. DBGWCR2_EL1 = 0x8017,
  119. DBGBVR3_EL1 = 0x801c,
  120. DBGBCR3_EL1 = 0x801d,
  121. DBGWVR3_EL1 = 0x801e,
  122. DBGWCR3_EL1 = 0x801f,
  123. DBGBVR4_EL1 = 0x8024,
  124. DBGBCR4_EL1 = 0x8025,
  125. DBGWVR4_EL1 = 0x8026,
  126. DBGWCR4_EL1 = 0x8027,
  127. DBGBVR5_EL1 = 0x802c,
  128. DBGBCR5_EL1 = 0x802d,
  129. DBGWVR5_EL1 = 0x802e,
  130. DBGWCR5_EL1 = 0x802f,
  131. DBGBVR6_EL1 = 0x8034,
  132. DBGBCR6_EL1 = 0x8035,
  133. DBGWVR6_EL1 = 0x8036,
  134. DBGWCR6_EL1 = 0x8037,
  135. DBGBVR7_EL1 = 0x803c,
  136. DBGBCR7_EL1 = 0x803d,
  137. DBGWVR7_EL1 = 0x803e,
  138. DBGWCR7_EL1 = 0x803f,
  139. DBGBVR8_EL1 = 0x8044,
  140. DBGBCR8_EL1 = 0x8045,
  141. DBGWVR8_EL1 = 0x8046,
  142. DBGWCR8_EL1 = 0x8047,
  143. DBGBVR9_EL1 = 0x804c,
  144. DBGBCR9_EL1 = 0x804d,
  145. DBGWVR9_EL1 = 0x804e,
  146. DBGWCR9_EL1 = 0x804f,
  147. DBGBVR10_EL1 = 0x8054,
  148. DBGBCR10_EL1 = 0x8055,
  149. DBGWVR10_EL1 = 0x8056,
  150. DBGWCR10_EL1 = 0x8057,
  151. DBGBVR11_EL1 = 0x805c,
  152. DBGBCR11_EL1 = 0x805d,
  153. DBGWVR11_EL1 = 0x805e,
  154. DBGWCR11_EL1 = 0x805f,
  155. DBGBVR12_EL1 = 0x8064,
  156. DBGBCR12_EL1 = 0x8065,
  157. DBGWVR12_EL1 = 0x8066,
  158. DBGWCR12_EL1 = 0x8067,
  159. DBGBVR13_EL1 = 0x806c,
  160. DBGBCR13_EL1 = 0x806d,
  161. DBGWVR13_EL1 = 0x806e,
  162. DBGWCR13_EL1 = 0x806f,
  163. DBGBVR14_EL1 = 0x8074,
  164. DBGBCR14_EL1 = 0x8075,
  165. DBGWVR14_EL1 = 0x8076,
  166. DBGWCR14_EL1 = 0x8077,
  167. DBGBVR15_EL1 = 0x807c,
  168. DBGBCR15_EL1 = 0x807d,
  169. DBGWVR15_EL1 = 0x807e,
  170. DBGWCR15_EL1 = 0x807f,
  171. MIDR_EL1 = 0xc000,
  172. MPIDR_EL1 = 0xc005,
  173. ID_AA64PFR0_EL1 = 0xc020,
  174. ID_AA64PFR1_EL1 = 0xc021,
  175. ID_AA64DFR0_EL1 = 0xc028,
  176. ID_AA64DFR1_EL1 = 0xc029,
  177. ID_AA64ISAR0_EL1 = 0xc030,
  178. ID_AA64ISAR1_EL1 = 0xc031,
  179. ID_AA64MMFR0_EL1 = 0xc038,
  180. ID_AA64MMFR1_EL1 = 0xc039,
  181. ID_AA64MMFR2_EL1 = 0xc03a,
  182. SCTLR_EL1 = 0xc080,
  183. CPACR_EL1 = 0xc082,
  184. TTBR0_EL1 = 0xc100,
  185. TTBR1_EL1 = 0xc101,
  186. TCR_EL1 = 0xc102,
  187. APIAKEYLO_EL1 = 0xc108,
  188. APIAKEYHI_EL1 = 0xc109,
  189. APIBKEYLO_EL1 = 0xc10a,
  190. APIBKEYHI_EL1 = 0xc10b,
  191. APDAKEYLO_EL1 = 0xc110,
  192. APDAKEYHI_EL1 = 0xc111,
  193. APDBKEYLO_EL1 = 0xc112,
  194. APDBKEYHI_EL1 = 0xc113,
  195. APGAKEYLO_EL1 = 0xc118,
  196. APGAKEYHI_EL1 = 0xc119,
  197. SPSR_EL1 = 0xc200,
  198. ELR_EL1 = 0xc201,
  199. SP_EL0 = 0xc208,
  200. AFSR0_EL1 = 0xc288,
  201. AFSR1_EL1 = 0xc289,
  202. ESR_EL1 = 0xc290,
  203. FAR_EL1 = 0xc300,
  204. PAR_EL1 = 0xc3a0,
  205. MAIR_EL1 = 0xc510,
  206. AMAIR_EL1 = 0xc518,
  207. VBAR_EL1 = 0xc600,
  208. CONTEXTIDR_EL1 = 0xc681,
  209. TPIDR_EL1 = 0xc684,
  210. CNTKCTL_EL1 = 0xc708,
  211. CSSELR_EL1 = 0xd000,
  212. TPIDR_EL0 = 0xde82,
  213. TPIDRRO_EL0 = 0xde83,
  214. CNTV_CTL_EL0 = 0xdf19,
  215. CNTV_CVAL_EL0 = 0xdf1a,
  216. SP_EL1 = 0xe208,
  217. }
  218. enum HvMemoryFlags : ulong
  219. {
  220. Read = 1UL << 0,
  221. Write = 1UL << 1,
  222. Exec = 1UL << 2,
  223. }
  224. enum HvResult : uint
  225. {
  226. Success = 0,
  227. Error = 0xfae94001,
  228. Busy = 0xfae94002,
  229. BadArgument = 0xfae94003,
  230. NoResources = 0xfae94005,
  231. NoDevice = 0xfae94006,
  232. Denied = 0xfae94007,
  233. Unsupported = 0xfae9400f,
  234. }
  235. enum HvInterruptType : uint
  236. {
  237. IRQ,
  238. FIQ,
  239. }
  240. struct HvSimdFPUchar16
  241. {
  242. public ulong Low;
  243. public ulong High;
  244. }
  245. static class HvResultExtensions
  246. {
  247. public static void ThrowOnError(this HvResult result)
  248. {
  249. if (result != HvResult.Success)
  250. {
  251. throw new Exception($"Unexpected result \"{result}\".");
  252. }
  253. }
  254. }
  255. [SupportedOSPlatform("macos")]
  256. static partial class HvApi
  257. {
  258. public const string LibraryName = "/System/Library/Frameworks/Hypervisor.framework/Hypervisor";
  259. [LibraryImport(LibraryName, SetLastError = true)]
  260. public static partial HvResult hv_vm_get_max_vcpu_count(out uint max_vcpu_count);
  261. [LibraryImport(LibraryName, SetLastError = true)]
  262. public static partial HvResult hv_vm_create(IntPtr config);
  263. [LibraryImport(LibraryName, SetLastError = true)]
  264. public static partial HvResult hv_vm_destroy();
  265. [LibraryImport(LibraryName, SetLastError = true)]
  266. public static partial HvResult hv_vm_map(ulong addr, ulong ipa, ulong size, HvMemoryFlags flags);
  267. [LibraryImport(LibraryName, SetLastError = true)]
  268. public static partial HvResult hv_vm_unmap(ulong ipa, ulong size);
  269. [LibraryImport(LibraryName, SetLastError = true)]
  270. public static partial HvResult hv_vm_protect(ulong ipa, ulong size, HvMemoryFlags flags);
  271. [LibraryImport(LibraryName, SetLastError = true)]
  272. public unsafe static partial HvResult hv_vcpu_create(out ulong vcpu, ref HvVcpuExit* exit, IntPtr config);
  273. [LibraryImport(LibraryName, SetLastError = true)]
  274. public unsafe static partial HvResult hv_vcpu_destroy(ulong vcpu);
  275. [LibraryImport(LibraryName, SetLastError = true)]
  276. public static partial HvResult hv_vcpu_run(ulong vcpu);
  277. [LibraryImport(LibraryName, SetLastError = true)]
  278. public static partial HvResult hv_vcpus_exit(ref ulong vcpus, uint vcpu_count);
  279. [LibraryImport(LibraryName, SetLastError = true)]
  280. public static partial HvResult hv_vcpu_set_vtimer_mask(ulong vcpu, [MarshalAs(UnmanagedType.Bool)] bool vtimer_is_masked);
  281. [LibraryImport(LibraryName, SetLastError = true)]
  282. public static partial HvResult hv_vcpu_get_reg(ulong vcpu, HvReg reg, out ulong value);
  283. [LibraryImport(LibraryName, SetLastError = true)]
  284. public static partial HvResult hv_vcpu_set_reg(ulong vcpu, HvReg reg, ulong value);
  285. [LibraryImport(LibraryName, SetLastError = true)]
  286. public static partial HvResult hv_vcpu_get_simd_fp_reg(ulong vcpu, HvSimdFPReg reg, out HvSimdFPUchar16 value);
  287. [LibraryImport(LibraryName, SetLastError = true)]
  288. public static partial HvResult hv_vcpu_set_simd_fp_reg(ulong vcpu, HvSimdFPReg reg, HvSimdFPUchar16 value); // DO NOT USE DIRECTLY!
  289. [LibraryImport(LibraryName, SetLastError = true)]
  290. public static partial HvResult hv_vcpu_get_sys_reg(ulong vcpu, HvSysReg reg, out ulong value);
  291. [LibraryImport(LibraryName, SetLastError = true)]
  292. public static partial HvResult hv_vcpu_set_sys_reg(ulong vcpu, HvSysReg reg, ulong value);
  293. [LibraryImport(LibraryName, SetLastError = true)]
  294. public static partial HvResult hv_vcpu_get_pending_interrupt(ulong vcpu, HvInterruptType type, [MarshalAs(UnmanagedType.Bool)] out bool pending);
  295. [LibraryImport(LibraryName, SetLastError = true)]
  296. public static partial HvResult hv_vcpu_set_pending_interrupt(ulong vcpu, HvInterruptType type, [MarshalAs(UnmanagedType.Bool)] bool pending);
  297. }
  298. }