https://gcc.gnu.org/bugzilla/show_bug.cgi?id=70955

--- Comment #12 from Richard Biener <rguenth at gcc dot gnu.org> ---
The patch hints at type merging not being performed properly.  AFAIR I saw
that for some of the eventually late built "global" types in the backend:

/* Calling abi specific va_list type nodes.  */
static GTY(()) tree sysv_va_list_type_node;
static GTY(()) tree ms_va_list_type_node;

those are not streamed by-index and thus while cross-TU merging will produce
exactly _one_ ms_va_list_type_node the one created by the backend for lto1
is _not_ merged with the one coming from the input TUs.

And type "sharing" in the middle-end is broken by the explicit call
to build_variant_type_copy in

/* Setup the builtin va_list data type and for 64-bit the additional
   calling convention specific va_list data types.  */

static tree
ix86_build_builtin_va_list (void)
{
  if (TARGET_64BIT)
    {
      /* Initialize ABI specific va_list builtin types.  */
      tree sysv_va_list, ms_va_list;

      sysv_va_list = ix86_build_builtin_va_list_64 ();
      sysv_va_list_type_node = build_variant_type_copy (sysv_va_list);

      /* For MS_ABI we use plain pointer to argument area.  */
      ms_va_list = build_pointer_type (char_type_node);
      ms_va_list_type_node = build_variant_type_copy (ms_va_list);

      return (ix86_abi == MS_ABI) ? ms_va_list : sysv_va_list;

because just having a char * pointer would otherwise be matching too
many "random" pointers?

Anyway, dispatching based on the type given the above "non-difference"
is not going to work reliably.

LTO type merging will have merged the incoming TUs ms_va_list_type_node
with char_type_node.  I suggest to differentiate the type by
attaching an attribute, say, do the equivalent of

typedef char *ms_va_list_type_node __attribute__((ms_va_list_type));

or similar.

Reply via email to