Strength-reduce multiplication by known constants

a81e17175b498e57b8ed31f044c7508a47e93a13695c0c19c368fe0605f40a1b
Alexis Sellier committed ago 1 parent ebab4823
lib/std/arch/rv64/isel.rad +26 -5
677 677
                encode::subw(rd, rs1, rs2)
678 678
                    if typ == il::Type::W32 else
679 679
                encode::sub(rd, rs1, rs2));
680 680
        }
681 681
        case il::BinOp::Mul => {
682 -
            let rs2 = resolveVal(s, super::SCRATCH2, b);
683 -
            emit::emit(s.e,
684 -
                encode::mulw(rd, rs1, rs2)
685 -
                    if typ == il::Type::W32 else
686 -
                encode::mul(rd, rs1, rs2));
682 +
            // Strength-reduce multiplication by known constants.
683 +
            if let case il::Val::Imm(imm) = b {
684 +
                if imm == 0 {
685 +
                    emit::emit(s.e, encode::mv(rd, super::ZERO));
686 +
                } else if imm == 1 {
687 +
                    emitMv(s, rd, rs1);
688 +
                } else if imm == 2 {
689 +
                    emit::emit(s.e, encode::slli(rd, rs1, 1));
690 +
                } else if imm == 4 {
691 +
                    emit::emit(s.e, encode::slli(rd, rs1, 2));
692 +
                } else if imm == 8 {
693 +
                    emit::emit(s.e, encode::slli(rd, rs1, 3));
694 +
                } else {
695 +
                    let rs2 = resolveVal(s, super::SCRATCH2, b);
696 +
                    emit::emit(s.e,
697 +
                        encode::mulw(rd, rs1, rs2)
698 +
                            if typ == il::Type::W32 else
699 +
                        encode::mul(rd, rs1, rs2));
700 +
                }
701 +
            } else {
702 +
                let rs2 = resolveVal(s, super::SCRATCH2, b);
703 +
                emit::emit(s.e,
704 +
                    encode::mulw(rd, rs1, rs2)
705 +
                        if typ == il::Type::W32 else
706 +
                    encode::mul(rd, rs1, rs2));
707 +
            }
687 708
        }
688 709
        case il::BinOp::Sdiv => {
689 710
            let rs2 = resolveVal(s, super::SCRATCH2, b);
690 711
            emitTrapIfZero(s, rs2);
691 712
            emit::emit(s.e,