Skip to content

Commit bc99986

Browse files
committed
SIL: add a dependency token operand to global_addr
Optionally, the dependency to the initialization of the global can be specified with a dependency token `depends_on <token>`. This is usually a `builtin "once"` which calls the initializer for the global variable.
1 parent eaabcfd commit bc99986

31 files changed

+198
-77
lines changed

SwiftCompilerSources/Sources/Optimizer/FunctionPasses/AllocVectorLowering.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -246,7 +246,7 @@ private func createOutlinedGlobal(
246246
}
247247

248248
let builder = Builder(before: allocVectorBuiltin, context)
249-
let globalAddr = builder.createGlobalAddr(global: outlinedGlobal)
249+
let globalAddr = builder.createGlobalAddr(global: outlinedGlobal, dependencyToken: nil)
250250
let rawVectorPointer = builder.createAddressToPointer(address: globalAddr, pointerType: allocVectorBuiltin.type,
251251
needStackProtection: false)
252252
allocVectorBuiltin.uses.replaceAll(with: rawVectorPointer, context)

SwiftCompilerSources/Sources/Optimizer/FunctionPasses/ObjectOutliner.swift

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -503,7 +503,7 @@ private func replace(findStringCall: ApplyInst,
503503
_ = varBuilder.createStruct(type: cacheType, elements: [zero, zero])
504504

505505
let builder = Builder(before: findStringCall, context)
506-
let cacheAddr = builder.createGlobalAddr(global: cacheVar)
506+
let cacheAddr = builder.createGlobalAddr(global: cacheVar, dependencyToken: nil)
507507
let findStringRef = builder.createFunctionRef(cachedFindStringFunc)
508508
let newCall = builder.createApply(function: findStringRef, SubstitutionMap(),
509509
arguments: [findStringCall.arguments[0],

SwiftCompilerSources/Sources/Optimizer/InstructionSimplification/SimplifyBuiltin.swift

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -109,6 +109,10 @@ private extension BuiltinInst {
109109
if callee.instructions.contains(where: hasSideEffectForBuiltinOnce) {
110110
return
111111
}
112+
for use in uses {
113+
let ga = use.instruction as! GlobalAddrInst
114+
ga.clearToken(context)
115+
}
112116
context.erase(instruction: self)
113117
}
114118

SwiftCompilerSources/Sources/Optimizer/InstructionSimplification/SimplifyLoad.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -110,6 +110,8 @@ extension LoadInst : OnoneSimplifyable, SILCombineSimplifyable {
110110
let initVal = cloner.clone(globalInitVal)
111111

112112
uses.replaceAll(with: initVal, context)
113+
// Also erases a builtin "once" on which the global_addr depends on. This is fine
114+
// because we only replace the load if the global init function doesn't have any side effect.
113115
transitivelyErase(load: self, context)
114116
return true
115117
}

SwiftCompilerSources/Sources/Optimizer/PassManager/Context.swift

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -535,6 +535,14 @@ extension RefElementAddrInst {
535535
}
536536
}
537537

538+
extension GlobalAddrInst {
539+
func clearToken(_ context: some MutatingContext) {
540+
context.notifyInstructionsChanged()
541+
bridged.GlobalAddrInst_clearToken()
542+
context.notifyInstructionChanged(self)
543+
}
544+
}
545+
538546
extension GlobalValueInst {
539547
func setIsBare(_ context: some MutatingContext) {
540548
context.notifyInstructionsChanged()

SwiftCompilerSources/Sources/SIL/Builder.swift

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -305,8 +305,8 @@ public struct Builder {
305305
return notifyNew(vectorInst.getAs(VectorInst.self))
306306
}
307307

308-
public func createGlobalAddr(global: GlobalVariable) -> GlobalAddrInst {
309-
return notifyNew(bridged.createGlobalAddr(global.bridged).getAs(GlobalAddrInst.self))
308+
public func createGlobalAddr(global: GlobalVariable, dependencyToken: Value?) -> GlobalAddrInst {
309+
return notifyNew(bridged.createGlobalAddr(global.bridged, dependencyToken.bridged).getAs(GlobalAddrInst.self))
310310
}
311311

312312
public func createGlobalValue(global: GlobalVariable, isBare: Bool) -> GlobalValueInst {

SwiftCompilerSources/Sources/SIL/Instruction.swift

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -650,6 +650,10 @@ final public class GlobalAddrInst : GlobalAccessInst, VarDeclInstruction {
650650
public var varDecl: VarDecl? {
651651
VarDecl(bridged: bridged.GlobalAddr_getDecl())
652652
}
653+
654+
public var dependencyToken: Value? {
655+
operands.count == 1 ? operands[0].value : nil
656+
}
653657
}
654658

655659
final public class GlobalValueInst : GlobalAccessInst {

docs/SIL.rst

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -5739,15 +5739,21 @@ global_addr
57395739

57405740
::
57415741

5742-
sil-instruction ::= 'global_addr' sil-global-name ':' sil-type
5742+
sil-instruction ::= 'global_addr' sil-global-name ':' sil-type ('depends_on' sil-operand)?
57435743

57445744
%1 = global_addr @foo : $*Builtin.Word
5745+
%3 = global_addr @globalvar : $*Builtin.Word depends_on %2
5746+
// %2 has type $Builtin.SILToken
57455747

57465748
Creates a reference to the address of a global variable which has been
57475749
previously initialized by ``alloc_global``. It is undefined behavior to
57485750
perform this operation on a global variable which has not been
57495751
initialized, except the global variable has a static initializer.
57505752

5753+
Optionally, the dependency to the initialization of the global can be
5754+
specified with a dependency token ``depends_on <token>``. This is usually
5755+
a ``builtin "once"`` which calls the initializer for the global variable.
5756+
57515757
global_value
57525758
`````````````
57535759
::

include/swift/AST/DiagnosticsParse.def

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1502,6 +1502,9 @@ WARNING(warning_in_effects_attribute,none,
15021502
ERROR(expected_in_attribute_list,none,
15031503
"expected ']' or ',' in attribute list", ())
15041504

1505+
ERROR(expected_depends_on,none,
1506+
"expected 'depends_on'", ())
1507+
15051508
ERROR(type_attribute_applied_to_decl,none,
15061509
"attribute can only be applied to types, not declarations", ())
15071510
ERROR(decl_attribute_applied_to_type,none,

include/swift/SIL/SILBridging.h

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -809,6 +809,7 @@ struct BridgedInstruction {
809809
BRIDGED_INLINE void TermInst_replaceBranchTarget(BridgedBasicBlock from, BridgedBasicBlock to) const;
810810
BRIDGED_INLINE SwiftInt KeyPathInst_getNumComponents() const;
811811
BRIDGED_INLINE void KeyPathInst_getReferencedFunctions(SwiftInt componentIdx, KeyPathFunctionResults * _Nonnull results) const;
812+
BRIDGED_INLINE void GlobalAddrInst_clearToken() const;
812813
BRIDGED_INLINE bool GlobalValueInst_isBare() const;
813814
BRIDGED_INLINE void GlobalValueInst_setIsBare() const;
814815
BRIDGED_INLINE void LoadInst_setOwnership(SwiftInt ownership) const;
@@ -1093,7 +1094,8 @@ struct BridgedBuilder{
10931094
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createObject(BridgedType type, BridgedValueArray arguments,
10941095
SwiftInt numBaseElements) const;
10951096
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createVector(BridgedValueArray arguments) const;
1096-
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createGlobalAddr(BridgedGlobalVar global) const;
1097+
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createGlobalAddr(BridgedGlobalVar global,
1098+
OptionalBridgedValue dependencyToken) const;
10971099
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createGlobalValue(BridgedGlobalVar global,
10981100
bool isBare) const;
10991101
SWIFT_IMPORT_UNSAFE BRIDGED_INLINE BridgedInstruction createStruct(BridgedType type,

0 commit comments

Comments
 (0)