aboutsummaryrefslogtreecommitdiff
path: root/llvm/lib/Analysis/ConstantFolding.cpp
diff options
context:
space:
mode:
authorNikita Popov <npopov@redhat.com>2022-01-05 12:17:22 +0100
committerNikita Popov <npopov@redhat.com>2022-01-05 12:30:46 +0100
commit99c6b12b924f375a80540de721a2bc438ed3cf49 (patch)
tree3d9f4f58eb13d0f101b5411367f94bcd97ddb82c /llvm/lib/Analysis/ConstantFolding.cpp
parent00686ab4afd967fb3c10127a48096d72e4f218b5 (diff)
downloadllvm-99c6b12b924f375a80540de721a2bc438ed3cf49.zip
llvm-99c6b12b924f375a80540de721a2bc438ed3cf49.tar.gz
llvm-99c6b12b924f375a80540de721a2bc438ed3cf49.tar.bz2
[ConstantFolding] Unify handling of load from uniform value
There are a number of places that specially handle loads from a uniform value where all the bits are the same (zero, one, undef, poison), because we a) don't care about the load offset in that case b) it bypasses casts that might not be legal generally but do work with uniform values. We had multiple implementations of this, with a different set of supported values each time. This replaces two usages with a more complete helper. Other usages will be replaced separately, because they have larger impact. This is part of D115924.
Diffstat (limited to 'llvm/lib/Analysis/ConstantFolding.cpp')
-rw-r--r--llvm/lib/Analysis/ConstantFolding.cpp25
1 files changed, 18 insertions, 7 deletions
diff --git a/llvm/lib/Analysis/ConstantFolding.cpp b/llvm/lib/Analysis/ConstantFolding.cpp
index 7f7c9a5..e475f5e 100644
--- a/llvm/lib/Analysis/ConstantFolding.cpp
+++ b/llvm/lib/Analysis/ConstantFolding.cpp
@@ -704,15 +704,13 @@ Constant *llvm::ConstantFoldLoadFromConstPtr(Constant *C, Type *Ty,
Offset, DL))
return Result;
- // If this load comes from anywhere in a constant global, and if the global
- // is all undef or zero, we know what it loads.
+ // If this load comes from anywhere in a uniform constant global, the value
+ // is always the same, regardless of the loaded offset.
if (auto *GV = dyn_cast<GlobalVariable>(getUnderlyingObject(C))) {
if (GV->isConstant() && GV->hasDefinitiveInitializer()) {
- if (GV->getInitializer()->isNullValue() && !Ty->isX86_MMXTy() &&
- !Ty->isX86_AMXTy())
- return Constant::getNullValue(Ty);
- if (isa<UndefValue>(GV->getInitializer()))
- return UndefValue::get(Ty);
+ if (Constant *Res =
+ ConstantFoldLoadFromUniformValue(GV->getInitializer(), Ty))
+ return Res;
}
}
@@ -725,6 +723,19 @@ Constant *llvm::ConstantFoldLoadFromConstPtr(Constant *C, Type *Ty,
return ConstantFoldLoadFromConstPtr(C, Ty, Offset, DL);
}
+Constant *llvm::ConstantFoldLoadFromUniformValue(Constant *C, Type *Ty) {
+ if (isa<PoisonValue>(C))
+ return PoisonValue::get(Ty);
+ if (isa<UndefValue>(C))
+ return UndefValue::get(Ty);
+ if (C->isNullValue() && !Ty->isX86_MMXTy() && !Ty->isX86_AMXTy())
+ return Constant::getNullValue(Ty);
+ if (C->isAllOnesValue() &&
+ (Ty->isIntOrIntVectorTy() || Ty->isFPOrFPVectorTy()))
+ return Constant::getAllOnesValue(Ty);
+ return nullptr;
+}
+
namespace {
/// One of Op0/Op1 is a constant expression.