Skip to content

Commit ddb3882

Browse files
committed
Added opt.
1 parent 7d53230 commit ddb3882

File tree

2 files changed

+42
-7
lines changed

2 files changed

+42
-7
lines changed

llvm/lib/Transforms/Scalar/InferAlignment.cpp

Lines changed: 39 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -12,19 +12,26 @@
1212
//===----------------------------------------------------------------------===//
1313

1414
#include "llvm/Transforms/Scalar/InferAlignment.h"
15+
#include "llvm/ADT/STLFunctionalExtras.h"
1516
#include "llvm/Analysis/AssumptionCache.h"
1617
#include "llvm/Analysis/ValueTracking.h"
18+
#include "llvm/IR/Instruction.h"
1719
#include "llvm/IR/Instructions.h"
1820
#include "llvm/IR/IntrinsicInst.h"
21+
#include "llvm/IR/PatternMatch.h"
22+
#include "llvm/IR/Value.h"
23+
#include "llvm/Support/Alignment.h"
1924
#include "llvm/Support/KnownBits.h"
2025
#include "llvm/Transforms/Scalar.h"
2126
#include "llvm/Transforms/Utils/Local.h"
2227

2328
using namespace llvm;
29+
using namespace llvm::PatternMatch;
2430

2531
static bool tryToImproveAlign(
2632
const DataLayout &DL, Instruction *I,
27-
function_ref<Align(Value *PtrOp, Align OldAlign, Align PrefAlign)> Fn) {
33+
function_ref<Align(Value *PtrOp, Align OldAlign, Align PrefAlign)> Fn,
34+
function_ref<Align(Instruction &I, Value *PtrOp)> ActualAlignFn) {
2835

2936
if (auto *PtrOp = getLoadStorePointerOperand(I)) {
3037
Align OldAlign = getLoadStoreAlignment(I);
@@ -37,6 +44,17 @@ static bool tryToImproveAlign(
3744
}
3845
}
3946

47+
Value *PtrOp;
48+
ConstantInt *Const;
49+
if (match(I,
50+
m_c_And(m_PtrToIntOrAddr(m_Value(PtrOp)), m_ConstantInt(Const)))) {
51+
Align ActualAlign = ActualAlignFn(*I, PtrOp);
52+
if (Const->getValue().ult(ActualAlign.value())) {
53+
I->replaceAllUsesWith(Constant::getNullValue(I->getType()));
54+
return true;
55+
}
56+
}
57+
4058
IntrinsicInst *II = dyn_cast<IntrinsicInst>(I);
4159
if (!II)
4260
return false;
@@ -75,11 +93,15 @@ bool inferAlignment(Function &F, AssumptionCache &AC, DominatorTree &DT) {
7593
for (BasicBlock &BB : F) {
7694
for (Instruction &I : BB) {
7795
Changed |= tryToImproveAlign(
78-
DL, &I, [&](Value *PtrOp, Align OldAlign, Align PrefAlign) {
96+
DL, &I,
97+
[&](Value *PtrOp, Align OldAlign, Align PrefAlign) {
7998
if (PrefAlign > OldAlign)
8099
return std::max(OldAlign,
81100
tryEnforceAlignment(PtrOp, PrefAlign, DL));
82101
return OldAlign;
102+
},
103+
[&](Instruction &, Value *PtrOp) {
104+
return PtrOp->getPointerAlignment(DL);
83105
});
84106
}
85107
}
@@ -120,6 +142,17 @@ bool inferAlignment(Function &F, AssumptionCache &AC, DominatorTree &DT) {
120142
return LoadStoreAlign;
121143
};
122144

145+
auto ActualAlginFn = [&](Instruction &I, Value *PtrOp) {
146+
Align KnownAlign = InferFromKnownBits(I, PtrOp);
147+
Align BaseAlign = PtrOp->getPointerAlignment(DL);
148+
if (auto It = BestBasePointerAligns.find(PtrOp);
149+
It != BestBasePointerAligns.end()) {
150+
BaseAlign = std::max(BaseAlign, It->second);
151+
}
152+
Align ActualAlign = std::max(KnownAlign, BaseAlign);
153+
return ActualAlign;
154+
};
155+
123156
for (BasicBlock &BB : F) {
124157
// We need to reset the map for each block because alignment information
125158
// can only be propagated from instruction A to B if A dominates B.
@@ -131,10 +164,12 @@ bool inferAlignment(Function &F, AssumptionCache &AC, DominatorTree &DT) {
131164

132165
for (Instruction &I : BB) {
133166
Changed |= tryToImproveAlign(
134-
DL, &I, [&](Value *PtrOp, Align OldAlign, Align PrefAlign) {
167+
DL, &I,
168+
[&](Value *PtrOp, Align OldAlign, Align PrefAlign) {
135169
return std::max(InferFromKnownBits(I, PtrOp),
136170
InferFromBasePointer(PtrOp, OldAlign));
137-
});
171+
},
172+
ActualAlginFn);
138173
}
139174
}
140175

llvm/test/Transforms/InferAlignment/ptrtoint.ll

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -7,7 +7,7 @@ define i64 @base(ptr %0) {
77
; CHECK-NEXT: [[V1:%.*]] = load i32, ptr [[TMP0]], align 4
88
; CHECK-NEXT: [[V3:%.*]] = ptrtoint ptr [[TMP0]] to i64
99
; CHECK-NEXT: [[V5:%.*]] = and i64 [[V3]], 2
10-
; CHECK-NEXT: ret i64 [[V5]]
10+
; CHECK-NEXT: ret i64 0
1111
;
1212
%v1 = load i32, ptr %0, align 4
1313
%v3 = ptrtoint ptr %0 to i64
@@ -22,7 +22,7 @@ define i64 @best_alignment(ptr %0) {
2222
; CHECK-NEXT: [[V1_3:%.*]] = load i32, ptr [[TMP0]], align 16
2323
; CHECK-NEXT: [[V3:%.*]] = ptrtoint ptr [[TMP0]] to i64
2424
; CHECK-NEXT: [[V5:%.*]] = and i64 [[V3]], 15
25-
; CHECK-NEXT: ret i64 [[V5]]
25+
; CHECK-NEXT: ret i64 0
2626
;
2727
%v1 = load i32, ptr %0, align 8
2828
%v2 = load i32, ptr %0, align 16
@@ -55,7 +55,7 @@ define i64 @ptrtoaddr(ptr %0) {
5555
; CHECK-NEXT: [[V3:%.*]] = ptrtoaddr ptr [[TMP0]] to i64
5656
; CHECK-NEXT: [[V1:%.*]] = load i32, ptr [[TMP0]], align 4
5757
; CHECK-NEXT: [[V5:%.*]] = and i64 2, [[V3]]
58-
; CHECK-NEXT: ret i64 [[V5]]
58+
; CHECK-NEXT: ret i64 0
5959
;
6060
%v3 = ptrtoaddr ptr %0 to i64
6161
%v1 = load i32, ptr %0, align 4

0 commit comments

Comments
 (0)