x

Search in
Sort by:

Question Status:

Search help

  • Simple searches use one or more words. Separate the words with spaces (cat dog) to search cat,dog or both. Separate the words with plus signs (cat +dog) to search for items that may contain cat but must contain dog.
  • You can further refine your search on the search results page, where you can search by keywords, author, topic. These can be combined with each other. Examples
    • cat dog --matches anything with cat,dog or both
    • cat +dog --searches for cat +dog where dog is a mandatory term
    • cat -dog -- searches for cat excluding any result containing dog
    • [cats] —will restrict your search to results with topic named "cats"
    • [cats] [dogs] —will restrict your search to results with both topics, "cats", and "dogs"

Demangled used std::__1::basic_string but I need std::__cxx11::basic_string

Hi all,

I'm trying to use a Shared Library (.so) in a Unreal Project. I already have tried Unreal 4.14.x, 4.15.x. 4.16.x, 4.17.x, 4.18.0 and I always have one problem or another.

At the end, I came back to Unreal 4.14.3 and the problem that I'm having is that Unreal can't find a symbol when I run my external_library::init.

With the name of the symbol raised on the error, I used c++filt SYMBOL_HERE to demangle.

The demangled symbol is:

 external_library::init(int&, char**, std::__1::basic_string<char, std::__1::char_traits<char>, std::__1::allocator<char> > const&, unsigned int)

Using nm and c++filt I was able to demangle all symbols on the external_library, and the demangled version of external_libray::init found on the .so is:

 external_library::init(int&, char**, std::__cxx11::basic_string<char, std::char_traits<char>, std::allocator<char> > const&, unsigned int)

If you use diff (or the graphical version called meld), you can see the Unreal is using std::__1::basic_string but the compiled .so library is using std::__cxx11::basic_string, which means c++11.

In order to try to solve this problem, I have changed LinuxToolChain.cs to pass the parameter -std=c++11 when compiling my Unreal Project, but this didn't solve the problem, because Unreal keeps using std::__1::basic_string instead of std::__cxx11::basic_string.

Then my question is: how can I force unreal use c++11, specially for std::string?

I already have tried everything that I can but I couldn't find a solution.

Product Version: UE 4.14
Tags:
more ▼

asked Oct 30 '17 at 07:44 PM in Linux

avatar image

Ruben Alves
20 5 10 12

(comments are locked)
10|2000 characters needed characters left
Viewable by all users

1 answer: sort voted first

This is because your library is compiled against libstdc++, while Unreal by default uses bundled libc++. Different STL implementations decorate symbols differently to avoid clashes (which would be even worse).

Your options are:

  • compile your library against libc++ (which means using clang with -stdlib=libc++ argument)

  • switch LinuxToolChain.cs to NOT use libc++ (but that may mean rebuilding some other libraries bundled with Unreal).

  • Avoid using STL across module boundaries (have extern "C" interface for your library).

If you're using UE earlier than 4.16, you'll need to remove (in LinuxToolChain.cs) the linker script that hides new/delete signatures or you may run into other obscure problems.

more ▼

answered Oct 30 '17 at 08:01 PM

avatar image

RCL STAFF
2.7k 59 6 88

avatar image Ruben Alves Oct 31 '17 at 11:03 AM

I have modified the LinuxToolChain.cs on Unreal 4.14.3 to disable libc++ (by chaning if (ShouldUseLibcxx(LinkEnvironment.Config.Target)) to if (ShouldUseLibcxx(LinkEnvironment.Config.Target) && false)) and build Unreal from zero two times, and there is a library that still using std::__1::basic_iostream instead of libstdc++.

The library that fails to load is Engine/Binaries/Linux/libUE4Editor-ShaderFormatOpenGL.so because the symbol _ZTINSt3__114basic_iostreamIcNS_11char_traitsIcEEEE is not found.

The symbol demangled is typeinfo for std::__1::basic_iostream<char, std::__1::char_traits<char> >

This libUE4Editor-ShaderFormatOpenGL.so should be compiled with libstdc++ since I have disabled libc++ in LinuxToolChain.cs, right?

What do you think I'm doing wrong now?

Thanks.

avatar image RCL STAFF Oct 31 '17 at 12:11 PM

Nothing wrong, you just need to rebuild the third party libraries bundled with Unreal to use your system's libstdc++. Most third party software provided with the engine is built against libc++ to avoid potential incompatibilities between libstdc++ on different systems (libstdc++ cannot be bundled due to its license).

EDIT: in this case I believe that rebuilding hlslcc should unblock you.

avatar image Ruben Alves Oct 31 '17 at 03:57 PM

If I download the Unreal code, run ./Setup.sh, ./GenerateProjectFiles.sh and make, I building the entire Unreal and the Third Party as well,right? Because this is what I have done, but changing the LinuxToolChain.cs before running ./Setup.sh.

Or the ThirdParty are previously compiled and downloaded when I run ./Setup.sh?

If they are previously built, what are the steps to rebuild them? I only know how to rebuild my own unreal projects or the "entire Unreal" with the steps mentioned above.

avatar image RCL STAFF Oct 31 '17 at 05:39 PM

No, Third Party libraries are supplied as pre-built binaries and aren't rebuilt during the usual build process. The reasons for that is that some of them can take a long to compile (e.g. PhysX), unnecessarily making engine compilation even longer, while others require specialized environment/headers that aren't available on most user systems out of the box (the third reason is that for some libraries - like steam or FBX sdk - there are no sources at all).

There is unfortunately no uniform rebuild process for rebuilding them. Each library in Engine/Source/ThirdParty contains some kind of a readme file or sometimes build scripts that can facilitate rebuilding, but may not work right away on your system.

In your case, you need to go to Engine/Source/ThirdParty/hlslcc/hlslcc/projects/Linux and change the Makefile to not use libc++, then run make and replace the resulting .a file with the locally built one

Arguably a better solution is not to use C++ interface (especially STL classes) when calling a third party DSO from Unreal, which would greatly reduce or likely eliminate binary compatibility issues altogether.

avatar image Ruben Alves Oct 31 '17 at 07:51 PM

What I have done:

  1. Changed the Makefile you mentioned

  2. Compiled that specific ThirdParty

  3. Replaced all libhlslcc.a with the one that was generated locally.

  4. After that I went to the root folder of Unreal, executed ./GenerateProjectFiles.sh and later make.

  5. Then I've removed all temp files of my project (`rm Binaries/ Content/StarterContent/ DerivedDataCache/ Intermediate/AssetRegistryCache/ Intermediate/Build/Linux/ Intermediate/CachedAssetRegistry.bin Intermediate/Config/ Intermediate/ReimportCache/ Saved/ -rf`)

  6. Compiled by project again

  7. Crashed with the same error when trying to open the project.

I think that many of the problems that I'm facing is because I don't understand very well how Unreal itself is structured.

On the documentation I can find instructions for users that want just want to develop games that work in "any" platform, but in my case, I want something else.

I don't need all Unreal capabilities (like compile for Android, Windows, IOS, etc).

I would like to use Unreal only for Linux, the smallest possible version of Unreal, specially to avoid problems because of "incompatibilities".

So my "final" question is: Is there any documentation about how Unreal itself is structured? How could I disable "Build for Android" or how completely disable "Blueprints" and only use C++, for example?

I couldn't find (yet) this information on the documentation.

avatar image RCL STAFF Oct 31 '17 at 08:23 PM

Before running in step 5, you may want to double check that your plugin is compiled against libstdc++ (i.e. all STL symbols in it are mangled appropriately). Turning off libc++ and switching to libstdc++ is not something that we officially support. UBT has code to use libstdc++ to make it easier for advanced folks who want to modify the engine, but we don't test that path, so hlslcc may not be the only thing that needs to be changed.

Even on Linux there's a problem of binary compatibility between different libstdc++ versions (for example between CentOS/RHEL 7 and Ubuntu 17.10), this is why we opted to bundle libc++ instead so the same UE4 binary can run on both.

Re: structuring of the engine modules, I am not sure if this is covered in documentation, which is geared towards gameplay programmers. Some concepts are discussed here: https://docs.unrealengine.com/latest/INT/Programming/UnrealArchitecture/Reference/index.html However, if you want to substantially modify the engine you will probably need to experiment first. You can absolutely use just C++ and not program in Blueprints, but this is a separate question from compiling out Blueprint modules. Reducing the number of modules to minimum takes some experimentation and modifications to the engine due to existing interdependencies.

avatar image Ruben Alves Nov 08 '17 at 10:42 PM

Hi @RCL,

I went through the steps again from the beginning on Unreal4.14.3, removed (in LinuxToolChain.cs) the part the hides the new/delete signatures, compiled HLSLCC with libstdc++ and that libc++/libstdc++ problem when loading`libUE4Editor-ShaderFormatOpenGL.so` was solved.

THANK YOU VERY MUCH FOR THE INSTRUCTIONS!!!

avatar image Ruben Alves Nov 08 '17 at 10:52 PM

@RCL, I have created a new question about Large Memory Pool error on a computer with 60GB because trying to ask as a comment wasn't possible (I don't know why).

Could you have a look at the question? I already tried to solve it looking for similar problems on the Unreal forum but I couldn't make it work.

Thank you very much.

(comments are locked)
10|2000 characters needed characters left
Viewable by all users
Your answer
toggle preview:

Up to 5 attachments (including images) can be used with a maximum of 5.2 MB each and 5.2 MB total.

Follow this question

Once you sign in you will be able to subscribe for any updates here

Answers to this question