aboutsummaryrefslogtreecommitdiff
path: root/ARMeilleure
diff options
context:
space:
mode:
Diffstat (limited to 'ARMeilleure')
-rw-r--r--ARMeilleure/Translation/ArmEmitterContext.cs7
-rw-r--r--ARMeilleure/Translation/PTC/IPtcLoadState.cs10
-rw-r--r--ARMeilleure/Translation/PTC/Ptc.cs136
-rw-r--r--ARMeilleure/Translation/PTC/PtcProfiler.cs74
-rw-r--r--ARMeilleure/Translation/Translator.cs46
5 files changed, 158 insertions, 115 deletions
diff --git a/ARMeilleure/Translation/ArmEmitterContext.cs b/ARMeilleure/Translation/ArmEmitterContext.cs
index 33355dae..48254de4 100644
--- a/ARMeilleure/Translation/ArmEmitterContext.cs
+++ b/ARMeilleure/Translation/ArmEmitterContext.cs
@@ -6,7 +6,6 @@ using ARMeilleure.Instructions;
using ARMeilleure.IntermediateRepresentation;
using ARMeilleure.Memory;
using ARMeilleure.State;
-using ARMeilleure.Translation.PTC;
using System;
using System.Collections.Generic;
using System.Reflection;
@@ -44,14 +43,13 @@ namespace ARMeilleure.Translation
public IMemoryManager Memory { get; }
- public bool HasPtc { get; }
-
public EntryTable<uint> CountTable { get; }
public AddressTable<ulong> FunctionTable { get; }
public TranslatorStubs Stubs { get; }
public ulong EntryAddress { get; }
public bool HighCq { get; }
+ public bool HasPtc { get; }
public Aarch32Mode Mode { get; }
private int _ifThenBlockStateIndex = 0;
@@ -66,15 +64,16 @@ namespace ARMeilleure.Translation
TranslatorStubs stubs,
ulong entryAddress,
bool highCq,
+ bool hasPtc,
Aarch32Mode mode)
{
- HasPtc = Ptc.State != PtcState.Disabled;
Memory = memory;
CountTable = countTable;
FunctionTable = funcTable;
Stubs = stubs;
EntryAddress = entryAddress;
HighCq = highCq;
+ HasPtc = hasPtc;
Mode = mode;
_labels = new Dictionary<ulong, Operand>();
diff --git a/ARMeilleure/Translation/PTC/IPtcLoadState.cs b/ARMeilleure/Translation/PTC/IPtcLoadState.cs
new file mode 100644
index 00000000..1b11ac0b
--- /dev/null
+++ b/ARMeilleure/Translation/PTC/IPtcLoadState.cs
@@ -0,0 +1,10 @@
+using System;
+
+namespace ARMeilleure.Translation.PTC
+{
+ public interface IPtcLoadState
+ {
+ event Action<PtcLoadingState, int, int> PtcStateChanged;
+ void Continue();
+ }
+} \ No newline at end of file
diff --git a/ARMeilleure/Translation/PTC/Ptc.cs b/ARMeilleure/Translation/PTC/Ptc.cs
index c2d358c1..f99d6e51 100644
--- a/ARMeilleure/Translation/PTC/Ptc.cs
+++ b/ARMeilleure/Translation/PTC/Ptc.cs
@@ -22,7 +22,7 @@ using static ARMeilleure.Translation.PTC.PtcFormatter;
namespace ARMeilleure.Translation.PTC
{
- public static class Ptc
+ class Ptc : IPtcLoadState
{
private const string OuterHeaderMagicString = "PTCohd\0\0";
private const string InnerHeaderMagicString = "PTCihd\0\0";
@@ -35,45 +35,49 @@ namespace ARMeilleure.Translation.PTC
private const string TitleIdTextDefault = "0000000000000000";
private const string DisplayVersionDefault = "0";
- internal static readonly Symbol PageTableSymbol = new(SymbolType.Special, 1);
- internal static readonly Symbol CountTableSymbol = new(SymbolType.Special, 2);
- internal static readonly Symbol DispatchStubSymbol = new(SymbolType.Special, 3);
+ public static readonly Symbol PageTableSymbol = new(SymbolType.Special, 1);
+ public static readonly Symbol CountTableSymbol = new(SymbolType.Special, 2);
+ public static readonly Symbol DispatchStubSymbol = new(SymbolType.Special, 3);
private const byte FillingByte = 0x00;
private const CompressionLevel SaveCompressionLevel = CompressionLevel.Fastest;
+ public PtcProfiler Profiler { get; }
+
// Carriers.
- private static MemoryStream _infosStream;
- private static List<byte[]> _codesList;
- private static MemoryStream _relocsStream;
- private static MemoryStream _unwindInfosStream;
+ private MemoryStream _infosStream;
+ private List<byte[]> _codesList;
+ private MemoryStream _relocsStream;
+ private MemoryStream _unwindInfosStream;
- private static readonly ulong _outerHeaderMagic;
- private static readonly ulong _innerHeaderMagic;
+ private readonly ulong _outerHeaderMagic;
+ private readonly ulong _innerHeaderMagic;
- private static readonly ManualResetEvent _waitEvent;
+ private readonly ManualResetEvent _waitEvent;
- private static readonly object _lock;
+ private readonly object _lock;
- private static bool _disposed;
+ private bool _disposed;
- internal static string TitleIdText { get; private set; }
- internal static string DisplayVersion { get; private set; }
+ public string TitleIdText { get; private set; }
+ public string DisplayVersion { get; private set; }
- private static MemoryManagerMode _memoryMode;
+ private MemoryManagerType _memoryMode;
- internal static string CachePathActual { get; private set; }
- internal static string CachePathBackup { get; private set; }
+ public string CachePathActual { get; private set; }
+ public string CachePathBackup { get; private set; }
- internal static PtcState State { get; private set; }
+ public PtcState State { get; private set; }
// Progress reporting helpers.
- private static volatile int _translateCount;
- private static volatile int _translateTotalCount;
- public static event Action<PtcLoadingState, int, int> PtcStateChanged;
+ private volatile int _translateCount;
+ private volatile int _translateTotalCount;
+ public event Action<PtcLoadingState, int, int> PtcStateChanged;
- static Ptc()
+ public Ptc()
{
+ Profiler = new PtcProfiler(this);
+
InitializeCarriers();
_outerHeaderMagic = BinaryPrimitives.ReadUInt64LittleEndian(EncodingCache.UTF8NoBOM.GetBytes(OuterHeaderMagicString).AsSpan());
@@ -94,12 +98,12 @@ namespace ARMeilleure.Translation.PTC
Disable();
}
- public static void Initialize(string titleIdText, string displayVersion, bool enabled, MemoryManagerMode memoryMode)
+ public void Initialize(string titleIdText, string displayVersion, bool enabled, MemoryManagerType memoryMode)
{
Wait();
- PtcProfiler.Wait();
- PtcProfiler.ClearEntries();
+ Profiler.Wait();
+ Profiler.ClearEntries();
Logger.Info?.Print(LogClass.Ptc, $"Initializing Profiled Persistent Translation Cache (enabled: {enabled}).");
@@ -137,12 +141,12 @@ namespace ARMeilleure.Translation.PTC
CachePathBackup = Path.Combine(workPathBackup, DisplayVersion);
PreLoad();
- PtcProfiler.PreLoad();
+ Profiler.PreLoad();
Enable();
}
- private static void InitializeCarriers()
+ private void InitializeCarriers()
{
_infosStream = new MemoryStream();
_codesList = new List<byte[]>();
@@ -150,7 +154,7 @@ namespace ARMeilleure.Translation.PTC
_unwindInfosStream = new MemoryStream();
}
- private static void DisposeCarriers()
+ private void DisposeCarriers()
{
_infosStream.Dispose();
_codesList.Clear();
@@ -158,12 +162,12 @@ namespace ARMeilleure.Translation.PTC
_unwindInfosStream.Dispose();
}
- private static bool AreCarriersEmpty()
+ private bool AreCarriersEmpty()
{
return _infosStream.Length == 0L && _codesList.Count == 0 && _relocsStream.Length == 0L && _unwindInfosStream.Length == 0L;
}
- private static void ResetCarriersIfNeeded()
+ private void ResetCarriersIfNeeded()
{
if (AreCarriersEmpty())
{
@@ -175,7 +179,7 @@ namespace ARMeilleure.Translation.PTC
InitializeCarriers();
}
- private static void PreLoad()
+ private void PreLoad()
{
string fileNameActual = string.Concat(CachePathActual, ".cache");
string fileNameBackup = string.Concat(CachePathBackup, ".cache");
@@ -199,7 +203,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- private static unsafe bool Load(string fileName, bool isBackup)
+ private unsafe bool Load(string fileName, bool isBackup)
{
using (FileStream compressedStream = new(fileName, FileMode.Open))
using (DeflateStream deflateStream = new(compressedStream, CompressionMode.Decompress, true))
@@ -376,12 +380,12 @@ namespace ARMeilleure.Translation.PTC
return true;
}
- private static void InvalidateCompressedStream(FileStream compressedStream)
+ private void InvalidateCompressedStream(FileStream compressedStream)
{
compressedStream.SetLength(0L);
}
- private static void PreSave()
+ private void PreSave()
{
_waitEvent.Reset();
@@ -409,7 +413,7 @@ namespace ARMeilleure.Translation.PTC
_waitEvent.Set();
}
- private static unsafe void Save(string fileName)
+ private unsafe void Save(string fileName)
{
int translatedFuncsCount;
@@ -517,7 +521,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static void LoadTranslations(Translator translator)
+ public void LoadTranslations(Translator translator)
{
if (AreCarriersEmpty())
{
@@ -550,7 +554,7 @@ namespace ARMeilleure.Translation.PTC
bool isEntryChanged = infoEntry.Hash != ComputeHash(translator.Memory, infoEntry.Address, infoEntry.GuestSize);
- if (isEntryChanged || (!infoEntry.HighCq && PtcProfiler.ProfiledFuncs.TryGetValue(infoEntry.Address, out var value) && value.HighCq))
+ if (isEntryChanged || (!infoEntry.HighCq && Profiler.ProfiledFuncs.TryGetValue(infoEntry.Address, out var value) && value.HighCq))
{
infoEntry.Stubbed = true;
infoEntry.CodeLength = 0;
@@ -601,38 +605,38 @@ namespace ARMeilleure.Translation.PTC
Logger.Info?.Print(LogClass.Ptc, $"{translator.Functions.Count} translated functions loaded");
}
- private static int GetEntriesCount()
+ private int GetEntriesCount()
{
return _codesList.Count;
}
[Conditional("DEBUG")]
- private static void SkipCode(int index, int codeLength)
+ private void SkipCode(int index, int codeLength)
{
Debug.Assert(_codesList[index].Length == 0);
Debug.Assert(codeLength == 0);
}
- private static void SkipReloc(int relocEntriesCount)
+ private void SkipReloc(int relocEntriesCount)
{
_relocsStream.Seek(relocEntriesCount * RelocEntry.Stride, SeekOrigin.Current);
}
- private static void SkipUnwindInfo(BinaryReader unwindInfosReader)
+ private void SkipUnwindInfo(BinaryReader unwindInfosReader)
{
int pushEntriesLength = unwindInfosReader.ReadInt32();
_unwindInfosStream.Seek(pushEntriesLength * UnwindPushEntry.Stride + UnwindInfo.Stride, SeekOrigin.Current);
}
- private static byte[] ReadCode(int index, int codeLength)
+ private byte[] ReadCode(int index, int codeLength)
{
Debug.Assert(_codesList[index].Length == codeLength);
return _codesList[index];
}
- private static RelocEntry[] GetRelocEntries(BinaryReader relocsReader, int relocEntriesCount)
+ private RelocEntry[] GetRelocEntries(BinaryReader relocsReader, int relocEntriesCount)
{
RelocEntry[] relocEntries = new RelocEntry[relocEntriesCount];
@@ -648,7 +652,7 @@ namespace ARMeilleure.Translation.PTC
return relocEntries;
}
- private static void PatchCode(Translator translator, Span<byte> code, RelocEntry[] relocEntries, out Counter<uint> callCounter)
+ private void PatchCode(Translator translator, Span<byte> code, RelocEntry[] relocEntries, out Counter<uint> callCounter)
{
callCounter = null;
@@ -702,7 +706,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- private static UnwindInfo ReadUnwindInfo(BinaryReader unwindInfosReader)
+ private UnwindInfo ReadUnwindInfo(BinaryReader unwindInfosReader)
{
int pushEntriesLength = unwindInfosReader.ReadInt32();
@@ -723,7 +727,7 @@ namespace ARMeilleure.Translation.PTC
return new UnwindInfo(pushEntries, prologueSize);
}
- private static TranslatedFunction FastTranslate(
+ private TranslatedFunction FastTranslate(
byte[] code,
Counter<uint> callCounter,
ulong guestSize,
@@ -736,19 +740,19 @@ namespace ARMeilleure.Translation.PTC
return new TranslatedFunction(gFunc, callCounter, guestSize, highCq);
}
- private static void UpdateInfo(InfoEntry infoEntry)
+ private void UpdateInfo(InfoEntry infoEntry)
{
_infosStream.Seek(-Unsafe.SizeOf<InfoEntry>(), SeekOrigin.Current);
SerializeStructure(_infosStream, infoEntry);
}
- private static void StubCode(int index)
+ private void StubCode(int index)
{
_codesList[index] = Array.Empty<byte>();
}
- private static void StubReloc(int relocEntriesCount)
+ private void StubReloc(int relocEntriesCount)
{
for (int i = 0; i < relocEntriesCount * RelocEntry.Stride; i++)
{
@@ -756,7 +760,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- private static void StubUnwindInfo(BinaryReader unwindInfosReader)
+ private void StubUnwindInfo(BinaryReader unwindInfosReader)
{
int pushEntriesLength = unwindInfosReader.ReadInt32();
@@ -766,9 +770,9 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static void MakeAndSaveTranslations(Translator translator)
+ public void MakeAndSaveTranslations(Translator translator)
{
- var profiledFuncsToTranslate = PtcProfiler.GetProfiledFuncsToTranslate(translator.Functions);
+ var profiledFuncsToTranslate = Profiler.GetProfiledFuncsToTranslate(translator.Functions);
_translateCount = 0;
_translateTotalCount = profiledFuncsToTranslate.Count;
@@ -811,7 +815,7 @@ namespace ARMeilleure.Translation.PTC
{
ulong address = item.address;
- Debug.Assert(PtcProfiler.IsAddressInStaticCodeRange(address));
+ Debug.Assert(Profiler.IsAddressInStaticCodeRange(address));
TranslatedFunction func = translator.Translate(address, item.funcProfile.Mode, item.funcProfile.HighCq);
@@ -861,7 +865,7 @@ namespace ARMeilleure.Translation.PTC
preSaveThread.Start();
}
- private static void ReportProgress(object state)
+ private void ReportProgress(object state)
{
const int refreshRate = 50; // ms.
@@ -882,12 +886,12 @@ namespace ARMeilleure.Translation.PTC
while (!endEvent.WaitOne(refreshRate));
}
- internal static Hash128 ComputeHash(IMemoryManager memory, ulong address, ulong guestSize)
+ public static Hash128 ComputeHash(IMemoryManager memory, ulong address, ulong guestSize)
{
return XXHash128.ComputeHash(memory.GetSpan(address, checked((int)(guestSize))));
}
- internal static void WriteCompiledFunction(ulong address, ulong guestSize, Hash128 hash, bool highCq, CompiledFunction compiledFunc)
+ public void WriteCompiledFunction(ulong address, ulong guestSize, Hash128 hash, bool highCq, CompiledFunction compiledFunc)
{
lock (_lock)
{
@@ -936,12 +940,12 @@ namespace ARMeilleure.Translation.PTC
}
}
- private static void WriteCode(ReadOnlySpan<byte> code)
+ private void WriteCode(ReadOnlySpan<byte> code)
{
_codesList.Add(code.ToArray());
}
- internal static bool GetEndianness()
+ public static bool GetEndianness()
{
return BitConverter.IsLittleEndian;
}
@@ -955,7 +959,7 @@ namespace ARMeilleure.Translation.PTC
(uint)HardwareCapabilities.FeatureInfo7Ecx);
}
- private static byte GetMemoryManagerMode()
+ private byte GetMemoryManagerMode()
{
return (byte)_memoryMode;
}
@@ -1050,12 +1054,12 @@ namespace ARMeilleure.Translation.PTC
public int RelocEntriesCount;
}
- private static void Enable()
+ private void Enable()
{
State = PtcState.Enabled;
}
- public static void Continue()
+ public void Continue()
{
if (State == PtcState.Enabled)
{
@@ -1063,7 +1067,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- public static void Close()
+ public void Close()
{
if (State == PtcState.Enabled ||
State == PtcState.Continuing)
@@ -1072,17 +1076,17 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static void Disable()
+ public void Disable()
{
State = PtcState.Disabled;
}
- private static void Wait()
+ private void Wait()
{
_waitEvent.WaitOne();
}
- public static void Dispose()
+ public void Dispose()
{
if (!_disposed)
{
diff --git a/ARMeilleure/Translation/PTC/PtcProfiler.cs b/ARMeilleure/Translation/PTC/PtcProfiler.cs
index bb70da8d..0d554628 100644
--- a/ARMeilleure/Translation/PTC/PtcProfiler.cs
+++ b/ARMeilleure/Translation/PTC/PtcProfiler.cs
@@ -16,7 +16,7 @@ using static ARMeilleure.Translation.PTC.PtcFormatter;
namespace ARMeilleure.Translation.PTC
{
- public static class PtcProfiler
+ class PtcProfiler
{
private const string OuterHeaderMagicString = "Pohd\0\0\0\0";
@@ -26,27 +26,31 @@ namespace ARMeilleure.Translation.PTC
private const CompressionLevel SaveCompressionLevel = CompressionLevel.Fastest;
- private static readonly System.Timers.Timer _timer;
+ private readonly Ptc _ptc;
- private static readonly ulong _outerHeaderMagic;
+ private readonly System.Timers.Timer _timer;
- private static readonly ManualResetEvent _waitEvent;
+ private readonly ulong _outerHeaderMagic;
- private static readonly object _lock;
+ private readonly ManualResetEvent _waitEvent;
- private static bool _disposed;
+ private readonly object _lock;
- private static Hash128 _lastHash;
+ private bool _disposed;
- internal static Dictionary<ulong, FuncProfile> ProfiledFuncs { get; private set; }
+ private Hash128 _lastHash;
- internal static bool Enabled { get; private set; }
+ public Dictionary<ulong, FuncProfile> ProfiledFuncs { get; private set; }
- public static ulong StaticCodeStart { internal get; set; }
- public static ulong StaticCodeSize { internal get; set; }
+ public bool Enabled { get; private set; }
- static PtcProfiler()
+ public ulong StaticCodeStart { get; set; }
+ public ulong StaticCodeSize { get; set; }
+
+ public PtcProfiler(Ptc ptc)
{
+ _ptc = ptc;
+
_timer = new System.Timers.Timer((double)SaveInterval * 1000d);
_timer.Elapsed += PreSave;
@@ -63,7 +67,7 @@ namespace ARMeilleure.Translation.PTC
Enabled = false;
}
- internal static void AddEntry(ulong address, ExecutionMode mode, bool highCq)
+ public void AddEntry(ulong address, ExecutionMode mode, bool highCq)
{
if (IsAddressInStaticCodeRange(address))
{
@@ -76,7 +80,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static void UpdateEntry(ulong address, ExecutionMode mode, bool highCq)
+ public void UpdateEntry(ulong address, ExecutionMode mode, bool highCq)
{
if (IsAddressInStaticCodeRange(address))
{
@@ -91,12 +95,12 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static bool IsAddressInStaticCodeRange(ulong address)
+ public bool IsAddressInStaticCodeRange(ulong address)
{
return address >= StaticCodeStart && address < StaticCodeStart + StaticCodeSize;
}
- internal static ConcurrentQueue<(ulong address, FuncProfile funcProfile)> GetProfiledFuncsToTranslate(TranslatorCache<TranslatedFunction> funcs)
+ public ConcurrentQueue<(ulong address, FuncProfile funcProfile)> GetProfiledFuncsToTranslate(TranslatorCache<TranslatedFunction> funcs)
{
var profiledFuncsToTranslate = new ConcurrentQueue<(ulong address, FuncProfile funcProfile)>();
@@ -111,18 +115,18 @@ namespace ARMeilleure.Translation.PTC
return profiledFuncsToTranslate;
}
- internal static void ClearEntries()
+ public void ClearEntries()
{
ProfiledFuncs.Clear();
ProfiledFuncs.TrimExcess();
}
- internal static void PreLoad()
+ public void PreLoad()
{
_lastHash = default;
- string fileNameActual = string.Concat(Ptc.CachePathActual, ".info");
- string fileNameBackup = string.Concat(Ptc.CachePathBackup, ".info");
+ string fileNameActual = string.Concat(_ptc.CachePathActual, ".info");
+ string fileNameBackup = string.Concat(_ptc.CachePathBackup, ".info");
FileInfo fileInfoActual = new FileInfo(fileNameActual);
FileInfo fileInfoBackup = new FileInfo(fileNameBackup);
@@ -143,7 +147,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- private static bool Load(string fileName, bool isBackup)
+ private bool Load(string fileName, bool isBackup)
{
using (FileStream compressedStream = new(fileName, FileMode.Open))
using (DeflateStream deflateStream = new(compressedStream, CompressionMode.Decompress, true))
@@ -228,22 +232,22 @@ namespace ARMeilleure.Translation.PTC
return DeserializeDictionary<ulong, FuncProfile>(stream, (stream) => DeserializeStructure<FuncProfile>(stream));
}
- private static ReadOnlySpan<byte> GetReadOnlySpan(MemoryStream memoryStream)
+ private ReadOnlySpan<byte> GetReadOnlySpan(MemoryStream memoryStream)
{
return new(memoryStream.GetBuffer(), (int)memoryStream.Position, (int)memoryStream.Length - (int)memoryStream.Position);
}
- private static void InvalidateCompressedStream(FileStream compressedStream)
+ private void InvalidateCompressedStream(FileStream compressedStream)
{
compressedStream.SetLength(0L);
}
- private static void PreSave(object source, System.Timers.ElapsedEventArgs e)
+ private void PreSave(object source, System.Timers.ElapsedEventArgs e)
{
_waitEvent.Reset();
- string fileNameActual = string.Concat(Ptc.CachePathActual, ".info");
- string fileNameBackup = string.Concat(Ptc.CachePathBackup, ".info");
+ string fileNameActual = string.Concat(_ptc.CachePathActual, ".info");
+ string fileNameBackup = string.Concat(_ptc.CachePathBackup, ".info");
FileInfo fileInfoActual = new FileInfo(fileNameActual);
@@ -257,7 +261,7 @@ namespace ARMeilleure.Translation.PTC
_waitEvent.Set();
}
- private static void Save(string fileName)
+ private void Save(string fileName)
{
int profiledFuncsCount;
@@ -329,7 +333,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- private static void Serialize(Stream stream, Dictionary<ulong, FuncProfile> profiledFuncs)
+ private void Serialize(Stream stream, Dictionary<ulong, FuncProfile> profiledFuncs)
{
SerializeDictionary(stream, profiledFuncs, (stream, structure) => SerializeStructure(stream, structure));
}
@@ -361,7 +365,7 @@ namespace ARMeilleure.Translation.PTC
}
[StructLayout(LayoutKind.Sequential, Pack = 1/*, Size = 5*/)]
- internal struct FuncProfile
+ public struct FuncProfile
{
public ExecutionMode Mode;
public bool HighCq;
@@ -373,10 +377,10 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static void Start()
+ public void Start()
{
- if (Ptc.State == PtcState.Enabled ||
- Ptc.State == PtcState.Continuing)
+ if (_ptc.State == PtcState.Enabled ||
+ _ptc.State == PtcState.Continuing)
{
Enabled = true;
@@ -384,7 +388,7 @@ namespace ARMeilleure.Translation.PTC
}
}
- public static void Stop()
+ public void Stop()
{
Enabled = false;
@@ -394,12 +398,12 @@ namespace ARMeilleure.Translation.PTC
}
}
- internal static void Wait()
+ public void Wait()
{
_waitEvent.WaitOne();
}
- public static void Dispose()
+ public void Dispose()
{
if (!_disposed)
{
diff --git a/ARMeilleure/Translation/Translator.cs b/ARMeilleure/Translation/Translator.cs
index 2edbe401..77ccdaea 100644
--- a/ARMeilleure/Translation/Translator.cs
+++ b/ARMeilleure/Translation/Translator.cs
@@ -44,6 +44,8 @@ namespace ARMeilleure.Translation
private readonly IJitMemoryAllocator _allocator;
private readonly ConcurrentQueue<KeyValuePair<ulong, TranslatedFunction>> _oldFuncs;
+ private readonly Ptc _ptc;
+
internal TranslatorCache<TranslatedFunction> Functions { get; }
internal AddressTable<ulong> FunctionTable { get; }
internal EntryTable<uint> CountTable { get; }
@@ -63,6 +65,8 @@ namespace ARMeilleure.Translation
_oldFuncs = new ConcurrentQueue<KeyValuePair<ulong, TranslatedFunction>>();
+ _ptc = new Ptc();
+
Queue = new TranslatorQueue();
JitCache.Initialize(allocator);
@@ -80,22 +84,37 @@ namespace ARMeilleure.Translation
}
}
+ public IPtcLoadState LoadDiskCache(string titleIdText, string displayVersion, bool enabled)
+ {
+ _ptc.Initialize(titleIdText, displayVersion, enabled, Memory.Type);
+ return _ptc;
+ }
+
+ public void PrepareCodeRange(ulong address, ulong size)
+ {
+ if (_ptc.Profiler.StaticCodeSize == 0)
+ {
+ _ptc.Profiler.StaticCodeStart = address;
+ _ptc.Profiler.StaticCodeSize = size;
+ }
+ }
+
public void Execute(State.ExecutionContext context, ulong address)
{
if (Interlocked.Increment(ref _threadCount) == 1)
{
IsReadyForTranslation.WaitOne();
- if (Ptc.State == PtcState.Enabled)
+ if (_ptc.State == PtcState.Enabled)
{
Debug.Assert(Functions.Count == 0);
- Ptc.LoadTranslations(this);
- Ptc.MakeAndSaveTranslations(this);
+ _ptc.LoadTranslations(this);
+ _ptc.MakeAndSaveTranslations(this);
}
- PtcProfiler.Start();
+ _ptc.Profiler.Start();
- Ptc.Disable();
+ _ptc.Disable();
// Simple heuristic, should be user configurable in future. (1 for 4 core/ht or less, 2 for 6 core + ht
// etc). All threads are normal priority except from the last, which just fills as much of the last core
@@ -148,6 +167,12 @@ namespace ARMeilleure.Translation
Stubs.Dispose();
FunctionTable.Dispose();
CountTable.Dispose();
+
+ _ptc.Close();
+ _ptc.Profiler.Stop();
+
+ _ptc.Dispose();
+ _ptc.Profiler.Dispose();
}
}
@@ -189,9 +214,9 @@ namespace ARMeilleure.Translation
func = oldFunc;
}
- if (PtcProfiler.Enabled)
+ if (_ptc.Profiler.Enabled)
{
- PtcProfiler.AddEntry(address, mode, highCq: false);
+ _ptc.Profiler.AddEntry(address, mode, highCq: false);
}
RegisterFunction(address, func);
@@ -217,6 +242,7 @@ namespace ARMeilleure.Translation
Stubs,
address,
highCq,
+ _ptc.State != PtcState.Disabled,
mode: Aarch32Mode.User);
Logger.StartPass(PassName.Decoding);
@@ -262,7 +288,7 @@ namespace ARMeilleure.Translation
{
Hash128 hash = Ptc.ComputeHash(Memory, address, funcSize);
- Ptc.WriteCompiledFunction(address, funcSize, hash, highCq, compiledFunc);
+ _ptc.WriteCompiledFunction(address, funcSize, hash, highCq, compiledFunc);
}
GuestFunction func = compiledFunc.Map<GuestFunction>();
@@ -284,9 +310,9 @@ namespace ARMeilleure.Translation
return func;
});
- if (PtcProfiler.Enabled)
+ if (_ptc.Profiler.Enabled)
{
- PtcProfiler.UpdateEntry(request.Address, request.Mode, highCq: true);
+ _ptc.Profiler.UpdateEntry(request.Address, request.Mode, highCq: true);
}
RegisterFunction(request.Address, func);