Warning: file_get_contents(/data/phpspider/zhask/data//catemap/7/jsf/5.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Linux 如何在从mmap获取的地址上使用值?_Linux_Segmentation Fault_X86 64_Nasm_Mmap - Fatal编程技术网

Linux 如何在从mmap获取的地址上使用值?

Linux 如何在从mmap获取的地址上使用值?,linux,segmentation-fault,x86-64,nasm,mmap,Linux,Segmentation Fault,X86 64,Nasm,Mmap,有这个nasm: %define O_RDONLY 0 %define PROT_READ 0x1 %define MAP_PRIVATE 0x2 section .data fname: db 'test.txt', 0 section .text global _start print: ; ---- THIS PART ADDED mov r15, [rdi] add r15, 1 ; have tried `inc byte[rdi]` - did not work

有这个nasm:

%define O_RDONLY 0
%define PROT_READ 0x1
%define MAP_PRIVATE 0x2

section .data
fname: db 'test.txt', 0

section .text
global _start
print:
 ; ---- THIS PART ADDED
    mov r15, [rdi]
    add r15, 1 ; have tried `inc byte[rdi]` - did not work either
    mov [rdi], r15
 ; ---- END OF ADDED PART
 ; else is according to book (so correct)
    push rdi


    call str_len
    pop rsi
    mov rdx, rax
    mov rax, 1
    mov rdi, 1
    syscall
    ret
str_len:
    xor rax, rax
.loop:
    cmp byte [rdi+rax], 0
    je .end
    inc rax
    jmp .loop
.end:
    ret

_start:
    ;call open
    mov rax, 2
    mov rdi, fname
    mov rsi, O_RDONLY 
    mov rdx, 0 
    syscall

    ;mmap
    mov r8, rax 
    mov rax, 9 
    mov rdi, 0 
    mov rsi, 4094 
    mov rdx, PROT_READ 
    mov r10, MAP_PRIVATE  
    mov r9, 0 
    syscall

    mov rdi, rax ;returned address 
    call print
    mov rax, 60
    xor rdi, rdi
    syscall
文件test.txt在开头仅包含一个字符-5

我从mmap在rax询问的地区得到了地址,然后我转到rdi。 我只想增加该地址的值-现在在rdi中:

所以我临时移动r15上的值,增量加1,并尝试将其移回仍然在rdi中的区域地址。但这是一个错误

为什么呢?为什么我不能使用从mmap获取的区域的地址上的值,它包含rdi指向的5-1字节,并在算术中使用它

若那个将是在数据段中声明的地址,那个么我尝试过并没有问题。但是地址来自mmap,那么它有什么区别,以及如何修复它?

写入只读存储器SEGFULTS mov[rdi]、r15 qword store或inc字节[rdi]字节RMW

如果你想既能读又能写,你就需要保护读,保护写


请注意,写入MAP_私有映射会在写入时触发一个副本,留下一个不再由文件支持的私有页面,就像读取MAP_匿名页面一样。

您是否使用strace检查mmap是否返回了指针,而不是错误代码?不过,一个mov[rdi],r15存储到PROT_READ中,而没有PROT_WRITE内存,看起来似乎是它发生故障的一个明显原因。使用调试器,查看它在哪个指令上出错。@Peter,是的。代码同样正确-从书中,我只是在尝试使用间接寻址返回的地址上的值时添加了部分。它从数据段中初始化的地址开始工作,但不能在上使用mmap中的地址runtime@PeterCordes,问题不在于我请求的内存大小为一页4096,但需要mmap以rax返回的起始地址的值,而只访问一个字节?第一个。这不是问题的原因吗?您正在以只读方式打开文件,并使用PROT_read not PROT_WRITE调用map,然后在尝试写入时出错,这与预期的完全一致。请详细说明“写时拷贝”机制,或者它是如何工作的?你留下一个不再由文件支持的私人页面是什么意思,为什么写入私人页面会将其更改为匿名页面?我认为每一页都由文件或它们对应的对象支持。我知道只有堆栈是匿名的,但代码段应该始终使用exe文件备份,还是不备份?。你能给你的答案加一点吗?@牧民:用谷歌搜索那些短语,尤其是“写时拷贝”,例如。MAP_PRIVATE意味着对这些页面的写入不会反映在文件内容中,因此该页面实际上是匿名的,只能调出以交换空间,而不能调出任何文件。e、 g.如果您对mmap的工作原理有不同的问题,请提问;这个问题不是关于mmap做什么的指南,也不是关于MAP_ANONYMOUS分配stack和BSS以外的新匿名页面的指南。
    mov r15, [rdi]
    add r15, 1 ; have tried `inc byte[rdi]` - did not work either
    mov [rdi], r15
    push rdi