鍍金池/ 教程/ GO/ go env
go install
go clean
go list
go test
go doc與godoc
go build
go fix與go tool fix
go tool pprof
go run
go env
go tool cgo
標(biāo)準(zhǔn)命令詳解
go get
go vet與go tool vet

go env

命令go env用于打印Go語言的環(huán)境信息。其中的一些信息我們在之前已經(jīng)多次提及,但是卻沒有進(jìn)行詳細(xì)的說明。在本小節(jié),我們會(huì)對(duì)這些信息進(jìn)行深入介紹。我們先來看一看go env命令情況下都會(huì)打印出哪些Go語言通用環(huán)境信息。

表0-25 go env命令可打印出的Go語言通用環(huán)境信息

名稱 說明
CGO_ENABLED 指明cgo工具是否可用的標(biāo)識(shí)。
GOARCH 程序構(gòu)建環(huán)境的目標(biāo)計(jì)算架構(gòu)。
GOBIN 存放可執(zhí)行文件的目錄的絕對(duì)路徑。
GOCHAR 程序構(gòu)建環(huán)境的目標(biāo)計(jì)算架構(gòu)的單字符標(biāo)識(shí)。
GOEXE 可執(zhí)行文件的后綴。
GOHOSTARCH 程序運(yùn)行環(huán)境的目標(biāo)計(jì)算架構(gòu)。
GOOS 程序構(gòu)建環(huán)境的目標(biāo)操作系統(tǒng)。
GOHOSTOS 程序運(yùn)行環(huán)境的目標(biāo)操作系統(tǒng)。
GOPATH 工作區(qū)目錄的絕對(duì)路徑。
GORACE 用于數(shù)據(jù)競爭檢測的相關(guān)選項(xiàng)。
GOROOT Go語言的安裝目錄的絕對(duì)路徑。
GOTOOLDIR Go工具目錄的絕對(duì)路徑。

下面我們對(duì)這些環(huán)境信息進(jìn)行逐一說明。

CGO_ENABLED

通過上一小節(jié)的介紹,相信讀者對(duì)cgo工具已經(jīng)很熟悉了。我們提到過,標(biāo)準(zhǔn)go命令可以自動(dòng)的使用cgo工具對(duì)導(dǎo)入了代碼包C的代碼包和源碼文件進(jìn)行處理。這里所說的“自動(dòng)”并不是絕對(duì)的。因?yàn)楫?dāng)環(huán)境變量CGO_ENABLED被設(shè)置為0時(shí),標(biāo)準(zhǔn)go命令就不能處理導(dǎo)入了代碼包C的代碼包和源碼文件了。請看下面的示例:

hc@ubt:~/golang/goc2p/src/basic/cgo$ export CGO_ENABLED=0
hc@ubt:~/golang/goc2p/src/basic/cgo$ go build -x
WORK=/tmp/go-build775234613

我們臨時(shí)把環(huán)境變量CGO_ENABLED的值設(shè)置為0,然后執(zhí)行go build命令并加入了標(biāo)記-x。標(biāo)記-x會(huì)讓命令程序?qū)⑦\(yùn)行期間所有實(shí)際執(zhí)行的命令都打印到標(biāo)準(zhǔn)輸出。但是,在執(zhí)行命令之后沒有任何命令被打印出來。這說明對(duì)代碼包basic/cgo的構(gòu)建操作并沒有被執(zhí)行。這是因?yàn)?,?gòu)建這個(gè)代碼包需要用到cgo工具,但cgo工具已經(jīng)被禁用了。下面,我們再來運(yùn)行調(diào)用了代碼包basic/cgo中函數(shù)的命令源碼文件cgo_demo.go。也就是說,命令源碼文件cgo_demo.go間接的導(dǎo)入了代碼包C。還記得嗎?這個(gè)命令源碼文件被存放在goc2p項(xiàng)目的代碼包basic/cgo中。示例如下:

hc@ubt:~/golang/goc2p/src/basic/cgo$ export CGO_ENABLED=0
hc@ubt:~/golang/goc2p/src/basic/cgo$ go run -work cgo_demo.go
WORK=/tmp/go-build856581210
# command-line-arguments
./cgo_demo.go:4: can't find import: "basic/cgo/lib"

在上面的示例中,我們在執(zhí)行go run命令時(shí)加入了兩個(gè)標(biāo)記——-a-work。標(biāo)記-a會(huì)使命令程序強(qiáng)行重新構(gòu)建所有的代碼包(包括涉及到的標(biāo)準(zhǔn)庫),即使它們已經(jīng)是最新的了。標(biāo)記-work會(huì)使命令程序?qū)⑴R時(shí)工作目錄的絕對(duì)路徑打印到標(biāo)準(zhǔn)輸出。命令程序輸出的錯(cuò)誤信息顯示,命令程序沒有找到代碼包basic/cgo。其原因是由于代碼包basic/cgo無法被構(gòu)建。所以,命令程序在臨時(shí)工作目錄和工作區(qū)中都找不到代碼包basic/cgo對(duì)應(yīng)的歸檔文件cgo.a。如果我們使用命令ll /tmp/go-build856581210查看臨時(shí)工作目錄,也找不到名為basic的目錄。

不過,如果我們在環(huán)境變量CGO_ENABLED的值為1的情況下生成代碼包basic/cgo對(duì)應(yīng)的歸檔文件cgo.a,那么無論我們之后怎樣改變環(huán)境變量CGO_ENABLED的值也都可以正確的運(yùn)行命令源碼文件cgo_demo.go。即使我們在執(zhí)行go run命令時(shí)加入標(biāo)記-a也是如此。因?yàn)槊畛绦蛞廊豢梢栽诠ぷ鲄^(qū)中找到之前在我們執(zhí)行go install命令時(shí)生成的歸檔文件cgo.a。示例如下:

hc@ubt:~/golang/goc2p/src/basic/cgo$ export CGO_ENABLED=1
hc@ubt:~/golang/goc2p/src/basic/cgo$ go install ../basic/cgo
hc@ubt:~/golang/goc2p/src/basic/cgo$ export CGO_ENABLED=0
hc@ubt:~/golang/goc2p/src/basic/cgo$ go run -a -work cgo_demo.go
WORK=/tmp/go-build130612063
The square root of 2.330000 is 1.526434.
ABC
CFunction1() is called.
GoFunction1() is called.

由此可知,只要我們事先成功安裝了引用了代碼包C的代碼包,即生成了對(duì)應(yīng)的代碼包歸檔文件,即使cgo工具在之后被禁用,也不會(huì)影響到其它Go語言代碼對(duì)該代碼包的使用。當(dāng)然,命令程序首先會(huì)到臨時(shí)工作目錄中尋找需要的代碼包歸檔文件。

關(guān)于cgo工具還有一點(diǎn)需要特別注意,即:當(dāng)存在交叉編譯的情況時(shí),cgo工具一定是不可用的。在標(biāo)準(zhǔn)go命令的上下文環(huán)境中,交叉編譯意味著程序構(gòu)建環(huán)境的目標(biāo)計(jì)算架構(gòu)的標(biāo)識(shí)與程序運(yùn)行環(huán)境的目標(biāo)計(jì)算架構(gòu)的標(biāo)識(shí)不同,或者程序構(gòu)建環(huán)境的目標(biāo)操作系統(tǒng)的標(biāo)識(shí)與程序運(yùn)行環(huán)境的目標(biāo)操作系統(tǒng)的標(biāo)識(shí)不同。在這里,我們可以粗略認(rèn)為交叉編譯就是在當(dāng)前的計(jì)算架構(gòu)和操作系統(tǒng)下編譯和構(gòu)建Go語言代碼并生成針對(duì)于其他計(jì)算架構(gòu)或/和操作系統(tǒng)的編譯結(jié)果文件和可執(zhí)行文件。

GOARCH

GOARCH的值的含義是程序構(gòu)建環(huán)境的目標(biāo)計(jì)算架構(gòu)的標(biāo)識(shí),也就是程序在構(gòu)建或安裝時(shí)所對(duì)應(yīng)的計(jì)算架構(gòu)的名稱。在默認(rèn)情況下,它會(huì)與程序運(yùn)行環(huán)境的目標(biāo)計(jì)算架構(gòu)一致。即它的值會(huì)與GOHOSTARCH的值是相同。但如果我們顯式的設(shè)置了環(huán)境變量GOARCH,則它的值就會(huì)是這個(gè)環(huán)境變量的值。

GOBIN

GOBIN的值為存放可執(zhí)行文件的目錄的絕對(duì)路徑。它的值來自環(huán)境變量GOBIN。在我們使用go tool install命令安裝命令源碼文件時(shí)生成的可執(zhí)行文件會(huì)存放于這個(gè)目錄中。

GOCHAR

GOCHAR的值是程序構(gòu)建環(huán)境的目標(biāo)計(jì)算架構(gòu)的單字符標(biāo)識(shí)。它的值會(huì)根據(jù)GOARCH的值來設(shè)置。當(dāng)GOARCH的值為386時(shí),GOCHAR的值就是8。當(dāng)GOARCH的值為amd64時(shí)GOCHAR的值就是6。而GOCHAR的值5與GOARCH的值arm相對(duì)應(yīng)。

GOCHAR主要有兩個(gè)用途,列舉如下:

  1. Go語言官方的平臺(tái)相關(guān)的工具的名稱會(huì)以它的值為前綴。的名稱會(huì)以GOCHAR的值為前綴。比如,在amd64計(jì)算架構(gòu)下,用于編譯Go語言代碼的編譯器的名稱是6g,鏈接器的名稱是6l。用于編譯C語言代碼的編譯器的名稱是6c。而用于編譯匯編語言代碼的編譯器的名稱為6a。

  2. Go語言的官方編譯器生成的結(jié)果文件會(huì)以GOCHAR的值作為擴(kuò)展名。Go語言的官方編譯器6g在對(duì)命令源碼文件編譯之后會(huì)把結(jié)果文件go.6存放到臨時(shí)工作目錄的相應(yīng)位置中。

GOEXE

GOEXE的值會(huì)被作為可執(zhí)行文件的后綴。它的值與GOOS的值存在一定關(guān)系,即只有GOOS的值為“windows”時(shí)GOEXE的值才會(huì)是“.exe”,否則其值就為空字符串“”。這與在各個(gè)操作系統(tǒng)下的可執(zhí)行文件的默認(rèn)后綴是一致的。

GOHOSTARCH

GOHOSTARCH的值的含義是程序運(yùn)行環(huán)境的目標(biāo)計(jì)算架構(gòu)的標(biāo)識(shí),也就是程序在運(yùn)行時(shí)所在的計(jì)算機(jī)系統(tǒng)的計(jì)算架構(gòu)的名稱。在通常情況下,它的值不需要被顯式的設(shè)置。因?yàn)橛脕戆惭bGo語言的二進(jìn)制分發(fā)文件和MSI(Microsoft軟件安裝)軟件包文件都是平臺(tái)相關(guān)的。所以,對(duì)于不同計(jì)算架構(gòu)的Go語言環(huán)境來說,它都會(huì)是一個(gè)常量。

GOHOSTOS

GOHOSTOS的值的含義是程序運(yùn)行環(huán)境的目標(biāo)操作系統(tǒng)的標(biāo)識(shí),也即程序在運(yùn)行時(shí)所在的計(jì)算機(jī)系統(tǒng)的操作系統(tǒng)的名稱。與GOHOSTARCH類似,它的值在不同的操作系統(tǒng)下是固定不變的,同樣不需要顯式的設(shè)置。

GOPATH

這個(gè)環(huán)境信息我們在之前已經(jīng)提到過很多次。它的值指明了Go語言工作區(qū)目錄的絕對(duì)路徑。我們需要顯式的設(shè)置環(huán)境變量GOPATH。如果有多個(gè)工作區(qū),那么多個(gè)工作區(qū)的絕對(duì)路徑之間需要用分隔符分隔。在windows操作系統(tǒng)下,這個(gè)分隔符為“;”。在其它操作系統(tǒng)下,這個(gè)分隔符為“:”。注意,GOPATH的值不能與GOROOT的值相同。

GORACE

GORACE的值包含了用于數(shù)據(jù)競爭檢測的相關(guān)選項(xiàng)。數(shù)據(jù)競爭是在并發(fā)程序中最常見和最難調(diào)試的一類bug。數(shù)據(jù)競爭會(huì)發(fā)生在多個(gè)Goroutine爭相訪問相同的變量且至少有一個(gè)Goroutine中的程序在對(duì)這個(gè)變量進(jìn)行寫操作的情況下。

數(shù)據(jù)競爭檢測需要被顯式的開啟。還記得標(biāo)記-race嗎?我們可以通過在執(zhí)行一些標(biāo)準(zhǔn)go命令時(shí)加入這個(gè)標(biāo)記來開啟數(shù)據(jù)競爭檢測。在這種情況下,GORACE的值就會(huì)被使用到了。支持-race標(biāo)記的標(biāo)準(zhǔn)go命令包括:go test命令、go run命令、go build命令和go install命令。

GORACE的值形如“option1=val1 option2=val2”,即:選項(xiàng)名稱與選項(xiàng)值之間以等號(hào)“=”分隔,多個(gè)選項(xiàng)之間以空格“ ”分隔。數(shù)據(jù)競爭檢測的選項(xiàng)包括log_path、exitcode、strip_path_prefix和history_size。為了設(shè)置GORACE的值,我們需要設(shè)置環(huán)境變量GORACE?;蛘?,我們也可以在執(zhí)行g(shù)o命令時(shí)臨時(shí)設(shè)置它,像這樣:

hc@ubt:~/golang/goc2p/src/cnet/ctcp$ GORACE="log_path=/home/hc/golang/goc2p /race/report strip_path_prefix=home/hc/golang/goc2p/" go test -race

關(guān)于數(shù)據(jù)競爭檢測的更多細(xì)節(jié)我們將會(huì)在本書的第三部分予以說明。

GOROOT

GOROOT會(huì)是我們在安裝Go語言時(shí)第一個(gè)碰到Go語言環(huán)境變量。它的值指明了Go語言的安裝目錄的絕對(duì)路徑。但是,只有在非默認(rèn)情況下我們才需要顯式的設(shè)置環(huán)境變量GOROOT。這里所說的默認(rèn)情況是指:在Windows操作系統(tǒng)下我們把Go語言安裝到c:\Go目錄下,或者在其它操作系統(tǒng)下我們把Go語言安裝到/usr/local/go目錄下。另外,當(dāng)我們不是通過二進(jìn)制分發(fā)包來安裝Go語言的時(shí)候,也不需要設(shè)置環(huán)境變量GOROOT的值。比如,在Windows操作系統(tǒng)下,我們可以使用MSI軟件包文件來安裝Go語言。

GOTOOLDIR

GOTOOLDIR的值指明了Go工具目錄的絕對(duì)路徑。根據(jù)GOROOT、GOHOSTOS和GOHOSTARCH來設(shè)置。其值為$GOROOT/pkg/tool/$GOOS_$GOARCH。關(guān)于這個(gè)目錄,我們在之前也提到過多次。

除了上面介紹的這些通用的Go語言環(huán)境信息,還兩個(gè)針對(duì)于非Plan 9操作系統(tǒng)的環(huán)境信息。它們是CC和GOGCCFLAGS。環(huán)境信息CC的值是操作系統(tǒng)默認(rèn)的C語言編譯器的命令名稱。環(huán)境信息GOGCCFLAGS的值則是Go語言在使用操作系統(tǒng)的默認(rèn)C語言編譯器對(duì)C語言代碼進(jìn)行編譯時(shí)加入的參數(shù)。

如果我們要有針對(duì)性的查看上述的一個(gè)或多個(gè)環(huán)境信息,可以在go env命令的后面加入它們的名字并執(zhí)行之。在go env命令和環(huán)境信息名稱之間需要用空格分隔,多個(gè)環(huán)境信息名稱之間也需要用空格分隔。示例如下:

hc@ubt:~$ go env GOARCH GOCHAR
386
8

上例的go env命令的輸出信息中,每一行對(duì)一個(gè)環(huán)境信息的值,且其順序與我們輸入的環(huán)境信息名稱的順序一致。比如,386為環(huán)境信息GOARCH,而8則是環(huán)境信息GOCHAR的值。

go env命令能夠讓我們對(duì)當(dāng)前的Go語言環(huán)境進(jìn)行簡要的了解。通過它,我們也可以對(duì)當(dāng)前安裝的Go語言的環(huán)境設(shè)置進(jìn)行簡單的檢查。

上一篇:go install下一篇:go tool cgo