improve cmake Cython wrapper scripts to be usable in other projects
							parent
							
								
									f154be176f
								
							
						
					
					
						commit
						70552e9f6d
					
				|  | @ -18,6 +18,7 @@ install(FILES | |||
|   GtsamMakeConfigFile.cmake | ||||
|   GtsamMatlabWrap.cmake | ||||
|   GtsamPythonWrap.cmake | ||||
|   GtsamCythonWrap.cmake | ||||
|   GtsamTesting.cmake | ||||
|   README.html | ||||
|   DESTINATION "${SCRIPT_INSTALL_DIR}/GTSAMCMakeTools") | ||||
|  |  | |||
|  | @ -4,76 +4,72 @@ if(NOT GTSAM_CYTHON_INSTALL_PATH) | |||
| 	set(GTSAM_CYTHON_INSTALL_PATH "${CMAKE_INSTALL_PREFIX}/gtsam_cython") | ||||
| endif() | ||||
| 
 | ||||
| # User-friendly wrapping function.  Builds a mex module from the provided | ||||
| # interfaceHeader.  For example, for the interface header gtsam.h, | ||||
| # User-friendly Cython wrapping and installing function.   | ||||
| # Builds a Cython module from the provided interface_header.   | ||||
| # For example, for the interface header gtsam.h, | ||||
| # this will build the wrap module 'gtsam'. | ||||
| # | ||||
| # Arguments: | ||||
| # | ||||
| # interfaceHeader:  The relative path to the wrapper interface definition file. | ||||
| # linkLibraries:    Any *additional* libraries to link.  Your project library | ||||
| #                   (e.g. `lba`), libraries it depends on, and any necessary | ||||
| #                   MATLAB libraries will be linked automatically.  So normally, | ||||
| #                   leave this empty. | ||||
| # extraIncludeDirs: Any *additional* include paths required by dependent | ||||
| #                   libraries that have not already been added by | ||||
| #                   include_directories.  Again, normally, leave this empty. | ||||
| function(wrap_and_install_library_cython interfaceHeader linkLibraries extraIncludeDirs) | ||||
| 	wrap_library_internal_cython("${interfaceHeader}" "${linkLibraries}" "${extraIncludeDirs}") | ||||
| 	install_wrapped_library_internal_cython("${interfaceHeader}") | ||||
| # interface_header:  The relative path to the wrapper interface definition file. | ||||
| # extra_imports: extra header to import in the Cython pxd file.  | ||||
| #                For example, to use Cython gtsam.pxd in your own module,  | ||||
| #				 use "from gtsam cimport *" | ||||
| # setup_py_in_path: Path to the setup.py.in config file, which will be converted | ||||
| #                   to setup.py file by cmake and used to compile the Cython module | ||||
| #                   by invoking "python setup.py build_ext --inplace" | ||||
| # install_path: destination to install the library | ||||
| function(wrap_and_install_library_cython interface_header extra_imports setup_py_in_path install_path) | ||||
| 	# Paths for generated files | ||||
| 	get_filename_component(module_name "${interface_header}" NAME_WE) | ||||
| 	set(generated_files_path "${PROJECT_BINARY_DIR}/cython/${module_name}") | ||||
| 	wrap_library_cython("${interface_header}" "${generated_files_path}" "${extra_imports}" "${setup_py_in_path}") | ||||
| 	install_cython_wrapped_library("${interface_header}" "${generated_files_path}" "${install_path}") | ||||
| endfunction() | ||||
| 
 | ||||
| 
 | ||||
| # Internal function that wraps a library and compiles the wrapper | ||||
| function(wrap_library_internal_cython interfaceHeader linkLibraries extraIncludeDirs) | ||||
| function(wrap_library_cython interface_header generated_files_path extra_imports setup_py_in_path) | ||||
| 	# Wrap codegen interface | ||||
|     #usage: wrap --cython interfacePath moduleName toolboxPath headerPath | ||||
|     #  interfacePath : *absolute* path to directory of module interface file | ||||
|     #  moduleName    : the name of the module, interface file must be called moduleName.h | ||||
|     #  toolboxPath   : the directory in which to generate the wrappers | ||||
|     #  headerPath    : path to matlab.h  | ||||
| 	# Extract module path and name from interface header file name | ||||
| 	get_filename_component(interface_header "${interface_header}" ABSOLUTE) | ||||
| 	get_filename_component(module_path "${interface_header}" PATH) | ||||
| 	get_filename_component(module_name "${interface_header}" NAME_WE) | ||||
| 
 | ||||
| 	set(generated_cpp_file "${generated_files_path}/${module_name}.cpp") | ||||
| 	 | ||||
| 	# Extract module name from interface header file name | ||||
| 	get_filename_component(interfaceHeader "${interfaceHeader}" ABSOLUTE) | ||||
| 	get_filename_component(modulePath "${interfaceHeader}" PATH) | ||||
| 	get_filename_component(moduleName "${interfaceHeader}" NAME_WE) | ||||
| 	 | ||||
| 	# Paths for generated files | ||||
| 	set(generated_files_path "${PROJECT_BINARY_DIR}/cython/${moduleName}") | ||||
| 	set(generated_cpp_file "${generated_files_path}/${moduleName}.cpp") | ||||
| 	 | ||||
| 	message(STATUS "Building wrap module ${moduleName}") | ||||
| 	message(STATUS "Building wrap module ${module_name}") | ||||
| 	 | ||||
| 	# Set up generation of module source file | ||||
| 	file(MAKE_DIRECTORY "${generated_files_path}") | ||||
| 	configure_file(../cython/setup.py.in ${generated_files_path}/setup.py) | ||||
| 	configure_file(${setup_py_in_path}/setup.py.in ${generated_files_path}/setup.py) | ||||
| 	add_custom_command( | ||||
| 		OUTPUT ${generated_cpp_file} | ||||
| 		DEPENDS ${interfaceHeader} wrap ${module_library_target}  | ||||
| 		DEPENDS ${interface_header} wrap  | ||||
|         COMMAND  | ||||
|             wrap --cython | ||||
|             ${modulePath} | ||||
|             ${moduleName}  | ||||
|             ${module_path} | ||||
|             ${module_name}  | ||||
|             ${generated_files_path}  | ||||
| 			. | ||||
| 			"${extra_imports}" | ||||
| 			&& python setup.py build_ext --inplace | ||||
| 		VERBATIM | ||||
| 		WORKING_DIRECTORY ${generated_files_path}) | ||||
| 		 | ||||
| 	# Set up building of mex module | ||||
| 	add_custom_target(${moduleName}_cython_wrapper ALL DEPENDS ${generated_cpp_file} ${interfaceHeader}) | ||||
|     add_custom_target(wrap_${moduleName}_cython_distclean  | ||||
| 	add_custom_target(${module_name}_cython_wrapper ALL DEPENDS ${generated_cpp_file} ${interface_header}) | ||||
|     add_custom_target(wrap_${module_name}_cython_distclean  | ||||
| 	    COMMAND cmake -E remove_directory ${generated_files_path}) | ||||
| endfunction() | ||||
| 
 | ||||
| # Internal function that installs a wrap toolbox | ||||
| function(install_wrapped_library_internal_cython interfaceHeader) | ||||
| 	get_filename_component(moduleName "${interfaceHeader}" NAME_WE) | ||||
| 	set(generated_files_path "${PROJECT_BINARY_DIR}/cython/${moduleName}") | ||||
| function(install_cython_wrapped_library interface_header generated_files_path install_path) | ||||
| 	get_filename_component(module_name "${interface_header}" NAME_WE) | ||||
| 
 | ||||
|     # NOTE: only installs .pxd and .pyx and binary files (not .cpp) - the trailing slash on the directory name | ||||
| 	# here prevents creating the top-level module name directory in the destination. | ||||
| 	message(STATUS "Installing Cython Toolbox to ${GTSAM_CYTHON_INSTALL_PATH}") | ||||
| 	message(STATUS "Installing Cython Toolbox to ${install_path}") #${GTSAM_CYTHON_INSTALL_PATH}") | ||||
| 	message(generated_files_path: "${generated_files_path}") | ||||
| 	if(GTSAM_BUILD_TYPE_POSTFIXES) | ||||
| 		foreach(build_type ${CMAKE_CONFIGURATION_TYPES}) | ||||
| 			string(TOUPPER "${build_type}" build_type_upper) | ||||
|  | @ -83,9 +79,9 @@ function(install_wrapped_library_internal_cython interfaceHeader) | |||
| 				set(build_type_tag "${build_type}") | ||||
| 			endif() | ||||
| 			# Split up filename to strip trailing '/' in GTSAM_CYTHON_INSTALL_PATH if there is one | ||||
| 			get_filename_component(location "${GTSAM_CYTHON_INSTALL_PATH}" PATH) | ||||
| 			get_filename_component(name "${GTSAM_CYTHON_INSTALL_PATH}" NAME) | ||||
| 			install(DIRECTORY "${generated_files_path}/../" DESTINATION "${location}/${name}${build_type_tag}"  | ||||
| 			get_filename_component(location "${install_path}" PATH) | ||||
| 			get_filename_component(name "${install_path}" NAME) | ||||
| 			install(DIRECTORY "${generated_files_path}/" DESTINATION "${location}/${name}${build_type_tag}"  | ||||
| 					CONFIGURATIONS "${build_type}"  | ||||
| 					PATTERN "build" EXCLUDE | ||||
| 					PATTERN "CMakeFiles" EXCLUDE | ||||
|  | @ -95,7 +91,7 @@ function(install_wrapped_library_internal_cython interfaceHeader) | |||
| 					PATTERN "*.py" EXCLUDE) | ||||
| 		endforeach() | ||||
| 	else() | ||||
| 		install(DIRECTORY "${generated_files_path}/../" DESTINATION ${GTSAM_CYTHON_INSTALL_PATH}  | ||||
| 		install(DIRECTORY "${generated_files_path}/" DESTINATION ${install_path}  | ||||
| 				PATTERN "build" EXCLUDE | ||||
| 				PATTERN "CMakeFiles" EXCLUDE | ||||
| 				PATTERN "Makefile" EXCLUDE | ||||
|  |  | |||
|  | @ -172,5 +172,9 @@ if (GTSAM_INSTALL_CYTHON_TOOLBOX) | |||
|     include(GtsamCythonWrap) | ||||
| 
 | ||||
|     # Wrap | ||||
|     wrap_and_install_library_cython(../cython/gtsam.h "${GTSAM_ADDITIONAL_LIBRARIES}" "") | ||||
|     wrap_and_install_library_cython("../cython/gtsam.h" # interface_header | ||||
|                                     ""                  # extra imports   | ||||
|                                     "../cython"         # path to setup.py.in  | ||||
|                                     "${GTSAM_CYTHON_INSTALL_PATH}/gtsam" # install path | ||||
|                                     ) | ||||
| endif () | ||||
		Loading…
	
		Reference in New Issue