Xilinx vhdl counter recognised as register

Discussion in 'VHDL' started by Sanka Piyaratna, May 9, 2006.

  1. Hi,

    I have a peice of VHDL code that has a counter implemented as shown below:

    signal rx_frame_counter : unsigned(REGISTER_SIZE - 1 downto 0);

    frame_counter <= frame_counter + 1;
    if frame_counter >= registered_error_freq then
    ----
    end if;

    Post synthesis report from ISE 8.1 (xst), tells me that it recognised
    frame_counter as a register. Shouldn't frame_counter be recognised as a
    counter to be the optimum design. My question is why this is happening
    and also is there any way to tell the xst to recognise this as a counter.

    Thank you,

    Sanka
     
    Sanka Piyaratna, May 9, 2006
    #1
    1. Advertising

  2. Sanka Piyaratna

    Guest

    Sorry, but if you don't post the code you actually use, how can anyone
    tell
    what you are actually doing ?

    I assume that your

    frame_counter <= frame_counter + 1;

    statement is in a process (otherwise it doesn't make sense) ?
    How is it implemented exactly ? (Any resets , enable signals ... ?)

    so long
    lundril
     
    , May 9, 2006
    #2
    1. Advertising

  3. My appologies.

    This code is implemented in a process and this particular process is
    very large, but the process where the counter is implemented as follows.

    Sanka

    p_main_sm : process (rxclk_i, rst_i)
    variable tmp_header : std_logic_vector(HEADER_SIZE - 1 downto 0);
    variable local_ref_parift : std_logic;
    variable local_parity_bit : std_logic;
    begin -- process p_main_sm
    if rst_i = '1' then -- asynchronous reset (active low)
    rxstart_ind_o <= '0';
    rxdata_valid_o <= '0';
    rxend_ind_o <= '0';
    stateID <= Idle;
    data_counter <= (others => '0');
    rxcca_ind_o <= '0';
    rxcca_ind_internal <= '0';
    frame_counter <= (others => '0');
    rxdatarate_z1 <= (others => '0');
    rxlength_z1 <= (others => '0');
    header <= (others => '0');
    rxdata_o <= '0';
    rxdata_o_zm1 <= '0';
    rxdata_valid_o_zm1 <= '0';
    rxerror_o_zm1 <= (others => '0');
    tsf_timeval <= (others => '0');
    error_bit_counter <= (others => '0');
    add_error_flag <= '0';
    rx_frame_counter <= (others => '0');
    parity_error_flag <= '0';
    state_debug <= (others => '0');
    inc_datacounter_flag <= '0';
    rst_data_counter_flag <= '0';
    registered_preambles_num <= (others => '0');
    registered_error_freq <= (others => '0');
    registered_cca_trig_point <= (others => '0');
    registered_corr_bit_loc <= (others => '0');
    rxerror_o <= (others => '0');
    rxdatarate_o <= (others => '0');
    rxlength_o <= (others => '0');
    elsif rxclk_i'event and rxclk_i = '1' then -- rising clock edge
    -- create pulse signals
    rxstart_ind_o <= '0';
    rxdata_valid_o_zm1 <= '0';
    rxend_ind_o <= '0';
    inc_datacounter_flag <= '0';
    rst_data_counter_flag <= '0';
    -- registered inputs
    registered_preambles_num <= tmp_preambles_num;
    registered_error_freq <= tmp_error_freq;
    registered_cca_trig_point <= tmp_cca_trig_point;
    registered_corr_bit_loc <= tmp_corr_bit_loc;

    -- data counter updated on the inc_counter_flag
    if rst_data_counter_flag = '1' then
    data_counter <= (others => '0');
    elsif inc_datacounter_flag = '1' then
    data_counter <= data_counter + 1;
    end if;

    if clear_error_reg = '1' then
    rxerror_o_zm1 <= (others => '0');
    end if;

    -- set error bit if a colision is detected
    if error_data_enable = '1' then
    rxerror_o_zm1(3) <= '1';
    end if;

    -- detect fifo full
    if full_a = '1' then
    rxerror_o_zm1(1) <= '1';
    end if;
    if full_b = '1' then
    rxerror_o_zm1(2) <= '1';
    end if;

    if common_data_valid = '0' then
    stateID <= Idle;
    if stateID /= Idle then
    rxend_ind_o <= '1';
    --rxcca_ind_o <= '0';
    rxcca_ind_internal <= '0';
    rst_data_counter_flag <= '1';
    end if;
    else

    if data_valid = '1' then

    case stateID is
    when Idle =>
    inc_datacounter_flag <= '1';

    tsf_timeval <= tsf_reg;
    rx_frame_counter <= rx_frame_counter + 1;
    -- count the number of frames
    frame_counter <= frame_counter + 1;
    stateID <= WaitRxStart;
    state_debug <= "000";

    when WaitRxStart =>
    inc_datacounter_flag <= '1';
    if data_counter = registered_cca_trig_point then
    --rxcca_ind_o <= '1';
    rxcca_ind_internal <= '1';
    stateID <= WaitStartData;
    state_debug <= "001";
    end if;


    when WaitStartData =>
    inc_datacounter_flag <= '1';
    if data_counter = registered_preambles_num then
    rst_data_counter_flag <= '1';
    if registered_error_freq /= 0 then
    if frame_counter >= registered_error_freq then
    add_error_flag <= '1';
    error_bit_counter <= registered_corr_bit_loc;
    frame_counter <= (others => '0');
    end if;
    end if;
    state_debug <= "010";
    stateID <= ReceiveHeader;
    end if;



    when ReceiveHeader =>
    inc_datacounter_flag <= '1';
    -- if the data bit counter is where the error should be
    -- introduced flip the bit corresponding to the bit location
    if (add_error_flag = '1' and data_counter =
    error_bit_counter) then
    tmp_header := header(HEADER_SIZE - 2 downto 0) &
    not(data_val);
    add_error_flag <= '0';
    rxerror_o_zm1(4) <= '1';
    else
    tmp_header := header(HEADER_SIZE - 2 downto 0) & data_val;
    end if;

    if data_counter = HEADER_SIZE - 1 then

    rxdatarate_z1 <= tmp_header(HEADER_SIZE - 1 downto
    HEADER_SIZE - TXDR_SIZE);
    rxlength_z1 <=
    tmp_header(HEADER_SIZE - TXDR_SIZE - 1 downto
    HEADER_SIZE - TXDR_SIZE - DATALEN_SIZE);
    local_parity_bit :=
    tmp_header(HEADER_SIZE - TXDR_SIZE - DATALEN_SIZE - 1);
    local_ref_parift := '0';

    for kk in HEADER_SIZE - 1 downto
    HEADER_SIZE - TXDR_SIZE - DATALEN_SIZE loop
    local_ref_parift := local_ref_parift xor tmp_header(kk);
    end loop; -- kk

    if local_ref_parift /= local_parity_bit then
    parity_error_flag <= '1';
    else
    parity_error_flag <= '0';
    end if;
    stateID <= WaitSettle;
    state_debug <= "011";
    end if;
    header <= tmp_header;




    when ReceiveData =>
    inc_datacounter_flag <= '1';
    -- bit counter matches the register indicated value
    if (add_error_flag = '1'
    and data_counter = error_bit_counter) then

    rxdata_o_zm1 <= not(data_val);
    add_error_flag <= '0';
    rxerror_o_zm1(5) <= '1';
    else
    rxdata_o_zm1 <= data_val;
    end if;
    rxdata_valid_o_zm1 <= '1';

    when others => null;
    end case;
    end if; -- if data_valid = '1' then

    if stateID = WaitSettle then
    if parity_error_flag = '1' then
    rxerror_o_zm1(0) <= '1';
    end if;
    -- pull the rxstart_ind_o high
    rxstart_ind_o <= '1';
    state_debug <= "100";
    stateID <= ReceiveData;

    end if;

    end if;

    rxcca_ind_o <= rxcca_ind_internal;
    rxdata_o <= rxdata_o_zm1;
    rxdata_valid_o <= rxdata_valid_o_zm1;
    rxerror_o <= rxerror_o_zm1;
    rxdatarate_o <= rxdatarate_z1;
    rxlength_o <= rxlength_z1;

    end if;
    end process p_main_sm;

    wrote:
    > Sorry, but if you don't post the code you actually use, how can anyone
    > tell
    > what you are actually doing ?
    >
    > I assume that your
    >
    > frame_counter <= frame_counter + 1;
    >
    > statement is in a process (otherwise it doesn't make sense) ?
    > How is it implemented exactly ? (Any resets , enable signals ... ?)
    >
    > so long
    > lundril
    >
     
    Sanka Piyaratna, May 9, 2006
    #3
  4. Sanka Piyaratna

    KJ Guest

    This has nothing to do with the question about the counter but I'm
    always amazed when I see the following line of code (copied from the
    post)

    elsif rxclk_i'event and rxclk_i = '1' then -- rising clock edge

    instead of

    elsif rising_edge(rxclk_i) then

    The 'rising_edge' function is defined in the same ieee library where
    'std_logic' is. It's much cleaner, more correct and doesn't require
    comments to know what it does.

    KJ
     
    KJ, May 10, 2006
    #4
  5. Sanka Piyaratna

    KJ Guest

    OK, now to be back ON topic this time. The posted question was...

    > Post synthesis report from ISE 8.1 (xst), tells me that it recognised
    > frame_counter as a register. Shouldn't frame_counter be recognised as a
    > counter to be the optimum design. My question is why this is happening
    > and also is there any way to tell the xst to recognise this as a counter.


    My question to you are:
    - Why do you think how ISE 8.1 calls it matters? (Hint: It doesn't)
    - What do you think a counter consists of? (Hint: Registers and
    combinatorial logic)

    If the code in your design
    - Meets all of the requirements of your application (i.e. function,
    performance, timing, power, etc.)
    - And all the constraints (part, package, airflow, etc.)

    then it don't sweat what ISE calls it. If you want an 'optimum' design
    then you first you have to define your 'optimization function' and that
    will go right back to the requirements and constraints.

    KJ
     
    KJ, May 10, 2006
    #5
  6. On 2006-05-10, KJ <> wrote:
    > This has nothing to do with the question about the counter but I'm
    > always amazed when I see the following line of code (copied from the
    > post)
    >
    > elsif rxclk_i'event and rxclk_i = '1' then -- rising clock edge
    >
    > instead of
    >
    > elsif rising_edge(rxclk_i) then
    >
    > The 'rising_edge' function is defined in the same ieee library where
    > 'std_logic' is. It's much cleaner, more correct and doesn't require
    > comments to know what it does.
    >


    For myself.. I don't need a comment to understand what it's do... it's
    obvious.. If there's an event on the signal and after this event you
    look at the signal and the value is one.. for sure it's a rising edge..

    I guest.. a lot of people use that because they get used to it long time
    ago when "rising_edge" keyword was not known by their old legacy vhdl
    interpreter.. The "if clk'event and clk = '1'" way is the original
    way to define a rising edge (or falling edge) in vhdl. May be some
    others people start with something that support it but learn it at
    school the way the teacher use it... who knows..

    Personnally.. I don't care... I understand both way and both generate
    exactly the same logic.

    --
    Martin
     
    Martin Gagnon, May 11, 2006
    #6
  7. Sanka Piyaratna

    Dave Pollum Guest

    Sanka Piyaratna wrote:
    > My appologies.
    >
    > This code is implemented in a process and this particular process is
    > very large, but the process where the counter is implemented as follows.
    >
    > Sanka
    >
    > p_main_sm : process (rxclk_i, rst_i)
    > variable tmp_header : std_logic_vector(HEADER_SIZE - 1 downto 0);
    > variable local_ref_parift : std_logic;
    > variable local_parity_bit : std_logic;
    > begin -- process p_main_sm
    > if rst_i = '1' then -- asynchronous reset (active low)
    > rxstart_ind_o <= '0';
    > rxdata_valid_o <= '0';
    > rxend_ind_o <= '0';
    > stateID <= Idle;
    > data_counter <= (others => '0');
    > rxcca_ind_o <= '0';
    > rxcca_ind_internal <= '0';
    > frame_counter <= (others => '0');
    > rxdatarate_z1 <= (others => '0');
    > rxlength_z1 <= (others => '0');
    > header <= (others => '0');
    > rxdata_o <= '0';
    > rxdata_o_zm1 <= '0';
    > rxdata_valid_o_zm1 <= '0';
    > rxerror_o_zm1 <= (others => '0');
    > tsf_timeval <= (others => '0');
    > error_bit_counter <= (others => '0');
    > add_error_flag <= '0';
    > rx_frame_counter <= (others => '0');
    > parity_error_flag <= '0';
    > state_debug <= (others => '0');
    > inc_datacounter_flag <= '0';
    > rst_data_counter_flag <= '0';
    > registered_preambles_num <= (others => '0');
    > registered_error_freq <= (others => '0');
    > registered_cca_trig_point <= (others => '0');
    > registered_corr_bit_loc <= (others => '0');
    > rxerror_o <= (others => '0');
    > rxdatarate_o <= (others => '0');
    > rxlength_o <= (others => '0');
    > elsif rxclk_i'event and rxclk_i = '1' then -- rising clock edge
    > -- create pulse signals
    > rxstart_ind_o <= '0';
    > rxdata_valid_o_zm1 <= '0';
    > rxend_ind_o <= '0';
    > inc_datacounter_flag <= '0';
    > rst_data_counter_flag <= '0';
    > -- registered inputs
    > registered_preambles_num <= tmp_preambles_num;
    > registered_error_freq <= tmp_error_freq;
    > registered_cca_trig_point <= tmp_cca_trig_point;
    > registered_corr_bit_loc <= tmp_corr_bit_loc;
    >
    > -- data counter updated on the inc_counter_flag
    > if rst_data_counter_flag = '1' then
    > data_counter <= (others => '0');
    > elsif inc_datacounter_flag = '1' then
    > data_counter <= data_counter + 1;
    > end if;
    >
    > if clear_error_reg = '1' then
    > rxerror_o_zm1 <= (others => '0');
    > end if;
    >
    > -- set error bit if a colision is detected
    > if error_data_enable = '1' then
    > rxerror_o_zm1(3) <= '1';
    > end if;
    >
    > -- detect fifo full
    > if full_a = '1' then
    > rxerror_o_zm1(1) <= '1';
    > end if;
    > if full_b = '1' then
    > rxerror_o_zm1(2) <= '1';
    > end if;
    >
    > if common_data_valid = '0' then
    > stateID <= Idle;
    > if stateID /= Idle then
    > rxend_ind_o <= '1';
    > --rxcca_ind_o <= '0';
    > rxcca_ind_internal <= '0';
    > rst_data_counter_flag <= '1';
    > end if;
    > else
    >
    > if data_valid = '1' then
    >
    > case stateID is
    > when Idle =>
    > inc_datacounter_flag <= '1';
    >
    > tsf_timeval <= tsf_reg;
    > rx_frame_counter <= rx_frame_counter + 1;
    > -- count the number of frames
    > frame_counter <= frame_counter + 1;
    > stateID <= WaitRxStart;
    > state_debug <= "000";
    >
    > when WaitRxStart =>
    > inc_datacounter_flag <= '1';
    > if data_counter = registered_cca_trig_point then
    > --rxcca_ind_o <= '1';
    > rxcca_ind_internal <= '1';
    > stateID <= WaitStartData;
    > state_debug <= "001";
    > end if;
    >
    >
    > when WaitStartData =>
    > inc_datacounter_flag <= '1';
    > if data_counter = registered_preambles_num then
    > rst_data_counter_flag <= '1';
    > if registered_error_freq /= 0 then
    > if frame_counter >= registered_error_freq then
    > add_error_flag <= '1';
    > error_bit_counter <= registered_corr_bit_loc;
    > frame_counter <= (others => '0');
    > end if;
    > end if;
    > state_debug <= "010";
    > stateID <= ReceiveHeader;
    > end if;
    >
    >
    >
    > when ReceiveHeader =>
    > inc_datacounter_flag <= '1';
    > -- if the data bit counter is where the error should be
    > -- introduced flip the bit corresponding to the bit location
    > if (add_error_flag = '1' and data_counter =
    > error_bit_counter) then
    > tmp_header := header(HEADER_SIZE - 2 downto 0) &
    > not(data_val);
    > add_error_flag <= '0';
    > rxerror_o_zm1(4) <= '1';
    > else
    > tmp_header := header(HEADER_SIZE - 2 downto 0) & data_val;
    > end if;
    >
    > if data_counter = HEADER_SIZE - 1 then
    >
    > rxdatarate_z1 <= tmp_header(HEADER_SIZE - 1 downto
    > HEADER_SIZE - TXDR_SIZE);
    > rxlength_z1 <=
    > tmp_header(HEADER_SIZE - TXDR_SIZE - 1 downto
    > HEADER_SIZE - TXDR_SIZE - DATALEN_SIZE);
    > local_parity_bit :=
    > tmp_header(HEADER_SIZE - TXDR_SIZE - DATALEN_SIZE - 1);
    > local_ref_parift := '0';
    >
    > for kk in HEADER_SIZE - 1 downto
    > HEADER_SIZE - TXDR_SIZE - DATALEN_SIZE loop
    > local_ref_parift := local_ref_parift xor tmp_header(kk);
    > end loop; -- kk
    >
    > if local_ref_parift /= local_parity_bit then
    > parity_error_flag <= '1';
    > else
    > parity_error_flag <= '0';
    > end if;
    > stateID <= WaitSettle;
    > state_debug <= "011";
    > end if;
    > header <= tmp_header;
    >
    >
    >
    >
    > when ReceiveData =>
    > inc_datacounter_flag <= '1';
    > -- bit counter matches the register indicated value
    > if (add_error_flag = '1'
    > and data_counter = error_bit_counter) then
    >
    > rxdata_o_zm1 <= not(data_val);
    > add_error_flag <= '0';
    > rxerror_o_zm1(5) <= '1';
    > else
    > rxdata_o_zm1 <= data_val;
    > end if;
    > rxdata_valid_o_zm1 <= '1';
    >
    > when others => null;
    > end case;
    > end if; -- if data_valid = '1' then
    >
    > if stateID = WaitSettle then
    > if parity_error_flag = '1' then
    > rxerror_o_zm1(0) <= '1';
    > end if;
    > -- pull the rxstart_ind_o high
    > rxstart_ind_o <= '1';
    > state_debug <= "100";
    > stateID <= ReceiveData;
    >
    > end if;
    >
    > end if;
    >
    > rxcca_ind_o <= rxcca_ind_internal;
    > rxdata_o <= rxdata_o_zm1;
    > rxdata_valid_o <= rxdata_valid_o_zm1;
    > rxerror_o <= rxerror_o_zm1;
    > rxdatarate_o <= rxdatarate_z1;
    > rxlength_o <= rxlength_z1;
    >
    > end if;
    > end process p_main_sm;
    >
    > wrote:
    > > Sorry, but if you don't post the code you actually use, how can anyone
    > > tell
    > > what you are actually doing ?
    > >
    > > I assume that your
    > >
    > > frame_counter <= frame_counter + 1;
    > >
    > > statement is in a process (otherwise it doesn't make sense) ?
    > > How is it implemented exactly ? (Any resets , enable signals ... ?)
    > >
    > > so long
    > > lundril
    > >


    > p_main_sm : process (rxclk_i, rst_i)
    > ...
    > begin -- process p_main_sm
    > if rst_i = '1' then -- asynchronous reset (active low)


    In the above line, either the comment is wrong or the code is!
    -Dave Pollum
     
    Dave Pollum, May 11, 2006
    #7
    1. Advertising

Want to reply to this thread or ask your own question?

It takes just 2 minutes to sign up (and it's free!). Just click the sign up button to choose a username and then you can ask your own questions on the forum.
Similar Threads
  1. Georges Konstantinidis

    asynchronous counter an Xilinx FPGA for a newbie

    Georges Konstantinidis, Jan 30, 2004, in forum: VHDL
    Replies:
    12
    Views:
    6,014
  2. The Eeediot
    Replies:
    3
    Views:
    2,304
    =?Utf-8?B?UnVsaW4gSG9uZw==?=
    Dec 22, 2004
  3. afd
    Replies:
    1
    Views:
    8,549
    Colin Paul Gloster
    Mar 23, 2007
  4. Replies:
    1
    Views:
    1,027
    Mike Treseler
    Apr 27, 2007
  5. George2
    Replies:
    1
    Views:
    850
    Alf P. Steinbach
    Jan 31, 2008
Loading...

Share This Page