Code cleaning

git-svn-id: https://svn.code.sf.net/p/gnss-sdr/code/trunk@128 64b25241-fba3-4117-9849-534c7e92360d
This commit is contained in:
Carles Fernandez 2012-01-16 18:27:31 +00:00
parent 276f7dd2dc
commit 60da2f4336
14 changed files with 389 additions and 296 deletions

View File

@ -61,27 +61,16 @@ gps_l1_ca_pcps_acquisition_cc::gps_l1_ca_pcps_acquisition_cc(
sizeof(gr_complex) * samples_per_ms), gr_make_io_signature(0, 0,
sizeof(gr_complex) * samples_per_ms))
{
// SAMPLE COUNTER
d_sample_counter = 0;
d_sample_counter = 0; // SAMPLE COUNTER
d_active = false;
d_dump = dump;
d_queue = queue;
d_dump_filename = dump_filename;
d_freq = freq;
d_fs_in = fs_in;
d_samples_per_ms = samples_per_ms;
d_sampled_ms = sampled_ms;
d_doppler_max = doppler_max;
d_satellite = 0;
d_fft_size = d_sampled_ms * d_samples_per_ms;
d_doppler_freq = 0.0;
d_code_phase = 0;
d_mag = 0;
@ -97,6 +86,9 @@ gps_l1_ca_pcps_acquisition_cc::gps_l1_ca_pcps_acquisition_cc(
// Inverse FFT
d_ifft = new gri_fft_complex(d_fft_size, false);
d_dump = dump;
d_dump_filename = dump_filename;
DLOG(INFO) << "fs in " << d_fs_in;
DLOG(INFO) << "samples per ms " << d_samples_per_ms;
DLOG(INFO) << "doppler max " << d_doppler_max;
@ -121,6 +113,9 @@ gps_l1_ca_pcps_acquisition_cc::~gps_l1_ca_pcps_acquisition_cc()
}
}
void gps_l1_ca_pcps_acquisition_cc::set_satellite(unsigned int satellite)
{
d_satellite = satellite;
@ -136,11 +131,13 @@ void gps_l1_ca_pcps_acquisition_cc::set_satellite(unsigned int satellite)
//TODO Optimize it ! try conj()
for (unsigned int i = 0; i < d_fft_size; i++)
{
d_fft_codes[i] = std::complex<float>(
d_fft_if->get_outbuf()[i].real(),
-d_fft_if->get_outbuf()[i].imag());
//d_fft_codes[i] = std::complex<float>(
// d_fft_if->get_outbuf()[i].real(),
// -d_fft_if->get_outbuf()[i].imag());
d_fft_codes[i] = std::complex<float>(conj(d_fft_if->get_outbuf()[i]));
d_fft_codes[i] = d_fft_codes[i] / (float)d_fft_size; //to correct the scale factor introduced by FFTW
}
//memcpy(d_fft_codes,d_fft_if->get_outbuf(),sizeof(gr_complex)*d_samples_per_ms);
// std::stringstream filename;
@ -156,6 +153,10 @@ void gps_l1_ca_pcps_acquisition_cc::set_satellite(unsigned int satellite)
// //d_dump_file.write((char*)d_sine_if, n); //to be read with read_complex_binary() -> test OK
// d_dump_file.close();
}
signed int gps_l1_ca_pcps_acquisition_cc::prn_code_phase()
{
return d_code_phase;
@ -166,9 +167,9 @@ int gps_l1_ca_pcps_acquisition_cc::general_work(int noutput_items,
gr_vector_void_star &output_items)
{
/*!
/*
* By J.Arribas
* Acquisition A strategy (Kay Borre book + CFAR threshold):
* Acquisition strategy (Kay Borre book + CFAR threshold):
* 1. Compute the input signal power estimation
* 2. Doppler serial search loop
* 3. Perform the FFT-based circular convolution (parallel time search)
@ -178,159 +179,154 @@ int gps_l1_ca_pcps_acquisition_cc::general_work(int noutput_items,
*/
if (!d_active)
{
d_sample_counter += d_fft_size * noutput_items; // sample counter
consume_each(noutput_items);
}
{
d_sample_counter += d_fft_size * noutput_items; // sample counter
consume_each(noutput_items);
}
else
{
d_sample_counter += d_fft_size; // sample counter
//restart acquisition variables
d_code_phase = 0;
d_doppler_freq = 0;
d_mag = 0.0;
d_input_power = 0.0;
// initialize acquisition algorithm
int doppler;
unsigned int indext = 0;
float magt = 0.0;
float tmp_magt = 0.0;
const gr_complex *in = (const gr_complex *)input_items[0]; //Get the input samples pointer
bool positive_acquisition = false;
int acquisition_message = -1; //0=STOP_CHANNEL 1=ACQ_SUCCEES 2=ACQ_FAIL
//aux vars
unsigned int i;
std::stringstream filename;
std::streamsize n = 2 * sizeof(float) * (d_fft_size); // complex file write
LOG_AT_LEVEL(INFO) << "Channel: " << d_channel
<< " , doing acquisition of satellite: " << d_satellite
<< " ,sample stamp: " << d_sample_counter << ", threshold: "
<< d_threshold << ", doppler_max: " << d_doppler_max
<< ", doppler_step: " << d_doppler_step;
// 1- Compute the input signal power estimation
//! \TODO try norm()
for (i = 0; i < d_fft_size; i++)
{
d_input_power += std::abs(in[i]) * std::abs(in[i]);
}
d_sample_counter += d_fft_size; // sample counter
d_input_power = d_input_power / (float)d_fft_size;
//restart acquisition variables
// 2- Doppler frequency search loop
for (doppler = (int)(-d_doppler_max); doppler < (int)d_doppler_max; doppler
+= d_doppler_step)
{ // doppler search steps
//Perform the carrier wipe-off
sine_gen_complex(d_sine_if, d_freq + doppler, d_fs_in, d_fft_size);
d_code_phase = 0;
d_doppler_freq = 0;
d_mag = 0.0;
d_input_power = 0.0;
// initialize acquisition algorithm
int doppler;
unsigned int indext = 0;
float magt = 0.0;
float tmp_magt = 0.0;
const gr_complex *in = (const gr_complex *)input_items[0]; //Get the input samples pointer
bool positive_acquisition = false;
int acquisition_message = -1; //0=STOP_CHANNEL 1=ACQ_SUCCEES 2=ACQ_FAIL
//aux vars
unsigned int i;
DLOG(INFO) << "Channel: " << d_channel
<< " , doing acquisition of satellite: " << d_satellite
<< " ,sample stamp: " << d_sample_counter << ", threshold: "
<< d_threshold << ", doppler_max: " << d_doppler_max
<< ", doppler_step: " << d_doppler_step;
// 1- Compute the input signal power estimation
for (i = 0; i < d_fft_size; i++)
{
d_fft_if->get_inbuf()[i] = in[i] * d_sine_if[i];
}
{
d_input_power += std::norm(in[i]);
}
//3- Perform the FFT-based circular convolution (parallel time search)
d_fft_if->execute();
d_input_power = d_input_power / (float)d_fft_size;
//TODO Optimize me
for (i = 0; i < d_fft_size; i++)
{
d_ifft->get_inbuf()[i] = (d_fft_if->get_outbuf()[i]
* d_fft_codes[i]) / (float)d_fft_size;
}
d_ifft->execute();
// 2- Doppler frequency search loop
for (doppler = (int)(-d_doppler_max); doppler < (int)d_doppler_max; doppler += d_doppler_step)
{
// doppler search steps
//Perform the carrier wipe-off
sine_gen_complex(d_sine_if, d_freq + doppler, d_fs_in, d_fft_size);
for (i = 0; i < d_fft_size; i++)
{
d_fft_if->get_inbuf()[i] = in[i] * d_sine_if[i];
}
// old version
//x86_gr_complex_mag(d_ifft->get_outbuf(), d_fft_size); // d_ifft->get_outbuf()=|abs(·)|^2 and the array is converted from CPX->Float
//x86_float_max((float*)d_ifft->get_outbuf(), &indext, &magt,
// d_fft_size); // find max of |abs(·)|^2 -> index and magt
//3- Perform the FFT-based circular convolution (parallel time search)
d_fft_if->execute();
for (i = 0; i < d_fft_size; i++)
{
d_ifft->get_inbuf()[i] = (d_fft_if->get_outbuf()[i]
* d_fft_codes[i]) / (float)d_fft_size;
}
d_ifft->execute();
// C++ version
indext=0;
magt=0;
for (i = 0; i < d_fft_size; i++)
{
tmp_magt=std::norm(d_ifft->get_outbuf()[i]);
if (tmp_magt>magt){
magt=tmp_magt;
indext=i;
}
}
// Search maximum
indext = 0;
magt = 0;
for (i = 0; i < d_fft_size; i++)
{
tmp_magt = std::norm(d_ifft->get_outbuf()[i]);
if (tmp_magt > magt)
{
magt = tmp_magt;
indext = i;
}
}
// Record results to files
if (d_dump)
{
filename.str("");
filename << "./data/fft_" << doppler << "_.dat";
std::cout << filename.str().c_str();
std::cout << ".\n";
d_dump_file.open(filename.str().c_str(), std::ios::out
| std::ios::binary);
d_dump_file.write((char*)d_ifft->get_outbuf(), n); //write directly |abs(·)|^2 in this Doppler bin
d_dump_file.close();
}
// 4- record the maximum peak and the associated synchronization parameters
if (d_mag < magt)
{
d_mag = magt;
d_code_phase = indext;
d_doppler_freq = doppler;
}
// Record results to files
if (d_dump)
{
std::stringstream filename;
std::streamsize n = 2 * sizeof(float) * (d_fft_size); // complex file write
filename.str("");
filename << "./data/fft_" << doppler << "_.dat";
std::cout << filename.str().c_str();
std::cout << ".\n";
d_dump_file.open(filename.str().c_str(), std::ios::out
| std::ios::binary);
d_dump_file.write((char*)d_ifft->get_outbuf(), n); //write directly |abs(á)|^2 in this Doppler bin?
d_dump_file.close();
}
// 4- record the maximum peak and the associated synchronization parameters
if (d_mag < magt)
{
d_mag = magt;
d_code_phase = indext;
d_doppler_freq = doppler;
}
}
// 5- Compute the test statistics and compare to the threshold
d_test_statistics = 2 * d_fft_size * d_mag / d_input_power;
// 6- Declare positive or negative acquisition using a message queue
if (d_test_statistics > d_threshold)
{
positive_acquisition = true;
d_acq_sample_stamp = d_sample_counter;
DLOG(INFO) << "positive acquisition";
DLOG(INFO) << "satellite " << d_satellite;
DLOG(INFO) << "sample_stamp " << d_sample_counter;
DLOG(INFO) << "test statistics value " << d_test_statistics;
DLOG(INFO) << "test statistics threshold " << d_threshold;
DLOG(INFO) << "code phase " << d_code_phase;
DLOG(INFO) << "doppler " << d_doppler_freq;
DLOG(INFO) << "magnitude " << d_mag;
DLOG(INFO) << "input signal power " << d_input_power;
}
else
{
DLOG(INFO) << "negative acquisition";
DLOG(INFO) << "satellite " << d_satellite;
DLOG(INFO) << "sample_stamp " << d_sample_counter;
DLOG(INFO) << "test statistics value " << d_test_statistics;
DLOG(INFO) << "test statistics threshold " << d_threshold;
DLOG(INFO) << "code phase " << d_code_phase;
DLOG(INFO) << "doppler " << d_doppler_freq;
DLOG(INFO) << "magnitude " << d_mag;
DLOG(INFO) << "input signal power " << d_input_power;
}
d_active = false;
if (positive_acquisition)
{
acquisition_message = 1;
}
else
{
acquisition_message = 2;
}
d_channel_internal_queue->push(acquisition_message);
consume_each(1);
}
// 5- Compute the test statistics and compare to the threshold
d_test_statistics = 2*d_fft_size*d_mag / d_input_power;
// 6- Declare positive or negative acquisition using a message queue
if (d_test_statistics > d_threshold)
{ //0.004
positive_acquisition = true;
d_acq_sample_stamp = d_sample_counter;
LOG_AT_LEVEL(INFO) << "positive acquisition";
LOG_AT_LEVEL(INFO) << "satellite " << d_satellite;
LOG_AT_LEVEL(INFO) << "sample_stamp " << d_sample_counter;
LOG_AT_LEVEL(INFO) << "test statistics value "
<< d_test_statistics;
LOG_AT_LEVEL(INFO) << "test statistics threshold " << d_threshold;
LOG_AT_LEVEL(INFO) << "code phase " << d_code_phase;
LOG_AT_LEVEL(INFO) << "doppler " << d_doppler_freq;
LOG_AT_LEVEL(INFO) << "magnitude " << d_mag;
LOG_AT_LEVEL(INFO) << "input signal power " << d_input_power;
}
else
{
LOG_AT_LEVEL(INFO) << "negative acquisition";
LOG_AT_LEVEL(INFO) << "satellite " << d_satellite;
LOG_AT_LEVEL(INFO) << "sample_stamp " << d_sample_counter;
LOG_AT_LEVEL(INFO) << "test statistics value "
<< d_test_statistics;
LOG_AT_LEVEL(INFO) << "test statistics threshold " << d_threshold;
LOG_AT_LEVEL(INFO) << "code phase " << d_code_phase;
LOG_AT_LEVEL(INFO) << "doppler " << d_doppler_freq;
LOG_AT_LEVEL(INFO) << "magnitude " << d_mag;
LOG_AT_LEVEL(INFO) << "input signal power " << d_input_power;
}
d_active = false;
if (positive_acquisition)
{
acquisition_message = 1;
}
else
{
acquisition_message = 2;
}
d_channel_internal_queue->push(acquisition_message);
consume_each(1);
}
return 0;
}

View File

@ -157,11 +157,16 @@ void gps_l1_ca_tong_pcps_acquisition_cc::set_satellite(unsigned int satellite)
-d_fft_if->get_outbuf()[i].imag());
}
}
signed int gps_l1_ca_tong_pcps_acquisition_cc::prn_code_phase()
{
return d_code_phase;
}
int gps_l1_ca_tong_pcps_acquisition_cc::general_work(int noutput_items,
gr_vector_int &ninput_items, gr_vector_const_void_star &input_items,
gr_vector_void_star &output_items)

View File

@ -71,19 +71,19 @@ public:
gr_basic_block_sptr get_left_block();
gr_basic_block_sptr get_right_block();
std::string role(){ return role_;}
std::string role(){ return role_; }
std::string implementation(){ return "Channel";}
std::string implementation(){ return "Channel"; }
size_t item_size(){ return 0;}
size_t item_size(){ return 0; }
unsigned int satellite(){ return satellite_;}
unsigned int satellite(){ return satellite_; }
AcquisitionInterface* acquisition(){ return acq_;}
AcquisitionInterface* acquisition(){ return acq_; }
TrackingInterface* tracking(){ return trk_;}
TrackingInterface* tracking(){ return trk_; }
TelemetryDecoderInterface* telemetry(){ return nav_;}
TelemetryDecoderInterface* telemetry(){ return nav_; }
void start_acquisition();
void set_satellite(unsigned int satellite);

View File

@ -7,18 +7,19 @@
/*!
* The SV ID is _prn=ID -1
*/
void code_gen_conplex(std::complex<float>* _dest, int32 _prn, unsigned int _chip_shift) {
void code_gen_conplex(std::complex<float>* _dest, signed int _prn, unsigned int _chip_shift)
{
uint32 G1[1023];
uint32 G2[1023];
uint32 G1_register[10], G2_register[10];
uint32 feedback1, feedback2;
uint32 lcv, lcv2;
uint32 delay;
int32 prn = _prn-1; //Move the PRN code to fit an array indices
unsigned int G1[1023];
unsigned int G2[1023];
unsigned int G1_register[10], G2_register[10];
unsigned int feedback1, feedback2;
unsigned int lcv, lcv2;
unsigned int delay;
signed int prn = _prn-1; //Move the PRN code to fit an array indices
/* G2 Delays as defined in GPS-ISD-200D */
int32 delays[51] = {5, 6, 7, 8, 17, 18, 139, 140, 141, 251, 252, 254 ,255, 256, 257, 258, 469, 470, 471, 472,
signed int delays[51] = {5, 6, 7, 8, 17, 18, 139, 140, 141, 251, 252, 254 ,255, 256, 257, 258, 469, 470, 471, 472,
473, 474, 509, 512, 513, 514, 515, 516, 859, 860, 861, 862, 145, 175, 52, 21, 237, 235, 886, 657, 634, 762,
355, 1012, 176, 603, 130, 359, 595, 68, 386};
@ -43,8 +44,8 @@ void code_gen_conplex(std::complex<float>* _dest, int32 _prn, unsigned int _chip
for(lcv2 = 0; lcv2 < 9; lcv2++)
{
G1_register[lcv2] = G1_register[lcv2+1];
G2_register[lcv2] = G2_register[lcv2+1];
G1_register[lcv2] = G1_register[lcv2 + 1];
G2_register[lcv2] = G2_register[lcv2 + 1];
}
G1_register[9] = feedback1;
@ -53,13 +54,13 @@ void code_gen_conplex(std::complex<float>* _dest, int32 _prn, unsigned int _chip
/* Set the delay */
delay = 1023 - delays[prn];
delay+=_chip_shift;
delay += _chip_shift;
delay %= 1023;
/* Generate PRN from G1 and G2 Registers */
for(lcv = 0; lcv < 1023; lcv++)
{
_dest[lcv] = std::complex<float>(G1[(lcv+_chip_shift)%1023]^G2[delay], 0);
if(_dest[lcv].real()==0.0) //javi
_dest[lcv] = std::complex<float>(G1[(lcv + _chip_shift)%1023]^G2[delay], 0);
if(_dest[lcv].real() == 0.0) //javi
{
_dest[lcv].real(-1.0);
}
@ -75,19 +76,19 @@ void code_gen_conplex(std::complex<float>* _dest, int32 _prn, unsigned int _chip
/*!
* code_gen, generate the given prn code
* */
int32 code_gen(CPX *_dest, int32 _prn)
signed int code_gen(CPX *_dest, signed int _prn)
{
uint32 G1[1023];
uint32 G2[1023];
uint32 G1_register[10], G2_register[10];
uint32 feedback1, feedback2;
uint32 lcv, lcv2;
uint32 delay;
int32 prn = _prn-1; //Move the PRN code to fit an array indices
unsigned int G1[1023];
unsigned int G2[1023];
unsigned int G1_register[10], G2_register[10];
unsigned int feedback1, feedback2;
unsigned int lcv, lcv2;
unsigned int delay;
signed int prn = _prn-1; //Move the PRN code to fit an array indices
/* G2 Delays as defined in GPS-ISD-200D */
int32 delays[51] = {5, 6, 7, 8, 17, 18, 139, 140, 141, 251, 252, 254 ,255, 256, 257, 258, 469, 470, 471, 472,
signed int delays[51] = {5, 6, 7, 8, 17, 18, 139, 140, 141, 251, 252, 254 ,255, 256, 257, 258, 469, 470, 471, 472,
473, 474, 509, 512, 513, 514, 515, 516, 859, 860, 861, 862, 145, 175, 52, 21, 237, 235, 886, 657, 634, 762,
355, 1012, 176, 603, 130, 359, 595, 68, 386};
@ -143,15 +144,15 @@ int32 code_gen(CPX *_dest, int32 _prn)
/*!
* code_gen_complex_sampled, generate GPS L1 C/A code complex for the desired SV ID and sampled to specific sampling frequency
*/
void code_gen_complex_sampled(std::complex<float>* _dest, unsigned int _prn, int32 _fs, unsigned int _chip_shift)
void code_gen_complex_sampled(std::complex<float>* _dest, unsigned int _prn, signed int _fs, unsigned int _chip_shift)
{
// This function is based on the GNU software GPS for MATLAB in the Kay Borre book
std::complex<float> _code[1023];
int32 _samplesPerCode,_codeValueIndex;
signed int _samplesPerCode,_codeValueIndex;
float _ts;
float _tc;
const int32 _codeFreqBasis=1023000; //Hz
const int32 _codeLength=1023;
const signed int _codeFreqBasis=1023000; //Hz
const signed int _codeLength=1023;
//--- Find number of samples per spreading code ----------------------------
_samplesPerCode = round(_fs / (_codeFreqBasis / _codeLength));
@ -163,7 +164,7 @@ void code_gen_complex_sampled(std::complex<float>* _dest, unsigned int _prn, int
//std::cout<<"ts="<<_ts<<std::endl;
//std::cout<<"tc="<<_tc<<std::endl;
//std::cout<<"sv="<<_prn<<std::endl;
for (int32 i=0;i<_samplesPerCode;i++)
for (signed int i=0;i<_samplesPerCode;i++)
{
//=== Digitizing =======================================================
@ -235,10 +236,10 @@ void sine_gen_complex(std::complex<float>* _dest, double _f, double _fs, unsigne
/*----------------------------------------------------------------------------------------------*/
void sine_gen(CPX *_dest, double _f, double _fs, int32 _samps, double _p)
void sine_gen(CPX *_dest, double _f, double _fs, signed int _samps, double _p)
{
int32 lcv;
signed int lcv;
int16 c, s;
double phase, phase_step;
@ -263,10 +264,10 @@ void sine_gen(CPX *_dest, double _f, double _fs, int32 _samps, double _p)
/*!
* wipeoff_gen, generate a full scale sinusoid of frequency f with sampling frequency fs for _samps samps and put it into _dest
* */
void wipeoff_gen(MIX *_dest, double _f, double _fs, int32 _samps)
void wipeoff_gen(MIX *_dest, double _f, double _fs, signed int _samps)
{
int32 lcv;
signed int lcv;
int16 c, s;
double phase, phase_step;
@ -289,14 +290,14 @@ void wipeoff_gen(MIX *_dest, double _f, double _fs, int32 _samps)
/*----------------------------------------------------------------------------------------------*/
void downsample(CPX *_dest, CPX *_source, double _fdest, double _fsource, int32 _samps)
void downsample(CPX *_dest, CPX *_source, double _fdest, double _fsource, signed int _samps)
{
int32 lcv, k;
uint32 phase_step;
uint32 lphase, phase;
signed int lcv, k;
unsigned int phase_step;
unsigned int lphase, phase;
phase_step = (uint32)floor((double)4294967296.0*_fdest/_fsource);
phase_step = (unsigned int)floor((double)4294967296.0*_fdest/_fsource);
k = lphase = phase = 0;
@ -325,9 +326,9 @@ void downsample(CPX *_dest, CPX *_source, double _fdest, double _fsource, int32
/*!
* Gather statistics and run AGC
* */
int32 run_agc(CPX *_buff, int32 _samps, int32 _bits, int32 _scale)
signed int run_agc(CPX *_buff, signed int _samps, signed int _bits, signed int _scale)
{
int32 lcv, num;
signed int lcv, num;
int16 max, *p;
int16 val;
@ -366,11 +367,11 @@ int32 run_agc(CPX *_buff, int32 _samps, int32 _bits, int32 _scale)
/*!
* Get a rough first guess of scale value to quickly initialize agc
* */
void init_agc(CPX *_buff, int32 _samps, int32 bits, int32 *scale)
void init_agc(CPX *_buff, signed int _samps, signed int bits, signed int *scale)
{
int32 lcv;
signed int lcv;
int16 *p;
int32 max;
signed int max;
p = (int16 *)&_buff[0];

View File

@ -42,7 +42,7 @@
#include <glog/logging.h>
#include "control_message_factory.h"
#define _lrotl(X,N) ((X << N) ^ (X >> (32-N))) //!< Used in the parity check algorithm
#define _lrotl(X,N) ((X << N) ^ (X >> (32-N))) // Used in the parity check algorithm
using google::LogMessage;
@ -80,19 +80,19 @@ gps_l1_ca_telemetry_decoder_cc::gps_l1_ca_telemetry_decoder_cc(unsigned int sate
d_dump = dump;
d_satellite = satellite;
d_vector_length = vector_length;
d_samples_per_bit = 20; // it is exactly 1000*(1/50)=20
d_samples_per_bit = ( GPS_L1_CA_CODE_RATE_HZ / GPS_L1_CA_CODE_LENGTH_CHIPS ) / GPS_CA_TELEMETRY_RATE_BITS_SECOND;
d_fs_in = fs_in;
d_preamble_duration_seconds = (1.0/(float)GPS_CA_TELEMETRY_RATE_BITS_SECOND)*(float)GPS_CA_PREAMBLE_LENGTH_BITS;
d_preamble_duration_seconds = (1.0 / GPS_CA_TELEMETRY_RATE_BITS_SECOND) * GPS_CA_PREAMBLE_LENGTH_BITS;
//std::cout<<"d_preamble_duration_seconds="<<d_preamble_duration_seconds<<"\r\n";
// set the preamble
unsigned short int preambles_bits[8] = GPS_PREAMBLE;
unsigned short int preambles_bits[GPS_CA_PREAMBLE_LENGTH_BITS] = GPS_PREAMBLE;
memcpy((unsigned short int*)this->d_preambles_bits, (unsigned short int*)preambles_bits, 8*sizeof(unsigned short int));
memcpy((unsigned short int*)this->d_preambles_bits, (unsigned short int*)preambles_bits, GPS_CA_PREAMBLE_LENGTH_BITS*sizeof(unsigned short int));
// preamble bits to sampled symbols
d_preambles_symbols = (signed int*)malloc(sizeof(signed int)*8*d_samples_per_bit);
d_preambles_symbols = (signed int*)malloc(sizeof(signed int) * GPS_CA_PREAMBLE_LENGTH_BITS * d_samples_per_bit);
int n = 0;
for (int i=0; i<8; i++)
for (int i=0; i<GPS_CA_PREAMBLE_LENGTH_BITS; i++)
{
for (unsigned int j=0; j<d_samples_per_bit; j++)
{
@ -219,7 +219,7 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
{
d_GPS_FSM.Event_gps_word_preamble();
d_preamble_index = d_sample_counter;//record the preamble sample stamp
std::cout << "Preamble detection for SAT " << d_satellite<< std::endl;
std::cout << "Preamble detection for SAT " << d_satellite << std::endl;
d_symbol_accumulator = 0; //sync the symbol to bits integrator
d_symbol_accumulator_counter = 0;
d_frame_bit_index = 8;
@ -227,12 +227,12 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
}
else if (d_stat == 1) //check 6 seconds of preample separation
{
preamble_diff=abs(d_sample_counter-d_preamble_index);
preamble_diff = abs(d_sample_counter - d_preamble_index);
if (abs(preamble_diff - 6000) < 1)
{
d_GPS_FSM.Event_gps_word_preamble();
d_flag_preamble = true;
d_preamble_index = d_sample_counter;//record the preamble sample stamp (t_P)
d_preamble_index = d_sample_counter; //record the preamble sample stamp (t_P)
d_preamble_time_seconds = in[2][0] - d_preamble_duration_seconds; //record the PRN start sample index associated to the preamble
d_preamble_code_phase_seconds = in[4][0];
@ -285,11 +285,11 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
// prepare the extended frame [-2 -1 0 ... 30]
if (d_prev_GPS_frame_4bytes & 0x00000001)
{
d_GPS_frame_4bytes = d_GPS_frame_4bytes|0x40000000;
d_GPS_frame_4bytes = d_GPS_frame_4bytes | 0x40000000;
}
if (d_prev_GPS_frame_4bytes & 0x00000002)
{
d_GPS_frame_4bytes = d_GPS_frame_4bytes|0x80000000;
d_GPS_frame_4bytes = d_GPS_frame_4bytes | 0x80000000;
}
/* Check that the 2 most recently logged words pass parity. Have to first
invert the data bits according to bit 30 of the previous word. */
@ -299,7 +299,7 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
}
if (gps_l1_ca_telemetry_decoder_cc::gps_word_parityCheck(d_GPS_frame_4bytes))
{
memcpy(&d_GPS_FSM.d_GPS_frame_4bytes,&d_GPS_frame_4bytes,sizeof(char)*4);
memcpy(&d_GPS_FSM.d_GPS_frame_4bytes, &d_GPS_frame_4bytes, sizeof(char)*4);
d_GPS_FSM.d_preamble_time_ms = d_preamble_time_seconds*1000.0;
d_GPS_FSM.Event_gps_word_valid();
d_flag_parity = true;
@ -321,6 +321,8 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
// output the frame
consume_each(1); //one by one
//! \todo This has to be documented and included in the header!!!!
gps_synchro.valid_word = (d_flag_frame_sync == true and d_flag_parity == true);
gps_synchro.flag_preamble = d_flag_preamble;
gps_synchro.preamble_delay_ms = d_preamble_time_seconds*1000.0;

View File

@ -57,6 +57,24 @@ gps_l1_ca_make_telemetry_decoder_cc(unsigned int satellite, long if_freq, long f
*/
class gps_l1_ca_telemetry_decoder_cc : public gr_block {
public:
~gps_l1_ca_telemetry_decoder_cc();
void set_satellite(int satellite); //!< Set satellite PRN
void set_channel(int channel); //!< Set receiver's channel
/*!
* \brief Set the navigation queue
*/
void set_navigation_queue(concurrent_queue<Gps_Navigation_Message> *nav_queue){d_GPS_FSM.d_nav_queue=nav_queue;}
int general_work (int noutput_items, gr_vector_int &ninput_items,
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items);
void forecast (int noutput_items, gr_vector_int &ninput_items_required);
private:
friend gps_l1_ca_telemetry_decoder_cc_sptr
@ -112,20 +130,6 @@ private:
std::string d_dump_filename;
std::ofstream d_dump_file;
public:
~gps_l1_ca_telemetry_decoder_cc();
void set_satellite(int satellite);
void set_channel(int channel);
void set_navigation_queue(concurrent_queue<Gps_Navigation_Message> *nav_queue){d_GPS_FSM.d_nav_queue=nav_queue;}
int general_work (int noutput_items, gr_vector_int &ninput_items,
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items);
void forecast (int noutput_items, gr_vector_int &ninput_items_required);
};
#endif

View File

@ -83,9 +83,9 @@ public:
void set_channel_queue(concurrent_queue<int> *channel_internal_queue);
void start_tracking();
void set_acq_sample_stamp(unsigned long int sample_stamp);
private:
gps_l1_ca_dll_fll_pll_tracking_cc_sptr tracking_;

View File

@ -41,6 +41,7 @@
#include "CN_estimators.h"
#include "tracking_FLL_PLL_filter.h"
#include "control_message_factory.h"
#include "gnss_flowgraph.h"
#include <boost/lexical_cast.hpp>
#include <iostream>
#include <sstream>
@ -98,7 +99,7 @@ Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc(unsigned in
d_fs_in = fs_in;
d_vector_length = vector_length;
d_early_late_spc_chips = early_late_space_chips; // Define early-late offset (in chips)
d_dump_filename=dump_filename;
d_dump_filename = dump_filename;
// Initialize tracking variables ==========================================
d_carrier_loop_filter.set_params(fll_bw_hz,pll_bw_hz,order);
@ -129,6 +130,7 @@ Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc(unsigned in
d_CN0_SNV_dB_Hz = 0;
d_carrier_lock_fail_counter = 0;
d_carrier_lock_threshold = 5;
}
@ -142,7 +144,6 @@ void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::start_tracking()
unsigned long int acq_trk_diff_samples;
float acq_trk_diff_seconds;
acq_trk_diff_samples = d_sample_counter - d_acq_sample_stamp;//-d_vector_length;
//std::cout<<"acq_trk_diff_samples="<<acq_trk_diff_samples<<"\r\n";
acq_trk_diff_seconds = (float)acq_trk_diff_samples / (float)d_fs_in;
//doppler effect
// Fd=(C/(C+Vr))*F
@ -181,6 +182,7 @@ void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::start_tracking()
// generate local reference ALWAYS starting at chip 1 (1 sample per chip)
code_gen_conplex(&d_ca_code[1], d_satellite, 0);
d_ca_code[0] = d_ca_code[(int)GPS_L1_CA_CODE_LENGTH_CHIPS];
d_ca_code[(int)GPS_L1_CA_CODE_LENGTH_CHIPS + 1] = d_ca_code[1];
@ -229,7 +231,7 @@ void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::update_local_code()
d_prompt_code[i] = d_ca_code[associated_chip_index];
associated_chip_index = 1 + round(fmod(tcode_chips + d_early_late_spc_chips, code_length_chips));
d_late_code[i] = d_ca_code[associated_chip_index];
tcode_chips = tcode_chips+code_phase_step_chips;
tcode_chips = tcode_chips + code_phase_step_chips;
}
//d_code_phase_samples=d_code_phase_samples+(float)d_fs_in*GPS_L1_CA_CODE_LENGTH_CHIPS*(1/d_code_freq_hz-1/GPS_L1_CA_CODE_RATE_HZ);
}
@ -316,14 +318,14 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
d_sample_counter = d_sample_counter + samples_offset; //count for the processed samples
d_pull_in = false;
//std::cout<<" samples_offset="<<samples_offset<<"\r\n";
consume_each(samples_offset); //shift input to perform alignement with local replica
consume_each(samples_offset); //shift input to perform alignment with local replica
return 1;
}
// get the sample in and out pointers
const gr_complex* in = (gr_complex*) input_items[0]; //block input samples pointer
double **out = (double **) &output_items[0]; //block output streams pointer
// check for samples consistency
// check for samples consistency (this should be done before in the receiver / here only if the source is a file)
for(int i=0; i<d_current_prn_length_samples; i++)
{
if (std::isnan(in[i].real()) == true or std::isnan(in[i].imag()) == true)// or std::isinf(in[i].real())==true or std::isinf(in[i].imag())==true)
@ -353,10 +355,10 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
{
//Perform the carrier wipe-off
bb_signal_sample = in[i] * d_carr_sign[i];
// Now get early, late, and prompt values for each
d_Early += bb_signal_sample*d_early_code[i];
d_Prompt += bb_signal_sample*d_prompt_code[i];
d_Late += bb_signal_sample*d_late_code[i];
// Now get early, late, and prompt correlation values
d_Early += bb_signal_sample * d_early_code[i];
d_Prompt += bb_signal_sample * d_prompt_code[i];
d_Late += bb_signal_sample * d_late_code[i];
}
/*
@ -366,7 +368,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
code_error_chips = dll_nc_e_minus_l_normalized(d_Early,d_Late);
//compute FLL error
correlation_time_s = ((float)d_current_prn_length_samples)/(float)d_fs_in;
correlation_time_s = ((float)d_current_prn_length_samples) / (float)d_fs_in;
if (d_FLL_wait == 1)
{
d_Prompt_prev = d_Prompt;
@ -374,7 +376,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
}
else
{
d_FLL_discriminator_hz = fll_four_quadrant_atan(d_Prompt_prev, d_Prompt, 0, correlation_time_s)/(float)TWO_PI;
d_FLL_discriminator_hz = fll_four_quadrant_atan(d_Prompt_prev, d_Prompt, 0, correlation_time_s) / (float)TWO_PI;
d_Prompt_prev = d_Prompt;
d_FLL_wait = 1;
}
@ -394,7 +396,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
*/
carr_nco_hz = d_carrier_loop_filter.get_carrier_error(d_FLL_discriminator_hz, PLL_discriminator_hz, correlation_time_s);
d_carrier_doppler_hz = (float)d_if_freq + carr_nco_hz;
d_code_freq_hz = GPS_L1_CA_CODE_RATE_HZ- (((d_carrier_doppler_hz - (float)d_if_freq)*GPS_L1_CA_CODE_RATE_HZ)/GPS_L1_FREQ_HZ) - code_error_chips;
d_code_freq_hz = GPS_L1_CA_CODE_RATE_HZ - (((d_carrier_doppler_hz - (float)d_if_freq) * GPS_L1_CA_CODE_RATE_HZ) / GPS_L1_FREQ_HZ) - code_error_chips;
/*!
* \todo Improve the lock detection algorithm!
@ -409,8 +411,8 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
else
{
d_cn0_estimation_counter = 0;
d_CN0_SNV_dB_Hz=gps_l1_ca_CN0_SNV(d_Prompt_buffer, CN0_ESTIMATION_SAMPLES,d_fs_in);
d_carrier_lock_test=carrier_lock_detector(d_Prompt_buffer,CN0_ESTIMATION_SAMPLES);
d_CN0_SNV_dB_Hz = gps_l1_ca_CN0_SNV(d_Prompt_buffer, CN0_ESTIMATION_SAMPLES, d_fs_in);
d_carrier_lock_test = carrier_lock_detector(d_Prompt_buffer, CN0_ESTIMATION_SAMPLES);
// ###### TRACKING UNLOCK NOTIFICATION #####
int tracking_message;
if (d_carrier_lock_test < d_carrier_lock_threshold or d_carrier_lock_test > MINIMUM_VALID_CN0)
@ -423,7 +425,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
}
if (d_carrier_lock_fail_counter > MAXIMUM_LOCK_FAIL_COUNTER)
{
std::cout<<"Channel "<< d_channel << " loss of lock!" << std::endl;
std::cout << "Channel " << d_channel << " loss of lock!" << std::endl;
tracking_message = 3; //loss of lock
d_channel_internal_queue->push(tracking_message);
d_carrier_lock_fail_counter = 0;
@ -438,15 +440,15 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
*/
// ########### Output the tracking data to navigation and PVT ##########
// Output channel 0: Prompt correlator output Q
*out[0]=(double)d_Prompt.real();
*out[0] = (double)d_Prompt.real();
// Output channel 1: Prompt correlator output I
*out[1]=(double)d_Prompt.imag();
*out[1] = (double)d_Prompt.imag();
// Output channel 2: PRN absolute delay [s]
*out[2]=d_sample_counter_seconds;
*out[2] = d_sample_counter_seconds;
// Output channel 3: d_acc_carrier_phase_rad [rad]
*out[3]=(double)d_acc_carrier_phase_rad;
*out[3] = (double)d_acc_carrier_phase_rad;
// Output channel 4: PRN code phase [s]
*out[4]=(double)d_code_phase_samples*(1/(float)d_fs_in);
*out[4] = (double)d_code_phase_samples * (1/(float)d_fs_in);
// ########## DEBUG OUTPUT
/*!
@ -459,7 +461,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
{
d_last_seg = floor(d_sample_counter/d_fs_in);
std::cout << "Current input signal time=" << d_last_seg << " [s]" << std::endl;
std::cout << "Tracking CH "<< d_channel << " CN0=" << d_CN0_SNV_dB_Hz << " [dB-Hz]" <<std::endl;
std::cout << "Tracking CH "<< d_channel << " CN0=" << d_CN0_SNV_dB_Hz << " [dB-Hz]" << std::endl;
//std::cout<<"TRK CH "<<d_channel<<" Carrier_lock_test="<<d_carrier_lock_test<< std::endl;
//if (d_last_seg==5) d_carrier_lock_fail_counter=500; //DEBUG: force unlock!
}
@ -480,22 +482,22 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
float T_prn_samples;
float K_blk_samples;
T_chip_seconds = 1/d_code_freq_hz;
T_prn_seconds = T_chip_seconds*GPS_L1_CA_CODE_LENGTH_CHIPS;
T_prn_samples = T_prn_seconds*(float)d_fs_in;
T_prn_seconds = T_chip_seconds * GPS_L1_CA_CODE_LENGTH_CHIPS;
T_prn_samples = T_prn_seconds * (float)d_fs_in;
d_rem_code_phase_samples = d_next_rem_code_phase_samples;
K_blk_samples = T_prn_samples+d_rem_code_phase_samples;
K_blk_samples = T_prn_samples + d_rem_code_phase_samples;
// Update the current PRN delay (code phase in samples)
float T_prn_true_seconds = GPS_L1_CA_CODE_LENGTH_CHIPS/GPS_L1_CA_CODE_RATE_HZ;
float T_prn_true_samples = T_prn_true_seconds*(float)d_fs_in;
float T_prn_true_seconds = GPS_L1_CA_CODE_LENGTH_CHIPS / GPS_L1_CA_CODE_RATE_HZ;
float T_prn_true_samples = T_prn_true_seconds * (float)d_fs_in;
d_code_phase_samples = d_code_phase_samples + T_prn_samples - T_prn_true_samples;
if (d_code_phase_samples < 0)
{
d_code_phase_samples = T_prn_true_samples + d_code_phase_samples;
}
d_code_phase_samples = fmod(d_code_phase_samples, T_prn_true_samples);
d_next_prn_length_samples = round(K_blk_samples);//round to a discrete samples
d_next_rem_code_phase_samples = K_blk_samples-d_next_prn_length_samples; //rounding error
d_next_prn_length_samples = round(K_blk_samples); //round to a discrete sample
d_next_rem_code_phase_samples = K_blk_samples - d_next_prn_length_samples; //rounding error
}
else
{
@ -513,7 +515,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
// MULTIPLEXED FILE RECORDING - Record results to file
float prompt_I;
float prompt_Q;
float tmp_E,tmp_P,tmp_L;
float tmp_E, tmp_P, tmp_L;
float tmp_float;
prompt_I = d_Prompt.imag();
prompt_Q = d_Prompt.real();
@ -558,11 +560,11 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
}
catch (std::ifstream::failure e)
{
std::cout << "Exception writing trk dump file "<<e.what()<<"\r\n";
std::cout << "Exception writing trk dump file "<< e.what() << std::endl;
}
}
consume_each(d_current_prn_length_samples); // this is necesary in gr_block derivates
d_sample_counter_seconds = d_sample_counter_seconds + (((double)d_current_prn_length_samples)/(double)d_fs_in);
d_sample_counter_seconds = d_sample_counter_seconds + (((double)d_current_prn_length_samples) / (double)d_fs_in);
d_sample_counter += d_current_prn_length_samples; //count for the processed samples
return 1; //output tracking result ALWAYS even in the case of d_enable_tracking==false
}
@ -574,7 +576,7 @@ int Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::general_work (int noutput_items, gr_vecto
void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_acq_code_phase(float code_phase)
{
d_acq_code_phase_samples = code_phase;
LOG_AT_LEVEL(INFO) << "Tracking code phase set to " << d_acq_code_phase_samples;
DLOG(INFO) << "Tracking code phase set to " << d_acq_code_phase_samples;
}
@ -583,7 +585,7 @@ void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_acq_code_phase(float code_phase)
void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_acq_doppler(float doppler)
{
d_acq_carrier_doppler_hz = doppler;
LOG_AT_LEVEL(INFO) << "Tracking carrier doppler set to " << d_acq_carrier_doppler_hz;
DLOG(INFO) << "Tracking carrier doppler set to " << d_acq_carrier_doppler_hz;
}
@ -592,7 +594,7 @@ void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_acq_doppler(float doppler)
void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_satellite(unsigned int satellite)
{
d_satellite = satellite;
LOG_AT_LEVEL(INFO) << "Tracking Satellite set to " << d_satellite;
DLOG(INFO) << "Tracking Satellite set to " << d_satellite;
}
@ -600,7 +602,7 @@ void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_satellite(unsigned int satellite)
void Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc::set_channel(unsigned int channel)
{
d_channel = channel;
LOG_AT_LEVEL(INFO) << "Tracking Channel set to " << d_channel;
DLOG(INFO) << "Tracking Channel set to " << d_channel;
// ############# ENABLE DATA FILE LOG #################
if (d_dump == true)
{

View File

@ -47,6 +47,7 @@
#include <boost/thread/mutex.hpp>
#include <boost/thread/thread.hpp>
#include "concurrent_queue.h"
//#include "GPS_L1_CA.h"
class Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc;
typedef boost::shared_ptr<Gps_L1_Ca_Dll_Fll_Pll_Tracking_cc>

View File

@ -42,7 +42,7 @@
/*!
* \brief This abstract class represents an interface to a channel GNSS block.
*
* Abstract class for channel blocks. Since all its methods are virtual,
* Abstract class for channel blocks. Since all its methods are pure virtual,
* this class cannot be instantiated directly, and a subclass can only be
* instantiated directly if all inherited pure virtual methods have been
* implemented by that class or a parent class.

View File

@ -55,6 +55,7 @@ GNSSFlowgraph::GNSSFlowgraph(ConfigurationInterface *configuration,
block_factory_ = new GNSSBlockFactory();
queue_ = queue;
available_GPS_satellites_IDs_ = new std::list<unsigned int>();
init();
}
@ -109,7 +110,7 @@ void GNSSFlowgraph::connect()
{
/* Connects the blocks in the flowgraph
*
* Signal Source > Signal conditioner > Channels >> Observables >> PVT > Output filter
* Signal Source > Signal conditioner >> Channels >> Observables >> PVT > Output filter
*/
DLOG(INFO) << "Connecting flowgraph";
if (connected_)
@ -118,7 +119,7 @@ void GNSSFlowgraph::connect()
return;
}
// Connect GNSS block internally
try
{
signal_source()->connect(top_block_);
@ -131,6 +132,7 @@ void GNSSFlowgraph::connect()
return;
}
// Signal Source > Signal conditioner >
try
{
signal_conditioner()->connect(top_block_);
@ -144,6 +146,7 @@ void GNSSFlowgraph::connect()
return;
}
for (unsigned int i = 0; i < channels_count_; i++)
{
try
@ -160,6 +163,7 @@ void GNSSFlowgraph::connect()
}
}
try
{
observables()->connect(top_block_);
@ -172,6 +176,7 @@ void GNSSFlowgraph::connect()
return;
}
// Signal Source > Signal conditioner >> Channels >> Observables > PVT
try
{
pvt()->connect(top_block_);
@ -184,6 +189,7 @@ void GNSSFlowgraph::connect()
return;
}
// Signal Source > Signal conditioner >> Channels >> Observables > PVT > Output Filter
try
{
output_filter()->connect(top_block_);
@ -198,6 +204,7 @@ void GNSSFlowgraph::connect()
DLOG(INFO) << "blocks connected internally";
// Signal Source > Signal conditioner >
try
{
top_block_->connect(signal_source()->get_right_block(), 0,
@ -213,6 +220,7 @@ void GNSSFlowgraph::connect()
}
DLOG(INFO) << "Signal source connected to signal conditioner";
// Signal Source > Signal conditioner >> channels_count_ number of Channels in parallel
for (unsigned int i = 0; i < channels_count_; i++)
{
try
@ -231,6 +239,7 @@ void GNSSFlowgraph::connect()
DLOG(INFO) << "signal conditioner connected to channel " << i;
// Signal Source > Signal conditioner >> Channels >> Observables
try
{
top_block_->connect(channel(i)->get_right_block(), 0,
@ -388,10 +397,13 @@ GNSSBlockInterface* GNSSFlowgraph::output_filter()
return blocks_->at(4);
}
void GNSSFlowgraph::init()
{
/*
* Instantiates the receiver blocks
* Instantiates the receiver blocks
*/
blocks_->push_back(
block_factory_->GetSignalSource(configuration_, queue_));

View File

@ -40,6 +40,7 @@
#include <queue>
#include <gnuradio/gr_top_block.h>
#include <gnuradio/gr_msg_queue.h>
#include "GPS_L1_CA.h"
class GNSSBlockInterface;
class ChannelInterface;

View File

@ -32,19 +32,21 @@
#ifndef GNSS_SDR_GPS_L1_CA_H_
#define GNSS_SDR_GPS_L1_CA_H_
#include <complex>
// Physical constants
const double GPS_C_m_s = 299792458.0; //!< The speed of light, [m/s]
const double GPS_C_m_ms = 299792.4580; //!< The speed of light, [m/ms]
const double GPS_PI = 3.1415926535898; //!< Pi as defined in IS-GPS-200E
const double OMEGA_EARTH_DOT = 7.2921151467e-5; //!< Earth rotation rate, [rad/s]
const double GM = 3.986005e14; //!< Universal gravitational constant times the mass of the Earth, [m^3/s^2]
const double F = -4.442807633e-10; //!< Constant, [s/(m)^(1/2)]
const double GPS_PI = 3.1415926535898; //!< Pi as defined in IS-GPS-200E
const double OMEGA_EARTH_DOT = 7.2921151467e-5; //!< Earth rotation rate, [rad/s]
const double GM = 3.986005e14; //!< Universal gravitational constant times the mass of the Earth, [m^3/s^2]
const double F = -4.442807633e-10; //!< Constant, [s/(m)^(1/2)]
// carrier and code frequencies
const float GPS_L1_FREQ_HZ = 1.57542e9; //!< L1 [Hz]
const float GPS_L1_CA_CODE_RATE_HZ = 1.023e6; //!< GPS L1 C/A code rate [chips/s]
const float GPS_L1_CA_CODE_LENGTH_CHIPS = 1023.0; //!< GPS L1 C/A code length [chips]
const double GPS_L1_FREQ_HZ = 1.57542e9; //!< L1 [Hz]
const double GPS_L1_CA_CODE_RATE_HZ = 1.023e6; //!< GPS L1 C/A code rate [chips/s]
const double GPS_L1_CA_CODE_LENGTH_CHIPS = 1023.0; //!< GPS L1 C/A code length [chips]
/*!
* \brief Maximum Time-Of-Arrival (TOA) difference between satellites for a receiver operated on Earth surface is 20 ms
@ -54,19 +56,19 @@ const float GPS_L1_CA_CODE_LENGTH_CHIPS = 1023.0; //!< GPS L1 C/A code length
* [1] J. Bao-Yen Tsui, Fundamentals of Global Positioning System Receivers. A Software Approach, John Wiley & Sons,
* Inc., Hoboken, NJ, 2nd edition, 2005.
*/
const double MAX_TOA_DELAY_MS=20;
const double MAX_TOA_DELAY_MS = 20;
#define NAVIGATION_SOLUTION_RATE_MS 1000 // this cannot go here
const float GPS_STARTOFFSET_ms= 68.802; //[ms] Initial sign. travel time (this cannot go here)
const float GPS_STARTOFFSET_ms = 68.802; //[ms] Initial sign. travel time (this cannot go here)
// NAVIGATION MESSAGE DEMODULATION AND DECODING
#define GPS_PREAMBLE {1, 0, 0, 0, 1, 0, 1, 1}
#define GPS_CA_PREAMBLE_LENGTH_BITS 8
#define GPS_CA_TELEMETRY_RATE_BITS_SECOND 50 //!< NAV message bit rate [bits/s]
const int GPS_CA_PREAMBLE_LENGTH_BITS = 8;
const int GPS_CA_TELEMETRY_RATE_BITS_SECOND = 50; //!< NAV message bit rate [bits/s]
#define GPS_WORD_LENGTH 4 // CRC + GPS WORD (-2 -1 0 ... 29) Bits = 4 bytes
#define GPS_SUBFRAME_LENGTH 40 // GPS_WORD_LENGTH x 10 = 40 bytes
const int GPS_SUBFRAME_BITS=300; //!< Number of bits per subframe in the NAV message [bits]
@ -81,14 +83,15 @@ const int GPS_WORD_BITS=30; //!< Number of bits per word in t
/*!
* \brief Navigation message bits slice structure: A portion of bits is indicated by
* the start position inside the subframe and the length in number of bits */
typedef struct bits_slice{
int position;
int length;
bits_slice(int p,int l)
{
position=p;
length=l;
}
typedef struct bits_slice
{
int position;
int length;
bits_slice(int p,int l)
{
position=p;
length=l;
}
} bits_slice;
@ -341,6 +344,72 @@ const bits_slice HEALTH_SV24[]={{259,6}};
inline void ca_code_generator_complex(std::complex<float>* _dest, signed int _prn, unsigned int _chip_shift)
{
unsigned int G1[1023];
unsigned int G2[1023];
unsigned int G1_register[10], G2_register[10];
unsigned int feedback1, feedback2;
unsigned int lcv, lcv2;
unsigned int delay;
signed int prn = _prn-1; //Move the PRN code to fit an array indices
/* G2 Delays as defined in IS-GPS-200E */
signed int delays[32] = {5, 6, 7, 8, 17, 18, 139, 140, 141, 251,
252, 254, 255, 256, 257, 258, 469, 470, 471, 472,
473, 474, 509, 512, 513, 514, 515, 516, 859, 860,
861, 862};
// PRN sequences 33 through 37 are reserved for other uses (e.g. ground transmitters)
/* A simple error check */
if((prn < 0) || (prn > 32))
return;
for(lcv = 0; lcv < 10; lcv++)
{
G1_register[lcv] = 1;
G2_register[lcv] = 1;
}
/* Generate G1 & G2 Register */
for(lcv = 0; lcv < 1023; lcv++)
{
G1[lcv] = G1_register[0];
G2[lcv] = G2_register[0];
feedback1 = G1_register[7]^G1_register[0];
feedback2 = (G2_register[8] + G2_register[7] + G2_register[4] + G2_register[2] + G2_register[1] + G2_register[0]) & 0x1;
for(lcv2 = 0; lcv2 < 9; lcv2++)
{
G1_register[lcv2] = G1_register[lcv2 + 1];
G2_register[lcv2] = G2_register[lcv2 + 1];
}
G1_register[9] = feedback1;
G2_register[9] = feedback2;
}
/* Set the delay */
delay = 1023 - delays[prn];
delay += _chip_shift;
delay %= 1023;
/* Generate PRN from G1 and G2 Registers */
for(lcv = 0; lcv < 1023; lcv++)
{
_dest[lcv] = std::complex<float>(G1[(lcv + _chip_shift)%1023]^G2[delay], 0);
if(_dest[lcv].real() == 0.0) //javi
{
_dest[lcv].real(-1.0);
}
delay++;
delay %= 1023;
//std::cout<<_dest[lcv].real(); //OK
}
}
#endif /* GNSS_SDR_GPS_L1_CA_H_ */

View File

@ -70,7 +70,7 @@ private:
public:
//broadcast orbit 1
double d_TOW;
double d_TOW; //!< Time of GPS Week [s]
double d_IODE_SF2;
double d_IODE_SF3;
double d_Crs; //!< Amplitude of the Sine Harmonic Correction Term to the Orbit Radius [m]