为CMake项目配置OpenSSL跨平台编译(Android/Windows)
解决OpenSSL跨Android/Windows平台编译的CMake配置优化
问题背景
我下载了OpenSSL稳定版,发现旧版本没有可用的CMakeLists.txt,无法通过add_subdirectory(vendor/openssl)将其引入项目。目前OpenSSL仅能在Linux环境下编译,需要实现它在Android和Windows平台的编译,以下是初始CMake配置代码:
cmake_minimum_required(VERSION 3.5) cmake_policy(SET CMP0076 NEW) cmake_policy(SET CMP0091 NEW) cmake_policy(SET CMP0071 NEW) set(CMAKE_AUTOUIC ON) set(CMAKE_AUTOMOC ON) set(CMAKE_AUTORCC ON) set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_STANDARD_REQUIRED ON) set(CMAKE_CXX_EXTENSIONS OFF) set(PROJECT_NAME Control) set(APP_VERSION 0.1.0) project(${PROJECT_NAME} VERSION ${APP_VERSION} LANGUAGES CXX) add_subdirectory(vendor/libzip) find_package(Qt6 6.2 REQUIRED COMPONENTS Core Gui Quick Network NetworkAuth Sql Positioning Widgets QuickWidgets UiTools Xml QUIET ) file(GLOB_RECURSE HEADERS "${CMAKE_SOURCE_DIR}/src/*.h") file(GLOB_RECURSE SOURCES "${CMAKE_SOURCE_DIR}/src/*.cpp") qt_policy(SET QTP0001 NEW) qt_add_executable(${PROJECT_NAME} MANUAL_FINALIZATION resources.qrc ${HEADERS} ${SOURCES} ) qt_add_qml_module(${PROJECT_NAME} URI control VERSION ${APP_VERSION} RESOURCES android/AndroidManifest.xml android/src/org/control/AndroidAPI.java SOURCES ${HEADERS} ${SOURCES} ) set_target_properties(${PROJECT_NAME} PROPERTIES MACOSX_BUNDLE TRUE WIN32_EXECUTABLE TRUE ) include(ExternalProject) set(ANDROID_NDK_ROOT "~/Android/Sdk/ndk/25.1.8937393") set(ANDROID_ABI "arm64-v8a") set(ANDROID_PLATFORM "android-29") ExternalProject_Add( openssl PREFIX ${CMAKE_BINARY_DIR}/vendor/openssl GIT_REPOSITORY https://github.com/openssl/openssl.git GIT_TAG OpenSSL_3_0_0 CMAKE_ARGS -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR> -DCMAKE_BUILD_TYPE=Release -DOPENSSL_NO_SHARED=ON -DANDROID_ABI=${ANDROID_ABI} -DANDROID_PLATFORM=${ANDROID_PLATFORM} -DCMAKE_TOOLCHAIN_FILE=${ANDROID_NDK_ROOT}/build/cmake/android.toolchain.cmake -DANDROID_NDK=${ANDROID_NDK_ROOT} ) ExternalProject_Get_Property(openssl install_dir) set(OPENSSL_INCLUDE_DIR ${install_dir}/include) set(OPENSSL_LIBRARIES ${install_dir}/lib/libssl.a ${install_dir}/lib/libcrypto.a) include_directories(${OPENSSL_INCLUDE_DIR}) link_directories(${OPENSSL_LIBRARIES}) target_link_libraries(${PROJECT_NAME} PRIVATE Qt6::Core Qt6::Gui Qt6::Quick Qt6::Network Qt6::NetworkAuth Qt6::Sql Qt6::Positioning Qt6::Widgets Qt6::Xml Qt6::QuickWidgets Qt6::UiTools libzip::zip ${OPENSSL_LIBRARIES} ) # Ensure the project depends on OpenSSL # add_dependencies(${PROJECT_NAME} openssl) set_property(TARGET ${PROJECT_NAME} APPEND PROPERTY QT_ANDROID_PACKAGE_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/android ) qt_finalize_executable(${PROJECT_NAME}) install(TARGETS ${PROJECT_NAME} RUNTIME DESTINATION . BUNDLE DESTINATION . LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} )
修正后的完整CMake配置
cmake_minimum_required(VERSION 3.5) cmake_policy(SET CMP0076 NEW) cmake_policy(SET CMP0091 NEW) cmake_policy(SET CMP0071 NEW) set(CMAKE_AUTOUIC ON) set(CMAKE_AUTOMOC ON) set(CMAKE_AUTORCC ON) set(CMAKE_CXX_STANDARD 17) set(CMAKE_CXX_STANDARD_REQUIRED ON) set(CMAKE_CXX_EXTENSIONS OFF) set(PROJECT_NAME Control) set(APP_VERSION 0.1.0) project(${PROJECT_NAME} VERSION ${APP_VERSION} LANGUAGES CXX) add_subdirectory(vendor/libzip) find_package(Qt6 6.2 REQUIRED COMPONENTS Core Gui Quick Network NetworkAuth Sql Positioning Widgets QuickWidgets UiTools Xml QUIET ) file(GLOB_RECURSE HEADERS "${CMAKE_SOURCE_DIR}/src/*.h") file(GLOB_RECURSE SOURCES "${CMAKE_SOURCE_DIR}/src/*.cpp") qt_policy(SET QTP0001 NEW) qt_add_executable(${PROJECT_NAME} MANUAL_FINALIZATION resources.qrc ${HEADERS} ${SOURCES} ) qt_add_qml_module(${PROJECT_NAME} URI control VERSION ${APP_VERSION} RESOURCES android/AndroidManifest.xml android/src/org/control/AndroidAPI.java SOURCES ${HEADERS} ${SOURCES} ) set_target_properties(${PROJECT_NAME} PROPERTIES MACOSX_BUNDLE TRUE WIN32_EXECUTABLE TRUE ) include(ExternalProject) # 平台差异化编译配置 if(ANDROID) set(ANDROID_NDK_ROOT "~/Android/Sdk/ndk/25.1.8937393") set(ANDROID_ABI "arm64-v8a") set(ANDROID_PLATFORM "android-29") ExternalProject_Add( openssl PREFIX ${CMAKE_BINARY_DIR}/vendor/openssl GIT_REPOSITORY https://github.com/openssl/openssl.git GIT_TAG OpenSSL_3_0_0 CMAKE_ARGS -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR> -DCMAKE_BUILD_TYPE=Release -DOPENSSL_NO_SHARED=ON -DANDROID_ABI=${ANDROID_ABI} -DANDROID_PLATFORM=${ANDROID_PLATFORM} -DCMAKE_TOOLCHAIN_FILE=${ANDROID_NDK_ROOT}/build/cmake/android.toolchain.cmake -DANDROID_NDK=${ANDROID_NDK_ROOT} ) set(OPENSSL_LIB_SUFFIX ".a") elseif(WIN32) ExternalProject_Add( openssl PREFIX ${CMAKE_BINARY_DIR}/vendor/openssl GIT_REPOSITORY https://github.com/openssl/openssl.git GIT_TAG OpenSSL_3_0_0 CMAKE_ARGS -DCMAKE_INSTALL_PREFIX=<INSTALL_DIR> -DCMAKE_BUILD_TYPE=Release -DOPENSSL_NO_SHARED=ON -DOPENSSL_MSVC_STATIC_RT=ON -A ${CMAKE_GENERATOR_PLATFORM} ) set(OPENSSL_LIB_SUFFIX ".lib") endif() # 获取OpenSSL安装路径 ExternalProject_Get_Property(openssl install_dir) set(OPENSSL_INCLUDE_DIR ${install_dir}/include) set(OPENSSL_LIBS_DIR ${install_dir}/lib) set(OPENSSL_LIBRARIES ${OPENSSL_LIBS_DIR}/libssl${OPENSSL_LIB_SUFFIX} ${OPENSSL_LIBS_DIR}/libcrypto${OPENSSL_LIB_SUFFIX} ) # 配置头文件目录(使用target级别的配置替代全局) target_include_directories(${PROJECT_NAME} PRIVATE ${OPENSSL_INCLUDE_DIR}) # 配置链接目录 link_directories(${OPENSSL_LIBS_DIR}) # 启用依赖关系,确保OpenSSL先编译完成 add_dependencies(${PROJECT_NAME} openssl) target_link_libraries(${PROJECT_NAME} PRIVATE Qt6::Core Qt6::Gui Qt6::Quick Qt6::Network Qt6::NetworkAuth Qt6::Sql Qt6::Positioning Qt6::Widgets Qt6::Xml Qt6::QuickWidgets Qt6::UiTools libzip::zip ${OPENSSL_LIBRARIES} ) set_property(TARGET ${PROJECT_NAME} APPEND PROPERTY QT_ANDROID_PACKAGE_SOURCE_DIR ${CMAKE_CURRENT_SOURCE_DIR}/android ) qt_finalize_executable(${PROJECT_NAME}) install(TARGETS ${PROJECT_NAME} RUNTIME DESTINATION . BUNDLE DESTINATION . LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} )
关键修改说明
- 平台分支处理:通过
if(ANDROID)和elseif(WIN32)分别配置对应平台的编译参数,Windows下添加OPENSSL_MSVC_STATIC_RT保证和项目运行时库一致,避免链接冲突。 - 修复依赖逻辑:取消注释
add_dependencies,确保主项目编译前完成OpenSSL的编译安装。 - 规范路径配置:用
target_include_directories替代全局include_directories,同时修正link_directories参数为库目录而非具体库文件。 - 统一库后缀:通过
OPENSSL_LIB_SUFFIX变量适配Android的.a静态库和Windows的.lib静态库。
额外注意事项
- OpenSSL 3.0及以上版本自带CMakeLists.txt,无需额外适配;若使用1.1.1等更旧版本,需改用官方
Configure脚本编译,此时需将ExternalProject_Add的CMAKE_ARGS替换为对应编译命令。 - Windows下需确保使用MSVC编译器,若用MinGW,需调整OpenSSL编译参数为MinGW适配配置。
内容的提问来源于stack exchange,提问作者user20973570
相关产品推荐
相关产品推荐

