diff --git a/cmake/modules/NativeExecutable.cmake b/cmake/modules/NativeExecutable.cmake new file mode 100644 index 0000000000..6f1f6c89a3 --- /dev/null +++ b/cmake/modules/NativeExecutable.cmake @@ -0,0 +1,49 @@ +# Allow to easily build native executable. +# Useful for cross compilation. + +# If we are cross compiling, create a directory for native build. +set(NATIVE_BUILD_DIR "${CMAKE_BINARY_DIR}/native" CACHE PATH "Path to the native build directory") +set(NATIVE_BINARY_DIR "${NATIVE_BUILD_DIR}/bin" CACHE PATH "Path to the native binary directory") +set(NATIVE_BUILD_TARGET "${NATIVE_BUILD_DIR}/CMakeCache.txt") + +if(CMAKE_CROSSCOMPILING AND NOT TARGET native-cmake-build) + find_program(NINJA "ninja") + + file(MAKE_DIRECTORY ${NATIVE_BUILD_DIR}) + add_custom_command( + OUTPUT ${NATIVE_BUILD_TARGET} + COMMAND ${CMAKE_COMMAND} + -GNinja + "${CMAKE_SOURCE_DIR}" + -DCMAKE_RUNTIME_OUTPUT_DIRECTORY:PATH=${NATIVE_BINARY_DIR} + WORKING_DIRECTORY ${NATIVE_BUILD_DIR} + VERBATIM USES_TERMINAL + ) + + add_custom_target(native-cmake-build DEPENDS ${NATIVE_BUILD_TARGET}) +endif() + +macro(add_native_executable NAME) + if(CMAKE_CROSSCOMPILING) + set(NATIVE_BINARY "${NATIVE_BINARY_DIR}/${NAME}") + add_custom_target("build-native-${NAME}" + COMMAND ${NINJA} ${NAME} + DEPENDS ${NATIVE_BUILD_TARGET} + BYPRODUCTS ${NATIVE_BINARY} + WORKING_DIRECTORY ${NATIVE_BUILD_DIR} + VERBATIM USES_TERMINAL + ) + + add_executable(${NAME} IMPORTED) + add_dependencies(${NAME} "build-native-${NAME}") + set_property(TARGET ${NAME} PROPERTY IMPORTED_LOCATION ${NATIVE_BINARY}) + else() + add_executable(${NAME} EXCLUDE_FROM_ALL ${ARGN}) + endif(CMAKE_CROSSCOMPILING) +endmacro(add_native_executable) + +function(native_target_include_directories) + if(NOT CMAKE_CROSSCOMPILING) + target_include_directories(${ARGN}) + endif(NOT CMAKE_CROSSCOMPILING) +endfunction(native_target_include_directories) diff --git a/src/univalue/CMakeLists.txt b/src/univalue/CMakeLists.txt index 8a048cb904..0888cafc34 100644 --- a/src/univalue/CMakeLists.txt +++ b/src/univalue/CMakeLists.txt @@ -1,59 +1,54 @@ # Copyright (c) 2017 The Bitcoin developers cmake_minimum_required(VERSION 3.1) project(univalue) option(UNIVALUE_BUILD_TESTS "Build univalue's unit tests" ON) # TODO: Version info add_library(univalue lib/univalue.cpp lib/univalue_get.cpp lib/univalue_read.cpp lib/univalue_write.cpp ) target_include_directories(univalue PUBLIC include PRIVATE lib ) if(UNIVALUE_BUILD_TESTS) include(TestSuite) create_test_suite(univalue) function(create_univalue_test NAME FILES) add_test_to_suite(univalue ${NAME} ${FILES}) target_link_libraries(${NAME} univalue) endfunction() create_univalue_test(unitester_test test/unitester.cpp) target_compile_definitions(unitester_test PUBLIC JSON_TEST_SRC="${PROJECT_SOURCE_DIR}/test" ) create_univalue_test(no_nul_test test/no_nul.cpp) create_univalue_test(object_test test/object.cpp) # test_json is not meant to run in an automated test suite. add_executable(json_test EXCLUDE_FROM_ALL test/test_json.cpp) target_link_libraries(json_test univalue) add_dependencies(check-univalue json_test) endif(UNIVALUE_BUILD_TESTS) # Generate lib/univalue_escapes.h -add_executable(univalue_gen gen/gen.cpp) -target_include_directories(univalue_gen PUBLIC include) - -file(MAKE_DIRECTORY ${CMAKE_CURRENT_BINARY_DIR}/lib) -add_custom_command( - OUTPUT ${CMAKE_CURRENT_BINARY_DIR}/lib/univalue_escapes.h - COMMAND univalue_gen > ${CMAKE_CURRENT_BINARY_DIR}/lib/univalue_escapes.h - DEPENDS univalue_gen ${CMAKE_CURRENT_SOURCE_DIR}/lib/univalue_escapes.h -) +include(NativeExecutable) +add_native_executable(univalue_gen gen/gen.cpp) +native_target_include_directories(univalue_gen PUBLIC include) + +# Custom target to regenerate univalue_escapes.h add_custom_target(generate_univalue_escapes_h - DEPENDS - ${CMAKE_CURRENT_BINARY_DIR}/lib/univalue_escapes.h + COMMAND univalue_gen > ${CMAKE_CURRENT_SOURCE_DIR}/lib/univalue_escapes.h )