标题: 简易FPGA UART源程序 [打印本页]

作者: bran-班    时间: 2019-12-26 16:11
标题: 简易FPGA UART源程序
简易FPGA UART
  1. module uart_rx
  2.         #(
  3.         parameter N_DATA_BITS = 8, // 串口数据位个数, 取值范围: 5, 6, 7, 8, 默认值: 8位
  4.                   HOW_MANY_TICKS_FOR_STOP_BIT = 16
  5.         )
  6.         (
  7.         input wire clk,
  8.         input wire reset,
  9.         input wire rx,
  10.         input wire s_tick,
  11.         output reg rx_done_tick,
  12.         output wire [7:0] dout
  13.         );

  14. // symbolic state declaration for UART receiver
  15. localparam [1:0]
  16.         idle = 2'b00,
  17.         start = 2'b01,
  18.         data = 2'b10,
  19.         stop = 2'b11;

  20. // state register
  21. reg [1:0] state_reg, state_next;

  22. // signal declaration
  23. reg [7:0] b_reg, b_next; // 数据位在寄存器内每个周期向右移1bit
  24. reg [2:0] n_reg, n_next;
  25. reg [3:0] s_reg, s_next; // 作为s_tick的计数器, 递增计数

  26. // body
  27. // FSMD state and data registers
  28. always @(posedge clk, posedge reset)
  29. begin
  30.         if (reset)
  31.                 begin
  32.                         state_reg <= idle;
  33.                         b_reg <= 8'b0;
  34.                         n_reg <= 3'd0;
  35.                         s_reg <= 4'd0;
  36.                 end
  37.         else
  38.                 begin
  39.                         state_reg <= state_next;
  40.                         b_reg <= b_next;
  41.                         n_reg <= n_next;
  42.                         s_reg <= s_next;
  43.                 end
  44. end

  45. // FSMD next-state logic
  46. always @*
  47. begin
  48.         rx_done_tick = 1'b0;
  49.         state_next = state_reg;
  50.         b_next = b_reg;
  51.         n_next = n_reg;
  52.         s_next = s_reg;
  53.         case (state_reg)
  54.                 /* 空闲位阶段 */
  55.                 idle:
  56.                 if (rx == 1'b0)
  57.                         begin
  58.                                 state_next = start; // 当rx首次出现低电平时空闲位结束, 准备进入下一状态读起始位
  59.                                 s_next = 0;
  60.                         end
  61.                 /* 起始位阶段 */
  62.                 start:
  63.                 if (s_tick)
  64.                         begin
  65.                                 s_next = s_reg + 1;
  66.                                 if (s_reg == 7)
  67.                                         begin
  68.                                                 s_next = 0;
  69.                                                 state_next = data; // 准备开始读数据位
  70.                                                 n_next = 0;
  71.                                         end
  72.                         end
  73.                 /* 数据位阶段 */
  74.                 data:
  75.                 if (s_tick)
  76.                         begin
  77.                                 s_next = s_reg + 1;
  78.                                 if (s_reg == (16-1))
  79.                                         begin
  80.                                                 s_next = 0;
  81.                                                 b_next = {rx, b_reg[7:1]};
  82.                                                 n_next = n_reg + 1;
  83.                                                 if (n_reg == (N_DATA_BITS-1))
  84.                                                         begin
  85.                                                                 state_next = stop;
  86.                                                                 //n_next = n_reg;
  87.                                                         end
  88.                                         end
  89.                         end
  90.                 /* 停止位阶段 */
  91.                 stop:
  92.                 if (s_tick)
  93.                         begin
  94.                                 s_next = s_reg + 1;
  95.                                 if (s_reg == (HOW_MANY_TICKS_FOR_STOP_BIT-1))
  96.                                         begin
  97.                                                 rx_done_tick = 1'b1;
  98.                                                 state_next = idle;
  99.                                                 //s_next = s_reg;
  100.                                         end
  101.                         end
  102.         endcase
  103. end

  104. // output
  105. assign dout = b_reg;

  106. endmodule
复制代码


verilog_code_tips-uart.zip

2.07 KB, 下载次数: 16, 下载积分: 黑币 -5






欢迎光临 (http://www.51hei.com/bbs/) Powered by Discuz! X3.1