Commit c8904b67 authored by Andrey Filippov's avatar Andrey Filippov

added modules, simulating

parent 5034058e
// This file may be used to define same pre-processor macros to be included into each parsed file
// It can be used to check different `ifdef branches
`define XIL_TIMING //Simprim
//`define XIL_TIMING //Simprim
`define IVERILOG
\ No newline at end of file
......@@ -2,3 +2,4 @@ unisims
glbl.v
vivado_*
syntax_*
simulation/*
......@@ -51,7 +51,7 @@
<link>
<name>vivado_logs/VivadoOpt.log</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoOpt-20140515155524262.log</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoOpt-20140520232524498.log</location>
</link>
<link>
<name>vivado_logs/VivadoOptPhys.log</name>
......@@ -61,12 +61,12 @@
<link>
<name>vivado_logs/VivadoOptPower.log</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoOptPower-20140515155524262.log</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoOptPower-20140520232524498.log</location>
</link>
<link>
<name>vivado_logs/VivadoPlace.log</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoPlace-20140515155524262.log</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoPlace-20140520232524498.log</location>
</link>
<link>
<name>vivado_logs/VivadoRoute.log</name>
......@@ -76,7 +76,7 @@
<link>
<name>vivado_logs/VivadoSynthesis.log</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoSynthesis-20140515155524262.log</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoSynthesis-20140520232242973.log</location>
</link>
<link>
<name>vivado_logs/VivadoTimimgSummaryReportImplemented.log</name>
......@@ -86,7 +86,7 @@
<link>
<name>vivado_logs/VivadoTimimgSummaryReportSynthesis.log</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoTimimgSummaryReportSynthesis-20140515155524262.log</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoTimimgSummaryReportSynthesis-20140520232524498.log</location>
</link>
<link>
<name>vivado_logs/VivadoTimingReportImplemented.log</name>
......@@ -96,7 +96,7 @@
<link>
<name>vivado_logs/VivadoTimingReportSynthesis.log</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoTimingReportSynthesis-20140515155524262.log</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_logs/VivadoTimingReportSynthesis-20140520232524498.log</location>
</link>
<link>
<name>vivado_state/eddr3-opt-phys.dcp</name>
......@@ -106,7 +106,7 @@
<link>
<name>vivado_state/eddr3-place.dcp</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_state/eddr3-place-20140515155524262.dcp</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_state/eddr3-place-20140520232524498.dcp</location>
</link>
<link>
<name>vivado_state/eddr3-route.dcp</name>
......@@ -116,7 +116,7 @@
<link>
<name>vivado_state/eddr3-synth.dcp</name>
<type>1</type>
<location>/data/vdt/vdt-projects/eddr3/vivado_state/eddr3-synth-20140515155524262.dcp</location>
<location>/data/vdt/vdt-projects/eddr3/vivado_state/eddr3-synth-20140520204515091.dcp</location>
</link>
</linkedResources>
</projectDescription>
FPGA_project_2_ImplementationTopFile=phy/test_phy_top_01.v
FPGA_project_0_SimulationTopFile=ddrc_test01_testbench.tf
FPGA_project_1_SimulationTopModule=ddrc_test01_testbench
FPGA_project_2_ImplementationTopFile=ddrc_test01.v
FPGA_project_4_part=xc7z030fbg484-2
com.elphel.store.context.FPGA_project=FPGA_project_2_ImplementationTopFile<-@\#\#@->FPGA_project_4_part<-@\#\#@->
com.elphel.store.context.FPGA_project=FPGA_project_2_ImplementationTopFile<-@\#\#@->FPGA_project_4_part<-@\#\#@->FPGA_project_0_SimulationTopFile<-@\#\#@->FPGA_project_1_SimulationTopModule<-@\#\#@->
eclipse.preferences.version=1
VivadoSynthesis_102_ConstraintsFiles=phy/test_phy_top_01.xdc<-@\#\#@->
com.elphel.store.context.VivadoSynthesis=VivadoSynthesis_102_ConstraintsFiles<-@\#\#@->
VivadoSynthesis_102_ConstraintsFiles=ddrc_test01.xdc<-@\#\#@->
VivadoSynthesis_95_ShowInfo=false
com.elphel.store.context.VivadoSynthesis=VivadoSynthesis_102_ConstraintsFiles<-@\#\#@->VivadoSynthesis_95_ShowInfo<-@\#\#@->
eclipse.preferences.version=1
......@@ -308,7 +308,7 @@ ram_1kx32_1kx32
.data_in(wdata_out[31:0]) // data out
);
fifo_reg_W_D #( .DATA_WIDTH(30),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(30),.DATA_DEPTH(4))
raddr_i (
.rst(rst),
.clk(aclk),
......@@ -320,7 +320,7 @@ fifo_reg_W_D #( .DATA_WIDTH(30),.DATA_DEPTH(4))
.full(),
.half_full(ar_half_full)
);
fifo_reg_W_D #( .DATA_WIDTH(30),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(30),.DATA_DEPTH(4))
waddr_i (
.rst(rst),
.clk(aclk),
......@@ -332,7 +332,7 @@ fifo_reg_W_D #( .DATA_WIDTH(30),.DATA_DEPTH(4))
.full(),
.half_full(aw_half_full)
);
fifo_reg_W_D #( .DATA_WIDTH(49),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(49),.DATA_DEPTH(4))
wdata_i (
.rst(rst),
.clk(aclk),
......@@ -344,7 +344,7 @@ fifo_reg_W_D #( .DATA_WIDTH(49),.DATA_DEPTH(4))
.full(),
.half_full(w_half_full)
);
fifo_reg_W_D #( .DATA_WIDTH(14),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(14),.DATA_DEPTH(4))
wresp_i (
.rst(rst),
.clk(aclk),
......
......@@ -223,7 +223,7 @@ module axibram_read #(
*/
// assign start_read_burst_w= ar_nempty && (rready?start_read_burst_1:start_read_burst_0);
fifo_reg_W_D #( .DATA_WIDTH(ADDRESS_BITS+20),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(ADDRESS_BITS+20),.DATA_DEPTH(4))
raddr_i (
.rst(rst),
.clk(aclk),
......
......@@ -92,16 +92,25 @@ module axibram_write #(
wire bram_we_w; //,bram_we_nonmasked; // write BRAM memory non-masked - should be combined with
wire start_write_burst_w;
wire write_in_progress_w;
wire aw_nempty_ready; // aw_nempty and device ready
wire w_nempty_ready; // w_nempty and device ready
assign aw_nempty_ready=aw_nempty && dev_ready_r; // should it be dev_ready?
assign w_nempty_ready=w_nempty && dev_ready_r; // should it be dev_ready?
reg dev_ready_r; // device, selected at start burst
assign next_wr_address_w=
wburst[1]?
(wburst[0]? {ADDRESS_BITS{1'b0}}:((write_address[ADDRESS_BITS-1:0]+1) & {{(ADDRESS_BITS-4){1'b1}}, ~wlen[3:0]})):
(wburst[0]? (write_address[ADDRESS_BITS-1:0]+1):(write_address[ADDRESS_BITS-1:0]));
assign bram_we_w= w_nempty && write_in_progress && dev_ready_r;
assign bram_we_w= w_nempty_ready && write_in_progress;
// assign bram_we_nonmasked= w_nempty && write_in_progress;
assign start_write_burst_w=aw_nempty && (!write_in_progress || (w_nempty && (write_left[3:0]==4'b0)));
assign write_in_progress_w=aw_nempty || (write_in_progress && !(w_nempty && (write_left[3:0]==4'b0)));
// assign start_write_burst_w=aw_nempty && (!write_in_progress || (w_nempty && (write_left[3:0]==4'b0)));
// assign start_write_burst_w=aw_nempty_ready && (!write_in_progress || (w_nempty_ready && (write_left[3:0]==4'b0)));
assign start_write_burst_w=w_nempty_ready && aw_nempty_ready && (!write_in_progress || (w_nempty_ready && (write_left[3:0]==4'b0)));
// assign write_in_progress_w=aw_nempty || (write_in_progress && !(w_nempty && (write_left[3:0]==4'b0)));
assign write_in_progress_w=aw_nempty_ready || (write_in_progress && !(w_nempty_ready && (write_left[3:0]==4'b0)));
always @ (posedge aclk or posedge rst) begin
if (rst) wburst[1:0] <= 0;
......@@ -152,7 +161,7 @@ module axibram_write #(
assign bram_wstb = wstb_out[3:0];
assign bram_wdata = wdata_out[31:0];
fifo_reg_W_D #( .DATA_WIDTH(20+ADDRESS_BITS),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(20+ADDRESS_BITS),.DATA_DEPTH(4))
waddr_i (
.rst(rst),
.clk(aclk),
......@@ -164,7 +173,7 @@ fifo_reg_W_D #( .DATA_WIDTH(20+ADDRESS_BITS),.DATA_DEPTH(4))
.full(),
.half_full(aw_half_full)
);
fifo_reg_W_D #( .DATA_WIDTH(49),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(49),.DATA_DEPTH(4))
wdata_i (
.rst(rst),
.clk(aclk),
......@@ -176,7 +185,7 @@ fifo_reg_W_D #( .DATA_WIDTH(49),.DATA_DEPTH(4))
.full(),
.half_full(w_half_full)
);
fifo_reg_W_D #( .DATA_WIDTH(14),.DATA_DEPTH(4))
fifo_same_clock #( .DATA_WIDTH(14),.DATA_DEPTH(4))
wresp_i (
.rst(rst),
.clk(aclk),
......
......@@ -2,7 +2,7 @@
** -----------------------------------------------------------------------------**
** macros353.v
**
** I/O pads related circuitry
** temporary, modules to be moved
**
** Copyright (C) 2002 Elphel, Inc
**
......@@ -25,42 +25,8 @@
** -----------------------------------------------------------------------------**
**
*/
// just make more convenient A[3:0] instead of 4 one-bit inputs
// TODO: Replace direct instances of SRL16 to imporve portability
/*
module MSRL16 (Q, A, CLK, D);
output Q;
input [3:0] A;
input CLK, D;
SRL16 i_q(.Q(Q), .A0(A[0]), .A1(A[1]), .A2(A[2]), .A3(A[3]), .CLK(CLK), .D(D));
endmodule
module MSRL16_1 (Q, A, CLK, D);
output Q;
input [3:0] A;
input CLK, D;
SRL16_1 i_q(.Q(Q), .A0(A[0]), .A1(A[1]), .A2(A[2]), .A3(A[3]), .CLK(CLK), .D(D));
endmodule
*/
/*
module myRAM_WxD_D(D,WE,clk,AW,AR,QW,QR);
parameter DATA_WIDTH=16;
parameter DATA_DEPTH=4;
parameter DATA_2DEPTH=(1<<DATA_DEPTH)-1;
input [DATA_WIDTH-1:0] D;
input WE,clk;
input [DATA_DEPTH-1:0] AW;
input [DATA_DEPTH-1:0] AR;
output [DATA_WIDTH-1:0] QW;
output [DATA_WIDTH-1:0] QR;
reg [DATA_WIDTH-1:0] ram [0:DATA_2DEPTH];
always @ (posedge clk) if (WE) ram[AW] <= D;
assign QW= ram[AW];
assign QR= ram[AR];
endmodule
*/
module ram_WxD
#(
parameter integer DATA_WIDTH=16,
......@@ -82,75 +48,4 @@ module ram_WxD
assign QR= ram[AR];
endmodule
/*
FIFO with minimal latency 1, uses 1 register slice on the data input, output - 1 mux after register
*/
module fifo_reg_W_D
#(
parameter integer DATA_WIDTH=16,
parameter integer DATA_DEPTH=4,
parameter integer DATA_2DEPTH=(1<<DATA_DEPTH)-1
)
(
input rst, // reset, active high
input clk, // clock - positive edge
input we, // write enable
input re, // read enable
input [DATA_WIDTH-1:0] data_in, // input data
output [DATA_WIDTH-1:0] data_out, // output data
output reg nempty, // FIFO has some data
output reg full, // FIFO full
output reg half_full // FIFO half full
);
reg [DATA_DEPTH :0] fill=0;
reg just_one=0;
reg [DATA_WIDTH-1:0] inreg;
reg [DATA_WIDTH-1:0] outreg;
reg [DATA_DEPTH-1:0] ra;
reg [DATA_DEPTH-1:0] wa;
wire [DATA_DEPTH :0] next_fill;
reg wem;
wire rem;
reg [DATA_WIDTH-1:0] ram [0:DATA_2DEPTH];
// wire [DATA_DEPTH :0] pre_next_fill= ((we && ~re)?1:((~we && re)?-1:0));
assign next_fill = fill[4:0]+((we && ~re)?1:((~we && re)?5'b11111:5'b00000));
// assign next_fill = fill+((we && ~re)?1:((~we && re)?-1:0));
// assign next_fill[DATA_DEPTH :0] = fill[DATA_DEPTH :0]+pre_next_fill[DATA_DEPTH :0];
// assign next_fill[DATA_DEPTH :0] = fill[DATA_DEPTH :0]+1;
// assign next_fill[DATA_DEPTH :0] = fill[DATA_DEPTH :0]+((we && ~re)?5'b1:0);
// assign next_fill[4 :0] = fill[4 :0]+((we && ~re)?5'b1:0);
assign data_out = just_one?inreg:outreg;
assign rem = just_one? wem : re;
always @ (posedge clk or posedge rst) begin
if (rst) fill <= 0;
// else fill <= next_fill;
// else fill <= fill+1;
// else fill <= fill[4 :0]+((we && ~re)?1:((~we && re)?-1:0));
// else fill <= fill[4 :0]+((we && ~re)?5'b00001:((~we && re)?5'b11111:5'b00000));
else if (we && ~re) fill <= fill+1;
else if (~we && re) fill <= fill-1;
if (rst) wa <= 0;
else if (wem) wa <= wa+1;
if (rst) ra <= 1; // 0;
// else if (re) ra <= ra+1; //wrong?
// else if (rem) ra <= ra+1; //may be still wrong
else if (re) ra <= ra+1; //now ra is 1 ahead
else if (!nempty) ra <= wa+1; // Just recover from bit errors TODO: fix
if (rst) nempty <= 0;
else nempty <= (next_fill != 0);
end
always @ (posedge clk) begin
if (wem) ram[wa] <= inreg;
just_one <= (next_fill == 1);
// nempty <= (next_fill != 0);
half_full <=(fill & (1<<(DATA_DEPTH-1)))!=0;
full <= (fill & (1<< DATA_DEPTH ))!=0;
if (we) inreg <= data_in;
if (rem) outreg <= just_one?inreg:ram[ra];
wem <= we;
end
endmodule
// tri0 GSR = glbl.GSR;
This diff is collapsed.
......@@ -20,31 +20,35 @@
*******************************************************************************/
`timescale 1ns/1ps
module ddrc_status#(
parameter AXI_RD_ADDR_BITS= 12,
parameter SELECT_ADDR = 'h800, // address to select this module
parameter SELECT_ADDR_MASK = 'h800, // address mask to select this module
parameter BUSY_ADDR = 'hc00, // address to generate busy
parameter BUSY_ADDR_MASK = 'hc00 // address mask to generate busy
)(
input clk,
input mclk,
input rst,
input [AXI_RD_ADDR_BITS-1:0] pre_raddr, // AXI reade address, before actual reads (to generate busy), valid@start_burst
input start_rburst, // burst start - should generate ~ready (should be AND-ed with !busy internally)
input [AXI_RD_ADDR_BITS-1:0] raddr, // read address, valid with rd_en
input rd_en, // read enable
module ddrc_status
//#(
// parameter AXI_RD_ADDR_BITS= 12
// parameter SELECT_ADDR = 'h800, // address to select this module
// parameter SELECT_ADDR_MASK = 'h800, // address mask to select this module
// parameter BUSY_ADDR = 'hc00, // address to generate busy
// parameter BUSY_ADDR_MASK = 'hc00 // address mask to generate busy
//)
(
// input clk,
// input mclk,
// input rst,
// input [AXI_RD_ADDR_BITS-1:0] pre_raddr, // AXI reade address, before actual reads (to generate busy), valid@start_burst
// input start_rburst, // burst start - should generate ~ready (should be AND-ed with !busy internally)
// input [AXI_RD_ADDR_BITS-1:0] raddr, // read address, valid with rd_en
// input rd_en, // read enable
output [31:0] rdata, // read data, should valid with raddr and rd_en
output busy, // interface busy (combinatorial delay from start_wburst and pre_addr
// status/readback signals
input run_done, // sequencer done (add busy?)
// input run_done, // sequencer done (add busy?)
input run_busy, // sequencer busy
input locked, // MMCM and PLL locked
input ps_rdy, // MMCM phase shift control ready
input [ 7:0] ps_out // MMCM phase shift value (in 1/56 of the Fvco period)
);
assign busy=0;
assign rdata={21'b0,run_busy,locked,ps_rdy,ps_out[7:0]};
endmodule
This diff is collapsed.
#################################################################################
# Filename: ddrc_test01.xdc
# Date:2014-05-20
# Author: Andrey Filippov
# Description: DDR3 controller test with axi constraints
#
# Copyright (c) 2014 Elphel, Inc.
# ddrc_test01.xdc is free software; you can redistribute it and/or modify
# it under the terms of the GNU General Public License as published by
# the Free Software Foundation, either version 3 of the License, or
# (at your option) any later version.
#
# ddrc_test01.xdc is distributed in the hope that it will be useful,
# but WITHOUT ANY WARRANTY; without even the implied warranty of
# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
# GNU General Public License for more details.
#
# You should have received a copy of the GNU General Public License
# along with this program. If not, see <http://www.gnu.org/licenses/> .
#################################################################################
# output SDCLK, // DDR3 clock differential output, positive
set_property IOSTANDARD DIFF_SSTL15 [get_ports {SDCLK}]
set_property PACKAGE_PIN K3 [get_ports {SDCLK}]
# output SDNCLK,// DDR3 clock differential output, negative
set_property IOSTANDARD DIFF_SSTL15 [get_ports {SDNCLK}]
set_property PACKAGE_PIN K2 [get_ports {SDNCLK}]
# output [ADDRESS_NUMBER-1:0] SDA, // output address ports (14:0) for 4Gb device
set_property IOSTANDARD SSTL15 [get_ports {SDA[0]}]
set_property PACKAGE_PIN N3 [get_ports {SDA[0]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[1]}]
set_property PACKAGE_PIN H2 [get_ports {SDA[1]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[2]}]
set_property PACKAGE_PIN M2 [get_ports {SDA[2]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[3]}]
set_property PACKAGE_PIN P5 [get_ports {SDA[3]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[4]}]
set_property PACKAGE_PIN H1 [get_ports {SDA[4]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[5]}]
set_property PACKAGE_PIN M3 [get_ports {SDA[5]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[6]}]
set_property PACKAGE_PIN J1 [get_ports {SDA[6]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[7]}]
set_property PACKAGE_PIN P4 [get_ports {SDA[7]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[8]}]
set_property PACKAGE_PIN K1 [get_ports {SDA[8]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[9]}]
set_property PACKAGE_PIN P3 [get_ports {SDA[9]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[10]}]
set_property PACKAGE_PIN F2 [get_ports {SDA[10]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[11]}]
set_property PACKAGE_PIN H3 [get_ports {SDA[11]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[12]}]
set_property PACKAGE_PIN G3 [get_ports {SDA[12]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[13]}]
set_property PACKAGE_PIN N2 [get_ports {SDA[13]}]
set_property IOSTANDARD SSTL15 [get_ports {SDA[14]}]
set_property PACKAGE_PIN J3 [get_ports {SDA[14]}]
# output [2:0] SDBA, // output bank address ports
set_property IOSTANDARD SSTL15 [get_ports {SDBA[0]}]
set_property PACKAGE_PIN N1 [get_ports {SDBA[0]}]
set_property IOSTANDARD SSTL15 [get_ports {SDBA[1]}]
set_property PACKAGE_PIN F1 [get_ports {SDBA[1]}]
set_property IOSTANDARD SSTL15 [get_ports {SDBA[2]}]
set_property PACKAGE_PIN P1 [get_ports {SDBA[2]}]
# output SDWE, // output WE port
set_property IOSTANDARD SSTL15 [get_ports {SDWE}]
set_property PACKAGE_PIN G4 [get_ports {SDWE}]
# output SDRAS, // output RAS port
set_property IOSTANDARD SSTL15 [get_ports {SDRAS}]
set_property PACKAGE_PIN L2 [get_ports {SDRAS}]
# output SDCAS, // output CAS port
set_property IOSTANDARD SSTL15 [get_ports {SDCAS}]
set_property PACKAGE_PIN L1 [get_ports {SDCAS}]
# output SDCKE, // output Clock Enable port
set_property IOSTANDARD SSTL15 [get_ports {SDCKE}]
set_property PACKAGE_PIN E1 [get_ports {SDCKE}]
# output SDODT, // output ODT port
set_property IOSTANDARD SSTL15 [get_ports {SDODT}]
set_property PACKAGE_PIN M7 [get_ports {SDODT}]
#
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[0]}]
set_property PACKAGE_PIN K6 [get_ports {SDD[0]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[1]}]
set_property PACKAGE_PIN L4 [get_ports {SDD[1]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[2]}]
set_property PACKAGE_PIN K7 [get_ports {SDD[2]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[3]}]
set_property PACKAGE_PIN K4 [get_ports {SDD[3]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[4]}]
set_property PACKAGE_PIN L6 [get_ports {SDD[4]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[5]}]
set_property PACKAGE_PIN M4 [get_ports {SDD[5]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[6]}]
set_property PACKAGE_PIN L7 [get_ports {SDD[6]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[7]}]
set_property PACKAGE_PIN N5 [get_ports {SDD[7]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[8]}]
set_property PACKAGE_PIN H5 [get_ports {SDD[8]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[9]}]
set_property PACKAGE_PIN J6 [get_ports {SDD[9]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[10]}]
set_property PACKAGE_PIN G5 [get_ports {SDD[10]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[11]}]
set_property PACKAGE_PIN H6 [get_ports {SDD[11]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[12]}]
set_property PACKAGE_PIN F5 [get_ports {SDD[12]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[13]}]
set_property PACKAGE_PIN F7 [get_ports {SDD[13]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[14]}]
set_property PACKAGE_PIN F4 [get_ports {SDD[14]}]
# inout [15:0] SDD, // DQ I/O pads
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDD[15]}]
set_property PACKAGE_PIN F6 [get_ports {SDD[15]}]
# inout DQSL, // LDQS I/O pad
set_property PACKAGE_PIN N7 [get_ports {DQSL}]
set_property SLEW FAST [get_ports {DQSL}]
set_property IOSTANDARD DIFF_SSTL15_T_DCI [get_ports {DQSL}]
# inout NDQSL, // ~LDQS I/O pad
set_property PACKAGE_PIN N6 [get_ports {NDQSL}]
set_property SLEW FAST [get_ports {NDQSL}]
set_property IOSTANDARD DIFF_SSTL15_T_DCI [get_ports {NDQSL}]
# inout DQSU, // UDQS I/O pad
set_property PACKAGE_PIN H7 [get_ports {DQSU}]
#set_property SLEW FAST [get_ports {DQSU}]
set_property IOSTANDARD DIFF_SSTL15_T_DCI [get_ports {DQSU}]
# inout NDQSU, // ~UDQS I/O pad
set_property PACKAGE_PIN G7 [get_ports {NDQSU}]
#set_property SLEW FAST [get_ports {NDQSU}]
set_property IOSTANDARD DIFF_SSTL15_T_DCI [get_ports {NDQSU}]
# inout SDDML, // LDM I/O pad (actually only output)
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDDML}]
set_property PACKAGE_PIN L5 [get_ports {SDDML}]
# inout SDDMU, // UDM I/O pad (actually only output)
set_property IOSTANDARD SSTL15_T_DCI [get_ports {SDDMU}]
set_property PACKAGE_PIN J5 [get_ports {SDDMU}]
# Global constraints
set_property INTERNAL_VREF 0.750 [get_iobanks 34]
set_property DCI_CASCADE 34 [get_iobanks 35]
set_property INTERNAL_VREF 0.750 [get_iobanks 35]
set_property CFGBVS GND [current_design]
set_property CONFIG_VOLTAGE 1.8 [current_design]
This diff is collapsed.
This diff is collapsed.
......@@ -284,7 +284,8 @@ BUFG mclk_i (.O(mclk),.I(mclk_pre) );
) mmcm_phase_cntr_i (
.clkin (clk_in), // input
.clkfbin (clk_fb), // input
.rst (rst), // input
// .rst (rst), // input
.rst (rst_in), // input
.pwrdwn (1'b0), // input
.psclk (clk_div), // input
.ps_we (ld_mmcm), // input
......@@ -318,7 +319,8 @@ BUFG mclk_i (.O(mclk),.I(mclk_pre) );
) pll_base_i (
.clkin(clk_in), // input
.clkfbin(clkfb_ref), // input
.rst(rst), // input
// .rst(rst), // input
.rst(rst_in), // input
.pwrdwn(1'b0), // input
.clkout0(clk_ref_pre), // output
.clkout1(), // output
......
/**************************************
* Module: simul_axi_fifo
* Date:2014-03-23
* Author: andrey
*
* Description:
***************************************/
`timescale 1ns/1ps
module simul_axi_fifo
#(
parameter integer WIDTH= 64, // total number of output bits
parameter integer LATENCY=0, // minimal delay between inout and output ( 0 - next cycle)
parameter integer DEPTH=8, // maximal number of commands in FIFO
// parameter OUT_DELAY = 3.5,
parameter integer FIFO_DEPTH=LATENCY+DEPTH+1
// parameter integer DATA_2DEPTH=(1<<DATA_DEPTH)-1
)(
input clk,
input reset,
input [WIDTH-1:0] data_in,
input load,
output input_ready,
output [WIDTH-1:0] data_out,
output valid,
input ready);
reg [WIDTH-1:0] fifo [0:FIFO_DEPTH-1];
integer in_address;
integer out_address;
integer in_count;
integer out_count;
reg [LATENCY:0] latency_delay_r;
wire [LATENCY+1:0] latency_delay={latency_delay_r,load};
wire out_inc=latency_delay[LATENCY];
assign data_out= fifo[out_address];
assign valid= out_count!=0;
assign input_ready= in_count<DEPTH;
// assign out_inc={
always @ (posedge clk or posedge reset) begin
if (reset) latency_delay_r <= 0;
else latency_delay_r <= latency_delay[LATENCY:0];
if (reset) in_address <= 0;
else if (load) in_address <= (in_address==(FIFO_DEPTH-1))?0:in_address+1;
if (reset) out_address <= 0;
else if (valid && ready) out_address <= (out_address==(FIFO_DEPTH-1))?0:out_address+1;
if (reset) in_count <= 0;
else if (!(valid && ready) && load) in_count <= in_count+1;
else if (valid && ready && !load) in_count <= in_count-1;
if (reset) out_count <= 0;
else if (!(valid && ready) && out_inc) out_count <= out_count+1;
else if (valid && ready && !out_inc) out_count <= out_count-1;
end
always @ (posedge clk) begin
if (load) fifo[in_address] <= data_in;
end
endmodule
\ No newline at end of file
/*******************************************************************************
* Module: simul_axi_master_rdaddr
* Date:2014-03-23
* Author: andrey
* Description: Simulation model for AXI read address channel
*
* Copyright (c) 2014 Elphel, Inc.
* simul_axi_master_rdaddr.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* simul_axi_master_rdaddr.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module simul_axi_master_rdaddr
#(
parameter integer ID_WIDTH=12,
parameter integer ADDRESS_WIDTH=32,
parameter integer LATENCY=0, // minimal delay between inout and output ( 0 - next cycle)
parameter integer DEPTH=8, // maximal number of commands in FIFO
parameter DATA_DELAY = 3.5,
parameter VALID_DELAY = 4.0
// parameter integer DATA_2DEPTH=(1<<DATA_DEPTH)-1
)(
input clk,
input reset,
input [ID_WIDTH-1:0] arid_in,
input [ADDRESS_WIDTH-1:0] araddr_in,
input [3:0] arlen_in,
input [2:0] arsize_in,
input [1:0] arburst_in,
input [3:0] arcache_in,
input [2:0] arprot_in,
output [ID_WIDTH-1:0] arid,
output [ADDRESS_WIDTH-1:0] araddr,
output [3:0] arlen,
output [2:0] arsize,
output [1:0] arburst,
output [3:0] arcache,
output [2:0] arprot,
output arvalid,
input arready,
input set_cmd, // latch all other input data at posedge of clock
output ready // command/data FIFO can accept command
);
wire [ID_WIDTH-1:0] arid_out;
wire [ADDRESS_WIDTH-1:0] araddr_out;
wire [3:0] arlen_out;
wire [2:0] arsize_out;
wire [1:0] arburst_out;
wire [3:0] arcache_out;
wire [2:0] arprot_out;
wire arvalid_out;
assign #(DATA_DELAY) arid= arid_out;
assign #(DATA_DELAY) araddr= araddr_out;
assign #(DATA_DELAY) arlen= arlen_out;
assign #(DATA_DELAY) arsize= arsize_out;
assign #(DATA_DELAY) arburst= arburst_out;
assign #(DATA_DELAY) arcache= arcache_out;
assign #(DATA_DELAY) arprot= arprot_out;
assign #(VALID_DELAY) arvalid=arvalid_out;
simul_axi_fifo
#(
.WIDTH(ID_WIDTH+ADDRESS_WIDTH+16), // total number of output bits
.LATENCY(LATENCY), // minimal delay between inout and output ( 0 - next cycle)
.DEPTH(DEPTH) // maximal number of commands in FIFO
// parameter OUT_DELAY = 3.5,
) simul_axi_fifo_i (
.clk(clk), // input clk,
.reset(reset), // input reset,
.data_in({arid_in,araddr_in,arlen_in,arsize_in,arburst_in,arcache_in,arprot_in}), // input [WIDTH-1:0] data_in,
.load(set_cmd), // input load,
.input_ready(ready), // output input_ready,
.data_out({arid_out,araddr_out,arlen_out,arsize_out,arburst_out,arcache_out,arprot_out}), // output [WIDTH-1:0] data_out,
.valid(arvalid_out), // output valid,
.ready(arready)); // input ready);
endmodule
/*******************************************************************************
* Module: simul_axi_master_wdata
* Date:2014-03-24
* Author: Andrey Filippov
* Description: Simulation model for AXI write data channel
*
* Copyright (c) 2014 Elphel, Inc..
* simul_axi_master_wdata.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* simul_axi_master_wdata.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module simul_axi_master_wdata#(
parameter integer ID_WIDTH=12,
parameter integer DATA_WIDTH=32,
parameter integer WSTB_WIDTH= 4,
parameter integer LATENCY=0, // minimal delay between inout and output ( 0 - next cycle)
parameter integer DEPTH=8, // maximal number of commands in FIFO
parameter DATA_DELAY = 3.5,
parameter VALID_DELAY = 4.0
)(
input clk,
input reset,
input [ID_WIDTH-1:0] wid_in,
input [DATA_WIDTH-1:0] wdata_in,
input [WSTB_WIDTH-1:0] wstrb_in,
input wlast_in,
output [ID_WIDTH-1:0] wid,
output [DATA_WIDTH-1:0] wdata,
output [WSTB_WIDTH-1:0] wstrb,
output wlast,
output wvalid,
input wready,
input set_cmd, // latch all other input data at posedge of clock
output ready // command/data FIFO can accept command
);
wire [ID_WIDTH-1:0] wid_out;
wire [DATA_WIDTH-1:0] wdata_out;
wire [WSTB_WIDTH-1:0] wstrb_out;
wire wlast_out;
wire wvalid_out;
assign #(DATA_DELAY) wid= wid_out;
assign #(DATA_DELAY) wdata= wdata_out;
assign #(DATA_DELAY) wstrb= wstrb_out;
assign #(DATA_DELAY) wlast= wlast_out;
assign #(VALID_DELAY) wvalid= wvalid_out;
simul_axi_fifo
#(
.WIDTH(ID_WIDTH+DATA_WIDTH+WSTB_WIDTH+1), // total number of output bits
.LATENCY(LATENCY), // minimal delay between inout and output ( 0 - next cycle)
.DEPTH(DEPTH) // maximal number of commands in FIFO
) simul_axi_fifo_i (
.clk(clk), // input clk,
.reset(reset), // input reset,
.data_in({wid_in, wdata_in, wstrb_in, wlast_in}), // input [WIDTH-1:0] data_in,
.load(set_cmd), // input load,
.input_ready(ready), // output input_ready,
.data_out({wid_out, wdata_out, wstrb_out, wlast_out}), // output [WIDTH-1:0] data_out,
.valid(wvalid_out), // output valid,
.ready(wready)); // input ready);
endmodule
/*******************************************************************************
* Module: simul_axi_master_wraddr
* Date:2014-03-24
* Author: Andrey Filippov
* Description: Simulation model for AXI write address channel
*
* Copyright (c) 2014 Elphel, Inc..
* simul_axi_master_wraddr.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* simul_axi_master_wraddr.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module simul_axi_master_wraddr
#(
parameter integer ID_WIDTH=12,
parameter integer ADDRESS_WIDTH=32,
parameter integer LATENCY=0, // minimal delay between inout and output ( 0 - next cycle)
parameter integer DEPTH=8, // maximal number of commands in FIFO
parameter DATA_DELAY = 3.5,
parameter VALID_DELAY = 4.0
)(
input clk,
input reset,
input [ID_WIDTH-1:0] awid_in,
input [ADDRESS_WIDTH-1:0] awaddr_in,
input [3:0] awlen_in,
input [2:0] awsize_in,
input [1:0] awburst_in,
input [3:0] awcache_in,
input [2:0] awprot_in,
output [ID_WIDTH-1:0] awid,
output [ADDRESS_WIDTH-1:0] awaddr,
output [3:0] awlen,
output [2:0] awsize,
output [1:0] awburst,
output [3:0] awcache,
output [2:0] awprot,
output awvalid,
input awready,
input set_cmd, // latch all other input data at posedge of clock
output ready // command/data FIFO can accept command
);
wire [ID_WIDTH-1:0] awid_out;
wire [ADDRESS_WIDTH-1:0] awaddr_out;
wire [3:0] awlen_out;
wire [2:0] awsize_out;
wire [1:0] awburst_out;
wire [3:0] awcache_out;
wire [2:0] awprot_out;
wire awvalid_out;
assign #(DATA_DELAY) awid= awid_out;
assign #(DATA_DELAY) awaddr= awaddr_out;
assign #(DATA_DELAY) awlen= awlen_out;
assign #(DATA_DELAY) awsize= awsize_out;
assign #(DATA_DELAY) awburst= awburst_out;
assign #(DATA_DELAY) awcache= awcache_out;
assign #(DATA_DELAY) awprot= awprot_out;
assign #(VALID_DELAY) awvalid= awvalid_out;
simul_axi_fifo
#(
.WIDTH(ID_WIDTH+ADDRESS_WIDTH+16), // total number of output bits
.LATENCY(LATENCY), // minimal delay between inout and output ( 0 - next cycle)
.DEPTH(DEPTH) // maximal number of commands in FIFO
// parameter OUT_DELAY = 3.5,
) simul_axi_fifo_i (
.clk(clk), // input clk,
.reset(reset), // input reset,
.data_in({awid_in,awaddr_in,awlen_in,awsize_in,awburst_in,awcache_in,awprot_in}), // input [WIDTH-1:0] data_in,
.load(set_cmd), // input load,
.input_ready(ready), // output input_ready,
.data_out({awid_out,awaddr_out,awlen_out,awsize_out,awburst_out,awcache_out,awprot_out}), // output [WIDTH-1:0] data_out,
.valid(awvalid_out), // output valid,
.ready(awready)); // input ready);
endmodule
/*******************************************************************************
* Module: simul_axi_read
* Date:2014-04-06
* Author: Andrey Filippov
* Description: simulation of read data through maxi channel
*
* Copyright (c) 2014 Elphel, Inc.
* simul_axi_read.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* simul_axi_read.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module simul_axi_read(
input clk,
input reset,
input last, // last data word in burst
input data_stb, // data strobe (RVALID & RREADY) genearted externally
input [ 9:0] raddr, // read burst address as written by axi master, 10 significant bits [11:2], valid at rcmd
input [ 3:0] rlen, // burst length as written by axi master, valid at rcmd
input rcmd, // read command (address+length) strobe
output [ 9:0] addr_out, // output address
output burst, // burst in progress
output reg err_out); // data last does not match predicted or FIFO over/under run
wire [ 9:0] raddr_fifo; // raddr after fifo
wire [ 3:0] rlen_fifo; // rlen after fifo
wire fifo_valid; // fifo out valid
// wire fifo_re; // fifo read strobe
reg burst_r=0;
reg [ 3:0] left_plus_1;
// wire start_burst=fifo_valid && (!burst_r || (last && data_stb));
// wire start_burst=fifo_valid && data_stb && (!burst_r || last );
wire start_burst=fifo_valid && data_stb && !burst_r;
wire generated_last= burst?(left_plus_1==1): ( fifo_valid && (rlen_fifo==0)) ;
wire fifo_in_rdy;
wire error_w= (data_stb && (last != generated_last)) || (rcmd && !fifo_in_rdy) || (start_burst && !fifo_valid);
reg [ 9:0] adr_out_r;
// reg was_last;
assign burst=burst_r || start_burst;
assign addr_out=start_burst?raddr_fifo:adr_out_r;
always @ (posedge reset or posedge clk) begin
if (reset) burst_r <= 0;
else if (start_burst) burst_r <= rlen_fifo!=0;
// else if (last && data_stb) burst_r <= 0;
else if (generated_last && data_stb) burst_r <= 0;
if (reset) left_plus_1 <= 0;
else if (start_burst) left_plus_1 <= rlen_fifo;
else if (data_stb) left_plus_1 <= left_plus_1-1;
if (reset) err_out <= 0;
else err_out <= error_w;
// if (reset) was_last <= 0;
// else if (data_stb) was_last <= last;
end
always @ (posedge clk) begin
if (start_burst) adr_out_r <= raddr_fifo+1; // simulating only address incremental mode
else if (data_stb) adr_out_r <= adr_out_r + 1;
end
simul_fifo
#(
.WIDTH(14),
.DEPTH(64)
)simmul_fifo_i(
.clk(clk),
.reset(reset),
// .data_in({rlen[3:0],raddr[11:2]}), // did not detect raddr[11:2] for input [ 9:0] raddr
.data_in({rlen[3:0],raddr}),
.load(rcmd),
.input_ready(fifo_in_rdy),
.data_out({rlen_fifo, raddr_fifo}),
.valid(fifo_valid),
.ready(start_burst));
endmodule
/*******************************************************************************
* Module: simul_axi_slow_ready
* Date:2014-03-24
* Author: Andrey Filippov
* Description: Simulation model for AXI: slow ready generation
*
* Copyright (c) 2014 Elphel, Inc..
* simul_axi_slow_ready.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* simul_axi_slow_ready.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module simul_axi_slow_ready(
input clk,
input reset,
input [3:0] delay,
input valid,
output ready
);
reg [14:0] rdy_reg;
assign ready=(delay==0)?1'b1: ((((rdy_reg[14:0] >> (delay-1)) & 1'b1) != 0)?1'b1:1'b0);
always @ (posedge clk or posedge reset) begin
if (reset) rdy_reg <=0;
else if (!valid || ready) rdy_reg <=0;
else rdy_reg <={rdy_reg[13:0],valid};
end
endmodule
/*******************************************************************************
* Module: simul_fifo
* Date:2014-04-06
* Author: Andrey Filippov
* Description: simple fifo for simulation
*
* Copyright (c) 2014 Elphel, Inc.
* simul_fifo.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* simul_fifo.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module simul_fifo
#(
parameter integer WIDTH= 32, // total number of output bits
parameter integer DEPTH= 64, // maximal number of words in FIFO
// parameter OUT_DELAY = 3.5,
parameter integer FIFO_DEPTH=DEPTH+1
// parameter integer DATA_2DEPTH=(1<<DATA_DEPTH)-1
)(
input clk,
input reset,
input [WIDTH-1:0] data_in,
input load,
output input_ready,
output [WIDTH-1:0] data_out,
output valid,
input ready);
reg [WIDTH-1:0] fifo [0:FIFO_DEPTH-1];
integer in_address;
integer out_address;
integer count;
assign data_out= fifo[out_address];
assign valid= count!=0;
assign input_ready= count<DEPTH;
always @ (posedge clk or posedge reset) begin
if (reset) in_address <= 0;
else if (load) in_address <= (in_address==(FIFO_DEPTH-1))?0:in_address+1;
if (reset) out_address <= 0;
else if (valid && ready) out_address <= (out_address==(FIFO_DEPTH-1))?0:out_address+1;
if (reset) count <= 0;
else if (!(valid && ready) && load) count <= count+1;
else if (valid && ready && !load) count <= count-1;
end
always @ (posedge clk) begin
if (load) fifo[in_address] <= data_in;
end
endmodule
\ No newline at end of file
/*******************************************************************************
* Module: fifo_cross_clocks
* Date:2014-05-20
* Author: Andrey Filippov
* Description: Configurable FIFO with separate read and write clocks
*
* Copyright (c) 2014 Elphel, Inc.
* fifo_cross_clocks.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* fifo_cross_clocks.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module fifo_cross_clocks
#(
parameter integer DATA_WIDTH=16,
parameter integer DATA_DEPTH=4 // >=3
) (
input rst, // reset, active high
input rclk, // read clock - positive edge
input wclk, // write clock - positive edge
input we, // write enable
input re, // read enable
input [DATA_WIDTH-1:0] data_in, // input data
output [DATA_WIDTH-1:0] data_out, // output data
output nempty, // FIFO has some data (sync to rclk)
output half_empty // FIFO half full (wclk) -(not more than 5/8 full)
);
localparam integer DATA_2DEPTH=(1<<DATA_DEPTH)-1;
reg [DATA_WIDTH-1:0] ram [0:DATA_2DEPTH];
reg [DATA_DEPTH-1:0] raddr;
reg [DATA_DEPTH-1:0] waddr;
reg [DATA_DEPTH-1:0] waddr_gray;
reg [DATA_DEPTH-1:0] waddr_gray_rclk;
wire [DATA_DEPTH-1:0] waddr_plus1 = waddr +1;
wire [DATA_DEPTH-1:0] waddr_plus1_gray = waddr_plus1 ^ {1'b0,waddr_plus1[DATA_DEPTH-1:1]};
wire [DATA_DEPTH-1:0] raddr_gray = raddr ^ {1'b0,raddr[DATA_DEPTH-1:1]};
wire [DATA_DEPTH-1:0] raddr_plus1 = raddr +1;
wire [2:0] raddr_plus1_gray_top3 = raddr_plus1[DATA_DEPTH-1:DATA_DEPTH-3] ^ {1'b0,raddr_plus1[DATA_DEPTH-1:DATA_DEPTH-2]};
reg [2:0] raddr_gray_top3;
reg [2:0] raddr_gray_top3_wclk;
wire [2:0] raddr_top3_wclk = {
raddr_gray_top3_wclk[2],
raddr_gray_top3_wclk[2]^raddr_gray_top3_wclk[1],
raddr_gray_top3_wclk[2]^raddr_gray_top3_wclk[1]^raddr_gray_top3_wclk[0]};
//(* keep = "true" *) wire [2:0] addr_diff=waddr[DATA_DEPTH-1-:3]-raddr_top3_wclk; // just debugging 8-3332
wire [2:0] waddr_top3=waddr[DATA_DEPTH-1:DATA_DEPTH-3];
//(* keep = "true" *) wire [2:0] addr_diff=waddr[DATA_DEPTH-1:DATA_DEPTH-4]-raddr_top3_wclk; // just debugging 8-3332
wire [2:0] addr_diff=waddr_top3[2:0]-raddr_top3_wclk[2:0];
// half-empty does not need to be precise, it uses 3 MSBs of the write address
// converting to Gray code (easy) and then back (can not be done parallel easily).
// Comparing to 1/8'th of the depth with one-bit Gray code error results in uncertainty
// of +/-1/8, so half_empty means "no more than 5/8 full"
assign half_empty=~addr_diff[2];
// False positive in nempty can only happen if
// a) it is transitioning from empty to non-empty due to we pulse
// b) it is transitioning to overrun - too bad already
// false negative - OK, just wait fro the next rclk
assign nempty=waddr_gray_rclk != raddr_gray;
assign data_out=ram[raddr];
always @ (posedge wclk or posedge rst) begin
if (rst) waddr <= 0;
else if (we) waddr <= waddr_plus1;
if (rst) waddr_gray <= 0;
else if (we) waddr_gray <= waddr_plus1_gray;
end
always @ (posedge rclk or posedge rst) begin
if (rst) raddr <= 0;
else if (re) raddr <= raddr_plus1;
if (rst) raddr_gray_top3 <= 0;
else if (re) raddr_gray_top3 <= raddr_plus1_gray_top3;
end
always @ (posedge rclk) begin
waddr_gray_rclk <= waddr_gray;
end
always @ (posedge wclk) begin
raddr_gray_top3_wclk <= raddr_gray_top3;
if (we) ram[waddr] <= data_in;
end
endmodule
/*******************************************************************************
* Module: fifo_same_clock
* Date:2014-05-20
* Author: Andrey Filippov
* Description: Configurable synchronous FIFO using the same clock for read and write
*
* Copyright (c) 2014 Elphel, Inc.
* fifo_same_clock.v is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 3 of the License, or
* (at your option) any later version.
*
* fifo_same_clock.v is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <http://www.gnu.org/licenses/> .
*******************************************************************************/
`timescale 1ns/1ps
module fifo_same_clock
#(
parameter integer DATA_WIDTH=16,
parameter integer DATA_DEPTH=4
)
(
input rst, // reset, active high
input clk, // clock - positive edge
input we, // write enable
input re, // read enable
input [DATA_WIDTH-1:0] data_in, // input data
output [DATA_WIDTH-1:0] data_out, // output data
output reg nempty, // FIFO has some data
output reg full, // FIFO full
output reg half_full // FIFO half full
);
localparam integer DATA_2DEPTH=(1<<DATA_DEPTH)-1;
reg [DATA_DEPTH :0] fill=0;
reg just_one=0;
reg [DATA_WIDTH-1:0] inreg;
reg [DATA_WIDTH-1:0] outreg;
reg [DATA_DEPTH-1:0] ra;
reg [DATA_DEPTH-1:0] wa;
wire [DATA_DEPTH :0] next_fill;
reg wem;
wire rem;
reg out_full=0; //output register full
reg [DATA_WIDTH-1:0] ram [0:DATA_2DEPTH];
// assign next_fill = fill[4:0]+((we && ~re)?1:((~we && re)?5'b11111:5'b00000));
// assign data_out = just_one?inreg:outreg;
assign data_out = out_full?outreg:inreg;
assign rem = (!out_full || re)&& (just_one? wem : re);
// assign next_fill = fill[4:0]+((we && ~rem)?1:((~we && rem)?5'b11111:5'b00000));
// TODO: verify rem is not needed instead of re
assign next_fill = fill[4:0]+((we && ~re)?1:((~we && re)?5'b11111:5'b00000));
always @ (posedge clk or posedge rst) begin
if (rst) fill <= 0;
else if (we && ~re) fill <= fill+1;
else if (~we && re) fill <= fill-1;
if (rst) wa <= 0;
else if (wem) wa <= wa+1;
if (rst) ra <= 1; // 0;
else if (re) ra <= ra+1; //now ra is 1 ahead
else if (!nempty) ra <= wa+1; // Just recover from bit errors TODO: fix
if (rst) nempty <= 0;
else nempty <= (next_fill != 0);
if (rst) out_full <= 0;
else if (rem && ~re) out_full <= 1;
else if (re && ~rem) out_full <= 0;
end
always @ (posedge clk) begin
if (wem) ram[wa] <= inreg;
just_one <= (next_fill == 1);
half_full <=(fill & (1<<(DATA_DEPTH-1)))!=0;
full <= (fill & (1<< DATA_DEPTH ))!=0;
if (we) inreg <= data_in;
if (rem) outreg <= just_one?inreg:ram[ra];
wem <= we;
end
endmodule
......@@ -105,7 +105,7 @@ module mmcm_phase_cntr#(
reg ps_busy=0;
// TODO: find out why it was optimized out!
(* keep = "true" *) reg ps_start0, ps_start; // debugging
assign ps_ready=!ps_busy && locked && ps_start0 && ps_start;
assign ps_ready=!ps_busy && locked && !ps_start0 && !ps_start;
assign psen=ps_start && (diff != 0);
// wire [PHASE_WIDTH:0] diff= ps_target-ps_dout_r;
// made a difference, so it doesn't seem Vivado extends bits of operands "+", "-"
......
......@@ -93,7 +93,7 @@ localparam integer DATA_WIDTH_TRI= (MODE_DDR=="TRUE")?4:1;
.DATA_RATE_OQ (DATA_RATE),
.DATA_RATE_TQ (DATA_RATE),
.DATA_WIDTH (DATA_WIDTH),
.DDR3_DATA (DDR3_DATA), //For DDR3 DQ, DQS: 1, Address, ctrl, clock - 0
// .DDR3_DATA (DDR3_DATA), //For DDR3 DQ, DQS: 1, Address, ctrl, clock - 0
.INIT_OQ (1'b0),
.INIT_TQ (1'b0),
.INTERFACE_TYPE ("DEFAULT"), //"DEFAULT", "MEMORY_DDR3"
......@@ -101,7 +101,7 @@ localparam integer DATA_WIDTH_TRI= (MODE_DDR=="TRUE")?4:1;
.SERDES_MODE ("MASTER"),
.SRVAL_OQ (1'b0),
.SRVAL_TQ (1'b0),
.TRISTATE_WIDTH (DATA_WIDTH)
.TRISTATE_WIDTH (DATA_WIDTH_TRI)
) oserdes_i (
.OFB (dout_dly),
.OQ (dout_iob),
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment