CMake shorten build paths

CMake can be configured to use shorter paths for build paths, which is important for large or complex projects on Windows where the 260 character path limit is a problem for some tools. This is done via CMAKE_INTERMEDIATE_DIR_STRATEGY which is a CMake environment variable as well as a CMake command-line option. The default is to use full paths for human readability, but for those occasions where the path length is a problem, this option can be set to SHORT to use shorter paths.

This example below is contrived to use a long source file path - the problem in practice comes from nested dependencies and build directories, which can easily exceed the 260 character limit on Windows when building a project with CMake. However, this example still demonstrates the issue and the solution with the shorten build path option.

cmake_minimum_required(VERSION 4.2)

project(soLong LANGUAGES CXX)

# make a long path to demonstrate the issue
set(long_path "${CMAKE_BINARY_DIR}/this/is/a/very/long/path/that/will/exceed/the/260/character/limit/on/windows/when/building/a/project/with/cmake/lets/see/if/it/works/with/the/shorten/build/path/option/just/to/make/sure/it/is/long/enough/to/exceed/the/limit/we/need/to/make/sure/it/is/long/enough/to/exceed/the/limit/")

string(LENGTH "${long_path}" L)

message(STATUS "Long path length: ${L} characters")
message(STATUS "CMAKE_INTERMEDIATE_DIR_STRATEGY: ${CMAKE_INTERMEDIATE_DIR_STRATEGY}")

set(CMAKE_EXPORT_COMPILE_COMMANDS ON)
message(STATUS "See file ${CMAKE_BINARY_DIR}/compile_commands.json for the compile commands with the long path")

file(MAKE_DIRECTORY "${long_path}")

file(GENERATE OUTPUT "${long_path}/main.cpp" CONTENT "int main() { return 0; }")

add_executable(soLong "${long_path}/main.cpp")

Compare the -o flag parameter between these two commands. The SHORT will be much shorter than FULL.

cmake -Bbuild -DCMAKE_INTERMEDIATE_DIR_STRATEGY=SHORT && cat build/compile_commands.json
cmake -Bbuild -DCMAKE_INTERMEDIATE_DIR_STRATEGY=FULL && cat build/compile_commands.json