Why do optimisation flags cause linker errors for some template functions?

情到浓时终转凉″ 提交于 2020-01-24 05:23:08

问题


I have a problem where an app compiles fine in debug mode with all optimization turned off. But the moment I compile for release it prints out unresolved link errors.

The functions in question are the following:

template <typename T>
T & Block::val(size_t offset) 
{
    return *(reinterpret_cast<T*>(_data + offset)); 
}

template <typename T>
const T & Block::val(size_t offset) const 
{ 
    return *(reinterpret_cast<T*>(_data + offset)); 
}

And the errors I'm getting all look like:

undefined reference to `unsigned long long& Block::val<unsigned long long>(unsigned long)'

What might be causing this?


回答1:


You normally wouldn't put template implementations in a .cpp but rather a .h or .inl which is included from a .h, it could be that the debug build of the .o is more liberal with the symbols it exports.

Run nm on the debug and release builds of the .o and diff the symbols.

Templates are unusual in linkers because of the One Definition Rule. When it comes to templates, where the body is in the header, this results in multiple equivalent definitions, one for each translation unit. The linker lets them all be until the last moment, where it selects one arbitrarily and discards the others.

I am guessing here, but I suspect that when you compile without optimisations the body is treated like normal, but when optimisations are on the compiler spends a bit of extra effort determining that this body is not visible in other translation units and declines to export it.

Look up extern templates.




回答2:


Odd, moving them from the source file into the header file and it compiles fine.

This is not odd in the slightest. Function template definitions belong to header files since day one. Do not put them in sources. If you do, the compiler won't see them at instantiation time.



来源:https://stackoverflow.com/questions/6828576/why-do-optimisation-flags-cause-linker-errors-for-some-template-functions

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!