143 lines
4.8 KiB
Systemverilog
143 lines
4.8 KiB
Systemverilog
import definitions::*;
|
|
|
|
/*
|
|
* Builds one coherent tracking measurement for every decoded 20 ms NAV bit.
|
|
*
|
|
* The payload is registered in the tracking clock domain and remains unchanged
|
|
* until the next measurement. measurement_valid_o remains asserted for the
|
|
* rest of bit_valid_i so the APB clock can synchronize it without a CDC FIFO.
|
|
*/
|
|
module tracking_measurement #(
|
|
parameter int unsigned CORR_WL = TRCK_CORR_WL,
|
|
parameter int unsigned ENERGY_WL = (2 * TRCK_CORR_WL) + 1,
|
|
parameter int unsigned SUM_WL = TRCK_CORR_WL + $clog2(MS_PER_BIT),
|
|
parameter int unsigned WBP_WL = ENERGY_WL + $clog2(MS_PER_BIT),
|
|
parameter int unsigned COUNT_WL = $clog2(MS_PER_BIT + 1),
|
|
parameter int unsigned CARRIER_WL =
|
|
ACQUIRED_FREQ_IL + TRCK_CARR_NCO_FREQ_FL,
|
|
parameter int unsigned SNAPSHOT_DELAY_CYCLES = 4
|
|
) (
|
|
input logic clk,
|
|
input logic rstn,
|
|
input logic bit_valid_i,
|
|
input logic nav_bit_i,
|
|
input logic [ABS_SAMPLE_CNTR_WL-1:0] absolute_sample_i,
|
|
input logic [REM_CODE_PH_I_WL-1:0] rem_code_phase_i,
|
|
input logic signed [CARRIER_WL-1:0] carrier_freq_q7_i,
|
|
input logic corr_valid_i,
|
|
input logic signed [CORR_WL-1:0] i_prompt_i,
|
|
input logic signed [CORR_WL-1:0] q_prompt_i,
|
|
input logic prompt_energy_valid_i,
|
|
input logic [ENERGY_WL-1:0] prompt_energy_i,
|
|
|
|
output logic measurement_valid_o,
|
|
output logic nav_bit_o,
|
|
output logic [ABS_SAMPLE_CNTR_WL-1:0] absolute_sample_o,
|
|
output logic [REM_CODE_PH_I_WL-1:0] rem_code_phase_o,
|
|
output logic signed [CARRIER_WL-1:0] carrier_freq_q7_o,
|
|
output logic signed [SUM_WL-1:0] cn0_sum_i_o,
|
|
output logic signed [SUM_WL-1:0] cn0_sum_q_o,
|
|
output logic [WBP_WL-1:0] cn0_wbp_o,
|
|
output logic [COUNT_WL-1:0] cn0_sample_count_o,
|
|
output logic [15:0] sequence_o
|
|
);
|
|
|
|
localparam int unsigned DELAY_WL =
|
|
(SNAPSHOT_DELAY_CYCLES < 2) ? 1 : $clog2(SNAPSHOT_DELAY_CYCLES + 1);
|
|
|
|
logic bit_valid_r;
|
|
logic measurement_armed;
|
|
logic snapshot_pending;
|
|
logic [DELAY_WL-1:0] snapshot_delay;
|
|
logic signed [SUM_WL-1:0] sum_i;
|
|
logic signed [SUM_WL-1:0] sum_q;
|
|
logic [WBP_WL-1:0] wbp;
|
|
logic [COUNT_WL-1:0] sample_count;
|
|
|
|
wire bit_epoch = bit_valid_i && !bit_valid_r;
|
|
|
|
always_ff @(posedge clk or negedge rstn) begin
|
|
if(!rstn) begin
|
|
bit_valid_r <= 1'b0;
|
|
measurement_armed <= 1'b0;
|
|
snapshot_pending <= 1'b0;
|
|
snapshot_delay <= '0;
|
|
sum_i <= '0;
|
|
sum_q <= '0;
|
|
wbp <= '0;
|
|
sample_count <= '0;
|
|
measurement_valid_o <= 1'b0;
|
|
nav_bit_o <= 1'b0;
|
|
absolute_sample_o <= '0;
|
|
rem_code_phase_o <= '0;
|
|
carrier_freq_q7_o <= '0;
|
|
cn0_sum_i_o <= '0;
|
|
cn0_sum_q_o <= '0;
|
|
cn0_wbp_o <= '0;
|
|
cn0_sample_count_o <= '0;
|
|
sequence_o <= '0;
|
|
end else begin
|
|
bit_valid_r <= bit_valid_i;
|
|
|
|
if(!bit_valid_i) begin
|
|
measurement_valid_o <= 1'b0;
|
|
end
|
|
|
|
if(measurement_armed && corr_valid_i) begin
|
|
sum_i <= sum_i + $signed(i_prompt_i);
|
|
sum_q <= sum_q + $signed(q_prompt_i);
|
|
sample_count <= sample_count + 1'b1;
|
|
end
|
|
if(measurement_armed && prompt_energy_valid_i) begin
|
|
wbp <= wbp + prompt_energy_i;
|
|
end
|
|
|
|
/*
|
|
* The first synchronized NAV-bit edge defines the integration phase.
|
|
* Samples gathered before that edge are intentionally discarded.
|
|
*/
|
|
if(bit_epoch) begin
|
|
if(!measurement_armed) begin
|
|
measurement_armed <= 1'b1;
|
|
sum_i <= '0;
|
|
sum_q <= '0;
|
|
wbp <= '0;
|
|
sample_count <= '0;
|
|
end else begin
|
|
snapshot_pending <= 1'b1;
|
|
snapshot_delay <= DELAY_WL'(SNAPSHOT_DELAY_CYCLES);
|
|
end
|
|
end
|
|
|
|
/*
|
|
* Prompt energy is pipelined in lock_detector. There is almost one
|
|
* millisecond before the next correlator result, so waiting a few
|
|
* tracking clocks includes the last energy term without mixing epochs.
|
|
*/
|
|
if(snapshot_pending) begin
|
|
if(snapshot_delay != 0) begin
|
|
snapshot_delay <= snapshot_delay - 1'b1;
|
|
end else begin
|
|
snapshot_pending <= 1'b0;
|
|
measurement_valid_o <= 1'b1;
|
|
nav_bit_o <= nav_bit_i;
|
|
absolute_sample_o <= absolute_sample_i;
|
|
rem_code_phase_o <= rem_code_phase_i;
|
|
carrier_freq_q7_o <= carrier_freq_q7_i;
|
|
cn0_sum_i_o <= sum_i;
|
|
cn0_sum_q_o <= sum_q;
|
|
cn0_wbp_o <= wbp;
|
|
cn0_sample_count_o <= sample_count;
|
|
sequence_o <= sequence_o + 1'b1;
|
|
|
|
sum_i <= '0;
|
|
sum_q <= '0;
|
|
wbp <= '0;
|
|
sample_count <= '0;
|
|
end
|
|
end
|
|
end
|
|
end
|
|
|
|
endmodule
|