endmodule
/*====================================================== 文件名:period_BCD.v
功能:周期/时间间隔测量模块
======================================================*/
module period_BCD(rst,clk,curr_s,mode,signal_x,signal_div,sig_sel,clr, dec11,dec10,dec9,dec8,dec7,dec6,dec5,dec4,dec3,dec2,dec1,dec0);
//if mode=1 measure the period, else (mode=0) measure the interval.
input rst;
input clr; //clear the counter number reg input clk; input mode;
input signal_x,signal_div;
//output [48:0] cnt; output [2:0] curr_s; output sig_sel;
reg signal; reg sig_sel; reg [48:0] cnt;
reg [48:0] cnt_idle; reg [48:0] cnt_hold;
reg [2:0] curr_s,ns; reg clr_BCD;
parameter idle=3'b001;// When curr_s=1, the register is
transparent(latch=1),When curr_s=counting the num_out is latched. parameter counting=3'b010; parameter hold=3'b100;
//////判断被测信号是否需要分频(sig_sel状态机)/////////// always @ (sig_sel) //when the freq is very high, sig_sel=1; begin
if(sig_sel==1)
begin
signal=signal_div; end else
signal=signal_x; end
always @ (posedge clk) begin
if(rst==0 || mode==0) sig_sel<=0; else if (cnt>=1_0000_000 || cnt_hold>=1_0000_000 || cnt_idle>=1_0000_000) sig_sel<=0;
else if (curr_s==hold && sig_sel==0 && cnt<1_0000) sig_sel<=1; else
sig_sel<=sig_sel; end
//////////////////////主状态机/////////////////////////// always @ (posedge sgnal or negedge rst) begin
if(rst==0) curr_s<=idle; else
curr_s<=ns; end
always @ (curr_s) begin
case(curr_s)
idle: begin ns=counting; clr_BCD=0;end counting: begin ns=hold; clr_BCD=1; end hold:
if(mode==1) begin ns=idle; clr_BCD=1;
end //measure the period else if(mode==0) begin ns=hold; clr_BCD=1; end
default: begin ns=idle;clr_BCD=1; end endcase end
////////对主状态机的三种状态计数(计时)///////////////// always @ (posedge clk) begin
if(curr_s==idle) begin
if(cnt_idle>=32'b11111111_11111111_11111111_11111111) cnt_idle<=0; else
cnt_idle<=cnt_idle+1; end else
cnt_idle<=0; end
always @ (posedge clk) begin
if(curr_s==hold) begin
if(cnt_hold>=32'b11111111_11111111_11111111_11111111) cnt_hold<=0; else
cnt_hold<=cnt_hold+1; end else
cnt_hold<=0; end
always @ (posedge clk or negedge rst) begin if(!rst)
begin cnt<=0; end
else if(curr_s==counting) begin
if(cnt>=32'b11111111_11111111_11111111_11111111) cnt<=0; else
cnt<=cnt+1; end
else if (curr_s==hold) cnt<=cnt;
else if (curr_s==idle) cnt<=0; else
cnt<=cnt; end
//////////////宽度为12位的 BCD计数器////////////////////////// always @ (posedge clk or negedge clr_BCD or negedge rst) begin
if(rst==0 || clr_BCD==0) d0<=0; else if(curr_s==counting) begin
if(d0>=9)
begin d0<=0; cout0<=1;end else
begin d0<=d0+1;cout0<=0;end end
else if (curr_s==hold)
begin d0<=d0; cout0<=cout0;end // else if (curr_s==idle) // begin d0<=0; cout0<=0;end else d0<=d0; end
always @ (posedge cout9 or negedge clr_BCD or negedge rst) begin
if(rst==0 || clr_BCD==0) d10<=0; else begin
if(d10>=9)
begin d10<=0; cout10<=1;end else
begin d10<=d10+1;cout10<=0;end end end
.......//限于篇幅,省略部分BCD计数器的VERILOG描述
always @ (posedge cout10 or negedge clr_BCD or negedge rst) begin
if(rst==0 || clr_BCD==0) d11<=0; else begin
if(d11>=9)
begin d11<=0; cout11<=1;end else
begin d11<=d11+1;cout11<=0;end end end
////////////////////////////////////////////////////////////// always @ (posedge clk) //BCD计数器数值锁存 begin
if(curr_s==hold && clr!=0 ) begin
dec0<=d0; dec1<=d1; dec2<=d2; dec3<=d3; dec4<=d4; dec5<=d5; dec6<=d6; dec7<=d7; dec8<=d8; dec9<=d9; dec10<=d10; dec11<=d11; end
else if(clr==0) begin dec0<=0; dec1<=0; dec2<=0; dec3<=0; dec4<=0; dec5<=0; dec6<=0; dec7<=0; dec8<=0; dec9<=0; dec10<=0; dec11<=0; end else begin
dec0<=dec0; dec1<=dec1; dec2<=dec2; dec3<=dec3;
dec4<=dec4; dec5<=dec5; dec6<=dec6; dec7<=dec7; dec8<=dec8; dec9<=dec9; dec10<=dec10; dec11<=dec11; end end
endmodule