如何在汇编中正确调用 64 位 Windows API [英] How To Properly call 64 Bit Windows API In Assembly

查看:34
本文介绍了如何在汇编中正确调用 64 位 Windows API的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

使用 NASM 和 Mingw-w64 我一直在尝试运行以下程序,该程序应该使用 Windows API 将消息打印到屏幕上.它运行,但控制台上没有显示任何内容,并导致对内存位置的无效访问(错误代码 0x3e6h).为什么会这样,我怎样才能让程序正常运行?

Using NASM and Mingw-w64 I've been trying to run the following program which is supposed to print a message to the screen using the Windows API. It runs, but nothing shows on the console and it results in an invalid access to memory location (error code 0x3e6h). Why is that, and how can I get the program to run properly?

global main
extern ExitProcess
extern GetStdHandle
extern WriteFile

section .text
main:
    mov     rcx,                  0fffffff5h
    call    GetStdHandle

    mov     rcx,                  rax
    mov     rdx,                  NtlpBuffer
    mov     r8,                   NtnNBytesToWrite
    mov     r9,                   NtlpNBytesWritten
    mov     dword [rsp - 04h],    00h
    call    WriteFile
ExitProgram:
    mov     rcx,                  00h
    call    ExitProcess

section .data
NtlpBuffer:        db    'Hello, World!', 00h
NtnNBytesToWrite:  dd    0eh

section .bss
NtlpNBytesWritten: resd  01h

编译

nasm -f win64 test.asm
gcc -s -o test.exe test.obj

推荐答案

[rsp-04h] 正在堆栈指针下方寻址,这是个坏主意.无论如何,您在那里写的任何内容都会被 call 覆盖.看起来您需要复习一下调用约定的知识.必须为寄存器中的 4 个参数分配影子空间,并且必须将更多参数放置在它们之上.

[rsp-04h] is addressing below the stack pointer, that's a bad idea. Whatever you write there will be overwritten by the call anyway. Looks like you need to brush up on your knowledge of the calling convention. Shadow space for the 4 arguments in registers have to be allocated and further arguments must be placed on top of them.

另外,要写入的字节数应该是实际数字,而不是指针.

Also, the number of bytes to write should be the actual number, not a pointer.

global main
extern GetStdHandle
extern WriteFile

section .text
main:
    mov     rcx, 0fffffff5h
    call    GetStdHandle

    mov     rcx, rax
    mov     rdx, NtlpBuffer
    mov     r8, [NtnNBytesToWrite]
    mov     r9, NtlpNBytesWritten
    sub     rsp, 40
    mov     dword [rsp + 32], 00h
    call    WriteFile
    add     rsp, 40
ExitProgram:
    xor     eax, eax
    ret

section .data
NtlpBuffer:        db    'Hello, World!', 00h
NtnNBytesToWrite:  dq    0eh

section .bss
NtlpNBytesWritten: resd  01h

这篇关于如何在汇编中正确调用 64 位 Windows API的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆