⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 decoder_arm.v

📁 若干VHDL语言的源代码
💻 V
📖 第 1 页 / 共 5 页
字号:
	
	Next_PrevOperationWantWriteRegisterFromMEM=1'b0;
	Next_PrevWriteRegister=`Def_RegisterSelectZero;
	
	Next_IncRegNumber=`Def_RegisterSelectZero;
	Next_DecRegNumber=`Def_RegisterSelectAllOne;
	
	
	//end of latch infer prevent
	
	if(in_TrueFiq==1'b1)
	begin
		//fast interrupt
			out_LeftReadRegisterEnable=1'b0;
			out_LeftReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALULeftFromImm=1'b0;

			//right read bus will be use to pass target address
			out_RightReadRegisterEnable=1'b0;
			out_RightReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALURightFromImm=1'b1;
			out_ALUExtendedImmediateValue=`Def_FIQ_Service;
		
			out_ThirdReadRegisterEnable=1'b0;
			out_ThirdReadRegisterNumber=ThirdRegisterNumber;
			out_ALUThirdFromImm=1'b0;

			//alu main thread will be use to branch
			out_ALUEnable=1'b1;
			out_ALUType=`ALUType_Mov;
			out_ALUTargetRegister=`Def_LinkRegister;

			//do not shift, just use right operand as branch target address
			out_ALURightShiftType=2'b00;
			out_ALUSecondImmediateValue=`WordDontCare;
			
			out_IDOwnCanGo=1'b1;

			//mem not enable
			out_MEMEnable=1'b0;
			out_MEMType=`MEMType_Null;
			out_MEMTargetRegister=`Def_LinkRegister;

			//simple will be use to write pc+4 to r14_svc
			out_SimpleALUType=`ALUType_MvNextInstructionAddress;
			out_SimpleALUTargetRegister=`Def_SBLRegister;
			out_NextAddressGoWithInstruction2ALU=PCAdder4Result;
			
			//branch to service
			out_ALUMisc=`WordZero;
			//send out the condition code
			out_ALUMisc[31:28]=in_PipelineRegister_IFID[31:28];
			//a branch
			out_ALUMisc[6]=1'b1;
			//exception
			out_ALUMisc[8]=1'b1;
			out_ALUMisc[13:9]=`MODE_FIQ;

			//simple MEM thread will be use to write pc+4 to r14_svc
			out_SimpleMEMType=`MEMType_MovSimple;
			out_SimpleMEMTargetRegister=`Def_SBLRegister;

			//condition code valid in alu and mem stage
			out_ALUPSRType=`ALUPSRType_CPSR2SPSR;
			out_MEMPSRType=`MEMPSRType_WriteBoth;

			//default is come from register
			out_CPSRFromImm=1'b0;
			out_SPSRFromImm=1'b0;
	
			//only a branch or alu/load/store use pc as base will send address on this port 
			//out to LeftReadBus
			//not use here
			out_AddressGoWithInstruction2ALU=`WordDontCare;
	
	
			Next_PrevOperationWantWriteRegisterFromMEM=1'b0;
			Next_PrevWriteRegister=`Def_RegisterSelectZero;
	end
	else if(in_TrueIrq==1'b1)
	begin
		//normal interrupt
		//almost same as FIQ
			out_LeftReadRegisterEnable=1'b0;
			out_LeftReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALULeftFromImm=1'b0;

			//right read bus will be use to pass target address
			out_RightReadRegisterEnable=1'b0;
			out_RightReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALURightFromImm=1'b1;
			out_ALUExtendedImmediateValue=`Def_IRQ_Service;	//first not same as fiq
		
			out_ThirdReadRegisterEnable=1'b0;
			out_ThirdReadRegisterNumber=ThirdRegisterNumber;
			out_ALUThirdFromImm=1'b0;

			//alu main thread will be use to branch
			out_ALUEnable=1'b1;
			out_ALUType=`ALUType_Mov;
			out_ALUTargetRegister=`Def_LinkRegister;

			//do not shift, just use right operand as branch target address
			out_ALURightShiftType=2'b00;
			out_ALUSecondImmediateValue=`WordDontCare;
			
			out_IDOwnCanGo=1'b1;

			//mem not enable
			out_MEMEnable=1'b0;
			out_MEMType=`MEMType_Null;
			out_MEMTargetRegister=`Def_LinkRegister;

			//simple will be use to write pc+4 to r14_svc
			out_SimpleALUType=`ALUType_MvNextInstructionAddress;
			out_SimpleALUTargetRegister=`Def_SBLRegister;
			out_NextAddressGoWithInstruction2ALU=PCAdder4Result;
			
			//branch to service
			out_ALUMisc=`WordZero;
			//send out the condition code
			out_ALUMisc[31:28]=in_PipelineRegister_IFID[31:28];
			//a branch
			out_ALUMisc[6]=1'b1;
			//exception
			out_ALUMisc[8]=1'b1;
			out_ALUMisc[13:9]=`MODE_IRQ;

			//simple MEM thread will be use to write pc+4 to r14_svc
			out_SimpleMEMType=`MEMType_MovSimple;
			out_SimpleMEMTargetRegister=`Def_SBLRegister;

			//condition code valid in alu and mem stage
			out_ALUPSRType=`ALUPSRType_CPSR2SPSR;
			out_MEMPSRType=`MEMPSRType_WriteBoth;

			//default is come from register
			out_CPSRFromImm=1'b0;
			out_SPSRFromImm=1'b0;
	
			//only a branch or alu/load/store use pc as base will send address on this port 
			//out to LeftReadBus
			//not use here
			out_AddressGoWithInstruction2ALU=`WordDontCare;
	
	
			Next_PrevOperationWantWriteRegisterFromMEM=1'b0;
			Next_PrevWriteRegister=`Def_RegisterSelectZero;
	end
	else if(in_ValidInstruction_IFID==1'b1)
	begin
	   if(in_ALUCanGo==1'b1)
	   begin
	   	//ALU can go
		//valid instruction
		if(`Def_IsBX)
		begin
			//deal with left operand
			out_LeftReadRegisterEnable=1'b0;
			out_LeftReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALULeftFromImm=1'b1;
			
			//right operand use reg
			out_RightReadRegisterEnable=1'b1;
			out_RightReadRegisterNumber=RightRegisterNumber;
			out_ALURightFromImm=1'b0;
			
			//shift count act as third operand
			out_ThirdReadRegisterEnable=1'b0;
			out_ThirdReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALUThirdFromImm=1'b1;
			
			out_ALUEnable=1'b1;
			out_ALUType=`ALUType_Mov;
			out_ALUTargetRegister=`Def_LinkRegister;
			
			out_ALURightShiftType=2'b00;
			//right operand
			out_ALUExtendedImmediateValue=`WordDontCare;
			//shift count
			out_ALUSecondImmediateValue=`WordDontCare;
			out_IDOwnCanGo=1'b1;
			
			out_MEMEnable=1'b1;
			//main mem stage wil not be use
			out_MEMType=`MEMType_Null;
			out_MEMTargetRegister=`Def_LinkRegister;
			out_ALUMisc=`WordZero;
			out_ALUMisc[31:28]=in_PipelineRegister_IFID[31:28];
			//main thread result must be used to change pc
			//output new pc to IF using main alu
			out_ALUMisc[6]=1'b1;
			
			//exchange between thumb and ARM state
			out_ALUPSRType=`ALUPSRType_ModifyThumbState;
			out_MEMPSRType=`MEMPSRType_WriteCPSR;

			//default is come from register
			out_CPSRFromImm=1'b0;
			out_SPSRFromImm=1'b0;

			//only when there is a branch or a alu using pc
			//can i out address of this instrcution to out_AddressGoWithInstruction2ALU
			//because it go to LeftReadBus
			out_AddressGoWithInstruction2ALU=`WordZero;
			//no need to deal with psr
		end
		else if(`Def_IsSWI)
		begin
			//software interrupt
			
			out_LeftReadRegisterEnable=1'b0;
			out_LeftReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALULeftFromImm=1'b0;

			//right read bus will be use to pass target address -- 0x8
			out_RightReadRegisterEnable=1'b0;
			out_RightReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALURightFromImm=1'b1;
			out_ALUExtendedImmediateValue=`Def_SWI_Service;
		
			out_ThirdReadRegisterEnable=1'b0;
			out_ThirdReadRegisterNumber=ThirdRegisterNumber;
			out_ALUThirdFromImm=1'b0;

			//alu main thread will be use to branch
			out_ALUEnable=1'b1;
			out_ALUType=`ALUType_Mov;
			out_ALUTargetRegister=`Def_LinkRegister;

			//do not shift, just use right operand as branch target address
			out_ALURightShiftType=2'b00;
			out_ALUSecondImmediateValue=`WordZero;
			
			out_IDOwnCanGo=1'b1;

			//mem not enable
			out_MEMEnable=1'b0;
			out_MEMType=`MEMType_Null;
			out_MEMTargetRegister=`Def_LinkRegister;

			//simple will be use to write pc+4 to r14_svc
			out_SimpleALUType=`ALUType_MvNextInstructionAddress;
			out_SimpleALUTargetRegister=`Def_SBLRegister;
			out_NextAddressGoWithInstruction2ALU=in_NextInstructionAddress;
			
			//branch to service
			out_ALUMisc=`WordZero;
			//send out the condition code
			out_ALUMisc[31:28]=in_PipelineRegister_IFID[31:28];
			//a branch
			out_ALUMisc[6]=1'b1;
			//exception
			out_ALUMisc[8]=1'b1;
			out_ALUMisc[13:9]=`MODE_SVC;

			//simple MEM thread will be use to write pc+4 to r14_svc
			out_SimpleMEMType=`MEMType_MovSimple;
			out_SimpleMEMTargetRegister=`Def_SBLRegister;

			//condition code valid in alu and mem stage
			out_ALUPSRType=`ALUPSRType_CPSR2SPSR;
			out_MEMPSRType=`MEMPSRType_WriteBoth;

			//default is come from register
			out_CPSRFromImm=1'b0;
			out_SPSRFromImm=1'b0;
	
			//only a branch or alu/load/store use pc as base will send address on this port 
			//out to LeftReadBus
			//not use here
			out_AddressGoWithInstruction2ALU=`WordDontCare;
	
	
			Next_PrevOperationWantWriteRegisterFromMEM=1'b0;
			Next_PrevWriteRegister=`Def_RegisterSelectZero;
		end
		else if(`Def_IsMultiple)
		begin
			out_LeftReadRegisterEnable=1'b1;
			out_LeftReadRegisterNumber=LeftRegisterNumber;
			out_ALULeftFromImm=1'b0;
			
			out_RightReadRegisterEnable=1'b1;
			out_RightReadRegisterNumber=RightRegisterNumber;
			out_ALURightFromImm=1'b0;
			
			out_ThirdReadRegisterEnable=1'b1;
			out_ThirdReadRegisterNumber=ThirdRegisterNumber;
			out_ALUThirdFromImm=1'b0;
			
			out_ALUEnable=1'b1;
			if(in_PipelineRegister_IFID[21]==1'b0)
			begin
				//multiple only
				out_ALUType=`ALUType_Mul;
			end
			else
			begin
				//mul and add
				out_ALUType=`ALUType_Mla;
			end
			
			out_ALUTargetRegister=TargetRegisterNumber;

			//no use here
			out_ALURightShiftType=2'b00;

			out_ALUExtendedImmediateValue=`WordDontCare;
			out_ALUSecondImmediateValue=`WordDontCare;
			out_IDOwnCanGo=1'b1;

			out_MEMEnable=1'b1;
			out_MEMType=`MEMType_MovMain;
			out_MEMTargetRegister=TargetRegisterNumber;
			
			//simple thread will not be use
			
			//psr thread
			if(in_PipelineRegister_IFID[20]==1'b0)
			begin
				//do not set condition code
				out_ALUPSRType=`ALUPSRType_Null;
				out_MEMPSRType=`MEMPSRType_Null;
			end
			else
			begin
				//set condition code
				out_ALUPSRType=`ALUPSRType_WriteConditionCode;
				out_MEMPSRType=`MEMPSRType_WriteConditionCode;
			end
		end
		else if(`Def_IsBranch)
		begin
			//deal with left operand
			//first i must use my pc ahead as the left register
			out_LeftReadRegisterEnable=1'b0;
			out_LeftReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALULeftFromImm=1'b1;
			
			//right operand use imm
			out_RightReadRegisterEnable=1'b0;
			out_RightReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALURightFromImm=1'b1;
			
			//shift count act as third operand
			out_ThirdReadRegisterEnable=1'b0;
			out_ThirdReadRegisterNumber=`Def_RegisterSelectZero;
			out_ALUThirdFromImm=1'b1;
			
			out_ALUEnable=1'b1;
			out_ALUType=`ALUType_Add;
			out_ALUTargetRegister=`Def_LinkRegister;
			
			out_ALURightShiftType=2'b00;
			//right operand
			if(in_ThumbState==1'b0)
				out_ALUExtendedImmediateValue={{6{in_PipelineRegister_IFID[23]}},in_PipelineRegister_IFID[23:0],2'b00};
			else
				out_ALUExtendedImmediateValue={{7{in_PipelineRegister_IFID[23]}},in_PipelineRegister_IFID[23:0],1'b0};

			//shift count
			out_ALUSecondImmediateValue=`WordZero;
			out_IDOwnCanGo=1'b1;
			
			out_MEMEnable=1'b1;
			//main mem stage wil not be use
			out_MEMType=`MEMType_Null;
			out_MEMTargetRegister=`Def_LinkRegister;
			out_ALUMisc=`WordZero;
			out_ALUMisc[31:28]=in_PipelineRegister_IFID[31:28];
			//main thread result must be used to change pc
			//output new pc to IF using main alu
			out_ALUMisc[6]=1'b1;
			if(in_PipelineRegister_IFID[24]==1'b1)
			begin
				//branch with link
				//write pc+4 to R14 unsing simple thread
				out_SimpleALUType=`ALUType_MvNextInstructionAddress;
				out_SimpleALUTargetRegister=`Def_SBLRegister;
				out_NextAddressGoWithInstruction2ALU=in_NextInstructionAddress;
				
				out_SimpleMEMType=`MEMType_MovSimple;
				out_SimpleMEMTargetRegister=`Def_SBLRegister;
			end//normal branch do not need to store pc+4 to R14
			
			//only when there is a branch or a alu using pc
			//can i out address of this instrcution to out_AddressGoWithInstruction2ALU
			//because it go to LeftReadBus
			out_AddressGoWithInstruction2ALU=PCAdder8or4Result;
			//no need to deal with psr
		end
		else if(`Def_IsMRS)
		begin
			out_ALUEnable=1'b1;
			if(in_PipelineRegister_IFID[22]==1'b1)
				out_SimpleALUType=`ALUType_MvSPSR;
			else
				out_SimpleALUType=`ALUType_MvCPSR;
				
			out_SimpleALUTargetRegister=TargetRegisterNumber;
			
			out_MEMEnable=1'b1;
			out_SimpleMEMType=`MEMType_MovSimple;
			out_SimpleMEMTargetRegister=TargetRegisterNumber;
		end
		else if(`Def_IsMSRReg)//move a reg to status
		begin
			out_ALUEnable=1'b1;
			
			//read right register
			out_RightReadRegisterEnable=1'b1;
			out_RightReadRegisterNumber=RightRegisterNumber;
			out_ALURightFromImm=1'b0;
			
			//do not shift right register
			out_ALURightShiftType=2'b00;
			out_ALUSecondImmediateValue=`WordDontCare;
			
			if(in_PipelineRegister_IFID[22]==1'b1)

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -