using ARMeilleure.Common; using ARMeilleure.Memory; using ARMeilleure.Translation; using ARMeilleure.Translation.PTC; using Ryujinx.Cpu.Signal; namespace Ryujinx.Cpu.Jit { class JitCpuContext : ICpuContext { private readonly ITickSource _tickSource; private readonly Translator _translator; public JitCpuContext(ITickSource tickSource, IMemoryManager memory, bool for64Bit) { _tickSource = tickSource; bool sparse = memory.Type is not MemoryManagerType.SoftwareMmu and not MemoryManagerType.SoftwarePageTable; IAddressTable functionTable = sparse ? SparseAddressTable.CreateForArm(for64Bit) : AddressTable.CreateForArm(for64Bit); _translator = new Translator(new JitMemoryAllocator(forJit: true), memory, functionTable); if (memory.Type.IsHostMappedOrTracked()) { NativeSignalHandler.InitializeSignalHandler(); } memory.UnmapEvent += UnmapHandler; } private void UnmapHandler(ulong address, ulong size) { _translator.InvalidateJitCacheRegion(address, size); } /// public IExecutionContext CreateExecutionContext(ExceptionCallbacks exceptionCallbacks) { return new JitExecutionContext(new JitMemoryAllocator(), _tickSource, exceptionCallbacks); } /// public void Execute(IExecutionContext context, ulong address) { _translator.Execute(((JitExecutionContext)context).Impl, address); } /// public void InvalidateCacheRegion(ulong address, ulong size) { _translator.InvalidateJitCacheRegion(address, size); } /// public IDiskCacheLoadState LoadDiskCache(PtcCacheInfo cacheInfo, bool enabled) { return new JitDiskCacheLoadState(_translator.LoadDiskCache(cacheInfo, enabled)); } /// public void PrepareCodeRange(ulong address, ulong size) { _translator.FunctionTable.SignalCodeRange(address, size); _translator.PrepareCodeRange(address, size); } public void Dispose() { } } }