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

Jakub Jelinek <jakub at gcc dot gnu.org> changed:

           What    |Removed                     |Added
----------------------------------------------------------------------------
                 CC|                            |jakub at gcc dot gnu.org

--- Comment #1 from Jakub Jelinek <jakub at gcc dot gnu.org> ---
I fail to see the usefulness of warn_unused_result attribute on functions that
return such types, what kind of problem is calling those without assigning that
to a var?  There are no data copied...
>From implementation POV, the problem is that the empty structure copies are
discarded during gimplification (in different spots, for C++ they are discarded
through cp-gimplify.c (cp_gimplify_expr) doing:
        else if (simple_empty_class_p (TREE_TYPE (op0), op1))
          {
            /* Remove any copies of empty classes.  Also drop volatile
               variables on the RHS to avoid infinite recursion from
               gimplify_expr trying to load the value.  */
            if (TREE_SIDE_EFFECTS (op1))
              {
                if (TREE_THIS_VOLATILE (op1)
                    && (REFERENCE_CLASS_P (op1) || DECL_P (op1)))
                  op1 = build_fold_addr_expr (op1);

                gimplify_and_add (op1, pre_p);
              }
            gimplify_expr (&TREE_OPERAND (*expr_p, 0), pre_p, post_p,
                           is_gimple_lvalue, fb_lvalue);
            *expr_p = TREE_OPERAND (*expr_p, 0);
          }
while for C, it is done through gimplify.c (gimplify_modify_expr) doing:
  /* For zero sized types only gimplify the left hand side and right hand
     side as statements and throw away the assignment.  Do this after
     gimplify_modify_expr_rhs so we handle TARGET_EXPRs of addressable
     types properly.  */
  if (zero_sized_type (TREE_TYPE (*from_p)) && !want_value)
    {
      gimplify_stmt (from_p, pre_p);
      gimplify_stmt (to_p, pre_p);
      *expr_p = NULL_TREE;
      return GS_ALL_DONE;
    }

and after that there is no way to differentiate if the call had a lhs or not.

Perhaps we could add a langhook and for zero_sized_type or if the langhook is
true (would use simple_empty_class_p for C++, otherwise false) just ignore the
warn_unused_result attribute or something similar; that would mean we wouldn't
warn in should_warn at least for C though (for C++ we would, because we turn it
into a TARGET_EXPR and warn as we voidify the call).

Reply via email to