Skip to content

Commit ea21d32

Browse files
authored
Merge pull request #60983 from nkcsgexi/warn-all-spi-available
2 parents 0ecf885 + 4f9cfd3 commit ea21d32

File tree

5 files changed

+34
-4
lines changed

5 files changed

+34
-4
lines changed

include/swift/AST/DiagnosticsSema.def

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1646,6 +1646,10 @@ ERROR(originally_definedin_must_not_before_available_version,none,
16461646
"symbols are moved to the current module before they were available in "
16471647
"the OSs", ())
16481648

1649+
WARNING(spi_preferred_over_spi_available,none,
1650+
"symbols that are @_spi_available on all platforms should use @_spi "
1651+
"instead", ())
1652+
16491653
// Alignment attribute
16501654
ERROR(alignment_not_power_of_two,none,
16511655
"alignment value must be a power of two", ())

lib/Sema/TypeCheckAttr.cpp

Lines changed: 21 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -328,6 +328,7 @@ class AttributeChecker : public AttributeVisitor<AttributeChecker> {
328328

329329
void visitCompilerInitializedAttr(CompilerInitializedAttr *attr);
330330

331+
void checkAvailableAttrs(ArrayRef<AvailableAttr *> Attrs);
331332
void checkBackDeployAttrs(ArrayRef<BackDeployAttr *> Attrs);
332333

333334
void visitKnownToBeLocalAttr(KnownToBeLocalAttr *attr);
@@ -1421,8 +1422,10 @@ void TypeChecker::checkDeclAttributes(Decl *D) {
14211422
TypeChecker::applyAccessNote(VD);
14221423

14231424
AttributeChecker Checker(D);
1424-
// We need to check all OriginallyDefinedInAttr and BackDeployAttr relative
1425-
// to each other, so collect them and check in batch later.
1425+
// We need to check all availableAttrs, OriginallyDefinedInAttr and
1426+
// BackDeployAttr relative to each other, so collect them and check in
1427+
// batch later.
1428+
llvm::SmallVector<AvailableAttr *, 4> availableAttrs;
14261429
llvm::SmallVector<BackDeployAttr *, 4> backDeployAttrs;
14271430
llvm::SmallVector<OriginallyDefinedInAttr*, 4> ODIAttrs;
14281431
for (auto attr : D->getAttrs()) {
@@ -1436,6 +1439,10 @@ void TypeChecker::checkDeclAttributes(Decl *D) {
14361439
} else if (auto *BD = dyn_cast<BackDeployAttr>(attr)) {
14371440
backDeployAttrs.push_back(BD);
14381441
} else {
1442+
// check @available attribute both collectively and individually.
1443+
if (auto *AV = dyn_cast<AvailableAttr>(attr)) {
1444+
availableAttrs.push_back(AV);
1445+
}
14391446
// Otherwise, check it.
14401447
Checker.visit(attr);
14411448
}
@@ -1475,6 +1482,7 @@ void TypeChecker::checkDeclAttributes(Decl *D) {
14751482
else
14761483
Checker.diagnoseAndRemoveAttr(attr, diag::invalid_decl_attribute, attr);
14771484
}
1485+
Checker.checkAvailableAttrs(availableAttrs);
14781486
Checker.checkBackDeployAttrs(backDeployAttrs);
14791487
Checker.checkOriginalDefinedInAttrs(ODIAttrs);
14801488
}
@@ -4002,6 +4010,17 @@ void AttributeChecker::checkOriginalDefinedInAttrs(
40024010
}
40034011
}
40044012

4013+
void AttributeChecker::checkAvailableAttrs(ArrayRef<AvailableAttr *> Attrs) {
4014+
if (Attrs.empty())
4015+
return;
4016+
// If all available are spi available, we should use @_spi instead.
4017+
if (std::all_of(Attrs.begin(), Attrs.end(), [](AvailableAttr *AV) {
4018+
return AV->IsSPI;
4019+
})) {
4020+
diagnose(D->getLoc(), diag::spi_preferred_over_spi_available);
4021+
};
4022+
}
4023+
40054024
void AttributeChecker::checkBackDeployAttrs(ArrayRef<BackDeployAttr *> Attrs) {
40064025
if (Attrs.empty())
40074026
return;

test/Sema/spi-available-context.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,11 @@
33
// RUN: %target-typecheck-verify-swift -target %target-cpu-apple-macosx11.9 -library-level api
44

55
@_spi_available(macOS 10.4, *)
6+
@available(iOS 8.0, *)
67
public protocol Foo { }
78

89
@_spi_available(macOS 10.4, *)
10+
@available(iOS 8.0, *)
911
public class Bar {
1012
public var foo: Foo?
1113
}

test/Sema/spi-available-inline.swift

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -3,9 +3,11 @@
33
// RUN: %target-typecheck-verify-swift -target %target-cpu-apple-macosx11.9 -library-level api
44

55
@_spi_available(macOS 10.4, *)
6+
@available(iOS 8.0, *)
67
public class MacOSSPIClass { public init() {} }
78

89
@_spi_available(iOS 8.0, *)
10+
@available(macOS 10.4, *)
911
public class iOSSPIClass { public init() {} }
1012

1113
@inlinable public func foo() {

test/attr/spi_available.swift

Lines changed: 5 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,10 +1,13 @@
11
// RUN: %target-typecheck-verify-swift
22

33
@_spi_available(*, deprecated, renamed: "another") // expected-error {{SPI available only supports introducing version on specific platform}}
4-
public class SPIClass1 {}
4+
public class SPIClass1 {} // expected-warning {{symbols that are @_spi_available on all platforms should use @_spi instead}}
55

66
@_spi_available(*, unavailable) // expected-error {{SPI available only supports introducing version on specific platform}}
7-
public class SPIClass2 {}
7+
public class SPIClass2 {} // expected-warning {{symbols that are @_spi_available on all platforms should use @_spi instead}}
88

99
@_spi_available(AlienPlatform 5.2, *) // expected-warning {{unrecognized platform name 'AlienPlatform'}}
1010
public class SPIClass3 {}
11+
12+
@_spi_available(macOS 10.4, *)
13+
public class SPIClass4 {} // expected-warning {{symbols that are @_spi_available on all platforms should use @_spi instead}}

0 commit comments

Comments
 (0)