OpenGauss内核中的线程系统和内存系统(MemoryContext)

目录

一、线程系统 

二、内存系统


一、线程系统 

opengauss使用了gcc提供的线程局部存储(TLS),定义了一个巨大的t_thrd结构体(knl_thrd_context),这个结构体定义在全局,不过是 __thread 修饰的线程局部存储。每个线程创建时,运行时库会为这个线程创建其独占的TLS变量,线程退出时运行时库也会释放这个线程的TLS变量。

opengauss的线程对应postgres的进程,opengauss的线程创建后,函数也经历了一遍完整的进程初始化流程,包括应用guc参数、t_thrd结构体的初始化。

opengauss中线程的初始化过程:

参考:

(21条消息) linux编程 - C/C++每线程(thread-local)变量的使用_落尘纷扰的博客-CSDN博客

Thread-Local (Using the GNU Compiler Collection (GCC))

t_thrd和u_sess的关系:

u_sess应该是user session的缩写,是线程局部的knl_session_context指针。

t_thrd.fake_session --> u_sess,两者是一 一对应,t_thrd包括了u_sess,但是,如果使用线程池的话,线程可能被分配给另一个session,一个线程(t_thrd)在同一时刻只会属于一个session,只有这个session结束,或者执行的事务结束后,运行它的线程才会分配给另一个session。

snapshot 信息存储在 u_sess 里面,事务Id由线程变量CurrentTransactionState存储。

二、内存系统

每个线程都有自己独立的一套内存上下文(MemoryContext),它们都是线程局部存储:

THR_LOCAL MemoryContext CurrentMemoryContext = NULL;

THR_LOCAL MemoryContext ErrorContext = NULL;
THR_LOCAL MemoryContext SelfMemoryContext = NULL;
THR_LOCAL MemoryContext TopMemoryContext = NULL;
THR_LOCAL MemoryContext AlignMemoryContext = NULL;

MemoryContext是PG的内存管理机制,为了避免编程实现中意外的内存泄露,PG不再简单地使用malloc/free,而是要求query运行中所需的内存必须在MemoryContext中分配,其间不释放内存,在query执行完成后释放整个MemoryContext所管理的内存(也许还包括MemoryContext)。

由于各个模块之间生命周期不同,每个模块都可以在生命周期开始时创建自己的MemoryContext,在生命周期结束时释放自己的MemoryContext。

如果模块之间或是生命周期之间有包含关系,各模块的MemoryContext可以组成一个树结构,父节点所在模块的生命周期应该包含(长于)子节点所在模块的生命周期。MemoryContext释放内存或删除时,要先删除子MemoryContext。

关于PostgreSQL  MemoryContext,我见过写的最好的文章,解释清晰不啰嗦不记流水账:

Postgresql源码赏析(4)--内存管理 - 简书 (jianshu.com)

还有源码中的文档:src/common/backend/utils/mmgr/README

其中比较重要的一个中间数据结构是AllocBlockData,它的后面就连着被分配的内存,只是它是个中间数据结构,分配时在它后面管理的内存中建立AllocChunkData,AllocBlockData后面的内存,怎么分配是没有限制的,但分配AllocChunkData的大小是有限制的。

研究源代码要注意思维模型深入到什么程度,而不是总以最底层的思维模型,来理解宏观系统,这就是博大和精深的差异。

AllocBlockData和它所连着的内存,是用malloc分配的。

在opengauss的程序运行中,MemoryContextDelete和MemoryContextReset会频繁的调用,以释放MemoryContext所管理的内存,并不需要pfree来释放MemoryContext中分配的内存,不过代码中,也有调用pfree的。

这篇文章介绍了调试内存问题的一些视图: openGauss内存管理初探 - 知乎 (zhihu.com)

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值