• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1cmake_minimum_required(VERSION 3.0)
2
3project(CpuFeatures VERSION 0.1.0)
4
5set(CMAKE_C_STANDARD 99)
6
7# Default Build Type to be Release
8if(NOT CMAKE_BUILD_TYPE)
9  set(CMAKE_BUILD_TYPE "Release" CACHE STRING
10      "Choose the type of build, options are: Debug Release RelWithDebInfo MinSizeRel."
11      FORCE)
12endif(NOT CMAKE_BUILD_TYPE)
13
14# BUILD_TESTING is a standard CMake variable, but we declare it here to make it
15# prominent in the GUI.
16option(BUILD_TESTING "Enable test (depends on googletest)." OFF)
17# BUILD_SHARED_LIBS is a standard CMake variable, but we declare it here to make
18# it prominent in the GUI.
19# cpu_features uses bit-fields which are - to some extends - implementation-defined (see https://en.cppreference.com/w/c/language/bit_field).
20# As a consequence it is discouraged to use cpu_features as a shared library because different compilers may interpret the code in different ways.
21# Prefer static linking from source whenever possible.
22option(BUILD_SHARED_LIBS "Build library as shared." OFF)
23# PIC
24option(BUILD_PIC "Build with Position Independant Code." OFF) # Default is off at least for GCC
25
26include(CheckIncludeFile)
27include(CheckSymbolExists)
28include(GNUInstallDirs)
29
30macro(setup_include_and_definitions TARGET_NAME)
31  target_include_directories(${TARGET_NAME}
32    PUBLIC  $<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/include>
33    PRIVATE $<BUILD_INTERFACE:${PROJECT_SOURCE_DIR}/include/internal>
34  )
35  target_compile_definitions(${TARGET_NAME}
36    PUBLIC STACK_LINE_READER_BUFFER_SIZE=1024
37  )
38endmacro()
39
40set(PROCESSOR_IS_MIPS FALSE)
41set(PROCESSOR_IS_ARM FALSE)
42set(PROCESSOR_IS_AARCH64 FALSE)
43set(PROCESSOR_IS_X86 FALSE)
44set(PROCESSOR_IS_POWER FALSE)
45
46if(CMAKE_SYSTEM_PROCESSOR MATCHES "^mips")
47  set(PROCESSOR_IS_MIPS TRUE)
48elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^arm")
49  set(PROCESSOR_IS_ARM TRUE)
50elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^aarch64")
51  set(PROCESSOR_IS_AARCH64 TRUE)
52elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "(x86_64)|(AMD64|amd64)|(^i.86$)")
53  set(PROCESSOR_IS_X86 TRUE)
54elseif(CMAKE_SYSTEM_PROCESSOR MATCHES "^(powerpc|ppc)")
55  set(PROCESSOR_IS_POWER TRUE)
56endif()
57
58macro(add_cpu_features_headers_and_sources HDRS_LIST_NAME SRCS_LIST_NAME)
59  list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpu_features_macros.h)
60  list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpu_features_cache_info.h)
61  if(PROCESSOR_IS_MIPS)
62      list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpuinfo_mips.h)
63      list(APPEND ${SRCS_LIST_NAME} ${PROJECT_SOURCE_DIR}/src/cpuinfo_mips.c)
64  elseif(PROCESSOR_IS_ARM)
65      list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpuinfo_arm.h)
66      list(APPEND ${SRCS_LIST_NAME} ${PROJECT_SOURCE_DIR}/src/cpuinfo_arm.c)
67  elseif(PROCESSOR_IS_AARCH64)
68      list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpuinfo_aarch64.h)
69      list(APPEND ${SRCS_LIST_NAME} ${PROJECT_SOURCE_DIR}/src/cpuinfo_aarch64.c)
70  elseif(PROCESSOR_IS_X86)
71      list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpuinfo_x86.h)
72      list(APPEND ${SRCS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/internal/cpuid_x86.h)
73      list(APPEND ${SRCS_LIST_NAME} ${PROJECT_SOURCE_DIR}/src/cpuinfo_x86.c)
74  elseif(PROCESSOR_IS_POWER)
75      list(APPEND ${HDRS_LIST_NAME} ${PROJECT_SOURCE_DIR}/include/cpuinfo_ppc.h)
76      list(APPEND ${SRCS_LIST_NAME} ${PROJECT_SOURCE_DIR}/src/cpuinfo_ppc.c)
77  else()
78    message(FATAL_ERROR "Unsupported architectures ${CMAKE_SYSTEM_PROCESSOR}")
79  endif()
80endmacro()
81
82#
83# library : utils
84#
85
86add_library(utils OBJECT
87  ${PROJECT_SOURCE_DIR}/include/internal/bit_utils.h
88  ${PROJECT_SOURCE_DIR}/include/internal/filesystem.h
89  ${PROJECT_SOURCE_DIR}/include/internal/stack_line_reader.h
90  ${PROJECT_SOURCE_DIR}/include/internal/string_view.h
91  ${PROJECT_SOURCE_DIR}/src/filesystem.c
92  ${PROJECT_SOURCE_DIR}/src/stack_line_reader.c
93  ${PROJECT_SOURCE_DIR}/src/string_view.c
94)
95setup_include_and_definitions(utils)
96
97#
98# library : unix_based_hardware_detection
99#
100
101if(UNIX)
102  add_library(unix_based_hardware_detection OBJECT
103    ${PROJECT_SOURCE_DIR}/include/internal/hwcaps.h
104    ${PROJECT_SOURCE_DIR}/include/internal/unix_features_aggregator.h
105    ${PROJECT_SOURCE_DIR}/src/hwcaps.c
106    ${PROJECT_SOURCE_DIR}/src/unix_features_aggregator.c
107  )
108  setup_include_and_definitions(unix_based_hardware_detection)
109  check_include_file(dlfcn.h HAVE_DLFCN_H)
110  if(HAVE_DLFCN_H)
111    target_compile_definitions(unix_based_hardware_detection PRIVATE HAVE_DLFCN_H)
112  endif()
113  check_symbol_exists(getauxval "sys/auxv.h" HAVE_STRONG_GETAUXVAL)
114  if(HAVE_STRONG_GETAUXVAL)
115    target_compile_definitions(unix_based_hardware_detection PRIVATE HAVE_STRONG_GETAUXVAL)
116  endif()
117  set_property(TARGET unix_based_hardware_detection PROPERTY POSITION_INDEPENDENT_CODE ${BUILD_PIC})
118endif()
119
120#
121# library : cpu_features
122#
123set (CPU_FEATURES_HDRS)
124set (CPU_FEATURES_SRCS)
125add_cpu_features_headers_and_sources(CPU_FEATURES_HDRS CPU_FEATURES_SRCS)
126list(APPEND CPU_FEATURES_SRCS $<TARGET_OBJECTS:utils>)
127if(NOT PROCESSOR_IS_X86 AND UNIX)
128  list(APPEND CPU_FEATURES_SRCS $<TARGET_OBJECTS:unix_based_hardware_detection>)
129endif()
130add_library(cpu_features ${CPU_FEATURES_HDRS} ${CPU_FEATURES_SRCS})
131set_target_properties(cpu_features PROPERTIES PUBLIC_HEADER "${CPU_FEATURES_HDRS}")
132setup_include_and_definitions(cpu_features)
133target_link_libraries(cpu_features PUBLIC ${CMAKE_DL_LIBS})
134set_property(TARGET cpu_features PROPERTY POSITION_INDEPENDENT_CODE ${BUILD_PIC})
135target_include_directories(cpu_features
136  PUBLIC $<INSTALL_INTERFACE:${CMAKE_INSTALL_INCLUDEDIR}/cpu_features>
137)
138
139#
140# program : list_cpu_features
141#
142
143add_executable(list_cpu_features ${PROJECT_SOURCE_DIR}/src/utils/list_cpu_features.c)
144target_link_libraries(list_cpu_features PRIVATE cpu_features)
145add_executable(CpuFeature::list_cpu_features ALIAS list_cpu_features)
146
147#
148# ndk_compat
149#
150
151if(ANDROID)
152add_subdirectory(ndk_compat)
153endif()
154
155#
156# tests
157#
158
159include(CTest)
160if(BUILD_TESTING)
161  # Automatically incorporate googletest into the CMake Project if target not
162  # found.
163  if(NOT TARGET gtest OR NOT TARGET gmock_main)
164    # Download and unpack googletest at configure time.
165    configure_file(
166      cmake/googletest.CMakeLists.txt.in
167      googletest-download/CMakeLists.txt
168    )
169
170    execute_process(
171      COMMAND ${CMAKE_COMMAND} -G "${CMAKE_GENERATOR}" .
172      RESULT_VARIABLE result
173      WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/googletest-download)
174
175    if(result)
176      message(FATAL_ERROR "CMake step for googletest failed: ${result}")
177    endif()
178
179    execute_process(
180      COMMAND ${CMAKE_COMMAND} --build .
181      RESULT_VARIABLE result
182      WORKING_DIRECTORY ${CMAKE_BINARY_DIR}/googletest-download)
183
184    if(result)
185      message(FATAL_ERROR "Build step for googletest failed: ${result}")
186    endif()
187
188    # Prevent overriding the parent project's compiler/linker settings on
189    # Windows.
190    set(gtest_force_shared_crt ON CACHE BOOL "" FORCE)
191
192    # Add googletest directly to our build. This defines the gtest and
193    # gtest_main targets.
194    add_subdirectory(${CMAKE_BINARY_DIR}/googletest-src
195                     ${CMAKE_BINARY_DIR}/googletest-build
196                     EXCLUDE_FROM_ALL)
197  endif()
198
199  add_subdirectory(test)
200endif()
201
202#
203# Install cpu_features and list_cpu_features
204#
205
206include(GNUInstallDirs)
207install(TARGETS cpu_features list_cpu_features
208  EXPORT CpuFeaturesTargets
209  PUBLIC_HEADER DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}/cpu_features
210  ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR}
211  LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR}
212  RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR}
213)
214install(EXPORT CpuFeaturesTargets
215  NAMESPACE CpuFeatures::
216  DESTINATION ${CMAKE_INSTALL_LIBDIR}/cmake/CpuFeatures
217  COMPONENT Devel
218)
219include(CMakePackageConfigHelpers)
220configure_package_config_file(cmake/CpuFeaturesConfig.cmake.in
221  "${PROJECT_BINARY_DIR}/CpuFeaturesConfig.cmake"
222  INSTALL_DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/CpuFeatures"
223  NO_SET_AND_CHECK_MACRO
224  NO_CHECK_REQUIRED_COMPONENTS_MACRO
225)
226write_basic_package_version_file(
227  "${PROJECT_BINARY_DIR}/CpuFeaturesConfigVersion.cmake"
228  COMPATIBILITY SameMajorVersion
229)
230install(
231  FILES
232    "${PROJECT_BINARY_DIR}/CpuFeaturesConfig.cmake"
233    "${PROJECT_BINARY_DIR}/CpuFeaturesConfigVersion.cmake"
234  DESTINATION "${CMAKE_INSTALL_LIBDIR}/cmake/CpuFeatures"
235  COMPONENT Devel
236)
237