(3)RS232总线电平转换:
(4)RS232数据传输格式:
串行通信中,线路空闲时,线路的TTL电平总是高,经反向RS232的电平总是低。一个数据的开始RS232线路为高电平,结束时RS232为低电平。数据总是从低位向高位一位一位的传输。示波器读数时,左边是数据的低位。例如,对于16进制数据55H和aaH,当采用8位数据位、1位停位传输时位停止位传输时:55H=01010101B,高低位倒序后为10101010B,加入一个起始位0,一个停止位1,55H的数据格式为0101010101。aaH=10101010B,高低位倒序后为01010101B,加入一个起始位0,一个停止位1,aaH的数据格式为:0010101011 (5)RS232通信过程:
I:开始通信时,信号线为空闲(逻辑),当检测到由到的跳变时,开始对“接收 时钟”计数。
II:当计到8个时钟时,对输入信号进行检测,若仍为低电平,则确认这是“起 始位”,而不是干扰信号。
III:接收端检测到起始位后,隔16个接收时钟,对输入信号检测一次,把对应的值 作为D0位数据。若为逻辑1, 作为数据位1;若为逻辑0,作为数据位0。 IV:再隔16个接收时钟,对输入信号检测一次,把对应的值作为D1位数据。?., 直到全部数据位都输入。 V:检测校验位P(如果有的话)。
VI:接收到规定的数据位个数和校验位后,通信接口电路希望收到停止位S(逻辑 1),若此时未收到逻辑说明出现了错误在状态寄存器中置“帧错误”标志若没 若此时未收到逻辑1,说明出现了错误,在状态寄存器中置“帧错误”标志。若 没有错误,对全部数据位进行奇偶校验,无校验错时,把数据位从移位寄存器 中送数据输入寄存器。若校验错,在状态寄存器中置奇偶错标志。 VII:本幀信息全部接收完把线路上出现的高电平作为空闲位。 VIII:当信号再次变为低时,开始进入下一帧的检测。
3.2软件设计
(1)Quartus顶层设计
如上图所示,整个顶层设计可以分为4个部分,(1)锁相环;作用是将输入的系统时钟信号(系统时钟50MHZ)转换为12MHZ的sysclk时钟,在进入RS232前先进行第一次分频弥补RS232自身分频不足的特点。(2)核心模块RS232;作用是将计算机输入的串行数据转换为并行数据便于给后方的显示模块处理。(3)分频模块;作用是给显示模块提供所需的时钟,由于显示模块的本质是一个个显示,所以为了能同时显示故将输入频率调至1KHz以上让人眼无法一个个识别形成同时显示的效果。(4)显示模块;作用是将输入的并行信号(8位)分成4位一组,即两组进行处理后在试验箱的数码管上显示。 (1-1)模块一分析:
从上图可以看出:1.inclk=50MHz 2.DC=50% 3.Ratio=12/25 ,从而可以得出outclk=50MHz*12/25=24MHz,再通过D触发器2分频后得到12MHz的输出系统时钟来弥补RS232模块分频不足的缺点。 (1-2)模块二分析:
上图所示的为RS232集成模块,经VHDL编译生成的模块文件。输入为sysclk=12MHz,rxd=计算机输入的串行数据串,disp为8位的并行数据段。 程序1:
library ieee;
use ieee.std_logic_1164.all; use ieee.std_logic_unsigned.all; entity rs232 is
port(sysclk: in std_logic; rxd: in std_logic;
disp: out std_logic_vector(7 downto 0) ); end rs232;
分析:定义实体。输入信号,输入时钟信号为逻辑信号,输出信号disp为8位矢量信号,低位为0 高位为7。
architecture behv of rs232 is
signal b: std_logic_vector(9 downto 0); signal r: std_logic_vector(3 downto 0); signal j: std_logic_vector(15 downto 0); signal frxd,gt,gtclr,cclk,gate: std_logic; begin
gate<=gt and cclk;
disp(7 downto 0)<=b(8 downto 1); 将串行数据段的1-8位数据位从b中取出至于disp中。 frxd<=not rxd;
分析:定义机构体。先定义可信号b,r,j。其中的b作为数据转移的临时载体。R,j分别作为后 续程序的计数单元,其中需要注意的是j的位数控制,因为当需要控制波特率的时候,由于 输入的sysclk是固定的12MHz的系统时钟信号无法改变,故能改变的只有RS232中的分频系 数,但由于分频的系数的改变,于是j作为计数信号其值也将随之改变。 s1:process(sysclk,gt) begin
if gt='0' then j<=(others=>'0');
elsif sysclk'event and sysclk='1' then
if j=\
else j<=j+1; end if; end if; end process; 分析:s1的段码作用是用来计数,所记数为RS232的分频系数,上述代码中的\为40000, 通过计算12M/1250=9600,故可以得知波特率为9600b/s。通过改变j的值可以很方便的来设 置所需要的波特率。 s2:process(j) begin
if j=\ else cclk<='0'; end if; end process;
分析:s2的段码作用是当j计数到一定数值的时候产生一个脉冲,从而实现分频的作用。其中j值 的设定关系到分频的占空比,只需要j 的值在分频系数之内即可产生分频的效果。 s3:process(gate,gtclr) begin
if gtclr='1' then r<=\
elsif gate'event and gate='1' then r<=r+1; end if; end process;
s4:process(gate,r) begin
if r=\ else gtclr<='0'; end if; end process;
分析:s3,s4段码的作用是计数从0-10,即计数输入数据段的10位,0-起始位,1-8-数据位,9- 终止位。
s5:process(gate,rxd,b) begin
if gate'event and gate='1' then
b(9 downto 0)<=rxd&b(9 downto 1); 将b的后9位并上rxd 的第一位组合成新的信号b。 end if; end process;
分析:s5段码的作用是,将rxd的输入信号通过移位寄存的方法将RXD中的数据一一取出移动到信 号b中,然后再通过的b的移位从而将rxd中的数据段完整的转移到信号b中保存。 s6:process(frxd,gtclr) begin
if gtclr='1' then gt<='0';
elsif frxd'event and frxd='1' then gt<='1'; end if;
end process; end behv;
分析:s6的段码的作用是用于判断起始位,gt做为标志位,当已经确定为开始时,将 gt的值置‘1’。 (1-3)模块三分析:
分析:从上图可以看出其作用是作为分频,将50MHz的输入信号先通过PIN1MHZ模块将50MHZ 分为1Mhz,再将1MHZ的信号输入到下一个分频信号中分为频率为:1HZ,488HZ,1953HZ, 7812HZ,31250HZ,125kHZ,500kHZ的信号。
程序1:PIN1hz
LIBRARY IEEE;
USE IEEE.STD_LOGIC_1164.ALL; USE IEEE.STD_LOGIC_UNSIGNED.ALL; ENTITY PIN1MHZ IS
PORT(CLKIN:IN STD_LOGIC; CLKOUT:OUT STD_LOGIC); END PIN1MHZ;
ARCHITECTURE A OF PIN1MHZ IS BEGIN
PROCESS(CLKIN)
VARIABLE CNTTEMP:INTEGER RANGE 0 TO 49; BEGIN
IF CLKIN='1' AND CLKIN 'EVENT THEN IF CNTTEMP=49 THEN CNTTEMP:=0; ELSE
IF CNTTEMP<25 THEN CLKOUT<='1'; ELSE CLKOUT<='0'; END IF;
CNTTEMP:=CNTTEMP+1; END IF ; END IF; END PROCESS; END A;
分析:上述程序段中可以知道,使用变量VARIABLE做为计数,从0-49刚好为50个数,