Verilog语言描述常见电路结构范例精.docx
《Verilog语言描述常见电路结构范例精.docx》由会员分享,可在线阅读,更多相关《Verilog语言描述常见电路结构范例精.docx(7页珍藏版)》请在冰豆网上搜索。
Verilog语言描述常见电路结构范例精
Verilog语言描述常见电路结构范例
组合逻辑
常见的组合逻辑有:
算术逻辑部件、多路选择器、编码器、优先编码器、译码器和比较器等。
逻辑结构控制
使用括号可以改变组合逻辑的结构。
虽然EDA工具可以对组合逻辑设计进行重新优化组合,但在Verilog描述中使用括号可以降低EDA工具的压力,并且减少工具的综合时间。
在下面的例子中,虽然y2和y1的功能是一样的,但y1会使用三级加法器,使用括号的y2只使用二级加法器。
always@(a1ora2orb1orb2orc1orc2ord1ord2begin
y1=a1+b1+c1+d1;
y2=(a2+b2+(c2+d2;
end
二选一多路选择器
下面给出了三种描述2:
1MUX的方法。
y1是通过条件赋值语句实现的,y2和y3都是通过if语句实现的。
wirey1=sel1?
a1:
b1;
always@(a2ora3orb2orb3orsel2orsel3begin
y2=b2;
if(sel2y2=a2;
if(sel3y3=a3;
elsey3=b3;
end
四选一多路选择器
用Verilog描述4:
1MUX可以有如下方法:
一个if语句加多个elseif从句
嵌套if语句
case语句
always@(aorborcordorselbegin
if(sel==2'b00y=a;
elseif(sel==2'b01y=b;
elseif(sel==2'b10y=c;
elsey=d;
end
always@(aorborcordorselbegin
if(sel[1]==0
if(sel[0]==0y=a;
elsey=b;
else
if(sel[0]==0y=c;
elsey=d;
end
always@(aorborcordorselbegin
case(sel
2'b00:
y=a;
2'b01:
y=b;
2'b10:
y=c;
2'b11:
y=d;
default:
y=a;
endcase
end
八选一多路选择器
描述8:
1MUX最好使用case语句
always@(a0ora1ora2ora3ora4ora5ora6ora7orselbegin
case(sel
0:
y=a0;
1:
y=a1;
2:
y=a2;
3:
y=a3;
4:
y=a4;
5:
y=a5;
6:
y=a6;
7:
y=a7;
default:
y=a0;
endcase
end
8:
3编码器
编码器可以将多个离散的信号用编码表示出来,比如3位的编码可以表示8个信号。
下面的例子给出了三种8:
3编码器的描述方法。
always@(abegin
if(a==8'b00000001y=0;
elseif(a==8'b00000010y=1;
elseif(a==8'b00000100y=2;
elseif(a==8'b00001000y=3;
elseif(a==8'b00010000y=4;
elseif(a==8'b00100000y=5;
elseif(a==8'b01000000y=6;
elseif(a==8'b10000000y=7;
elsey=3'bX;
end
always@(abegin
case(a
8'b00000001:
y=0;
8'b00000010:
y=1;
8'b00000100:
y=2;
8'b00001000:
y=3;
8'b00010000:
y=4;
8'b00100000:
y=5;
8'b01000000:
y=6;
8'b10000000:
y=7;
default:
y=3'bX;
endcase
end
always@(abegin
test=8'b00000001;
y=3'bX;
for(i=0;i<8;i=i+1begin
if(a==test
y=i;
test=test<<1;
end
end
优先级编码器
优先级编码器是一种特殊的编码器,就是当多个输入信号同时有效时,它只输出优先级最高的信号的编码。
下面的例子给出了8:
3优先级编译器的描述方法。
always@(abegin
valid=1;
if(a[7]y=7;
elseif(a[6]y=6;
elseif(a[5]y=5;
elseif(a[4]y=4;
elseif(a[3]y=3;
elseif(a[2]y=2;
elseif(a[1]y=1;
elseif(a[0]y=0;
elsebegin
valid=0;
y=3'bx;
end
end
always@(abegin
valid=1;
casez(a
8'b1?
?
?
?
?
?
?
:
y=7;
8'b01?
?
?
?
?
?
:
y=6;
8'b001?
?
?
?
?
:
y=5;
8'b0001?
?
?
?
:
y=4;
8'b00001?
?
?
:
y=3;
8'b000001?
?
:
y=2;
8'b0000001?
:
y=1;
8'b00000001:
y=0;
default:
begin
valid=0;
y=3'bx;
end
endcase
end
always@(aornbegin
valid=0;
y=3'bx;
for(i=8;i<8;i=i+1begin
if(a[i]begin
valid=1;
y=i;
end
end
end
译码器
译码器的作用恰好与编码器相反,它从编好的码中把原始信号还原出来。
下面的例子给出了三种3:
8译码器的描述方法:
always@(abegin
if(a==0y=8'b00000001;
elseif(a==1y=8'b00000010;
elseif(a==2y=8'b00000100;
elseif(a==3y=8'b00001000;
elseif(a==4y=8'b00010000;
elseif(a==5y=8'b00100000;
elseif(a==6y=8'b01000000;
elsey=8'b10000000;
end
always@(abegin
case(a
0:
y=8'b00000001;
1:
y=8'b00000010;
2:
y=8'b00000100;
3:
y=8'b00001000;
4:
y=8'b00010000;
5:
y=8'b00100000;
6:
y=8'b01000000;
7:
y=8'b10000000;
default:
y=8'bX;
endcase
end
always@(aornbegin
for(i=0;i<8;i=i+1begin
if(a==ny[i]=1;
elsey[i]=0;
end
end
比较器
比较器用于比较两个或多个输入的关系,如相等、不等、大小等。
下面的例子给出了三种6位比较器的描述方法。
always@(a1ora2ora3orb1orb2orb3begin
y1=1;
for(n=0;n<6;n=n+1
if(a1[n]!
=b1[n]y1=0;
y2=0;
if(a2==b2y2=1;
if(a3==b3y3=1;
elsey3=0;
end
时序逻辑时序逻辑包括latch、触发器、计数器等,latch产生的主要原因是if或case语句中的条件不完整,这是要努力避免的。
D触发器always@(posedgeclkbeginif(!
rst_syny1<=0;elsey1<=d1;endalways@(posedgeclkornegedgerst_nbeginif(!
rst_ny2<=0;elsey2<=d2;endalways@(posedgeclkornegedgerst_nbeginif(!
rst_ny3<=0;elseif(rst_syny3<=0;elsey3<=d3;endalways@(posedgeclkif(eny4<=d4;always@(posedgeclkif(rst_syny5<=0;elseif(eny5<=d5;always@(posedgeclkornegedgerst_nif(rst_ny6<=0;elseif(eny6<=d6;计数器always@(posedgeclkornegedgerst_nbeginif(!
rst_ncounter=0;elsebegincase({up,down}2'b10:
counter<=counter+1;2'b01:
counter<=counter-1;endcaseendend
有限状态机FSM由状态寄存器、下一状态逻辑和输出逻辑组成。
下面的例子给出了一个FSM的描述方法。
modulefsm1(ds,rd,go,ws,clk,rst_n;outputds,rd;inputgo,ws;inputclk,rst_n;regds,rd;parameter[1:
0]IDLE=2'b00,READ=2'b01,DLY=2'b10,DONE=2'b11;reg[1:
0]state,next;always@(posedgeclkornegedgerst_nif(!
rst_nstate<=IDLE;elsestate<=next;always@(stateorgoorwsbeginnext=2'bx;ds=1'b0;rd=1'b0;case(stateIDLE:
if(gonext=READ;elsenext=IDLE;READ:
beginrd=1'b1;next=DLY;endDLY:
beginrd=1'b1;if(wsnext=READ;elsenext=DONE;endDONE:
beginds=1'b1;next=IDLE;endendcaseendendmodule