@@ -162,6 +162,21 @@ struct SILDeclRef {
162
162
AsyncEntryPoint,
163
163
};
164
164
165
+ // / Represents the variants of a back deployable function.
166
+ enum class BackDeploymentKind : unsigned {
167
+ // / Default value. If a SILDecRef references a function that has been back
168
+ // / deployed and has this back deployment kind, then it references the
169
+ // / original ABI stable function.
170
+ None,
171
+ // / The thunk variant of a function that calls either the original function
172
+ // / or the fallback variant if the original is unavailable. This thunk will
173
+ // / be emitted with PublicNonABI linkage.
174
+ Thunk,
175
+ // / The fallback variant of the function. This function will be emitted with
176
+ // / PublicNonABI linkage.
177
+ Fallback,
178
+ };
179
+
165
180
// / The AST node represented by this SILDeclRef.
166
181
Loc loc;
167
182
// / The Kind of this SILDeclRef.
@@ -170,6 +185,8 @@ struct SILDeclRef {
170
185
unsigned isForeign : 1 ;
171
186
// / True if this references a distributed function.
172
187
unsigned isDistributed : 1 ;
188
+ // / The BackDeploymentKind of this SILDeclRef.
189
+ BackDeploymentKind backDeploymentKind : 2 ;
173
190
// / The default argument index for a default argument getter.
174
191
unsigned defaultArgIndex : 10 ;
175
192
@@ -204,13 +221,15 @@ struct SILDeclRef {
204
221
205
222
// / Produces a null SILDeclRef.
206
223
SILDeclRef ()
207
- : loc(), kind(Kind::Func), isForeign(0 ), isDistributed(0 ), defaultArgIndex(0 ) {}
224
+ : loc(), kind(Kind::Func), isForeign(0 ), isDistributed(0 ),
225
+ backDeploymentKind (BackDeploymentKind::None), defaultArgIndex(0 ) {}
208
226
209
227
// / Produces a SILDeclRef of the given kind for the given decl.
210
228
explicit SILDeclRef (
211
229
ValueDecl *decl, Kind kind,
212
230
bool isForeign = false ,
213
231
bool isDistributed = false ,
232
+ BackDeploymentKind backDeploymentKind = BackDeploymentKind::None,
214
233
AutoDiffDerivativeFunctionIdentifier *derivativeId = nullptr );
215
234
216
235
// / Produces a SILDeclRef for the given ValueDecl or
@@ -224,7 +243,10 @@ struct SILDeclRef {
224
243
// / for the containing ClassDecl.
225
244
// / - If 'loc' is a global VarDecl, this returns its GlobalAccessor
226
245
// / SILDeclRef.
227
- explicit SILDeclRef (Loc loc, bool isForeign = false , bool isDistributed = false );
246
+ explicit SILDeclRef (
247
+ Loc loc,
248
+ bool isForeign = false ,
249
+ bool isDistributed = false );
228
250
229
251
// / See above put produces a prespecialization according to the signature.
230
252
explicit SILDeclRef (Loc loc, GenericSignature prespecializationSig);
@@ -360,6 +382,7 @@ struct SILDeclRef {
360
382
return loc.getOpaqueValue () == rhs.loc .getOpaqueValue () &&
361
383
kind == rhs.kind && isForeign == rhs.isForeign &&
362
384
isDistributed == rhs.isDistributed &&
385
+ backDeploymentKind == rhs.backDeploymentKind &&
363
386
defaultArgIndex == rhs.defaultArgIndex &&
364
387
pointer == rhs.pointer ;
365
388
}
@@ -378,6 +401,7 @@ struct SILDeclRef {
378
401
return SILDeclRef (loc.getOpaqueValue (), kind,
379
402
/* foreign=*/ foreign,
380
403
/* distributed=*/ false ,
404
+ backDeploymentKind,
381
405
defaultArgIndex,
382
406
pointer.get <AutoDiffDerivativeFunctionIdentifier *>());
383
407
}
@@ -387,6 +411,16 @@ struct SILDeclRef {
387
411
return SILDeclRef (loc.getOpaqueValue (), kind,
388
412
/* foreign=*/ false ,
389
413
/* distributed=*/ distributed,
414
+ backDeploymentKind,
415
+ defaultArgIndex,
416
+ pointer.get <AutoDiffDerivativeFunctionIdentifier *>());
417
+ }
418
+ // / Returns a copy of the decl with the given back deployment kind.
419
+ SILDeclRef asBackDeploymentKind (BackDeploymentKind backDeploymentKind) const {
420
+ return SILDeclRef (loc.getOpaqueValue (), kind,
421
+ isForeign,
422
+ isDistributed,
423
+ backDeploymentKind,
390
424
defaultArgIndex,
391
425
pointer.get <AutoDiffDerivativeFunctionIdentifier *>());
392
426
}
@@ -431,6 +465,14 @@ struct SILDeclRef {
431
465
// / True if the decl ref references a thunk handling potentially distributed actor functions
432
466
bool isDistributedThunk () const ;
433
467
468
+ // / True if the decl ref references a thunk handling a call to a function that
469
+ // / supports back deployment.
470
+ bool isBackDeploymentThunk () const ;
471
+
472
+ // / True if the decl ref references a function that is the back deployment
473
+ // / fallback for an original function which may be unavailable at runtime.
474
+ bool isBackDeploymentFallback () const ;
475
+
434
476
// / True if the decl ref references a method which introduces a new vtable
435
477
// / entry.
436
478
bool requiresNewVTableEntry () const ;
@@ -508,10 +550,12 @@ struct SILDeclRef {
508
550
explicit SILDeclRef (void *opaqueLoc, Kind kind,
509
551
bool isForeign,
510
552
bool isDistributed,
553
+ BackDeploymentKind backDeploymentKind,
511
554
unsigned defaultArgIndex,
512
555
AutoDiffDerivativeFunctionIdentifier *derivativeId)
513
556
: loc(Loc::getFromOpaqueValue(opaqueLoc)), kind(kind),
514
557
isForeign(isForeign), isDistributed(isDistributed),
558
+ backDeploymentKind(backDeploymentKind),
515
559
defaultArgIndex(defaultArgIndex),
516
560
pointer(derivativeId) {}
517
561
};
@@ -529,17 +573,18 @@ namespace llvm {
529
573
template <> struct DenseMapInfo <swift::SILDeclRef> {
530
574
using SILDeclRef = swift::SILDeclRef;
531
575
using Kind = SILDeclRef::Kind;
576
+ using BackDeploymentKind = SILDeclRef::BackDeploymentKind;
532
577
using Loc = SILDeclRef::Loc;
533
578
using PointerInfo = DenseMapInfo<void *>;
534
579
using UnsignedInfo = DenseMapInfo<unsigned >;
535
580
536
581
static SILDeclRef getEmptyKey () {
537
- return SILDeclRef (PointerInfo::getEmptyKey (), Kind::Func, false , false , 0 ,
538
- nullptr );
582
+ return SILDeclRef (PointerInfo::getEmptyKey (), Kind::Func, false , false ,
583
+ BackDeploymentKind::None, 0 , nullptr );
539
584
}
540
585
static SILDeclRef getTombstoneKey () {
541
586
return SILDeclRef (PointerInfo::getTombstoneKey (), Kind::Func, false , false ,
542
- 0 , nullptr );
587
+ BackDeploymentKind::None, 0 , nullptr );
543
588
}
544
589
static unsigned getHashValue (swift::SILDeclRef Val) {
545
590
unsigned h1 = PointerInfo::getHashValue (Val.loc .getOpaqueValue ());
@@ -550,7 +595,9 @@ template<> struct DenseMapInfo<swift::SILDeclRef> {
550
595
unsigned h4 = UnsignedInfo::getHashValue (Val.isForeign );
551
596
unsigned h5 = PointerInfo::getHashValue (Val.pointer .getOpaqueValue ());
552
597
unsigned h6 = UnsignedInfo::getHashValue (Val.isDistributed );
553
- return h1 ^ (h2 << 4 ) ^ (h3 << 9 ) ^ (h4 << 7 ) ^ (h5 << 11 ) ^ (h6 << 8 );
598
+ unsigned h7 = UnsignedInfo::getHashValue (unsigned (Val.backDeploymentKind ));
599
+ return h1 ^ (h2 << 4 ) ^ (h3 << 9 ) ^ (h4 << 7 ) ^ (h5 << 11 ) ^ (h6 << 8 ) ^
600
+ (h7 << 10 );
554
601
}
555
602
static bool isEqual (swift::SILDeclRef const &LHS,
556
603
swift::SILDeclRef const &RHS) {
0 commit comments