内存管理及优化和编译器 | 青训营笔记

33 阅读2分钟

内存管理及优化

内存分配

分块

目标: 为对象在heap上分配内存

提前将内存分块

  1. 调用系统调用mmap()向OS申请一大块内存
  2. 先将内存划分成大块,称作mspan
  3. 再将大块继续划分成特定大小的小块,用于对象分配
  • noscan mspan: 分配不包含指针的对象,GC不需要扫描
  • scan mspan: 分配包含指针的对象,GC需要扫描

对象分配: 根据对象的大小,选择最合适的块返回

缓存

TCMalloc(thread caching): 用于快速为对象分配内存空间

image.png

  • 每个p包含一个mcache用于快速分配,用于为绑定在p上的g分配对象
  • mcache管理一组mspan
  • 当mcache中的mspan分配完毕,向mcentral申请带有未分配块的mspan
  • 当mspan中没有分配的对象,mspan会被缓存在mcentral中,而不是立刻释放并归还给OS

内存管理优化

原因

  • 对象分配是非常高频的操作:每秒分配GB级别的内存
  • 小对象占比较高
  • go内存分配比较耗时

Balanced GC

  • 每个g都绑定一大块内存(1KB),称作GAB(goroutine allocation buffer)
  • GAB用于noscan类型的小对象(<128B)分配
  • 使用base,end,top三个指针维护GAB
  • 指针碰撞风格对象分配:无需和其他分配请求互斥,分配动作简单高效
  • 本质:将多个小对象的分配合并成一次大对象的分配

编译器和静态分析

编译器的结构

重要的系统软件

  • 识别符合语法和非法的程序
  • 生成正确且高效的代码

分析部分(前端)

  • 语法分析,生成词素
  • 语法分析,生成语法树
  • 语义分析,收集类型信息,进行语义检查
  • 中间代码生成,生成IR(intermediate representation)

综合部分(后端)

  • 代码优化,生成优化后的IR
  • 代码生成,生成目标代码