Avoid creation of cmake_install.cmake file - cmake

I have several small personal projects that I execute directly from the build directory, and never are going "to be installed". Is there a way to avoid the creation of the cmake_install.cmake file in my build directory each time I run cmake?
I have seen the install documentation that explain how to configure install, but not how to disable the install procedure. Is there a cmake command line argument or cmake rule to avoid the creation of file cmake_install.cmake?

Add this line to your project's CMakeLists.txt:
set(CMAKE_SKIP_INSTALL_RULES True)
This is a documented CMake variable.

Related

CMake: How can I add a search path for include() from the environment?

I try to create a collection of CMake scripts that are supposed to provide some useful macros and functions for our group of developers and all the projects we're working on. These scripts should be rolled out to all development machines (Win10 & Centos Linux) and the top-level CMakeLists.txt of the projects can include this collection.
From what I read from the CMake docs, include() is what should be used to import these scripts. But, of course, CMake doesn't know about the location on the file system. The documentation points to CMAKE_MODULE_PATH, but I couldn't figure out a way to set it from "outside" on a global scope, e.g. an environment variable or a CMake configuration value. Setting it from within a project's CMake file would drop portability, as especially on Windows users potentially could choose the install directory of the scripts.
I also don't want to deploy the script collection into CMake's installation directory. Although it would work, it feels dirty to mix up my own scripts with the ones from the CMake distribution.
I could use find_package() instead and also provide a package config file and use the CMAKE_PREFIX_PATH environment variable. But from my understanding of the docu this is meant to be for build dependencies, e.g. libraries.
I also found questions similar to mine here and in other places, but they usually were about importing external projects for building the own one ( -> find_package()). And, of course, about include directories for the compilation process. If I just didn't found the proper question & answer, please point me there.
So, what is the best/proper way to make CMake aware of my script collection? Preferably in a way that just a call to include() is required in a project's CMakeLists.txt.
but I couldn't figure out a way to set it from "outside" on a global scope, e.g. an environment variable or a CMake configuration value.
Just cmake -D CMAKE_MODULE_PATH=/some/path. Works for me:
$ cd /tmp; echo "include(ulumulu)" > CMakeLists.txt ; strace -e trace=file cmake -D CMAKE_MODULE_PATH=/some/path . |& grep access | grep ulumulu
access("/some/path/ulumulu.cmake", R_OK) = -1 ENOENT (No such file or directory)
access("/usr/share/cmake-3.19/Modules/ulumulu.cmake", R_OK) = -1 ENOENT (No such file or directory)
access("/tmp/ulumulu", R_OK) = -1 ENOENT (No such file or directory)
How can I add a search path for include() from the environment?
I would setup my own logic. As simplest as include($ENV{SEARCH_IN_THIS_PATH}), but way better would be with cmake -D PATH_TO_MY_LIBRARY=some_path and then include(${PATH_TO_MY_LIBRARY}).
I could use find_package() instead and also provide a package config file and use the CMAKE_PREFIX_PATH environment variable. But from my understanding of the docu this is meant to be for build dependencies, e.g. libraries.
And module mode find_package( ... MODULE) is for finding modules. I would use it. And I would use it also not for libraries.
what is the best/proper way to make CMake aware of my script collection?
Install your script at /usr/share/cmake/ path on linux and I think c:/Program Files/CMake/share/cmake on windows (I have no experience in windows) and use find_package(the_library MODULE).
If not, I recommend just use find_package anyway and install your Find*.cmake file to <prefix>/<name>/cmake/.

CMake - how to call installation commands from the top level AFTER these commands from subdirectories?

My project contains a top-level CMakeLists.txt, which has this structure:
add_subdirectory(piece1)
add_subdirectory(piece2)
# --- etc.
install(CODE "execute_process(...)")
When I do make install all the installation commands from this file are called first - and it's not good for me, cause I need to setup symlinks and to do other steps, which require presence of files in destination directories.
So, I want to tell CMake to call install commands from this file after all the install commands from all my subdirectories.
How to do that?
Just move install(CODE) into subdirectory (but add this subdirectory at the end ot the script, after others add_subdirectory calls).
I know no other ways to force CMake to execute your installation code after all others.
See also my answer to the related question.

cpack and install(CODE ...) - CPACK_PACKAGING_INSTALL_PREFIX vs CMAKE_INSTALL_PREFIX

as a "post-install hook" I need to execute an install command like
install(CODE "execute_process(COMMAND some_command ${CMAKE_INSTALL_PREFIX}/some_folder"))
which creates a file in some_folder based on the files which were previously installed into some_folder (it compiles an index/cache of those files).
This works fine for the install target, however as soon as using cpack ${CMAKE_INSTALL_PREFIX} is not the correct location anymore.
Is there a variable like ${CMAKE_CURRENT_INSTALL_PREFIX} that always points towards the current installation directory, regardless of wether the default install target or cpack is used and can be used for this purpose?
The only alternative I see is to try to execute the command at an earlier stage on the original files, create a temporary file and install the temporary file. Unfortunately this is much more error prone, as some_command should be run on the "final" files after installation (in order to create a valid cache)
The answer turns out to be extremely simple (kudos to Nils Gladitz from IRC):
Escaping the variable ${CMAKE_INSTALL_PREFIX} with a backslash delays its expansion until install time at which it holds the correct value also for installs via CPack:
install(CODE "execute_process(COMMAND some_command \${CMAKE_INSTALL_PREFIX}/some_folder"))

CMake rpm installing a file in /etc/init.d

I want to install a file in
/etc/init.d directory
I have written code
INSTALL(FILES ${CMAKE_SOURCE_DIR}/app/script/appd DESTINATION /etc/init.d/appd)
but when I run packing code using cmake I get error
CMake Error at /home/vivek/workspace/app/build/standalone/cmake_install.cmake:54 (FILE):
file cannot create directory: /etc/init.d/appd. Maybe need
administrative privileges.
How can I set cmake to install a file inside /etc/init.d directory ?
You can do this, but you may need to explicitly set:
set(CPACK_SET_DESTDIR ON)
prior to:
include(CPack)
in your CMakeLists.txt file. (You will need to do this only for older versions on CMake/CPack, prior to 2.8.3)
The reason you need to do this is that you are specifying a full path name as the DESTINATION of one of your installed files. In order to do that properly in the packing phase, CPack needs to use a DESTDIR environment variable in its "make install" call.
We didn't do this automatically by default for backwards compatibility reasons.
But then, this bug was fixed in version 2.8.3 so that it could be done transparently and automatically with install rules that use full path names:
http://public.kitware.com/Bug/view.php?id=7000
Hopefully, you can use either CPACK_SET_DESTDIR to ON for your rpm packages, OR use a more recent version of CMake/CPack that includes the automatic fix.
You can't. Only thing you can do is to ask user to run make install for your app with administrative priveleges.
Also, you can try detecting presense of sudo command and add_custom_command() which would install your files with sudo.

CMake Configure File Build Rule

I'm using CMake for my build system and in the project, we will have a bunch of configuration files. Some of them will just need to be copied over, some will need to be modified per computer. I'm currently using CMake's "configure_file" command to copy/replace parts of the file. This works great, and I love how I can use any variable from CMake in the configure routine.
But if you change the original file, CMake will not pick this up and you have to rerun cmake for it to configure the directory. When I run "make", I want it to pick up that I've changed the file and rerun configure.
It will also reconfigure files always, even if the file it is overwriting is newer. I want it to act like a custom target.
I think I can do this with add_custom_command, but I don't think I can run a CMake command from add_custom_command. So is there anyway to duplicate the behaviour that configure_file does in CMake?
I recently upgraded to CMake 2.8. It seems like it automatically has the exact behavior I wanted.
I do not think this has an easy answer. I see two options:
To trigger a re-run of cmake if an input changes, you might be able to make your input file depend on CMakeLists.txt.
To run a cmake command as part of and add_custom_command, there is the variable ${CMAKE_COMMAND}, which will give you the path to the running cmake. You could, as part of the configure step, generate a fragment of CMake code (that calls configure_file) that is invoked using the -P option. Either pass substitutions on the command line using -D, or write them to the CMake fragment.