Skip to content

Commit e042918

Browse files
committed
use worklist
1 parent da187ea commit e042918

File tree

1 file changed

+31
-24
lines changed

1 file changed

+31
-24
lines changed

llvm/lib/IR/Verifier.cpp

Lines changed: 31 additions & 24 deletions
Original file line numberDiff line numberDiff line change
@@ -3653,20 +3653,22 @@ void Verifier::visitCallBase(CallBase &Call) {
36533653
// well.
36543654
for (unsigned i = 0, e = FTy->getNumParams(); i != e; ++i) {
36553655
if (Call.paramHasAttr(i, Attribute::SwiftError)) {
3656-
SetVector<const Value *> Args;
3657-
Args.insert(Call.getArgOperand(i));
3658-
bool DidChange;
3659-
do {
3660-
DidChange = false;
3661-
// Inherit the incoming values of phi instructions to capture all
3662-
// values.
3663-
for (const Value *Arg : Args)
3664-
if (auto *PhiI = dyn_cast<PHINode>(Arg))
3665-
for (const auto &Op : PhiI->incoming_values())
3666-
DidChange |= Args.insert(Op.get());
3667-
} while (DidChange);
3668-
3669-
for (const Value *SwiftErrorArg : Args) {
3656+
const Value *Arg = Call.getArgOperand(i);
3657+
SetVector<const Value *> Values;
3658+
Values.insert(Arg);
3659+
SmallVector<const PHINode *> PHIWorkList;
3660+
if (auto *PhiI = dyn_cast<PHINode>(Arg))
3661+
PHIWorkList.push_back(PhiI);
3662+
3663+
while (!PHIWorkList.empty()) {
3664+
const auto *PhiI = PHIWorkList.pop_back_val();
3665+
for (const auto &Op : PhiI->incoming_values()) {
3666+
const auto *NextPhiI = dyn_cast<PHINode>(Op.get());
3667+
if (Values.insert(Op.get()) && NextPhiI)
3668+
PHIWorkList.push_back(NextPhiI);
3669+
}
3670+
}
3671+
for (const Value *SwiftErrorArg : Values) {
36703672
if (isa<PHINode>(SwiftErrorArg))
36713673
continue;
36723674
if (auto AI =
@@ -4376,21 +4378,26 @@ void Verifier::verifySwiftErrorCall(CallBase &Call,
43764378
void Verifier::verifySwiftErrorValue(const Value *SwiftErrorVal) {
43774379
SetVector<const User *> Users(SwiftErrorVal->users().begin(),
43784380
SwiftErrorVal->users().end());
4379-
bool DidChange;
4380-
do {
4381-
DidChange = false;
4382-
// Inherit the users of phi instructions to capture all users.
4383-
for (const User *U : Users)
4384-
if (auto PhiI = dyn_cast<PHINode>(U))
4385-
for (const User *U : PhiI->users())
4386-
DidChange |= Users.insert(U);
4387-
} while (DidChange);
4381+
SmallVector<const PHINode *> PHIWorkList;
4382+
for (const User *U : Users)
4383+
if (auto *PhiI = dyn_cast<PHINode>(U))
4384+
PHIWorkList.push_back(PhiI);
43884385

4386+
while (!PHIWorkList.empty()) {
4387+
const auto *PhiI = PHIWorkList.pop_back_val();
4388+
for (const User *U : PhiI->users()) {
4389+
const auto *NextPhiI = dyn_cast<PHINode>(U);
4390+
if (Users.insert(U) && NextPhiI)
4391+
PHIWorkList.push_back(NextPhiI);
4392+
}
4393+
}
43894394
// Check that swifterror value is only used by loads, stores, or as
43904395
// a swifterror argument.
43914396
for (const User *U : Users) {
4397+
if (isa<PHINode>(U))
4398+
continue;
43924399
Check(isa<LoadInst>(U) || isa<StoreInst>(U) || isa<CallInst>(U) ||
4393-
isa<InvokeInst>(U) || isa<PHINode>(U),
4400+
isa<InvokeInst>(U),
43944401
"swifterror value can only be loaded and stored from, or "
43954402
"as a swifterror argument!",
43964403
SwiftErrorVal, U);

0 commit comments

Comments
 (0)