如何隐藏一个全局变量,它在多个文件中是可见的? [英] How to hide a global variable, which is visible across multiple files?
问题描述
我写一个C(共享)库。它开始了作为一个单一的翻译单元中,我可以定义一对静态
全局变量,必须从外部模块隐藏。
I am writing a C (shared) library. It started out as a single translation unit, in which I could define a couple of static
global variables, to be hidden from external modules.
现在该库已经成长,我想模块分解成几个较小的源文件。问题是,现在我有提到全局两种选择:
Now that the library has grown, I want to break the module into a couple of smaller source files. The problem is that now I have two options for the mentioned globals:
-
在每个源文件有私人副本,并通过功能莫名其妙地同步它们的值调用 - 这会非常难看非常快
Have private copies at each source file and somehow sync their values via function calls - this will get very ugly very fast.
删除静态
定义,所以变量使用的extern
所有翻译单元共享 - 但现在,针对库链接的应用程序code可以访问这些全局变量,如果需要作出声明那里。
Remove the static
definition, so the variables are shared across all translation units using extern
- but now application code that is linked against the library can access these globals, if the required declaration is made there.
那么,有没有制作多个共用私人全局变量一种巧妙的方法,具体的翻译单位的?
So, is there a neat way for making private global variable shared across multiple, specific translation units?
推荐答案
您想要的 visibility属性扩展GCC的。
You want the visibility attribute extension of GCC.
在实践中,是这样的:
#define MODULE_VISIBILITY __attribute__ ((visibility ("hidden")))
#define PUBLIC_VISIBILITY __attribute__ ((visibility ("default")))
(你可能想 #IFDEF
上面的宏,使用一些技巧配置点菜的autoconf
和其他的自动工具的;在其他系统上,你只会有一个像空的定义的#define PUBLIC_VISIBILITY / * *空/
等)
(You probably want to #ifdef
the above macros, using some configuration tricks à la autoconf
and other autotools; on other systems you would just have empty definitions like #define PUBLIC_VISIBILITY /*empty*/
etc...)
然后,声明一个变量:
int module_var MODULE_VISIBILITY;
或函数
void module_function (int) MODULE_VISIBILITY;
然后你可以使用 module_var
或致电 module_function
共享库里面,而不是外面。
Then you can use module_var
or call module_function
inside your shared library, but not outside.
又见 -fvisibility $ C GCC的$ C生成选项。
See also the -fvisibility code generation option of GCC.
顺便说一句,你也可以用 -Dsomeglobal = alongname3419a6
编译你的整个库,并使用 someglobal
照常使用;要真正找到你的用户需要在同一preprocessor定义传递给编译器,可以使名称 alongname3419a6
随机足够不可能使冲突不可能
BTW, you could also compile your whole library with -Dsomeglobal=alongname3419a6
and use someglobal
as usual; to really find it your user would need to pass the same preprocessor definition to the compiler, and you can make the name alongname3419a6
random and improbable enough to make the collision improbable.
PS。这能见度具体到GCC (也许以ELF共享库如在Linux上)。它不会没有GCC或共享库之外的工作....所以相当Linux特有的(即使有少数其他的系统,或许用的Solaris GCC,有它)。可能是一些其他的编译器(铛
通过 LLVM )也可能支持的在Linux 的对的共享库的(而不是静态的)。其实,真正的隐藏(单个共享库的几个编译单元),由连接器主要是做(因为的 ELF 共享库允许的)。
PS. This visibility is specific to GCC (and probably to ELF shared libraries such as those on Linux). It won't work without GCC or outside of shared libraries.... so is quite Linux specific (even if some few other systems, perhaps Solaris with GCC, have it). Probably some other compilers (clang
from LLVM) might support also that on Linux for shared libraries (not static ones). Actually, the real hiding (to the several compilation units of a single shared library) is done mostly by the linker (because the ELF shared libraries permit that).
这篇关于如何隐藏一个全局变量,它在多个文件中是可见的?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!