• 串行并行数据转换


    前言

            串行数据传输通常在数据传输距离较远时使用,而并行数据传输适用于短距离、高速数据交换。通过转换,可以根据实际需求选择合适的传输方式,以优化数据传输效率和速度。串行数据传输在长距离传输中可以减少信号的干扰和失真,因为它只使用一条数据线。而并行传输由于多条数据线可能引入干扰,串行并行转换可以在需要时将数据转为串行传输,以减少干扰。在多种接口标准之间转换数据时,串行并行转换可以实现不同接口之间的数据兼容。例如,许多现代通信系统使用串行接口,而内部处理可能使用并行数据格式,转换可以使系统之间的数据交换顺畅。在某些应用中,FPGA等硬件平台可以通过串行并行数据转换实现灵活的设计,简化电路结构,降低成本和复杂度,同时提高系统的整体性能。

    正文

    一、串行并行数据转换

            1.项目需求

            进行串行数据转换为并行数据,并行数据转化为串行数据实验

            2.技术介绍

            并转串的设计思想:首先准备好一组寄存器,把需要发送的数据(并行数据)放到这个寄存器组里面,然后通过位拼接的移位方式把这个并行数据一位一位地发送给接收端,同时拉高标志信号en,当全部数据发送完之后,再把标志信号en拉低。

            串转并的设计思想:准备好一组寄存器,接收串行数据,将数据按位移入寄存器组,然后将整个寄存器组的数据组合成一个完整的并行数据字。使用一组寄存器暂时存储数据,然后逐位将数据移出至串行输出端,同时使用标志信号指示何时数据转换完成。

            3.顶层架构

    并转串

    串转并

            4.端口描述

    并转串

    clk系统时钟(50Mhz)
    rst_n复位按键(低电平有效)
    sda_in[7:0]并行数据输入
    en串行数据串行输出有效信号
    sda_out串行输出

    串转并

    clk系统时钟(50Mhz)
    rst_n复位按键(低电平有效)
    en串行输入有效信号
    sda_in串行输入
    sda_out[7:0]并行输出

    二、代码验证

    并转串:

    1. module para_serial(
    2. input clk,
    3. input rst_n,
    4. input [7:0]sda_in,//并行输入
    5. output reg en,
    6. output reg sda_out//串行输出
    7. );
    8. reg [7:0]sda;//并行数据寄存器
    9. reg [3:0]cnt;//移位计数器
    10. always @(posedge clk,negedge rst_n)
    11. begin
    12. if(rst_n == 0)
    13. begin
    14. sda_out <= 1'b0;
    15. cnt <= 4'd0;
    16. sda <= 8'b0;
    17. en <= 1'b0;
    18. end
    19. else
    20. begin
    21. if(cnt == 0)//数据加载
    22. begin
    23. sda <= sda_in;
    24. cnt <= 4'd1;
    25. end
    26. else if(cnt < 9)//移位输出
    27. begin
    28. en <= 1'b1;
    29. cnt <= cnt + 4'd1;
    30. sda <= {sda[6:0],sda[7]};
    31. sda_out <= sda[7];
    32. end
    33. else
    34. begin
    35. cnt <= 4'd0;//系统复位
    36. sda <= 8'b0;
    37. en <= 1'b0;
    38. end
    39. end
    40. end
    41. endmodule

            仿真程序

    1. `timescale 1ns/1ps
    2. module para_serial_tb;
    3. reg clk;
    4. reg rst_n;
    5. reg [7:0]sda_in;
    6. wire en;
    7. wire sda_out;
    8. para_serial para_serial_inst(
    9. .clk(clk),
    10. .rst_n(rst_n),
    11. .sda_in(sda_in),
    12. .en(en),
    13. .sda_out(sda_out)
    14. );
    15. initial clk = 1;
    16. always #10 clk = ~clk;
    17. initial begin
    18. rst_n = 0;
    19. #10
    20. rst_n = 1;
    21. sda_in = 8'b1011_0100;//数据载入
    22. #200
    23. sda_in = 8'b1010_0001;//数据载入
    24. #200
    25. $stop;
    26. end
    27. endmodule

    串转并

    1. module serial_para(
    2. input clk,
    3. input rst_n,
    4. input sda_in,//串行输入
    5. input en,//输入有效
    6. output reg [7:0] sda//并行输出
    7. );
    8. always @(posedge clk,negedge rst_n)
    9. begin
    10. if(rst_n == 0)
    11. begin
    12. sda <= 8'b0;
    13. end
    14. else
    15. begin
    16. if(en == 1)//输入使能
    17. sda <= {sda[6:0],sda_in};//数据并位
    18. else
    19. sda <= 8'b0;
    20. end
    21. end
    22. endmodule

    创建顶层,利用并转串输出数据

    1. module top(//进行数据连线
    2. input clk,
    3. input rst_n,
    4. input [7:0]sda_in,
    5. output en,
    6. output sda_out,
    7. output [7:0]sda
    8. );
    9. para_serial para_serial_inst(
    10. .clk(clk),
    11. .rst_n(rst_n),
    12. .sda_in(sda_in),
    13. .en(en),
    14. .sda_out(sda_out)
    15. );
    16. serial_para serial_para_inst(
    17. .clk(clk),
    18. .rst_n(rst_n),
    19. .sda_in(sda_out),
    20. .en(en),
    21. .sda(sda)
    22. );
    23. endmodule

            仿真程序

    1. `timescale 1ns/1ps
    2. module para_serial_tb;
    3. reg clk;
    4. reg rst_n;
    5. reg [7:0]sda_in;
    6. wire en;
    7. wire sda_out;
    8. wire [7:0]sda;
    9. top top_inst(
    10. .clk(clk),
    11. .rst_n(rst_n),
    12. .sda_in(sda_in),
    13. .en(en),
    14. .sda_out(sda_out),
    15. .sda(sda)
    16. );
    17. initial clk = 1;
    18. always #10 clk = ~clk;
    19. initial begin
    20. rst_n = 0;
    21. #10
    22. rst_n = 1;
    23. sda_in = 8'b1011_0100;
    24. #200
    25. sda_in = 8'b1010_0001;
    26. #200
    27. $stop;
    28. end
    29. endmodule

    三、仿真验证

    并转串:观察仿真波形图,数据有正常显示,调出过程信号

    数据在cnt=0的时钟上升沿时候加载sda,在cnt=1的时候显示输入并进行移位,在cnt=2的时候显示移位结果,并将移位结果输出,依次循环移,直到cnt=8的时钟上升沿对输入数据移位完8次,在cnt = 9的时候输出数据并系统复位,在下一个cnt=0的上升沿时钟加载数据

    上图输入10110100,输出电平在en有效下依次为10110100,下图输入10100001输出电平在en有效下依次为10100001,数据转化正确。

    串转并:可以观察到在en拉低后sda输出10110100与并转串模块输入数据相同。

    在时钟上升沿读取到en=1后将串行输入依次移位保存到并行输出串口并输出,串行输入10100001,经过8次en=1的时钟上升沿后由于输入en为并转串的输出使能,经过8个时钟周期后数据输出完成,en拉低,此时串转并模块输出上个时钟周期产生的完整串转并数据。此时数据为10100001与串行输入结果相同,实验成功。

    参考资料

    串并转换

  • 相关阅读:
    【Java数据类型】
    Go基础语法:map
    浏览器从输入URL到展示的流程
    Zuul使用总结
    swiper获取当前页的索引值
    BP神经网络简单应用实例,bp神经网络的应用案例
    CSS选择器分类(儿子选择器、 序选择器、下一个兄弟选择器+)
    通过SpringCloudGateway中的GlobalFilter实现鉴权过滤
    【vue设计与实现】非原始值的响应式方案 10-如何代理Set和Map
    Cocos2dx-lua ScrollView[二]进阶篇
  • 原文地址:https://blog.csdn.net/m0_66619666/article/details/140622126