ClangModuleUnit::getOverlayModule implies that it requests the Swift
module with the same name as the top level module, and loads it if it is
available. Unfortunately, it used ASTContext::getModule to do so, which
consults every module loader, including the clang importer. So, even
though you couldn't actually get a clang module out at the end of the
day, you could still force a clang module to load implicitly.
When combined with namelookup's import graph computation forcing
overlays, this meant the entire transitive import graph would be loaded
because of the complicated mix of recursion and re-entrancy this
created.
The first step in teasing this apart is to define an API that doesn't
re-enter the clang importer when it loads modules. Then, the callers
that were relying on this need to be updated to explicitly call
ASTContext::getModule themselves.
This will also fix rdar://70745521 by happenstance.
The FileCollectorBase is the common interface shared by different
implementations. In lldb, we implement our own lazy variant that allows
us to do the heavy lifting out-of-process instead of inside the signal
handler.
To help consolidate our various types describing imports, this commit moves the following types and methods to Import.h:
* ImplicitImports
* ImplicitStdlibKind
* ImplicitImportInfo
* ModuleDecl::ImportedModule
* ModuleDecl::OrderImportedModules (as ImportedModule::Order)
* ModuleDecl::removeDuplicateImports() (as ImportedModule::removeDuplicates())
* SourceFile::ImportFlags
* SourceFile::ImportOptions
* SourceFile::ImportedModuleDesc
This commit is large and intentionally kept mechanical—nothing interesting to see here.
* Update tests that relied on old behavior.
* Use mangleCXXName instead of mangleCXXCtor.
* Call VisitCXXRecordDecl not VisitRecordDecl from
VisitClassTemplateSpecializationDecl. This allows template constructors
to be imported and called correctly.
Because C++ constructors always take a `this` pointer to the object to
be initialized, we mark the SIL function return type with the `@out`
attribute.
On the IRGen side, we retrofit support for formal indirect return values as
well as thin metatypes.
The Clang importer was filtering out cases where the same declaration
is imported twice under the same name, which can now happen when one
is synchronous and one is asynchronous. This happens when, e.g., an
Objective-C class provides both a completion-hander-based asynchronous
version and a synchronous version, and the Swift names line up after
the completion-handler parameter is dropped.
Stop filtering these out. Overload resolution is capable of handling
synchronous/asynchronous overloading based on context.
In #31686 changes were introduced to ensure that capacity was stored in
the ManagedBuffer allocation, and @lorentey sugested that as a stopgap
measure for addressing the lack of platform malloc introspection on
OpenBSD, we use Swift availability attributes instead on the relevant
parts of ManagedBuffer and friends.
Since platform availability symbols must be specifically set up to be
used, this commit does so in advance of the above change.
We need ClangImporterOptions to be persistent for several scenarios: (1)
when creating a sub-ASTContext to build Swift modules from interfaces; and
(2) when creating a new Clang instance to invoke Clang dependencies scanner.
This change is NFC.
When the checker found a breakage listed in the user-specified list,
the breage should be consumed internally without failing the check.
rdar://68086477
When a given Objective-C method has a completion handler parameter
with an appropriate signature, import that Objective-C method as
async. For example, consider the following CloudKit API:
- (void)fetchShareParticipantWithUserRecordID:(CKRecordID
*)userRecordID
completionHandler:(void (^)(CKShareParticipant * _Nullable shareParticipant, NSError * _Nullable error))completionHandler;
With the experimental concurrency model, this would import as:
func fetchShareParticipant(withUserRecordID userRecordID: CKRecord.ID) async throws -> CKShare.Participant?
The compiler will be responsible for turning the caller's continuation
into a block to pass along to the completion handler. When the error
parameter of the completion handler is non-null, the async call
will result in that error being thrown. Otherwise, the other arguments
passed to that completion handler will be returned as the result of
the async call.
async versions of methods are imported alongside their
completion-handler versions, to maintain source compatibility with
existing code that provides a completion handler.
Note that this only covers the Clang importer portion of this task.
Clang has two sources of IdentifierInfo pointers: the ASTContext and the
Preprocessor. Even though the keys from each can be used to index into
the other's tables, doing so has detrimental effects on the Clang
Importer.
At the very least, it will cause the Clang Importer to re-load modules
that should have already been cached down by implicit module builds.
This is because the module will build itself against a properly interned
key from the Preprocessor, but be looked up by a key from the ASTContext
after the next time.
Once in a blue moon, this may even allow Clang to return garbage to us,
though I'm still verifying that. For now, let's patch up this mess by
using the right source of keys.
The Clang Importer currently has a ridiculous re-entrant submodule loading path that winds up doing this anyways. Take Darwin as a prime example.
import Darwin.C.tgmath
In theory, this should load Darwin.C.tgmath and its immediate clang-only dependencies. In practice, namelookup::getAllImports winds up asking for the overlay associated with Darwin.C.tgmath. In order to load the overlay, it walks to the top-level module (Darwin) and tries to load a module with that name. Becuase we're in the middle of loading Darwin while importing tgmath, and because the compiler does not distinguish the act of loading a module from the act of loading an overlay, the Clang Importer would re-enter itself. The net effect is that every submodule import of a clang module *always* loads the top-most module and makes it visible. So
import Darwin.C.tgmath
actually becomes
import Darwin.C.tgmath
import Darwin
As long as we're here, and because this doesn't seem to actually hurt anything, let's optimize for this behavior. If the top-level module is requested, we need not call finishLoadingClangModule twice, just return the wrapper module it gives back.
Eventually, we should tame this implicit behavior with respect to overlay module loading.
We need to traverse the module dependency graph and track which modules expose
which other modules' ABIs, while making sure that we don't hit a loop while
trawling through Clang (sub)modules.
Fixes rdar://64993153.
The difference with `ModuleFile` is that `ModuleFileSharedCore` provides immutable data and is independent of a particular ASTContext.
It is designed to be able to be shared across multiple `ModuleFile`s of different `ASTContext`s in a thread-safe manner.
This adds support to `ClangImporter` to import C++ member function operators as static methods into Swift, which is part of SR-12748.
The left-hand-side operand, which gets passed as the `this` pointer to the C++ function is represented as an additional first parameter in the Swift method. It gets mapped back in SILGen.
Two of the tests are disabled on Windows because we can't yet call member functions correctly on Windows (SR-13129).
Expand the FrontendOptions to allow the enabling
of the dependency tracker for non-system
dependencies, and switch the previous clients of
`createDependencyTracker` over to using this
option. This ensures that the dependency tracker
is now set only during `CompilerInstance::setup`.
There's no reason clients need to be able to access this data directly.
It obscures where module loading is actually happening, and makes it too
easy to accidentally register a module with the wrong identifier in the
context.
Hide the registration operations behind opaque accessors.
clang::Decl::isHidden() is misleadingly named (see the associated FIXME
comment) and doesn't do what we want when
`-fmodules-local-submodule-visibility` is turned on.
This change alone isn't unfortunately enough to make Swift work with
`-fmodules-local-submodule-visibility`. For one thing, Clang's
Objective-C component doesn't work correctly with
`-fmodules-local-submodule-visibility`:
https://bugs.llvm.org/show_bug.cgi?id=46248
However, in the meantime, we should still clean up our use of
clang::Decl::isHidden().