【问题标题】:Checking if an address is writable in x86 assembly检查地址在 x86 程序集中是否可写
【发布时间】:2015-04-11 10:53:21
【问题描述】:

仅使用(32 位)x86 程序集,是否可以检查地址是否可写, 不与操作系统交互,并且不存在段错误的风险?

程序将在环 3 中的 Linux 系统上运行。我无法使用“verw”指令。

举个例子,我可能想检查地址 0x0804a000 是否可写。但是如果我例如执行 "mov eax, 0x0804a000; mov [eax], eax" 然后,如果地址不可写,程序将出现段错误。我知道的唯一其他方法是例如调用 sys_read 进入地址,看看是否失败,但这与操作系统交互。

在给定约束的情况下,有没有办法检查地址是否可写?如果是这样,怎么做?

【问题讨论】:

  • 你当然可以处理段错误。这有什么问题吗?
  • @Jester 处理它需要一个系统调用,这是一个问题。
  • 您可以查看/proc/self/maps 并查看地址属于哪个范围(如果有)。当然,读取该文件也是一个系统调用......此外,该地址目前可能无法访问(已分页),但操作系统显然可以在页面错误处理程序期间更改它。你永远不会从用户空间知道这一点。
  • @Jester 假设我可以忽略段错误,但不能使用自定义函数处理它。这有帮助吗?我想不是因为错误的指令只会在段错误上重新执行,从而产生更多段错误。我错过了什么吗?
  • 你是对的,处理程序必须更改某些内容以避免错误,例如将寄存器值更改为已知的正确地址(假设指令是间接访问)。

标签: linux assembly x86


【解决方案1】:

如果您有内核权限,您可能会在 MMU 中找到该信息。

但如果您不这样做,您根本无法访问它并且必须使用操作系统工具。

如果您的意思是不调用操作系统函数,那么至少在 Windows 上可以使用结构化异常处理。当然,它仍然是特定于操作系统的,因为您需要在 FS 段访问 Windows TIB。

【讨论】:

  • 我没有内核权限,我会将这些信息添加到我的问题中。我的问题是针对 Linux 的。
  • 检查地址是否可读怎么样?这同样是不可能的吗?
  • @Chris 是的,读、写、执行内存都是一样的问题。
猜你喜欢
  • 2020-05-17
  • 2015-07-21
  • 1970-01-01
  • 1970-01-01
  • 2011-11-30
  • 2021-07-30
  • 2017-05-16
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多