mspi是对网络芯片W5500进行控制的master spi接口,rw_w5500_intfw5500是命令控制逻辑,命令格式按照w5500芯片的要求,分为地址段,控制段和数据段进行统一控制。
////////////////////////////////////////////////////////////////////////////////// module rw_w5500_intf( clk, // global clock rst, // global async low reset rw, // w5500 write/read rw_done, // write done /read done w5500_addr, // w5500 addr phase 16bit w5500_ctl, // w5500 controlphase 8bit w5500_wr_data, // w5500 data 32bit w5500_rd_data, // w5500 data 32bit w5500_data_len, // w5500 data byte number:0:1BYTE 1:2BYTE 2:4BYTE sck, // spi master clock out sdi, // spi master data in (MISO) sdo, // spi master data out (MOSI) ss, // spi cs ready // spi master ready (idle) ); // ======================================================== // input clk; input rst; input rw; input [1:0] w5500_data_len; input [15:0] w5500_addr; input [7:0] w5500_ctl; input [31:0] w5500_wr_data; output [31:0] w5500_rd_data; output rw_done; output sck; output sdo; output ready; output ss; input sdi; // ========================================================= // parameter BYTE_NUM_1 = 0; parameter BYTE_NUM_2 = 1; parameter BYTE_NUM_4 = 2; parameter IDLE = 0; parameter STEP1 = 1; parameter STEP2 = 2; parameter STEP3 = 3; parameter STEP4 = 4; // ========================================================= // reg spi_wr; reg [31:0] spi_tx_data; reg [31:0] w5500_rd_data_reg; reg [2:0] state; reg [1:0] spi_wr_len; reg [1:0] rw_reg; // ========================================================= // wire spi_wr_done; wire [31:0] spi_rddata; (*KEEP = "TRUE" *)wire ss = (state==IDLE);/*synthesis keep*/ wire rw_pos = (rw_reg[1:0] == 2'b01); wire ready = (state==IDLE); wire rw_done = (state==STEP4); assign w5500_rd_data = w5500_rd_data_reg; // ========================================================= // mspi mspi_inst ( .clk ( clk ), .rst ( rst ), .clk_div ( 4 ), .wr ( spi_wr ), .wr_len ( spi_wr_len ), .wr_done ( spi_wr_done ), .wrdata ( spi_tx_data ), .rddata ( spi_rddata ), .sck ( sck ), .sdi ( sdi ), .sdo ( sdo ), .ss ( ), .ready ( ) ); // --------------------------------------------------------- // always @(posedge clk or posedge rst) if(rst) rw_reg <= 0; else rw_reg <= {rw_reg[0],rw}; // --------------------------------------------------------- // always @(posedge clk or posedge rst) if(rst) begin state <= IDLE; spi_wr <= 0; spi_tx_data <= 0; spi_wr_len <= 0; w5500_rd_data_reg <= 0; end else case(state) IDLE: if(rw_pos) begin state <= STEP1; spi_wr <= 0; spi_tx_data <= 0; spi_wr_len <= 0; end STEP1: begin spi_wr <= 1'b1; spi_tx_data[31:16] <= w5500_addr[15:0]; spi_tx_data[15:0] <= 0; spi_wr_len <= BYTE_NUM_2; // |