相关疑难解决方法(0)

为什么分段错误不可恢复?

我之前的问题之后,大多数评论都说“不要这样做,你处于一种不确定的状态,你必须杀死一切并重新开始”。还有一个“安全”的解决方法

我不明白的是为什么分段错误本质上是不可恢复的。

写入受保护内存的时刻被捕获 - 否则,将SIGSEGV不会被发送。

如果可以捕获写入受保护内存的时刻,我不明白为什么 - 理论上 - 它不能在某个低级别上恢复,并且不能将 SIGSEGV 转换为标准软件异常。

请解释为什么在分段错误之后程序处于不确定状态,因为很明显,在内存实际更改之前抛出了错误(我可能是错的,不明白为什么)。如果它被抛出,人们可以创建一个程序来更改受保护的内存,一次一个字节,出现分段错误,并最终重新编程内核 - 这种安全风险并不存在,因为我们可以看到世界仍然存在。

  1. 分段错误究竟何时发生(=何时发送SIGSEGV)?
  2. 为什么该进程在该点之后处于未定义的行为状态?
  3. 为什么无法恢复?
  4. 为什么这个解决方案可以避免这种不可恢复的状态?甚至吗?

c c++ exception segmentation-fault

112
推荐指数
11
解决办法
1万
查看次数

退出系统调用的正确常量是什么?

我正在尝试学习 x86_64 汇编,并使用 GCC 作为我的汇编程序。我正在使用的确切命令是:

gcc -nostdlib tapydn.S -D__ASSEMBLY__
Run Code Online (Sandbox Code Playgroud)

我主要使用 gcc 作为它的预处理器。这是tapydn.S

.global _start

#include <asm-generic/unistd.h>

syscall=0x80

.text
_start:
    movl $__NR_exit, %eax
    movl $0x00, %ebx
    int  $syscall
Run Code Online (Sandbox Code Playgroud)

这会导致分段错误。我相信问题出在以下几行:

 movl $__NR_exit, %eax
Run Code Online (Sandbox Code Playgroud)

我使用__NR_exit它是因为它比一些神奇的数字更具描述性。但是,我对它的使用似乎是不正确的。我相信情况确实如此,因为当我将有问题的行更改为以下内容时,它运行良好:

movl $0x01, %eax
Run Code Online (Sandbox Code Playgroud)

进一步支持这一思路的是以下内容usr/include/asm-generic/unistd.h

#define __NR_exit 93
__SYSCALL(__NR_exit, sys_exit)
Run Code Online (Sandbox Code Playgroud)

我预计 __NR_exit 的值为 1,而不是 93!显然我误解了它的目的,因此误解了它的用法。据我所知,我很幸运能在$0x01案例中工作(很像 C++ 中的未定义行为),所以我一直在挖掘......

接下来,我寻找sys_exit. 我找不到。我尝试使用它如下(有和没有前面的 $):

movl $sys_exit, %eax
Run Code Online (Sandbox Code Playgroud)

这不会链接:

/tmp/cc7tEUtC.o: In function `_start':
(.text+0x1): undefined reference to `sys_exit'
collect2: error: ld returned 1 exit …
Run Code Online (Sandbox Code Playgroud)

assembly gcc x86-64

7
推荐指数
1
解决办法
2286
查看次数

Syscall实现exit()

我写了一个简单的C程序,只调用exit()函数,但是strace说二进制文件实际上是调用exit_group,exit()是一个exit_group()包装器吗?这两个功能是否相同?如果是这样,为什么编译器会选择exit_group()而不是exit()?

c x86 assembly gcc system-calls

6
推荐指数
1
解决办法
2300
查看次数

Polygot包含nasm / yasm和C的文件

我想在C程序和要由nasm或yasm编译的程序集文件中包括很多魔术数字。

在纯C语言中,文件看起来像一系列定义,例如:

#define BLESS   55378008
#define ANSWER        42
...
Run Code Online (Sandbox Code Playgroud)

在nasm或yasm中,相同的include可以实现为:

%define BLESS   55378008
%define ANSWER        42
...
Run Code Online (Sandbox Code Playgroud)

唯一的不同是C和nasm 的define:前面的主角。#%

有什么办法可以编写一个polygot include,它可以让我将它同时包含在C和nasm中,并且只列出一次常量?

是的,我知道我可以使用sed或其他方法从另一个文件生成一个文件。

c x86 assembly nasm yasm

5
推荐指数
1
解决办法
356
查看次数

在函数内部使用 DB(定义字节)时出现分段错误

我很好奇如果我把db 0x41这个.text部分放在它通常所属的地方,而不是放在.data它通常所属的地方,会发生什么。它会出现段错误,但到底为什么呢?

下面的代码是在 Mint 19.1 中使用 和 进行编译、链接和执行nasmld

无段错误:

global _start
section .data
db 0x41
section .text
_start:
    mov rax, 60    ; Exit(0) syscall
    xor rdi, rdi
    syscall
Run Code Online (Sandbox Code Playgroud)

段错误:

global _start
section .text
_start:
    db 0x41
    mov rax, 60     ; Exit(0) syscall
    xor rdi, rdi
    syscall
Run Code Online (Sandbox Code Playgroud)

我使用以下命令来组装、链接和运行它:

global _start
section .data
db 0x41
section .text
_start:
    mov rax, 60    ; Exit(0) syscall
    xor rdi, rdi
    syscall
Run Code Online (Sandbox Code Playgroud)

assembly x86-64 nasm machine-code

3
推荐指数
1
解决办法
862
查看次数

在 x64 Linux 上,syscall、int 0x80 和 ret 之间有什么区别来退出程序?

经过多年的 C++ 和 Python,我昨天决定学习汇编(NASM 语法),我已经对退出程序的方式感到困惑。它主要是关于 ret 因为它是 SASM IDE 上的建议指令。

我显然是在为主要说话。我不关心 x86 向后兼容性。只有 x64 Linux 的最佳方式。我很好奇。

linux assembly x86-64 system-calls exit

3
推荐指数
1
解决办法
150
查看次数

Nasm分割错误

对不起,我是汇编代码的新手.我编码这个线条

section .text
     global _start
_start:
     nop
main:
     mov eax, 1
     mov ebx, 2
     xor eax, eax
     ret
Run Code Online (Sandbox Code Playgroud)

我用这些命令编译:

nasm -f elf main.asm
ld -melf_i386 -o main main.o
Run Code Online (Sandbox Code Playgroud)

当我运行代码时,Linux抛出了分段错误错误(我正在使用Linux Mint Nadia 64位).为什么会产生这个错误?

提前致谢

linux x86 assembly nasm

1
推荐指数
1
解决办法
3059
查看次数

如何绕过操作系统运行汇编代码?

首先,我不了解现代CPU和操作系统。为此,我将针对intel 8085处理器进行解释。当然,我希望你想象有一个操作系统可以在intel 8085上运行。

我们有这样的汇编代码:

MVI A,16
MVI B,16

ADD B

HLT
Run Code Online (Sandbox Code Playgroud)

这段代码非常简单。当此代码运行时,它会执行以下操作: 将数字 16 加载到 intel 8085 处理器的寄存器 a 和 b 中。然后将这两个寄存器的值相加。

当然,当我们尝试在操作系统中运行这段代码时,很可能什么也不会发生。

我想问的是:如何在操作系统上运行不包含任何系统调用(或任何特定于操作系统)的代码(绕过操作系统)?我不希望操作系统在执行此操作时崩溃。

cpu assembly operating-system 8085

1
推荐指数
1
解决办法
537
查看次数