I have a question related to embedding one library in another.
我有一个关于在另一个库中嵌入一个库的问题。
I have a code that is pure C and my users rely on that, they don't want to depend on C++ libraries. However, the need arose to embed a 3rd party library (ICU) into mine. None of the ICU functions would be exported, they would only be used internally in my library. Unfortunately ICU is a C++ library, though it does have a C wrapper. ICU does not use exceptions, but it does use RTTI (abstract base classes).
我有一个纯C的代码,我的用户依赖它,他们不想依赖c++库。然而,需要将第三方图书馆(ICU)嵌入到我的数据库中。没有一个ICU函数会被导出,它们只会在我的库中内部使用。不幸的是,ICU是一个c++库,尽管它有一个C包装器。ICU不使用异常,但它使用RTTI(抽象基类)。
The question is how could I create my static library so that
问题是如何创建静态库
- ICU is embedded in my library (all references to ICU functions are resolved within my library)
- ICU嵌入到我的库中(对ICU函数的所有引用都在我的库中解析)
- all references to libstdc++ are also resolved and the necessary code is embedded into my library
- 所有对libstdc++的引用也被解析,必要的代码被嵌入到我的库中
- if a user does not even have libstdc++ installed on their system things work just fine
- 如果用户没有在系统上安装libstdc++,那么就可以正常工作。
- if a user does happen to use my library within a C++ project then there are no conflicts with whatever libstdc++ (presumably the system libstdc++) he uses.
- 如果用户碰巧在c++项目中使用我的库,那么无论使用什么libstdc++ +(可能是系统libstdc++ +),都不会发生冲突。
Is this possible at all? The targeted platforms are pretty much everything: windows (there my library is dynamic), and all sort of unix versions (linux, solaris, aix, hpux - here my library needs to be static).
这可能吗?目标平台几乎是所有的东西:windows(我的库是动态的)和所有类型的unix版本(linux、solaris、aix、hpux——这里我的库需要是静态的)。
gcc-4.5 and later does have --static-libstdc++, but as far as I understand it is only for creating shared libs or executables, and not static libs.
gcc-4.5和以后的版本确实有——static-libstdc++,但是据我所知,它只用于创建共享的lib或可执行的,而不是静态的libs。
Thanks for any help!
感谢任何帮助!
2 个解决方案
#1
4
The solution to this problem is pretty simple, but may not fall inside the parameters you have set.
这个问题的解决方案非常简单,但可能不属于您设置的参数。
The simple rules are:
一个简单的规则:
- You can dynamically link a C++ library to a C caller, but you have to wrap the library inside an extern C layer. You design the extern C API and implement it using C++ internals, which are forever hidden from view. [You can also use COM or .NET to do this on Windows.]
- 您可以动态地将一个c++库链接到一个C调用者,但是您必须将库封装在一个外部C层中。您设计了extern C API并使用c++内部构件(永远隐藏在视图之外)来实现它。[你也可以在Windows上使用COM或。net来实现这一点。]
- You cannot statically link a C++ library to a C caller. The libraries are different and the calling sequences/linker symbols are different. [You often can't even statically link between different versions of the same compiler, and almost never between different compilers.]
- 您不能静态地将一个c++库链接到一个C调用方。库是不同的,调用序列/链接符号是不同的。[您经常不能在同一个编译器的不同版本之间进行静态链接,而且几乎不可能在不同的编译器之间进行链接。]
In other words, the solution is simple: use dynamic linking. If that's not the right answer, then I don't think there is one.
换句话说,解决方案很简单:使用动态链接。如果这不是正确的答案,那么我认为没有。
Just to make things interesting, you can even implement your own plug-in architecture. That's just another name for dynamic linking, but you get to choose the API.
为了使事情变得有趣,您甚至可以实现自己的插件体系结构。这只是动态链接的另一个名称,但是您可以选择API。
Just to be clear, the only viable portable option I can see is that you link ICU inside its own dynamic library (DLL or SO). Its symbols, C++ libs, RTTI and exceptions all stay inside that. Your static lib links to the ICU dynamic lib by extern C. That's exactly how much of Windows is built: C++ inside DLL, extern C.
要清楚的是,我能看到的唯一可行的可移植的选项是您将ICU链接到它自己的动态库中(DLL或SO)。它的符号,c++ libs, RTTI和exception都在其中。您的静态库通过extern C链接到ICU动态库的链接,这正是构建Windows的程度:c++中的DLL, extern C。
You can debug across the boundary, but you cannot export type information. If you need to do that, you will have to use a different API, such as .NET or COM.
您可以在边界上进行调试,但是不能导出类型信息。如果需要这样做,就必须使用不同的API,如. net或COM。
#2
0
I don't know if this will work, but let me at least suggest that you try it!
我不知道这是否可行,但至少让我建议你试试!
The excellent LLVM project (origin of clang compiler) has many front-ends and back-ends for different languages, such as C++ and C. And according to this S.O. question it should be possible for LLVM to compile C++ into C which in turn can be compiled as normal.
优秀的LLVM项目(clang编译器的起源)对于不同的语言有很多前端和后端,比如c++和C。根据这个S.O.的问题,LLVM应该有可能将c++编译成C语言,而C语言又可以正常编译。
I imagine this route is a bumpy one, but if it works, it might solve your problem without the need to link dynamically. It all depends on if ICU will compile with LLVM C++.
我认为这条路是崎岖不平的,但如果可行的话,它可能会解决你的问题,而不需要动态链接。这完全取决于ICU是否使用LLVM c++编译。
If you do decide to give it a go, please let us know how you fare!
如果你决定试一试,请告诉我们你的情况!
#1
4
The solution to this problem is pretty simple, but may not fall inside the parameters you have set.
这个问题的解决方案非常简单,但可能不属于您设置的参数。
The simple rules are:
一个简单的规则:
- You can dynamically link a C++ library to a C caller, but you have to wrap the library inside an extern C layer. You design the extern C API and implement it using C++ internals, which are forever hidden from view. [You can also use COM or .NET to do this on Windows.]
- 您可以动态地将一个c++库链接到一个C调用者,但是您必须将库封装在一个外部C层中。您设计了extern C API并使用c++内部构件(永远隐藏在视图之外)来实现它。[你也可以在Windows上使用COM或。net来实现这一点。]
- You cannot statically link a C++ library to a C caller. The libraries are different and the calling sequences/linker symbols are different. [You often can't even statically link between different versions of the same compiler, and almost never between different compilers.]
- 您不能静态地将一个c++库链接到一个C调用方。库是不同的,调用序列/链接符号是不同的。[您经常不能在同一个编译器的不同版本之间进行静态链接,而且几乎不可能在不同的编译器之间进行链接。]
In other words, the solution is simple: use dynamic linking. If that's not the right answer, then I don't think there is one.
换句话说,解决方案很简单:使用动态链接。如果这不是正确的答案,那么我认为没有。
Just to make things interesting, you can even implement your own plug-in architecture. That's just another name for dynamic linking, but you get to choose the API.
为了使事情变得有趣,您甚至可以实现自己的插件体系结构。这只是动态链接的另一个名称,但是您可以选择API。
Just to be clear, the only viable portable option I can see is that you link ICU inside its own dynamic library (DLL or SO). Its symbols, C++ libs, RTTI and exceptions all stay inside that. Your static lib links to the ICU dynamic lib by extern C. That's exactly how much of Windows is built: C++ inside DLL, extern C.
要清楚的是,我能看到的唯一可行的可移植的选项是您将ICU链接到它自己的动态库中(DLL或SO)。它的符号,c++ libs, RTTI和exception都在其中。您的静态库通过extern C链接到ICU动态库的链接,这正是构建Windows的程度:c++中的DLL, extern C。
You can debug across the boundary, but you cannot export type information. If you need to do that, you will have to use a different API, such as .NET or COM.
您可以在边界上进行调试,但是不能导出类型信息。如果需要这样做,就必须使用不同的API,如. net或COM。
#2
0
I don't know if this will work, but let me at least suggest that you try it!
我不知道这是否可行,但至少让我建议你试试!
The excellent LLVM project (origin of clang compiler) has many front-ends and back-ends for different languages, such as C++ and C. And according to this S.O. question it should be possible for LLVM to compile C++ into C which in turn can be compiled as normal.
优秀的LLVM项目(clang编译器的起源)对于不同的语言有很多前端和后端,比如c++和C。根据这个S.O.的问题,LLVM应该有可能将c++编译成C语言,而C语言又可以正常编译。
I imagine this route is a bumpy one, but if it works, it might solve your problem without the need to link dynamically. It all depends on if ICU will compile with LLVM C++.
我认为这条路是崎岖不平的,但如果可行的话,它可能会解决你的问题,而不需要动态链接。这完全取决于ICU是否使用LLVM c++编译。
If you do decide to give it a go, please let us know how you fare!
如果你决定试一试,请告诉我们你的情况!