物理/逻辑/虚拟内存地址之间的差异

2024-01-17

我对操作系统中的术语物理/逻辑/虚拟地址有点困惑(我使用 Linux-open SU​​SE)

这是我的理解:

  1. 物理地址-当处理器处于系统模式时,处理器使用的地址是物理地址。

  2. 逻辑地址-当处理器处于用户模式时,使用的地址是逻辑地址。无论如何,通过添加带有偏移值的基址寄存器,这些都映射到某个物理地址。它在某种程度上提供了一种内存保护。

  3. 我曾经遇到过这样的讨论:虚拟地址和逻辑地址/地址空间是相同的。这是真的吗?

非常感谢任何帮助。


我的答案对于运行在现代 Linux 系统上的 Intel CPU 来说是正确的,而且我说的是用户级进程,而不是内核代码。尽管如此,我认为它会给你一些足够的洞察力来思考其他可能性

地址类型

关于问题3:

我遇到过虚拟和逻辑的讨论 地址/地址空间是相同的。这是真的吗?

据我所知,它们是相同的,至少在英特尔处理器上运行的现代操作系统中是这样。

在解释更多内容之前,让我尝试定义两个概念:

  • 实际地址:RAM 芯片中某物物理位置的地址。
  • 逻辑/虚拟地址:您的程序用来访问其内容的地址。它通常稍后由硬件芯片转换为物理地址(大多数情况下,甚至 CPU 都没有真正意识到这种转换)。

虚拟/逻辑地址

虚拟地址是一个虚拟地址,操作系统以及称为 MMU(内存管理单元)的硬件电路欺骗您的程序,它是在系统中单独运行的,它拥有整个地址空间(拥有 32 位系统意味着您的程序会认为它有 4 GB RAM;粗略地说)。

显然,如果您同时运行多个程序(您总是这样做,GUI、Init 进程、Shell、时钟应用程序、日历等),则这将不起作用。

将会发生的情况是,操作系统会将大部分程序内存放在硬盘中,它使用最多的部分将出现在 RAM 中,但是,嘿,这并不意味着它们将拥有您和您的程序的地址知道。

Example:您的进程可能有一个名为 (counter) 的变量,该变量被赋予虚拟地址 0xff(可以想象......),另一个名为 (oftenNotUsed) 的变量被赋予虚拟地址 (0xaa)。

如果您在所有链接发生后读取编译代码的汇编,您将使用这些地址访问它们,但是(oftenNotUsed)变量不会真正存在于 RAM 中的 0xaa 处,它将位于硬盘中因为该进程没有使用它。

此外,变量(计数器)可能不会物理上位于(0xff),它将位于 RAM 中的其他位置,当您的 CPU 尝试获取 0xff 中的内容时,MMU 和操作系统的一部分将进行映射从 RAM 中真正可用的位置获取该变量,CPU 甚至不会注意到它不在 0xff 中。

现在,如果您的程序要求 (oftenNotUsed) 变量,会发生什么? MMU+OS会注意到这个“未命中”,并将其从硬盘中为CPU获取到RAM中,然后将其交给CPU,就好像它位于地址(0xaa)中一样;此获取意味着 RAM 中存在的一些数据将被发送回硬盘。

现在想象一下它为系统中的每个进程运行。每个进程都认为自己有 4GB RAM,实际上没有人拥有,但一切正常,因为每个人的程序的某些部分在 RAM 中物理可用,但大部分程序驻留在硬盘中。不要将HD中的这部分程序存储器与您可以通过文件操作访问的程序数据混淆。

Summary

虚拟地址:您在程序中使用的地址,即您的 CPU 用于获取数据的地址,不是真实的,而是通过 MMU 转换为某个物理地址;每个人都有一个,其大小取决于您的系统(运行 32 位的 Linux 有 4GB 地址空间)

实际地址:如果您在操作系统之上运行,您将永远无法到达该地址。这是您的数据(无论其虚拟地址如何)驻留在 RAM 中的位置。如果您的数据来回发送到硬盘以便为其他进程提供更多空间,这种情况将会改变。

我上面提到的所有内容,虽然是整个概念的简化版本,但都是所谓的计算机系统的内存管理部分。

该系统的后果

  • 进程无法访问彼此的内存,每个进程都有自己单独的虚拟地址,并且每个进程都会对不同区域进行不同的转换,即使有时您可能会发现两个进程尝试访问相同的虚拟地址。
  • 该系统作为缓存系统运行良好,您通常不会使用可用的整个 4GB,那么为什么要浪费它呢?让其他人分享并让他们也使用它;当您的进程需要更多数据时,操作系统将从硬盘中获取您的数据并替换其他进程的数据,当然这是有代价的。
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

物理/逻辑/虚拟内存地址之间的差异 的相关文章

  • 使用sk_buff添加以太网帧头

    我有一个捕获传出互联网流量的内核模块 Netfilter hook LOCAL OUT 在此挂钩处 仍然没有以太网标头 我构建了以太网头并且可以使用了 但是如何将其连接到skb这样我就可以将整个 skb 结构发送到dev queue xmi
  • 有谁知道在哪里定义硬件、版本和序列号。 /proc/cpuinfo 的字段?

    我想确保我的 proc cpuinfo 是准确的 目前它输出 Hardware am335xevm Revision 0000 Serial 0000000000000000 我可以在代码中的哪里更改它以给出实际值 这取决于 Linux 的
  • ftrace:仅打印trace_printk()的输出

    是否可以只转储trace printk 输出于trace文件 我的意思是过滤掉函数跟踪器 或任何其他跟踪器 中的所有函数 一般来说 您可以在选项目录中关闭选项 sys kernel debug tracing options Use ls显
  • 内核模式下的线程(和进程)与用户模式下的线程(和进程)有什么区别?

    我的问题 1 书中现代操作系统 它说线程和进程可以处于内核模式或用户模式 但没有明确说明它们之间有什么区别 2 为什么内核态线程和进程的切换比用户态线程和进程的切换花费更多 3 现在 我正在学习Linux 我想知道如何在LINUX系统中分别
  • 内核makefile中的$(call cmd,tags)这里的cmd指的是什么?

    在内核 Makefile 中我发现如下代码 ctags CTAGS CSCOPE HEADERS SOURCES ETAGS ETAGSFALGS HEADERS SOURCES call cmd ctags 另外 在哪里可以找到宏或函数
  • 如何访问 mmaped /dev/mem 而不导致 Linux 内核崩溃?

    我有一个简单的程序 尝试访问用户空间中的物理内存 其中内核存储第一个结构页 在 64 位机器上 该地址是 内核虚拟地址 ffffea0000000000 物理地址 0000620000000000 我正在尝试通过用户空间中的 mmap 访问
  • 在许多驱动程序文件夹中创建 build-in.o

    我正在用我的自定义驱动程序构建内核 成功构建后 我发现了许多 build in o 文件 任何人都可以详细说明这些文件是如何在这里结束的吗 我只能怀疑这些与更高级别的 makefile 有关 built in o 文件是未构建为模块的内核的
  • 这些工作队列标志意味着什么?

    在研究工作队列时 我遇到了内核中定义的工作队列标志和常量 我有以下我无法理解的疑问 这里的排水和救援到底是什么意思 WQ DRAINING 1 lt lt 6 internal workqueue is draining WQ RESCUE
  • gem5 se模式如何执行具有操作系统依赖的程序?

    Gem5 se 模式是非操作系统模式 但我能够在其上执行 row hammer 代码 其中包含具有操作系统依赖性的命令 但是如果在 se 模式下没有操作系统 那么它们如何在 se 模式下执行 大多数用户态允许的指令只做通常的事情 即稍微改变
  • 有没有办法让我的程序用更少的代码运行?

    我为学校作业编写了以下代码 它编译并打印所有正确的消息 但出于我自己的好奇心 我想知道我的代码是否可以缩短并且仍然有效 我尝试了 signal 而不是 sigaction 但我听说 sigaction 比 signal 更受青睐 此外 此任
  • ftrace 是否允许捕获 Linux 内核的系统调用参数,或者仅捕获函数名称?

    目标是检查任何进程传递给特定系统调用 例如 exec open 等 的参数 来自官方文档 https www kernel org doc Documentation trace ftrace txt 没有描述记录函数参数的功能 主要查看
  • C 文件 I/O 操作如何在底层处理?

    扩展标题 我想知道操作系统如何处理 fwrite fread fopen 和 fclose 等函数 实际上什么是流 抱歉 如果我不够清楚 顺便说一句 我正在使用 GNU Linux Ubuntu 11 04 对我想问的问题有更好的解释 我想
  • 在Python中使用子文件夹的名称为每个子文件夹创建空文件

    如果我的文件夹结构如下 folder sub1 sub1 1 sub1 sub1 2 sub1 sub1 3 sub2 sub2 1 sub2 sub2 2 sub2 sub2 3 我想让每个子文件夹的文件使用子文件夹的名称 我怎样才能用P
  • 如何通过jiffies实现经过时间

    我想了解如何在 C 中使用 jiffies 实现经过时间 假设我有一系列指令 include
  • crt0 是否加载 msvcrt.dll?

    我想弄清楚标准 C 函数是什么样的printf 在 Windows 环境下加载到内存中 我知道crt0 obj准备堆栈 调用int main int argc char argv 然后使用 main 返回的退出代码退出进程 我还听说 C 标
  • 操作系统和元操作系统有什么区别

    最近听到这个词元操作系统当我学习ros时 你能帮我区分一下吗操作系统 and 元操作系统 ROS 是什么和不是什么最好的解释是这张纸 http www robotics stanford edu ang papers icraoss09 R
  • 尝试在 ubuntu 中编译 android 内核时出错

    我正在尝试从源代码编译 Android 内核 并且我已经下载了所有正确的软件包来执行此操作 但由于某种原因我收到此错误 arm linux androideabi gcc error unrecognized command line op
  • 如何使用系统凭据自动登录网站?

    我需要为 Intranet 用户开发一个 Web 应用程序 我不希望他们每次访问该网站时都输入登录凭据 它应该从系统用户名和密码自动加载 即 如果他们拥有有效的系统用户名和密码 他们应该能够登录应用程序 我正在使用Java 如何满足这个要求
  • 使用 gdb 调试 Linux 内核模块

    我想知道 API 在内核模块 中返回什么 从几种形式可以知道 这并不是那么简单 我们需要加载符号表来调试内核模块 所以我所做的就是 1 尝试找到内核模块的 text bss和 data段地址 2 在 gdb 中使用 add symbol f
  • 如何在 Linux 内核中定义并触发我自己的新软中断?

    我想在 Linux 内核中创建自己的软中断 这是正确的方法吗 In the init我想触发该模块的softirq我将添加一个调用 394 void open softirq int nr void action struct softir

随机推荐