导致从用户空间重新启动

导致从用户空间重新启动

这个程序是为 x86 Linux 系统上的 Gnu Assembler 编写的,应该会导致三重错误,然后重新启动。

.text
.global _start
_start:
# write our string to stdout

    movl    $len,%edx   # third argument: message length
    movl    $msg,%ecx   # second argument: pointer to message to write
    movl    $1,%ebx     # first argument: file handle (stdout)
    movl    $4,%eax     # system call number (sys_write)
    int $0x80       # call kernel
# Triple Fault -- reboot
    movq    $1, %rsp    # Load the stack pointer with a one
    pushq    %rax       # Push the A register, should cause a triple fault.

# and exit

    movl    $0,%ebx     # first argument: exit code
    movl    $1,%eax     # system call number (sys_exit)
    int $0x80       # call kernel

.data                   # section declaration

msg:
    .ascii  "Will reboot by triple fault!\n"    # our dear string
    len = . - msg           # length of our dear string

相反,它会导致分段错误。如果以 root 身份运行,是否可以使其在用户模式下工作?

答案1

Linux 内核不允许用户空间执行此类可能影响其他用户的操作。作为 root,您可能能够执行类似的操作,但内核可能仍然会阻止这种直接控制;毕竟,根进程仍然是用户态进程,但可以不受限制地访问内核的系统调用。

更正确的/UNIXy 方法是在内核中执行此类操作,并公开用户态进程可以用来调用它的接口。然后您的代码将在内核的上下文中执行,并且可以完全访问用户通常不应访问的硬件/系统功能。

答案2

此类 CPU 故障由内核模式中断处理程序处理。内核代码很好,如果发生用户空间故障(如除以零或访问无效内存),第一个中断处理程序应该可以正确处理。其他任何事情都是内核中的错误 - 如果中断处理程序中存在故障,基本上唯一明智的做法是转储寄存器和堆栈,然后放到调试器(如 OpenBSD 所做的)或 HCF 中,以便可以记录恐慌消息。存在三重故障是因为到那时,您的代码已经无法正常工作。

TL;DR:要使其发挥作用,您必须在 Linux 的故障处理代码中找到错误。

您也许可以在故意破坏中断处理程序的内核模块中执行此操作,但也很可能导致系统崩溃。和效果不一样啊shutdown -r now

答案3

在Linux上,您可以使用reboot系统调用:

#include <unistd.h>
#include <sys/reboot.h>

int main(void) {
    return reboot(LINUX_REBOOT_CMD_RESTART);
}

答案4

如果您确实需要汇编程序(?!),这曾经可以从 root 运行(我认为使用 nasm):

BITS    32
    mov eax, 88
    mov ebx, 0xfee1dead
    mov ecx, 85072278
    mov edx, 0x01234567
    int  0x80

相关内容