NativeInterface.cs
1 using ARMeilleure.Memory; 2 using ARMeilleure.State; 3 using ARMeilleure.Translation; 4 using System; 5 6 namespace ARMeilleure.Instructions 7 { 8 static class NativeInterface 9 { 10 private class ThreadContext 11 { 12 public ExecutionContext Context { get; } 13 public IMemoryManager Memory { get; } 14 public Translator Translator { get; } 15 16 public ThreadContext(ExecutionContext context, IMemoryManager memory, Translator translator) 17 { 18 Context = context; 19 Memory = memory; 20 Translator = translator; 21 } 22 } 23 24 [ThreadStatic] 25 private static ThreadContext Context; 26 27 public static void RegisterThread(ExecutionContext context, IMemoryManager memory, Translator translator) 28 { 29 Context = new ThreadContext(context, memory, translator); 30 } 31 32 public static void UnregisterThread() 33 { 34 Context = null; 35 } 36 37 public static void Break(ulong address, int imm) 38 { 39 Statistics.PauseTimer(); 40 41 GetContext().OnBreak(address, imm); 42 43 Statistics.ResumeTimer(); 44 } 45 46 public static void SupervisorCall(ulong address, int imm) 47 { 48 Statistics.PauseTimer(); 49 50 GetContext().OnSupervisorCall(address, imm); 51 52 Statistics.ResumeTimer(); 53 } 54 55 public static void Undefined(ulong address, int opCode) 56 { 57 Statistics.PauseTimer(); 58 59 GetContext().OnUndefined(address, opCode); 60 61 Statistics.ResumeTimer(); 62 } 63 64 #region "System registers" 65 public static ulong GetCtrEl0() 66 { 67 return GetContext().CtrEl0; 68 } 69 70 public static ulong GetDczidEl0() 71 { 72 return GetContext().DczidEl0; 73 } 74 75 public static ulong GetCntfrqEl0() 76 { 77 return GetContext().CntfrqEl0; 78 } 79 80 public static ulong GetCntpctEl0() 81 { 82 return GetContext().CntpctEl0; 83 } 84 85 public static ulong GetCntvctEl0() 86 { 87 return GetContext().CntvctEl0; 88 } 89 #endregion 90 91 #region "Read" 92 public static byte ReadByte(ulong address) 93 { 94 return GetMemoryManager().ReadGuest<byte>(address); 95 } 96 97 public static ushort ReadUInt16(ulong address) 98 { 99 return GetMemoryManager().ReadGuest<ushort>(address); 100 } 101 102 public static uint ReadUInt32(ulong address) 103 { 104 return GetMemoryManager().ReadGuest<uint>(address); 105 } 106 107 public static ulong ReadUInt64(ulong address) 108 { 109 return GetMemoryManager().ReadGuest<ulong>(address); 110 } 111 112 public static V128 ReadVector128(ulong address) 113 { 114 return GetMemoryManager().ReadGuest<V128>(address); 115 } 116 #endregion 117 118 #region "Write" 119 public static void WriteByte(ulong address, byte value) 120 { 121 GetMemoryManager().WriteGuest(address, value); 122 } 123 124 public static void WriteUInt16(ulong address, ushort value) 125 { 126 GetMemoryManager().WriteGuest(address, value); 127 } 128 129 public static void WriteUInt32(ulong address, uint value) 130 { 131 GetMemoryManager().WriteGuest(address, value); 132 } 133 134 public static void WriteUInt64(ulong address, ulong value) 135 { 136 GetMemoryManager().WriteGuest(address, value); 137 } 138 139 public static void WriteVector128(ulong address, V128 value) 140 { 141 GetMemoryManager().WriteGuest(address, value); 142 } 143 #endregion 144 145 public static void EnqueueForRejit(ulong address) 146 { 147 Context.Translator.EnqueueForRejit(address, GetContext().ExecutionMode); 148 } 149 150 public static void SignalMemoryTracking(ulong address, ulong size, bool write) 151 { 152 GetMemoryManager().SignalMemoryTracking(address, size, write); 153 } 154 155 public static void ThrowInvalidMemoryAccess(ulong address) 156 { 157 throw new InvalidAccessException(address); 158 } 159 160 public static ulong GetFunctionAddress(ulong address) 161 { 162 TranslatedFunction function = Context.Translator.GetOrTranslate(address, GetContext().ExecutionMode); 163 164 return (ulong)function.FuncPointer.ToInt64(); 165 } 166 167 public static void InvalidateCacheLine(ulong address) 168 { 169 Context.Translator.InvalidateJitCacheRegion(address, InstEmit.DczSizeInBytes); 170 } 171 172 public static bool CheckSynchronization() 173 { 174 Statistics.PauseTimer(); 175 176 ExecutionContext context = GetContext(); 177 178 context.CheckInterrupt(); 179 180 Statistics.ResumeTimer(); 181 182 return context.Running; 183 } 184 185 public static ExecutionContext GetContext() 186 { 187 return Context.Context; 188 } 189 190 public static IMemoryManager GetMemoryManager() 191 { 192 return Context.Memory; 193 } 194 } 195 }