Skip to content

Commit 97db5d8

Browse files
committed
AliasAnalysis: handle global let-variables in ImmutableScope
Global let-variables are immutable, except in functions which initialize them. This brings back handling of global let-variables in alias analysis, which was removed in the previous commit.
1 parent a312732 commit 97db5d8

File tree

3 files changed

+89
-1
lines changed

3 files changed

+89
-1
lines changed

SwiftCompilerSources/Sources/Optimizer/Analysis/AliasAnalysis.swift

+14
Original file line numberDiff line numberDiff line change
@@ -615,6 +615,12 @@ private enum ImmutableScope {
615615
return nil
616616
}
617617
object = tailAddr.instance
618+
case .global(let global):
619+
if global.isLet && !basedAddress.parentFunction.canInitializeGlobal {
620+
self = .wholeFunction
621+
return
622+
}
623+
return nil
618624
default:
619625
return nil
620626
}
@@ -894,6 +900,14 @@ private extension Type {
894900
}
895901
}
896902

903+
private extension Function {
904+
var canInitializeGlobal: Bool {
905+
return isGlobalInitOnceFunction ||
906+
// In non -parse-as-library mode globals are initialized in the `main` function.
907+
name == "main"
908+
}
909+
}
910+
897911
//===--------------------------------------------------------------------===//
898912
// Bridging
899913
//===--------------------------------------------------------------------===//

test/SILOptimizer/copy-to-borrow-optimization.sil

+23
Original file line numberDiff line numberDiff line change
@@ -257,6 +257,29 @@ bb0(%x : @guaranteed $SubclassLet):
257257
return undef : $()
258258
}
259259

260+
// CHECK-LABEL: sil [ossa] @dont_copy_let_global :
261+
// CHECK: global_addr
262+
// CHECK-NEXT: load_borrow
263+
// CHECK-NEXT: begin_borrow
264+
// CHECK-NEXT: apply
265+
// CHECK-NEXT: end_borrow
266+
// CHECK-NEXT: end_borrow
267+
// CHECK-NEXT: return
268+
// CHECK-NEXT: } // end sil function 'dont_copy_let_global'
269+
sil [ossa] @dont_copy_let_global : $@convention(thin) () -> () {
270+
bb0:
271+
%f = function_ref @black_hole : $@convention(thin) (@guaranteed Klass) -> ()
272+
273+
%p = global_addr @a_let_global : $*Klass
274+
%v = load [copy] %p : $*Klass
275+
%b = begin_borrow %v : $Klass
276+
apply %f(%b) : $@convention(thin) (@guaranteed Klass) -> ()
277+
end_borrow %b : $Klass
278+
destroy_value %v : $Klass
279+
280+
return undef : $()
281+
}
282+
260283
// CHECK-LABEL: sil [ossa] @dont_copy_let_properties_with_guaranteed_base_structural
261284
// CHECK: ref_element_addr
262285
// CHECK-NEXT: tuple_element_addr

test/SILOptimizer/mem-behavior.sil

+52-1
Original file line numberDiff line numberDiff line change
@@ -841,12 +841,44 @@ bb0(%0 : $*C, %1 : $*C):
841841
sil_global hidden [let] @globalC : $C
842842
sil_global hidden @globalCVar : $C
843843

844+
// CHECK-LABEL: @testGlobalLet
845+
// CHECK: PAIR #1.
846+
// CHECK-NEXT: %3 = apply %2() : $@convention(thin) () -> ()
847+
// CHECK-NEXT: %0 = global_addr @globalC : $*C
848+
// CHECK-NEXT: r=1,w=0
849+
sil hidden @testGlobalLet : $@convention(thin) () -> () {
850+
bb0:
851+
%0 = global_addr @globalC : $*C
852+
%1 = load %0 : $*C
853+
%2 = function_ref @nouser_func : $@convention(thin) () -> ()
854+
%3 = apply %2() : $@convention(thin) () -> ()
855+
%4 = function_ref @read_C : $@convention(thin) (@in_guaranteed C) -> ()
856+
%5 = apply %4(%0) : $@convention(thin) (@in_guaranteed C) -> ()
857+
%8 = tuple ()
858+
return %8 : $()
859+
}
860+
844861
// CHECK-LABEL: @testInitGlobalLet
845862
// CHECK: PAIR #0.
846863
// CHECK-NEXT: %2 = apply %1(%0) : $@convention(thin) () -> @out C
847864
// CHECK-NEXT: %0 = global_addr @globalC : $*C
848865
// CHECK-NEXT: r=1,w=1
849-
sil hidden @testInitGlobalLet : $@convention(thin) () -> () {
866+
sil hidden [global_init_once_fn] @testInitGlobalLet : $@convention(thin) () -> () {
867+
bb0:
868+
%0 = global_addr @globalC : $*C
869+
%1 = function_ref @init_C : $@convention(thin) () -> @out C
870+
%2 = apply %1(%0) : $@convention(thin) () -> @out C
871+
%3 = load %0 : $*C
872+
%8 = tuple ()
873+
return %8 : $()
874+
}
875+
876+
// CHECK-LABEL: @main
877+
// CHECK: PAIR #0.
878+
// CHECK-NEXT: %2 = apply %1(%0) : $@convention(thin) () -> @out C
879+
// CHECK-NEXT: %0 = global_addr @globalC : $*C
880+
// CHECK-NEXT: r=1,w=1
881+
sil [global_init_once_fn] @main : $@convention(thin) () -> () {
850882
bb0:
851883
%0 = global_addr @globalC : $*C
852884
%1 = function_ref @init_C : $@convention(thin) () -> @out C
@@ -885,6 +917,25 @@ bb0:
885917
return %1 : $Builtin.RawPointer
886918
}
887919

920+
// CHECK-LABEL: @testGlobalViaAddressorLet
921+
// CHECK: PAIR #2.
922+
// CHECK-NEXT: %5 = apply %4() : $@convention(thin) () -> ()
923+
// CHECK-NEXT: %2 = pointer_to_address %1 : $Builtin.RawPointer to [strict] $*C
924+
// CHECK-NEXT: r=1,w=0
925+
sil @testGlobalViaAddressorLet : $@convention(thin) () -> () {
926+
bb0:
927+
%0 = function_ref @addressor_of_globalC : $@convention(thin) () -> Builtin.RawPointer
928+
%1 = apply %0() : $@convention(thin) () -> Builtin.RawPointer
929+
%2 = pointer_to_address %1 : $Builtin.RawPointer to [strict] $*C
930+
%3 = load %2 : $*C
931+
%4 = function_ref @nouser_func : $@convention(thin) () -> ()
932+
%5 = apply %4() : $@convention(thin) () -> ()
933+
%6 = function_ref @read_C : $@convention(thin) (@in_guaranteed C) -> ()
934+
%7 = apply %6(%2) : $@convention(thin) (@in_guaranteed C) -> ()
935+
%8 = tuple ()
936+
return %8 : $()
937+
}
938+
888939
// CHECK-LABEL: @testGlobalViaAddressorVar
889940
// CHECK: PAIR #2.
890941
// CHECK-NEXT: %5 = apply %4() : $@convention(thin) () -> ()

0 commit comments

Comments
 (0)