test-X86-CMakeLists


[TOC]

经常会看到的:

#CMake变量使用 ${ }取值
#但是在IF控制语句中是直接使用变量名。

文件内容

cmake_minimum_required(VERSION 3.2) 
#  规定cmake软件的版本
#定义一个可在CMake脚本其他位置调用的函数
function(COMPILE_X86_TESTS name address_size has_avx has_avx512)
······
endfunction()
#到endfunction()为止结束,····为函数体内容

function内部

function(COMPILE_X86_TESTS name address_size has_avx has_avx512)
  set(X86_TEST_FLAGS
    -I${CMAKE_SOURCE_DIR}
    -DADDRESS_SIZE_BITS=${address_size}
    -DHAS_FEATURE_AVX=${has_avx}
    -DHAS_FEATURE_AVX512=${has_avx512}
    -DGTEST_HAS_RTTI=0
    -DGTEST_HAS_TR1_TUPLE=0
  )
    
  add_executable(lift-${name}-tests     
    EXCLUDE_FROM_ALL
    Lift.cpp
    Tests.S
  )
    
  target_compile_options(lift-${name}-tests
    PRIVATE ${X86_TEST_FLAGS} -DIN_TEST_GENERATOR
  )
  
  file(GLOB X86_TEST_FILES
    "${CMAKE_CURRENT_LIST_DIR}/*/*.S"
  )
  
  set_target_properties(lift-${name}-tests PROPERTIES OBJECT_DEPENDS "${X86_TEST_FILES}")

  target_link_libraries(lift-${name}-tests PRIVATE remill GTest::gtest)
  target_compile_definitions(lift-${name}-tests PUBLIC ${PROJECT_DEFINITIONS})

  add_custom_command(
    OUTPUT tests_${name}.bc
    COMMAND lift-${name}-tests --arch ${name} --bc_out tests_${name}.bc
    DEPENDS semantics
  )
    
  add_custom_command(
    OUTPUT tests_${name}.S
    COMMAND ${CMAKE_BC_COMPILER} -Wno-override-module -S -O0 -g0 -c tests_${name}.bc -o tests_${name}.S
    DEPENDS tests_${name}.bc
  )
 
  add_executable(run-${name}-tests EXCLUDE_FROM_ALL Run.cpp Tests.S tests_${name}.S)
  set_target_properties(run-${name}-tests PROPERTIES OBJECT_DEPENDS "${X86_TEST_FILES}")

  target_link_libraries(run-${name}-tests PUBLIC remill GTest::gtest)
  target_compile_definitions(run-${name}-tests PUBLIC ${PROJECT_DEFINITIONS})
    
  target_compile_options(run-${name}-tests
    PRIVATE ${X86_TEST_FLAGS}
  )

  message(STATUS "Adding test: ${name} as run-${name}-tests")
  add_test(NAME "${name}" COMMAND "run-${name}-tests")
  add_dependencies(test_dependencies "run-${name}-tests")
endfunction()

逐条解释

#SET命令用于赋值
#CMake变量使用 ${ }取值
set(X86_TEST_FLAGS
    -I${CMAKE_SOURCE_DIR}
    -DADDRESS_SIZE_BITS=${address_size}
    -DHAS_FEATURE_AVX=${has_avx}
    -DHAS_FEATURE_AVX512=${has_avx512}
    -DGTEST_HAS_RTTI=0
    -DGTEST_HAS_TR1_TUPLE=0
  )
 
#生成可执行文件
#生成 lift.cpp和Tests.s的可执行文件
#格式:add_executable(${TARGET_NAME} ${SOURCES})
#     ${TARGET_NAME}代表你设置的项目名称变量;
#     ${SOURCES}代表你的源文件变量
add_executable(lift-${name}-tests     
   EXCLUDE_FROM_ALL
   Lift.cpp
   Tests.S
 )
#在编译给定目标文件时,指定要用到的编译选项。target目标文件必须已经存在(由命令add_executable()或add_library()创建)且不能被IMPORTED修饰。
# 格式:target_compile_options(<target> [BEFORE] <INTERFACE|PUBLIC|PRIVATE> [items1...] [<INTERFACE|PUBLIC|PRIVATE> [items2...] ...])

target_compile_options(lift-${name}-tests
    PRIVATE ${X86_TEST_FLAGS} -DIN_TEST_GENERATOR
  )
# 文件写入与追加
#  格式:file(WRITE <filename> <content>...)
#  例子:file(WRITE test.txt "this is a test to wirte\n")

# 此处大概是指把 "${CMAKE_CURRENT_LIST_DIR}/*/*.S"  GLOB(一种操作)  到 X86_TEST_FILES文件里。

file(GLOB X86_TEST_FILES
    "${CMAKE_CURRENT_LIST_DIR}/*/*.S"
  )
# 设置输出的名称,设置动态库的版本和API版本
# 格式 set_target_properties(${TARGET_NAME} PROPERTIES LINK_FLAGS "/SUBSYSTEM:WINDOWS")

set_target_properties(lift-${name}-tests PROPERTIES OBJECT_DEPENDS "${X86_TEST_FILES}")
# 格式: TARGET_LINK_LIBRARIES(target lib1 lib2 …)
# 为target添加需要链接的共享库
target_link_libraries(lift-${name}-tests PRIVATE remill GTest::gtest)
  # 为目标增加编译定义
  # 格式 target_compile_definitions(<target>
                           #<INTERFACE|PUBLIC|PRIVATE> [items1...]
                           #[<INTERFACE|PUBLIC|PRIVATE> [items2...] ...]
#                          )
 
 #指定编译给定 <target> 时要使用的编译定义。命名的 <target> 必须由诸如 add_executable() 或 add_library() 之类的命令创建,并且不能是导入的目标。
 
 target_compile_definitions(lift-${sname}-tests PUBLIC ${PROJECT_DEFINITIONS})
# 增加一个没有输出的目标,使得它总是被构建。
#在很多时候,需要在cmake中创建一些目标,如clean、copy等等,这就需要通过add_custom_target来指定。同时,add_custom_command可以用来完成对add_custom_target生成的target的补充。

add_custom_command(
   OUTPUT tests_${name}.bc
   COMMAND lift-${name}-tests --arch ${name} --bc_out tests_${name}.bc
   DEPENDS semantics
 )
 
  add_custom_command(
   OUTPUT tests_${name}.S
   COMMAND ${CMAKE_BC_COMPILER} -Wno-override-module -S -O0 -g0 -c tests_${name}.bc -o tests_${name}.S
   DEPENDS tests_${name}.bc
 )
 
# 之前有过解释,还不清楚为什么要重新写一遍
add_executable(run-${name}-tests EXCLUDE_FROM_ALL Run.cpp Tests.S tests_${name}.S)
  set_target_properties(run-${name}-tests PROPERTIES OBJECT_DEPENDS "${X86_TEST_FILES}")

  target_link_libraries(run-${name}-tests PUBLIC remill GTest::gtest)
  target_compile_definitions(run-${name}-tests PUBLIC ${PROJECT_DEFINITIONS})
  target_compile_options(run-${name}-tests
    PRIVATE ${X86_TEST_FLAGS}
  )
#为用户显示一条消息
#格式 message( [STATUS|WARNING|AUTHOR_WARNING|FATAL_ERROR|SEND_ERROR] "message to display" ...)
# STATUS = 非重要消息

  message(STATUS "Adding test: ${name} as run-${name}-tests")
#向要由ctest运行的项目添加测试
#格式     add_test(NAME <name> COMMAND <command> [<arg>...]
#         [CONFIGURATIONS <config>...]
#         [WORKING_DIRECTORY <dir>]
#         [COMMAND_EXPAND_LISTS])
#添加名为< name >的测试。测试名称可以包含任意字符,如果需要,可以用引号参数或括号参数表示
#COMMAND:指定测试命令行。如果< command >指定了一个可执行目标(由add_executable()创建),它将自动被构建时创建的可执行文件的位置所取代。

add_test(NAME "${name}" COMMAND "run-${name}-tests")
#在顶层目标之间添加依赖关系
# 使顶层< target >依赖于其他顶层目标,以确保它们在< target >之前构建。顶层目标是由add_executable()、add_library()或add_custom_target()命令之一创建的目标(但不是由CMake生成的类似于install的目标)。
add_dependencies(test_dependencies "run-${name}-tests")

function外部

#  如果我们在cmake某个程序的时候,经常会提示找不到某个所依赖的库,那么这是时候我们就需要检查我们引入依赖库的路径对不对了, Cmake中一个自动寻找函数find_package()可以帮我们实现这个功能。
#REQUIRED可选字段。表示一定要找到包,找不到的话就立即停掉整个cmake。而如果不指定REQUIRED则cmake会继续执行。

find_package(GTest CONFIG REQUIRED)
# 开启项目的测试功能
enable_testing()
# 如果不是苹果系统
if (NOT APPLE)
  COMPILE_X86_TESTS(x86 32 0 0)
  COMPILE_X86_TESTS(x86_avx 32 1 0)
endif()
# 不太清楚,但是是function的参数
COMPILE_X86_TESTS(amd64 64 0 0)
COMPILE_X86_TESTS(amd64_avx 64 1 0)

文章作者: Raina Jung
版权声明: 本博客所有文章除特別声明外,均采用 CC BY 4.0 许可协议。转载请注明来源 Raina Jung !
  目录