mirror of
https://github.com/RobotechLille/cdf2018-principal
synced 2024-11-22 08:06:04 +01:00
FPGA : Communication sur plusieurs octets
This commit is contained in:
parent
9a2bf3d9cd
commit
81a7fd8bd7
|
@ -1,5 +1,6 @@
|
||||||
library IEEE;
|
library IEEE;
|
||||||
use IEEE.STD_LOGIC_1164.ALL;
|
use IEEE.STD_LOGIC_1164.ALL;
|
||||||
|
use IEEE.NUMERIC_STD.ALL;
|
||||||
|
|
||||||
|
|
||||||
entity Principal is
|
entity Principal is
|
||||||
|
@ -17,8 +18,8 @@ end Principal;
|
||||||
|
|
||||||
architecture Behavioral of Principal is
|
architecture Behavioral of Principal is
|
||||||
-- Blink led
|
-- Blink led
|
||||||
signal pulse : std_logic := '0';
|
|
||||||
signal count : integer := 0;
|
signal count : integer := 0;
|
||||||
|
signal theled: std_logic_vector(3 downto 0) := "0000";
|
||||||
|
|
||||||
-- General
|
-- General
|
||||||
signal reset : std_logic := '0';
|
signal reset : std_logic := '0';
|
||||||
|
@ -30,8 +31,6 @@ architecture Behavioral of Principal is
|
||||||
-- Sensors
|
-- Sensors
|
||||||
signal front : integer;
|
signal front : integer;
|
||||||
signal back : integer;
|
signal back : integer;
|
||||||
signal frontTrigger : integer := 0;
|
|
||||||
signal backTrigger : integer := 0;
|
|
||||||
|
|
||||||
-- AF
|
-- AF
|
||||||
component uart is
|
component uart is
|
||||||
|
@ -61,16 +60,22 @@ architecture Behavioral of Principal is
|
||||||
signal rxData : std_logic_vector(7 downto 0);
|
signal rxData : std_logic_vector(7 downto 0);
|
||||||
signal rxStb : std_logic := '0';
|
signal rxStb : std_logic := '0';
|
||||||
|
|
||||||
constant A2FD_PING : std_logic_vector := x"50"; -- 'P'
|
-- Handling
|
||||||
|
component communication is
|
||||||
type readStates is (readIdle);
|
Port (
|
||||||
signal readState : readStates := readIdle;
|
clock : in std_logic;
|
||||||
|
reset : in std_logic;
|
||||||
type sendMessages is (none, A2FD_PINGs);
|
left : in integer;
|
||||||
signal resetSendMessageRead : std_logic := '0';
|
right : in integer;
|
||||||
signal resetSendMessageSend : std_logic := '0';
|
front : in integer;
|
||||||
signal sendMessage : sendMessages := none;
|
back : in integer;
|
||||||
signal sendOffset : integer := 0;
|
txData : out std_logic_vector(7 downto 0);
|
||||||
|
txStb : out std_logic;
|
||||||
|
txAck : in std_logic;
|
||||||
|
rxData : in std_logic_vector(7 downto 0);
|
||||||
|
rxStb : in std_logic
|
||||||
|
);
|
||||||
|
end component;
|
||||||
|
|
||||||
-- Debug
|
-- Debug
|
||||||
component sevenseg is
|
component sevenseg is
|
||||||
|
@ -100,63 +105,41 @@ begin
|
||||||
rx => IO(20)
|
rx => IO(20)
|
||||||
);
|
);
|
||||||
|
|
||||||
readsendFA : process(reset, rxStb, txAck)
|
com: communication port map(
|
||||||
begin
|
clock => CLK,
|
||||||
if reset = '1' then
|
reset => reset,
|
||||||
readState <= readIdle;
|
left => left,
|
||||||
sendMessage <= none;
|
right => right,
|
||||||
txStb <= '0';
|
front => front,
|
||||||
sendOffset <= 0;
|
back => back,
|
||||||
else
|
txData => txData,
|
||||||
-- If read something
|
txStb => txStb,
|
||||||
if rxStb = '1' then
|
txAck => txAck,
|
||||||
if readState = readIdle then
|
rxData => rxData,
|
||||||
case rxData is
|
rxStb => rxStb
|
||||||
when A2FD_PING => -- 'P'
|
);
|
||||||
sendMessage <= A2FD_PINGs; -- TODO Not so brutal
|
|
||||||
when others =>
|
|
||||||
end case;
|
|
||||||
end if;
|
|
||||||
end if;
|
|
||||||
|
|
||||||
-- Reset sending if UART module has begun sending (and has a copy of the byte)
|
|
||||||
if txAck = '1' then
|
|
||||||
txStb <= '0';
|
|
||||||
end if;
|
|
||||||
|
|
||||||
-- If what was sent is acknowledged and there is still something to send
|
|
||||||
if txStb = '0' then
|
|
||||||
case sendMessage is
|
|
||||||
when none =>
|
|
||||||
when A2FD_PINGs =>
|
|
||||||
txData <= A2FD_PING;
|
|
||||||
txStb <= '1';
|
|
||||||
sendMessage <= none;
|
|
||||||
end case;
|
|
||||||
end if;
|
|
||||||
end if;
|
|
||||||
end process;
|
|
||||||
|
|
||||||
-- Debug
|
-- Debug
|
||||||
blinkled : process(CLK, reset)
|
blinkled : process(CLK, reset)
|
||||||
begin
|
begin
|
||||||
if reset = '1' then
|
if reset = '1' then
|
||||||
count <= 0;
|
count <= 0;
|
||||||
pulse <= '0';
|
theled <= "0000";
|
||||||
elsif CLK'event and CLK = '1' then
|
elsif CLK'event and CLK = '1' then
|
||||||
if count = 9999999 then
|
if count = 9999999 then
|
||||||
count <= 0;
|
count <= 0;
|
||||||
pulse <= not pulse;
|
theled(3) <= not theled(3);
|
||||||
|
theled(2 downto 0) <= "000";
|
||||||
else
|
else
|
||||||
count <= count + 1;
|
count <= count + 1;
|
||||||
|
theled(2 downto 0) <= theled(2 downto 0) or (txStb & rxStb & txAck);
|
||||||
end if;
|
end if;
|
||||||
|
|
||||||
end if;
|
end if;
|
||||||
end process;
|
end process;
|
||||||
LED(3) <= pulse;
|
|
||||||
|
|
||||||
LED(2) <= txStb;
|
LED <= theled;
|
||||||
LED(1) <= rxStb;
|
|
||||||
LED(0) <= txAck;
|
|
||||||
|
|
||||||
debugSeg: sevenseg port map(
|
debugSeg: sevenseg port map(
|
||||||
data => sevensegdata,
|
data => sevensegdata,
|
||||||
|
|
62
fpga/Principal_tb.gtkw
Normal file
62
fpga/Principal_tb.gtkw
Normal file
|
@ -0,0 +1,62 @@
|
||||||
|
[*]
|
||||||
|
[*] GTKWave Analyzer v3.3.86 (w)1999-2017 BSI
|
||||||
|
[*] Sun Feb 25 14:12:54 2018
|
||||||
|
[*]
|
||||||
|
[dumpfile] "/home/geoffrey/Documents/Polytech/Robotech/2017-2018/CdF/cdf2018-principal/fpga/build/Principal_tb.vcd"
|
||||||
|
[dumpfile_mtime] "Sun Feb 25 14:10:51 2018"
|
||||||
|
[dumpfile_size] 38271255
|
||||||
|
[savefile] "/home/geoffrey/Documents/Polytech/Robotech/2017-2018/CdF/cdf2018-principal/fpga/Principal_tb.gtkw"
|
||||||
|
[timestart] 0
|
||||||
|
[size] 1680 1012
|
||||||
|
[pos] -1 -1
|
||||||
|
*-40.000000 3481820000000 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
|
||||||
|
[treeopen] dut.
|
||||||
|
[sst_width] 213
|
||||||
|
[signals_width] 198
|
||||||
|
[sst_expanded] 1
|
||||||
|
[sst_vpaned_height] 296
|
||||||
|
@28
|
||||||
|
[color] 4
|
||||||
|
clk
|
||||||
|
dut.reset
|
||||||
|
[color] 2
|
||||||
|
dut.fa.rx_baud_tick
|
||||||
|
[color] 2
|
||||||
|
dut.fa.rx
|
||||||
|
@8028
|
||||||
|
[color] 2
|
||||||
|
dut.fa.uart_rx_count[2:0]
|
||||||
|
@22
|
||||||
|
[color] 2
|
||||||
|
dut.fa.uart_rx_data_vec[7:0]
|
||||||
|
dut.rxdata[7:0]
|
||||||
|
@820
|
||||||
|
dut.rxdata[7:0]
|
||||||
|
@28
|
||||||
|
dut.rxstb
|
||||||
|
@420
|
||||||
|
[color] 5
|
||||||
|
dut.com.readoffset
|
||||||
|
[color] 5
|
||||||
|
dut.com.sendoffset
|
||||||
|
@22
|
||||||
|
[color] 4
|
||||||
|
dut.txdata[7:0]
|
||||||
|
@820
|
||||||
|
[color] 4
|
||||||
|
dut.txdata[7:0]
|
||||||
|
@28
|
||||||
|
dut.txstb
|
||||||
|
dut.txack
|
||||||
|
[color] 2
|
||||||
|
dut.fa.tx
|
||||||
|
[color] 2
|
||||||
|
dut.fa.tx_baud_tick
|
||||||
|
@8028
|
||||||
|
[color] 2
|
||||||
|
dut.fa.uart_tx_count[2:0]
|
||||||
|
@22
|
||||||
|
[color] 2
|
||||||
|
dut.fa.uart_tx_data_vec[7:0]
|
||||||
|
[pattern_trace] 1
|
||||||
|
[pattern_trace] 0
|
111
fpga/Principal_tb.vhd
Normal file
111
fpga/Principal_tb.vhd
Normal file
|
@ -0,0 +1,111 @@
|
||||||
|
-- Testbench automatically generated online
|
||||||
|
-- at http://vhdl.lapinoo.net
|
||||||
|
-- Generation date : 25.2.2018 11:52:20 GMT
|
||||||
|
|
||||||
|
library ieee;
|
||||||
|
use ieee.std_logic_1164.all;
|
||||||
|
|
||||||
|
entity Principal_tb is
|
||||||
|
end Principal_tb;
|
||||||
|
|
||||||
|
architecture tb of Principal_tb is
|
||||||
|
|
||||||
|
component Principal
|
||||||
|
port (CLK : in std_logic;
|
||||||
|
BTN : in std_logic;
|
||||||
|
IO : inout std_logic_vector (21 downto 20);
|
||||||
|
LED : out std_logic_vector (3 downto 0);
|
||||||
|
AN : out std_logic_vector (3 downto 0);
|
||||||
|
A_TO_G : out std_logic_vector (6 downto 0);
|
||||||
|
DOT : out std_logic);
|
||||||
|
end component;
|
||||||
|
|
||||||
|
signal CLK : std_logic;
|
||||||
|
signal BTN : std_logic;
|
||||||
|
signal IO : std_logic_vector (21 downto 20);
|
||||||
|
signal LED : std_logic_vector (3 downto 0);
|
||||||
|
signal AN : std_logic_vector (3 downto 0);
|
||||||
|
signal A_TO_G : std_logic_vector (6 downto 0);
|
||||||
|
signal DOT : std_logic;
|
||||||
|
|
||||||
|
constant TbPeriod : time := 20 ns;
|
||||||
|
signal TbClock : std_logic := '0';
|
||||||
|
signal TbSimEnded : std_logic := '0';
|
||||||
|
|
||||||
|
constant BaudPeriod : time := 104167 ns; -- 9600 baud
|
||||||
|
constant CharacterPeriod : time := 10 * BaudPeriod;
|
||||||
|
signal rx : std_logic;
|
||||||
|
signal tx : std_logic;
|
||||||
|
begin
|
||||||
|
|
||||||
|
dut : Principal
|
||||||
|
port map (CLK => CLK,
|
||||||
|
BTN => BTN,
|
||||||
|
IO => IO,
|
||||||
|
LED => LED,
|
||||||
|
AN => AN,
|
||||||
|
A_TO_G => A_TO_G,
|
||||||
|
DOT => DOT);
|
||||||
|
|
||||||
|
-- Clock generation
|
||||||
|
TbClock <= not TbClock after TbPeriod/2 when TbSimEnded /= '1' else '0';
|
||||||
|
|
||||||
|
CLK <= TbClock;
|
||||||
|
|
||||||
|
IO(20) <= rx;
|
||||||
|
tx <= IO(21);
|
||||||
|
|
||||||
|
|
||||||
|
stimuli : process
|
||||||
|
variable sending : std_logic_vector(7 downto 0);
|
||||||
|
begin
|
||||||
|
rx <= '1';
|
||||||
|
|
||||||
|
-- Reset generation
|
||||||
|
BTN <= '1';
|
||||||
|
wait for 100 ns;
|
||||||
|
BTN <= '0';
|
||||||
|
wait for 100 ns;
|
||||||
|
|
||||||
|
wait for 2 * BaudPeriod;
|
||||||
|
|
||||||
|
-- Send 'P'
|
||||||
|
rx <= '0'; -- Start bit
|
||||||
|
sending := x"50"; -- 'P'
|
||||||
|
wait for BaudPeriod;
|
||||||
|
for I in 0 to 7 loop
|
||||||
|
rx <= sending(I);
|
||||||
|
wait for BaudPeriod;
|
||||||
|
end loop;
|
||||||
|
rx <= '1'; -- Stop bit
|
||||||
|
wait for BaudPeriod;
|
||||||
|
|
||||||
|
-- Wait for 1 byte receive
|
||||||
|
wait for CharacterPeriod;
|
||||||
|
|
||||||
|
-- Wait margin
|
||||||
|
wait for 2 * BaudPeriod;
|
||||||
|
|
||||||
|
-- Send '?'
|
||||||
|
rx <= '0'; -- Start bit
|
||||||
|
sending := x"3F"; -- '?'
|
||||||
|
wait for BaudPeriod;
|
||||||
|
for I in 0 to 7 loop
|
||||||
|
rx <= sending(I);
|
||||||
|
wait for BaudPeriod;
|
||||||
|
end loop;
|
||||||
|
rx <= '1'; -- Stop bit
|
||||||
|
wait for BaudPeriod;
|
||||||
|
|
||||||
|
-- Wait for 2 bytes receive
|
||||||
|
wait for 2 * CharacterPeriod;
|
||||||
|
|
||||||
|
-- Wait margin
|
||||||
|
wait for 2 * BaudPeriod;
|
||||||
|
|
||||||
|
-- Stop the clock and hence terminate the simulation
|
||||||
|
TbSimEnded <= '1';
|
||||||
|
wait;
|
||||||
|
end process;
|
||||||
|
|
||||||
|
end tb;
|
95
fpga/communication.vhd
Normal file
95
fpga/communication.vhd
Normal file
|
@ -0,0 +1,95 @@
|
||||||
|
library IEEE;
|
||||||
|
use IEEE.STD_LOGIC_1164.ALL;
|
||||||
|
use IEEE.NUMERIC_STD.ALL;
|
||||||
|
|
||||||
|
|
||||||
|
entity communication is
|
||||||
|
Port (
|
||||||
|
clock : in std_logic;
|
||||||
|
reset : in std_logic;
|
||||||
|
left : in integer;
|
||||||
|
right : in integer;
|
||||||
|
front : in integer;
|
||||||
|
back : in integer;
|
||||||
|
txData : out std_logic_vector(7 downto 0);
|
||||||
|
txStb : out std_logic;
|
||||||
|
txAck : in std_logic;
|
||||||
|
rxData : in std_logic_vector(7 downto 0);
|
||||||
|
rxStb : in std_logic
|
||||||
|
);
|
||||||
|
end communication;
|
||||||
|
|
||||||
|
architecture Behavioral of communication is
|
||||||
|
|
||||||
|
constant A2FD_PING : std_logic_vector(7 downto 0) := x"50"; -- 'P'
|
||||||
|
constant A2FD_RESETCODER : std_logic_vector(7 downto 0) := x"52"; -- 'R'
|
||||||
|
constant F2AD_ERR : std_logic_vector(7 downto 0) := x"45"; -- 'E'
|
||||||
|
constant ERR_UNKNOWN_CODE : std_logic_vector(7 downto 0) := x"43"; -- 'C'
|
||||||
|
constant F2AI_CODER : std_logic_vector(7 downto 0) := x"44"; -- 'D'
|
||||||
|
constant F2AI_CAPT : std_logic_vector(7 downto 0) := x"43"; -- 'C'
|
||||||
|
constant F2AT_CAPT : std_logic_vector(7 downto 0) := x"63"; -- 'c'
|
||||||
|
|
||||||
|
type readStates is (readIdle);
|
||||||
|
signal readState : readStates := readIdle;
|
||||||
|
signal readOffset : integer := 0;
|
||||||
|
|
||||||
|
type sendMessages is (none, A2FD_PINGs, F2AD_ERR_UNKNOWN_CODEs);
|
||||||
|
signal sendMessage : sendMessages := none;
|
||||||
|
signal sendOffset : integer := 0;
|
||||||
|
|
||||||
|
signal frontTrigger : integer := 0;
|
||||||
|
signal backTrigger : integer := 0;
|
||||||
|
|
||||||
|
signal txStbs : std_logic := '0';
|
||||||
|
|
||||||
|
begin
|
||||||
|
|
||||||
|
txStb <= txStbs;
|
||||||
|
|
||||||
|
readsendFA : process(clock, reset)
|
||||||
|
begin
|
||||||
|
if reset = '1' then
|
||||||
|
readState <= readIdle;
|
||||||
|
txStbs <= '0';
|
||||||
|
sendMessage <= none;
|
||||||
|
sendOffset <= 0;
|
||||||
|
else
|
||||||
|
if rising_edge(clock) then
|
||||||
|
-- If read something
|
||||||
|
if rxStb = '1' then
|
||||||
|
if readState = readIdle then
|
||||||
|
case rxData is
|
||||||
|
when A2FD_PING =>
|
||||||
|
sendMessage <= A2FD_PINGs; -- TODO Not so brutal
|
||||||
|
when others =>
|
||||||
|
sendMessage <= F2AD_ERR_UNKNOWN_CODEs;
|
||||||
|
end case;
|
||||||
|
end if;
|
||||||
|
end if;
|
||||||
|
|
||||||
|
-- If what was sent is acknowledged and there is still something to send
|
||||||
|
if txStbs = '0' or txAck = '1' then
|
||||||
|
txStbs <= '1';
|
||||||
|
sendOffset <= sendOffset + 1;
|
||||||
|
case sendMessage is
|
||||||
|
when none =>
|
||||||
|
txStbs <= '0';
|
||||||
|
sendOffset <= 0;
|
||||||
|
when A2FD_PINGs =>
|
||||||
|
txData <= A2FD_PING;
|
||||||
|
sendMessage <= none;
|
||||||
|
when F2AD_ERR_UNKNOWN_CODEs =>
|
||||||
|
case sendOffset is
|
||||||
|
when 0 =>
|
||||||
|
txData <= F2AD_ERR;
|
||||||
|
when others =>
|
||||||
|
txData <= ERR_UNKNOWN_CODE;
|
||||||
|
sendMessage <= none;
|
||||||
|
end case;
|
||||||
|
end case;
|
||||||
|
end if;
|
||||||
|
end if;
|
||||||
|
end if;
|
||||||
|
end process;
|
||||||
|
|
||||||
|
end Behavioral;
|
41
fpga/communication_tb.gtkw
Normal file
41
fpga/communication_tb.gtkw
Normal file
|
@ -0,0 +1,41 @@
|
||||||
|
[*]
|
||||||
|
[*] GTKWave Analyzer v3.3.86 (w)1999-2017 BSI
|
||||||
|
[*] Sun Feb 25 17:14:08 2018
|
||||||
|
[*]
|
||||||
|
[dumpfile] "/home/geoffrey/Documents/Polytech/Robotech/2017-2018/CdF/cdf2018-principal/fpga/build/communication_tb.vcd"
|
||||||
|
[dumpfile_mtime] "Sun Feb 25 17:12:53 2018"
|
||||||
|
[dumpfile_size] 4479
|
||||||
|
[savefile] "/home/geoffrey/Documents/Polytech/Robotech/2017-2018/CdF/cdf2018-principal/fpga/communication_tb.gtkw"
|
||||||
|
[timestart] 0
|
||||||
|
[size] 1680 1012
|
||||||
|
[pos] -1 -1
|
||||||
|
*-27.785210 1133000000 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1 -1
|
||||||
|
[sst_width] 213
|
||||||
|
[signals_width] 118
|
||||||
|
[sst_expanded] 1
|
||||||
|
[sst_vpaned_height] 244
|
||||||
|
@28
|
||||||
|
clock
|
||||||
|
reset
|
||||||
|
@820
|
||||||
|
[color] 2
|
||||||
|
rxdata[7:0]
|
||||||
|
@22
|
||||||
|
[color] 2
|
||||||
|
rxdata[7:0]
|
||||||
|
@28
|
||||||
|
[color] 2
|
||||||
|
rxstb
|
||||||
|
@820
|
||||||
|
[color] 5
|
||||||
|
txdata[7:0]
|
||||||
|
@22
|
||||||
|
[color] 5
|
||||||
|
txdata[7:0]
|
||||||
|
@28
|
||||||
|
[color] 5
|
||||||
|
txstb
|
||||||
|
[color] 5
|
||||||
|
txack
|
||||||
|
[pattern_trace] 1
|
||||||
|
[pattern_trace] 0
|
139
fpga/communication_tb.vhd
Normal file
139
fpga/communication_tb.vhd
Normal file
|
@ -0,0 +1,139 @@
|
||||||
|
-- Testbench automatically generated online
|
||||||
|
-- at http://vhdl.lapinoo.net
|
||||||
|
-- Generation date : 24.2.2018 16:12:08 GMT
|
||||||
|
|
||||||
|
library ieee;
|
||||||
|
use ieee.std_logic_1164.all;
|
||||||
|
|
||||||
|
entity communication_tb is
|
||||||
|
end communication_tb;
|
||||||
|
|
||||||
|
architecture tb of communication_tb is
|
||||||
|
|
||||||
|
component communication
|
||||||
|
port (clock : in std_logic;
|
||||||
|
reset : in std_logic;
|
||||||
|
left : in integer;
|
||||||
|
right : in integer;
|
||||||
|
front : in integer;
|
||||||
|
back : in integer;
|
||||||
|
txData : out std_logic_vector (7 downto 0);
|
||||||
|
txStb : out std_logic;
|
||||||
|
txAck : in std_logic;
|
||||||
|
rxData : in std_logic_vector (7 downto 0);
|
||||||
|
rxStb : in std_logic);
|
||||||
|
end component;
|
||||||
|
|
||||||
|
signal clock : std_logic;
|
||||||
|
signal reset : std_logic;
|
||||||
|
signal left : integer;
|
||||||
|
signal right : integer;
|
||||||
|
signal front : integer;
|
||||||
|
signal back : integer;
|
||||||
|
signal txData : std_logic_vector (7 downto 0);
|
||||||
|
signal txStb : std_logic;
|
||||||
|
signal txAck : std_logic;
|
||||||
|
signal rxData : std_logic_vector (7 downto 0);
|
||||||
|
signal rxStb : std_logic;
|
||||||
|
|
||||||
|
constant TbPeriod : time := 20 ns;
|
||||||
|
signal TbClock : std_logic := '0';
|
||||||
|
signal TbSimEnded : std_logic := '0';
|
||||||
|
|
||||||
|
begin
|
||||||
|
|
||||||
|
dut : communication
|
||||||
|
port map (clock => clock,
|
||||||
|
reset => reset,
|
||||||
|
left => left,
|
||||||
|
right => right,
|
||||||
|
front => front,
|
||||||
|
back => back,
|
||||||
|
txData => txData,
|
||||||
|
txStb => txStb,
|
||||||
|
txAck => txAck,
|
||||||
|
rxData => rxData,
|
||||||
|
rxStb => rxStb);
|
||||||
|
|
||||||
|
-- Clock generation
|
||||||
|
TbClock <= not TbClock after TbPeriod/2 when TbSimEnded /= '1' else '0';
|
||||||
|
|
||||||
|
clock <= TbClock;
|
||||||
|
|
||||||
|
stimuli : process
|
||||||
|
begin
|
||||||
|
left <= 0;
|
||||||
|
right <= 0;
|
||||||
|
front <= 0;
|
||||||
|
back <= 0;
|
||||||
|
txAck <= '0';
|
||||||
|
rxData <= (others => '0');
|
||||||
|
rxStb <= '0';
|
||||||
|
|
||||||
|
-- Reset generation
|
||||||
|
reset <= '1';
|
||||||
|
wait for 100 ns;
|
||||||
|
reset <= '0';
|
||||||
|
wait for 100 ns;
|
||||||
|
|
||||||
|
|
||||||
|
-- Test Ping
|
||||||
|
report "Receiving 'P'" severity note;
|
||||||
|
rxData <= x"50";
|
||||||
|
rxStb <= '1';
|
||||||
|
wait for TbPeriod;
|
||||||
|
rxStb <= '0';
|
||||||
|
|
||||||
|
wait for 100 ns;
|
||||||
|
assert txData = x"50" report "Not sent 'P'" severity error;
|
||||||
|
assert txStb = '1' report "Not sending" severity error;
|
||||||
|
|
||||||
|
report "Acknowledging send" severity note;
|
||||||
|
wait for 100 ns;
|
||||||
|
txAck <= '1';
|
||||||
|
wait for TbPeriod;
|
||||||
|
txAck <= '0';
|
||||||
|
|
||||||
|
wait for 100 ns;
|
||||||
|
assert txStb = '0' report "Not stopping send" severity error;
|
||||||
|
|
||||||
|
wait for 100 ns; -- Margin
|
||||||
|
|
||||||
|
|
||||||
|
-- Test unknown char
|
||||||
|
report "Receiving '?'" severity note;
|
||||||
|
rxData <= x"3F";
|
||||||
|
rxStb <= '1';
|
||||||
|
wait for TbPeriod;
|
||||||
|
rxStb <= '0';
|
||||||
|
|
||||||
|
wait for 100 ns;
|
||||||
|
assert txData = x"45" report "Not sent 'E'" severity error;
|
||||||
|
assert txStb = '1' report "Not sending" severity error;
|
||||||
|
|
||||||
|
report "Acknowledging send" severity note;
|
||||||
|
wait for 100 ns;
|
||||||
|
txAck <= '1';
|
||||||
|
wait for TbPeriod;
|
||||||
|
txAck <= '0';
|
||||||
|
|
||||||
|
wait for 100 ns;
|
||||||
|
assert txData = x"43" report "Not sent 'C'" severity error;
|
||||||
|
assert txStb = '1' report "Not sending" severity error;
|
||||||
|
|
||||||
|
report "Acknowledging send" severity note;
|
||||||
|
wait for 100 ns;
|
||||||
|
txAck <= '1';
|
||||||
|
wait for TbPeriod;
|
||||||
|
txAck <= '0';
|
||||||
|
|
||||||
|
wait for 100 ns;
|
||||||
|
assert txStb = '0' report "Not stopping send" severity error;
|
||||||
|
wait for 100 ns; -- Margin
|
||||||
|
|
||||||
|
|
||||||
|
TbSimEnded <= '1';
|
||||||
|
wait;
|
||||||
|
end process;
|
||||||
|
|
||||||
|
end tb;
|
|
@ -1,6 +1,5 @@
|
||||||
LIBRARY ieee;
|
LIBRARY ieee;
|
||||||
USE ieee.std_logic_1164.all;
|
USE ieee.std_logic_1164.all;
|
||||||
USE ieee.std_logic_unsigned.all;
|
|
||||||
|
|
||||||
ENTITY hcSr04 IS
|
ENTITY hcSr04 IS
|
||||||
GENERIC(
|
GENERIC(
|
||||||
|
|
|
@ -1,69 +0,0 @@
|
||||||
LIBRARY ieee;
|
|
||||||
USE ieee.std_logic_1164.all;
|
|
||||||
USE ieee.std_logic_unsigned.all;
|
|
||||||
USE ieee.std_logic_arith.all;
|
|
||||||
|
|
||||||
ENTITY hcSr04 IS
|
|
||||||
GENERIC(
|
|
||||||
fFpga : INTEGER := 50_000_000; -- frequency of the FPGA clock (Hz)
|
|
||||||
maxOutput : INTEGER := 65535 -- maximum number to store the distance
|
|
||||||
);
|
|
||||||
PORT(
|
|
||||||
clk : IN STD_LOGIC; -- clock of the FPGA
|
|
||||||
echo : IN STD_LOGIC; -- echo pin of the hcSr04
|
|
||||||
distance : OUT INTEGER RANGE 0 TO maxOutput; -- Ranges from 0 to 4 meters, 0 if no data
|
|
||||||
trigger : OUT STD_LOGIC; -- trigger pin of the hcSr04
|
|
||||||
start : IN STD_LOGIC; -- Set to '1' everytime a measurement is needed (or keep at '1' for continuous measurement)
|
|
||||||
finished : OUT STD_LOGIC -- Driven to '1' everytime a measurement has finished
|
|
||||||
);
|
|
||||||
END hcSr04;
|
|
||||||
|
|
||||||
ARCHITECTURE Behavioral OF hcSr04 IS
|
|
||||||
CONSTANT triggerTicks : INTEGER := fFPGA / 100000; -- Number of FPGA ticks that makes 10us (used for trigger)
|
|
||||||
CONSTANT measurementTicks : INTEGER := fFPGA / 17; -- Number of FPGA ticks that makes 60ms (used for measurement cycles)
|
|
||||||
CONSTANT maximumRange : INTEGER := 4; -- Maximum range the sensor can detect
|
|
||||||
CONSTANT distanceTicks : INTEGER := maximumRange * fFPGA / 172; -- Number of FPGA ticks that makes the maximum distance that can be measured
|
|
||||||
-- 172 = 1 / 58 s/m
|
|
||||||
SIGNAL measurementCounter : INTEGER RANGE 0 to measurementTicks - 1 := 0; -- Progress in the measurement
|
|
||||||
SIGNAL distanceCounter : INTEGER RANGE 0 to distanceTicks - 1 := 0; -- Ticks for wich echo has been at one
|
|
||||||
SIGNAL triggerCounter : INTEGER RANGE 0 to triggerTicks - 1 := 0; -- Progress in the trigger
|
|
||||||
TYPE stateType IS (init, waiting, triggering, measuring);
|
|
||||||
SIGNAL state : stateType;
|
|
||||||
BEGIN
|
|
||||||
measure : process(clk)
|
|
||||||
begin
|
|
||||||
if rising_edge(clk) then
|
|
||||||
CASE state IS
|
|
||||||
WHEN init =>
|
|
||||||
trigger <= '0';
|
|
||||||
distance <= 0;
|
|
||||||
state <= waiting;
|
|
||||||
WHEN waiting =>
|
|
||||||
finished <= '0';
|
|
||||||
IF start = '1' THEN
|
|
||||||
trigger <= '1';
|
|
||||||
triggerCounter <= 0;
|
|
||||||
state <= triggering;
|
|
||||||
END IF;
|
|
||||||
WHEN triggering =>
|
|
||||||
triggerCounter <= triggerCounter + 1;
|
|
||||||
IF triggerCounter = triggerTicks - 1 THEN
|
|
||||||
trigger <= '0';
|
|
||||||
measurementCounter <= 0;
|
|
||||||
distanceCounter <= 0;
|
|
||||||
state <= measuring;
|
|
||||||
END IF;
|
|
||||||
WHEN measuring =>
|
|
||||||
IF echo = '1' and distanceCounter < distanceTicks THEN
|
|
||||||
distanceCounter <= distanceCounter + 1;
|
|
||||||
END IF;
|
|
||||||
measurementCounter <= measurementCounter + 1;
|
|
||||||
IF measurementCounter = measurementTicks - 1 THEN
|
|
||||||
distance <= distanceCounter * maxOutput / distanceTicks;
|
|
||||||
finished <= '1';
|
|
||||||
state <= waiting;
|
|
||||||
END IF;
|
|
||||||
END CASE;
|
|
||||||
end if;
|
|
||||||
end process;
|
|
||||||
END Behavioral;
|
|
|
@ -39,9 +39,9 @@ begin
|
||||||
An <= chA;
|
An <= chA;
|
||||||
Bn <= chB;
|
Bn <= chB;
|
||||||
|
|
||||||
-- On pourrait optimiser la logique avec un tableau de Karnaugh ou autres méthodes
|
-- On pourrait optimiser la logique avec un tableau de Karnaugh ou autres méthodes
|
||||||
-- de simplification d'algèbre de Boole, mais le "compilateur" pour FPGA fera un
|
-- de simplification d'algèbre de Boole, mais le synthétiseur pour FPGA fera un
|
||||||
-- tout aussi bon travail, on garde donc le code suivant pour la lisibilité
|
-- tout aussi bon travail, on garde donc le code suivant pour la lisibilité
|
||||||
|
|
||||||
if (Ap = '0' and An = '1') then -- Front montant A
|
if (Ap = '0' and An = '1') then -- Front montant A
|
||||||
if (Bn = '0') then
|
if (Bn = '0') then
|
||||||
|
|
|
@ -8,7 +8,7 @@ TOPLEVEL = Principal
|
||||||
# VHDSOURCE = $(TOPLEVEL).vhd uart.vhd
|
# VHDSOURCE = $(TOPLEVEL).vhd uart.vhd
|
||||||
# CONSTRAINTS = mercury.ucf
|
# CONSTRAINTS = mercury.ucf
|
||||||
# Debug
|
# Debug
|
||||||
VHDSOURCE = $(TOPLEVEL).vhd $(wildcard *.vhd)
|
VHDSOURCE = $(TOPLEVEL).vhd $(filter-out %_tb.vhd,$(wildcard *.vhd))
|
||||||
CONSTRAINTS = debug.ucf
|
CONSTRAINTS = debug.ucf
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue