From patchwork Tue Dec 19 14:29:56 2023 Content-Type: text/plain; charset="utf-8" MIME-Version: 1.0 Content-Transfer-Encoding: 7bit X-Patchwork-Submitter: =?utf-8?q?Marc_Poulhi=C3=A8s?= X-Patchwork-Id: 82485 Return-Path: X-Original-To: patchwork@sourceware.org Delivered-To: patchwork@sourceware.org Received: from server2.sourceware.org (localhost [IPv6:::1]) by sourceware.org (Postfix) with ESMTP id E3D34385DC38 for ; Tue, 19 Dec 2023 14:30:28 +0000 (GMT) X-Original-To: gcc-patches@gcc.gnu.org Delivered-To: gcc-patches@gcc.gnu.org Received: from mail-wm1-x32f.google.com (mail-wm1-x32f.google.com [IPv6:2a00:1450:4864:20::32f]) by sourceware.org (Postfix) with ESMTPS id 9D000385C6E0 for ; Tue, 19 Dec 2023 14:30:06 +0000 (GMT) DMARC-Filter: OpenDMARC Filter v1.4.2 sourceware.org 9D000385C6E0 Authentication-Results: sourceware.org; dmarc=pass (p=none dis=none) header.from=adacore.com Authentication-Results: sourceware.org; spf=pass smtp.mailfrom=adacore.com ARC-Filter: OpenARC Filter v1.0.0 sourceware.org 9D000385C6E0 Authentication-Results: server2.sourceware.org; arc=none smtp.remote-ip=2a00:1450:4864:20::32f ARC-Seal: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1702996209; cv=none; b=wbzBoDDVDnsEaI/ouVCwniZLw5w1RdOEODgOFo6eg2ARCflSPltHtU+mk0PWzLsJr2HuFuMYoLTDIQZWIRW9Mu1wZU93vYfmBzsY/3ZxNy3mlu/Eu9oBfH9m21aCNxZSGd7RyfYmLndAwrAKw6GFCapE1NNIRsPXCrwQk5KC4Z8= ARC-Message-Signature: i=1; a=rsa-sha256; d=sourceware.org; s=key; t=1702996209; c=relaxed/simple; bh=Tb1xH/j55MXbX5L8mXwIrRygxCbWL8Ber2SmS1hx4hY=; h=DKIM-Signature:From:To:Subject:Date:Message-ID:MIME-Version; b=xm1aU3umhfgSH58QHzy1gqYEpaQfI8iP6+pIXYst2kapIqHcNP7I/+LcP+j3g9PnsgCMAQZrh0AnSSUHmTuIHFh0ARl2lXGns0SxLvBVAbjk+2tDo4KNL6LDuRLRbp/c4VMSRmODRe9dZJQEplvtTXvOHN172lKbR2VV5JdCbxg= ARC-Authentication-Results: i=1; server2.sourceware.org Received: by mail-wm1-x32f.google.com with SMTP id 5b1f17b1804b1-40c3fe6c1b5so50788625e9.2 for ; Tue, 19 Dec 2023 06:30:06 -0800 (PST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=adacore.com; s=google; t=1702996205; x=1703601005; darn=gcc.gnu.org; h=content-transfer-encoding:mime-version:message-id:date:subject:cc :to:from:from:to:cc:subject:date:message-id:reply-to; bh=/E4r4LEYGryGAML6ZCFVhyfY+9IqkZkiPJXBAuaSmz0=; b=IOqla9QAdwGMYHlszKJzcMbvYcvCGEwA4U8SHUkmYbNtdAYql2DoRH+PbYkfZ8epEr oG4pLHw0GKTEnWbM1MY8SOYTgpzR9dECAdi2n3CdpSCnYp6TpPDZc3X14a33SxxUkscQ Oec8Ap8Gj4PvsZGctA4H2Xhd8MIOvkILOxkYNFDuQCCe0xvl5IjdfA6hjk7eljq1mecd Kzm6n+YLbtICx5WQraHvhWb+v+3Bb5o4WomSK42RhRFWdUscnfBUkycEGtuay+UDONH1 Iqf/CiSzRi7HYqp3yM2S5FstEDsl6desFqa+RdLDbCJkPdJzOAXb9GCFXUZSILWqy4VI cOtQ== X-Google-DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=1e100.net; s=20230601; t=1702996205; x=1703601005; h=content-transfer-encoding:mime-version:message-id:date:subject:cc :to:from:x-gm-message-state:from:to:cc:subject:date:message-id :reply-to; bh=/E4r4LEYGryGAML6ZCFVhyfY+9IqkZkiPJXBAuaSmz0=; b=mUjR9bnhZ6/RC523Ody9aAeh2l13f9vxxwKI07skKNn08JNNIAfuctgp/LluWsv4wi kKZ00mf+3DgNPIJ0BM6T2RC7QaSeZt+Rzi9RBJPQv7Hee6rgJj5/vihENzBbYvFMEiE/ K/qPV8uWaz8q3G4Md0UNVpd+NU6WYxB3VizQNLoynHYlGyL0PxaVw3Uzfy+wQHBu9V8f gnFTeotLSA6jnS2dQ+/exss38OxjvGovOtcFAaBNn8fqJNbbDAtei2rIiQBgOO4ef0zy sVh+dD4XxADTY5cbjdWQfdG5j7yZUCOWoFKV1WuJ9ChWIiPW7xuN9Fx9YXWzSGPLC7Rn A/og== X-Gm-Message-State: AOJu0YwRlzXPR09XJEnOQmSvBTtGutykPffHQS9pqO3iQ/Jt0zZ9lOoI ubFQWYC7LIMrC+jp7NM8nRD2S4NFmyiA64wJ+DI= X-Google-Smtp-Source: AGHT+IGhNbIHCOaDqJgt7Bkf34BoaVHH3016im0O/nJO9JjZaI+vLMqJOH97z6mLGjGeyumxD/3iRg== X-Received: by 2002:a7b:cb92:0:b0:40c:3308:3b02 with SMTP id m18-20020a7bcb92000000b0040c33083b02mr9969036wmi.99.1702996204939; Tue, 19 Dec 2023 06:30:04 -0800 (PST) Received: from poulhies-Precision-5550.lan ([2001:861:3382:1a90:fe1e:443:c34f:edaa]) by smtp.gmail.com with ESMTPSA id p20-20020a05600c359400b0040c440f9393sm3080945wmq.42.2023.12.19.06.30.04 (version=TLS1_3 cipher=TLS_AES_256_GCM_SHA384 bits=256/256); Tue, 19 Dec 2023 06:30:04 -0800 (PST) From: =?utf-8?q?Marc_Poulhi=C3=A8s?= To: gcc-patches@gcc.gnu.org Cc: Eric Botcazou Subject: [COMMITTED] ada: Further cleanup in finalization machinery Date: Tue, 19 Dec 2023 15:29:56 +0100 Message-ID: <20231219142956.454370-1-poulhies@adacore.com> X-Mailer: git-send-email 2.43.0 MIME-Version: 1.0 X-Spam-Status: No, score=-9.5 required=5.0 tests=BAYES_00, DKIM_SIGNED, DKIM_VALID, DKIM_VALID_AU, DKIM_VALID_EF, GIT_PATCH_0, KAM_ASCII_DIVIDERS, RCVD_IN_DNSWL_NONE, SPAM_BODY, SPF_HELO_NONE, SPF_PASS, TXREP, T_SCC_BODY_TEXT_LINE autolearn=ham autolearn_force=no version=3.4.6 X-Spam-Checker-Version: SpamAssassin 3.4.6 (2021-04-09) on server2.sourceware.org X-BeenThere: gcc-patches@gcc.gnu.org X-Mailman-Version: 2.1.30 Precedence: list List-Id: Gcc-patches mailing list List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: gcc-patches-bounces+patchwork=sourceware.org@gcc.gnu.org From: Eric Botcazou This streamlines the submachinery that makes it so that the finalization of temporaries created for EWAs and conditional expressions is deferred to the enclosing context. The original implementation was using a deep tree traversal for EWAs, which was later restricted to immediate subexpressions; this further flattens it to the traversal of the immediate list of actions of the EWA in keeping with the implementation for conditional expressions. This should not change anything because the enclosing context found by the machinery is the same, whatever the starting position in a nest of EWAs or conditional expressions. gcc/ada/ * exp_ch4.adb (Process_If_Case_Statements): Rename into... (Process_Transients_In_Expression): ...this and beef up comment. (Expand_N_Case_Expression): Call Process_Transients_In_Expression unconditionally on the list of actions of each alternative. (Expand_N_Expression_With_Actions): Do not deal with actions in nested subexpressions, but call Process_Transients_In_Expression on the list of actions only. (Expand_N_If_Expression): Adjust to above renaming. Add missing calls to Process_Transients_In_Expression in the case when an EWA is not used because of Minimize_Expression_With_Actions. Tested on x86_64-pc-linux-gnu, committed on master. --- gcc/ada/exp_ch4.adb | 154 +++++++++++++++++++------------------------- 1 file changed, 66 insertions(+), 88 deletions(-) diff --git a/gcc/ada/exp_ch4.adb b/gcc/ada/exp_ch4.adb index 99be96d3ab7..8f4cf0808dc 100644 --- a/gcc/ada/exp_ch4.adb +++ b/gcc/ada/exp_ch4.adb @@ -241,11 +241,6 @@ package body Exp_Ch4 is -- and X is a simple entity, and op is a comparison operator, optimizes it -- into a comparison of X'First and X'Last. - procedure Process_If_Case_Statements (N : Node_Id; Stmts : List_Id); - -- Inspect and process statement list Stmt of if or case expression N for - -- transient objects. If such objects are found, the routine generates code - -- to clean them up when the context of the expression is evaluated. - procedure Process_Transient_In_Expression (Obj_Decl : Node_Id; Expr : Node_Id; @@ -255,9 +250,25 @@ package body Exp_Ch4 is -- object when the enclosing context is elaborated or evaluated. Obj_Decl -- denotes the declaration of the transient object, which is usually the -- result of a controlled function call. Expr denotes the expression with - -- actions, if expression, or case expression node. Stmts denotes the - -- statement list which contains Decl, either at the top level or within a - -- nested construct. + -- actions, if expression, or case expression node. Stmts denotes one of + -- the actions list of Expr, which contains Decl. + + procedure Process_Transients_In_Expression + (Expr : Node_Id; + Stmts : List_Id); + -- Subsidiary routine to the expansion of expression_with_actions, if and + -- case expressions. Inspect and process actions list Stmts of expression + -- Expr for transient objects. If such objects are found, the routine will + -- generate code to finalize them when the enclosing context is elaborated + -- or evaluated. + + -- This specific processing is required for these expressions because the + -- management of transient objects for expressions implemented in Exp_Ch7 + -- cannot deal with nested lists of actions whose effects may outlive the + -- lists and affect the result of the parent expressions. In these cases, + -- the lifetime of temporaries created in these lists must be extended to + -- match that of the enclosing context of the parent expressions and, in + -- particular, their finalization must be deferred to this context. procedure Rewrite_Comparison (N : Node_Id); -- If N is the node for a comparison whose outcome can be determined at @@ -5411,14 +5422,10 @@ package body Exp_Ch4 is Statements => Stmts)); -- Finalize any transient objects on exit from the alternative. - -- This needs to be done only when the case expression is _not_ - -- later converted into an expression with actions, which already - -- contains this form of processing, and after Stmts is attached + -- Note that this needs to be done only after Stmts is attached -- to the Alternatives list above (for Safe_To_Capture_Value). - if Optimize_Return_Stmt or else not Is_Copy_Type (Typ) then - Process_If_Case_Statements (N, Stmts); - end if; + Process_Transients_In_Expression (N, Stmts); end; Next (Alt); @@ -5482,12 +5489,6 @@ package body Exp_Ch4 is procedure Force_Boolean_Evaluation (Expr : Node_Id); -- Force the evaluation of Boolean expression Expr - function Process_Action (Act : Node_Id) return Traverse_Result; - -- Inspect and process a single action of an expression_with_actions for - -- transient objects. If such objects are found, the routine generates - -- code to clean them up when the context of the expression is evaluated - -- or elaborated. - ------------------------------ -- Force_Boolean_Evaluation -- ------------------------------ @@ -5520,42 +5521,6 @@ package body Exp_Ch4 is Analyze (Expression (N)); end Force_Boolean_Evaluation; - -------------------- - -- Process_Action -- - -------------------- - - function Process_Action (Act : Node_Id) return Traverse_Result is - begin - if Nkind (Act) = N_Object_Declaration - and then Is_Finalizable_Transient (Act, N) - then - Process_Transient_In_Expression (Act, N, Acts); - return Skip; - - -- Avoid processing temporary function results multiple times when - -- dealing with nested expression_with_actions or nested blocks. - -- Similarly, do not process temporary function results in loops. - -- This is done by Expand_N_Loop_Statement and Build_Finalizer. - -- Note that we used to wrongly return Abandon instead of Skip here: - -- this is wrong since it means that we were ignoring lots of - -- relevant subsequent statements. - - elsif Nkind (Act) in N_Expression_With_Actions - | N_Block_Statement - | N_Loop_Statement - then - return Skip; - end if; - - return OK; - end Process_Action; - - procedure Process_Single_Action is new Traverse_Proc (Process_Action); - - -- Local variables - - Act : Node_Id; - -- Start of processing for Expand_N_Expression_With_Actions begin @@ -5616,14 +5581,9 @@ package body Exp_Ch4 is Force_Evaluation (Expression (N)); end if; - -- Process all transient objects found within the actions of the EWA - -- node. + -- Process transient objects found within the actions of the EWA node - Act := First (Acts); - while Present (Act) loop - Process_Single_Action (Act); - Next (Act); - end loop; + Process_Transients_In_Expression (N, Acts); -- Deal with case where there are no actions. In this case we simply -- rewrite the node with its expression since we don't need the actions @@ -5802,8 +5762,8 @@ package body Exp_Ch4 is -- of actions. These temporaries need to be finalized after the if -- expression is evaluated. - Process_If_Case_Statements (N, Then_Actions (N)); - Process_If_Case_Statements (N, Else_Actions (N)); + Process_Transients_In_Expression (N, Then_Actions (N)); + Process_Transients_In_Expression (N, Else_Actions (N)); New_If := Make_Implicit_If_Statement (N, @@ -5843,8 +5803,8 @@ package body Exp_Ch4 is -- of actions. These temporaries need to be finalized after the if -- expression is evaluated. - Process_If_Case_Statements (N, Then_Actions (N)); - Process_If_Case_Statements (N, Else_Actions (N)); + Process_Transients_In_Expression (N, Then_Actions (N)); + Process_Transients_In_Expression (N, Else_Actions (N)); declare Cnn : constant Entity_Id := Make_Temporary (Loc, 'C', N); @@ -6186,13 +6146,20 @@ package body Exp_Ch4 is or else Present (Else_Actions (N)) or else Force_Expand then - -- We now wrap the actions into the appropriate expression if Minimize_Expression_With_Actions and then (Is_Elementary_Type (Underlying_Type (Typ)) or else Is_Constrained (Underlying_Type (Typ))) then + -- When the "then" or "else" expressions involve controlled + -- function calls, generated temporaries are chained on the + -- corresponding list of actions. These temporaries need to + -- be finalized after the if expression is evaluated. + + Process_Transients_In_Expression (N, Then_Actions (N)); + Process_Transients_In_Expression (N, Else_Actions (N)); + -- If we can't use N_Expression_With_Actions nodes, then we insert -- the following sequence of actions (using Insert_Actions): @@ -6239,6 +6206,10 @@ package body Exp_Ch4 is -- Regular path using Expression_With_Actions else + -- We do not need to call Process_Transients_In_Expression on + -- the list of actions in this case, because the expansion of + -- Expression_With_Actions will do it. + if Present (Then_Actions (N)) then Rewrite (Thenx, Make_Expression_With_Actions (Sloc (Thenx), @@ -14938,26 +14909,6 @@ package body Exp_Ch4 is Analyze_And_Resolve (N, Typ, Suppress => Overflow_Check); end Optimize_Length_Comparison; - -------------------------------- - -- Process_If_Case_Statements -- - -------------------------------- - - procedure Process_If_Case_Statements (N : Node_Id; Stmts : List_Id) is - Decl : Node_Id; - - begin - Decl := First (Stmts); - while Present (Decl) loop - if Nkind (Decl) = N_Object_Declaration - and then Is_Finalizable_Transient (Decl, N) - then - Process_Transient_In_Expression (Decl, N, Stmts); - end if; - - Next (Decl); - end loop; - end Process_If_Case_Statements; - ------------------------------------- -- Process_Transient_In_Expression -- ------------------------------------- @@ -15116,6 +15067,33 @@ package body Exp_Ch4 is end if; end Process_Transient_In_Expression; + -------------------------------------- + -- Process_Transients_In_Expression -- + -------------------------------------- + + procedure Process_Transients_In_Expression + (Expr : Node_Id; + Stmts : List_Id) + is + Decl : Node_Id; + + begin + pragma Assert (Nkind (Expr) in N_Case_Expression + | N_Expression_With_Actions + | N_If_Expression); + + Decl := First (Stmts); + while Present (Decl) loop + if Nkind (Decl) = N_Object_Declaration + and then Is_Finalizable_Transient (Decl, Expr) + then + Process_Transient_In_Expression (Decl, Expr, Stmts); + end if; + + Next (Decl); + end loop; + end Process_Transients_In_Expression; + ------------------------ -- Rewrite_Comparison -- ------------------------