⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 smartcard.vhd

📁 SD卡读写的VHDL VHDL Source Files in Smartcard: Top.vhd - top level file smartcard.vhd conver2asci
💻 VHD
字号:
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 smartcard is
    Port ( reset_button 	: in std_logic;
           card_enable 		: in std_logic;
           clk 				: in std_logic;
           card_vpp 			: out std_logic;
           card_vcc 			: out std_logic;
           card_clk 			: out std_logic;
           card_rst	 		: out std_logic;
           card_io 			: inout std_logic;
			  data_ready		: out std_logic;
			  done				: out std_logic;
           data_out			: out std_logic_vector(7 downto 0));
			  attribute DONT_OPTIMIZE : string;
			  attribute KEEP : string;
end smartcard;

architecture Behavioral of smartcard is
--**************************************************************************
-- STATE MACHINE SIGNAL DECLARATION:
type StateType is (IDLE, Init, ClkEnable, WaitForData, ReadData, ProcessData, WriteCommand);
signal CurrentState, NextState : StateType;
--**************************************************************************
signal io_rw				: std_logic;
signal clk_en				: std_logic;
signal counter_enable	: std_logic;
signal counter				: std_logic_vector(8 downto 0);
signal Bitcounter			: std_logic_vector(3 downto 0);
signal Bitcounter_clk	: std_logic;
signal Bytecounter		: std_logic_vector(7 downto 0);
signal Bytecounter_clk	: std_logic;
signal data					: std_logic_vector(9 downto 0);
signal data_mux			: std_logic_vector(9 downto 0);
signal Enable_signal		: std_logic;
signal Wait_a_Byte		: std_logic;
signal Command_ready		: std_logic;
signal Command_end		: std_logic;
signal data_valid			: std_logic;
signal reset				: std_logic;

attribute DONT_OPTIMIZE of card_io : signal is "TRUE";
--attribute KEEP of data_valid : signal is "TRUE";

begin
--**************************************************************************
COMB: process(CurrentState, Enable_signal, Card_io, Bitcounter, Wait_a_byte, Command_ready, Command_end)
begin
	case CurrentState is
		when IDLE =>
			if(Enable_signal = '1') then
				NextState <= Init;
			else
				NextState <= IDLE;
			end if;
		when Init =>
			NextState <= ClkEnable;
		when ClkEnable =>
			NextState <= WaitForData;
		when WaitForData =>
			if(Card_io = '0') then
				NextState <= ReadData;
			else
				Nextstate <= WaitForData;
			end if;
		when ReadData =>
			if (Bitcounter = 11)then 							  
				NextState <= ProcessData;
			else
				NextState <= ReadData;	
			end if;
		when Processdata =>
			if (Wait_a_byte = '1') then
				NextState <= ReadData;
			elsif (Command_ready = '1') then
				NextState <= WriteCommand;
			else
				NextState <= WaitForData;
			end if;
		when WriteCommand =>
			if (Command_end = '1') then
				Nextstate <= WaitForData;
			else
				NextState <= WriteCommand;
			end if;
	end case;
end process COMB;

--**************************************************************************
SEQ: process(Clk,Reset)
begin
	if(Reset = '1') then
		CurrentState <= Idle;
	elsif (clk'event and clk = '1') then
		CurrentState <= NextState;
	end if;
end process SEQ;

--**************************************************************************
with CurrentState select
	Card_rst <= '0' when IDLE,
			 		'0' when Init,
					'0' when ClkEnable,
			 		'1' when others;

with CurrentState select
	clk_en   <= '0' when IDLE,
			 		'0' when Init,
			 		'1' when others;

with CurrentState select	
	Card_vcc <= '0' when IDLE,
					'Z' when others;

with CurrentState select	
	Card_vpp <= '0' when IDLE,
					'Z' when others;

with CurrentState select	
	io_rw	  <=  '0' when WriteCommand,
					'1' when others;

with CurrentState select	
	counter_enable	  <=  '1' when ReadData,
								'1' when WriteCommand,
								'0' when others;

--**************************************************************************
--  9-bit counter, elementary time unit etu = 372 / f
--**************************************************************************
process(counter_enable, clk)
begin
	if(counter_enable = '0') then
		counter <= (others=>'0');
	elsif (clk'event and clk = '1') then
		if (counter = 371) then
			counter <= (others=>'0');
		else 
			counter <= counter + 1;
		end if;
	end if;
end process;

--**************************************************************************
--  4-bit Bitcounter, counting bits in a character frame
--**************************************************************************
Bitcounter_clk <= '1' when (counter = 371) else '0';
process(counter_enable, clk)
begin
	if(counter_enable = '0') then
		Bitcounter <= (others=>'0');
	elsif (Bitcounter_clk'event and Bitcounter_clk = '1') then
		if (Bitcounter = 11) then
			Bitcounter <= (others=>'0');
		else 
			Bitcounter <= Bitcounter + 1;
		end if;
	end if;
end process;

--**************************************************************************
--  8-bit Bytecounter, counting bytes in a command/response
--**************************************************************************
Bytecounter_clk <= '1' when (Bitcounter = 11) else '0';
process(Enable_signal, Bytecounter_clk)
begin
	if(Enable_signal = '0') then
		Bytecounter <= (others=>'0');
	elsif (Bytecounter_clk'event and Bytecounter_clk = '1') then
		Bytecounter <= Bytecounter + 1;
	end if;
end process;

--**************************************************************************
--  9 bit shifter
--**************************************************************************
process(counter_enable, clk)
begin										  	
	if(counter_enable = '0')  then
		data <= (others=>'0');
	elsif (clk'event and clk = '1') then
		if ((counter = 186) and (io_rw = '1')) then	--read
			data <= data(8 downto 0) & Card_io;
		elsif ((bitcounter = 0) and (counter = 0) and (io_rw = '0')) then	 --write
			data <= data_mux;
		elsif ((counter = 371) and (io_rw = '0')) then
			data(9 downto 0) <= '1' & data(9 downto 1);
		else
			data <= data;
		end if;
	end if;
end process;

--**************************************************************************
--  debounce ff
--**************************************************************************
process(Reset, clk)
begin
	if(reset = '1') then
		Enable_signal <= '0';
	elsif (clk'event and clk = '1') then
		Enable_signal <= Card_enable or Enable_signal;
	end if;
end process;


--**************************************************************************
--  COMBINATORIAL SIGNALS
--**************************************************************************
--shift_end <= '0' when ((Bitcounter = 10) and (counter < 160))  else '1';
Card_clk <= clk and clk_en;
Card_io <= data(0) when (io_rw = '0') else 'Z';
--data_out <= data(8 downto 1) when (data_valid = '1') else (others => '0');
reset <= reset_button or (not card_enable);

data_out(7) <= data(1) when (data_valid = '1') else '0';
data_out(6) <= data(2) when (data_valid = '1') else '0';
data_out(5) <= data(3) when (data_valid = '1') else '0';
data_out(4) <= data(4) when (data_valid = '1') else '0';
data_out(3) <= data(5) when (data_valid = '1') else '0';
data_out(2) <= data(6) when (data_valid = '1') else '0';
data_out(1) <= data(7) when (data_valid = '1') else '0';
data_out(0) <= data(8) when (data_valid = '1') else '0';

--data_out <= Bytecounter;
data_ready <= '1' when ((data_valid = '1') and (Bitcounter = 10)) else '0';

data_mux <= "1100000000" when (Bytecounter = 20)	--80
		 else "1101001000" when (Bytecounter = 21)	--A4
		 else "0000000000" when (Bytecounter = 22)	--00
		 else "0000000000" when (Bytecounter = 23)	--00
		 else "1000000100" when (Bytecounter = 24)	--02
		 --														  A4
		 else "0111100000" when (Bytecounter = 27)	--F0
		 else "0000000000" when (Bytecounter = 28)	--00
		 --														  91
		 --														  00
		 else "1100000000" when (Bytecounter = 32)	--80
		 else "0101100100" when (Bytecounter = 33)	--B2
		 else "0000000000" when (Bytecounter = 34)	--00
		 else "0000000000" when (Bytecounter = 35)	--00
		 else "1001000000" when (Bytecounter = 36)	--20
		 --														  B2
		 -- 32 bytes data
		 --
		 else "1100000000" when (Bytecounter = 73)	--80
		 else "1101001000" when (Bytecounter = 74)	--A4
		 else "0000000000" when (Bytecounter = 75)	--00
		 else "0000000000" when (Bytecounter = 76)	--00
		 else "1000000100" when (Bytecounter = 77)	--02
		 --														  A4
		 else "0111100000" when (Bytecounter = 80)	--F0
		 else "1000000010" when (Bytecounter = 81)	--01
		 --														  91
		 --														  00
		 else "1100000000" when (Bytecounter = 86)	--80
		 else "0101100100" when (Bytecounter = 87)	--B2
		 else "0000000000" when (Bytecounter = 88)	--00
		 else "0000000000" when (Bytecounter = 89)	--00
		 else "0000000110" when (Bytecounter = 90)	--03
		 --  B2 01 01 12 90 00
		 else "1100000000" when (Bytecounter = 99)	--80
		 else "0111000010" when (Bytecounter = 100)	--E1
		 else "0000000000" when (Bytecounter = 101)	--00
		 else "0000000000" when (Bytecounter = 102)	--00
		 else "1000001000" when (Bytecounter = 103)	--04
		 --														  E1 
		 else "0000000000" when (Bytecounter = 106)	--00
		 else "0000000000" when (Bytecounter = 107)	--00
		 else "0000000000" when (Bytecounter = 108)	--00
		 else "0000000000" when (Bytecounter = 109)	--00
		 -- 61 19
		 else "1100000000" when (Bytecounter = 113)	--80
		 else "0110000000" when (Bytecounter = 114)	--C0
		 else "0000000000" when (Bytecounter = 115)	--00
		 else "0000000000" when (Bytecounter = 116)	--00
		 else "1000110010" when (Bytecounter = 117)	--19
		 -- 25 byte data
		 else "1111111111";

Wait_a_byte <= '1' when	((Bytecounter = 19) 
							or	 (Bytecounter = 26)
							or	 (Bytecounter = 31)
							or	 (Bytecounter = 72)
							or	 (Bytecounter = 79)
							or	 (Bytecounter = 84)
							or	 (Bytecounter = 85)
							or	 (Bytecounter = 97)
							or	 (Bytecounter = 98)
							or	 (Bytecounter = 105)
							or	 (Bytecounter = 112)) else '0';

Command_ready <= '1' when	((Bytecounter = 20) 
							or	 (Bytecounter = 27)
							or	 (Bytecounter = 32)
							or	 (Bytecounter = 73)
							or	 (Bytecounter = 80)
							or	 (Bytecounter = 86)
							or	 (Bytecounter = 99)
							or	 (Bytecounter = 106)
							or	 (Bytecounter = 113)) else '0';

Command_end <= '1' when	((Bytecounter = 25) 
							or	 (Bytecounter = 29)
							or	 (Bytecounter = 37)
							or	 (Bytecounter = 78)
							or	 (Bytecounter = 82)
							or	 (Bytecounter = 91)
							or	 (Bytecounter = 104)
							or	 (Bytecounter = 110)
							or	 (Bytecounter = 118)) else '0';

data_valid <= '1' when	(((Bytecounter > 37) and (Bytecounter < 53))
							or	 ((Bytecounter > 91) and (Bytecounter < 95))
							--or	 ((Bytecounter > 124) and (Bytecounter < 127))
							) else '0';

done <= '1' when (Bytecounter >= 95) else '0';

end Behavioral;

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -