views:

113

answers:

4

Essentially, I'd like to be able to do something like this:

//assume myFunction is defined and takes one argument that is an int
char * functionName = "myFunction";
int arg = 5;

__asm{
    push a
    call functionName
}

Basically I want to call a function whose name is stored in a string. What would be the proper syntax for doing this?

Edit: We are talking about x86 assembly

+1  A: 

You can't, at least not directly.

call takes an address as a parameter. Even though you write "call functionName", the linker replaces functionname with the actual address of the function. You'd need to first map that string to its address. In general, C and C++ don't support any sort of runtime metadata about function name mappings that would allow for this. If the function is exported from a DLL, you can use GetProcAddress to find its address.

If the list of functions is static, you can create the mapping ahead of time yourself.

Something like:

std:map<string, PVOID> functionMappings;
functionMappings["MyFunction"] = MyFunction;


// Later


PVOID function = functionMappings["MyFunction"];

__asm
{
    push a;
    call [function]
}

Some notes:

I believe the standard says that a function pointer may be larger than a PVOID. This should work on Windows x86/x64 platforms.

You didn't say what calling convention you were using - this code presumes stdcall.

This is a very, very odd thing to want to accomplish - what problem are you trying to solve?

Michael
I guess that I need to use GetProcAddress then. Sorry if it is a dumb question , but what exaclty is the type return value of that function?for example, would`int a = GetProcAddress( dllHandle, "myFunction" );`work?
Emil D
Btw, what in the code suggests __stdcall ? Is it just the fact that the caller is not popping the arguments from the stack , or is there something else?
Emil D
__stdcall is a calling convention - if you are writing assembly that does function calls, you need to understand calling conventions. Lots of resources are available on the net for GetProcAddress and calling conventions. MSDN even has sample code showing how to use the return value for GetProcAddress.
Michael
A: 

Short answer: Forget about it, if that's allowable, this will most likely be far too difficult to implement.

Longer answer: The easiest way I can think of to do this would be to create a look-up table that maps strings to functions (or more exactly, to function pointers). You would first need to think of a reasonable data structure for holding that map, and implement a string comparison function in order to compare functionName to the keys during a look-up. Last but not least, you would have to manually load the mapping entries into that table structure.

(I won't go into any more specifics, first because my assembler days are in the far past, and second, because I'm a little curious to find out if you couldn't achieve what you want to do with another, easier-to-implement solution... sorry.)

stakx
+1  A: 

This is not possible, you are trying to do a call-by-name operation. Assembler only has a call-by-value where value is an address. You need to convert the name to an address and pass the address to the assembler which means you need some kind of cross-reference between names and addresses. The compiler can help you out here, in C and C++ you need to look up function pointers to see the required syntax for getting the address of a function which can then be passed to the assembler.

Pre-emptive: Yes, sometimes the compiler can embed symbols into the executable which could then be searched through, but that's a method that is full of problems. The format of the data can change between compiler versions, the information can be stripped out by the linker and so on.

Skizz
A: 

I don't know of any way to do this easily. In some higher level languages you can use reflection to achieve this but neither C nor assembly has that functionality available. By the time the linker is done all function calls are resolved to addresses. Maybe if you had access to some debug infrastructure you could do a reverse lookup on the function name to get its address but that would not be a trivial thing to achieve from assembly.

Or you could use function pointers defined at compile time to store the addresses of the functions you are interested in (although you'd still need some way to translate your string to a function pointer, presumably via a string compare table lookup). If this is something you are interested in doing I'd suggest writing the C equivalent and then looking at the assembly code that the compiler outputs to see how it handles function pointers.

Andrew O'Reilly