Other Parts Discussed in Thread: HSMC-ADC-BRIDGE, ADS6445
Hello,
I am using an ADS6445 EVM board connected to a Terasic DE4 FPGA board. The connection is through the HSMC-ADC-BRIDGE REV C. The ADC 125 MHz reference clock is generated using a CDCE6005 EVM board.
The ADC samples at 125 MSPS and communicates the digital data using 7 times serialization so the bit rate is 875 MHz. The data clock is 437.5 MHz. I am powering the EVM board using a 3.3V regulator.
In the FPGA I am using the ALTLVDS_RX megafunction to deserialize the data. This is fed the data clock and generates a core clock signal at 125 MHz. This core clock is used to clock the digital logic.
I am sending the digital data to an on-chip RAM which I can easily read using Altera's In-system memory content editor.
To test my setup, I put a 1 MHz sine signal into the ADC and plotted the data in Matlab. This data is shown in the figure. I am certain those spikes are caused by bit errors because their offset from the sine curve is almost always a power of two.
Does anyone have any suggestions as to how to get this thing working? I need this data to be reliable otherwise my project will be put under severe limitations. Thank you!
My timing constraints are as follows:
=======================================================================================
# Clocks from ADC
create_clock -name rx_data_clk_a -period 2.285714 -waveform {0 1.142857} [get_ports {a_CLKIN_p2}]
# Virtual clocks with waveform edges at the data edges
create_clock -name adc_launch_clk_a -period 2.285714 -waveform {0.571429 1.714286}
create_clock -name adc_launch_clk_a -period 2.285714 -waveform {0.571429 1.714286}
derive_pll_clocks
derive_clock_uncertainty
set_input_delay -clock { adc_launch_clk_a } -max 0.35 [get_ports {a_RX_p[*]*}]
set_input_delay -clock { adc_launch_clk_a } -min -0.35 [get_ports {a_RX_p[*]*}]
set_input_delay -clock { adc_launch_clk_a } -max 0.35 [get_ports {a_RX_p[*]*}] -clock_fall -add_delay
set_input_delay -clock { adc_launch_clk_a } -min -0.35 [get_ports {a_RX_p[*]*}] -clock_fall -add_delay
=======================================================================================
My Verilog code looks like the following:
=======================================================================================
/*********************************
******* PULL DATA FROM ADC *******
**********************************/
///////////////// RECIEVE /////////////////
// Define rx connections
wire rx_core_clk_a;
wire frame_clk_a;
wire rx_data_clk_a;
wire [7:0] rx_in_a;
wire rx_locked_a;
// Assign rx connections
assign frame_clk_a = a_RX_p[16];
assign rx_data_clk_a = a_CLKIN_p2;
assign rx_in_a = a_RX_p[11:4];
deserialize deserialize_inst (
.rx_in ( {frame_clk_a, rx_in_a} ),
.rx_inclock ( rx_data_clk_a ),
.rx_locked ( rx_locked_a ),
.rx_out ( rx_out_a ),
.rx_outclock ( rx_core_clk_a )
);
/////////////////////////////////////////////////
////////////// PUSH DATA TO MEMORY //////////////
/////////////////////////////////////////////////
//////////// CREATE ADDRESS COUNTER ////////////////
reg [11:0] cnt;
wire inc_cnt;
always_ff @(posedge rx_core_clk_a, negedge BUTTON[1]) begin
if(!BUTTON[1])
cnt <= 0;
else if(inc_cnt)
cnt <= cnt + 1;
else
cnt <= cnt;
end
assign inc_cnt = (cnt != 12'h0fff);
////////// INSTANTIATE RAM MEGAFUNCTION ///////////
// declare signals
wire [11:0] address;
wire [255:0] write_data;
wire rden;
wire wren;
wire [255:0] read_data;
// assign signals
assign address = cnt;
assign rden = 1'b0;
assign wren = inc_cnt; //1'b1;
ram ram_inst (
.address ( address ),
.clock ( rx_core_clk_a ),
.data ( {rx_locked_a, rx_out_a } ),
.rden ( rden ),
.wren ( wren ),
.q ( read_data )
);
=======================================================================================
