On Wed, Dec 02, 2020 at 01:13:26PM +0100, Jakub Jelinek via Gcc-patches wrote:
> On Tue, Dec 01, 2020 at 04:05:22PM -0500, Jason Merrill via Gcc-patches wrote:
> > Or simpler might be to always defer immediate evaluation of
> > source_location::current() until genericize time.
> 
> That works.
> I had to change constexpr.c too so that it temporarily adjusts
> current_function_decl from the constexpr evaluation context, but we do the
> same already from __builtin_FUNCTION ().
> 
> Tested on x86_64-linux and i686-linux, ok for trunk if it passes full
> bootstrap/regtest?

I have a few comments, but only minor things; please feel free to ignore
them.

> --- gcc/cp/tree.c.jj  2020-12-01 16:13:01.717818429 +0100
> +++ gcc/cp/tree.c     2020-12-02 11:53:19.032696933 +0100
> @@ -2968,6 +2968,37 @@ array_type_nelts_total (tree type)
>    return sz;
>  }
>  
> +/* Return true if FNDECL is std::source_location::current () method.  */
> +
> +bool
> +source_location_current_p (tree fndecl)
> +{
> +  gcc_checking_assert (TREE_CODE (fndecl) == FUNCTION_DECL
> +                    && DECL_IMMEDIATE_FUNCTION_P (fndecl));
> +  if (DECL_NAME (fndecl) == NULL_TREE
> +      || TREE_CODE (TREE_TYPE (fndecl)) != FUNCTION_TYPE
> +      || TREE_CODE (TREE_TYPE (TREE_TYPE (fndecl))) != RECORD_TYPE
> +      || DECL_CONTEXT (fndecl) != TREE_TYPE (TREE_TYPE (fndecl)))
> +    return false;
> +
> +  if (strcmp (IDENTIFIER_POINTER (DECL_NAME (fndecl)), "current") != 0)
> +    return false;

You could use id_equal.

> +  tree source_location = DECL_CONTEXT (fndecl);
> +  if (TYPE_NAME (source_location) == NULL_TREE
> +      || TREE_CODE (TYPE_NAME (source_location)) != TYPE_DECL
> +      || DECL_NAME (TYPE_NAME (source_location)) == NULL_TREE
> +      || strcmp (IDENTIFIER_POINTER (DECL_NAME (TYPE_NAME 
> (source_location))),
> +              "source_location") != 0)
> +    return false;

And here too.

> +  tree decl
> +    = lookup_qualified_name (std_node,
> +                          DECL_NAME (TYPE_NAME (source_location)),
> +                          LOOK_want::TYPE, tf_none);
> +  return TYPE_NAME (source_location) == decl;

Can this be decl_in_std_namespace_p?

> --- gcc/cp/constexpr.c.jj     2020-11-26 16:22:24.250407040 +0100
> +++ gcc/cp/constexpr.c        2020-12-02 12:35:11.458852298 +0100
> @@ -1332,7 +1332,14 @@ cxx_eval_builtin_function_call (const co
>      }
>  
>    if (fndecl_built_in_p (fun, CP_BUILT_IN_SOURCE_LOCATION, 
> BUILT_IN_FRONTEND))
> -    return fold_builtin_source_location (EXPR_LOCATION (t));
> +    {
> +      tree save_cur_fn = current_function_decl;

You could use 

temp_override<tree> ovr (current_function_decl);

to avoid having to restore c_f_d manually.

> +      if (ctx->call && ctx->call->fundef)
> +     current_function_decl = ctx->call->fundef->decl;
> +      t = fold_builtin_source_location (EXPR_LOCATION (t));
> +      current_function_decl = save_cur_fn;
> +      return t;
> +    }
>  
>    int strops = 0;
>    int strret = 0;
> --- gcc/cp/cp-gimplify.c.jj   2020-11-26 16:22:24.250407040 +0100
> +++ gcc/cp/cp-gimplify.c      2020-12-02 12:26:21.596922205 +0100
> @@ -1374,6 +1374,15 @@ cp_genericize_r (tree *stmt_p, int *walk
>         break;
>       }
>  
> +      if (call_expr_nargs (stmt) == 0)
> +     if (tree fndecl = cp_get_callee_fndecl (stmt))
> +       if (DECL_IMMEDIATE_FUNCTION_P (fndecl)
> +           && source_location_current_p (fndecl))
> +         {
> +           *stmt_p = cxx_constant_value (stmt, NULL_TREE);

You can drop the ", NULL_TREE".

Thanks,
Marek

Reply via email to