📄 litenandfsm.vhdl
字号:
library IEEE;
use IEEE.STD_LOGIC_1164.ALL;
use IEEE.STD_LOGIC_ARITH.ALL;
use IEEE.STD_LOGIC_UNSIGNED.ALL;
-- Uncomment the following lines to use the declarations that are
-- provided for instantiating Xilinx primitive components.
--library UNISIM;
--use UNISIM.VComponents.all;
entity LITEnandFSM is
generic(
ErrorFetchCommand: std_logic_vector(7 downto 0) := x"23"
);
Port(
DEBUGvector : out std_logic_vector (3 downto 0);
-- disabling ECC
enableECCmodule: in std_logic;
-- The basics of synchronous design
clk : in std_logic;
clkDIVx3 : in std_logic;
Reset_L : in std_logic;
-- Output interface
hostIOin : in std_logic_vector (7 downto 0);
hostIOout : out std_logic_vector (7 downto 0);
hostIOdrv : out std_logic;
--hostIO : inout std_logic_vector(7 downto 0);
hostCE_L : in std_logic;
hostCLE_H : in std_logic;
hostALE_H : in std_logic;
hostWE_L : in std_logic;
hostRE_L : in std_logic;
hostWP_L : in std_logic;
intPRE : in std_logic;
hostRB_L : out std_logic;
interrINT_H : out std_logic;
-- NAND flash Interface
nandCE_L : out std_logic;
nandCLE_H : out std_logic;
nandALE_H : out std_logic;
nandWE_L : out std_logic;
nandRE_L : out std_logic;
nandWP_L : out std_logic;
nandPRE : out std_logic;
nandRB_L : in std_logic;
nandIO : inout std_logic_vector(7 downto 0);
-- ECC state machine control
ResetECCgen : out std_logic;
EnableECCgen: out std_logic;
ECCgenCNT: out std_logic_vector(8 downto 0);
-- CounterCONTROL
count12BIT : out std_logic_vector(11 downto 0);
-- Interrupt required or not
NeedINT : in std_logic;
REen_OUT : out std_logic;
-- Address output for internal 56 bit signal
ADDR : out std_logic_vector(2 downto 0);
-- For outputting to the tristate
HAMMING8bitin: in std_logic_vector(7 downto 0);
ErrorLOCations: in std_logic_vector(7 downto 0);
loadERRlocERRORS: out std_logic;
dataFORecc: out std_logic_vector(7 downto 0);
STATEvec: out std_logic_vector(3 downto 0)
);
end LITEnandFSM;
architecture syn of LITEnandFSM is
type state is (Start,
ReadNAND, ReadNANDwaitforRB, ReadECCcalc,
ReadECCfromNAND,
ProgramNAND, ProgramNANDaddr, ProgramNANDeccCALC,
ProgramNANDeccwrite, ThrowINT,
ProgramNANDfillinOther, ProgramNANDbufST0,
ProgramNANDbufST1, ProgramNANDbufST2, ProgramNANDbufST3,
ProgramNANDcmd10h, FetchERRORS,
FetchERRORS_waitforRE);
--FetchERRORSread,
signal cSTATE, nextSTATE: state;
signal ResetCOUNTER_L, incCOUNT: std_logic;
-- TUG the lines signals
signal cntTUG: std_logic_vector(2 downto 0);
signal ResetTUGthelines, TUGthelines: std_logic;
signal Done2100Bytes: std_logic;
signal firstVAL: std_logic;
--ONEdelayedRE,, secondVAL: std_logic;
-- Tristate buffer control
signal nandIOtempVAL: std_logic_vector(7 downto 0);
signal HammingINmuxSEL, triSTATEnandIO : std_logic;
-- whtHOSTio, HAMMINGtoNANDsel, REstatus,
signal intIO : std_logic_vector(7 downto 0);
signal intCE_L, intCLE_H, intALE_H, intWE_L, intRE_L, intWP_L,
intRB_L : std_logic;
-- signal to make intIO 0xFF so that the extra writes can be done
signal FFintIO, SELintIO10: std_logic;
-- registers for double latching the signals
signal hostIOin_tmp: std_logic_vector(7 downto 0);
signal hostCE_L_tmp, hostCLE_H_tmp, hostALE_H_tmp, hostWE_L_tmp,
hostRE_L_tmp, hostWP_L_tmp, hostRB_L_tmp:
std_logic;
signal internal_COUNT : std_logic_vector(11 downto 0);
signal incrADDR_errLOC, errlocADDRsel, ECCgenCNTsel: std_logic;
signal SHOOTenable, internal_REGeccgen : std_logic;
begin
count12BIT <= internal_COUNT;
nandPRE <= intPRE;
REen_OUT <= incrADDR_errLOC;
RisingEDGEdetctECCgen: process(clk, SHOOTenable)
--variable internal_REGeccgen: std_logic;
begin
if(rising_edge(clk)) then
if(Reset_L = '0') then
internal_REGeccgen <= '1';
else
internal_REGeccgen <= SHOOTenable;
end if;
if(Reset_L = '0') then
EnableECCgen <= '0';
else
if(SHOOTenable = '1' and internal_REGeccgen = '0') then
EnableECCgen <= '1';
else
EnableECCgen <= '0';
end if;
end if;
end if;
end process RisingEDGEdetctECCgen;
CountUP: process(clk, ResetCOUNTER_L, incCOUNT, internal_COUNT, errlocADDRsel,
ECCgenCNTsel)
variable internal_REG: std_logic;
variable refCNT: std_logic_vector(3 downto 0);
begin
if(rising_edge(clk)) then
if(ResetCOUNTER_L = '0') then
internal_COUNT <= X"FFF";
internal_REG := '0';
elsif(incCOUNT = '1' and internal_REG = '0') then
internal_COUNT <= internal_COUNT + '1';
internal_REG := '1';
elsif(incCOUNT = '0') then
internal_REG := '0';
end if;
end if;
if(rising_edge(clk)) then
if(Done2100Bytes = '0') then
refCNT := "0000";
else
if(incrADDR_errLOC = '1') then
refCNT := refCNT + 1;
end if;
if(refCNT(1 downto 0) = "11" and TUGthelines = '0') then
refCNT := refCNT + "0001";
end if;
loadERRlocERRORS <= incrADDR_errLOC;
--if(refCNT(1 downto 0) = "10") then
-- loadERRlocERRORS <= '1';
--else
-- loadERRlocERRORS <= '0';
--end if;
end if;
end if;
if(errlocADDRsel = '0') then
ADDR <= refCNT(3 downto 2) & '0';
else
ADDR <= internal_COUNT(2 downto 0);
end if;
if(ECCgenCNTsel = '0') then
ECCgenCNT <= internal_COUNT(8 downto 0);
else
ECCgenCNT <= "00000" & refCNT;
end if;
if(internal_COUNT >= x"833" and not(internal_COUNT = x"FFF")) then
Done2100Bytes <= '1';
else
Done2100Bytes <= '0';
end if;
end process CountUP;
SlowDOWNclk: process(clk, ResetTUGthelines, cntTUG)
variable clkOUT : std_logic;
begin
if(rising_edge(clk)) then
if(ResetTUGthelines = '0') then
cntTUG <= "000";
clkOUT := '0';
else
cntTUG <= cntTUG + 1;
if(cntTUG = "011") then
clkOUT := '1';
elsif(cntTUG = "101") then
cntTUG <= "000";
clkOUT := '0';
end if;
end if;
end if;
TUGthelines <= clkOUT;
-- slowCLK <= clkOUT;
end process SlowDOWNclk;
SYNCfsmSYSTEM: process(clkDIVx3, Reset_L, cSTATE, nextSTATE, enableECCmodule)
begin
if(rising_edge(clkDIVx3)) then
if (Reset_L = '0') then
cSTATE <= Start;
else
incrADDR_errLOC <= '0';
triSTATEnandIO <= '1';
case cSTATE is
when Start =>
triSTATEnandIO <= not(hostRE_L_tmp) or not(intRE_L)
or(not(enableECCmodule) and not(hostRE_L));
when ReadNAND =>
triSTATEnandIO <= '0';
when ReadNANDwaitforRB =>
triSTATEnandIO <= '1';
when ReadECCcalc =>
triSTATEnandIO <= '1';
when ReadECCfromNAND =>
if(cntTUG = "011") then
incrADDR_errLOC <= '1';
else
incrADDR_errLOC <= '0';
end if;
triSTATEnandIO <= '1';
when ThrowINT =>
triSTATEnandIO <= '1';
when ProgramNAND =>
triSTATEnandIO <= '0';
when ProgramNANDaddr =>
triSTATEnandIO <= '0';
when ProgramNANDbufST2 =>
triSTATEnandIO <= '0';
when ProgramNANDeccCALC =>
triSTATEnandIO <= '0';
when ProgramNANDbufST0 =>
triSTATEnandIO <= '0';
when ProgramNANDfillinOther =>
triSTATEnandIO <= '0';
when ProgramNANDbufST1 =>
triSTATEnandIO <= '0';
when ProgramNANDeccwrite=>
if(cntTUG = "011") then
incrADDR_errLOC <= '1';
else
incrADDR_errLOC <= '0';
end if;
triSTATEnandIO <= '0';
when ProgramNANDbufST3 =>
triSTATEnandIO <= '0';
when ProgramNANDcmd10h => -- this state writes the command
triSTATEnandIO <= '0';
when FetchERRORS =>
triSTATEnandIO <= '1';
when FetchERRORS_waitforRE =>
triSTATEnandIO <= '1';
when others =>
triSTATEnandIO <= '1';
end case;
cSTATE <= nextSTATE;
end if;
end if;
end process SYNCfsmSYSTEM;
COMBfsmOUTPUTS: process(cSTATE, hostCLE_H_tmp, hostCE_L_tmp, hostWE_L_tmp,
hostIOin_tmp, hostRB_L_tmp, hostRE_L_tmp,
intRE_L, Done2100Bytes, TUGthelines,
NeedINT, intALE_H, intWE_L, cntTUG, hostALE_H_tmp,
internal_COUNT, intRB_L, intCE_L, intCLE_H, intWP_L,
intIO, firstVAL, nandIO, HAMMING8bitin, ErrorLOCations,
enableECCmodule, hostIOin, nandRB_L, hostCE_L,
hostCLE_H, hostALE_H, hostWE_L, hostRE_L, hostWP_L)
variable MUXselIO: std_logic := '0';
variable fsmRB_L, fsmCE_L, fsmCLE_H, fsmALE_H, fsmWE_L,
fsmRE_L, fsmWP_L :std_logic;
begin
-- Variable outputs
MUXselIO := '0'; --keep defaults
-- FSM outputs
fsmRB_L := '1';
fsmCE_L := '1';
fsmCLE_H := '0';
fsmALE_H := '0';
fsmWE_L := '1';
fsmRE_L := '1';
fsmWP_L := '1';
interrINT_H <= '0';
errlocADDRsel <= '0';
-- WriteHAMMING to hostIO
--whtHOSTio <= '0';
--REstatus <= '0';
--HAMMINGtoNANDsel <= '0';
-- ECC state machine control
ResetECCgen <= '1';
SHOOTenable <= '1';
ECCgenCNTsel <= '0';
-- CounterCONTROL
ResetCOUNTER_L <= '1';
incCOUNT <= '0';
-- MUX selects
HammingINmuxSEL <= '0';
-- TUG the lines
ResetTUGthelines <= '0';
--nandDriveBuffer <= hostDriveBuffer;
STATEvec <= "1110";
FFintIO <= '0';
SELintIO10 <= '0';
hostIOdrv <= '0';
hostIOout <= x"BB";
if(enableECCmodule = '0') then
nandIOtempVAL <= hostIOin;
else
nandIOtempVAL <= intIO;
end if;
case cSTATE is
when Start =>
if(enableECCmodule = '0') then
nandIOtempVAL <= hostIOin;
else
nandIOtempVAL <= intIO;
end if;
MUXselIO := '1';
ResetCOUNTER_L <= '0';
if (hostCLE_H_tmp = '1' and hostCE_L_tmp = '0'
and hostWE_L_tmp = '0'
and enableECCmodule = '1') then
if(hostIOin_tmp = x"00") then
nextSTATE <= ReadNAND;
elsif(hostIOin_tmp = x"80") then
nextSTATE <= ProgramNAND;
elsif(hostIOin_tmp = ErrorFetchCommand) then
nextSTATE <= FetchERRORS;
end if;
else
nextSTATE <= Start;
end if;
STATEvec <= "0001";
--STATEvec <= hostRB_L_tmp & "001";
if(not(firstVAL) = '1' or not(intRE_L) = '1') then
hostIOdrv <= '1';
hostIOout <= nandIO;
else
hostIOdrv <= '0';
hostIOout <= x"BB";
end if;
-------------------- ERROR fetch States --------------------------
when FetchERRORS =>
errlocADDRsel <= '1';
MUXselIO := '0';
if(hostCLE_H_tmp = '0' and hostWE_L_tmp = '1') then
nextSTATE <= FetchERRORS_waitforRE;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -