90 lines
3.3 KiB
Diff
90 lines
3.3 KiB
Diff
commit 8eb2b102a203d83fb713f3bf79acf235dabdd8cd
|
|
Author: Keno Fischer <keno@juliacomputing.com>
|
|
Date: Mon Jul 30 16:59:08 2018 -0400
|
|
|
|
[VNCoercion] Disallow coercion between different ni addrspaces
|
|
|
|
Summary:
|
|
I'm not sure if it would be legal by the IR reference to introduce
|
|
an addrspacecast here, since the IR reference is a bit vague on
|
|
the exact semantics, but at least for our usage of it (and I
|
|
suspect for many other's usage) it is not. For us, addrspacecasts
|
|
between non-integral address spaces carry frontend information that the
|
|
optimizer cannot deduce afterwards in a generic way (though we
|
|
have frontend specific passes in our pipline that do propagate
|
|
these). In any case, I'm sure nobody is using it this way at
|
|
the moment, since it would have introduced inttoptrs, which
|
|
are definitely illegal.
|
|
|
|
Fixes PR38375
|
|
|
|
Reviewers: sanjoy, reames, dberlin
|
|
|
|
Subscribers: llvm-commits
|
|
|
|
Differential Revision: https://reviews.llvm.org/D50010
|
|
|
|
diff --git a/lib/Transforms/Utils/VNCoercion.cpp b/lib/Transforms/Utils/VNCoercion.cpp
|
|
index c3feea6a0a4..735d1e7b792 100644
|
|
--- a/lib/Transforms/Utils/VNCoercion.cpp
|
|
+++ b/lib/Transforms/Utils/VNCoercion.cpp
|
|
@@ -20,14 +20,21 @@ bool canCoerceMustAliasedValueToLoad(Value *StoredVal, Type *LoadTy,
|
|
StoredVal->getType()->isStructTy() || StoredVal->getType()->isArrayTy())
|
|
return false;
|
|
|
|
+ Type *StoredValTy = StoredVal->getType();
|
|
+
|
|
// The store has to be at least as big as the load.
|
|
if (DL.getTypeSizeInBits(StoredVal->getType()) < DL.getTypeSizeInBits(LoadTy))
|
|
return false;
|
|
|
|
- // Don't coerce non-integral pointers to integers or vice versa.
|
|
- if (DL.isNonIntegralPointerType(StoredVal->getType()) !=
|
|
- DL.isNonIntegralPointerType(LoadTy))
|
|
+ bool StoredNI = DL.isNonIntegralPointerType(StoredValTy);
|
|
+ bool LoadNI = DL.isNonIntegralPointerType(LoadTy);
|
|
+ if (StoredNI != LoadNI) {
|
|
return false;
|
|
+ } else if (StoredNI && LoadNI &&
|
|
+ cast<PointerType>(StoredValTy)->getAddressSpace() !=
|
|
+ cast<PointerType>(LoadTy)->getAddressSpace()) {
|
|
+ return false;
|
|
+ }
|
|
|
|
return true;
|
|
}
|
|
diff --git a/test/Transforms/GVN/non-integral-pointers.ll b/test/Transforms/GVN/non-integral-pointers.ll
|
|
index 9ae4132231d..5217fc1a06a 100644
|
|
--- a/test/Transforms/GVN/non-integral-pointers.ll
|
|
+++ b/test/Transforms/GVN/non-integral-pointers.ll
|
|
@@ -1,6 +1,6 @@
|
|
; RUN: opt -gvn -S < %s | FileCheck %s
|
|
|
|
-target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128-ni:4"
|
|
+target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128-ni:4:5"
|
|
target triple = "x86_64-unknown-linux-gnu"
|
|
|
|
define void @f0(i1 %alwaysFalse, i64 %val, i64* %loc) {
|
|
@@ -37,3 +37,21 @@ define i64 @f1(i1 %alwaysFalse, i8 addrspace(4)* %val, i8 addrspace(4)** %loc) {
|
|
alwaysTaken:
|
|
ret i64 42
|
|
}
|
|
+
|
|
+ define i8 addrspace(5)* @multini(i1 %alwaysFalse, i8 addrspace(4)* %val, i8 addrspace(4)** %loc) {
|
|
+ ; CHECK-LABEL: @multini(
|
|
+ ; CHECK-NOT: inttoptr
|
|
+ ; CHECK-NOT: ptrtoint
|
|
+ ; CHECK-NOT: addrspacecast
|
|
+ entry:
|
|
+ store i8 addrspace(4)* %val, i8 addrspace(4)** %loc
|
|
+ br i1 %alwaysFalse, label %neverTaken, label %alwaysTaken
|
|
+
|
|
+ neverTaken:
|
|
+ %loc.bc = bitcast i8 addrspace(4)** %loc to i8 addrspace(5)**
|
|
+ %differentas = load i8 addrspace(5)*, i8 addrspace(5)** %loc.bc
|
|
+ ret i8 addrspace(5)* %differentas
|
|
+
|
|
+ alwaysTaken:
|
|
+ ret i8 addrspace(5)* null
|
|
+ }
|