Skip to content

Commit 8f966ce

Browse files
committed
[SelectionDAG] Use int64_t to store the integer power of llvm.powi
https://llvm.org/docs/LangRef.html#llvm-powi-intrinsic The max length of the integer power of `llvm.powi` intrinsic is 32, and the value can be negative. If we use `int32_t` to store this value, `-Val` will underflow when it is `INT32_MIN` The issue was reported in D149033.
1 parent c2dd36c commit 8f966ce

File tree

2 files changed

+18
-1
lines changed

2 files changed

+18
-1
lines changed

llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp

+1-1
Original file line numberDiff line numberDiff line change
@@ -5451,7 +5451,7 @@ static SDValue ExpandPowI(const SDLoc &DL, SDValue LHS, SDValue RHS,
54515451
// it's beneficial on the target, otherwise we end up lowering to a call to
54525452
// __powidf2 (for example).
54535453
if (ConstantSDNode *RHSC = dyn_cast<ConstantSDNode>(RHS)) {
5454-
int Val = RHSC->getSExtValue();
5454+
int64_t Val = RHSC->getSExtValue();
54555455

54565456
// powi(x, 0) -> 1.0
54575457
if (Val == 0)
+17
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,17 @@
1+
; RUN: llc -mtriple=x86_64-unknown-unknown < %s | FileCheck %s
2+
3+
define float @test_powi(ptr %p) nounwind {
4+
; CHECK-LABEL: test_powi:
5+
; CHECK: # %bb.0: # %bb
6+
; CHECK-NEXT: movss {{.*#+}} xmm1 = mem[0],zero,zero,zero
7+
; CHECK-COUNT-31: mulss %xmm1, %xmm1
8+
; CHECK-NEXT: movss {{.*#+}} xmm0 = mem[0],zero,zero,zero
9+
; CHECK-NEXT: divss %xmm1, %xmm0
10+
; CHECK-NEXT: retq
11+
bb:
12+
%load = load float, ptr %p, align 4
13+
%call = call contract float @llvm.powi.f32.i32(float %load, i32 -2147483648)
14+
ret float %call
15+
}
16+
17+
declare float @llvm.powi.f32.i32(float, i32)

0 commit comments

Comments
 (0)