如何将字符串作为参数传递给“调用”函数内联汇编指令?
本质上,我希望能够做这样的事情:
//assume myFunction is defined and takes one argument that is an int
char * functionName = "myFunction";
int arg = 5;
__asm{
push a
call functionName
}
基本上我想调用一个名称存储在字符串中的函数。执行此操作的正确语法是什么?
编辑: 我们正在谈论 x86 汇编
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
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(3)
你不能,至少不能直接。
call 将地址作为参数。即使您编写“call functionName”,链接器也会将 functionname 替换为函数的实际地址。您需要首先将该字符串映射到其地址。一般来说,C 和 C++ 不支持任何类型的有关函数名称映射的运行时元数据,从而实现这一点。如果函数是从 DLL 导出的,则可以使用 GetProcAddress 查找其地址。
如果函数列表是静态的,您可以自己提前创建映射。
类似的东西:
一些注释:
我相信标准说函数指针可能比 PVOID 更大。这应该适用于 Windows x86/x64 平台。
您没有说明您使用的调用约定 - 这段代码假定 stdcall。
这是一件非常非常奇怪的事情——你想解决什么问题?
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:
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?
这是不可能的,您正在尝试执行按名称调用操作。汇编器仅具有按值调用,其中值是地址。您需要将名称转换为地址并将地址传递给汇编器,这意味着您需要名称和地址之间的某种交叉引用。编译器可以在这里帮助您,在 C 和 C++ 中,您需要查找函数指针来查看获取函数地址所需的语法,然后将其传递给汇编器。
先发制人:是的,有时编译器可以将符号嵌入到可执行文件中,然后可以对其进行搜索,但这是一种充满问题的方法。数据的格式可能会在编译器版本之间发生变化,信息可能会被链接器删除等等。
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.
我不知道有什么方法可以轻松做到这一点。在某些高级语言中,您可以使用反射来实现此目的,但 C 和汇编都没有该功能。当链接器完成时,所有函数调用都解析为地址。也许如果您有权访问某些调试基础设施,您可以对函数名称进行反向查找以获取其地址,但这对于汇编来说并不是一件容易实现的事情。
或者,您可以使用在编译时定义的函数指针来存储您感兴趣的函数的地址(尽管您仍然需要某种方法将字符串转换为函数指针,大概是通过字符串比较表查找)。如果您对此感兴趣,我建议您编写 C 等效代码,然后查看编译器输出的汇编代码,了解它如何处理函数指针。
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.