From patchwork Mon Oct 20 14:29:43 2014 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: Bernd Schmidt X-Patchwork-Id: 401161 Return-Path: X-Original-To: incoming@patchwork.ozlabs.org Delivered-To: patchwork-incoming@bilbo.ozlabs.org Received: from sourceware.org (server1.sourceware.org [209.132.180.131]) (using TLSv1.2 with cipher ECDHE-RSA-AES256-GCM-SHA384 (256/256 bits)) (No client certificate requested) by ozlabs.org (Postfix) with ESMTPS id B33E7140081 for ; Tue, 21 Oct 2014 01:31:18 +1100 (AEDT) DomainKey-Signature: a=rsa-sha1; c=nofws; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :message-id:date:from:mime-version:to:subject:references :in-reply-to:content-type; q=dns; s=default; b=eiaFLzChecQpEwcRL iEmKgVZVFBgAbpp1vWgBpZQTN7wtRcq0bBZGySq74VjpnaD0dsjJrd+SZ6Yfnyy3 3XIM8WJJaaeQjodUCIUEb4tP49l21K6bAXqSSMpSEuyl/ju/lAd2LFCF+KZBXlcw 2BiBZ9bJrIGltKCm5uJrheR5JE= DKIM-Signature: v=1; a=rsa-sha1; c=relaxed; d=gcc.gnu.org; h=list-id :list-unsubscribe:list-archive:list-post:list-help:sender :message-id:date:from:mime-version:to:subject:references :in-reply-to:content-type; s=default; bh=NdO62nB6LSoZ+6U8swAsMq6 1ChY=; b=Bl/LiYtvJrUMvqf9P0U8JImoSfBsuqcdAT9kjv9nWXSb0uUuflz+3yA XaQDVAFqNaOBoa1dH3mYsVmMJgTCKaUYCFvYbOFMbxVtVztaGiPd88FESIA7+S89 0QTA7k/NEAq/iK1q7e8g0wF6pilEYib910vqHPIlZUMYf4D6Vm50= Received: (qmail 4179 invoked by alias); 20 Oct 2014 14:31:10 -0000 Mailing-List: contact gcc-patches-help@gcc.gnu.org; run by ezmlm Precedence: bulk List-Id: List-Unsubscribe: List-Archive: List-Post: List-Help: Sender: gcc-patches-owner@gcc.gnu.org Delivered-To: mailing list gcc-patches@gcc.gnu.org Received: (qmail 4170 invoked by uid 89); 20 Oct 2014 14:31:09 -0000 Authentication-Results: sourceware.org; auth=none X-Virus-Found: No X-Spam-SWARE-Status: No, score=-1.8 required=5.0 tests=AWL, BAYES_00, RCVD_IN_DNSWL_NONE autolearn=ham version=3.3.2 X-HELO: relay1.mentorg.com Received: from relay1.mentorg.com (HELO relay1.mentorg.com) (192.94.38.131) by sourceware.org (qpsmtpd/0.93/v0.84-503-g423c35a) with ESMTP; Mon, 20 Oct 2014 14:31:03 +0000 Received: from nat-ies.mentorg.com ([192.94.31.2] helo=SVR-IES-FEM-01.mgc.mentorg.com) by relay1.mentorg.com with esmtp id 1XgDz8-0004rj-Kz from Bernd_Schmidt@mentor.com for gcc-patches@gcc.gnu.org; Mon, 20 Oct 2014 07:30:59 -0700 Received: from [127.0.0.1] (137.202.0.76) by SVR-IES-FEM-01.mgc.mentorg.com (137.202.0.104) with Microsoft SMTP Server id 14.3.181.6; Mon, 20 Oct 2014 15:30:57 +0100 Message-ID: <54451C57.5020705@codesourcery.com> Date: Mon, 20 Oct 2014 16:29:43 +0200 From: Bernd Schmidt User-Agent: Mozilla/5.0 (X11; Linux x86_64; rv:24.0) Gecko/20100101 Thunderbird/24.8.0 MIME-Version: 1.0 To: GCC Patches Subject: The nvptx port [7/11+] Inform the port about call arguments References: <54451994.9070209@codesourcery.com> In-Reply-To: <54451994.9070209@codesourcery.com> In ptx assembly we need to decorate call insns with the arguments that are being passed. We also need to know the exact function type. This is kind of hard to do with the existing infrastructure since things like function_arg are called at other times rather than just when emitting a call, so this patch adds two more hooks, one called just before argument registers are loaded (once for each arg), and the other just after the call is complete. Bernd gcc/ * target.def (call_args, end_call_args): New hooks. * hooks.c (hook_void_rtx_tree): New empty function. * hooks.h (hook_void_rtx_tree): Declare. * doc/tm.texi.in (TARGET_CALL_ARGS, TARGET_END_CALL_ARGS): Add. * doc/tm.texi: Regenerate. * calls.c (expand_call): Slightly rearrange the code. Use the two new hooks. (expand_library_call_value_1): Use the two new hooks. ------------------------------------------------------------------------ Index: gcc/doc/tm.texi =================================================================== --- gcc/doc/tm.texi.orig +++ gcc/doc/tm.texi @@ -5027,6 +5027,29 @@ except the last are treated as named. You need not define this hook if it always returns @code{false}. @end deftypefn +@deftypefn {Target Hook} void TARGET_CALL_ARGS (rtx, @var{tree}) +While generating RTL for a function call, this target hook is invoked once +for each argument passed to the function, either a register returned by +@code{TARGET_FUNCTION_ARG} or a memory location. It is called just +before the point where argument registers are stored. The type of the +function to be called is also passed as the second argument; it is +@code{NULL_TREE} for libcalls. The @code{TARGET_END_CALL_ARGS} hook is +invoked just after the code to copy the return reg has been emitted. +This functionality can be used to perform special setup of call argument +registers if a target needs it. +For functions without arguments, the hook is called once with @code{pc_rtx} +passed instead of an argument register. +Most ports do not need to implement anything for this hook. +@end deftypefn + +@deftypefn {Target Hook} void TARGET_END_CALL_ARGS (void) +This target hook is invoked while generating RTL for a function call, +just after the point where the return reg is copied into a pseudo. It +signals that all the call argument and return registers for the just +emitted call are now no longer in use. +Most ports do not need to implement anything for this hook. +@end deftypefn + @deftypefn {Target Hook} bool TARGET_PRETEND_OUTGOING_VARARGS_NAMED (cumulative_args_t @var{ca}) If you need to conditionally change ABIs so that one works with @code{TARGET_SETUP_INCOMING_VARARGS}, but the other works like neither Index: gcc/doc/tm.texi.in =================================================================== --- gcc/doc/tm.texi.in.orig +++ gcc/doc/tm.texi.in @@ -3929,6 +3929,10 @@ These machine description macros help im @hook TARGET_STRICT_ARGUMENT_NAMING +@hook TARGET_CALL_ARGS + +@hook TARGET_END_CALL_ARGS + @hook TARGET_PRETEND_OUTGOING_VARARGS_NAMED @node Trampolines Index: gcc/hooks.c =================================================================== --- gcc/hooks.c.orig +++ gcc/hooks.c @@ -245,6 +245,11 @@ hook_void_tree (tree a ATTRIBUTE_UNUSED) } void +hook_void_rtx_tree (rtx, tree) +{ +} + +void hook_void_constcharptr (const char *a ATTRIBUTE_UNUSED) { } Index: gcc/hooks.h =================================================================== --- gcc/hooks.h.orig +++ gcc/hooks.h @@ -70,6 +70,7 @@ extern void hook_void_constcharptr (cons extern void hook_void_rtx_int (rtx, int); extern void hook_void_FILEptr_constcharptr (FILE *, const char *); extern bool hook_bool_FILEptr_rtx_false (FILE *, rtx); +extern void hook_void_rtx_tree (rtx, tree); extern void hook_void_tree (tree); extern void hook_void_tree_treeptr (tree, tree *); extern void hook_void_int_int (int, int); Index: gcc/target.def =================================================================== --- gcc/target.def.orig +++ gcc/target.def @@ -3825,6 +3825,33 @@ not generate any instructions in this ca default_setup_incoming_varargs) DEFHOOK +(call_args, + "While generating RTL for a function call, this target hook is invoked once\n\ +for each argument passed to the function, either a register returned by\n\ +@code{TARGET_FUNCTION_ARG} or a memory location. It is called just\n\ +before the point where argument registers are stored. The type of the\n\ +function to be called is also passed as the second argument; it is\n\ +@code{NULL_TREE} for libcalls. The @code{TARGET_END_CALL_ARGS} hook is\n\ +invoked just after the code to copy the return reg has been emitted.\n\ +This functionality can be used to perform special setup of call argument\n\ +registers if a target needs it.\n\ +For functions without arguments, the hook is called once with @code{pc_rtx}\n\ +passed instead of an argument register.\n\ +Most ports do not need to implement anything for this hook.", + void, (rtx, tree), + hook_void_rtx_tree) + +DEFHOOK +(end_call_args, + "This target hook is invoked while generating RTL for a function call,\n\ +just after the point where the return reg is copied into a pseudo. It\n\ +signals that all the call argument and return registers for the just\n\ +emitted call are now no longer in use.\n\ +Most ports do not need to implement anything for this hook.", + void, (void), + hook_void_void) + +DEFHOOK (strict_argument_naming, "Define this hook to return @code{true} if the location where a function\n\ argument is passed depends on whether or not it is a named argument.\n\ Index: gcc/calls.c =================================================================== --- gcc/calls.c.orig +++ gcc/calls.c @@ -3011,6 +3011,33 @@ expand_call (tree exp, rtx target, int i funexp = rtx_for_function_call (fndecl, addr); + /* Precompute all register parameters. It isn't safe to compute anything + once we have started filling any specific hard regs. */ + precompute_register_parameters (num_actuals, args, ®_parm_seen); + + if (CALL_EXPR_STATIC_CHAIN (exp)) + static_chain_value = expand_normal (CALL_EXPR_STATIC_CHAIN (exp)); + else + static_chain_value = 0; + +#ifdef REG_PARM_STACK_SPACE + /* Save the fixed argument area if it's part of the caller's frame and + is clobbered by argument setup for this call. */ + if (ACCUMULATE_OUTGOING_ARGS && pass) + save_area = save_fixed_argument_area (reg_parm_stack_space, argblock, + &low_to_save, &high_to_save); +#endif + + bool any_regs = false; + for (i = 0; i < num_actuals; i++) + if (args[i].reg != NULL_RTX) + { + any_regs = true; + targetm.calls.call_args (args[i].reg, funtype); + } + if (!any_regs) + targetm.calls.call_args (pc_rtx, funtype); + /* Figure out the register where the value, if any, will come back. */ valreg = 0; if (TYPE_MODE (rettype) != VOIDmode @@ -3037,23 +3064,6 @@ expand_call (tree exp, rtx target, int i } } - /* Precompute all register parameters. It isn't safe to compute anything - once we have started filling any specific hard regs. */ - precompute_register_parameters (num_actuals, args, ®_parm_seen); - - if (CALL_EXPR_STATIC_CHAIN (exp)) - static_chain_value = expand_normal (CALL_EXPR_STATIC_CHAIN (exp)); - else - static_chain_value = 0; - -#ifdef REG_PARM_STACK_SPACE - /* Save the fixed argument area if it's part of the caller's frame and - is clobbered by argument setup for this call. */ - if (ACCUMULATE_OUTGOING_ARGS && pass) - save_area = save_fixed_argument_area (reg_parm_stack_space, argblock, - &low_to_save, &high_to_save); -#endif - /* Now store (and compute if necessary) all non-register parms. These come before register parms, since they can require block-moves, which could clobber the registers used for register parms. @@ -3458,6 +3468,8 @@ expand_call (tree exp, rtx target, int i for (i = 0; i < num_actuals; ++i) free (args[i].aligned_regs); + targetm.calls.end_call_args (); + insns = get_insns (); end_sequence (); @@ -3985,6 +3997,18 @@ emit_library_call_value_1 (int retval, r } #endif + /* When expanding a normal call, args are stored in push order, + which is the reverse of what we have here. */ + bool any_regs = false; + for (int i = nargs; i-- > 0; ) + if (argvec[i].reg != NULL_RTX) + { + targetm.calls.call_args (argvec[i].reg, NULL_TREE); + any_regs = true; + } + if (!any_regs) + targetm.calls.call_args (pc_rtx, NULL_TREE); + /* Push the args that need to be pushed. */ /* ARGNUM indexes the ARGVEC array in the order in which the arguments @@ -4224,6 +4248,8 @@ emit_library_call_value_1 (int retval, r valreg = gen_rtx_REG (TYPE_MODE (tfom), REGNO (valreg)); } + targetm.calls.end_call_args (); + /* For calls to `setjmp', etc., inform function.c:setjmp_warnings that it should complain if nonvolatile values are live. For functions that cannot return, inform flow that control does not