基于FPGA的QSPI底层驱动代码实现

2024-03-13 1686阅读

温馨提示:这篇文章已超过382天没有更新,请注意相关的内容是否还可用!

基于FPGA的QSPI底层驱动代码实现

  • QSPI简介
  • 写时序
  • 读时序
  • QSPI实现的Verilog代码
  • 仿真波形图
  • 总结

    QSPI简介

    相信各位优秀的工程师们对SPI协议已经是非常了解了,SPI全名为串行外围设备接口(Serial Peripheral Interface),是一种高速全双工的同步通信总线,广泛应用于设备间的通讯传输。

    而本文所要讲的QSPI,为SPI接口的扩展,Q代表quad即4倍传输的意思,也称为四线制SPI,因此该接口的传输速率将远远快于标准的SPI,其广泛应用于SPI Flash存储介质。下面本文将通过一个Flash芯片的Datasheet,来详细的描述该如何利用FPGA实现QSPI的通信。

    写时序

    基于FPGA的QSPI底层驱动代码实现

    由时序图可以看到,图中总共有6个信号,从上至下分别为CE(片选信号)、CLK(时钟信号)、SIO0–SIO34根数据线。其中与SPI接口相似的是片选和时钟信号不变,在读写数据时片选信号均为低电平,在采样或发送数据时均在时钟的上升沿或者下降沿。唯一的区别在数据线由原来的MOSI、MISO变成了4根数据线,那么我们该如何将这四根数据线应用起来呢?由图中可知,SIO0会发送命令、地址以及数据,而SIO1–SIO3则只发送命令和数据,再进一步观察可以看到,写命令为0x38,它由8个CLK发送完成,地址信号总共24bit,由4跟数据线在6个CLK内同时完成发送,且每根数据线所发送的起始比特位都不同,最后便是发送数据,同理也由4根数据线同时进行发送,1个CLK发送4bit数据,发送的大小可由用户自己设定。总结一下,QSPI通信写的流程可以概括为先发送一个字节的命令字(这个命令字对于不同的芯片是不一样的),再是发送3个字节的地址(同理),最后才是发送数据。因此在FPGA的设计上就有思路了,最简单的方法就是采用状态机来描述这一过程,具体代码将在下面展示。

    读时序

    基于FPGA的QSPI底层驱动代码实现

    由图可知,读时序的操作流程与写时序大同小异,只是命令字由0x38变成了0xEB,其余操作流程均与写时序相同,因此不再进行详细阐述。

    但需要注意的是,由SPI扩展为QSPI,它已经不是全双工通信了,而是变成了半双工。SIO0–SIO3 4根线将变成三态门,也就是FPGA中的inout接口,需要满足特定的条件才能输入或者输出数据。

    下面将给出QSPI通信的底层驱动代码,在实际工程应用中,还需要结合芯片的数据手册来编写应用层的程序,再结合底层的逻辑来实现特定的功能,例如利用QSPI或者SPI接口对某个Flash芯片进行读写。

    QSPI实现的Verilog代码

    module QSPI_DRIVE #(
    		parameter DIV = 3
    )(
    	input wire clk,
    	input wire rst,
    	//--------应用层传输进该模块的命令、地址、数据等--------//
    	input wire [3:0] i_cmd_mode,
        input wire [7:0] i_flash_cmd,
        input wire [23:0] i_addr,
        input wire [7:0] i_data,
        input wire [15:0] i_data_num,
        input wire i_wr,
     	output reg [7:0] o_data,
     	//---------QSPI 接口---------//
    	output reg qspi_cs,
    	output reg qspi_csk,
    	inout   reg qspi_sio0,
    	inout   reg qspi_sio1,
    	inout   reg qspi_sio2,
    	inout   reg qspi_sio3
    );
    reg [7:0] div_cnt;
    reg [7:0] cmd_cnt;
    reg [7:0] addr_cnt;
    reg [7:0] data_cnt;
    reg [15:0] num_cnt;
    reg [3:0] cmd_mode_lock;
    reg [7:0] flash_cmd_lock;
    reg [23:0] addr_lock;
    reg [7:0] r_data_temp;
    reg  qspi_sckd0;
    wire qspi_sck_p,qspi_sck_n;
    //---------------FSM---------------//
    reg [7:0] state,n_state;
    localparam  IDLE  = 8'h00,
    			START = 8'h01,
    			CMD   = 8'h02,
    			ADDR  = 8'h04,
    			DATA  = 8'h08,
    			STOP  = 8'h10;
    always@(posedge clk)begin
    	if(rst)
    		state 
VPS购买请点击我

免责声明:我们致力于保护作者版权,注重分享,被刊用文章因无法核实真实出处,未能及时与作者取得联系,或有版权异议的,请联系管理员,我们会立即处理! 部分文章是来自自研大数据AI进行生成,内容摘自(百度百科,百度知道,头条百科,中国民法典,刑法,牛津词典,新华词典,汉语词典,国家院校,科普平台)等数据,内容仅供学习参考,不准确地方联系删除处理! 图片声明:本站部分配图来自人工智能系统AI生成,觅知网授权图片,PxHere摄影无版权图库和百度,360,搜狗等多加搜索引擎自动关键词搜索配图,如有侵权的图片,请第一时间联系我们,邮箱:ciyunidc@ciyunshuju.com。本站只作为美观性配图使用,无任何非法侵犯第三方意图,一切解释权归图片著作权方,本站不承担任何责任。如有恶意碰瓷者,必当奉陪到底严惩不贷!

目录[+]