Skip to content

Commit e4b5ded

Browse files
committed
Do not load a package module if built from interface
Resolves rdar://104617990
1 parent 25280cb commit e4b5ded

File tree

3 files changed

+48
-1
lines changed

3 files changed

+48
-1
lines changed

include/swift/AST/DiagnosticsSema.def

Lines changed: 5 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1005,6 +1005,11 @@ ERROR(module_not_testable,Fatal,
10051005
ERROR(module_not_compiled_for_private_import,none,
10061006
"module %0 was not compiled for private import", (Identifier))
10071007

1008+
ERROR(package_module_not_compiled_from_source,Fatal,
1009+
"module %0 is a package module but was built from interface; "
1010+
"it must be compiled from source instead",
1011+
(Identifier))
1012+
10081013
ERROR(import_restriction_conflict,none,
10091014
"module %0 cannot be both "
10101015
"%select{implementation-only|SPI only|exported}1 and "

lib/Serialization/SerializedModuleLoader.cpp

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -798,8 +798,14 @@ LoadedFile *SerializedModuleLoaderBase::loadAST(
798798
M.setABIName(Ctx.getIdentifier(loadedModuleFile->getModuleABIName()));
799799
if (loadedModuleFile->isConcurrencyChecked())
800800
M.setIsConcurrencyChecked();
801-
if (!loadedModuleFile->getModulePackageName().empty())
801+
if (!loadedModuleFile->getModulePackageName().empty()) {
802+
if (loadedModuleFile->isBuiltFromInterface()) {
803+
Ctx.Diags.diagnose(SourceLoc(),
804+
diag::package_module_not_compiled_from_source,
805+
M.getBaseIdentifier());
806+
}
802807
M.setPackageName(Ctx.getIdentifier(loadedModuleFile->getModulePackageName()));
808+
}
803809
M.setUserModuleVersion(loadedModuleFile->getUserModuleVersion());
804810
for (auto name: loadedModuleFile->getAllowableClientNames()) {
805811
M.addAllowableClientName(Ctx.getIdentifier(name));
Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,36 @@
1+
// RUN: %empty-directory(%t)
2+
// RUN: split-file %s %t
3+
4+
// RUN: %target-swift-frontend -module-name LibFromInterface -emit-module -emit-module-interface-path %t/LibFromInterface.swiftinterface -parse-as-library %t/Lib.swift -enable-library-evolution -package-name myPkg -swift-version 5
5+
// RUN: test -f %t/LibFromInterface.swiftinterface
6+
// RUN: %FileCheck %s -check-prefix CHECK-LIB < %t/LibFromInterface.swiftinterface
7+
// CHECK-LIB: -package-name myPkg
8+
// CHECK-LIB-NOT: func log(level: Int)
9+
10+
// RUN: not %target-swift-frontend -module-name Client1 %t/Client1.swift -emit-module -emit-module-path %t/Client1.swiftmodule -enable-library-evolution -package-name myPkg -I %t 2> %t/result.output
11+
// RUN: %FileCheck %s -check-prefix CHECK-CLIENT < %t/result.output
12+
// CHECK-CLIENT: module 'LibFromInterface' is a package module but was built from interface; it must be compiled from source instead
13+
14+
// RUN: %target-swift-frontend -module-name LibFromSource -emit-module -emit-module-path %t/LibFromSource.swiftmodule -parse-as-library %t/Lib.swift -package-name myPkg
15+
// RUN: test -f %t/LibFromSource.swiftmodule
16+
17+
// RUN: %target-swift-frontend -module-name Client2 %t/Client2.swift -emit-module -emit-module-path %t/Client2.swiftmodule -enable-library-evolution -package-name myPkg -I %t
18+
// RUN: test -f %t/Client2.swiftmodule
19+
20+
//--- Lib.swift
21+
package func log(level: Int) {}
22+
23+
//--- Client1.swift
24+
import LibFromInterface
25+
26+
func someFun() {
27+
log(level: 1)
28+
}
29+
30+
//--- Client2.swift
31+
import LibFromSource
32+
33+
func someFun() {
34+
log(level: 1)
35+
}
36+

0 commit comments

Comments
 (0)