mirror of
https://github.com/myhdl/myhdl.git
synced 2025-01-24 21:52:56 +08:00
manual update
This commit is contained in:
parent
5e1045ef9b
commit
62675e6a80
@ -94,156 +94,34 @@ A hierarchical design
|
|||||||
The converter can handle designs with an arbitrarily deep hierarchy.
|
The converter can handle designs with an arbitrarily deep hierarchy.
|
||||||
|
|
||||||
For example, suppose we want to design an incrementer with Gray code output.
|
For example, suppose we want to design an incrementer with Gray code output.
|
||||||
Using the designs from previous sections, we can proceed as follows::
|
Using the designs from previous sections, we can proceed as follows:
|
||||||
|
|
||||||
def GrayInc(graycnt, enable, clock, reset, width):
|
.. include-example:: gray_inc.py
|
||||||
|
|
||||||
bincnt = Signal(intbv(0)[width:])
|
|
||||||
|
|
||||||
inc_1 = inc(bincnt, enable, clock, reset, n=2**width)
|
|
||||||
bin2gray_1 = bin2gray(B=bincnt, G=graycnt, width=width)
|
|
||||||
|
|
||||||
return inc_1, bin2gray_1
|
|
||||||
|
|
||||||
According to Gray code properties, only a single bit will change in consecutive
|
According to Gray code properties, only a single bit will change in consecutive
|
||||||
values. However, as the ``bin2gray`` module is combinatorial, the output bits
|
values. However, as the ``bin2gray`` module is combinatorial, the output bits
|
||||||
may have transient glitches, which may not be desirable. To solve this, let's
|
may have transient glitches, which may not be desirable. To solve this, let's
|
||||||
create an additional level of hierarchy and add an output register to the
|
create an additional level of hierarchy and add an output register to the
|
||||||
design. (This will create an additional latency of a clock cycle, which may not
|
design. (This will create an additional latency of a clock cycle, which may not
|
||||||
be acceptable, but we will ignore that here.) ::
|
be acceptable, but we will ignore that here.)
|
||||||
|
|
||||||
def GrayIncReg(graycnt, enable, clock, reset, width):
|
.. include-example:: gray_inc_reg.py
|
||||||
|
|
||||||
graycnt_comb = Signal(intbv(0)[width:])
|
We can convert this hierarchical design as follows:
|
||||||
gray_inc_1 = GrayInc(graycnt_comb, enable, clock, reset, width)
|
|
||||||
|
|
||||||
@always(clock.posedge)
|
.. include-example:: convert_gray_inc_reg.py
|
||||||
def reg_1():
|
|
||||||
graycnt.next = graycnt_comb
|
|
||||||
|
|
||||||
return gray_inc_1, reg_1
|
|
||||||
|
|
||||||
We can convert this hierarchical design as before::
|
|
||||||
|
|
||||||
width = 8
|
|
||||||
graycnt = Signal(modbv(0)[width:])
|
|
||||||
enable = Signal(bool())
|
|
||||||
clock = Signal(bool())
|
|
||||||
reset = ResetSignal(0, active=0, async=True)
|
|
||||||
|
|
||||||
toVerilog(GrayIncReg, graycnt, enable, clock, reset, width)
|
|
||||||
toVHDL(GrayIncReg, graycnt, enable, clock, reset, width)
|
|
||||||
|
|
||||||
|
|
||||||
The Verilog output code looks as follows::
|
|
||||||
|
|
||||||
module GrayIncReg (
|
|
||||||
graycnt,
|
|
||||||
enable,
|
|
||||||
clock,
|
|
||||||
reset
|
|
||||||
);
|
|
||||||
|
|
||||||
output [7:0] graycnt;
|
|
||||||
reg [7:0] graycnt;
|
|
||||||
input enable;
|
|
||||||
input clock;
|
|
||||||
input reset;
|
|
||||||
|
|
||||||
reg [7:0] graycnt_comb;
|
|
||||||
reg [7:0] gray_inc_1_bincnt;
|
|
||||||
|
|
||||||
always @(posedge clock, negedge reset) begin: GRAYINCREG_GRAY_INC_1_INC_1_INCLOGIC
|
|
||||||
if (reset == 0) begin
|
|
||||||
gray_inc_1_bincnt <= 0;
|
|
||||||
end
|
|
||||||
else begin
|
|
||||||
if (enable) begin
|
|
||||||
gray_inc_1_bincnt <= (gray_inc_1_bincnt + 1);
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
always @(gray_inc_1_bincnt) begin: GRAYINCREG_GRAY_INC_1_BIN2GRAY_1_LOGIC
|
|
||||||
integer i;
|
|
||||||
reg [9-1:0] Bext;
|
|
||||||
Bext = 9'h0;
|
|
||||||
Bext = gray_inc_1_bincnt;
|
|
||||||
for (i=0; i<8; i=i+1) begin
|
|
||||||
graycnt_comb[i] = (Bext[(i + 1)] ^ Bext[i]);
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
always @(posedge clock) begin: GRAYINCREG_REG_1
|
|
||||||
graycnt <= graycnt_comb;
|
|
||||||
end
|
|
||||||
|
|
||||||
endmodule
|
|
||||||
|
|
||||||
The VHDL output code looks as follows::
|
|
||||||
|
|
||||||
library IEEE;
|
|
||||||
use IEEE.std_logic_1164.all;
|
|
||||||
use IEEE.numeric_std.all;
|
|
||||||
use work.pck_myhdl_08.all;
|
|
||||||
|
|
||||||
entity GrayIncReg is
|
|
||||||
port (
|
|
||||||
graycnt: out unsigned(7 downto 0);
|
|
||||||
enable: in std_logic;
|
|
||||||
clock: in std_logic;
|
|
||||||
reset: in std_logic
|
|
||||||
);
|
|
||||||
end entity GrayIncReg;
|
|
||||||
|
|
||||||
|
|
||||||
architecture MyHDL of GrayIncReg is
|
|
||||||
|
|
||||||
signal graycnt_comb: unsigned(7 downto 0);
|
|
||||||
signal gray_inc_1_bincnt: unsigned(7 downto 0);
|
|
||||||
|
|
||||||
begin
|
|
||||||
|
|
||||||
GRAYINCREG_GRAY_INC_1_INC_1_INCLOGIC: process (clock, reset) is
|
|
||||||
begin
|
|
||||||
if (reset = '0') then
|
|
||||||
gray_inc_1_bincnt <= (others => '0');
|
|
||||||
elsif rising_edge(clock) then
|
|
||||||
if bool(enable) then
|
|
||||||
gray_inc_1_bincnt <= (gray_inc_1_bincnt + 1);
|
|
||||||
end if;
|
|
||||||
end if;
|
|
||||||
end process GRAYINCREG_GRAY_INC_1_INC_1_INCLOGIC;
|
|
||||||
|
|
||||||
|
|
||||||
GRAYINCREG_GRAY_INC_1_BIN2GRAY_1_LOGIC: process (gray_inc_1_bincnt) is
|
|
||||||
variable Bext: unsigned(8 downto 0);
|
|
||||||
begin
|
|
||||||
Bext := to_unsigned(0, 9);
|
|
||||||
Bext := resize(gray_inc_1_bincnt, 9);
|
|
||||||
for i in 0 to 8-1 loop
|
|
||||||
graycnt_comb(i) <= (Bext((i + 1)) xor Bext(i));
|
|
||||||
end loop;
|
|
||||||
end process GRAYINCREG_GRAY_INC_1_BIN2GRAY_1_LOGIC;
|
|
||||||
|
|
||||||
|
|
||||||
GRAYINCREG_REG_1: process (clock) is
|
|
||||||
begin
|
|
||||||
if rising_edge(clock) then
|
|
||||||
graycnt <= graycnt_comb;
|
|
||||||
end if;
|
|
||||||
end process GRAYINCREG_REG_1;
|
|
||||||
|
|
||||||
end architecture MyHDL;
|
|
||||||
|
|
||||||
|
The Verilog output code looks as follows:
|
||||||
|
|
||||||
|
.. include-example:: gray_inc_reg.v
|
||||||
|
|
||||||
|
The VHDL output code looks as follows:
|
||||||
|
|
||||||
|
.. include-example:: gray_inc_reg.vhd
|
||||||
|
|
||||||
Note that the output is a flat "net list of blocks", and that hierarchical
|
Note that the output is a flat "net list of blocks", and that hierarchical
|
||||||
signal names are generated as necessary.
|
signal names are generated as necessary.
|
||||||
|
|
||||||
|
|
||||||
.. _conv-usage-fsm:
|
.. _conv-usage-fsm:
|
||||||
|
|
||||||
Optimizations for finite state machines
|
Optimizations for finite state machines
|
||||||
|
@ -1,56 +0,0 @@
|
|||||||
// File: GrayIncReg.v
|
|
||||||
// Generated by MyHDL 0.8dev
|
|
||||||
// Date: Fri Dec 21 15:02:38 2012
|
|
||||||
|
|
||||||
|
|
||||||
`timescale 1ns/10ps
|
|
||||||
|
|
||||||
module GrayIncReg (
|
|
||||||
graycnt,
|
|
||||||
enable,
|
|
||||||
clock,
|
|
||||||
reset
|
|
||||||
);
|
|
||||||
|
|
||||||
|
|
||||||
output [7:0] graycnt;
|
|
||||||
reg [7:0] graycnt;
|
|
||||||
input enable;
|
|
||||||
input clock;
|
|
||||||
input reset;
|
|
||||||
|
|
||||||
reg [7:0] graycnt_comb;
|
|
||||||
reg [7:0] gray_inc_1_bincnt;
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
always @(posedge clock, negedge reset) begin: GRAYINCREG_GRAY_INC_1_INC_1_INCLOGIC
|
|
||||||
if (reset == 0) begin
|
|
||||||
gray_inc_1_bincnt <= 0;
|
|
||||||
end
|
|
||||||
else begin
|
|
||||||
if (enable) begin
|
|
||||||
gray_inc_1_bincnt <= (gray_inc_1_bincnt + 1);
|
|
||||||
end
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
always @(gray_inc_1_bincnt) begin: GRAYINCREG_GRAY_INC_1_BIN2GRAY_1_LOGIC
|
|
||||||
integer i;
|
|
||||||
reg [9-1:0] Bext;
|
|
||||||
Bext = 9'h0;
|
|
||||||
Bext = gray_inc_1_bincnt;
|
|
||||||
for (i=0; i<8; i=i+1) begin
|
|
||||||
graycnt_comb[i] = (Bext[(i + 1)] ^ Bext[i]);
|
|
||||||
end
|
|
||||||
end
|
|
||||||
|
|
||||||
|
|
||||||
always @(posedge clock) begin: GRAYINCREG_REG_1
|
|
||||||
graycnt <= graycnt_comb;
|
|
||||||
end
|
|
||||||
|
|
||||||
endmodule
|
|
@ -1,63 +0,0 @@
|
|||||||
-- File: GrayIncReg.vhd
|
|
||||||
-- Generated by MyHDL 0.8dev
|
|
||||||
-- Date: Fri Dec 21 15:02:38 2012
|
|
||||||
|
|
||||||
|
|
||||||
library IEEE;
|
|
||||||
use IEEE.std_logic_1164.all;
|
|
||||||
use IEEE.numeric_std.all;
|
|
||||||
use std.textio.all;
|
|
||||||
|
|
||||||
use work.pck_myhdl_08.all;
|
|
||||||
|
|
||||||
entity GrayIncReg is
|
|
||||||
port (
|
|
||||||
graycnt: out unsigned(7 downto 0);
|
|
||||||
enable: in std_logic;
|
|
||||||
clock: in std_logic;
|
|
||||||
reset: in std_logic
|
|
||||||
);
|
|
||||||
end entity GrayIncReg;
|
|
||||||
|
|
||||||
|
|
||||||
architecture MyHDL of GrayIncReg is
|
|
||||||
|
|
||||||
signal graycnt_comb: unsigned(7 downto 0);
|
|
||||||
signal gray_inc_1_bincnt: unsigned(7 downto 0);
|
|
||||||
|
|
||||||
begin
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
GRAYINCREG_GRAY_INC_1_INC_1_INCLOGIC: process (clock, reset) is
|
|
||||||
begin
|
|
||||||
if (reset = '0') then
|
|
||||||
gray_inc_1_bincnt <= (others => '0');
|
|
||||||
elsif rising_edge(clock) then
|
|
||||||
if bool(enable) then
|
|
||||||
gray_inc_1_bincnt <= (gray_inc_1_bincnt + 1);
|
|
||||||
end if;
|
|
||||||
end if;
|
|
||||||
end process GRAYINCREG_GRAY_INC_1_INC_1_INCLOGIC;
|
|
||||||
|
|
||||||
|
|
||||||
GRAYINCREG_GRAY_INC_1_BIN2GRAY_1_LOGIC: process (gray_inc_1_bincnt) is
|
|
||||||
variable Bext: unsigned(8 downto 0);
|
|
||||||
begin
|
|
||||||
Bext := to_unsigned(0, 9);
|
|
||||||
Bext := resize(gray_inc_1_bincnt, 9);
|
|
||||||
for i in 0 to 8-1 loop
|
|
||||||
graycnt_comb(i) <= (Bext((i + 1)) xor Bext(i));
|
|
||||||
end loop;
|
|
||||||
end process GRAYINCREG_GRAY_INC_1_BIN2GRAY_1_LOGIC;
|
|
||||||
|
|
||||||
|
|
||||||
GRAYINCREG_REG_1: process (clock) is
|
|
||||||
begin
|
|
||||||
if rising_edge(clock) then
|
|
||||||
graycnt <= graycnt_comb;
|
|
||||||
end if;
|
|
||||||
end process GRAYINCREG_REG_1;
|
|
||||||
|
|
||||||
end architecture MyHDL;
|
|
15
example/manual/convert_gray_inc_reg.py
Normal file
15
example/manual/convert_gray_inc_reg.py
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
from myhdl import Signal, ResetSignal, modbv
|
||||||
|
|
||||||
|
from gray_inc_reg import gray_inc_reg
|
||||||
|
|
||||||
|
def convert_gray_inc_reg(hdl, width=8):
|
||||||
|
graycnt = Signal(modbv(0)[width:])
|
||||||
|
enable = Signal(bool())
|
||||||
|
clock = Signal(bool())
|
||||||
|
reset = ResetSignal(0, active=0, async=True)
|
||||||
|
|
||||||
|
inst = gray_inc_reg(graycnt, enable, clock, reset, width)
|
||||||
|
inst.convert(hdl)
|
||||||
|
|
||||||
|
convert_gray_inc_reg(hdl='Verilog')
|
||||||
|
convert_gray_inc_reg(hdl='VHDL')
|
15
example/manual/gray_inc.py
Normal file
15
example/manual/gray_inc.py
Normal file
@ -0,0 +1,15 @@
|
|||||||
|
from myhdl import block, Signal, modbv
|
||||||
|
|
||||||
|
from bin2gray import bin2gray
|
||||||
|
from inc import inc
|
||||||
|
|
||||||
|
@block
|
||||||
|
def gray_inc(graycnt, enable, clock, reset, width):
|
||||||
|
|
||||||
|
bincnt = Signal(modbv(0)[width:])
|
||||||
|
|
||||||
|
inc_0 = inc(bincnt, enable, clock, reset)
|
||||||
|
bin2gray_0 = bin2gray(B=bincnt, G=graycnt)
|
||||||
|
|
||||||
|
return inc_0, bin2gray_0
|
||||||
|
|
18
example/manual/gray_inc_reg.py
Normal file
18
example/manual/gray_inc_reg.py
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
from myhdl import block, always_seq, Signal, modbv
|
||||||
|
|
||||||
|
from gray_inc import gray_inc
|
||||||
|
|
||||||
|
@block
|
||||||
|
def gray_inc_reg(graycnt, enable, clock, reset, width):
|
||||||
|
|
||||||
|
graycnt_comb = Signal(modbv(0)[width:])
|
||||||
|
|
||||||
|
gray_inc_0 = gray_inc(graycnt_comb, enable, clock, reset, width)
|
||||||
|
gray_inc_0.name = "gray_inc_0"
|
||||||
|
|
||||||
|
@always_seq(clock.posedge, reset=reset)
|
||||||
|
def reg_0():
|
||||||
|
graycnt.next = graycnt_comb
|
||||||
|
|
||||||
|
return gray_inc_0, reg_0
|
||||||
|
|
51
example/manual/gray_inc_reg.v
Normal file
51
example/manual/gray_inc_reg.v
Normal file
@ -0,0 +1,51 @@
|
|||||||
|
// File: gray_inc_reg.v
|
||||||
|
// Generated by MyHDL 1.0dev
|
||||||
|
// Date: Mon May 23 18:06:58 2016
|
||||||
|
|
||||||
|
|
||||||
|
`timescale 1ns/10ps
|
||||||
|
|
||||||
|
module gray_inc_reg (
|
||||||
|
graycnt,
|
||||||
|
enable,
|
||||||
|
clock,
|
||||||
|
reset
|
||||||
|
);
|
||||||
|
|
||||||
|
|
||||||
|
output [7:0] graycnt;
|
||||||
|
reg [7:0] graycnt;
|
||||||
|
input enable;
|
||||||
|
input clock;
|
||||||
|
input reset;
|
||||||
|
|
||||||
|
wire [7:0] graycnt_comb;
|
||||||
|
reg [7:0] gray_inc_0_bincnt;
|
||||||
|
|
||||||
|
|
||||||
|
always @(posedge clock, negedge reset) begin: GRAY_INC_REG_GRAY_INC_0_INC_0_SEQ
|
||||||
|
if (reset == 0) begin
|
||||||
|
gray_inc_0_bincnt <= 0;
|
||||||
|
end
|
||||||
|
else begin
|
||||||
|
if (enable) begin
|
||||||
|
gray_inc_0_bincnt <= (gray_inc_0_bincnt + 1);
|
||||||
|
end
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
assign graycnt_comb = ((gray_inc_0_bincnt >>> 1) ^ gray_inc_0_bincnt);
|
||||||
|
|
||||||
|
|
||||||
|
always @(posedge clock, negedge reset) begin: GRAY_INC_REG_REG_0
|
||||||
|
if (reset == 0) begin
|
||||||
|
graycnt <= 0;
|
||||||
|
end
|
||||||
|
else begin
|
||||||
|
graycnt <= graycnt_comb;
|
||||||
|
end
|
||||||
|
end
|
||||||
|
|
||||||
|
endmodule
|
57
example/manual/gray_inc_reg.vhd
Normal file
57
example/manual/gray_inc_reg.vhd
Normal file
@ -0,0 +1,57 @@
|
|||||||
|
-- File: gray_inc_reg.vhd
|
||||||
|
-- Generated by MyHDL 1.0dev
|
||||||
|
-- Date: Mon May 23 18:06:58 2016
|
||||||
|
|
||||||
|
|
||||||
|
library IEEE;
|
||||||
|
use IEEE.std_logic_1164.all;
|
||||||
|
use IEEE.numeric_std.all;
|
||||||
|
use std.textio.all;
|
||||||
|
|
||||||
|
use work.pck_myhdl_10.all;
|
||||||
|
|
||||||
|
entity gray_inc_reg is
|
||||||
|
port (
|
||||||
|
graycnt: out unsigned(7 downto 0);
|
||||||
|
enable: in std_logic;
|
||||||
|
clock: in std_logic;
|
||||||
|
reset: in std_logic
|
||||||
|
);
|
||||||
|
end entity gray_inc_reg;
|
||||||
|
|
||||||
|
|
||||||
|
architecture MyHDL of gray_inc_reg is
|
||||||
|
|
||||||
|
|
||||||
|
signal graycnt_comb: unsigned(7 downto 0);
|
||||||
|
signal gray_inc_0_bincnt: unsigned(7 downto 0);
|
||||||
|
|
||||||
|
begin
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
GRAY_INC_REG_GRAY_INC_0_INC_1_SEQ: process (clock, reset) is
|
||||||
|
begin
|
||||||
|
if (reset = '0') then
|
||||||
|
gray_inc_0_bincnt <= to_unsigned(0, 8);
|
||||||
|
elsif rising_edge(clock) then
|
||||||
|
if bool(enable) then
|
||||||
|
gray_inc_0_bincnt <= (gray_inc_0_bincnt + 1);
|
||||||
|
end if;
|
||||||
|
end if;
|
||||||
|
end process GRAY_INC_REG_GRAY_INC_0_INC_1_SEQ;
|
||||||
|
|
||||||
|
|
||||||
|
graycnt_comb <= (shift_right(gray_inc_0_bincnt, 1) xor gray_inc_0_bincnt);
|
||||||
|
|
||||||
|
GRAY_INC_REG_REG_0: process (clock, reset) is
|
||||||
|
begin
|
||||||
|
if (reset = '0') then
|
||||||
|
graycnt <= to_unsigned(0, 8);
|
||||||
|
elsif rising_edge(clock) then
|
||||||
|
graycnt <= graycnt_comb;
|
||||||
|
end if;
|
||||||
|
end process GRAY_INC_REG_REG_0;
|
||||||
|
|
||||||
|
end architecture MyHDL;
|
@ -1,6 +1,6 @@
|
|||||||
-- File: pck_myhdl_10.vhd
|
-- File: pck_myhdl_10.vhd
|
||||||
-- Generated by MyHDL 1.0dev
|
-- Generated by MyHDL 1.0dev
|
||||||
-- Date: Mon May 23 16:09:27 2016
|
-- Date: Mon May 23 18:06:58 2016
|
||||||
|
|
||||||
|
|
||||||
library ieee;
|
library ieee;
|
||||||
|
26
example/manual/tb_gray_inc_reg.v
Normal file
26
example/manual/tb_gray_inc_reg.v
Normal file
@ -0,0 +1,26 @@
|
|||||||
|
module tb_gray_inc_reg;
|
||||||
|
|
||||||
|
wire [7:0] graycnt;
|
||||||
|
reg enable;
|
||||||
|
reg clock;
|
||||||
|
reg reset;
|
||||||
|
|
||||||
|
initial begin
|
||||||
|
$from_myhdl(
|
||||||
|
enable,
|
||||||
|
clock,
|
||||||
|
reset
|
||||||
|
);
|
||||||
|
$to_myhdl(
|
||||||
|
graycnt
|
||||||
|
);
|
||||||
|
end
|
||||||
|
|
||||||
|
gray_inc_reg dut(
|
||||||
|
graycnt,
|
||||||
|
enable,
|
||||||
|
clock,
|
||||||
|
reset
|
||||||
|
);
|
||||||
|
|
||||||
|
endmodule
|
Loading…
x
Reference in New Issue
Block a user