spi接口的Verilog程序
哪位高手给个简单的spi接口的Verilog程序,要非常简单的,能帮助我理解就行。网上有很多,可是偶看不懂。我是菜鸟级!!...
哪位高手给个简单的spi接口的Verilog程序,要非常简单的,能帮助我理解就行。网上有很多,可是偶看不懂。我是菜鸟级!!
展开
展开全部
module
spi_mosi(rst,clk,rd,wr,datain,
spics,spiclk,spido,spidi,dataout);
input
rst;
//置位信号,低有效
input
clk;
//时钟信号
input
rd;
//接收数据命令
input
wr;
//发送数据命令
input
spidi;
//SPI数据输入信号
input
[7:0]
datain;
//发送数据输入
output
spics;
//SPI片选信号
output
spiclk;
//SPI时钟信号
output
spido;
//SPI数据输出信号
output
[7:0]
dataout;
//接收数据输出
reg
spics;
reg
spiclk;
reg
spido;
reg
[7:0]
dstate,
dsend,dataout,dreceive
;//,cnt;
reg
[1:0]
spistate;
parameter
idle
=
2'b00;
parameter
send_data
=
2'b01;
parameter
receive_data
=
2'b10;
initial
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
end
always
@(posedge
clk)
begin
if(!rst)
begin
spistate
<=
idle;
//
cnt
<=
8'd0;
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd0;
end
else
begin
case
(spistate)
2'b00:
begin
//
spics
<=
1'b1;
//
spiclk
<=
1'b1;
//
spido
<=
1'b1;
//
if(cnt
==
8'd0)
//
begin
//
cnt
<=
8'd0;
if((wr
==
1'b0)
&&
(rd
==
1'b1))
//发送资料转换
begin
spistate
<=
send_data;
dstate
<=
8'd0;
dsend
<=
datain;
end
else
if((wr
==
1'b1)
&&
(rd
==
1'b0))
//接收数据转换
begin
spistate
<=
receive_data;
dstate
<=
8'd0;
end
else
begin
spistate
<=
idle;
dstate
<=
8'd0;
end
//
end
//
else
//
begin
//
cnt
<=
cnt
+
8'd1;
//
end
end
2'b01:
//发送数据状态
begin
case
(dstate)
8'd0:
//产生片选信号有效
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd1;
end
8'd1:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd2;
end
8'd2:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
1'b1;
dstate
<=
8'd3;
end
8'd3:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[7];
//发送数据最高位
dstate
<=
8'd4;
end
8'd4:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[7];
dstate
<=
8'd5;
end
8'd5:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[6];
dstate
<=
8'd6;
end
8'd6:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[6];
dstate
<=
8'd7;
end
8'd7:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[5];
dstate
<=
8'd8;
end
8'd8:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[5];
dstate
<=
8'd9;
end
8'd9:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[4];
dstate
<=
8'd10;
end
8'd10:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[4];
dstate
<=
8'd11;
end
8'd11:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[3];
dstate
<=
8'd12;
end
8'd12:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[3];
dstate
<=
8'd13;
end
8'd13:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[2];
dstate
<=
8'd14;
end
8'd14:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[2];
dstate
<=
8'd15;
end
8'd15:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[1];
dstate
<=
8'd16;
end
8'd16:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[1];
dstate
<=
8'd17;
end
8'd17:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
//发送最低位数据
spido
<=
dsend[0];
dstate
<=
8'd18;
end
8'd18:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[0];
//spiclk的下降沿让最低位数据被读取
dstate
<=
8'd19;
end
8'd19:
//置片选信号无效
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd20;
end
8'd20:
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd0;
spistate
<=
idle;
end
default
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
spistate
<=
idle;
end
endcase
end
2'b10:
//接收数据状态
begin
case
(dstate)
//片选信号有效
8'd0:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd1;
end
8'd1:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd2;
end
8'd2:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
1'b1;
dstate
<=
8'd3;
end
8'd3:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd4;
end
8'd4:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
//紧接着上升沿的下降沿数据被读取
dreceive[7]
<=
spidi;
//接收数据最高位
dstate
<=
8'd5;
end
8'd5:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd6;
end
8'd6:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[6]
<=
spidi;
dstate
<=
8'd7;
end
8'd7:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd8;
end
8'd8:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[5]
<=
spidi;
dstate
<=
8'd9;
end
8'd9:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd10;
end
8'd10:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[4]
<=
spidi;
dstate
<=
8'd11;
end
8'd11:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd12;
end
8'd12:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[3]
<=
spidi;
dstate
<=
8'd13;
end
8'd13:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd14;
end
8'd14:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[2]
<=
spidi;
dstate
<=
8'd15;
end
8'd15:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd16;
end
8'd16:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[1]
<=
spidi;
dstate
<=
8'd17;
end
8'd17:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd18;
end
8'd18:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[0]
<=
spidi;
//接收数据最低位
dstate
<=
8'd19;
end
8'd19:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd20;
dataout<=
dreceive;
end
8'd20:
begin
spics
<=
1'b1;
//片选信号无效
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd0;
spistate
<=
idle;
end
endcase
end
default:
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
spistate
<=
idle;
end
endcase
//对应上面的发送数据情形
end
//对应上面的RST没有按下的情形
end
//对应最上面的always@(posedge
clk)
endmodule
spi_mosi(rst,clk,rd,wr,datain,
spics,spiclk,spido,spidi,dataout);
input
rst;
//置位信号,低有效
input
clk;
//时钟信号
input
rd;
//接收数据命令
input
wr;
//发送数据命令
input
spidi;
//SPI数据输入信号
input
[7:0]
datain;
//发送数据输入
output
spics;
//SPI片选信号
output
spiclk;
//SPI时钟信号
output
spido;
//SPI数据输出信号
output
[7:0]
dataout;
//接收数据输出
reg
spics;
reg
spiclk;
reg
spido;
reg
[7:0]
dstate,
dsend,dataout,dreceive
;//,cnt;
reg
[1:0]
spistate;
parameter
idle
=
2'b00;
parameter
send_data
=
2'b01;
parameter
receive_data
=
2'b10;
initial
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
end
always
@(posedge
clk)
begin
if(!rst)
begin
spistate
<=
idle;
//
cnt
<=
8'd0;
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd0;
end
else
begin
case
(spistate)
2'b00:
begin
//
spics
<=
1'b1;
//
spiclk
<=
1'b1;
//
spido
<=
1'b1;
//
if(cnt
==
8'd0)
//
begin
//
cnt
<=
8'd0;
if((wr
==
1'b0)
&&
(rd
==
1'b1))
//发送资料转换
begin
spistate
<=
send_data;
dstate
<=
8'd0;
dsend
<=
datain;
end
else
if((wr
==
1'b1)
&&
(rd
==
1'b0))
//接收数据转换
begin
spistate
<=
receive_data;
dstate
<=
8'd0;
end
else
begin
spistate
<=
idle;
dstate
<=
8'd0;
end
//
end
//
else
//
begin
//
cnt
<=
cnt
+
8'd1;
//
end
end
2'b01:
//发送数据状态
begin
case
(dstate)
8'd0:
//产生片选信号有效
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd1;
end
8'd1:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd2;
end
8'd2:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
1'b1;
dstate
<=
8'd3;
end
8'd3:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[7];
//发送数据最高位
dstate
<=
8'd4;
end
8'd4:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[7];
dstate
<=
8'd5;
end
8'd5:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[6];
dstate
<=
8'd6;
end
8'd6:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[6];
dstate
<=
8'd7;
end
8'd7:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[5];
dstate
<=
8'd8;
end
8'd8:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[5];
dstate
<=
8'd9;
end
8'd9:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[4];
dstate
<=
8'd10;
end
8'd10:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[4];
dstate
<=
8'd11;
end
8'd11:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[3];
dstate
<=
8'd12;
end
8'd12:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[3];
dstate
<=
8'd13;
end
8'd13:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[2];
dstate
<=
8'd14;
end
8'd14:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[2];
dstate
<=
8'd15;
end
8'd15:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
dsend[1];
dstate
<=
8'd16;
end
8'd16:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[1];
dstate
<=
8'd17;
end
8'd17:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
//发送最低位数据
spido
<=
dsend[0];
dstate
<=
8'd18;
end
8'd18:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
dsend[0];
//spiclk的下降沿让最低位数据被读取
dstate
<=
8'd19;
end
8'd19:
//置片选信号无效
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd20;
end
8'd20:
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd0;
spistate
<=
idle;
end
default
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
spistate
<=
idle;
end
endcase
end
2'b10:
//接收数据状态
begin
case
(dstate)
//片选信号有效
8'd0:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd1;
end
8'd1:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd2;
end
8'd2:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
spido
<=
1'b1;
dstate
<=
8'd3;
end
8'd3:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd4;
end
8'd4:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
//紧接着上升沿的下降沿数据被读取
dreceive[7]
<=
spidi;
//接收数据最高位
dstate
<=
8'd5;
end
8'd5:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd6;
end
8'd6:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[6]
<=
spidi;
dstate
<=
8'd7;
end
8'd7:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd8;
end
8'd8:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[5]
<=
spidi;
dstate
<=
8'd9;
end
8'd9:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd10;
end
8'd10:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[4]
<=
spidi;
dstate
<=
8'd11;
end
8'd11:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd12;
end
8'd12:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[3]
<=
spidi;
dstate
<=
8'd13;
end
8'd13:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd14;
end
8'd14:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[2]
<=
spidi;
dstate
<=
8'd15;
end
8'd15:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd16;
end
8'd16:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[1]
<=
spidi;
dstate
<=
8'd17;
end
8'd17:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
dstate
<=
8'd18;
end
8'd18:
begin
spics
<=
1'b0;
spiclk
<=
1'b0;
dreceive[0]
<=
spidi;
//接收数据最低位
dstate
<=
8'd19;
end
8'd19:
begin
spics
<=
1'b0;
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd20;
dataout<=
dreceive;
end
8'd20:
begin
spics
<=
1'b1;
//片选信号无效
spiclk
<=
1'b1;
spido
<=
1'b1;
dstate
<=
8'd0;
spistate
<=
idle;
end
endcase
end
default:
begin
spics
<=
1'b1;
spiclk
<=
1'b1;
spido
<=
1'b1;
spistate
<=
idle;
end
endcase
//对应上面的发送数据情形
end
//对应上面的RST没有按下的情形
end
//对应最上面的always@(posedge
clk)
endmodule
展开全部
这个要看你的外挂spi的芯片具体型号,spi接口也有8位,12位,16位,24位等等的。程序都有些不一样。
而且这样直接求代码,一般是求不到的。虽然是个简单的代码。
而且这样直接求代码,一般是求不到的。虽然是个简单的代码。
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
展开全部
module spi_mosi(rst,clk,rd,wr,datain, spics,spiclk,spido,spidi,dataout);
input rst; //置位信号,低有效
input clk; //时钟信号
input rd; //接收数据命令
input wr; //发送数据命令
input spidi; //SPI数据输入信号
input [7:0] datain; //发送数据输入
output spics; //SPI片选信号
output spiclk; //SPI时钟信号
output spido; //SPI数据输出信号
output [7:0] dataout; //接收数据输出
reg spics;
reg spiclk;
reg spido;
reg [7:0] dstate, dsend,dataout,dreceive ;//,cnt;
reg [1:0] spistate;
parameter idle = 2'b00;
parameter send_data = 2'b01;
parameter receive_data = 2'b10;
initial
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
end
always @(posedge clk)
begin
if(!rst)
begin
spistate <= idle;
// cnt <= 8'd0;
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd0;
end
else
begin
case (spistate)
2'b00:
begin
// spics <= 1'b1;
// spiclk <= 1'b1;
// spido <= 1'b1;
// if(cnt == 8'd0)
// begin
// cnt <= 8'd0;
if((wr == 1'b0) && (rd == 1'b1)) //发送资料转换
begin
spistate <= send_data;
dstate <= 8'd0;
dsend <= datain;
end
else if((wr == 1'b1) && (rd == 1'b0)) //接收数据转换
begin
spistate <= receive_data;
dstate <= 8'd0;
end
else
begin
spistate <= idle;
dstate <= 8'd0;
end
// end
// else
// begin
// cnt <= cnt + 8'd1;
// end
end
2'b01: //发送数据状态
begin
case (dstate)
8'd0: //产生片选信号有效
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd1;
end
8'd1:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd2;
end
8'd2:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= 1'b1;
dstate <= 8'd3;
end
8'd3:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[7]; //发送数据最高位
dstate <= 8'd4;
end
8'd4:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[7];
dstate <= 8'd5;
end
8'd5:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[6];
dstate <= 8'd6;
end
8'd6:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[6];
dstate <= 8'd7;
end
8'd7:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[5];
dstate <= 8'd8;
end
8'd8:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[5];
dstate <= 8'd9;
end
8'd9:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[4];
dstate <= 8'd10;
end
8'd10:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[4];
dstate <= 8'd11;
end
8'd11:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[3];
dstate <= 8'd12;
end
8'd12:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[3];
dstate <= 8'd13;
end
8'd13:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[2];
dstate <= 8'd14;
end
8'd14:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[2];
dstate <= 8'd15;
end
8'd15:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[1];
dstate <= 8'd16;
end
8'd16:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[1];
dstate <= 8'd17;
end
8'd17:
begin
spics <= 1'b0;
spiclk <= 1'b1; //发送最低位数据
spido <= dsend[0];
dstate <= 8'd18;
end
8'd18:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[0]; //spiclk的下降沿让最低位数据被读取
dstate <= 8'd19;
end
8'd19: //置片选信号无效
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd20;
end
8'd20:
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd0;
spistate <= idle;
end
default
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
spistate <= idle;
end
endcase
end
2'b10: //接收数据状态
begin
case (dstate) //片选信号有效
8'd0:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd1;
end
8'd1:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd2;
end
8'd2:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= 1'b1;
dstate <= 8'd3;
end
8'd3:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd4;
end
8'd4:
begin
spics <= 1'b0;
spiclk <= 1'b0; //紧接着上升沿的下降沿数据被读取
dreceive[7] <= spidi; //接收数据最高位
dstate <= 8'd5;
end
8'd5:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd6;
end
8'd6:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[6] <= spidi;
dstate <= 8'd7;
end
8'd7:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd8;
end
8'd8:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[5] <= spidi;
dstate <= 8'd9;
end
8'd9:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd10;
end
8'd10:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[4] <= spidi;
dstate <= 8'd11;
end
8'd11:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd12;
end
8'd12:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[3] <= spidi;
dstate <= 8'd13;
end
8'd13:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd14;
end
8'd14:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[2] <= spidi;
dstate <= 8'd15;
end
8'd15:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd16;
end
8'd16:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[1] <= spidi;
dstate <= 8'd17;
end
8'd17:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd18;
end
8'd18:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[0] <= spidi; //接收数据最低位
dstate <= 8'd19;
end
8'd19:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd20;
dataout<= dreceive;
end
8'd20:
begin
spics <= 1'b1; //片选信号无效
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd0;
spistate <= idle;
end
endcase
end
default:
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
spistate <= idle;
end
endcase //对应上面的发送数据情形
end //对应上面的RST没有按下的情形
end //对应最上面的always@(posedge clk)
endmodule
input rst; //置位信号,低有效
input clk; //时钟信号
input rd; //接收数据命令
input wr; //发送数据命令
input spidi; //SPI数据输入信号
input [7:0] datain; //发送数据输入
output spics; //SPI片选信号
output spiclk; //SPI时钟信号
output spido; //SPI数据输出信号
output [7:0] dataout; //接收数据输出
reg spics;
reg spiclk;
reg spido;
reg [7:0] dstate, dsend,dataout,dreceive ;//,cnt;
reg [1:0] spistate;
parameter idle = 2'b00;
parameter send_data = 2'b01;
parameter receive_data = 2'b10;
initial
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
end
always @(posedge clk)
begin
if(!rst)
begin
spistate <= idle;
// cnt <= 8'd0;
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd0;
end
else
begin
case (spistate)
2'b00:
begin
// spics <= 1'b1;
// spiclk <= 1'b1;
// spido <= 1'b1;
// if(cnt == 8'd0)
// begin
// cnt <= 8'd0;
if((wr == 1'b0) && (rd == 1'b1)) //发送资料转换
begin
spistate <= send_data;
dstate <= 8'd0;
dsend <= datain;
end
else if((wr == 1'b1) && (rd == 1'b0)) //接收数据转换
begin
spistate <= receive_data;
dstate <= 8'd0;
end
else
begin
spistate <= idle;
dstate <= 8'd0;
end
// end
// else
// begin
// cnt <= cnt + 8'd1;
// end
end
2'b01: //发送数据状态
begin
case (dstate)
8'd0: //产生片选信号有效
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd1;
end
8'd1:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd2;
end
8'd2:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= 1'b1;
dstate <= 8'd3;
end
8'd3:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[7]; //发送数据最高位
dstate <= 8'd4;
end
8'd4:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[7];
dstate <= 8'd5;
end
8'd5:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[6];
dstate <= 8'd6;
end
8'd6:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[6];
dstate <= 8'd7;
end
8'd7:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[5];
dstate <= 8'd8;
end
8'd8:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[5];
dstate <= 8'd9;
end
8'd9:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[4];
dstate <= 8'd10;
end
8'd10:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[4];
dstate <= 8'd11;
end
8'd11:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[3];
dstate <= 8'd12;
end
8'd12:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[3];
dstate <= 8'd13;
end
8'd13:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[2];
dstate <= 8'd14;
end
8'd14:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[2];
dstate <= 8'd15;
end
8'd15:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= dsend[1];
dstate <= 8'd16;
end
8'd16:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[1];
dstate <= 8'd17;
end
8'd17:
begin
spics <= 1'b0;
spiclk <= 1'b1; //发送最低位数据
spido <= dsend[0];
dstate <= 8'd18;
end
8'd18:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= dsend[0]; //spiclk的下降沿让最低位数据被读取
dstate <= 8'd19;
end
8'd19: //置片选信号无效
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd20;
end
8'd20:
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd0;
spistate <= idle;
end
default
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
spistate <= idle;
end
endcase
end
2'b10: //接收数据状态
begin
case (dstate) //片选信号有效
8'd0:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd1;
end
8'd1:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd2;
end
8'd2:
begin
spics <= 1'b0;
spiclk <= 1'b0;
spido <= 1'b1;
dstate <= 8'd3;
end
8'd3:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd4;
end
8'd4:
begin
spics <= 1'b0;
spiclk <= 1'b0; //紧接着上升沿的下降沿数据被读取
dreceive[7] <= spidi; //接收数据最高位
dstate <= 8'd5;
end
8'd5:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd6;
end
8'd6:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[6] <= spidi;
dstate <= 8'd7;
end
8'd7:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd8;
end
8'd8:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[5] <= spidi;
dstate <= 8'd9;
end
8'd9:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd10;
end
8'd10:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[4] <= spidi;
dstate <= 8'd11;
end
8'd11:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd12;
end
8'd12:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[3] <= spidi;
dstate <= 8'd13;
end
8'd13:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd14;
end
8'd14:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[2] <= spidi;
dstate <= 8'd15;
end
8'd15:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd16;
end
8'd16:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[1] <= spidi;
dstate <= 8'd17;
end
8'd17:
begin
spics <= 1'b0;
spiclk <= 1'b1;
dstate <= 8'd18;
end
8'd18:
begin
spics <= 1'b0;
spiclk <= 1'b0;
dreceive[0] <= spidi; //接收数据最低位
dstate <= 8'd19;
end
8'd19:
begin
spics <= 1'b0;
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd20;
dataout<= dreceive;
end
8'd20:
begin
spics <= 1'b1; //片选信号无效
spiclk <= 1'b1;
spido <= 1'b1;
dstate <= 8'd0;
spistate <= idle;
end
endcase
end
default:
begin
spics <= 1'b1;
spiclk <= 1'b1;
spido <= 1'b1;
spistate <= idle;
end
endcase //对应上面的发送数据情形
end //对应上面的RST没有按下的情形
end //对应最上面的always@(posedge clk)
endmodule
本回答被提问者采纳
已赞过
已踩过<
评论
收起
你对这个回答的评价是?
推荐律师服务:
若未解决您的问题,请您详细描述您的问题,通过百度律临进行免费专业咨询