Assembly 将气体转换为MASM时,我做错了什么?

Assembly 将气体转换为MASM时,我做错了什么?,assembly,x86-64,masm,avx,calling-convention,Assembly,X86 64,Masm,Avx,Calling Convention,我已经注意到了其他各种各样的合成税,比如常数的对齐和寻址(所有这些都是全局性的),我已经尽力将气体转换为与windows兼容的。但如果运气不好,我的单元测试在windows上会一直失败。。。请不要建议使用内部函数,我必须在这个例程的最终程序中控制程序集。谢谢大家! eecos: vmovaps %xmm0, %xmm1 # xmm1 = xmm0 vmovaps one(%rip), %xmm0 # initialize register to 1 vmulps %x

我已经注意到了其他各种各样的合成税,比如常数的对齐和寻址(所有这些都是全局性的),我已经尽力将气体转换为与windows兼容的。但如果运气不好,我的单元测试在windows上会一直失败。。。请不要建议使用内部函数,我必须在这个例程的最终程序中控制程序集。谢谢大家!

eecos:
    vmovaps %xmm0, %xmm1 # xmm1 = xmm0

    vmovaps one(%rip), %xmm0 # initialize register to 1

    vmulps %xmm1, %xmm1, %xmm2 # x^2
    vmulps %xmm2, %xmm2, %xmm3 # x^4
    vmulps %xmm2, %xmm3, %xmm4 # x^6
    vmulps %xmm2, %xmm4, %xmm5 # x^8
    vmulps %xmm2, %xmm5, %xmm6 # x^10
    vmulps %xmm2, %xmm6, %xmm7 # x^12
    vmulps %xmm2, %xmm7, %xmm8 # x^14

    vmulps coef2(%rip), %xmm2, %xmm2
    vmulps coef4(%rip), %xmm3, %xmm3
    vmulps coef6(%rip), %xmm4, %xmm4
    vmulps coef8(%rip), %xmm5, %xmm5
    vmulps coef10(%rip), %xmm6, %xmm6
    vmulps coef12(%rip), %xmm7, %xmm7
    vmulps coef14(%rip), %xmm8, %xmm8

    vaddps %xmm2, %xmm0, %xmm0
    vaddps %xmm3, %xmm0, %xmm0
    vaddps %xmm4, %xmm0, %xmm0
    vaddps %xmm5, %xmm0, %xmm0
    vaddps %xmm6, %xmm0, %xmm0
    vaddps %xmm7, %xmm0, %xmm0
    vaddps %xmm8, %xmm0, %xmm0

    # setup rounding at the hundred thousanth place
    # hundred thousanth place should be stable enough for physics
    vmulps hunth(%rip), %xmm0, %xmm0
    vroundps $8, %xmm0, %xmm0
    vmulps invhunth(%rip), %xmm0, %xmm0
    ret # return xmm0
我在MASM有什么

eecos PROC FRAME
    .endprolog
    vmovaps xmm1, xmm0 ; xmm1 = xmm0

    vmovaps xmm0, XMMWORD PTR one ; initialize register to 1

    vmulps xmm2, xmm1, xmm1 ; x^2
    vmulps xmm3, xmm2, xmm2 ; x^4
    vmulps xmm4, xmm3, xmm2 ; x^6
    vmulps xmm5, xmm4, xmm2 ; x^8
    vmulps xmm6, xmm5, xmm2 ; x^10
    vmulps xmm7, xmm6, xmm2 ; x^12
    vmulps xmm8, xmm7, xmm2 ; x^14

    vmulps xmm2, xmm2, XMMWORD PTR coef2
    vmulps xmm3, xmm3, XMMWORD PTR coef4
    vmulps xmm4, xmm4, XMMWORD PTR coef6
    vmulps xmm5, xmm5, XMMWORD PTR coef8
    vmulps xmm6, xmm6, XMMWORD PTR coef10
    vmulps xmm7, xmm7, XMMWORD PTR coef12
    vmulps xmm8, xmm8, XMMWORD PTR coef14

    vaddps xmm0, xmm0, xmm2
    vaddps xmm0, xmm0, xmm3
    vaddps xmm0, xmm0, xmm4
    vaddps xmm0, xmm0, xmm5
    vaddps xmm0, xmm0, xmm6
    vaddps xmm0, xmm0, xmm7
    vaddps xmm0, xmm0, xmm8

    ; setup rounding at the hundred thousanth place
    ; hundred thousanth place should be stable enough for physics
    vmulps xmm0, xmm0, XMMWORD PTR hunth
    vroundps xmm0, xmm0, 8
    vmulps xmm0, xmm0, XMMWORD PTR invhunth
    ret ; return xmm0
; cosine subroutine here
eecos ENDP
END
输出(首先是气体)

我的第一个猜测是Windows上的调用约定不同。但我不能肯定。你能用一个测试工具做一个测试吗,这样其他人就可以正确地调试它了?另外,请把输出日志复制到问题中。堆栈溢出问题必须是自包含的,不应依赖外部粘贴服务。如果您使用MinGW-binutils/gcc或clang构建GAS代码,它是否在Windows上工作?如果它是为x86-64 SystemV ABI的调用约定编写的,我想不会。Agner Fog有一个呼叫约定指南:。我建议查看调用者中编译器生成的代码,看看它是如何传递参数的。顺便说一句,没有FMA的AVX1只在少数机器上有用,比如推土机(在Piledriver之前)和Sandy/Ivy Bridge(在Haswell之前)。也许还有捷豹。如果这是你需要的;很好,否则您可能会考虑用内存源VFMA指令进行累加。除非FMA与附加组件Haswell或Broadwell的延迟更长会成为瓶颈。奇怪的是,在这一步中,你做的是线性加法链,而不是组合向量对来获得指令级并行性,除非这对于舍入是严格必要的。问题是我如何访问全局变量,比如XMMWORD PTR coef2,应该是[coef2]我似乎不知道如何为AVX编辑OP as,这实际上只是困扰SSE(注意xmm寄存器而不是ymm)以防止cpu点击真正的AVX指令时发生的开销。我首先猜测Windows上的调用约定是不同的。但我不能肯定。你能用一个测试工具做一个测试吗,这样其他人就可以正确地调试它了?另外,请把输出日志复制到问题中。堆栈溢出问题必须是自包含的,不应依赖外部粘贴服务。如果您使用MinGW-binutils/gcc或clang构建GAS代码,它是否在Windows上工作?如果它是为x86-64 SystemV ABI的调用约定编写的,我想不会。Agner Fog有一个呼叫约定指南:。我建议查看调用者中编译器生成的代码,看看它是如何传递参数的。顺便说一句,没有FMA的AVX1只在少数机器上有用,比如推土机(在Piledriver之前)和Sandy/Ivy Bridge(在Haswell之前)。也许还有捷豹。如果这是你需要的;很好,否则您可能会考虑用内存源VFMA指令进行累加。除非FMA与附加组件Haswell或Broadwell的延迟更长会成为瓶颈。奇怪的是,在这一步中,你做的是线性加法链,而不是组合向量对来获得指令级并行性,除非这对于舍入是严格必要的。问题是我如何访问全局变量,比如XMMWORD PTR coef2,应该是[coef2]我似乎不知道如何为AVX编辑OP as,这实际上只是困扰SSE(注意xmm寄存器而不是ymm)以防止cpu命中真正的AVX指令时发生的开销