I did a poor investigation of SR-15586:
import Foundation hides declarations (derived from C) in other modules on Linux for these few months.
I finally found that it is a bug caused by
ClangImporter which is due to how it imports C declarations. Furthermore, the issue would occur on any platforms, even on macOS. (Filed as SR-15822: Existence of modulemap disables declarations in simple C headers in some cases.)
ClangImporter::Implementation) holds the instances of
ClangModuleUnit which wraps a clang module. On the other hand, it also holds
BridgingHeaderLookupTable that contains C declarations derived from bridging headers, for example, from headers imported with
The problem here is that
ClangImporter::Implementation has only one unique instance of
clang::CompilerInstance (created in
ClangImporter::create). It also uses one unique instance of
clang::Preprocessor which holds a unique instance of
clang::HeaderSearch. (The status quo of Swift's implementation)
ClangImporter::Implementation::loadModuleClang calls the instance of
clang::HeaderSearch to load a clang module. At the time of it, #include guards in the headers required by the module are being enabled.
That does matter when
ClangImporter::Implementation tries to import bridging headers.
ClangImporter::Implementation::importHeader uses the instance of
clang::Preprocessor to parse the bridging header such as
#include "c.h" which is generated in
However, if the bridging header wants to include some headers already imported by some other clang modules, #include guards block to include the same headers.
Then, no declarations in those headers are added to
As a result, for example,
LookupByName::doLocalLookup fails to look up some types, because it doesn't try to look up the type in other (clang) modules.
I think this feature of
Clang::Importer causes some bugs such as SR-15822, SR-15586, SR-15532, and SR-15462.
The error messages don't imply the nature of the problem, but the compiler would be confused by such feature.
ClangImporter import separately clang modules and bridging C headers?