On 2020-02-06 11:04, Rick C wrote:
On Thursday, February 6, 2020 at 6:29:01 AM UTC-5, [email protected] wrote:
I have created a register file that holds 4 32 bit registers.Now i would like to check whether the first 3 bits of the first register(CTL) is 1 and then check if the 1st bit of 2nd register is 1 .If so the BC_en bit should go high.....which is not
happening....can anyone please see the code below and help me?
............................................................................ >> library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
use ieee.numeric_std_UNSIGNED.ALL;
entity cntrregFile is
port
(
input : in std_logic_vector (31 downto 0);
writeEnable : in std_logic;
clk : in std_logic;
readregSel : in std_logic_vector (2 downto 0);
writeregSel : in std_logic_vector (2 downto 0);
readEnable : in std_logic;
output : out std_logic_vector (31 downto 0);
bc_en : out std_logic
);
end cntrregFile;
architecture behavioral of cntrregFile is
type registerFile is array(0 to 3) of std_logic_vector(31 downto 0);
signal registers : registerFile;
signal CTL : std_logic_vector(31 downto 0);
signal BC_CTL : std_logic_vector(31 downto 0);
signal BC_FIFO_CTL : std_logic_vector(31 downto 0);
signal ENCDEC_CTL : std_logic_vector(31 downto 0);
begin
process (clk,writeregSel,writeEnable,readregSel,readEnable) is
begin
if (rising_edge(clk) and writeEnable='1' ) then
if ( writeregSel="000") then
registers (to_integer(writeregSel)) <= input ;
elsif ( writeregSel="001") then
registers (to_integer(writeregSel)) <= input ;
elsif ( writeregSel="010") then
registers (to_integer(writeregSel)) <= input ;
elsif ( writeregSel="011") then
registers (to_integer(writeregSel)) <= input ;
end if;
elsif (rising_edge(clk) and readEnable='1') then
if (readregSel="000") then
CTL <= registers(to_integer(readregSel));
output <= CTL;
elsif(readregSel="001") then
BC_CTL <= registers(to_integer(readregSel));
output<= BC_CTL;
elsif(readregSel="010") then
BC_FIFO_CTL <= registers(to_integer(readregSel));
output<= BC_FIFO_CTL;
elsif(readregSel="011") then
ENCDEC_CTL <= registers(to_integer(readregSel));
output<=ENCDEC_CTL ;
end if;
end if;
end process;
process (clk,CTL,BC_CTL) is
begin
if (CTL(0)= '1') and (CTL(1)='1') and
(CTL(2)='0') and (CTL(3)='0')then
if (BC_CTL(0) ='1') then
bc_en<= '1';
else
bc_en<='0';
end if;
end if;
end process;
end behavioral;
A couple of small issues that aren't your problem. A clocked process only needs the signals in the sensitivity list that are prerequisites to any of the outputs changing. So it should include the clock signal and if you had an async input such as
reset, that too. But only if the reset or any other signal is asynchronous. So clean up your sensitivity list and your simulations will run faster.
Then by convention there is an outer conditional to detect the rising edge of the clock and all other logic is inside this structure as separate conditionals. I can't say this causes any problems, but I've never seen anyone do it in two separate
conditionals so I can't say for sure. But it will be easier to get help if your code has the same basic structure as everyone else's.
Your use of IEEE.STD_LOGIC_UNSIGNED along with ieee.numeric_std_UNSIGNED has several problems. The former is deprecated and you should stop using it. The latter is not even a thing... the name is ieee.numeric_std. It includes both signed and
unsigned types.
Another style issue which may be causing a failure (not sure) is with writing the registers. You are using a conditional to decode the register select, then you are addressing the register directly by turning writeregSel into an integer. You only
need to do one of those things, not both.
There is a mismatch with the number of registers (4) and the possible registers selected by the select lines (8 or 3 depending on whether or not they are 1-hot). So which is right?
Do you realize that when reading you have a register delay between the read enable and the register value being saved in CTL, BC_CTL, BC_FIFO_CTL and ENCDEC_CTL? Then you add another register delay before assigning those values to output? I'm not
saying this is wrong, I just want to make sure you have it right from the assignment.
The register delays can be important to your application and in particular to the decoding. Right now the decode is on the registers CTL and BC_CTL while you are also storing the data in the register file "registers". registers is updated when you
write the register file. CTL and BC_CTL are only written when you read the register file.
So I think you have many errors in your code that are logical errors. I suggest that you try drawing a block diagram of the logic you would use to implement this design. Show the registers, data flow and decodes. Then you can write code to describe
that structure and it should be a closer match.
I'll echo Rick's comments. A clocked process should contain only the
clock signal in the sensitivity list, and possibly also the reset signal
if you are using an asynchronous reset. Your second process shouldn't
contain the clk signal because it is not a clocked process.
Forget the STD_LOGIC_ARITH and STD_LOGIC_UNSIGNED packages. Those are
old, non-standard packages that were developed by Synopsis before IEEE
came out with the numberic_std package. VHDL purists will argue that
they shouldn't even be in the ieee library, because they were not
developed by IEEE, but that is where tool vendors usually put them. Use ieee.numeric_std instead.
You need to understand the difference between variable assignments and
signal assignments in VHDL. Variable assignments happen immediately,
like in common programming languages, before the next statement is
executed. Signal assignments do not happen immediately. What they do is
put an event into the simulator's event queue to be processed later.
For example, let's take a look at two statements from your code:
CTL <= registers(to_integer(readregSel));
output <= CTL;
What that says is:
Put an event into the simulator's event queue to assign the current
value of registers(0) to the signal CTL.
Put an event into the simulator's event queue to assign the current
value of CTL to the signal "output".
So CTL and OUTPUT do not necessary get the same value. OUTPUT gets the
value that CTL already had BEFORE the assignment
CTL <= registers(to_integer(readregSel));
got carried out.
Variable assignments in VHDL take place immediately. Variables don't
trigger events or other processes. Signals in VHDL hold both a value and
time and event information. Signals can trigger other processes.
It isn't clear from your code just what you were trying to accomplish,
but take a look at the way I recoded it to see if it might be closer to
your intentions:
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use ieee.numeric_std.ALL;
entity cntrregFile is
port
(
input : in std_logic_vector (31 downto 0);
writeEnable : in std_logic;
clk : in std_logic;
readregSel : in std_logic_vector (2 downto 0);
writeregSel : in std_logic_vector (2 downto 0);
readEnable : in std_logic;
output : out std_logic_vector (31 downto 0);
bc_en : out std_logic
);
end cntrregFile;
architecture behavioral of cntrregFile is
type registerFile is array(0 to 3) of std_logic_vector(31 downto 0);
signal registers : registerFile;
signal CTL : std_logic_vector(31 downto 0);
signal BC_CTL : std_logic_vector(31 downto 0);
signal BC_FIFO_CTL : std_logic_vector(31 downto 0);
signal ENCDEC_CTL : std_logic_vector(31 downto 0);
begin
clk_proc: process (clk) is
variable reg_addr : integer range 0 to 3;
begin
if (rising_edge(clk) ) then
if writeEnable='1' and writeregSel(2)='0' then
reg_addr := to_integer(writeregSel(1 downto 0));
registers(reg_addr) <= input ;
end if;
if readEnable='1' then
if (readregSel="000") then
CTL <= registers(0);
end if;
if (readregSel="001") then
BC_CTL <= registers(1);
end if;
if (readregSel="010") then
BC_FIFO_CTL <= registers(2);
end if;
if (readregSel="011") then
ENCDEC_CTL <= registers(3);
end if;
if readregSel(2)='0' then
reg_addr := to_integer(readregSel(1 downto 0));
output <= registers(reg_addr);
end if;
end if;
end if;
end process;
bc_en <= CTL(0) and CTL(1) and not CTL(2) and BC_CTL(0);
end behavioral;
Charles Bailey
--- SoupGate-Win32 v1.05
* Origin: fsxNet Usenet Gateway (21:1/5)