Skip to content

Commit 2c1925d

Browse files
authored
Merge pull request #74921 from tshortli/private-module-interface-flags
Frontend: Only print `-project-name` in private and package interfaces
2 parents b6c6e86 + a6faa5a commit 2c1925d

File tree

6 files changed

+121
-82
lines changed

6 files changed

+121
-82
lines changed

include/swift/Frontend/ModuleInterfaceSupport.h

Lines changed: 17 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,6 @@
2121
#define SWIFT_COMPILER_VERSION_KEY "swift-compiler-version"
2222
#define SWIFT_MODULE_FLAGS_KEY "swift-module-flags"
2323
#define SWIFT_MODULE_FLAGS_IGNORABLE_KEY "swift-module-flags-ignorable"
24-
#define SWIFT_MODULE_FLAGS_IGNORABLE_PRIVATE_KEY "swift-module-flags-ignorable-private"
2524

2625
namespace swift {
2726

@@ -42,23 +41,26 @@ struct ModuleInterfaceOptions {
4241
/// [TODO: Clang-type-plumbing] This check should go away.
4342
bool PrintFullConvention = false;
4443

45-
/// Copy of all the command-line flags passed at .swiftinterface
46-
/// generation time, re-applied to CompilerInvocation when reading
47-
/// back .swiftinterface and reconstructing .swiftmodule.
48-
std::string Flags;
44+
struct InterfaceFlags {
45+
/// Copy of all the command-line flags passed at .swiftinterface
46+
/// generation time, re-applied to CompilerInvocation when reading
47+
/// back .swiftinterface and reconstructing .swiftmodule.
48+
std::string Flags = "";
4949

50-
/// Keep track of flags to be printed in package.swiftinterface only.
51-
/// If -disable-print-package-name-for-non-package-interface is passed,
52-
/// package-name flag should only be printed in package.swiftinterface.
53-
std::string FlagsForPackageOnly;
50+
/// Flags that should be emitted to the .swiftinterface file but are OK to
51+
/// be ignored by the earlier version of the compiler.
52+
std::string IgnorableFlags = "";
53+
};
5454

55-
/// Flags that should be emitted to the .swiftinterface file but are OK to be
56-
/// ignored by the earlier version of the compiler.
57-
std::string IgnorableFlags;
55+
/// Flags which appear in all .swiftinterface files.
56+
InterfaceFlags PublicFlags = {};
5857

59-
/// Ignorable flags that should only be printed in .private.swiftinterface file;
60-
/// e.g. -package-name PACKAGE_ID
61-
std::string IgnorablePrivateFlags;
58+
/// Flags which appear in both the private and package .swiftinterface files,
59+
/// but not the public interface.
60+
InterfaceFlags PrivateFlags = {};
61+
62+
/// Flags which appear only in the .package.swiftinterface.
63+
InterfaceFlags PackageFlags = {};
6264

6365
/// Print imports with both @_implementationOnly and @_spi, only applies
6466
/// when PrintSPIs is true.

include/swift/Option/Options.h

Lines changed: 2 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -41,9 +41,8 @@ namespace options {
4141
SwiftAPIDigesterOption = (1 << 16),
4242
NewDriverOnlyOption = (1 << 17),
4343
ModuleInterfaceOptionIgnorable = (1 << 18),
44-
ModuleInterfaceOptionIgnorablePrivate = (1 << 19),
45-
ArgumentIsFileList = (1 << 20),
46-
CacheInvariant = (1 << 21),
44+
ArgumentIsFileList = (1 << 19),
45+
CacheInvariant = (1 << 20),
4746
};
4847

4948
enum ID {

include/swift/Option/Options.td

Lines changed: 0 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -56,12 +56,6 @@ def ModuleInterfaceOption : OptionFlag;
5656
// The option can be safely ignored by the older compiler.
5757
def ModuleInterfaceOptionIgnorable : OptionFlag;
5858

59-
// The option should be written into a .private.swiftinterface or
60-
// .package.swiftinterface module interface file, and read/parsed from
61-
// there when reconstituting a .swiftmodule from it.
62-
// The option can be safely ignored by the older compiler.
63-
def ModuleInterfaceOptionIgnorablePrivate : OptionFlag;
64-
6559
// The option causes the output of a supplementary output, or is the path option
6660
// for a supplementary output. E.g., `-emit-module` and `-emit-module-path`.
6761
def SupplementaryOutput : OptionFlag;

lib/Frontend/CompilerInvocation.cpp

Lines changed: 50 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -475,6 +475,10 @@ static void ParseModuleInterfaceArgs(ModuleInterfaceOptions &Opts,
475475
/// Checks if an arg is generally allowed to be included
476476
/// in a module interface
477477
static bool ShouldIncludeModuleInterfaceArg(const Arg *A) {
478+
if (!A->getOption().hasFlag(options::ModuleInterfaceOption) &&
479+
!A->getOption().hasFlag(options::ModuleInterfaceOptionIgnorable))
480+
return false;
481+
478482
if (!A->getOption().matches(options::OPT_enable_experimental_feature))
479483
return true;
480484

@@ -485,65 +489,69 @@ static bool ShouldIncludeModuleInterfaceArg(const Arg *A) {
485489
return true;
486490
}
487491

488-
static bool ShouldIncludeArgInPackageInterfaceOnly(const Arg *A,
489-
ArgList &Args) {
492+
static bool IsPackageInterfaceFlag(const Arg *A, ArgList &Args) {
490493
return A->getOption().matches(options::OPT_package_name) &&
491494
Args.hasArg(
492495
options::OPT_disable_print_package_name_for_non_package_interface);
493496
}
494497

498+
static bool IsPrivateInterfaceFlag(const Arg *A, ArgList &Args) {
499+
return A->getOption().matches(options::OPT_project_name);
500+
}
501+
495502
/// Save a copy of any flags marked as ModuleInterfaceOption, if running
496503
/// in a mode that is going to emit a .swiftinterface file.
497504
static void SaveModuleInterfaceArgs(ModuleInterfaceOptions &Opts,
498505
FrontendOptions &FOpts,
499506
ArgList &Args, DiagnosticEngine &Diags) {
500507
if (!FOpts.InputsAndOutputs.hasModuleInterfaceOutputPath())
501508
return;
502-
ArgStringList RenderedArgs;
503-
ArgStringList RenderedArgsForPackageOnly;
504-
ArgStringList RenderedArgsIgnorable;
505-
ArgStringList RenderedArgsIgnorablePrivate;
509+
510+
struct RenderedInterfaceArgs {
511+
ArgStringList Standard = {};
512+
ArgStringList Ignorable = {};
513+
};
514+
515+
RenderedInterfaceArgs PublicArgs{};
516+
RenderedInterfaceArgs PrivateArgs{};
517+
RenderedInterfaceArgs PackageArgs{};
518+
519+
auto interfaceArgListForArg = [&](Arg *A) -> ArgStringList & {
520+
bool ignorable =
521+
A->getOption().hasFlag(options::ModuleInterfaceOptionIgnorable);
522+
if (IsPackageInterfaceFlag(A, Args))
523+
return ignorable ? PackageArgs.Ignorable : PackageArgs.Standard;
524+
525+
if (IsPrivateInterfaceFlag(A, Args))
526+
return ignorable ? PrivateArgs.Ignorable : PrivateArgs.Standard;
527+
528+
return ignorable ? PublicArgs.Ignorable : PublicArgs.Standard;
529+
};
506530

507531
for (auto A : Args) {
508532
if (!ShouldIncludeModuleInterfaceArg(A))
509533
continue;
510534

511-
if (A->getOption().hasFlag(options::ModuleInterfaceOptionIgnorablePrivate)) {
512-
A->render(Args, RenderedArgsIgnorablePrivate);
513-
} else if (A->getOption().hasFlag(options::ModuleInterfaceOptionIgnorable)) {
514-
A->render(Args, RenderedArgsIgnorable);
515-
} else if (A->getOption().hasFlag(options::ModuleInterfaceOption)) {
516-
if (ShouldIncludeArgInPackageInterfaceOnly(A, Args))
517-
A->render(Args, RenderedArgsForPackageOnly);
518-
else
519-
A->render(Args, RenderedArgs);
520-
}
521-
}
522-
{
523-
llvm::raw_string_ostream OS(Opts.Flags);
524-
interleave(RenderedArgs,
525-
[&](const char *Argument) { PrintArg(OS, Argument, StringRef()); },
526-
[&] { OS << " "; });
527-
}
528-
{
529-
llvm::raw_string_ostream OS(Opts.FlagsForPackageOnly);
530-
interleave(
531-
RenderedArgsForPackageOnly,
532-
[&](const char *Argument) { PrintArg(OS, Argument, StringRef()); },
533-
[&] { OS << " "; });
534-
}
535-
{
536-
llvm::raw_string_ostream OS(Opts.IgnorablePrivateFlags);
537-
interleave(RenderedArgsIgnorablePrivate,
538-
[&](const char *Argument) { PrintArg(OS, Argument, StringRef()); },
539-
[&] { OS << " "; });
540-
}
541-
{
542-
llvm::raw_string_ostream OS(Opts.IgnorableFlags);
543-
interleave(RenderedArgsIgnorable,
544-
[&](const char *Argument) { PrintArg(OS, Argument, StringRef()); },
545-
[&] { OS << " "; });
546-
}
535+
ArgStringList &ArgList = interfaceArgListForArg(A);
536+
A->render(Args, ArgList);
537+
}
538+
539+
auto updateInterfaceOpts = [](ModuleInterfaceOptions::InterfaceFlags &Flags,
540+
RenderedInterfaceArgs &RenderedArgs) {
541+
auto printFlags = [](std::string &str, ArgStringList argList) {
542+
llvm::raw_string_ostream OS(str);
543+
interleave(
544+
argList,
545+
[&](const char *Argument) { PrintArg(OS, Argument, StringRef()); },
546+
[&] { OS << " "; });
547+
};
548+
printFlags(Flags.Flags, RenderedArgs.Standard);
549+
printFlags(Flags.IgnorableFlags, RenderedArgs.Ignorable);
550+
};
551+
552+
updateInterfaceOpts(Opts.PublicFlags, PublicArgs);
553+
updateInterfaceOpts(Opts.PrivateFlags, PrivateArgs);
554+
updateInterfaceOpts(Opts.PackageFlags, PackageArgs);
547555
}
548556

549557
enum class CxxCompatMode {

lib/Frontend/ModuleInterfaceSupport.cpp

Lines changed: 29 additions & 16 deletions
Original file line numberDiff line numberDiff line change
@@ -60,15 +60,15 @@ static void printToolVersionAndFlagsComment(raw_ostream &out,
6060
<< InterfaceFormatVersion << "\n";
6161
out << "// " SWIFT_COMPILER_VERSION_KEY ": "
6262
<< ToolsVersion << "\n";
63-
out << "// " SWIFT_MODULE_FLAGS_KEY ": "
64-
<< Opts.Flags;
63+
out << "// " SWIFT_MODULE_FLAGS_KEY ": " << Opts.PublicFlags.Flags;
6564

66-
// Adding package-name can be disabled in non-package
67-
// swiftinterfaces; add only to package.swiftinterface
68-
// in such case.
69-
if (Opts.printPackageInterface() &&
70-
!Opts.FlagsForPackageOnly.empty())
71-
out << " " << Opts.FlagsForPackageOnly;
65+
if (Opts.InterfaceContentMode >= PrintOptions::InterfaceMode::Private &&
66+
!Opts.PrivateFlags.Flags.empty())
67+
out << " " << Opts.PrivateFlags.Flags;
68+
69+
if (Opts.InterfaceContentMode >= PrintOptions::InterfaceMode::Package &&
70+
!Opts.PackageFlags.Flags.empty())
71+
out << " " << Opts.PackageFlags.Flags;
7272

7373
// Insert additional -module-alias flags
7474
if (Opts.AliasModuleNames) {
@@ -104,15 +104,28 @@ static void printToolVersionAndFlagsComment(raw_ostream &out,
104104
}
105105
out << "\n";
106106

107-
if (!Opts.IgnorableFlags.empty()) {
108-
out << "// " SWIFT_MODULE_FLAGS_IGNORABLE_KEY ": "
109-
<< Opts.IgnorableFlags << "\n";
110-
}
107+
// Add swift-module-flags-ignorable: if non-empty.
108+
{
109+
llvm::SmallVector<StringRef, 4> ignorableFlags;
110+
111+
if (!Opts.PublicFlags.IgnorableFlags.empty())
112+
ignorableFlags.push_back(Opts.PublicFlags.IgnorableFlags);
113+
114+
if (Opts.InterfaceContentMode >= PrintOptions::InterfaceMode::Private &&
115+
!Opts.PrivateFlags.IgnorableFlags.empty())
116+
ignorableFlags.push_back(Opts.PrivateFlags.IgnorableFlags);
111117

112-
auto hasPrivateIgnorableFlags = !Opts.printPublicInterface() && !Opts.IgnorablePrivateFlags.empty();
113-
if (hasPrivateIgnorableFlags) {
114-
out << "// " SWIFT_MODULE_FLAGS_IGNORABLE_PRIVATE_KEY ": "
115-
<< Opts.IgnorablePrivateFlags << "\n";
118+
if (Opts.InterfaceContentMode >= PrintOptions::InterfaceMode::Package &&
119+
!Opts.PackageFlags.IgnorableFlags.empty())
120+
ignorableFlags.push_back(Opts.PackageFlags.IgnorableFlags);
121+
122+
if (!ignorableFlags.empty()) {
123+
out << "// " SWIFT_MODULE_FLAGS_IGNORABLE_KEY ": ";
124+
llvm::interleave(
125+
ignorableFlags, [&out](StringRef str) { out << str; },
126+
[&out] { out << " "; });
127+
out << "\n";
128+
}
116129
}
117130
}
118131

Lines changed: 23 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,23 @@
1+
// RUN: %empty-directory(%t)
2+
3+
// RUN: %target-swift-frontend -emit-module %s -I %t \
4+
// RUN: -module-name Library -project-name ProjectName \
5+
// RUN: -enable-library-evolution -swift-version 5 \
6+
// RUN: -emit-module-interface-path %t/Library.swiftinterface \
7+
// RUN: -emit-private-module-interface-path %t/Library.private.swiftinterface \
8+
// RUN: -emit-package-module-interface-path %t/Library.package.swiftinterface
9+
10+
// RUN: %target-swift-typecheck-module-from-interface(%t/Library.swiftinterface) -module-name Library
11+
// RUN: %target-swift-typecheck-module-from-interface(%t/Library.private.swiftinterface) -module-name Library
12+
// RUN: %target-swift-typecheck-module-from-interface(%t/Library.package.swiftinterface) -module-name Library
13+
14+
// RUN: %FileCheck %s < %t/Library.swiftinterface --check-prefix CHECK-PUBLIC
15+
// RUN: %FileCheck %s < %t/Library.private.swiftinterface --check-prefix CHECK-NONPUBLIC
16+
// RUN: %FileCheck %s < %t/Library.package.swiftinterface --check-prefix CHECK-NONPUBLIC
17+
18+
// CHECK-PUBLIC-NOT: -project-name
19+
20+
// CHECK-NONPUBLIC: swift-module-flags-ignorable:
21+
// CHECK-NONPUBLIC-SAME: -project-name ProjectName
22+
23+
public func foo() {}

0 commit comments

Comments
 (0)