error in quadrature design

zes

Joined
Sep 18, 2008
Messages
4
Reaction score
0
Hello,



I am designing a vhdl quadrature decoder. The result of the decoder should be set in a register called "slv_reg2". Because the device can turn both ways i will cast the signed value to a std_logic_vector one (so my software can directly see which way is has turned).



The design works perfect exept if I turn de shaft clockwise first and then counter-clockwise (and vice versa). When this happens i see the following on hyperterminal: 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 8, 7, 6 -4543453453. I've already spend 2 days finding the bug, but I really can't find it. Can the clock speed be to fast ??



Here is my vhdl source:





signal last_quad : std_logic_vector(0 to 1);
signal look_up : std_logic_vector(0 to 3);
signal signed_slv_reg2 : signed(0 to 31);

begin

slv_reg2 <= std_logic_vector(signed_slv_reg2);
look_up <= quadrature & last_quad;

p0:
process(Bus2IP_Clk)
begin
if(Bus2IP_Clk'EVENT and Bus2IP_Clk = '1') then -- sample @ every rising clock cycle

last_quad <= quadrature;
signed_slv_reg2 <= signed_slv_reg2;

if(slv_reg0(31) = '1') then -- check for reset events in control reg
signed_slv_reg2 <= to_signed(0,32); -- if reset then empty register
else
case look_up is
-- no change
when "0000" | "1010" | "0101" | "1111" =>
signed_slv_reg2 <= signed_slv_reg2;
-- error
when "0011" | "1100" | "1001"| "0110" =>
signed_slv_reg2 <= signed_slv_reg2;
-- turn ClockWise
when "0010" | "0100" | "1011" | "1101" =>
signed_slv_reg2 <= signed_slv_reg2 + to_signed(1,32);
-- turn Counter - ClockWise
when "0001" | "0111" | "1000" | "1110" =>
signed_slv_reg2 <= signed_slv_reg2 - to_signed(1,32);
-- not necessary because all states covered
when others => null;
end case;
end if;
end if;
end process p0;
 
Joined
Mar 10, 2008
Messages
348
Reaction score
0
Missing signals in sensivity list

Try this - and let me know if it solves the problem - then I explain:

Code:
	signal last_quad : std_logic_vector(0 to 1);
	signal look_up : std_logic_vector(0 to 3);
	signal signed_slv_reg2 : signed(0 to 31);
begin
	slv_reg2 <= std_logic_vector(signed_slv_reg2);
	--look_up <= quadrature & last_quad;

p0:
process(Bus2IP_Clk)
begin
	if(Bus2IP_Clk'EVENT and Bus2IP_Clk = '1') then -- sample @ every rising clock cycle
		look_up <= quadrature & look_up( 0 to 1);
		--signed_slv_reg2 <= signed_slv_reg2;

		if(slv_reg0(31) = '1') then -- check for reset events in control reg
			signed_slv_reg2 <= to_signed(0,32); -- if reset then empty register
		else
			case look_up is
			-- no change
				when "0000" | "1010" | "0101" | "1111" =>
					signed_slv_reg2 <= signed_slv_reg2;
			-- error
				when "0011" | "1100" | "1001"| "0110" =>
					signed_slv_reg2 <= signed_slv_reg2;
			-- turn ClockWise
				when "0010" | "0100" | "1011" | "1101" =>
					signed_slv_reg2 <= signed_slv_reg2 + to_signed(1,32);
			-- turn Counter - ClockWise
				when "0001" | "0111" | "1000" | "1110" =>
					signed_slv_reg2 <= signed_slv_reg2 - to_signed(1,32);
			-- not necessary because all states covered
				when others => null;
			end case;
		end if;
	end if;
end process p0

end Behavioral;
Your welcome
Jeppe
 
Last edited:

zes

Joined
Sep 18, 2008
Messages
4
Reaction score
0
this will never work because in your changed design you dont do anything with look_up(2 to 3). And the purpose of this register is to take the current and the last value of the quadrature and this combination determines the turn.
 
Joined
Mar 10, 2008
Messages
348
Reaction score
0
Hi Zes

Well I dont agree - may be you should take a second look in order to understand the statement:
look_up <= quadrature & look_up( 0 to 1);
:)

Please visit this page: http://www.jjmk.dk/MMMI/Exercises/05_Counters_Shreg/No5_Quadrature/index.htm - with a new modified example (below) and a simulation which verifies the usefulnes (hopefully)

Code:
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_SIGNED.ALL;

entity Test is
   port( Bus2IP_Clk: in std_logic;
	      slv_reg2:   inout std_logic_vector(31 downto 0) := (others=>'0');
			slv_reg0:   in    std_logic_vector(31 downto 0);
	      quadrature: in    std_logic_vector(0 to 1));
end Test;

architecture Behavioral of Test is
   signal errors:   std_logic_vector(7 downto 0);
	signal look_up : std_logic_vector(0 to 3);
begin

p0: process(Bus2IP_Clk)
begin
	if(Bus2IP_Clk'EVENT and Bus2IP_Clk = '1') then -- sample @ every rising clock cycle	   

		look_up <= quadrature & look_up( 0 to 1);	-- look below
	-- look_up(0) <= quadrature(0);
	-- look_up(1) <= quadrature(1);
	-- look_up(2) <= look_up(0);
	-- look_up(3) <= look_up(1);
	
		if(slv_reg0(31) = '1') then -- check for reset events in control reg
			slv_reg2 <= (others=>'0'); -- if reset then empty register
			errors   <= (others=>'0');
		else
			case look_up is
			-- no change
				when "0000" | "1010" | "0101" | "1111" =>
					null;
			-- error
				when "0011" | "1100" | "1001"| "0110" =>
					errors <= errors+1;  -- Just to display nunber of errors
			-- turn ClockWise
				when "0010" | "0100" | "1011" | "1101" =>
					slv_reg2 <= slv_reg2 + 1;
			-- turn Counter - ClockWise
				when "0001" | "0111" | "1000" | "1110" =>
					slv_reg2 <= slv_reg2 - 1;
			-- not necessary because all states covered
				when others => null;
			end case;
		end if;
	end if;
end process p0;

end Behavioral;
 

zes

Joined
Sep 18, 2008
Messages
4
Reaction score
0
if just synthesized and implemented your correction and it works :)

thank you very much !!

I just don't understand why the design works, but didn't work when i concatenated the "look_up" outside the process, can you explain why? because in simulation(modelsim XE/PE) my design worked.

thx !! :)
 
Joined
Mar 10, 2008
Messages
348
Reaction score
0
Your welcome
The problem (which may be not a problem actually ;-) ) could be the fact that the process in which you use look_up will only be trigged by clk pulses.
But this will only course some delays in the detection of changes.
There could be some (great) problems if the synthesize tool generates unexpected f/f's and hence courses your design to behave stangely, but I'm not sure this the case here.

No the REAL problem could be your notation signed_xx ( 0 to 31) - try to change this to signed_xx( 31 downto 0)

Jeppe
 
Last edited:

zes

Joined
Sep 18, 2008
Messages
4
Reaction score
0
well i have been turning the shaft for some times and no hazzards occured. I still have everything set as <name>(0 to 31) . And this works perfectly, i dont see why that should be different with downto, doesnt it synthesizes/simulates the same?
 
Joined
Mar 10, 2008
Messages
348
Reaction score
0
Ok - your right - just an old habbit for me to use (31 downto 0) - the result will be the same for synthesize

About your problem - I found it :) :


If you draw a block diagram of the circuit from your code will you find that the quadrature signals NOT synchronized.
The Last_quad will always hold its value thanks to the Clock driven process and hence the implementation of F/F's

Please note that this kind of problem will seldom (read never) shows in a simulation as the generatated stimulation will
be synchone with the clock.
 
Last edited:

Ask a Question

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

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Members online

Forum statistics

Threads
473,755
Messages
2,569,535
Members
45,007
Latest member
obedient dusk

Latest Threads

Top