• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1# See www/CMake.html for instructions on how to build libcxx with CMake.
2
3#===============================================================================
4# Setup Project
5#===============================================================================
6
7project(libcxx CXX C)
8cmake_minimum_required(VERSION 2.8)
9
10set(PACKAGE_NAME libcxx)
11set(PACKAGE_VERSION trunk-svn)
12set(PACKAGE_STRING "${PACKAGE_NAME} ${PACKAGE_VERSION}")
13set(PACKAGE_BUGREPORT "llvmbugs@cs.uiuc.edu")
14
15# Add path for custom modules
16set(CMAKE_MODULE_PATH
17  "${CMAKE_CURRENT_SOURCE_DIR}/cmake"
18  "${CMAKE_CURRENT_SOURCE_DIR}/cmake/Modules"
19  ${CMAKE_MODULE_PATH}
20  )
21
22# Require out of source build.
23include(MacroEnsureOutOfSourceBuild)
24MACRO_ENSURE_OUT_OF_SOURCE_BUILD(
25 "${PROJECT_NAME} requires an out of source build. Please create a separate
26 build directory and run 'cmake /path/to/${PROJECT_NAME} [options]' there."
27 )
28
29if(CMAKE_SOURCE_DIR STREQUAL CMAKE_CURRENT_SOURCE_DIR)
30  set(LIBCXX_BUILT_STANDALONE 1)
31endif()
32
33#===============================================================================
34# Setup CMake Options
35#===============================================================================
36
37# Define options.
38option(LIBCXX_ENABLE_EXCEPTIONS "Use exceptions." ON)
39option(LIBCXX_ENABLE_RTTI "Use run time type information." ON)
40option(LIBCXX_ENABLE_ASSERTIONS "Enable assertions independent of build mode." ON)
41option(LIBCXX_ENABLE_PEDANTIC "Compile with pedantic enabled." ON)
42option(LIBCXX_ENABLE_WERROR "Fail and stop if a warning is triggered." OFF)
43option(LIBCXX_ENABLE_CXX0X "Enable -std=c++0x and use of c++0x language features if the compiler supports it." ON)
44option(LIBCXX_ENABLE_SHARED "Build libc++ as a shared library." ON)
45option(LIBCXX_INSTALL_SUPPORT_HEADERS "Install libc++ support headers." ON)
46
47set(CXXABIS none libcxxabi libcxxrt libstdc++ libsupc++)
48if (NOT DEFINED LIBCXX_CXX_ABI)
49  set(LIBCXX_CXX_ABI "none")
50endif()
51set(LIBCXX_CXX_ABI "${LIBCXX_CXX_ABI}" CACHE STRING
52    "Specify C++ ABI library to use." FORCE)
53set_property(CACHE LIBCXX_CXX_ABI PROPERTY STRINGS ;${CXXABIS})
54
55#===============================================================================
56# Configure System
57#===============================================================================
58
59# Get triples.
60include(GetTriple)
61get_host_triple(LIBCXX_HOST_TRIPLE
62  LIBCXX_HOST_ARCH
63  LIBCXX_HOST_VENDOR
64  LIBCXX_HOST_OS
65  )
66set(LIBCXX_HOST_TRIPLE ${LIBCXX_HOST_TRIPLE} CACHE STRING "Host triple.")
67get_target_triple(LIBCXX_TARGET_TRIPLE
68  LIBCXX_TARGET_ARCH
69  LIBCXX_TARGET_VENDOR
70  LIBCXX_TARGET_OS
71  )
72set(LIBCXX_TARGET_TRIPLE ${LIBCXX_TARGET_TRIPLE} CACHE STRING "Target triple.")
73
74#===============================================================================
75# Add an ABI library if appropriate
76#===============================================================================
77
78#
79# _setup_abi: Set up the build to use an ABI library
80#
81# Parameters:
82#   abidefines: A list of defines needed to compile libc++ with the ABI library
83#   abilibs   : A list of libraries to link against
84#   abifiles  : A list of files (which may be relative paths) to copy into the
85#               libc++ build tree for the build.  These files will also be
86#               installed alongside the libc++ headers.
87#   abidirs   : A list of relative paths to create under an include directory
88#               in the libc++ build directory.
89#
90macro(setup_abi_lib abipathvar abidefines abilibs abifiles abidirs)
91  list(APPEND LIBCXX_CXX_FEATURE_FLAGS ${abidefines})
92  set(${abipathvar} "${${abipathvar}}"
93    CACHE STRINGS
94    "Paths to ABI include directories separate by ';'."
95    )
96  set(LIBCXX_CXX_ABI_LIBRARIES ${abilibs})
97  set(LIBCXX_ABILIB_FILES ${abifiles})
98  file(MAKE_DIRECTORY "${CMAKE_BINARY_DIR}/include")
99  foreach(_d ${abidirs})
100    file(MAKE_DIRECTORY "${CMAKE_BINARY_DIR}/include/${_d}")
101  endforeach()
102  set(LIBCXX_ABILIB_FILE_PATHS)
103  foreach(fpath ${LIBCXX_ABILIB_FILES})
104    set(found FALSE)
105    foreach(incpath ${${abipathvar}})
106      if (EXISTS "${incpath}/${fpath}")
107        set(found TRUE)
108        get_filename_component(dstdir ${fpath} PATH)
109        get_filename_component(ifile ${fpath} NAME)
110        add_custom_command(
111          OUTPUT "${CMAKE_BINARY_DIR}/include/${dstdir}/${ifile}"
112          COMMAND ${CMAKE_COMMAND} -E copy_if_different
113            "${incpath}/${fpath}"
114            "${CMAKE_BINARY_DIR}/include/${dstdir}"
115          MAIN_DEPENDENCY "${incpath}/${fpath}"
116          )
117        list(APPEND LIBCXX_CXX_ABI_DEPS
118          "${CMAKE_BINARY_DIR}/include/${dstdir}/${ifile}"
119          )
120      endif()
121    endforeach()
122    if (NOT found)
123      message(FATAL_ERROR "Failed to find ${fpath}")
124    endif()
125  endforeach()
126  add_custom_target(abilib_headers DEPENDS ${LIBCXX_CXX_ABI_DEPS})
127  set(LIBCXX_CXX_ABI_DEPS abilib_headers)
128  include_directories("${CMAKE_BINARY_DIR}/include")
129  install(DIRECTORY "${CMAKE_BINARY_DIR}/include/"
130    DESTINATION include/c++/v1
131    FILES_MATCHING
132    PATTERN "*"
133    )
134endmacro()
135
136if ("${LIBCXX_CXX_ABI}" STREQUAL "libstdc++" OR
137    "${LIBCXX_CXX_ABI}" STREQUAL "libsupc++")
138  set(_LIBSUPCXX_INCLUDE_FILES
139    cxxabi.h bits/c++config.h bits/os_defines.h bits/cpu_defines.h
140    bits/cxxabi_tweaks.h bits/cxxabi_forced.h
141    )
142  if ("${LIBCXX_CXX_ABI}" STREQUAL "libstdc++")
143    set(_LIBSUPCXX_DEFINES "-DLIBSTDCXX")
144    set(_LIBSUPCXX_LIBNAME stdc++)
145  else()
146    set(_LIBSUPCXX_DEFINES "")
147    set(_LIBSUPCXX_LIBNAME supc++)
148  endif()
149  setup_abi_lib("LIBCXX_LIBSUPCXX_INCLUDE_PATHS"
150    "-D__GLIBCXX__ ${_LIBSUPCXX_DEFINES}"
151    "${_LIBSUPCXX_LIBNAME}" "${_LIBSUPCXX_INCLUDE_FILES}" "bits"
152    )
153elseif ("${LIBCXX_CXX_ABI}" STREQUAL "libcxxabi")
154  setup_abi_lib("LIBCXX_LIBCXXABI_INCLUDE_PATHS" ""
155    "c++abi" "cxxabi.h" ""
156    )
157elseif ("${LIBCXX_CXX_ABI}" STREQUAL "libcxxrt")
158  setup_abi_lib("LIBCXX_LIBCXXRT_INCLUDE_PATHS" "-DLIBCXXRT"
159    "cxxrt" "cxxabi.h;unwind.h;unwind-arm.h;unwind-itanium.h" ""
160    )
161elseif (NOT "${LIBCXX_CXX_ABI}" STREQUAL "none")
162  message(FATAL_ERROR
163    "Currently libstdc++, libsupc++, libcxxabi, libcxxrt and none are "
164    "supported for c++ abi."
165    )
166endif ()
167
168# Configure compiler.
169include(config-ix)
170
171#===============================================================================
172# Setup Compiler Flags
173#===============================================================================
174
175# Get required flags.
176# On all systems the system c++ standard library headers need to be excluded.
177if (MSVC)
178  # MSVC only has -X, which disables all default includes; including the crt.
179  # Thus, we do nothing and hope we don't accidentally include any of the C++
180  # headers.
181else()
182  if (LIBCXX_HAS_NOSTDINCXX_FLAG)
183    list(APPEND LIBCXX_CXX_REQUIRED_FLAGS -nostdinc++)
184  endif()
185  if (LIBCXX_ENABLE_CXX0X AND LIBCXX_HAS_STDCXX0X_FLAG)
186    list(APPEND LIBCXX_CXX_REQUIRED_FLAGS -std=c++0x)
187  endif()
188endif()
189
190macro(append_if list condition var)
191  if (${condition})
192    list(APPEND ${list} ${var})
193  endif()
194endmacro()
195
196# Get warning flags
197if (NOT MSVC)
198  append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WALL_FLAG -Wall)
199  list(APPEND LIBCXX_CXX_REQUIRED_FLAGS -Werror=return-type)
200endif()
201
202append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_W_FLAG -W)
203append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WNO_UNUSED_PARAMETER_FLAG -Wno-unused-parameter)
204append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WWRITE_STRINGS_FLAG -Wwrite-strings)
205append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WNO_LONG_LONG_FLAG -Wno-long-long)
206if (LIBCXX_ENABLE_WERROR)
207  append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WERROR_FLAG -Werror)
208  append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WX_FLAG -WX)
209else()
210  append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_WNO_ERROR_FLAG -Wno-error)
211  append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_NO_WX_FLAG -WX-)
212endif()
213if (LIBCXX_ENABLE_PEDANTIC)
214  append_if(LIBCXX_CXX_WARNING_FLAGS LIBCXX_HAS_PEDANTIC_FLAG -pedantic)
215endif()
216
217# Get feature flags.
218# Exceptions
219if (LIBCXX_ENABLE_EXCEPTIONS)
220  # Catches C++ exceptions only and tells the compiler to assume that extern C
221  # functions never throw a C++ exception.
222  append_if(LIBCXX_CXX_FEATURE_FLAGS LIBCXX_HAS_EHSC_FLAG -EHsc)
223else()
224  list(APPEND LIBCXX_CXX_FEATURE_FLAGS -D_LIBCPP_NO_EXCEPTIONS)
225  append_if(LIBCXX_CXX_FEATURE_FLAGS LIBCXX_HAS_NO_EHS_FLAG -EHs-)
226  append_if(LIBCXX_CXX_FEATURE_FLAGS LIBCXX_HAS_NO_EHA_FLAG -EHa-)
227  append_if(LIBCXX_CXX_FEATURE_FLAGS LIBCXX_HAS_FNO_EXCEPTIONS_FLAG -fno-exceptions)
228endif()
229# RTTI
230if (NOT LIBCXX_ENABLE_RTTI)
231  list(APPEND LIBCXX_CXX_FEATURE_FLAGS -D_LIBCPP_NO_RTTI)
232  append_if(LIBCXX_CXX_FEATURE_FLAGS LIBCXX_HAS_NO_GR_FLAG -GR-)
233  append_if(LIBCXX_CXX_FEATURE_FLAGS LIBCXX_HAS_FNO_RTTI_FLAG -fno-rtti)
234endif()
235# Assert
236string(TOUPPER "${CMAKE_BUILD_TYPE}" uppercase_CMAKE_BUILD_TYPE)
237if (LIBCXX_ENABLE_ASSERTIONS)
238  # MSVC doesn't like _DEBUG on release builds. See PR 4379.
239  if (NOT MSVC)
240    list(APPEND LIBCXX_CXX_FEATURE_FLAGS -D_DEBUG)
241  endif()
242  # On Release builds cmake automatically defines NDEBUG, so we
243  # explicitly undefine it:
244  if (uppercase_CMAKE_BUILD_TYPE STREQUAL "RELEASE")
245    list(APPEND LIBCXX_CXX_FEATURE_FLAGS -UNDEBUG)
246  endif()
247else()
248  if (NOT uppercase_CMAKE_BUILD_TYPE STREQUAL "RELEASE")
249    list(APPEND LIBCXX_CXX_FEATURE_FLAGS -DNDEBUG)
250  endif()
251endif()
252# Static library
253if (NOT LIBCXX_ENABLE_SHARED)
254  list(APPEND LIBCXX_CXX_FEATURE_FLAGS -D_LIBCPP_BUILD_STATIC)
255endif()
256
257# This is the _ONLY_ place where add_definitions is called.
258if (MSVC)
259  add_definitions(-D_CRT_SECURE_NO_WARNINGS)
260endif()
261
262string(REPLACE ";" " " LIBCXX_CXX_REQUIRED_FLAGS "${LIBCXX_CXX_REQUIRED_FLAGS}")
263set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LIBCXX_CXX_REQUIRED_FLAGS}")
264
265string(REPLACE ";" " " LIBCXX_CXX_WARNING_FLAGS "${LIBCXX_CXX_WARNING_FLAGS}")
266set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LIBCXX_CXX_WARNING_FLAGS}")
267
268string(REPLACE ";" " " LIBCXX_CXX_FEATURE_FLAGS "${LIBCXX_CXX_FEATURE_FLAGS}")
269set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} ${LIBCXX_CXX_FEATURE_FLAGS}")
270
271#===============================================================================
272# Setup Source Code
273#===============================================================================
274
275include_directories(include)
276add_subdirectory(include)
277
278# Add source code. This also contains all of the logic for deciding linker flags
279# soname, etc...
280add_subdirectory(lib)
281
282#===============================================================================
283# Setup Tests
284#===============================================================================
285
286add_subdirectory(test)
287