@@ -21,6 +21,10 @@ import SILBridging
21
21
public protocol ForwardingInstruction : Instruction {
22
22
var singleForwardedOperand : Operand ? { get }
23
23
24
+ /// Return true if the result has the same object identify, and therefore the same reference counting semantics as the
25
+ /// source. This is true for most forwarding operations unless they extract or aggregate components.
26
+ var preservesIdentity : Bool { get }
27
+
24
28
/// Return true if the forwarded value has the same representation. If true, then the result can be mapped to the same storage without a move or copy.
25
29
var preservesRepresentation : Bool { get }
26
30
@@ -154,6 +158,7 @@ public struct ForwardedResults : Collection {
154
158
extension StructInst : ForwardingInstruction {
155
159
public var singleForwardedOperand : Operand ? { nil }
156
160
161
+ public var preservesIdentity : Bool { false }
157
162
public var preservesRepresentation : Bool { true }
158
163
public var canForwardGuaranteedValues : Bool { true }
159
164
public var canForwardOwnedValues : Bool { true }
@@ -162,6 +167,7 @@ extension StructInst : ForwardingInstruction {
162
167
extension TupleInst : ForwardingInstruction {
163
168
public var singleForwardedOperand : Operand ? { nil }
164
169
170
+ public var preservesIdentity : Bool { false }
165
171
public var preservesRepresentation : Bool { true }
166
172
public var canForwardGuaranteedValues : Bool { true }
167
173
public var canForwardOwnedValues : Bool { true }
@@ -170,6 +176,7 @@ extension TupleInst : ForwardingInstruction {
170
176
extension LinearFunctionInst : ForwardingInstruction {
171
177
public var singleForwardedOperand : Operand ? { nil }
172
178
179
+ public var preservesIdentity : Bool { false }
173
180
public var preservesRepresentation : Bool { true }
174
181
public var canForwardGuaranteedValues : Bool { true }
175
182
public var canForwardOwnedValues : Bool { true }
@@ -178,6 +185,7 @@ extension LinearFunctionInst : ForwardingInstruction {
178
185
extension DifferentiableFunctionInst : ForwardingInstruction {
179
186
public var singleForwardedOperand : Operand ? { nil }
180
187
188
+ public var preservesIdentity : Bool { false }
181
189
public var preservesRepresentation : Bool { true }
182
190
public var canForwardGuaranteedValues : Bool { true }
183
191
public var canForwardOwnedValues : Bool { true }
@@ -191,6 +199,7 @@ extension MarkDependenceInst : ForwardingInstruction {
191
199
return valueOperand
192
200
}
193
201
202
+ public var preservesIdentity : Bool { true }
194
203
public var preservesRepresentation : Bool { true }
195
204
public var canForwardGuaranteedValues : Bool { true }
196
205
public var canForwardOwnedValues : Bool { true }
@@ -201,6 +210,7 @@ extension RefToBridgeObjectInst : ForwardingInstruction {
201
210
return convertedOperand
202
211
}
203
212
213
+ public var preservesIdentity : Bool { true }
204
214
public var preservesRepresentation : Bool { true }
205
215
public var canForwardGuaranteedValues : Bool { true }
206
216
public var canForwardOwnedValues : Bool { true }
@@ -209,6 +219,7 @@ extension RefToBridgeObjectInst : ForwardingInstruction {
209
219
extension TuplePackExtractInst : ForwardingInstruction {
210
220
public var singleForwardedOperand : Operand ? { return tupleOperand }
211
221
222
+ public var preservesIdentity : Bool { false }
212
223
public var preservesRepresentation : Bool { true }
213
224
public var canForwardGuaranteedValues : Bool { true }
214
225
public var canForwardOwnedValues : Bool { false }
@@ -229,6 +240,13 @@ extension TuplePackExtractInst : ForwardingInstruction {
229
240
/// support type-dependent operands.
230
241
public protocol ConversionInstruction : SingleValueInstruction , UnaryInstruction , ForwardingInstruction { }
231
242
243
+ extension ConversionInstruction {
244
+ /// Conversion instructions naturally preserve identity as long as they preserve reference counts because they do not
245
+ /// aggregate or disaggregate values. They can only lose identity by destroying the source object and instantiating a
246
+ /// new object, like certain bridging casts do.
247
+ public var preservesIdentity : Bool { preservesReferenceCounts }
248
+ }
249
+
232
250
extension MarkUnresolvedNonCopyableValueInst : ConversionInstruction {
233
251
public var preservesRepresentation : Bool { true }
234
252
public var canForwardGuaranteedValues : Bool { true }
@@ -309,90 +327,105 @@ extension EnumInst : ForwardingInstruction {
309
327
return operand // nil for an enum with no payload
310
328
}
311
329
330
+ public var preservesIdentity : Bool { false }
312
331
public var preservesRepresentation : Bool { true }
313
332
public var canForwardGuaranteedValues : Bool { true }
314
333
public var canForwardOwnedValues : Bool { true }
315
334
}
316
335
317
336
extension DestructureTupleInst : ForwardingInstruction {
337
+ public var preservesIdentity : Bool { false }
318
338
public var preservesRepresentation : Bool { true }
319
339
public var canForwardGuaranteedValues : Bool { true }
320
340
public var canForwardOwnedValues : Bool { true }
321
341
}
322
342
323
343
extension DestructureStructInst : ForwardingInstruction {
344
+ public var preservesIdentity : Bool { false }
324
345
public var preservesRepresentation : Bool { true }
325
346
public var canForwardGuaranteedValues : Bool { true }
326
347
public var canForwardOwnedValues : Bool { true }
327
348
}
328
349
329
350
extension InitExistentialRefInst : ForwardingInstruction {
351
+ public var preservesIdentity : Bool { false }
330
352
public var preservesRepresentation : Bool { true }
331
353
public var canForwardGuaranteedValues : Bool { true }
332
354
public var canForwardOwnedValues : Bool { true }
333
355
}
334
356
335
357
extension OpenExistentialRefInst : ForwardingInstruction {
358
+ public var preservesIdentity : Bool { false }
336
359
public var preservesRepresentation : Bool { true }
337
360
public var canForwardGuaranteedValues : Bool { true }
338
361
public var canForwardOwnedValues : Bool { true }
339
362
}
340
363
341
364
extension OpenExistentialValueInst : ForwardingInstruction {
365
+ public var preservesIdentity : Bool { false }
342
366
public var preservesRepresentation : Bool { true }
343
367
public var canForwardGuaranteedValues : Bool { true }
344
368
public var canForwardOwnedValues : Bool { true }
345
369
}
346
370
347
371
extension OpenExistentialBoxValueInst : ForwardingInstruction {
372
+ public var preservesIdentity : Bool { false }
348
373
public var preservesRepresentation : Bool { true }
349
374
public var canForwardGuaranteedValues : Bool { true }
350
375
public var canForwardOwnedValues : Bool { true }
351
376
}
352
377
353
378
extension StructExtractInst : ForwardingInstruction {
379
+ public var preservesIdentity : Bool { false }
354
380
public var preservesRepresentation : Bool { true }
355
381
public var canForwardGuaranteedValues : Bool { true }
356
382
public var canForwardOwnedValues : Bool { false }
357
383
}
358
384
359
385
extension TupleExtractInst : ForwardingInstruction {
386
+ public var preservesIdentity : Bool { false }
360
387
public var preservesRepresentation : Bool { true }
361
388
public var canForwardGuaranteedValues : Bool { true }
362
389
public var canForwardOwnedValues : Bool { false }
363
390
}
364
391
365
392
extension DifferentiableFunctionExtractInst : ForwardingInstruction {
393
+ public var preservesIdentity : Bool { false }
366
394
public var preservesRepresentation : Bool { true }
367
395
public var canForwardGuaranteedValues : Bool { true }
368
396
public var canForwardOwnedValues : Bool { false }
369
397
}
370
398
371
399
extension CheckedCastBranchInst : ForwardingInstruction {
400
+ public var preservesIdentity : Bool { false }
372
401
public var preservesRepresentation : Bool { true }
373
402
public var canForwardGuaranteedValues : Bool { true }
374
403
public var canForwardOwnedValues : Bool { true }
375
404
}
376
405
377
406
extension UncheckedEnumDataInst : ForwardingInstruction {
407
+ public var preservesIdentity : Bool { false }
378
408
public var preservesRepresentation : Bool { true }
379
409
public var canForwardGuaranteedValues : Bool { true }
380
410
public var canForwardOwnedValues : Bool { true }
381
411
}
382
412
383
413
extension SwitchEnumInst : ForwardingInstruction {
414
+ public var preservesIdentity : Bool { false }
384
415
public var preservesRepresentation : Bool { true }
385
416
public var canForwardGuaranteedValues : Bool { true }
386
417
public var canForwardOwnedValues : Bool { true }
387
418
}
388
419
389
420
extension MarkUnresolvedReferenceBindingInst : ForwardingInstruction {
421
+ public var preservesIdentity : Bool { true }
390
422
public var preservesRepresentation : Bool { true }
391
423
public var canForwardGuaranteedValues : Bool { true }
392
424
public var canForwardOwnedValues : Bool { true }
393
425
}
394
426
395
427
extension LinearFunctionExtractInst : ForwardingInstruction {
428
+ public var preservesIdentity : Bool { false }
396
429
public var preservesRepresentation : Bool { true }
397
430
public var canForwardGuaranteedValues : Bool { true }
398
431
public var canForwardOwnedValues : Bool { true }
@@ -404,6 +437,8 @@ extension LinearFunctionExtractInst: ForwardingInstruction {
404
437
/// An instruction that transfers lifetime dependence from a single operand to a single result. The operand and result
405
438
/// have the same identity, but they are not part of the same forwarded lifetime:
406
439
/// copy_value, move_value, begin_borrow.
440
+ ///
441
+ /// OwnershipTransitionInstructions always preserve the identity of the source. See swift::isIdentityPreservingRefCast.
407
442
public protocol OwnershipTransitionInstruction : UnaryInstruction {
408
443
var ownershipResult : Value { get }
409
444
}
0 commit comments