在Linux(或Solaris)上有一种比手动解析/proc/self/maps
更好的方法来判断你是否可以读取,写入或执行存储在内存中一个或多个地址的任何内容吗?
例如,在Windows中,您有VirtualQuery
。
在Linux中,我可以mprotect
更改这些值,但我无法读回来。
此外,有没有办法知道这些权限何时发生变化(例如,当有人在我背后的文件上使用mmap
时),而不是做一些非常具有侵略性的事情,并且在所有线程上使用ptrace
处理和拦截任何可能影响内存映射的syscall
的尝试?
更新
不幸的是,我在JIT中使用它,它几乎没有关于它正在执行的代码的信息,以获得常量的近似值。是的,我意识到我可以有一个可变数据的常量映射,比如Linux使用的vsyscall页面。我可以安全地假设初始解析中未包含的任何内容都是可变且危险的,但我对该选项并不完全满意。
现在我所做的是阅读/proc/self/maps
并构建一个我可以二进制搜索的结构,以获得给定地址的保护。每当我需要了解一些不在我的结构中的页面时,我会重新阅读/ proc / self / maps,假设它已经在此期间添加,或者我将要进行段错误。
似乎解析文本以获取此信息并且不知道何时更改是非常苛刻的。 (/dev/inotify
对/proc
}
答案 0 :(得分:6)
我不知道Linux上的等效VirtualQuery
。但其他一些可能或可能不起作用的方法是:
你设置了一个信号处理程序捕获SIGBUS / SIGSEGV并继续你的读或写。如果内存受到保护,将调用您的信号捕获代码。如果不是,则不会调用您的信号捕获代码。无论哪种方式,你都会赢。
您可以在每次调用mprotect
时跟踪并构建相应的数据结构,以帮助您了解区域是读还是写保护。如果您可以访问使用mprotect
。
您可以通过将代码与重新定义函数mprotect
的库相关联来监控流程中的所有mprotect
次调用。然后,您可以构建必要的数据结构,以了解区域是读还是写保护,然后调用系统mprotect
以实际设置保护。
您可以尝试使用/dev/inotify
并监控文件/proc/self/maps
以进行任何更改。我想这个不行,但应该值得一试。
答案 1 :(得分:0)
sorta是/是/ proc / [pid | self] / pagemap,内核中的文档,请注意: https://lkml.org/lkml/2015/7/14/477 所以它并非完全无害......