aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
diff options
context:
space:
mode:
authorLemonBoy <thatlemon@gmail.com>2021-05-22 09:40:00 +0200
committerLemonBoy <thatlemon@gmail.com>2021-05-22 09:43:37 +0200
commitfd5cc418186ab0fc0650ec373fdf016101eba21d (patch)
tree01573e2620eefbe066d05ab7cd54b311fb79a6ec /llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
parentc9c05a91c4843c243d508c39bdfbc5e26f311af2 (diff)
downloadllvm-fd5cc418186ab0fc0650ec373fdf016101eba21d.zip
llvm-fd5cc418186ab0fc0650ec373fdf016101eba21d.tar.gz
llvm-fd5cc418186ab0fc0650ec373fdf016101eba21d.tar.bz2
[SelectionDAG] Fix argument copy elision with irregular types
D29668 enabled to avoid a useless copy of the argument value into an alloca if the caller places it in memory (as it often happens on x86) by directly forwarding the pointer to it. This optimization is illegal if the type contains padding bytes: if a truncating store into the alloca is replaced the upper bits are filled with garbage and produce code misbehaving at runtime. Reviewed By: rnk Differential Revision: https://reviews.llvm.org/D102153
Diffstat (limited to 'llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp')
-rw-r--r--llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp6
1 files changed, 5 insertions, 1 deletions
diff --git a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
index 12b7b57..0031b18 100644
--- a/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
+++ b/llvm/lib/CodeGen/SelectionDAG/SelectionDAGBuilder.cpp
@@ -9886,13 +9886,17 @@ findArgumentCopyElisionCandidates(const DataLayout &DL,
continue;
// Check if the stored value is an argument, and that this store fully
- // initializes the alloca. Don't elide copies from the same argument twice.
+ // initializes the alloca.
+ // If the argument type has padding bits we can't directly forward a pointer
+ // as the upper bits may contain garbage.
+ // Don't elide copies from the same argument twice.
const Value *Val = SI->getValueOperand()->stripPointerCasts();
const auto *Arg = dyn_cast<Argument>(Val);
if (!Arg || Arg->hasPassPointeeByValueCopyAttr() ||
Arg->getType()->isEmptyTy() ||
DL.getTypeStoreSize(Arg->getType()) !=
DL.getTypeAllocSize(AI->getAllocatedType()) ||
+ !DL.typeSizeEqualsStoreSize(Arg->getType()) ||
ArgCopyElisionCandidates.count(Arg)) {
*Info = StaticAllocaInfo::Clobbered;
continue;