The MASM Forum Archive 2004 to 2012

Project Support Forums => GoAsm Assembler and Tools => Topic started by: scalprum.eu on May 18, 2009, 07:02:58 AM

Title: calling external labels from C/C++ inline assembly
Post by: scalprum.eu on May 18, 2009, 07:02:58 AM
Hi,
this is my very first post.
Here is my question, hope someone can help.

I have two files, interface.c and interface.asm

interface.c
...
__asm call label_2 // inline assembly : call an assembly label defined in interface.asm
...


interface.asm
...
label_2:
...


I compile interface.asm with GoAsm and interface.c with MinGW, then I link the two object files using the MinGW linker, and it works perfectly, that is label_2 is called correctly. I do not declare label_2 as "extern" in the two files.

The problem arises when I compile interface.asm with GoAsm and interface.c with the microsoft compiler cl.exe .
The cl.exe compiler complains saying ".\interface.c(55) : error C2094: label 'label_2' was undefined"

Now, being aware of name mangling, scope, etc, I tried to prefix underscores, declaring "extern", using the GoAsm switch "/ms", any combination really, but nothing works.
Any ideas? ... thanks 

Title: Re: calling external labels from inline assembly
Post by: UtillMasm on May 18, 2009, 07:05:39 AM
MinGW?
:(
Title: Re: calling external labels from inline assembly
Post by: scalprum.eu on May 18, 2009, 07:09:16 AM
MinGW is the port of the GNU gcc compiler on windows ...
www.mingw.org/ (http://www.mingw.org/)
Title: Re: calling external labels from inline assembly
Post by: jorgon on May 18, 2009, 08:32:15 AM
Hi scalprum.eu

Welcome to the forum.

Have you tried decorating label_2 in the asm file as follows:-

_label_2@0

The number after the @ sign being the number of bytes (in decimal) taken up by the parameters?
Title: Re: calling external labels from inline assembly
Post by: scalprum.eu on May 18, 2009, 09:22:23 AM
Hi jorgon.

.... reading the GoAsm manual, I was aware of the _label_2@0 decoration issue, so I tried, but cl.exe replied the same error code.

I think that cl.exe expects any label to be explicitly declared as global or extern before its use. The problem is that inline assembly does not allow the "extern" keyword.
Moreover, if I declare label_2 as extern in the .c file ...
interface.c
...
extern label_2
...

... cl.exe compiles ok, but then link.exe is unable to match label_2 in the .asm file.

One obvious solution would be to declare label2 as follow:
interface.c
...
extern void __cdecl label_2(  ); // let the compiler think label_2 is a C external function
...
label_2(); // call label_2 as a normal C function. Within the interface.asm file there must be a " _label_2: " label. 
...


Although this approach may works, it's rather a sort of "hack" that somehow complicates things in frequent use of the "interfacing feature" . The MinGW-gcc compiler does not need this approach.

... does anyone know a simple way of calling/jumping to external labels from C inline assembly ? Thanks ...


Title: Re: calling external labels from inline assembly
Post by: MichaelW on May 18, 2009, 06:53:57 PM
I can't find any way to do it without an extern statement, but you can readily call the label from inline assembly. My example complicates the call somewhat, but it could be minimized to simply a call instruction.

code section
_label_2:
    mov eax, [esp+4]
    add eax, 1
    ret


#include <windows.h>
extern cdecl int label_2(int);
int main(void)
{
    int x = 12345;
    __asm push x
    __asm call label_2
    __asm mov x, eax
    printf("%d\n",x);
    getch();
    return 0;
}


Title: Re: calling external labels from inline assembly
Post by: scalprum.eu on May 19, 2009, 05:21:32 AM
.... yes, the only way of calling an externally-declared label from C inline assembly, must be of declaring that label as a function first.

Thank you to jorgon and MichaelW for replying!
Title: Re: calling external labels from inline assembly
Post by: Vortex on May 19, 2009, 10:25:44 AM
Here is another example built with Pelles C :

/* Coded with Pelles C 6.00 RC 1 */

#define WIN32_LEAN_AND_MEAN
#include <windows.h>

extern int __stdcall StdOut(char *);

int main(int argc,char *argv[])
{
    char *msg="Calling an external label with Pelles C";

    __asm{
            mov     eax,msg
            push    eax
            call    StdOut
         }

    return 0;
}


.code

StdOut  FRAME lpszText      ; Masm32 function translated to GoAsm

LOCALS  hOutPut,bWritten,sl

    invoke GetStdHandle,-11
    mov [hOutPut], eax
    invoke lstrlen,[lpszText]
    mov [sl],eax
    invoke WriteFile,[hOutPut],[lpszText],[sl],ADDR bWritten,0
    mov eax,[bWritten]
    ret
   
ENDF


All the trick is to instruct GoAsm to output decorated symbols :

\GoAsm\GoAsm /ms StdOut.asm
[attachment deleted by admin]
Title: Re: calling external labels from inline assembly
Post by: mitchi on May 19, 2009, 04:01:51 PM
Linking / name decoration is a tricky subject. It's a good thing that we have an expert like Vortex around  :bg