summaryrefslogtreecommitdiffstats
path: root/llvm/lib
diff options
context:
space:
mode:
authorEric Fiselier <eric@efcs.ca>2018-04-04 19:01:51 +0000
committerEric Fiselier <eric@efcs.ca>2018-04-04 19:01:51 +0000
commit96bbec79b4e8db04befd9d7aa2647d222fab7cab (patch)
tree6da228213b980ffca65a08eb8a2e6155f8e1adca /llvm/lib
parente03d45fa8e3190f81d06f3970e57b71b8875d9a4 (diff)
downloadbcm5719-llvm-96bbec79b4e8db04befd9d7aa2647d222fab7cab.tar.gz
bcm5719-llvm-96bbec79b4e8db04befd9d7aa2647d222fab7cab.zip
[Analysis] Support aligned new/delete functions.
Summary: Clang's __builtin_operator_new/delete was recently taught about the aligned allocation overloads (r328134). This patch makes LLVM aware of them as well. This allows the compiler to perform certain optimizations including eliding new/delete calls. Reviewers: rsmith, majnemer, dblaikie, vsk, bkramer Reviewed By: bkramer Subscribers: ckennelly, llvm-commits Differential Revision: https://reviews.llvm.org/D44769 llvm-svn: 329218
Diffstat (limited to 'llvm/lib')
-rw-r--r--llvm/lib/Analysis/MemoryBuiltins.cpp17
-rw-r--r--llvm/lib/Analysis/TargetLibraryInfo.cpp28
2 files changed, 45 insertions, 0 deletions
diff --git a/llvm/lib/Analysis/MemoryBuiltins.cpp b/llvm/lib/Analysis/MemoryBuiltins.cpp
index 8c0c374d530..2e5197a8ff1 100644
--- a/llvm/lib/Analysis/MemoryBuiltins.cpp
+++ b/llvm/lib/Analysis/MemoryBuiltins.cpp
@@ -75,12 +75,24 @@ static const std::pair<LibFunc, AllocFnsTy> AllocationFnData[] = {
{LibFunc_valloc, {MallocLike, 1, 0, -1}},
{LibFunc_Znwj, {OpNewLike, 1, 0, -1}}, // new(unsigned int)
{LibFunc_ZnwjRKSt9nothrow_t, {MallocLike, 2, 0, -1}}, // new(unsigned int, nothrow)
+ {LibFunc_ZnwjSt11align_val_t, {OpNewLike, 2, 0, -1}}, // new(unsigned int, align_val_t)
+ {LibFunc_ZnwjSt11align_val_tRKSt9nothrow_t, // new(unsigned int, align_val_t, nothrow)
+ {MallocLike, 3, 0, -1}},
{LibFunc_Znwm, {OpNewLike, 1, 0, -1}}, // new(unsigned long)
{LibFunc_ZnwmRKSt9nothrow_t, {MallocLike, 2, 0, -1}}, // new(unsigned long, nothrow)
+ {LibFunc_ZnwmSt11align_val_t, {OpNewLike, 2, 0, -1}}, // new(unsigned long, align_val_t)
+ {LibFunc_ZnwmSt11align_val_tRKSt9nothrow_t, // new(unsigned long, align_val_t, nothrow)
+ {MallocLike, 3, 0, -1}},
{LibFunc_Znaj, {OpNewLike, 1, 0, -1}}, // new[](unsigned int)
{LibFunc_ZnajRKSt9nothrow_t, {MallocLike, 2, 0, -1}}, // new[](unsigned int, nothrow)
+ {LibFunc_ZnajSt11align_val_t, {OpNewLike, 2, 0, -1}}, // new[](unsigned int, align_val_t)
+ {LibFunc_ZnajSt11align_val_tRKSt9nothrow_t, // new[](unsigned int, align_val_t, nothrow)
+ {MallocLike, 3, 0, -1}},
{LibFunc_Znam, {OpNewLike, 1, 0, -1}}, // new[](unsigned long)
{LibFunc_ZnamRKSt9nothrow_t, {MallocLike, 2, 0, -1}}, // new[](unsigned long, nothrow)
+ {LibFunc_ZnamSt11align_val_t, {OpNewLike, 2, 0, -1}}, // new[](unsigned long, align_val_t)
+ {LibFunc_ZnamSt11align_val_tRKSt9nothrow_t, // new[](unsigned long, align_val_t, nothrow)
+ {MallocLike, 3, 0, -1}},
{LibFunc_msvc_new_int, {OpNewLike, 1, 0, -1}}, // new(unsigned int)
{LibFunc_msvc_new_int_nothrow, {MallocLike, 2, 0, -1}}, // new(unsigned int, nothrow)
{LibFunc_msvc_new_longlong, {OpNewLike, 1, 0, -1}}, // new(unsigned long long)
@@ -372,9 +384,11 @@ const CallInst *llvm::isFreeCall(const Value *I, const TargetLibraryInfo *TLI) {
else if (TLIFn == LibFunc_ZdlPvj || // delete(void*, uint)
TLIFn == LibFunc_ZdlPvm || // delete(void*, ulong)
TLIFn == LibFunc_ZdlPvRKSt9nothrow_t || // delete(void*, nothrow)
+ TLIFn == LibFunc_ZdlPvSt11align_val_t || // delete(void*, align_val_t)
TLIFn == LibFunc_ZdaPvj || // delete[](void*, uint)
TLIFn == LibFunc_ZdaPvm || // delete[](void*, ulong)
TLIFn == LibFunc_ZdaPvRKSt9nothrow_t || // delete[](void*, nothrow)
+ TLIFn == LibFunc_ZdaPvSt11align_val_t || // delete[](void*, align_val_t)
TLIFn == LibFunc_msvc_delete_ptr32_int || // delete(void*, uint)
TLIFn == LibFunc_msvc_delete_ptr64_longlong || // delete(void*, ulonglong)
TLIFn == LibFunc_msvc_delete_ptr32_nothrow || // delete(void*, nothrow)
@@ -384,6 +398,9 @@ const CallInst *llvm::isFreeCall(const Value *I, const TargetLibraryInfo *TLI) {
TLIFn == LibFunc_msvc_delete_array_ptr32_nothrow || // delete[](void*, nothrow)
TLIFn == LibFunc_msvc_delete_array_ptr64_nothrow) // delete[](void*, nothrow)
ExpectedNumParams = 2;
+ else if (TLIFn == LibFunc_ZdaPvSt11align_val_tRKSt9nothrow_t || // delete(void*, align_val_t, nothrow)
+ TLIFn == LibFunc_ZdlPvSt11align_val_tRKSt9nothrow_t) // delete[](void*, align_val_t, nothrow)
+ ExpectedNumParams = 3;
else
return nullptr;
diff --git a/llvm/lib/Analysis/TargetLibraryInfo.cpp b/llvm/lib/Analysis/TargetLibraryInfo.cpp
index c605c91c11c..ff6aae8b5ec 100644
--- a/llvm/lib/Analysis/TargetLibraryInfo.cpp
+++ b/llvm/lib/Analysis/TargetLibraryInfo.cpp
@@ -992,8 +992,26 @@ bool TargetLibraryInfoImpl::isValidProtoForLibFunc(const FunctionType &FTy,
case LibFunc_msvc_new_array_int_nothrow:
// new[](unsigned long long, nothrow);
case LibFunc_msvc_new_array_longlong_nothrow:
+ // new(unsigned int, align_val_t)
+ case LibFunc_ZnwjSt11align_val_t:
+ // new(unsigned long, align_val_t)
+ case LibFunc_ZnwmSt11align_val_t:
+ // new[](unsigned int, align_val_t)
+ case LibFunc_ZnajSt11align_val_t:
+ // new[](unsigned long, align_val_t)
+ case LibFunc_ZnamSt11align_val_t:
return (NumParams == 2 && FTy.getReturnType()->isPointerTy());
+ // new(unsigned int, align_val_t, nothrow)
+ case LibFunc_ZnwjSt11align_val_tRKSt9nothrow_t:
+ // new(unsigned long, align_val_t, nothrow)
+ case LibFunc_ZnwmSt11align_val_tRKSt9nothrow_t:
+ // new[](unsigned int, align_val_t, nothrow)
+ case LibFunc_ZnajSt11align_val_tRKSt9nothrow_t:
+ // new[](unsigned long, align_val_t, nothrow)
+ case LibFunc_ZnamSt11align_val_tRKSt9nothrow_t:
+ return (NumParams == 3 && FTy.getReturnType()->isPointerTy());
+
// void operator delete[](void*);
case LibFunc_ZdaPv:
// void operator delete(void*);
@@ -1020,6 +1038,10 @@ bool TargetLibraryInfoImpl::isValidProtoForLibFunc(const FunctionType &FTy,
case LibFunc_ZdlPvj:
// void operator delete(void*, unsigned long);
case LibFunc_ZdlPvm:
+ // void operator delete(void*, align_val_t)
+ case LibFunc_ZdlPvSt11align_val_t:
+ // void operator delete[](void*, align_val_t)
+ case LibFunc_ZdaPvSt11align_val_t:
// void operator delete[](void*, unsigned int);
case LibFunc_msvc_delete_array_ptr32_int:
// void operator delete[](void*, nothrow);
@@ -1038,6 +1060,12 @@ bool TargetLibraryInfoImpl::isValidProtoForLibFunc(const FunctionType &FTy,
case LibFunc_msvc_delete_ptr64_nothrow:
return (NumParams == 2 && FTy.getParamType(0)->isPointerTy());
+ // void operator delete(void*, align_val_t, nothrow)
+ case LibFunc_ZdlPvSt11align_val_tRKSt9nothrow_t:
+ // void operator delete[](void*, align_val_t, nothrow)
+ case LibFunc_ZdaPvSt11align_val_tRKSt9nothrow_t:
+ return (NumParams == 3 && FTy.getParamType(0)->isPointerTy());
+
case LibFunc_memset_pattern16:
return (!FTy.isVarArg() && NumParams == 3 &&
FTy.getParamType(0)->isPointerTy() &&
OpenPOWER on IntegriCloud