[visual-studio]从内联程序集 VS2012-segfault 调用 C 函数吗?

标签: Visual-Studio
发布时间: 2014/3/1 3:52:25
注意事项: 本文中文内容可能为机器翻译,如要查看英文原文请点击上面连接.

好,我读过和我类似的问题,但还无法解决这个问题尚未。我也查过这个,很明显,可以解决我的问题。但它却没有。

我在我工作的文件中有一个 C 函数:

void copiarMuestreo(unsigned short * source, int * sPos, unsigned short * destination, int * dPos, int bitsPerSample ) {...}

其内部操作 C.中所做的一切是一个指针,指向一个向量,正的目的地

我想从内联程序集代码 (在这里我会把整个函数) 中调用此函数:

void unirArchivosWAVE( unsigned short *parte1, unsigned short *parte2, unsigned short *salida, int bitsPorMuestreo ){
int posParte1;                                                                                                  //Posicion en la que lee la primera muestra
int posParte2;                                                                                                  //Posicion en la que lee la segunda muestra
int posSalida;                                                                                                  //Posicion en la que escribe las muestras
int i = pistaEntrada1.numSamples;

__asm {
    push eax
    push ebx
    push ecx
    push edx
    push edi
    mov edi, i
    mov i, 0
    mov posParte1, 0
    mov posParte2, 0
    mov salida, 0
    forGrande:
      cmp i, edi
      jge finForGrande

      lea bx, posParte1
      lea cx, posParte2
      lea dx, posSalida

      push bitsPorMuestreo
      push dx
      push salida
      push bx
      push parte1
      call copiarMuestreo
      pop parte1
      pop bx
      pop salida
      pop dx
      pop bitsPorMuestreo

      push bitsPorMuestreo
      push dx
      push salida
      push cx
      push parte2
      call copiarMuestreo
      pop parte2
      pop cx
      pop salida
      pop dx
      pop bitsPorMuestreo

      inc i
      jmp forGrande
    finForGrande:
    fin:
      pop edi
      pop edx
      pop ecx
      pop ebx
      pop eax
    }
}

我 64 位,与 VS2012 表示,在英特尔酷睿 i5 在 Windows 8 中的编程。程序崩溃精美没有任何的任意位置,错误消息的我怀疑它是 segfault。但为什么呢?

起初我推的 32 位寄存器之前调用,我还以为他们正在 4 字节而不是 2 个字节使用的短裤是问题。没问题,它仍然崩溃。

我很笨。我还没试别的因为很好,我只是不知道什么尝试。我是新的程序集。

对不起,我的西班牙的变量名称。

解决方法 1:

使用 16 位寄存器的地址参数绝对不会工作。它只会使用一半的地址,所以每当这些指针获取取消引用他们可能在任何地方。

所有这些:

  lea bx, posParte1
  lea cx, posParte2
  lea dx, posSalida

应该是:

  lea ebx, posParte1
  lea ecx, posParte2
  lea edx, posSalida

很明显的 push 下面的老年退休金计划也应使用 32 位寄存器。

更新:

刚刚注意到别的东西。您正在设置您 salida 参数为 NULL,当你想要设置的 assumedly posSalida 为零。这条线:

mov salida, 0

大概应该是:

mov posSalida, 0

更新 2:

此外值得一提 ecx 寄存器不能保证在函数调用之间保留。所以很有可能的时候您返回从第一次调用 copiarMuestreo ,您设置的地址到 ecx posParte2 已不再正确。

可能最好的解决方案,将进行第一次调用之后只初始化 ecx copiarMuestreo ,因为它不直到第二次调用需要。

官方微信
官方QQ群
31647020