How to put a result file to any subdirectory

I try to compile my Cortex-M0 project with CMake and arm-none-eabi-gcc (mingw32-make as make).
Everything is Ok, I get my hex and binary as result, but I want to have them not in the main directory with CMakeLists.txt, but in the separate directory, “bin” for example.
I’ve found, that CMAKE_RUNTIME_OUTPUT_DIRECTORY must do the thing, but it doesn’t work properly.
I try to define it within my CMakeLists.txt:

set(CMAKE_RUNTIME_OUTPUT_DIRECTORY bin)

But I get this error during the linking:

[100%] Linking C executable bin\xxx.out
arm-none-eabi-size: ‘xxx.out’: No such file
mingw32-make[2]: *** [CMakeFiles\xxx.out.dir\build.make:913: bin/xxx.out] Error 1
mingw32-make[2]: *** Deleting file ‘bin/xxx.out’
mingw32-make[1]: *** [CMakeFiles\Makefile2:82: CMakeFiles/xxx.out.dir/all] Error 2
mingw32-make: *** [Makefile:90: all] Error 2

Bin directory was created, but it’s empty, so probably xxx.out was not created properly. How could I get it working?
If I remove CMAKE_RUNTIME_OUTPUT_DIRECTORY definition, everything is Ok, linking is successful, but all my files (xxx.out, xxx.bin, xxx.hex) are placed to a root directory.

Here is the whole content of my CMakeLists.txt:

cmake_minimum_required(VERSION 3.5)
project(xxx)

enable_language(C ASM)
set(CMAKE_C_STANDARD 99)
set(CMAKE_C_STANDARD_REQUIRED ON)
set(CMAKE_C_EXTENSIONS OFF)

set(EXECUTABLE ${PROJECT_NAME}.out)

#set(CMAKE_RUNTIME_OUTPUT_DIRECTORY bin)

include_directories(src)
set(sources
src/main.c
)
add_executable (${EXECUTABLE} ${sources})

target_compile_definitions(${EXECUTABLE} PRIVATE
-D__ATSAMC21E18A__
-D__TARGET_CPU_CORTEX_M0
)

target_compile_options(${EXECUTABLE} PRIVATE
-mcpu=cortex-m0plus
-march=armv6-m
-mthumb
-mfloat-abi=soft
-fdata-sections
-ffunction-sections
-fno-strict-aliasing
-Wall
-O2
)

target_link_options(${EXECUTABLE} PRIVATE
-Tsys/samc21g18a_release.ld
-mcpu=cortex-m0plus
-march=armv6-m
-mthumb
-mfloat-abi=soft
-Wl,-Map=${PROJECT_NAME}.map,–cref
-specs=nano.specs
-Wl,–gc-sections
-lm
-lc
-lnosys
)

target_link_libraries(${EXECUTABLE} PRIVATE
m
)

add_custom_command(TARGET ${EXECUTABLE}
POST_BUILD
COMMAND arm-none-eabi-size ${EXECUTABLE})

add_custom_command(TARGET ${EXECUTABLE}
POST_BUILD
COMMAND arm-none-eabi-objcopy -O ihex ${EXECUTABLE} ${PROJECT_NAME}.hex
COMMAND arm-none-eabi-objcopy -O binary ${EXECUTABLE} ${PROJECT_NAME}.bin)

Do you have any ideas? Thank you in advance!

The problem is in your POST_BUILD commands. They used to work because, by default the working directory is CMAKE_CURRENT_BINARY_DIR. Now that the binary has moved to another directory, they cannot “find” the executable by just its name. Instead of passing ${EXECUTABLE} as an argument, I would recommend $<TARGET_FILE:${EXECUTABLE}> instead. This will also work reliably for multi-config generators.

Thank you for your reply!
Probably you are right, the configuration was not Ok, but I’ve found another problem with this solution - the whole building process will be done in the project’s root directory, but I prefer to have everything in a separate directory. My previous workout was like that:

cmake -G “MinGW Makefiles” -DCMAKE_TOOLCHAIN_FILE=arm-none-eabi-gcc.cmake
mingw32-make

But now I define the build directory in the command line and perform the build process with cmake tools only:

cmake -G “MinGW Makefiles” -DCMAKE_TOOLCHAIN_FILE=arm-none-eabi-gcc.cmake . -Bbin
cmake --build ./bin

The only problem is a lot of temporary files I wish to delete after the build process. But this is another issue.

Now everything related to the build process is in the bin directory including the hex and bin files.

Such as? And why are they a problem. If you want it for packaging or other purposes, it is usually far better to use installation to pull things out of the build tree for use elsewhere.

Maybe I’m confused. This is what you wanted right?

It seems you were using in-source builds and wanted to move the binaries? I would recommend using out-of-source builds (as -Bbin will do) and then use installation to “remove” the temporary files.