当前位置: 首页 > news >正文

用户虚拟地址空间布局架构

目录

一、Linux内核整体架构及子系统

二、内存管理模块架构

三、用户地址空间的内存布局

(1)mm_struct

(2)vm_area_struct


一、Linux内核整体架构及子系统

        Linux内核是操作系统中最为关键的一个部分,对下管理所有硬件资源,对上提供系统调用接口给程序员使用。

        下图是对操作系统整体架构的简图:

但是我们可以将其更具体化一点,专门看看内核以下部分:

二、内存管理模块架构

整体架构如下:

        对于我们上层无论是malloc还是new,本质都调用到了比如ptmalloc、tcmalloc等。即malloc是对外呈现的状态,但是可以根据需求选择底层的逻辑。

        ptmalloc和tcmalloc本质是一个内存池,因为操作系统本身的系统调用并未提供合适的内存管理机制,仅仅是通过brk、sbrk等来移动堆的指针(是在操作虚拟地址,实际物理地址分配则是第一次使用的时候再和硬件交互)。但是这样就必须要求程序员自己管理每一个内存块,而ptmalloc等则直接利用brk向内存硬件申请一大片连续的内存,然后自己对这个内存进行切分,挂载形成内存池,我们之前曾模拟过tcmalloc,原理也是如此。

        比如tcmalloc就很适合多线程高并发的状态,而ptmalloc则更加全能一点,各方面都比较均衡。

        MMU是CPU内部的一个模块,他的作用就将虚拟地址转换成物理地址,即每一个线程误以为自己独享整个内存空间,而其中有一个页表缓存,用于缓解CPU和内存速度不匹配的问题。

        每一次进程切换的时候,都会把pgd的值给到MMU模块,MMU根据pgd的地址找到真实物理内存的页表,从而完成进程后续的操作。

三、用户地址空间的内存布局

(1)mm_struct

/* 包含必要的头文件 */
#include <linux/list.h>
#include <linux/rbtree.h>
#include <linux/spinlock_types.h>
#include <linux/types.h>struct vm_area_struct;/* 定义mm_struct结构体 */
struct mm_struct {struct vm_area_struct *mmap;          /* 指向虚拟内存区域链表的指针 */struct rb_root mm_rb;                 /* 管理虚拟内存区域的红黑树根节点 */spinlock_t mmap_lock;                 /* 用于保护对mmap链表和mm_rb红黑树的并发访问 */unsigned long task_size;              /* 任务的虚拟地址空间大小 */pgd_t * pgd;                         /* 指向页全局目录(Page Global Directory)的指针 */atomic_t mm_users;                    /* 使用该地址空间的用户数(包括内核线程) */atomic_t mm_count;                    /* 地址空间的引用计数 *//* 以下字段用于标识代码段和数据段的地址范围 */unsigned long start_code, end_code, start_data, end_data;/* 堆相关地址 */unsigned long start_brk, brk;         /* 堆的起始地址和当前顶部地址 */unsigned long start_stack;           /* 栈的起始地址 *//* 用于跟踪内存分配和释放的统计信息 */struct mm_rss_stat rss_stat;/* 内存管理的其他相关字段 */struct list_head mmlist;             /* 用于将mm_struct链接到全局内存描述符链表 */struct file *core_file;              /* 指向核心转储文件的指针(如果有的话) */struct user_struct *user;            /* 指向用户结构体的指针,包含用户相关的资源限制等信息 */struct mm_struct *user_ns_exposed;   /* 指向用于用户命名空间暴露的mm_struct */struct anon_vma *root_anon_vma;      /* 用于管理匿名虚拟内存区域的根节点 */
};

        mm_struct是pcb中管理该进程的宏观结构体。他定义了堆、栈、代码段以及数据段的地址范围等,同时还维护了一个vm_area_struct链表来记录上述区域的细节。

具体如下图所示:

        注意这里vm_area_struct是一个链表指针,并非一个mm_struct中只有一个,而是每一个区域都会有,比如代码段、堆、栈、数据段都有自己的vm_area_struct

(2)vm_area_struct

struct vm_area_struct {struct mm_struct *vm_mm;             /* 指向所属的mm_struct结构体 */unsigned long vm_start;             /* 虚拟内存区域的起始地址 */unsigned long vm_end;               /* 虚拟内存区域的结束地址 */unsigned long vm_flags;             /* 内存区域的标志,如读写权限、可执行等 */struct rb_node vm_rb;               /* 用于将该vma插入到mm_rb红黑树中的节点 */union {struct list_head vm_next_share; /* 用于链接到共享该vma的链表 */struct raw_prio_tree_node prio_tree_node;};struct list_head vm_list;           /* 用于链接到mmap链表 */struct file * vm_file;              /* 如果该vma映射了文件,指向对应的文件结构体 */void * vm_private_data;             /* 私有数据指针,用于特定的内存映射场景 */struct vm_area_struct *vm_next;     /* 指向下一个vma(在链表中) */
};

        既然已经有了brk、start_stack等为什么还需要vm_area_struct这样一个结构体呢?我们看到在mm_struct中,存放的是一个vm_area_struct的链表,而非单个的vm_area_struct。

        这说明每一个区域(如堆、栈,代码段、数据段),都会有一个vm_area_struct。他就是用来精细化管理进程虚拟地址空间的结构体。我们知道不同的区域往往有着不同的属性,如可读、可写权限,以及是否和文件相关。

        同时我们可以看到其中有一个成员是rb_node类型的,他是一个将该vm_area_struct结构体插入红黑树的字段,其键值为虚拟内存区域的起始地址,利用红黑树高效的查询效率,内核可以快速定位某个虚拟地址属于哪个vm_area_struct。例如内存访问缺页中断的时候,就利用到了它。

        再比如我们平时的非法访问错误。就是在这里产生的,当程序想对一个只读区域尽心修改,内核首先会找到该区域的vm_area_struct,然后获取vm_flags标志位,得到读写权限,如果权限不对则发生错误。

http://www.lryc.cn/news/595314.html

相关文章:

  • git_guide
  • 【Git#6】多人协作 企业级开发模型
  • 【面经】实习经历
  • 深入理解 C++ 中的指针与自增表达式:*a++、(*a)++ 和 *++a 的区别解析
  • 破除扫描边界Photoneo MotionCam-3D Color 解锁动态世界新维度
  • 京东疯狂投资具身智能:众擎机器人+千寻智能+逐际动力 | AI早报
  • 2021 RoboCom 世界机器人开发者大赛-本科组(复赛)解题报告 | 珂学家
  • [硬件电路-64]:模拟器件 -二极管在稳压电路中的应用
  • 物流链上的智慧觉醒:Deepoc具身智能如何重塑搬运机器人的“空间思维”
  • 库卡气体保护焊机器人省气的方法
  • Java IO流体系详解:字节流、字符流与NIO/BIO对比及文件拷贝实践
  • 大模型高效适配:软提示调优 Prompt Tuning
  • 【Windows】多标签显示文件夹
  • PLC之间跨区域通讯!无线通讯方案全解析
  • SQL通用增删改查
  • Spring Cache 扩展:Redis 批量操作优化方案与 BatchCache 自定义实现
  • C++中的deque容器
  • vue3实现可视化大屏布局
  • 相机标定(非ROS相机)
  • hard_err错误
  • 【PTA数据结构 | C语言版】哥尼斯堡的“七桥问题”
  • 2000 兆瓦挖矿合作落地,GSP 2031 携 Whitebird 拓展全球合规算力版图
  • 【安全篇 / 反病毒】(7.6) ❀ 01. 查杀HTTPS加密网站病毒 ❀ FortiGate 防火墙
  • 服务器设置国外IP无法访问对防御攻击有用吗?
  • uni-api交互反馈组件(showToast)的用法
  • 处理excel/wps表格中数值格式的警告的工具和脚本
  • Nacos中feign.FeignException$BadGateway: [502 Bad Gateway]
  • kafka 生产消息和消费消息 kafka-console-producer.sh kafka-console-consumer.sh
  • A316-HF-DAC-V1:专业USB HiFi音频解码器评估板技术解析
  • 用window字体替换zabbix 默认的字体