diff mbox

Support dumping type bindings and 'mutable' qualifier in lambda diagnostics.

Message ID 1377651279-30425-1-git-send-email-adam@jessamine.co.uk
State New
Headers show

Commit Message

Adam Butcher Aug. 28, 2013, 12:54 a.m. UTC
* error.c (dump_function_decl): Use standard diagnostic flow to dump a
	lambda diagnostic, albeit without stating the function name or
	duplicating the parameter spec (which is dumped as part of the type).
	Rather than qualifying the diagnostic with 'const' for plain lambdas,
	qualify with 'mutable' if non-const.
---
Okay to commit?
---
 gcc/cp/error.c | 27 +++++++++++++++------------
 1 file changed, 15 insertions(+), 12 deletions(-)

Comments

Gabriel Dos Reis Aug. 28, 2013, 12:53 p.m. UTC | #1
On Tue, Aug 27, 2013 at 7:54 PM, Adam Butcher <adam@jessamine.co.uk> wrote:
>         * error.c (dump_function_decl): Use standard diagnostic flow to dump a
>         lambda diagnostic, albeit without stating the function name or
>         duplicating the parameter spec (which is dumped as part of the type).
>         Rather than qualifying the diagnostic with 'const' for plain lambdas,
>         qualify with 'mutable' if non-const.
> ---
> Okay to commit?

This looks good to me.  I have one suggestion.  See below.

> ---
>  gcc/cp/error.c | 27 +++++++++++++++------------
>  1 file changed, 15 insertions(+), 12 deletions(-)
>
> diff --git a/gcc/cp/error.c b/gcc/cp/error.c
> index c82a0ce..a8ca269 100644
> --- a/gcc/cp/error.c
> +++ b/gcc/cp/error.c
> @@ -1380,14 +1380,7 @@ dump_function_decl (cxx_pretty_printer *pp, tree t, int flags)
>    int do_outer_scope = ! (flags & TFF_UNQUALIFIED_NAME);
>    tree exceptions;
>    vec<tree, va_gc> *typenames = NULL;
> -
> -  if (DECL_NAME (t) && LAMBDA_FUNCTION_P (t))
> -    {
> -      /* A lambda's signature is essentially its "type", so defer.  */
> -      gcc_assert (LAMBDA_TYPE_P (DECL_CONTEXT (t)));
> -      dump_type (pp, DECL_CONTEXT (t), flags);
> -      return;
> -    }
> +  bool lambda_p = false;
>
>    flags &= ~(TFF_UNQUALIFIED_NAME | TFF_TEMPLATE_NAME);
>    if (TREE_CODE (t) == TEMPLATE_DECL)
> @@ -1449,21 +1442,31 @@ dump_function_decl (cxx_pretty_printer *pp, tree t, int flags)
>    else if (cname)
>      {
>        dump_type (pp, cname, flags);
> -      pp_cxx_colon_colon (pp);
> +      if (LAMBDA_TYPE_P (cname))
> +       lambda_p = true;

Instead of introducing the local variable lambda_p and then
weave your way through the existing maze, do this instead:
    (1)  Introduce a new function, call it dump_lambda_expr
          (or something like that) that does only the formatting
          of a lambda expression, and nothing else.

   (2) when you arrive here where you test LAMBDA_TYPE_P
        then do a
            return dump_lambda_expr (pp, flags);

The result is much simpler and cleaner that way.
Thanks,

> +      else
> +       pp_cxx_colon_colon (pp);
>      }
>    else
>      dump_scope (pp, CP_DECL_CONTEXT (t), flags);
>
> -  dump_function_name (pp, t, flags);
> +  /* A lambda's signature is essentially its "type", which has already been
> +     dumped.  */
> +  if (!lambda_p)
> +    dump_function_name (pp, t, flags);
>
>    if (!(flags & TFF_NO_FUNCTION_ARGUMENTS))
>      {
> -      dump_parameters (pp, parmtypes, flags);
> +      if (!lambda_p)
> +       dump_parameters (pp, parmtypes, flags);
>
>        if (TREE_CODE (fntype) == METHOD_TYPE)
>         {
>           pp->padding = pp_before;
> -         pp_cxx_cv_qualifier_seq (pp, class_of_this_parm (fntype));
> +         if (!lambda_p)
> +           pp_cxx_cv_qualifier_seq (pp, class_of_this_parm (fntype));
> +         else if (!(TYPE_QUALS (class_of_this_parm (fntype)) & TYPE_QUAL_CONST))
> +           pp_c_ws_string (pp, "mutable");
>           dump_ref_qualifier (pp, fntype, flags);
>         }
>
> --
> 1.8.4
>
diff mbox

Patch

diff --git a/gcc/cp/error.c b/gcc/cp/error.c
index c82a0ce..a8ca269 100644
--- a/gcc/cp/error.c
+++ b/gcc/cp/error.c
@@ -1380,14 +1380,7 @@  dump_function_decl (cxx_pretty_printer *pp, tree t, int flags)
   int do_outer_scope = ! (flags & TFF_UNQUALIFIED_NAME);
   tree exceptions;
   vec<tree, va_gc> *typenames = NULL;
-
-  if (DECL_NAME (t) && LAMBDA_FUNCTION_P (t))
-    {
-      /* A lambda's signature is essentially its "type", so defer.  */
-      gcc_assert (LAMBDA_TYPE_P (DECL_CONTEXT (t)));
-      dump_type (pp, DECL_CONTEXT (t), flags);
-      return;
-    }
+  bool lambda_p = false;
 
   flags &= ~(TFF_UNQUALIFIED_NAME | TFF_TEMPLATE_NAME);
   if (TREE_CODE (t) == TEMPLATE_DECL)
@@ -1449,21 +1442,31 @@  dump_function_decl (cxx_pretty_printer *pp, tree t, int flags)
   else if (cname)
     {
       dump_type (pp, cname, flags);
-      pp_cxx_colon_colon (pp);
+      if (LAMBDA_TYPE_P (cname))
+	lambda_p = true;
+      else
+	pp_cxx_colon_colon (pp);
     }
   else
     dump_scope (pp, CP_DECL_CONTEXT (t), flags);
 
-  dump_function_name (pp, t, flags);
+  /* A lambda's signature is essentially its "type", which has already been
+     dumped.  */
+  if (!lambda_p)
+    dump_function_name (pp, t, flags);
 
   if (!(flags & TFF_NO_FUNCTION_ARGUMENTS))
     {
-      dump_parameters (pp, parmtypes, flags);
+      if (!lambda_p)
+	dump_parameters (pp, parmtypes, flags);
 
       if (TREE_CODE (fntype) == METHOD_TYPE)
 	{
 	  pp->padding = pp_before;
-	  pp_cxx_cv_qualifier_seq (pp, class_of_this_parm (fntype));
+	  if (!lambda_p)
+	    pp_cxx_cv_qualifier_seq (pp, class_of_this_parm (fntype));
+	  else if (!(TYPE_QUALS (class_of_this_parm (fntype)) & TYPE_QUAL_CONST))
+	    pp_c_ws_string (pp, "mutable");
 	  dump_ref_qualifier (pp, fntype, flags);
 	}