Ich arbeite an dem Versuch, ein billiges FPGA (das Altera Cyclone II Mini-Board ep2c5t144) mit einem SNES zu verbinden, um als SNES-Controller zu arbeiten. Bis jetzt scheint es ein- und auszuschalten ... mit dem aktuellen Problem, es funktioniert nach dem Einschalten für etwa 1 Sekunde ... aber dann scheint es in einem Zustand stecken zu bleiben, bis es zurückgesetzt wird.VHDL - SNES Schnittstelle über Controller-Port mit FPGA
Da ich mich lange mit dem Code für ein logisches Problem beschäftigt habe, frage ich mich, ob es eine merkwürdige Eigenart ist, FPGAs zu verwenden, aber ich habe bereits versucht, nach Zuständen zu suchen, die nicht definiert sind und das hat das Problem nicht behoben. Ich werde den SNES-Code unten und den Ausgang von meinem billigen Logikanalysator veröffentlichen, der das Problem zeigt. Warnung, der Code ist ziemlich chaotisch ... vor allem, wenn ich etwas herumwechsle, um es zu reparieren. Irgendwelche Ideen überhaupt werden sehr geschätzt!
Vielen Dank im Voraus für jede Hilfe!
Problem vom Logikanalysator:
When a request works - State transitions occur as expected
library ieee;
use ieee.std_logic_1164.all;
use ieee.numeric_std.all;
entity snes_controller is
generic (
hp : integer := 300
);
port (
clk : in std_logic;
latch : in std_logic;
data : out std_logic := '0';
clock : in std_logic;
enable : in std_logic;
btn_B : in std_logic;
btn_Y : in std_logic;
btn_select : in std_logic;
btn_start : in std_logic;
btn_up : in std_logic;
btn_down : in std_logic;
btn_left : in std_logic;
btn_right : in std_logic;
btn_A : in std_logic;
btn_X : in std_logic;
btn_L : in std_logic;
btn_R : in std_logic;
helpA : out std_logic := '0';
helpB : out std_logic := '0';
helpC : out std_logic := '0';
helpD : out std_logic := '0';
helpE : out std_logic := '0'
);
end entity;
architecture Behav of snes_controller is
signal buttons : unsigned(16 downto 0) := "10000000000000000";
type state_type is (s_idle, s_latching_1, s_latching_2, s_working);
signal state : state_type := s_idle;
type cycle_type is (c_high, c_low);
signal cycle : cycle_type := c_high;
begin
process (clk)
variable i : integer range 0 to 16;
variable count : integer range 0 to hp;
begin
if(rising_edge(clk)) then
data <= not buttons(i);
if(state = s_latching_1 or state = s_latching_2 or state = s_working) then
if(count < hp) then
count := count+1;
else
count := 0;
if(state = s_latching_1) then
if(latch = '1') then
state <= s_latching_2;
buttons(0) <= btn_B;
buttons(1) <= btn_Y;
buttons(2) <= btn_select;
buttons(3) <= btn_start;
buttons(4) <= btn_up;
buttons(5) <= btn_down;
buttons(6) <= btn_left;
buttons(7) <= btn_right;
buttons(8) <= btn_A;
buttons(9) <= btn_X;
buttons(10) <= btn_L;
buttons(11) <= btn_R;
else
state <= s_idle;
end if;
elsif(state = s_latching_2) then
state <= s_working;
i := 0;
cycle <= c_high;
elsif(state = s_working) then
if(latch = '1') then
state <= s_idle;
helpD <= '1';
elsif(cycle = c_low) then
cycle <= c_high;
if(i < 16) then
i := i+1;
else
state <= s_idle;
helpD <= '0';
helpE <= '0';
end if;
else
cycle <= c_low;
end if;
end if;
end if;
elsif(state = s_idle) then
if(latch = '1') then
state <= s_latching_1;
count := 0;
i := 0;
end if;
else
helpE <= '1';
state <= s_idle;
count := 0;
i := 0;
end if;
end if;
end process;
process(state)
begin
if(state = s_idle) then
helpA <= '0';
helpB <= '0';
elsif(state = s_latching_1) then
helpA <= '1';
helpB <= '0';
elsif(state = s_latching_2) then
helpA <= '0';
helpB <= '1';
elsif(state = s_working) then
helpA <= '1';
helpB <= '1';
else
helpA <= clk;
helpB <= not clk;
end if;
if(cycle = c_low) then
helpC <= '0';
elsif(cycle = c_high) then
helpC <= '1';
end if;
end process;
end Behav;
Ihre Frage schlägt vor, dass Sie Ihren Code nicht simulieren, aber versuchen, es auf der Bank zu debuggen. Es ist eine viel bessere Idee, eine Testbench zu schreiben und zuerst Ihren Code zu simulieren. Wenn Sie in einer Testbench Ihren eigenen Stimulus erzeugen, haben Sie die volle Kontrolle. Eine Simulation ist reproduzierbar. Sie können überall in Ihrem Design testen, um beim Debuggen zu helfen. Sie können das Verhalten Ihres Entwurfs automatisch überprüfen (manuelle Überprüfung ist zu fehleranfällig). Wenn Sie im Rahmen von "Stack Overflow" eine Testbench gehabt hätten, könnte Ihnen jemand anders helfen, Ihre Simulation auszuführen, um Ihren Fehler zu reproduzieren. –
@MatthewTaylor In diesem Fall würde ein Prüfstand nur funktionieren, wenn Sie die Asynchronität der Eingänge korrekt simulieren würden. Ich wette, dass die Antwort von Oron Port korrekt ist. Das Fehlen von Synchronisierern blockiert wahrscheinlich die FSMs. – JHBonarius