Golang源码编译的一次实践

前言

Google为Golang提供了源码和针对常用CPU架构的预编译包,但也有一些Linux嵌入式设备CPU架构实际上也是支持的,不过需要我们通过Golang源码编译目标嵌入式设备所需的编译包,然后部署在相应的嵌入式设备上使用。

检查嵌入式设备的操作系统

我们需要开发的一台设备是一台嵌入式的Linux设备,通过SSH连接到该设备,执行以下命令:

bash 复制代码
lsb_release -a

获得操作系统的信息如下:

bash 复制代码
Distributor ID: Ubuntu
Description:    Ubuntu 20.04.2 LTS
Release:        20.04
Codename:       focal

获取到操作系统信息后,可为后面Golang的环境变量设置提供必要的信息支持。

检查嵌入式设备的CPU架构

执行以下命令:

bash 复制代码
uname -m

获取CPU架构信息如下:

bash 复制代码
armv7l

这表示设备或系统是基于 ARMv7 架构的。 ARMv7 是 ARM(Advanced RISC Machines)架构的第七代版本,广泛用于许多嵌入式设备和移动设备,如智能手机、平板电脑和单板计算机。ARMv7 架构包含多个变体和配置,包括 ARMv7-A(应用程序处理器)、ARMv7-R(实时处理器)和 ARMv7-M(微控制器)。

"armv7l" 标识符中的 "l" 表示 "little-endian",这是指存储字节序的一种方式。在 little-endian 字节序中,较小的字节位于较低的内存地址处,而较大的字节位于较高的内存地址处。

检查Golang的预发行包并安装测试

Golang官网的release列表中,可以看到比较接近的发行版是linux-arm64和linux-armv6l,通过stackoverflow查询,有答主回答arm7与arm6指令兼容。 将linux-armv6l安装到设备后,执行以下命令:

bash 复制代码
go version

可以正常返回go的版本信息。 测试运行程序:

golang 复制代码
package main

import "fmt"

func main() {
	fmt.Printf("hello, world!\n")
}

则输出:

bash 复制代码
cannot execute binary file: Exec format error

这说明事实上linux-armv6l并不能在armv7l上正常工作,因此需要使用源码编译Golang包。

通过源码编译Golang包

Golang源码编译的方法说明

从Golang官网的源码编译说明页面可以看到(建议完整读完说明):从1.5版本开始,Golang的编译工具链是使用Golang实现的,官方编译包自带该工具链。 因此通过源码编译目标平台的包的方法是:编译机器安装好Golang环境(1.5版本以上,最好接近希望使用的目标版本),然后使用该Golang环境自带的工具链,使用目标平台的参数编译源码,编译成功的结果为一个压缩文件,将其拷贝到目标平台的设备上解压,配置环境后即可使用。

Mac OSX下编译(Linux下编译方法相同)

在解压后的golang源码的src目录下,执行以下命令:

ini 复制代码
GOOS=linux GOARCH=arm GOARM=7 ./bootstrap.bash

编译需要些时间,编译成功后,将在源码上层目录生成以下压缩文件:

go 复制代码
go-linux-arm-bootstrap.tbz

将编译包安装到目标设备

将go-linux-arm-bootstrap.tbz重命名为go.tbz,然后上传到目标设备,执行以下命令解压:

bash 复制代码
tar -xvf go.tbz -C /usr/local

解压后,可以看到在/usr/local下面有go目录,即我们熟悉的go环境目录。

然后添加环境变量(ubuntu为~/.profile):

ruby 复制代码
export PATH=$PATH:/usr/local/go/bin
export GOPATH=$HOME/go
export PATH=$PATH:$GOPATH/bin

更新生效:

bash 复制代码
source ~/.profile

编译包安装测试

验证Golang版本:

go 复制代码
go version

写一个hello.go:

go 复制代码
package main

import "fmt"

func main() {
	fmt.Printf("hello, world\n")
}

然后在命令行执行:

go 复制代码
go run hello.go

正确的结果如下:

复制代码
hello, world
相关推荐
zhuyasen15 小时前
当Go框架拥有“大脑”,Sponge框架集成AI开发项目,从“手写”到一键“生成”业务逻辑代码
后端·go·ai编程
写代码的比利17 小时前
Kratos 对接口进行加密转发处理的两个方法
go
chenqianghqu18 小时前
goland编译过程加载dll路径时出现失败
go
马里嗷21 小时前
Go 1.25 标准库更新
后端·go·github
郭京京1 天前
go语言redis中使用lua脚本
redis·go·lua
心月狐的流火号1 天前
分布式锁技术详解与Go语言实现
分布式·微服务·go
一个热爱生活的普通人1 天前
使用 Makefile 和 Docker 简化你的 Go 服务部署流程
后端·go
HyggeBest2 天前
Golang 并发原语 Sync Pool
后端·go
来杯咖啡2 天前
使用 Go 语言别在反向优化 MD5
后端·go