簡體   English   中英

檢查 Makefile 中的 gcc 版本?

[英]Checking the gcc version in a Makefile?

我想使用一些舊 gcc 版本中不可用的 gcc 警告開關(例如 -Wtype-limits)。

是否有一種簡單的方法可以檢查 gcc 版本,並且僅在使用最近的 gcc 時才添加這些額外選項?

我不會說這很容易,但是您可以使用 GNU make 的shell函數來執行像gcc --version這樣的 shell 命令,然后使用ifeq條件表達式來檢查版本號並適當地設置您的CFLAGS變量。

這是一個快速示例生成文件:

CC = gcc
GCCVERSION = $(shell gcc --version | grep ^gcc | sed 's/^.* //g')
CFLAGS = -g

ifeq "$(GCCVERSION)" "4.4.3"
    CFLAGS += -Wtype-limits
endif

all:
        $(CC) $(CFLAGS) prog.c -o prog

編輯:沒有ifgt 但是,您可以使用 shell expr命令進行大於比較。 這是一個例子

CC = gcc
GCCVERSIONGTEQ4 := $(shell expr `gcc -dumpversion | cut -f1 -d.` \>= 4)
CFLAGS = -g

ifeq "$(GCCVERSIONGTEQ4)" "1"
    CFLAGS += -Wtype-limits
endif

all:
        $(CC) $(CFLAGS) prog.c -o prog

將完整的 3 部分 gcc 版本(不僅是第一個數字)轉換為數字格式,適合比較(例如40701 )使用

gcc -dumpversion | sed -e 's/\.\([0-9][0-9]\)/\1/g' -e 's/\.\([0-9]\)/0\1/g' -e 's/^[0-9]\{3,4\}$/&00/'

這解決了任何版本部分中出現兩位數的可能性,以及在gcc -dumpversion輸出中丟失版本的第三部分的gcc -dumpversion (在一些早期的 gcc 版本中就是這種情況)。

因此,要測試 makefile 中的版本,請使用類似的內容(注意最后一個 sed 命令中的$$

GCC_GTEQ_472 := $(shell expr `gcc -dumpversion | sed -e 's/\.\([0-9][0-9]\)/\1/g' -e 's/\.\([0-9]\)/0\1/g' -e 's/^[0-9]\{3,4\}$$/&00/'` \>= 40702)
ifeq "$(GCC_GTEQ_472)" "1"
  ...
endif

我剛遇到這個問題,我需要測試 gcc 的前兩位數字,並且想要一個比上面聰明的 sed 黑客更易讀的選項。 我使用 bc 進行比較,因為它支持浮點數(expr 將非整數視為字符串):

GCC_VER_GTE44 := $(shell echo `gcc -dumpversion | cut -f1-2 -d.` \>= 4.4 | bc )
ifeq ($(GCC_VER_GTE44),1)
...
endif

如果他們在 gcc 4.9 之后發布 gcc 4.10,那么一些 sed hacking 是必要的,但這仍然非常可讀:

GCC_VER_GTE44 := $(shell echo `gcc -dumpversion | cut -f1-2 -d.` \>= 4.4 | sed -e 's/\./*100+/g' | bc )
ifeq ($(GCC_VER_GTE44),1)
...
endif

我根據上面的答案制作了一個現成的 IF_GCC 宏:

MY_GCC_VERSION=$(if $(GCC_VERSION),$(GCC_VERSION),$(GCC_DEFAULT_VER))
MY_GCC_TOINT=$(shell echo $(1) | sed -e 's/\.\([0-9][0-9]\)/\1/g' -e 's/\.\([0-9]\)/0\1/g' -e 's/^[0-9]\{3,4\}$$//')
MY_IF_GCC=$(if $(shell test $(call MY_GCC_TOINT, $(MY_GCC_VERSION)) -$(1) $(2) || echo 0),$(4),$(3)) 
GCC_DEFAULT_VER:=$(firstword $(shell cc -V 2>&1 | grep default | sed -r 's/( *)([0-9.]+),(.*)/\2/g')) 

用法: $(call MY_IF_GCC,ge,30305,-fan_option_for_gcc_ge_3.3.5)

作為第二個參數,您可以使用 test(1) 支持的任何運算符:eq、gt、lt、ge、le 等。

如果 cc -V 對您不起作用,請將其替換為 gcc -dumpversion 或任何合適的

希望有幫助。

你在使用類似 autoconf 的東西嗎?

可能值得通過啟用標志的 gcc 調用“虛擬”編譯,如果由於編譯器無法識別該標志而失敗,您可以退回到不使用較新警告選項的命令行。

跟隨克里斯,但使用 awk

GCC_VER_GTE44 := $(shell expr $$(gcc -dumpversion | awk -F. '{print $$3+100*($$2+100*$$1)}') \>= 40400)

注意$需要在 Makefile 中使用另一個$進行轉義。

我發現了這個,並認為它真的很聰明。 它使用較少的 shell 調用實現了 >、>=、< 和 <=:

GCC_VERSION := $(shell gcc -dumpversion)
VERSION := 7.4.0

ifeq ($(VERSION),$(firstword $(sort $(GCC_VERSION) $(VERSION))))
    # stuff that requires GCC_VERSION >= VERSION
endif

此示例顯示 >=。 您可以使用 ifneq 和 $(lastword) 的組合來實現 >、<= 或 <。

參考:

https://lists.gnu.org/archive/html/help-make/2006-04/msg00065.html

我認為awk是用於此目的的更好工具,因為它可以將版本字符串拆分為$1 $2$3然后在一個命令中與><>=等進行比較。

如果表達式為假, awk省略整行,這是ifdef ifdef將空字符串視為未定義。

GCC_VERSION_GT_75 = $(shell gcc -dumpfullversion -dumpversion | awk -F. '$1 > 7 && $2 > 5')
ifdef GCC_VERSION_GT_75
    # stuff that requires gcc version > 7.5
endif

有時您想顯示帶有額外信息的版本。

GCCVER=$(gcc --version | awk '/gcc /{print $0;exit 0;}')
echo $GCCVER

gcc (Ubuntu 4.8.1-2ubuntu1~12.04) 4.8.1

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM