I am trying to obtain two digit number from a std_logic_vector. I know... it is not a professional way to do that(the way I made it), but I am in the process of learning. My real problem is the 'while' loop. I can't figure it out why it is an infinite loop. Anyone who can help? In testbench the value for d is "10010"; here is the error and the code:
[Synth 8-3380]loop condition does not converge after 2000 iterations [afisare.vhd:30]
line 30 is while aux>noua loop
. I am synthesizing and want to simulate after that
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.NUMERIC_STD.ALL;
use ieee.std_logic_arith.all;
use ieee.std_logic_unsigned.all;
entity bcd is
port( y0: out std_logic_vector(6 downto 0);
y1: out std_logic_vector(6 downto 0);
d: in std_logic_vector(4 downto 0);
anode: out std_logic_vector(7 downto 0));
end bcd;
architecture afis of bcd is
begin
process(d)
variable prima: integer;
variable aux: std_logic_vector(4 downto 0);
variable din: std_logic_vector(3 downto 0);
variable noua: std_logic_vector(4 downto 0);
variable unu: std_logic;
variable zero: std_logic;
begin
prima:=0;
noua:="01001";
aux:=d;
unu:='1';
zero:='0';
while aux>noua loop
if (aux(4)=unu and aux(3)=zero) then
aux(4):=zero;
end if;
if (aux(1)=unu and aux(0)=zero) then
aux(1):=zero;
end if;
aux:=aux xor noua;
prima:=prima+1;
end loop;
din:=aux(3 downto 0);
case din is
when "0000"=> y0<="0000001";
when "0001"=>y0<="1001111";
when "0010"=>y0<="0010010";
when "0011"=>y0<="0000110";
when "0100"=>y0<="1001100";
when "0101"=>y0<="0100100";
when "0110"=>y0<="0100000";
when "0111"=>y0<="0001111";
when "1000"=>y0<="0000000";
when "1001"=>y0<="0000100";
when others=>y0<="0110110";
end case;
case prima is
when 0=>y1<="0000001";
when 1=>y1<="1001111";
when 2=>y1<="0010010";
when 3=>y1<="0000110";
when others=>y1<="0110110";
end case;
anode<="11111100";
end process;
end afis;
The synthesizer does not care about the testbench, it tries to create a piece of hardware that would be equivalent to your loop and would work for any possible input. And in order to do this it somehow tries all possibilities (32). Unfortunately it is apparently not smart enough to detect that this loop always terminates in at most 3 iterations (not sure of this "3", I may be wrong).
Generally speaking, for synthesis, it is better to use loops with caution (static bounds of for loops, static condition of while loops). In this case it is difficult to say if you are beyond Vivado's capabilities or not. If the documentation says that non-static conditions of while loops are supported for synthesis you can open a service request, you found a bug.
Anyway, it would be better to describe this differently. Try maybe to fix the number of iterations (after verifying by simulation or plain reasoning that 3 is enough, of course, I am just guessing):
for i in 1 to 3 loop
if aux>noua then
if (aux(4)=unu and aux(3)=zero) then
aux(4):=zero;
end if;
if (aux(1)=unu and aux(0)=zero) then
aux(1):=zero;
end if;
aux := aux xor noua;
prima:=prima+1;
end if;
end loop;