Compile Time Configuration 編譯期配置

Library compile time configuration 庫的編譯期配置

The C++ preprocessor iterator library may be configured at compile time by specifying different preprocessor constants to include different additional features. The possible preprocessor constants are described in the following table.
C++預處理迭代器庫可以在編譯期進行配置,方法是通過指定不同的預處理器常量來包含不同的額外特性。下表列出了可用的預處理器常量。

Summary of possible preprocessor constants for library configuration
可以用於庫配置的預處理器常量概要
BOOST_WAVE_SUPPORT_WARNING_DIRECTIVE

Support the #warning directive

支持 #warning 指令

BOOST_WAVE_SUPPORT_MS_EXTENSIONS

Support several MS specific language extensions (i.e. __int8 et.al.)

支持幾個 MS 專用的語言擴展(即 __int8 等等)

BOOST_WAVE_PREPROCESS_ERROR_MESSAGE_BODY

Enable the preprocessing of the message bodies of #error and #warning directives.

激活對 #error#warning 指令的信息體的預處理。

BOOST_WAVE_EMIT_PRAGMA_DIRECTIVES

If defined, then the #pragma directives are returned as a token sequence to the caller, if not defined, the whole #pragma directive is skipped.

如果被定義,則 #pragma 指令以一個單詞序列返回給調用者,如果未定義,則忽略整個 #pragma 指令。

BOOST_WAVE_PREPROCESS_PRAGMA_BODY

Enable the preprocessing of the bodies of all #pragma directives.
Note though, that the body of an operator _Pragma() is always preprocessed as this is required by the C99 Standard [2].

激活對所有 #pragma 指令體的預處理。不過請注意,operator _Pragma() 的指令體總是要進行預處理的,這是 C99 標準[2]的要求。

BOOST_WAVE_ENABLE_COMMANDLINE_MACROS

Enable the functionality required to define macros with the command line syntax (-DMACRO(x)=definition)
激活以命令行語法進行宏定義(-DMACRO(x)=definition)所需要的功能。

BOOST_WAVE_STRINGTYPE

The tokens generated by the Wave library contain the token data and the file position, where this token was found in the input stream.
This constant may be used to redefine the data type, which is used to hold the token data and the corresponding file name. If this isn't defined it defaults to std::string. (The here defined data type should be compatible to the std::string type)

Wave 庫生成的單詞含有單詞數據和文件位置,即單詞在輸入流的何處被找到。
這個常量可用於重新定義數據類型,以保存單詞數據和對應的文件名。如果未定義,則缺省為 std::string。(所定義的數據類型應兼容於 std::string 類型)

BOOST_WAVE_SUPPORT_VARIADICS_PLACEMARKERS

If defined, then the preprocessor library supports variadics and placemarkers. Note, to support C99 mode, this constant must be defined too.
如果被定義,則預處理器庫支持variadics和placemarkers。注意,要支持C99模式,這個常量也必須被定義。

BOOST_WAVE_MAX_INCLUDE_LEVEL_DEPTH

If defined, it will determine the initial maximal possible include file nesting depth supported. It defaults to 1024.
如果被定義,它將決定可支持的包含文件嵌套深度的初始最大值。缺省為1024.

BOOST_WAVE_SUPPORT_PRAGMA_ONCE

If defined, then the #pragma once directive is supported by Wave. This specifies that the file, in which the pragma resides, will be included (opened) only once by the compiler in a build.
如果被定義,則 Wave 支持 #pragma once 指令。它指定該 pragma 所在的文件在一次構建中只能被編譯器包含(打開)一次。

BOOST_WAVE_SUPPORT_PRAGMA_MESSAGE

If defined, then the #pragma message("") directive is supported by Wave. This pragma simply generates a remark cotaining the message text. The body of the #pragma message is preprocessed whenever the BOOST_WAVE_PREPROCESS_PRAGMA_BODY constant is defined as well .

如果被定義,則 Wave 支持 #pragma message("") 指令。這個 pragma 只是生成一個含有信息文字的註釋。當 BOOST_WAVE_PREPROCESS_PRAGMA_BODY 常量被定義時,#pragma 信息的內容也會被預處理。

BOOST_WAVE_SUPPORT_INCLUDE_NEXT

If defined, then the #include_next directive is supported by Wave. This is syntactically equivalent to the #include directives, but may be used to inherit a header file (i.e. to include a file, which is named as the current file containing the #include_next).

如果被定義,則 Wave 支持 #include_next 指令。該指令在語法上與 #include 指令等價,但可以用於繼承一個頭文件(即包含一個與含有 #include_next 的當前文件同名的文件)。

BOOST_WAVE_USE_STRICT_LEXER

If this is defined to something != 0, then the C/C++ lexers recognize the strict C99/C++ basic source character set. If it is not defined or defined to zero, the lexers recognize the '$' character as part of identifiers.

如果被定義為 != 0,則 C/C++ lexers 將識別嚴格的 C99/C++ 基本源代碼字符集。如果未定義為零,則 lexers 將字符'$'識別為標識符的一部分。

BOOST_WAVE_PRAGMA_KEYWORD

If this is defined to a string literal it will be used as the pragma keyword recogniyed by the library as specific Wave pragma's. This constant defaults to "wave", i.e. the library recognizes all #pragma wave option [(argument)] directives and dispatches the handling to the interpret_pragma() preprocessing hook function (see: Preprocessing Hooks). The arguments part of the pragma is optional.

如果被定義為一個字符串文字,則它將被本庫當作 pragma 關鍵字識別為特定的 Wave pragma。該常量缺省為 "wave",即本庫識別所有 #pragma wave option [(argument)] 指令並將它們的處理分發到 interpret_pragma() 預處理鉤子函數(請見:預處理鉤子)。pragma 的參數部分是可選的。

BOOST_WAVE_USE_DEPRECIATED_PREPROCESSING_HOOKS

If defined to something not equal to zero ('0') Wave will be compiled to use the depreciated preprocessing hooks. The interface of the preprocessing hooks has been changed after the Boost V1.34.x releases. This constant allows to compile applications using the older interface.
如果被定義為不等於零('0'),則 Wave 將被編譯為使用舊的預處理鉤子。這些預處理鉤子的接口在 Boost V1.34.x 版本後已經被修改。該常量允許使用舊的接口來編譯應用程序。

BOOST_WAVE_SUPPORT_LONGLONG_INTEGER_LITERALS

The C++ standard requires the preprocessor to use one of the following types for integer literals: long or unsigned long depending on a optional suffix ('u', 'l', 'ul', or 'lu'). Sometimes it is required to preprocess integer literals larger than that (i.e. long long or unsigned long long). Defining this pp constant enables the recognition of long long integers even if these do not have the 'll' suffix.

C++標準要求預處理器根據一個可選的後綴('u', 'l', 'ul', 或 'lu')使用以下各種整數類型之一:longunsigned long。有時需要預處理的整數文字更大些(即 long longunsigned long long)。定義了這個pp常量就可以識別出 long long 整數,即使沒有使用 'll' 後綴。

This preprocessor constant is effective only, if your target platform supports long long integers (BOOST_HAS_LONG_LONG is defined). Please note, that this setting doesn't relate to the Wave support option support_option_long_long, which enables the recognition of 'll' suffixes only.
這個預處理器常量僅當你的目標平台支持 long long 整數時有效(定義了 BOOST_HAS_LONG_LONG 時)。請注意,這個設置與 Wave 的支持選項 support_option_long_long 無關,後者只啟用了對 'll' 後綴的識別。

BOOST_WAVE_SUPPORT_THREADING

This preprocessor constant allows to configer whether the Wave library will be built with threading support enabled or not. This value (if defined) should be set to zero ('0') if threading needs to be disabled and to a numerical value not equal to zero, if threading should be enabled explicitely.

這個預處理器常量允許對 Wave 庫是否被構建為支持線程進行配置。如果要禁止線程,則該值(如果被定義)應被設為零('0'),如果要明確啟用線程,則應設為一個不等於零的數字。

If this constant is not defined, the Wave library will be built using the threading as picked up from the Boost build environment (see BOOST_HAS_THREADS in the Boost configuration dosumentation).
如果這個常量未定義,則 Wave 庫將從 Boost 構建環境(參見 Boost 配置文檔中的 BOOST_HAS_THREADS)獲取配置決定是否構建為支持線程。

Using a different token type or lexer type in conjunction with Wave 將不同的單詞類型或lexer類型用於Wave

It is possible to use the Wave library while using your own token and/or lexer types. This may be achieved by providing your lexer type as the second template parameter while instantiating the boost::wave::context<> object. The token type used by the library is derived from the token_type typedef to be provided by the lexer type. If you want to provide your own token type only, you may use the boost::wave::lex_iterator<> type contained with the library. This type needs to be parametrized with the token type to use.
可以將你自己的單詞類型和/或lexer類型用於 Wave 庫。可以在初始化 boost::wave::context<> 對像時通過將你自己的lexer類型作為第二個模板參數來實現這一點。本庫所使用的單詞類型派生自由該lexer類型所提供的 token_type typedef。如果你只想提供自己的單詞類型,可以使用本庫中的 boost::wave::lex_iterator<> 類型。這個類型以其所用的單詞類型進行參數化。

The Wave library contains several samples illustrating these possibilities. The cpp_tokens sample shows the usage of a custom lexer and a custom token types. The lexer type used is functionally fully compatible to the re2c [3] based lexer used by default. It is implemented based on the SLex [5] lexer example written by Dan Nuffer. The token type used therein is functionally equivalent to the default token type except for an additional operator<< used for dumping the information carried by the token.
Wave 庫包含有幾個示範這些可能性的例子。例子 cpp_tokens 示範了一個定制的lexer和一個定制的單詞類型的使用。該lexer類型在功能上完全兼容於缺省使用的基於 re2c [3] 的lexer。它是基於 Dan Nuffer 所編寫的 SLex [5] lexer實現的。所用的單詞類型在功能上等價於缺省的單詞類型,除了增加了一個 operator<< 用於輸出單詞所帶的信息。

Separation and inclusion compilation models 分離和包含的編譯模式

The Wave C++ preprocessor iterator library is build almost completely as a header only library (except for the re2c based lexer). If you're trying to include all required files at once you will mention, that the resulting compilation times are very large (up to an hour - depending on your system configuration). This straightforward method we'll call the inclusion compilation model. If you do not pay attention to compilation times, that's the way to go, no special handling is needed.
Wave C++ 預處理迭代器庫被構建為一個差不多完全只有頭文件的庫(除了基於 re2c 的 lexer)。如果你嘗試一次過包含所有需要的文件,你將會發現所需的編譯時間非常長(最多一個小時 - 取決於你的系統配置)。我們把這種簡單的方法稱為包含編譯模式。如果你不在意編譯時間,就按這種方法去做,不需要特別的處理。

If you're interested in decreasing compilation times, the following method is to be used. This we will call it the separation compilation model. The trick is to separate the different objects such, that they are compilable separately. The function, which instantiates the templated object in question is factored out such, that its definition is visible to only one translation unit. To simplify this further this creation function is packaged into a small generator template structure.
如果你想減少編譯時間,可以使用以下方法。我們稱之為分離編譯模式。訣竅是分離不同的對象,即將它們分開編譯。問題在於,對模板對像進行實例化的函數,其定義僅在一個編譯單元中可見。為了進一步簡化它,我們將這個創建函數打包進一個小型的生成器模板結構。

There are two levels of separation implemented: the separation of the compilation of the C++ lexer and the separation of the compilation of the different Spirit grammars used. To use these separations you will have to define two preprocessor constants while compiling the whole application and you will have to explicitely instantiate some helper templates. The following tables shows these constants in detail.
已實現了兩個分離層:C++ lexer編譯的分離和所用的不同Spirit語法編譯的分離。要使用這些分離,你必須在編譯整個應用時定義兩個預處理器常量,並且要顯式地實例化一些輔助模板。下表詳細列出這些常量。

Summary of possible compilation constants required to enable the separation compilation model
啟用分離編譯模式所需的編譯常量概要
Separate 分離層

Preprocessor constant 預處理器常量

C++ lexer

BOOST_WAVE_SEPARATE_LEXER_INSTANTIATION

Spirit grammars

BOOST_WAVE_SEPARATE_GRAMMAR_INSTANTIATION

The following table shows the explicit template instantiations required, if you want to use the separation compilation model. The TokenT placeholder type has to be replaced with your token type to use and the LexIteratorT placeholder type has to be replaced with your lex iterator type you've used while instantiation of the boost::wave::context<> object. You will achieve the best results, if you place these into separate compilation units each. The IteratorT placeholder should be replaced by the iterator type, which was used to instantiate the boost::wave::context<> object.
下表列出了使用分離編譯模式所要進行顯式實例化的模板。TokenT 佔位符類型要替換為你所使用的單詞類型,而 LexIteratorT 佔位符類型則要替換為你在初始化 boost::wave::context<> 對像時使用的lex迭代器類型。如果你將它們放在各自的編譯單詞中,將會得到最好的結果。IteratorT 佔位符應替換為初始化 boost::wave::context<> 對像時使用的迭代器類型。

Summary of required explicit template instantiations required when using the separation compilation model
使用分離編譯模式時需要顯式實例化的模板概要
Separate 分離層

Templates to explicitly instantiate 要顯式實例化的模板

C++ lexer template cpplexer::re2clex::new_lexer_gen<IteratorT>;
Spirit grammars

template wave::grammars::expression_grammar_gen<TokenT>;
template wave::grammars::intlit_grammar_gen<TokenT>;
template wave::grammars::chlit_grammar_gen<TokenT>;
template wave::grammars::cpp_grammar_gen<LexIteratorT>;
template wave::grammars::predefined_macros_grammar_gen<LexIteratorT>;
template wave::grammars::defined_grammar_gen<LexIteratorT>;

To see an example of this you can look at the Wave driver program included as an acompanion sample to the C++ preprocessor iterator library. The corresponding files are named obviously "instantiate_...something.cpp", where the '...somthing' is a hint, which grammars are explicitely instantiated inside. By using the separation model the compilation times required to build the Wave example are dropped by up to 90%.
要看一下例子的話,你可以看 Wave 驅動器程序,它作為一個例子包含在這個 C++ 預處理迭代器庫中。相應的文件被命名為 "instantiate_...something.cpp",其中 '...somthing' 是一個提示,表示其中顯式實例化的是哪一個語法。通過使用分離編譯模式,構建這個 Wave 例子的編譯時間減少了多達 90%.