UART 通信逻辑协议设计(2)
来源:互联网 发布:window 安装ubuntu 编辑:程序博客网 时间:2024/06/07 22:37
5 . 各模块详细设计
1)波特率发生器模块:假定系统时钟为50M,波特率为115200,则传输每一位所需的时间为8.6805us,而将其分频至波特率的16倍则需计数则在系统时钟下当计数值为27时则将Baud16Tick置为1,其他时间都为0。要得到波特率脉冲时则在Baud16Tick节拍下计数至16时将BaudTick置为1,其他值时为0。程序如下:
always @(posedge clk ) begin if (rst) begin OverSampleCnt <=8'b0; Baud16Tick <= 1'b0; end elseif(OverSampleCnt== OverSampleCntnum) OverSampleCnt <= 1'b0; else OverSampleCnt <=OverSampleCnt+1; case(OverSampleCnt== OverSampleCntnum/2) OverSampleCntnum/2:Baud16Tick <= 1'b1; default:Baud16Tick <= 1'b0; endcase End always @(posedge clk or negedge rst)begin if (rst) begin BaudTick <= 1'b0; BaudTickCnt <= 4'b0000 ; end else if (Baud16Tick&&BaudTick_EN) BaudTickCnt = BaudTickCnt +1 ; elseif((BaudTickCnt== 4’b1111) BaudTickCnt <= 4'b0000 ; case(BaudTickCnt) 4'b1000:BaudTick <= 1'b1; default:BaudTick <= 1'b0; endcaseend
2)数据发送器模块:在Baud16Tick的节拍下捕捉TXD_start的下降沿,之后将din8的数据存入缓冲器tbr中,再启动BaudTick脉冲并计数,在计数为4’b0000时发送停止位0,在4’b0001至4’b1000时发送数据位,并在之后两位发送奇偶校验位和停止位。没有发送是则发送空闲位1。校验每发一位就将parity进行异或数据位得到其值并发送。当发送停止位后,即将发送完成标志位TXD_done置1.程序如下:
always@(posedge clk) begin if(rst) begin {TxD_start0,TxD_start1} <= {1'b0,1'b0}; end else TxD_start0 <= TxD_start; TxD_start1 <= TxD_start0; endassign start = TxD_start1&!TxD_start0;always@(posedge clk or posedge rst) begin if(rst) tbr<= 8'b0; else if(BaudTick_EN&&BaudTick) tbr <= TxD_data; end always @(posedge clk or posedge rst) begin if (rst) BaudTick_EN <= 1'b0; else if (start) BaudTick_EN <= 1'b1 ; else if (no_bits_tran == 4'b1100) BaudTick_EN <= 1'b0 ; endalways @(posedge clk or negedge rst ) begin if (rst) no_bits_tran <= 4'b0000; else if (BaudTick&&Baud16Tick) no_bits_tran <= no_bits_tran + 1 ; else if (no_bits_tran ==4'b1100) no_bits_tran <= 4'b0000 ; endalways @(posedge clk or negedge rst) if (rst) begin TxD <= 1'b1; tbr <= 8'b0 ; tsr <= 8'b0 ; parity <= 1'b0 ; TxD_done <= 1'b0; end else begin if(BaudTick) begin case (no_bits_tran) 4'b0000: begin TxD <= 1'b0; tsr <= tbr; parity <= ^tsr ; TxD_done <= 1'b0; end 4'b0001: begin TxD <= tsr[0]; end 4'b0010: begin TxD <= tsr[1]; end 4'b0011: begin TxD <= tsr[2]; end 4'b0100: begin TxD <= tsr[3]; end 4'b0101: begin TxD <= tsr[4]; end 4'b0110: begin TxD <= tsr[5]; end 4'b0111: begin TxD <= tsr[6]; end 4'b1000: begin TxD <= tsr[7]; end 4'b1001: begin TxD <= parity; end 4'b1010: begin TxD <= 1'b1; end 4'b1011: begin TxD_done <= 1'b1; end default: TxD_done <= 1'b0 ; endcase end end
3)数据接收器模块:首先利用波特率16的采样脉冲对发送模块发送过来的串行数据进行下降沿采样,若采集到下降沿则开始启动BaudTick,并开启计数使能。在BaudTick的脉冲下进行计数并逐位读取发送端发过来的数据位,奇偶校验在case值为4’b0001至4’b1000时进行,当计数为4’b1001时发送判断校验位和检测停止位,在4’b1010时将奇偶校验和帧检查结果发送到端口中。程序如下所示:
always@(posedge clk or negedge rst) begin if(rst) begin {TxD_start0,TxD_start1} <= {1'b0,1'b0}; end else TxD_start0 <= TxD_start; TxD_start1 <= TxD_start0; endassign start = TxD_start1&!TxD_start0;always @(posedge clk or negedge rst ) begin if (rst) no_bits_tran <= 4'b0000; else if (BaudTick&&Baud16Tick) no_bits_tran <= no_bits_tran + 1 ; else if (no_bits_tran ==4'b1100) no_bits_tran <= 4'b0000 ; Endalways@(posedge clk or posedge rst) begin if(rst) tbr<= 8'b0; else if(BaudTick_EN&&BaudTick) tbr <= TxD_data; end always @(posedge clk or negedge rst ) begin if (rst) no_bits_tran <= 4'b0000; else if (BaudTick&&Baud16Tick) no_bits_tran <= no_bits_tran + 1 ; else if (no_bits_tran ==4'b1100) no_bits_tran <= 4'b0000 ; endalways @(posedge clk or negedge rst) if (rst) begin TxD <= 1'b1; tbr <= 8'b0 ; tsr <= 8'b0 ; parity <= 1'b0 ; TxD_done <= 1'b0; end else begin if(BaudTick) begin case (no_bits_tran) 4'b0000: begin TxD <= 1'b0; tsr <= tbr; parity <= ^tsr ;TxD_done <= 1'b0; end 4'b0001: begin TxD <= tsr[0]; end 4'b0010: begin TxD <= tsr[1]; end 4'b0011: begin TxD <= tsr[2]; end 4'b0100: begin TxD <= tsr[3]; end 4'b0101: begin TxD <= tsr[4]; end 4'b0110: begin TxD <= tsr[5]; end 4'b0111: begin TxD <= tsr[6]; end 4'b1000: begin TxD <= tsr[7]; end 4'b1001: begin TxD <= parity; end 4'b1010: begin TxD <= 1'b1; end 4'b1011: begin TxD_done <= 1'b1; end default: TxD_done <= 1'b0 ; endcase end end
3)顶层文件设计:两模块之间用wire类型连接,公共端用分别在两个模块中连接。顶层端口定义最终需要的端口即可。顶层模块如下:
TxD_Module u1( .clk(clk_sys), .rst(rst_N), .TxD_data(din8), .TxD_done(TxDdne_rdn), .TxD(TxD_RxD), .TxD_start(TxD_start_in) );RxD_Module u2 ( .clk(clk_sys), .rst(rst_N), .rdn(TxDdne_rdn), .RxD(TxD_RxD), .RxD_data(dout8), .parity_error(parity_err_out), .framing_error(frame_err_out), .RxD_data_ready(RxD_data_rdy) );
6.Modelsim仿真验证
1)测试激励:高电平初始化后进行发送递加的数据,并观察输入输出数据的差异,以及奇偶校验位和帧检查的正确性。
initial begin clk_sys = 0; rst_N = 1; din8 = 0; TxD_start_in = 0; #100; rst_N = 0; repeat(100) begin # 86800; TxD_start_in = 1; # 86800; TxD_start_in = 0; end end always #10 clk_sys = ~clk_sys; always @(posedge TxD_start_in) begin din8 = din8 + 8'd1; end
2)输入输出结果。激励文件和输出结果如下:
3) 结果分析:由上图可知
1 整个联合模块的并行输入与并行输出结果相同,接发送和接收正确。
2 奇偶校验位发现当数据为01010010时校验的结果为1,当数据为01010011时校验结果为0;由此可知奇偶校验正确
3 检查帧结果显示一致为0,而发送端的数据均为8位且停止位都为1。所以帧检查结果正确。
- UART 通信逻辑协议设计(2)
- UART 通信逻辑协议设计(1)
- UART 通信逻辑协议设计(3)
- UART , 通信模型, 协议
- 基于FPGA的UART接口协议设计
- UART通信
- uart通信
- UART通信
- UART协议
- UART协议
- UART协议
- 蓝牙BLE基础:CC2541通信系列之模拟UART协议
- 软件模拟串行通信——UART协议实现
- FPGA基础设计(三):UART串口通信
- 基于modbus的UART通信2
- 网络通信中的协议设计
- 串行异步通信-UART
- UART串口通信
- const functions 总结
- Huffman tree(赫夫曼树、霍夫曼树、哈夫曼树、最优二叉树)
- 预装win8 centos 双系统 双硬盘 efi 启动
- glOrtho2D函数
- Linux下的虚拟Bridge实现
- UART 通信逻辑协议设计(2)
- Android开发中调用系统设置界面
- nefu998整除问题(高精度除法)
- uva 146
- Bestcoder比赛再次爆0(应该是一直是0)
- 面试题36:数组中的逆序对
- hdu 5327 Olympiad
- 那些年,这些年
- Python Requests快速入门