8.1 KiB
[module.interface]
10 Modules [module]
10.2 Export declaration [module.interface]
export-declaration:
export name-declaration
export { declaration-seqopt }
export-keyword module-import-declaration
An export-declaration shall inhabit a namespace scope and appear in the purview of a module interface unit.
An export-declaration shall not appear directly or indirectly within an unnamed namespace or a private-module-fragment.
An export-declaration has the declarative effects of itsname-declaration,declaration-seq (if any), ormodule-import-declaration.
The name-declaration of an export-declaration shall not declare a partial specialization ([temp.decls.general]).
The declaration-seq of an export-declaration shall not contain an export-declaration ormodule-import-declaration.
[Note 1:
An export-declaration does not establish a scope.
â end note]
A declaration is exported if it is declared within an export-declaration and inhabits a namespace scope or it is
a namespace-definition that contains an exported declaration, or
a declaration within a header unit ([module.import]) that introduces at least one name.
If an exported declaration is not within a header unit, it shall not declare a name with internal linkage.
[Example 1:
Source file "a.h":export int x;
Translation unit #1:module;#include "a.h" // error: declaration of x is not in the// purview of a module interface unitexport module M;export namespace {} // error: namespace has internal linkagenamespace {export int a2; // error: export of name with internal linkage}export static int b; // error: b explicitly declared staticexport int f(); // OKexport namespace N { } // OKexport using namespace N; // OK â end example]
If an exported declaration is a using-declaration ([namespace.udecl]) and is not within a header unit, all entities named by theusing-declarators (if any) shall either be a type alias or have been introduced with a name having external linkage.
[Example 2:
Source file "b.h":int f();
Importable header "c.h":int g();
Translation unit #1:export module X;export int h();
Translation unit #2:module;#include "b.h"export module M;import "c.h";import X;export using ::f, ::g, ::h; // OKstruct S;export using ::S; // error: S has module linkagenamespace N {export int h(); static int h(int); // #1}export using N::h; // error: #1 has internal linkage â end example]
[Note 2:
The underlying entity of an exported type alias need not have a name with external linkage.
[Example 3: export module M;struct S;export using T = S; // OK, exports name T denoting type S â end example]
â end note]
A redeclaration of an entity X is implicitly exported if X was introduced by an exported declaration; otherwise it shall not be exported unless it is a type alias, a namespace, or a namespace alias.
[Example 4: export module M;struct S { int n; };typedef S S;export typedef S S; // OKexport struct S; // error: exported declaration follows non-exported declarationnamespace N { // external linkage, attached to global module, not exportedvoid f();}namespace N { // OK, exported namespace redeclaring non-exported namespaceexport void g();} â end example]
[Note 3:
Names introduced by exported declarations have either external linkage or no linkage; see [basic.link].
Namespace-scope declarations exported by a module can be found by name lookup in any translation unit importing that module ([basic.lookup]).
Class and enumeration member names can be found by name lookup in any context in which a definition of the type is reachable.
â end note]
[Example 5:
Interface unit of M:export module M;export struct X {static void f(); struct Y { };};
namespace {struct S { };}export void f(S); // OKstruct T { };export T id(T); // OKexport struct A; // A exported as incompleteexport auto rootFinder(double a) {return [=](double x) { return (x + a/x)/2; };}export const int n = 5; // OK, n has external linkage
Implementation unit of M:module M;struct A {int value;};
Main program:import M;int main() { X::f(); // OK, X is exported and definition of X is reachable X::Y y; // OK, X::Y is exported as a complete typeauto f = rootFinder(2); // OKreturn A{45}.value; // error: A is incomplete} â end example]
[Note 4:
Declarations in an exported namespace-definition or in an exported linkage-specification ([dcl.link]) are exported and subject to the rules of exported declarations.
[Example 6: export module M;int g;export namespace N {int x; // OKusing ::g; // error: ::g has module linkage} â end example]
â end note]