逆向映射用于建立物理内存页和使用该页的进程的对应页表项之间的联系,在换出页时以便更新所有涉及的进程。得到物理页基址后,根据pfn_to_page可以将页框转换为page实例,page实例中的mapping成员,在映射匿名页面的时候该成员指向一个anon_vma结构,在映射文件页面的时候指向inode节点的address-space。这里简述一下匿名映射的情况:

一个物理页面可以同时被多个进程的虚拟地址内存映射,但一个虚拟页面同时只能有一个物理页面与之映射。不同虚拟页面同时映射到同一物理页面是因为子进程克隆父进程VMA,和KSM机制的存在。逆向映射实现的基础是通过struct anon_vma(简称AV)、struct anon_vma_chain(简称AVC)和sturct vm_area_struct(简称VMA)建立了联系,通过物理页面反向查找到VMA,这三个结构体的关系如下:

static void anon_vma_chain_link(struct vm_area_struct *vma, struct anon_vma_chain *avc, struct anon_vma *anon_vma)

{
avc->vma = vma; //建立struct anon_vma_chain和struct vm_area_struct关联
avc->anon_vma = anon_vma; //建立struct anon_vma_chain和struct anon_vma关联
list_add(&avc->same_vma, &vma->anon_vma_chain);//将AVC添加到struct vm_area_struct->anon_vma_chain链表中。
anon_vma_interval_tree_insert(avc, &anon_vma->rb_root);//将AVC添加到struct anon_vma->rb_root红黑树中。
}

说一下匿名映射情况下如何通过page得到对应的pte:匿名映射的情况下page->mapping指向anon_vma结构,AVC通过红黑树结点链接到AV中,而AVC又指向VMA,遍历anon_vma->rb_root红黑树中的AVC,从AVC可以得到相应的VMA,因此通过page指向的anon_vma结构可以得到与该进程相关的所有vma。前面说到,由于子进程复制父进程的vma,因此多个不同子进程中的虚拟页面会同时映射到同一个物理页面,另外多个不相干进程虚拟页面也可以通过KSM机制映射到同一个物理页面。这两种情况下通过逆向映射解除对一个页面的映射的实现是不一样的。函数page_referenced会先判断页面的类型,如果是KSM页面走page_referenced_ksm。如果是匿名映射页,走page_referenced_anon,如果是文件映射页,走page_referenced_file(对于文件主要就是根据page->mapping->i_mmap得到相关的vma),page_referenced_ksmpage_referenced_anon的区别在于获取page对应的虚拟地址上存在差异。

对于page_referenced_anon,对应到前面说的多个不同子进程中的虚拟页面同时映射到同一个物理页面的情况,page->index为page对应的虚拟页框在对应vma中的偏移,因为子进程复制父进程的vma,因此他们对应的vma结构都是一样的,因此page->index在不同子进程的vma中的偏移都是一致的,故对于每个关联的vma,都通过vma_address(page, vma)便可以获取page在当前vma对应的虚拟地址,且通过vma可以得到mm,进一步得到pgd。通过pgd和虚拟地址,可以继续遍历页表得到pte,然后解除映射。

对于page_referenced_ksm,由于是不同进程的虚拟页面映射到同一个物理页面,因此page对应的虚拟页框在不同进程的vma中的偏移肯定是不一致的,这里就不能对每个vma都通过vma_address(page, vma)得到page对应的虚拟地址。内核中对于ksm页面,内核维护了一个结构体rmap_item,通过stable_node->hlist将使用了ksm页面的rmap_item连接起来。rmap_item中维护了page对应的虚拟地址addressanon_vma结构,基于此得到对应的vma,虚拟地址通过rmap_item得到,然后进一步解除映射。

共享内存方式的页如何通过逆向映射解除映射:应该是通过文件的方式,内核实现的shm共享内存会分配一个文件标识符,而mmap实现的共享内存要么是在父子进程之间,要么就是文件映射。

参考:https://www.cnblogs.com/arnoldlu/p/8335483.html

https://www.cnblogs.com/ck1020/p/6883061.html

linux 逆向映射的更多相关文章

  1. linux 逆向映射机制浅析

    2017-05-20 聚会回来一如既往的看了会羽毛球比赛,然后想到前几天和朋友讨论的逆向映射的问题,还是简要总结下,免得以后再忘记了!可是当我添加时间……这就有点尴尬了……520还在写技术博客…… 闲 ...

  2. KVm中EPT逆向映射机制分析

    2017-05-30 前几天简要分析了linux remap机制,虽然还有些许瑕疵,但总算大致分析的比较清楚.今天分析下EPT下的逆向映射机制.EPT具体的工作流程可参考前面博文,本文对于EPT以及其 ...

  3. 逆向映射是干嘛的anon_vma, vma, anon_vma_chain

    逆向映射是为了从page得到进程信息,里面有三个比较重要的结构体: mm_area_struct, anon_vma_chain, anon_vma 想象一种复杂的场景 所以其实一个进程对应着很多an ...

  4. 【原创】ARMv8 MMU及Linux页表映射

    背景 Read the fucking source code! --By 鲁迅 A picture is worth a thousand words. --By 高尔基 说明: Kernel版本: ...

  5. 快速配置 Samba 将 Linux 目录映射为 Windows 驱动器,用于跨平台编程

    一.局域网内的 Linux 服务器上操作步骤: 1.安装samba(CentOS Linux): yum install samba system-config-samba samba-client ...

  6. Linux内存映射(mmap)系列(1)

    看到同事的代码中出现了mmap.所以自己私下学习学习,研究研究..... http://www.cnblogs.com/lknlfy/archive/2012/04/27/2473804.html ( ...

  7. 快速配置 Samba 将 Linux 目录映射为 Windows 驱动器

    原文链接 samba client ubuntu redhat ubuntu gui tools 1,列出某个IP地址所提供的共享文件夹 smbclient -L 198.168.0.1   2,在s ...

  8. Linux内存映射--mmap函数

    Linux提供了内存映射函数mmap, 它把文件内容映射到一段内存上(准确说是虚拟内存上), 通过对这段内存的读取和修改, 实现对文件的读取和修改, 先来看一下mmap的函数声明: 头文件: < ...

  9. [转载]linux内存映射mmap原理分析【转】

    转自:http://www.cnblogs.com/wanpengcoder/articles/5306688.html 转自:http://blog.csdn.net/yusiguyuan/arti ...

随机推荐

  1. noj算法 堡垒问题 回溯法

    描述: 城堡是一个4×4的方格,为了保卫城堡,现需要在某些格子里修建一些堡垒.城堡中的某些格子是墙,其余格子都是空格,堡垒只能建在空格里,每个堡垒都可以向上下左右四个方向射击,如果两个堡垒在同一行或同 ...

  2. java基础编程题练习(二)

    1.回文数 思路一:使用java特有解法,将原数字以字符串存储,翻转后赋值给新的字符串变量,再使用equals与原字符串进行对比 import java.util.Scanner; public cl ...

  3. linux的时间问题

    在linux系统中时间分为修改时间(modify time 简写:mtime ),访问时间(access time 简写: atime),状态修改时间(change time 简写:ctime)三种: ...

  4. js 读取文件

    读取文本文件 读取文本文件: <input type="file" id="file1" accept="*" /> </ ...

  5. 详解 CAP 定理 Consistency(一致性)、 Availability(可用性)、Partition tolerance(分区容错性)

    CAP原则又称CAP定理,指的是在一个分布式系统中,Consistency(一致性). Availability(可用性).Partition tolerance(分区容错性),三者不可得兼. 分布式 ...

  6. Postgresql/Greenplum中将数字转换为字符串TO_CHAR函数前面会多出一个空格

    -- 问题1..Postgresql中将数字转换为字符串前面多出一个空格. SELECT TO_CHAR(, '); -- 解决1.使用如下,参数二前面加上fm就可以去掉空格了,如下: SELECT ...

  7. 使用navicat连接 mysql时出现client does not support auth...upgrading Mysql Client

    问题报错:使用navicat时发现出现如下情况: 原因:发现是由于navicat版本的问题,出现连接失败的原因:mysql8 之前的版本中加密规则是mysql_native_password,而在my ...

  8. .net 本地日志的添加

    /// <summary> /// 写入日志到文本文件 /// </summary> /// <param name="userName">用户 ...

  9. 2018-2019-1 20189201 《LInux内核原理与分析》第七周作业

    我的愿望是 好好学习Linux 一.书本第六章知识总结[进程的描述和进程的创建] 基础知识1 操作系统内核实现操作系统的三大管理功能,即进程管理功能,内存管理和文件系统.对应的三个抽象的概念是进程,虚 ...

  10. event.target 和 event.currentTarget 的区别

    event.target This property of event objects is the object the event was dispatched on. It is differe ...