From mboxrd@z Thu Jan 1 00:00:00 1970 Return-Path: Received: by sourceware.org (Postfix, from userid 48) id 269E63858C50; Sat, 13 Apr 2024 17:09:33 +0000 (GMT) DKIM-Filter: OpenDKIM Filter v2.11.0 sourceware.org 269E63858C50 DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/relaxed; d=gcc.gnu.org; s=default; t=1713028173; bh=s9Lb4kGUuRdIQCyf9DhcOeKrWufxfdIphlwCnsGvVkQ=; h=From:To:Subject:Date:From; b=M5WsuFMdvSXgLb6HoFwyUeL3kIRAvVL1OBHnRcV+V9IGciDPJEZebosE4OxANm5Na hC8bS445DpcTnNNd/3DBgB16KydaDjwcVXLCgfI8Yv3+BlXjM/klCQbvL7gq2vlckZ kppCrGCa5uUHRPpiGYfETBBgNVtrdIx17fKh9r4U= From: "jhb.chat at gmail dot com" To: gcc-bugs@gcc.gnu.org Subject: [Bug ada/114710] New: Temporary object finalized too late Date: Sat, 13 Apr 2024 17:09:31 +0000 X-Bugzilla-Reason: CC X-Bugzilla-Type: new X-Bugzilla-Watch-Reason: None X-Bugzilla-Product: gcc X-Bugzilla-Component: ada X-Bugzilla-Version: 13.2.0 X-Bugzilla-Keywords: X-Bugzilla-Severity: normal X-Bugzilla-Who: jhb.chat at gmail dot com X-Bugzilla-Status: UNCONFIRMED X-Bugzilla-Resolution: X-Bugzilla-Priority: P3 X-Bugzilla-Assigned-To: unassigned at gcc dot gnu.org X-Bugzilla-Target-Milestone: --- X-Bugzilla-Flags: X-Bugzilla-Changed-Fields: bug_id short_desc product version bug_status bug_severity priority component assigned_to reporter cc target_milestone attachments.created Message-ID: Content-Type: text/plain; charset="UTF-8" Content-Transfer-Encoding: quoted-printable X-Bugzilla-URL: http://gcc.gnu.org/bugzilla/ Auto-Submitted: auto-generated MIME-Version: 1.0 List-Id: https://gcc.gnu.org/bugzilla/show_bug.cgi?id=3D114710 Bug ID: 114710 Summary: Temporary object finalized too late Product: gcc Version: 13.2.0 Status: UNCONFIRMED Severity: normal Priority: P3 Component: ada Assignee: unassigned at gcc dot gnu.org Reporter: jhb.chat at gmail dot com CC: dkm at gcc dot gnu.org Target Milestone: --- Created attachment 57940 --> https://gcc.gnu.org/bugzilla/attachment.cgi?id=3D57940&action=3Dedit temporrary finalized too late Version: GCC/GNAT version 13.2.0, Win10 msys2 and Godbolt Godbolt indicates this is a long standing functionality (all the way down to 8.2, which is the last I could check there). When making a scoped lock / scoped mutex, I found that temporary variables generated by a function were not being finalized after they were no longer used. This lead to a deadlock situation with the scope lock / scoped mutex= .=20 There doesn't appear to be any reason to hold onto the object returned by t= he Lock function in this example. The call to the Lock function returns a temporary object that is never saved and should be finalized immediately In the example below, you can see the finalization happen after the body of main completes instead of before by commenting out the v2 declaration (to remove the deadlock). Example: ------------------------------------------------------- with Ada.Finalization; with Ada.Text_IO; use Ada.Text_IO; procedure Example is package Deadlocker is protected type Mutex is entry Lock; procedure Unlock; private Locked : Boolean :=3D False; end Mutex; type Instance (Element : not null access Integer)=20 is=20 new Ada.Finalization.Limited_Controlled with record M : not null access Mutex; end record; overriding procedure Finalize(Self : in out Instance); type Object is tagged limited record Locker : aliased Mutex; Item : aliased Integer; end record; function Lock (Self : aliased in out Object)=20 return Instance'Class; end Deadlocker; package body Deadlocker is protected body Mutex is entry Lock when not Locked is begin Locked :=3D True; Put_Line("Locked!"); end Lock; procedure Unlock is begin Locked :=3D False; Put_Line("Unlocked!"); end Unlock; end Mutex; function Lock (Self : aliased in out Object)=20 return Instance'Class is begin return Result : Instance :=3D Instance' (Ada.Finalization.Limited_Controlled with Element =3D> Self.Item'Access,=20 M =3D> Self.Locker'Access) do=20 Put_Line("Locking..."); Result.M.Lock; end return; end Lock; procedure Finalize(Self : in out Instance) is begin Put_Line("Unlocking..."); Self.M.Unlock; end Finalize; end Deadlocker; Test : Deadlocker.Object; v1 : constant Integer :=3D Test.Lock.Element.all; -- Should release lock after v2 : constant Integer :=3D Test.Lock.Element.all; -- Should release lock after begin Put_Line("In main body"); end Example; ------------------------------------------------------- Output: ------------------------------------------------------- Program returned: 143 Program stdout Locking... Locked! Locking... Program stderr Killed - processing time exceeded Program terminated with signal: SIGKILL ------------------------------------------------------- Expected Output: ------------------------------------------------------- Program returned: 0 Program stdout Locking... Locked! Unlocking... Unlocked! Locking... Locked! Unlocking... Unlocked! In main body -------------------------------------------------------=