mirror of
https://github.com/apple/swift.git
synced 2025-12-21 12:14:44 +01:00
[mem-access-utils] Refactor isSingleInitAllocStack into getSingleInitAllocStackUse and rewrite the former in terms of the first.
This enabled me to expand this API to return the underlying single init use. I want this information in OptRemarkGen.
This commit is contained in:
@@ -1545,12 +1545,13 @@ bool swift::memInstMustInitialize(Operand *memOper) {
|
||||
}
|
||||
}
|
||||
|
||||
bool swift::isSingleInitAllocStack(AllocStackInst *asi,
|
||||
SmallVectorImpl<Operand *> &destroyingUses) {
|
||||
Operand *
|
||||
swift::getSingleInitAllocStackUse(AllocStackInst *asi,
|
||||
SmallVectorImpl<Operand *> *destroyingUses) {
|
||||
// For now, we just look through projections and rely on memInstMustInitialize
|
||||
// to classify all other uses as init or not.
|
||||
SmallVector<Operand *, 32> worklist(asi->getUses());
|
||||
bool foundInit = false;
|
||||
Operand *singleInit = nullptr;
|
||||
|
||||
while (!worklist.empty()) {
|
||||
auto *use = worklist.pop_back_val();
|
||||
@@ -1571,14 +1572,15 @@ bool swift::isSingleInitAllocStack(AllocStackInst *asi,
|
||||
continue;
|
||||
}
|
||||
// Treat load [take] as a write.
|
||||
return false;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
switch (user->getKind()) {
|
||||
default:
|
||||
break;
|
||||
case SILInstructionKind::DestroyAddrInst:
|
||||
destroyingUses.push_back(use);
|
||||
if (destroyingUses)
|
||||
destroyingUses->push_back(use);
|
||||
continue;
|
||||
case SILInstructionKind::DeallocStackInst:
|
||||
case SILInstructionKind::LoadBorrowInst:
|
||||
@@ -1589,21 +1591,21 @@ bool swift::isSingleInitAllocStack(AllocStackInst *asi,
|
||||
// See if we have an initializer and that such initializer is in the same
|
||||
// block.
|
||||
if (memInstMustInitialize(use)) {
|
||||
if (user->getParent() != asi->getParent() || foundInit) {
|
||||
return false;
|
||||
if (user->getParent() != asi->getParent() || singleInit) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
foundInit = true;
|
||||
singleInit = use;
|
||||
continue;
|
||||
}
|
||||
|
||||
// Otherwise, if we have found something not in our allowlist, return false.
|
||||
return false;
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
// We did not find any users that we did not understand. So we can
|
||||
// conservatively return true here.
|
||||
return true;
|
||||
// conservatively return the single initializing write that we found.
|
||||
return singleInit;
|
||||
}
|
||||
|
||||
/// Return true if the given address value is produced by a special address
|
||||
|
||||
Reference in New Issue
Block a user