C++ C++;外部程序集:我的代码中的错误在哪里?

C++ C++;外部程序集:我的代码中的错误在哪里?,c++,assembly,x86,C++,Assembly,X86,main.cpp // Calls the external LongRandom function, written in // assembly language, that returns an unsigned 32-bit // random integer. Compile in the Large memory model. // Procedure called LongRandomArray that fills an array with 32-bit unsigned

main.cpp

// Calls the external LongRandom function, written in

// assembly language, that returns an unsigned 32-bit

// random integer. Compile in the Large memory model.

// Procedure called LongRandomArray that fills an array with 32-bit unsigned 

// random integers

#include <iostream.h>

#include <conio.h>

extern "C" {

          unsigned long LongRandom();

          void LongRandomArray(unsigned long * buffer, unsigned count);

           }

const int ARRAY_SIZE = 20;

int main()

{

  // Allocate array storage and fill with 32-bit

  // unsigned random integers.

  unsigned long * rArray = new unsigned long[ARRAY_SIZE];

  LongRandomArray(rArray,ARRAY_SIZE);

  for(unsigned i = 0; i < 20; i++)

  {

    cout << rArray[i] << ',';

  }

  cout << endl;

  getch();

  return 0;

}

这个代码是基于Kip欧文汇编手册(第六版)的MS-DOS的16位示例,并为Borland C++ 5.01和TASM 4(参见第13.4章“链接到C/C++的实地址模式”)进行了详细说明。 16位模式下的指针由一个段和一个偏移量组成,通常写为
段:偏移量
。这不是处理器将计算的实际内存地址。您可以not在32位寄存器(
EDI
)中加载
段:偏移量
,并将值存储到内存中。所以

...
mov edi,bufferPtr
...
mov word ptr [edi],dx
...
错误了。您必须将指针的段部分加载到段寄存器中,例如
ES
,将偏移部分加载到适当的通用16位寄存器中,例如
DI
,并可能使用段覆盖:

...
push es
les di,bufferPtr         ; bufferPtr => ES:DI
...
mov word ptr es:[di],dx
...
pop es
...
ARG
将变量的名称替换为相应的
[bp+x]
操作数。因此,你需要一个开场白(和一个尾声)。TASM插入正确的指令,如果
PROC
头写得很好,这里就不是这样了。请看以下工作功能:

_LongRandomArray PROC C FAR
ARG bufferPtr:DWORD, count:WORD
    push es
    les di,bufferPtr
    mov cx, count
L1:
    call _LongRandom
    mov word ptr es:[di],dx
    add di,2
    mov word ptr es:[di],ax
    add di,2
    loop L1
    pop es
    ret
_LongRandomArray ENDP
使用BCC编译代码(BCC32):


那里发生了什么事?我们不是编译器,输出是什么?预期产量?到底出了什么问题?没错,请告诉我们发生了什么,以及您预期会发生什么。@DimitriMockelyn,“我们不是编译器”很酷!另外,这不是内联汇编,它只是普通的x86汇编代码。您在哪里退出
L1
循环?
_LongRandomArray PROC C FAR
ARG bufferPtr:DWORD, count:WORD
    push es
    les di,bufferPtr
    mov cx, count
L1:
    call _LongRandom
    mov word ptr es:[di],dx
    add di,2
    mov word ptr es:[di],ax
    add di,2
    loop L1
    pop es
    ret
_LongRandomArray ENDP
BCC -ml main.cpp longrand.asm