비동기식 FIFO(二)-손찢기 코드
module (
clk_w,rst_w,b_w,full_w,
clk_r,rst_r,b_r,empty_r,
data_in,data_out,rst_n
);
parameter WIDTH_A=8;
parameter WIDTH_D=16;
parameter DEPTH=256;
input clk_w,rst_w,b_w;
input clk_r,rst_r,b_r;
input [WIDTH_D-1:0] data_in;
input rst_n;
output empty_r;
output full_w;
output [WIDTH_D-1:0]data_out;
//write wire
wire [WIDTH_A:0] addr_w,addr_w_g;
wire [WIDTH_A:0] syn_data_w,addr_w_syn;
//read
wire [WIDTH_A:0] addr_r,addr_r_g,syn_data_r,addr_r_syn;
//RAM
wire en_r,en_w;
write_controll #(
.WIDTH_A(WIDTH_A)
)write_control( .clk_w(clk_w),
.rst_w(rst_w),
.b_w(b_w),
.addr_r_syn(addr_r_syn),
.addr_w(addr_w),
.full_w(full_w));
b2g #(
.WIDTH_A(WIDTH_A)
)bin_gray_w(.bin(addr_w),
.gray(addr_w_g));
generate
genvar i;
for (i=0;i<=WIDTH_A;i=i+1) begin:
fast_syn_slow write_syn_read(
.vcc(1'b1),
.data_in(addr_w_g[i]),
.clk_s(clk_r),
.rst_s(rst_r),
.syn_data(syn_data_w[i]));
end
endgenerate
g2b #(
.WIDTH_A(WIDTH_A)
)gray_bin(
.bin(addr_w_syn)
.gray(syn_data_w)
);
read_controll #(
.WIDTH_A(WIDTH_A)
)read_control(.clk_r(clk_r),
.rst_r(rst_r),
.addr_w_syn(addr_w_syn),
.b_r(b_r),
.empty_r(empty_r),
.addr_r(addr_r));
b2g #(
.WIDTH_A(WIDTH_A)
)bin_gray_r( .bin(addr_r),
.gray(addr_r_g));
slow_syn_fast #(
.WIDTH_A(WIDTH_A)
)read_syn_write(
.clk_f(clk_w),
.rst_f(rst_w),
.data_in(addr_r_g),
.syn_data(syn_data_r));
g2b #(
.WIDTH_A(WIDTH_A)
)gray_bin(
.bin(addr_r_syn)
.gray(syn_data_r)
);
assign en_r=(!empty_r)&b_r;
assign en_w=(!full_w)&b_w;
RAM #(
.DEPTH(DEPTH),
.WIDTH_A(WIDTH_A),
.WIDTH_D(WIDTH_D)
)data_path(
.clk_r(clk_r),.en_r(en_r),.addr_r(addr_r),
.clk_w(clk_w),.en_w(en_w),.addr_w(addr_w),
.data_in(data_in),.data_out(data_out),
.rst_n(rst_n));
endmodule
쓰기 제어 모듈
module write_controll(
clk_w,
rst_w,
b_w,//begin write to stack
addr_r_syn,//read address
full_w,
addr_w
);
parameter WIDTH_A=8;
input clk_w,rst_w,b_w;
input [WIDTH_A:0]addr_r_syn;
output [WIDTH_A:0]addr_w;
output full_w;
always@(posedge clk_w)
if (!rst_w)
addr_w<='h00;
else if (b_w&&(!w_full))
addr_w<=addr_w+1'b1;
assign w_full=({~addr_w[WIDTH_A],addr_w[WIDTH_A-1:0]}==addr_r_syn)?1'b1:1'b0;
endmodule
읽기 제어 모듈
module read_controll(
clk_r,
rst_r,
b_r,//begin read from stack
addr_w_syn,//write address
empty_r,
addr_r);
parameter WIDTH_A=8;
output empty_r ;
output [WIDTH_A:0] addr_r;
input clk_r,rst_r,b_r;
input [WIDTH_A:0]addr_w;
reg [WIDTH_A:0] addr_r;
always@(posedge clk_r)
if (! rst_r)
addr_r<='h00;
else if
addr_r<=addr_r+1'b1;
assign empty_r=(addr_r==addr_w_syn)?1'b1:1'b0;
endmodule
2진 코드 변환 그레코드
module b2g (bin,gray);
parameter WIDTH_A=8
output [WIDTH_A:0] gray;
input [WIDTH_A:0] bin;
wire h_b; //high
reg [WIDTH_A-1:0]gray_l;
assign h_b=bin[WIDTH_A];
integer i;
always@(*)
for (i=0;i<WIDTH_A;i=i+1) begin
gray_l[i] = bin[i]^bin[i+1];
end
assign gray={h_b,gray_l};
endmodule
그레코드
module g2b(
bin,
gray
);
parameter WIDTH_A=8;
input [WIDTH_A:0] gray;
output [WIDTH_A:0] bin;
reg bin_reg;
integer i;
always @(*)
begin
bin_reg=gray;
for (i=WIDTH_A-1;i>0;i=i-1) begin
bin_reg[i]=bin_reg[i+1]^gray[i];
end
end
assign bin=bin_reg;
endmodule
동기화기 느린 시계역에서 빠른 시계역까지
module slow_syn_fast(
clk_f,
rst_f,
data_in,
syn_data
);
parameter WIDTH_A=8;
input clk_f,rst_f;
input [WIDTH_A:0]data_in;
output [WIDTH_A:0]data_out;
reg [WIDTH_A:0] syn_reg_1,syn_reg_2;
always@(posedge clk_f)
if (!rst_f) begin
syn_reg_1<='h00;
syn_reg_2<='h00;
end
else begin
syn_reg_1<=data_in;
syn_reg_2<=syn_reg_1;
end
assign syn_data=syn_reg_2;
endmodule
동기화기 빠른 시계역에서 느린 시계역까지
module slow_syn_fast(
vcc,
data_in,
clk_s,
rst_s,
syn_data);
input vcc,clk_s,rst_s;
input data_in;
output syn_data;
reg syn_reg_1,syn_reg_2,syn_reg_3;
wire rst_1,rst_2,rst_3;
assign rst_1=((~data_in)&syn_reg_3)|rst_s;
assign rst_2=((~data_in)&syn_reg_3)|rst_s;
assign rst_3=rst_s;
always@(posedge data_in)
if (!rst_1)
syn_reg_1<=1'b0;
else
syn_reg_1<=vcc;
always@(posedge clk_s)
if (!rst_2)
syn_reg_2<=1'b0;
else
syn_reg_2<=syn_reg_1;
always@(posedge clk_s)
if (!rst_3)
syn_reg_3<=1'b0;
else
syn_reg_3<=syn_reg_2;
assign syn_data=syn_reg_3;
endmodule
RAM
module RAM (
clk_r,en_r,addr_r,
clk_w,en_w,addr_w,
data_in,data_out,
rst_n);
parameter DEPTH = 256;
parameter WIDTH_A = 8;
parameter WIDTH_D = 16;
input clk_r,rst_r,en_r;
input clk_w,rst_w,en_w;
input [WIDTH_A:0]addr_r,addr_w;
input [WIDTH_D-1:0]data_in;
output [WIDTH_D-1:0]data_out;
reg [WIDTH_D-1:0]data_out;
reg [WIDTH_D-1:0] mem[0:DEPTH-1];
integer i;
always@(posedge clk_w)
if (!rst_n) begin
for (i=0;i<DEPTH;i=i+1)
mem[i]<='h0000;
end
else if (en_w)
mem[addr_r]<=data_out;
always@(posedge clk_r)
if (!rst_n)
data_out<='h0000;
else if (en_r)
data_out<=mem[addr_r];
endmodule
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Vivado > Add Module to Block Design > Verilog: 추가 가능 | System Verilog: 추가 불가능?운영 환경 개요 System Verilog 구현의 UART RX를 Block Design에 추가 할 수 없습니다. Verilog는 할 수 있고 System Verilog는 추가 할 수없는 것 같습니다. UART RX...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.