aboutsummaryrefslogtreecommitdiffstats
path: root/src/synth
diff options
context:
space:
mode:
authorTristan Gingold <tgingold@free.fr>2019-08-31 07:58:43 +0200
committerTristan Gingold <tgingold@free.fr>2019-08-31 07:58:43 +0200
commitbefcd7309285746fdb6c6af2424daf9329f682c1 (patch)
treee779224a6402082056ba5d4d63f87cc99f1ff142 /src/synth
parent6daefbc5e6ffc2da14cca618fd8207e04dff665b (diff)
downloadghdl-befcd7309285746fdb6c6af2424daf9329f682c1.tar.gz
ghdl-befcd7309285746fdb6c6af2424daf9329f682c1.tar.bz2
ghdl-befcd7309285746fdb6c6af2424daf9329f682c1.zip
synth: improve synth_uresize.
Diffstat (limited to 'src/synth')
-rw-r--r--src/synth/netlists-builders.adb23
-rw-r--r--src/synth/netlists-builders.ads4
-rw-r--r--src/synth/synth-expr.adb49
3 files changed, 50 insertions, 26 deletions
diff --git a/src/synth/netlists-builders.adb b/src/synth/netlists-builders.adb
index 3f79bbc9e..70a8b37a4 100644
--- a/src/synth/netlists-builders.adb
+++ b/src/synth/netlists-builders.adb
@@ -584,7 +584,7 @@ package body Netlists.Builders is
Val : Uns32;
W : Width) return Net
is
- pragma Assert (W > 0 and W <= 32);
+ pragma Assert (W > 0);
Inst : Instance;
O : Net;
begin
@@ -640,6 +640,27 @@ package body Netlists.Builders is
return Inst;
end Build_Const_Log;
+ function Build2_Const_Uns (Ctxt : Context_Acc; Val : Uns64; W : Width)
+ return Net is
+ begin
+ if Val < 2**32 then
+ return Build_Const_UB32 (Ctxt, Uns32 (Val), W);
+ else
+ pragma Assert (W > 32);
+ declare
+ Inst : Instance;
+ begin
+ Inst := Build_Const_Bit (Ctxt, W);
+ Set_Param_Uns32 (Inst, 0, Uns32 (Val and 16#ffff_ffff#));
+ Set_Param_Uns32 (Inst, 1, Uns32 (Shift_Right (Val, 32)));
+ for I in 2 .. (W + 31) / 32 loop
+ Set_Param_Uns32 (Inst, Param_Idx (I), 0);
+ end loop;
+ return Get_Output (Inst, 0);
+ end;
+ end if;
+ end Build2_Const_Uns;
+
function Build_Edge (Ctxt : Context_Acc; Src : Net) return Net
is
pragma Assert (Get_Width (Src) = 1);
diff --git a/src/synth/netlists-builders.ads b/src/synth/netlists-builders.ads
index 8aa4501c0..82f05962d 100644
--- a/src/synth/netlists-builders.ads
+++ b/src/synth/netlists-builders.ads
@@ -60,6 +60,10 @@ package Netlists.Builders is
Xz : Uns32;
W : Width) return Net;
+ -- Build a const from VAL. Result is either a Const_UB32 or a Const_Bit.
+ function Build2_Const_Uns (Ctxt : Context_Acc; Val : Uns64; W : Width)
+ return Net;
+
-- Large constants.
-- Bit means only 0 or 1.
-- Log means 0/1/Z/X. Parameters 2N are aval, 2N+1 are bval.
diff --git a/src/synth/synth-expr.adb b/src/synth/synth-expr.adb
index 4d443d999..d99e1acc1 100644
--- a/src/synth/synth-expr.adb
+++ b/src/synth/synth-expr.adb
@@ -163,8 +163,9 @@ package body Synth.Expr is
end case;
end Bit_Extract;
- function Synth_Uresize (N : Net; W : Width) return Net
+ function Synth_Uresize (N : Net; W : Width; Loc : Node) return Net
is
+ pragma Unreferenced (Loc);
Wn : constant Width := Get_Width (N);
begin
if Wn > W then
@@ -176,17 +177,21 @@ package body Synth.Expr is
end if;
end Synth_Uresize;
- function Synth_Uresize (Val : Value_Acc; Vtype : Node; W : Width)
- return Net is
+ function Synth_Uresize (Val : Value_Acc; W : Width; Loc : Node) return Net
+ is
+ Res : Net;
begin
- if Is_Const (Val)
- and then (Get_Kind (Get_Base_Type (Vtype))
- = Iir_Kind_Integer_Type_Definition)
- then
- return Build_Const_UB32
- (Build_Context, Uns32 (Val.Scal), W);
+ if Is_Const (Val) and then Val.Typ.Kind = Type_Discrete then
+ if Val.Typ.Drange.Is_Signed then
+ -- TODO.
+ raise Internal_Error;
+ else
+ Res := Build2_Const_Uns (Build_Context, To_Uns64 (Val.Scal), W);
+ end if;
+ Set_Location (Res, Loc);
+ return Res;
end if;
- return Synth_Uresize (Get_Net (Val), W);
+ return Synth_Uresize (Get_Net (Val), W, Loc);
end Synth_Uresize;
-- Resize for a discrete value.
@@ -930,8 +935,7 @@ package body Synth.Expr is
is
N : Net;
begin
- N := Synth_Uresize (Right, Right_Type, Get_Width (Left));
- Set_Location (N, Expr);
+ N := Synth_Uresize (Right, Get_Width (Left), Expr);
N := Build_Compare (Build_Context, Id, Get_Net (Left), N);
Set_Location (N, Expr);
return Create_Value_Net (N, Boolean_Type);
@@ -973,10 +977,8 @@ package body Synth.Expr is
else
Rtype := Left.Typ;
end if;
- L1 := Synth_Uresize (L, W);
- Set_Location (L1, Expr);
- R1 := Synth_Uresize (R, W);
- Set_Location (R1, Expr);
+ L1 := Synth_Uresize (L, W, Expr);
+ R1 := Synth_Uresize (R, W, Expr);
N := Build_Dyadic (Build_Context, Id, L1, R1);
Set_Location (N, Expr);
return Create_Value_Net (N, Rtype);
@@ -991,10 +993,8 @@ package body Synth.Expr is
L1, R1 : Net;
N : Net;
begin
- L1 := Synth_Uresize (L, W);
- Set_Location (L1, Expr);
- R1 := Synth_Uresize (R, W);
- Set_Location (R1, Expr);
+ L1 := Synth_Uresize (L, W, Expr);
+ R1 := Synth_Uresize (R, W, Expr);
N := Build_Compare (Build_Context, Id, L1, R1);
Set_Location (N, Expr);
return Create_Value_Net (N, Boolean_Type);
@@ -1006,8 +1006,7 @@ package body Synth.Expr is
R1 : Net;
N : Net;
begin
- R1 := Synth_Uresize (Right, Right_Type, Get_Width (Left));
- Set_Location (R1, Expr);
+ R1 := Synth_Uresize (Right, Get_Width (Left), Expr);
N := Build_Dyadic (Build_Context, Id, L, R1);
Set_Location (N, Expr);
return Create_Value_Net (N, Create_Res_Bound (Left, L));
@@ -2127,7 +2126,7 @@ package body Synth.Expr is
else
Arg_Net := Get_Net (Arg);
return Create_Value_Net
- (Synth_Uresize (Arg_Net, Uns32 (Size.Scal)),
+ (Synth_Uresize (Arg_Net, Uns32 (Size.Scal), Expr),
Create_Res_Bound (Arg, Arg_Net));
end if;
end if;
@@ -2141,7 +2140,7 @@ package body Synth.Expr is
begin
return Create_Value_Net
(Synth_Uresize (Get_Net (Subprg_Inst.Objects (1)),
- Nat_Type.Drange.W),
+ Nat_Type.Drange.W, Expr),
Nat_Type);
end;
when Iir_Predefined_Ieee_Numeric_Std_Resize_Uns_Nat =>
@@ -2156,7 +2155,7 @@ package body Synth.Expr is
end if;
W := Uns32 (Sz.Scal);
return Create_Value_Net
- (Synth_Uresize (Get_Net (V), W),
+ (Synth_Uresize (Get_Net (V), W, Expr),
Create_Vec_Type_By_Length (W, Logic_Type));
end;
when Iir_Predefined_Ieee_Math_Real_Log2 =>