C 内核函数可以有不同的虚拟地址吗

C 内核函数可以有不同的虚拟地址吗,c,windows,linux,compiler-construction,kernel,C,Windows,Linux,Compiler Construction,Kernel,这更像是一个知识问题,而不是实际的实现。我想知道在系统启动后,是否有内核函数可以有不同的虚拟地址。我对可执行文件编译的理解是,虚拟地址是为其二进制文件分配的,而虚拟到物理地址是在运行时由os.paging完成的。我知道这些。所以,不需要解释 但对于内核函数,每次重启系统时,我都会看到它们有不同的虚拟地址。 1.内核函数如何在地址范围内映射?2.它们可以在运行时映射到不同的虚拟地址。我不知道这怎么可能。DLL的地址映射如何?它们在编译时被赋予一个虚拟地址,还是在运行时被赋予一个相对地址?我想就是这

这更像是一个知识问题,而不是实际的实现。我想知道在系统启动后,是否有内核函数可以有不同的虚拟地址。我对可执行文件编译的理解是,虚拟地址是为其二进制文件分配的,而虚拟到物理地址是在运行时由os.paging完成的。我知道这些。所以,不需要解释 但对于内核函数,每次重启系统时,我都会看到它们有不同的虚拟地址。 1.内核函数如何在地址范围内映射?2.它们可以在运行时映射到不同的虚拟地址。我不知道这怎么可能。DLL的地址映射如何?它们在编译时被赋予一个虚拟地址,还是在运行时被赋予一个相对地址?我想就是这样做的。4.是否有任何方法可以找到是否有任何内核虚拟地址被固定到物理内存


感谢

传统上,可执行文件在编译时被分配一个固定的虚拟地址映射。然而,最近几年,这显然对安全性有害——攻击者可以利用他们对内存中的确切位置的了解作为攻击的一部分。为了帮助缓解这种情况,可以使用位置独立的或可重定位的可执行文件,以允许至少在Linux上随机化加载地址。然而,这也带来了一个缺点——启动程序需要更多的时间,因为动态加载程序必须执行重新定位,否则在运行时,位置无关的机器代码会带来额外的开销


对于操作系统内核,与引导所花费的其余时间相比,额外的开销微不足道;事实上,Windows内核实际上动态链接了它的许多组件。因此,内核显然是随机分配加载地址的地方。

传统上,可执行文件在编译时被分配一个固定的虚拟地址映射。然而,最近几年,这显然对安全性有害——攻击者可以利用他们对内存中的确切位置的了解作为攻击的一部分。为了帮助缓解这种情况,可以使用位置独立的或可重定位的可执行文件,以允许至少在Linux上随机化加载地址。然而,这也带来了一个缺点——启动程序需要更多的时间,因为动态加载程序必须执行重新定位,否则在运行时,位置无关的机器代码会带来额外的开销

对于操作系统内核,与引导所花费的其余时间相比,额外的开销微不足道;事实上,Windows内核实际上动态链接了它的许多组件。因此,内核显然是随机分配加载地址的地方

内核函数如何在地址范围内映射? 它们根本不必映射到用户空间。直到我停止在这方面的练习,他们才被软中断

内核函数如何在地址范围内映射?
它们根本不必映射到用户空间。直到我停止在这一领域的实践之前,它们都是通过软中断到达的。

谢谢。内核可以在运行时在不同的位置卸载和重新加载模块吗。它尝试对内核库进行相对映射,但一旦加载,虚拟地址会改变吗?我想不会,因为其他模块依赖于这些地址。但是如果这些地址在需要查询的表中维护,然后运行时加载/卸载可以工作。因此,内核可以在运行时保持虚拟地址移动。但是,对于一些在运行时无法卸载的关键内核例程,系统可能无法做到这一点。您知道我们是否可以确定是否有任何虚拟地址被固定到phy内存?@agent.smith,请提出不同的问题,而不是在评论中提出复杂的后续问题。而且,你似乎有很多问题要问;请确保将这些问题作为单独的问题提问,因为有些人可能只知道一些问题的答案,但不知道所有问题的答案。谢谢。内核是否可以在运行时在不同的位置卸载和重新加载模块。它尝试对内核库进行相对映射,但一旦加载,虚拟地址会改变吗?我想不会,因为其他模块依赖于这些地址。但是如果地址保存在需要查询的表中,然后运行时加载/卸载可以工作。因此,内核可以在运行时保持虚拟地址移动。但是,对于一些关键的内核例程,系统可能无法在运行时卸载。您知道我们是否可以找出是否有任何虚拟地址被固定到phy内存?@agent.smith,请提出不同的问题,而不是在评论中提出复杂的后续问题。而且,你似乎有很多问题要问;请确保将这些问题作为单独的问题提问,因为有些人可能只知道部分问题的答案,但不知道所有问题的答案是的。所以,如果我考虑4GB地址空间,那么大约一半的空间包含内核代码/数据。
和一半的用户空间程序。内核代码在所有用户空间程序中保持不变。当你想调用任何内核例程时,方法就是软件中断,因为你无法访问该地址范围。我想知道的是这些内核虚拟地址是如何给出的。@agent.smith如果你接受我说的话,这个问题毫无意义。内核有自己的地址空间,它不同于任何进程的用户模式空间,因此不可能出现内核地址如何映射到用户空间的问题。因此,如果我考虑4GB地址空间,那么大约一半的空间包含内核代码/数据和半个用户空间进程。内核代码在所有用户空间程序中保持不变。当你想调用任何内核例程时,方法就是软件中断,因为你无法访问该地址范围。我想知道的是这些内核虚拟地址是如何给出的。@agent.smith如果你接受我说的话,这个问题毫无意义。内核有自己的地址空间,它不同于任何进程的用户模式空间,因此不可能出现内核地址如何映射到用户空间的问题。