summaryrefslogtreecommitdiff
path: root/llvm/lib/IR/Globals.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'llvm/lib/IR/Globals.cpp')
-rw-r--r--llvm/lib/IR/Globals.cpp37
1 files changed, 25 insertions, 12 deletions
diff --git a/llvm/lib/IR/Globals.cpp b/llvm/lib/IR/Globals.cpp
index 3265050261c8..51a22897babd 100644
--- a/llvm/lib/IR/Globals.cpp
+++ b/llvm/lib/IR/Globals.cpp
@@ -316,32 +316,38 @@ bool GlobalObject::canIncreaseAlignment() const {
return true;
}
+template <typename Operation>
static const GlobalObject *
-findBaseObject(const Constant *C, DenseSet<const GlobalAlias *> &Aliases) {
- if (auto *GO = dyn_cast<GlobalObject>(C))
+findBaseObject(const Constant *C, DenseSet<const GlobalAlias *> &Aliases,
+ const Operation &Op) {
+ if (auto *GO = dyn_cast<GlobalObject>(C)) {
+ Op(*GO);
return GO;
- if (auto *GA = dyn_cast<GlobalAlias>(C))
+ }
+ if (auto *GA = dyn_cast<GlobalAlias>(C)) {
+ Op(*GA);
if (Aliases.insert(GA).second)
- return findBaseObject(GA->getOperand(0), Aliases);
+ return findBaseObject(GA->getOperand(0), Aliases, Op);
+ }
if (auto *CE = dyn_cast<ConstantExpr>(C)) {
switch (CE->getOpcode()) {
case Instruction::Add: {
- auto *LHS = findBaseObject(CE->getOperand(0), Aliases);
- auto *RHS = findBaseObject(CE->getOperand(1), Aliases);
+ auto *LHS = findBaseObject(CE->getOperand(0), Aliases, Op);
+ auto *RHS = findBaseObject(CE->getOperand(1), Aliases, Op);
if (LHS && RHS)
return nullptr;
return LHS ? LHS : RHS;
}
case Instruction::Sub: {
- if (findBaseObject(CE->getOperand(1), Aliases))
+ if (findBaseObject(CE->getOperand(1), Aliases, Op))
return nullptr;
- return findBaseObject(CE->getOperand(0), Aliases);
+ return findBaseObject(CE->getOperand(0), Aliases, Op);
}
case Instruction::IntToPtr:
case Instruction::PtrToInt:
case Instruction::BitCast:
case Instruction::GetElementPtr:
- return findBaseObject(CE->getOperand(0), Aliases);
+ return findBaseObject(CE->getOperand(0), Aliases, Op);
default:
break;
}
@@ -351,7 +357,7 @@ findBaseObject(const Constant *C, DenseSet<const GlobalAlias *> &Aliases) {
const GlobalObject *GlobalValue::getAliaseeObject() const {
DenseSet<const GlobalAlias *> Aliases;
- return findBaseObject(this, Aliases);
+ return findBaseObject(this, Aliases, [](const GlobalValue &) {});
}
bool GlobalValue::isAbsoluteSymbolRef() const {
@@ -544,7 +550,7 @@ void GlobalAlias::setAliasee(Constant *Aliasee) {
const GlobalObject *GlobalAlias::getAliaseeObject() const {
DenseSet<const GlobalAlias *> Aliases;
- return findBaseObject(getOperand(0), Aliases);
+ return findBaseObject(getOperand(0), Aliases, [](const GlobalValue &) {});
}
//===----------------------------------------------------------------------===//
@@ -577,5 +583,12 @@ void GlobalIFunc::eraseFromParent() {
const Function *GlobalIFunc::getResolverFunction() const {
DenseSet<const GlobalAlias *> Aliases;
- return dyn_cast<Function>(findBaseObject(getResolver(), Aliases));
+ return dyn_cast<Function>(
+ findBaseObject(getResolver(), Aliases, [](const GlobalValue &) {}));
+}
+
+void GlobalIFunc::applyAlongResolverPath(
+ function_ref<void(const GlobalValue &)> Op) const {
+ DenseSet<const GlobalAlias *> Aliases;
+ findBaseObject(getResolver(), Aliases, Op);
}