user3314204
user3314204

Reputation: 21

What is wrong with the following inline assembly?

When I try to compile the following, gcc fails with

error: inconsistent operand constraints in an 'asm'"

Unfortunately, when I pull the function into a standalone file it compiles fine, so I'm really not sure what the issue is. The idea behind the function is to provide a wrapper around a function written in assembly that will enforce the expected calling convention regardless of the target platform.

int wrap(int(*asmfn)(int,int,int,int), int param1, int param2, int param3, int param4) {
    int x;
    asm ( "push %1;"            //save the input operand so it's not clobbered
          "push %5;"            //push the params RTL
          "push %4;"
          "push %3;"
          "push %2;"
          "call *%1;"           //call the function
          "pop %2;"             //caller cleanup / restore the param operands so they are not clobbered
          "pop %3;"
          "pop %4;"
          "pop %5;"
          "pop %1;"             //restore the other operand so it's not clobbered
          "mov %%eax, %0;"      //save the retval to a local
          : "=X" (x)
          : "c" (asmfn), "d" (param1), "b" (param2), "S" (param3), "D" (param4)
          : "cc", "memory", "%eax" );
    return x;
}

I've tried constraining the output operand into either memory only or a register, or even constraining it specifically into eax and dropping "%eax" from the clobber list, but I get the same error either way. What am I missing?

Upvotes: 1

Views: 505

Answers (1)

user3314204
user3314204

Reputation: 21

After much experimentation I realized the issue and why it wasn't causing an error when standalone: this was in code being compiled into a shared object, and hence "-fPIC" was enabled. This causes gcc to use ebx to store current eip on entrance to a function so it can find the GOT via a relative offset from the function (which is known at compile time) so that the code can be position independent. As a result, any inline assembly in PIC that uses ebx as an operand will give this completely opaque error.

Upvotes: 1

Related Questions