public CpuEmiter(MipsMethodEmiter MipsMethodEmiter, InstructionReader InstructionReader, Stream MemoryStream, CpuProcessor CpuProcessor) { this.MipsMethodEmiter = MipsMethodEmiter; this.InstructionReader = InstructionReader; this.MemoryStream = MemoryStream; this.CpuProcessor = CpuProcessor; }
public override void InitializeComponent() { this.Callbacks = new HleUidPool <HleCallback>(); this.ScheduledCallbacks = new Queue <HleCallback>(); this.CpuProcessor = PspEmulatorContext.GetInstance <CpuProcessor>(); this.HleInterop = PspEmulatorContext.GetInstance <HleInterop>(); }
public override void InitializeComponent() { this.IsRunning = true; this.CpuProcessor = PspEmulatorContext.GetInstance <CpuProcessor>(); this.GpuProcessor = PspEmulatorContext.GetInstance <GpuProcessor>(); this.PspAudio = PspEmulatorContext.GetInstance <PspAudio>(); this.PspConfig = PspEmulatorContext.PspConfig; this.PspRtc = PspEmulatorContext.GetInstance <PspRtc>(); this.PspDisplay = PspEmulatorContext.GetInstance <PspDisplay>(); this.PspController = PspEmulatorContext.GetInstance <PspController>(); this.MipsEmiter = new MipsEmiter(); this.Kirk = new Kirk(); this.Kirk.kirk_init(); this.HleOutputHandler = PspEmulatorContext.GetInstance <HleOutputHandler>(); // @TODO FIX! New Instances!? this.ThreadManager = PspEmulatorContext.GetInstance <HleThreadManager>(); this.SemaphoreManager = PspEmulatorContext.GetInstance <HleSemaphoreManager>(); this.EventFlagManager = PspEmulatorContext.GetInstance <HleEventFlagManager>(); this.MemoryManager = new HleMemoryManager(this.CpuProcessor.Memory); this.ModuleManager = PspEmulatorContext.GetInstance <HleModuleManager>(); this.CallbackManager = PspEmulatorContext.GetInstance <HleCallbackManager>(); this.HleIoManager = PspEmulatorContext.GetInstance <HleIoManager>(); this.HleRegistryManager = PspEmulatorContext.GetInstance <HleRegistryManager>(); this.HleInterruptManager = PspEmulatorContext.GetInstance <HleInterruptManager>(); }
public LlePspCpu(string name, InjectContext injectContext, CpuProcessor cpuProcessor, uint entryPoint = 0x1fc00000) { _name = name; //this.CachedGetMethodCache = PspEmulatorContext.GetInstance<CachedGetMethodCache>(); CpuThreadState = new CpuThreadState(cpuProcessor); EntryPoint = entryPoint; }
public static AstNodeStm GlobalOptimize(CpuProcessor processor, AstNodeStm astNodeStm) { if (processor == null || processor.CpuConfig.EnableAstOptimizations) { return((AstNodeStm)(new AstOptimizerPsp(processor?.Memory)).Optimize( ast.Statements(astNodeStm, ast.Return()))); } return(astNodeStm); }
public static AstNodeStm GlobalOptimize(CpuProcessor Processor, AstNodeStm AstNodeStm) { if (Processor == null || Processor.CpuConfig.EnableAstOptimizations) { return (AstNodeStm)(new AstOptimizerPsp(Processor != null ? Processor.Memory : null)).Optimize(ast.Statements(AstNodeStm, ast.Return())); } else { return AstNodeStm; } }
public static AstNodeStm GlobalOptimize(CpuProcessor Processor, AstNodeStm AstNodeStm) { if (Processor.PspConfig.StoredConfig.EnableAstOptimizations) { return (AstNodeStm)(new AstOptimizerPsp(Processor)).Optimize(ast.Statements(AstNodeStm, ast.Return())); } else { return AstNodeStm; } }
public void SetUp() { PspConfig = new PspConfig(); PspEmulatorContext = new PspEmulatorContext(PspConfig); PspEmulatorContext.SetInstanceType <PspMemory, LazyPspMemory>(); Processor = PspEmulatorContext.GetInstance <CpuProcessor>(); MipsAssembler = new MipsAssembler(new PspMemoryStream(PspEmulatorContext.GetInstance <PspMemory>())); }
public override void InitializeComponent() { CpuProcessor = PspEmulatorContext.GetInstance <CpuProcessor>(); PspRtc = PspEmulatorContext.GetInstance <PspRtc>(); ThreadManager = PspEmulatorContext.GetInstance <HleThreadManager>(); HleState = PspEmulatorContext.GetInstance <HleState>(); PspMemory = PspEmulatorContext.GetInstance <PspMemory>(); RegisterDevices(); }
public void TestMethod2() { var processor = new CpuProcessor(); var state = new CpuThreadState(processor); var interpreter = new CpuInterpreter(state); state.Gpr2 = 3; state.Gpr3 = 7; interpreter.Interpret(MipsAssembler.StaticAssembleInstructions(@"add r1, r2, r3").Instructions[0]); Assert.Equal(3 + 7, (int)state.Gpr1); }
public MipsMethodEmitter(CpuProcessor Processor, uint PC, bool DoDebug = false, bool DoLog = false) { this.Processor = Processor; DynamicMethod = new DynamicMethod( String.Format("DynamicMethod_0x{0:X}", PC), typeof(void), new Type[] { typeof(CpuThreadState) }, Assembly.GetExecutingAssembly().ManifestModule ); }
public MethodCompilerThread(CpuProcessor cpuProcessor, MethodCache methodCache) { _cpuProcessor = cpuProcessor; _methodCache = methodCache; var thread = new Thread(Main) { Name = "MethodCompilerThread", IsBackground = true }; thread.Start(); }
internal InternalFunctionCompiler(CpuProcessor CpuProcessor, MipsMethodEmitter MipsMethodEmiter, DynarecFunctionCompiler DynarecFunctionCompiler, IInstructionReader InstructionReader, Action<uint> _ExploreNewPcCallback, uint EntryPC, bool DoLog) { this._ExploreNewPcCallback = _ExploreNewPcCallback; this.CpuEmitter = new CpuEmitter(MipsMethodEmiter, InstructionReader, CpuProcessor); this.MipsMethodEmitter = MipsMethodEmiter; this.GlobalInstructionStats = CpuProcessor.GlobalInstructionStats; this.InstructionStats = MipsMethodEmiter.InstructionStats; this.NewInstruction = new Dictionary<string, bool>(); this.DoLog = DoLog; this.CpuProcessor = CpuProcessor; this.DynarecFunctionCompiler = DynarecFunctionCompiler; this.InstructionReader = InstructionReader; this.EntryPC = EntryPC; }
public override void InitializeComponent() { this.HleCallbackManager = PspEmulatorContext.GetInstance <HleCallbackManager>(); this.CpuProcessor = PspEmulatorContext.GetInstance <CpuProcessor>(); this.HleInterop = PspEmulatorContext.GetInstance <HleInterop>(); //uint MaxHandlers = Enum.GetValues(typeof(PspInterrupts)).OfType<uint>().Max() + 1; InterruptHandlers = new HleInterruptHandler[(int)PspInterrupts._MAX]; for (int n = 0; n < InterruptHandlers.Length; n++) { InterruptHandlers[n] = new HleInterruptHandler( this, (PspInterrupts)n, HleCallbackManager ); } }
static public Action <CpuThreadState> CreateDelegateForPC(CpuProcessor CpuProcessor, Stream MemoryStream, uint EntryPC) { DateTime Start, End; int InstructionsProcessed = 0; Start = DateTime.Now; try { return(_CreateDelegateForPC(CpuProcessor, MemoryStream, EntryPC, out InstructionsProcessed)); } finally { End = DateTime.Now; //Console.WriteLine("Generated 0x{0:X} {1} ({2})", EntryPC, End - Start, InstructionsProcessed); } }
public AstNodeExprCallDelegate MethodCacheInfoCallStaticPc(CpuProcessor cpuProcessor, uint pc) { if (DynarecConfig.FunctionCallWithStaticReferences) { var methodCacheInfo = cpuProcessor.MethodCache.GetForPc(pc); return(Ast.CallDelegate(Ast.StaticFieldAccess(methodCacheInfo.StaticField.FieldInfo), Ast.CpuThreadStateExpr)); } else { return(Ast.CallDelegate( Ast.CallInstance(Ast.CpuThreadStateExpr, (Func <uint, Action <CpuThreadState> >)CpuThreadStateMethods.GetFuncAtPc, pc), Ast.CpuThreadStateExpr)); } }
public MipsMethodEmiter(MipsEmiter MipsEmiter, CpuProcessor Processor) { this.Processor = Processor; if (!InitializedOnce) { Field_GPRList = new FieldInfo[32]; Field_FPRList = new FieldInfo[32]; for (int n = 0; n < 32; n++) { Field_GPRList[n] = typeof(CpuThreadState).GetField("GPR" + n); Field_FPRList[n] = typeof(CpuThreadState).GetField("FPR" + n); } InitializedOnce = true; } UniqueCounter++; #if USE_DYNAMIC_METHOD DynamicMethod = new DynamicMethod( "", typeof(void), new Type[] { typeof(CpuThreadState) }, Assembly.GetExecutingAssembly().ManifestModule ); ILGenerator = DynamicMethod.GetILGenerator(); #else TypeBuilder = MipsEmiter.ModuleBuilder.DefineType("type" + UniqueCounter, TypeAttributes.Sealed | TypeAttributes.Public); MethodBuilder = TypeBuilder.DefineMethod( name: MethodName = "method" + UniqueCounter, attributes: MethodAttributes.Static | MethodAttributes.Public | MethodAttributes.UnmanagedExport | MethodAttributes.Final, returnType: typeof(void), parameterTypes: new Type[] { typeof(CpuThreadState) } ); ILGenerator = MethodBuilder.GetILGenerator(); #endif }
public override void InitializeComponent() { this.Processor = PspEmulatorContext.GetInstance <CpuProcessor>(); this.HleCallbackManager = PspEmulatorContext.GetInstance <HleCallbackManager>(); this.HleInterruptManager = PspEmulatorContext.GetInstance <HleInterruptManager>(); }
private AstOptimizerPsp(CpuProcessor Processor) { this.Processor = Processor; }
public static AstNodeStm Optimize(this AstNodeStm astNodeStm, CpuProcessor cpuProcessor) => AstOptimizerPsp.GlobalOptimize(cpuProcessor, astNodeStm);
static private Action <CpuThreadState> _CreateDelegateForPC(CpuProcessor CpuProcessor, Stream MemoryStream, uint EntryPC, out int InstructionsProcessed) { InstructionsProcessed = 0; if (EntryPC == 0) { if (MemoryStream is PspMemoryStream) { throw (new InvalidOperationException("EntryPC can't be NULL")); } } if (CpuProcessor.PspConfig.TraceJIT) { Console.WriteLine("Emiting EntryPC=0x{0:X}", EntryPC); } MemoryStream.Position = EntryPC; if ((MemoryStream.Length >= 8) && new BinaryReader(MemoryStream).ReadUInt64() == 0x0000000003E00008) { Console.WriteLine("NullSub detected at 0x{0:X}!", EntryPC); } var InstructionReader = new InstructionReader(MemoryStream); var MipsMethodEmiter = new MipsMethodEmiter(MipsEmiter, CpuProcessor); var ILGenerator = MipsMethodEmiter.ILGenerator; var CpuEmiter = new CpuEmiter(MipsMethodEmiter, InstructionReader, MemoryStream, CpuProcessor); uint PC; uint EndPC = (uint)MemoryStream.Length; uint MinPC = uint.MaxValue, MaxPC = uint.MinValue; var Labels = new SortedDictionary <uint, Label>(); var BranchesToAnalyze = new Queue <uint>(); var AnalyzedPC = new HashSet <uint>(); Labels[EntryPC] = ILGenerator.DefineLabel(); BranchesToAnalyze.Enqueue(EntryPC); // PASS1: Analyze and find labels. PC = EntryPC; //Debug.WriteLine("PASS1: (PC={0:X}, EndPC={1:X})", PC, EndPC); var GlobalInstructionStats = CpuProcessor.GlobalInstructionStats; var InstructionStats = new Dictionary <string, uint>(); var NewInstruction = new Dictionary <string, bool>(); int MaxNumberOfInstructions = 8 * 1024; //int MaxNumberOfInstructions = 60; while (BranchesToAnalyze.Count > 0) { bool EndOfBranchFound = false; for (PC = BranchesToAnalyze.Dequeue(); PC < EndPC; PC += 4) { // If already analyzed, stop scanning this branch. if (AnalyzedPC.Contains(PC)) { break; } AnalyzedPC.Add(PC); //Console.WriteLine("%08X".Sprintf(PC)); if (AnalyzedPC.Count > MaxNumberOfInstructions) { throw (new InvalidDataException("Code sequence too long: >= " + MaxNumberOfInstructions + "")); } MinPC = Math.Min(MinPC, PC); MaxPC = Math.Max(MaxPC, PC); //Console.WriteLine(" PC:{0:X}", PC); CpuEmiter.LoadAT(PC); var BranchInfo = GetBranchInfo(CpuEmiter.Instruction.Value); if (CpuProcessor.PspConfig.LogInstructionStats) { var InstructionName = GetInstructionName(CpuEmiter.Instruction.Value, null); if (!InstructionStats.ContainsKey(InstructionName)) { InstructionStats[InstructionName] = 0; } InstructionStats[InstructionName]++; if (!GlobalInstructionStats.ContainsKey(InstructionName)) { NewInstruction[InstructionName] = true; GlobalInstructionStats[InstructionName] = 0; } GlobalInstructionStats[InstructionName]++; //var GlobalInstructionStats = CpuProcessor.GlobalInstructionStats; //var InstructionStats = new Dictionary<string, uint>(); //var NewInstruction = new Dictionary<string, bool>(); } // Branch instruction. if ((BranchInfo & CpuBranchAnalyzer.Flags.JumpInstruction) != 0) { //Console.WriteLine("Instruction"); EndOfBranchFound = true; continue; } else if ((BranchInfo & CpuBranchAnalyzer.Flags.BranchOrJumpInstruction) != 0) { var BranchAddress = CpuEmiter.Instruction.GetBranchAddress(PC); Labels[BranchAddress] = ILGenerator.DefineLabel(); BranchesToAnalyze.Enqueue(BranchAddress); // Jump Always performed. /* * if ((BranchInfo & CpuBranchAnalyzer.Flags.JumpAlways) != 0) * { * EndOfBranchFound = true; * continue; * } */ } else if ((BranchInfo & CpuBranchAnalyzer.Flags.SyscallInstruction) != 0) { // On this special Syscall if (CpuEmiter.Instruction.CODE == FunctionGenerator.NativeCallSyscallCode) { //PC += 4; break; } } // A Jump Always found. And we have also processed the delayed branch slot. End the branch. if (EndOfBranchFound) { EndOfBranchFound = false; break; } } } // PASS2: Generate code and put labels; Action <uint> _EmitCpuInstructionAT = (_PC) => { if (CpuProcessor.PspConfig.TraceJIT) { ILGenerator.Emit(OpCodes.Ldarg_0); ILGenerator.Emit(OpCodes.Ldc_I4, _PC); ILGenerator.Emit(OpCodes.Call, typeof(CpuThreadState).GetMethod("Trace")); Console.WriteLine(" PC=0x{0:X}", _PC); } CpuEmiter.LoadAT(_PC); CpuEmiterInstruction(CpuEmiter.Instruction.Value, CpuEmiter); }; uint InstructionsEmitedSinceLastWaypoint = 0; Action StorePC = () => { MipsMethodEmiter.SavePC(PC); }; Action <bool> EmitInstructionCountIncrement = (bool CheckForYield) => { if (!CpuProcessor.PspConfig.CountInstructionsAndYield) { return; } //Console.WriteLine("EmiteInstructionCountIncrement: {0},{1}", InstructionsEmitedSinceLastWaypoint, CheckForYield); if (InstructionsEmitedSinceLastWaypoint > 0) { MipsMethodEmiter.SaveStepInstructionCount(() => { MipsMethodEmiter.LoadStepInstructionCount(); ILGenerator.Emit(OpCodes.Ldc_I4, InstructionsEmitedSinceLastWaypoint); //ILGenerator.Emit(OpCodes.Add); ILGenerator.Emit(OpCodes.Sub); }); //ILGenerator.Emit(OpCodes.Ldc_I4, 100); //ILGenerator.EmitCall(OpCodes.Call, typeof(Console).GetMethod("WriteLine"), new Type[] { typeof(int) }); InstructionsEmitedSinceLastWaypoint = 0; } if (CheckForYield) { if (!CpuProcessor.PspConfig.BreakInstructionThreadSwitchingForSpeed) { var NoYieldLabel = ILGenerator.DefineLabel(); MipsMethodEmiter.LoadStepInstructionCount(); ILGenerator.Emit(OpCodes.Ldc_I4_0); ILGenerator.Emit(OpCodes.Bgt, NoYieldLabel); //ILGenerator.Emit(OpCodes.Ldc_I4, 1000000); //ILGenerator.Emit(OpCodes.Blt, NoYieldLabel); MipsMethodEmiter.SaveStepInstructionCount(() => { ILGenerator.Emit(OpCodes.Ldc_I4_0); }); StorePC(); ILGenerator.Emit(OpCodes.Ldarg_0); ILGenerator.Emit(OpCodes.Call, typeof(CpuThreadState).GetMethod("Yield")); //ILGenerator.Emit(OpCodes.Call, typeof(GreenThread).GetMethod("Yield")); ILGenerator.MarkLabel(NoYieldLabel); } } }; Action EmitCpuInstruction = () => { if (CpuProcessor.NativeBreakpoints.Contains(PC)) { ILGenerator.Emit(OpCodes.Call, typeof(DebugUtils).GetMethod("IsDebuggerPresentDebugBreak")); } // Marks label. if (Labels.ContainsKey(PC)) { EmitInstructionCountIncrement(false); ILGenerator.MarkLabel(Labels[PC]); } _EmitCpuInstructionAT(PC); PC += 4; InstructionsEmitedSinceLastWaypoint++; }; //Debug.WriteLine("PASS2: MinPC:{0:X}, MaxPC:{1:X}", MinPC, MaxPC); // Jumps to the entry point. ILGenerator.Emit(OpCodes.Br, Labels[EntryPC]); for (PC = MinPC; PC <= MaxPC;) { uint CurrentInstructionPC = PC; Instruction CurrentInstruction = InstructionReader[PC]; InstructionsProcessed++; /* * if (!AnalyzedPC.Contains(CurrentInstructionPC)) * { * // Marks label. * if (Labels.ContainsKey(PC)) * { * ILGenerator.MarkLabel(Labels[PC]); * } * * * PC += 4; * continue; * } */ var BranchInfo = GetBranchInfo(CurrentInstruction.Value); // Delayed branch instruction. if ((BranchInfo & CpuBranchAnalyzer.Flags.BranchOrJumpInstruction) != 0) { InstructionsEmitedSinceLastWaypoint += 2; EmitInstructionCountIncrement(true); var BranchAddress = CurrentInstruction.GetBranchAddress(PC); if ((BranchInfo & CpuBranchAnalyzer.Flags.JumpInstruction) != 0) { // Marks label. if (Labels.ContainsKey(PC)) { ILGenerator.MarkLabel(Labels[PC]); } _EmitCpuInstructionAT(PC + 4); _EmitCpuInstructionAT(PC + 0); PC += 8; } else { // Branch instruction. EmitCpuInstruction(); //if ((BranchInfo & CpuBranchAnalyzer.Flags.Likely) != 0) if (BranchInfo.HasFlag(CpuBranchAnalyzer.Flags.Likely)) { //Console.WriteLine("Likely"); // Delayed instruction. CpuEmiter._branch_likely(() => { EmitCpuInstruction(); }); } else { //Console.WriteLine("Not Likely"); // Delayed instruction. EmitCpuInstruction(); } if (CurrentInstructionPC + 4 != BranchAddress) { if (Labels.ContainsKey(BranchAddress)) { CpuEmiter._branch_post(Labels[BranchAddress]); } // Code not reached. else { } } } } // Normal instruction. else { // Syscall instruction. if ((BranchInfo & CpuBranchAnalyzer.Flags.SyscallInstruction) != 0) { StorePC(); } EmitCpuInstruction(); if ((BranchInfo & CpuBranchAnalyzer.Flags.SyscallInstruction) != 0) { // On this special Syscall if (CurrentInstruction.CODE == FunctionGenerator.NativeCallSyscallCode) { //PC += 4; break; } } } } if (CpuProcessor.PspConfig.ShowInstructionStats) { Console.Error.WriteLine("-------------------------- {0:X}-{1:X} ", MinPC, MaxPC); foreach (var Pair in InstructionStats.OrderByDescending(Item => Item.Value)) { Console.Error.Write("{0} : {1}", Pair.Key, Pair.Value); if (NewInstruction.ContainsKey(Pair.Key)) { Console.Error.Write(" <-- NEW!"); } Console.Error.WriteLine(""); } } //if (BreakPoint) IsDebuggerPresentDebugBreak(); Action <CpuThreadState> Delegate = MipsMethodEmiter.CreateDelegate(); return(Delegate); }
public MethodCompilerThread(CpuProcessor CpuProcessor, MethodCache MethodCache) { this.CpuProcessor = CpuProcessor; this.MethodCache = MethodCache; this.Thread = new Thread(Main) { IsBackground = true }; this.Thread.Start(); }
//public readonly Dictionary<string, uint> InstructionStats = new Dictionary<string, uint>(); public MipsMethodEmitter(CpuProcessor Processor, uint PC, bool DoDebug = false, bool DoLog = false) { this.Processor = Processor; this.PC = PC; }
static public AstNodeExprCallDelegate MethodCacheInfoCallStaticPC(CpuProcessor CpuProcessor, uint PC) { var MethodCacheInfo = CpuProcessor.MethodCache.GetForPC(PC); return ast.CallDelegate(ast.StaticFieldAccess(MethodCacheInfo.StaticField.FieldInfo), CpuThreadStateArgument()); }
public void SetUp() { Processor = PspEmulatorContext.GetInstance <CpuProcessor>(); CpuThreadState = new CpuThreadState(Processor); }
//public readonly Dictionary<string, uint> InstructionStats = new Dictionary<string, uint>(); public MipsMethodEmitter(CpuProcessor processor, uint pc, bool doDebug = false, bool doLog = false) { _processor = processor; _pc = pc; }
public CpuEmiter(MipsMethodEmiter MipsMethodEmiter, IInstructionReader InstructionReader, CpuProcessor CpuProcessor) { this.MipsMethodEmiter = MipsMethodEmiter; this.InstructionReader = InstructionReader; this.CpuProcessor = CpuProcessor; }