【嵌入式开发】FPGA/CPLD控制串口(VHDL版)

简介:

采用自顶向下设计:

top_rs232_port.vhd

library ieee; 
use ieee.std_logic_1164.all;

entity rs232_port is 
    port (    serialinput   : in  std_logic; 
              clock         : in  std_logic; 
              reset         : in  std_logic; 
              readinput     : in  std_logic; 
              sendoutput          : in  std_logic; 
              serial_in        : in  std_logic_vector(7 downto 0); 
              serialoutput  : out std_logic; 
              getinput            : out std_logic; 
              outputsent          : out std_logic; 
              serial_out    : out std_logic_vector(7 downto 0)); 
     end rs232_port;

architecture behavioral of rs232_port is 
signal fastclk    : std_logic; 
signal slowclk    : std_logic;

component rs232_in 
    port(data_out : out std_logic_vector(7 downto 0); 
           reset    : in std_logic; 
           clock    : in std_logic; 
           getdata  : in std_logic; 
           ready    : out std_logic; 
           serialinput: in std_logic); 
  end component;

component rs232_out 
    port(data_in : in std_logic_vector(7 downto 0); 
           reset   : in std_logic; 
           clock   : in std_logic; 
           load    : in std_logic; 
           ready   : out std_logic; 
           serialoutput : out std_logic); 
  end component;

component clkdiv 
   Generic (Divisor1: positive :=1311; -- clock for sending 
            Divisor2: positive :=82 ); -- clock for receiving 
      PORT(fast_clock : IN STD_LOGIC; 
           reset      : IN STD_LOGIC; 
           slow_clock1: out STD_LOGIC; 
           slow_clock2: out STD_LOGIC); 
END component;

begin 
serin:     rs232_in 
                port map(data_out      => serial_out, 
                            reset         => reset, 
                            clock         => fastclk, 
                            getdata    => readinput, 
                            ready         => getinput, 
                            serialinput=> serialinput);

serout:     rs232_out 
                port map(data_in        => serial_in, 
                            reset          => reset, 
                            clock          => slowclk, 
                            load           => sendoutput, 
                            ready          => outputsent, 
                            serialoutput=> serialoutput); 
clocks:        clkdiv 
                port map(fast_clock     => clock, 
                         reset             => reset, 
                         slow_clock1 => slowclk, 
                         slow_clock2 => fastclk);

end behavioral;

rs232_input.vhd

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

entity rs232_in is 
    port(data_out: out std_logic_vector(7 downto 0); 
           reset   : in std_logic; 
           clock   : in std_logic; 
           getdata : in std_logic; 
           ready   : out std_logic; 
           serialinput : in std_logic); 
  end rs232_in;

architecture behavioural of rs232_in is 
signal   indata   : std_logic_vector(7 downto 0);    
constant countmax : natural := 153; 
begin

process (clock) 
variable count:natural range 0 to 170; 
variable startbit : integer range 0 to 2 ; 
    begin 
        if (clock'event and clock='1') then 
             if ( reset = '1' or getdata = '1')then 
               indata <= (others => '0'); 
               ready  <= '0'; 
               count  := 0; 
               data_out <= (others => '0'); 
          startbit := 0 ; 
           elsif (serialinput = '0' and startbit = 0) then 
                 startbit := 1;    
        elsif (serialinput = '1' and count  >= countmax) then 
           startbit := 0; 
           data_out <= indata; 
                 count:= 0; 
                 ready <= '1'; 
                 indata <= (others => '0'); 
           end if;      

          if (startbit = 1) then    
             count:= (count +1);    
                        case count is 
                           when 24 => 
                               indata(0) <= serialinput; 
                           when 40 => 
                               indata(1) <= serialinput; 
                           when 56 => 
                               indata(2) <= serialinput; 
                           when 72 => 
                               indata(3) <= serialinput; 
                           when 88 => 
                               indata(4) <= serialinput; 
                           when 104 => 
                               indata(5) <= serialinput; 
                           when 120 => 
                               indata(6) <= serialinput; 
                           when 136 => 
                               indata(7) <= serialinput; 
                           when others => 
                               count:= count; 
                         end case; 
            end if; 
end if; 
end process ; 
end behavioural;

rs232_output.vhd

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

entity rs232_out is 
    port(data_in : in std_logic_vector(7 downto 0); 
           reset   : in std_logic; 
           clock   : in std_logic; 
           load    : in std_logic; 
           ready   : out std_logic; 
           serialoutput : out std_logic); 
end rs232_out;

architecture behavioural of rs232_out is 
signal frame : std_logic_vector(10 downto 0); 
signal internaldata : std_logic_vector(7 downto 0); 
signal ready_s : std_logic;    
begin 
  frame(0) <= '1'; 
    frame(1) <= '0'; 
    frame(9 downto 2) <= internaldata; 
    frame(10)<= '1'; 
    ready    <= ready_s; 
process (clock) 
variable count:natural range 0 to 10; 
begin 
    if (clock'event and clock ='1') then 
        if (reset = '1') then 
            internaldata <= (others => '0'); 
            ready_s <= '1'; 
            count   := 0; 
            serialoutput <= frame(0); 
        elsif load = '1' then 
            ready_s <= '0'; 
            internaldata <= data_in; 
            serialoutput <= frame(0); 
            count:= 0; 
        elsif ready_s = '1' then 
            serialoutput <= frame(0); 
        elsif count = 10 then 
            ready_s <= '1'; 
            serialoutput <= frame(count); 
            count:= 0; 
        else 
            count:= (count +1); 
            serialoutput <= frame(count); 
        end if;        
    end if; 
end process ; 
end behavioural;

clockkdiv.vhd

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

ENTITY clkdiv IS 
   Generic (Divisor1: positive :=1311; -- clock for sending 
            Divisor2: positive :=82 ); -- clock for receiving 
   PORT(fast_clock : IN  STD_LOGIC; 
        reset      : IN  STD_LOGIC; 
        slow_clock1: out STD_LOGIC; 
        slow_clock2: out STD_LOGIC); 
END clkdiv;

ARCHITECTURE behaviour OF clkdiv IS 
signal  slow_clock1_s : std_logic; 
signal  slow_clock2_s : std_logic; 
BEGIN 
slow_clock1 <= slow_clock1_s; 
slow_clock2 <= slow_clock2_s; 
process (fast_clock) 
   variable c1:natural range 0 to Divisor1; 
   variable c2:natural range 0 to Divisor2; 
BEGIN 
if( fast_clock'EVENT and fast_clock = '1') then 
   if (reset = '1') then 
           c1:= 0; 
      c2:= 0; 
      slow_clock1_s <='0' ;  
         slow_clock2_s <= '0';  
    else                                 
         c1 := (c1 + 1); 
      c2 := (c2 + 1); 
         IF (c1=Divisor1) THEN 
            slow_clock1_s <= not slow_clock1_s; 
            c1 := 0; 
         elsif (c2 = Divisor2) then 
            slow_clock2_s <= not slow_clock2_s; 
            c2:= 0; 
         END IF; 
     end if;   
end if; 
END PROCESS ; 
END behaviour;

 




本文转自gnuhpc博客园博客,原文链接:http://www.cnblogs.com/gnuhpc/archive/2012/12/21/2828339.html,如需转载请自行联系原作者

相关文章
|
5月前
|
算法 异构计算
基于FPGA的Lorenz混沌系统verilog开发,含testbench和matlab辅助测试程序
基于FPGA的Lorenz混沌系统verilog开发,含testbench和matlab辅助测试程序
|
7月前
|
算法 芯片 异构计算
通过FPGA实现基于RS232串口的指令发送并控制显示器中目标位置
通过FPGA实现基于RS232串口的指令发送并控制显示器中目标位置
|
5月前
|
算法 测试技术 计算机视觉
基于FPGA的图像中值滤波开发,包括tb测试文件以及matlab验证代码
基于FPGA的图像中值滤波开发,包括tb测试文件以及matlab验证代码
|
5月前
|
算法 异构计算
基于FPGA的图像sobel边缘提取算法开发,包括tb测试文件以及matlab验证代码
基于FPGA的图像sobel边缘提取算法开发,包括tb测试文件以及matlab验证代码
|
10月前
|
编解码 算法 异构计算
基于FPGA的DDS开发和实现,可修改输出正弦的频率和相位,包含testbench
基于FPGA的DDS开发和实现,可修改输出正弦的频率和相位,包含testbench
278 1
|
11月前
|
存储 算法 异构计算
基于FPGA的Hamming编译码verilog开发实现,包括testbench测试程序
基于FPGA的Hamming编译码verilog开发实现,包括testbench测试程序
163 0
|
11月前
|
机器学习/深度学习 算法 异构计算
基于FPGA的FIR低通滤波器verilog开发,包含testbench测试程序,输入噪声信号使用MATLAB模拟产生
基于FPGA的FIR低通滤波器verilog开发,包含testbench测试程序,输入噪声信号使用MATLAB模拟产生
128 0
|
11月前
|
算法 异构计算
基于FPGA的FSK调制解调系统verilog开发
基于FPGA的FSK调制解调系统verilog开发
153 0
|
算法 数据安全/隐私保护 异构计算
基于FPGA的AES加密解密vivado仿真,verilog开发,包含testbench
基于FPGA的AES加密解密vivado仿真,verilog开发,包含testbench
234 0
基于FPGA的AES加密解密vivado仿真,verilog开发,包含testbench