Forum Discussion
Altera_Forum
Honored Contributor
15 years agoBCD counter vhdl code
I am a newbie quartus user.. please help me thanks
http://i54.tinypic.com/2zp2p3p.png This is my written code: library ieee;use ieee.std_logic_1164.all;
use ieee.numeric_std.all; entity d4 is
port (reset, sensor, load :in std_logic;
p :in std_logic_vector (5 downto 0);
led_on :out std_logic;
q :out std_logic_vector (5 downto 0));
end d4; architecture flow of d4 is signal count_sig : unsigned (5 downto 0);
signal load_sig : unsigned (5 downto 0); begin
process (sensor, reset, load, p)
begin
if (reset = '1') then
count_sig <= "000000"; elsif rising_edge (sensor) then
if (count_sig = 32) then
count_sig <= "000000"; else
count_sig <= count_sig + 1; if (load = '0') then
count_sig <= load_sig; else
count_sig <= count_sig + 1;
end if;
end if;
end if;
end process;
q <= std_logic_vector (count_sig); end flow;
------------------------------------------------------------------------ I did not add LED_ON in the code because i don't know the correct way to to put in the LED, always getting error when i try to put in LED code.. and i can't make P to activate Q when load is low. i don't know what i am talking about too. Please help me ! appreciate if u do so :confused:
16 Replies
- Altera_Forum
Honored Contributor
LED_ON is just an output, you can assign it anywhere you want:
LED_on <= '1'; or LED_on <= some_other_signal; or if something_happened then led_on <= '1'; else led_on <= '0'; end if; etc. - Altera_Forum
Honored Contributor
is LED_ON a predefined output?
It's the second time i read about it. - Altera_Forum
Honored Contributor
Try this.library ieee; use ieee.std_logic_1164.all; use ieee.numeric_std.all; entity d4 is port (reset, sensor, load :in std_logic; p :in std_logic_vector (5 downto 0); led_on :out std_logic; q :out std_logic_vector (5 downto 0)); end d4; architecture flow of d4 is signal count_sig : unsigned (5 downto 0); signal load_sig : unsigned (5 downto 0); begin process (sensor, reset, load, p) begin if (reset = '1') then count_sig <= "000000"; elsif rising_edge (sensor) then if (count_sig = 32) then LED_ON <= '1'; count_sig <= "000000"; else LED_ON <= '0'; count_sig <= count_sig + 1; if (load = '0') then count_sig <= p; end if; end if; end if; end process; q <= std_logic_vector (count_sig); end flow; - Altera_Forum
Honored Contributor
--- Quote Start ---
Try this. --- Quote End --- Error (10476): VHDL error at d4.vhdl(27): type of identifier "p" does not agree with its usage as UNSIGNED type thanks for assisting, it's not only the LED that i don't know about .. i feel that my code is not written properly and i can't find out the reason because i was not taught properly.. this one is way beyond my levellibrary ieee; use ieee.std_logic_1164.all; use ieee.numeric_std.all; entity d4 is port (reset, sensor, load :in std_logic; p :in std_logic_vector (5 downto 0); led_on :out std_logic; q :out std_logic_vector (5 downto 0)); end d4; architecture flow of d4 is signal count_sig : unsigned (5 downto 0); signal load_sig : unsigned (5 downto 0); begin process (sensor, reset, load, p) begin if (reset = '1') then count_sig <= "000000"; elsif rising_edge (sensor) then if (count_sig = 32) then LED_ON <= '1'; count_sig <= "000000"; else LED_ON <= '0'; count_sig <= count_sig + 1; if (load = '0') then count_sig <= p; end if; end if; end if; end process; q <= std_logic_vector (count_sig); end flow; - Altera_Forum
Honored Contributor
--- Quote Start --- Error (10476): VHDL error at d4.vhdl(27): type of identifier "p" does not agree with its usage as UNSIGNED type --- Quote End --- Truely. You need a type cast when assigning std_logic_vector to unsigned. Why don't you simply correct it and proceed. - Altera_Forum
Honored Contributor
--- Quote Start --- Truely. You need a type cast when assigning std_logic_vector to unsigned. Why don't you simply correct it and proceed. --- Quote End --- how do u do that lol .. sry i am really a noob my lecturer didn't taught us trial and error.. - Altera_Forum
Honored Contributor
You really should have a VHDL tutorial or text book to get some ideas for trial and error. And furthermore learn about the basic concepts of the language and HDL programming in general.
For compatible types, e.g. bit vectors of same length, a typecast is simple. You already have one in your code
Trial and error actually has a good chance for a hit with the opposite directionq <= std_logic_vector (count_sig);count_sig <= unsigned(p); - Altera_Forum
Honored Contributor
expected result
http://i54.tinypic.com/2zp2p3p.png
my result http://i51.tinypic.com/al6iyc.png library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity d4 is
port (reset, sensor, load :in std_logic;
p :in std_logic_vector (5 downto 0);
led_on :out std_logic;
q :out std_logic_vector (5 downto 0));
end d4;
architecture flow of d4 is
signal count_sig : unsigned (5 downto 0);
signal load_sig : unsigned (5 downto 0);
begin
process (sensor, reset, load, p)
begin
if (reset = '1') then
count_sig <= "000000";
elsif rising_edge (sensor) then
if (count_sig = 32) then
led_on <= '0';
count_sig <= "010000";
else
led_on <= '1';
count_sig <= count_sig + 1;
if (load = '0') then
count_sig <= unsigned(p);
end if;
end if;
end if;
end process;
q <= std_logic_vector (count_sig);
end flow;
---------------------------------------------------------------------- When load is '0' on P=2 .. q is not starting from 2... why??? btw LED is kind of correct now. no idea why is it '0' when q = 0.. sorry for the troubles guys please help me ..
- Altera_Forum
Honored Contributor
Basically the simulation result is doing what your code commands, which is different from the above shown reference waveform. But as you have a working code now, you are on the right track.
A first, possibly less obvious problem is brought up by performing a functional rather than a timing simulation. This causes the load signal to be ignored, if it's deasserted on the rising edge of the sensor signal. This detail suggests, that the reference waveform is a timing simulation. For small designs, I would generally suggest a timing simulation, because it shows the real hardware behaviour. By slightly increasing the pulse width of load, it should work also in functional simulation. The second point is about initial signal states. All registers are initialized to zero by default on power-up, unless you alllow power-up don't care as a synthesis option. This means, that the led output signal must be explicitely set to '1' in your code, preferably under the reset condition. The third, general point is about the counter operation. In the reference waveform, the counter is counting from 31 to 0, which suggests a 5 bit wide counter, not 6 bit as in your code. I don't know if the exercise is explicitely stating the width of input and output signals. A 5 bit counter would automatically overflow from 31 to 0 without writing it in your code. But it's not bad to write the condition if count = 31 then explicitely. And it's required to trigger the led action. Finally, how about the led signal? Strictly spoken, the reference waveform is not an exact specification, because it doesn't say, what happens, when the next 32 events are counted, but the most simple assumption is to repeat the LED action. In this case, the led output can be understood as a counter overflow signal, delayed by one cycle. You need an additional flag signal (a register) to implement it in your code. I would write it like this. I left the counter bit width open in this place by using a different zero syntax.if count_sig = 31 then led_flag <= '1'; count_sig <= (others => '0'); else led_flag <= '0'; count_sig <= count_sig + 1; end if; led <= NOT led_flag; - Altera_Forum
Honored Contributor
thanks for ur explanation and assist.. understood a lot!
"By slightly increasing the pulse width of load, it should work also in functional simulation." could you explain it more ? how do u increase the pulse width of load. http://i53.tinypic.com/2lbkkrt.png library ieee;use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity d4 is
port (reset, sensor, load :in std_logic;
p :in std_logic_vector (4 downto 0);
led_on :out std_logic;
q :out std_logic_vector (4 downto 0));
end d4;
architecture flow of d4 is
signal count_sig : unsigned (4 downto 0);
begin
process (sensor, reset, load, p)
begin
if (reset = '1') then
count_sig <= "00000";
elsif rising_edge (sensor) then
count_sig <= count_sig + 1;
if (count_sig = 31) then
led_on <= '1';
count_sig <= (others => '0');
else
led_on <= '0';
count_sig <= count_sig + 1;
if (load = '0') then
count_sig <= unsigned(p);
end if;
end if;
end if;
end process;
q <= std_logic_vector (count_sig);
end flow; looking better now. but if (load = '0') then
count_sig <= unsigned(p);
this code seems useless.. When load is '0' on P=2 .. q is not starting from 2... or when load is '0' on P=20.. q is not starting from 20, like shown in the correct stimulation. please enlighten me. i have been saying countless times of thank you but really i appreciate ur help.. happy lunar new year to all of u!