Question

I have a manipulator defined:

inline std::ostream& my_manip(std::ostream& os);

Which I am using like so:

std::cout << my_manip << ...;

All of this compiles just fine using Boost.bjam in both debug and release mode. However, when it comes time to link I get the following error in release mode only:

Undefined symbols for architecture x86_64:
  "std::__1::basic_ostream<char, std::__1::char_traits<char> >::operator<<(std::__1::basic_ostream<char, std::__1::char_traits<char> >& (*)(std::__1::basic_ostream<char, std::__1::char_traits<char> >&))", referenced from:
      my_routine in main.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

Or, more legibly:

Undefined symbols for architecture x86_64:
  "std::ostream::operator<<(std::ostream& (*)(std::ostream&))", referenced from:
      my_routine in main.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)

If I comment out the manipulator, everything compiles and links just fine in both debug and release modes.

If I leave in the manipulator I can work around the linker error by rebuilding the project with -O0, however I would prefer it if my release mode were the bjam default (-O3).

I am running Xcode 4.6.2 and its associated clang:

Apple LLVM version 4.2 (clang-425.0.28) (based on LLVM 3.2svn)
Target: x86_64-apple-darwin12.5.0
Thread model: posix

How do I get this manipulator to link properly with optimizations on?

Was it helpful?

Solution

Drop the inline. I suspect you have the manipulator declared in some header and only defined in one translation unit? With inline you are changing the symbol's visibility and that probably means the compiler generated the function but it is not exporting the symbol so that the other translation units can see it, i.e., the linker doesn't find it.

Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top