I have problems with the output of the vhdl entity that always sends out U.
I looked at various forums but I could not find a solution.
The project is a 5-story lift that has to wait 5 seconds to close the door and 10 seconds to get to the next plane up to the target.
Use Logisim (v 2.13.22) and ghdl (v 0.29.1).
Does anyone have any idea what the problem might be? Thanks in advance
Here the vhdl code i made.
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity Elevator is
Port (
clk : in std_logic;
rst : in std_logic;
rstPorta : in std_logic;
rstMotore : in std_logic;
zero : in std_logic;
one : in std_logic;
two : in std_logic;
three : in std_logic;
four : in std_logic;
upEngine : out std_logic;
downEngine : out std_logic;
ledReady: out std_logic;
ledUp: out std_logic;
ledDown: out std_logic;
ledDoorOpen: out std_logic;
ledDoorClosed: out std_logic;
ledBusy: out std_logic;
ledUsable: out std_logic;
doorOpenEngine : out std_logic;
doorCloseEngine : out std_logic;
cntPiano : out std_logic_vector(4 downto 0)
);
end Elevator;
architecture Ascensore of Elevator is
type state_type is (s0,s1,s2,s3,s4);
signal current_s,next_s: state_type;
signal cf, df: std_logic_vector(3 downto 0); -- vettore a 4 bit
signal countPorta: std_logic_vector(2 downto 0); -- vettore a 3 bit
signal countMotore: std_logic_vector(3 downto 0); -- vettore a 4 bit
begin
-- Questo processo modifica il segnale countPorta in modo tale da segnalare il tempo rimanente prima della chiusura della porta
process (clk,rstPorta)
begin
if (rstPorta='1') then countPorta <= "000"; -- Condizione di bypass della porta, apre la porta senza tempi d'attesa, per casi di emergenza
elsif (clk'event and clk='1') then
if (countPorta = "100") then countPorta <= "011";
elsif (countPorta = "011") then countPorta <= "010";
elsif (countPorta = "010") then countPorta <= "001";
else countPorta <= "000";
end if;
end if;
end process;
-- Questo processo modifica il segnale countMotore in modo tale da segnalare il tempo necessario all'arrivo al piano successivo
process (clk,rstMotore)
begin
if (rstMotore='1') then countMotore <= "0000"; -- Condizione di bypass del motore, ferma lo spostamento in casi di emergenza
elsif (clk'event and clk='1') then
if (countMotore = "1001") then countMotore <= "1000";
elsif (countMotore = "1000") then countMotore <= "0111";
elsif (countMotore = "0111") then countMotore <= "0110";
elsif (countMotore = "0110") then countMotore <= "0101";
elsif (countMotore = "0101") then countMotore <= "0100";
elsif (countMotore = "0100") then countMotore <= "0011";
elsif (countMotore = "0011") then countMotore <= "0010";
elsif (countMotore = "0010") then countMotore <= "0001";
else countMotore <= "0000";
end if;
end if;
end process;
-- Questo processo serve a controllare le chiamate dell ascensore nei vari piani
process (clk,rst)
begin
-- si inizializza ascensore considerando che esso parta dal piano 0 in una condizione priva di richieste esterne (stato 3)
if (rst='1') then
df <= "0000";
cf <= "0000";
upEngine <= '1';
downEngine <= '1';
ledReady <= '1';
ledUp <= '1';
ledDown <= '1';
ledDoorOpen <= '1';
ledDoorClosed <= '1';
ledBusy <= '1';
ledUsable <= '1';
doorOpenEngine <= '1';
doorCloseEngine <= '1';
current_s <= s3;
end if;
-- verifica se vi sono state richieste nei vari piani ad ogni ciclo di clock assegnando a df (desired floor) il piano della richiesta
if (clk'event and clk='1') then
if (zero = '1') then df <= "0000";
elsif (one = '1') then df <= "0001";
elsif (two = '1') then df <= "0010";
elsif (three = '1') then df <= "0011";
elsif (four = '1') then df <= "0100";
end if;
-- lo stato corrente corrisponde allo stato successivo
current_s <= next_s;
end if;
end process;
-- Processo Ascensore
process (current_s, cf, df, clk)
begin
if (clk'event and clk='1') then
case current_s is
-- STATO 0: fase di salita ascensore fino a che il piano desiderato non e' uguale al piano corrente
when s0 =>
if(cf < df) then
upEngine <= '1';
-- se il motore non e' ancora arrivato al piano resta nello Stato 0
if((countMotore= "1001") or (countMotore= "1000") or (countMotore= "0111") or (countMotore= "0110") or (countMotore= "0101") or (countMotore= "0100") or (countMotore = "0011") or (countMotore = "0010") or (countMotore = "0001"))
then then next_s <= s0;
end if;
-- se sono passati 10 sec, siamo arrivati al piano. cf verra' aumentato
if(countMotore = "0000") then
if (cf = "0000") then cf <= "0001";
elsif (cf = "0001") then cf <= "0010";
elsif (cf = "0010") then cf <= "0011";
elsif (cf = "0011") then cf <= "0100";
end if;
end if;
-- se il piano desiderato e' > del corrente fai un altro ciclo dello Stato 0
if(cf < df) then
next_s <= s0;
end if;
-- se il piano desiderato e' = al corrente vai nello Stato 2
if(cf = df) then
ledUp <= '0';
upEngine <= '0';
next_s <= s2;
countPorta <= "100";
end if;
end if;
-- STATO 1: fase di discesa ascensore fino a che il piano desiderato non e' uguale al piano corrente
when s1 =>
if(cf > df) then
downEngine <= '1';
-- se il motore non e' ancora arrivato al piano resta nello Stato 1
if((countMotore= "1001") or (countMotore= "1000") or (countMotore= "0111") or (countMotore= "0110") or (countMotore= "0101") or (countMotore= "0100") or (countMotore = "0011") or (countMotore = "0010") or (countMotore = "0001")) then
elsif(countMotore = "0000") then next_s <= s1;
end if;
-- se sono passati 10 sec, siamo arrivati al piano. cf verra' diminuito
if(countMotore = "0000") then
if (cf = "0100") then cf <= "0011";
elsif (cf = "0011") then cf <= "0010";
elsif (cf = "0010") then cf <= "0001";
elsif (cf = "0001") then cf <= "0000";
else cf <= cf;
end if;
end if;
-- se il piano desiderato e' < del corrente fai un altro ciclo dello Stato 1
if (cf > df) then
next_s <= s1;
end if;
-- se il piano desiderato e' = al corrente vai nello Stato 2
if(cf = df) then
ledDown <= '0';
downEngine <= '0';
next_s <= s2;
countPorta <= "100";
end if;
end if;
-- STATO 2: fase di apertura della porta nel piano desiderato
when s2 =>
if(countPorta = "000") then next_s <= s3;
else next_s <= s2;
end if;
-- STATO 3: ascensore in attesa di richieste con porta aperta
when s3 =>
doorOpenEngine <= '1';
doorCloseEngine <= '0';
ledDoorOpen <= '1';
ledDoorClosed <= '0';
ledReady <= '1';
ledUp <= '0';
ledDown <= '0';
ledBusy <= '0';
ledUsable <= '1';
if(cf = df) then
next_s <= s3;
end if;
if ((cf<df) or (cf>df)) then
countPorta <= "100";
next_s <= s4;
end if;
-- STATO 4: fase di chiusura della porta e selezione dello stato successivo per la salita (Stato 0) o discesa (Stato 1) dell'ascensore
when s4 =>
if((countPorta = "100") or (countPorta = "011") or (countPorta = "010") or (countPorta = "001")) then
next_s <= s4;
elsif((countPorta = "000") and (cf<df)) then
doorOpenEngine <= '0';
doorCloseEngine <= '1';
ledDoorOpen <= '0';
ledDoorClosed <= '1';
ledReady <= '0';
ledUp <= '1';
ledDown <= '0';
ledBusy <= '1';
ledUsable <= '0';
countMotore <= "1001";
next_s <= s0;
elsif((countPorta = "000") and (cf>df)) then
doorOpenEngine <= '0';
doorCloseEngine <= '1';
ledDoorOpen <= '0';
ledDoorClosed <= '1';
ledReady <= '0';
ledUp <= '0';
ledDown <= '1';
ledBusy <= '1';
ledUsable <= '0';
countMotore <= "1001";
next_s <= s1;
end if;
end case;
end if;
end process;
end Ascensore;
Most of the times, errors like this occur because of erroneous connection of ports in testbench, for to be sure about this, you can check the connection, but if you can't find any mistake, you can test your module without testbench and use force value and force clock But if it is still unknown, your mistake is in wave selection to view.
good luck
I am not sure where you are at with this design but I am hoping you made some progress on your own since posting.
Now, to the heart of your problem. The signals upEngine, downEngine, ... , doorCloseEngine and current_s are not assigned in a single process. They are driven in both the third and fourth process statements which therefore constitutes a case of multiply driven nets.
In your simulator, look for a command that will report the drivers for any given signal. Here is what I see in Vivado for the upEngine signal (your line numbers might not match exactly -- I was tweaking the code):
report_drivers {/Elevator/upEngine}
Drivers for /Elevator/upEngine
U : Net /Elevator/upEngine
U : Driver /Elevator/line__125 at C:/temp/new1.vhd:125
1 : Driver /Elevator/line__82 at C:/temp/new1.vhd:82
This is somewhat subtle. VHDL employs a resolution function to decide what to do when there are multiple drivers. In this case, since the signals are std_logic type, the std_logic_1164 library specifies the resolution function and it says that 'U' always wins in a contest between two values. So, no matter what is driven in the third process, the uninitialized signals in the 4th process will contribute 'U' and determine the signal state. (At least until the state machine gets to a state that actually drives a known value onto upEngine).
You might have noticed in your simulation that signals ledUp and ledDown were 'X' after the first rising clock edge. That is because they are both multiply driven as well -- however one driver contributes '1' and the other '0'. The resolution function says in that case that the result is unknown -- 'X'.
Check the log output of your synthesis tool as it should report these multiply driven nets as errors or possibly just warnings. (There is a time and place for multiply driven nets in designs that use tri-state signal assignments or ones that employ wired-and/or logic.)
Happily, the solution is simply to merge everything into a single process and try again. I suspect you will have additional work to do as the logical function of your design is not apparent to me in my cursory examination of it. (As a useful exercise, change all std_logic types to bit and re-analyze. The multiply driven nets stand out like a sore thumb.)
Here are some tips concerning the coding style you have employed:
Use the rising_edge() function rather than clk'event and clk='1'. While unusual, the later approach can lead to subtle simulation errors if the clk transitions to '1' from say 'X' or 'U' which might lead you to believe the circuit is working only to discover that the hardware behaves differently.
You want your state machine to be reset. So the Processo Ascensore should have either a synchronous or asynchronous reset signal clearing the state register.
You have several if statements that appear to be decrementing various signals. The if-elsif-elsif compound statement synthesizes to a priority encoder which will result in longer combinatorial paths and possibly slower timing. Always look for an opportunity to use a case statement to implement parallel logic.
With that said, what your VHDL really needs is to use unsigned type signals to implement the decrement arithmetic necessary for the various counters in your design. For example, the countPorta signal should be declared as unsigned(2 downto 0) and the clocked process that operates on it should simply specify countPorta <= countPorta - "001"; -- same for the other decrementing counters.
The third process incorrectly (but not illegally) specifies two distinct if clauses where only one is necessary. In fact, the second if clause always 'wins' as it comes later when evaluating the assignment to signal df.
Since you have not supplied a testbench after your original post, as requested by #user1155120, I can go no further. Good luck.
Related
I am coding a 16-bit CPU for a school project and I've run into an issue that has dumbfounded me. The first three steps of my clock cycle are naturally to increment the program counter and load a new instruction into the instruction register. So the problem; the value in the program counter increments as expected but stalls at 6 for several cycles then picks up again and stalls at 12 for several more, again at 18 and then 24, this is as far as I've let it run, I assume it'll persist at succeeding multiples of six. I dunno if it is something to do with the way VHDL treats signed values, I edited the ALU code to achieve this by adding one to the Program Counter value instead of incrementing but there was no change, I changed the ALUs representation of the values to unsigned but that didn't help and I honestly cannot see why it would. My code is as follows:
library IEEE;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity CPU_1 is
port( prim_clk : in std_logic;
achtung : out std_logic_vector(15 downto 0) ;
HEX0, HEX1, HEX2 : out std_logic_vector(6 downto 0));
end CPU_1;
Architecture behaviour of Nandos is
signal sys_clk, clk, cu_s, cu_e: std_logic;
signal step : std_logic_vector(5 downto 0);
signal acc_ena, acc_set, pc_set, pc_ena: std_logic := 'Z';
signal data_bus, alu_acc : std_logic_vector(15 downto 0);--M_addr_bus,
component Clock
port( clk : in std_logic; --50 MHz
clk_s : out std_logic;--set data clk
clk_e : out std_logic);--enable data(on bus) clk
end component;
component Control_Unit
port( sys_clk, clk_s, clk_e : in std_logic;
acc_ena, acc_set, pc_set, pc_ena: out std_logic;
stepp : out std_logic_vector(5 downto 0));
end component;
component program_Counter
port( clk: in std_logic;
set, en : in std_logic;
pc_in : in std_logic_vector(15 downto 0);
pc_out : out std_logic_vector(15 downto 0));
end component;
component ALU
port( clk: in std_logic;
d1 : in std_logic_vector(15 downto 0);
d3 : out std_logic_vector(15 downto 0));
end component;
component accumulator
port( clk: in std_logic;
frm_ALU: in std_logic_vector(15 downto 0);
acc_set, acc_ena : in std_logic;
to_bus : out std_logic_vector(15 downto 0));
end component;
begin
HEX2(5 downto 0) <= step;--serves to demonstrate on the board that it is running
achtung <= data_bus;--debug what is on the bus
clk0 : Clock port map(prim_clk, cu_s, cu_e);
cu0 : Control_Unit port map(prim_clk, cu_s, cu_e, acc_ena, acc_set, pc_set, pc_ena, step);
p_c : program_Counter port map(prim_clk, pc_set, pc_ena, data_bus, data_bus);
alu0 : ALU port map(prim_clk, data_bus, alu_acc);
acc : accumulator port map(prim_clk, alu_acc, acc_set, acc_ena, data_bus);
end behaviour;
LIBRARY ieee;
USE ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity Control_Unit is
port( sys_clk, clk_s, clk_e : in std_logic;
acc_ena, acc_set, pc_set, pc_ena: out std_logic;
stepp : out std_logic_vector(5 downto 0)); --just to ko
end Control_Unit;
architecture behaviour of Control_Unit is
signal step : std_logic_vector(5 downto 0);
component Stepper
port( clk : in std_logic;
step : out std_logic_vector(5 downto 0));
end component;
begin
stpr : Stepper port map(sys_clk, step);
stepp <= step;
process(sys_clk, step)
begin
if rising_edge(sys_clk) then
if step(0) = '1' then
case clk_s is
when '1' =>
acc_set <= '1';
when '0' =>
acc_set <= '0';
end case;
case clk_e is
when '1' =>
pc_ena <= '1';
when '0' =>
pc_ena <= '0';
end case;
elsif step(1) = '1' then
case clk_s is
when '1' =>
null;
when '0' =>
null;
end case;
case clk_e is
when '1' =>
null;
when '0' =>
null;
end case;
elsif step(2) = '1' then
case clk_s is
when '1' =>
pc_set <= '1';
when '0' =>
pc_set <= '0';
end case;
case clk_e is
when '1' =>
acc_ena <= '1';
when '0' =>
acc_ena <= '0';
end case;
end if;
end if;
end process;
end behaviour;
LIBRARY ieee;
USE ieee.std_logic_1164.all;
use ieee.numeric_std.all;
ENTITY ALU IS
port( clk: in std_logic;
d1: in std_logic_vector(15 downto 0);
d3 : out std_logic_vector(15 downto 0));
END ALU;
ARCHITECTURE behaviour OF ALU IS
signal Zsig: signed(15 downto 0);
begin
process(clk, d1)
begin
if rising_edge(clk) then
Zsig <= signed(d1) + 1;
end if;
end process;
d3 <= std_logic_vector(signed(Zsig));
end behaviour;
LIBRARY ieee;
USE ieee.std_logic_1164.all;
entity Clock is
port( clk :in std_logic;
clk_s : out std_logic;
clk_e : out std_logic);
end Clock;
--slowing down the clock so I can track data flow.
architecture Behavioral of Clock is
signal count: integer := 1;
signal clock_1: std_logic := '1';
signal clock_2: std_logic := '0';
begin
process(clk)
begin
if rising_edge(clk) then
count <= count + 1;
if count = 12500000 then --10
clock_1 <= not clock_1;
count <= 1;
elsif count = 5000000 then--4
clock_2 <= not clock_2;
end if;
end if;
end process;
clk_e <= clock_1 or clock_2;
clk_s <= clock_1 and clock_2;
end Behavioral;
library ieee;
use ieee.std_logic_1164.all;
entity stepper is
port (clk : in std_logic;
step: out std_logic_vector(5 downto 0));
end stepper;
architecture behav of stepper is
signal count : integer := 0;
begin
Process(clk)
begin
if rising_edge(clk) then
count <= count+1;
if count = 0 then --0
step <= "000001";
elsif count = 23750000 then --19
step <= "000010";
elsif count = 48750000 then --39
step <= "000100";
elsif count = 73750000 then --59
step <= "001000";
elsif count = 98750000 then --79
step <= "010000";
elsif count = 123750000 then --99
step <= "100000";
elsif count = 148750000 then --119
count <= 0;
end if;
end if;
end Process;
end behav;
library IEEE;
use ieee.std_logic_1164.all;
entity program_Counter is
port( clk: in std_logic;
set, en : in std_logic;
pc_in : in std_logic_vector(15 downto 0);
pc_out : out std_logic_vector(15 downto 0));
end program_Counter;
Architecture behaviour of program_Counter is
signal RAM : std_logic_vector(15 downto 0);
begin
process(clk, RAM, set, en)
begin
if rising_edge(clk) then
if set = '1' then
RAM <= pc_in;
elsif en = '1' then
pc_out <= RAM;
else
pc_out <= "ZZZZZZZZZZZZZZZZ";
end if;
end if;
end process;
end behaviour;
library IEEE;
use ieee.std_logic_1164.all;
entity accumulator is
port( clk: in std_logic;
frm_ALU: in std_logic_vector(15 downto 0);
acc_set, acc_ena : in std_logic;
to_bus : out std_logic_vector(15 downto 0));
end accumulator;
Architecture behaviour of accumulator is
signal RAM : std_logic_vector(15 downto 0);
begin
process(clk, acc_set, acc_ena, RAM)
begin
if rising_edge(clk) then
if acc_set = '1' then
RAM <= frm_ALU;
elsif acc_ena = '1' then
to_bus <= RAM;
else
to_bus <= "ZZZZZZZZZZZZZZZZ";
end if;
end if;
end process;
end behaviour;
Sorry for what must be riddled with coding taboos. I feel I should point out that when I originally wrote the code it ran fine with an ADD instruction, I changed it to increment for simplification and didn't run into any problems that I can remember. Several additions later I start getting this error so I strip everything else down to bare bones, removing registers and such but here the error still is.
I use the Quartus II 13.0 software to code and an Altera DE2 EP2C35F672C6 to run the code. Thank you.
I found the problem, after preloading the program counter with the value for 5 and not immediately running into the error when it tried to increment 6 to 7 but instead at 11 it became clear that the logic was not the culprit. The steppers first stage lasts a little shorter than the others(1250000 ticks to be exact) and it desyncs after 6 cycles, after a few more cycles it syncs up again, runs correctly and desyncs again after 6 more. This has been resolved and the counter now increments endlessly, as desired.
I have condition.m, and it has inside it a loop that calculates the condition number of a user asked matrix:
if(p == 1)
for i = 1:co
for j = 1:li
somacolunas(j) = somacolunas(j) + A(j,i);
end
end
for i = 1:co
for j = 1:li
somacolunasinvA(j) = somacolunasinvA(j) + abs(invA)(j,i);
end
end
% encontrar o valor máximo
maxco = somacolunas(1);
for i = 1:length(somacolunas)
if somacolunas(i) > maxco
maxco = somacolunas(i);
end
end
maxcoinv = somacolunasinvA(1);
for y = 1:length(somacolunasinvA)
if somacolunasinvA(y) > maxcoinv
maxcoinv = somacolunasinvA(y);
end
end
printf('o número de condição segundo a norma 1 é: %3.2f\n', maxco * maxcoinv);
I want to call the condition.m file inside another m.file (that is in the same directory) and make use of the output vars (maxco and maxcoinv) to do some other math.
I know that i can do condition; inside the other m file to access the condition.m file. But how to get access to it's variables, and if i need pass values to condition.m for loop iterate?
Any ideas for the best method?
So I am a beginner in VHDL and I am trying to code a MIPS processor for a FPGA. The file for the CPU Register is not compiling. It is generating an error code as following Error (10818): Can't infer register for "Reg[0][2]" at cpu_register.vhd(32) because it does not hold its value outside the clock edge
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
entity cpu_register is
Port ( Source_Register_Address : in std_logic_vector(4 downto 0);
Target_Register_Address : in std_logic_vector(4 downto 0);
Destination_Register_Address : in std_logic_vector(4 downto 0);
Cyclic_Target_Register_Address : in std_logic_vector(4 downto 0);
Program_Counter : in std_logic_vector(31 downto 0);
Load_Data : in std_logic_vector(31 downto 0);
Execution_Result : in std_logic_vector(31 downto 0);
Operation_Code : in std_logic_vector(5 downto 0);
Source_Register_Data : out std_logic_vector(31 downto 0);
Target_Register_Data : out std_logic_vector(31 downto 0);
Clock : in std_logic);
end cpu_register;
architecture behavioral of cpu_register is
type Register_Array is array (0 to 31) of std_logic_vector(31 downto 0);
signal Reg: Register_Array;
begin
t1:process
(Operation_Code,Source_Register_Address,Target_Register_Address,Clock)
begin
Reg(0) <= "00000000000000000000000000000000";
Source_Register_Data <= Reg(CONV_INTEGER(Source_Register_Address));
Target_Register_Data <= Reg(CONV_INTEGER(Target_Register_Address));
end process;
t2: process (Clock)
begin
Reg(0) <= "00000000000000000000000000000000";
if (Clock'event and Clock='0') then
case Operation_Code is
when "000000" =>
if (Destination_Register_Address="00000") then
Reg(0) <= "00000000000000000000000000000000";
else
Reg(CONV_INTEGER(Destination_Register_Address)) <=
Execution_Result;
end if;
when "001000" | "001001" | "001100" | "001101" | "001110" | "001111" |
"001010" | "001011" =>
if (Cyclic_Target_Register_Address="00000") then
Reg(0) <= "00000000000000000000000000000000";
else
Reg(CONV_INTEGER(Cyclic_Target_Register_Address)) <= Execution_Result;
end if;
when "100011" =>
if (Cyclic_Target_Register_Address="00000") then
Reg(0) <= "00000000000000000000000000000000";
else
Reg(CONV_INTEGER(Cyclic_Target_Register_Address)) <= Load_Data;
end if;
when "000011" =>
Reg(31) <= Program_Counter;
when others =>
Reg(0) <= "00000000000000000000000000000000";
end case;
end if;
end process;
end behavioral;
Any help on how to fix it would be much appreciated. Thanks
Comment out the two Reg(0) assignments outside the if statement conditioned by clock'event and clock = '0'.
The assignment in t1 looks unintentional and can cause 'X's during simulation. You'd expect your synthesis software might complain as well.
t1:process
(Operation_Code,Source_Register_Address,Target_Register_Address,Clock)
begin
-- Reg(0) <= "00000000000000000000000000000000";
Source_Register_Data <= Reg(CONV_INTEGER(Source_Register_Address));
Target_Register_Data <= Reg(CONV_INTEGER(Target_Register_Address));
end process;
t2:
process (Clock)
begin
-- Reg(0) <= "00000000000000000000000000000000";
if Clock'event and Clock ='0' then
case Operation_Code is
when "000000" =>
if (Destination_Register_Address="00000") then
Reg(0) <= "00000000000000000000000000000000";
else
Reg(CONV_INTEGER(Destination_Register_Address)) <=
Execution_Result;
end if;
when "001000" | "001001" | "001100" |
"001101" | "001110" | "001111" |
"001010" | "001011" =>
if (Cyclic_Target_Register_Address="00000") then
Reg(0) <= "00000000000000000000000000000000";
else
Reg(CONV_INTEGER(Cyclic_Target_Register_Address)) <=
Execution_Result;
end if;
when "100011" =>
if (Cyclic_Target_Register_Address="00000") then
Reg(0) <= "00000000000000000000000000000000";
else
Reg(CONV_INTEGER(Cyclic_Target_Register_Address)) <=
Load_Data;
end if;
when "000011" =>
Reg(31) <= Program_Counter;
when others =>
Reg(0) <= "00000000000000000000000000000000";
end case;
end if;
end process;
The one commented out in t2 is causing your error.
So I'm trying to implement a I2C master on a FPGA, and I get the following Errors. Does someone know how to solve them?
Thanks!
WARNING:Xst:646 - Signal <thirdaddress> is assigned but never used. This unconnected signal will be trimmed during the optimization process.
WARNING:Xst:646 - Signal <secondaddress> is assigned but never used. This unconnected signal will be trimmed during the optimization process.
WARNING:Xst:646 - Signal <firstaddress> is assigned but never used. This unconnected signal will be trimmed during the optimization process.
WARNING:Xst:736 - Found 1-bit latch for signal <Mtridata_sda> created at line 44. Latches may be generated from incomplete case or if statements. We do not recommend the use of latches in FPGA/CPLD designs, as they may lead to timing problems.
WARNING:Xst:736 - Found 1-bit latch for signal <Mtrien_sda> created at line 44. Latches may be generated from incomplete case or if statements. We do not recommend the use of latches in FPGA/CPLD designs, as they may lead to timing problems.
WARNING:Xst:737 - Found 3-bit latch for signal <sendcount>. Latches may be generated from incomplete case or if statements. We do not recommend the use of latches in FPGA/CPLD designs, as they may lead to timing problems.
WARNING:Xst:1293 - FF/Latch <XLXI_9/sendcount_2> has a constant value of 0 in block <top_level>. This FF/Latch will be trimmed during the optimization process.
WARNING:Xst:1293 - FF/Latch <XLXI_9/sendcount_1> has a constant value of 0 in block <top_level>. This FF/Latch will be trimmed during the optimization process.
WARNING:Xst:1293 - FF/Latch <XLXI_9/sendcount_0> has a constant value of 0 in block <top_level>. This FF/Latch will be trimmed during the optimization process.
WARNING:Xst:1896 - Due to other FF/Latch trimming, FF/Latch <XLXI_9/current_state_FSM_FFd1> has a constant value of 0 in block <top_level>. This FF/Latch will be trimmed during the optimization process.
WARNING:Xst:1294 - Latch <XLXI_9/Mtridata_sda> is equivalent to a wire in block <top_level>.
WARNING:Xst:1294 - Latch <XLXI_9/Mtrien_sda> is equivalent to a wire in block <top_level>.
Here is the code:
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
entity i2cmaster is
Port ( sda : inout STD_LOGIC;
scl : out STD_LOGIC;
sclclk : in STD_LOGIC;
reset : in STD_LOGIC;
clk : in STD_LOGIC;
dataout : out STD_LOGIC_VECTOR (7 downto 0);
resettodivider : out STD_LOGIC);
end i2cmaster;
architecture Behavioral of i2cmaster is
type state_type is (startstate1, startstate2, sendaddress1, acknowlegde1, sendinternaladdress, acknowlegde2, startstate3, startstate4, sendaddress2, acknowlegde3, readdata, notacknowlegde, stopstate );
signal current_state : state_type;
signal next_state : state_type :=startstate1;
signal firstaddress: std_logic_vector(7 downto 0);
signal secondaddress: std_logic_vector(7 downto 0);
signal thirdaddress: std_logic_vector(7 downto 0);
signal sendcount: integer range 0 to 7 := 0;
signal temp : std_logic := '0';
signal tempdata : std_logic_vector(7 downto 0):="00000000";
begin
firstaddress<="10101010"; -- Slaveaddress + Writebit
secondaddress<="10101010"; -- Internal Address(first)
thirdaddress<="10101010"; -- Slaveaddress + Readbit
process(current_state, sda, sclclk, temp, sendcount, firstaddress, secondaddress, thirdaddress)
begin
case current_state is
------------------------
when startstate1 =>
temp<='0';
sendcount <=0;
resettodivider <='1';
sda<='1';
next_state <= startstate2;
------------------------
when startstate2 =>
temp<='0';
sendcount <=0;
resettodivider <='0';
sda<='0';
if sclclk = '0' then
next_state <= sendaddress1;
else
next_state <= startstate2;
end if;
------------------------
when sendaddress1 =>
resettodivider <='0';
if sendcount <= 7 then
if sclclk = '0' and temp='0' then
sda<=firstaddress(sendcount);
sendcount <= sendcount + 1;
temp<='1';
next_state<=sendaddress1;
elsif sclclk='1' then
temp<='0';
sendcount <=sendcount;
next_state<=sendaddress1;
else
temp<='0';
sda<='Z';
sendcount <= sendcount;
next_state<=sendaddress1;
end if;
else
temp<='0';
sendcount <= 0;
next_state<=acknowlegde1;
end if;
------------------------
when acknowlegde1 =>
temp<='0';
resettodivider <='0';
sendcount <=0;
if sclclk='1' then
if sda ='1' then
next_state<=startstate1;
else
next_state<=acknowlegde1;
end if;
else
next_state<=sendinternaladdress;
end if;
------------------------
when sendinternaladdress =>
resettodivider <='0';
if sendcount <= 7 then
if sclclk = '0' and temp='0' then
sda<=secondaddress(sendcount);
sendcount<= sendcount + 1;
temp<='1';
next_state<=sendinternaladdress;
elsif sclclk='1' then
temp<='0';
sendcount <=sendcount;
next_state<=sendinternaladdress;
else
temp<='0';
sendcount <= sendcount;
next_state<=sendinternaladdress;
sda<='Z';
end if;
else
temp<='0';
sendcount<= 0;
next_state<=acknowlegde2;
end if;
------------------------
when acknowlegde2 =>
sendcount <=0;
temp<='0';
resettodivider <='0';
if sclclk='1' then
if sda ='1' then
next_state<=startstate1;
else
next_state<=acknowlegde2;
end if;
else
next_state<=startstate3;
end if;
------------------------
when startstate3 =>
sendcount <=0;
temp<='0';
resettodivider <='1';
sda<='1';
next_state <= startstate4;
------------------------
when startstate4 =>
temp<='0';
resettodivider <='0';
sda<='0';
sendcount <=0;
if sclclk = '0' then
next_state <= sendaddress2;
else
next_state <= startstate4;
end if;
------------------------
when sendaddress2 =>
resettodivider <='0';
if sendcount <= 7 then
if sclclk = '0' and temp='0' then
sda<=thirdaddress(sendcount);
sendcount<= sendcount + 1;
temp<='1';
next_state<=sendaddress2;
elsif sclclk='1' then
sendcount<= sendcount;
temp<='0';
next_state<=sendaddress2;
else
sendcount<= sendcount;
temp<='0';
sda<='Z';
next_state<=sendaddress2;
end if;
else
temp<='0';
sendcount <=0;
next_state<=acknowlegde3;
end if;
------------------------
when acknowlegde3 =>
temp<='0';
sendcount<=0;
resettodivider <='0';
if sclclk='1' then
if sda ='1' then
next_state<=startstate1;
else
next_state<=acknowlegde3;
end if;
else
next_state<=readdata;
end if;
------------------------
when readdata =>
resettodivider <='0';
if sendcount <= 7 then
if sclclk = '0' and temp='0' then
tempdata(sendcount)<=sda;
tempdata<=tempdata;
sendcount<= sendcount + 1;
temp<='1';
next_state<=readdata;
elsif sclclk='1' then
tempdata(sendcount)<='0';
temp<='0';
sendcount <= sendcount;
next_state<=readdata;
else
temp<='0';
tempdata(sendcount)<='0';
sendcount <= sendcount;
next_state<=readdata;
end if;
else
temp<='0';
tempdata(sendcount)<='0';
sendcount <= 0;
next_state<=notacknowlegde;
end if;
------------------------
when notacknowlegde =>
sendcount<=0;
temp<='0';
resettodivider <='0';
if sclclk='0' then
next_state<=stopstate;
sda<='Z';
else
sda<='1';
next_state<=notacknowlegde;
end if;
------------------------
when stopstate =>
sendcount<=0;
temp<='0';
sda<='0';
resettodivider <='1';
next_state<=startstate1;
------------------------
when others =>
sendcount<=0;
temp<='0';
resettodivider <='0';
next_state<=startstate1;
sda<='Z';
scl<='Z';
end case;
end process;
-------
process(clk, reset)
begin
if (reset='1') then
current_state <= startstate1;
elsif rising_edge(clk) then
current_state <= next_state;
end if;
end process;
-------
scl<=sclclk;
dataout<= tempdata;
end Behavioral;
Complaining about dead/unused code
WARNING:Xst:646
Signal <thirdaddress> is assigned but never used.
Signal <secondaddress> is assigned but never used.
Signal <firstaddress> is assigned but never used.
This means these three signals are unused in your design. If you don't plan to use them in future, you can remove them -> dead code.
Warning about latches -> bad design
WARNING:Xst:736
Found 1-bit latch for signal <Mtridata_sda> created at line 44.
Found 1-bit latch for signal <Mtrien_sda> created at line 44.
Found 3-bit latch for signal <sendcount>.
Latches may be generated from incomplete case or if statements.
We do not recommend the use of latches in FPGA/CPLD designs, as
they may lead to timing problems.
Your state transition process does not assign each output signal for every input combination. This can be solved by extending your others case or generally introducing default assignments before the case statement.
Warning about registers, which don't change there value => constant content
WARNING:Xst:1293
FF/Latch <XLXI_9/sendcount_2> has a constant value of 0 in block <top_level>.
FF/Latch <XLXI_9/sendcount_1> has a constant value of 0 in block <top_level>.
FF/Latch <XLXI_9/sendcount_0> has a constant value of 0 in block <top_level>.
This FF/Latch will be trimmed during the optimization process.
Your counter sendcount gets removed. This fault is mostly caused if:
- a FSM hangs up and does not generate controls for a counter
- the counter is held in reset
- the counter does not get any increment/enable signal
Warning of unreached states
WARNING:Xst:1896
Due to other FF/Latch trimming, FF/Latch <XLXI_9/current_state_FSM_FFd1> has
a constant value of 0 in block <top_level>.
This FF/Latch will be trimmed during the optimization process.
This is a propagation message. Trimming registers, latches and logic on one end of the circuit can cause further "optimizations" / trimming on the other side.
An unreached state report can be found in the synthesis report. Search for 'unreached'.
I want to create a circuit which has two inputs a clock and an enable
and three outputs. What I want this circuit to do is that it has a
variable (cont) that goes from "00" to "11" and two of the outputs
(sal_1 and sal_2) take the values of cont(0) and cont(1) and go to the
inputs of a ttl ic (AND , OR, XOR) and then the output of the ttl ic
goes back to the circuit and is saved (results) after that, the vector
that is created from the differents results of the ttl ic ouputs is
compared with vectors already predefined and find the one that matches
it and returns the value.
I have a hard time with the output and then input times, it seems that
there is a special way to do this.
Here is my code:
library IEEE;
use IEEE.std_logic_1164.all;
use IEEE.numeric_std.all;
use IEEE.std_logic_unsigned.all;
use IEEE.std_logic_arith.all;
entity ttl_finder is
port( clk, ena, sal_ttl : in std_logic;
sal_1, sal_2 : out std_logic;
sal_f : out std_logic_vector(3 downto 0));
end entity;
architecture ttl_tester of ttl_finder is
signal cont : std_logic_vector(1 downto 0) := "00";
signal results : std_logic_vector(3 downto 0) := "0000";
begin
process(clk, ena)
variable c : std_logic;
variable d : std_logic;
variable e : std_logic;
begin
if ena = '1' then
if cont < "11" then
sal_1 <= cont(0);
sal_2 <= cont(1);
if rising_edge(clk) then
results(conv_integer(cont)) <= sal_ttl;
end if;
cont <= cont + 1;
else
sal_1 <= cont(0);
sal_2 <= cont(1);
if rising_edge(clk) then
results(conv_integer(cont)) <= sal_ttl;
end if;
cont <= "00";
end if;
end if;
end process;
sal_f <= results;
end ttl_tester;