Skip to content

Commit e90e2de

Browse files
committed
[Sema] Report use of conformances from non-public imports in inlinable code
Conformances imported as non-public cannot be used in API or inlinable code, report it as an error.
1 parent 0a24844 commit e90e2de

5 files changed

+43
-2
lines changed

include/swift/AST/DiagnosticsSema.def

+2-1
Original file line numberDiff line numberDiff line change
@@ -3461,7 +3461,8 @@ ERROR(conformance_from_implementation_only_module,none,
34613461
"the conformance is declared as SPI|"
34623462
"%3 was imported for SPI only|"
34633463
"%3 was not imported by this file|"
3464-
"C++ types from imported module %3 do not support library evolution}4",
3464+
"C++ types from imported module %3 do not support library evolution|"
3465+
"%3 was not imported publicly}4",
34653466
(Type, Identifier, unsigned, Identifier, unsigned))
34663467
NOTE(assoc_conformance_from_implementation_only_module,none,
34673468
"in associated type %0 (inferred as %1)", (Type, Type))

lib/Sema/ResilienceDiagnostics.cpp

+2-1
Original file line numberDiff line numberDiff line change
@@ -290,7 +290,8 @@ TypeChecker::diagnoseConformanceExportability(SourceLoc loc,
290290
static_cast<unsigned>(originKind))
291291
.warnUntilSwiftVersionIf((useConformanceAvailabilityErrorsOption &&
292292
!ctx.LangOpts.EnableConformanceAvailabilityErrors &&
293-
originKind != DisallowedOriginKind::SPIOnly) ||
293+
originKind != DisallowedOriginKind::SPIOnly &&
294+
originKind != DisallowedOriginKind::NonPublicImport) ||
294295
originKind == DisallowedOriginKind::MissingImport,
295296
6);
296297

lib/Sema/TypeCheckAccess.cpp

+7
Original file line numberDiff line numberDiff line change
@@ -1909,6 +1909,13 @@ swift::getDisallowedOriginKind(const Decl *decl,
19091909
isFragileClangNode(decl->getClangNode()))
19101910
return DisallowedOriginKind::FragileCxxAPI;
19111911

1912+
// Report non-public import last as it can be ignored by the caller.
1913+
// See \c diagnoseValueDeclRefExportability.
1914+
auto importSource = decl->getImportAccessFrom(where.getDeclContext());
1915+
if (importSource.has_value() &&
1916+
importSource->accessLevel < AccessLevel::Public)
1917+
return DisallowedOriginKind::NonPublicImport;
1918+
19121919
return DisallowedOriginKind::None;
19131920
}
19141921

lib/Sema/TypeCheckAccess.h

+1
Original file line numberDiff line numberDiff line change
@@ -47,6 +47,7 @@ enum class DisallowedOriginKind : uint8_t {
4747
SPIOnly,
4848
MissingImport,
4949
FragileCxxAPI,
50+
NonPublicImport,
5051
None
5152
};
5253

Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
// RUN: %empty-directory(%t)
2+
// RUN: split-file --leading-lines %s %t
3+
4+
/// Build the libraries.
5+
// RUN: %target-swift-frontend -emit-module %t/ConformanceBaseTypes.swift -o %t
6+
// RUN: %target-swift-frontend -emit-module %t/ConformanceDefinition.swift -o %t -I %t
7+
8+
/// Check diagnostics.
9+
// RUN: %target-swift-frontend -typecheck -verify %t/Client.swift -I %t \
10+
// RUN: -enable-experimental-feature AccessLevelOnImport
11+
12+
//--- ConformanceBaseTypes.swift
13+
public protocol Proto {}
14+
public struct ConformingType {
15+
public init () {}
16+
}
17+
18+
//--- ConformanceDefinition.swift
19+
import ConformanceBaseTypes
20+
extension ConformingType : Proto {}
21+
22+
//--- Client.swift
23+
public import ConformanceBaseTypes
24+
internal import ConformanceDefinition
25+
26+
public func useInAPI(a: any Proto = ConformingType()) { // expected-error {{cannot use conformance of 'ConformingType' to 'Proto' here; 'ConformanceDefinition' was not imported publicly}}
27+
}
28+
29+
@inlinable public func inlinableFunc() {
30+
let _: any Proto = ConformingType() // expected-error {{cannot use conformance of 'ConformingType' to 'Proto' here; 'ConformanceDefinition' was not imported publicly}}
31+
}

0 commit comments

Comments
 (0)