在看 redis 1.0 源码时,总会看到需要申请内存的地方,如果申请不到需要大的内存就会返回 NULL,然后在调用层抛出 oom。

比如 listDup 中在复制特殊 value 或者加入新节点时都有可能返回 NULL

if (copy->dup) {
value = copy->dup(node->value);
if (value == NUL) {
...
return NULL;
}
}
...
if (listAddNodeTail(copy, value) == NULL) {
...
return NULL;
}

调用层中发现复制失败,抛出 oom

c->reply = listDup(slave->reply);
if (!c->reply) oom("listDup copying slave reply list");

oom 中执行 abort()

static void oom(const char *msg) {
fprintf(stderr, "%s: Out of memory\n",msg);
fflush(stderr);
sleep(1);
abort();
}

然后我就想到了 golang 的 make/new,平时都不会遇到 oom 的情况,感觉每次 make/new 都会成功,并且这两个函数都没有特殊返回值来标识失败的情况,因此在底层应该是做了处理。

由于之前在 mapassign 中看到分配桶的情节,最终在 mallocgc 函数中找到了目标函数 allocLarge

// allocLarge allocates a span for a large object.
func (c *mcache) allocLarge(size uintptr, noscan bool) *mspan {
if size+_PageSize < size {
throw("out of memory")
}
npages := size >> _pageShift
if size&_PageMask != 0 {
npages++
}
// Deduct credit for this span allocation and sweep if
// necessary. mHeap_Alloc will also sweep npages, so this only
// pays the debt down to npage pages.
deductSweepCredit(npages*_PageSize, npages)
spc := makeSpanClass(0, noscan)
s := mheap_.alloc(npages, spc)
if s == nil {
throw("out of memory")
}
...
}

throw 最终调用 fatalthrow

// fatalthrow implements an unrecoverable runtime throw. It freezes the

// system, prints stack traces starting from its caller, and terminates the

// process.

最终也是终止程序,看上去和 abort 一样

嗯,既然 golang 已经做了这部工作,那我就需要担心内存不够如何处理的问题了(虽然很大概率遇不到)

【小记】如果 golang 内存不够了怎么办的更多相关文章

  1. golang内存分配

    golang内存分配 new一个对象的时候,入口函数是malloc.go中的newobject函数 func newobject(typ *_type) unsafe.Pointer { flags ...

  2. golang 内存监控

    golang 内存监控 - 简书 https://www.jianshu.com/p/38dc129b6870

  3. Golang内存管理

    Golang 内存管理 原文链接[http://legendtkl.com/2017/04/02/golang-alloc/] Golang 的内存管理基于 tcmalloc,可以说起点挺高的.但是 ...

  4. Golang内存模型

    Ref: https://golang.org/ref/mem 简介 golang内存模型,主要说明了如下问题.在一个goroutine中读取变量,而该变量是由其他goroutine赋值的,这种情况下 ...

  5. 记一次golang内存泄露

    记一次golang内存泄露 最近在QA环境上验证功能时,发现机器特别卡,查看系统内存,发现可用(available)内存仅剩200多M,通过对进程耗用内存进行排序,发现有一个名为application ...

  6. [golang]内存不断增长bytes.makeSlice

    ------------------------------------------ 2015.7月更新 后面发现这里其实有一个sb的问题,在于内存回收和释放. 每个http请求,都会带一个http. ...

  7. 图解golang内存分配机制 (转)

    一般程序的内存分配 在讲Golang的内存分配之前,让我们先来看看一般程序的内存分布情况: 以上是程序内存的逻辑分类情况. 我们再来看看一般程序的内存的真实(真实逻辑)图: Go的内存分配核心思想 G ...

  8. golang 内存模型

    1,是什么 是一套规范.内存操作指导 解决多线程编程的 程序的 原子性,有序性,可见性(主要)的问题. 多核操作系统,会存在缓存不一致的情况,说到底是一个同步的问题. 2, 内容 内存模型,除了定义了 ...

  9. Golang内存分配内置函数之new函数

    new函数用来分配内存,主要分配值类型,比如int.float32.struct等,返回的是指针 package main import ( "fmt" ) func main() ...

  10. golang 内存分析/动态追踪

    如果你的go程序是用http包启动的web服务器,你想查看自己的web服务器的状态.这个时候就可以选择net/http/pprof.你只需要引入包_"net/http/pprof" ...

随机推荐

  1. pg高可用方案repmgr带witness搭建

    一.总体架构 操作系统版本: linux redhat7.6pg版本: 12.2repmgr版本 5.2192.168.3.73 主库: repmgr+master192.168.3.74 从库1: ...

  2. MySQL 修改字段子表中的顺序

    修改字段排列位置 ALTER TABLE 表名 MODIFY 字段名1 数据类型 FIRST|AFTER 字段名2 参数说明 FIRST,可选参数 将字段1,修改为表的第一个字段. AFTER 字段名 ...

  3. 2022-02-17 Python学习笔记

    2022-02-17 22:51:30 由于中文注释会导致报错,所以文件开头要加一行注释 #coding:utf-8 file = open('文件路径路径',w)#w表示没有就创建文件,有就打开 查 ...

  4. Python 闭包,生成式,推导式

    闭包概念 闭包,又称闭包函数或者闭合函数,其实和前面讲的嵌套函数类似, 不同之处在于,闭包中外部函数返回的不是一个具体的值,而是一个函数.一般情况下,返回的函数会赋值给一个变量,这个变量可以在后面被继 ...

  5. CodeGym自学笔记12——类名

    类的全名 类的全名由所有包的名称(由句点分隔)和类名组成. "要在代码中使用类,你需要指出类的全名.你也可以使用类的短名称,即只使用类名,但你需要'导入类'.这意味着在声明类之前,你要指出单 ...

  6. A调用B方法,@Transactional事务问题

    总结:方法A调用方法B:1.如果只有A加@Transactional注解:则AB在同一事务中,任意异常都回滚:2.如果只有B加@Transactional注解:AB方法为同一类,事务失效任意异常都不回 ...

  7. 四、流程控制、break、continue、return

    一. 程序流程控制概述 流程控制语句是用来控制程序中各语句执行顺序的语句,可以把语句组合成能完成一定功能的小逻辑模块. 流程控制方式采用结构化程序设计中规定的只有三种基本流程结构,即:1.顺序结构程序 ...

  8. myJRebel 已不可用

    周末在家里撸代码,突然 IDEA 提示 JRebel 需要激活. 原来一直使用的 myJRebel 的激活码,天真的以为是我的网络问题,尝试重新激活,结果不管用,就想去 myJrebel 的网站上去看 ...

  9. 沁恒蓝牙系列芯片USB烧录故障排查

    目录 使用USB烧录时让ISP工具能够识别芯片的操作是按住评估板上的"Download"按键,或者将PB22短接到GND,同时给板子上电.若是第一次拿到芯片,codeflash中是 ...

  10. Request processing failed;

    用 ssm 框架修改数据库数据时,出现了 Request processing failed; nested exception is org.mybatis.spring.MyBatisSystem ...