Go的交叉编译
Go的交叉编译
Go 1.5以前,交叉编译程序还是有一点麻烦的,你需要massive scripts t来编译和宿主机器不同的程序。
正如 comes with support for all architectures built in文章中介绍的, Go 1.5可就简单的多了,你只需设置 GOOS 和 GOARCH 两个环境变量就能生成所需平台的Go程序。
比如使用下面的代码测试:
package main
import "fmt"
import "runtime"
func main() {
fmt.Printf("OS: %s\nArchitecture: %s\n", runtime.GOOS, runtime.GOARCH)
}
编译它: $ GOOS=darwin GOARCH=386 go build
*** 跨系统编译
Mac下编译Linux和Windows平台64位可执行程序需要设置
Linux
CGO_ENABLED=0 GOOS=linux GOARCH=amd64 go build;
Windows
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build;
Linux下编译Mac和Windows平台64位可执行程序
Mac
CGO_ENABLED=0 GOOS=darwin GOARCH=amd64 go build;
Windows
CGO_ENABLED=0 GOOS=windows GOARCH=amd64 go build;
Windows下编译Mac和Linux平台64位可执行程序
Mac
SET CGO_ENABLED=0 // 禁用CGO
SET GOOS=darwin // 目标平台设定
SET GOARCH=amd64 // 64位系统
go build
Linux
SET CGO_ENABLED=0
SET GOOS=linux
SET GOARCH=amd64
go build
就可以生成运行在OS X
上的程序。
可用的OS和ARCH的值如下:
$GOOS |
$GOARCH |
|
---|---|---|
darwin |
386 |
|
darwin |
amd64 |
|
darwin |
arm |
|
darwin |
arm64 |
|
dragonfly |
amd64 |
|
freebsd |
386 |
|
freebsd |
amd64 |
|
freebsd |
arm |
|
linux |
386 |
|
linux |
amd64 |
|
linux |
arm |
|
linux |
arm64 |
|
linux |
ppc64 |
|
linux |
ppc64le |
|
netbsd |
386 |
|
netbsd |
amd64 |
|
netbsd |
arm |
|
openbsd |
386 |
|
openbsd |
amd64 |
|
openbsd |
arm |
|
plan9 |
386 |
|
plan9 |
amd64 |
|
solaris |
amd64 |
|
windows |
386 |
|
windows |
amd64 |
不同的操作系统下的库可能有不同的实现, 比如syscall库。go build没有内置的#define
或者预处理器之类的处理平台相关的代码取舍, 而是采用tag和文件后缀的方式实现。
tag方式
tag遵循一下规则
- a build tag is evaluated as the OR of space-separated options
- each option evaluates as the AND of its comma-separated terms
- each term is an alphanumeric word or, preceded by !, its negation
在文件的头部增加tag:
// +build darwin freebsd netbsd openbsd
可以有多个tag,之间是AND的关系
// +build linux darwin
// +build 386
注意tag和package中间需要有空行分隔,下面的例子是不对的:
// +build !linux
package mypkg // wrong
文件后缀方式
以_$GOOS.go为后缀的文件只在此平台上编译,其它平台上编译时就当此文件不存在。完整的后缀如:
_$GOOS_$GOARCH.go
如syscall_linux_amd64.go,syscall_windows_386.go,syscall_windows.go等。
Songzhibin