Skip to content

Commit 5349b5c

Browse files
committed
[GlobalISel] Add computeNumSignBits for ASHR
1 parent 3d6f698 commit 5349b5c

File tree

9 files changed

+209
-70
lines changed

9 files changed

+209
-70
lines changed

llvm/include/llvm/CodeGen/GlobalISel/GISelValueTracking.h

Lines changed: 14 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,6 +102,20 @@ class GISelValueTracking : public GISelChangeObserver {
102102
/// \return The known alignment for the pointer-like value \p R.
103103
Align computeKnownAlignment(Register R, unsigned Depth = 0);
104104

105+
/// If a G_SHL/G_ASHR/G_LSHR node with shift operand \p R has shift amounts
106+
/// that are all less than the element bit-width of the shift node, return the
107+
/// valid constant range.
108+
std::optional<ConstantRange>
109+
getValidShiftAmountRange(Register R, const APInt &DemandedElts,
110+
unsigned Depth);
111+
112+
/// If a G_SHL/G_ASHR/G_LSHR node with shift operand \p R has shift amounts
113+
/// that are all less than the element bit-width of the shift node, return the
114+
/// minimum possible value.
115+
std::optional<uint64_t> getValidMinimumShiftAmount(Register R,
116+
const APInt &DemandedElts,
117+
unsigned Depth = 0);
118+
105119
/// Determine which floating-point classes are valid for \p V, and return them
106120
/// in KnownFPClass bit sets.
107121
///

llvm/lib/CodeGen/GlobalISel/GISelValueTracking.cpp

Lines changed: 66 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1857,6 +1857,14 @@ unsigned GISelValueTracking::computeNumSignBits(Register R,
18571857
}
18581858
break;
18591859
}
1860+
case TargetOpcode::G_ASHR: {
1861+
Register Src1 = MI.getOperand(1).getReg();
1862+
Register Src2 = MI.getOperand(2).getReg();
1863+
FirstAnswer = computeNumSignBits(Src1, DemandedElts, Depth + 1);
1864+
if (auto C = getValidMinimumShiftAmount(Src2, DemandedElts, Depth + 1))
1865+
FirstAnswer = std::min<uint64_t>(FirstAnswer + *C, TyBits);
1866+
break;
1867+
}
18601868
case TargetOpcode::G_TRUNC: {
18611869
Register Src = MI.getOperand(1).getReg();
18621870
LLT SrcTy = MRI.getType(Src);
@@ -2003,6 +2011,64 @@ unsigned GISelValueTracking::computeNumSignBits(Register R, unsigned Depth) {
20032011
return computeNumSignBits(R, DemandedElts, Depth);
20042012
}
20052013

2014+
std::optional<ConstantRange> GISelValueTracking::getValidShiftAmountRange(
2015+
Register R, const APInt &DemandedElts, unsigned Depth) {
2016+
// Shifting more than the bitwidth is not valid.
2017+
MachineInstr &MI = *MRI.getVRegDef(R);
2018+
unsigned Opcode = MI.getOpcode();
2019+
2020+
LLT Ty = MRI.getType(R);
2021+
unsigned BitWidth = Ty.getScalarSizeInBits();
2022+
2023+
if (Opcode == TargetOpcode::G_CONSTANT) {
2024+
const APInt &ShAmt = MI.getOperand(1).getCImm()->getValue();
2025+
if (ShAmt.uge(BitWidth))
2026+
return std::nullopt;
2027+
return ConstantRange(ShAmt);
2028+
}
2029+
2030+
if (Opcode == TargetOpcode::G_BUILD_VECTOR) {
2031+
const APInt *MinAmt = nullptr, *MaxAmt = nullptr;
2032+
for (unsigned I = 0, E = MI.getNumOperands() - 1; I != E; ++I) {
2033+
if (!DemandedElts[I])
2034+
continue;
2035+
MachineInstr *Op = MRI.getVRegDef(MI.getOperand(I + 1).getReg());
2036+
if (Op->getOpcode() != TargetOpcode::G_CONSTANT) {
2037+
MinAmt = MaxAmt = nullptr;
2038+
break;
2039+
}
2040+
2041+
const APInt &ShAmt = Op->getOperand(1).getCImm()->getValue();
2042+
if (ShAmt.uge(BitWidth))
2043+
return std::nullopt;
2044+
if (!MinAmt || MinAmt->ugt(ShAmt))
2045+
MinAmt = &ShAmt;
2046+
if (!MaxAmt || MaxAmt->ult(ShAmt))
2047+
MaxAmt = &ShAmt;
2048+
}
2049+
assert(((!MinAmt && !MaxAmt) || (MinAmt && MaxAmt)) &&
2050+
"Failed to find matching min/max shift amounts");
2051+
if (MinAmt && MaxAmt)
2052+
return ConstantRange(*MinAmt, *MaxAmt + 1);
2053+
}
2054+
2055+
// Use computeKnownBits to find a hidden constant/knownbits (usually type
2056+
// legalized). e.g. Hidden behind multiple bitcasts/build_vector/casts etc.
2057+
KnownBits KnownAmt = getKnownBits(R, DemandedElts, Depth);
2058+
if (KnownAmt.getMaxValue().ult(BitWidth))
2059+
return ConstantRange::fromKnownBits(KnownAmt, /*IsSigned=*/false);
2060+
2061+
return std::nullopt;
2062+
}
2063+
2064+
std::optional<uint64_t> GISelValueTracking::getValidMinimumShiftAmount(
2065+
Register R, const APInt &DemandedElts, unsigned Depth) {
2066+
if (std::optional<ConstantRange> AmtRange =
2067+
getValidShiftAmountRange(R, DemandedElts, Depth))
2068+
return AmtRange->getUnsignedMin().getZExtValue();
2069+
return std::nullopt;
2070+
}
2071+
20062072
void GISelValueTrackingAnalysisLegacy::getAnalysisUsage(
20072073
AnalysisUsage &AU) const {
20082074
AU.setPreservesAll();
Lines changed: 109 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,109 @@
1+
# NOTE: Assertions have been autogenerated by utils/update_givaluetracking_test_checks.py UTC_ARGS: --version 5
2+
# RUN: llc -mtriple aarch64 -passes="print<gisel-value-tracking>" %s -o - 2>&1 | FileCheck %s
3+
4+
---
5+
name: Cst
6+
body: |
7+
bb.1:
8+
; CHECK-LABEL: name: @Cst
9+
; CHECK-NEXT: %0:_ KnownBits:10000000 SignBits:1
10+
; CHECK-NEXT: %1:_ KnownBits:00000011 SignBits:6
11+
; CHECK-NEXT: %2:_ KnownBits:11110000 SignBits:4
12+
%0:_(s8) = G_CONSTANT i8 128
13+
%1:_(s8) = G_CONSTANT i8 3
14+
%2:_(s8) = G_ASHR %0, %1
15+
...
16+
---
17+
name: CstBig
18+
body: |
19+
bb.1:
20+
; CHECK-LABEL: name: @CstBig
21+
; CHECK-NEXT: %0:_ KnownBits:11111000 SignBits:5
22+
; CHECK-NEXT: %1:_ KnownBits:00000110 SignBits:5
23+
; CHECK-NEXT: %2:_ KnownBits:11111111 SignBits:8
24+
%0:_(s8) = G_CONSTANT i8 248
25+
%1:_(s8) = G_CONSTANT i8 6
26+
%2:_(s8) = G_ASHR %0, %1
27+
...
28+
---
29+
name: ScalarVar
30+
body: |
31+
bb.1:
32+
; CHECK-LABEL: name: @ScalarVar
33+
; CHECK-NEXT: %0:_ KnownBits:???????? SignBits:1
34+
; CHECK-NEXT: %1:_ KnownBits:???????? SignBits:1
35+
; CHECK-NEXT: %2:_ KnownBits:???????? SignBits:1
36+
%0:_(s8) = COPY $b0
37+
%1:_(s8) = COPY $b1
38+
%2:_(s8) = G_ASHR %0, %1
39+
...
40+
---
41+
name: ScalarCst
42+
body: |
43+
bb.1:
44+
; CHECK-LABEL: name: @ScalarCst
45+
; CHECK-NEXT: %0:_ KnownBits:???????? SignBits:1
46+
; CHECK-NEXT: %1:_ KnownBits:00000011 SignBits:6
47+
; CHECK-NEXT: %2:_ KnownBits:???????? SignBits:4
48+
%0:_(s8) = COPY $b0
49+
%1:_(s8) = G_CONSTANT i8 3
50+
%2:_(s8) = G_ASHR %0, %1
51+
...
52+
---
53+
name: VectorVar
54+
body: |
55+
bb.1:
56+
; CHECK-LABEL: name: @VectorVar
57+
; CHECK-NEXT: %0:_ KnownBits:???????????????? SignBits:1
58+
; CHECK-NEXT: %1:_ KnownBits:???????????????? SignBits:1
59+
; CHECK-NEXT: %2:_ KnownBits:???????????????? SignBits:1
60+
%0:_(<4 x s16>) = COPY $d0
61+
%1:_(<4 x s16>) = COPY $d1
62+
%2:_(<4 x s16>) = G_ASHR %0, %1
63+
...
64+
---
65+
name: VectorCst
66+
body: |
67+
bb.1:
68+
; CHECK-LABEL: name: @VectorCst
69+
; CHECK-NEXT: %0:_ KnownBits:???????????????? SignBits:1
70+
; CHECK-NEXT: %1:_ KnownBits:0000000000000011 SignBits:14
71+
; CHECK-NEXT: %2:_ KnownBits:0000000000000011 SignBits:14
72+
; CHECK-NEXT: %3:_ KnownBits:???????????????? SignBits:4
73+
%0:_(<4 x s16>) = COPY $d0
74+
%1:_(s16) = G_CONSTANT i16 3
75+
%2:_(<4 x s16>) = G_BUILD_VECTOR %1, %1, %1, %1
76+
%3:_(<4 x s16>) = G_ASHR %0, %2
77+
...
78+
---
79+
name: VectorCst36
80+
body: |
81+
bb.1:
82+
; CHECK-LABEL: name: @VectorCst36
83+
; CHECK-NEXT: %0:_ KnownBits:???????????????? SignBits:1
84+
; CHECK-NEXT: %1:_ KnownBits:0000000000000011 SignBits:14
85+
; CHECK-NEXT: %2:_ KnownBits:0000000000000110 SignBits:13
86+
; CHECK-NEXT: %3:_ KnownBits:0000000000000?1? SignBits:13
87+
; CHECK-NEXT: %4:_ KnownBits:???????????????? SignBits:4
88+
%0:_(<4 x s16>) = COPY $d0
89+
%1:_(s16) = G_CONSTANT i16 3
90+
%2:_(s16) = G_CONSTANT i16 6
91+
%3:_(<4 x s16>) = G_BUILD_VECTOR %1, %2, %2, %1
92+
%4:_(<4 x s16>) = G_ASHR %0, %3
93+
...
94+
---
95+
name: VectorCst3unknown
96+
body: |
97+
bb.1:
98+
; CHECK-LABEL: name: @VectorCst3unknown
99+
; CHECK-NEXT: %0:_ KnownBits:???????????????? SignBits:1
100+
; CHECK-NEXT: %1:_ KnownBits:???????????????? SignBits:1
101+
; CHECK-NEXT: %2:_ KnownBits:0000000000000011 SignBits:14
102+
; CHECK-NEXT: %3:_ KnownBits:???????????????? SignBits:1
103+
; CHECK-NEXT: %4:_ KnownBits:???????????????? SignBits:1
104+
%0:_(<4 x s16>) = COPY $d0
105+
%2:_(s16) = COPY $h0
106+
%1:_(s16) = G_CONSTANT i16 3
107+
%3:_(<4 x s16>) = G_BUILD_VECTOR %1, %2, %2, %1
108+
%4:_(<4 x s16>) = G_ASHR %0, %3
109+
...

llvm/test/CodeGen/AArch64/aarch64-dup-ext.ll

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -14,10 +14,10 @@ define <8 x i16> @dupsext_v8i8_v8i16(i8 %src, <8 x i8> %b) {
1414
; CHECK-GI-LABEL: dupsext_v8i8_v8i16:
1515
; CHECK-GI: // %bb.0: // %entry
1616
; CHECK-GI-NEXT: lsl w8, w0, #8
17-
; CHECK-GI-NEXT: sshll v0.8h, v0.8b, #0
1817
; CHECK-GI-NEXT: sbfx w8, w8, #8, #8
1918
; CHECK-GI-NEXT: dup v1.8h, w8
20-
; CHECK-GI-NEXT: mul v0.8h, v1.8h, v0.8h
19+
; CHECK-GI-NEXT: xtn v1.8b, v1.8h
20+
; CHECK-GI-NEXT: smull v0.8h, v1.8b, v0.8b
2121
; CHECK-GI-NEXT: ret
2222
entry:
2323
%in = sext i8 %src to i16

llvm/test/CodeGen/AArch64/aarch64-smull.ll

Lines changed: 12 additions & 55 deletions
Original file line numberDiff line numberDiff line change
@@ -2265,68 +2265,25 @@ define <2 x i64> @lsr_const(<2 x i64> %a, <2 x i64> %b) {
22652265
}
22662266

22672267
define <2 x i64> @asr(<2 x i64> %a, <2 x i64> %b) {
2268-
; CHECK-NEON-LABEL: asr:
2269-
; CHECK-NEON: // %bb.0:
2270-
; CHECK-NEON-NEXT: shrn v0.2s, v0.2d, #32
2271-
; CHECK-NEON-NEXT: shrn v1.2s, v1.2d, #32
2272-
; CHECK-NEON-NEXT: smull v0.2d, v0.2s, v1.2s
2273-
; CHECK-NEON-NEXT: ret
2274-
;
2275-
; CHECK-SVE-LABEL: asr:
2276-
; CHECK-SVE: // %bb.0:
2277-
; CHECK-SVE-NEXT: shrn v0.2s, v0.2d, #32
2278-
; CHECK-SVE-NEXT: shrn v1.2s, v1.2d, #32
2279-
; CHECK-SVE-NEXT: smull v0.2d, v0.2s, v1.2s
2280-
; CHECK-SVE-NEXT: ret
2281-
;
2282-
; CHECK-GI-LABEL: asr:
2283-
; CHECK-GI: // %bb.0:
2284-
; CHECK-GI-NEXT: sshr v0.2d, v0.2d, #32
2285-
; CHECK-GI-NEXT: sshr v1.2d, v1.2d, #32
2286-
; CHECK-GI-NEXT: fmov x8, d0
2287-
; CHECK-GI-NEXT: fmov x9, d1
2288-
; CHECK-GI-NEXT: mov x10, v0.d[1]
2289-
; CHECK-GI-NEXT: mov x11, v1.d[1]
2290-
; CHECK-GI-NEXT: mul x8, x8, x9
2291-
; CHECK-GI-NEXT: mul x9, x10, x11
2292-
; CHECK-GI-NEXT: mov v0.d[0], x8
2293-
; CHECK-GI-NEXT: mov v0.d[1], x9
2294-
; CHECK-GI-NEXT: ret
2268+
; CHECK-LABEL: asr:
2269+
; CHECK: // %bb.0:
2270+
; CHECK-NEXT: shrn v0.2s, v0.2d, #32
2271+
; CHECK-NEXT: shrn v1.2s, v1.2d, #32
2272+
; CHECK-NEXT: smull v0.2d, v0.2s, v1.2s
2273+
; CHECK-NEXT: ret
22952274
%x = ashr <2 x i64> %a, <i64 32, i64 32>
22962275
%y = ashr <2 x i64> %b, <i64 32, i64 32>
22972276
%z = mul nsw <2 x i64> %x, %y
22982277
ret <2 x i64> %z
22992278
}
23002279

23012280
define <2 x i64> @asr_const(<2 x i64> %a, <2 x i64> %b) {
2302-
; CHECK-NEON-LABEL: asr_const:
2303-
; CHECK-NEON: // %bb.0:
2304-
; CHECK-NEON-NEXT: movi v1.2s, #31
2305-
; CHECK-NEON-NEXT: shrn v0.2s, v0.2d, #32
2306-
; CHECK-NEON-NEXT: smull v0.2d, v0.2s, v1.2s
2307-
; CHECK-NEON-NEXT: ret
2308-
;
2309-
; CHECK-SVE-LABEL: asr_const:
2310-
; CHECK-SVE: // %bb.0:
2311-
; CHECK-SVE-NEXT: movi v1.2s, #31
2312-
; CHECK-SVE-NEXT: shrn v0.2s, v0.2d, #32
2313-
; CHECK-SVE-NEXT: smull v0.2d, v0.2s, v1.2s
2314-
; CHECK-SVE-NEXT: ret
2315-
;
2316-
; CHECK-GI-LABEL: asr_const:
2317-
; CHECK-GI: // %bb.0:
2318-
; CHECK-GI-NEXT: adrp x8, .LCPI81_0
2319-
; CHECK-GI-NEXT: sshr v0.2d, v0.2d, #32
2320-
; CHECK-GI-NEXT: ldr q1, [x8, :lo12:.LCPI81_0]
2321-
; CHECK-GI-NEXT: fmov x8, d0
2322-
; CHECK-GI-NEXT: fmov x9, d1
2323-
; CHECK-GI-NEXT: mov x10, v0.d[1]
2324-
; CHECK-GI-NEXT: mov x11, v1.d[1]
2325-
; CHECK-GI-NEXT: mul x8, x8, x9
2326-
; CHECK-GI-NEXT: mul x9, x10, x11
2327-
; CHECK-GI-NEXT: mov v0.d[0], x8
2328-
; CHECK-GI-NEXT: mov v0.d[1], x9
2329-
; CHECK-GI-NEXT: ret
2281+
; CHECK-LABEL: asr_const:
2282+
; CHECK: // %bb.0:
2283+
; CHECK-NEXT: movi v1.2s, #31
2284+
; CHECK-NEXT: shrn v0.2s, v0.2d, #32
2285+
; CHECK-NEXT: smull v0.2d, v0.2s, v1.2s
2286+
; CHECK-NEXT: ret
23302287
%x = ashr <2 x i64> %a, <i64 32, i64 32>
23312288
%z = mul nsw <2 x i64> %x, <i64 31, i64 31>
23322289
ret <2 x i64> %z

llvm/test/CodeGen/AMDGPU/GlobalISel/legalize-smulh.mir

Lines changed: 3 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -80,8 +80,7 @@ body: |
8080
; GFX8-NEXT: [[MUL:%[0-9]+]]:_(s32) = G_MUL [[SEXT_INREG]], [[SEXT_INREG1]]
8181
; GFX8-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 16
8282
; GFX8-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[MUL]], [[C]](s32)
83-
; GFX8-NEXT: [[SEXT_INREG2:%[0-9]+]]:_(s32) = G_SEXT_INREG [[ASHR]], 16
84-
; GFX8-NEXT: $vgpr0 = COPY [[SEXT_INREG2]](s32)
83+
; GFX8-NEXT: $vgpr0 = COPY [[ASHR]](s32)
8584
;
8685
; GFX9-LABEL: name: test_smulh_s16
8786
; GFX9: liveins: $vgpr0, $vgpr1
@@ -93,8 +92,7 @@ body: |
9392
; GFX9-NEXT: [[MUL:%[0-9]+]]:_(s32) = G_MUL [[SEXT_INREG]], [[SEXT_INREG1]]
9493
; GFX9-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 16
9594
; GFX9-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[MUL]], [[C]](s32)
96-
; GFX9-NEXT: [[SEXT_INREG2:%[0-9]+]]:_(s32) = G_SEXT_INREG [[ASHR]], 16
97-
; GFX9-NEXT: $vgpr0 = COPY [[SEXT_INREG2]](s32)
95+
; GFX9-NEXT: $vgpr0 = COPY [[ASHR]](s32)
9896
%0:_(s32) = COPY $vgpr0
9997
%1:_(s32) = COPY $vgpr1
10098
%2:_(s16) = G_TRUNC %0
@@ -200,9 +198,7 @@ body: |
200198
; GFX9-NEXT: [[SEXT_INREG3:%[0-9]+]]:_(s32) = G_SEXT_INREG [[UV3]], 16
201199
; GFX9-NEXT: [[MUL1:%[0-9]+]]:_(s32) = G_MUL [[SEXT_INREG2]], [[SEXT_INREG3]]
202200
; GFX9-NEXT: [[ASHR1:%[0-9]+]]:_(s32) = G_ASHR [[MUL1]], [[C]](s32)
203-
; GFX9-NEXT: [[SEXT_INREG4:%[0-9]+]]:_(s32) = G_SEXT_INREG [[ASHR]], 16
204-
; GFX9-NEXT: [[SEXT_INREG5:%[0-9]+]]:_(s32) = G_SEXT_INREG [[ASHR1]], 16
205-
; GFX9-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x s32>) = G_BUILD_VECTOR [[SEXT_INREG4]](s32), [[SEXT_INREG5]](s32)
201+
; GFX9-NEXT: [[BUILD_VECTOR:%[0-9]+]]:_(<2 x s32>) = G_BUILD_VECTOR [[ASHR]](s32), [[ASHR1]](s32)
206202
; GFX9-NEXT: $vgpr0_vgpr1 = COPY [[BUILD_VECTOR]](<2 x s32>)
207203
%0:_(<2 x s32>) = COPY $vgpr0_vgpr1
208204
%1:_(<2 x s32>) = COPY $vgpr2_vgpr3

llvm/test/CodeGen/AMDGPU/GlobalISel/postlegalizercombiner-sbfx.mir

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -92,8 +92,7 @@ body: |
9292
; GCN-NEXT: [[COPY:%[0-9]+]]:_(s32) = COPY $vgpr0
9393
; GCN-NEXT: [[C:%[0-9]+]]:_(s32) = G_CONSTANT i32 16
9494
; GCN-NEXT: [[ASHR:%[0-9]+]]:_(s32) = G_ASHR [[COPY]], [[C]](s32)
95-
; GCN-NEXT: [[SEXT_INREG:%[0-9]+]]:_(s32) = G_SEXT_INREG [[ASHR]], 20
96-
; GCN-NEXT: $vgpr0 = COPY [[SEXT_INREG]](s32)
95+
; GCN-NEXT: $vgpr0 = COPY [[ASHR]](s32)
9796
%0:_(s32) = COPY $vgpr0
9897
%1:_(s32) = G_CONSTANT i32 16
9998
%2:_(s32) = G_ASHR %0, %1(s32)

llvm/test/CodeGen/RISCV/GlobalISel/legalizer/legalize-abs-rv64.mir

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -88,8 +88,7 @@ body: |
8888
; RV64I-NEXT: [[ADD:%[0-9]+]]:_(s64) = G_ADD [[ASSERT_SEXT]], [[ASHR]]
8989
; RV64I-NEXT: [[SEXT_INREG:%[0-9]+]]:_(s64) = G_SEXT_INREG [[ADD]], 32
9090
; RV64I-NEXT: [[XOR:%[0-9]+]]:_(s64) = G_XOR [[SEXT_INREG]], [[ASHR]]
91-
; RV64I-NEXT: [[SEXT_INREG1:%[0-9]+]]:_(s64) = G_SEXT_INREG [[XOR]], 32
92-
; RV64I-NEXT: $x10 = COPY [[SEXT_INREG1]](s64)
91+
; RV64I-NEXT: $x10 = COPY [[XOR]](s64)
9392
; RV64I-NEXT: PseudoRET implicit $x10
9493
;
9594
; RV64ZBB-LABEL: name: abs_i32

llvm/test/CodeGen/RISCV/GlobalISel/rv64zbb.ll

Lines changed: 1 addition & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1053,9 +1053,8 @@ define signext i32 @abs_i32_sext(i32 signext %x) {
10531053
; RV64I-LABEL: abs_i32_sext:
10541054
; RV64I: # %bb.0:
10551055
; RV64I-NEXT: srai a1, a0, 31
1056-
; RV64I-NEXT: add a0, a0, a1
1056+
; RV64I-NEXT: addw a0, a0, a1
10571057
; RV64I-NEXT: xor a0, a0, a1
1058-
; RV64I-NEXT: sext.w a0, a0
10591058
; RV64I-NEXT: ret
10601059
;
10611060
; RV64ZBB-LABEL: abs_i32_sext:

0 commit comments

Comments
 (0)