如何在C/C++使用内联汇编[英文版]
2010-01-10 09:37:23 来源:WEB开发网Using ASM RegistersThe asm statement alters the registers outside the programmer's explicit assembly language instructions. Registers contain whatever values the normal control flow leaves in them at the point of the asm statement. For 16-bit memory modelsYou do not need to preserve the following registers when writing inline assembly language: AX, BX, CX, DX, SI, DI, ES, and flags (other than DF).
C and C++ do not expect these registers to be maintained between statements, but they do preserve the following registers: CS, DS, SS, SP and BP.
NoteThe compiler does not use registers to hold register variables for functions containing inline assembly code. For 32-bit memory modelsFunctions can change the values in the EAX, ECX, EDX, ESI, EDI registers.
Functions must preserve the values in the EBX, ESI, EDI, EBP, ESP, SS, CS, DS registers (plus ES and GS for the NT memory model).
Always set the direction flag to forward.
To maximize speed on 32-bit buses, make sure data aligns along 32-Function return values
For 16-bit models. If the return value for a function is short (a char, int, or near pointer) store it in the AX register, as in the previous example, expon2. If the return value is long, store the high word in the DX register and the low word in AX. To return a longer value, store the value in memory and return a pointer to the value. For 32-bit models. Return near pointers, ints, unsigned ints, chars, shorts, longs and unsigned longs in EAX. 32-bit models return far pointers in EDX, EAX, where EDX contains the segment and EAX contains the offset. When C linkage is in effect. Floats are returned in EAX and doubles in EDX, EAX, where EDX contains the most significant 32 bits and EAX the least significant. When C++ linkage is in effect. The compiler creates a temporary copy on the stack and returns a pointer to it. Function return valuesFor 16-bit memory models. If the return value for a function is short (a char, int, or near pointer) store it in the AX register, as in the previous example, expon2. If the return value is long, store the high word in the DX register and the low word in AX. To return a longer value, store the value in memory and return a pointer to the value. For 32-bit models. Return near pointers, ints, unsigned ints, chars, shorts, longs, and unsigned longs in EAX. 32-bit models return far pointers in EDX, EAX, where EDX contains the segment and EAX contains the offset. When C linkage is in effect. Floats are returned in EAX and doubles in EDX, EAX, where EDX contains the most significant 32 bits and EAX the least significant. When C++ linkage is in effect. The compiler creates a temporary copy on the stack and returns a pointer to it. Interfacing to a member functionThe easiest way to interface an assembly language routine to a class member function is to provide a C wrapper function that can be called from the assembly language routine.
An alternative is to write the member function in C++ and compile it with normal out-of -line member functions.
Calling C Functions from an ASM BlockC functions, including C library functions, can be called from within the asm block, as in the following example:
#include <stdio.h>
char format [] = "% s %s %s ";
char alas[] = "Alas,";
char poor[] = "poor";
char Yorick[] = "Yorick!";
void main(void)
{
asm
{ mov AX, offset Yorick
push AX
mov AX, offset poor
push AX
mov AX, offset Alas
push AX
mov AX, offset format
push AX
call printf
}
}
Simply push the needed arguments from right to left before calling the function, since function arguments are passed on the stack. To print the message, the example pushes pointers to the three strings, formats them, and then calls printf. Calling C++ functionsAn ASM block can call only global C++ functions that are not overloaded because the types of the arguments are unknown. The compiler issues an error if an ASM block calls an overloaded global C++ function or a C member function.
You can also call a function declared with extern "C" linkage from an asm statement within a C++ program, because all the standard header files declare the library functions to have extern "C" linkage.
Defining ASM blocks as C macrosA C++ macro is a convenient way to insert assembly language into source code. But, because a macro expands into a single, logical line, take care when writing them.
If the macro expands into multiple instructions, enclose the instructions in an ASM block. The asm statement must precede each instruction. Also separate comments from code with /**/ characters rather than //. Unless you take these precautions, the compiler can be confused by C or C++ statements to the left or right of the assembly code or interpret instructions as comments when the macro becomes a single line. Without the closing brace, the compiler cannot tell where the assembly language ends.
Warning: Do not use double-slash (//) characters within a macro. The compiler terminates the macro when it sees a double-slash.
An ASM block written as a macro can accept arguments but, unlike a C macro, it cannot return values. But some MASM macros can be written as macros for C. The following MASM macro sets a video page to the value specified in the argument page:
findpage MACRO page
The following C macro does the same thing:
mov AH, 5
MOV AL,page
int 10h
ENDM#define findpage (page) asm
{
asm mov AH,5
asm mov AL,page
asm int 10h
}
更多精彩
赞助商链接