简体   繁体   中英

Symbol visibility and gcc warnings

This is kind of a follow-up question to Symbol visibility and namespace

I'll modify the example slightly because it isn't really about namespacing:

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

struct Bar {
  MyDSO::Foo foo;
};

int main() {}

Compiling via gcc example.cpp -o example spits out the warning 'Bar' declared with greater visibility than the type of its field 'Bar::foo' as in the linked question.

Question: Why don't I get the warning if I

a) explicitly add default visibility to the struct Bar, ie I have

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

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

int main() {}

b) delete the hidden visiblity, add default visibility to Bar and compile using -fvisibility="hidden" ?

It seems to me that the end result is the same, and indeed, all binaries are exactly the same (gcc 7.3.1, but also older ones). If I split the two structs into two classes and build a static library with them, the symbol tables (objdump -t -C) contain the exact same symbols with the exact same modifiers (global, local, etc), only a few entries in the first column (virtual adresses) differ.

In both cases, an explicit visibility attribute is the intended way to silence the warning on a per-class basis. From gcc/cp/decl2.c :

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

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM