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

--- Comment #26 from acsawdey at gcc dot gnu.org ---
A little bit more info:

It appears the parameter asmhdr in this function is at the center of this:

func (tools gccgoToolchain) gc(b *Builder, a *Action, archive string, importcfg
[]byte, asmhdr bool, gofiles []string) (ofile string, output []byte, err error)
{

vt_add_function_parameter first sees this as (reg/v:DI 194 [ asmhdrD_4038 ])

but then near the top of the function is uses replace_equiv_address_nv to
rewrite it as:

(mem/c:QI (plus:DI (plus:DI (reg/f:DI 187)
            (const_int 32 [0x20]))
        (const_int 72 [0x48])) [8 asmhdrD_4038+0 S1 A64])

Then this piece of code in the same function gets ahold of it:

      lowpart = var_lowpart (mode, incoming);
      if (!lowpart)
        return;

      val = cselib_lookup_from_insn (lowpart, mode, true,
                                     VOIDmode, get_insns ());

      /* ??? Float-typed values in memory are not handled by
         cselib.  */
      if (val)
        {
          preserve_value (val);
          set_variable_part (out, val->val_rtx, dv, const_offset,
                             VAR_INIT_STATUS_INITIALIZED, NULL, INSERT);
          dv = dv_from_value (val->val_rtx);
        }

      if (MEM_P (incoming))
        {
          val = cselib_lookup_from_insn (XEXP (incoming, 0), mode, true,
                                         VOIDmode, get_insns ());
          if (val)
            {
              preserve_value (val);
              incoming = replace_equiv_address_nv (incoming, val->val_rtx);
            }
        }

This preserves the whole thing at the first preserve call:

(mem/c:QI (plus:DI (plus:DI (reg/f:DI 187)
                (const_int 32 [0x20]))
            (const_int 72 [0x48])) [8 asmhdrD_4038+0 S1 A64])

and this piece at the second call inside the MEM_P condition:

(plus:DI (plus:DI (reg/f:DI 187)
            (const_int 32 [0x20]))
        (const_int 72 [0x48]))

The expression that later causes the problem is the (reg/f:DI 187) in the
center of that which is not preserved.

Later when cselib_expand_value expands asmhdr, vt_expand_var_loc_chain gets
called on all 3 pieces of this and throws the assert on the innermost one
(reg/f:DI 187) when it sees it is not marked preserve.

Reply via email to