fpga那些事-04.驱动篇_第1页
fpga那些事-04.驱动篇_第2页
fpga那些事-04.驱动篇_第3页
fpga那些事-04.驱动篇_第4页
fpga那些事-04.驱动篇_第5页
免费预览已结束,剩余16页可下载查看

下载本文档

版权说明:本文档由用户提供并上传,收益归属内容提供方,若内容存在侵权,请进行举报或认领

文档简介

实验十六:IIC模(24LC04 烦归麻烦,笔者终究还要吃饭,为了肚子,再麻烦的事情也要硬着头皮捱过去...这也16.1IICIIC16.1IIC总线与IIC设备常见的示意图。理想上,一条IIC总线允许千万IIC设备占据在上...物理下,一条IIC总监究竟允许多少IIC设备占据其中必须根据设备地址位,即[7..4]记录硬件ID,接续三位即[3..1]则记录硬件地址,最后一位则是设备的访问方向。结果如表16.1所示:16.1设备地址的位分配硬件IDIICIDID会随着厂商还有设备的种类而有所改变。开发板上的IIC设备是某厂商的IIC器,即24LC04,硬件ID为4’b1010。至于硬IIC3IICIIC总线上仅允许占据8个而已。然而,开发板上的24LC04为3’b000。最后的方向存器24LC04,设备地址就是8’b1010_000_×。图16.224LC04的写操作(主机视角(二)主机发送设备地址(写所以设备地址的方向是“写”,所以方向位设置为0。图16.324LC04的读操作(主机视角(二)主机发送设备地址(写(六)主机发送设备地址(读(八)主机数据(九)从机没有应答(主机无视应答未进入正题之前,请允许笔者加入一些小插曲。IIC总线是一种低速的总线,不过IIC总线有100Khz还有400Khz两种速率提供选择,要么100Khz,要么400Khz,要么两者兼施,不管哪一种《整合篇》都曾实验过。在此,实验十六会以400Khz的速率笔者曾面,IIC总线之所以麻烦,因为IIC总线有大小不同的时序参数(时间选择无视时序参数...那么,打从一开始还是不学为好IIC的总线时序有各种各样的方法,但是笔者会选择表达能力更高,控制能力更细的描述。知道IIC的总线时序是由一块又一块的拼图拼凑而成,当在建模的时候,会针对各个拼图作出局部性的描述。期间,也必须考虑各种时序参数,如表16.2所示:16.2各种时序参数(50Mhz量化相关参标Cck----CckigTeTGH----CckLowe----Reie----llie----Startle----StartSetup----DataIulie0----DataIutSetup5----StopSetupT----Opirmlk----BusFreei----ClockFrequency,既是频率也是速率,在此是400KhzClockHighTimeSCLClockLowTimeSCLStartHoldTime,既起始位所需最小的保StartSetupTime,既起始位所需最小的建立时间DataInputHoldTimeDataInputSetupTimeOuputValidFromClock,既数据位经时钟沿触发以后的有效时间BusFreeTime,既总线的最小时间表示SCL信号的频率,ClockHighTime表示SCL信号保持高电平所需的最小时间,ClockLowTime则表示SCL信号保持低电平所需的最小的时间。至于RiseTime与FallTime表示,SCL信号还有SDA信号由高变低或者由低变高时所需的最小时间,即上山与下山时间。HoldTime与SetupTime是用来评估数据是否成功打入寄存器的时序参数,算是典型中的典型。SetupTime表示建立时间,即数据写入寄存器之前所需的稳定时间;反之,HoldTime则是保持时间,即数据打入寄存器之StartIIC总线的起始位,StopIIC总线的结束位,DataIIC总线的数据位,为了确保三者成功写入从机,SetupTime与HoldTime必须得到满足。OuputValidFromClock是关系数据位的时序参数,还有BusFreeTime是关系结束位的时序参数,在此先丢胃口一下。此外,为了简化时序,笔者将各种参数的实际时间转换为50Mhz量化以后的结果。对此,Verilog可以这样表示,结果如代码16.1所示:aaeFCLK=1d5,FHALF=1'2,FQUARTER=';araerHIH='0,TLOW=1d,TR=0d,TF=01;aaerTHD_STA=1'0,TSU_STA=1d0,TSU_STO=d;如代码16.1所示,FCLK表示400Khz的周期,FHALF表示1/2周期,FQUARTER表1/4周期。至于为什么代码16.1不见,DataInputHoldTime与BusFreeTime的时序(话题继续之前,请读者确保自己对“整合时序”有一定的理解,不然的话...接下来的内容,读者一定会看到泪流满面。图16.4起始位起始位的物理时序。IICPS/2等传输协议的起始位,然而不同的是,IIC总线的起始位是SCL拉高TR+TSU_STA+THD_STA+TF之久,换之SDA则是拉高TRTHIGH然后拉低TF+TLOW。起始位总和所用掉的时间,恰恰好有一个速率的周期。对此,Verilog则可以这样描述,结果如代码16.2所示:ii=;rSCL<=11;if(C1==0)rSDA<=';eeif(C1==(TR+TG)rSDA<=';if(C1==(FCLK)-1)biC1<=';i<=i+'b;endeeC1<=C1+1'1;如代码16.2所示,第2行的isQ=1表示设置SDA为输出状态(即时结果3行则表示SCL一直持续拉高状态,第4~5行表示C1为0的时候SDA拉高,直到C1为TR+THIGH才拉低SDA。第6~7行表示一个步骤所逗留的时间。16.5结束16.5是结束位的时序图,IIC设备的操作好坏一般都取决结束位。保险起见,SCL与SDA都事先拉低1/4周期,紧接着SCL会拉高TR+TSU_STO(或者1/2周期,最后又保持高电平1/2周期。反之,SDA会拉低1/2周期,随之拉高TR+THIGH(或者1/2周期。对此,Verilog可以这样表示,结果如代码16.3所示:iiQ='b;if(C1==0)rSCL<=';seif(C1==FQUARTER)rSCL<='1;if(C1==0)rSDA<='0eeif(C1==FATER+TR+S_O)rSDA<=bif(C1==(FQUARTER+FCLK)-1)bgC1<=00i<=i+';eseC1<=C1+如代码16.3所示,第2行表示SDA为输出状态(即时,第3~4行表示C1为0SCL,C11/45~6行表示,C10拉低SDA,C1为1/4周期TRTSU_STO就拉高SDA。第7~8图16.6总线此外,结束位还有BusFreeTme这个时序参数,IIC总线在闲置的状态下SCL与SDA等信号都持续高电平。主机发送结束位以示结束操作,然而主机持续拉高SCL信号与SDA信号TBUF以示总线。TBUF的有效时间从SCL信号与SDA信号拉高那一刻16.2所示,TBUF65个时钟,结果如图16.6所示,SDA信号拉高之后,SCL与SDA信号只要持续保持1/2周期(即62个时,基本上就能满足TBUF。如果笔者是一位紧密控时狂人,可能无法接受这样的结果,因为满足TBUF少了3个时钟,为此代码16.3需要更动一下:if(C1==(FQUARTER+FCLK+3)-1)egnC1<=0d;i<=i+'b;eeC1<=C1+16.7数据位。IIC总线类似其他传输协议,它有时钟信号也有上升沿与下降沿。如图16.7所示,SCL信号的下降沿导致设备设置(更新)数据,上升沿则是锁存()数据。期间,TF+TLOW表示时钟信号的前半周期,TR+THIGH则表示后半周期。此外,为了确保数据成功打入寄存器,数据被上升沿锁存哪一刻起,TSU_DAT还有THD_DAT必须得16.8数据位更新有效除此之外,为了确保数据有效被更新,也必须确保TAA得到满足,结果如图16.816.9写一字节IIC总线一般都是一个字节一个字节读写数据,如图16.9所示,那是写一字节的理想 4,,:isQ=';rSDA<=[7-if(C1==0)rSCL<=';leif(C1==(TF+W))rSCL<='if(C1==FCLK-1)biC1<='0;i<=i+'b;leC1<=C1+'如代码16.5所示,第1行有8个步骤,表示写一个字节。第3isQ1SDA为输出状态。第4行表示从最开始更新SDA的数据位。第5~6行表示,C1为0拉低SCL,C1为TF+TLOW则拉高SCL。第7~8行表示该步骤逗留一个周期的时间。16.10应答位应答位是从机给予主机的回答,0为是1为否。然而,从旁,应答位也如图16.10所示,上升沿会产生在TFTLOW之后,也是1/2周期。对此,Verilog可以这样表示,结果如代码16.6所示:isQ=';if(C1==FHALF)ic<=A;if(C1==0)rSCL<=b;eeif(C1==FHALF)rSCL<=';if(C1==FCLK-1)egnC1<=1d;i<=i+11;eeC1<=C1+1; 如代码16.6所示,第2行表示SDA为输入状态。第4~5行表示,C1为0拉低SCL,C1为1/2周期则拉高SCL。第3行表示,C1为1/2周期的时候应答位。第6~7行表示该步骤逗留1个周期的时间。16.11读一字节所谓读一字节数据就是重复8次应答位。如图16.11所示,SCL的下降沿导致从机至于Verilog则可以这样表示,结果如代码16.7所示:,,,isQ=';if(C1==FHALF)[7i]<=A;if(C1==0)rSCL<='0;leif(C1==FHALF)rSCL<=bif(C1==FCLK-1)biC1<='0;i<=i+'b;leC1<=C1+'如代码16.7所示,第1行表示一字节。第3行表示SDA为输入状态,第5~6行表示,C10拉低SCL,C11/2周期则拉高SCL。第4行表示,C11/2周期的时候数据,而且数据位由高至低存入D1。第7~8行表示该步骤逗留一个周期的时间。16.12第二次起始位16.12所示,感觉上第二次起始位也是第一次起始位,不过为了促使改以这样表示,结果如代码16.8所示:isQ=';if(C1==0)rSCL<=';eeif(C1==FQUARTER)rSCL<=';s(ATb;if(C1==0)rSDA<=';eleif(C1==FQUARTER)rSDA<=';eleif(C1==(FQUARTER+TR+I))rSDA<=';if(C1==QUA+FCLK+FUAT-1)enC1<=1';i<=i+11leC1<=C1+'如代码16.8所示,第2行表示SDA为输出状态。第3~5行表示,C1为0拉低SCL,C1为1/4周期拉高SCL,C1为1/4周期+TR+TSU_STA+THD_STA+TF便拉低SCL。第7~9行表示,C10SDA,C11/4SDA,C11/4周期TRTHIGH便拉低SDA11~1216.13实验十六的建模图图16.13是实验十六的建模图,组合模块iic_demo内容包含IIC模块,操作还有SMG基础模块。首先操作会将数据纯如IIC模块,然后又从中,完后再将读出的数据驱动SMG基础模块。图16.14IIC模块的建模图图16.14是IIC模块的建模图,左边是顶层信号,右边则是沟通用的问答信号,写入地址iAddr,写入数据iData,还有读出数据oDall/Done有两位,即表示该模块modulemodule(inputCLOCK,outputinoutinputoutputinputinputoutput parameterFCLK=10'd125,FHALF=10'd62,FQUARTER=10'd31;//(1/400E+3)/(1/50E+6)parameterTHIGH=10'd30,TLOW=10'd65,TR=10'd15,TF=10'd15;parameterTHD_STA=10'd30,TSU_STA=10'd30,TSU_STO=parameterFF_Write1=parameterFF_Write2=5'd9,RDFUNC=以上内容为相关的速率还有时序参数。第15~16行则是相关的伪函数regregregregregalways@(posedgeCLOCKornegedgeRESETif(!RESET{i,Go}<={5'd0,5'd0C1<=D1<=elseif(iCall[1]case(iisQ=rSCL<=if(C1==0)rSDA<=elseif(C1==(TR+THIGH))rSDA<=if(C1==(FCLK)-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;以上内容为部分操作。第33行的iCall[1]为使能写操作。步骤0用来产生起始位1://WriteDevicebeginD1<={4'b1010,3'b000,1'b0};i<=5'd7;Go<=i+1'b1;beginD1<=iAddr;i<=FF_Write1;Go<=i+1'b1;3://WritebeginD1<=iData;i<=FF_Write1;Go<=i+1'b1;34://StopisQ=if(C1==0)rSCL<=elseif(C1==FQUARTER)rSCL<=if(C1==0)rSDA<=elseif(C1==(FQUARTER+TR+TSU_STO))rSDA<=if(C1==(FQUARTER+FCLK)-1)beginC1<=10'd0;i<=i+1'b1;elseC1<=C1+以上内容为部分操作。步骤4用来产生结束位beginisDone<=1'b1;i<=i+1'b1;beginisDone<=1'b0;i<=5'd0;以上内容为部分操作。步骤5~6用来产生完成信号isQ=rSDA<=D1[14-if(C1==0)rSCL<=elseif(C1==(TF+TLOW))rSCL<=if(C1==FCLK-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;以上内容为部分操作。步骤7~14是写一个字节的伪函数15://waitingforacknowledgeisQ=if(C1==FHALF)isAck<=if(C1==0)rSCL<=elseif(C1==FHALF)rSCL<=if(C1==FCLK-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;if(isAck!=0)i<=5'd0;elsei<=Go;elseif(iCall[0]case(i0://isQ=rSCL<=if(C1==0)rSDA<=elseif(C1==(TR+THIGH))rSDA<=if(C1==FCLK-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;1://WriteDevicebeginD1<={4'b1010,3'b000,1'b0};i<=5'd9;Go<=i+1'b1;beginD1<=iAddr;i<=FF_Write2;Go<=i+1'b1;3://StartagainisQ=if(C1==0)rSCL<=elseif(C1==FQUARTER)rSCL<=elseif(C1==(FQUARTER+TR+TSU_STA+THD_STA+)rSCL<=if(C1==0)rSDA<=elseif(C1==FQUARTER)rSDA<=elseif(C1==(FQUARTER+TR+THIGH))rSDA<=if(C1==(FQUARTER+FCLK+FQUARTER)-1)beginC1<=10'd0;i<=i+1'b1;elseC1<=C1+34://WriteDeviceAddr(ReadbeginD1<={4'b1010,3'b000,1'b1};i<=5'd9;Go<=i+1'b1;5://ReadbeginD1<=8'd0;i<=RDFUNC;Go<=i+1'b1;6://StopisQ=if(C1==0)rSCL<=elseif(C1==FQUARTER)rSCL<=if(C1==0)rSDA<=elseif(C1==(FQUARTER+TR+TSU_STO))rSDA<=if(C1==(FCLK+FQUARTER)-1)beginC1<=10'd0;i<=i+1'b1;elseC1<=C1+beginisDone<=1'b1;i<=i+1'b1;beginisDone<=1'b0;i<=5'd0;以上内容为部分操作。步骤4用来写入设备地址(读,并且调用伪函数。步骤5用来一个字节,并且调用伪函数。步骤6用来产生结束位。步骤7~8则用来产生完isQ=rSDA<=D1[16-if(C1==0)rSCL<=elseif(C1==(TF+TLOW))rSCL<=if(C1==FCLK-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;以上内容为部分操作。步骤9~16是用来写一字节的伪函数17://waitingforacknowledgeisQ=if(C1==FHALF)isAck<=if(C1==0)rSCL<=elseif(C1==FHALF)rSCL<=if(C1==FCLK-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;if(isAck!=0)i<=5'd0;elsei<=Go;以上内容为部分操作。步骤17用来应答位,步骤18则用来判断应答位isQ=if(C1==FHALF)D1[26-i]<=if(C1==0)rSCL<=elseif(C1==FHALF)rSCL<=if(C1==FCLK-1)beginC1<=10'd0;i<=i+1'b1;endelseC1<=C1+1'b1;以上内容为部分操作。步骤19~26是一字节的伪函数27://noacknowledgeisQ=//if(C1==100)isAck<=if(C1==0)rSCL<=elseif(C1==FHALF)rSCL<=if(C1==FCLK-1)beginC1<=10'd0;i<=Go;elseC1<=C1+以上内容为部分操作。步骤27用来无视应答位assignSCL=assignSDA=isQ?rSDA:1'bz;assignoDone=isDone;assignoData=247.(inputCLOCK,outputinoutoutputoutput wire.oDone(DoneU1//>.iAddr(D1//<.iData(D2//< .oData(DataU1//>wirewire.RESET(RESET.SCL(SCL.SDA(SDA//>//<>.iCall(isCall//<smg_basemod(.CLOCK(CLOCK.RESET(RESET.DIG(DIG//>.SEL(SEL//>.iData(D3//<regregregregalways@(posedgeCLOCKornegedgeRESET//if(!RESETi<={D1,D2}<={8'd0,8'd0D3<=isCall<=case(iif(DoneU1)beginisCall<=2'b00;i<=i+1'b1;elsebeginisCall<=2'b10;D1<=8'd0;D2<=8'hAB;if(DoneU1)beginisCall<=2'b00;i<=i+1'b1;elsebeginisCall<=2'b10;D1<=8'd1;D2<=8'hCD;if(DoneU1)beginisCall<=2'b00;i<=i+1'b1;elsebeginisCall<=2'b10;D1<=8'd2;D2<=8'hEF;if(DoneU1)beginD3[23:16]<=DataU1;isCall<=2'b00;i<=i+1'b1;elsebeginisCall<=2'b01;D1<=8'd0;if(DoneU1)beginD3[15:8]<=DataU1

温馨提示

  • 1. 本站所有资源如无特殊说明,都需要本地电脑安装OFFICE2007和PDF阅读器。图纸软件为CAD,CAXA,PROE,UG,SolidWorks等.压缩文件请下载最新的WinRAR软件解压。
  • 2. 本站的文档不包含任何第三方提供的附件图纸等,如果需要附件,请联系上传者。文件的所有权益归上传用户所有。
  • 3. 本站RAR压缩包中若带图纸,网页内容里面会有图纸预览,若没有图纸预览就没有图纸。
  • 4. 未经权益所有人同意不得将文件中的内容挪作商业或盈利用途。
  • 5. 人人文库网仅提供信息存储空间,仅对用户上传内容的表现方式做保护处理,对用户上传分享的文档内容本身不做任何修改或编辑,并不能对任何下载内容负责。
  • 6. 下载文件中如有侵权或不适当内容,请与我们联系,我们立即纠正。
  • 7. 本站不保证下载资源的准确性、安全性和完整性, 同时也不承担用户因使用这些下载资源对自己和他人造成任何形式的伤害或损失。

评论

0/150

提交评论