1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206
|
------------------------------------------------------------------------------
-- G P S --
-- --
-- Copyright (C) 2013-2018, AdaCore --
-- --
-- This is free software; you can redistribute it and/or modify it under --
-- terms of the GNU General Public License as published by the Free Soft- --
-- ware Foundation; either version 3, or (at your option) any later ver- --
-- sion. This software is distributed in the hope that it will be useful, --
-- but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHAN- --
-- TABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public --
-- License for more details. You should have received a copy of the GNU --
-- General Public License distributed with this software; see file --
-- COPYING3. If not, go to http://www.gnu.org/licenses for a complete copy --
-- of the license. --
------------------------------------------------------------------------------
package body GPS.Scripts is
type Ownership_Mode is (Ada_Owns_Python, Python_Owns_Ada);
------------
-- Create --
------------
function Create
(Kernel : GPS.Core_Kernels.Core_Kernel)
return Kernel_Scripts_Repository is
begin
return (Scripts_Repository_Record with Kernel => Kernel);
end Create;
----------------
-- Get_Kernel --
----------------
function Get_Kernel
(Data : GNATCOLL.Scripts.Callback_Data'Class)
return GPS.Core_Kernels.Core_Kernel is
begin
return Kernel_Scripts_Repository (Get_Repository (Data).all).Kernel;
end Get_Kernel;
----------------
-- Get_Kernel --
----------------
function Get_Kernel
(Script : access GNATCOLL.Scripts.Scripting_Language_Record'Class)
return GPS.Core_Kernels.Core_Kernel is
begin
return Kernel_Scripts_Repository (Get_Repository (Script).all).Kernel;
end Get_Kernel;
----------
-- Free --
----------
procedure Free (Self : in out Script_Proxy) is
C : Inst_Cursor := First (Self.Instances);
begin
-- Severe the connection between instances and Ada object
while Has_Element (C) loop
Unset_Data
(Element (Self.Instances, C),
Script_Proxy'Class (Self).Class_Name);
Next (Self.Instances, C);
end loop;
-- Unref all instances (and possibly destroy them). Also
-- release memory on the Ada side.
Free (Self.Instances);
end Free;
--------------------
-- Script_Proxies --
--------------------
package body Script_Proxies is
type Element_Properties_Record is new Instance_Property_Record with
record
Element : Element_Type;
Ownership : Ownership_Mode;
end record;
overriding procedure Destroy (Prop : in out Element_Properties_Record);
-------------
-- Destroy --
-------------
overriding procedure Destroy
(Prop : in out Element_Properties_Record) is
begin
if Prop.Ownership = Python_Owns_Ada then
Free (Prop.Element);
end if;
end Destroy;
----------------------------
-- Get_Or_Create_Instance --
----------------------------
function Get_Or_Create_Instance
(Self : in out Proxy'Class;
Obj : Element_Type;
Script : not null access Scripting_Language_Record'Class;
Class_To_Create : String := "")
return Class_Instance
is
C : Class_Instance := Get (Self.Instances, Script);
begin
if C = No_Class_Instance then
-- This assumes the class has already been declared with its
-- proper base classes.
C := New_Instance
(Script, New_Class (Script.Get_Repository,
(if Class_To_Create = "" then Self.Class_Name
else Class_To_Create)));
Store_In_Instance (Self, C, Obj);
end if;
return C;
end Get_Or_Create_Instance;
-----------------------
-- Store_In_Instance --
-----------------------
procedure Store_In_Instance
(Self : in out Proxy'Class;
Inst : Class_Instance;
Obj : Element_Type) is
begin
Set_Data
(Inst, Self.Class_Name,
Element_Properties_Record'
(Element => Obj,
Ownership => Ada_Owns_Python));
Set (Self.Instances, Inst);
end Store_In_Instance;
-----------------
-- Has_Element --
-----------------
function Has_Element (Inst : Class_Instance) return Boolean is
P : Proxy; -- Only to retrieve class name
Data : constant Instance_Property := Get_Data (Inst, P.Class_Name);
begin
return Data /= null;
end Has_Element;
-------------------
-- From_Instance --
-------------------
function From_Instance (Inst : Class_Instance) return Element_Type is
P : Proxy; -- Only to retrieve class name
Data : constant Instance_Property := Get_Data (Inst, P.Class_Name);
begin
if Data = null then
raise No_Data_Set_For_Instance with
"No Ada object associated with python " & P.Class_Name
& " instance";
end if;
return Element_Properties_Record (Data.all).Element;
end From_Instance;
------------------------
-- Transfer_Ownership --
------------------------
function Transfer_Ownership
(Self : in out Proxy'Class) return Instances_Status
is
Found : Boolean := False;
C : Inst_Cursor := First (Self.Instances);
Detached : Element_Type;
begin
while Has_Element (C) loop
if not Found then
Detached := Detach
(From_Instance (Element (Self.Instances, C)));
Found := True;
end if;
Set_Data
(Element (Self.Instances, C),
Self.Class_Name,
Element_Properties_Record'
(Element => Detached,
Ownership => Python_Owns_Ada));
Next (Self.Instances, C);
end loop;
Free (Self.Instances);
if Found then
return Has_Instances;
else
return Has_No_Instances;
end if;
end Transfer_Ownership;
end Script_Proxies;
end GPS.Scripts;
|