基于VHDL的UA(R)T状态机

基于VHDL的UA(R)T状态机,vhdl,state-machine,hardware-programming,Vhdl,State Machine,Hardware Programming,我正在尝试用vhdl为UA(R)T(仅发送部分)创建一个状态机 我对程序的流程有问题。我知道buad费率部分目前不起作用。我正在尝试让它在目前只使用一个时钟工作,然后将实现波特率除法器 当我在我的测试台上运行它时(没有什么复杂的,只需为x时间分配两个初始值reset=1,din=z,baud=y,等等),什么都没有发生。我的输出txd保持在重置阶段设置的初始“1”值,如果我将其设置为“0”,则在循环中保持相同 我在设计状态机时遇到的问题是,它有两个值可以转换,但不会处于任何状态 基本上,它应该做

我正在尝试用vhdl为UA(R)T(仅发送部分)创建一个状态机

我对程序的流程有问题。我知道buad费率部分目前不起作用。我正在尝试让它在目前只使用一个时钟工作,然后将实现波特率除法器

当我在我的测试台上运行它时(没有什么复杂的,只需为x时间分配两个初始值reset=1,din=z,baud=y,等等),什么都没有发生。我的输出txd保持在重置阶段设置的初始“1”值,如果我将其设置为“0”,则在循环中保持相同

我在设计状态机时遇到的问题是,它有两个值可以转换,但不会处于任何状态

基本上,它应该做的是: 重置:txd=1,计数=1,忙=0,we=0 空闲:忙时=1设置移位=初始值 等待:下一时钟信号转换 trans:如果计数小于9,则txd=移位(0),移位 如果计数=9,忙=0,计数=0 然后回到空闲状态

我认为我的问题与忙信号设置不当有关

-- Universal Asynch Receiver Transmitter
---------------------
library ieee;
use ieee.std_logic_1164.all;

entity eds_uart is
   generic (width : positive := 16);
   port ( clk,reset: in std_logic ;
     din_wen: buffer std_logic; -- state machine sets value thus buffer needed
     brd : in std_logic_vector(23 downto 0); -- buad rate dividor
     din : in std_logic_vector(7 downto 0); -- input value
     txd: out std_logic; -- sent data bit
     tx_busy : buffer std_logic -- sent data bit active
     );
end entity eds_uart;

architecture behaviour of eds_uart is
    type state_type is (idle_s, wait_s, transmit_s);  -- three possible states of uat
    signal current_s: state_type; 
    signal tick: std_logic; -- baud rate clock
    signal count: integer := 0; -- count number of characters sent
    signal shift: std_logic_vector(9 downto 0); -- intermediate vector to be shifted

begin
   -- assign tick value based on baud rate 
   -- need to implement divisor
   process(clk, brd) begin
      tick <= clk;
   end process; 

   process(tick, reset, din) begin 
       if (reset = '1') then
           current_s <= idle_s; -- default state
           count <= 0; -- reset character counter
           txd <= '1'; 
           tx_busy <= '0'; 
           din_wen <= '0'; -- able to start sending
       elsif (current_s = idle_s and din_wen = '1') then -- transition when write enable is high
           current_s <= wait_s; -- transition
           tx_busy <= '1';  
           shift <= '1' & din & '0'; -- init shift value
       elsif (current_s = wait_s and rising_edge(tick)) then -- transition on clock signal
            current_s <= transmit_s;
       elsif (current_s = transmit_s and rising_edge(tick)) then -- test transition on clock signal
            if (count < 9) then
                txd <= shift(0); -- output value
                shift <= '0' & shift(9 downto 1); -- shift to next value
                count <= count + 1; -- increment counter
                current_s <= transmit_s; -- dont change state
            elsif (count = 9) then 
                txd <= shift(0); -- send last element
                count <= 0;
                tx_busy <= '0'; -- reset busy signal
                current_s <= idle_s; -- start process again
           end if;
       end if;
   end process;
end architecture behaviour ;
——通用异步收发信机
---------------------
图书馆ieee;
使用ieee.std_logic_1164.all;
实体eds_uart是
通用(宽度:正:=16);
端口(时钟,复位:在标准逻辑中;
din_wen:buffer std_logic;--状态机设置所需缓冲区的值
brd:在标准逻辑向量(23到0)中--buad速率除法器
din:标准逻辑向量(7到0);--输入值
txd:out std_logic;--发送的数据位
tx_忙:缓冲区标准逻辑——发送数据位激活
);
终端实体eds_uart;
eds_uart的体系结构行为是
类型状态_类型为(空闲、等待、传输);--uat的三种可能状态
信号电流:状态类型;
信号勾号:标准逻辑;——波特率时钟
信号计数:整数:=0;--计数发送的字符数
信号移位:标准逻辑向量(9到0);--要移位的中间向量
开始
--根据波特率分配刻度值
--需要实现除数
流程(clk、brd)开始
勾选评论:

-- state machine sets value thus buffer needed

建议您可能希望为
dinu wen
提供额外的外部驱动程序。如果是这种情况,
buffer
模式对您没有任何好处,因为它只公开了
dinu wen
的内部驱动程序的值,该驱动程序只驱动“0”。在VHDL-2002之后,
buffer
实际上是
out
的一个奇特的可读版本,没有早期标准的限制。它不实现输入端口。更重要的是,如果在该实体之外有其他信号驱动器,则它不允许您查看外部解析值

不清楚为什么您甚至需要在内部驱动
dinu wen
,因为它是一个控制输入,会导致转换到
wait_s
状态。考虑在端口模式中将其更改为<代码>,并删除重置赋值。


风格说明:这里所描述的同步和异步逻辑的混合使用,正在引起危险。您应该坚持在顶级
if
块中调用
rissing\u edge()
,该块包含所有同步逻辑。

您似乎没有将
dinu wen
设置为
'1'
任何位置。这正是问题所在。谢谢并切换了时钟的使用。
-- transition when write enable is high