mirror of
				https://git.suyu.dev/suyu/suyu
				synced 2025-11-03 16:39:01 -06:00 
			
		
		
		
	Merge pull request #458 from Subv/fmnmx
Shaders: Implemented the FMNMX shader instruction.
This commit is contained in:
		@@ -193,6 +193,11 @@ union Instruction {
 | 
			
		||||
        BitField<50, 1, u64> abs_d;
 | 
			
		||||
        BitField<56, 1, u64> negate_imm;
 | 
			
		||||
 | 
			
		||||
        union {
 | 
			
		||||
            BitField<39, 3, u64> pred;
 | 
			
		||||
            BitField<42, 1, u64> negate_pred;
 | 
			
		||||
        } fmnmx;
 | 
			
		||||
 | 
			
		||||
        float GetImm20_19() const {
 | 
			
		||||
            float result{};
 | 
			
		||||
            u32 imm{static_cast<u32>(imm20_19)};
 | 
			
		||||
 
 | 
			
		||||
@@ -580,14 +580,17 @@ private:
 | 
			
		||||
     * @param instr Instruction to generate the if condition for.
 | 
			
		||||
     * @returns string containing the predicate condition.
 | 
			
		||||
     */
 | 
			
		||||
    std::string GetPredicateCondition(Instruction instr) const {
 | 
			
		||||
    std::string GetPredicateCondition(u64 index, bool negate) const {
 | 
			
		||||
        using Tegra::Shader::Pred;
 | 
			
		||||
        ASSERT(instr.pred.pred_index != static_cast<u64>(Pred::UnusedIndex));
 | 
			
		||||
        std::string variable;
 | 
			
		||||
 | 
			
		||||
        std::string variable =
 | 
			
		||||
            'p' + std::to_string(static_cast<u64>(instr.pred.pred_index.Value()));
 | 
			
		||||
        // Index 7 is used as an 'Always True' condition.
 | 
			
		||||
        if (index == static_cast<u64>(Pred::UnusedIndex))
 | 
			
		||||
            variable = "true";
 | 
			
		||||
        else
 | 
			
		||||
            variable = 'p' + std::to_string(index);
 | 
			
		||||
 | 
			
		||||
        if (instr.negate_pred) {
 | 
			
		||||
        if (negate) {
 | 
			
		||||
            return "!(" + variable + ')';
 | 
			
		||||
        }
 | 
			
		||||
 | 
			
		||||
@@ -634,7 +637,9 @@ private:
 | 
			
		||||
                   "NeverExecute predicate not implemented");
 | 
			
		||||
 | 
			
		||||
        if (instr.pred.pred_index != static_cast<u64>(Pred::UnusedIndex)) {
 | 
			
		||||
            shader.AddLine("if (" + GetPredicateCondition(instr) + ')');
 | 
			
		||||
            shader.AddLine("if (" +
 | 
			
		||||
                           GetPredicateCondition(instr.pred.pred_index, instr.negate_pred != 0) +
 | 
			
		||||
                           ')');
 | 
			
		||||
            shader.AddLine('{');
 | 
			
		||||
            ++shader.scope;
 | 
			
		||||
        }
 | 
			
		||||
@@ -730,6 +735,16 @@ private:
 | 
			
		||||
                }
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
            case OpCode::Id::FMNMX: {
 | 
			
		||||
                std::string condition =
 | 
			
		||||
                    GetPredicateCondition(instr.alu.fmnmx.pred, instr.alu.fmnmx.negate_pred != 0);
 | 
			
		||||
                std::string parameters = op_a + ',' + op_b;
 | 
			
		||||
                regs.SetRegisterToFloat(instr.gpr0, 0,
 | 
			
		||||
                                        '(' + condition + ") ? min(" + parameters + ") : max(" +
 | 
			
		||||
                                            parameters + ')',
 | 
			
		||||
                                        1, 1);
 | 
			
		||||
                break;
 | 
			
		||||
            }
 | 
			
		||||
            case OpCode::Id::RRO: {
 | 
			
		||||
                NGLOG_DEBUG(HW_GPU, "Skipping RRO instruction");
 | 
			
		||||
                break;
 | 
			
		||||
 
 | 
			
		||||
		Reference in New Issue
	
	Block a user