📄 dp_test.vhd
字号:
library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_unsigned.all;
entity dp_test is
generic (N:integer :=4); -- 时钟4分频
port (
clk : in std_logic;
rst : in std_logic;
mcu_nwr : in std_logic; -- mcu的wr
mcu_nrd : in std_logic; -- mcu的rd
mcu_ncs : in std_logic;
data : inout std_logic_vector(15 downto 0); --数据总线
Addr_Bus : in std_logic_vector(5 downto 0);
servo_poisition : in std_logic_vector(15 downto 0); --伺服电机位置和外部其他一些信息输入信息
luola_in : in std_logic_vector(9 downto 0); --罗拉位置输入和外部其他一些信息输入
clk_out : out std_logic; -- Test
Moto_A_dir : out std_logic; -- 步进电机A方向输出
Moto_A_cp : out std_logic; -- 步进电机A脉冲输出
Servo_A_dir : out std_logic; -- 伺服电机A方向输出
Servo_A_cp : out std_logic; -- 伺服电机A脉冲输出
Servo_B_dir : out std_logic; -- 伺服电机B方向输出
Servo_B_cp : out std_logic; -- 伺服电机B脉冲输出
Servo_A_on : out std_logic; -- 伺服电机A伺服控制器使能输出
Servo_B_on : out std_logic; -- 伺服电机B伺服控制器使能输出
Servo_A_clr : out std_logic; -- 伺服电机A伺服控制器累积脉冲清零输出
Servo_B_clr : out std_logic; -- 伺服电机B伺服控制器累积脉冲清零输出
Servo_A_Lock : in std_logic; -- MCU发给CPLD的驱动使能信号
Servo_unable : in std_logic;
----------------------------------------------------------
Servo_Phase_A : in std_logic; -- 伺服编码器编码输入
Servo_Phase_B : in std_logic;
servo_cp_test : out std_logic; -- 伺服编码器4倍频输出
servo_dir_test : out std_logic
--data_out : out std_logic_vector(3 downto 0)
);
end;
architecture exam of dp_test is
constant Moto : integer :=10;
signal count : integer;
signal clk_in : std_logic;
--SIGNAL Dout : std_logic_vector(3 downto 0);--总线输出
--步进电机------------------------------------------
signal A_moto : std_logic_vector(3 downto 0);--步进电机A控制寄存器
signal A_moto_en :std_logic; -- 步进电机A使能控制寄存器
signal A_moto_dir :std_logic; -- 步进电机A方向控制寄存器
signal A_moto_cp :std_logic; -- 步进电机A脉冲控制寄存器
signal A_moto_count :integer; -- 步进电机A脉冲对内部时钟的分频计数器
--伺服电机------------------------------------------
signal A_servo : std_logic_vector(7 downto 0); -- 伺服电机A控制寄存器
signal B_servo : std_logic_vector(15 downto 8);-- 伺服电机B控制寄存器
signal A_sv_enable:std_logic_vector (1 downto 0);-- 伺服电机A使能控制
signal B_sv_enable:std_logic_vector (1 downto 0);-- 伺服电机B使能控制
signal A_sv_clr :std_logic; -- 伺服电机A控制器累积脉冲清零数输出寄存器
signal B_sv_clr :std_logic; -- 伺服电机B控制器累积脉冲清零数输出寄存器
signal A_servo_on :std_logic; -- 伺服电机A控制器使能输出寄存器
signal B_servo_on :std_logic; -- 伺服电机B控制器使能输出寄存器
signal A_servo_dir:std_logic; -- 伺服电机A方向控制寄存器
signal B_servo_dir:std_logic; -- 伺服电机B方向控制寄存器
signal A_servo_cp :std_logic; -- 伺服电机A脉冲控制寄存器
signal B_servo_cp :std_logic; -- 伺服电机B脉冲控制寄存器
signal A_phase_ctr: std_logic; -- 伺服电机A脉冲相位输出控制寄存器
signal B_phase_ctr: std_logic; -- 伺服电机B脉冲相位输出控制寄存器
signal A_servo_fre:integer ; -- 伺服电机A频率输出寄存器
signal B_servo_fre:integer ; -- 伺服电机B频率输出寄存器
signal A_fre_buf:integer ; -- 伺服电机A频率输出缓存
signal B_fre_buf:integer ; -- 伺服电机B频率输出缓存
signal A_servo_stop:std_logic; -- 伺服电机A因为到了行程极限而停止
signal B_servo_stop:std_logic; -- 伺服电机B因为到了行程极限而停止
signal A_run_state:std_logic_vector(1 downto 0); --伺服电机运行状态
signal B_run_state:std_logic_vector(1 downto 0); --伺服电机运行状态
signal A_speed_ctr :std_logic_vector(3 downto 0); -- 伺服电机A速度控制寄存器
signal B_speed_ctr :std_logic_vector(3 downto 0); -- 伺服电机B速度控制寄存器
signal A_servo_counter :integer; -- 伺服电机A脉冲控制计数器
signal B_servo_counter :integer; -- 伺服电机B脉冲控制计数器
signal A_frequecy:integer range 0 to 200; -- 伺服电机A频率输出控制字
constant A_fre_min:integer:=2000; -- 伺服电机A频率输出最小控制寄存器
constant A_fre_max0:integer:=156; -- 伺服电机A频率输出第0档最大控制寄存器
constant A_fre_max1:integer:=104; -- 伺服电机A频率输出第1档最大控制寄存器
constant A_fre_max2:integer:=78; -- 伺服电机A频率输出第2档最大控制寄存器
constant A_fre_max3:integer:=62; -- 伺服电机A频率输出第3档最大控制寄存器
constant A_fre_max4:integer:=52; -- 伺服电机A频率输出第4档最大控制寄存器
constant A_fre_max5:integer:=46; -- 伺服电机A频率输出第5档最大控制寄存器
constant A_fre_max6:integer:=40; -- 伺服电机A频率输出第6档最大控制寄存器
constant A_fre_max7:integer:=36; -- 伺服电机A频率输出第7档最大控制寄存器
constant A_fre_max8:integer:=32; -- 伺服电机A频率输出第8档最大控制寄存器
constant A_fre_max9:integer:=26; -- 伺服电机A频率输出第9档最大控制寄存器
constant B_fre_min:integer:=80000; -- 伺服电机B频率输出最小控制寄存器
constant B_fre_max:integer:=40; -- 伺服电机B频率输出最大控制寄存器
----------------------------------------------------------------------
------编码器--------
signal Not_A_phase_a :std_logic; -- 伺服电机编码器读取
signal A_phase_a :std_logic;
signal A_phase_b :std_logic;
signal A_cw_test :std_logic; -- 测试
signal A_ccw_test :std_logic;
signal A_servo_count_clr :std_logic_vector(1 downto 0);
signal A_servo_pdir:std_logic; -- 伺服电机A编码器反馈的方向
signal A_servo_cp_clr :std_logic; -- 伺服电机A编码器读数清零
signal A_cp_number :std_logic_vector(15 downto 0); -- 伺服电机A编码器读数存储
signal A_servo_cp_cw :std_logic_vector(15 downto 0); -- 伺服电机A编码器正向脉冲读数存储
signal A_servo_cp_ccw :std_logic_vector(15 downto 0); -- 伺服电机A编码器反向脉冲读数存储
signal A_servo_cp_temp :std_logic_vector(15 downto 0); -- 伺服电机A编码器读数缓存
signal A_servo_count:integer;
signal B_servo_count_clr :std_logic_vector(1 downto 0);
signal B_servo_cp_clr :std_logic;
signal cpld_mcu_interupt :std_logic; --CPLD发送给MCU的中断信号寄存器
------------------------------------------------------------
begin
process(clk)
begin
if(clk'event and clk ='1') then
if(count =N-1) then count<= 0;
else count <=count +1;
if count < (integer (N/2)) then clk_in <= '0';
else clk_in<= '1';
end if;
end if;
end if;
end process;
clk_out <= clk_in;
--data_out<= Dout;
Moto_A_cp <= A_moto_cp; -- 步进电机A控制输出
Moto_A_dir <= A_moto_dir;
--Read :process (mcu_nrd,mcu_ncs,servo_poisition,luola_in,A_cp_number,Addr_Bus)
Read: process(clk_in)
begin
if (clk_in'event and clk_in ='1') then
if (mcu_nrd='0' and mcu_ncs ='0') then
case Addr_Bus is
when "000000" => data <= servo_poisition; -- 地址0x00000000读取伺服位置等信息
when "000001" => data <= "000000" & luola_in ; -- 地址0x00000002读取罗拉位置等信息
when "000010" => data <= A_cp_number(15 downto 0); --地址0x00000004读取伺服电机A的低16位值
when "000011" => data <= A_cp_number(15 downto 0); --地址0x00000006读取伺服电机A的高4位值
when others => data <="0000000000000000";
end case;
else
data <="ZZZZZZZZZZZZZZZZ";
end if;
end if;
end process Read;
Write :process (clk_in,rst)
begin
if (clk_in'event and clk_in ='1') then
if rst = '0' then A_moto <= "0000"; -- 电机控制字初始化
A_servo<= "00000000";
B_servo<= "00000000";
else
if ( mcu_nwr = '0' and mcu_ncs ='0' ) then
case Addr_Bus is
when "001000" => A_moto <= data (3 downto 0); -- 地址0x00000010写步进电机控制信息
when "001001" => A_servo<= data (7 downto 0); -- 地址0x00000012写伺服电机A控制信息
when "001010" => B_servo<= data (7 downto 0); -- 地址0x00000014写伺服电机B控制信息
when "001111" => A_servo_count_clr <= data (1 downto 0); -- 地址0x00000016写伺服电机A编码器清零信息
when "001100" => B_servo_count_clr <= data (1 downto 0); -- 地址0x00000018写伺服电机B编码器清零信息
when "001011" => A_sv_enable<= data (1 downto 0); -- 地址0x0000001a写伺服电机A使能信息
when "001110" => B_sv_enable<= data (1 downto 0); -- 地址0x0000001c写伺服电机B使能信息
when others => A_moto <= A_moto; -- 电机控制字初始化
A_servo<= A_servo;
B_servo<= B_servo;
end case;
end if;
end if;
end if;
end process Write;
--步进电机A控制---------------------------------------
Moto_A: process (A_moto,rst) -- 步进电机控制进程
begin
if rst ='0' then A_moto_en<= '0'; A_moto_dir <= '0'; -- 复位方向为正方向,不发脉冲
else
-- A_moto第0位为使能控制位 0->关 1->开
-- A_moto第1位为方向控制位 0->正方向 1->反方向
case A_moto is
when "0000" => A_moto_en<= '0'; A_moto_dir <= '0';
when "0001" => A_moto_en<= '1'; A_moto_dir <= '0';
when "0011" => A_moto_en<= '1'; A_moto_dir <= '1';
when others => A_moto_en<= '0'; A_moto_dir <= '0';
end case;
end if;
end process Moto_A;
Moto_A_Run: process (clk_in,rst,A_moto_en) -- 步进电机脉冲产生进程
begin
if (rst ='0' or A_moto_en ='0') then A_moto_cp <='0';
else
if (clk_in'event and clk_in ='1') then
if(A_moto_count =Moto-1) then A_moto_count<= 0;
else A_moto_count <=A_moto_count +1;
if A_moto_count < (integer (Moto/2)) then A_moto_cp <= '0';
else A_moto_cp<= '1';
end if;
end if;
end if;
end if;
end process Moto_A_Run;
-------------------------------------------------------------
-------------------------------------------------------------
A_servo_sensor_test:process(clk_in,rst)
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -