关于golang:Golang内部构件第1部分主要概念和项目结构

51次阅读

共计 1628 个字符,预计需要花费 5 分钟才能阅读完成。

FROM: https://www.altoros.com/blog/…

本系列博客文章供那些曾经相熟 Go 基础知识并心愿对它的内部结构有更深刻理解的人应用。本教程致力于 Go 源代码的构造以及 Go 编译器的一些外部细节。浏览此书后,您应该可能答复以下问题:

Go 源代码的构造是什么?
Go 编译器如何工作?
Go 中节点树的根本构造是什么?

入门

当您开始学习一种新的编程语言时,通常能够找到许多 ”hello-world” 教程,初学者指南和书籍,其中蕴含无关次要语言概念,语法甚至规范库的详细信息。然而,获取无关诸如语言运行时调配的次要数据结构的布局或调用内置函数时生成的汇编代码之类的信息并不是那么容易。答案显然在源代码中,然而依据咱们本人的教训,您能够花大量工夫在源代码中彷徨,而无需获得太大的提高。本文的目标是演示如何自行解密 Go 源码。

在开始之前,咱们当然须要咱们本人的 Go 源文件正本。获取它们没有什么特地的。只需执行以下命令。

git clone https://github.com/golang/go

请留神,main 分支中的代码正在一直更改,因而咱们在此博客文章中应用 release-branch.go1.4 分支。

理解我的项目构造

如果查看 Go 存储库的 / src 文件夹,则能够看到很多文件夹。其中大多数蕴含规范 Go 库的源文件。规范命名约定始终在此处利用,因而每个程序包都在一个文件夹内,其名称与该程序包名称间接对应。除了规范库外,还有很多其余的货色。咱们认为,最重要和最有用的文件夹在下表中列出。

文件夹 形容
/src/cmd/ 蕴含不同的命令行工具。
/src/cmd/go/ 蕴含 Go 工具的源文件,该工具下载并构建 Go 源文件并装置软件包。在执行此操作时,它将收集所有源文件并调用 Go 链接器和 Go 编译器命令行工具。
/src/cmd/dist/ 蕴含一个负责构建所有其余命令行工具和规范库中所有软件包的工具。您可能须要剖析其源代码,以理解在每个特定工具或程序包中应用了哪些库。
/src/cmd/gc/ 这是 Go 编译器与体系结构无关的局部。
/src/cmd/ld/Go 链接器的与体系结构无关的局部。与体系结构相干的局部位于带有“l”后缀的文件夹中,该后缀应用与编译器雷同的命名约定。
/src/cmd/5a/,6a,8a 和 9a 在这里,您能够找到实用于不同体系结构的 Go 汇编程序编译器。Go 汇编程序是一种汇编语言,不能准确地映射到根底计算机的汇编程序。取而代之的是,每种架构都有一个独特的编译器,能够将 Go 汇编程序转换为机器的汇编程序。您能够在官网文档中找到更多详细信息。
/src/lib9/,/src/libbio,/ src /liblink 在编译器,链接器和运行时包内应用的不同库。
/src/runtime/ 间接蕴含在所有程序中的最重要的 Go 软件包。它蕴含整个运行时性能,例如内存治理,垃圾回收,goroutines 创立等。

在 Go 编译器外部

如上所述,Go 编译器的与体系结构无关的局部位于 /src/cmd/gc/ 文件夹中。入口点位于 lex.c 文件中。除了一些常见的货色(例如解析命令行参数)之外,编译器还执行以下操作:

  • 初始化一些常见的数据结构。
  • 遍历所有提供的 Go 文件,并为每个文件调用 yyparse 办法。这导致理论的解析产生。Go 编译器应用 Bison 作为解析器生成器。该语言的语法在 go.y 文件中有残缺形容(我将在稍后提供更多详细信息)。后果,此步骤生成一个残缺的分析树,其中每个节点代表已编译程序的一个元素。
  • 递归地迭代生成的树几次,并进行一些批改,例如,为应隐式键入的节点定义类型信息,将某些语言元素(如类型转换)重写为对运行时包中某些函数的调用,并执行其余一些工作。
  • 解析树实现后执行理论的编译。节点被翻译成汇编代码。
  • 创立蕴含已生成的汇编代码和其余一些数据结构(例如,符号表)的指标文件,该文件已生成并写入磁盘。

Diving into the Go grammar

Understanding nodes

正文完
 0