> On 05/10/2015 12:33 PM, Jan Hubicka wrote: > >This is properly honored by C++ FE but other FEs are bit random, which in > >turn > >confuses type_in_anonymous_namespace_p predicate that leads to flase > >poistives > >on type mismatch warnings. I used to be able to get around by checking only > >C++ types at LTO time, but with type checking in lto-symtab I can not, > >because > >I do want to compare type compatibility cross translation units and cross > >languages > >and we have no reliable way to say what type originated as C++ and what did > >not. > > I think we should, as only C++ declarations are subject to the ODR. > C has different (structural) compatibility rules, and I think they > should apply when comparing C and C++ types. > > Since C struct names have no linkage, I don't think it's right to > set TREE_PUBLIC on them.
Yes, I need safe way to tell what type is subject to ODR and what is not. I am not quite sure what is the best approach here. This is what the code is doing currently: To detect ODR types at LTO time I use combination of presence of mangled name and type_in_anonymous_namespace_p check. (The idea is that we do not really need to mangle anonymous type as we do not need to deal with cross-module merging.): odr_type_p (const_tree t) { if (type_in_anonymous_namespace_p (t)) return true; /* We do not have this information when not in LTO, but we do not need to care, since it is used only for type merging. */ gcc_assert (in_lto_p || flag_lto); return (TYPE_NAME (t) && (DECL_ASSEMBLER_NAME_SET_P (TYPE_NAME (t)))); } bool type_in_anonymous_namespace_p (const_tree t) { /* TREE_PUBLIC of TYPE_STUB_DECL may not be properly set for bulitin types; those have CONTEXT NULL. */ if (!TYPE_CONTEXT (t)) return false; return (TYPE_STUB_DECL (t) && !TREE_PUBLIC (TYPE_STUB_DECL (t))); } the catch is that type_in_anonymous_namespace_p returns true for some C types. The TYPE_CONTEXT test is already hack as I run into cases of pre-streamed LTO types to get injected into C++ classes (i.e. if you refere to int, LTO streaming will replace C++ int with TREE_PUBLIC (TYPE_STUB_DECL (t)) by its own int that is !TREE_PUBLIC (TYPE_STUB_DECL (t)). The hack to avoid builtin types made type_in_anonymous_namespace_p to work well in cases I needed for class types. (I believe it is because C builds record with TREE_PUBLIC (TYPE_STUB_DECL (t))=1 but it is a while I checked this) We could certainly just add a flag TYPE_ODR_P that says "this type is controlled by odr rule". I considered that but it is generally not so nice to introduce new flags and it seemed to me that because C standard allows to match all types cross-module on structural basis, it makes sense to consider them all as having public linkage because they are "accessible from outside this translation unit." as tree.h defines the flag. I would be happy with TYPE_ODR_P or any other solution that looks better. Honza > > Jason