I am analyzing a macOS app with radare2, and the app depends on a number of Qt frameworks. When I printed out the import symbols of the app's main executable, the names of the frameworks' functions have strange characters in them.

For example, if a framework exports a function name: QLocalServer::listen(QStringconst&), it becomes _sym.imp._ZN12QLocalServer6listenERK7QString in the main executable's imports.

Another example: QNetworkProxyFactory::setUseSystemConfiguration(bool) becomes sym.imp._ZN20QNetworkProxyFactory25setUseSystemConfigurationEb

Can anyone explain why there are those characters? I don't see those characters when analyzing the export functions of the frameworks.


These "weird" names are produced by the compiler and are called Name Mangling or Name Decoration. These names are shown by radare2 but are not produced or generated by it.

To quote from MSDN:

Functions, data, and objects in C and C++ programs are represented internally by their decorated names. A decorated name is an encoded string created by the compiler during compilation of an object, data, or function definition. It records calling conventions, types, function parameters and other information together with the name. This name decoration, also known as name mangling, helps the linker find the correct functions and objects when linking an executable.

The Wikipedia article about Name Mangling has some great examples of Name Mangling of C++ produced by GCC. I suggest you read it thoroughly to understand the subject better. It explains how mangled names are produced and describes the structure of it.

radare2, just as many different Disassemblers, knows to demangle the different names. There are several configuration variables that handle Name Mangling:

asm.demangle: Show demangled symbols in disasm
bin.demangle: Import demangled symbols from RBin
bin.demanglecmd: run xcrun swift-demangle and similar if available (SLOW)
bin.lang: Language for bin.demangle

So if you want radare2 to show you the demangled names on the assembly, use e asm.demangle = true. Make sure to tell radare2 to load the demangled symbols. You can do this by setting e bin.demangle to true. You might need to load the binary again - use oo for this.

If you just want to demangle a specific name, you can use iD <lang> <name> which will demangle a symbol name for a specific language. Just use it like this: iD cxx <mangled name> for C++ Name Mangling.

  • The strangest thing is that its entire purpose is exactly the opposite of what OP is (bluntly) assuming: it is because all those "strange" characters that appear in the original declarations ('(, ), :, &, ~) are not allowed in linker symbols. – Jongware Jun 29 '18 at 8:33
  • Thanks Megabeets for a very detailed answer! It worked. I just want to note that Demangling does not work on import symbols (i.e. results of ii command) – Thanh Bui Jun 29 '18 at 16:52

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.