编写库时,最重要的规则和最佳实践之一是将库的所有符号放入特定于库的命名空间.由于namespace关键字,C++使这很容易.在C中,通常的方法是在标识符前面加上一些特定于库的前缀.
C标准的规则放在那些一些限制(安全编译):AC编译器可以看只是一个标识符的前8个字符,所以foobar2k_eggs并foobar2k_spam可能被解释为有效相同标识符-但是每一个现代的编译器允许任意长标识符所以在我们这个时代(21世纪),我们不应该为此烦恼.
但是如果你面对一些你无法改变符号名称/标识符的库呢?也许你只有一个静态二进制文件和标题或者不想要,或者不允许自己调整和重新编译.
我正在尝试在visual studio中创建一个能够访问已存在的.dll文件的应用程序.我需要应用程序来调用例程.我还有一个已经存在的头文件.
我一直在研究互联网,发现我需要创建一个.lib文件.在这里查看类似的问题我找到了一个链接:http://support.microsoft.com/kb/131313 但是我不能按照指示操作.
链接中的信息表示要创建一个DEF文件(我在别处读到这需要编译为具有相同名称的DLL,但不确定该名称是什么,与.dll文件同名?).但我不明白第一个方向,即"使用DUMPBIN/EXPORTS".然后我需要"存根"函数,然后与.OBJ文件有关(我不知道这些文件是什么).
是否有任何分步指导,类似于上面的链接,很容易遵循?
嗨,我正在使用一个全局覆盖新/删除的库.但是这个库有问题,问题是它必须在main函数中手动初始化.
现在我正在尝试使用另一个在调用main之前初始化一些函数的库,不幸的是这个库在这些函数中使用new.所以我得到错误,因为使用重写的new/delete关键字的内存管理器尚未初始化.
我真的很想使用默认的内存管理器,因为我想将单元测试添加到这个库中.使用我想要测试的库所使用的内存也没有多大意义,我的单元测试库也使用了这个内存.
所以我的问题是,当包含第二个库并且只使用默认的new/delete时,是否可以忽略全局覆盖的new/delete?
我在Windows 7上使用visual studio 2010和标准的C++编译器.
我已将以下库包含在我的代码中.
#include <minix/drivers.h>
#include <curl/curl.h>
#include <sys/stat.h>
#include <time.h>
#include <assert.h>
#include <string.h>
Run Code Online (Sandbox Code Playgroud)
现在我收到以下错误:
In file included from /usr/local/include/curl/curlbuild.h:152
from /usr/local/include/curl/curl.h:34
from xxx.c:2
/usr/pkg/gcc44/lib/gcc/i686-pc-minix/4.4.3/include-fixed/sys/socket.h:134: error: conflicting types for '_send'
/usr/include/minix/ipc.h:152: note: previous declaration was here
Run Code Online (Sandbox Code Playgroud)
据我所知,这意味着_send已在两个库(minix/drivers.h和curl/curl.h)中声明,我想知道是否有可能解决这个问题或以某种方式解决它?
背景
我建立一个iOS应用程序(这我就打电话MyApp从这里开始),这将依赖于由几个独立的静态库进行计算(我称之为Lib1,Lib2,Lib3,...).每个库建在它自己的项目,然后导入到一个工作区(这样的工作区将包含MyApp,Lib1,Lib2,...).有关如何设置此处的更多详细信息.这些库由其他独立的产品使用MyApp,因此我希望尽量减少库中的任何更改.这些库也是用(plain)编写的C,因此没有头文件.
某些功能名称由多个存储库中使用(因此两者Lib1和Lib2可能各自具有DoStuff方法).具有相同名称的功能大致做同样的事情,但对于如何是做到这一点,可以是磁带库之间不同的一些具体的,所以在实际的代码DoStuff就Lib1可能比代码完全不同DoStuff的Lib2.编写一个DoStuff在每个库中完全相同的通用将是非常困难的.
问题
当应用程序正在运行时,它没有DoStuff从正确的库中调用正确的.我发现了这一点,因为在调试会话期间调用了错误的函数(由于DoStuff函数的细微差别,最终导致应用程序崩溃).
我在寻找什么
每个库只有一个入口点MyApp,每个入口点都有唯一的名称.如果DoStuff从入口点方法Lib1(或任何其他方法Lib1)调用,那么我希望它调用该DoStuff方法Lib1.实现这一目标的最佳方法是什么?
有没有办法(可能通过XCode中的某个设置)我可以这样做,以便每个库都是它自己的命名空间?这将是我解决问题的首选方法.我想我可以通过并重命名重复的函数,以便它们都是唯一的(因此DoStuff方法Lib1可以重命名为Lib1DoStuff或类似的东西),但有数百个函数可能有重复的名称,我们将是将数百个库添加到项目中,因此必须手动重命名所有函数并修复对它们的所有调用将花费大量时间,而我的老板并不认为这是一个可行的选择.
UPDATE
在查看了Josh Caswell的评论以及他提供的一些链接后,看起来可能会在编译库时自动重命名所有函数,这将是尝试修复THE ISSUE上述内容的最佳方法.从我所看到的,objcopy在评论中的几个链接中提到的内容不支持iOS.我终于碰上了这个博客条目,其中谈到创建自定义生成Xcode的目标规则,这个博客,谈到了自定义生成设置和构建阶段.
我是否正确地假设我可以在构建过程中的某个时刻使用脚本自动附加到我的每个库中的所有函数的名称,而不是像我在上一WHAT …
重复以下问题:C函数冲突
嗨,在我目前的项目中,我必须使用某种接口库.函数名由这个接口给出,这个函数做的是开发人员的选择.据我所知,项目应该使用这个函数,当涉及到编译时,你可以选择lib并使用它来实现功能.我尝试做的是通过包装另一个并在mein函数中调用它来同时使用现有的lib和我的lib:
otherlib:
int function1 (int a) {
// do something
}
Run Code Online (Sandbox Code Playgroud)
MYLIB:
int function1 (int a) {
//my code here
otherlib::function1(a);
}
Run Code Online (Sandbox Code Playgroud)
问题是我没有访问其他lib,而其他lib没有任何名称空间.我已经试过了
namespace old {
#include "otherlib.h"
}
Run Code Online (Sandbox Code Playgroud)
然后在我的函数中通过old :: function1调用旧函数.只要它是唯一的头文件,这就可以工作.lib将它的符号输出回全球空间.还有类似的东西
namespace new {
function1 (int a) {
::function1(a);
}
}
Run Code Online (Sandbox Code Playgroud)
没用.最后但并非最不重要的是我尝试了ifdef和这里建议的定义
但我没有成功.
任何想法如何解决这个问题?提前致谢.
编辑:我既没有访问旧的lib也没有项目的两个库都应该使用.
EDIT2:至少旧的lib是静态的
我在代码块中有一个项目,它使用许多不同的文件 - 通常由其他程序员编写。目前,我有两个不同的子项目,其中包含以相同方式命名的函数。假设:F(int x)。所以 F(int x) 在两个不同位置的两个源文件中定义,它们有两个不同的标题。我还为这些标头创建了两个不同的命名空间:
namespace NS1
{
extern "C"{
#include "header1definingF.h"
}
}
namespace NS2
{
extern "C"{
#include "header2definingF.h"
}
}
Run Code Online (Sandbox Code Playgroud)
但是编译器仍然抱怨它有多个 F(int x) 定义。我如何在 Code::Blocks 中解决这个问题(在 Visual Studio 中它工作得很好)。
编辑:为了更清楚这些头文件包括 C 代码。没想到会这么乱 有数千个源文件使用其他项目,包括数千个函数……那该怎么办。我完全不知道如何使它工作。
有没有一种方法可以将全局函数(例如,不允许修改代码的库中的函数)包含到命名空间的范围内,并且仍然可以使用它?
我有两个功能:
base64_decode()
base64_encode()
Run Code Online (Sandbox Code Playgroud)
在两个文件中:Base64.cpp Base64.h。
(很明显)当包含Base64.h在我的Extensions命名空间中时,函数声明可用,但是链接器找不到定义(在中Base64.cpp),因为它们现在已包含在我的命名空间中。例:
namespace Extensions {
#include "Base64.h"
}
Run Code Online (Sandbox Code Playgroud)
有没有办法有两种执行和命名空间内的两个函数的声明没有修改原始代码,并没有 #include荷兰国际集团Base64.cpp?
我需要更改共享库 (.so) 文件中的某些符号,如下例所示:我需要将abc.so 文件中的符号重命名为 symbol xyz。我有一个工具可以在头文件中替换它,我面临的唯一挑战是更改我的 .so 共享库。对于共享库,是否有任何工具或命令可以帮助我反汇编 .so 文件、更新符号并再次重新组装为 .so 文件?对于共享库,我们需要一种重建符号表的机制。如果有任何工具可以完成我的任务,需要帮助吗?
仅供参考:更改源是最好的方法,但对于短期的解决方案来说,它可以帮助在符号级别替换代码字。