FPGA简易加减法计算器设计

题目要求:
(1)设计10以内的加减法计算器。
(2)1个按键用于指定加法或减法,一个用于指定加数或被加数,还有两个分别控制加数或被加数的增加或减少。
(3)设置的结果和计算的结果用数码管显示。

本实验我还是将其视作Mealy型向量机,具体的见我之前关于秒表的内容:VHDL实验:基于有限状态机实现秒表
按照题目意思,有4个键是必不可少的,但我还是决定增加两个推键,本实验状态图如下:
FPGA简易加减法计算器设计_第1张图片
S0:初态模式,所有数码管置零
S1:计算模式,等待用户设置并计算
这两者之间的转换我用开发板上的推键来完成。
另一个推键指示是进行整数运算还是一位小数。

我的代码:(抱歉注释是全英文的)

library ieee ;
use ieee.std_logic_1164.all ;
use ieee.std_logic_unsigned.all ;
use ieee.std_logic_arith.all ;

entity Computer is
	port (
		key3 : in std_logic ;						-- is addition or subtraction?
		key2 : in std_logic ;						-- who is augend or minuend?
		key1 : in std_logic ;						-- change the value of augend or minuend
		key0 : in std_logic ;						-- change the value of addend or subtrahend
		sw0 : in std_logic ;						-- change the state of circuit
		sw1 : in std_logic ;
		first1 : out std_logic_vector(0 to 6) ;
		first2 : out std_logic_vector(0 to 6) ;
		second1 : out std_logic_vector(0 to 6) ;
		second2 : out std_logic_vector(0 to 6) ;
		negative : out std_logic_vector(0 to 6) ;	-- Is the result a negative number?
		empty : out std_logic_vector(0 to 6) ;
		result1 : out std_logic_vector(0 to 6) ;	-- the result of computing
		result2 : out std_logic_vector(0 to 6) ;	-- the result of computing
		Point : out std_logic_vector(7 downto 0) ;	-- Radix point
		ledg8 : out std_logic ;						-- if substraction
		ledr16 : out std_logic ;					-- it is augend or minuend
		ledr13 : out std_logic 						-- it is augend or minuend
	) ;
end Computer ;

architecture mathematic of Computer is
	constant matrix_num : integer := 9 ;
	TYPE Number is array (0 to matrix_num) of std_logic_vector(0 to 6);
	signal Display : Number := (('0', '0', '0', '0', '0', '0', '1'),		-- 0
							   ('1', '0', '0', '1', '1', '1', '1'),			-- 1
							   ('0', '0', '1', '0', '0', '1', '0'),			-- 2
							   ('0', '0', '0', '0', '1', '1', '0'),			-- 3
							   ('1', '0', '0', '1', '1', '0', '0'),			-- 4
							   ('0', '1', '0', '0', '1', '0', '0'),			-- 5
							   ('0', '1', '0', '0', '0', '0', '0'),			-- 6
							   ('0', '0', '0', '1', '1', '1', '1'),			-- 7
							   ('0', '0', '0', '0', '0', '0', '0'),			-- 8
							   ('0', '0', '0', '0', '1', '0', '0')			-- 9
							  ) ;
	TYPE state_type is (s0, s1) ;		-- how many states does the circuit have?
	signal current_state : state_type ;
	-- all of them below are middle data
	signal neg : std_logic_vector(0 to 6) := ('1', '1', '1', '1', '1', '1', '1') ;
	signal led8 : std_logic ;						
	signal led16 : std_logic ;					
	signal led13 : std_logic ;
	signal p : std_logic_vector(7 downto 0) ;					
begin
	process(sw0)											 -- to change the state of circuit
	begin
		if (sw0 = '0') then
			current_state <= s0 ;
		else
			current_state <= s1 ;
		end if ;
	end process ;
	
	process(current_state, key3, key2, key1, key0, sw1) -- take action according to state
		variable First : integer := 0 ;
		variable Second : integer := 0 ;
		variable Result : integer := 0 ;
		variable num3 : integer := 0 ;
		variable num2 : integer := 0 ;
	begin
		if (current_state = s0) then
			First := 0 ;
			Second:= 0 ;
			Result:= 0 ;
			num3  := 0 ;
			num2  := 0 ;
			neg <= ('1', '1', '1', '1', '1', '1', '1') ;					
			p <= ('1', '1', '1', '1', '1', '1', '1', '1') ;
			led8 <= '0' ;
			led16 <= '0' ;				
			led13 <= '0' ;
		elsif (current_state = s1) then
			if (sw1 = '1') then			-- make sure integer or float
				p <= ('0', '1', '0', '1', '1', '1', '0', '1') ;
			else 
				p <= ('1', '1', '1', '1', '1', '1', '1', '1') ;
			end if ;
			
			if falling_edge(key2) then	-- make sure who is augend or minuend?
				num2 := num2 + 1 ;
			end if ;
			if ((num2 > 0) and(num2 MOD 2 = 0)) then
				led16 <= '0' ;
				led13 <= '1' ;
			elsif (num2 MOD 2 = 1) then
				led16 <= '1' ;
				led13 <= '0' ;
			end if ;
			
			if falling_edge(key1) then		-- decide the value of first number
				First := First + 1 ;
				if (First > 10) then
					First := 0 ;
				end if ;
			end if ;
			
			if falling_edge(key0) then 		-- decide the value of second number
				Second := Second + 1 ;
				if (Second > 10) then
					Second := 0 ;
				end if ;
			end if ;
			
			if falling_edge(key3) then
				num3 := num3 + 1 ;
			end if ;
			if (num3 MOD 2 = 1) then
				led8 <= '0' ;
				neg(6) <= '1' ;
				Result := First + Second ;
			elsif ((num3>0) and (num3 MOD 2 = 0)) then
				led8 <= '1' ;
				if (led13 = '1') then
					if (Second < first) then
						neg(6) <= '0' ;
						Result := First - Second ;
					else
						neg(6) <= '1' ;
						Result := Second - First ;
					end if ;
				elsif (led16 = '1') then
					if (first < Second) then
						neg(6) <= '0' ;
						Result := Second - First ;
					else
						neg(6) <= '1' ;
						Result := First - Second ;
					end if ;
				end if ;
			end if ;
		end if ;
		
		empty <= ('1', '1', '1', '1', '1', '1', '1') ;
		first1 <= Display(First/10) ;
		first2 <= Display(First MOD 10) ;
		second1 <= Display(Second/10) ;
		second2 <= Display(Second MOD 10) ;
		negative <= neg ;
		result1 <= Display(Result/10) ;
		result2 <= Display(Result MOD 10);
		Point <= p ;
		ledg8 <= led8 ;
		ledr16 <= led16 ;
		ledr13 <= led13 ;
	end process ;
end mathematic ;

你可能感兴趣的:(FPGA,fpga开发,VHDL)