C++通过功能模板中的通过功能指针

发布于 2025-01-21 04:59:21 字数 466 浏览 1 评论 0 原文

我正在尝试将功能指针传递在模板中,然后在ASM代码中使用它:

template <auto T>
_declspec(naked) void Test()
{
    __asm
    {
        lea eax, T
        jmp [eax]
    }
}

int main()
{
    Test<MessageBoxA>();
    Test<Sleep>();
}

我知道执行时裸函数会崩溃,但我简化了代码以显示我要实现的目标。

该代码的问题是,一旦编译,如果您以拆卸器中的汇编代码查看,它将看起来像这样:

lea eax, 0
jmp [eax]

它在EAX中存储0。相反,它应将 MessageBoxa 地址存储在EAX中。

我不知道我在做错事还是编译器失败。

I'm trying to pass a function pointer in a template, to then use it in asm code:

template <auto T>
_declspec(naked) void Test()
{
    __asm
    {
        lea eax, T
        jmp [eax]
    }
}

int main()
{
    Test<MessageBoxA>();
    Test<Sleep>();
}

I know the naked function will crash when executed but I've simplified the code to show only what I'm trying to achieve.

The problem with this code is that once compiled, if you look at the assembly code in a disassembler, it will look like this:

lea eax, 0
jmp [eax]

It is storing 0 in eax. Instead, it should store the MessageBoxA address (and Sleep in another function) in eax.

I don't know if I'm doing something wrong or the compiler is failing.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(1

帥小哥 2025-01-28 04:59:21

我不是组装专家,而是创建 static constexpr void*将设置为非类型模板参数值似乎有能力:

template <auto T>
__declspec(naked) void Test()
{
    static constexpr void* fptr = T;
    
    __asm 
    {
        lea eax, fptr
        jmp [eax]
    }
}

const void sleep()
{
}

int main()
{
    Test<(&sleep)>();
    return 0;
}

生成

lea     eax, OFFSET void * `void Test<&void sleep(void)>(void)'::`2'::fptr
jmp     SHORT DWORD PTR [eax]

示例可以在编译器资源管理器上播放: https://godbolt.org/z/f1d7daa49

I'm not an assembly expert, but creating a static constexpr void* set to the non-type template parameter value seems to do the trick:

template <auto T>
__declspec(naked) void Test()
{
    static constexpr void* fptr = T;
    
    __asm 
    {
        lea eax, fptr
        jmp [eax]
    }
}

const void sleep()
{
}

int main()
{
    Test<(&sleep)>();
    return 0;
}

generates

lea     eax, OFFSET void * `void Test<&void sleep(void)>(void)'::`2'::fptr
jmp     SHORT DWORD PTR [eax]

The example can be played with on compiler explorer: https://godbolt.org/z/f1d7daa49

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文