예제 #1
0
파일: CPUImpl.cs 프로젝트: nstone101/Cosmos
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.ClrDirFlag();
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EDI, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 0xC
     };                                                                                                                                                             //address
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.ECX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 0x8
     };                                                                                                                                                             //length
     // set EAX to value of fill (zero)
     new CPUx86.Xor {
         DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EAX
     };
     new CPUx86.ShiftRight {
         DestinationReg = CPUx86.Registers.ECX, SourceValue = 1
     };
     new CPUx86.ConditionalJump {
         Condition = CPUx86.ConditionalTestEnum.NotBelow, DestinationLabel = ".step2"
     };
     new CPUx86.StoreByteInString();
     new CPUAll.Label(".step2");
     new CPUx86.ShiftRight {
         DestinationReg = CPUx86.Registers.ECX, SourceValue = 1
     };
     new CPUx86.ConditionalJump {
         Condition = CPUx86.ConditionalTestEnum.NotBelow, DestinationLabel = ".step3"
     };
     new CPUx86.StoreWordInString();
     new CPUAll.Label(".step3");
     new CPUx86.Stos {
         Size = 32, Prefixes = CPUx86.InstructionPrefixes.Repeat
     };
 }
예제 #2
0
        /*public static void BlockCopy(
         *			Array src, [ebp + 24]
         *			int srcOffset, [ebp + 20]
         *			Array dst, [ebp + 16]
         *			int dstOffset, [ebp + 12]
         *			int count); [ebp + 8]
         */
        public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
        {
            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.ESI, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 24
            };
            new CPUx86.Add {
                DestinationReg = CPUx86.Registers.ESI, SourceValue = 16
            };
            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 20
            };
            new CPUx86.Add {
                DestinationReg = CPUx86.Registers.ESI, SourceReg = CPUx86.Registers.EAX
            };

            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.EDI, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 16
            };
            new CPUx86.Add {
                DestinationReg = CPUx86.Registers.EDI, SourceValue = 16
            };
            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 12
            };
            new CPUx86.Add {
                DestinationReg = CPUx86.Registers.EDI, SourceReg = CPUx86.Registers.EAX
            };

            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.ECX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 8
            };
            new CPUx86.Movs {
                Size = 8, Prefixes = CPUx86.InstructionPrefixes.Repeat
            };
        }
예제 #3
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     XS.Set(XSRegisters.EAX, "MultiBootInfo_Memory_High", sourceIsIndirect: true);
     XS.Xor(XSRegisters.EDX, XSRegisters.EDX);
     XS.Set(XSRegisters.ECX, 1024);
     XS.Divide(XSRegisters.ECX);
     XS.Add(XSRegisters.EAX, 1);
     XS.Push(XSRegisters.EAX);
 }
예제 #4
0
파일: IOPortImpl.cs 프로젝트: zer09/Cosmos
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     //TODO: This is a lot of work to write to a single port.
     // We need to have some kind of inline ASM option that can
     // emit a single out instruction
     XS.Set(XSRegisters.EDX, XSRegisters.EBP, sourceDisplacement: 0x0C);
     XS.Set(XSRegisters.EAX, XSRegisters.EBP, sourceDisplacement: 0x08);
     XS.WriteToPortDX(XSRegisters.AL);
 }
예제 #5
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EDX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 0x0C
     };
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 0x08
     };
     new CPUx86.OutToDX {
         DestinationReg = CPUx86.Registers.EAX
     };
 }
예제 #6
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     //TODO: This is a lot of work to write to a single port.
     // We need to have some kind of inline ASM option that can
     // emit a single out instruction
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EDX, SourceReg = CPUx86.Registers.EBP, SourceDisplacement = 0x0C, SourceIsIndirect = true
     };
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EBP, SourceDisplacement = 0x08, SourceIsIndirect = true
     };
     new CPUx86.OutToDX {
         DestinationReg = CPUx86.Registers.AL
     };
 }
예제 #7
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.x87.FloatLoad {
         DestinationReg = CPUx86.Registers.EBP, Size = 64, DestinationIsIndirect = true, DestinationDisplacement = 8
     };
     new CPUx86.x87.FloatSqrt {
     };
     // reservate 8 byte for returntype double on stack
     new CPUx86.Sub {
         DestinationReg = CPUx86.Registers.ESP, SourceValue = 8
     };
     // write double value to this reservation
     new CPUx86.x87.FloatStoreAndPop {
         DestinationReg = CPUx86.Registers.ESP, Size = 64, DestinationIsIndirect = true
     };
     // after this is the result popped
 }
예제 #8
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EDX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 0x08
     };
     //TODO: Do we need to clear rest of EAX first?
     //    MTW: technically not, as in other places, it _should_ be working with AL too..
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EAX, SourceValue = 0
     };
     new CPUx86.InFromDX {
         DestinationReg = CPUx86.Registers.AL
     };
     new CPUx86.Push {
         DestinationReg = CPUx86.Registers.EAX
     };
 }
예제 #9
0
파일: CPUImpl.cs 프로젝트: nstone101/Cosmos
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.EAX, SourceRef = CPUAll.ElementReference.New("MultiBootInfo_Memory_High"), SourceIsIndirect = true
     };
     new CPUx86.Xor {
         DestinationReg = CPUx86.Registers.EDX, SourceReg = CPUx86.Registers.EDX
     };
     new CPUx86.Mov {
         DestinationReg = CPUx86.Registers.ECX, SourceValue = 1024
     };
     new CPUx86.Divide {
         DestinationReg = CPUx86.Registers.ECX
     };
     new CPUx86.Add {
         DestinationReg = CPUx86.Registers.EAX, SourceValue = 1
     };
     new CPUx86.Push {
         DestinationReg = CPUx86.Registers.EAX
     };
 }
예제 #10
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     XS.EnableInterrupts();
 }
예제 #11
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     XS.ClearInterruptFlag();
 }
예제 #12
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     XS.Halt();
 }
예제 #13
0
파일: CPUImpl.cs 프로젝트: nstone101/Cosmos
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.Push {
         DestinationRef = CPUAll.ElementReference.New("_end_code")
     };
 }
예제 #14
0
파일: CPUImpl.cs 프로젝트: nstone101/Cosmos
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.x87.FloatInit();
 }
예제 #15
0
        public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
        {
            // IDT is already initialized but just for base hooks, and asm only.
            // ie Int 1, 3 and GPF
            // This routine updates the IDT now that we have C# running to allow C# hooks to handle
            // the other INTs

            // We are updating the IDT, disable interrupts
            new CPUx86.ClearInterruptFlag();

            for (int i = 0; i < 256; i++)
            {
                // These are already mapped, don't remap them.
                // Maybe in the future we can look at ones that are present
                // and skip them, but some we may want to overwrite anyways.
                if (i == 1 || i == 3)
                {
                    continue;
                }

                new CPUx86.Mov {
                    DestinationReg = CPUx86.Registers.EAX, SourceRef = CPUAll.ElementReference.New("__ISR_Handler_" + i.ToString("X2"))
                };
                new CPUx86.Mov {
                    DestinationRef        = CPUAll.ElementReference.New("_NATIVE_IDT_Contents"),
                    DestinationIsIndirect = true, DestinationDisplacement = ((i * 8) + 0),
                    SourceReg             = CPUx86.Registers.AL
                };
                new CPUx86.Mov {
                    DestinationRef        = CPUAll.ElementReference.New("_NATIVE_IDT_Contents"),
                    DestinationIsIndirect = true, DestinationDisplacement = ((i * 8) + 1),
                    SourceReg             = CPUx86.Registers.AH
                };
                new CPUx86.Mov {
                    DestinationRef        = CPUAll.ElementReference.New("_NATIVE_IDT_Contents"),
                    DestinationIsIndirect = true, DestinationDisplacement = ((i * 8) + 2),
                    SourceValue           = 0x8,
                    Size = 8
                };

                new CPUx86.Mov {
                    DestinationRef          = CPUAll.ElementReference.New("_NATIVE_IDT_Contents"),
                    DestinationIsIndirect   = true,
                    DestinationDisplacement = ((i * 8) + 5),
                    SourceValue             = 0x8E,
                    Size = 8
                };
                new CPUx86.ShiftRight {
                    DestinationReg = CPUx86.Registers.EAX, SourceValue = 16
                };
                new CPUx86.Mov {
                    DestinationRef          = CPUAll.ElementReference.New("_NATIVE_IDT_Contents"),
                    DestinationIsIndirect   = true,
                    DestinationDisplacement = ((i * 8) + 6),
                    SourceReg = CPUx86.Registers.AL
                };
                new CPUx86.Mov {
                    DestinationRef          = CPUAll.ElementReference.New("_NATIVE_IDT_Contents"),
                    DestinationIsIndirect   = true,
                    DestinationDisplacement = ((i * 8) + 7),
                    SourceReg = CPUx86.Registers.AH
                };
            }

            new CPUx86.Jump {
                DestinationLabel = "__AFTER__ALL__ISR__HANDLER__STUBS__"
            };
            var xInterruptsWithParam = new int[] { 8, 10, 11, 12, 13, 14 };

            for (int j = 0; j < 256; j++)
            {
                new CPUAll.Label("__ISR_Handler_" + j.ToString("X2"));
                new CPUx86.Call {
                    DestinationLabel = "__INTERRUPT_OCCURRED__"
                };

                if (Array.IndexOf(xInterruptsWithParam, j) == -1)
                {
                    new CPUx86.Push {
                        DestinationValue = 0
                    };
                }
                new CPUx86.Push {
                    DestinationValue = (uint)j
                };
                new CPUx86.Pushad();

                new CPUx86.Sub {
                    DestinationReg = CPUx86.Registers.ESP, SourceValue = 4
                };
                new CPUx86.Mov {
                    DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.ESP
                };                                                                                  // preserve old stack address for passing to interrupt handler

                // store floating point data
                new CPUx86.And {
                    DestinationReg = CPUx86.Registers.ESP, SourceValue = 0xfffffff0
                };                                                                          // fxsave needs to be 16-byte alligned
                new CPUx86.Sub {
                    DestinationReg = CPUx86.Registers.ESP, SourceValue = 512
                };                                                                   // fxsave needs 512 bytes
                new CPUx86.x87.FXSave {
                    DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true
                };                                                                                     // save the registers
                new CPUx86.Mov {
                    DestinationReg = CPUx86.Registers.EAX, DestinationIsIndirect = true, SourceReg = CPUx86.Registers.ESP
                };

                new CPUx86.Push {
                    DestinationReg = CPUx86.Registers.EAX
                };                                                 //
                new CPUx86.Push {
                    DestinationReg = CPUx86.Registers.EAX
                };                                                 // pass old stack address (pointer to InterruptContext struct) to the interrupt handler
                //new CPUx86.Move("eax",
                //                "esp");
                //new CPUx86.Push("eax");
                new CPUx86.JumpToSegment {
                    Segment = 8, DestinationLabel = "__ISR_Handler_" + j.ToString("X2") + "_SetCS"
                };
                new CPUAll.Label("__ISR_Handler_" + j.ToString("X2") + "_SetCS");
                MethodBase xHandler = GetInterruptHandler((byte)j);
                if (xHandler == null)
                {
                    xHandler = GetMethodDef(typeof(INTs).Assembly, typeof(INTs).FullName, "HandleInterrupt_Default", true);
                }
                new CPUx86.Call {
                    DestinationLabel = CPUAll.LabelName.Get(xHandler)
                };
                new CPUx86.Pop {
                    DestinationReg = CPUx86.Registers.EAX
                };
                new CPUx86.x87.FXStore {
                    DestinationReg = CPUx86.Registers.ESP, DestinationIsIndirect = true
                };

                new CPUx86.Mov {
                    DestinationReg = CPUx86.Registers.ESP, SourceReg = CPUx86.Registers.EAX
                };                                                                                  // this restores the stack for the FX stuff, except the pointer to the FX data
                new CPUx86.Add {
                    DestinationReg = CPUx86.Registers.ESP, SourceValue = 4
                };                                                                 // "pop" the pointer

                new CPUx86.Popad();

                new CPUx86.Add {
                    DestinationReg = CPUx86.Registers.ESP, SourceValue = 8
                };
                new CPUAll.Label("__ISR_Handler_" + j.ToString("X2") + "_END");
                new CPUx86.IRET();
            }
            new CPUAll.Label("__INTERRUPT_OCCURRED__");
            new CPUx86.Return();
            new CPUAll.Label("__AFTER__ALL__ISR__HANDLER__STUBS__");
            new CPUx86.Noop();
            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.EAX, SourceReg = CPUx86.Registers.EBP, SourceIsIndirect = true, SourceDisplacement = 8
            };
            new CPUx86.Compare {
                DestinationReg = CPUx86.Registers.EAX, SourceValue = 0
            };
            new CPUx86.ConditionalJump {
                Condition = CPUx86.ConditionalTestEnum.Zero, DestinationLabel = ".__AFTER_ENABLE_INTERRUPTS"
            };

            // reload interrupt list
            new CPUx86.Mov {
                DestinationReg = CPUx86.Registers.EAX, SourceRef = Cosmos.Assembler.ElementReference.New("_NATIVE_IDT_Pointer")
            };
            new CPUx86.Mov {
                DestinationRef = CPUAll.ElementReference.New("static_field__Cosmos_Core_CPU_mInterruptsEnabled"), DestinationIsIndirect = true, SourceValue = 1
            };
            new CPUx86.Lidt {
                DestinationReg = CPUx86.Registers.EAX, DestinationIsIndirect = true
            };
            // Reenable interrupts
            new CPUx86.Sti();

            new CPUAll.Label(".__AFTER_ENABLE_INTERRUPTS");
        }
예제 #16
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     XS.FPU.FloatInit();
 }
예제 #17
0
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     XS.SSE.SSEInit();
     //new CPUx86.SSE.SSEInit();
 }
예제 #18
0
파일: CPUImpl.cs 프로젝트: nstone101/Cosmos
 public override void AssembleNew(Cosmos.Assembler.Assembler aAssembler, object aMethodInfo)
 {
     new CPUx86.Sti();
 }