`default_nettype none module max2771_capture #( parameter bit CAPTURE_RISING = 1'b1 ) ( input wire logic rf_clk_pmod, input wire logic rst, input wire logic [3:0] rf_data_pmod, input wire logic fifo_full, output wire logic fifo_w_clk, output wire logic fifo_w_en, output wire logic [68:0] fifo_w_data, output logic [63:0] samples_seen, output logic [63:0] samples_captured, output logic [63:0] samples_dropped, output logic loss_latched, output logic sample_activity_pulse ); // The inversion selects the physical falling edge while retaining a single // positive-edge sequential implementation. Vivado maps clock inversion onto // the clocking resource; fifo_w_clk clocks both capture bookkeeping and FIFO. assign fifo_w_clk = CAPTURE_RISING ? rf_clk_pmod : ~rf_clk_pmod; (* IOB = "TRUE" *) logic [3:0] sample_iob; logic [63:0] sample_index_iob; logic sample_valid; logic discontinuity_pending; assign fifo_w_en = sample_valid; // Entry format: loss immediately before this sample, absolute index, nibble. assign fifo_w_data = {discontinuity_pending, sample_index_iob, sample_iob}; always_ff @(posedge fifo_w_clk or posedge rst) begin if (rst) begin sample_iob <= 4'd0; sample_index_iob <= 64'd0; sample_valid <= 1'b0; discontinuity_pending <= 1'b0; samples_seen <= 64'd0; samples_captured <= 64'd0; samples_dropped <= 64'd0; loss_latched <= 1'b0; sample_activity_pulse <= 1'b0; end else begin // IOB input register: no combinational data path reaches the FIFO. sample_iob <= rf_data_pmod; sample_index_iob <= samples_seen; sample_valid <= 1'b1; samples_seen <= samples_seen + 64'd1; sample_activity_pulse <= 1'b0; if (samples_seen[15:0] == 16'hffff) sample_activity_pulse <= 1'b1; if (sample_valid) begin if (fifo_full) begin samples_dropped <= samples_dropped + 64'd1; discontinuity_pending <= 1'b1; loss_latched <= 1'b1; end else begin samples_captured <= samples_captured + 64'd1; discontinuity_pending <= 1'b0; end end end end endmodule `default_nettype wire