]> SALOME platform Git repositories - modules/shaper.git/blob - CMakeCommon/SalomeMacros.cmake
Salome HOME
Issue #2543: Provide completion on editing.
[modules/shaper.git] / CMakeCommon / SalomeMacros.cmake
1 # Copyright (C) 2012-2016  CEA/DEN, EDF R&D, OPEN CASCADE\r
2 #\r
3 # This library is free software; you can redistribute it and/or\r
4 # modify it under the terms of the GNU Lesser General Public\r
5 # License as published by the Free Software Foundation; either\r
6 # version 2.1 of the License, or (at your option) any later version.\r
7 #\r
8 # This library is distributed in the hope that it will be useful,\r
9 # but WITHOUT ANY WARRANTY; without even the implied warranty of\r
10 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r
11 # Lesser General Public License for more details.\r
12 #\r
13 # You should have received a copy of the GNU Lesser General Public\r
14 # License along with this library; if not, write to the Free Software\r
15 # Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA\r
16 #\r
17 # See http://www.salome-platform.org/ or email : webmaster.salome@opencascade.com\r
18 #\r
19 # Author: A.Geay, V. Sandler, A. Bruneton\r
20 #\r
21 \r
22 #----------------------------------------------------------------------------\r
23 # LIST_CONTAINS is a macro useful for determining whether a list has a \r
24 # particular entry\r
25 #----------------------------------------------------------------------------\r
26 MACRO(LIST_CONTAINS var value)\r
27   SET(${var})\r
28   FOREACH(value2 ${ARGN})\r
29     IF(${value} STREQUAL "${value2}")\r
30       SET(${var} TRUE)\r
31     ENDIF (${value} STREQUAL "${value2}")\r
32   ENDFOREACH (value2)\r
33 ENDMACRO(LIST_CONTAINS)\r
34 \r
35 #----------------------------------------------------------------------------\r
36 # The PARSE_ARGUMENTS macro will take the arguments of another macro and\r
37 # define several variables.\r
38 #\r
39 # USAGE:  PARSE_ARGUMENTS(prefix arg_names options arg1 arg2...)\r
40 #\r
41 # ARGUMENTS:\r
42 #\r
43 # prefix: IN: a prefix to put on all variables it creates.\r
44 #\r
45 # arg_names: IN: a list of names.\r
46 # For each item in arg_names, PARSE_ARGUMENTS will create a \r
47 # variable with that name, prefixed with prefix_. Each variable will be filled\r
48 # with the arguments that occur after the given arg_name is encountered\r
49 # up to the next arg_name or the end of the arguments. All options are\r
50 # removed from these lists. PARSE_ARGUMENTS also creates a\r
51 # prefix_DEFAULT_ARGS variable containing the list of all arguments up\r
52 # to the first arg_name encountered.\r
53 #\r
54 # options: IN: a list of options.\r
55 # For each item in options, PARSE_ARGUMENTS will create a\r
56 # variable with that name, prefixed with prefix_. So, for example, if prefix is\r
57 # MY_MACRO and options is OPTION1;OPTION2, then PARSE_ARGUMENTS will\r
58 # create the variables MY_MACRO_OPTION1 and MY_MACRO_OPTION2. These\r
59 # variables will be set to true if the option exists in the command line\r
60 # or false otherwise.\r
61 # arg_names and options lists should be quoted.\r
62 #\r
63 # The rest of PARSE_ARGUMENTS are arguments from another macro to be parsed.\r
64 #----------------------------------------------------------------------------\r
65 MACRO(PARSE_ARGUMENTS prefix arg_names option_names)\r
66   SET(DEFAULT_ARGS)\r
67   FOREACH(arg_name ${arg_names})\r
68     SET(${prefix}_${arg_name})\r
69   ENDFOREACH(arg_name)\r
70   FOREACH(option ${option_names})\r
71     SET(${prefix}_${option} FALSE)\r
72   ENDFOREACH(option)\r
73   SET(current_arg_name DEFAULT_ARGS)\r
74   SET(current_arg_list)\r
75   FOREACH(arg ${ARGN})\r
76     LIST_CONTAINS(is_arg_name ${arg} ${arg_names})\r
77     IF (is_arg_name)\r
78       SET(${prefix}_${current_arg_name} ${current_arg_list})\r
79       SET(current_arg_name ${arg})\r
80       SET(current_arg_list)\r
81     ELSE (is_arg_name)\r
82       LIST_CONTAINS(is_option ${arg} ${option_names})\r
83       IF (is_option)\r
84       SET(${prefix}_${arg} TRUE)\r
85       ELSE (is_option)\r
86       SET(current_arg_list ${current_arg_list} ${arg})\r
87       ENDIF (is_option)\r
88     ENDIF (is_arg_name)\r
89   ENDFOREACH(arg)\r
90   SET(${prefix}_${current_arg_name} ${current_arg_list})\r
91 ENDMACRO(PARSE_ARGUMENTS)\r
92 \r
93 #----------------------------------------------------------------------------\r
94 # SALOME_INSTALL_SCRIPTS is a macro useful for installing scripts.\r
95 #\r
96 # USAGE: SALOME_INSTALL_SCRIPTS(file_list path [WORKING_DIRECTORY dir] [DEF_PERMS])\r
97 #\r
98 # ARGUMENTS:\r
99 # file_list: IN : list of files to be installed. This list should be quoted.\r
100 # path: IN : full pathname for installing.\r
101\r
102 # By default files to be installed as executable scripts.\r
103 # If DEF_PERMS option is provided, than permissions for installed files are\r
104 # only OWNER_WRITE, OWNER_READ, GROUP_READ, and WORLD_READ. \r
105 #----------------------------------------------------------------------------\r
106 MACRO(SALOME_INSTALL_SCRIPTS file_list path)\r
107   PARSE_ARGUMENTS(SALOME_INSTALL_SCRIPTS "WORKING_DIRECTORY" "DEF_PERMS" ${ARGN})\r
108   SET(PERMS OWNER_READ OWNER_WRITE GROUP_READ WORLD_READ)\r
109   IF(NOT SALOME_INSTALL_SCRIPTS_DEF_PERMS)\r
110     SET(PERMS ${PERMS} OWNER_EXECUTE GROUP_EXECUTE WORLD_EXECUTE)\r
111   ENDIF(NOT SALOME_INSTALL_SCRIPTS_DEF_PERMS)\r
112   SET(_all_pyc)\r
113   SET(_all_pyo)\r
114   SET(_all_subdirs)\r
115   FOREACH(file ${file_list})\r
116     SET(PREFIX "")\r
117     SET(_source_prefix "")\r
118     GET_FILENAME_COMPONENT(file_name ${file} NAME)\r
119     IF(NOT IS_ABSOLUTE ${file})\r
120       IF(SALOME_INSTALL_SCRIPTS_WORKING_DIRECTORY)\r
121             SET(PREFIX "${SALOME_INSTALL_SCRIPTS_WORKING_DIRECTORY}/")\r
122       ENDIF(SALOME_INSTALL_SCRIPTS_WORKING_DIRECTORY)\r
123       SET(_source_prefix "${CMAKE_CURRENT_SOURCE_DIR}/")\r
124     ENDIF(NOT IS_ABSOLUTE ${file})\r
125     INSTALL(FILES ${PREFIX}${file} DESTINATION ${path} PERMISSIONS ${PERMS})\r
126     GET_FILENAME_COMPONENT(ext ${file} EXT)\r
127     GET_FILENAME_COMPONENT(we_ext ${file} NAME_WE)\r
128 \r
129     IF(ext STREQUAL .py)    \r
130       # Generate and install the pyc and pyo\r
131       # [ABN] Important: we avoid references or usage of CMAKE_INSTALL_PREFIX which is not correctly set \r
132       # when using CPack.       \r
133       SET(_pyc_file "${CMAKE_CURRENT_BINARY_DIR}/${we_ext}.pyc")\r
134       SET(_pyo_file "${CMAKE_CURRENT_BINARY_DIR}/${we_ext}.pyo")\r
135       LIST(APPEND _all_pyc ${_pyc_file})\r
136       LIST(APPEND _all_pyo ${_pyo_file})\r
137       ADD_CUSTOM_COMMAND(\r
138            OUTPUT ${_pyc_file}\r
139            COMMAND ${PYTHON_EXECUTABLE} -c "import py_compile ; py_compile.compile('${_source_prefix}${file}', '${_pyc_file}', doraise=True )"\r
140            DEPENDS ${PREFIX}${file}\r
141            VERBATIM\r
142        )\r
143       ADD_CUSTOM_COMMAND(\r
144            OUTPUT ${_pyo_file}\r
145            COMMAND ${PYTHON_EXECUTABLE} -O -c "import py_compile ; py_compile.compile('${_source_prefix}${file}', '${_pyo_file}', doraise=True )"\r
146            DEPENDS ${PREFIX}${file}\r
147            VERBATIM\r
148        )\r
149       # Install the .pyo and the .pyc\r
150       INSTALL(FILES ${_pyc_file} DESTINATION ${path} PERMISSIONS ${PERMS})\r
151       INSTALL(FILES ${_pyo_file} DESTINATION ${path} PERMISSIONS ${PERMS})\r
152     ENDIF(ext STREQUAL .py)\r
153 \r
154   # get relativa path (from CMAKE_SOURCE_DIR to CMAKE_CURRENT_SOURCE_DIR)\r
155   STRING(REGEX REPLACE ${CMAKE_SOURCE_DIR} "" rel_dir ${CMAKE_CURRENT_SOURCE_DIR})\r
156   # convert "/" to "_"\r
157   IF(rel_dir)\r
158     STRING(REGEX REPLACE "/" "_" unique_name ${rel_dir})\r
159   ELSE(rel_dir)\r
160     SET(unique_name _)\r
161   ENDIF(rel_dir)\r
162 \r
163   ENDFOREACH(file ${file_list})\r
164   # Generate only one target for all requested Python script compilation.\r
165   # Make sure that the target name is unique too. \r
166   IF(_all_pyc)\r
167      SET(_cnt 0)\r
168      WHILE(TARGET "PYCOMPILE${unique_name}_${_cnt}")\r
169        MATH(EXPR _cnt ${_cnt}+1)\r
170      ENDWHILE()\r
171      ADD_CUSTOM_TARGET("PYCOMPILE${unique_name}_${_cnt}" ALL DEPENDS ${_all_pyc} ${_all_pyo})\r
172   ENDIF()\r
173 ENDMACRO(SALOME_INSTALL_SCRIPTS)\r
174 \r
175 #----------------------------------------------------------------------------\r
176 # SALOME_CONFIGURE_FILE is a macro useful for copying a file to another location \r
177 # and modify its contents.\r
178 #\r
179 # USAGE: SALOME_CONFIGURE_FILE(in_file out_file [INSTALL dir])\r
180 #\r
181 # ARGUMENTS:\r
182 # in_file: IN : input file (if relative path is given, full file path is computed from current source dir).\r
183 # out_file: IN : output file (if relative path is given, full file path is computed from current build dir).\r
184 # If INSTALL is specified, then 'out_file' will be installed to the 'dir' directory.\r
185 #----------------------------------------------------------------------------\r
186 MACRO(SALOME_CONFIGURE_FILE IN_FILE OUT_FILE)\r
187   IF(IS_ABSOLUTE ${IN_FILE})\r
188     SET(_in_file ${IN_FILE})\r
189   ELSE()\r
190     SET(_in_file ${CMAKE_CURRENT_SOURCE_DIR}/${IN_FILE})\r
191   ENDIF()\r
192   IF(IS_ABSOLUTE  ${OUT_FILE})\r
193     SET(_out_file ${OUT_FILE})\r
194   ELSE()\r
195     SET(_out_file ${CMAKE_CURRENT_BINARY_DIR}/${OUT_FILE})\r
196   ENDIF()\r
197   MESSAGE(STATUS "Creation of ${_out_file}")\r
198   CONFIGURE_FILE(${_in_file} ${_out_file} @ONLY)\r
199   PARSE_ARGUMENTS(SALOME_CONFIGURE_FILE "INSTALL" "" ${ARGN})\r
200   IF(SALOME_CONFIGURE_FILE_INSTALL)\r
201     INSTALL(FILES ${_out_file} DESTINATION ${SALOME_CONFIGURE_FILE_INSTALL})\r
202   ENDIF(SALOME_CONFIGURE_FILE_INSTALL)\r
203 ENDMACRO(SALOME_CONFIGURE_FILE)\r
204 \r
205 \r
206 #######################################################################################\r
207 # Useful macros for SALOME own package detection system\r
208 #\r
209 \r
210 ###\r
211 # SALOME_CHECK_EQUAL_PATHS(result path1 path2)\r
212 #  Check if two paths are identical, resolving links. If the paths do not exist a simple\r
213 #  text comparison is performed.\r
214 #  result is a boolean.\r
215 ###\r
216 MACRO(SALOME_CHECK_EQUAL_PATHS varRes path1 path2)  \r
217   SET("${varRes}" OFF)\r
218   IF(EXISTS "${path1}")\r
219     GET_FILENAME_COMPONENT(_tmp1 "${path1}" REALPATH)\r
220   ELSE()\r
221     SET(_tmp1 "${path1}")\r
222   ENDIF() \r
223 \r
224   IF(EXISTS "${path2}")\r
225     GET_FILENAME_COMPONENT(_tmp2 "${path2}" REALPATH)\r
226   ELSE()\r
227     SET(_tmp2 "${path2}")\r
228   ENDIF() \r
229 \r
230   IF("${_tmp1}" STREQUAL "${_tmp2}")\r
231     SET("${varRes}" ON)\r
232   ENDIF()\r
233 #  MESSAGE(${${varRes}})\r
234 ENDMACRO()\r
235 \r
236 ####\r
237 # SALOME_LOG_OPTIONAL_PACKAGE(pkg flag)\r
238 #\r
239 # Register in global variables the detection status (found or not) of the optional package 'pkg' \r
240 # and the configuration flag that should be turned off to avoid detection of the package.\r
241 # The global variables are read again by SALOME_PACKAGE_REPORT_AND_CHECK to produce \r
242 # a summary report of the detection status and stops the process if necessary.\r
243 MACRO(SALOME_LOG_OPTIONAL_PACKAGE pkg flag)\r
244   # Was the package found\r
245   STRING(TOUPPER ${pkg} _pkg_UC)\r
246   IF(${pkg}_FOUND OR ${_pkg_UC}_FOUND)\r
247     SET(_isFound TRUE)\r
248   ELSE()\r
249     SET(_isFound FALSE)\r
250   ENDIF()\r
251 \r
252   # Is the package already in the list? Then update its status:\r
253   LIST(FIND _SALOME_OPTIONAL_PACKAGES_names ${pkg} _result)\r
254   IF(NOT ${_result} EQUAL -1)\r
255     LIST(REMOVE_AT _SALOME_OPTIONAL_PACKAGES_found ${_result})\r
256     LIST(REMOVE_AT _SALOME_OPTIONAL_PACKAGES_flags ${_result})\r
257     LIST(INSERT    _SALOME_OPTIONAL_PACKAGES_found ${_result} ${_isFound})\r
258     LIST(INSERT    _SALOME_OPTIONAL_PACKAGES_flags ${_result} ${flag})\r
259   ELSE()\r
260     # Otherwise insert it\r
261     LIST(APPEND _SALOME_OPTIONAL_PACKAGES_names ${pkg})\r
262     LIST(APPEND _SALOME_OPTIONAL_PACKAGES_found ${_isFound})\r
263     LIST(APPEND _SALOME_OPTIONAL_PACKAGES_flags ${flag})\r
264   ENDIF() \r
265   \r
266 ENDMACRO(SALOME_LOG_OPTIONAL_PACKAGE)\r
267 \r
268 ####\r
269 # SALOME_JUSTIFY_STRING()\r
270 #\r
271 # Justifies the string specified as an argument to the given length\r
272 # adding required number of spaces to the end. Does noting if input\r
273 # string is longer as required length.\r
274 # Puts the result to the output variable.\r
275 #\r
276 # USAGE: SALOME_JUSTIFY_STRING(input length result)\r
277 #\r
278 # ARGUMENTS:\r
279 #   input  [in] input string\r
280 #   length [in] required length of resulting string\r
281 #   result [out] name of variable where the result string is put to\r
282 #\r
283 MACRO(SALOME_JUSTIFY_STRING input length result)\r
284   SET(${result} ${input})\r
285   STRING(LENGTH ${input} _input_length)\r
286   MATH(EXPR _nb_spaces "${length}-${_input_length}-1")\r
287   IF (_nb_spaces GREATER 0)\r
288     FOREACH(_idx RANGE ${_nb_spaces})  \r
289       SET(${result} "${${result}} ")\r
290     ENDFOREACH()\r
291   ENDIF()\r
292 ENDMACRO(SALOME_JUSTIFY_STRING)\r
293 \r
294 ####\r
295 # SALOME_PACKAGE_REPORT_AND_CHECK()\r
296 #\r
297 # Print a quick summary of the detection of optional prerequisites.\r
298 # If a package was not found, the configuration is stopped. The summary also indicates \r
299 # which flag should be turned off to skip the detection of the package. \r
300 #\r
301 # If optional JUSTIFY argument is specified, names of packages\r
302 # are left-justified to the given length; default value is 10.\r
303 #\r
304 # USAGE: SALOME_PACKAGE_REPORT_AND_CHECK([JUSTIFY length])\r
305 #\r
306 MACRO(SALOME_PACKAGE_REPORT_AND_CHECK)\r
307   SET(_will_fail OFF)\r
308   PARSE_ARGUMENTS(SALOME_PACKAGE_REPORT "JUSTIFY" "" ${ARGN})\r
309   IF(SALOME_PACKAGE_REPORT_JUSTIFY)\r
310     SET(_length ${SALOME_PACKAGE_REPORT_JUSTIFY})\r
311   ELSE()\r
312     SET(_length 23)\r
313   ENDIF()\r
314   MESSAGE(STATUS "") \r
315   MESSAGE(STATUS "  Optional packages - Detection report ")\r
316   MESSAGE(STATUS "  ==================================== ")\r
317   MESSAGE(STATUS "")\r
318   IF(DEFINED _SALOME_OPTIONAL_PACKAGES_names)\r
319     LIST(LENGTH _SALOME_OPTIONAL_PACKAGES_names _list_len)\r
320     # Another CMake stupidity - FOREACH(... RANGE r) generates r+1 numbers ...\r
321     MATH(EXPR _range "${_list_len}-1")\r
322     FOREACH(_idx RANGE ${_range})  \r
323       LIST(GET _SALOME_OPTIONAL_PACKAGES_names ${_idx} _pkg_name)\r
324       LIST(GET _SALOME_OPTIONAL_PACKAGES_found ${_idx} _pkg_found)\r
325       LIST(GET _SALOME_OPTIONAL_PACKAGES_flags ${_idx} _pkg_flag)\r
326       SALOME_JUSTIFY_STRING(${_pkg_name} ${_length} _pkg_name)\r
327       IF(_pkg_found)\r
328         SET(_found_msg "Found")\r
329         SET(_flag_msg "")\r
330       ELSE()\r
331         SET(_will_fail ON)\r
332         SET(_found_msg "NOT Found")\r
333         SET(_flag_msg " - ${_pkg_flag} can be switched OFF to skip this prerequisite.")\r
334       ENDIF()\r
335     \r
336       MESSAGE(STATUS "  * ${_pkg_name}  ->  ${_found_msg}${_flag_msg}")\r
337     ENDFOREACH()\r
338   ENDIF(DEFINED _SALOME_OPTIONAL_PACKAGES_names)\r
339   MESSAGE(STATUS "")\r
340   MESSAGE(STATUS "")\r
341   \r
342   # Failure if some packages were missing:\r
343   IF(_will_fail)\r
344     MESSAGE(FATAL_ERROR "Some required prerequisites have NOT been found. Take a look at the report above to fix this.")\r
345   ENDIF()\r
346 ENDMACRO(SALOME_PACKAGE_REPORT_AND_CHECK)\r
347 \r
348 ####\r
349 # SALOME_FIND_PACKAGE(englobingPackageName standardPackageName modus [onlyTryQuietly])\r
350 #\r
351 # example:  SALOME_FIND_PACKAGE(SalomeVTK VTK CONFIG)\r
352 #\r
353 # Encapsulate the call to the standard FIND_PACKAGE(standardPackageName) passing all the options\r
354 # given when calling the command FIND_PACKAGE(SalomeXYZ). Those options are stored implicitly in \r
355 # CMake variables: xyz__FIND_QUIETLY, xyz_FIND_REQUIRED, etc ...\r
356\r
357 # If a list of components was specified when invoking the initial FIND_PACKAGE(SalomeXyz ...) this is \r
358 # also handled properly.\r
359 #\r
360 # Modus is either MODULE or CONFIG (cf standard FIND_PACKAGE() documentation).\r
361 # The last argument is optional and if set to TRUE will force the search to be OPTIONAL and QUIET.\r
362 # If the package is looked for in CONFIG mode, the standard system paths are skipped. If you still want a \r
363 # system installation to be found in this mode, you have to set the ROOT_DIR variable explicitly to /usr (for\r
364 # example). \r
365 #  \r
366 # This macro is to be called from within the FindSalomeXXXX.cmake file.\r
367 #\r
368 ####\r
369 MACRO(SALOME_FIND_PACKAGE englobPkg stdPkg mode)\r
370   SET(_OPT_ARG ${ARGV3})\r
371   # Only bother if the package was not already found:\r
372   # Some old packages use the lower case version - standard should be to always use\r
373   # upper case:\r
374   STRING(TOUPPER ${stdPkg} stdPkgUC)\r
375   IF(NOT (${stdPkg}_FOUND OR ${stdPkgUC}_FOUND))\r
376     IF(${englobPkg}_FIND_QUIETLY OR _OPT_ARG)\r
377       SET(_tmp_quiet "QUIET")\r
378     ELSE()\r
379       SET(_tmp_quiet)\r
380     ENDIF()  \r
381     IF(${englobPkg}_FIND_REQUIRED AND NOT _OPT_ARG)\r
382       SET(_tmp_req "REQUIRED")\r
383     ELSE()\r
384       SET(_tmp_req)\r
385     ENDIF()  \r
386     IF(${englobPkg}_FIND_VERSION_EXACT)\r
387       SET(_tmp_exact "EXACT")\r
388     ELSE()\r
389       SET(_tmp_exact)\r
390     ENDIF()\r
391 \r
392     # Call the CMake FIND_PACKAGE() command:    \r
393     STRING(TOLOWER ${stdPkg} _pkg_lc)\r
394     IF(("${mode}" STREQUAL "NO_MODULE") OR ("${mode}" STREQUAL "CONFIG"))\r
395       # Hope to find direclty a CMake config file, indicating the SALOME CMake file\r
396       # paths (the command already looks in places like "share/cmake", etc ... by default)\r
397       # Note the options NO_CMAKE_BUILDS_PATH, NO_CMAKE_PACKAGE_REGISTRY to avoid (under Windows)\r
398       # looking into a previous CMake build done via a GUI, or into the Win registry.\r
399       # NO_CMAKE_SYSTEM_PATH and NO_SYSTEM_ENVIRONMENT_PATH ensure any _system_ files like 'xyz-config.cmake' \r
400       # don't get loaded (typically Boost). To force their loading, set the XYZ_ROOT_DIR variable to '/usr'. \r
401       # See documentation of FIND_PACKAGE() for full details.\r
402       \r
403       # Do we need to call the signature using components?\r
404       IF(${englobPkg}_FIND_COMPONENTS)\r
405         FIND_PACKAGE(${stdPkg} ${${englobPkg}_FIND_VERSION} ${_tmp_exact} \r
406               NO_MODULE ${_tmp_quiet} ${_tmp_req} COMPONENTS ${${englobPkg}_FIND_COMPONENTS}\r
407               PATH_SUFFIXES "salome_adm/cmake_files" "adm_local/cmake_files" "adm/cmake"\r
408               NO_CMAKE_BUILDS_PATH NO_CMAKE_PACKAGE_REGISTRY NO_CMAKE_SYSTEM_PACKAGE_REGISTRY NO_CMAKE_SYSTEM_PATH\r
409                 NO_SYSTEM_ENVIRONMENT_PATH)\r
410       ELSE()\r
411         FIND_PACKAGE(${stdPkg} ${${englobPkg}_FIND_VERSION} ${_tmp_exact} \r
412               NO_MODULE ${_tmp_quiet} ${_tmp_req}\r
413               PATH_SUFFIXES "salome_adm/cmake_files" "adm_local/cmake_files" "adm/cmake"\r
414               NO_CMAKE_BUILDS_PATH NO_CMAKE_PACKAGE_REGISTRY NO_CMAKE_SYSTEM_PACKAGE_REGISTRY NO_CMAKE_SYSTEM_PATH\r
415                  NO_SYSTEM_ENVIRONMENT_PATH)\r
416       ENDIF()\r
417       MARK_AS_ADVANCED(${stdPkg}_DIR)\r
418       \r
419     ELSEIF("${mode}" STREQUAL "MODULE")\r
420     \r
421       # Do we need to call the signature using components?\r
422       IF(${englobPkg}_FIND_COMPONENTS)\r
423         FIND_PACKAGE(${stdPkg} ${${englobPkg}_FIND_VERSION} ${_tmp_exact} \r
424               MODULE ${_tmp_quiet} ${_tmp_req} COMPONENTS ${${englobPkg}_FIND_COMPONENTS})\r
425       ELSE()\r
426         FIND_PACKAGE(${stdPkg} ${${englobPkg}_FIND_VERSION} ${_tmp_exact} \r
427               MODULE ${_tmp_quiet} ${_tmp_req})\r
428       ENDIF()\r
429       \r
430     ELSE()\r
431     \r
432       MESSAGE(FATAL_ERROR "Invalid mode argument in the call to the macro SALOME_FIND_PACKAGE. Should be CONFIG or MODULE.")\r
433       \r
434     ENDIF()\r
435     \r
436   ENDIF()\r
437 ENDMACRO()\r
438 \r
439 \r
440 ####################################################################\r
441 # SALOME_FIND_PACKAGE_DETECT_CONFLICTS(pkg referenceVariable upCount)\r
442 #    pkg              : name of the system package to be detected\r
443 #    referenceVariable: variable containing a path that can be browsed up to \r
444 # retrieve the package root directory (xxx_ROOT_DIR)\r
445 #    upCount          : number of times we have to go up from the path <referenceVariable>\r
446 # to obtain the package root directory.\r
447 # If this is a path to a file, going up one time gives the directory containing the file\r
448 # going up 2 times gives the parent directory.\r
449 #   \r
450 # For example:  SALOME_FIND_PACKAGE_DETECT_CONFLICTS(SWIG SWIG_EXECUTABLE 2)\r
451 #     with SWIG_EXECUTABLE set to '/usr/bin/swig'\r
452 #     will produce '/usr' \r
453 #\r
454 # Generic detection (and conflict check) procedure for package XYZ:\r
455 # 1. Load a potential env variable XYZ_ROOT_DIR as a default choice for the cache entry XYZ_ROOT_DIR\r
456 #    If empty, load a potential XYZ_ROOT_DIR_EXP as default value (path exposed by another package depending\r
457 # directly on XYZ)\r
458 # 2. Invoke FIND_PACKAGE() in this order:\r
459 #    * in CONFIG mode first (if possible): priority is given to a potential \r
460 #    "XYZ-config.cmake" file\r
461 #    * then switch to the standard MODULE mode, appending on CMAKE_PREFIX_PATH \r
462 # the above XYZ_ROOT_DIR variable\r
463 # 3. Extract the path actually found into a temp variable _XYZ_TMP_DIR\r
464 # 4. Warn if XYZ_ROOT_DIR is set and doesn't match what was found (e.g. when CMake found the system installation\r
465 #    instead of what is pointed to by XYZ_ROOT_DIR - happens when a typo in the content of XYZ_ROOT_DIR).\r
466 # 5. Conflict detection:\r
467 #    * check the temp variable against a potentially existing XYZ_ROOT_DIR_EXP\r
468 # 6. Finally expose what was *actually* found in XYZ_ROOT_DIR.  \r
469 # 7. Specific stuff: for example exposing a prerequisite of XYZ to the rest of the world for future \r
470 # conflict detection. This is added after the call to the macro by the callee.\r
471 #\r
472 MACRO(SALOME_FIND_PACKAGE_AND_DETECT_CONFLICTS pkg referenceVariable upCount)\r
473   ##\r
474   ## 0. Initialization\r
475   ##\r
476   PARSE_ARGUMENTS(SALOME_FIND_PACKAGE_AND_DETECT_CONFLICTS "ENVVAR" "" ${ARGN})\r
477   \r
478   # Package name, upper case\r
479   STRING(TOUPPER ${pkg} pkg_UC)\r
480 \r
481   ##\r
482   ## 1. Load environment or any previously detected root dir for the package\r
483   ##\r
484   SET(_envvar ${pkg_UC}_ROOT_DIR)\r
485   IF(SALOME_FIND_PACKAGE_AND_DETECT_CONFLICTS_ENVVAR)\r
486     SET(_envvar "${SALOME_FIND_PACKAGE_AND_DETECT_CONFLICTS_ENVVAR}")\r
487   ENDIF()\r
488   IF(DEFINED ENV{${_envvar}})\r
489     FILE(TO_CMAKE_PATH "$ENV{${_envvar}}" _${pkg_UC}_ROOT_DIR_ENV)\r
490     SET(_dflt_value "${_${pkg_UC}_ROOT_DIR_ENV}")\r
491   ELSE()\r
492     # will be blank if no package was previously loaded:\r
493     SET(_dflt_value "${${pkg_UC}_ROOT_DIR_EXP}")\r
494   ENDIF()\r
495   # Detect if the variable has been set on the command line or elsewhere:\r
496   IF(DEFINED ${_envvar})\r
497      SET(_var_already_there TRUE)\r
498   ELSE()\r
499      SET(_var_already_there FALSE)\r
500   ENDIF()\r
501   #   Make cache entry \r
502   SET(${_envvar} "${_dflt_value}" CACHE PATH "Path to ${pkg_UC} directory")\r
503 \r
504   ##\r
505   ## 2. Find package - try CONFIG mode first (i.e. looking for XYZ-config.cmake)\r
506   ##\r
507   \r
508   # Override the variable - don't append to it, as it would give precedence\r
509   # to what was stored there before!  \r
510   IF(DEFINED ${_envvar})\r
511     SET(CMAKE_PREFIX_PATH "${${_envvar}}")\r
512   ENDIF()\r
513     \r
514   # Try find_package in config mode. This has the priority, but is \r
515   # performed QUIET and not REQUIRED:\r
516   SALOME_FIND_PACKAGE("Salome${pkg}" ${pkg} NO_MODULE TRUE)\r
517   \r
518   IF (${pkg_UC}_FOUND OR ${pkg}_FOUND)\r
519     MESSAGE(STATUS "Found ${pkg} in CONFIG mode!")\r
520   ENDIF()\r
521 \r
522   # Otherwise try the standard way (module mode, with the standard CMake Find*** macro):\r
523   # We do it quietly to produce our own error message, except if we are in debug mode:\r
524   IF(SALOME_CMAKE_DEBUG)\r
525     SALOME_FIND_PACKAGE("Salome${pkg}" ${pkg} MODULE FALSE)\r
526   ELSE()\r
527     SALOME_FIND_PACKAGE("Salome${pkg}" ${pkg} MODULE TRUE)\r
528   ENDIF()\r
529   \r
530   # Set the "FOUND" variable for the SALOME wrapper:\r
531   IF(${pkg_UC}_FOUND OR ${pkg}_FOUND)\r
532     SET(SALOME${pkg_UC}_FOUND TRUE)\r
533   ELSE()\r
534     SET(SALOME${pkg_UC}_FOUND FALSE)\r
535     IF(NOT Salome${pkg}_FIND_QUIETLY)\r
536       IF(Salome${pkg}_FIND_REQUIRED)\r
537          MESSAGE(FATAL_ERROR "Package ${pkg} couldn't be found - did you set the corresponing root dir correctly? "\r
538          "It currently contains ${_envvar}=${${_envvar}}  "\r
539          "Append -DSALOME_CMAKE_DEBUG=ON on the command line if you want to see the original CMake error.")\r
540       ELSE()\r
541          MESSAGE(WARNING "Package ${pkg} couldn't be found - did you set the corresponing root dir correctly? "\r
542          "It currently contains ${_envvar}=${${_envvar}}  "\r
543          "Append -DSALOME_CMAKE_DEBUG=ON on the command line if you want to see the original CMake error.")\r
544       ENDIF()\r
545     ENDIF()\r
546   ENDIF()\r
547   \r
548   IF (${pkg_UC}_FOUND OR ${pkg}_FOUND)\r
549     ## 3. Set the root dir which was finally retained by going up "upDir" times\r
550     ## from the given reference path. The variable "referenceVariable" may be a list.\r
551     ## In this case we take its first element. \r
552     \r
553     # First test if the variable exists, warn otherwise:\r
554     IF(NOT DEFINED ${referenceVariable})\r
555       MESSAGE(WARNING "${pkg}: the reference variable '${referenceVariable}' used when calling the macro "\r
556       "SALOME_FIND_PACKAGE_AND_DETECT_CONFLICTS() is not defined.")\r
557     ENDIF()\r
558     \r
559     LIST(LENGTH ${referenceVariable} _tmp_len)\r
560     IF(_tmp_len)\r
561        LIST(GET ${referenceVariable} 0 _tmp_ROOT_DIR)\r
562     ELSE()\r
563        #  Note the double de-reference of "referenceVariable":\r
564        SET(_tmp_ROOT_DIR "${${referenceVariable}}")\r
565     ENDIF()\r
566     # Up cound can be reset by detection procedure\r
567     SET(_upCount ${upCount})\r
568     IF(DEFINED ${pkg_UC}_UPCOUNT)\r
569       SET(_upCount ${${pkg_UC}_UPCOUNT})\r
570     ENDIF()\r
571     IF(${_upCount}) \r
572       FOREACH(_unused RANGE 1 ${_upCount})        \r
573         GET_FILENAME_COMPONENT(_tmp_ROOT_DIR "${_tmp_ROOT_DIR}" PATH)\r
574       ENDFOREACH()\r
575     ENDIF()\r
576 \r
577     ##\r
578     ## 4. Warn if CMake found something not located under ENV(XYZ_ROOT_DIR)\r
579     ##\r
580     IF(DEFINED ENV{${_envvar}})\r
581       SALOME_CHECK_EQUAL_PATHS(_res "${_tmp_ROOT_DIR}" "${_${pkg_UC}_ROOT_DIR_ENV}")\r
582       IF(NOT _res)\r
583         MESSAGE(WARNING "${pkg} was found, but not at the path given by the "\r
584             "environment ${_envvar}! Is the variable correctly set? "\r
585             "The two paths are: ${_tmp_ROOT_DIR} and: ${_${pkg_UC}_ROOT_DIR_ENV}")\r
586         \r
587       ELSE()\r
588         MESSAGE(STATUS "${pkg} found directory matches what was specified in the ${_envvar} variable, all good!")    \r
589       ENDIF()\r
590     ELSE()\r
591         IF(NOT _var_already_there) \r
592           MESSAGE(STATUS "Variable ${_envvar} was not explicitly defined. "\r
593           "An installation was found anyway: ${_tmp_ROOT_DIR}")\r
594         ENDIF()\r
595     ENDIF()\r
596 \r
597     ##\r
598     ## 5. Conflict detection\r
599     ##     From another prerequisite using the package:\r
600     ##\r
601     IF(${pkg_UC}_ROOT_DIR_EXP)\r
602         SALOME_CHECK_EQUAL_PATHS(_res "${_tmp_ROOT_DIR}" "${${pkg_UC}_ROOT_DIR_EXP}") \r
603         IF(NOT _res)\r
604            MESSAGE(WARNING "Warning: ${pkg}: detected version conflicts with a previously found ${pkg}!"\r
605                            " The two paths are " ${_tmp_ROOT_DIR} " vs " ${${pkg_UC}_ROOT_DIR_EXP})\r
606         ELSE()\r
607             MESSAGE(STATUS "${pkg} directory matches what was previously exposed by another prereq, all good!")\r
608         ENDIF()        \r
609     ENDIF()\r
610     \r
611     ##\r
612     ## 6. Save the detected installation\r
613     ##\r
614     SET(${_envvar} "${_tmp_ROOT_DIR}")\r
615      \r
616   ELSE()\r
617     MESSAGE(STATUS "${pkg} was not found.")  \r
618   ENDIF()\r
619   \r
620   SET(Salome${pkg}_FOUND "${pkg}_FOUND")\r
621 ENDMACRO(SALOME_FIND_PACKAGE_AND_DETECT_CONFLICTS)\r
622 \r
623 \r
624 ####################################################################\r
625 # SALOME_ADD_MPI_TO_HDF5()\r
626\r
627 # Overload the HDF5 flags so that they also contain MPI references.\r
628 # This is to be used when HDF5 was compiled with MPI support;\r
629 MACRO(SALOME_ADD_MPI_TO_HDF5)  \r
630   SET(HDF5_INCLUDE_DIRS ${HDF5_INCLUDE_DIRS} ${MPI_INCLUDE_DIRS})\r
631   SET(HDF5_DEFINITIONS "${HDF5_DEFINITIONS} ${MPI_DEFINITIONS}")\r
632   SET(HDF5_LIBRARIES ${HDF5_LIBRARIES} ${MPI_LIBRARIES})\r
633 ENDMACRO(SALOME_ADD_MPI_TO_HDF5)\r
634 \r
635 ####################################################################\r
636 # SALOME_TOHEXA()\r
637 # Convert a number (smaller than 16) into hexadecimal representation\r
638 # with a leading 0.\r
639 MACRO(SALOME_TOHEXA num result)\r
640   SET(_hexa_map a b c d e f)\r
641   IF(${num} LESS 10)\r
642     SET(${result} "0${num}")\r
643   ELSE()\r
644     MATH(EXPR _res "${num}-10" )\r
645     LIST(GET _hexa_map ${_res} _out)\r
646     SET(${result} "0${_out}")\r
647   ENDIF()\r
648 ENDMACRO(SALOME_TOHEXA)\r
649 \r
650 ####################################################################\r
651 # SALOME_XVERSION()\r
652\r
653 # Computes hexadecimal version of SALOME package\r
654 #\r
655 # USAGE: SALOME_XVERSION(package)\r
656 #\r
657 # ARGUMENTS:\r
658 #\r
659 # package: IN: SALOME package name\r
660 #\r
661 # The macro reads SALOME package version from PACKAGE_VERSION variable\r
662 # (note package name in uppercase as assumed for SALOME modules);\r
663 # hexadecimal version value in form 0xAABBCC (where AA, BB and CC are\r
664 # major, minor and maintenance components of package version in\r
665 # hexadecimal form) is put to the PACKAGE_XVERSION variable\r
666 MACRO(SALOME_XVERSION pkg)\r
667   STRING(TOUPPER ${pkg} _pkg_UC)\r
668   IF(${_pkg_UC}_VERSION)\r
669     SET(_major)\r
670     SET(_minor)\r
671     SET(_patch)\r
672     SALOME_TOHEXA(${${_pkg_UC}_MAJOR_VERSION} _major)\r
673     SALOME_TOHEXA(${${_pkg_UC}_MINOR_VERSION} _minor)\r
674     SALOME_TOHEXA(${${_pkg_UC}_PATCH_VERSION} _patch)\r
675     SET(${_pkg_UC}_XVERSION "0x${_major}${_minor}${_patch}")\r
676   ENDIF()\r
677 ENDMACRO(SALOME_XVERSION)\r
678 \r
679 \r
680 #########################################################################\r
681 # SALOME_ACCUMULATE_HEADERS()\r
682\r
683 # This macro is called in the various FindSalomeXYZ.cmake modules to accumulate\r
684 # internally the list of include headers to be saved for future export. \r
685 # The full set of include is saved in a variable called \r
686 #      _${PROJECT_NAME}_EXTRA_HEADERS\r
687 #\r
688 MACRO(SALOME_ACCUMULATE_HEADERS lst)\r
689   FOREACH(l IN LISTS ${lst})\r
690     LIST(FIND _${PROJECT_NAME}_EXTRA_HEADERS "${l}" _res)\r
691     IF(_res EQUAL "-1")\r
692       IF(NOT "${l}" STREQUAL "/usr/include")\r
693         LIST(APPEND _${PROJECT_NAME}_EXTRA_HEADERS "${l}")\r
694       ENDIF()\r
695     ENDIF()\r
696   ENDFOREACH()\r
697 ENDMACRO(SALOME_ACCUMULATE_HEADERS)\r
698 \r
699 #########################################################################\r
700 # SALOME_ACCUMULATE_ENVIRONMENT()\r
701\r
702 # USAGE: SALOME_ACCUMULATE_ENVIRONMENT(envvar value [value ...])\r
703 #\r
704 # ARGUMENTS:\r
705 #   envvar [in] environment variable name, e.g. PATH\r
706 #   value  [in] value(s) to be added to environment variable\r
707 #\r
708 # This macro is called in the various FindSalomeXYZ.cmake modules to \r
709 # accumulate environment variables, to be used later to run some command\r
710 # in proper environment.\r
711 #\r
712 # 1. Each envrironment variable is stored in specific CMake variable\r
713 #    _${PROJECT_NAME}_EXTRA_ENV_<var>, where <var> is name of variable.\r
714 # 2. Full list of environment variable names is stored in CMake variable\r
715 #    _${PROJECT_NAME}_EXTRA_ENV.\r
716 #\r
717 # Notes:\r
718 # - The arguments list can include optional CHECK or NOCHECK keywords:\r
719 #   * For all arguments following CHECK keyword the macro perform an\r
720 #     additional check (see below); this is the default mode, it is suitable\r
721 #     for path variables (PATH, LD_LIBRARY_PATH, etc).\r
722 #   * For all arguments following NOCHECK keyword, no additional check is\r
723 #     performed.\r
724 #   Checking an argument means that we check:\r
725 #    - That the path actually exists\r
726 #    - That this is not a standard system path (starting with "/usr"); this avoids\r
727 #   polluting LD_LIBRARY_PATH or PATH with things like "/usr/lib64" ...\r
728 #\r
729 MACRO(SALOME_ACCUMULATE_ENVIRONMENT envvar)\r
730   SET(_is_check ON)\r
731   FOREACH(_item ${ARGN})\r
732     IF(${_item} STREQUAL "NOCHECK")\r
733       SET(_is_check OFF)\r
734     ELSEIF(${_item} STREQUAL "CHECK")\r
735       SET(_is_check ON)\r
736     ELSE()\r
737       IF(_is_check)\r
738         IF(NOT IS_DIRECTORY ${_item})\r
739           IF(TARGET ${_item})\r
740             GET_TARGET_PROPERTY(_item ${_item} LOCATION)\r
741           ENDIF()        \r
742           GET_FILENAME_COMPONENT(_item ${_item} PATH)\r
743         ENDIF()    \r
744         IF(EXISTS ${_item})\r
745           STRING(REGEX MATCH "^(/usr|/lib|/bin)" _usr_find ${_item})\r
746           LIST(FIND _${PROJECT_NAME}_EXTRA_ENV_${envvar} ${_item} _res)\r
747           IF(NOT _usr_find AND _res EQUAL -1)\r
748               LIST(APPEND _${PROJECT_NAME}_EXTRA_ENV_${envvar} ${_item})\r
749           ENDIF()  \r
750         ENDIF()\r
751       ELSE(_is_check)\r
752         LIST(FIND _${PROJECT_NAME}_EXTRA_ENV_${envvar} ${_item} _res)\r
753         IF( _res EQUAL -1)\r
754           LIST(APPEND _${PROJECT_NAME}_EXTRA_ENV_${envvar} ${_item})\r
755         ENDIF()  \r
756       ENDIF(_is_check)\r
757     ENDIF()   \r
758   ENDFOREACH()\r
759   \r
760   LIST(FIND _${PROJECT_NAME}_EXTRA_ENV ${envvar} _res)\r
761   IF(_res EQUAL -1)\r
762     LIST(APPEND _${PROJECT_NAME}_EXTRA_ENV ${envvar})\r
763   ENDIF()\r
764   SET(_${PROJECT_NAME}_EXTRA_ENV_FULL "SET\(${PROJECT_NAME}_EXTRA_ENV ${_${PROJECT_NAME}_EXTRA_ENV}\)")\r
765   FOREACH(_res ${_${PROJECT_NAME}_EXTRA_ENV})\r
766     STRING(REPLACE "${CMAKE_INSTALL_PREFIX}" "\${PACKAGE_PREFIX_DIR}" _res_path "${_${PROJECT_NAME}_EXTRA_ENV_${_res}}")\r
767     SET(_${PROJECT_NAME}_EXTRA_ENV_FULL "${_${PROJECT_NAME}_EXTRA_ENV_FULL}\nSET\(${PROJECT_NAME}_EXTRA_ENV_${_res} ${_res_path}\)")\r
768   ENDFOREACH()\r
769 ENDMACRO(SALOME_ACCUMULATE_ENVIRONMENT)\r
770 \r
771 #########################################################################\r
772 # SALOME_GENERATE_ENVIRONMENT_SCRIPT()\r
773\r
774 # USAGE: SALOME_GENERATE_ENVIRONMENT_SCRIPT(output script cmd opts)\r
775 #\r
776 # ARGUMENTS:\r
777 #   output [out] output command, e.g. for creation of target.\r
778 #   script [in]  output environement script name\r
779 #   cmd    [in]  input command, e.g. sphinx or python command.\r
780 #   opts   [in]  options for input command (cmd).\r
781 #\r
782 # This macro is called when it's necessary to use given environment to run some command. \r
783 # Macro generates environement script using previously created variables\r
784 # _${PROJECT_NAME}_EXTRA_ENV_<var>, where <var> is name of variable and\r
785 # _${PROJECT_NAME}_EXTRA_ENV (see marco SALOME_ACCUMULATE_ENVIRONMENT);\r
786 # and puts generated command in proper environment into <output> argument.\r
787\r
788 # Notes:\r
789 # - If <script> is specified as relative path, it is computed from the current build\r
790 #   directory.\r
791 #\r
792 MACRO(SALOME_GENERATE_ENVIRONMENT_SCRIPT output script cmd opts)\r
793   IF(IS_ABSOLUTE ${script})\r
794     SET(_script ${script})\r
795   ELSE()\r
796     SET(_script ${CMAKE_CURRENT_BINARY_DIR}/${script})\r
797   ENDIF()\r
798 \r
799   IF(WIN32)\r
800     SET(_ext "bat")\r
801     SET(_call_cmd "call")\r
802   ELSE()\r
803     SET(_ext "sh")\r
804     SET(_call_cmd ".")\r
805   ENDIF()\r
806   \r
807   SET(_env)\r
808   FOREACH(_item ${_${PROJECT_NAME}_EXTRA_ENV})\r
809     FOREACH(_val ${_${PROJECT_NAME}_EXTRA_ENV_${_item}})\r
810       IF(WIN32)\r
811         IF(${_item} STREQUAL "LD_LIBRARY_PATH")\r
812           SET(_item PATH)\r
813         ENDIF()\r
814         STRING(REPLACE "/" "\\" _env "${_env} @SET ${_item}=${_val};%${_item}%\n")        \r
815       ELSE(WIN32)\r
816         SET(_env "${_env} export ${_item}=${_val}:\${${_item}}\n")\r
817       ENDIF(WIN32)\r
818     ENDFOREACH()\r
819   ENDFOREACH()\r
820   \r
821   SET(_script ${_script}.${_ext})\r
822   FILE(WRITE ${_script} "${_env}")\r
823   \r
824   SET(${output} ${_call_cmd} ${_script} && ${cmd} ${opts})\r
825   \r
826 ENDMACRO(SALOME_GENERATE_ENVIRONMENT_SCRIPT)\r
827 \r
828 #########################################################################\r
829 # SALOME_GENERATE_TESTS_ENVIRONMENT()\r
830\r
831 # USAGE: SALOME_GENERATE_TESTS_ENVIRONMENT(output)\r
832 #\r
833 # ARGUMENTS:\r
834 #   output [out] output environement variable.\r
835 #\r
836 # This macro generates <output> variable to use given environment to run some tests. \r
837 # Macro generates environement variable using previously created variables\r
838 # _${PROJECT_NAME}_EXTRA_ENV_<var>, where <var> is name of variable and\r
839 # _${PROJECT_NAME}_EXTRA_ENV (see marco SALOME_ACCUMULATE_ENVIRONMENT);\r
840 # and puts this variable into <output> argument.\r
841 #\r
842 MACRO(SALOME_GENERATE_TESTS_ENVIRONMENT output)\r
843  SET(_env)\r
844  SET(_WIN_LD_LIBRARY OFF)\r
845  FOREACH(_item ${_${PROJECT_NAME}_EXTRA_ENV})\r
846    IF(${_item} STREQUAL "LD_LIBRARY_PATH")\r
847      SET(_WIN_LD_LIBRARY ON)\r
848    ENDIF()\r
849    SET(_env_${_item})\r
850    FOREACH(_val ${_${PROJECT_NAME}_EXTRA_ENV_${_item}})\r
851      IF(WIN32)\r
852        STRING(REPLACE "/" "\\" _val "${_val}")\r
853        SET(_env_${_item} "${_val};${_env_${_item}}")\r
854      ELSE()\r
855        SET(_env_${_item} "${_val}:${_env_${_item}}")\r
856      ENDIF()\r
857    ENDFOREACH()\r
858  ENDFOREACH()\r
859 \r
860  IF(_WIN_LD_LIBRARY AND WIN32)\r
861    SET(_env_PATH "${_env_PATH}$ENV{LD_LIBRARY_PATH};${_env_LD_LIBRARY_PATH}")\r
862  ENDIF()\r
863 \r
864  IF(WIN32)\r
865    SET(sep ",")\r
866  ELSE()\r
867    SET(sep ";")\r
868  ENDIF()\r
869  \r
870  FOREACH(_item ${_${PROJECT_NAME}_EXTRA_ENV})\r
871    IF(WIN32)\r
872      IF(NOT ${_item} STREQUAL "LD_LIBRARY_PATH")\r
873        SET(_env "${_item}=$ENV{${_item}};${_env_${_item}}${sep}${_env}")\r
874      ENDIF()\r
875    ELSE()\r
876      STRING(REPLACE ";" ":" _iii "$ENV{${_item}}")\r
877      SET(_env "${_item}=${_iii}:${_env_${_item}}${sep}${_env}")\r
878    ENDIF()\r
879  ENDFOREACH()\r
880 \r
881  # Get module name as substring of "Salome<ModuleName>"\r
882  STRING(REGEX MATCH "^Salome" _is_salome_project ${PROJECT_NAME})\r
883  IF(_is_salome_project)\r
884    STRING(SUBSTRING "${PROJECT_NAME}" 6 -1 PRNAME) \r
885  ELSE()\r
886    SET(PRNAME ${PROJECT_NAME})\r
887  ENDIF()\r
888  SET(_env "${PRNAME}_ROOT_DIR=${CMAKE_INSTALL_PREFIX}${sep}${_env}")\r
889   \r
890  # Creating follow string for Windows environement:\r
891  # "VAR1_ENV=1\;2\;3\;...\;...\;...;VAR2_ENV=1\;2\;3\;...\;...\;...;VAR3_ENV=1\;2\;3\;...\;...\;...;..."\r
892  IF(WIN32)\r
893    STRING(REGEX REPLACE "\\\\*;" "\\\\;" _env "${_env}")\r
894    STRING(REGEX REPLACE "\\\\*;*," ";" _env "${_env}")\r
895  ENDIF()\r
896 \r
897  SET(${output} "${_env}")\r
898 \r
899 ENDMACRO(SALOME_GENERATE_TESTS_ENVIRONMENT) \r
900 \r
901 #########################################################################\r
902 # SALOME_APPEND_LIST_OF_LIST()\r
903\r
904 # USAGE: SALOME_APPEND_LIST_OF_LIST(result element_list)\r
905 #\r
906 # Build a list of lists. The element_list is first parsed to convert it \r
907 # from \r
908 #     a;b;c;d;e\r
909 # to \r
910 #     a,b,c,d,e\r
911 #\r
912 # It is then added to the big list 'result'. Hence 'result' looks like:\r
913 #     a,b,c,d,e;f,g,h; ...\r
914 #\r
915 MACRO(SALOME_APPEND_LIST_OF_LIST result element_list)\r
916   SET(_tmp_res)\r
917   STRING(REPLACE ";" "," _tmp_res "${${element_list}}")\r
918 \r
919   # Yet another CMake stupidity - LIST(LENGTH ";" var) returns 0\r
920   STRING(LENGTH result _list_len)\r
921   IF(NOT _list_len EQUAL 0)\r
922     SET(${result} "${${result}}${_tmp_res};")  # LIST(APPEND ...) doesn't handle well empty elements!?\r
923   ELSE()\r
924     SET(${result} "${_tmp_res};")              # to avoid redundant ';' at the beginning of the list\r
925   ENDIF()\r
926 \r
927 ENDMACRO(SALOME_APPEND_LIST_OF_LIST)\r
928 \r
929 #########################################################################\r
930 # SALOME_CONFIGURE_PREPARE()\r
931\r
932 # USAGE: SALOME_CONFIGURE_PREPARE(pkg1 pkg2 ...)\r
933 #\r
934 # Prepare the variable that will be used to configure the file Salome<MODULE>Config.cmake,\r
935 # namely:\r
936 #    - _PREREQ_LIST      : the list of level 1 external prerequisites\r
937 #    - _PREREQ_DIR_LIST  : their corresponding CMake directories (i.e. where the CMake configuration\r
938 #    file for this package can be found, if there is any!)\r
939 #    - _PREREQ_COMPO_LIST: the list of components requested when this package was invoked\r
940 #\r
941 # All this information is built from the package_list, the list of level 1 packages for this module.\r
942 # Only the packages found in CONFIG mode are retained.\r
943 #\r
944 MACRO(SALOME_CONFIGURE_PREPARE)\r
945   SET(_tmp_prereq "${ARGV}")\r
946   SET(_PREREQ_LIST)\r
947   SET(_PREREQ_DIR_LIST)\r
948   SET(_PREREQ_COMPO_LIST)\r
949   FOREACH(_prereq IN LISTS _tmp_prereq)\r
950     IF(${_prereq}_DIR)\r
951       SET(_PREREQ_LIST "${_PREREQ_LIST} ${_prereq}")\r
952       FILE(TO_CMAKE_PATH ${${_prereq}_DIR} CURR_DIR)\r
953       SET(_PREREQ_DIR_LIST "${_PREREQ_DIR_LIST} \"${CURR_DIR}\"")\r
954       SALOME_APPEND_LIST_OF_LIST(_PREREQ_COMPO_LIST Salome${_prereq}_COMPONENTS)\r
955     ENDIF()\r
956   ENDFOREACH()\r
957 ENDMACRO(SALOME_CONFIGURE_PREPARE)\r
958 \r
959 #######################################################################\r
960 #\r
961 # From a version string like "2.7.12+" extract the major, minor and patch number\r
962 # taking ONLY the numerical part.\r
963 # This macro was created to treat Ubuntu Python version number where the libs are\r
964 # version 2.7.12+ and the interp is 2.7.12 ...\r
965 #\r
966 MACRO(SALOME_EXTRACT_VERSION version_string major minor patch)\r
967   IF(${version_string} MATCHES "[0-9]+[^0-9]*\\.[0-9]+[^0-9]*\\.[0-9]+[^0-9]*")\r
968     STRING(REGEX REPLACE "^([0-9]+)[^0-9]*\\.[0-9]+[^0-9]*\\.[0-9]+[^0-9]*" "\\1" ${major} "${version_string}")\r
969     STRING(REGEX REPLACE "^[0-9]+[^0-9]*\\.([0-9]+)[^0-9]*\\.[0-9]+[^0-9]*" "\\1" ${minor} "${version_string}")\r
970     STRING(REGEX REPLACE "^[0-9]+[^0-9]*\\.[0-9]+[^0-9]*\\.([0-9]+)[^0-9]*" "\\1" ${patch} "${version_string}")\r
971   ELSE()\r
972     MESSAGE("MACRO(SALOME_EXTRACT_VERSION ${version_string} ${major} ${minor} ${patch}")\r
973     MESSAGE(FATAL_ERROR "Problem parsing version string, I can't parse it properly.")\r
974   ENDIF()\r
975 ENDMACRO(SALOME_EXTRACT_VERSION)\r