Skip to content

Commit d8c946d

Browse files
committed
AST: Introduce Decl::getActiveAvailableAttrForCurrentPlatform().
1 parent 5cdcb5d commit d8c946d

File tree

5 files changed

+38
-48
lines changed

5 files changed

+38
-48
lines changed

include/swift/AST/Attr.h

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -2925,12 +2925,6 @@ class DeclAttributes {
29252925
return UnaryOperatorKind::None;
29262926
}
29272927

2928-
/// Finds the most-specific platform-specific attribute that is
2929-
/// active for the current platform.
2930-
const AvailableAttr *
2931-
findMostSpecificActivePlatform(const ASTContext &ctx,
2932-
bool ignoreAppExtensions = false) const;
2933-
29342928
/// Returns the `@backDeployed` attribute that is active for the current
29352929
/// platform.
29362930
const BackDeployedAttr *getBackDeployed(const ASTContext &ctx,

include/swift/AST/Decl.h

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1390,6 +1390,12 @@ class alignas(1 << DeclAlignInBits) Decl : public ASTAllocated<Decl>, public Swi
13901390
/// and its DeclContext does not.
13911391
bool isOutermostPrivateOrFilePrivateScope() const;
13921392

1393+
/// Returns the active platform-specific `@available` attribute for this decl.
1394+
/// There may be multiple `@available` attributes that are relevant to the
1395+
/// current platform, but the returned one has the highest priority.
1396+
const AvailableAttr *getActiveAvailableAttrForCurrentPlatform(
1397+
bool ignoreAppExtensions = false) const;
1398+
13931399
/// Returns true if the declaration is deprecated at the current deployment
13941400
/// target.
13951401
bool isDeprecated() const { return getDeprecatedAttr() != nullptr; }

lib/AST/Attr.cpp

Lines changed: 0 additions & 34 deletions
Original file line numberDiff line numberDiff line change
@@ -370,40 +370,6 @@ DeclAttribute *DeclAttribute::clone(ASTContext &ctx) const {
370370
}
371371
}
372372

373-
const AvailableAttr *
374-
DeclAttributes::findMostSpecificActivePlatform(const ASTContext &ctx,
375-
bool ignoreAppExtensions) const {
376-
const AvailableAttr *bestAttr = nullptr;
377-
378-
for (auto attr : *this) {
379-
auto *avAttr = dyn_cast<AvailableAttr>(attr);
380-
if (!avAttr)
381-
continue;
382-
383-
if (avAttr->isInvalid())
384-
continue;
385-
386-
if (!avAttr->hasPlatform())
387-
continue;
388-
389-
if (!avAttr->isActivePlatform(ctx))
390-
continue;
391-
392-
if (ignoreAppExtensions &&
393-
isApplicationExtensionPlatform(avAttr->getPlatform()))
394-
continue;
395-
396-
// We have an attribute that is active for the platform, but
397-
// is it more specific than our current best?
398-
if (!bestAttr || inheritsAvailabilityFromPlatform(
399-
avAttr->getPlatform(), bestAttr->getPlatform())) {
400-
bestAttr = avAttr;
401-
}
402-
}
403-
404-
return bestAttr;
405-
}
406-
407373
const BackDeployedAttr *
408374
DeclAttributes::getBackDeployed(const ASTContext &ctx,
409375
bool forTargetVariant) const {

lib/AST/Availability.cpp

Lines changed: 28 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -486,11 +486,36 @@ bool Decl::isAvailableAsSPI() const {
486486
return AvailabilityInference::isAvailableAsSPI(this);
487487
}
488488

489+
const AvailableAttr *
490+
Decl::getActiveAvailableAttrForCurrentPlatform(bool ignoreAppExtensions) const {
491+
auto &ctx = getASTContext();
492+
const AvailableAttr *bestAttr = nullptr;
493+
494+
for (auto attr :
495+
getAttrs().getAttributes<AvailableAttr, /*AllowInvalid=*/false>()) {
496+
if (!attr->hasPlatform() || !attr->isActivePlatform(ctx))
497+
continue;
498+
499+
if (ignoreAppExtensions &&
500+
isApplicationExtensionPlatform(attr->getPlatform()))
501+
continue;
502+
503+
// We have an attribute that is active for the platform, but is it more
504+
// specific than our current best?
505+
if (!bestAttr || inheritsAvailabilityFromPlatform(
506+
attr->getPlatform(), bestAttr->getPlatform())) {
507+
bestAttr = attr;
508+
}
509+
}
510+
511+
return bestAttr;
512+
}
513+
489514
const AvailableAttr *Decl::getDeprecatedAttr() const {
490515
auto &ctx = getASTContext();
491516
auto attrs = getAttrs();
492517
const AvailableAttr *result = nullptr;
493-
const AvailableAttr *bestActive = attrs.findMostSpecificActivePlatform(ctx);
518+
const AvailableAttr *bestActive = getActiveAvailableAttrForCurrentPlatform();
494519

495520
for (auto attr :
496521
attrs.getAttributes<AvailableAttr, /*AllowInvalid=*/false>()) {
@@ -531,7 +556,7 @@ const AvailableAttr *Decl::getSoftDeprecatedAttr() const {
531556
auto &ctx = getASTContext();
532557
auto attrs = getAttrs();
533558
const AvailableAttr *result = nullptr;
534-
const AvailableAttr *bestActive = attrs.findMostSpecificActivePlatform(ctx);
559+
const AvailableAttr *bestActive = getActiveAvailableAttrForCurrentPlatform();
535560

536561
for (auto attr :
537562
attrs.getAttributes<AvailableAttr, /*AllowInvalid=*/false>()) {
@@ -608,10 +633,9 @@ bool Decl::isUnavailableInCurrentSwiftVersion() const {
608633
static const AvailableAttr *
609634
getDeclUnavailableAttr(const Decl *D, bool ignoreAppExtensions) {
610635
auto &ctx = D->getASTContext();
611-
auto attrs = D->getAttrs();
612636
const AvailableAttr *result = nullptr;
613637
const AvailableAttr *bestActive =
614-
attrs.findMostSpecificActivePlatform(ctx, ignoreAppExtensions);
638+
D->getActiveAvailableAttrForCurrentPlatform(ignoreAppExtensions);
615639

616640
for (auto attr :
617641
D->getAttrs().getAttributes<AvailableAttr, /*AllowInvalid=*/false>()) {

lib/Sema/TypeCheckAttr.cpp

Lines changed: 4 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2162,18 +2162,18 @@ void AttributeChecker::visitAvailableAttr(AvailableAttr *attr) {
21622162
return;
21632163

21642164
// Make sure there isn't a more specific attribute we should be using instead.
2165-
// findMostSpecificActivePlatform() is O(N), so only do this if we're checking
2166-
// an iOS attribute while building for macCatalyst.
2165+
// getActiveAvailableAttrForCurrentPlatform() is O(N), so only do this if
2166+
// we're checking an iOS attribute while building for macCatalyst.
21672167
if (attr->getPlatform() == PlatformKind::iOS &&
21682168
isPlatformActive(PlatformKind::macCatalyst, Ctx.LangOpts)) {
2169-
if (attr != D->getAttrs().findMostSpecificActivePlatform(Ctx)) {
2169+
if (attr != D->getActiveAvailableAttrForCurrentPlatform()) {
21702170
return;
21712171
}
21722172
}
21732173

21742174
if (attr->getPlatform() == PlatformKind::iOS &&
21752175
isPlatformActive(PlatformKind::visionOS, Ctx.LangOpts)) {
2176-
if (attr != D->getAttrs().findMostSpecificActivePlatform(Ctx)) {
2176+
if (attr != D->getActiveAvailableAttrForCurrentPlatform()) {
21772177
return;
21782178
}
21792179
}

0 commit comments

Comments
 (0)