【问题标题】:Detect underlying platform/flavour in Cmake在 Cmake 中检测底层平台/风味
【发布时间】:2015-01-11 05:10:11
【问题描述】:

有人知道任何 cmake 变量或钩子或可以给我执行它的底层平台名称/风味名称的东西吗? 例如Linux-CentO Linux-Ubuntu Linux-SLES

我知道 cmake 有“CMAKE_SYSTEM”变量,但这无助于区分 linux 的风格,例如任何帮助表示赞赏。

编辑: 我刚刚读到可以使用 lsb_release 命令来完成?

【问题讨论】:

    标签: linux cmake platform


    【解决方案1】:

    以下 sn-p 使用有关底层 Linux 系统的信息填充 LSB_RELEASE_ID_SHORT cmake 变量:

    find_program(LSB_RELEASE_EXEC lsb_release)
    execute_process(COMMAND ${LSB_RELEASE_EXEC} -is
        OUTPUT_VARIABLE LSB_RELEASE_ID_SHORT
        OUTPUT_STRIP_TRAILING_WHITESPACE
    )
    

    例如,在 Ubuntu 上,它产生 Ubuntu

    【讨论】:

    • 不同的发行版将相同的东西放在不同的地方。这是使用这些发行版特定位置包含库的完美方式。
    • 可能想以某种方式对 linux 进行简洁的检查。只是自己学习 cmake。
    • 在 ARM64 的 Ubuntu 上测试,上面写着 No LSB modules are available.
    • 您的系统中是否安装了lsb_release 二进制文件?例如,在 Arch 上,它的包名为 lsb-release
    【解决方案2】:

    比检查文件系统上的文件稍微复杂一点的是从可用的 CMAKE_SYSTEM 变量中推断出最好的。例如,包含如下行的 CMakeLists.txt 文件:

    message("-- CMAKE_SYSTEM_INFO_FILE: ${CMAKE_SYSTEM_INFO_FILE}")
    message("-- CMAKE_SYSTEM_NAME:      ${CMAKE_SYSTEM_NAME}")
    message("-- CMAKE_SYSTEM_PROCESSOR: ${CMAKE_SYSTEM_PROCESSOR}")
    message("-- CMAKE_SYSTEM:           ${CMAKE_SYSTEM}")
    
    string (REGEX MATCH "\\.el[1-9]" os_version_suffix ${CMAKE_SYSTEM})
    message("-- os_version_suffix:      ${os_version_suffix}")
    

    当我运行 cmake . 时输出这个:

    -- CMAKE_SYSTEM_INFO_FILE: Platform/Linux
    -- CMAKE_SYSTEM_NAME:      Linux
    -- CMAKE_SYSTEM_PROCESSOR: x86_64
    -- CMAKE_SYSTEM:           Linux-2.6.32-573.7.1.el6.x86_64
    -- os_version_suffix:      .el6
    

    对于我的情况,.el6 足以区分。

    【讨论】:

      【解决方案3】:

      您可能必须自己编写这样的测试。这是一个可能的例子,刚刚用谷歌搜索:https://htcondor-wiki.cs.wisc.edu/index.cgi/fileview?f=build/cmake/FindLinuxPlatform.cmake&v=4592599fecc08e5588c4244e2b0ceb7d32363a56

      但是根据您的实际需要,测试可能会相当复杂。例如,作为基于 Debian 的操作系统的 Ubuntu 始终具有/etc/debian_version,而许多基于 RPM 的操作系统传统上具有/etc/redhat-release。在 Linux 标准基础 (LSB) 规范中有一个文件 /etc/os-release,但例如在 localhost 上,这个文件是空的,原因不明:)

      【讨论】:

      • 是的,问题很复杂,我正在考虑手动设置变量,但只是想看看是否有任何解决方案。
      • 好吧,我上面给出的可能实现之一。对于基于 SuSE 的您还可以查看 /etc/SuSE-release 另一个可能的解决方案是检测“主要风味”(例如,它是基于 RPM-、DEB- 还是基于 <YOU-NAME-THE-PACKAGE-MANAGER>,然后调用检测到的包管理器并查看对于here 中描述的特定包
      • 请注意,/etc/os-release 至少适用于所有基于 systemd 的发行版。
      【解决方案4】:

      我知道这是一个老问题,但到目前为止,仍然没有cmake 内置函数可以详细查找此信息。我已经实现了一个小实用函数,它在 Linux 上使用lsb_release 来查找一些相关的系统详细信息:

      function(get_linux_lsb_release_information)
          find_program(LSB_RELEASE_EXEC lsb_release)
          if(NOT LSB_RELEASE_EXEC)
              message(FATAL_ERROR "Could not detect lsb_release executable, can not gather required information")
          endif()
      
          execute_process(COMMAND "${LSB_RELEASE_EXEC}" --short --id OUTPUT_VARIABLE LSB_RELEASE_ID_SHORT OUTPUT_STRIP_TRAILING_WHITESPACE)
          execute_process(COMMAND "${LSB_RELEASE_EXEC}" --short --release OUTPUT_VARIABLE LSB_RELEASE_VERSION_SHORT OUTPUT_STRIP_TRAILING_WHITESPACE)
          execute_process(COMMAND "${LSB_RELEASE_EXEC}" --short --codename OUTPUT_VARIABLE LSB_RELEASE_CODENAME_SHORT OUTPUT_STRIP_TRAILING_WHITESPACE)
      
          set(LSB_RELEASE_ID_SHORT "${LSB_RELEASE_ID_SHORT}" PARENT_SCOPE)
          set(LSB_RELEASE_VERSION_SHORT "${LSB_RELEASE_VERSION_SHORT}" PARENT_SCOPE)
          set(LSB_RELEASE_CODENAME_SHORT "${LSB_RELEASE_CODENAME_SHORT}" PARENT_SCOPE)
      endfunction()
      

      将其添加到您的 CMakeLists.txt 并像这样使用它:

      if(CMAKE_SYSTEM_NAME MATCHES "Linux")
          get_linux_lsb_release_information()
          message(STATUS "Linux ${LSB_RELEASE_ID_SHORT} ${LSB_RELEASE_VERSION_SHORT} ${LSB_RELEASE_CODENAME_SHORT}")
      endif()
      

      如果您需要更多详细信息,请查看lsb_releaselsb_release -a 还能提供什么。

      请注意,并非每个 Linux 都安装了 lsb_release。大多数系统都提供它,但它不是强制性的。例如,在较新的 Ubuntu 上,它是桌面安装的默认设置,ubuntu-minimal 需要它。如果您的机器上应该缺少它,您可以使用sudo apt install lsb-release 安装它。

      【讨论】:

        【解决方案5】:

        在我的机器上

        CMAKE_SYSTEM_INFO_FILE == "Platform/Linux"
        CMAKE_SYSTEM_NAME == "Linux"
        CMAKE_SYSTEM == "Linux-<kernel version>"
        

        通过cmake --system-information 获得,我知道有人在他们自己的CMakeLists.txt 文件中使用所述宏,因此它们按预期工作,可能CMAKE_SYSTEM_NAME 是您真正想要的,但现在您可以得到这个 3 和就cmake而言,检查您机器的属性的命令。

        【讨论】:

        • 不幸的是,Linux 内核版本通常是给定 Linux 安装最不重要的特征。从技术上讲,我可以在我的工作站上设置一个非常古老的内核。好吧,那么我可能还需要降级或专门编译 LIBC ......好吧,使用一些“核心软件”。
        • @user3159253 这就是我添加命令的原因,该命令为您提供编译软件所需的任何信息
        • 不,我有一个基于 Ubuntu 的发行版,但它没有说明任何内容,它甚至没有告诉我我的实际发行版(KDE Neon)。必须使用uname
        【解决方案6】:

        基于thiagowfx answer,如果你想获取发行版的代号(如果有的话):

        execute_process(COMMAND lsb_release -cs
            OUTPUT_VARIABLE RELEASE_CODENAME
            OUTPUT_STRIP_TRAILING_WHITESPACE
        )
        

        例如在 Ubuntu 14.04 中,变量 RELEASE_CODENAME 将保持 trusty

        【讨论】:

          【解决方案7】:
          ### find our os (wins, centos, ubuntu, etc)
          set(VAR_OS "")
          IF(CMAKE_SYSTEM_NAME MATCHES "Linux")
                  MESSAGE(DEBUG "Linux")
                  execute_process (
                          COMMAND bash -c "awk -F= '/^ID=/{print $2}' /etc/os-release |tr -d '\n' | tr -d '\"'"
                          OUTPUT_VARIABLE outOS
                  )
                  MESSAGE(DEBUG "Linux os: ${outOS}")
          ELSEIF(CMAKE_SYSTEM_NAME MATCHES "Windows")
                  MESSAGE(DEBUG "Windows")
                  set(VAR_OS "wins")
          ELSE()
                  MESSAGE(FATAL "No OS detected!")
          ENDIF(CMAKE_SYSTEM_NAME MATCHES "Linux")
          

          【讨论】:

            猜你喜欢
            • 2012-04-02
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 2017-11-28
            • 2021-08-04
            • 2011-07-11
            相关资源
            最近更新 更多