通过程序集

时间:2017-12-12 19:09:07

标签: c++ arrays assembly x86

目前,我遇到了很多问题。当我调试我的代码时,我的C ++正常运行,直到我进入汇编函数调用,它在汇编代码而不是L1中跳转到L2。我不确定为什么会这样做。最重要的是,我试图将阵列打印到屏幕上,但截至目前,我只是获得了一个巨大的数字。我尝试包括欧文的图书馆并使用" WriteDec"尝试打印出元素,但图书馆甚至无法被识别。

下面是我目前的程序集代码,用于从C ++代码中获取3个数组,并将它们加在一起。

.model flat, C
.model flat, STDCALL

.code
ASMsumarray PROC,
ptr1:PTR DWORD,     ; points to array
ptr2:PTR DWORD,     ; points to array
ptr3:PTR DWORD      ; points to array
pushad              

    mov esi,ptr2  
    mov edi,ptr3  
    mov ecx,10    

    L1:
        mov ebx,[edi]  ;mov first elem of ptr3 to ebx
        add ebx,[esi]  ;add elem from ptr2 to ebx
        mov [esi],ebx  ;mov ebx to spot in ptr2. ptr2 elem now contains sum of ptr2 and 3
        add edi,4
        add esi,4
    loop L1
        mov edi,ptr1  ;mov ptr1 to esi
        mov ecx,10    ;mov ptr2 to edi
        sub edi,40
        sub esi,40
    L2:
        mov ebx,[edi]  ;mov first elem of ptr2 to ebx
        add ebx,[esi]  ;add elem from ptr1 to ebx
        mov [esi],ebx  ;mov ebx to spot in ptr1. ptr1 elem now contains sum of ptr1 and 2
        add edi,4
        add esi,4
    loop L2

    popad               ;//pop registers off the stack
        ret
ASMsumarray ENDP

这是c ++代码。

#include <iostream>
#include <ctime>

using namespace std;

extern "C" int ASMsumarray(int array1[], int array2[], int array3[]);

int main() {
    srand(time(NULL));      //seed rand num     

    int array1[10] = { 1,1,1,1,1,1,1,1,1,1 };
    int array2[10] = { 1,1,1,1,1,1,1,1,1,1 };
    int array3[10] = { 1,1,1,1,1,1,1,1,1,1 };
/*
    for (int i = 0; i < 10; i++) {
    array1[i] = rand() % 10;
    array2[i] = rand() % 10;
    array3[i] = rand() % 10;
    cout << endl;
    }
    cout << endl;
    */

    //for (int i = 0; i < 10; i++) {
    //cout << array1[i] << endl;
    //}

    cout << "The number is " << ASMsumarray(array1, array2, array3) << endl;
    return 0;
}

1 个答案:

答案 0 :(得分:0)

  

最重要的是,我试图将数组打印到屏幕上,但截至目前,我只是获得了一个巨大的数字。

您的函数应该返回int,但您正在使用popad来恢复所有寄存器,包括来电者{的值{ {1}}。因此,您的返回值是调用者在eax中留下的垃圾。

此外,您从未将值放入eax:您正在使用的调用约定需要eax中的返回值,就像几乎所有x86调用约定一样。

使用eax / push保存/恢复您实际需要使用的保留调用的寄存器。 (并尽可能少地使用,例如使用popeaxecx作为指针和临时用户。)

顺便说一句,你的C ++调用者不打印数组,它只打印 sum (函数返回值)。你的函数的返回值是一个标量。目前尚不清楚为什么要修改数组内容。

  

当我调试我的代码时,我的C ++正常运行,直到我进入汇编函数调用,它在汇编代码而不是L1中跳转到L2。

这没有任何意义。确保在实际功能入口点(不是L1或L2)设置断点。或者单步执行单个指令到您的函数中,而不是通过C语句。