1

I have an Static C Library ohNetCoreFatEntotem.a and I have imported it into an existing projects originally written in ObjctiveC. Now the project is almost Swift.

When I try to build the project I get the following error:

enter image description here

The Library is a fat Library compiled for arm64, armv7 and x86

What does this error mean?

Thank you

EDITED I might not have enough deep knowledge about compilers and libraries... Sorry for that.

I have build a library from https://github.com/openhome/ohNet and I generated the compressed file like the one you can find Here.

The structure is:

enter image description here

I created a Fat library with all the fileLib.a from different structures that also can be found Here.

I have a created a folder with the fat libraries and the headers. enter image description here

How do I Declare them in xcode?

Reimond Hill
  • 4,278
  • 40
  • 52

3 Answers3

2

From HERE, two of the main topics (likely related to what you are seeing) are shown below in summarized form. Go to the linked page for many more details on the topic. (Embarcadero is Borland specific, but much of the information in this tutorial is generally applicable)

UNDEFINED SYMBOL AT COMPILE TIME
An undefined symbol at compile time indicates that the named identifier was used in the named source file, but had no definition in the source file. This is usually caused by a misspelled identifier name, or missing declaration of the identifier used. (examples follow)

Or

UNDEFINED SYMBOL AT LINK TIME
When linking multi-file projects, the linker must resolve all references to functions and global variables shared between modules. When these references cannot be resolved, the linker generates an "undefined symbol" error message. This means that after searching all of the object files and libraries which are included in the link, the linker was unable to find a declaration for the identifier you were using. This can be caused by... (read more...)

ryyker
  • 22,849
  • 3
  • 43
  • 87
  • Note that the missing symbols are compiler internas. Likely the wrong linker was used. E.g. c++ code can't be simply linked with ld. Instead c++ must be used because it adds needed runtime libs to the linker call. Link Obj-C with the Obj-C compiler. C++ code with the c++ compiler. And so on. – Goswin von Brederlow Jun 21 '18 at 12:40
  • @GoswinvonBrederlow - Assuming you meant _compiler internals_? If so, what do you mean by that term? I believe the missing symbols are the result of the missing implementations in the libraries OP is attempting to use. Either missing altogether, or older versions. In any case, I don't think the undefined symbol would ever be defined _in a compiler_, however it could very well could be defined in an operating system, and exposed as an API for developer use. OP needs to identify which library contains implementation for `__cxa_guard_abort`, and provide it to the linker. – ryyker Jun 21 '18 at 13:02
  • I mean that they are part of the compilers implementation of the languages runtime. In the case of gcc __cxa_guard_abort appears in libstdc++.a, libsupc++.a and libtsan.a. From https://libcxxabi.llvm.org/spec.html: "This function is called if the initialization terminates by throwing an exception." But if you link c++ code without g++ then libstdc++.a isn't passed to the linker. – Goswin von Brederlow Jun 21 '18 at 13:11
  • @GoswinvonBrederlow - I see, and I agree. This is good information, you should offer this in an answer. It is more specific and relevant than what I posted. – ryyker Jun 21 '18 at 13:36
2

Symbols starting with __cxa_ are part of the c++ runtime.

For example libcxxabi.llvm.org/spec.html says about __cxa_guard_abort: "This function is called if the initialization terminates by throwing an exception."

The c++ runtime is automatically linked into your program IF you link it using the c++ compiler. On the other hand if you link the object files using ld directly, cc, obj-c or other languages compilers then the necessary C++ runtime libraries are not added to the linker call.

If you link object files from multiple languages then care must be taken to include all the necessary language runtime supports and that can get complicated. Otherwise always use the compiler used to compile the object files to later link them.

Goswin von Brederlow
  • 11,875
  • 2
  • 24
  • 42
  • Thank you, How can I ad them in xcode? I have defined the header paths and Declared them into the bridging header – Reimond Hill Jun 21 '18 at 14:12
  • You have to tell xcode that you are building a c++ project. – Goswin von Brederlow Jun 21 '18 at 14:16
  • It could be that obj-c uses the same symbols as c++. Then telling xcode that you are building an obj-c project should do. From the error it looks like it's building a C project. – Goswin von Brederlow Jun 21 '18 at 14:20
  • How do I tell xcode is an Objctive-C project? If I include a c++ header file into the bringing header, would I be ok? – Reimond Hill Jun 21 '18 at 14:30
  • @ReimondHill - There is a lot of information out there, just vary your Google search phrases to include new information as you discover it. For example, just by reading the most recent comments here, I found, _[this](https://stackoverflow.com/questions/15973472/how-to-add-static-libraries-inside-a-c-project-with-xcode)_, and _[this](http://www.maximporges.com/2010/02/08/adding-headers-and-external-libraries-to-xcode-projects/)_ (IMO the second being more relevant to your question) by using the search phrase: _using c++ libs and headers with xcode_. I hope this helps. – ryyker Jun 21 '18 at 15:33
  • @ryyker Thank you Very much. I have read And Understood. My Problem Is My project is Swift. I think I figured out the issue. I have created a .hpp and .cpp class and I Import the headers there. And imported the .hpp into my bridging file. The compiling errors are gone now... – Reimond Hill Jun 21 '18 at 19:27
0

I think I have figured out the issue. Note: This solution is for importing a .a Fat, or not Library into a swift project.

From the the last folder structure defined in the question:

  1. Follow the following link:Here
  2. Create a C++ file in xcode and make sure the "Create Header" is Selected
  3. Create Bridging Header and import the .hpp header
  4. In the .hpp file the import the Headers.

As shown in the last picture from the question, The root folder where the .a are defined also have an include folder. The headers declared in the .hpp are these headers. Depending How you solved point 1, the path might vary.

I hope It can be helpful.

Reimond Hill
  • 4,278
  • 40
  • 52