Files
cppdraft_translate/cppdraft/module/interface.md
2025-10-25 03:02:53 +03:00

8.1 KiB
Raw Blame History

[module.interface]

10 Modules [module]

10.2 Export declaration [module.interface]

export-declaration:
export name-declaration
export { declaration-seqopt }
export-keyword module-import-declaration

1

#

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]

2

#

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.

3

#

If an exported declaration is not within a header unit, it shall not declare a name with internal linkage.

4

#

[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]

5

#

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]

6

#

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]

7

#

[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]

8

#

[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]