The first header file defines a function called ret with external linkage in every translation unit that includes it. This is incorrect if more than one such TU is linked in the same program.
The second header file defines a function called ret with internal linkage in every translation unit that includes it. This means that each TU has its own private copy of the function (with a different address) no matter how many are linked together.
There are three correct ways to share code using a header file:
- function with internal linkage (as in your second header, or in C++11 by putting it in a nameless namespace).
- inline function with external linkage (replace staticwithinline). The meaning ofinlineis that although there is only one copy of the function in the program, every TU that uses the function contains its definition.
- declare the function in the header, and define in it exactly one .cpp file (for example ret.cpp).
In C++03 there was a fourth way:
- function with external linkage in a nameless namespace
I believe this is still available in C++11, but in C++11 functions in nameless namespaces have internal linkage by default. I'm not aware of any use in C++11 for making a function in a nameless namespace have external linkage. So as far as functions are concerned, nameless namespaces are a nice way of giving the function internal linkage.
Which one you use depends on your needs. The third option means that you can change the definition of the function without re-compiling the calling code, although you'd still need to re-link the executable unless the function is in a dll.
The first two (static or inline) differ in their behaviour if:
- the function contains staticlocal variables,
- you compare function pointers to rettaken in different TUs,
- you examine your executable size or symbol table,
- the definition of the function is different in different TUs (perhaps due to different #defines), which is forbidden if the function has external linkage but not if internal.
Otherwise they're much the same.
According to the standard, inline is also a hint that the compiler should optimize calls to that function for fast execution (which in practice means, inline the code at the call site). Most compilers ignore this hint most of the time. They will happily inline a static but non-inline function if they assess it to be a good candidate for inlining, and they will happily avoid inlining an inline function if they assess it to be a bad candidate for inlining.