1set(CMAKE_LEGACY_CYGWIN_WIN32 0) 2cmake_minimum_required(VERSION 3.0) 3 4project(cJSON 5 VERSION 1.7.17 6 LANGUAGES C) 7 8cmake_policy(SET CMP0054 NEW) # set CMP0054 policy 9 10include(GNUInstallDirs) 11 12set(CJSON_VERSION_SO 1) 13set(CJSON_UTILS_VERSION_SO 1) 14 15set(custom_compiler_flags) 16 17option(ENABLE_INT64 "Enable the use of int64(long long), please note this will use c99 instead of c89" OFF) 18if (ENABLE_INT64) 19 add_definitions(-DENABLE_INT64) 20 list(APPEND custom_compiler_flags 21 -std=c99 22 ) 23else() 24 list(APPEND custom_compiler_flags 25 -std=c89 26 ) 27endif () 28 29include(CheckCCompilerFlag) 30option(ENABLE_CUSTOM_COMPILER_FLAGS "Enables custom compiler flags" ON) 31if (ENABLE_CUSTOM_COMPILER_FLAGS) 32 if (("${CMAKE_C_COMPILER_ID}" STREQUAL "Clang") OR ("${CMAKE_C_COMPILER_ID}" STREQUAL "GNU")) 33 list(APPEND custom_compiler_flags 34 -pedantic 35 -Wall 36 -Wextra 37 -Werror 38 -Wstrict-prototypes 39 -Wwrite-strings 40 -Wshadow 41 -Winit-self 42 -Wcast-align 43 -Wformat=2 44 -Wmissing-prototypes 45 -Wstrict-overflow=2 46 -Wcast-qual 47 -Wundef 48 -Wswitch-default 49 -Wconversion 50 -Wc++-compat 51 -fstack-protector-strong 52 -Wcomma 53 -Wdouble-promotion 54 -Wparentheses 55 -Wformat-overflow 56 -Wunused-macros 57 -Wmissing-variable-declarations 58 -Wused-but-marked-unused 59 -Wswitch-enum 60 ) 61 elseif("${CMAKE_C_COMPILER_ID}" STREQUAL "MSVC") 62 # Disable warning c4001 - nonstandard extension 'single line comment' was used 63 # Define _CRT_SECURE_NO_WARNINGS to disable deprecation warnings for "insecure" C library functions 64 list(APPEND custom_compiler_flags 65 /GS 66 /Za 67 /sdl 68 /W4 69 /wd4001 70 /D_CRT_SECURE_NO_WARNINGS 71 ) 72 endif() 73endif() 74 75option(ENABLE_SANITIZERS "Enables AddressSanitizer and UndefinedBehaviorSanitizer." OFF) 76if (ENABLE_SANITIZERS) 77 list(APPEND custom_compiler_flags 78 -fno-omit-frame-pointer 79 -fsanitize=address 80 -fsanitize=undefined 81 -fsanitize=float-cast-overflow 82 -fsanitize-address-use-after-scope 83 -fsanitize=integer 84 -01 85 -fno-sanitize-recover 86 ) 87endif() 88 89option(ENABLE_SAFE_STACK "Enables the SafeStack instrumentation pass by the Code Pointer Integrity Project" OFF) 90if (ENABLE_SAFE_STACK) 91 if (ENABLE_SANITIZERS) 92 message(FATAL_ERROR "ENABLE_SAFE_STACK cannot be used in combination with ENABLE_SANITIZERS") 93 endif() 94 list(APPEND custom_compiler_flags 95 -fsanitize=safe-stack 96 ) 97endif() 98 99option(ENABLE_PUBLIC_SYMBOLS "Export library symbols." On) 100if (ENABLE_PUBLIC_SYMBOLS) 101 list(APPEND custom_compiler_flags -fvisibility=hidden) 102 add_definitions(-DCJSON_EXPORT_SYMBOLS -DCJSON_API_VISIBILITY) 103endif() 104option(ENABLE_HIDDEN_SYMBOLS "Hide library symbols." Off) 105if (ENABLE_HIDDEN_SYMBOLS) 106 add_definitions(-DCJSON_HIDE_SYMBOLS -UCJSON_API_VISIBILITY) 107endif() 108 109# apply custom compiler flags 110foreach(compiler_flag ${custom_compiler_flags}) 111 #remove problematic characters 112 string(REGEX REPLACE "[^a-zA-Z0-9]" "" current_variable ${compiler_flag}) 113 114 CHECK_C_COMPILER_FLAG(${compiler_flag} "FLAG_SUPPORTED_${current_variable}") 115 if (FLAG_SUPPORTED_${current_variable}) 116 list(APPEND supported_compiler_flags) 117 set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${compiler_flag}") 118 endif() 119endforeach() 120 121set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} ${supported_compiler_flags}") 122 123option(BUILD_SHARED_LIBS "Build shared libraries" ON) 124option(ENABLE_TARGET_EXPORT "Enable exporting of CMake targets. Disable when it causes problems!" ON) 125 126#cJSON 127set(CJSON_LIB cjson) 128 129file(GLOB HEADERS cJSON.h) 130set(SOURCES cJSON.c) 131 132option(BUILD_SHARED_AND_STATIC_LIBS "Build both shared and static libraries" Off) 133option(CJSON_OVERRIDE_BUILD_SHARED_LIBS "Override BUILD_SHARED_LIBS with CJSON_BUILD_SHARED_LIBS" OFF) 134option(CJSON_BUILD_SHARED_LIBS "Overrides BUILD_SHARED_LIBS if CJSON_OVERRIDE_BUILD_SHARED_LIBS is enabled" ON) 135option(ENABLE_CJSON_VERSION_SO "Enables cJSON so version" ON) 136 137if ((CJSON_OVERRIDE_BUILD_SHARED_LIBS AND CJSON_BUILD_SHARED_LIBS) OR ((NOT CJSON_OVERRIDE_BUILD_SHARED_LIBS) AND BUILD_SHARED_LIBS)) 138 set(CJSON_LIBRARY_TYPE SHARED) 139else() 140 set(CJSON_LIBRARY_TYPE STATIC) 141endif() 142 143 144if (NOT BUILD_SHARED_AND_STATIC_LIBS) 145 add_library("${CJSON_LIB}" "${CJSON_LIBRARY_TYPE}" "${HEADERS}" "${SOURCES}") 146else() 147 # See https://cmake.org/Wiki/CMake_FAQ#How_do_I_make_my_shared_and_static_libraries_have_the_same_root_name.2C_but_different_suffixes.3F 148 add_library("${CJSON_LIB}" SHARED "${HEADERS}" "${SOURCES}") 149 add_library("${CJSON_LIB}-static" STATIC "${HEADERS}" "${SOURCES}") 150 set_target_properties("${CJSON_LIB}-static" PROPERTIES OUTPUT_NAME "${CJSON_LIB}") 151 set_target_properties("${CJSON_LIB}-static" PROPERTIES PREFIX "lib") 152endif() 153if (NOT WIN32) 154 target_link_libraries("${CJSON_LIB}" m) 155endif() 156 157configure_file("${CMAKE_CURRENT_SOURCE_DIR}/library_config/libcjson.pc.in" 158 "${CMAKE_CURRENT_BINARY_DIR}/libcjson.pc" @ONLY) 159 160install(FILES cJSON.h DESTINATION "${CMAKE_INSTALL_FULL_INCLUDEDIR}/cjson") 161install (FILES "${CMAKE_CURRENT_BINARY_DIR}/libcjson.pc" DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}/pkgconfig") 162install(TARGETS "${CJSON_LIB}" 163 EXPORT "${CJSON_LIB}" 164 ARCHIVE DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}" 165 LIBRARY DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}" 166 RUNTIME DESTINATION "${CMAKE_INSTALL_FULL_BINDIR}" 167 INCLUDES DESTINATION "${CMAKE_INSTALL_FULL_INCLUDEDIR}" 168) 169if (BUILD_SHARED_AND_STATIC_LIBS) 170 install(TARGETS "${CJSON_LIB}-static" 171 EXPORT "${CJSON_LIB}" 172 ARCHIVE DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}" 173 INCLUDES DESTINATION "${CMAKE_INSTALL_FULL_INCLUDEDIR}" 174) 175endif() 176if(ENABLE_TARGET_EXPORT) 177 # export library information for CMake projects 178 install(EXPORT "${CJSON_LIB}" DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}/cmake/cJSON") 179endif() 180 181if(ENABLE_CJSON_VERSION_SO) 182 set_target_properties("${CJSON_LIB}" 183 PROPERTIES 184 SOVERSION "${CJSON_VERSION_SO}" 185 VERSION "${PROJECT_VERSION}") 186endif() 187 188#cJSON_Utils 189option(ENABLE_CJSON_UTILS "Enable building the cJSON_Utils library." OFF) 190if(ENABLE_CJSON_UTILS) 191 set(CJSON_UTILS_LIB cjson_utils) 192 193 file(GLOB HEADERS_UTILS cJSON_Utils.h) 194 set(SOURCES_UTILS cJSON_Utils.c) 195 196 if (NOT BUILD_SHARED_AND_STATIC_LIBS) 197 add_library("${CJSON_UTILS_LIB}" "${CJSON_LIBRARY_TYPE}" "${HEADERS_UTILS}" "${SOURCES_UTILS}") 198 target_link_libraries("${CJSON_UTILS_LIB}" "${CJSON_LIB}") 199 else() 200 add_library("${CJSON_UTILS_LIB}" SHARED "${HEADERS_UTILS}" "${SOURCES_UTILS}") 201 target_link_libraries("${CJSON_UTILS_LIB}" "${CJSON_LIB}") 202 add_library("${CJSON_UTILS_LIB}-static" STATIC "${HEADERS_UTILS}" "${SOURCES_UTILS}") 203 target_link_libraries("${CJSON_UTILS_LIB}-static" "${CJSON_LIB}-static") 204 set_target_properties("${CJSON_UTILS_LIB}-static" PROPERTIES OUTPUT_NAME "${CJSON_UTILS_LIB}") 205 set_target_properties("${CJSON_UTILS_LIB}-static" PROPERTIES PREFIX "lib") 206 endif() 207 208 configure_file("${CMAKE_CURRENT_SOURCE_DIR}/library_config/libcjson_utils.pc.in" 209 "${CMAKE_CURRENT_BINARY_DIR}/libcjson_utils.pc" @ONLY) 210 211 install(TARGETS "${CJSON_UTILS_LIB}" 212 EXPORT "${CJSON_UTILS_LIB}" 213 ARCHIVE DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}" 214 LIBRARY DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}" 215 RUNTIME DESTINATION "${CMAKE_INSTALL_FULL_BINDIR}" 216 INCLUDES DESTINATION "${CMAKE_INSTALL_FULL_INCLUDEDIR}" 217 ) 218 if (BUILD_SHARED_AND_STATIC_LIBS) 219 install(TARGETS "${CJSON_UTILS_LIB}-static" 220 EXPORT "${CJSON_UTILS_LIB}" 221 ARCHIVE DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}" 222 INCLUDES DESTINATION "${CMAKE_INSTALL_FULL_INCLUDEDIR}" 223 ) 224 endif() 225 install(FILES cJSON_Utils.h DESTINATION "${CMAKE_INSTALL_FULL_INCLUDEDIR}/cjson") 226 install (FILES "${CMAKE_CURRENT_BINARY_DIR}/libcjson_utils.pc" DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}/pkgconfig") 227 if(ENABLE_TARGET_EXPORT) 228 # export library information for CMake projects 229 install(EXPORT "${CJSON_UTILS_LIB}" DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}/cmake/cJSON") 230 endif() 231 232 if(ENABLE_CJSON_VERSION_SO) 233 set_target_properties("${CJSON_UTILS_LIB}" 234 PROPERTIES 235 SOVERSION "${CJSON_UTILS_VERSION_SO}" 236 VERSION "${PROJECT_VERSION}") 237 endif() 238endif() 239 240# create the other package config files 241configure_file( 242 "${CMAKE_CURRENT_SOURCE_DIR}/library_config/cJSONConfig.cmake.in" 243 ${PROJECT_BINARY_DIR}/cJSONConfig.cmake @ONLY) 244configure_file( 245 "${CMAKE_CURRENT_SOURCE_DIR}/library_config/cJSONConfigVersion.cmake.in" 246 ${PROJECT_BINARY_DIR}/cJSONConfigVersion.cmake @ONLY) 247 248if(ENABLE_TARGET_EXPORT) 249 # Install package config files 250 install(FILES ${PROJECT_BINARY_DIR}/cJSONConfig.cmake 251 ${PROJECT_BINARY_DIR}/cJSONConfigVersion.cmake 252 DESTINATION "${CMAKE_INSTALL_FULL_LIBDIR}/cmake/cJSON") 253endif() 254 255option(ENABLE_CJSON_TEST "Enable building cJSON test" ON) 256if(ENABLE_CJSON_TEST) 257 enable_testing() 258 259 set(TEST_CJSON cJSON_test) 260 add_executable("${TEST_CJSON}" test.c) 261 target_link_libraries("${TEST_CJSON}" "${CJSON_LIB}") 262 263 add_test(NAME ${TEST_CJSON} COMMAND "${CMAKE_CURRENT_BINARY_DIR}/${TEST_CJSON}") 264 265 # Disable -fsanitize=float-divide-by-zero for cJSON_test 266 if (FLAG_SUPPORTED_fsanitizefloatdividebyzero) 267 if ("${CMAKE_VERSION}" VERSION_LESS "2.8.12") 268 set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fno-sanitize=float-divide-by-zero") 269 else() 270 target_compile_options(${TEST_CJSON} PRIVATE "-fno-sanitize=float-divide-by-zero") 271 endif() 272 endif() 273 274 #"check" target that automatically builds everything and runs the tests 275 add_custom_target(check 276 COMMAND ${CMAKE_CTEST_COMMAND} --output-on-failure 277 DEPENDS ${TEST_CJSON}) 278endif() 279 280#Create the uninstall target 281option(ENABLE_CJSON_UNINSTALL "Enable creating uninstall target" ON) 282if(ENABLE_CJSON_UNINSTALL) 283 add_custom_target(uninstall "${CMAKE_COMMAND}" -P 284 "${PROJECT_SOURCE_DIR}/library_config/uninstall.cmake") 285endif() 286 287# Enable the use of locales 288option(ENABLE_LOCALES "Enable the use of locales" ON) 289if(ENABLE_LOCALES) 290 add_definitions(-DENABLE_LOCALES) 291endif() 292 293add_subdirectory(tests) 294add_subdirectory(fuzzing) 295