符号可见性和gcc警告

时间:2018-05-31 21:29:08

标签: c++ gcc visibility symbols gcc-warning

这是Symbol visibility and namespace

的后续问题

我稍微修改一下这个例子,因为它并不是关于命名空间的:

namespace MyDSO {
  struct __attribute__ ((visibility ("hidden"))) Foo {
    void bar() {}
  };
}

struct Bar {
  MyDSO::Foo foo;
};

int main() {}

通过gcc example.cpp -o example进行编译会在链接问题中吐出警告‘Bar’ declared with greater visibility than the type of its field ‘Bar::foo’

问题:为什么如果我

我会收到警告

a)明确地向结构栏添加默认可见性,即我有

namespace MyDSO {
  struct __attribute__ ((visibility ("hidden"))) Foo {
    void bar() {}
  };
}

struct __attribute__ ((visibility ("default"))) Bar {
  MyDSO::Foo foo;
};

int main() {}

b)删除隐藏的可见性,向Bar添加默认可见性并使用-fvisibility="hidden"进行编译?

在我看来,最终结果是一样的,事实上,所有二进制文件都是完全相同的(gcc 7.3.1,还有较旧的二进制文件)。如果我将两个结构分成两个类并用它们构建一个静态库,那么符号表(objdump -t -C)包含完全相同的符号和完全相同的修饰符(全局,本地等),只有几个条目第一列(虚拟地址)不同。

1 个答案:

答案 0 :(得分:1)

在这两种情况下,显式可见性属性是在每个类的基础上使警告静音的预期方法。来自gcc/cp/decl2.c

/* Don't warn about visibility if the class has explicit visibility.  */
if (CLASSTYPE_VISIBILITY_SPECIFIED (type))
  vis = VISIBILITY_INTERNAL;