golang glog文件名命令_Golang编译-编译前的准备工作

Golang的命令go类似于一个工具箱,当我们执行go build时,go会进行包依赖分析,然后创建若干子进程去执行compile命令编译源码。go的入口函数是cmd/go/main.go:main。下面以go build为例简略分析这个过程。下文对代码做了非常多的精简,逻辑也做了简化。

一 main流程

main.go:main函数的的流程非常简单,如图所示。

8a85c94164d0c769b3b743b97f1c8265.png
main.go:main流程

go在解析完参数后,会查找对应的command。所有支持的command在main.go:init中初始化,并由internal目录下的各个包实现相对应的command。

func 

如internal/work实现build命令,build.go中定义的CmdBuild如下所示。

var 

确定command后,main会调用command定义的Run函数,运行command。

二 运行command

func 

build.go初始化了CmdBuild的Run为runBuild函数。runBuild函数包含如下两个步骤

  • 包依赖关系分析
  • 根据依赖关系构造编译规则
  • 调用compile编译源码

三 依赖分析

依赖分析主要是由internal/load和src/go/build两个包实现,涉及到三个函数:

  • Import:分析go源文件,确定依赖关系。这一步涉及到语法解析。
  • load:根据包依赖关系,递归导入所依赖的包。
  • loadImport:先import,再load。

函数的调用关系如下图所示:

0c33c3bdf9cfec7b2520e2fa33230d5c.png
三个函数间的调用关系

3.1 Import函数分析:

3.1.1 首先查找包。下图所示代码在GOPATH中查找包。

for 

3.1.2 然后确定src/pkg/bin等目录

Found

3.1.3 最后解析源文件,确定依赖关系

for 

3.2 load函数分析

3.2.1 首先填充package信息,包括名称,路径等

p

3.2.2 然后递归地进行依赖分析

importPaths包括依赖包的导入路径,p.Internal.Imports包括依赖包的Package对象。LoadImport函数内部会调用loadImport函数。

imports 

总结下:经过以上的分析后,最终可以得到如下所示的依赖关系

bd677947695dea4e47d21a36104f47b1.png
package依赖关系示例

四 根据依赖关系构建编程规则

main包由LinkAction函数处理。下面的代码片段显示会根据main包的依赖关系再调用CompileAction函数构建编译规则。

a 

下图的CompileAction片段显示根据p.Internal.Imports中存在的依赖关系对象进行递归构建。

a 

五 调用compile编译源码

work包根据指定的编译规则进行编译

5.1 确定源代码,并调用gc函数

下面的代码片段显示从package对象中提出go, cxx等源文件名

gofiles 

5.2 gc函数会准备好相应的参数,并调用runOut函数

args 

5.3 runOut函数依赖exec包创建子进程,执行compile命令

cmdline 

那么最后子进行执行compile命令类似于下面这样的代码:

link命令类似于下面这样的代码:

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值