aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
Diffstat (limited to 'src')
-rw-r--r--src/synth/elab-vhdl_types.adb10
-rw-r--r--src/synth/elab-vhdl_values.adb4
-rw-r--r--src/synth/synth-vhdl_expr.adb39
-rw-r--r--src/synth/synth-vhdl_expr.ads3
-rw-r--r--src/synth/synth-vhdl_insts.adb5
-rw-r--r--src/synth/synth-vhdl_oper.adb60
-rw-r--r--src/synth/synth-vhdl_stmts.adb7
-rw-r--r--src/vhdl/vhdl-annotations.adb23
8 files changed, 100 insertions, 51 deletions
diff --git a/src/synth/elab-vhdl_types.adb b/src/synth/elab-vhdl_types.adb
index 7d726d154..54bd3469b 100644
--- a/src/synth/elab-vhdl_types.adb
+++ b/src/synth/elab-vhdl_types.adb
@@ -198,6 +198,8 @@ package body Elab.Vhdl_Types is
function Synth_Record_Type_Definition
(Syn_Inst : Synth_Instance_Acc; Def : Node) return Type_Acc
is
+ Is_Subtype : constant Boolean :=
+ Get_Kind (Def) = Iir_Kind_Record_Subtype_Definition;
El_List : constant Node_Flist := Get_Elements_Declaration_List (Def);
Rec_Els : Rec_El_Array_Acc;
El : Node;
@@ -210,7 +212,13 @@ package body Elab.Vhdl_Types is
for I in Flist_First .. Flist_Last (El_List) loop
El := Get_Nth_Element (El_List, I);
El_Type := Get_Type (El);
- El_Typ := Synth_Subtype_Indication_If_Anonymous (Syn_Inst, El_Type);
+ if Is_Subtype then
+ Synth_Subtype_Indication_If_Anonymous (Syn_Inst, El_Type);
+ El_Typ := Get_Subtype_Object (Syn_Inst, El_Type);
+ else
+ El_Typ := Synth_Subtype_Indication_If_Anonymous
+ (Syn_Inst, El_Type);
+ end if;
Rec_Els.E (Iir_Index32 (I + 1)).Typ := El_Typ;
end loop;
diff --git a/src/synth/elab-vhdl_values.adb b/src/synth/elab-vhdl_values.adb
index 90e72f223..017edc700 100644
--- a/src/synth/elab-vhdl_values.adb
+++ b/src/synth/elab-vhdl_values.adb
@@ -246,9 +246,9 @@ package body Elab.Vhdl_Values is
Res.Val.Mem (I - 1) := Src.Val.Mem (I - 1);
end loop;
when Value_Net =>
- Res := (Src.Typ, Create_Value_Net (Src.Val.S));
+ Res := (Src.Typ, Create_Value_Net (Src.Val.N));
when Value_Wire =>
- Res := (Src.Typ, Create_Value_Wire (Src.Val.S));
+ Res := (Src.Typ, Create_Value_Wire (Src.Val.N));
when Value_File =>
Res := Create_Value_File (Src.Typ, Src.Val.File);
when Value_Signal =>
diff --git a/src/synth/synth-vhdl_expr.adb b/src/synth/synth-vhdl_expr.adb
index ee691d8f5..c7eb117b6 100644
--- a/src/synth/synth-vhdl_expr.adb
+++ b/src/synth/synth-vhdl_expr.adb
@@ -893,6 +893,12 @@ package body Synth.Vhdl_Expr is
end case;
end Synth_Name;
+ procedure Bound_Error (Syn_Inst : Synth_Instance_Acc; Loc : Node) is
+ begin
+ Error_Msg_Synth (+Loc, "index not within bounds");
+ Elab.Debugger.Debug_Error (Syn_Inst, Loc);
+ end Bound_Error;
+
-- Convert index IDX in PFX to an offset.
-- SYN_INST and LOC are used in case of error.
function Index_To_Offset
@@ -902,8 +908,7 @@ package body Synth.Vhdl_Expr is
Res : Value_Offsets;
begin
if not In_Bounds (Bnd, Int32 (Idx)) then
- Error_Msg_Synth (+Loc, "index not within bounds");
- Elab.Debugger.Debug_Error (Syn_Inst, Loc);
+ Bound_Error (Syn_Inst, Loc);
return (0, 0);
end if;
@@ -1000,13 +1005,15 @@ package body Synth.Vhdl_Expr is
Name : Node;
Pfx_Type : Type_Acc;
Voff : out Net;
- Off : out Value_Offsets)
+ Off : out Value_Offsets;
+ Error : out Boolean)
is
Ctxt : constant Context_Acc := Get_Build (Syn_Inst);
Indexes : constant Iir_Flist := Get_Index_List (Name);
El_Typ : constant Type_Acc := Get_Array_Element (Pfx_Type);
Idx_Expr : Node;
Idx_Val : Valtyp;
+ Idx : Int64;
Bnd : Bound_Type;
Stride : Uns32;
Ivoff : Net;
@@ -1014,6 +1021,7 @@ package body Synth.Vhdl_Expr is
begin
Voff := No_Net;
Off := (0, 0);
+ Error := False;
Stride := 1;
for I in reverse Flist_First .. Flist_Last (Indexes) loop
@@ -1022,9 +1030,8 @@ package body Synth.Vhdl_Expr is
-- Use the base type as the subtype of the index is not synth-ed.
Idx_Val := Synth_Expression_With_Basetype (Syn_Inst, Idx_Expr);
if Idx_Val = No_Valtyp then
- -- Propagate errorc
- Voff := No_Net;
- Off := (0, 0);
+ -- Propagate error.
+ Error := True;
return;
end if;
@@ -1033,11 +1040,17 @@ package body Synth.Vhdl_Expr is
Bnd := Get_Array_Bound (Pfx_Type, Dim_Type (I + 1));
if Is_Static_Val (Idx_Val.Val) then
- Idx_Off := Index_To_Offset (Syn_Inst, Bnd,
- Get_Static_Discrete (Idx_Val), Name);
- Off.Net_Off := Off.Net_Off + Idx_Off.Net_Off * Stride * El_Typ.W;
- Off.Mem_Off := Off.Mem_Off
- + Idx_Off.Mem_Off * Size_Type (Stride) * El_Typ.Sz;
+ Idx := Get_Static_Discrete (Idx_Val);
+ if not In_Bounds (Bnd, Int32 (Idx)) then
+ Bound_Error (Syn_Inst, Name);
+ Error := True;
+ else
+ Idx_Off := Index_To_Offset (Syn_Inst, Bnd, Idx, Name);
+ Off.Net_Off := Off.Net_Off
+ + Idx_Off.Net_Off * Stride * El_Typ.W;
+ Off.Mem_Off := Off.Mem_Off
+ + Idx_Off.Mem_Off * Size_Type (Stride) * El_Typ.Sz;
+ end if;
else
Ivoff := Dyn_Index_To_Offset (Ctxt, Bnd, Idx_Val, Name);
Ivoff := Build_Memidx
@@ -2202,6 +2215,10 @@ package body Synth.Vhdl_Expr is
Dyn : Dyn_Name;
begin
Synth_Assignment_Prefix (Syn_Inst, Expr, Base, Typ, Off, Dyn);
+ if Base = No_Valtyp then
+ -- Propagate error.
+ return No_Valtyp;
+ end if;
if Dyn.Voff = No_Net and then Is_Static (Base.Val) then
Res := Create_Value_Memory (Typ);
Copy_Memory
diff --git a/src/synth/synth-vhdl_expr.ads b/src/synth/synth-vhdl_expr.ads
index 7081aef95..33b908de3 100644
--- a/src/synth/synth-vhdl_expr.ads
+++ b/src/synth/synth-vhdl_expr.ads
@@ -119,7 +119,8 @@ package Synth.Vhdl_Expr is
Name : Node;
Pfx_Type : Type_Acc;
Voff : out Net;
- Off : out Value_Offsets);
+ Off : out Value_Offsets;
+ Error : out Boolean);
-- Conversion to logic vector.
type Digit_Index is new Natural;
diff --git a/src/synth/synth-vhdl_insts.adb b/src/synth/synth-vhdl_insts.adb
index b02d2df69..cd6f55e2a 100644
--- a/src/synth/synth-vhdl_insts.adb
+++ b/src/synth/synth-vhdl_insts.adb
@@ -638,11 +638,12 @@ package body Synth.Vhdl_Insts is
declare
Voff : Net;
Arr_Off : Value_Offsets;
+ Err : Boolean;
begin
Synth_Individual_Prefix
(Syn_Inst, Inter_Inst, Get_Prefix (Formal), Off, Typ);
- Synth_Indexed_Name (Syn_Inst, Formal, Typ, Voff, Arr_Off);
- if Voff /= No_Net then
+ Synth_Indexed_Name (Syn_Inst, Formal, Typ, Voff, Arr_Off, Err);
+ if Voff /= No_Net or Err then
raise Internal_Error;
end if;
Off := Off + Arr_Off.Net_Off;
diff --git a/src/synth/synth-vhdl_oper.adb b/src/synth/synth-vhdl_oper.adb
index e6221075d..b423bd149 100644
--- a/src/synth/synth-vhdl_oper.adb
+++ b/src/synth/synth-vhdl_oper.adb
@@ -1743,7 +1743,8 @@ package body Synth.Vhdl_Oper is
return Create_Value_Net (Get_Net (Ctxt, Operand),
Create_Res_Bound (Operand));
- when Iir_Predefined_Ieee_1164_Condition_Operator =>
+ when Iir_Predefined_Ieee_1164_Condition_Operator
+ | Iir_Predefined_Bit_Condition =>
return Create_Value_Net
(Get_Net (Ctxt, Operand),
Get_Subtype_Object (Syn_Inst, Get_Type (Imp)));
@@ -1846,6 +1847,21 @@ package body Synth.Vhdl_Oper is
Res_Typ, False, Expr);
end Synth_Find_Bit;
+ -- Resize ARG to SIZE bits according to IS_SIGNED.
+ function Synth_Resize (Ctxt : Context_Acc;
+ Arg : Valtyp;
+ Size : Width;
+ Is_Signed : Boolean;
+ Loc : Node) return Valtyp
+ is
+ N : Net;
+ begin
+ N := Get_Net (Ctxt, Arg);
+ N := Build2_Resize (Ctxt, N, Size, Is_Signed, Get_Location (Loc));
+ return Create_Value_Net
+ (N, Create_Vec_Type_By_Length (Size, Logic_Type));
+ end Synth_Resize;
+
function Synth_Dynamic_Predefined_Function_Call
(Subprg_Inst : Synth_Instance_Acc; Expr : Node) return Valtyp
is
@@ -1865,7 +1881,6 @@ package body Synth.Vhdl_Oper is
Arg : constant Valtyp := Get_Value (Subprg_Inst, Param1);
Size_Vt : Valtyp;
Size : Width;
- Arg_Net : Net;
begin
Size_Vt := Get_Value (Subprg_Inst, Param2);
Strip_Const (Size_Vt);
@@ -1874,11 +1889,7 @@ package body Synth.Vhdl_Oper is
return No_Valtyp;
end if;
Size := Uns32 (Read_Discrete (Size_Vt));
- Arg_Net := Get_Net (Ctxt, Arg);
- Arg_Net := Build2_Resize (Ctxt, Arg_Net, Size, Is_Signed,
- Get_Location (Expr));
- return Create_Value_Net
- (Arg_Net, Create_Vec_Type_By_Length (Size, Logic_Type));
+ return Synth_Resize (Ctxt, Arg, Size, Is_Signed, Expr);
end Synth_Conv_Vector;
L : Valtyp;
@@ -1941,6 +1952,12 @@ package body Synth.Vhdl_Oper is
when Iir_Predefined_Ieee_Numeric_Std_Touns_Nat_Nat_Uns
| Iir_Predefined_Ieee_Std_Logic_Arith_Conv_Unsigned_Int =>
return Synth_Conv_Vector (False);
+ when Iir_Predefined_Ieee_Numeric_Std_Touns_Nat_Uns_Uns =>
+ declare
+ B : constant Bound_Type := Get_Array_Bound (R.Typ, 1);
+ begin
+ return Synth_Resize (Ctxt, L, B.Len, False, Expr);
+ end;
when Iir_Predefined_Ieee_Numeric_Std_Tosgn_Int_Nat_Sgn
| Iir_Predefined_Ieee_Std_Logic_Arith_Conv_Vector_Int =>
return Synth_Conv_Vector (True);
@@ -1992,30 +2009,17 @@ package body Synth.Vhdl_Oper is
| Iir_Predefined_Ieee_Std_Logic_Arith_Conv_Vector_Sgn
| Iir_Predefined_Ieee_Std_Logic_Arith_Conv_Unsigned_Sgn
| Iir_Predefined_Ieee_Std_Logic_Arith_Sxt =>
- declare
- W : Width;
- begin
- if not Is_Static (R.Val) then
- Error_Msg_Synth (+Expr, "size must be constant");
- return No_Valtyp;
- end if;
- W := Uns32 (Read_Discrete (R));
- return Create_Value_Net
- (Build2_Sresize (Ctxt, Get_Net (Ctxt, L),
- W, Get_Location (Expr)),
- Create_Vec_Type_By_Length (W, Logic_Type));
- end;
+ if not Is_Static (R.Val) then
+ Error_Msg_Synth (+Expr, "size must be constant");
+ return No_Valtyp;
+ end if;
+ return Synth_Resize
+ (Ctxt, L, Uns32 (Read_Discrete (R)), True, Expr);
when Iir_Predefined_Ieee_Numeric_Std_Resize_Sgn_Sgn =>
declare
- B : Bound_Type;
- W : Width;
+ B : constant Bound_Type := Get_Array_Bound (R.Typ, 1);
begin
- B := Get_Array_Bound (R.Typ, 1);
- W := B.Len;
- return Create_Value_Net
- (Build2_Sresize (Ctxt, Get_Net (Ctxt, L),
- W, Get_Location (Expr)),
- Create_Vec_Type_By_Length (W, Logic_Type));
+ return Synth_Resize (Ctxt, L, B.Len, True, Expr);
end;
when Iir_Predefined_Ieee_Numeric_Std_Shf_Left_Uns_Nat
| Iir_Predefined_Ieee_Numeric_Std_Shf_Left_Sgn_Nat
diff --git a/src/synth/synth-vhdl_stmts.adb b/src/synth/synth-vhdl_stmts.adb
index df8a851ce..3d8c7bba2 100644
--- a/src/synth/synth-vhdl_stmts.adb
+++ b/src/synth/synth-vhdl_stmts.adb
@@ -144,14 +144,17 @@ package body Synth.Vhdl_Stmts is
declare
Voff : Net;
Off : Value_Offsets;
+ Err : Boolean;
begin
Synth_Assignment_Prefix
(Syn_Inst, Get_Prefix (Pfx),
Dest_Base, Dest_Typ, Dest_Off, Dest_Dyn);
Strip_Const (Dest_Base);
- Synth_Indexed_Name (Syn_Inst, Pfx, Dest_Typ, Voff, Off);
+ Synth_Indexed_Name (Syn_Inst, Pfx, Dest_Typ, Voff, Off, Err);
- if Voff = No_Net then
+ if Err then
+ Dest_Base := No_Valtyp;
+ elsif Voff = No_Net then
-- Static index.
Dest_Off := Dest_Off + Off;
else
diff --git a/src/vhdl/vhdl-annotations.adb b/src/vhdl/vhdl-annotations.adb
index 630f3ef84..9fc9788bf 100644
--- a/src/vhdl/vhdl-annotations.adb
+++ b/src/vhdl/vhdl-annotations.adb
@@ -340,8 +340,8 @@ package body Vhdl.Annotations is
then
-- This subtype has created a new anonymous subtype for the
-- element.
- Annotate_Type_Definition
- (Block_Info, Get_Element_Subtype (Def));
+ El := Get_Element_Subtype (Def);
+ Annotate_Type_Definition (Block_Info, El);
end if;
if Flag_Synthesis then
-- For the bounds.
@@ -378,8 +378,23 @@ package body Vhdl.Annotations is
when Iir_Kind_Record_Subtype_Definition =>
if Flag_Synthesis then
- -- For the offsets.
- Create_Object_Info (Block_Info, Def, Kind_Type);
+ declare
+ List : constant Iir_Flist :=
+ Get_Elements_Declaration_List (Def);
+ El : Iir;
+ El_Type : Iir;
+ begin
+ for I in Flist_First .. Flist_Last (List) loop
+ El := Get_Nth_Element (List, I);
+ if Get_Subtype_Indication (El) /= Null_Iir then
+ El_Type := Get_Type (El);
+ Annotate_Anonymous_Type_Definition
+ (Block_Info, El_Type);
+ end if;
+ end loop;
+ -- For the offsets.
+ Create_Object_Info (Block_Info, Def, Kind_Type);
+ end;
end if;
when Iir_Kind_Access_Type_Definition =>