コード例 #1
0
        public ASyncRAMInterfaceRW1Low(RAM ram)
        {
            this.RAM = ram;

            Read_IFace  = CreateInputface <ReadCommand>();
            Write_IFace = CreateInputface <WriteCommand>();

            Read_OFace = CreateAsyncOutputface <ushort>();

            PreviousRead = new ReadCommand()
            {
                Enabled = false,
                Address = -1
            };

            Read_OFace.SetFunc(() =>
            {
                ReadCommand rCmd = Read_IFace.Get();
                uint res;
                if (rCmd.Enabled)
                {
                    this.RAM.LoadWord(
                        (uint)rCmd.Address, out res,
                        rCmd.Address != PreviousRead.Address ? rCmd.AccessType : EnumMemorymAccessType.No, 2, 1);
                }
                else
                {
                    res = 0;
                }
                return((ushort)(res & 0xFFFF));
            });
        }
コード例 #2
0
        public Alu()
        {
            OperandA_IFace = CreateInputface <uint>();
            OperandB_IFace = CreateInputface <uint>();
            OpFlag_IFace   = CreateInputface <bool>();
            CondFlag_IFace = CreateInputface <byte>();

            OpResult_OFace   = CreateAsyncOutputface <uint>();
            CondResult_OFace = CreateAsyncOutputface <bool>();

            OpResult_OFace.SetFunc(() =>
            {
                bool opcode = OpFlag_IFace;
                if (!opcode)
                { //subneg
                    uint res;
                    bool cond;
                    ComputeSubneg(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(res);
                }
                else
                { //subnegx
                    uint res;
                    bool cond;
                    ComputeSubnegX(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(res);
                }
            });
            CondResult_OFace.SetFunc(() =>
            {
                byte opcode = CondFlag_IFace;
                if ((opcode & 1) != 0)
                { //!cout
                    ulong opa = (ulong)OperandA_IFace;
                    ulong opb = (ulong)OperandB_IFace;
                    ulong sub = opb - opa;

                    return(!((sub & 0x100000000) != 0)); //has no carry (carry bit == 0)
                }
                else if ((opcode & 4) != 0)
                { //subneg
                    uint res;
                    bool cond;
                    ComputeSubneg(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(cond);
                }
                else
                { //subnegx
                    uint res;
                    bool cond;
                    ComputeSubnegX(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(cond);
                }
            });
        }
コード例 #3
0
        public ApplyStage()
        {
            MemOp_IFace     = CreateInputface <bool>();
            MemRw_IFace     = CreateInputface <bool>();
            AluRes_IFace    = CreateInputface <uint>();
            RegRdataC_IFace = CreateInputface <uint>();
            RegNoC_IFace    = CreateInputface <byte>();
            ValidAS_IFace   = CreateInputface <bool>();
            MemRdata_IFace  = CreateInputface <uint>();

            MemoryStallRequest_OFace = CreateAsyncOutputface <bool>();
            MemEn_OFace    = CreateAsyncOutputface <bool>();
            MemAddr_OFace  = CreateAsyncOutputface <uint>();
            MemWen_OFace   = CreateAsyncOutputface <bool>();
            MemWdata_OFace = CreateAsyncOutputface <uint>();
            RegWen_OFace   = CreateAsyncOutputface <bool>();
            RegWdata_OFace = CreateAsyncOutputface <uint>();
            RegWno_OFace   = CreateAsyncOutputface <byte>();

            memReaded = CreateSyncOutputface <bool>(false);

            MemoryStallRequest_OFace.SetFunc(() =>
            {
                return(ValidAS_IFace && !memReaded.Value && MemOp_IFace);
            });
            MemEn_OFace.SetFunc(() =>
            {
                return(!memReaded.Value);
            });
            MemAddr_OFace.SetFunc(() =>
            {
                return(AluRes_IFace);// >> 2;
            });
            MemWen_OFace.SetFunc(() =>
            {
                return(!memReaded.Value && MemRw_IFace);
            });
            MemWdata_OFace.SetFunc(() =>
            {
                return(RegRdataC_IFace);
            });
            RegWen_OFace.SetFunc(() =>
            {
                return(ValidAS_IFace && (!MemOp_IFace || (!MemRw_IFace && !memReaded.Value)));
            });
            RegWdata_OFace.SetFunc(() =>
            {
                return(MemOp_IFace ? MemRdata_IFace : AluRes_IFace);
            });
            RegWno_OFace.SetFunc(() =>
            {
                return(RegNoC_IFace);
            });
        }
コード例 #4
0
        public SyncRAMInterfaceRW1R1(RAM ram)
        {
            this.RAM = ram;

            ReadCmd1_IFace = CreateInputface <ReadCommand>();
            ReadCmd2_IFace = CreateInputface <ReadCommand>();
            WriteCmd_IFace = CreateInputface <WriteCommand>();

            ReadValue1_OFace = CreateSyncOutputface <uint>();
            ReadValue2_OFace = CreateSyncOutputface <uint>();
        }
コード例 #5
0
ファイル: Alu.cs プロジェクト: Hara-Laboratory/oiscsim
        public Alu()
        {
            OperandA_IFace = CreateInputface <uint>();
            OperandB_IFace = CreateInputface <uint>();
            OperandD_IFace = CreateInputface <uint>();

            AluResult_OFace  = CreateAsyncOutputface <uint>();
            BranchCond_OFace = CreateAsyncOutputface <bool>();

            AluResult_OFace.SetFunc(() =>
            {
                bool opcode = ((OperandD_IFace & 0x80000000) != 0);
                if (!opcode)
                { //subneg
                    uint res;
                    bool cond;
                    ComputeSubneg(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(res);
                }
                else
                { //subnegx
                    uint res;
                    bool cond;
                    ComputeSubnegX(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(res);
                }
            });
            BranchCond_OFace.SetFunc(() =>
            {
                bool opcode = ((OperandD_IFace & 0x80000000) != 0);
                if (!opcode)
                { //subneg
                    uint res;
                    bool cond;
                    ComputeSubneg(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(cond);
                }
                else
                { //subnegx
                    uint res;
                    bool cond;
                    ComputeSubnegX(OperandA_IFace, OperandB_IFace, out res, out cond);

                    return(cond);
                }
            });
        }
コード例 #6
0
        public RegisterFile()
        {
            Entries = new SubRISC.RegisterFile.EntryElement[EntryCount];
            for (int i = 0; i < EntryCount; i++)
            {
                Entries[i] = new EntryElement()
                {
                    Content          = 0,
                    ReadAccessCount  = 0,
                    WriteAccessCount = 0
                };
            }

            Read0_IFace = CreateInputface <ReadCommand>();
            Read1_IFace = CreateInputface <ReadCommand>();
            Write_IFace = CreateInputface <WriteCommand>();

            Read0_OFace = CreateAsyncOutputface <uint>();
            Read1_OFace = CreateAsyncOutputface <uint>();

            PreviousRead0 = new SubRISC.RegisterFile.ReadCommand()
            {
                Enabled = false,
                No      = -1
            };
            PreviousRead1 = new SubRISC.RegisterFile.ReadCommand()
            {
                Enabled = false,
                No      = -1
            };

            Read0_OFace.SetFunc(() =>
            {
                ReadCommand rCmd  = Read0_IFace.Get();
                WriteCommand wCmd = Write_IFace.Get();
                int no            = rCmd.No % EntryCount;
                return(wCmd.Enabled && wCmd.No == no ? wCmd.Value
                                     : Entries[no].Content);
            });
            Read1_OFace.SetFunc(() =>
            {
                ReadCommand rCmd  = Read1_IFace.Get();
                WriteCommand wCmd = Write_IFace.Get();
                int no            = rCmd.No % EntryCount;
                return(wCmd.Enabled && wCmd.No == no ? wCmd.Value
                                     : Entries[no].Content);
            });
        }
コード例 #7
0
ファイル: FetchStage.cs プロジェクト: Hara-Laboratory/oiscsim
        public FetchStage(bool delayBranchEnabled)
        {
            DelayBranchEnabled = delayBranchEnabled;

            Stall_IFace                 = CreateInputface <bool>();
            LMemRdata_IFace             = CreateInputface <ushort>();
            HMemRdata_IFace             = CreateInputface <ushort>();
            BranchRequestFromCS_IFace   = CreateInputface <bool>();
            BranchPCRelModeFromCS_IFace = CreateInputface <bool>();
            BranchPCFromCS_IFace        = CreateInputface <uint>();

            PCOut_OFace       = CreateSyncOutputface <uint>(0);
            Instruction_OFace = CreateSyncOutputface <uint>(0);
            ValidCS_OFace     = CreateSyncOutputface <bool>(false);
            Branched_OFace    = CreateSyncOutputface <bool>(false);

            LMemEn_OFace   = CreateAsyncOutputface <bool>();
            LMemAddr_OFace = CreateAsyncOutputface <uint>();
            HMemEn_OFace   = CreateAsyncOutputface <bool>();
            HMemAddr_OFace = CreateAsyncOutputface <uint>();

            LMemEn_OFace.SetFunc(() =>
            {
                return(!Stall_IFace);
            });
            LMemAddr_OFace.SetFunc(() =>
            {
                bool isPCRelMemInstruction =
                    TestBit(Instruction_OFace.Value, 31) &&
                    TestBit(Instruction_OFace.Value, 24) &&
                    TestBit(Instruction_OFace.Value, 22);
                bool isJumpableInstruction =
                    !TestBit(Instruction_OFace.Value, 31) &&
                    TestBit(Instruction_OFace.Value, 29);

                uint res = PCOut_OFace.Value >> 1;
                if (Branched_OFace.Value)
                {
                    res += 0;
                }
                else if (isPCRelMemInstruction && TestBit(PCOut_OFace.Value, 0))
                {
                    res += 2;
                }
                else if (isPCRelMemInstruction || (isJumpableInstruction && TestBit(PCOut_OFace.Value, 0)))
                {
                    res += 1;
                }

                return(res);
            });
            HMemEn_OFace.SetFunc(() =>
            {
                return(!Stall_IFace);
            });
            HMemAddr_OFace.SetFunc(() =>
            {
                bool isPCRelMemInstruction =
                    TestBit(Instruction_OFace.Value, 31) &&
                    TestBit(Instruction_OFace.Value, 24) &&
                    TestBit(Instruction_OFace.Value, 22);
                bool isJumpableInstruction =
                    !TestBit(Instruction_OFace.Value, 31) &&
                    TestBit(Instruction_OFace.Value, 29);

                uint res = PCOut_OFace.Value >> 1;
                if (Branched_OFace.Value)
                {
                    if (TestBit(PCOut_OFace.Value, 0))
                    {
                        res += 1;
                    }
                    else
                    {
                        res += 0;
                    }
                }
                else if (isPCRelMemInstruction && TestBit(PCOut_OFace.Value, 0))
                {
                    res += 2;
                }
                else if (isPCRelMemInstruction || isJumpableInstruction || TestBit(PCOut_OFace.Value, 0))
                {
                    res += 1;
                }

                return(res);
            });
        }
コード例 #8
0
        public ComputeStage()
        {
            PC_IFace          = CreateInputface <uint>();
            Stall_IFace       = CreateInputface <bool>();
            Instruction_IFace = CreateInputface <uint>();
            ValidCS_IFace     = CreateInputface <bool>();
            RegWen_IFace      = CreateInputface <bool>();
            RegWdata_IFace    = CreateInputface <uint>();
            RegWno_IFace      = CreateInputface <byte>();

            MemOp_OFace     = CreateSyncOutputface <bool>(false);
            MemRw_OFace     = CreateSyncOutputface <bool>(false);
            AluRes_OFace    = CreateSyncOutputface <uint>(0);
            RegRdataC_OFace = CreateSyncOutputface <uint>(0);
            RegNoC_OFace    = CreateSyncOutputface <byte>(0);
            ValidAS_OFace   = CreateSyncOutputface <bool>(false);

            BranchRequest_OFace   = CreateAsyncOutputface <bool>();
            BranchPCRelMode_OFace = CreateAsyncOutputface <bool>();
            BranchPC_OFace        = CreateAsyncOutputface <uint>();

            RegisterFile     = new SubRISC.RegisterFile();
            reg_read0_OFace  = CreateAsyncOutputface <RegisterFile.ReadCommand>();
            reg_read1_OFace  = CreateAsyncOutputface <RegisterFile.ReadCommand>();
            reg_write0_OFace = CreateAsyncOutputface <RegisterFile.WriteCommand>();
            reg_read0_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                RegisterFile.ReadCommand res = new RegisterFile.ReadCommand();
                res.No = instrIsMemoryOperation ? instrOperandD
                                                : instrOperandA;
                res.Enabled = instrIsMemoryOperation ? instrMemoryOperationRW
                                                     : ((res.No & 12) != 0);
                return(res);
            });
            reg_read1_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                RegisterFile.ReadCommand res = new RegisterFile.ReadCommand();
                res.No      = (byte)(instrOperandB & 15);
                res.Enabled = !TestBit(instrOperandB, 4);
                return(res);
            });
            reg_write0_OFace.SetFunc(() =>
            {
                RegisterFile.WriteCommand res = new RegisterFile.WriteCommand();
                res.No      = RegWno_IFace;
                res.Enabled = RegWen_IFace;
                res.Value   = RegWdata_IFace;
                return(res);
            });
            RegisterFile.Read0_IFace.BindSource(reg_read0_OFace);
            RegisterFile.Read1_IFace.BindSource(reg_read1_OFace);
            RegisterFile.Write_IFace.BindSource(reg_write0_OFace);
            this.RegisterSubModule(RegisterFile);

            Alu                = new SubRISC.Alu();
            alu_a_OFace        = CreateAsyncOutputface <uint>();
            alu_b_OFace        = CreateAsyncOutputface <uint>();
            alu_opflag_OFace   = CreateAsyncOutputface <bool>();
            alu_condflag_OFace = CreateAsyncOutputface <byte>();
            alu_a_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                if (instrIsMemoryOperation)
                {
                    return((uint)(TestBit((uint)instrOperandA, 3) ? 0xFFFFFFF0 : 0u) | (uint)((instrOperandA & 7) << 1));
                }
                else if (reg_read0_OFace.Value.Enabled)
                {
                    return(RegisterFile.Read0_OFace.Value);
                }
                else if ((instrOperandA & 3) == 0)
                {
                    return(0);
                }
                else if ((instrOperandA & 3) == 1)
                {
                    return(0xFFFFFFFF);
                }
                else if ((instrOperandA & 3) == 2)
                {
                    return(1);
                }
                else
                {
                    return(0xFFFFFFFC);
                }
            });
            alu_b_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                if (reg_read1_OFace.Value.Enabled)
                {
                    return(RegisterFile.Read1_OFace.Value);
                }
                else if (TestBit(instrOperandB, 0))
                {
                    return(0xFFFFFFFF);
                }
                else if (TestBit(instrOperandB, 1))
                {
                    return(1);
                }
                else if (TestBit(instrOperandB, 2))
                {
                    return(PC_IFace << 1);
                }
                else if (TestBit(instrOperandB, 3))
                {
                    return(32);
                }
                else
                {
                    return(0);
                }
            });
            alu_opflag_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                return(TestBit(instrOpcode, 0));
            });
            alu_condflag_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                return(instrJumpCondition);
            });
            Alu.OperandA_IFace.BindSource(alu_a_OFace);
            Alu.OperandB_IFace.BindSource(alu_b_OFace);
            Alu.OpFlag_IFace.BindSource(alu_opflag_OFace);
            Alu.CondFlag_IFace.BindSource(alu_condflag_OFace);
            this.RegisterSubModule(Alu);

            BranchRequest_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                return(ValidCS_IFace && !TestBit(Instruction_IFace, 31) && instrJumpFlag && Alu.CondResult_OFace.Value);
            });
            BranchPCRelMode_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                return(true);
            });
            BranchPC_OFace.SetFunc(() =>
            {
                byte instrOpcode            = (byte)((Instruction_IFace >> 30) & 3);
                bool instrJumpFlag          = TestBit(Instruction_IFace, 29);
                byte instrOperandA          = (byte)((Instruction_IFace >> 25) & 15);
                byte instrOperandB          = (byte)((Instruction_IFace >> 20) & 31);
                byte instrOperandD          = (byte)((Instruction_IFace >> 16) & 15);
                bool instrJumpByRegister    = TestBit(Instruction_IFace, 15);
                byte instrJumpCondition     = (byte)((Instruction_IFace >> 12) & 7);
                uint instrJumpAddress       = (uint)((Instruction_IFace >> 0) & 0x7FF);
                bool instrIsMemoryOperation = TestBit(instrOpcode, 1) && !TestBit(instrOpcode, 0);
                bool instrMemoryOperationRW = instrJumpFlag;

                return((TestBit(Instruction_IFace, 11) ? 0xFFFFF800 : 0u) | (instrJumpAddress & 0x7FF));
            });
        }