aboutsummaryrefslogtreecommitdiffstats
path: root/src
diff options
context:
space:
mode:
authorTristan Gingold <tgingold@free.fr>2019-08-13 23:09:04 +0200
committerTristan Gingold <tgingold@free.fr>2019-08-13 23:09:04 +0200
commit3f3974481acdbaa36a607b9178f2ae751748020e (patch)
tree38a69c207ee47deaf51cf971e7296ce5f4097bdf /src
parentde92555dc278dbb5799aaa386e1bd9b980ce0cbc (diff)
downloadghdl-3f3974481acdbaa36a607b9178f2ae751748020e.tar.gz
ghdl-3f3974481acdbaa36a607b9178f2ae751748020e.tar.bz2
ghdl-3f3974481acdbaa36a607b9178f2ae751748020e.zip
synth: also extract edge in PSL expressions.
Diffstat (limited to 'src')
-rw-r--r--src/synth/synth-expr.adb24
-rw-r--r--src/synth/synth-expr.ads6
-rw-r--r--src/synth/synth-stmts.adb24
3 files changed, 36 insertions, 18 deletions
diff --git a/src/synth/synth-expr.adb b/src/synth/synth-expr.adb
index dab693362..592f25297 100644
--- a/src/synth/synth-expr.adb
+++ b/src/synth/synth-expr.adb
@@ -1728,29 +1728,24 @@ package body Synth.Expr is
-- Try to match: clk'event and clk = X
-- or: clk = X and clk'event
-- where X is '0' or '1'.
- function Synth_Clock_Edge (Syn_Inst : Synth_Instance_Acc; Expr : Node)
- return Value_Acc
+ function Synth_Clock_Edge
+ (Syn_Inst : Synth_Instance_Acc; Left, Right : Node) return Net
is
- pragma Assert (Get_Kind (Expr) = Iir_Kind_And_Operator);
- Left : constant Node := Get_Left (Expr);
- Right : constant Node := Get_Right (Expr);
Prefix : Node;
begin
-- Try with left.
Prefix := Extract_Event_Expr_Prefix (Left);
if Is_Valid (Prefix) then
- return Create_Value_Net
- (Extract_Clock_Level (Syn_Inst, Right, Prefix), Boolean_Type);
+ return Extract_Clock_Level (Syn_Inst, Right, Prefix);
end if;
-- Try with right.
Prefix := Extract_Event_Expr_Prefix (Right);
if Is_Valid (Prefix) then
- return Create_Value_Net
- (Extract_Clock_Level (Syn_Inst, Left, Prefix), Boolean_Type);
+ return Extract_Clock_Level (Syn_Inst, Left, Prefix);
end if;
- return null;
+ return No_Net;
end Synth_Clock_Edge;
function Synth_Type_Conversion (Syn_Inst : Synth_Instance_Acc; Conv : Node)
@@ -2038,13 +2033,14 @@ package body Synth.Expr is
Imp : constant Node := Get_Implementation (Expr);
Def : constant Iir_Predefined_Functions :=
Get_Implicit_Definition (Imp);
- Edge : Value_Acc;
+ Edge : Net;
begin
-- Match clock-edge
if Def = Iir_Predefined_Boolean_And then
- Edge := Synth_Clock_Edge (Syn_Inst, Expr);
- if Edge /= null then
- return Edge;
+ Edge := Synth_Clock_Edge (Syn_Inst,
+ Get_Left (Expr), Get_Right (Expr));
+ if Edge /= No_Net then
+ return Create_Value_Net (Edge, Boolean_Type);
end if;
end if;
diff --git a/src/synth/synth-expr.ads b/src/synth/synth-expr.ads
index be6daba0d..06b824fe2 100644
--- a/src/synth/synth-expr.ads
+++ b/src/synth/synth-expr.ads
@@ -42,6 +42,12 @@ package Synth.Expr is
procedure To_Logic
(Enum : Int64; Etype : Type_Acc; Val : out Uns32; Zx : out Uns32);
+ -- Try to match: clk'event and clk = X
+ -- or: clk = X and clk'event
+ -- where X is '0' or '1'.
+ function Synth_Clock_Edge
+ (Syn_Inst : Synth_Instance_Acc; Left, Right : Node) return Net;
+
function Bit_Extract (Val : Value_Acc; Off : Uns32; Loc : Node)
return Value_Acc;
diff --git a/src/synth/synth-stmts.adb b/src/synth/synth-stmts.adb
index 7c0039a8c..af833d634 100644
--- a/src/synth/synth-stmts.adb
+++ b/src/synth/synth-stmts.adb
@@ -1242,6 +1242,7 @@ package body Synth.Stmts is
function Synth_PSL_Expression
(Syn_Inst : Synth_Instance_Acc; Expr : PSL.Types.PSL_Node) return Net
is
+ use PSL.Types;
use PSL.Nodes;
begin
case Get_Kind (Expr) is
@@ -1256,10 +1257,25 @@ package body Synth.Stmts is
(Build_Context, Netlists.Gates.Id_Not,
Synth_PSL_Expression (Syn_Inst, Get_Boolean (Expr)));
when N_And_Bool =>
- return Build_Dyadic
- (Build_Context, Netlists.Gates.Id_And,
- Synth_PSL_Expression (Syn_Inst, Get_Left (Expr)),
- Synth_PSL_Expression (Syn_Inst, Get_Right (Expr)));
+ declare
+ L : constant PSL_Node := Get_Left (Expr);
+ R : constant PSL_Node := Get_Right (Expr);
+ Edge : Net;
+ begin
+ -- Handle edge (as it can be in default clock).
+ if Get_Kind (L) = N_HDL_Expr and then Get_Kind (R) = N_HDL_Expr
+ then
+ Edge := Synth_Clock_Edge
+ (Syn_Inst, Get_HDL_Node (L), Get_HDL_Node (R));
+ if Edge /= No_Net then
+ return Edge;
+ end if;
+ end if;
+ return Build_Dyadic
+ (Build_Context, Netlists.Gates.Id_And,
+ Synth_PSL_Expression (Syn_Inst, L),
+ Synth_PSL_Expression (Syn_Inst, R));
+ end;
when N_Or_Bool =>
return Build_Dyadic
(Build_Context, Netlists.Gates.Id_Or,