forked from eden-emu/eden
		
	Shader_IR: Implement ICMP.
This commit is contained in:
		
							parent
							
								
									47a8e03f14
								
							
						
					
					
						commit
						01b8a78a8a
					
				
					 2 changed files with 37 additions and 0 deletions
				
			
		|  | @ -933,6 +933,11 @@ union Instruction { | |||
|         BitField<49, 3, PredCondition> cond; | ||||
|     } isetp; | ||||
| 
 | ||||
|     union { | ||||
|         BitField<48, 1, u64> is_signed; | ||||
|         BitField<49, 3, PredCondition> cond; | ||||
|     } icmp; | ||||
| 
 | ||||
|     union { | ||||
|         BitField<0, 3, u64> pred0; | ||||
|         BitField<3, 3, u64> pred3; | ||||
|  | @ -1628,6 +1633,9 @@ public: | |||
|         SEL_C, | ||||
|         SEL_R, | ||||
|         SEL_IMM, | ||||
|         ICMP_RC, | ||||
|         ICMP_R, | ||||
|         ICMP_CR, | ||||
|         MUFU,  // Multi-Function Operator
 | ||||
|         RRO_C, // Range Reduction Operator
 | ||||
|         RRO_R, | ||||
|  | @ -1892,6 +1900,9 @@ private: | |||
|             INST("0100110010100---", Id::SEL_C, Type::ArithmeticInteger, "SEL_C"), | ||||
|             INST("0101110010100---", Id::SEL_R, Type::ArithmeticInteger, "SEL_R"), | ||||
|             INST("0011100-10100---", Id::SEL_IMM, Type::ArithmeticInteger, "SEL_IMM"), | ||||
|             INST("010100110100----", Id::ICMP_RC, Type::ArithmeticInteger, "ICMP_RC"), | ||||
|             INST("010110110100----", Id::ICMP_R, Type::ArithmeticInteger, "ICMP_R"), | ||||
|             INST("010010110100----", Id::ICMP_CR, Type::ArithmeticInteger, "ICMP_CR"), | ||||
|             INST("0101101111011---", Id::LEA_R2, Type::ArithmeticInteger, "LEA_R2"), | ||||
|             INST("0101101111010---", Id::LEA_R1, Type::ArithmeticInteger, "LEA_R1"), | ||||
|             INST("001101101101----", Id::LEA_IMM, Type::ArithmeticInteger, "LEA_IMM"), | ||||
|  |  | |||
|  | @ -138,6 +138,32 @@ u32 ShaderIR::DecodeArithmeticInteger(NodeBlock& bb, u32 pc) { | |||
|         SetRegister(bb, instr.gpr0, value); | ||||
|         break; | ||||
|     } | ||||
|     case OpCode::Id::ICMP_CR: | ||||
|     case OpCode::Id::ICMP_R: | ||||
|     case OpCode::Id::ICMP_RC: { | ||||
|         UNIMPLEMENTED_IF(instr.icmp.is_signed != 0); | ||||
|         const Node zero = Immediate(0); | ||||
| 
 | ||||
|         const auto [op_a, op_b] = [&]() -> std::tuple<Node, Node> { | ||||
|             switch (opcode->get().GetId()) { | ||||
|             case OpCode::Id::ICMP_CR: | ||||
|                 return {GetConstBuffer(instr.cbuf34.index, instr.cbuf34.offset), | ||||
|                         GetRegister(instr.gpr39)}; | ||||
|             case OpCode::Id::ICMP_R: | ||||
|                 return {GetRegister(instr.gpr20), GetRegister(instr.gpr39)}; | ||||
|             case OpCode::Id::ICMP_RC: | ||||
|                 return {GetRegister(instr.gpr39), | ||||
|                         GetConstBuffer(instr.cbuf34.index, instr.cbuf34.offset)}; | ||||
|             default: | ||||
|                 UNIMPLEMENTED(); | ||||
|                 return {zero, zero}; | ||||
|             } | ||||
|         }(); | ||||
|         const Node test = GetRegister(instr.gpr8); | ||||
|         const Node comparison = GetPredicateComparisonInteger(instr.icmp.cond, false, test, zero); | ||||
|         SetRegister(bb, instr.gpr0, Operation(OperationCode::Select, comparison, op_a, op_b)); | ||||
|         break; | ||||
|     } | ||||
|     case OpCode::Id::LOP_C: | ||||
|     case OpCode::Id::LOP_R: | ||||
|     case OpCode::Id::LOP_IMM: { | ||||
|  |  | |||
		Loading…
	
	Add table
		Add a link
		
	
		Reference in a new issue
	
	 Fernando Sahmkow
						Fernando Sahmkow