[cmake] ---- set_property

1 Background to study set_property

During the development process, we encounter situations where we need to build in the upper-level directory, and the source code is written in the lower-level directory respectively. At the same time, we need to selectively add different source codes for compilation according to different situations, so consider the source code that needs to be compiled. into a cmake list. However, the variables generated by set() are all local variables (that is, they are not shared in different directories), so use the set_property() command.

2 A simple demo that requires setting global properties using set_property

I assume here that a show_system() function is called under the main() function to display the name of the current system. The overall structure of the program is as follows:

$ tree
├── CMakeLists.txt              
├── linux
│   ├── CMakeLists.txt
│   ├── property.c
│   └── property.h
├── main.c
└── win
    ├── CMakeLists.txt
    ├── property.c
    └── property.h

main.c source code, main.c program is very simple, just call the function defined in the subdirectory.

#include <stdio.h>
 
#include <property.h>
 
int main()
{
    show_system();
 
    return 0;
}

Property.c source code, the implementation of property.c is the same in linux and win.

#include <stdio.h>
 
#include "property.h"
 
void show_system()
{
    printf("This is linux\n");    // in linux
    printf("This is windows\n");  // in win
}

CMakeLists.txt in the root directory

cmake_minimum_required (VERSION 3.13.0)
 
project (property_test VERSION 0.0.4)
 
# 设置全局属性 SOURCE_LIST
set_property( GLOBAL APPEND PROPERTY SOURCE_LIST)
 
# 如果是 Linux 系统,选择编译 linux 目录
IF (CMAKE_SYSTEM_NAME MATCHES "Linux")
    include_directories (linux)
    add_subdirectory (linux)
 
# Window 系统下选择编译 win 目录
ELSEIF (CMAKE_SYSTEM_NAME MATCHES "Windows")
    include_directories (win)
    add_subdirectory (win)
ENDIF (CMAKE_SYSTEM_NAME MATCHES "Linux")
 
# 将 SOURCE_LIST 的内容保存到 SRC_LIST 中
get_property(SRC_LIST GLOBAL PROPERTY SOURCE_LIST )
 
message("src list:" ${SRC_LIST})
 
# build exec
SET(exename "property")
add_executable (${exename} ${SRC_LIST} main.c)

CMakeLists.txt in subdirectory

file(GLOB_RECURSE SRC_LIST "*.cpp" "*.c")    # 查找当前目录下所有 .cpp 和 .c 文件
set_property( GLOBAL APPEND PROPERTY SOURCE_LIST ${SRC_LIST})   # 将这些文件路径附加到 SOURCE_LIST 后面

Because the aux_source_directory command generates the relative path of the source file, which cannot be used normally after being passed to the upper layer, so here we choose the file() command to find the source file, which will generate the absolute path of the file. Note that file() searches recursively, which means that source code in subdirectories will also be found.

Here SRC_LIST is a local variable and only takes effect in this directory, so each CMakeLists.txt can be used normally, while SOURCE_LIST is a global variable.

3 set_property syntax

The set_property() command is used to set the properties of an object within a given scope.
Command format:

set_property(<GLOBAL                      |
              DIRECTORY [<dir>]           |
              TARGET    [<target1> ...]   |
              SOURCE    [<src1> ...]
                        [DIRECTORY <dirs> ...]
                        [TARGET_DIRECTORY <targets> ...] |
              INSTALL   [<file1> ...]     |
              TEST      [<test1> ...]     |
              CACHE     [<entry1> ...]    >
             [APPEND] [APPEND_STRING]
             PROPERTY <name> [<value1> ...])
 
 # 其基本格式为:
 set_property(<Scope> [APPEND] [APPEND_STRING] PROPERTY <name> [value...])

The first parameter must be the scope of the attribute (Scope), followed by [APPEND | APPEND_STRING] optional, indicating that the attribute is an expandable list. PROPERTY is the identifier followed by the property name, whose value is optional. Scope has several options which can be:

Scope Description Similar commands
GLOBAL The attribute is valid in the global scope and the attribute name must be unique
DIRECTORY Valid within the specified directory, which can be a relative path or an absolute path. set_directory_properties
TARGET Set the attributes of the specified TARGET set_target_properties
SOURCE Property corresponds to zero or more source files. By default, source file properties are only visible to targets added in the same directory (CMakeLists.txt). set_source_files_properties
INSTALL Properties correspond to zero or more installed file paths. These can be used by CPack to affect deployment.
TEST Property corresponds to zero or more existing tests. set_tests_properties
CACHE Property corresponds to zero or more cached existing entries.

After version 3.18, SOURCE attributes can be made visible in other directories by setting the option DIRECTORY/TARGET_DIRECTORY.

  • DIRECTORY: The source file attribute will be valid at the scope of each directory, CMake must already know about each of these directories, either add them by calling add_subdirectory(), or it is the top-level source directory. Relative paths are considered relative to the current source directory. After version 3.19, the binary directory can be referenced.
  • TARGET_DIRECTORY: The source file attribute will be valid in the scope of each directory created and any specified must already exist.
    PROPERTY is a required parameter, followed by the name of the property, and the remaining parameters correspond to the value of the property, separated by semicolons.

APPEND and APPEND_STRING are optional parameters. If set, the following... will be appended to the specified attribute in the form of a list. APPEND_STRING means that the following will be added to the end of the attribute in the form of a string.

Guess you like

Origin blog.csdn.net/weixin_42445727/article/details/134696944