2424(SRLI [0] x) => x
2525(SLLI [0] x) => x
2626
27- // "Zicond" Extension for Integer Conditional Operations
27+ // "Zicond" Extension for Integer Conditional Operations
2828// Optimize specific patterns based on the unified OR(CZEROEQZ, CZERONEZ) form
2929// (x == 0) ? x : y -> CZEROEQZ y x (when x is the condition)
3030(OR (CZEROEQZ <t> x (SEQZ x)) (CZERONEZ <t> y (SEQZ x))) && buildcfg.GORISCV64 >= 23 => (CZEROEQZ <t> y x)
3131
32- // OR-form optimizations for arithmetic/logic ops (64-bit and 32-bit)
3332// (z == 0) ? ((OP x y)) : x => (OP x (CZERONEZ y z))
3433(OR (CZEROEQZ <t> ((ADD|SUB|OR|XOR|SUBW) x y) (SEQZ z)) (CZERONEZ <t> x (SEQZ z))) && buildcfg.GORISCV64 >= 23
3534 => ((ADD|SUB|OR|XOR|SUBW) x (CZERONEZ <t> y z))
3635// (z != 0) ? ((OP x y)) : x => (OP x (CZEROEQZ y z))
3736(OR (CZEROEQZ <t> ((ADD|SUB|OR|XOR|SUBW) x y) (SNEZ z)) (CZERONEZ <t> x (SNEZ z))) && buildcfg.GORISCV64 >= 23
3837 => ((ADD|SUB|OR|XOR|SUBW) x (CZEROEQZ <t> y z))
3938
40- // AND-specific optimizations
4139// (z == 0) ? (x & y) : x => OR(AND x y, CZEROEQZ x z)
4240(OR (CZEROEQZ <t> (AND x y) (SEQZ z)) (CZERONEZ <t> x (SEQZ z))) && buildcfg.GORISCV64 >= 23
4341 => (OR (AND <t> x y) (CZEROEQZ <t> x z))
4442// (z != 0) ? (x & y) : x => OR(AND x y, CZERONEZ x z)
4543(OR (CZEROEQZ <t> (AND x y) (SNEZ z)) (CZERONEZ <t> x (SNEZ z))) && buildcfg.GORISCV64 >= 23
4644 => (OR (AND <t> x y) (CZERONEZ <t> x z))
4745
48- // ANDI-specific optimizations (immediate version of AND)
4946// (z == 0) ? (x & c) : x => OR(AND x c, CZEROEQZ x z)
5047(OR (CZEROEQZ <t> (ANDI [c] x) (SEQZ z)) (CZERONEZ <t> x (SEQZ z))) && buildcfg.GORISCV64 >= 23
5148 => (OR (AND <t> x (MOVDconst [c])) (CZEROEQZ <t> x z))
5249// (z != 0) ? (x & c) : x => OR(AND x c, CZERONEZ x z)
5350(OR (CZEROEQZ <t> (ANDI [c] x) (SNEZ z)) (CZERONEZ <t> x (SNEZ z))) && buildcfg.GORISCV64 >= 23
5451 => (OR (AND <t> x (MOVDconst [c])) (CZERONEZ <t> x z))
5552
56- // Immediate variants (64-bit only) - immediate is on the right
5753// (z == 0) ? ((OPI [c] x)) : x => (OP x (CZERONEZ c z))
5854(OR (CZEROEQZ <t> ((ADDI|ORI|XORI) [c] x) (SEQZ z)) (CZERONEZ <t> x (SEQZ z))) && buildcfg.GORISCV64 >= 23
5955 => ((ADD|OR|XOR) x (CZERONEZ <t> (MOVDconst [c]) z))
6056// (z != 0) ? ((OPI [c] x)) : x => (OP x (CZEROEQZ c z))
6157(OR (CZEROEQZ <t> ((ADDI|ORI|XORI) [c] x) (SNEZ z)) (CZERONEZ <t> x (SNEZ z))) && buildcfg.GORISCV64 >= 23
6258 => ((ADD|OR|XOR) x (CZEROEQZ <t> (MOVDconst [c]) z))
6359
64- // 32-bit immediate variant (only ADDIW exists, no SUBIW/ORIW/XORIW/ANDIW)
6560// (z == 0) ? (ADDIW [c] x) : x
6661(OR (CZEROEQZ <t> (ADDIW [c] x) (SEQZ z)) (CZERONEZ <t> x (SEQZ z))) && buildcfg.GORISCV64 >= 23
6762 => (ADD x (CZERONEZ <t> (MOVDconst [int64(int32(c))]) z))
6863// (z != 0) ? (ADDIW [c] x) : x
6964(OR (CZEROEQZ <t> (ADDIW [c] x) (SNEZ z)) (CZERONEZ <t> x (SNEZ z))) && buildcfg.GORISCV64 >= 23
7065 => (ADD x (CZEROEQZ <t> (MOVDconst [int64(int32(c))]) z))
7166
72- // Optimize conditional selection of constant or zero to single CZERO instruction
7367// (cond == 0) ? 0 : const => CZERONEZ const cond
7468(OR (CZEROEQZ <t> (MOVDconst [0]) (SEQZ cond)) (CZERONEZ <t> (MOVDconst [c]) (SEQZ cond))) && buildcfg.GORISCV64 >= 23
7569 => (CZERONEZ <t> (MOVDconst [c]) cond)
76- // (cond != 0) ? 0 : const => CZEROEQZ const cond
70+ // (cond != 0) ? 0 : const => CZEROEQZ const cond
7771(OR (CZEROEQZ <t> (MOVDconst [0]) (SNEZ cond)) (CZERONEZ <t> (MOVDconst [c]) (SNEZ cond))) && buildcfg.GORISCV64 >= 23
7872 => (CZEROEQZ <t> (MOVDconst [c]) cond)
7973
8074// Constant propagation through CZERO(EQ|NE)Z
81- (CZERO(EQ|NE)Z <t> (MOVDconst [0]) _) && buildcfg.GORISCV64 >= 23 => (MOVDconst <t> [0])
75+ (CZERO(EQ|NE)Z <t> (MOVDconst [0]) _) && buildcfg.GORISCV64 >= 23 => (MOVDconst <t> [0])
0 commit comments