1 cmake_minimum_required(VERSION 2.6)
4 # This test is meant both as a test and as a reference for supported
5 # syntax on native tool command lines.
7 # We need ansi C support.
9 SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${CMAKE_ANSI_CFLAGS}")
10 ENDIF(CMAKE_ANSI_CFLAGS)
12 # Determine the build tool being used. Not all characters can be
13 # escaped for all build tools. This test checks all characters known
14 # to work with each tool and documents those known to not work.
15 if("${CMAKE_GENERATOR}" MATCHES "Xcode")
17 endif("${CMAKE_GENERATOR}" MATCHES "Xcode")
18 if("${CMAKE_GENERATOR}" MATCHES "Visual Studio 6")
20 endif("${CMAKE_GENERATOR}" MATCHES "Visual Studio 6")
21 if("${CMAKE_GENERATOR}" MATCHES "Unix Makefiles")
23 endif("${CMAKE_GENERATOR}" MATCHES "Unix Makefiles")
24 if("${CMAKE_GENERATOR}" MATCHES "NMake Makefiles")
26 endif("${CMAKE_GENERATOR}" MATCHES "NMake Makefiles")
27 if("${CMAKE_GENERATOR}" MATCHES "MinGW Makefiles")
29 endif("${CMAKE_GENERATOR}" MATCHES "MinGW Makefiles")
30 if("${CMAKE_GENERATOR}" MATCHES "Borland Makefiles")
32 endif("${CMAKE_GENERATOR}" MATCHES "Borland Makefiles")
33 if("${CMAKE_GENERATOR}" MATCHES "Watcom WMake")
35 endif("${CMAKE_GENERATOR}" MATCHES "Watcom WMake")
36 if("${CMAKE_GENERATOR}" MATCHES "Visual Studio 7$")
38 endif("${CMAKE_GENERATOR}" MATCHES "Visual Studio 7$")
39 if("${CMAKE_GENERATOR}" MATCHES "Visual Studio")
41 endif("${CMAKE_GENERATOR}" MATCHES "Visual Studio")
43 # Some tests below check the PP_* variables set above. They are meant
44 # to test the case that the build tool is at fault. Other tests below
45 # check the compiler that will be used when the compiler is at fault
46 # (does not work even from a command shell).
48 #-----------------------------------------------------------------------------
49 # Construct a C-string literal to test passing through a definition on
50 # the command line. We configure the value into a header so it can be
51 # checked in the executable at runtime. The semicolon is handled
52 # specially because it needs to be escaped in the COMPILE_DEFINITIONS
53 # property value to avoid separating definitions but the string value
54 # must not have it escaped inside the configured header.
57 if(NOT BORLAND AND NOT PP_VS70)
58 # Borland, VS70 IDE: ;
59 # The Borland compiler will simply not accept a non-escaped semicolon
60 # on the command line. If it is escaped \; then the escape character
61 # shows up in the preprocessing output too.
63 # The VS 7.0 IDE separates definitions on semicolons and commas with
64 # no regard for quotes. Fortunately VS 7.1 and above are okay.
66 endif(NOT BORLAND AND NOT PP_VS70)
68 if(NOT PP_BORLAND AND NOT PP_WATCOM)
69 # Borland, WMake: multiple spaces
70 # The make tool seems to remove extra whitespace from inside
71 # quoted strings when passing to the compiler. It does not have
72 # trouble passing to other tools, and the compiler may be directly
73 # invoked from the command line.
74 set(STRING_EXTRA "${STRING_EXTRA} ")
75 endif(NOT PP_BORLAND AND NOT PP_WATCOM)
79 # Visual Studio will not accept a comma in the value of a definition.
80 # The comma-separated list of PreprocessorDefinitions in the project
81 # file seems to be parsed before the content of entries is examined.
82 set(STRING_EXTRA "${STRING_EXTRA},")
87 # When inside -D"FOO=\"a & b\"" MinGW make wants -D"FOO=\"a "&" b\""
88 # but it does not like quoted ampersand elsewhere.
89 set(STRING_EXTRA "${STRING_EXTRA}&")
94 # When inside -D"FOO=\"a | b\"" MinGW make wants -D"FOO=\"a "|" b\""
95 # but it does not like quoted pipe elsewhere.
96 set(STRING_EXTRA "${STRING_EXTRA}|")
99 if(NOT PP_BORLAND AND NOT PP_MINGW AND NOT PP_NMAKE)
100 # Borland, NMake, MinGW: ^
101 # When inside -D"FOO=\"a ^ b\"" the make tools want -D"FOO=\"a "^" b\""
102 # but do not like quoted carrot elsewhere. In NMake the non-quoted
103 # syntax works when the flags are not in a make variable.
104 set(STRING_EXTRA "${STRING_EXTRA}^")
105 endif(NOT PP_BORLAND AND NOT PP_MINGW AND NOT PP_NMAKE)
107 if(NOT PP_BORLAND AND NOT PP_MINGW AND NOT PP_NMAKE)
108 # Borland, MinGW: < >
109 # Angle-brackets have funny behavior that is hard to escape.
110 set(STRING_EXTRA "${STRING_EXTRA}<>")
111 endif(NOT PP_BORLAND AND NOT PP_MINGW AND NOT PP_NMAKE)
114 if(NOT MSVC OR PP_NMAKE)
116 # When the cl compiler is invoked from the command line then % must
117 # be written %% (to distinguish from %ENV% syntax). However cl does
118 # not seem to accept the syntax when it is invoked from inside a
119 # make tool (nmake, mingw32-make, etc.). Instead the argument must
120 # be placed inside a response file. Then cl accepts it because it
121 # parses the response file as it would the normal windows command
122 # line. Currently only NMake supports running cl with a response
123 # file. Supporting other make tools would require CMake to generate
124 # response files explicitly for each object file.
125 set(STRING_EXTRA "${STRING_EXTRA}%")
127 endif(NOT MSVC OR PP_NMAKE)
130 # Make tools do not reliably accept \\\" syntax:
131 # - MinGW and MSYS make tools crash with \\\"
132 # - Borland make actually wants a mis-matched quote \\"
133 # or $(BACKSLASH)\" where BACKSLASH is a variable set to \\
134 # - VS IDE gets confused about the bounds of the definition value \\\"
135 # - NMake is okay with just \\\"
136 if(PP_NMAKE OR PP_UMAKE)
137 set(STRING_EXTRA "${STRING_EXTRA}\\\"")
138 endif(PP_NMAKE OR PP_UMAKE)
141 # MSVC will not accept a # in the value of a string definition on the
142 # command line. The character seems to be simply replaced by an
143 # equals =. According to "cl -help" definitions may be specified by
144 # -DMACRO#VALUE as well as -DMACRO=VALUE. It must be implemented by a
145 # simple search-and-replace.
147 # The Borland compiler will parse both # and \# as just # but the make
148 # tool seems to want \# sometimes and not others.
150 # Unix make does not like # in variable settings without extra
151 # escaping. This could probably be fixed but since MSVC does not
152 # support it and it is not an operator it is not worthwhile.
154 # Compose the final test string.
155 set(STRING_VALUE "hello `~!@$*)(_+-=}{][:'.?/ ${STRING_EXTRA}world")
157 #-----------------------------------------------------------------------------
158 # Function-style macro command-line support:
159 # - Borland does not support
160 # - MSVC does not support
161 # - Watcom does not support
164 # Too few platforms support this to bother implementing.
165 # People can just configure headers with the macros.
167 #-----------------------------------------------------------------------------
168 # Construct a sample expression to pass as a macro definition.
170 set(EXPR "x*y+!(x==(y+1*2))*f(x${EXPR_OP1}2)")
173 # Watcom does not support - or / because it parses them as options.
174 set(EXPR "${EXPR}+y/x-x")
177 #-----------------------------------------------------------------------------
179 # Inform the test if the debug configuration is getting built.
180 # The NDEBUG definition takes care of this for release.
181 set(CMAKE_C_FLAGS_DEBUG "${CMAKE_C_FLAGS_DEBUG} -DPREPROCESS_DEBUG")
182 set(CMAKE_CXX_FLAGS_DEBUG "${CMAKE_CXX_FLAGS_DEBUG} -DPREPROCESS_DEBUG")
184 # Inform the test if it built from Xcode or VS6 IDE.
186 set(PREPROCESS_XCODE 1)
189 set(PREPROCESS_VS6 1)
193 # Test old-style definitions.
194 add_definitions(-DOLD_DEF -DOLD_EXPR=2)
196 # Make sure old-style definitions are converted to directory property.
198 set(OLD_DEFS_EXPECTED "OLD_DEF")
200 set(OLD_DEFS_EXPECTED "OLD_DEF;OLD_EXPR=2")
201 endif(PREPROCESS_VS6)
202 get_property(OLD_DEFS DIRECTORY PROPERTY COMPILE_DEFINITIONS)
203 if(NOT "${OLD_DEFS}" STREQUAL "${OLD_DEFS_EXPECTED}")
204 message(SEND_ERROR "add_definitions not converted to directory property!")
205 endif(NOT "${OLD_DEFS}" STREQUAL "${OLD_DEFS_EXPECTED}")
207 add_executable(Preprocess preprocess.c preprocess${VS6}.cxx)
209 set(FILE_PATH "${Preprocess_SOURCE_DIR}/file_def.h")
210 set(TARGET_PATH "${Preprocess_SOURCE_DIR}/target_def.h")
212 # Set some definition properties.
213 foreach(c "" "_DEBUG" "_RELEASE")
216 APPEND PROPERTY COMPILE_DEFINITIONS${c} "DIRECTORY_DEF${c}"
220 PROPERTY COMPILE_DEFINITIONS${c} "TARGET_DEF${c}"
223 SOURCE preprocess.c preprocess${VS6}.cxx
224 PROPERTY COMPILE_DEFINITIONS${c} "FILE_DEF${c}"
228 # Add definitions with values. VS6 does not support this.
229 if(NOT PREPROCESS_VS6)
232 APPEND PROPERTY COMPILE_DEFINITIONS
233 "TARGET_STRING=\"${STRING_VALUE}${SEMICOLON}\""
234 "TARGET_EXPR=${EXPR}"
235 "TARGET_PATH=\"${TARGET_PATH}\""
238 SOURCE preprocess.c preprocess${VS6}.cxx
239 APPEND PROPERTY COMPILE_DEFINITIONS
240 "FILE_STRING=\"${STRING_VALUE}${SEMICOLON}\""
242 "FILE_PATH=\"${FILE_PATH}\""
244 endif(NOT PREPROCESS_VS6)
246 # Helper target for running test manually in build tree.
247 add_custom_target(drive COMMAND Preprocess)
249 # Configure the header file with the desired string value.
251 set(STRING_VALUE "${STRING_VALUE};")
253 configure_file(${Preprocess_SOURCE_DIR}/preprocess.h.in
254 ${Preprocess_BINARY_DIR}/preprocess.h)
255 include_directories(${Preprocess_BINARY_DIR})