1
votes

I'm writing TDC based on Vernier method in Vivado. My board is VC707 with virtex 7 core. After I finished writing my vhdl code i started simulation . Unfortunately I'm still learning fpga and vhdl so I stuck with one problem.

At first i wanted to check my my input circuit so i write a simple testbench to simulate. I generate short time interval to check this part of TDC. After i start simulation two of my outputs are uninicialized and other outputs have no sense ( should be high edge but simulation show zeros on the output).

On outputs should be rising edges. This circuit is intended to shape signals for my ring oscillators.

My vhdl desing:

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;

entity Uklad_WE is
Port ( Start : in STD_LOGIC;
       Stop : in STD_LOGIC;
       Reset : in STD_LOGIC;
       Pulse_st : out STD_LOGIC;
       Pulse_sp : out STD_LOGIC;
       Encnt_st : out STD_LOGIC;
       Encnt_sp : out STD_LOGIC);
end Uklad_WE;

architecture Behavioral of Uklad_WE is

signal dst1_out : std_logic;
signal dst2_out : std_logic;
signal dsp1_out : std_logic;
signal dsp2_out : std_logic;
signal INV_chain_13_o : std_logic;
signal INV_chain_15_o : std_logic;
signal gate_cnt1_o : std_logic;
signal gate_cnt2_o : std_logic;
signal dcnt1_out : std_logic;
signal dcnt2_out : std_logic;


component ffd
   port(
      D,CLK,R : in STD_LOGIC;
      Q: out STD_LOGIC
      );
 end component;

 component ffd_set
    port(
        D,S,CLK : in STD_LOGIC;
        Q : out STD_LOGIC
        );
  end component;

  component INV_chain_15
    port(
        input : in STD_LOGIC;
        output : out STD_LOGIC;
        cnt_sig : inout std_logic
    );
   end component;

   component INV_chain_13
     port(
         input : in STD_LOGIC;
         output : out STD_LOGIC;
         cnt_sig : inout std_logic
      );
   end component;


begin


DST1: ffd port map(
        D => '1',
        CLK => Start,
        R => Reset,
        Q => dst1_out);

DST2 : ffd_set port map(
        D => '0',
        CLK => dst1_out,
        S => INV_chain_13_o,
        Q => dst2_out);

DSP1 : ffd port map(
        D => dst1_out,
        CLK => Stop,
        R => Reset,
        Q => dsp1_out);

DSP2 : ffd_set port map(
        D => '0',
        CLK => dsp1_out,
        S => INV_chain_15_o,
        Q => dsp2_out);

DCNT1 : ffd port map(
        D => '1',
        CLK => gate_cnt1_o,
        R => Reset,
        Q => dcnt1_out);

DCNT2 : ffd port map(
        D => '1',
        CLK => gate_cnt2_o,
        R => Reset,
        Q => dcnt2_out);

INV_chain_st : INV_chain_13 port map(
        input => dst2_out,
        output => INV_chain_13_o,
        cnt_sig => gate_cnt1_o);

INV_chain_sp : INV_chain_15 port map(
        input => dsp2_out,
        output => INV_chain_15_o,
        cnt_sig => gate_cnt2_o);

Pulse_st <= dst2_out;
Pulse_sp <= dsp2_out;
Encnt_st <= dcnt1_out;
Encnt_sp <= dcnt2_out;


end Behavioral; 

My testbench :

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_unsigned.ALL;

entity symulacja_tdc_vo is

end symulacja_tdc_vo;

architecture Behavioral of symulacja_tdc_vo is

component Uklad_WE
    Port(
         Start : in STD_LOGIC;
         Stop : in STD_LOGIC;
         Reset : in STD_LOGIC;
         Pulse_st : out STD_LOGIC;
         Pulse_sp : out STD_LOGIC;
         Encnt_st : out STD_LOGIC;
         Encnt_sp : out STD_LOGIC);
end component;

--inputs

signal Start :  STD_LOGIC := '0';
signal Stop :  STD_LOGIC := '0';
signal Reset :  STD_LOGIC := '0';

--outputs

signal Pulse_st :  STD_LOGIC;
signal Pulse_sp :  STD_LOGIC;
signal Encnt_st :  STD_LOGIC;
signal Encnt_sp :  STD_LOGIC;

begin
  --uut
    uut: Uklad_WE port map(

        Start => Start,
        Stop => Stop,
        Reset => Reset,
        Pulse_st => Pulse_st,
        Pulse_sp => Pulse_sp, 
        Encnt_st => Encnt_st,
        Encnt_sp => Encnt_sp);
   -- stimuluis process

     stim_proc1: process
        begin
          Start <= not Start after 5 ps;
          wait for 500 ps;
     end process;


     stim_proc2: process
        begin
          Stop <= not Stop after 50 ps;
          wait for 500 ps;
     end process;


     stim_proc3: process
        begin
          wait for 250 ps;
          Reset <= not Reset;
          wait for 500 ps;
     end process;

end Behavioral;

Components code :

ffd - ffd with reset

library ieee;
use ieee.std_logic_1164.all;

entity ffd is
port (
     D, CLK, R : in std_logic;
    Q : out std_logic );
end ffd;

architecture Bech of ffd is
begin

process( CLK, R )
    begin
        if R = '0' then
            Q <= '0';
         elsif rising_edge(CLK) then
            Q <= D;
        end if;
   end process;
end Bech;

ffd_set - ffd with set

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;

entity ffd_set is
port ( 
    D, CLK, S : in std_logic;
    Q : out std_logic );
end ffd_set;

architecture Bech of ffd_set is
begin

process( CLK, S )
    begin
        if S = '0' then
            Q <= '1';
        elsif rising_edge(CLK) then
            Q <= D;
        end if;
    end process;
end Bech;

INV_chain_13 - inverters chain

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;

entity INV_chain_13 is
Port ( input : in STD_LOGIC;
       output : out STD_LOGIC;
       cnt_sig : inout STD_LOGIC);
end INV_chain_13;

architecture Behavioral of INV_chain_13 is

   signal gate_o : std_logic_vector(12 downto 0);
begin

gate_o(0) <= input; 

inv_g_chain : for i in 1 to gate_o'high generate
     gate_o(i) <= not gate_o(i-1);
end generate;

gate_o(1) <= cnt_sig;
output <= gate_o(12);

end Behavioral;

INV_chain_15 - also inverters chain, only number of inv is diffrent

library IEEE;
use IEEE.STD_LOGIC_1164.ALL;

entity INV_chain_15 is
Port ( input : in STD_LOGIC;
       output : out STD_LOGIC;
       cnt_sig : inout STD_LOGIC);
end INV_chain_15;

architecture Behavioral of INV_chain_15 is

   signal gate_o : std_logic_vector(14 downto 0);
begin

gate_o(0) <= input; 

inv_g_chain : for i in 1 to gate_o'high generate
    gate_o(i) <= not gate_o(i-1);
end generate;

gate_o(1) <= cnt_sig;
output <= gate_o(14);

end Behavioral;

RTL Analysis

This is schematic of my design

RTL form Vivado screenshot

Simulation

And major problem :

Simulation screenshot

Maybe it's vhdl code issue, I don't know every rule of vhdl programming yet, I hope someone with better experience can help me.

I think there is some problem with set and reset in ffd . I try many options but nothing helped.

1
How are you modelling the delays in your inverter chains, necessary for the ring oscillators to work? - user_1818839
That chains aren't necessary but they are useful. Their job is to shape pulse duration for oscillators. Of course STOP chain must be longer to ensure right order of start oscillators. I dont know exactly if that lenght is correct because i didnt do measurment yet. It's first prototype . - Arkady
"modelling delays in VHDL" might be a useful search term - user_1818839
Ok thanks I didn't know about that. You mean in design or in simulation? - Arkady
In simulation. In hardware you get the delays the hardware gives you. - user_1818839

1 Answers

0
votes

First of all: you're learning VHDL, and you have a Virtex-7??? I'm programming VHDL for 15 years now, but often only work with spartans... Virtex is just too expensive. Restectp.

But anyhow

inv_g_chain : for i in 1 to gate_o'high generate
     gate_o(i) <= not gate_o(i-1);
end generate;

What are you trying to do here? I expect you want to use inverters to get some delay? Only, in VHDL concurrent assignment is instantaneous, so it does not work. You should add the delay manually. E.g.:

 gate_o(i) <= not gate_o(i-1) after 10 ns;

by the way, do you know that you could use generics, more links to have a variable inverter delay chain length? Then you could combine INV_chain_13 and INV_chain_15 into one entity.

Then you have multiple drivers for the same signal:

gate_o(1) <= not gate_o(0);

and

gate_o(1) <= cnt_sig;

Multiple drivers does not work properly. And what's up with cnt_sig being of the inout type? <= is not a bidirectional assignment. VHDL is not good at bidirectional assignments, so try a different approach.

You are trying to build an asynchronous system. It is possible, but quite difficult. Please consider making something synchronous first, to get some experience.... Now you're trying to do F1 at your first driving lesson.