将GNU汇编程序编译为windows

时间:2014-10-19 11:11:00

标签: c++ c assembly x86-64 calling-convention

我需要编译在Windows中用GNU汇编程序编写的汇编文件。 使用as汇编程序在Linux中正确编译该文件。 程序集文件包含一个全局减速函数,它接收2个参数,应该从C / C ++ visual studio 2013中调用。

我该怎么做?

以下是.s文件的一部分:

.globl func
func:
pushq %rbp
pushq %r12
pushq %r15
pushq %r13
pushq %r14
subq $40,%rsp

movq %rdi,%rbp //the first param
movq %rsi,%r12 //the second param

//real code starts here...


//restore stack and return

addq $40,%rsp
popq %r14
popq %r13
popq %r15
popq %r12
popq %rbp
ret

全部谢谢!

1 个答案:

答案 0 :(得分:1)

Microsoft调用约定与sysv abi不同,它几乎与世界其他地方一样。如果你从问题中省略的代码是自包含的,你基本上只需要担心参数传递和保留寄存器。

幸运的是,要访问参数,您只需要分别用rdirsi替换两个寄存器rcxrdx

至于保存寄存器,代码可能不会修改rbx因为需要保留并且没有匹配的push。此外,这两项惯例都会保留r12r15,因此我们不必担心这些问题。但是,Microsoft约定还要求保留rdirsi,它们用于sysv abi下的参数,否则被视为volatile。因此,您需要为这些添加push / pop对。

你没有提到功能体是否使用任何SIMD或FPU的东西,所以我不打算涵盖那些。另外,我假设你的函数正在返回void

因此,修改后的程序集可能如下所示:

.globl func
func:
pushq %rbp
pushq %r12
pushq %r15
pushq %r13
pushq %r14
pushq %rdi
pushq %rsi
subq $40,%rsp

movq %rcx,%rbp //the first param
movq %rdx,%r12 //the second param

//real code starts here...


//restore stack and return

addq $40,%rsp
popq %rsi
popq %rdi
popq %r14
popq %r13
popq %r15
popq %r12
popq %rbp
ret

在C方面,您只需要将其声明为extern void func(int a, int b)或等效。从c ++调用时,您应该使用extern "C"