C++QED  2.100.2 (v2 Milestone 10 Development branch)
a framework for simulating open quantum dynamics
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Friends Macros Modules Pages
CMakeLists.cmake
1 # Copyright Raimar Sandner 2012–2014. Distributed under the Boost Software License, Version 1.0. (See accompanying file LICENSE.txt)
2 
3 #! \addtogroup Main
4 #! @{
5 
6 #! \file
7 #! \brief Top level %CMake file controlling monolithic builds.
8 #!
9 #! In monolithic builds, the paths to the subprojects (`CPPQEDcore`, `CPPQEDelements`, `CPPQEDscripts`, `cpypyqed`)
10 #! are known. All these components are built with calls to `add_subdirectory` from within this file. The subprojects
11 #! are built just as if they were standalone projects (with very few exceptions where the variable `CPPQED_MONOLITHIC`
12 #! is queried and things are handled differently if it is defined). `CPPQEDcore` and `CPPQEDelements`
13 #! export their relevant targets and other subprojects import them, just as for standalone projects. However, this
14 #! file sets the variables `CPPQED_DIR` and `CPPQEDelements_DIR`
15 #! (c.f. \ref cmake_find_components "how CMake finds components") to the build directories of this monolithic build,
16 #! so that the right subprojects are found even if C++QED is installed or other build directories are registered.
17 #!
18 #! This CMakeLists file has the following structure:
19 
20 #! @}
21 
22 cmake_minimum_required (VERSION 2.8.9)
23 project(cppqed)
24 
25 enable_testing()
26 
27 include(GNUInstallDirs)
28 
29 set(CMAKE_MODULE_PATH "${CMAKE_MODULE_PATH}" "${CMAKE_SOURCE_DIR}/CPPQEDcore/cmake/Modules" "${CMAKE_SOURCE_DIR}/cpypyqed/cmake/Modules")
30 
31 #! \name Project variables
32 #! These variables are used in the subprojects.
33 #! @{
34 
35 #! \brief Other subprojects use this variable to determine if this is a monolithic build
36 set(CPPQED_MONOLITHIC 1)
37 
38 set(cppqed_DOC_DIR ${CMAKE_BINARY_DIR}/doc/cppqed)
39 set(core_DOC_DIR ${CMAKE_BINARY_DIR}/doc/core)
40 set(core_DOXYGEN_TAG ${core_DOC_DIR}/core.tag)
41 set(elements_DOC_DIR ${CMAKE_BINARY_DIR}/doc/elements)
42 set(elements_DOXYGEN_TAG ${elements_DOC_DIR}/elements.tag)
43 set(cpypyqed_DOC_DIR ${CMAKE_BINARY_DIR}/doc/cpypyqed)
44 
45 #! @}
46 
47 #! \file
48 #! <!--#########################################################-->
49 #! ### Compilation of dependencies
50 #! <!--#########################################################-->
51 #!
52 #! This is a convenience feature to download and compile some selected
53 #! dependencies automatically. It uses %CMake's
54 #! [ExternalProject](http://www.cmake.org/cmake/help/v2.8.12/cmake.html#module:ExternalProject).
55 #!
56 #! We use a trick to install the bundled libraries. If the bundled version of a library is used,
57 #! we link it privately (\ref CMake::PRIVATE_LIBS instead of \ref CMake::PUBLIC_LIBS). Then
58 #! we add the library manually to `CPPQED_LIBRARIES` in CPPQEDConfig.cmake.in, with the correct
59 #! location for the build tree and installed tree, respectively.
60 
61 #! If this option is set, %CMake downloads and compiles the blitz++ dependency automatically.
62 option(BUNDLED_BLITZ "Download and compile blitz++ automatically" Off)
63 
64 if(BUNDLED_BLITZ)
65  include(ExternalProject)
66 
67  find_package(Boost QUIET COMPONENTS serialization)
68  if(Boost_SERIALIZATION_FOUND)
69  set(BLITZ_CONFIG_OPTIONS "${BLITZ_CONFIG_OPTIONS} --enable-serialization ")
70  set(blitz_SERIALIZATION_FOUND On)
71  endif()
72 
73  string(REGEX REPLACE "/include" "" local_boost_root ${Boost_INCLUDE_DIR})
74 
75  if( CMAKE_SIZEOF_VOID_P EQUAL 8 ) # 64bit system
76  set(BLITZ_CONFIG_OPTIONS "${BLITZ_CONFIG_OPTIONS} --enable-64bit ")
77  else( CMAKE_SIZEOF_VOID_P EQUAL 8 ) # 32bit system
78  set(BLITZ_CONFIG_OPTIONS "${BLITZ_CONFIG_OPTIONS} --enable-simd-width=8 ")
79  endif( CMAKE_SIZEOF_VOID_P EQUAL 8 )
80 
81  find_program(autoreconf autoreconf)
82  if(NOT autoreconf)
83  message(FATAL_ERROR "Program autoreconf not found, needed to compile blitz.")
84  endif()
85  get_filename_component(AUTOTOOLS_PATH ${autoreconf} DIRECTORY)
86 
87  if(XCODE)
88  set(AUTORECONF_NO_OUTPUT "&>/dev/null")
89  endif()
90  configure_file(misc/blitz-make.sh.in ${PROJECT_BINARY_DIR}/blitz-make.sh @ONLY)
91 
92  if(EXISTS ${CMAKE_SOURCE_DIR}/external/blitz)
93  set(BLITZ_SOURCE DOWNLOAD_COMMAND cp -a ${CMAKE_SOURCE_DIR}/external/blitz/. <SOURCE_DIR>/)
94  else()
95  set(BLITZ_SOURCE HG_REPOSITORY http://hg.code.sf.net/p/cppqed/blitz)
96  endif()
97 
98  ExternalProject_Add(
99  cppqed-blitz
100  ${BLITZ_SOURCE}
101  UPDATE_COMMAND ""
102  PATCH_COMMAND patch --dry-run -N -p1 -d <SOURCE_DIR> -i ${CMAKE_SOURCE_DIR}/misc/blitz_rename_library.patch | grep "previously applied" || patch -p1 -d <SOURCE_DIR> -i ${CMAKE_SOURCE_DIR}/misc/blitz_rename_library.patch
103  COMMAND patch --dry-run -N -p1 -d <SOURCE_DIR> -i ${CMAKE_SOURCE_DIR}/misc/blitz_python26.patch | grep "previously applied" || patch -p1 -d <SOURCE_DIR> -i ${CMAKE_SOURCE_DIR}/misc/blitz_python26.patch
104  CONFIGURE_COMMAND ${PROJECT_BINARY_DIR}/blitz-make.sh <SOURCE_DIR> <INSTALL_DIR>
105  BUILD_COMMAND make lib
106  )
107  ExternalProject_Get_Property(cppqed-blitz install_dir)
108  set(blitz_INCLUDE_DIRS ${install_dir}/include)
109  set(blitz_LIBRARIES ${install_dir}/lib/libblitzcppqed${CMAKE_SHARED_LIBRARY_SUFFIX})
110  set(BUNDLED_BLITZ_INSTALLED_LIBRARY ${CMAKE_INSTALL_FULL_LIBDIR}/libblitzcppqed${CMAKE_SHARED_LIBRARY_SUFFIX})
111  set(blitz_FOUND 1)
112 endif()
113 
114 #! If this option is set, %CMake downloads and compiles the optional FLENS dependency automatically.
115 option(BUNDLED_FLENS "Download and compile FLENS automatically" Off)
116 
117 if(BUNDLED_FLENS)
118  include(ExternalProject)
119 
120  if(EXISTS ${CMAKE_SOURCE_DIR}/external/flens)
121  set(FLENS_SOURCE DOWNLOAD_COMMAND cp -a ${CMAKE_SOURCE_DIR}/external/flens/. <SOURCE_DIR>/)
122  else()
123  set(FLENS_SOURCE GIT_REPOSITORY git://github.com/michael-lehn/FLENS.git GIT_TAG "757834a")
124  endif()
125 
126  ExternalProject_Add(
127  flens
128  ${FLENS_SOURCE}
129  UPDATE_COMMAND ""
130  CONFIGURE_COMMAND ${CMAKE_COMMAND} -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR> ../flens/
131  BUILD_COMMAND
132  INSTALL_COMMAND make install
133  )
134  ExternalProject_Get_Property(flens install_dir)
135  set(flens_INCLUDE_DIRS ${install_dir}/include)
136  set(flens_FOUND 1)
137 endif()
138 
139 #! \file
140 #! <!--#########################################################-->
141 #! ### Compilation of the components
142 #! <!--#########################################################-->
143 #!
144 #! Compile the components core, elements, scripts (optional) and cpypyqed (optional)
145 #! by adding their sub-directories.
146 
147 add_subdirectory(CPPQEDcore)
148 set(CPPQED_DIR ${core_BINARY_DIR})
149 add_subdirectory(CPPQEDelements)
150 set(CPPQEDelements_DIR ${elements_BINARY_DIR})
151 
152 #! \brief Install directory of the Doxygen documentation.
153 #!
154 #! Note that doxygen documentation can only be built and installed in monolithic builds.
155 set(CPPQED_DOC_DIR "${CMAKE_INSTALL_DATAROOTDIR}/doc/cppqed-doc-${CPPQED_ID}")
156 
157 #! \name Project options
158 #! @{
159 
160 #! This %CMake option determines if the Python modules should be compiled.
161 option(COMPILE_CPYPYQED "Compile Python wrapper and Python I/O module" On)
162 find_package(Boost QUIET COMPONENTS python)
163 find_package(PythonInterp 2 QUIET)
164 if(${PYTHON_VERSION_STRING} VERSION_LESS 2.6)
165  message(WARNING "Python2 >=2.6 needed, disabling cpypyqed and testsuite.")
166  set(PYTHONINTERP_FOUND 0)
167 else()
168  find_package(PythonLibs ${PYTHON_VERSION_STRING} EXACT QUIET)
169 endif()
170 find_package(Numpy QUIET)
171 
172 # Canopy workaround: the python interpreter is found, but not the libs and include dirs
173 if(PYTHONINTERP_FOUND AND NOT PYTHONLIBS_FOUND)
174  execute_process(COMMAND "${PYTHON_EXECUTABLE}-config" "--includes"
175  OUTPUT_VARIABLE _PYTHON_CONFIG_INCLUDES
176  RESULT_VARIABLE _PYTHON_CONFIG_SUCCESS)
177  if(_PYTHON_CONFIG_SUCCESS MATCHES 0)
178  string(REGEX REPLACE "-I(.*) .*" "\\1" PYTHON_INCLUDE_DIR ${_PYTHON_CONFIG_INCLUDES})
179  get_filename_component(_PYTHON_BASE ${PYTHON_INCLUDE_DIR} DIRECTORY)
180  get_filename_component(_PYTHON_BASE ${_PYTHON_BASE} DIRECTORY)
181  set(PYTHON_LIBRARY ${_PYTHON_BASE}/lib/libpython${PYTHON_VERSION_MAJOR}.${PYTHON_VERSION_MINOR}${CMAKE_SHARED_LIBRARY_SUFFIX})
182  message(STATUS "Trying to find python library at ${PYTHON_LIBRARY}")
183  message(STATUS "Trying to find python includes at ${PYTHON_INCLUDE_DIR}")
184  find_package(PythonLibs ${PYTHON_VERSION_STRING} EXACT QUIET)
185  endif()
186 endif()
187 
188 
189 # For some reason kdevelop does not recognize PYTHONLIBS_FOUND, use PYTHON_INCLUDE_DIRS instead
190 if(Boost_PYTHON_FOUND AND PYTHONINTERP_FOUND AND PYTHON_INCLUDE_DIRS AND NUMPY_FOUND AND COMPILE_CPYPYQED)
191  set(ENABLE_CPYPYQED 1)
192 endif()
193 add_subdirectory(cpypyqed)
194 
195 
196 #! \brief This %CMake option determines if the scripts should be compiled as part
197 #! of the monolithic build.
198 option(COMPILE_SCRIPTS "Compile the example scripts" On)
199 
200 #! \brief This %CMake configuration variable lets users exclude scripts from the ALL target. These
201 #! scripts can still be compiled by directly calling their target.
202 set(CPPQED_EXCLUDE_SCRIPTS "" CACHE STRING "Exclude from the ALL target")
203 #! @}
204 if(COMPILE_SCRIPTS)
205  add_subdirectory(CPPQEDscripts)
206 endif()
207 
208 add_subdirectory(Testing)
209 
210 # The EXCLUDE_FROM_ALL target makes Xcode scip the subdirectory entirely
211 if(XCODE)
212  add_subdirectory(CustomElementsExample)
213  set(CPPQEDelements_custom_example_DIR ${elements_custom_example_BINARY_DIR})
214  add_subdirectory(CustomScriptsExample)
215 else()
216  add_subdirectory(CustomElementsExample EXCLUDE_FROM_ALL)
217  set(CPPQEDelements_custom_example_DIR ${elements_custom_example_BINARY_DIR})
218  add_subdirectory(CustomScriptsExample EXCLUDE_FROM_ALL)
219 endif()
220 
221 #! \file
222 #! <!--#########################################################-->
223 #! ### Installation of dependencies
224 #! <!--#########################################################-->
225 #!
226 #! If blitz and flens are compiled as external projects, install them as well. Libraries
227 #! and header files are installed into the same locations as CPPQEDcore, this way it is
228 #! ensured they are found.
229 
230 set(BUNDLED_HEADERS "${CMAKE_INSTALL_INCLUDEDIR}/${CPPQED_INCLUDE_DIR}/bundled")
231 
232 if(BUNDLED_BLITZ)
233  ExternalProject_Get_Property(cppqed-blitz install_dir)
234  file(GLOB blitz_libs ${install_dir}/lib/*.so*)
235  set(blitz_libs ${install_dir}/lib/libblitzcppqed.so
236  ${install_dir}/lib/libblitzcppqed.so.0
237  ${install_dir}/lib/libblitzcppqed.so.0.0.0)
238  install(FILES ${blitz_libs}
239  PERMISSIONS OWNER_WRITE OWNER_READ GROUP_READ WORLD_READ OWNER_EXECUTE GROUP_EXECUTE WORLD_EXECUTE
240  DESTINATION ${CMAKE_INSTALL_LIBDIR})
241  install(DIRECTORY ${install_dir}/include/blitz ${install_dir}/include/random
242  DESTINATION ${BUNDLED_HEADERS})
243 endif()
244 
245 if(BUNDLED_FLENS)
246  ExternalProject_Get_Property(flens install_dir)
247  install(DIRECTORY ${install_dir}/include/flens
248  DESTINATION ${BUNDLED_HEADERS})
249 endif()
250 
251 #! \file
252 #! <!--#########################################################-->
253 #! ### Source package
254 #! <!--#########################################################-->
255 #!
256 #! Create source tar ball with CPack for publication on sourceforge.
257 
258 set(CPACK_PACKAGE_VERSION_MAJOR ${CPPQED_VERSION_MAJOR})
259 set(CPACK_PACKAGE_VERSION_MINOR ${CPPQED_VERSION_MINOR})
260 set(CPACK_PACKAGE_VERSION_PATCH ${CPPQED_VERSION_PATCH})
261 
262 set(CPACK_GENERATOR TGZ)
263 
264 set(CPACK_SOURCE_PACKAGE_FILE_NAME "cppqed-${CPPQED_VERSION}" CACHE INTERNAL "tarball basename")
265 set(CPACK_SOURCE_IGNORE_FILES "~$" "/build/" "\\\\.kdev4.*" "\\\\.git.*" ".*orig$")
266 
267 include(CPack)
268 
269 #! \file
270 #! <!--#########################################################-->
271 #! ### Documentation
272 #! <!--#########################################################-->
273 #!
274 #! This section builds the Doxygen documentation (if Doxygen is found) and furthermore
275 #! installs the example projects "CustomElementsExample" and "CustomScriptsExample" to
276 #! the system. The install location is \ref CMake::CPPQED_DOC_DIR "CPPQED_DOC_DIR".
277 #!
278 #! For the Doxygen documentation, the filter [CMakeDoxygenFilter](https://github.com/saschazelzer/CMakeDoxygenFilter),
279 #! is compiled, which allows to document %CMake in Doxygen. The overall C++QED documentation
280 #! is generated with cppqed_documentation(), and a target "doc" for the full documentation is created,
281 #! which depends on all the component documentation targets.
282 
283 include(${core_SOURCE_DIR}/cmake/Modules/CPPQEDUse.cmake)
284 add_executable(CMakeDoxygenFilter doc/CMakeDoxygenFilter.cpp)
285 set_target_properties(CMakeDoxygenFilter PROPERTIES COMPILE_FLAGS -DUSE_NAMESPACE=CMake)
286 set(CMakeDoxygenFilter_EXECUTABLE "${CMAKE_CURRENT_BINARY_DIR}/CMakeDoxygenFilter${CMAKE_EXECUTABLE_SUFFIX}")
287 cppqed_documentation("cppqed_" "${CMAKE_BINARY_DIR}/doc/core/core.tag;${CMAKE_BINARY_DIR}/doc/elements/elements.tag" core_doc elements_doc CMakeDoxygenFilter)
288 if(DOXYGEN_FOUND)
289  add_custom_target(doc)
290  add_dependencies(doc cppqed_doc core_doc elements_doc cpypyqed_doc)
291  configure_file(doc/index.html ${CMAKE_BINARY_DIR}/doc COPYONLY)
292 endif()
293 
294 install(DIRECTORY CustomElementsExample CustomScriptsExample
295  DESTINATION ${CPPQED_DOC_DIR}
296  PATTERN .git* EXCLUDE
297  PATTERN .bzr EXCLUDE
298  PATTERN *.kdev* EXCLUDE
299  PATTERN build* EXCLUDE
300 )
301 
302 #! \file
303 #! <!--#########################################################-->
304 #! ### Debian build
305 #! <!--#########################################################-->
306 #!
307 #! This adds the sub-directory "debianbuild" if it exists. If not this section is silently ignored.
308 #! The directory "debianbuild" is not part of the C++QED project. One can put a special
309 #! [repository](https://ge-c705.uibk.ac.at/cppqed/debian) here, which will then generate debian
310 #! directories for building source packages. This guarantees that debian packages have the right
311 #! version numbers and soversion in their package names, and also helps to maintain packages for different
312 #! distributions without code duplication.
313 
314 if(EXISTS ${PROJECT_SOURCE_DIR}/debianbuild)
315  add_subdirectory(debianbuild)
316 endif()
317 
318 add_feature_info("cpypyqed" ENABLE_CPYPYQED "Python part of C++QED (wrapper and input/output).")
319 feature_summary( WHAT ALL )