之前学习的虚拟内存机制,以及它如何为系统提供如此多的有功功能,随着这种大型连续字节数组的抽象,现在一旦我们获得了大量的字节,我们必须管理它,我们必须有一些机制来管理和使用这些资源,本周的主题是存储器的分配,以及储存器分配器的工作原理,以及如何使用它们来管理内存中的虚拟系统。

Basic concepts

Dynamic Memory Allocation 动态内存分配

动态储存器分配器的基本思想是:应用程序使用它去操纵虚拟内存,去构造、分配以及释放虚拟存储器片,在你的程序中会需要这些虚拟存储器,而且这个存储器在称为堆的虚拟存储器区域汇总被维护,所有语言都有一些用来分配和操纵动态存储器的机制,在C中,使用的是malloc的方式。但是像Java这样的语言使用的是其他新的方式,

Dynamic Memory Allocation

分配器将堆维护为连续的块的集合,块可以被分配或者被释放,被分配意味着它们被某些应用程序使用,空闲意味着可供应用程序使用,有两种类型的分配器。你可以在C中找到的那种分配器,比如malloc包,这种分配器,应用程序将决定是否显示分配内存,并在应用程序完成后是否显示的释放内存,所以系统不会释放你分配的任何内存,除非你通过调用free函数显示的释放内存。但是还有其他语言支持隐式分配器,在这些隐式分配器中,程序员显示地分配内存,释放的内存的负担从应用程序转移到系统,并且它使用称为垃圾收集的过程隐式的释放了这些内存。所以像Java,ML,Lisp这样的语言都支持隐式分配器(implicit allocatros)

这节课主要讲的是显示分配器。

The malloc Package

C语言中的分配器由C标准库中一组交malloc包的函数提供,它把以字节作为单元的参数作为函数的输入参数,然后返回一个指向内存块的指针,该内存块至少包含所声明的大小的字节,并且该块在x86系统上以8字节对齐,在x86-64系统上以16字节对齐。

程序员通过调用free函数释放内存,它以先前调用malloc时返回的指针作为参数。

使用sbrk函数可以调整heap的大小。

malloc Example 分配例子

上面的代码示例中,我们有一个指向整形的指针p,我们调用malloc,我们想要分配一个大小为n的整形数组,malloc返回一个泛型指针 void*,我们将它转换为指向整形的指针,以便于编译器编译,然后将其分配给p,我们检查返回值是否为空,应该指出它在出错时返回0,所以我们会重新检查这个指针是否是空指针,如果他为空,则打印错误,一旦我们得到了指针,我们就可以像对待一个数组一样对待他,完成分配这块内存后,我们通过只用指针p调用free来释放。

Assumptions Made in This Lecture 这节课做的假设

这节课要看看如何实现malloc和free等功能,这个课要做一些假设,我们知道内存的地址是按照字节的地址,我们只是关注以字为大小的单位,这里以字来说明。我们假设word字是4个字节,他们基本上是一个int的大小,这些字所构成的块能被分配或者释放。

Allocation Example 分配例子

Constraints限制

唯一的一个事实是,当它释放某些东西的时候,必须使用来自之前调用malloc时所返回的指针,malloc运行或者像malloc这样的分配器在很多不同的约束条件下运行,它们无法控制分配块的大小或者数量,因为他们无法控制应用程序正在做的事情,如果应用程序调用malloc malloc必须立即响应,当然必须从可用内存中分配块,一般来说不能触及任何已经分配的块,一旦它分配了那个块 那么该块就属于那个应用程序,而malloc包不能触及它,这意味着分配器不能移动块,比如分配器无法将已经分配的块放到一起以达到压缩块的目的,

Performance Goal: Throughput 吞吐量

分配器有趣的原因还有:它包括了时间和空间上的权衡,这是一种空间和性能的权衡,你正尝试使其运行得尽可能快,但是你希望尽可能高效地使用堆中的虚拟内存,我们定义了这些速度和内存效率指标。我们使用了两个指标,一个称为吞吐量

吞吐量评价malloc处理来自应用程序的这些请求的效率。

Performance Goal: Peak Memory Utilization峰值内存利用率

峰值内存利用率是一种衡量多少有用空间的标准,它衡量分配器使用堆的效率有多大,去衡量分配器在实现中必须使用的数据结构中的各种开销上浪费了多少,我们将定义一个payload,一个应用程序调用malloc以请求一定大小的块,该块称为payload有效载荷。因此如果我们使用10个字节的参数调用了malloc,我们要求一个有效载荷至少为10大小的块,我们请求的10个字节称为有效负载,该块中的其他内容都是overhead开销。

在完美的分配器中,聚合有效负载等于内存量,等于所有已分配块的总大小,因为没有开销,每个块都是有效载荷。

如果我们假设heap是单调非递减的,所有它总是在变大,这是简单的假设,真正的malloc包不是这样,

Uk就是我们的利用率,当利用率为1时,代表完美的分配。单实际上,在分配器将要放置的每个块的内部,都有数据结构和其他内容,这样会没法得到完美的利用率,一个显而易见的事是,因为块必须对齐,如果它们是16字节对其的,那么块必须以16字节边界开始,因此如果你请求2字节的有效负载,那么你有很多浪费的字节。因此有一些开销是不可避免的,要做的就是尽量减小损失。

Fragmentation碎片

我们刚才谈到的例子就是我们称之为fragmentation【碎片】的例子,而且有两种类型的碎片,

Internal Fragmentation

内部随便是刚才谈论到的,可能是由块中的填充或分配器需要的块中的某种数据结构引起的。

External Fragmentation

Knowing How Much to Free

Keeping Track of Free Blocks

如何记录free block ?

方法一:隐式列表

方法二:显示列表 利用块中的一些字,去创建某种链接列表,单链或者双链表,

方法三:单独的free list    list拥有不同的size

方法四:通过平衡树分割

Implicit free lists

Method 1: Implicit List

Detailed Implicit Free List Example

记住块的有效负载总是必须从8字节边界开始,是有效负载,而不是前面保存size的区域。

Implicit List: Finding a Free Block

最佳适配(best fit)法看起来会带来更大的消耗,因为你在找到合适的东西之前,你必须一直寻找,你必须扫描所有的空闲块,然后选择最好的区域,但是它有一个很好的属性,它提高了内存利用率,这是一个典型时空权衡的例子,它的速度较慢,但是提供了我们使用内存的效率。

Implicit List: Allocating in Free Block

Implicit List: Freeing a Block

Implicit List: Bidirectional Coalescing

Constant Time Coalescing

如果是case 1 我们只需要将分配状态设置为空闲。

如果是case2,我们要做的是检查前一个块的边界标记,我们看到它被分配,所以没什么可以做的,我们使用n跳转到下一个块的头部,我们看到它的下一个状态是空闲的,所以这两个块需要被合并,我们只需要将两个大小相加就可以创建更大的合并块,并将其分配状态设置为零。

如果是case3,和case2差不多

当我们检查前后块都是空的时候,我们就创造一个单个块,和为三个块。

Disadvantages of Boundary Tags

No Boundary Tag for Allocated Blocks (1)

No Boundary Tag for Allocated Blocks (2)

Summary of Key Allocator Policies

Implicit Lists: Summary

CMU 15-213 Introduction to Computer Systems学习笔记(18) Dynamic Memory Allocation: Basic Concepts相关推荐

  1. Introduction to Computer Networking学习笔记(十五):Queue Model 包交换中的缓冲模型

    本章知识点比较零散,因此一篇文章进行总结,并且不具有连贯性,仅记录自己认为有价值的内容. 将较大的包拆分为小包进行传输,可以减小端对端延迟,原因如下图: 数据传输时,突发大量的数据包会增加延迟,简单周 ...

  2. Python学习笔记18:实操案例十五(记录用户登录日志,模拟淘宝客服自动回复)

    Python学习笔记18:实操案例十五(记录用户登录日志,模拟淘宝客服自动回复) 网课传送门:https://www.bilibili.com/video/BV1Sw411Z779?p=168& ...

  3. Hadoop学习笔记—18.Sqoop框架学习

    Hadoop学习笔记-18.Sqoop框架学习 一.Sqoop基础:连接关系型数据库与Hadoop的桥梁 1.1 Sqoop的基本概念 Hadoop正成为企业用于大数据分析的最热门选择,但想将你的数据 ...

  4. Ext.Net学习笔记18:Ext.Net 可编辑的GridPanel

    Ext.Net GridPanel 有两种编辑模式:编辑单元格和编辑行. 单元格编辑: 行编辑: 可以看出,单元格编辑的时候,只有单元格会进入编辑模式,而行编辑模式中则对编辑行的所有可编辑字段统一进行 ...

  5. 华为HCIA-datacom 学习笔记18——SDN与NFV概述

    华为HCIA-datacom 学习笔记18--SDN与NFV概述 SDN与NFV概述 1.计算机时代的演进 1.1大型机 专门的硬件 专门的操作系统 专门的应用.(稳定性能好,但封闭) 1.2小型机 ...

  6. 2020-4-12 深度学习笔记18 - 直面配分函数 5 ( 去噪得分匹配,噪声对比估计NCE--绕开配分函数,估计配分函数)

    第十八章 直面配分函数 Confronting the Partition Function 中文 英文 2020-4-8 深度学习笔记18 - 直面配分函数 1 ( 配分函数概念,对数似然梯度) 2 ...

  7. CMU15-213学习笔记(七)Dynamic Memory Allocation

    CMU15-213学习笔记(七)Dynamic Memory Allocation 动态内存分配 程序员通过动态内存分配(例如 malloc)来让程序在运行时得到虚拟内存.动态内存分配器会管理一个虚拟 ...

  8. 【计算机网络学习笔记18】防火墙技术、入侵检测技术

    [计算机网络学习笔记18]防火墙技术.入侵检测技术 一.防火墙 防火墙 (firewall) :一种访问控制技术,通过严格控制进出网络边界的分组,禁止任何不必要的通信,从而减少潜在入侵的发生,尽可能降 ...

  9. 鸟叔的linux私房菜:第0章 计算机概论学习笔记(Learning Notes for Basic Computer Theory)

    本博客是针对<鸟叔的Linux私房菜 基础学习篇 第四版>的第0章 计算机概论的学习笔记. 1 电脑辅助人脑的好工具 11 计算机硬件的五大单元 12 一切设计的起点CPU的架构 其它单元 ...

  10. cs224w(图机器学习)2021冬季课程学习笔记18 Colab 4:异质图

    诸神缄默不语-个人CSDN博文目录 cs224w(图机器学习)2021冬季课程学习笔记集合 文章目录 Question 1. DeepSNAP异质图简介 1.1 Question 1.1:分配Node ...

最新文章

  1. LeetCode实战:设计循环双端队列
  2. HTML 表单(form) 使用详解
  3. MySQL选择数据库(MySQL USE语句)
  4. SQL-left(right,inner) join
  5. ./sqlplusSP2-0667: Message file sp1lang.msb not found。SP2-0750: You may need to set ORACLE_HOME t
  6. 使用代码创建SAP Sales area
  7. Prefactoring——Introduction
  8. (1)H5实现音乐播放器【正在播放-歌词篇】
  9. LINUX警告:检测到时钟错误。您的创建可能是不完整的。-转
  10. 一块神奇的树莓派电子板竟让我学会了Linux系统
  11. Python细节面试题--小整数对象池和大整数对象池
  12. 爬楼梯算法-java(递归与非递归)
  13. unity商店里下载的资源保存路径
  14. 【福利贴】教你如何移动联通电信免流
  15. 高通SDM845平台Sensor学习——3.SLPI(Physical Sensor)
  16. 国内小程序生态服务平台即速应用完成5000万元A+轮融资...
  17. kali系统破解WiFi密码(二)
  18. 网上讲的比较清晰的VOT跟踪评价指标EAO
  19. 我的物联网项目(五)下单渠道
  20. 串联谐振电路原理?串联谐振电路怎么工作?案例公式,几分钟搞定

热门文章

  1. UVA 10369 - Arctic NetWork (求最小生成树)
  2. 装载list的时候 一定要把每一个实体放到for里面
  3. 英特尔:赔你15亿算了;Nvidia:反正我早就不做你那块了
  4. 关于政府房价调控的一个误区
  5. 【Shiro第七篇】SpringBoot + Shiro实现会话管理
  6. Redis分布式锁零散知识
  7. 用Nuget图形化界面打包类库(一)
  8. HDFS中的NameNode和DataNode
  9. inotify+unison双向同步环境部署
  10. Purftpd的详细安装配置