调用具有不同arg计数的函数

时间:2018-06-24 11:50:15

标签: c++ function-pointers

我正在反编译一个非常老的游戏,我的目标是还原100%本机代码。因此,我需要尽可能地保留现有架构(例如,仅使用amp-custom并没有太大帮助)。

我有一组静态函数,它们具有不同数量的参数。它们存储在这样的结构中:

std::function

并且这样填充:

struct ScriptFunction 
{
    const wchar_t* m_name;
    void* m_func;  // ptr to specific function 
    void* m_returnType;
    int m_argCount;
};

那么,如何使用给定的 m_argCount void **参数调用 ScriptFunction :: m_func ?我必须以某种方式在堆栈上推送参数并调用func-call,但是我不知道。

一些asm代码? va_list?但是如何在运行时填充它?

UPD:调用方看起来像这样

ScriptFunction s_functions[206] = {
    {L"AddMoveAroundDesire", &ScriptFunctions::AddMoveAroundDesire, &CScriptType::s_void, 2},
    {L"AddDoNothingDesire", &ScriptFunctions::AddDoNothingDesire, &CScriptType::s_void, 2},
    {L"AddAttackDesire", &ScriptFunctions::AddAttackDesire, &CScriptType::s_void, 3},
    {L"AddAttackDesireEx", &ScriptFunctions::AddAttackDesireEx, &CScriptType::s_void, 4},
    {L"AddGetItemDesire", &ScriptFunctions::AddGetItemDesire, &CScriptType::s_void, 2},
 ...

1 个答案:

答案 0 :(得分:1)

在该语言内,仅存在switch / cast解决方案。这样,编译器就可以生成正确的调用约定:例如,在x86-64 Linux上,前几个参数在预定义的寄存器中传递。 (优化程序可能将不同的路径合并为跳转,成为您期望的那种展开循环。)还要记住,仅在C / C ++中根本没有“堆栈”。

顺便说一句,也不能保证为函数使用void*(因为它可以指向任何 object 但它们不是对象),尽管它通常可以工作(并且POSIX要求{ {1}}。