📄 timer.vhd
字号:
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_unsigned.all;
entity timer is
port(
rst : in std_logic;
clk : in std_logic;
cs : in std_logic;
oe : in std_logic;
we : in std_logic;
addr: in std_logic_vector(7 downto 0);
data: inout std_logic_vector(15 downto 0);
out1 : out std_logic; out2 : out std_logic;
out3 : out std_logic;
out4 : out std_logic
);
end timer;
architecture behave of timer iS
signal TCON : std_logic_vector(15 downto 0);
signal TCNTB1 : std_logic_vector(15 downto 0);
signal TCMPB1 : std_logic_vector(15 downto 0);
signal TDEADZONE : std_logic_vector(15 downto 0);
signal TCNT1 : integer range 0 to 65535;
signal TCMP1 : integer range 0 to 65535;
signal TCNTB2 : std_logic_vector(15 downto 0);
signal TCMPB2 : std_logic_vector(15 downto 0);
signal TCNT2 : integer range 0 to 65535;
signal TCMP2 : integer range 0 to 65535;
signal pwmout1 : std_logic;
signal pwmout2 : std_logic;
signal deadpwmout1 : std_logic;
signal deadpwmout2 : std_logic;
signal deadcount1 : integer range 0 to 255;
signal deadcount2 : integer range 0 to 255;
begin
process(clk,rst)
begin
if(rst = '0') then
TCON <= (others => '0');
TCNTB1 <= (others => '0');
TCMPB1 <= (others => '0');
TCNT1 <= 0;
TCMP1 <= 0;
TDEADZONE <= (others => '0');
TCNTB2 <= (others => '0');
TCMPB2 <= (others => '0');
TCNT2 <= 0;
TCMP2 <= 0;
deadcount1 <= 0;
deadcount2 <= 0;
elsif(clk'event and clk = '1') then
--write register
if(cs = '0' and we = '0' and oe = '1' and addr = "00000000") then
TCON <= data;
elsif(cs = '0' and we = '0' and oe = '1' and addr = "00000001") then
TDEADZONE <= data;
elsif(cs = '0' and we = '0' and oe = '1' and addr = "00000010") then
TCNTB1 <= data;
elsif(cs = '0' and we = '0' and oe = '1' and addr = "00000011") then
TCMPB1 <= data;
elsif(cs = '0' and we = '0' and oe = '1' and addr = "00000100") then
TCNTB2 <= data;
elsif(cs = '0' and we = '0' and oe = '1' and addr = "00000101") then
TCMPB2 <= data;
end if;
--read register
if(cs = '0' and oe = '0' and we = '1' and addr = "00000000") then
data <= TCON;
elsif(cs = '0' and oe = '0' and we = '1' and addr = "00000001") then
data <= TDEADZONE;
elsif(cs = '0' and oe = '0' and we = '1' and addr = "00000010") then
data <= TCNTB1;
elsif(cs = '0' and oe = '0' and we = '1' and addr = "00000011") then
data <= TCMPB1;
elsif(cs = '0' and oe = '0' and we = '1' and addr = "00000100") then
data <= TCNTB2;
elsif(cs = '0' and oe = '0' and we = '1' and addr = "00000101") then
data <= TCMPB2;
else
data <= (others => 'Z');
end if;
--timer1 control
if(TCON(0) = '0' and TCON(1) = '1') then
TCNT1 <= CONV_INTEGER(TCNTB1);
TCMP1 <= CONV_INTEGER(TCMPB1);
pwmout1 <= '0';
elsif(TCON(0) = '1' and TCON(1) = '0') then
TCNT1 <= TCNT1 - 1;
if(TCNT1 > TCMP1) then
pwmout1 <= '1';
else
pwmout1 <= '0';
end if;
if(TCNT1 = 0) then
TCNT1 <= CONV_INTEGER(TCNTB1);
TCMP1 <= CONV_INTEGER(TCMPB1);
end if;
else
pwmout1 <= '0';
end if;
--timer1 deadzone
if(TCON(0) = '1' and TCON(1) = '0' and TCON(2) = '1') then
if(pwmout1 = '1') then
if(deadcount1 < CONV_INTEGER(TDEADZONE(7 downto 0))) then
deadcount1 <= deadcount1 + 1;
else
deadcount1 <= CONV_INTEGER(TDEADZONE(7 downto 0));
deadpwmout1 <= '1';
end if;
elsif(pwmout1 = '0') then
if(deadcount1 > 0) then
deadcount1 <= deadcount1 - 1;
else
deadcount1 <= 0;
deadpwmout1 <= '0';
end if;
end if;
out1 <= pwmout1 and deadpwmout1;
out2 <= not(pwmout1 or deadpwmout1);
elsif(TCON(0) = '1' and TCON(1) = '0' and TCON(2) = '0') then
out1 <= pwmout1;
out2 <= not(pwmout1);
else
out1 <= '0';
out2 <= '0';
end if;
--timer2 control
if(TCON(4) = '0' and TCON(5) = '1') then
TCNT2 <= CONV_INTEGER(TCNTB2);
TCMP2 <= CONV_INTEGER(TCMPB2);
pwmout2 <= '0';
elsif(TCON(4) = '1' and TCON(5) = '0') then
TCNT2 <= TCNT2 - 1;
if(TCNT2 > TCMP2) then
pwmout2 <= '1';
else
pwmout2 <= '0';
end if;
if(TCNT2 = 0) then
TCNT2 <= CONV_INTEGER(TCNTB2);
TCMP2 <= CONV_INTEGER(TCMPB2);
end if;
else
pwmout2 <= '0';
end if;
--timer1 deadzone
if(TCON(4) = '1' and TCON(5) = '0' and TCON(6) = '1') then
if(pwmout2 = '1') then
if(deadcount2 < CONV_INTEGER(TDEADZONE(15 downto 8))) then
deadcount2 <= deadcount2 + 1;
else
deadcount2 <= CONV_INTEGER(TDEADZONE(15 downto 8));
deadpwmout2 <= '1';
end if;
elsif(pwmout2 = '0') then
if(deadcount2 > 0) then
deadcount2 <= deadcount2 - 1;
else
deadcount2 <= 0;
deadpwmout2 <= '0';
end if;
end if;
out3 <= pwmout2 and deadpwmout2;
out4 <= not(pwmout2 or deadpwmout2);
elsif(TCON(4) = '1' and TCON(5) = '0' and TCON(6) = '0') then
out3 <= pwmout2;
out4 <= not(pwmout2);
else
out3 <= '0';
out4 <= '0';
end if;
end if;
end process;
end behave;
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -