Thor-x86_128
Thor-x86_128

Reputation: 361

How do I ask CMake to copy include directory while running "cmake install"?

Previously, I'm looking for this kind of question but none of them are working as example this thread and this one.

Currently, I'm creating a C library which supposed to outputs a shared library (*.so or *.dll) file and multiple *.h files in a ./include directory. The shared library is successfully built and installed to /usr/local/lib. However, I have no idea how do I tell CMake to copy *.h files to the correct destination as below.

I know I could workaround this by copying those *.h with Python script or using if-else logic on CMake. But at least tell me if there is a feature in CMake for doing that thing. Thanks!

Here's my CMakeLists.txt:

cmake_minimum_required(VERSION 3.12)
project (
  learn_c_library
  VERSION 1.0.0
  LANGUAGES C
)

# Specify CMake build and output directory
set(CMAKE_BINARY_DIR "${PROJECT_SOURCE_DIR}/.cmake")
set(CMAKE_LIBRARY_OUTPUT_DIRECTORY "${PROJECT_SOURCE_DIR}/out")

# Use every .c file inside ./src
file(GLOB_RECURSE MY_SOURCE_PATH "src/*")

add_library(
  ${PROJECT_NAME} SHARED
  ${MY_SOURCE_PATH}
)
include_directories(
  ${PROJECT_NAME}
  "include/"
)

# Allows "make install" to install shared library
install(TARGETS ${PROJECT_NAME})

Upvotes: 0

Views: 1686

Answers (2)

Alex Reinking
Alex Reinking

Reputation: 20026

This answer improves on your answer:

cmake_minimum_required(VERSION 3.14)

# ...

include(GNUInstallDirs)

install(DIRECTORY "include/"
        TYPE INCLUDE
        COMPONENT MyProj_Development)

The GNUInstallDirs module provides standard configuration points for customizing a project's install layout. These variables should essentially always be used instead of hardcoding path/directory names.

The TYPE INCLUDE argument to install() was introduced in CMake 3.14 and uses GNUInstallDirs's CMAKE_INSTALL_INCLUDEDIR variable to determine the destination.

Finally, and especially if your project is a library, all your install() rules should be given a COMPONENT argument to allow splitting files between runtime and development packages (and potentially others like documentation and architecture-independent data files).

Upvotes: 2

Thor-x86_128
Thor-x86_128

Reputation: 361

After days of fiddling CMake, finally I found the solution!

Let's assume you store your public *.h inside ./include directory, then here's the syntax for installing your *.h files to your machine:

install(
  DIRECTORY
    "include/" # Your global headers location in the project
  DESTINATION
    include # This is your system's default "include" location
)

I got the solution from here with usr/myproject replaced to be include

Upvotes: 0

Related Questions