Skip to content

Commit 009ed74

Browse files
Merge pull request #41753 from nate-chandler/lexical_lifetimes/lexical_destroy_addr_hoisting/pointer-handling
[SSADestroyHoisting] Pointer handling.
2 parents 4a5962f + 4ffde96 commit 009ed74

File tree

2 files changed

+43
-7
lines changed

2 files changed

+43
-7
lines changed

lib/SILOptimizer/Transforms/SSADestroyHoisting.cpp

Lines changed: 5 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -173,13 +173,11 @@ struct KnownStorageUses : UniqueStorageUseVisitor {
173173

174174
bool visitUnknownUse(Operand *use) override {
175175
auto *user = use->getUser();
176-
// Recognize any leaf users not already recognized by UniqueAddressUses.
177-
//
178-
// Destroy hoisting considers address_to_pointer to be a leaf use because
179-
// any potential pointer access is already considered to be a
180-
// deinitializtion barrier.
181-
if (isa<PointerToAddressInst>(user)) {
182-
storageUsers.insert(use->getUser());
176+
if (isa<BuiltinRawPointerType>(use->get()->getType().getASTType())) {
177+
// Destroy hoisting considers address_to_pointer to be a leaf use because
178+
// any potential pointer access is already considered to be a
179+
// deinitializtion barrier. Consequently, any instruction that uses a
180+
// value produced by address_to_pointer isn't regarded as a storage use.
183181
return true;
184182
}
185183
LLVM_DEBUG(llvm::dbgs() << "Unknown user " << *user);

test/SILOptimizer/hoist_destroy_addr.sil

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -365,6 +365,44 @@ entry(%addr : $*X, %instance : @owned $X):
365365
return %retval : $()
366366
}
367367

368+
// Hoist up to a (transitive) use of an address_to_pointer instruction. In
369+
// particular, do _some_ hoisting despite the fact that such an instruction is
370+
// a use.
371+
//
372+
// CHECK-LABEL: sil [ossa] @hoist_upto_address_to_pointer_use : {{.*}} {
373+
// CHECK: address_to_pointer
374+
// CHECK: pointer_to_address
375+
// CHECK: load [copy]
376+
// CHECK: destroy_addr
377+
// CHECK: tuple
378+
// CHECK-LABEL: } // end sil function 'hoist_upto_address_to_pointer_use'
379+
sil [ossa] @hoist_upto_address_to_pointer_use : $@convention(thin) (@in X) -> (@owned X) {
380+
entry(%instance : $*X):
381+
%pointer = address_to_pointer %instance : $*X to $Builtin.RawPointer
382+
%addr = pointer_to_address %pointer : $Builtin.RawPointer to $*X
383+
%value = load [copy] %addr : $*X
384+
%retval = tuple ()
385+
destroy_addr %instance : $*X
386+
return %value : $X
387+
}
388+
389+
// Hoist even if the pointerified address gets used.
390+
//
391+
// CHECK-LABEL: sil [ossa] @hoist_despite_use_of_pointer : {{.*}} {
392+
// CHECK: {{bb[0-9]+}}([[INSTANCE:%[^,]+]] :
393+
// CHECK-NEXT: destroy_addr [[INSTANCE]]
394+
// CHECK-LABEL: } // end sil function 'hoist_despite_use_of_pointer'
395+
sil [ossa] @hoist_despite_use_of_pointer : $@convention(thin) (@inout X) -> () {
396+
entry(%instance : $*X):
397+
%addr_for_pointer = alloc_stack $Builtin.RawPointer
398+
%pointer = address_to_pointer %instance : $*X to $Builtin.RawPointer
399+
store %pointer to [trivial] %addr_for_pointer : $*Builtin.RawPointer
400+
%retval = tuple ()
401+
destroy_addr %instance : $*X
402+
dealloc_stack %addr_for_pointer : $*Builtin.RawPointer
403+
return %retval : $()
404+
}
405+
368406
// Fold destroy_addr and a load [copy] into a load [take] even when that
369407
// load [take] is guarded by an access scope.
370408
//

0 commit comments

Comments
 (0)