我正在跟踪一个偷偷摸摸的错误,该错误是在我向一个类中添加模板参数时发生的。在初始化期间,它将静态局部变量放置在内存的特定部分中。
在模板化的函数/类中使用GCC的section属性似乎只是被忽略了。我的问题听起来与this user was facing类似。但是,我看不到建议的工作环境适用于我的情况。
我整理了一个非常简单的示例来说明这一点。考虑这段代码:
void handler_func() { }
using handler_type = void(*)();
struct S { handler_type handler; };
template <typename T>
void templated()
{
static S __attribute__((section(".templ_section"))) __attribute__((used)) templ_instance {handler_func};
}
void free()
{
static S __attribute__((section(".free_section"))) __attribute__((used)) free_instance {handler_func};
}
struct Foo{};
int main(int argc, char** argv)
{
templated<Foo>();
free();
}
我希望将templ_instance
放在.templ_section
中,并将free_instance
放在.free_section
中。
但是,这是GCC变量的位置:
0000000000000000 l O .free_section 0000000000000008 _ZZ4freevE13free_instance
0000000000000000 l d .data.rel.local._ZZ9templatedI3FooEvvE14templ_instance 0000000000000000 .data.rel.local._ZZ9templatedI3FooEvvE14templ_instance
0000000000000000 u O .data.rel.local._ZZ9templatedI3FooEvvE14templ_instance 0000000000000008 _ZZ9templatedI3FooEvvE14templ_instance
这是Clang所做的:
0000000000000000 l O .free_section 0000000000000008 _ZZ4freevE13free_instance
0000000000000000 w O .templ_section 0000000000000008 _ZZ9templatedI3FooEvvE14templ_instance
我不敢相信这是GCC中的预期行为。有什么办法解决吗?
答案 0 :(得分:1)
如果碰巧templ_instance
的类型不取决于模板类型T
,则可以通过在自由函数中包含该对象来解决该问题:
S& templated_impl()
{
static S __attribute__((section(".templ_section"))) __attribute__((used)) templ_instance {nullptr};
return templ_instance;
}
template <typename T>
void templated()
{
static S& templ_instance = templated_impl();
templ_instance = { handler_func };
}
.zero 8
.section .free_section,"aw"
.align 8
.type free()::free_instance, @object
.size free()::free_instance, 8
free()::free_instance:
.quad handler_func()
.section .templ_section,"aw" // BINGO!
.align 8
.type templated_impl()::templ_instance, @object
.size templated_impl()::templ_instance, 8
templated_impl()::templ_instance:
.size void templated<Foo>(), .Lfunc_end4-void templated<Foo>()
.cfi_endproc
.type templated_impl()::templ_instance,@object # @templated_impl()::templ_instance
.section .templ_section,"aw",@progbits
.p2align 3
templated_impl()::templ_instance:
.quad handler_func()
.size templated_impl()::templ_instance, 8
.type free()::free_instance,@object # @free()::free_instance
.section .free_section,"aw",@progbits
.p2align 3
free()::free_instance: