0

This is my CmakeLists.txt file:

cmake_minimum_required(VERSION 3.5)

project(TestProject VERSION 0.1 LANGUAGES CXX)

set(CMAKE_AUTOUIC ON)
set(CMAKE_AUTOMOC ON)
set(CMAKE_AUTORCC ON)

set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)

find_package(QT NAMES Qt6 Qt5 REQUIRED COMPONENTS Widgets Network LinguistTools)
find_package(Qt${QT_VERSION_MAJOR} REQUIRED COMPONENTS Widgets Network LinguistTools)
include(ExternalProject)
add_subdirectory (dep/socketio)
ExternalProject_Add(HDiffPatch
        SOURCE_DIR ${CMAKE_SOURCE_DIR}/dep/hdiffpatch
        DOWNLOAD_COMMAND ""
        UPDATE_COMMAND ""
        CMAKE_ARGS
        -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR>
        -DCMAKE_CXX_FLAGS=${CMAKE_CXX_FLAGS}
        -DCMAKE_C_FLAGS=${CMAKE_C_FLAGS}
        -DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE}
        ${USE_PROJECT_CMAKE_MODULE_PATH}
        INSTALL_COMMAND "make LZMA=0 ZSTD=0 MD5=0")

add_definitions(-DQT_NO_KEYWORDS)

set(TS_FILES TestProject_en_US.ts)

set(PROJECT_SOURCES
        main.cpp
        TestProject.cpp
        TestProject.h
        TestProject.ui
        components/popupmenu.h
        components/popupmenu.cpp
        ${TS_FILES}
)

if(${QT_VERSION_MAJOR} GREATER_EQUAL 6)
    qt_add_executable(TestProject
        MANUAL_FINALIZATION
        ${PROJECT_SOURCES}
        login.h login.cpp login.ui
        resources.qrc
    )
# Define target properties for Android with Qt 6 as:
#    set_property(TARGET TestProject APPEND PROPERTY QT_ANDROID_PACKAGE_SOURCE_DIR
#                 ${CMAKE_CURRENT_SOURCE_DIR}/android)
# For more information, see https://doc.qt.io/qt-6/qt-add-executable.html#target-creation

    qt_create_translation(QM_FILES ${CMAKE_SOURCE_DIR} ${TS_FILES})
else()
    if(ANDROID)
        add_library(TestProject SHARED
            ${PROJECT_SOURCES}
        )
# Define properties for Android with Qt 5 after find_package() calls as:
#    set(ANDROID_PACKAGE_SOURCE_DIR "${CMAKE_CURRENT_SOURCE_DIR}/android")
    else()
        add_executable(TestProject
            ${PROJECT_SOURCES}
        )
    endif()

    qt5_create_translation(QM_FILES ${CMAKE_SOURCE_DIR} ${TS_FILES})
endif()

target_link_libraries(TestProject PRIVATE Qt${QT_VERSION_MAJOR}::Widgets Qt${QT_VERSION_MAJOR}::Network sioclient_tls)

# Qt for iOS sets MACOSX_BUNDLE_GUI_IDENTIFIER automatically since Qt 6.1.
# If you are developing for iOS or macOS you should consider setting an
# explicit, fixed bundle identifier manually though.
if(${QT_VERSION} VERSION_LESS 6.1.0)
  set(BUNDLE_ID_OPTION MACOSX_BUNDLE_GUI_IDENTIFIER com.example.TestProject)
endif()
set_target_properties(TestProject PROPERTIES
    ${BUNDLE_ID_OPTION}
    MACOSX_BUNDLE_BUNDLE_VERSION ${PROJECT_VERSION}
    MACOSX_BUNDLE_SHORT_VERSION_STRING ${PROJECT_VERSION_MAJOR}.${PROJECT_VERSION_MINOR}
    MACOSX_BUNDLE TRUE
    WIN32_EXECUTABLE TRUE
)


include(GNUInstallDirs)
install(TARGETS TestProject
    BUNDLE DESTINATION .
    LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
    RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
)

if(QT_VERSION_MAJOR EQUAL 6)
    qt_finalize_executable(TestProject)
endif()

As you can see this is a C++ Cmake Qt Project.

I want to add external project to my project. That external project is this one. As you can see the external project uses Makefile to build itself but not cmake. In their Readme it says to build the project run make LZMA=0 ZSTD=0 MD5=0 to build it.

If I build it manually there is no issues.

To add this project as external project to my project I have added these lines:

include(ExternalProject)
ExternalProject_Add(HDiffPatch
        SOURCE_DIR ${CMAKE_SOURCE_DIR}/dep/hdiffpatch
        DOWNLOAD_COMMAND ""
        UPDATE_COMMAND ""
        CMAKE_ARGS
        -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR>
        -DCMAKE_CXX_FLAGS=${CMAKE_CXX_FLAGS}
        -DCMAKE_C_FLAGS=${CMAKE_C_FLAGS}
        -DCMAKE_BUILD_TYPE=${CMAKE_BUILD_TYPE}
        ${USE_PROJECT_CMAKE_MODULE_PATH}
        INSTALL_COMMAND "make LZMA=0 ZSTD=0 MD5=0")

When I try from Clion to build the target HDiffPatch I get this error:

cmake-build-debug --target HDiffPatch -- -j 10
[ 12%] Creating directories for 'HDiffPatch'
[ 25%] No download step for 'HDiffPatch'
[ 37%] No update step for 'HDiffPatch'
[ 50%] No patch step for 'HDiffPatch'
[ 62%] Performing configure step for 'HDiffPatch'
CMake Error: The source directory "/Users/venelin/Development/BeastBurst-Launcher/dep/hdiffpatch" does not appear to contain CMakeLists.txt.
Specify --help for usage, or press the help button on the CMake GUI.
make[3]: *** [HDiffPatch-prefix/src/HDiffPatch-stamp/HDiffPatch-configure] Error 1
make[2]: *** [CMakeFiles/HDiffPatch.dir/all] Error 2
make[1]: *** [CMakeFiles/HDiffPatch.dir/rule] Error 2
make: *** [HDiffPatch] Error 2

How can I fix this issue and how can I link HDiffPatch so that I can use it as library in my project and execute it's functionalities from my project codebase ?

Venelin
  • 2,905
  • 7
  • 53
  • 117
  • Note, that if a directory specified with `SOURCE_DIR` argument already exists, download and update steps are disabled automatically. No needs to explicitly set DOWNLOAD_COMMAND and UPDATE_COMMAND variables in that case. – Tsyvarev Aug 15 '23 at 20:55

1 Answers1

0

Standard steps of ExternalProject are represented by CONFIGURE_COMMAND, BUILD_COMMAND, INSTALL_COMMAND options. By default, each such step calls cmake with appropriate arguments. For build a non-CMake project, you need to redefine these options to required command lines. E.g.

ExternalProject_Add(HDiffPatch
        SOURCE_DIR ${CMAKE_SOURCE_DIR}/dep/hdiffpatch
        # Tell CMake that project doesn't require a separate build directory:
        # all COMMANDs below will be run from the source directory itself
        BUILD_IN_SOURCE TRUE
        # Disable configuration: in most cases it is about calling
        # 'configure' script or similar, which is not needed in your case.
        CONFIGURE_COMMAND ""
        # All actions are performed in the build step
        BUILD_COMMAND "make LZMA=0 ZSTD=0 MD5=0"
        # Disable installation step too.
        INSTALL_COMMAND "")

As for using artifacts of External Project in your main project, such usage doesn't depends on the type of External Project (CMake or non-CMake) and explained e.g. in that answer.

# Extract source directory which has been used for the External Project.
ExternalProject_Get_Property(HDiffPatch SOURCE_DIR)

# Needed include directories are somewhere inside the source directory
target_include_directories(TestProject PRIVATE ${SOURCE_DIR}/path/to/include)

# Needed libraries are produced somewhere inside the source directory too
target_link_libraries(TestProject PRIVATE ${SOURCE_DIR}/path/to/lib1)

# Allow TestProject to be built only after all steps in the External project are completed.
add_dependencies(TestProject HDiffPatch)
Tsyvarev
  • 60,011
  • 17
  • 110
  • 153