SPI学习笔记:DAC与ACD

编程入门 行业动态 更新时间:2024-10-11 07:33:12

SPI<a href=https://www.elefans.com/category/jswz/34/1770117.html style=学习笔记:DAC与ACD"/>

SPI学习笔记:DAC与ACD

一、SPI协议简介

SPI = Serial Peripheral Interface,是串行外围设备接口,是一种高速,全双工,同步的通信总线。常规只占用四根线,节约了芯片管脚,PCB的布局省空间。现在越来越多的芯片集成了这种通信协议,常见的有EEPROM、FLASH、AD转换器等。

二、遵循SPI协议控制DAC:tlv5618

   1.时序分析

    从tlv5618芯片的数据手册中可找到其时序特性:

由tw确定sclk时钟频率为20MHz;根据DIN时序可知在SCLK上升沿DIN改变,在SCLK下降沿读取DIN;tsu与thd长度之和小于tw,故直接用20MHz时钟设计DIN长度即可满足;tsu用于限制CS的起止点,在仿真时检验并调整使CS满足tsu即可。

2.模块框图

        根据时序图可知,用线性序列机即可(LSM)实现。定义的信号如下:

3.代码实现

//采用线性序列机(LSM)来实现
module dac_driver(input fpga_clk ,input rst_n ,input dac_pulse ,input [15:0]dac_data ,output reg cs_n ,//low level validoutput reg sclk ,output reg mosi ,output reg dac_sig ,output reg dac_done 
);//供电电压不同,参数最小值不同,这里按照兼容VDD = 5V 和 VDD = 3V 的参数设计 
// 			tsu(cs-ck) : 20ns														// 
//				tsu(c16-cs): 20ns															//
//				th(D): 10ns																	//	
//				th(csh):50ns																//
//           sclk : 20Mhz    															//
//
// D15 - D12 : 设置位  根据手册来设置                                     //
// D11 - D0  : 数据位	  需要转化的电压值												//wire clk_40m ;
pll pll_inst(.inclk0(fpga_clk),.c0(clk_40m));//detect dac_pulse
reg dac_pulse_reg ;
always@(posedge fpga_clk or negedge rst_n)
if(!rst_n)dac_pulse_reg <= 0 ;
else dac_pulse_reg <= dac_pulse ;//dac_sig 
always@(posedge fpga_clk or negedge rst_n)
if(!rst_n)	dac_sig <= 0 ;
else if( (dac_pulse_reg == 0) & ( dac_pulse == 1) )dac_sig <= 1 ;
else if( dac_done )dac_sig <= 0 ;// dac_cnt : 0 - 15
reg [5:0]dac_cnt ;
always@(posedge clk_40m or negedge rst_n)
if(!rst_n)	begindac_cnt <= 0 ;end
else if(dac_sig)begindac_cnt <= dac_cnt + 1 ;	if(dac_cnt == 34 )dac_cnt <= 0 ;end
elsedac_cnt <= 0 ;//dac_done:
always@(posedge clk_40m or negedge rst_n)
if(!rst_n)	dac_done <= 0 ;
else if( dac_cnt == 34 )dac_done <= 1 ;
else if( dac_done )dac_done <= 0 ;// cs_n
always@(posedge clk_40m or negedge rst_n)
if(!rst_n)	cs_n <= 1 ;
else if(dac_sig)beginif(dac_cnt < 32 )cs_n <= 0 ;elsecs_n <= 1 ;end// sclk
always@(posedge clk_40m or negedge rst_n)
if(!rst_n)	sclk <= 0 ;
else if(dac_sig)beginsclk <= !sclk ; end
else sclk <= 0 ;//mosi
always@(posedge clk_40m or negedge rst_n)
if(!rst_n)	mosi <= 0 ;
else if(dac_sig)begincase(dac_cnt)0 :  mosi <= dac_data[15] ;2 :  mosi <= dac_data[14] ;4 :  mosi <= dac_data[13] ;6 :  mosi <= dac_data[12] ;8 :  mosi <= dac_data[11] ;10 : mosi <= dac_data[10] ;12 : mosi <= dac_data[9] ;14 : mosi <= dac_data[8] ;16 : mosi <= dac_data[7] ;18 : mosi <= dac_data[6] ;20 : mosi <= dac_data[5] ;22 : mosi <= dac_data[4] ;24 : mosi <= dac_data[3] ;26 : mosi <= dac_data[2] ;28 : mosi <= dac_data[1] ;	30 : mosi <= dac_data[0] ;	32 : mosi <= 0 ;	default:;endcaseend
else mosi <= 0 ;endmodule
`timescale 1ns/1ns
module dac_driver_tb();reg fpga_clk ;
reg rst_n  ;
reg dac_pulse ;
reg [15:0]dac_data ;
wire cs_n ;
wire sclk ;
wire mosi ;
wire dac_done ;dac_driver dac_driver_inst(.fpga_clk(fpga_clk) ,.rst_n(rst_n) ,.dac_pulse(dac_pulse) ,.dac_data(dac_data) ,.cs_n(cs_n) ,//low level valid.sclk(sclk) ,.mosi(mosi) ,.dac_done(dac_done)
);initial fpga_clk = 0 ;
always #10 fpga_clk = ! fpga_clk ;initial
beginrst_n = 0 ;dac_pulse = 0 ;dac_data = 0 ;#100 ;rst_n = 1 ;#100 ;dac_data = 16'h5a5a ;#100 ;dac_pulse = 1 ;#40 ;dac_pulse = 0 ;#100;wait(dac_done);#3000 ;dac_data = 16'ha5a5 ;#100 ;dac_pulse = 1 ;#40 ;dac_pulse = 0 ;#100;wait(dac_done);#3000 ;$stop;endendmodule

4.仿真验证

由图可知,tsu为25ns,th(csh)为50ns,满足要求。

更多推荐

SPI学习笔记:DAC与ACD

本文发布于:2023-12-07 19:49:09,感谢您对本站的认可!
本文链接:https://www.elefans.com/category/jswz/34/1671683.html
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。
本文标签:学习笔记   SPI   ACD   DAC

发布评论

评论列表 (有 0 条评论)
草根站长

>www.elefans.com

编程频道|电子爱好者 - 技术资讯及电子产品介绍!