|
| 1 | +--- |
| 2 | +title: "extern (C++) | Microsoft Docs" |
| 3 | +ms.custom: "" |
| 4 | +ms.date: "04/12/2018" |
| 5 | +ms.reviewer: "" |
| 6 | +ms.suite: "" |
| 7 | +ms.technology: ["cpp-language"] |
| 8 | +ms.tgt_pltfrm: "" |
| 9 | +ms.topic: "language-reference" |
| 10 | +f1_keywords: ["extern", "extern_CPP"] |
| 11 | +dev_langs: ["C++"] |
| 12 | +helpviewer_keywords: ["extern keyword [C++], linkage to non-C++ functions", "declarations, external", "external linkage, extern modifier"] |
| 13 | +ms.assetid: 1e2f0ae3-ae98-4410-85b5-222d6abc865a |
| 14 | +caps.latest.revision: 11 |
| 15 | +author: "mikeblome" |
| 16 | +ms.author: "mblome" |
| 17 | +manager: "ghogen" |
| 18 | +ms.workload: ["cplusplus"] |
| 19 | +--- |
| 20 | +# extern (C++) |
| 21 | + |
| 22 | +The **extern** keyword is applied to a global variable, function or template declaration to specify that the name of that thing has *external linkage*. For background information on linkage and why the use of global variables is discouraged, see [Program and linkage](program-and-linkage-cpp.md). |
| 23 | + |
| 24 | +The **extern** keyword has four meanings depending on the context: |
| 25 | + |
| 26 | +1. in a non-const global variable declaration, **extern** specifies that the variable or function is defined in another translation unit. The **extern** must be applied in all files except the one where the variable is defined. |
| 27 | +1. in a const variable declaration, it specifies that the variable has external linkage. The **extern** must be applied to all declarations in all files. (Global const variables have internal linkage by default.) |
| 28 | +1. **extern "C"** specifies that the function is defined elsewhere and uses the C-language calling convention. The extern "C" modifier may also be applied to multiple function declarations in a block. |
| 29 | +1. in a template declaration, it specifies that the template has already been instantiated elsewhere. This is an optimization that tells the compiler that it can re-use the other instantiation rather than creating a new one at the current location. For more information about this use of **extern**, see [Templates](templates-cpp.md). |
| 30 | + |
| 31 | +## extern linkage for non-const globals |
| 32 | + |
| 33 | +When the linker sees **extern** before a global variable declaration, it looks for the definition in another translation unit. Declarations of non-const variables at global scope are external by default; only apply **extern** to the declarations that don't provide the definition. |
| 34 | + |
| 35 | +```cpp |
| 36 | +//fileA.cpp |
| 37 | +int i = 42; // declaration and definition |
| 38 | + |
| 39 | +//fileB.cpp |
| 40 | +extern int i; // declaration only. same as i in FileA |
| 41 | + |
| 42 | +//fileC.cpp |
| 43 | +extern int i; // declaration only. same as i in FileA |
| 44 | + |
| 45 | +//fileD.cpp |
| 46 | +int i = 43; // LNK2005! 'i' already has a definition. |
| 47 | +extern int i = 43; // same error (extern is ignored on definitions) |
| 48 | +``` |
| 49 | + |
| 50 | +## extern linkage for const globals |
| 51 | + |
| 52 | +A **const** global variable has internal linkage by default. If you want the variable to have external linkage, apply the **extern** keyword to definition as well as to all other declarations in other files: |
| 53 | + |
| 54 | +```cpp |
| 55 | +//fileA.cpp |
| 56 | +extern const int i = 42; // extern const definition |
| 57 | + |
| 58 | +//fileB.cpp |
| 59 | +extern const int i; // declaration only. same as i in FileA |
| 60 | +``` |
| 61 | + |
| 62 | +## extern constexpr linkage |
| 63 | + |
| 64 | +In Visual Studio 2017 version 15.3 and earlier, the compiler always gave a constexpr variable internal linkage even when the variable was marked extern. In Visual Studio 2017 version 15.5, a new compiler switch ([/Zc:externConstexpr](../build/reference/zc-externconstexpr.md)) enables correct standards-conforming behavior. Eventually this will become the default. |
| 65 | + |
| 66 | +```cpp |
| 67 | +extern constexpr int x = 10; //error LNK2005: "int const x" already defined |
| 68 | +``` |
| 69 | + |
| 70 | +If a header file contains a variable declared extern constexpr, it needs to be marked **__declspec(selectany)** in order to correctly have its duplicate declarations combined: |
| 71 | + |
| 72 | +```cpp |
| 73 | +extern constexpr __declspec(selectany) int x = 10; |
| 74 | +``` |
| 75 | +
|
| 76 | +## extern "C" and extern "C++" function declarations |
| 77 | +
|
| 78 | + In C++, when used with a string, **extern** specifies that the linkage conventions of another language are being used for the declarator(s). C functions and data can be accessed only if they are previously declared as having C linkage. However, they must be defined in a separately compiled translation unit. |
| 79 | +
|
| 80 | + Microsoft C++ supports the strings **"C"** and **"C++"** in the *string-literal* field. All of the standard include files use the **extern** "C" syntax to allow the run-time library functions to be used in C++ programs. |
| 81 | +
|
| 82 | +## Example |
| 83 | +
|
| 84 | +The following example shows how to declare names that have C linkage: |
| 85 | +
|
| 86 | +```cpp |
| 87 | +// Declare printf with C linkage. |
| 88 | +extern "C" int printf(const char *fmt, ...); |
| 89 | +
|
| 90 | +// Cause everything in the specified |
| 91 | +// header files to have C linkage. |
| 92 | +extern "C" { |
| 93 | + // add your #include statements here |
| 94 | +#include <stdio.h> |
| 95 | +} |
| 96 | +
|
| 97 | +// Declare the two functions ShowChar |
| 98 | +// and GetChar with C linkage. |
| 99 | +extern "C" { |
| 100 | + char ShowChar(char ch); |
| 101 | + char GetChar(void); |
| 102 | +} |
| 103 | +
|
| 104 | +// Define the two functions |
| 105 | +// ShowChar and GetChar with C linkage. |
| 106 | +extern "C" char ShowChar(char ch) { |
| 107 | + putchar(ch); |
| 108 | + return ch; |
| 109 | +} |
| 110 | +
|
| 111 | +extern "C" char GetChar(void) { |
| 112 | + char ch; |
| 113 | + ch = getchar(); |
| 114 | + return ch; |
| 115 | +} |
| 116 | +
|
| 117 | +// Declare a global variable, errno, with C linkage. |
| 118 | +extern "C" int errno; |
| 119 | +``` |
| 120 | + |
| 121 | + If a function has more than one linkage specification, they must agree; it is an error to declare functions as having both C and C++ linkage. Furthermore, if two declarations for a function occur in a program — one with a linkage specification and one without — the declaration with the linkage specification must be first. Any redundant declarations of functions that already have linkage specification are given the linkage specified in the first declaration. For example: |
| 122 | + |
| 123 | +```cpp |
| 124 | +extern "C" int CFunc1(); |
| 125 | +... |
| 126 | +int CFunc1(); // Redeclaration is benign; C linkage is |
| 127 | + // retained. |
| 128 | + |
| 129 | +int CFunc2(); |
| 130 | +... |
| 131 | +extern "C" int CFunc2(); // Error: not the first declaration of |
| 132 | + // CFunc2; cannot contain linkage |
| 133 | + // specifier. |
| 134 | +``` |
| 135 | +
|
| 136 | +## See Also |
| 137 | +
|
| 138 | +- [Keywords](../cpp/keywords-cpp.md) |
| 139 | +- [Program and linkage](program-and-linkage-cpp.md) |
| 140 | +- [extern Storage-Class Specifier in C](../c-language/extern-storage-class-specifier.md) |
| 141 | +- [Behavior of Identifiers in C](../c-language/behavior-of-identifiers.md) |
| 142 | +- [Linkage in C](../c-language/linkage.md) |
0 commit comments