**这是本文档旧的修订版!**
——————————————————————–
»»»»»»»»»»»»> COPYRIGHT NOTICE ««««««««««««<
——————————————————————–
Module: DLEDDISP
Author: Step
Description: Display with Nixie tube
Web: www.ecbcamp.com
——————————————————————–
Code Revision History :
——————————————————————–
Version: |Mod. Date: |Changes Made:
V1.0 |2015/11/11 |Initial ver
——————————————————————–
module DLEDDISP
(
input clkin, 25mhz
input rstn_in, active with low
output reg rclkout, 74HC595 RCK
output reg sclkout, 74HC595 SCK
output reg sdio_out 74HC595 SER
);
parameter CLKDIVPERIOD=1000; related with clkdiv's frequency
parameter DELAYPERIOD=10000; related with delay time and refresh frequency
parameter CLKDIVPULSEPERIOD=25000000; related with clkdivpulseout's frequency
parameter CLKL=2'd0;
parameter CLKH=2'd1;
parameter CLKRISINGDEGE=2'd2;
parameter CLKFALLINGDEGE=2'd3;
parameter IDLE=3'd0;
parameter WRITE=3'd1;
parameter DELAY=3'd2;
parameter LOW =1'b0;
parameter HIGH =1'b1;
initial for memory register
reg[7:0] mem [15:0];
initial begin
mem[0]= 8'h3f; 0
mem[1]= 8'h06; 1
mem[2]= 8'h5b; 2
mem[3]= 8'h4f; 3
mem[4]= 8'h66; 4
mem[5]= 8'h6d; 5
mem[6]= 8'h7d; 6
mem[7]= 8'h07; 7
mem[8]= 8'h7f; 8
mem[9]= 8'h6f; 9
mem[10]= 8'h77; A
mem[11]= 8'h40; b
mem[12]= 8'h39; C
mem[13]= 8'h5e; d
mem[14]= 8'h79; E
mem[15]= 8'h71; F
end
clkdiv1Hz = clkin/CLKDIVPULSEPERIOD
reg[24:0] cnt;
reg clkdiv1Hz;
always@(posedge clkin or negedge rstnin)
begin
if(!rstnin) begin
cnt⇐0;
clkdiv1Hz⇐0;
end else if(cnt==(CLKDIVPULSEPERIOD-1)) begin
cnt⇐0;
clkdiv1Hz⇐1;
end else begin
cnt⇐cnt+1;
clkdiv1Hz⇐0;
end
end
reg [3:0] number = 0;
reg [3:0] numberr = 1;
reg [3:0] numberr1 = 2;
reg [3:0] numberr2 = 3;
generate the number need to display every second
always@(posedge clkdiv1Hz or negedge rstnin)
begin
if(!rstnin) begin
number⇐4'd3;
numberr⇐4'd2;
numberr1⇐4'd1;
numberr2⇐4'd0;
end else begin
numberr2⇐numberr1;
numberr1⇐numberr;
numberr⇐number;
if(number>=9) number⇐0;
else number⇐number+1;
end
end
clkdiv = clkin/CLKDIVPERIOD
reg clkdiv;
reg[15:0] clkcnt=0;
always@(posedge clkin or negedge rstnin) begin
if(!rstnin) clkcnt⇐0;
else begin
clkcnt⇐clkcnt+1;
if(clkcnt==(CLKDIVPERIOD-1)) clkcnt⇐0;
if(clkcnt<(CLKDIVPERIOD/2)) clkdiv⇐0;
else clkdiv⇐1;
end
end
Divide clkdiv 4 state,
RISING and FALLING state is keeped one cycle of clkin, like a pulse.
reg[1:0] clkdivstate=CLKL;
always@(posedge clkin or negedge rstnin) begin
if(!rstnin) clkdivstate⇐CLKL;
else case(clkdivstate)
CLKL: begin
if (clkdiv) clkdivstate⇐CLKRISINGDEGE;
else clkdivstate⇐CLKL;
end
CLKRISINGDEGE :clkdivstate⇐CLKH;
CLKH:begin
if (!clkdiv) clkdivstate⇐CLKFALLINGDEGE;
else clkdivstate⇐CLKH;
end
CLKFALLINGDEGE:clkdivstate⇐CLKL;
default;
endcase
end
Finite State Machine,
reg shiftflag = 0;
reg[15:0] datareg;
reg[2:0] datastate=IDLE;
reg[2:0] datastateback;
reg[3:0] datastatecnt=0;
reg[5:0] shiftcnt=0;
reg[25:0] delaycnt=0;
always@(posedge clkin or negedge rstnin) begin
if(!rstnin) begin
datastate⇐IDLE;
datastatecnt⇐0;
end else begin
case (datastate)
IDLE: begin
datastatecnt⇐datastatecnt+1;
case(datastatecnt)
0: begin
datareg⇐{mem[numberr2],8'h2e};
datastate⇐WRITE;datastateback⇐IDLE;
end
1: begin
datareg⇐{mem[numberr1],8'h2d};
datastate⇐WRITE;datastateback⇐IDLE;
end
2: begin
datareg⇐{mem[numberr],8'h2b};
datastate⇐WRITE;datastateback⇐IDLE;
end
3: begin
datareg⇐{mem[number],8'h27};
datastate⇐WRITE;datastateback⇐IDLE;
end
4: begin datastate⇐DELAY;datastateback⇐IDLE; end
5: begin datastatecnt⇐0; end
default;
endcase
end
WRITE: begin
if(!shiftflag) begin
if (clkdivstate==CLKFALLINGDEGE) begin
if (shiftcnt==10) rclkout⇐LOW;
if (shiftcnt==16) begin
shiftcnt⇐0;
rclkout⇐HIGH;
datastate⇐datastateback;
end else begin
sclkout⇐LOW;
sdioout⇐datareg[15];
shiftflag ⇐ 1;
end
end
end else begin
if (clkdivstate==CLKRISINGDEGE) begin
datareg⇐{datareg[14:0], datareg[15]};
shiftcnt⇐shiftcnt+1;
sclkout⇐HIGH;
shiftflag ⇐ 0;
end
end
end
DELAY: begin
if(delaycnt==DELAYPERIOD) begin
datastate⇐IDLE;
delaycnt⇐0;
end else delaycnt⇐delay_cnt+1;
end
default;
endcase
end
end
endmodule