Is [extern_c] necessary in module map?

Hi,

The original post was a bugzilla report ( http://llvm.org/bugs/show_bug.cgi?id=21626 ), Richard Smith suggested that bugzilla wasn’t a good place to discuss about the development details, so I moved the post to here.

I wanted to accelerate the build process of one of my OS X projects and I tried to use clang’s module feature but had no luck.

This is a trivial source code:

#import <Cocoa/Cocoa.h>
int main() { }

I built it with clang svn trunk:

$ /opt/bin/clang++ -fmodules -c -o m m.mm

and I got a huge bunch of error messages:

While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreFoundation' imported from /System/Library/Frameworks/Foundation.framework/Headers/Foundation.h:6:
While building module 'Dispatch' imported from /System/Library/Frameworks/CoreFoundation.framework/Headers/CFStream.h:15:
In file included from <module-includes>:1:
In file included from /usr/include/dispatch/dispatch.h:52:
/usr/include/dispatch/queue.h:368:1: error: import of C++ module 'Darwin.sys.qos' appears within extern "C" language linkage specification
#include <sys/qos.h>
^
/usr/include/dispatch/queue.h:69:1: note: extern "C" language linkage specification begins here
__BEGIN_DECLS
^
/usr/include/sys/cdefs.h:71:23: note: expanded from macro '__BEGIN_DECLS'
#define __BEGIN_DECLS extern "C" {
^

… tons of lines omitted …

I was told that this was because the system’s module map was not adapted to be built as C++ mode, and I should add [extern_c] to the module map files. So I modified module.map files in

/usr/include
/usr/include/mach-o
/usr/include/dispatch
/usr/include/objc

then cleaned ModuleCache in tmp directory and I compiled the source again, here was what I got from the compiler:

$ /opt/bin/clang++ -fmodules -c -o m m.mm
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreGraphics' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSGeometry.h:12:
While building module 'IOKit' imported from /System/Library/Frameworks/CoreGraphics.framework/Headers/CGDisplayConfiguration.h:8:
In file included from <module-includes>:7:
/System/Library/Frameworks/IOKit.framework/Headers/IOCFPlugIn.h:32:1: error: import of C++ module 'CoreFoundation.CFPlugIn' appears within extern "C" language linkage specification
#include <CoreFoundation/CFPlugIn.h>
^
/System/Library/Frameworks/IOKit.framework/Headers/IOCFPlugIn.h:30:1: note: extern "C" language linkage specification begins here
__BEGIN_DECLS
^
/usr/include/sys/cdefs.h:71:23: note: expanded from macro '__BEGIN_DECLS'
#define __BEGIN_DECLS extern "C" {

In short, I needed to add [extern_c] to every module map file in every framework.

I don't get the point of [extern_c], why it is required? In header files, all symbols that have C linkage can be recognized and exported correctly, clang does't have to depend on another marker to distinguish them against "C++" linkage.

Richard Smith kindly explained the point of [extern_c]:

The point of [extern_c] is twofold: (1) it builds thetarget module in an implicit extern "C" context (which
affects its semantics in lots of ways), and (2) it
allows the module to be imported in an extern "C"
context. You don't want (2) without (1), because that
can lead to silent and hard-to-diagnose build breaks.

So here is my problem:

I don't know whether it is correct: `module` works like precompiled headers which works fine without [extern_c]. Since `extern "C"` is a linkage, i.e., it is used in link-time, and the linker works fine with current defines in headers, why another marker is needed at compile-time?

My another problem is:

I have modified all module maps in OS X SDK and recompile the code, this time the header-file-scattering problem. In OS X/iOS SDK, header files in one framework could be in another framework, for example: IORegistryEntry.h belongs to IOKit,but it is placed under Kernel.framework. I know this is Apple's problem, too, but the old question: without `-fmodules`, the compiler works fine with locating the file in both objective-C and C++ mode.

Below was what I got from the compiler:

While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreGraphics' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSGeometry.h:12:
While building module 'IOKit' imported from /System/Library/Frameworks/CoreGraphics.framework/Headers/CGDisplayConfiguration.h:8:
In file included from <module-includes>:126:
/System/Library/Frameworks/IOKit.framework/Headers/video/IOVideoDevice.h:12:10: fatal error: 'IOKit/IOService.h' file not found
#include <IOKit/IOService.h>
^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreGraphics' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSGeometry.h:12:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/CoreGraphics.framework/Headers/CoreGraphics.h:41:
/System/Library/Frameworks/CoreGraphics.framework/Headers/CGDisplayConfiguration.h:8:10: fatal error: could not build module 'IOKit'
#include <IOKit/IOKitLib.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreGraphics' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSGeometry.h:12:
While building module 'IOSurface' imported from /System/Library/Frameworks/CoreGraphics.framework/Headers/CGDisplayStream.h:9:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/IOSurface.framework/Headers/IOSurface.h:13:
/System/Library/Frameworks/IOSurface.framework/Headers/IOSurfaceAPI.h:12:10: fatal error: could not build module 'IOKit'
#include <IOKit/IOKitLib.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/Foundation.framework/Headers/Foundation.h:42:
In file included from /System/Library/Frameworks/Foundation.framework/Headers/NSKeyedArchiver.h:8:
/System/Library/Frameworks/Foundation.framework/Headers/NSGeometry.h:12:9: fatal error: could not build module 'CoreGraphics'
#import <CoreGraphics/CGBase.h>
~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreServices' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSURLError.h:12:
While building module 'DiskArbitration' imported from /System/Library/Frameworks/CoreServices.framework/Frameworks/CarbonCore.framework/Headers/Files.h:56:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/DiskArbitration.framework/Headers/DiskArbitration.h:29:
/System/Library/Frameworks/DiskArbitration.framework/Headers/DADisk.h:28:10: fatal error: could not build module 'IOKit'
#include <IOKit/IOKitLib.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'CoreServices' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSURLError.h:12:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/CoreServices.framework/Headers/CoreServices.h:23:
In file included from /System/Library/Frameworks/CoreServices.framework/Frameworks/AE.framework/Headers/AE.h:20:
In file included from /System/Library/Frameworks/CoreServices.framework/Frameworks/CarbonCore.framework/Headers/CarbonCore.h:87:
In file included from /System/Library/Frameworks/CoreServices.framework/Frameworks/CarbonCore.framework/Headers/Components.h:26:
/System/Library/Frameworks/CoreServices.framework/Frameworks/CarbonCore.framework/Headers/Files.h:56:10: fatal error: could not build module 'DiskArbitration'
#include <DiskArbitration/DADisk.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'ApplicationServices' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSAppleEventDescriptor.h:7:
In file included from <module-includes>:1:
/System/Library/Frameworks/ApplicationServices.framework/Headers/ApplicationServices.h:23:10: fatal error: could not build module 'CoreServices'
#include <CoreServices/CoreServices.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'ApplicationServices' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSAppleEventDescriptor.h:7:
While building module 'CoreText' imported from /System/Library/Frameworks/ApplicationServices.framework/Frameworks/ATS.framework/Headers/SFNTLayoutTypes.h:16:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/ApplicationServices.framework/Frameworks/CoreText.framework/Headers/CoreText.h:21:
In file included from /System/Library/Frameworks/CoreText.framework/Headers/CTFont.h:21:
/System/Library/Frameworks/CoreText.framework/Headers/CTFontDescriptor.h:28:10: fatal error: could not build module 'CoreGraphics'
#include <CoreGraphics/CGAffineTransform.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'Foundation' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:
While building module 'ApplicationServices' imported from /System/Library/Frameworks/Foundation.framework/Headers/NSAppleEventDescriptor.h:7:
While building module 'ImageIO' imported from /System/Library/Frameworks/ApplicationServices.framework/Headers/ApplicationServices.h:47:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/ApplicationServices.framework/Frameworks/ImageIO.framework/Headers/ImageIO.h:16:
/System/Library/Frameworks/ImageIO.framework/Headers/CGImageSource.h:14:10: fatal error: could not build module 'CoreGraphics'
#include <CoreGraphics/CoreGraphics.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
In file included from <module-includes>:1:
/System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:12:9: fatal error: could not build module 'Foundation'
#import <Foundation/Foundation.h>
~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'AppKit' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:13:
In file included from <module-includes>:1:
/System/Library/Frameworks/AppKit.framework/Headers/AppKit.h:10:9: fatal error: could not build module 'Foundation'
#import <Foundation/Foundation.h>
~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'AppKit' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:13:
While building module 'QuartzCore' imported from /System/Library/Frameworks/AppKit.framework/Headers/NSColor.h:36:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/QuartzCore.framework/Headers/CAAnimation.h:6:
In file included from /System/Library/Frameworks/QuartzCore.framework/Headers/CALayer.h:6:
In file included from /System/Library/Frameworks/QuartzCore.framework/Headers/CAMediaTiming.h:6:
/System/Library/Frameworks/QuartzCore.framework/Headers/CABase.h:17:10: fatal error: could not build module 'ApplicationServices'
#include <ApplicationServices/ApplicationServices.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'AppKit' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:13:
While building module 'QuartzCore' imported from /System/Library/Frameworks/AppKit.framework/Headers/NSColor.h:36:
While building module 'CoreVideo' imported from /System/Library/Frameworks/QuartzCore.framework/Headers/CAOpenGLLayer.h:7:
In file included from <module-includes>:1:
In file included from /System/Library/Frameworks/CoreVideo.framework/Headers/CoreVideo.h:25:
/System/Library/Frameworks/CoreVideo.framework/Headers/CVDisplayLink.h:24:10: fatal error: could not build module 'ApplicationServices'
#include <ApplicationServices/ApplicationServices.h>
~~~~~~~~^
While building module 'Cocoa' imported from m.mm:1:
While building module 'AppKit' imported from /System/Library/Frameworks/Cocoa.framework/Headers/Cocoa.h:13:
While building module 'CoreData' imported from /System/Library/Frameworks/AppKit.framework/Headers/NSPredicateEditorRowTemplate.h:12:
In file included from <module-includes>:1:
/System/Library/Frameworks/CoreData.framework/Headers/CoreData.h:8:9: fatal error: could not build module 'Foundation'
#import <Foundation/Foundation.h>
~~~~~~~^
m.mm:1:9: fatal error: could not build module 'Cocoa'
#import <Cocoa/Cocoa.h>
~~~~~~~^
15 errors generated.