如何在不使用Assembly(NASM)中的变量的情况下将数据存储在内存中?

时间:2014-08-27 11:11:08

标签: memory-management assembly nasm

我在每个网页上搜索答案,但我似乎无法找到答案。我已经学习了大约2个月的网络汇编语法,我正在尝试找到一种在内存中存储数据的方法。

我知道sys_break:

    mov,eax 45

保留内存,我有一个保留16kb内存的功能宏:

    %macro reserve_mem
    mov eax,45
    xor ebx,ebx
    int 80h
    add eax,16384
    mov ebx,eax
    mov eax,45
    int 80h
    %endmacro

我也知道当你保留字节(resb),单词等。在.bss部分中,内存的一小部分被分配给未初始化的数据。

此外,还有虚拟内存,可以使用0x0000这样的地址访问,然后将其映射到实际的内存位置。

然而,我的问题是我试图将数据存储在内存中,但我尝试的所有内容都以分段错误(核心转储)结束,这是试图访问它无权访问的内存的程序。我尝试过如下代码。

     mov [0x0000],eax

谢谢你的帮助。

1 个答案:

答案 0 :(得分:1)

你似乎误解了虚拟内存的概念。它类似于电话号码,因为你不能在每个10位数的组合上打电话给某人。您只需拨打电话簿中列出的号码即可拨打电话。否则你会听到"抱歉,这个号码目前无法使用"。同样,只有每个进程的页表中列出的那些虚拟地址(始终由OS自动和透明地维护)对于访问进程是有效的。 SEGV是操作系统的说法"抱歉,这个虚拟地址目前无法使用。"

在您的代码中,您取消引用0x0000,但它是虚拟虚拟地址的最不可能的值之一。您最终这样做是因为您丢弃了brk(2)系统调用返回的有效虚拟地址(仔细阅读man 2 brk,因为原始系统调用从glibc brk和{{ 1}}。)您的代码将以这种方式转换为C(尽管如今glibc sbrk通常依赖于malloc(3)而不是mmap(2)):

brk(2)

这显然是错误的,你必须做这样的事情:

void *p = malloc(16384);
int eax = ...;
(void *)0 = eax;

应该转换为这样的NASM:

void *p = malloc(16384);
int *p0 = (int *)p + 0;
int *p1 = (int *)p + 1;
int eax = ...;
int ebx = ...; /* it's all up to you which register to use */
*p0 = eax;
*p1 = ebx;

我对汇编编程的了解很严重,上面的代码可能包含很多错误......但概念部分不应该是错误的。