mirror of
https://github.com/danbulant/Cosmos
synced 2026-05-19 04:18:43 +00:00
Add changes from @Og-Rok
This commit is contained in:
parent
274c5c8b7a
commit
6bef4e1fa0
14 changed files with 546 additions and 31 deletions
|
|
@ -234,6 +234,8 @@ namespace Cosmos.Core {
|
|||
[AsmMarker(AsmMarker.Type.Int_LastKnownAddress)]
|
||||
private static uint mLastKnownAddress;
|
||||
|
||||
public static uint mStackContext;
|
||||
|
||||
/// <summary>
|
||||
/// IRQ handlers.
|
||||
/// </summary>
|
||||
|
|
@ -845,6 +847,8 @@ namespace Cosmos.Core {
|
|||
HandleInterrupt_47(ref xCtx);
|
||||
HandleInterrupt_48(ref xCtx);
|
||||
HandleInterrupt_49(ref xCtx);
|
||||
Processing.ProcessorScheduler.SwitchTask();
|
||||
Processing.ProcessorScheduler.EntryPoint();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -2,6 +2,7 @@
|
|||
using System.Linq;
|
||||
using System.Threading.Tasks;
|
||||
using Cosmos.Core;
|
||||
using Cosmos.Core.Processing;
|
||||
using Cosmos.Debug.Kernel;
|
||||
|
||||
namespace Cosmos.Core.Memory.Old
|
||||
|
|
@ -19,6 +20,8 @@ namespace Cosmos.Core.Memory.Old
|
|||
|
||||
private static uint mLastEntryIndex = 0u;
|
||||
|
||||
private static Mutex mMemeoryGate = new Mutex();
|
||||
|
||||
private static bool mInitialized = false;
|
||||
|
||||
private static void DoInitialize(uint aEndOfRam)
|
||||
|
|
@ -59,6 +62,11 @@ namespace Cosmos.Core.Memory.Old
|
|||
{
|
||||
EnsureIsInitialized();
|
||||
|
||||
if (mMemeoryGate != null)
|
||||
{
|
||||
mMemeoryGate.Lock();
|
||||
}
|
||||
|
||||
DataLookupTable* xCurrentTable = GlobalSystemInfo.GlobalInformationTable->FirstDataLookupTable;
|
||||
DataLookupTable* xPreviousTable = null;
|
||||
uint xResult;
|
||||
|
|
@ -81,6 +89,11 @@ namespace Cosmos.Core.Memory.Old
|
|||
}
|
||||
}
|
||||
|
||||
if (mMemeoryGate != null)
|
||||
{
|
||||
mMemeoryGate.Unlock();
|
||||
}
|
||||
|
||||
return xResult;
|
||||
}
|
||||
mLastTable = xPreviousTable;
|
||||
|
|
@ -117,6 +130,12 @@ namespace Cosmos.Core.Memory.Old
|
|||
}
|
||||
mLastTable = xNextTablePointer;
|
||||
mLastEntryIndex = 0;
|
||||
|
||||
if (mMemeoryGate != null)
|
||||
{
|
||||
mMemeoryGate.Unlock();
|
||||
}
|
||||
|
||||
return xResult;
|
||||
}
|
||||
finally
|
||||
|
|
@ -129,6 +148,10 @@ namespace Cosmos.Core.Memory.Old
|
|||
{
|
||||
//Debugger.DoSend(" Not enabling interrupts, because they weren't enabled yet!");
|
||||
}
|
||||
if (mMemeoryGate != null)
|
||||
{
|
||||
mMemeoryGate.Unlock();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
19
source/Cosmos.Core/ObjUtilities.cs
Normal file
19
source/Cosmos.Core/ObjUtilities.cs
Normal file
|
|
@ -0,0 +1,19 @@
|
|||
using IL2CPU.API.Attribs;
|
||||
using System;
|
||||
|
||||
namespace Cosmos.Core
|
||||
{
|
||||
public static unsafe class ObjUtilities
|
||||
{
|
||||
public static uint GetPointer(Delegate aVal)
|
||||
{
|
||||
return (uint)aVal.GetHashCode();
|
||||
}
|
||||
|
||||
[PlugMethod(PlugRequired = true)]
|
||||
public static uint GetPointer(Object aVal) { return 0; }
|
||||
|
||||
[PlugMethod(PlugRequired = true)]
|
||||
public static uint GetEntryPoint() { return 0; }
|
||||
}
|
||||
}
|
||||
27
source/Cosmos.Core/Processing/Mutex.cs
Normal file
27
source/Cosmos.Core/Processing/Mutex.cs
Normal file
|
|
@ -0,0 +1,27 @@
|
|||
using IL2CPU.API.Attribs;
|
||||
|
||||
namespace Cosmos.Core.Processing
|
||||
{
|
||||
public unsafe class Mutex
|
||||
{
|
||||
public int gate;
|
||||
|
||||
[PlugMethod(PlugRequired = true)]
|
||||
public static void MutexLock(int* mtx) { }
|
||||
|
||||
public void Lock()
|
||||
{
|
||||
while (gate != 0) { }
|
||||
gate = 1;
|
||||
/*fixed (int* p = &gate)
|
||||
{
|
||||
MutexLock(p);
|
||||
}*/
|
||||
}
|
||||
|
||||
public void Unlock()
|
||||
{
|
||||
gate = 0;
|
||||
}
|
||||
}
|
||||
}
|
||||
154
source/Cosmos.Core/Processing/ProcessContext.cs
Normal file
154
source/Cosmos.Core/Processing/ProcessContext.cs
Normal file
|
|
@ -0,0 +1,154 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
|
||||
namespace Cosmos.Core.Processing
|
||||
{
|
||||
public static unsafe class ProcessContext
|
||||
{
|
||||
public enum Thread_State
|
||||
{
|
||||
ALIVE = 0,
|
||||
DEAD = 1,
|
||||
WAITING_SLEEP = 2,
|
||||
PAUSED = 3
|
||||
}
|
||||
|
||||
public enum Context_Type
|
||||
{
|
||||
THREAD = 0,
|
||||
PROCESS = 1
|
||||
}
|
||||
|
||||
public class Context
|
||||
{
|
||||
public Context next;
|
||||
public Context_Type type;
|
||||
public uint tid;
|
||||
public string name;
|
||||
public uint esp;
|
||||
public uint stacktop;
|
||||
public System.Threading.ThreadStart entry;
|
||||
public System.Threading.ParameterizedThreadStart paramentry;
|
||||
public Thread_State state;
|
||||
public object param;
|
||||
public int arg;
|
||||
public uint priority;
|
||||
public uint age;
|
||||
public uint parent;
|
||||
}
|
||||
|
||||
public const uint STACK_SIZE = 4096;
|
||||
public static uint m_NextCID;
|
||||
public static Context m_CurrentContext;
|
||||
public static Context m_ContextList;
|
||||
|
||||
public static Context GetContext(uint tid)
|
||||
{
|
||||
/*for(int i = 0; i < m_ContextList.Count; i++)
|
||||
{
|
||||
if(m_ContextList[i].tid == tid)
|
||||
{
|
||||
return m_ContextList[i];
|
||||
}
|
||||
}*/
|
||||
Context ctx = m_ContextList;
|
||||
while (ctx.next != null)
|
||||
{
|
||||
if (ctx.tid == tid)
|
||||
{
|
||||
return ctx;
|
||||
}
|
||||
ctx = ctx.next;
|
||||
}
|
||||
if (ctx.tid == tid)
|
||||
{
|
||||
return ctx;
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public static uint* SetupStack(uint* stack)
|
||||
{
|
||||
uint origin = (uint)stack;
|
||||
*--stack = 0xFFFFFFFF; // trash
|
||||
*--stack = 0xFFFFFFFF; // trash
|
||||
*--stack = 0xFFFFFFFF; // trash
|
||||
*--stack = 0xFFFFFFFF; // trash
|
||||
*--stack = 0x10; // ss ?
|
||||
*--stack = 0x00000202; // eflags
|
||||
*--stack = 0x8; // cs
|
||||
*--stack = ObjUtilities.GetEntryPoint(); // eip
|
||||
*--stack = 0; // error
|
||||
*--stack = 0; // int
|
||||
*--stack = 0; // eax
|
||||
*--stack = 0; // ebx
|
||||
*--stack = 0; // ecx
|
||||
*--stack = 0; // offset
|
||||
*--stack = 0; // edx
|
||||
*--stack = 0; // esi
|
||||
*--stack = 0; // edi
|
||||
*--stack = origin; //ebp
|
||||
*--stack = 0x10; // ds
|
||||
*--stack = 0x10; // fs
|
||||
*--stack = 0x10; // es
|
||||
*--stack = 0x10; // gs
|
||||
return stack;
|
||||
}
|
||||
|
||||
public static uint StartContext(string name, System.Threading.ThreadStart entry, Context_Type type)
|
||||
{
|
||||
Context context = new Context();
|
||||
context.type = type;
|
||||
context.tid = m_NextCID++;
|
||||
context.name = name;
|
||||
context.stacktop = GCImplementation.AllocNewObject(4096);
|
||||
context.esp = (uint)SetupStack((uint*)(context.stacktop + 4000));
|
||||
context.state = Thread_State.PAUSED;
|
||||
context.entry = entry;
|
||||
if (type == Context_Type.PROCESS)
|
||||
{
|
||||
context.parent = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
context.parent = m_CurrentContext.tid;
|
||||
}
|
||||
Context ctx = m_ContextList;
|
||||
while (ctx.next != null)
|
||||
{
|
||||
ctx = ctx.next;
|
||||
}
|
||||
ctx.next = context;
|
||||
return context.tid;
|
||||
}
|
||||
|
||||
public static uint StartContext(string name, System.Threading.ParameterizedThreadStart entry, Context_Type type, object param)
|
||||
{
|
||||
Context context = new Context();
|
||||
context.type = type;
|
||||
context.tid = m_NextCID++;
|
||||
context.name = name;
|
||||
context.stacktop = GCImplementation.AllocNewObject(4096);
|
||||
context.esp = (uint)SetupStack((uint*)(context.stacktop + 4000));
|
||||
context.state = Thread_State.ALIVE;
|
||||
context.paramentry = entry;
|
||||
context.param = param;
|
||||
if (type == Context_Type.PROCESS)
|
||||
{
|
||||
context.parent = 0;
|
||||
}
|
||||
else
|
||||
{
|
||||
context.parent = m_CurrentContext.tid;
|
||||
}
|
||||
Context ctx = m_ContextList;
|
||||
while (ctx.next != null)
|
||||
{
|
||||
ctx = ctx.next;
|
||||
}
|
||||
ctx.next = context;
|
||||
return context.tid;
|
||||
}
|
||||
}
|
||||
}
|
||||
102
source/Cosmos.Core/Processing/ProcessorScheduler.cs
Normal file
102
source/Cosmos.Core/Processing/ProcessorScheduler.cs
Normal file
|
|
@ -0,0 +1,102 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
using System.Text;
|
||||
using IL2CPU.API.Attribs;
|
||||
|
||||
namespace Cosmos.Core.Processing
|
||||
{
|
||||
public static unsafe class ProcessorScheduler
|
||||
{
|
||||
public static void Initialize()
|
||||
{
|
||||
var context = new ProcessContext.Context();
|
||||
context.type = ProcessContext.Context_Type.PROCESS;
|
||||
context.tid = ProcessContext.m_NextCID++;
|
||||
context.name = "Boot";
|
||||
context.esp = 0;
|
||||
context.stacktop = 0;
|
||||
context.state = ProcessContext.Thread_State.ALIVE;
|
||||
context.arg = 0;
|
||||
context.priority = 0;
|
||||
context.age = 0;
|
||||
context.parent = 0;
|
||||
ProcessContext.m_ContextList = context;
|
||||
ProcessContext.m_CurrentContext = context;
|
||||
|
||||
IOPort counter0 = new IOPort(0x40);
|
||||
IOPort cmd = new IOPort(0x43);
|
||||
|
||||
int divisor = 1193182 / 25;
|
||||
cmd.Byte = (0x06 | 0x30);
|
||||
counter0.Byte = (byte)divisor;
|
||||
counter0.Byte = (byte)(divisor >> 8);
|
||||
|
||||
IOPort pA1 = new IOPort(0xA1);
|
||||
IOPort p21 = new IOPort(0xA1);
|
||||
pA1.Byte = 0x00;
|
||||
p21.Byte = 0x00;
|
||||
}
|
||||
|
||||
public static void EntryPoint()
|
||||
{
|
||||
ProcessContext.m_CurrentContext.entry?.Invoke();
|
||||
ProcessContext.m_CurrentContext.paramentry?.Invoke(ProcessContext.m_CurrentContext.param);
|
||||
ProcessContext.m_CurrentContext.state = ProcessContext.Thread_State.DEAD;
|
||||
while (true) { } // remove from thread pool later
|
||||
}
|
||||
|
||||
public static int interruptCount;
|
||||
|
||||
public static void SwitchTask()
|
||||
{
|
||||
interruptCount++;
|
||||
if (ProcessContext.m_CurrentContext != null)
|
||||
{
|
||||
ProcessContext.Context ctx = ProcessContext.m_ContextList;
|
||||
ProcessContext.Context last = ctx;
|
||||
while (ctx != null)
|
||||
{
|
||||
if (ctx.state == ProcessContext.Thread_State.DEAD)
|
||||
{
|
||||
last.next = ctx.next;
|
||||
break;
|
||||
}
|
||||
last = ctx;
|
||||
ctx = ctx.next;
|
||||
}
|
||||
ctx = ProcessContext.m_ContextList;
|
||||
while (ctx != null)
|
||||
{
|
||||
if (ctx.state == ProcessContext.Thread_State.WAITING_SLEEP)
|
||||
{
|
||||
ctx.arg -= 1000 / 25;
|
||||
if (ctx.arg <= 0)
|
||||
{
|
||||
ctx.state = ProcessContext.Thread_State.ALIVE;
|
||||
}
|
||||
}
|
||||
ctx.age++;
|
||||
ctx = ctx.next;
|
||||
}
|
||||
ProcessContext.m_CurrentContext.esp = INTs.mStackContext;
|
||||
tryagain:;
|
||||
if (ProcessContext.m_CurrentContext.next != null)
|
||||
{
|
||||
ProcessContext.m_CurrentContext = ProcessContext.m_CurrentContext.next;
|
||||
}
|
||||
else
|
||||
{
|
||||
ProcessContext.m_CurrentContext = ProcessContext.m_ContextList;
|
||||
}
|
||||
if (ProcessContext.m_CurrentContext.state != ProcessContext.Thread_State.ALIVE)
|
||||
{
|
||||
goto tryagain;
|
||||
}
|
||||
ProcessContext.m_CurrentContext.age = ProcessContext.m_CurrentContext.priority;
|
||||
INTs.mStackContext = ProcessContext.m_CurrentContext.esp;
|
||||
}
|
||||
Global.PIC.EoiMaster();
|
||||
Global.PIC.EoiSlave();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -13,7 +13,7 @@ namespace Cosmos.Core_Asm
|
|||
{
|
||||
public class CPUUpdateIDTAsm : AssemblerMethod
|
||||
{
|
||||
private static MethodBase GetMethodDef(Assembly aAssembly, string aType, string aMethodName, bool aErrorWhenNotFound)
|
||||
public static MethodBase GetMethodDef(Assembly aAssembly, string aType, string aMethodName, bool aErrorWhenNotFound)
|
||||
{
|
||||
Type xType = aAssembly.GetType(aType, false);
|
||||
if (xType != null)
|
||||
|
|
@ -79,36 +79,71 @@ namespace Cosmos.Core_Asm
|
|||
XS.Push(0);
|
||||
}
|
||||
XS.Push((uint)j);
|
||||
XS.PushAllRegisters();
|
||||
|
||||
XS.Sub(ESP, 4);
|
||||
XS.Set(EAX, ESP); // preserve old stack address for passing to interrupt handler
|
||||
|
||||
// store floating point data
|
||||
XS.And(ESP, 0xfffffff0); // fxsave needs to be 16-byte alligned
|
||||
XS.Sub(ESP, 512); // fxsave needs 512 bytes
|
||||
XS.SSE.FXSave(ESP, isIndirect: true); // save the registers
|
||||
XS.Set(EAX, ESP, destinationIsIndirect: true);
|
||||
|
||||
XS.Push(EAX); //
|
||||
XS.Push(EAX); // pass old stack address (pointer to InterruptContext struct) to the interrupt handler
|
||||
|
||||
XS.JumpToSegment(8, "__ISR_Handler_" + j.ToString("X2") + "_SetCS");
|
||||
XS.Label("__ISR_Handler_" + j.ToString("X2") + "_SetCS");
|
||||
MethodBase xHandler = GetInterruptHandler((byte)j);
|
||||
if (xHandler == null)
|
||||
if (j != 0x20)
|
||||
{
|
||||
xHandler = GetMethodDef(typeof(Cosmos.Core.INTs).Assembly, typeof(Cosmos.Core.INTs).FullName, "HandleInterrupt_Default", true);
|
||||
XS.PushAllRegisters();
|
||||
|
||||
XS.Sub(ESP, 4);
|
||||
XS.Set(EAX, ESP); // preserve old stack address for passing to interrupt handler
|
||||
|
||||
// store floating point data
|
||||
XS.And(ESP, 0xfffffff0); // fxsave needs to be 16-byte alligned
|
||||
XS.Sub(ESP, 512); // fxsave needs 512 bytes
|
||||
XS.SSE.FXSave(ESP, isIndirect: true); // save the registers
|
||||
XS.Set(EAX, ESP, destinationIsIndirect: true);
|
||||
|
||||
XS.Push(EAX); //
|
||||
XS.Push(EAX); // pass old stack address (pointer to InterruptContext struct) to the interrupt handler
|
||||
|
||||
XS.JumpToSegment(8, "__ISR_Handler_" + j.ToString("X2") + "_SetCS");
|
||||
XS.Label("__ISR_Handler_" + j.ToString("X2") + "_SetCS");
|
||||
MethodBase xHandler = GetInterruptHandler((byte)j);
|
||||
if (xHandler == null)
|
||||
{
|
||||
xHandler = GetMethodDef(typeof(Cosmos.Core.INTs).Assembly, typeof(Cosmos.Core.INTs).FullName, "HandleInterrupt_Default", true);
|
||||
}
|
||||
XS.Call(LabelName.Get(xHandler));
|
||||
XS.Pop(EAX);
|
||||
XS.SSE.FXRestore(ESP, isIndirect: true);
|
||||
|
||||
XS.Set(ESP, EAX); // this restores the stack for the FX stuff, except the pointer to the FX data
|
||||
XS.Add(ESP, 4); // "pop" the pointer
|
||||
|
||||
XS.PopAllRegisters();
|
||||
}
|
||||
XS.Call(LabelName.Get(xHandler));
|
||||
XS.Pop(EAX);
|
||||
XS.SSE.FXRestore(ESP, isIndirect: true);
|
||||
|
||||
XS.Set(ESP, EAX); // this restores the stack for the FX stuff, except the pointer to the FX data
|
||||
XS.Add(ESP, 4); // "pop" the pointer
|
||||
|
||||
XS.PopAllRegisters();
|
||||
|
||||
else
|
||||
{
|
||||
new LiteralAssemblerCode("pushad");
|
||||
new LiteralAssemblerCode("mov eax, ds");
|
||||
new LiteralAssemblerCode("push eax");
|
||||
new LiteralAssemblerCode("mov eax, es");
|
||||
new LiteralAssemblerCode("push eax");
|
||||
new LiteralAssemblerCode("mov eax, fs");
|
||||
new LiteralAssemblerCode("push eax");
|
||||
new LiteralAssemblerCode("mov eax, gs");
|
||||
new LiteralAssemblerCode("push eax");
|
||||
new LiteralAssemblerCode("mov ax, 0x10");
|
||||
new LiteralAssemblerCode("mov ds, ax");
|
||||
new LiteralAssemblerCode("mov es, ax");
|
||||
new LiteralAssemblerCode("mov fs, ax");
|
||||
new LiteralAssemblerCode("mov gs, ax");
|
||||
new LiteralAssemblerCode("mov eax, esp");
|
||||
XS.Set("static_field__Cosmos_Core_INTs_mStackContext", EAX, destinationIsIndirect: true);
|
||||
XS.Call(LabelName.Get(GetMethodDef(typeof(Cosmos.Core.Processing.ProcessorScheduler).Assembly, typeof(Cosmos.Core.Processing.ProcessorScheduler).FullName, "SwitchTask", true)));
|
||||
XS.Set(EAX, "static_field__Cosmos_Core_INTs_mStackContext", sourceIsIndirect: true);
|
||||
new LiteralAssemblerCode("mov esp, eax");
|
||||
new LiteralAssemblerCode("pop eax");
|
||||
new LiteralAssemblerCode("mov gs, eax");
|
||||
new LiteralAssemblerCode("pop eax");
|
||||
new LiteralAssemblerCode("mov fs, eax");
|
||||
new LiteralAssemblerCode("pop eax");
|
||||
new LiteralAssemblerCode("mov es, eax");
|
||||
new LiteralAssemblerCode("pop eax");
|
||||
new LiteralAssemblerCode("mov ds, eax");
|
||||
new LiteralAssemblerCode("popad");
|
||||
}
|
||||
|
||||
XS.Add(ESP, 8);
|
||||
XS.Label("__ISR_Handler_" + j.ToString("X2") + "_END");
|
||||
XS.InterruptReturn();
|
||||
|
|
|
|||
|
|
@ -4,7 +4,7 @@ using IL2CPU.API.Attribs;
|
|||
namespace Cosmos.Core_Asm
|
||||
{
|
||||
[Plug(Target = typeof(Delegate), Inheritable = true)]
|
||||
public static class DelegateImpl
|
||||
public static unsafe class DelegateImpl
|
||||
{
|
||||
[PlugMethod(Assembler = typeof(DelegateCtorAsm), IsWildcard = true, WildcardMatchParameters = true)]
|
||||
public static void Ctor(Delegate aThis, object aTarget, IntPtr aMethod)
|
||||
|
|
@ -28,5 +28,10 @@ namespace Cosmos.Core_Asm
|
|||
{
|
||||
throw new NotImplementedException();
|
||||
}
|
||||
|
||||
public static int GetHashCode(Delegate aThis, [FieldAccess(Name = "System.IntPtr System.Delegate._methodPtr")] ref IntPtr aAddress)
|
||||
{
|
||||
return (int)aAddress.ToPointer();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
|
|||
36
source/Cosmos.Core_Asm/MutexImpl.cs
Normal file
36
source/Cosmos.Core_Asm/MutexImpl.cs
Normal file
|
|
@ -0,0 +1,36 @@
|
|||
using Cosmos.Core.Processing;
|
||||
using IL2CPU.API.Attribs;
|
||||
using XSharp;
|
||||
using XSharp.Assembler;
|
||||
|
||||
namespace Cosmos.Core_Asm
|
||||
{
|
||||
[Plug(Target = typeof(Mutex))]
|
||||
public static unsafe class MutexImpl
|
||||
{
|
||||
[PlugMethod(Assembler = typeof(MutexLockASM))]
|
||||
public static void MutexLock(int* mtx) { }
|
||||
}
|
||||
|
||||
public class MutexLockASM : AssemblerMethod
|
||||
{
|
||||
public override void AssembleNew(Assembler aAssembler, object aMethodInfo)
|
||||
{
|
||||
new LiteralAssemblerCode("lock_asm:");
|
||||
new LiteralAssemblerCode("mov eax, [esp + 8]");
|
||||
new LiteralAssemblerCode("mov ebx, 0");
|
||||
new LiteralAssemblerCode("lock bts[eax], ebx");
|
||||
new LiteralAssemblerCode("jc.spin_wait");
|
||||
new LiteralAssemblerCode("mov ebx, 1");
|
||||
new LiteralAssemblerCode("mov dword[eax], ebx");
|
||||
new LiteralAssemblerCode("jmp .finished");
|
||||
new LiteralAssemblerCode(".spin_wait:");
|
||||
new LiteralAssemblerCode("mov ebx, 1");
|
||||
new LiteralAssemblerCode("test dword[eax], ebx");
|
||||
new LiteralAssemblerCode("pause");
|
||||
new LiteralAssemblerCode("jnz.spin_wait");
|
||||
new LiteralAssemblerCode("jmp lock_asm");
|
||||
new LiteralAssemblerCode(".finished");
|
||||
}
|
||||
}
|
||||
}
|
||||
40
source/Cosmos.Core_Asm/ObjUtilitiesImpl.cs
Normal file
40
source/Cosmos.Core_Asm/ObjUtilitiesImpl.cs
Normal file
|
|
@ -0,0 +1,40 @@
|
|||
using Cosmos.Core;
|
||||
using IL2CPU.API;
|
||||
using IL2CPU.API.Attribs;
|
||||
using System;
|
||||
using XSharp;
|
||||
using XSharp.Assembler;
|
||||
|
||||
namespace Cosmos.Core_Asm
|
||||
{
|
||||
[Plug(Target = typeof(ObjUtilities))]
|
||||
public static unsafe class ObjUtilitiesImpl
|
||||
{
|
||||
[PlugMethod(Assembler = typeof(ObjUtilitiesGetPointer))]
|
||||
public static uint GetPointer(Delegate aVal) { return 0; }
|
||||
|
||||
[PlugMethod(Assembler = typeof(ObjUtilitiesGetPointer))]
|
||||
public static uint GetPointer(Object aVal) { return 0; }
|
||||
|
||||
[PlugMethod(Assembler = typeof(ObjUtilitiesGetEntry))]
|
||||
public static uint GetEntryPoint() { return 0; }
|
||||
}
|
||||
|
||||
public class ObjUtilitiesGetPointer : AssemblerMethod
|
||||
{
|
||||
public override void AssembleNew(Assembler aAssembler, object aMethodInfo)
|
||||
{
|
||||
XS.Set(XSRegisters.EAX, XSRegisters.EBP, sourceDisplacement: 0x8);
|
||||
XS.Push(XSRegisters.EAX);
|
||||
}
|
||||
}
|
||||
|
||||
public class ObjUtilitiesGetEntry : AssemblerMethod
|
||||
{
|
||||
public override void AssembleNew(Assembler aAssembler, object aMethodInfo)
|
||||
{
|
||||
XS.Set(XSRegisters.EAX, LabelName.Get(CPUUpdateIDTAsm.GetMethodDef(typeof(Cosmos.Core.Processing.ProcessorScheduler).Assembly, typeof(Cosmos.Core.Processing.ProcessorScheduler).FullName, "EntryPoint", true)));
|
||||
XS.Push(XSRegisters.EAX);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
|
@ -6,7 +6,7 @@ using IL2CPU.API.Attribs;
|
|||
namespace Cosmos.Core_Plugs.System
|
||||
{
|
||||
[Plug(Target = typeof(Delegate))]
|
||||
public static class DelegateImpl
|
||||
public static unsafe class DelegateImpl
|
||||
{
|
||||
[PlugMethod(Signature = "System_Boolean__System_Delegate_Equals_System_Object_")]
|
||||
public static bool Equals(Delegate aThis, object aThat)
|
||||
|
|
@ -24,6 +24,11 @@ namespace Cosmos.Core_Plugs.System
|
|||
|
||||
return xTypeA == xTypeB;
|
||||
}
|
||||
|
||||
public static int GetHashCode(Delegate aThis, [FieldAccess(Name = "System.IntPtr System.Delegate._methodPtr")] ref IntPtr aAddress)
|
||||
{
|
||||
return (int)aAddress.ToPointer();
|
||||
}
|
||||
}
|
||||
|
||||
[Plug(Target = typeof(Delegate), Inheritable = true)]
|
||||
|
|
|
|||
|
|
@ -1,3 +1,4 @@
|
|||
using System;
|
||||
using System.Threading;
|
||||
using IL2CPU.API.Attribs;
|
||||
|
||||
|
|
@ -16,6 +17,11 @@ namespace Cosmos.Core_Plugs.System.Threading
|
|||
|
||||
}
|
||||
|
||||
public static void Ctor(ThreadStart aThis, ThreadStart aEntry)
|
||||
{
|
||||
Console.WriteLine("Thread started");
|
||||
}
|
||||
|
||||
// public static void SleepInternal(int ms)
|
||||
// {
|
||||
// // Implementation of http://referencesource.microsoft.com/#mscorlib/system/threading/thread.cs,6a577476abf2f437,references
|
||||
|
|
|
|||
|
|
@ -1,6 +1,6 @@
|
|||
using System;
|
||||
using System.Collections.Generic;
|
||||
|
||||
using System.Threading;
|
||||
using Cosmos.Core;
|
||||
using Cosmos.Debug.Kernel;
|
||||
using Cosmos.HAL.BlockDevice;
|
||||
|
|
@ -63,6 +63,10 @@ namespace Cosmos.HAL
|
|||
AHCI.InitDriver();
|
||||
//EHCI.InitDriver();
|
||||
|
||||
Console.WriteLine("Starting Processor Scheduler");
|
||||
mDebugger.Send("Processor Scheduler");
|
||||
Core.Processing.ProcessorScheduler.Initialize();
|
||||
|
||||
mDebugger.Send("Done initializing Cosmos.HAL.Global");
|
||||
|
||||
}
|
||||
|
|
@ -80,6 +84,16 @@ namespace Cosmos.HAL
|
|||
/// </summary>
|
||||
public static bool InterruptsEnabled => CPU.mInterruptsEnabled;
|
||||
|
||||
public static uint SpawnThread(ThreadStart aStart)
|
||||
{
|
||||
return Core.Processing.ProcessContext.StartContext("", aStart, Core.Processing.ProcessContext.Context_Type.THREAD);
|
||||
}
|
||||
|
||||
public static uint SpawnThread(ParameterizedThreadStart aStart, object param)
|
||||
{
|
||||
return Core.Processing.ProcessContext.StartContext("", aStart, Core.Processing.ProcessContext.Context_Type.THREAD, param);
|
||||
}
|
||||
|
||||
/// <summary>
|
||||
/// Get keyboard devices.
|
||||
/// </summary>
|
||||
|
|
|
|||
45
source/Cosmos.System2/Thread.cs
Normal file
45
source/Cosmos.System2/Thread.cs
Normal file
|
|
@ -0,0 +1,45 @@
|
|||
using st = System.Threading;
|
||||
|
||||
namespace Cosmos.System
|
||||
{
|
||||
public class Thread
|
||||
{
|
||||
public uint ThreadID;
|
||||
private Cosmos.Core.Processing.ProcessContext.Context Data;
|
||||
|
||||
public Thread(st.ThreadStart start)
|
||||
{
|
||||
ThreadID = Cosmos.HAL.Global.SpawnThread(start);
|
||||
ThreadFinalSetup();
|
||||
}
|
||||
|
||||
public Thread(st.ParameterizedThreadStart start, object param)
|
||||
{
|
||||
ThreadID = Cosmos.HAL.Global.SpawnThread(start, param);
|
||||
ThreadFinalSetup();
|
||||
}
|
||||
|
||||
private void ThreadFinalSetup()
|
||||
{
|
||||
Data = Cosmos.Core.Processing.ProcessContext.GetContext(ThreadID);
|
||||
Data.state = Core.Processing.ProcessContext.Thread_State.PAUSED;
|
||||
}
|
||||
|
||||
public void Start()
|
||||
{
|
||||
Data.state = Core.Processing.ProcessContext.Thread_State.ALIVE;
|
||||
}
|
||||
|
||||
public void Stop()
|
||||
{
|
||||
Data.state = Core.Processing.ProcessContext.Thread_State.PAUSED;
|
||||
}
|
||||
|
||||
public static void Sleep(int ms)
|
||||
{
|
||||
Cosmos.Core.Processing.ProcessContext.m_CurrentContext.arg = ms;
|
||||
Cosmos.Core.Processing.ProcessContext.m_CurrentContext.state = Core.Processing.ProcessContext.Thread_State.WAITING_SLEEP;
|
||||
while (Cosmos.Core.Processing.ProcessContext.m_CurrentContext.state == Core.Processing.ProcessContext.Thread_State.WAITING_SLEEP) { }
|
||||
}
|
||||
}
|
||||
}
|
||||
Loading…
Reference in a new issue