Undefined Symbols in Crypto++/iOS 64-Bit Project

Undefined symbols in Crypto++/iOS 64-bit project

Undefined symbols for architecture arm64: "CryptoPP::BufferedTransformation::ChannelFlush(std::string const&, bool, int, bool)", referenced from:

vtable for CryptoPP::SimpleProxyFilter in MYCLASSBBB.o
vtable for CryptoPP::Bufferless<CryptoPP::Filter> in MYCLASSBBB.o

I think you are not using libc++, which is LLVM's C++ standard library. I think that because I don't see a -stdlib=libc++ (but I don't recall if that's passed to ld directly).

The symbol is defined in the github's prebuilt cryptopp (that's my github, btw). Here's how to verify.

First, extract the arm64 library from the fat library:

$ xcrun -sdk iphoneos lipo libcryptopp.a -thin arm64 -output libcryptopp-arm64.a
$ ls
libcryptopp-arm64.a libcryptopp.a

Next, use nm to dump global symbols, and use c++filt to demangle:

$ nm -g libcryptopp-arm64.a | c++filt | grep BufferedTransformation::ChannelFlush | grep " T "
0000000000002110 T CryptoPP::BufferedTransformation::ChannelFlush(std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, bool, int, bool)

The capitol T means you are searching for symbols that are defined and exported. Lower t means its defined but not exported - i.e., private. Capitol U means its undefined.

The __1 is what libc++ (LLVM) uses to differentiate from libstdc++ (GNU). std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > is a string, so that could be rewritten as:

CryptoPP::BufferedTransformation::ChannelFlush(std::__1::string const&, bool, int, bool)

If this library was built against libstdc++ (GNU), then the symbol from the library would be:

CryptoPP::BufferedTransformation::ChannelFlush(std:::string const&, bool, int, bool)

We can repeat for the second problem child, and it follows the same pattern (libc++, and not libstdc++):

$ nm -g libcryptopp-arm64.a | c++filt | grep CryptoPP::Filter::CopyRangeTo2 | grep " T "
00000000000001c4 T CryptoPP::Filter::CopyRangeTo2(CryptoPP::BufferedTransformation&, unsigned long long&, unsigned long long, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, bool) const

This can be rewritten as:

CryptoPP::Filter::CopyRangeTo2(CryptoPP::BufferedTransformation&, unsigned long long&, unsigned long long, std::__1::string const&, bool) const

-----

IF you need GNU's libstdc++, then you can build it yourself. Here are the steps:

  1. Download and unpack Crypto++ from the website
  2. Download and unpack cryptopp-mobile.zip. Unpack it right over top the Crypto++ source files
  3. Open the new GNUmakefile, find the iOS rule by searching for the block that begins with IS_IOS
  4. Change this line in the IS_IOS block: CXXFLAGS += -stdlib=libc++. Change it to CXXFLAGS += -stdlib=libstdc++
  5. Do the cross compile...

-----

I downloaded Cocos2D-x and tried to look at its configuration (I'm not a Cmake guy, so I could be wrong with what follows). It has the following in CmakeList.txt:

if(MSVC)
ADD_DEFINITIONS(-D_CRT_SECURE_NO_WARNINGS -D_SCL_SECURE_NO_WARNINGS
-wd4251 -wd4244 -wd4334 -wd4005 -wd4820 -wd4710
-wd4514 -wd4056 -wd4996 -wd4099)
else()
set(CMAKE_C_FLAGS_DEBUG "-g -Wall -DCOCOS2D_DEBUG=1")
set(CMAKE_CXX_FLAGS_DEBUG ${CMAKE_C_FLAGS_DEBUG})
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -fno-exceptions -std=c99")
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -fno-exceptions -std=c++11 -Wno-deprecated-declarations -Wno-reorder")
if(CLANG)
set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -stdlib=libc++")
endif()
endif(MSVC)

If Cmake is doing what I suspect, then its using LLVM's libc++. But its also using -std=c++11, and the GitHub project is not using it. But I'm not sure -std=c++11 makes a difference here.

Just bike shedding, but this is a bad sign: _SCL_SECURE_NO_WARNINGS. If they are blatantly doing that, then they probably have various degrees of of badness and brokenness. (Just my experience with auditing software).


If interested, the __1 is an inline namespace used for versioning. See What are inline namespaces for? and Where does the __1 symbol come from when using LLVM's libc++?.

Undefined symbols for architecture arm64

If your Architectures and Valid Architectures are all right, you may check whether you have added $(inherited) , which will add linker flags generated in pods, to Other Linker Flags as below:
Sample Image

Undefined symbols for architecture x86_64 when building for ARM64

I solved this--- in short, it have to build with -stdlib=libstdc++ flag(to CXXFLAGS in GNUMAKEFILE) when building libcryptopp.

because my project is legacy cocos2d-x project, that's standard library is setted to libstdc++.

more infomation is here. jeffrey answered me about this in great detail.

Xcode build failure Undefined symbols for architecture x86_64

It looks like you are missing including the IOBluetooth.framework in your project. You can add it by:

  • Clicking on your project in the upper left of the left pane (the blue icon).

  • In the middle pane, click on the Build Phases tab.

  • Under "Link Binary With Libraries", click on the plus button.

  • Find the IOBluetooth.framework from the list and hit Add.

Sample Image

Sample Image

This will make sure that the IOBluetooth.framework definitions are found by the linker. You can see that the framework is a member of your target by clicking on the framework in the left pane and seeing the framework's target membership in the right pane (note I've moved the framework under the Frameworks group for organization purposes):

Sample Image

OpenTok (iOS) v2.4.0 (64-bit) -- Undefined symbols for architecture armv7

Okay, I got this resolved thanks to a prompt response from OpenTok support team! I'd posted the same question on their support forum as well. (https://forums.tokbox.com/post55977)

Here's the solution that worked for me (verbatim from the above link)

What are your Build settings? armv7 is supported.

also make sure that you have added the new lib/frameworks as follows:

- Add VideoToolbox.framework.
- Remove libstdc++ and add libc++
- add GLKit.framework (if not there previously)

A couple of the above mentioned files were missing from my frameworks list. I'm attaching a screenshot of the complete list, just in case someone else comes across the same issue.

I wasted close to 6 hours on this!! :(

Sample Image



Related Topics



Leave a reply



Submit