【问题标题】:Get contents of a fixed memory location获取固定内存位置的内容
【发布时间】:2022-01-19 17:49:44
【问题描述】:

我正在尝试访问内存中的某个位置并检索该内存位置的内容,但是当我运行该程序时,它似乎无法运行。我没有收到任何错误,它只是一个空白的控制台屏幕。我首先想到的是,能够访问这样的内存位置可能会导致安全漏洞。是这个原因还是我的代码错了?

int main()
{
    int * pointer = 100;

    printf("%d", *pointer);

    return 0;
}

【问题讨论】:

  • 访问任意内存地址是 C 中未定义的行为。您的程序可能已经崩溃。
  • 这是未定义的行为,因为没有理由认为您的进程地址空间的地址 100 (0x64) 映射到任何东西。它在任何分配的内存分段之外,所以我每次都会遇到分段错误。这实际上不是 C 的事情(C 不关心这样的事情),但是你的内核会遇到问题。在可以直接访问内存(没有虚拟内存)的微控制器上,这实际上可以正常工作。
  • 这可能是内核内存位置,在用户模式下无法读取。
  • 上面的cmets是正确的,但是在某些情况下你可以任意访问内存位置。这就是内核通过将信息存储在特定地址来将文本打印到屏幕的方式,但您不是内核,操作系统可能会阻止您这样做。
  • 如果你想分析你的进程virtual address space的内存布局,你将不得不使用平台特定的函数。因此,如果您希望我们告诉您如何做到这一点,请指定您使用的平台(即操作系统)。

标签: c pointers memory


【解决方案1】:

内存映射寄存器是嵌入式编程不可或缺的一部分 - 但您需要知道在内存中的哪个位置进行刺激 - 随机位置可能会产生随机效应(由于未定义的行为)!

对于嵌入式编译器,通常有一个头文件,其中包含类似以下的行:

#define GPIO_PORTF_DIR_R (*( ( volatile unsigned int * )0x40025400 ) )

这些 (a) 适当地映射寄存器并 (b) 隐藏具体实现。

注意volatile 限定符的使用 - 任何内存映射访问都应该是volatile 限定的,否则编译器优化也会产生影响!

现在我们可以在您的代码中使用此名称来读取和写入该寄存器(无论它在哪里):

GPIO_PORTF_DIR_R = 0xF0;
data = GPIO_PORTF_DIR_R;

您的代码导致“只是一个空白的控制台屏幕”这一事实意味着它没有按照您的预期执行...您的随机位置导致随机(未定义)行为。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-04-06
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多