Commit c50d3948 authored by Maxime Perrotin's avatar Maxime Perrotin
parents 2266f355 4c7151a4
......@@ -50,7 +50,7 @@ install-data-local:
$(INSTALL_DATA) $$file $(DESTDIR)$(datadir)/ocarina/AADLv1 || exit 1; \
$(INSTALL_DATA) $$file $(DESTDIR)$(datadir)/ocarina/AADLv2 || exit 1; \
done
for file in $(AADL_V2_PROPERTIES); do \
for file in $(AADL_V2_PROPERTIES) $(AADL_V2_COMPONENTS); do \
$(INSTALL_DATA) $$file $(DESTDIR)$(datadir)/ocarina/AADLv2 || exit 1; \
done
for file in $(AADL_V1_PROPERTIES); do \
......
......@@ -24,7 +24,7 @@ property set Data_Model is
-- types (10**(-scale) is the precision).
Data_Representation : enumeration
(Array, Boolean, Character, Enum, Float,
(Array, Boolean, Bounded_Array, Character, Enum, Float,
Fixed, Integer, String, Struct, Union)
applies to ( data );
-- The Data_Representation property may be used to specify the
......
......@@ -6,7 +6,7 @@
-- --
-- B o d y --
-- --
-- Copyright (C) 2014-2016 ESA & ISAE. --
-- Copyright (C) 2014-2018 ESA & ISAE. --
-- --
-- Ocarina is free software; you can redistribute it and/or modify under --
-- terms of the GNU General Public License as published by the Free Soft- --
......@@ -29,16 +29,18 @@
-- --
------------------------------------------------------------------------------
with Ada.Text_IO;
with Charset; use Charset;
with Ocarina.Namet;
with Ocarina.ME_AADL;
with Ocarina.ME_AADL.AADL_Instances.Nodes;
with Ocarina.ME_AADL.AADL_Instances.Nutils;
with Ocarina.Instances; use Ocarina.Instances;
with Ocarina.ME_AADL.AADL_Instances.Entities;
use Ocarina.ME_AADL.AADL_Instances.Entities;
with Ocarina.Backends.Helper;
with Ocarina.Backends.Utils;
with Ada.Text_IO;
package body Ocarina.Backends.Alloy is
......@@ -47,14 +49,16 @@ package body Ocarina.Backends.Alloy is
use Ocarina.Namet;
use Ada.Text_IO;
use Ocarina.ME_AADL;
use Ocarina.ME_AADL.AADL_Instances.Entities;
use Ocarina.ME_AADL.AADL_Instances.Nutils;
use Ocarina.Backends.Helper;
use Ocarina.Backends.Utils;
use AIN;
procedure Visit (E : Node_Id);
procedure Visit_Architecture_Instance (E : Node_Id);
procedure Visit_Component_Instance (E : Node_Id);
procedure Visit_Subcomponents_Of is new Visit_Subcomponents_Of_G (Visit);
FD : File_Type;
Root_System_Name : Name_Id;
......@@ -91,27 +95,11 @@ package body Ocarina.Backends.Alloy is
------------------------------
procedure Visit_Component_Instance (E : Node_Id) is
Category_Name_String : constant array
(Component_Category'Range) of Name_Id :=
(CC_Abstract => Get_String_Name ("abstract"),
CC_Bus => Get_String_Name ("bus"),
CC_Data => Get_String_Name ("data"),
CC_Device => Get_String_Name ("device"),
CC_Memory => Get_String_Name ("memory"),
CC_Process => Get_String_Name ("process"),
CC_Processor => Get_String_Name ("processor"),
CC_Subprogram => Get_String_Name ("subprogram"),
CC_Subprogram_Group => Get_String_Name ("subprogram group"),
CC_System => Get_String_Name ("system"),
CC_Thread => Get_String_Name ("thread"),
CC_Thread_Group => Get_String_Name ("thread group"),
CC_Unknown => No_Name,
CC_Virtual_Bus => Get_String_Name ("virtual_bus"),
CC_Virtual_Processor => Get_String_Name ("virtual_processor"));
Category : constant Component_Category := Get_Category_Of_Component (E);
T : Node_Id;
E_Subcomponents : constant Node_Array := Subcomponents_Of (E);
E_Properties : constant Node_Array := Properties_Of (E);
begin
-- Create Alloy component
......@@ -137,30 +125,25 @@ package body Ocarina.Backends.Alloy is
" extends Component{}{");
end if;
Put_Line
(FD,
ASCII.HT &
"type=" &
Get_Name_String (Category_Name_String (Category)));
Put_Line (FD, ASCII.HT & "type=" & Category_Name (Category));
-- Rule #2: list subcomponents
Put (FD, ASCII.HT & "subcomponents=");
if Present (Subcomponents (E)) then
T := First_Node (Subcomponents (E));
while Present (T) loop
if E_Subcomponents'Length > 0 then
for J in E_Subcomponents'Range loop
declare
Subcomponent_Name : constant String :=
To_Lower
(Get_Name_String
(Normalize_Name
(Fully_Qualified_Instance_Name
(Corresponding_Instance (T)))));
(Corresponding_Instance (E_Subcomponents (J))))));
begin
Put (FD, Subcomponent_Name);
T := Next_Node (T);
if Present (T) then
if J < E_Subcomponents'Last then
Put (FD, "+");
end if;
end;
......@@ -174,16 +157,17 @@ package body Ocarina.Backends.Alloy is
-- Rule #3: list properties
Put (FD, ASCII.HT & "properties=");
if Present (AIN.Properties (E)) then
T := First_Node (AIN.Properties (E));
while Present (T) loop
if E_Properties'Length > 0 then
for J in E_Properties'Range loop
Put
(FD,
To_Lower
(Get_Name_String
(Normalize_Name (Display_Name (Identifier (T))))));
T := Next_Node (T);
if Present (T) then
(Normalize_Name (Display_Name (Identifier
(E_Properties (J)))))));
if J < E_Properties'Last then
Put (FD, "+");
end if;
end loop;
......@@ -200,14 +184,8 @@ package body Ocarina.Backends.Alloy is
-- Iterate over subcomponents
if Present (Subcomponents (E)) then
T := First_Node (Subcomponents (E));
while Present (T) loop
Visit (Corresponding_Instance (T));
Visit_Subcomponents_Of (E);
T := Next_Node (T);
end loop;
end if;
end Visit_Component_Instance;
----------
......@@ -226,16 +204,13 @@ package body Ocarina.Backends.Alloy is
--------------
procedure Generate (AADL_Root : Node_Id) is
Instance_Root : Node_Id;
begin
-- Instantiate the AADL tree
Instance_Root : constant Node_Id := Instantiate_Model (AADL_Root);
Instance_Root := Instantiate_Model (AADL_Root);
if No (Instance_Root) then
raise Program_Error;
end if;
Root_Subcomponents : constant Node_Array := Subcomponents_Of
(Root_System (Instance_Root));
begin
-- Open a new .als file
Create (File => FD, Name => "con_model.als");
......@@ -253,7 +228,7 @@ package body Ocarina.Backends.Alloy is
Put_Line (FD, "// Mapping of the AADL instance tree");
New_Line (FD);
Visit_Architecture_Instance (Instance_Root);
Visit (Instance_Root);
-- Add global contract
......@@ -271,45 +246,38 @@ package body Ocarina.Backends.Alloy is
declare
Print_Subcomponents : Boolean := True;
E : constant Node_Id := Root_System (Instance_Root);
T : Node_Id;
begin
-- We consider two patterns
-- a) system with subcomponents as system/bus/device only
-- b) general case
if Present (Subcomponents (E)) then
T := First_Node (Subcomponents (E));
while Present (T) loop
Print_Subcomponents :=
Print_Subcomponents
and then
(Get_Category_Of_Component (T) = CC_System
or else Get_Category_Of_Component (T) = CC_Device
or else Get_Category_Of_Component (T) = CC_Bus);
T := Next_Node (T);
end loop;
end if;
for Sub of Root_Subcomponents loop
Print_Subcomponents :=
Print_Subcomponents
and then
(Get_Category_Of_Component (Sub) = CC_System
or else Get_Category_Of_Component (Sub) = CC_Device
or else Get_Category_Of_Component (Sub) = CC_Bus);
end loop;
-- We are in case a), generate all subcomponents of root system
if Print_Subcomponents then
Put (FD, ASCII.HT & "output=");
if Present (Subcomponents (E)) then
T := First_Node (Subcomponents (E));
while Present (T) loop
if Root_Subcomponents'Length > 0 then
for J in Root_Subcomponents'Range loop
declare
Subcomponent_Name : constant String :=
To_Lower
(Get_Name_String
(Normalize_Name
(Fully_Qualified_Instance_Name
(Corresponding_Instance (T)))));
(Get_Name_String
(Normalize_Name
(Fully_Qualified_Instance_Name
(Corresponding_Instance
(Root_Subcomponents (J))))));
begin
Put (FD, Subcomponent_Name);
T := Next_Node (T);
if Present (T) then
if J < Root_Subcomponents'Last then
Put (FD, "+");
end if;
end;
......
......@@ -2165,7 +2165,11 @@ package body Ocarina.Backends.C_Tree.Nutils is
-- Get_Data_Size --
-------------------
function Get_Data_Size (Data : Node_Id) return Node_Id is
function Get_Data_Size (Data : Node_Id;
Is_Pointer : Boolean := False;
Maximum_Size : Boolean := False)
return Node_Id
is
Data_Representation : Supported_Data_Representation;
Value_UUL : Unsigned_Long_Long;
Value_Node : Node_Id := No_Node;
......@@ -2217,6 +2221,33 @@ package body Ocarina.Backends.C_Tree.Nutils is
Get_Data_Size
(ATN.Entity (ATN.First_Node (Get_Base_Type (Data)))));
when Data_Bounded_Array =>
if Maximum_Size then
Value_Node :=
Make_Expression
(Left_Expr =>
Make_Literal (New_Int_Value (Dimension (1), 1, 10)),
Operator => Op_Asterisk,
Right_Expr =>
Get_Data_Size
(ATN.Entity (ATN.First_Node (Get_Base_Type (Data)))));
else
Value_Node :=
Make_Expression
(Left_Expr =>
Make_Member_Designator
(Defining_Identifier =>
Make_Defining_Identifier (MN (M_length)),
Aggregate_Name =>
Make_Defining_Identifier (PN (P_Value)),
Is_Pointer => Is_Pointer),
Operator => Op_Asterisk,
Right_Expr =>
Get_Data_Size
(ATN.Entity (ATN.First_Node (Get_Base_Type (Data)))));
end if;
when Data_None =>
Value_Node :=
Make_Call_Profile
......
......@@ -6,7 +6,7 @@
-- --
-- S p e c --
-- --
-- Copyright (C) 2008-2009 Telecom ParisTech, 2010-2016 ESA & ISAE. --
-- Copyright (C) 2008-2009 Telecom ParisTech, 2010-2017 ESA & ISAE. --
-- --
-- Ocarina is free software; you can redistribute it and/or modify under --
-- terms of the GNU General Public License as published by the Free Soft- --
......@@ -157,6 +157,8 @@ package Ocarina.Backends.C_Tree.Nutils is
P_Msg,
P_Request,
P_Buffer,
P_Data,
P_Length,
P_Status,
P_Entity,
P_Task,
......@@ -179,6 +181,8 @@ package Ocarina.Backends.C_Tree.Nutils is
M_Entry,
M_Entry_Point,
M_Kind,
M_Data,
M_Length,
M_Msg,
M_Name,
M_Base_Priority,
......@@ -556,9 +560,15 @@ package Ocarina.Backends.C_Tree.Nutils is
(Array_Name : Node_Id;
Array_Item : Node_Id) return Node_Id;
function Get_Data_Size (Data : Node_Id) return Node_Id;
-- Returns a node that represent an expression with the size
-- (in bytes) of a data.
function Get_Data_Size (Data : Node_Id;
Is_Pointer : Boolean := False;
Maximum_Size : Boolean := False)
return Node_Id;
-- Returns a node that represent an expression with the size (in
-- bytes) of a data.
-- Note: for some types like Bounded_Array, this expression is dynamic.
-- - Is_Pointer controls wether we build a pointer-like expresison;
-- - Maximum_Size returns the maximum size (static value).
procedure Add_Return_Variable_In_Parameters (Parameters : List_Id);
-- Add the name of the return variable in the list.
......
......@@ -6,7 +6,7 @@
-- --
-- B o d y --
-- --
-- Copyright (C) 2010-2016 ESA & ISAE. --
-- Copyright (C) 2010-2018 ESA & ISAE. --
-- --
-- Ocarina is free software; you can redistribute it and/or modify under --
-- terms of the GNU General Public License as published by the Free Soft- --
......@@ -36,6 +36,7 @@ with Ocarina.Backends.XML_Tree.Nodes;
with Ocarina.Backends.XML_Tree.Nutils;
with Ocarina.Backends.Cheddar.Mapping;
with Ocarina.Backends.Utils;
with Ocarina.Backends.Helper;
package body Ocarina.Backends.Cheddar.Main is
......@@ -45,6 +46,7 @@ package body Ocarina.Backends.Cheddar.Main is
use Ocarina.Backends.XML_Tree.Nutils;
use Ocarina.Backends.Cheddar.Mapping;
use Ocarina.Backends.Utils;
use Ocarina.Backends.Helper;
package XTN renames Ocarina.Backends.XML_Tree.Nodes;
......@@ -117,33 +119,28 @@ package body Ocarina.Backends.Cheddar.Main is
------------------
procedure Visit_Thread (E : Node_Id) is
F : Node_Id;
begin
Append_Node_To_List (Map_Thread (E), XTN.Subitems (Tasks_Node));
if Present (Features (E)) then
F := First_Node (Features (E));
while Present (F) loop
if Kind (F) = K_Port_Spec_Instance and then Is_Event (F) then
if Is_In (F) then
Append_Node_To_List
(Map_Buffer (E, F),
XTN.Subitems (Buffers_Node));
end if;
for F of Features_Of (E) loop
if Kind (F) = K_Port_Spec_Instance and then Is_Event (F) then
if Is_In (F) then
Append_Node_To_List
(Map_Dependency (E, F),
XTN.Subitems (Dependencies_Node));
(Map_Buffer (E, F),
XTN.Subitems (Buffers_Node));
end if;
F := Next_Node (F);
end loop;
end if;
Append_Node_To_List
(Map_Dependency (E, F),
XTN.Subitems (Dependencies_Node));
end if;
end loop;
Visit_Subcomponents_Of (E);
end Visit_Thread;
------------------
----------------
-- Visit_Data --
------------------
----------------
procedure Visit_Data (E : Node_Id) is
begin
......
......@@ -6,7 +6,7 @@
-- --
-- B o d y --
-- --
-- Copyright (C) 2010-2017 ESA & ISAE. --
-- Copyright (C) 2010-2018 ESA & ISAE. --
-- --
-- Ocarina is free software; you can redistribute it and/or modify under --
-- terms of the GNU General Public License as published by the Free Soft- --
......@@ -33,14 +33,10 @@ with GNAT.OS_Lib; use GNAT.OS_Lib;
with Ocarina.Namet; use Ocarina.Namet;
with Utils; use Utils;
with Ocarina.ME_AADL.AADL_Instances.Nodes;
with Ocarina.ME_AADL.AADL_Instances.Nutils;
with Ocarina.ME_AADL.AADL_Instances.Entities;
with Ocarina.Backends.Build_Utils;
with Ocarina.Backends.Messages;
with Ocarina.Backends.Properties;
with Ocarina.Backends.Utils;
with Ocarina.Backends.XML_Common.Mapping;
with Ocarina.Backends.XML_Tree.Nodes;
with Ocarina.Backends.XML_Tree.Nutils;
......@@ -48,20 +44,15 @@ with Ocarina.Backends.XML_Values;
package body Ocarina.Backends.Cheddar.Mapping is
use Ocarina.ME_AADL;
use Ocarina.ME_AADL.AADL_Instances.Nodes;
use Ocarina.ME_AADL.AADL_Instances.Entities;
use Ocarina.Backends.Build_Utils;
use Ocarina.Backends.Messages;
use Ocarina.Backends.Properties;
use Ocarina.Backends.Utils;
use Ocarina.Backends.XML_Common.Mapping;
use Ocarina.Backends.XML_Tree.Nodes;
use Ocarina.Backends.XML_Tree.Nutils;
package AIN renames Ocarina.ME_AADL.AADL_Instances.Nodes;
package AINU renames Ocarina.ME_AADL.AADL_Instances.Nutils;
-- package AIN renames Ocarina.ME_AADL.AADL_Instances.Nodes;
package XTN renames Ocarina.Backends.XML_Tree.Nodes;
package XV renames Ocarina.Backends.XML_Values;
......@@ -290,60 +281,54 @@ package body Ocarina.Backends.Cheddar.Mapping is
-- enclosing process.
P := Make_XML_Node ("resource_used_by");
declare
Access_List : constant List_Id :=
Connections
Access_List : constant AINU.Node_Array :=
Connections_Of
(Corresponding_Instance
(Get_Container_Process (Parent_Subcomponent (E))));
Connection : Node_Id;
K, M : Node_Id;
begin
if not AINU.Is_Empty (Access_List) then
Connection := AIN.First_Node (Access_List);
while Present (Connection) loop
if Kind (Connection) = K_Connection_Instance
and then
Get_Category_Of_Connection (Connection) =
CT_Access_Data
for Connection of Access_List loop
if Kind (Connection) = K_Connection_Instance
and then Get_Category_Of_Connection (Connection) =
CT_Access_Data
then
if Item (AIN.First_Node (Path (Source (Connection)))) =
Parent_Subcomponent (E)
then
if Item (AIN.First_Node (Path (Source (Connection)))) =
Parent_Subcomponent (E)
then
M := Make_XML_Node ("resource_user");
K :=
Make_Defining_Identifier
(Fully_Qualified_Instance_Name
(Corresponding_Instance
(Item
(AIN.First_Node
(Path (Destination (Connection)))))));
Append_Node_To_List (K, XTN.Subitems (M));
-- For now, we assume all tasks take the
-- resource at the beginning, and release it at
-- the end of their dispatch.
K := Make_Literal (XV.New_Numeric_Value (1, 1, 10));
Append_Node_To_List (K, XTN.Subitems (M));
K :=
Make_Literal
(XV.New_Numeric_Value
(To_Microseconds
(Get_Execution_Time
(Corresponding_Instance
(Item
(AIN.First_Node
(Path (Destination (Connection))))))
(1)),
1,
10));
Append_Node_To_List (K, XTN.Subitems (M));
Append_Node_To_List (M, XTN.Subitems (P));
end if;
M := Make_XML_Node ("resource_user");
K :=
Make_Defining_Identifier
(Fully_Qualified_Instance_Name
(Corresponding_Instance
(Item
(AIN.First_Node
(Path (Destination (Connection)))))));
Append_Node_To_List (K, XTN.Subitems (M));
-- For now, we assume all tasks take the
-- resource at the beginning, and release it at
-- the end of their dispatch.
K := Make_Literal (XV.New_Numeric_Value (1, 1, 10));
Append_Node_To_List (K, XTN.Subitems (M));
K :=
Make_Literal
(XV.New_Numeric_Value
(To_Microseconds
(Get_Execution_Time
(Corresponding_Instance
(Item
(AIN.First_Node
(Path (Destination (Connection))))))
(1)),
1,
10));
Append_Node_To_List (K, XTN.Subitems (M));
Append_Node_To_List (M, XTN.Subitems (P));
end if;
Connection := AIN.Next_Node (Connection);
end loop;
end if;
end if;
end loop;
end;
Append_Node_To_List (P, XTN.Subitems (N));
......
------------------------------------------------------------------------------
-- --
-- OCARINA COMPONENTS --
......@@ -6,7 +7,7 @@
-- --
-- S p e c --
-- --
-- Copyright (C) 2010-2015 ESA & ISAE. --
-- Copyright (C) 2010-2018 ESA & ISAE. --
-- --
-- Ocarina is free software; you can redistribute it and/or modify under --
-- terms of the GNU General Public License as published by the Free Soft- --
......@@ -29,15 +30,122 @@
-- --
------------------------------------------------------------------------------
with Ocarina.ME_AADL;
with Ocarina.ME_AADL.AADL_Instances.Nutils;
with Ocarina.ME_AADL.AADL_Instances.Nodes;
with Ocarina.Backends.Properties;
with Ocarina.Backends.Helper;
with Ocarina.Backends.Utils;
package Ocarina.Backends.Cheddar.Mapping is
use Ocarina.ME_AADL;
use Ocarina.ME_AADL.AADL_Instances.Nodes;
use Ocarina.Backends.Properties;
use Ocarina.Backends.Helper;
use Ocarina.Backends.Utils;
package AIN renames Ocarina.ME_AADL.AADL_Instances.Nodes;
package AINU renames Ocarina.ME_AADL.AADL_Instances.Nutils;
function Map_HI_Node (E : Node_Id) return Node_Id;
function Map_HI_Unit (E : Node_Id) return Node_Id;
function Map_Processor (E : Node_Id) return Node_Id;
function Map_Process (E : Node_Id) return Node_Id;
function Map_Thread (E : Node_Id) return Node_Id;
function Map_Buffer (E : Node_Id; P : Node_Id) return Node_Id;
function Map_Processor (E : Node_Id) return Node_Id with
Pre => (True and then
-- 1/ Typing
AINU.Is_Processor (E) and then
-- 2/ Property requirements
-- a) Scheduling_Protocol policy is specified
(Get_Scheduling_Protocol (E) /= Unknown_Scheduler)
);
function Map_Process (E : Node_Id) return Node_Id with
Pre => (
-- 1/ Typing
AINU.Is_Process (E)
);
function Map_Thread (E : Node_Id) return Node_Id with
Pre => (True and then
-- 1/ Typing
AINU.Is_Thread (E) and then
-- 2/ Property requirements
-- The thread a) has dispatch protocol specified, b)
-- has compute_execution_time specified, if it is
-- either periodic or sporadic, then it has a period
(Get_Thread_Dispatch_Protocol (E) /= Thread_None) and then
(Get_Execution_Time (E) /= Empty_Time_Array) and then
(if Get_Thread_Dispatch_Protocol (E) = Thread_Periodic or else
Get_Thread_Dispatch_Protocol (E) = Thread_Sporadic then
Get_Thread_Period (E) /= Null_Time) and then
-- 3/ Architecture requirements
-- a) There is a linked processor P for E
(for some P of Processors (Get_Root_Component (E)) =>
AINU.Is_Processor (P) and then
P = Get_Bound_Processor
(Corresponding_Instance
(Get_Container_Process (Parent_Subcomponent (E)))))
);
function Map_Data (E : Node_Id) return Node_Id with
Pre => (True and then
-- 1/ Typing
AINU.Is_Data (E) and then
-- 2/ Architecture requirements
-- a) There is a linked processor P for E
(for some P of Processors (Get_Root_Component (E)) =>
AINU.Is_Processor (P) and then
P = Get_Bound_Processor
(Corresponding_Instance
(Get_Container_Process (Parent_Subcomponent (E)))))
and then
-- b) There is at least one thread accessing the data
(for some T of Threads (Get_Root_Component (E)) =>
(for some C of Connections_Of
(Corresponding_Instance
(Get_Container_Process
(Parent_Subcomponent (E))))
=> T = Corresponding_Instance
(Item (AIN.First_Node
(Path (Destination (C)))))))
);
function Map_Buffer (E : Node_Id; P : Node_Id) return Node_Id with
Pre => (True and then
-- 1/ Typing
-- a) E is a thread
AINU.Is_Thread (E) and then
-- b) P is an in event (data) port of E
AINU.Is_Port (P) and then
Is_Event (P) and then
Is_In (P) and then
(for some F of Features_Of (E) => P = F) and then
-- 2/ Architecture requirements
-- a) There is a linked processor P for E
(for some CPU of Processors (Get_Root_Component (E)) =>
AINU.Is_Processor (CPU) and then