Skip to content

Commit fd0f883

Browse files
authored
Merge pull request #2296 from MicrosoftDocs/master
9/4/2019 AM Publish
2 parents 6e1c182 + 79b2f74 commit fd0f883

File tree

273 files changed

+1444
-1108
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

273 files changed

+1444
-1108
lines changed

docs/build/reference/compiler-options-listed-alphabetically.md

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,8 @@ The following is a comprehensive alphabetical list of compiler options. For a ca
2929
|[/EP](ep-preprocess-to-stdout-without-hash-line-directives.md)|Copies preprocessor output to standard output.|
3030
|[/errorReport](errorreport-report-internal-compiler-errors.md)|Allows you to provide internal compiler error (ICE) information directly to the Microsoft C++ team.|
3131
|[/execution-charset](execution-charset-set-execution-character-set.md)|Set execution character set.|
32+
|[/experimental:module](experimental-module.md)|Enables experimental module support.|
33+
|[/experimental:preprocessor](experimental-preprocessor.md)|Enables experimental conforming preprocessor support.|
3234
|[/F](f-set-stack-size.md)|Sets stack size.|
3335
|[/favor](favor-optimize-for-architecture-specifics.md)|Produces code that is optimized for a specific x64 architecture or for the specifics of micro-architectures in both the AMD64 and Extended Memory 64 Technology (EM64T) architectures.|
3436
|[/FA](fa-fa-listing-file.md)|Creates a listing file.|
@@ -102,6 +104,7 @@ The following is a comprehensive alphabetical list of compiler options. For a ca
102104
|[/Qimprecise_fwaits](qimprecise-fwaits-remove-fwaits-inside-try-blocks.md)|Removes `fwait` commands inside `try` blocks.|
103105
|[/Qpar (Auto-Parallelizer)](qpar-auto-parallelizer.md)|Enables automatic parallelization of loops that are marked with the [#pragma loop()](../../preprocessor/loop.md) directive.|
104106
|[/Qsafe_fp_loads](qsafe-fp-loads.md)|Uses integer move instructions for floating-point values and disables certain floating point load optimizations.|
107+
|[/Qspectre](qspectre.md)|Specifies compiler generation of instructions to mitigate certain Spectre variant 1 security vulnerabilities.|
105108
|[/Qvec-report (Auto-Vectorizer Reporting Level)](qvec-report-auto-vectorizer-reporting-level.md)|Enables reporting levels for automatic vectorization.|
106109
|[/RTC](rtc-run-time-error-checks.md)|Enables run-time error checking.|
107110
|[/sdl](sdl-enable-additional-security-checks.md)|Enables additional security features and warnings.|

docs/build/reference/compiler-options-listed-by-category.md

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -188,6 +188,15 @@ This article contains a categorical list of compiler options. For an alphabetica
188188
|[/permissive-](permissive-standards-conformance.md)|Set standard-conformance mode.|
189189
|[/std](std-specify-language-standard-version.md)|C++ standard version compatibility selector.|
190190

191+
## Experimental options
192+
193+
Experimental options may only be supported by certain versions of the compiler, and may behave differently in different compiler versions. Often the best, or only, documentation for experimental options is in the [Microsoft C++ Team Blog](https://devblogs.microsoft.com/cppblog/).
194+
195+
|Option|Purpose|
196+
|------------|-------------|
197+
|[/experimental:module](experimental-module.md)|Enables experimental module support.|
198+
|[/experimental:preprocessor](experimental-preprocessor.md)|Enables experimental conforming preprocessor support.|
199+
191200
## Deprecated and removed compiler options
192201

193202
|Option|Purpose|
Lines changed: 42 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,42 @@
1+
---
2+
title: "/experimental:module (Enable module support)"
3+
description: "Use the /experimental:module compiler option to enable experimental compiler support for modules."
4+
ms.date: "09/03/2019"
5+
f1_keywords: ["module", "/experimental:module"]
6+
helpviewer_keywords: ["module", "/experimental:module", "Enable module support"]
7+
---
8+
# /experimental:module (Enable module support)
9+
10+
Enables experimental compiler support for modules, as specified by the draft C++20 standard.
11+
12+
## Syntax
13+
14+
> **/experimental:module**[**-**]
15+
16+
## Remarks
17+
18+
You can enable experimental modules support by use of the **/experimental:module** compiler option along with the [/std:c++latest](std-specify-language-standard-version.md) option. You can use **/experimental:module-** to disable module support explicitly.
19+
20+
This option is available starting in Visual Studio 2015 Update 1. As of Visual Studio 2019 version 16.2, Draft C++20 Standard modules are not fully implemented in the Microsoft C++ compiler. You can use the modules feature to create single-partition modules and to import the Standard Library modules provided by Microsoft. A module and the code that consumes it must be compiled with the same compiler options.
21+
22+
For more information on modules and how to use and create them, see [Overview of modules in C++](../../cpp/modules-cpp.md).
23+
24+
Here's an example of the compiler command-line options used to create an export module from source file *ModuleName.ixx*:
25+
26+
```cmd
27+
cl /EHsc /MD /experimental:module /module:export /module:name ModuleName /module:wrapper C:\Output\path\ModuleName.h /module:output C:\Output\path\ModuleName.ifc -c ModuleName.ixx
28+
```
29+
30+
### To set this compiler option in the Visual Studio development environment
31+
32+
1. Open the project's **Property Pages** dialog box. For details, see [Set C++ compiler and build properties in Visual Studio](../working-with-project-properties.md).
33+
34+
1. Set the **Configuration** drop-down to **All Configurations**.
35+
36+
1. Select the **Configuration Properties** > **C/C++** > **Language** property page.
37+
38+
1. Modify the **Enable C++ Modules (experimental)** property, and then choose **OK**.
39+
40+
## See also
41+
42+
[/Zc (Conformance)](zc-conformance.md)
Lines changed: 245 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,245 @@
1+
---
2+
title: "/experimental:preprocessor (Enable preprocessor conformance mode)"
3+
description: "Use the /experimental:preprocessor compiler option to enable experimental compiler support for a standard conforming preprocessor."
4+
ms.date: "09/03/2019"
5+
f1_keywords: ["preprocessor", "/experimental:preprocessor"]
6+
helpviewer_keywords: ["preprocessor conformance", "/experimental:preprocessor", "Enable preprocessor conformance mode"]
7+
---
8+
# /experimental:preprocessor (Enable preprocessor conformance mode)
9+
10+
This option enables an experimental, token-based preprocessor that conforms to C++11 standards, including C99 preprocessor features.
11+
12+
## Syntax
13+
14+
> **/experimental:preprocessor**[**-**]
15+
16+
## Remarks
17+
18+
Use the **/experimental:preprocessor** compiler option to enable the experimental conforming preprocessor. You can use **/experimental:preprocessor-** option to explicitly specify the traditional preprocessor.
19+
20+
The **/experimental:preprocessor** option is available starting in Visual Studio 2017 version 15.8.
21+
22+
You can detect which preprocessor is in use at compile time. Check the value of the predefined macro [\_MSVC\_TRADITIONAL](../../preprocessor/predefined-macros.md) to tell if the traditional preprocessor is in use. This macro is set unconditionally by versions of the compiler that support it, independent of which preprocessor is invoked. Its value is 1 for the traditional preprocessor. It's 0 for the conformant experimental preprocessor:
23+
24+
```cpp
25+
#if defined(_MSVC_TRADITIONAL) && _MSVC_TRADITIONAL
26+
// Logic using the traditional preprocessor
27+
#else
28+
// Logic using cross-platform compatible preprocessor
29+
#endif
30+
```
31+
32+
### Behavior changes in the experimental preprocessor
33+
34+
Here are some of the more common breaking changes found when preprocessor conformance mode is enabled:
35+
36+
#### Macro comments
37+
38+
The traditional preprocessor uses character buffers instead of preprocessor tokens. That allows some unusual behavior, such as this preprocessor comment trick, which doesn't work under the conforming preprocessor:
39+
40+
```cpp
41+
#if DISAPPEAR
42+
#define DISAPPEARING_TYPE /##/
43+
#else
44+
#define DISAPPEARING_TYPE int
45+
#endif
46+
47+
// myVal disappears when DISAPPEARING_TYPE is turned into a comment
48+
// To make standards compliant, wrap the following line with the appropriate #if/#endif
49+
DISAPPEARING_TYPE myVal;
50+
```
51+
52+
#### String prefixes (L#val)
53+
54+
The traditional preprocessor incorrectly combines a string prefix to the result of the [stringizing operator (#)](../../preprocessor/stringizing-operator-hash.md):
55+
56+
```cpp
57+
#define DEBUG_INFO(val) L"debug prefix:" L#val
58+
// ^
59+
// this prefix
60+
61+
const wchar_t *info = DEBUG_INFO(hello world);
62+
```
63+
64+
The `L` prefix is unnecessary here, because the adjacent string literals get combined after macro expansion anyway. The backward compatible fix is to change the definition to:
65+
66+
```cpp
67+
#define DEBUG_INFO(val) L"debug prefix:" #val
68+
// ^
69+
// no prefix
70+
```
71+
72+
This issue is also found in convenience macros that 'stringize' the argument to a wide string literal:
73+
74+
```cpp
75+
// The traditional preprocessor creates a single wide string literal token
76+
#define STRING(str) L#str
77+
78+
// Potential fixes:
79+
// Use string concatenation of L"" and #str to add prefix
80+
// This works because adjacent string literals are combined after macro expansion
81+
#define STRING1(str) L""#str
82+
83+
// Add the prefix after #str is stringized with additional macro expansion
84+
#define WIDE(str) L##str
85+
#define STRING2(str) WIDE(#str)
86+
87+
// Use concatenation operator ## to combine the tokens.
88+
// The order of operations for ## and # is unspecified, although all compilers
89+
// checked perform the # operator before ## in this case.
90+
#define STRING3(str) L## #str
91+
```
92+
93+
#### Warning on invalid ##
94+
95+
When the [token-pasting operator (##)](../../preprocessor/token-pasting-operator-hash-hash.md) doesn't result in a single, valid preprocessing token, the behavior is undefined. The traditional preprocessor silently fails to combine the tokens. The new preprocessor matches the behavior of most other compilers and emits a diagnostic.
96+
97+
```cpp
98+
// The ## is unnecessary and doesn't result in a single preprocessing token.
99+
#define ADD_STD(x) std::##x
100+
101+
// Declare a std::string
102+
ADD_STD(string) s;
103+
```
104+
105+
#### Comma elision in variadic macros
106+
107+
Consider the following example:
108+
109+
```cpp
110+
void func(int, int = 2, int = 3);
111+
// This macro replacement list has a comma followed by __VA_ARGS__
112+
#define FUNC(a, ...) func(a, __VA_ARGS__)
113+
int main()
114+
{
115+
// The following macro is replaced with:
116+
// func(10,20,30)
117+
FUNC(10, 20, 30);
118+
119+
// A conforming preprocessor replaces the following macro with:
120+
// func(1, );
121+
// which results in a syntax error.
122+
FUNC(1, );
123+
}
124+
```
125+
126+
All major compilers have a preprocessor extension that helps address this issue. The traditional MSVC preprocessor always removes commas before empty `__VA_ARGS__` replacements. The updated preprocessor more closely follows the behavior of other popular cross platform compilers. For the comma to be removed, the variadic argument must be missing, not just empty, and it must be marked with a `##` operator:
127+
128+
```cpp
129+
#define FUNC2(a, ...) func(a , ## __VA_ARGS__)
130+
int main()
131+
{
132+
// The variadic argument is missing in the macro being evoked
133+
// The comma is removed and replaced with:
134+
// func(1)
135+
FUNC2(1);
136+
137+
// The variadic argument is empty, but not missing. (Notice the
138+
// comma in the argument list.) The comma isn't removed
139+
// when the macro is replaced:
140+
// func(1, )
141+
FUNC2(1, );
142+
}
143+
```
144+
145+
In the upcoming C++2a standard, this issue has been addressed by adding `__VA_OPT__`, which isn't implemented yet.
146+
147+
#### Macro arguments are 'unpacked'
148+
149+
In the traditional preprocessor, if a macro forwards one of its arguments to another dependent macro, then the argument doesn't get "unpacked" when it's substituted. Usually this optimization goes unnoticed, but it can lead to unusual behavior:
150+
151+
```cpp
152+
// Create a string out of the first argument, and the rest of the arguments.
153+
#define TWO_STRINGS( first, ... ) #first, #__VA_ARGS__
154+
#define A( ... ) TWO_STRINGS(__VA_ARGS__)
155+
156+
const char* c[2] = { A(1, 2) };
157+
// Conformant preprocessor results:
158+
// const char c[2] = { "1", "2" };
159+
// Traditional preprocessor results, all arguments are in the first string:
160+
// const char c[2] = { "1, 2", };
161+
```
162+
163+
When expanding `A()`, the traditional preprocessor forwards all of the arguments packaged in `__VA_ARGS__` to the first argument of `TWO_STRINGS`. The variadic argument of `TWO_STRINGS` is empty, which causes the result of `#first` to be `"1, 2"` rather than just `"1"`. You may be wondering what happened to the result of `#__VA_ARGS__` in the traditional preprocessor expansion. if the variadic parameter is empty, it should result in an empty string literal "". Because of a separate issue, the empty string literal token wasn't generated.
164+
165+
#### Rescanning replacement list for macros
166+
167+
After a macro is replaced, the resulting tokens are rescanned for additional macro identifiers to replace. The rescan algorithm used by the traditional preprocessor isn't conformant, as shown in this example based on actual code:
168+
169+
```cpp
170+
#define CAT(a,b) a ## b
171+
#define ECHO(...) __VA_ARGS__
172+
173+
// IMPL1 and IMPL2 are implementation details
174+
#define IMPL1(prefix,value) do_thing_one( prefix, value)
175+
#define IMPL2(prefix,value) do_thing_two( prefix, value)
176+
// MACRO chooses the expansion behavior based on the value passed to macro_switch
177+
#define DO_THING(macro_switch, b) CAT(IMPL, macro_switch) ECHO(( "Hello", b))
178+
179+
DO_THING(1, "World");
180+
// Traditional preprocessor:
181+
// do_thing_one( "Hello", "World");
182+
// Conformant preprocessor:
183+
// IMPL1 ( "Hello","World");
184+
```
185+
186+
To see what is going on in this example, we break down the expansion starting with `DO_THING`:
187+
188+
`DO_THING(1, "World")` ->
189+
`CAT(IMPL, 1) ECHO(("Hello", "World"))`
190+
191+
Second, CAT is expanded:
192+
193+
`CAT(IMPL, 1)` -> `IMPL ## 1` -> `IMPL1`
194+
195+
Which puts the tokens into this state:
196+
197+
`IMPL1 ECHO(("Hello", "World"))`
198+
199+
The preprocessor finds the function-like macro identifier `IMPL1`, but it's not followed by a "(", so it's not considered a function-like macro invocation. It moves on to the following tokens and finds the function-like macro `ECHO` invoked:
200+
201+
`ECHO(("Hello", "World"))` -> `("Hello", "World")`
202+
203+
`IMPL1` is never considered again for expansion, so the full result of the expansions is:
204+
205+
`IMPL1("Hello", "World");`
206+
207+
The macro can be modified to behave the same way under both the experimental preprocessor and the traditional preprocessor. The solution is to add another layer of indirection:
208+
209+
```cpp
210+
#define CAT(a,b) a##b
211+
#define ECHO(...) __VA_ARGS__
212+
213+
// IMPL1 and IMPL2 are macros implementation details
214+
#define IMPL1(prefix,value) do_thing_one( prefix, value)
215+
#define IMPL2(prefix,value) do_thing_two( prefix, value)
216+
217+
#define CALL(macroName, args) macroName args
218+
#define DO_THING_FIXED(a,b) CALL( CAT(IMPL, a), ECHO(( "Hello",b)))
219+
220+
DO_THING_FIXED(1, "World");
221+
// macro expanded to:
222+
// do_thing_one( "Hello", "World");
223+
```
224+
225+
### Conformance mode conformance
226+
227+
The experimental preprocessor isn't complete yet, and some preprocessor directive logic still falls back to the traditional behavior. Here is a partial list of incomplete features:
228+
229+
- Support for `_Pragma`
230+
- C++20 features
231+
- Additional diagnostic improvements
232+
- Switches to control the output under /E and /P
233+
- Boost blocking bug: Logical operators in preprocessor constant expressions aren't fully implemented in the new preprocessor. On some `#if` directives, the new preprocessor can fall back to the traditional preprocessor. The effect is only noticeable when macros that are incompatible with the traditional preprocessor get expanded, which can happen when building Boost preprocessor slots.
234+
235+
### To set this compiler option in the Visual Studio development environment
236+
237+
1. Open the project's **Property Pages** dialog box. For details, see [Set C++ compiler and build properties in Visual Studio](../working-with-project-properties.md).
238+
239+
1. Select the **Configuration Properties** > **C/C++** > **Command Line** property page.
240+
241+
1. Modify the **Additional Options** property to include **/experimental:preprocessor** and then choose **OK**.
242+
243+
## See also
244+
245+
[/Zc (Conformance)](zc-conformance.md)

docs/build/reference/permissive-standards-conformance.md

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -452,5 +452,5 @@ In versions before Visual Studio 2017 version 15.5, use this procedure:
452452
453453
## See also
454454
455-
- [MSVC Compiler Options](compiler-options.md)
456-
- [MSVC Compiler Command-Line Syntax](compiler-command-line-syntax.md)
455+
[MSVC Compiler Options](compiler-options.md)\
456+
[MSVC Compiler Command-Line Syntax](compiler-command-line-syntax.md)

0 commit comments

Comments
 (0)