mirror of
https://github.com/gnss-sdr/gnss-sdr
synced 2024-12-15 20:50:33 +00:00
Merge branch 'next' of https://github.com/gnss-sdr/gnss-sdr into next
This commit is contained in:
commit
208c83dd41
22
README.md
22
README.md
@ -6,20 +6,20 @@
|
|||||||
|
|
||||||
This program is a software-defined receiver which is able to process (that is, to perform detection, synchronization, demodulation and decoding of the navigation message, computation of observables and, finally, computation of position fixes) the following Global Navigation Satellite System's signals:
|
This program is a software-defined receiver which is able to process (that is, to perform detection, synchronization, demodulation and decoding of the navigation message, computation of observables and, finally, computation of position fixes) the following Global Navigation Satellite System's signals:
|
||||||
|
|
||||||
In the L1 band (centered at 1575.42 MHz):
|
In the L1 band:
|
||||||
- 🛰 GPS L1 C/A :white_check_mark:
|
- 🛰 GPS L1 C/A (centered at 1575.42 MHz) :white_check_mark:
|
||||||
- 🛰 Galileo E1b/c :white_check_mark:
|
- 🛰 Galileo E1b/c (centered at 1575.42 MHz) :white_check_mark:
|
||||||
- 🛰 GLONASS L1 C/A :white_check_mark:
|
- 🛰 GLONASS L1 C/A (centered at 1601.72 MHz) :white_check_mark:
|
||||||
|
|
||||||
In the L2 band (centered at 1227.60 MHz):
|
In the L2 band:
|
||||||
- 🛰 GPS L2C :white_check_mark:
|
- 🛰 GPS L2C (centered at 1227.60 MHz) :white_check_mark:
|
||||||
- 🛰 GLONASS L2 C/A :white_check_mark:
|
- 🛰 GLONASS L2 C/A (centered at 1246 MHz) :white_check_mark:
|
||||||
|
|
||||||
In the L5 band (centered at 1176.45 MHz):
|
In the L5 band:
|
||||||
- 🛰 GPS L5 :white_check_mark:
|
- 🛰 GPS L5 (centered at 1176.45 MHz) :white_check_mark:
|
||||||
- 🛰 Galileo E5a :white_check_mark:
|
- 🛰 Galileo E5a (centered at 1176.45 MHz) :white_check_mark:
|
||||||
|
|
||||||
GNSS-SDR provides interfaces for a wide range of radio frequency front-ends, generates processing outputs in standard formats, allows for the full inspection of the whole signal processing chain, and offers a framework for the development of new features. Please visit [https://gnss-sdr.org](https://gnss-sdr.org "GNSS-SDR website") for more information about this open source software-defined GNSS receiver.
|
GNSS-SDR provides interfaces for a wide range of radio frequency front-ends and raw sample file formats, generates processing outputs in standard formats, allows for the full inspection of the whole signal processing chain, and offers a framework for the development of new features. Please visit [https://gnss-sdr.org](https://gnss-sdr.org "GNSS-SDR website") for more information about this open source software-defined GNSS receiver.
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
@ -18,7 +18,4 @@
|
|||||||
|
|
||||||
add_subdirectory(adapters)
|
add_subdirectory(adapters)
|
||||||
add_subdirectory(gnuradio_blocks)
|
add_subdirectory(gnuradio_blocks)
|
||||||
if(ENABLE_FPGA)
|
add_subdirectory(libs)
|
||||||
add_subdirectory(libs)
|
|
||||||
endif(ENABLE_FPGA)
|
|
||||||
|
|
||||||
|
@ -65,4 +65,4 @@ file(GLOB ACQ_ADAPTER_HEADERS "*.h")
|
|||||||
list(SORT ACQ_ADAPTER_HEADERS)
|
list(SORT ACQ_ADAPTER_HEADERS)
|
||||||
add_library(acq_adapters ${ACQ_ADAPTER_SOURCES} ${ACQ_ADAPTER_HEADERS})
|
add_library(acq_adapters ${ACQ_ADAPTER_SOURCES} ${ACQ_ADAPTER_HEADERS})
|
||||||
source_group(Headers FILES ${ACQ_ADAPTER_HEADERS})
|
source_group(Headers FILES ${ACQ_ADAPTER_HEADERS})
|
||||||
target_link_libraries(acq_adapters gnss_sp_libs gnss_sdr_flags acq_gr_blocks ${Boost_LIBRARIES} ${GNURADIO_RUNTIME_LIBRARIES} ${GNURADIO_BLOCKS_LIBRARIES})
|
target_link_libraries(acq_adapters acquisition_lib gnss_sp_libs gnss_sdr_flags acq_gr_blocks ${Boost_LIBRARIES} ${GNURADIO_RUNTIME_LIBRARIES} ${GNURADIO_BLOCKS_LIBRARIES})
|
||||||
|
@ -34,6 +34,7 @@
|
|||||||
#include "galileo_e1_signal_processing.h"
|
#include "galileo_e1_signal_processing.h"
|
||||||
#include "Galileo_E1.h"
|
#include "Galileo_E1.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <boost/lexical_cast.hpp>
|
#include <boost/lexical_cast.hpp>
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
@ -45,7 +46,7 @@ GalileoE1PcpsAmbiguousAcquisition::GalileoE1PcpsAmbiguousAcquisition(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters;
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "./data/acquisition.dat";
|
std::string default_dump_filename = "./data/acquisition.dat";
|
||||||
|
@ -33,6 +33,7 @@
|
|||||||
#include "galileo_e5_signal_processing.h"
|
#include "galileo_e5_signal_processing.h"
|
||||||
#include "Galileo_E5a.h"
|
#include "Galileo_E5a.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <boost/lexical_cast.hpp>
|
#include <boost/lexical_cast.hpp>
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
@ -44,7 +45,7 @@ using google::LogMessage;
|
|||||||
GalileoE5aPcpsAcquisition::GalileoE5aPcpsAcquisition(ConfigurationInterface* configuration,
|
GalileoE5aPcpsAcquisition::GalileoE5aPcpsAcquisition(ConfigurationInterface* configuration,
|
||||||
std::string role, unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
std::string role, unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters = Acq_Conf();
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "../data/acquisition.dat";
|
std::string default_dump_filename = "../data/acquisition.dat";
|
||||||
|
@ -35,6 +35,7 @@
|
|||||||
#include "configuration_interface.h"
|
#include "configuration_interface.h"
|
||||||
#include "glonass_l1_signal_processing.h"
|
#include "glonass_l1_signal_processing.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include "GLONASS_L1_L2_CA.h"
|
#include "GLONASS_L1_L2_CA.h"
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
@ -46,7 +47,7 @@ GlonassL1CaPcpsAcquisition::GlonassL1CaPcpsAcquisition(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters = Acq_Conf();
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "./data/acquisition.dat";
|
std::string default_dump_filename = "./data/acquisition.dat";
|
||||||
|
@ -35,6 +35,7 @@
|
|||||||
#include "glonass_l2_signal_processing.h"
|
#include "glonass_l2_signal_processing.h"
|
||||||
#include "GLONASS_L1_L2_CA.h"
|
#include "GLONASS_L1_L2_CA.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
|
|
||||||
@ -45,7 +46,7 @@ GlonassL2CaPcpsAcquisition::GlonassL2CaPcpsAcquisition(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters = Acq_Conf();
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "./data/acquisition.dat";
|
std::string default_dump_filename = "./data/acquisition.dat";
|
||||||
|
@ -38,6 +38,7 @@
|
|||||||
#include "gps_sdr_signal_processing.h"
|
#include "gps_sdr_signal_processing.h"
|
||||||
#include "GPS_L1_CA.h"
|
#include "GPS_L1_CA.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
|
|
||||||
@ -48,7 +49,7 @@ GpsL1CaPcpsAcquisition::GpsL1CaPcpsAcquisition(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters = Acq_Conf();
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "./data/acquisition.dat";
|
std::string default_dump_filename = "./data/acquisition.dat";
|
||||||
|
@ -36,6 +36,7 @@
|
|||||||
#include "gps_l2c_signal.h"
|
#include "gps_l2c_signal.h"
|
||||||
#include "GPS_L2C.h"
|
#include "GPS_L2C.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
|
|
||||||
@ -46,7 +47,7 @@ GpsL2MPcpsAcquisition::GpsL2MPcpsAcquisition(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters = Acq_Conf();
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "./data/acquisition.dat";
|
std::string default_dump_filename = "./data/acquisition.dat";
|
||||||
|
@ -36,6 +36,7 @@
|
|||||||
#include "gps_l5_signal.h"
|
#include "gps_l5_signal.h"
|
||||||
#include "GPS_L5.h"
|
#include "GPS_L5.h"
|
||||||
#include "gnss_sdr_flags.h"
|
#include "gnss_sdr_flags.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <boost/math/distributions/exponential.hpp>
|
#include <boost/math/distributions/exponential.hpp>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
|
|
||||||
@ -46,7 +47,7 @@ GpsL5iPcpsAcquisition::GpsL5iPcpsAcquisition(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
pcpsconf_t acq_parameters;
|
Acq_Conf acq_parameters = Acq_Conf();
|
||||||
configuration_ = configuration;
|
configuration_ = configuration;
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
std::string default_dump_filename = "./data/acquisition.dat";
|
std::string default_dump_filename = "./data/acquisition.dat";
|
||||||
|
@ -45,13 +45,13 @@
|
|||||||
|
|
||||||
using google::LogMessage;
|
using google::LogMessage;
|
||||||
|
|
||||||
pcps_acquisition_sptr pcps_make_acquisition(pcpsconf_t conf_)
|
pcps_acquisition_sptr pcps_make_acquisition(const Acq_Conf& conf_)
|
||||||
{
|
{
|
||||||
return pcps_acquisition_sptr(new pcps_acquisition(conf_));
|
return pcps_acquisition_sptr(new pcps_acquisition(conf_));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
pcps_acquisition::pcps_acquisition(pcpsconf_t conf_) : gr::block("pcps_acquisition",
|
pcps_acquisition::pcps_acquisition(const Acq_Conf& conf_) : gr::block("pcps_acquisition",
|
||||||
gr::io_signature::make(1, 1, conf_.it_size * conf_.sampled_ms * conf_.samples_per_ms * (conf_.bit_transition_flag ? 2 : 1)),
|
gr::io_signature::make(1, 1, conf_.it_size * conf_.sampled_ms * conf_.samples_per_ms * (conf_.bit_transition_flag ? 2 : 1)),
|
||||||
gr::io_signature::make(0, 0, conf_.it_size * conf_.sampled_ms * conf_.samples_per_ms * (conf_.bit_transition_flag ? 2 : 1)))
|
gr::io_signature::make(0, 0, conf_.it_size * conf_.sampled_ms * conf_.samples_per_ms * (conf_.bit_transition_flag ? 2 : 1)))
|
||||||
{
|
{
|
||||||
@ -60,6 +60,7 @@ pcps_acquisition::pcps_acquisition(pcpsconf_t conf_) : gr::block("pcps_acquisiti
|
|||||||
acq_parameters = conf_;
|
acq_parameters = conf_;
|
||||||
d_sample_counter = 0; // SAMPLE COUNTER
|
d_sample_counter = 0; // SAMPLE COUNTER
|
||||||
d_active = false;
|
d_active = false;
|
||||||
|
d_positive_acq = 0;
|
||||||
d_state = 0;
|
d_state = 0;
|
||||||
d_old_freq = 0;
|
d_old_freq = 0;
|
||||||
d_well_count = 0;
|
d_well_count = 0;
|
||||||
@ -121,6 +122,7 @@ pcps_acquisition::pcps_acquisition(pcpsconf_t conf_) : gr::block("pcps_acquisiti
|
|||||||
}
|
}
|
||||||
grid_ = arma::fmat();
|
grid_ = arma::fmat();
|
||||||
d_step_two = false;
|
d_step_two = false;
|
||||||
|
d_dump_number = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -335,6 +337,81 @@ void pcps_acquisition::send_negative_acquisition()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
void pcps_acquisition::dump_results(int effective_fft_size)
|
||||||
|
{
|
||||||
|
d_dump_number++;
|
||||||
|
std::string filename = acq_parameters.dump_filename;
|
||||||
|
filename.append("_");
|
||||||
|
filename.append(1, d_gnss_synchro->System);
|
||||||
|
filename.append("_");
|
||||||
|
filename.append(1, d_gnss_synchro->Signal[0]);
|
||||||
|
filename.append(1, d_gnss_synchro->Signal[1]);
|
||||||
|
filename.append("_ch_");
|
||||||
|
filename.append(std::to_string(d_channel));
|
||||||
|
filename.append("_");
|
||||||
|
filename.append(std::to_string(d_dump_number));
|
||||||
|
filename.append("_sat_");
|
||||||
|
filename.append(std::to_string(d_gnss_synchro->PRN));
|
||||||
|
filename.append(".mat");
|
||||||
|
|
||||||
|
mat_t* matfp = Mat_CreateVer(filename.c_str(), NULL, MAT_FT_MAT73);
|
||||||
|
if (matfp == NULL)
|
||||||
|
{
|
||||||
|
std::cout << "Unable to create or open Acquisition dump file" << std::endl;
|
||||||
|
acq_parameters.dump = false;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
size_t dims[2] = {static_cast<size_t>(effective_fft_size), static_cast<size_t>(d_num_doppler_bins)};
|
||||||
|
matvar_t* matvar = Mat_VarCreate("grid", MAT_C_SINGLE, MAT_T_SINGLE, 2, dims, grid_.memptr(), 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
dims[0] = static_cast<size_t>(1);
|
||||||
|
dims[1] = static_cast<size_t>(1);
|
||||||
|
matvar = Mat_VarCreate("doppler_max", MAT_C_UINT32, MAT_T_UINT32, 1, dims, &acq_parameters.doppler_max, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
matvar = Mat_VarCreate("doppler_step", MAT_C_UINT32, MAT_T_UINT32, 1, dims, &d_doppler_step, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
matvar = Mat_VarCreate("d_positive_acq", MAT_C_INT32, MAT_T_INT32, 1, dims, &d_positive_acq, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
float aux = static_cast<float>(d_gnss_synchro->Acq_doppler_hz);
|
||||||
|
matvar = Mat_VarCreate("acq_doppler_hz", MAT_C_SINGLE, MAT_T_SINGLE, 1, dims, &aux, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
aux = static_cast<float>(d_gnss_synchro->Acq_delay_samples);
|
||||||
|
matvar = Mat_VarCreate("acq_delay_samples", MAT_C_SINGLE, MAT_T_SINGLE, 1, dims, &aux, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
matvar = Mat_VarCreate("test_statistic", MAT_C_SINGLE, MAT_T_SINGLE, 1, dims, &d_test_statistics, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
matvar = Mat_VarCreate("threshold", MAT_C_SINGLE, MAT_T_SINGLE, 1, dims, &d_threshold, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
matvar = Mat_VarCreate("input_power", MAT_C_SINGLE, MAT_T_SINGLE, 1, dims, &d_input_power, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
matvar = Mat_VarCreate("sample_counter", MAT_C_UINT64, MAT_T_UINT64, 1, dims, &d_sample_counter, 0);
|
||||||
|
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
||||||
|
Mat_VarFree(matvar);
|
||||||
|
|
||||||
|
Mat_Close(matfp);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
||||||
{
|
{
|
||||||
gr::thread::scoped_lock lk(d_setlock);
|
gr::thread::scoped_lock lk(d_setlock);
|
||||||
@ -342,7 +419,7 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
// initialize acquisition algorithm
|
// initialize acquisition algorithm
|
||||||
uint32_t indext = 0;
|
uint32_t indext = 0;
|
||||||
float magt = 0.0;
|
float magt = 0.0;
|
||||||
const gr_complex* in = d_data_buffer; //Get the input samples pointer
|
const gr_complex* in = d_data_buffer; // Get the input samples pointer
|
||||||
int effective_fft_size = (acq_parameters.bit_transition_flag ? d_fft_size / 2 : d_fft_size);
|
int effective_fft_size = (acq_parameters.bit_transition_flag ? d_fft_size / 2 : d_fft_size);
|
||||||
if (d_cshort)
|
if (d_cshort)
|
||||||
{
|
{
|
||||||
@ -436,43 +513,6 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
if (acq_parameters.dump)
|
if (acq_parameters.dump)
|
||||||
{
|
{
|
||||||
memcpy(grid_.colptr(doppler_index), d_magnitude, sizeof(float) * effective_fft_size);
|
memcpy(grid_.colptr(doppler_index), d_magnitude, sizeof(float) * effective_fft_size);
|
||||||
if (doppler_index == (d_num_doppler_bins - 1))
|
|
||||||
{
|
|
||||||
std::string filename = acq_parameters.dump_filename;
|
|
||||||
filename.append("_");
|
|
||||||
filename.append(1, d_gnss_synchro->System);
|
|
||||||
filename.append("_");
|
|
||||||
filename.append(1, d_gnss_synchro->Signal[0]);
|
|
||||||
filename.append(1, d_gnss_synchro->Signal[1]);
|
|
||||||
filename.append("_sat_");
|
|
||||||
filename.append(std::to_string(d_gnss_synchro->PRN));
|
|
||||||
filename.append(".mat");
|
|
||||||
mat_t* matfp = Mat_CreateVer(filename.c_str(), NULL, MAT_FT_MAT73);
|
|
||||||
if (matfp == NULL)
|
|
||||||
{
|
|
||||||
std::cout << "Unable to create or open Acquisition dump file" << std::endl;
|
|
||||||
acq_parameters.dump = false;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
size_t dims[2] = {static_cast<size_t>(effective_fft_size), static_cast<size_t>(d_num_doppler_bins)};
|
|
||||||
matvar_t* matvar = Mat_VarCreate("grid", MAT_C_SINGLE, MAT_T_SINGLE, 2, dims, grid_.memptr(), 0);
|
|
||||||
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
|
||||||
Mat_VarFree(matvar);
|
|
||||||
|
|
||||||
dims[0] = static_cast<size_t>(1);
|
|
||||||
dims[1] = static_cast<size_t>(1);
|
|
||||||
matvar = Mat_VarCreate("doppler_max", MAT_C_SINGLE, MAT_T_UINT32, 1, dims, &acq_parameters.doppler_max, 0);
|
|
||||||
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
|
||||||
Mat_VarFree(matvar);
|
|
||||||
|
|
||||||
matvar = Mat_VarCreate("doppler_step", MAT_C_SINGLE, MAT_T_UINT32, 1, dims, &d_doppler_step, 0);
|
|
||||||
Mat_VarWrite(matfp, matvar, MAT_COMPRESSION_ZLIB); // or MAT_COMPRESSION_NONE
|
|
||||||
Mat_VarFree(matvar);
|
|
||||||
|
|
||||||
Mat_Close(matfp);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -538,6 +578,11 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
d_test_statistics = d_mag / d_input_power;
|
d_test_statistics = d_mag / d_input_power;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
// Record results to file if required
|
||||||
|
if (acq_parameters.dump)
|
||||||
|
{
|
||||||
|
memcpy(grid_.colptr(doppler_index), d_magnitude, sizeof(float) * effective_fft_size);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
lk.lock();
|
lk.lock();
|
||||||
@ -553,6 +598,7 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
send_positive_acquisition();
|
send_positive_acquisition();
|
||||||
d_step_two = false;
|
d_step_two = false;
|
||||||
d_state = 0; // Positive acquisition
|
d_state = 0; // Positive acquisition
|
||||||
|
d_positive_acq = 1;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -564,6 +610,7 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
{
|
{
|
||||||
send_positive_acquisition();
|
send_positive_acquisition();
|
||||||
d_state = 0; // Positive acquisition
|
d_state = 0; // Positive acquisition
|
||||||
|
d_positive_acq = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (d_well_count == acq_parameters.max_dwells)
|
else if (d_well_count == acq_parameters.max_dwells)
|
||||||
@ -586,6 +633,7 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
send_positive_acquisition();
|
send_positive_acquisition();
|
||||||
d_step_two = false;
|
d_step_two = false;
|
||||||
d_state = 0; // Positive acquisition
|
d_state = 0; // Positive acquisition
|
||||||
|
d_positive_acq = 1;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -597,6 +645,7 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
{
|
{
|
||||||
send_positive_acquisition();
|
send_positive_acquisition();
|
||||||
d_state = 0; // Positive acquisition
|
d_state = 0; // Positive acquisition
|
||||||
|
d_positive_acq = 1;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -607,6 +656,11 @@ void pcps_acquisition::acquisition_core(unsigned long int samp_count)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
d_worker_active = false;
|
d_worker_active = false;
|
||||||
|
// Record results to file if required
|
||||||
|
if (acq_parameters.dump)
|
||||||
|
{
|
||||||
|
pcps_acquisition::dump_results(effective_fft_size);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
@ -53,38 +53,20 @@
|
|||||||
#define GNSS_SDR_PCPS_ACQUISITION_H_
|
#define GNSS_SDR_PCPS_ACQUISITION_H_
|
||||||
|
|
||||||
#include "gnss_synchro.h"
|
#include "gnss_synchro.h"
|
||||||
|
#include "acq_conf.h"
|
||||||
#include <armadillo>
|
#include <armadillo>
|
||||||
#include <gnuradio/block.h>
|
#include <gnuradio/block.h>
|
||||||
#include <gnuradio/fft/fft.h>
|
#include <gnuradio/fft/fft.h>
|
||||||
#include <volk/volk.h>
|
#include <volk/volk.h>
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
typedef struct
|
|
||||||
{
|
|
||||||
/* pcps acquisition configuration */
|
|
||||||
unsigned int sampled_ms;
|
|
||||||
unsigned int max_dwells;
|
|
||||||
unsigned int doppler_max;
|
|
||||||
unsigned int num_doppler_bins_step2;
|
|
||||||
float doppler_step2;
|
|
||||||
long fs_in;
|
|
||||||
int samples_per_ms;
|
|
||||||
int samples_per_code;
|
|
||||||
bool bit_transition_flag;
|
|
||||||
bool use_CFAR_algorithm_flag;
|
|
||||||
bool dump;
|
|
||||||
bool blocking;
|
|
||||||
bool make_2_steps;
|
|
||||||
std::string dump_filename;
|
|
||||||
size_t it_size;
|
|
||||||
} pcpsconf_t;
|
|
||||||
|
|
||||||
class pcps_acquisition;
|
class pcps_acquisition;
|
||||||
|
|
||||||
typedef boost::shared_ptr<pcps_acquisition> pcps_acquisition_sptr;
|
typedef boost::shared_ptr<pcps_acquisition> pcps_acquisition_sptr;
|
||||||
|
|
||||||
pcps_acquisition_sptr
|
pcps_acquisition_sptr
|
||||||
pcps_make_acquisition(pcpsconf_t conf_);
|
pcps_make_acquisition(const Acq_Conf& conf_);
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \brief This class implements a Parallel Code Phase Search Acquisition.
|
* \brief This class implements a Parallel Code Phase Search Acquisition.
|
||||||
@ -96,9 +78,9 @@ class pcps_acquisition : public gr::block
|
|||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
friend pcps_acquisition_sptr
|
friend pcps_acquisition_sptr
|
||||||
pcps_make_acquisition(pcpsconf_t conf_);
|
pcps_make_acquisition(const Acq_Conf& conf_);
|
||||||
|
|
||||||
pcps_acquisition(pcpsconf_t conf_);
|
pcps_acquisition(const Acq_Conf& conf_);
|
||||||
|
|
||||||
void update_local_carrier(gr_complex* carrier_vector, int correlator_length_samples, float freq);
|
void update_local_carrier(gr_complex* carrier_vector, int correlator_length_samples, float freq);
|
||||||
void update_grid_doppler_wipeoffs();
|
void update_grid_doppler_wipeoffs();
|
||||||
@ -111,11 +93,14 @@ private:
|
|||||||
|
|
||||||
void send_positive_acquisition();
|
void send_positive_acquisition();
|
||||||
|
|
||||||
pcpsconf_t acq_parameters;
|
void dump_results(int effective_fft_size);
|
||||||
|
|
||||||
|
Acq_Conf acq_parameters;
|
||||||
bool d_active;
|
bool d_active;
|
||||||
bool d_worker_active;
|
bool d_worker_active;
|
||||||
bool d_cshort;
|
bool d_cshort;
|
||||||
bool d_step_two;
|
bool d_step_two;
|
||||||
|
int d_positive_acq;
|
||||||
float d_threshold;
|
float d_threshold;
|
||||||
float d_mag;
|
float d_mag;
|
||||||
float d_input_power;
|
float d_input_power;
|
||||||
@ -139,6 +124,7 @@ private:
|
|||||||
gr::fft::fft_complex* d_ifft;
|
gr::fft::fft_complex* d_ifft;
|
||||||
Gnss_Synchro* d_gnss_synchro;
|
Gnss_Synchro* d_gnss_synchro;
|
||||||
arma::fmat grid_;
|
arma::fmat grid_;
|
||||||
|
long int d_dump_number;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
~pcps_acquisition();
|
~pcps_acquisition();
|
||||||
|
@ -16,12 +16,9 @@
|
|||||||
# along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
# along with GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||||
#
|
#
|
||||||
|
|
||||||
|
if(ENABLE_FPGA)
|
||||||
set(ACQUISITION_LIB_SOURCES
|
set(ACQUISITION_LIB_SOURCES fpga_acquisition.cc )
|
||||||
fpga_acquisition.cc
|
include_directories(
|
||||||
)
|
|
||||||
|
|
||||||
include_directories(
|
|
||||||
${CMAKE_CURRENT_SOURCE_DIR}
|
${CMAKE_CURRENT_SOURCE_DIR}
|
||||||
${CMAKE_SOURCE_DIR}/src/core/system_parameters
|
${CMAKE_SOURCE_DIR}/src/core/system_parameters
|
||||||
${CMAKE_SOURCE_DIR}/src/core/interfaces
|
${CMAKE_SOURCE_DIR}/src/core/interfaces
|
||||||
@ -31,10 +28,16 @@ include_directories(
|
|||||||
${GLOG_INCLUDE_DIRS}
|
${GLOG_INCLUDE_DIRS}
|
||||||
${GFlags_INCLUDE_DIRS}
|
${GFlags_INCLUDE_DIRS}
|
||||||
${VOLK_GNSSSDR_INCLUDE_DIRS}
|
${VOLK_GNSSSDR_INCLUDE_DIRS}
|
||||||
)
|
)
|
||||||
|
|
||||||
file(GLOB ACQUISITION_LIB_HEADERS "*.h")
|
file(GLOB ACQUISITION_LIB_HEADERS "*.h")
|
||||||
|
endif(ENABLE_FPGA)
|
||||||
|
|
||||||
|
set(ACQUISITION_LIB_HEADERS ${ACQUISITION_LIB_HEADERS} acq_conf.h)
|
||||||
list(SORT ACQUISITION_LIB_HEADERS)
|
list(SORT ACQUISITION_LIB_HEADERS)
|
||||||
|
|
||||||
|
set(ACQUISITION_LIB_SOURCES ${ACQUISITION_LIB_SOURCES} acq_conf.cc)
|
||||||
|
|
||||||
add_library(acquisition_lib ${ACQUISITION_LIB_SOURCES} ${ACQUISITION_LIB_HEADERS})
|
add_library(acquisition_lib ${ACQUISITION_LIB_SOURCES} ${ACQUISITION_LIB_HEADERS})
|
||||||
source_group(Headers FILES ${ACQUISITION_LIB_HEADERS})
|
source_group(Headers FILES ${ACQUISITION_LIB_HEADERS})
|
||||||
target_link_libraries(acquisition_lib ${VOLK_LIBRARIES} ${VOLK_GNSSSDR_LIBRARIES} ${GNURADIO_RUNTIME_LIBRARIES})
|
target_link_libraries(acquisition_lib ${VOLK_LIBRARIES} ${VOLK_GNSSSDR_LIBRARIES} ${GNURADIO_RUNTIME_LIBRARIES})
|
||||||
@ -43,4 +46,3 @@ if(VOLK_GNSSSDR_FOUND)
|
|||||||
else(VOLK_GNSSSDR_FOUND)
|
else(VOLK_GNSSSDR_FOUND)
|
||||||
add_dependencies(acquisition_lib glog-${glog_RELEASE} volk_gnsssdr_module)
|
add_dependencies(acquisition_lib glog-${glog_RELEASE} volk_gnsssdr_module)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
|
52
src/algorithms/acquisition/libs/acq_conf.cc
Normal file
52
src/algorithms/acquisition/libs/acq_conf.cc
Normal file
@ -0,0 +1,52 @@
|
|||||||
|
/*!
|
||||||
|
* \file acq_conf.cc
|
||||||
|
* \brief Class that contains all the configuration parameters for generic
|
||||||
|
* acquisition block based on the PCPS algoritm.
|
||||||
|
* \author Carles Fernandez, 2018. cfernandez(at)cttc.es
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Copyright (C) 2010-2018 (see AUTHORS file for a list of contributors)
|
||||||
|
*
|
||||||
|
* GNSS-SDR is a software defined Global Navigation
|
||||||
|
* Satellite Systems receiver
|
||||||
|
*
|
||||||
|
* This file is part of GNSS-SDR.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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 GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "acq_conf.h"
|
||||||
|
|
||||||
|
Acq_Conf::Acq_Conf()
|
||||||
|
{
|
||||||
|
/* PCPS acquisition configuration */
|
||||||
|
sampled_ms = 0;
|
||||||
|
max_dwells = 0;
|
||||||
|
doppler_max = 0;
|
||||||
|
num_doppler_bins_step2 = 0;
|
||||||
|
doppler_step2 = 0.0;
|
||||||
|
fs_in = 0;
|
||||||
|
samples_per_ms = 0;
|
||||||
|
samples_per_code = 0;
|
||||||
|
bit_transition_flag = false;
|
||||||
|
use_CFAR_algorithm_flag = false;
|
||||||
|
dump = false;
|
||||||
|
blocking = false;
|
||||||
|
make_2_steps = false;
|
||||||
|
dump_filename = "";
|
||||||
|
it_size = sizeof(char);
|
||||||
|
}
|
61
src/algorithms/acquisition/libs/acq_conf.h
Normal file
61
src/algorithms/acquisition/libs/acq_conf.h
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
/*!
|
||||||
|
* \file acq_conf.cc
|
||||||
|
* \brief Class that contains all the configuration parameters for generic
|
||||||
|
* acquisition block based on the PCPS algoritm.
|
||||||
|
* \author Carles Fernandez, 2018. cfernandez(at)cttc.es
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Copyright (C) 2010-2018 (see AUTHORS file for a list of contributors)
|
||||||
|
*
|
||||||
|
* GNSS-SDR is a software defined Global Navigation
|
||||||
|
* Satellite Systems receiver
|
||||||
|
*
|
||||||
|
* This file is part of GNSS-SDR.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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 GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef GNSS_SDR_ACQ_CONF_H_
|
||||||
|
#define GNSS_SDR_ACQ_CONF_H_
|
||||||
|
|
||||||
|
#include <cstddef>
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
class Acq_Conf
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
/* PCPS Acquisition configuration */
|
||||||
|
unsigned int sampled_ms;
|
||||||
|
unsigned int max_dwells;
|
||||||
|
unsigned int doppler_max;
|
||||||
|
unsigned int num_doppler_bins_step2;
|
||||||
|
float doppler_step2;
|
||||||
|
long fs_in;
|
||||||
|
int samples_per_ms;
|
||||||
|
int samples_per_code;
|
||||||
|
bool bit_transition_flag;
|
||||||
|
bool use_CFAR_algorithm_flag;
|
||||||
|
bool dump;
|
||||||
|
bool blocking;
|
||||||
|
bool make_2_steps;
|
||||||
|
std::string dump_filename;
|
||||||
|
size_t it_size;
|
||||||
|
|
||||||
|
Acq_Conf();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
@ -34,6 +34,7 @@
|
|||||||
* -------------------------------------------------------------------------
|
* -------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
#include "galileo_e1_dll_pll_veml_tracking.h"
|
#include "galileo_e1_dll_pll_veml_tracking.h"
|
||||||
#include "configuration_interface.h"
|
#include "configuration_interface.h"
|
||||||
#include "Galileo_E1.h"
|
#include "Galileo_E1.h"
|
||||||
@ -48,7 +49,7 @@ GalileoE1DllPllVemlTracking::GalileoE1DllPllVemlTracking(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
dllpllconf_t trk_param;
|
Dll_Pll_Conf trk_param = Dll_Pll_Conf();
|
||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
//################# CONFIGURATION PARAMETERS ########################
|
//################# CONFIGURATION PARAMETERS ########################
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
|
@ -35,7 +35,7 @@
|
|||||||
*
|
*
|
||||||
* -------------------------------------------------------------------------
|
* -------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
#include "galileo_e5a_dll_pll_tracking.h"
|
#include "galileo_e5a_dll_pll_tracking.h"
|
||||||
#include "configuration_interface.h"
|
#include "configuration_interface.h"
|
||||||
#include "Galileo_E5a.h"
|
#include "Galileo_E5a.h"
|
||||||
@ -49,7 +49,7 @@ GalileoE5aDllPllTracking::GalileoE5aDllPllTracking(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
dllpllconf_t trk_param;
|
Dll_Pll_Conf trk_param = Dll_Pll_Conf();
|
||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
//################# CONFIGURATION PARAMETERS ########################
|
//################# CONFIGURATION PARAMETERS ########################
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
|
@ -35,7 +35,7 @@
|
|||||||
* -------------------------------------------------------------------------
|
* -------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
#include "gps_l1_ca_dll_pll_tracking.h"
|
#include "gps_l1_ca_dll_pll_tracking.h"
|
||||||
#include "configuration_interface.h"
|
#include "configuration_interface.h"
|
||||||
#include "GPS_L1_CA.h"
|
#include "GPS_L1_CA.h"
|
||||||
@ -49,7 +49,7 @@ GpsL1CaDllPllTracking::GpsL1CaDllPllTracking(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
dllpllconf_t trk_param;
|
Dll_Pll_Conf trk_param = Dll_Pll_Conf();
|
||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
//################# CONFIGURATION PARAMETERS ########################
|
//################# CONFIGURATION PARAMETERS ########################
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
@ -108,13 +108,13 @@ GpsL1CaDllPllTracking::GpsL1CaDllPllTracking(
|
|||||||
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
int cn0_samples = configuration->property(role + ".cn0_samples", 20);
|
||||||
if (FLAGS_cn0_samples != 20) cn0_samples = FLAGS_cn0_samples;
|
if (FLAGS_cn0_samples != 20) cn0_samples = FLAGS_cn0_samples;
|
||||||
trk_param.cn0_samples = cn0_samples;
|
trk_param.cn0_samples = cn0_samples;
|
||||||
int cn0_min = configuration->property(role + ".cn0_min", 25);
|
int cn0_min = configuration->property(role + ".cn0_min", 30);
|
||||||
if (FLAGS_cn0_min != 25) cn0_min = FLAGS_cn0_min;
|
if (FLAGS_cn0_min != 25) cn0_min = FLAGS_cn0_min;
|
||||||
trk_param.cn0_min = cn0_min;
|
trk_param.cn0_min = cn0_min;
|
||||||
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
int max_lock_fail = configuration->property(role + ".max_lock_fail", 50);
|
||||||
if (FLAGS_max_lock_fail != 50) max_lock_fail = FLAGS_max_lock_fail;
|
if (FLAGS_max_lock_fail != 50) max_lock_fail = FLAGS_max_lock_fail;
|
||||||
trk_param.max_lock_fail = max_lock_fail;
|
trk_param.max_lock_fail = max_lock_fail;
|
||||||
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.85);
|
double carrier_lock_th = configuration->property(role + ".carrier_lock_th", 0.80);
|
||||||
if (FLAGS_carrier_lock_th != 0.85) carrier_lock_th = FLAGS_carrier_lock_th;
|
if (FLAGS_carrier_lock_th != 0.85) carrier_lock_th = FLAGS_carrier_lock_th;
|
||||||
trk_param.carrier_lock_th = carrier_lock_th;
|
trk_param.carrier_lock_th = carrier_lock_th;
|
||||||
|
|
||||||
|
@ -34,7 +34,7 @@
|
|||||||
* -------------------------------------------------------------------------
|
* -------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
#include "gps_l2_m_dll_pll_tracking.h"
|
#include "gps_l2_m_dll_pll_tracking.h"
|
||||||
#include "configuration_interface.h"
|
#include "configuration_interface.h"
|
||||||
#include "GPS_L2C.h"
|
#include "GPS_L2C.h"
|
||||||
@ -49,7 +49,7 @@ GpsL2MDllPllTracking::GpsL2MDllPllTracking(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
dllpllconf_t trk_param;
|
Dll_Pll_Conf trk_param = Dll_Pll_Conf();
|
||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
//################# CONFIGURATION PARAMETERS ########################
|
//################# CONFIGURATION PARAMETERS ########################
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
|
@ -34,7 +34,7 @@
|
|||||||
* -------------------------------------------------------------------------
|
* -------------------------------------------------------------------------
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
#include "gps_l5_dll_pll_tracking.h"
|
#include "gps_l5_dll_pll_tracking.h"
|
||||||
#include "configuration_interface.h"
|
#include "configuration_interface.h"
|
||||||
#include "GPS_L5.h"
|
#include "GPS_L5.h"
|
||||||
@ -49,7 +49,7 @@ GpsL5DllPllTracking::GpsL5DllPllTracking(
|
|||||||
ConfigurationInterface* configuration, std::string role,
|
ConfigurationInterface* configuration, std::string role,
|
||||||
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
unsigned int in_streams, unsigned int out_streams) : role_(role), in_streams_(in_streams), out_streams_(out_streams)
|
||||||
{
|
{
|
||||||
dllpllconf_t trk_param;
|
Dll_Pll_Conf trk_param = Dll_Pll_Conf();
|
||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
//################# CONFIGURATION PARAMETERS ########################
|
//################# CONFIGURATION PARAMETERS ########################
|
||||||
std::string default_item_type = "gr_complex";
|
std::string default_item_type = "gr_complex";
|
||||||
|
@ -60,7 +60,7 @@
|
|||||||
|
|
||||||
using google::LogMessage;
|
using google::LogMessage;
|
||||||
|
|
||||||
dll_pll_veml_tracking_sptr dll_pll_veml_make_tracking(dllpllconf_t conf_)
|
dll_pll_veml_tracking_sptr dll_pll_veml_make_tracking(const Dll_Pll_Conf &conf_)
|
||||||
{
|
{
|
||||||
return dll_pll_veml_tracking_sptr(new dll_pll_veml_tracking(conf_));
|
return dll_pll_veml_tracking_sptr(new dll_pll_veml_tracking(conf_));
|
||||||
}
|
}
|
||||||
@ -76,7 +76,7 @@ void dll_pll_veml_tracking::forecast(int noutput_items,
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
dll_pll_veml_tracking::dll_pll_veml_tracking(dllpllconf_t conf_) : gr::block("dll_pll_veml_tracking", gr::io_signature::make(1, 1, sizeof(gr_complex)),
|
dll_pll_veml_tracking::dll_pll_veml_tracking(const Dll_Pll_Conf &conf_) : gr::block("dll_pll_veml_tracking", gr::io_signature::make(1, 1, sizeof(gr_complex)),
|
||||||
gr::io_signature::make(1, 1, sizeof(Gnss_Synchro)))
|
gr::io_signature::make(1, 1, sizeof(Gnss_Synchro)))
|
||||||
{
|
{
|
||||||
trk_parameters = conf_;
|
trk_parameters = conf_;
|
||||||
|
@ -31,6 +31,7 @@
|
|||||||
#ifndef GNSS_SDR_DLL_PLL_VEML_TRACKING_H
|
#ifndef GNSS_SDR_DLL_PLL_VEML_TRACKING_H
|
||||||
#define GNSS_SDR_DLL_PLL_VEML_TRACKING_H
|
#define GNSS_SDR_DLL_PLL_VEML_TRACKING_H
|
||||||
|
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
#include "gnss_synchro.h"
|
#include "gnss_synchro.h"
|
||||||
#include "tracking_2nd_DLL_filter.h"
|
#include "tracking_2nd_DLL_filter.h"
|
||||||
#include "tracking_2nd_PLL_filter.h"
|
#include "tracking_2nd_PLL_filter.h"
|
||||||
@ -39,37 +40,13 @@
|
|||||||
#include <fstream>
|
#include <fstream>
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <map>
|
#include <map>
|
||||||
|
#include <queue>
|
||||||
typedef struct
|
|
||||||
{
|
|
||||||
/* DLL/PLL tracking configuration */
|
|
||||||
double fs_in;
|
|
||||||
unsigned int vector_length;
|
|
||||||
bool dump;
|
|
||||||
std::string dump_filename;
|
|
||||||
float pll_bw_hz;
|
|
||||||
float dll_bw_hz;
|
|
||||||
float pll_bw_narrow_hz;
|
|
||||||
float dll_bw_narrow_hz;
|
|
||||||
float early_late_space_chips;
|
|
||||||
float very_early_late_space_chips;
|
|
||||||
float early_late_space_narrow_chips;
|
|
||||||
float very_early_late_space_narrow_chips;
|
|
||||||
int extend_correlation_symbols;
|
|
||||||
int cn0_samples;
|
|
||||||
int cn0_min;
|
|
||||||
int max_lock_fail;
|
|
||||||
double carrier_lock_th;
|
|
||||||
bool track_pilot;
|
|
||||||
char system;
|
|
||||||
char signal[3];
|
|
||||||
} dllpllconf_t;
|
|
||||||
|
|
||||||
class dll_pll_veml_tracking;
|
class dll_pll_veml_tracking;
|
||||||
|
|
||||||
typedef boost::shared_ptr<dll_pll_veml_tracking> dll_pll_veml_tracking_sptr;
|
typedef boost::shared_ptr<dll_pll_veml_tracking> dll_pll_veml_tracking_sptr;
|
||||||
|
|
||||||
dll_pll_veml_tracking_sptr dll_pll_veml_make_tracking(dllpllconf_t conf_);
|
dll_pll_veml_tracking_sptr dll_pll_veml_make_tracking(const Dll_Pll_Conf &conf_);
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \brief This class implements a code DLL + carrier PLL tracking block.
|
* \brief This class implements a code DLL + carrier PLL tracking block.
|
||||||
@ -89,9 +66,9 @@ public:
|
|||||||
void forecast(int noutput_items, gr_vector_int &ninput_items_required);
|
void forecast(int noutput_items, gr_vector_int &ninput_items_required);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
friend dll_pll_veml_tracking_sptr dll_pll_veml_make_tracking(dllpllconf_t conf_);
|
friend dll_pll_veml_tracking_sptr dll_pll_veml_make_tracking(const Dll_Pll_Conf &conf_);
|
||||||
|
|
||||||
dll_pll_veml_tracking(dllpllconf_t conf_);
|
dll_pll_veml_tracking(const Dll_Pll_Conf &conf_);
|
||||||
|
|
||||||
bool cn0_and_tracking_lock_status(double coh_integration_time_s);
|
bool cn0_and_tracking_lock_status(double coh_integration_time_s);
|
||||||
bool acquire_secondary();
|
bool acquire_secondary();
|
||||||
@ -104,7 +81,7 @@ private:
|
|||||||
int save_matfile();
|
int save_matfile();
|
||||||
|
|
||||||
// tracking configuration vars
|
// tracking configuration vars
|
||||||
dllpllconf_t trk_parameters;
|
Dll_Pll_Conf trk_parameters;
|
||||||
bool d_veml;
|
bool d_veml;
|
||||||
bool d_cloop;
|
bool d_cloop;
|
||||||
unsigned int d_channel;
|
unsigned int d_channel;
|
||||||
@ -201,6 +178,7 @@ private:
|
|||||||
// CN0 estimation and lock detector
|
// CN0 estimation and lock detector
|
||||||
int d_cn0_estimation_counter;
|
int d_cn0_estimation_counter;
|
||||||
int d_carrier_lock_fail_counter;
|
int d_carrier_lock_fail_counter;
|
||||||
|
std::deque<float> d_carrier_lock_detector_queue;
|
||||||
double d_carrier_lock_test;
|
double d_carrier_lock_test;
|
||||||
double d_CN0_SNV_dB_Hz;
|
double d_CN0_SNV_dB_Hz;
|
||||||
double d_carrier_lock_threshold;
|
double d_carrier_lock_threshold;
|
||||||
|
@ -43,6 +43,7 @@ set(TRACKING_LIB_SOURCES
|
|||||||
tracking_discriminators.cc
|
tracking_discriminators.cc
|
||||||
tracking_FLL_PLL_filter.cc
|
tracking_FLL_PLL_filter.cc
|
||||||
tracking_loop_filter.cc
|
tracking_loop_filter.cc
|
||||||
|
dll_pll_conf.cc
|
||||||
)
|
)
|
||||||
|
|
||||||
if(ENABLE_FPGA)
|
if(ENABLE_FPGA)
|
||||||
|
61
src/algorithms/tracking/libs/dll_pll_conf.cc
Normal file
61
src/algorithms/tracking/libs/dll_pll_conf.cc
Normal file
@ -0,0 +1,61 @@
|
|||||||
|
/*!
|
||||||
|
* \file dll_pll_conf.cc
|
||||||
|
* \brief Class that contains all the configuration parameters for generic
|
||||||
|
* tracking block based on a DLL and a PLL.
|
||||||
|
* \author Javier Arribas, 2018. jarribas(at)cttc.es
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Copyright (C) 2010-2018 (see AUTHORS file for a list of contributors)
|
||||||
|
*
|
||||||
|
* GNSS-SDR is a software defined Global Navigation
|
||||||
|
* Satellite Systems receiver
|
||||||
|
*
|
||||||
|
* This file is part of GNSS-SDR.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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 GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
#include "dll_pll_conf.h"
|
||||||
|
#include <cstring>
|
||||||
|
|
||||||
|
Dll_Pll_Conf::Dll_Pll_Conf()
|
||||||
|
{
|
||||||
|
/* DLL/PLL tracking configuration */
|
||||||
|
fs_in = 0.0;
|
||||||
|
vector_length = 0;
|
||||||
|
dump = false;
|
||||||
|
dump_filename = "./dll_pll_dump.dat";
|
||||||
|
pll_bw_hz = 40.0;
|
||||||
|
dll_bw_hz = 2.0;
|
||||||
|
pll_bw_narrow_hz = 5.0;
|
||||||
|
dll_bw_narrow_hz = 0.75;
|
||||||
|
early_late_space_chips = 0.5;
|
||||||
|
very_early_late_space_chips = 0.5;
|
||||||
|
early_late_space_narrow_chips = 0.1;
|
||||||
|
very_early_late_space_narrow_chips = 0.1;
|
||||||
|
extend_correlation_symbols = 5;
|
||||||
|
cn0_samples = 20;
|
||||||
|
carrier_lock_det_mav_samples = 20;
|
||||||
|
cn0_min = 25;
|
||||||
|
max_lock_fail = 50;
|
||||||
|
carrier_lock_th = 0.85;
|
||||||
|
track_pilot = false;
|
||||||
|
system = 'G';
|
||||||
|
char sig_[3] = "1C";
|
||||||
|
std::memcpy(signal, sig_, 3);
|
||||||
|
}
|
68
src/algorithms/tracking/libs/dll_pll_conf.h
Normal file
68
src/algorithms/tracking/libs/dll_pll_conf.h
Normal file
@ -0,0 +1,68 @@
|
|||||||
|
/*!
|
||||||
|
* \file dll_pll_conf.h
|
||||||
|
* \brief Class that contains all the configuration parameters for generic tracking block based on a DLL and a PLL.
|
||||||
|
* \author Javier Arribas, 2018. jarribas(at)cttc.es
|
||||||
|
*
|
||||||
|
* Class that contains all the configuration parameters for generic tracking block based on a DLL and a PLL.
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*
|
||||||
|
* Copyright (C) 2010-2018 (see AUTHORS file for a list of contributors)
|
||||||
|
*
|
||||||
|
* GNSS-SDR is a software defined Global Navigation
|
||||||
|
* Satellite Systems receiver
|
||||||
|
*
|
||||||
|
* This file is part of GNSS-SDR.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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.
|
||||||
|
*
|
||||||
|
* GNSS-SDR 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 GNSS-SDR. If not, see <https://www.gnu.org/licenses/>.
|
||||||
|
*
|
||||||
|
* -------------------------------------------------------------------------
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef GNSS_SDR_DLL_PLL_CONF_H_
|
||||||
|
#define GNSS_SDR_DLL_PLL_CONF_H_
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
class Dll_Pll_Conf
|
||||||
|
{
|
||||||
|
private:
|
||||||
|
public:
|
||||||
|
/* DLL/PLL tracking configuration */
|
||||||
|
double fs_in;
|
||||||
|
unsigned int vector_length;
|
||||||
|
bool dump;
|
||||||
|
std::string dump_filename;
|
||||||
|
float pll_bw_hz;
|
||||||
|
float dll_bw_hz;
|
||||||
|
float pll_bw_narrow_hz;
|
||||||
|
float dll_bw_narrow_hz;
|
||||||
|
float early_late_space_chips;
|
||||||
|
float very_early_late_space_chips;
|
||||||
|
float early_late_space_narrow_chips;
|
||||||
|
float very_early_late_space_narrow_chips;
|
||||||
|
int extend_correlation_symbols;
|
||||||
|
int cn0_samples;
|
||||||
|
int carrier_lock_det_mav_samples;
|
||||||
|
int cn0_min;
|
||||||
|
int max_lock_fail;
|
||||||
|
double carrier_lock_th;
|
||||||
|
bool track_pilot;
|
||||||
|
char system;
|
||||||
|
char signal[3];
|
||||||
|
|
||||||
|
Dll_Pll_Conf();
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif
|
@ -1304,6 +1304,7 @@ void GNSSFlowgraph::set_channels_state()
|
|||||||
}
|
}
|
||||||
DLOG(INFO) << "Channel " << i << " in state " << channels_state_[i];
|
DLOG(INFO) << "Channel " << i << " in state " << channels_state_[i];
|
||||||
}
|
}
|
||||||
|
std::lock_guard<std::mutex> lock(signal_list_mutex);
|
||||||
acq_channels_count_ = max_acq_channels_;
|
acq_channels_count_ = max_acq_channels_;
|
||||||
DLOG(INFO) << acq_channels_count_ << " channels in acquisition state";
|
DLOG(INFO) << acq_channels_count_ << " channels in acquisition state";
|
||||||
}
|
}
|
||||||
|
@ -107,17 +107,17 @@ public:
|
|||||||
|
|
||||||
void set_configuration(std::shared_ptr<ConfigurationInterface> configuration);
|
void set_configuration(std::shared_ptr<ConfigurationInterface> configuration);
|
||||||
|
|
||||||
unsigned int applied_actions()
|
unsigned int applied_actions() const
|
||||||
{
|
{
|
||||||
return applied_actions_;
|
return applied_actions_;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool connected()
|
bool connected() const
|
||||||
{
|
{
|
||||||
return connected_;
|
return connected_;
|
||||||
}
|
}
|
||||||
|
|
||||||
bool running()
|
bool running() const
|
||||||
{
|
{
|
||||||
return running_;
|
return running_;
|
||||||
}
|
}
|
||||||
|
@ -69,7 +69,7 @@
|
|||||||
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
||||||
//all UNIX-like OSs (Linux, *BSD, MacOSX, Solaris, ...)
|
//all UNIX-like OSs (Linux, *BSD, MacOSX, Solaris, ...)
|
||||||
#include <unistd.h> // for access(), mkstemp()
|
#include <unistd.h> // for access(), mkstemp()
|
||||||
#define GP_MAX_TMP_FILES 64
|
#define GP_MAX_TMP_FILES 1024
|
||||||
#else
|
#else
|
||||||
#error unsupported or unknown operating system
|
#error unsupported or unknown operating system
|
||||||
#endif
|
#endif
|
||||||
@ -302,9 +302,9 @@ public:
|
|||||||
///
|
///
|
||||||
/// \return <-- reference to the gnuplot object
|
/// \return <-- reference to the gnuplot object
|
||||||
// -----------------------------------------------
|
// -----------------------------------------------
|
||||||
inline Gnuplot &set_multiplot()
|
inline Gnuplot &set_multiplot(int rows, int cols)
|
||||||
{
|
{
|
||||||
cmd("set multiplot");
|
cmd("set multiplot layout " + std::to_string(rows) + "," + std::to_string(cols)); //+ " rowfirst");
|
||||||
return *this;
|
return *this;
|
||||||
};
|
};
|
||||||
|
|
||||||
@ -1906,11 +1906,11 @@ void Gnuplot::init()
|
|||||||
std::string tmp = Gnuplot::m_sGNUPlotPath + "/" +
|
std::string tmp = Gnuplot::m_sGNUPlotPath + "/" +
|
||||||
Gnuplot::m_sGNUPlotFileName;
|
Gnuplot::m_sGNUPlotFileName;
|
||||||
|
|
||||||
// FILE *popen(const char *command, const char *mode);
|
// FILE *popen(const char *command, const char *mode);
|
||||||
// The popen() function shall execute the command specified by the string
|
// The popen() function shall execute the command specified by the string
|
||||||
// command, create a pipe between the calling program and the executed
|
// command, create a pipe between the calling program and the executed
|
||||||
// command, and return a pointer to a stream that can be used to either read
|
// command, and return a pointer to a stream that can be used to either read
|
||||||
// from or write to the pipe.
|
// from or write to the pipe.
|
||||||
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
||||||
gnucmd = _popen(tmp.c_str(), "w");
|
gnucmd = _popen(tmp.c_str(), "w");
|
||||||
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
||||||
@ -1974,7 +1974,7 @@ bool Gnuplot::get_program_path()
|
|||||||
|
|
||||||
std::list<std::string> ls;
|
std::list<std::string> ls;
|
||||||
|
|
||||||
//split path (one long string) into list ls of strings
|
//split path (one long string) into list ls of strings
|
||||||
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
||||||
stringtok(ls, path_str, ";");
|
stringtok(ls, path_str, ";");
|
||||||
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
||||||
@ -2018,16 +2018,16 @@ bool Gnuplot::file_exists(const std::string &filename, int mode)
|
|||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
// int _access(const char *path, int mode);
|
// int _access(const char *path, int mode);
|
||||||
// returns 0 if the file has the given mode,
|
// returns 0 if the file has the given mode,
|
||||||
// it returns -1 if the named file does not exist or is not accessible in
|
// it returns -1 if the named file does not exist or is not accessible in
|
||||||
// the given mode
|
// the given mode
|
||||||
// mode = 0 (F_OK) (default): checks file for existence only
|
// mode = 0 (F_OK) (default): checks file for existence only
|
||||||
// mode = 1 (X_OK): execution permission
|
// mode = 1 (X_OK): execution permission
|
||||||
// mode = 2 (W_OK): write permission
|
// mode = 2 (W_OK): write permission
|
||||||
// mode = 4 (R_OK): read permission
|
// mode = 4 (R_OK): read permission
|
||||||
// mode = 6 : read and write permission
|
// mode = 6 : read and write permission
|
||||||
// mode = 7 : read, write and execution permission
|
// mode = 7 : read, write and execution permission
|
||||||
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
||||||
if (_access(filename.c_str(), mode) == 0)
|
if (_access(filename.c_str(), mode) == 0)
|
||||||
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
#elif defined(unix) || defined(__unix) || defined(__unix__) || defined(__APPLE__)
|
||||||
@ -2089,19 +2089,19 @@ std::string Gnuplot::create_tmpfile(std::ofstream &tmp)
|
|||||||
throw GnuplotException(except.str());
|
throw GnuplotException(except.str());
|
||||||
}
|
}
|
||||||
|
|
||||||
// int mkstemp(char *name);
|
// int mkstemp(char *name);
|
||||||
// shall replace the contents of the string pointed to by "name" by a unique
|
// shall replace the contents of the string pointed to by "name" by a unique
|
||||||
// filename, and return a file descriptor for the file open for reading and
|
// filename, and return a file descriptor for the file open for reading and
|
||||||
// writing. Otherwise, -1 shall be returned if no suitable file could be
|
// writing. Otherwise, -1 shall be returned if no suitable file could be
|
||||||
// created. The string in template should look like a filename with six
|
// created. The string in template should look like a filename with six
|
||||||
// trailing 'X' s; mkstemp() replaces each 'X' with a character from the
|
// trailing 'X' s; mkstemp() replaces each 'X' with a character from the
|
||||||
// portable filename character set. The characters are chosen such that the
|
// portable filename character set. The characters are chosen such that the
|
||||||
// resulting name does not duplicate the name of an existing file at the
|
// resulting name does not duplicate the name of an existing file at the
|
||||||
// time of a call to mkstemp()
|
// time of a call to mkstemp()
|
||||||
|
|
||||||
//
|
//
|
||||||
// open temporary files for output
|
// open temporary files for output
|
||||||
//
|
//
|
||||||
|
|
||||||
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
#if defined(WIN32) || defined(_WIN32) || defined(__WIN32__) || defined(__TOS_WIN__)
|
||||||
if (_mktemp(name) == NULL)
|
if (_mktemp(name) == NULL)
|
||||||
|
@ -175,7 +175,7 @@ void GpsL1CaPcpsAcquisitionTest::plot_grid()
|
|||||||
unsigned int sat = static_cast<unsigned int>(gnss_synchro.PRN);
|
unsigned int sat = static_cast<unsigned int>(gnss_synchro.PRN);
|
||||||
|
|
||||||
unsigned int samples_per_code = static_cast<unsigned int>(round(4000000 / (GPS_L1_CA_CODE_RATE_HZ / GPS_L1_CA_CODE_LENGTH_CHIPS))); // !!
|
unsigned int samples_per_code = static_cast<unsigned int>(round(4000000 / (GPS_L1_CA_CODE_RATE_HZ / GPS_L1_CA_CODE_LENGTH_CHIPS))); // !!
|
||||||
acquisition_dump_reader acq_dump(basename, sat, doppler_max, doppler_step, samples_per_code);
|
acquisition_dump_reader acq_dump(basename, sat, doppler_max, doppler_step, samples_per_code, 1);
|
||||||
|
|
||||||
if (!acq_dump.read_binary_acq()) std::cout << "Error reading files" << std::endl;
|
if (!acq_dump.read_binary_acq()) std::cout << "Error reading files" << std::endl;
|
||||||
|
|
||||||
|
@ -73,16 +73,51 @@ bool acquisition_dump_reader::read_binary_acq()
|
|||||||
Mat_Close(matfile);
|
Mat_Close(matfile);
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
matvar_t* var2_ = Mat_VarRead(matfile, "doppler_max");
|
||||||
|
d_doppler_max = *static_cast<unsigned int*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "doppler_step");
|
||||||
|
d_doppler_step = *static_cast<unsigned int*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "input_power");
|
||||||
|
input_power = *static_cast<float*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "acq_doppler_hz");
|
||||||
|
acq_doppler_hz = *static_cast<float*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "acq_delay_samples");
|
||||||
|
acq_delay_samples = *static_cast<float*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "test_statistic");
|
||||||
|
test_statistic = *static_cast<float*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "threshold");
|
||||||
|
threshold = *static_cast<float*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "sample_counter");
|
||||||
|
sample_counter = *static_cast<long unsigned int*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
|
var2_ = Mat_VarRead(matfile, "d_positive_acq");
|
||||||
|
positive_acq = *static_cast<int*>(var2_->data);
|
||||||
|
Mat_VarFree(var2_);
|
||||||
|
|
||||||
std::vector<std::vector<float> >::iterator it1;
|
std::vector<std::vector<float> >::iterator it1;
|
||||||
std::vector<float>::iterator it2;
|
std::vector<float>::iterator it2;
|
||||||
float* aux = static_cast<float*>(var_->data);
|
float* aux = static_cast<float*>(var_->data);
|
||||||
int k = 0;
|
int k = 0;
|
||||||
float normalization_factor = std::pow(d_samples_per_code, 2);
|
|
||||||
for (it1 = mag.begin(); it1 != mag.end(); it1++)
|
for (it1 = mag.begin(); it1 != mag.end(); it1++)
|
||||||
{
|
{
|
||||||
for (it2 = it1->begin(); it2 != it1->end(); it2++)
|
for (it2 = it1->begin(); it2 != it1->end(); it2++)
|
||||||
{
|
{
|
||||||
*it2 = static_cast<float>(std::sqrt(aux[k])) / normalization_factor;
|
*it2 = static_cast<float>(aux[k]) / input_power;
|
||||||
k++;
|
k++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -93,17 +128,30 @@ bool acquisition_dump_reader::read_binary_acq()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
acquisition_dump_reader::acquisition_dump_reader(const std::string& basename, unsigned int sat, unsigned int doppler_max, unsigned int doppler_step, unsigned int samples_per_code)
|
acquisition_dump_reader::acquisition_dump_reader(const std::string& basename,
|
||||||
|
unsigned int sat,
|
||||||
|
unsigned int doppler_max,
|
||||||
|
unsigned int doppler_step,
|
||||||
|
unsigned int samples_per_code,
|
||||||
|
int channel,
|
||||||
|
int execution)
|
||||||
{
|
{
|
||||||
d_basename = basename;
|
d_basename = basename;
|
||||||
d_sat = sat;
|
d_sat = sat;
|
||||||
d_doppler_max = doppler_max;
|
d_doppler_max = doppler_max;
|
||||||
d_doppler_step = doppler_step;
|
d_doppler_step = doppler_step;
|
||||||
d_samples_per_code = samples_per_code;
|
d_samples_per_code = samples_per_code;
|
||||||
|
acq_doppler_hz = 0.0;
|
||||||
|
acq_delay_samples = 0.0;
|
||||||
|
test_statistic = 0.0;
|
||||||
|
input_power = 0.0;
|
||||||
|
threshold = 0.0;
|
||||||
|
positive_acq = 0;
|
||||||
|
sample_counter = 0;
|
||||||
d_num_doppler_bins = static_cast<unsigned int>(ceil(static_cast<double>(static_cast<int>(d_doppler_max) - static_cast<int>(-d_doppler_max)) / static_cast<double>(d_doppler_step)));
|
d_num_doppler_bins = static_cast<unsigned int>(ceil(static_cast<double>(static_cast<int>(d_doppler_max) - static_cast<int>(-d_doppler_max)) / static_cast<double>(d_doppler_step)));
|
||||||
std::vector<std::vector<float> > mag_aux(d_num_doppler_bins, std::vector<float>(d_samples_per_code));
|
std::vector<std::vector<float> > mag_aux(d_num_doppler_bins, std::vector<float>(d_samples_per_code));
|
||||||
mag = mag_aux;
|
mag = mag_aux;
|
||||||
d_dump_filename = d_basename + "_sat_" + std::to_string(d_sat) + ".mat";
|
d_dump_filename = d_basename + "_ch_" + std::to_string(channel) + "_" + std::to_string(execution) + "_sat_" + std::to_string(d_sat) + ".mat";
|
||||||
for (unsigned int doppler_index = 0; doppler_index < d_num_doppler_bins; doppler_index++)
|
for (unsigned int doppler_index = 0; doppler_index < d_num_doppler_bins; doppler_index++)
|
||||||
{
|
{
|
||||||
doppler.push_back(-static_cast<int>(d_doppler_max) + d_doppler_step * doppler_index);
|
doppler.push_back(-static_cast<int>(d_doppler_max) + d_doppler_step * doppler_index);
|
||||||
|
@ -38,13 +38,26 @@
|
|||||||
class acquisition_dump_reader
|
class acquisition_dump_reader
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
acquisition_dump_reader(const std::string& basename, unsigned int sat, unsigned int doppler_max, unsigned int doppler_step, unsigned int samples_per_code);
|
acquisition_dump_reader(const std::string& basename,
|
||||||
|
unsigned int sat,
|
||||||
|
unsigned int doppler_max,
|
||||||
|
unsigned int doppler_step,
|
||||||
|
unsigned int samples_per_code,
|
||||||
|
int channel = 0,
|
||||||
|
int execution = 1);
|
||||||
~acquisition_dump_reader();
|
~acquisition_dump_reader();
|
||||||
bool read_binary_acq();
|
bool read_binary_acq();
|
||||||
|
|
||||||
std::vector<int> doppler;
|
std::vector<int> doppler;
|
||||||
std::vector<unsigned int> samples;
|
std::vector<unsigned int> samples;
|
||||||
std::vector<std::vector<float> > mag;
|
std::vector<std::vector<float> > mag;
|
||||||
|
float acq_doppler_hz;
|
||||||
|
float acq_delay_samples;
|
||||||
|
float test_statistic;
|
||||||
|
float input_power;
|
||||||
|
float threshold;
|
||||||
|
int positive_acq;
|
||||||
|
long unsigned int sample_counter;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::string d_basename;
|
std::string d_basename;
|
||||||
|
@ -112,6 +112,13 @@ bool observables_dump_reader::open_obs_file(std::string out_file)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void observables_dump_reader::close_obs_file()
|
||||||
|
{
|
||||||
|
if (d_dump_file.is_open() == false)
|
||||||
|
{
|
||||||
|
d_dump_file.close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
observables_dump_reader::observables_dump_reader(int n_channels_)
|
observables_dump_reader::observables_dump_reader(int n_channels_)
|
||||||
{
|
{
|
||||||
|
@ -44,6 +44,7 @@ public:
|
|||||||
bool restart();
|
bool restart();
|
||||||
long int num_epochs();
|
long int num_epochs();
|
||||||
bool open_obs_file(std::string out_file);
|
bool open_obs_file(std::string out_file);
|
||||||
|
void close_obs_file();
|
||||||
|
|
||||||
|
|
||||||
//dump variables
|
//dump variables
|
||||||
|
@ -89,15 +89,16 @@ bool tracking_true_obs_reader::open_obs_file(std::string out_file)
|
|||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
|
d_dump_file.clear();
|
||||||
d_dump_filename = out_file;
|
d_dump_filename = out_file;
|
||||||
d_dump_file.exceptions(std::ifstream::failbit | std::ifstream::badbit);
|
d_dump_file.exceptions(std::ifstream::failbit | std::ifstream::badbit);
|
||||||
d_dump_file.open(d_dump_filename.c_str(), std::ios::in | std::ios::binary);
|
d_dump_file.open(d_dump_filename.c_str(), std::ios::in | std::ios::binary);
|
||||||
std::cout << "Observables dump enabled, Log file: " << d_dump_filename.c_str() << std::endl;
|
std::cout << "Tracking Log file: " << d_dump_filename.c_str() << " open ok " << std::endl;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
catch (const std::ifstream::failure &e)
|
catch (const std::ifstream::failure &e)
|
||||||
{
|
{
|
||||||
std::cout << "Problem opening Observables dump Log file: " << d_dump_filename.c_str() << std::endl;
|
std::cout << "Problem opening Tracking dump Log file: " << d_dump_filename.c_str() << " Error: " << e.what() << std::endl;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -107,6 +108,13 @@ bool tracking_true_obs_reader::open_obs_file(std::string out_file)
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void tracking_true_obs_reader::close_obs_file()
|
||||||
|
{
|
||||||
|
if (d_dump_file.is_open() == true)
|
||||||
|
{
|
||||||
|
d_dump_file.close();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
tracking_true_obs_reader::~tracking_true_obs_reader()
|
tracking_true_obs_reader::~tracking_true_obs_reader()
|
||||||
{
|
{
|
||||||
|
@ -43,6 +43,7 @@ public:
|
|||||||
bool restart();
|
bool restart();
|
||||||
long int num_epochs();
|
long int num_epochs();
|
||||||
bool open_obs_file(std::string out_file);
|
bool open_obs_file(std::string out_file);
|
||||||
|
void close_obs_file();
|
||||||
bool d_dump;
|
bool d_dump;
|
||||||
|
|
||||||
double signal_timestamp_s;
|
double signal_timestamp_s;
|
||||||
|
@ -53,10 +53,32 @@
|
|||||||
#include "gnuplot_i.h"
|
#include "gnuplot_i.h"
|
||||||
#include "test_flags.h"
|
#include "test_flags.h"
|
||||||
|
|
||||||
DEFINE_bool(plot_gps_l1_tracking_test, false, "Plots results of GpsL1CADllPllTrackingTest with gnuplot");
|
|
||||||
DEFINE_double(CN0_dBHz, std::numeric_limits<double>::infinity(), "Enable noise generator and set the CN0 [dB-Hz]");
|
// Input signal configuration
|
||||||
|
DEFINE_bool(enable_external_signal_file, false, "Use an external signal file capture instead of the software-defined signal generator");
|
||||||
|
DEFINE_string(signal_file, std::string("gps_l1_capture.dat"), "Path of the external signal capture file");
|
||||||
|
DEFINE_double(CN0_dBHz_start, std::numeric_limits<double>::infinity(), "Enable noise generator and set the CN0 start sweep value [dB-Hz]");
|
||||||
|
DEFINE_double(CN0_dBHz_stop, std::numeric_limits<double>::infinity(), "Enable noise generator and set the CN0 stop sweep value [dB-Hz]");
|
||||||
|
DEFINE_double(CN0_dB_step, 3.0, "Noise generator CN0 sweep step value [dB]");
|
||||||
|
|
||||||
|
DEFINE_double(PLL_bw_hz_start, 40.0, "PLL Wide configuration start sweep value [Hz]");
|
||||||
|
DEFINE_double(PLL_bw_hz_stop, 40.0, "PLL Wide configuration stop sweep value [Hz]");
|
||||||
|
DEFINE_double(PLL_bw_hz_step, 5.0, "PLL Wide configuration sweep step value [Hz]");
|
||||||
|
|
||||||
|
DEFINE_double(DLL_bw_hz_start, 1.5, "DLL Wide configuration start sweep value [Hz]");
|
||||||
|
DEFINE_double(DLL_bw_hz_stop, 1.5, "DLL Wide configuration stop sweep value [Hz]");
|
||||||
|
DEFINE_double(DLL_bw_hz_step, 0.25, "DLL Wide configuration sweep step value [Hz]");
|
||||||
|
|
||||||
|
DEFINE_bool(plot_extra, false, "Enable or disable plots of the correlators output and constellation diagrams");
|
||||||
|
|
||||||
|
//Emulated acquisition configuration
|
||||||
|
|
||||||
|
//Tracking configuration
|
||||||
DEFINE_int32(extend_correlation_symbols, 1, "Set the tracking coherent correlation to N symbols (up to 20 for GPS L1 C/A)");
|
DEFINE_int32(extend_correlation_symbols, 1, "Set the tracking coherent correlation to N symbols (up to 20 for GPS L1 C/A)");
|
||||||
|
|
||||||
|
//Test output configuration
|
||||||
|
DEFINE_bool(plot_gps_l1_tracking_test, false, "Plots results of GpsL1CADllPllTrackingTest with gnuplot");
|
||||||
|
|
||||||
// ######## GNURADIO BLOCK MESSAGE RECEVER #########
|
// ######## GNURADIO BLOCK MESSAGE RECEVER #########
|
||||||
class GpsL1CADllPllTrackingTest_msg_rx;
|
class GpsL1CADllPllTrackingTest_msg_rx;
|
||||||
|
|
||||||
@ -130,20 +152,26 @@ public:
|
|||||||
std::string filename_rinex_obs = FLAGS_filename_rinex_obs;
|
std::string filename_rinex_obs = FLAGS_filename_rinex_obs;
|
||||||
std::string filename_raw_data = FLAGS_filename_raw_data;
|
std::string filename_raw_data = FLAGS_filename_raw_data;
|
||||||
|
|
||||||
int configure_generator();
|
int configure_generator(double CN0_dBHz, int file_idx);
|
||||||
int generate_signal();
|
int generate_signal();
|
||||||
void check_results_doppler(arma::vec& true_time_s,
|
std::vector<double> check_results_doppler(arma::vec& true_time_s,
|
||||||
arma::vec& true_value,
|
arma::vec& true_value,
|
||||||
arma::vec& meas_time_s,
|
arma::vec& meas_time_s,
|
||||||
arma::vec& meas_value);
|
arma::vec& meas_value,
|
||||||
void check_results_acc_carrier_phase(arma::vec& true_time_s,
|
double& mean_error,
|
||||||
|
double& std_dev_error);
|
||||||
|
std::vector<double> check_results_acc_carrier_phase(arma::vec& true_time_s,
|
||||||
arma::vec& true_value,
|
arma::vec& true_value,
|
||||||
arma::vec& meas_time_s,
|
arma::vec& meas_time_s,
|
||||||
arma::vec& meas_value);
|
arma::vec& meas_value,
|
||||||
void check_results_codephase(arma::vec& true_time_s,
|
double& mean_error,
|
||||||
|
double& std_dev_error);
|
||||||
|
std::vector<double> check_results_codephase(arma::vec& true_time_s,
|
||||||
arma::vec& true_value,
|
arma::vec& true_value,
|
||||||
arma::vec& meas_time_s,
|
arma::vec& meas_time_s,
|
||||||
arma::vec& meas_value);
|
arma::vec& meas_value,
|
||||||
|
double& mean_error,
|
||||||
|
double& std_dev_error);
|
||||||
|
|
||||||
GpsL1CADllPllTrackingTest()
|
GpsL1CADllPllTrackingTest()
|
||||||
{
|
{
|
||||||
@ -157,7 +185,11 @@ public:
|
|||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
void configure_receiver();
|
void configure_receiver(double PLL_wide_bw_hz,
|
||||||
|
double DLL_wide_bw_hz,
|
||||||
|
double PLL_narrow_bw_hz,
|
||||||
|
double DLL_narrow_bw_hz,
|
||||||
|
int extend_correlation_symbols);
|
||||||
|
|
||||||
gr::top_block_sptr top_block;
|
gr::top_block_sptr top_block;
|
||||||
std::shared_ptr<GNSSBlockFactory> factory;
|
std::shared_ptr<GNSSBlockFactory> factory;
|
||||||
@ -167,7 +199,7 @@ public:
|
|||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
int GpsL1CADllPllTrackingTest::configure_generator()
|
int GpsL1CADllPllTrackingTest::configure_generator(double CN0_dBHz, int file_idx)
|
||||||
{
|
{
|
||||||
// Configure signal generator
|
// Configure signal generator
|
||||||
generator_binary = FLAGS_generator_binary;
|
generator_binary = FLAGS_generator_binary;
|
||||||
@ -182,9 +214,9 @@ int GpsL1CADllPllTrackingTest::configure_generator()
|
|||||||
p2 = std::string("-obs_pos_file=") + std::string(FLAGS_dynamic_position);
|
p2 = std::string("-obs_pos_file=") + std::string(FLAGS_dynamic_position);
|
||||||
}
|
}
|
||||||
p3 = std::string("-rinex_obs_file=") + FLAGS_filename_rinex_obs; // RINEX 2.10 observation file output
|
p3 = std::string("-rinex_obs_file=") + FLAGS_filename_rinex_obs; // RINEX 2.10 observation file output
|
||||||
p4 = std::string("-sig_out_file=") + FLAGS_filename_raw_data; // Baseband signal output file. Will be stored in int8_t IQ multiplexed samples
|
p4 = std::string("-sig_out_file=") + FLAGS_filename_raw_data + std::to_string(file_idx); // Baseband signal output file. Will be stored in int8_t IQ multiplexed samples
|
||||||
p5 = std::string("-sampling_freq=") + std::to_string(baseband_sampling_freq); //Baseband sampling frequency [MSps]
|
p5 = std::string("-sampling_freq=") + std::to_string(baseband_sampling_freq); //Baseband sampling frequency [MSps]
|
||||||
p6 = std::string("-CN0_dBHz=") + std::to_string(FLAGS_CN0_dBHz); // Signal generator CN0
|
p6 = std::string("-CN0_dBHz=") + std::to_string(CN0_dBHz); // Signal generator CN0
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -193,7 +225,7 @@ int GpsL1CADllPllTrackingTest::generate_signal()
|
|||||||
{
|
{
|
||||||
int child_status;
|
int child_status;
|
||||||
|
|
||||||
char* const parmList[] = {&generator_binary[0], &generator_binary[0], &p1[0], &p2[0], &p3[0], &p4[0], &p5[0],&p6[0], NULL};
|
char* const parmList[] = {&generator_binary[0], &generator_binary[0], &p1[0], &p2[0], &p3[0], &p4[0], &p5[0], &p6[0], NULL};
|
||||||
|
|
||||||
int pid;
|
int pid;
|
||||||
if ((pid = fork()) == -1)
|
if ((pid = fork()) == -1)
|
||||||
@ -212,7 +244,12 @@ int GpsL1CADllPllTrackingTest::generate_signal()
|
|||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CADllPllTrackingTest::configure_receiver()
|
void GpsL1CADllPllTrackingTest::configure_receiver(
|
||||||
|
double PLL_wide_bw_hz,
|
||||||
|
double DLL_wide_bw_hz,
|
||||||
|
double PLL_narrow_bw_hz,
|
||||||
|
double DLL_narrow_bw_hz,
|
||||||
|
int extend_correlation_symbols)
|
||||||
{
|
{
|
||||||
gnss_synchro.Channel_ID = 0;
|
gnss_synchro.Channel_ID = 0;
|
||||||
gnss_synchro.System = 'G';
|
gnss_synchro.System = 'G';
|
||||||
@ -220,26 +257,40 @@ void GpsL1CADllPllTrackingTest::configure_receiver()
|
|||||||
signal.copy(gnss_synchro.Signal, 2, 0);
|
signal.copy(gnss_synchro.Signal, 2, 0);
|
||||||
gnss_synchro.PRN = FLAGS_test_satellite_PRN;
|
gnss_synchro.PRN = FLAGS_test_satellite_PRN;
|
||||||
|
|
||||||
|
config = std::make_shared<InMemoryConfiguration>();
|
||||||
config->set_property("GNSS-SDR.internal_fs_sps", std::to_string(baseband_sampling_freq));
|
config->set_property("GNSS-SDR.internal_fs_sps", std::to_string(baseband_sampling_freq));
|
||||||
// Set Tracking
|
// Set Tracking
|
||||||
config->set_property("Tracking_1C.implementation", implementation);
|
config->set_property("Tracking_1C.implementation", implementation);
|
||||||
config->set_property("Tracking_1C.item_type", "gr_complex");
|
config->set_property("Tracking_1C.item_type", "gr_complex");
|
||||||
config->set_property("Tracking_1C.pll_bw_hz", "20.0");
|
config->set_property("Tracking_1C.pll_bw_hz", std::to_string(PLL_wide_bw_hz));
|
||||||
config->set_property("Tracking_1C.dll_bw_hz", "1.5");
|
config->set_property("Tracking_1C.dll_bw_hz", std::to_string(DLL_wide_bw_hz));
|
||||||
config->set_property("Tracking_1C.early_late_space_chips", "0.5");
|
config->set_property("Tracking_1C.early_late_space_chips", "0.5");
|
||||||
config->set_property("Tracking_1C.extend_correlation_symbols", std::to_string(FLAGS_extend_correlation_symbols));
|
config->set_property("Tracking_1C.extend_correlation_symbols", std::to_string(extend_correlation_symbols));
|
||||||
config->set_property("Tracking_1C.pll_bw_narrow_hz", "2.0");
|
config->set_property("Tracking_1C.pll_bw_narrow_hz", std::to_string(PLL_narrow_bw_hz));
|
||||||
config->set_property("Tracking_1C.dll_bw_narrow_hz", "1.0");
|
config->set_property("Tracking_1C.dll_bw_narrow_hz", std::to_string(DLL_narrow_bw_hz));
|
||||||
config->set_property("Tracking_1C.early_late_space_narrow_chips", "0.5");
|
config->set_property("Tracking_1C.early_late_space_narrow_chips", "0.5");
|
||||||
config->set_property("Tracking_1C.dump", "true");
|
config->set_property("Tracking_1C.dump", "true");
|
||||||
config->set_property("Tracking_1C.dump_filename", "./tracking_ch_");
|
config->set_property("Tracking_1C.dump_filename", "./tracking_ch_");
|
||||||
|
|
||||||
|
std::cout << "*****************************************\n";
|
||||||
|
std::cout << "*** Tracking configuration parameters ***\n";
|
||||||
|
std::cout << "*****************************************\n";
|
||||||
|
std::cout << "pll_bw_hz: " << config->property("Tracking_1C.pll_bw_hz", 0.0) << " Hz\n";
|
||||||
|
std::cout << "dll_bw_hz: " << config->property("Tracking_1C.dll_bw_hz", 0.0) << " Hz\n";
|
||||||
|
std::cout << "pll_bw_narrow_hz: " << config->property("Tracking_1C.pll_bw_narrow_hz", 0.0) << " Hz\n";
|
||||||
|
std::cout << "dll_bw_narrow_hz: " << config->property("Tracking_1C.dll_bw_narrow_hz", 0.0) << " Hz\n";
|
||||||
|
std::cout << "extend_correlation_symbols: " << config->property("Tracking_1C.extend_correlation_symbols", 0) << " Symbols\n";
|
||||||
|
std::cout << "*****************************************\n";
|
||||||
|
std::cout << "*****************************************\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CADllPllTrackingTest::check_results_doppler(arma::vec& true_time_s,
|
std::vector<double> GpsL1CADllPllTrackingTest::check_results_doppler(arma::vec& true_time_s,
|
||||||
arma::vec& true_value,
|
arma::vec& true_value,
|
||||||
arma::vec& meas_time_s,
|
arma::vec& meas_time_s,
|
||||||
arma::vec& meas_value)
|
arma::vec& meas_value,
|
||||||
|
double& mean_error,
|
||||||
|
double& std_dev_error)
|
||||||
{
|
{
|
||||||
// 1. True value interpolation to match the measurement times
|
// 1. True value interpolation to match the measurement times
|
||||||
arma::vec true_value_interp;
|
arma::vec true_value_interp;
|
||||||
@ -256,6 +307,10 @@ void GpsL1CADllPllTrackingTest::check_results_doppler(arma::vec& true_time_s,
|
|||||||
arma::vec err;
|
arma::vec err;
|
||||||
|
|
||||||
err = meas_value - true_value_interp;
|
err = meas_value - true_value_interp;
|
||||||
|
|
||||||
|
//conversion between arma::vec and std:vector
|
||||||
|
std::vector<double> err_std_vector(err.colptr(0), err.colptr(0) + err.n_rows);
|
||||||
|
|
||||||
arma::vec err2 = arma::square(err);
|
arma::vec err2 = arma::square(err);
|
||||||
double rmse = sqrt(arma::mean(err2));
|
double rmse = sqrt(arma::mean(err2));
|
||||||
|
|
||||||
@ -263,6 +318,9 @@ void GpsL1CADllPllTrackingTest::check_results_doppler(arma::vec& true_time_s,
|
|||||||
double error_mean = arma::mean(err);
|
double error_mean = arma::mean(err);
|
||||||
double error_var = arma::var(err);
|
double error_var = arma::var(err);
|
||||||
|
|
||||||
|
mean_error = error_mean;
|
||||||
|
std_dev_error = sqrt(error_var);
|
||||||
|
|
||||||
// 4. Peaks
|
// 4. Peaks
|
||||||
double max_error = arma::max(err);
|
double max_error = arma::max(err);
|
||||||
double min_error = arma::min(err);
|
double min_error = arma::min(err);
|
||||||
@ -273,13 +331,16 @@ void GpsL1CADllPllTrackingTest::check_results_doppler(arma::vec& true_time_s,
|
|||||||
<< ", mean=" << error_mean
|
<< ", mean=" << error_mean
|
||||||
<< ", stdev=" << sqrt(error_var) << " (max,min)=" << max_error << "," << min_error << " [Hz]" << std::endl;
|
<< ", stdev=" << sqrt(error_var) << " (max,min)=" << max_error << "," << min_error << " [Hz]" << std::endl;
|
||||||
std::cout.precision(ss);
|
std::cout.precision(ss);
|
||||||
|
return err_std_vector;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CADllPllTrackingTest::check_results_acc_carrier_phase(arma::vec& true_time_s,
|
std::vector<double> GpsL1CADllPllTrackingTest::check_results_acc_carrier_phase(arma::vec& true_time_s,
|
||||||
arma::vec& true_value,
|
arma::vec& true_value,
|
||||||
arma::vec& meas_time_s,
|
arma::vec& meas_time_s,
|
||||||
arma::vec& meas_value)
|
arma::vec& meas_value,
|
||||||
|
double& mean_error,
|
||||||
|
double& std_dev_error)
|
||||||
{
|
{
|
||||||
// 1. True value interpolation to match the measurement times
|
// 1. True value interpolation to match the measurement times
|
||||||
arma::vec true_value_interp;
|
arma::vec true_value_interp;
|
||||||
@ -296,12 +357,17 @@ void GpsL1CADllPllTrackingTest::check_results_acc_carrier_phase(arma::vec& true_
|
|||||||
arma::vec err;
|
arma::vec err;
|
||||||
err = meas_value - true_value_interp;
|
err = meas_value - true_value_interp;
|
||||||
arma::vec err2 = arma::square(err);
|
arma::vec err2 = arma::square(err);
|
||||||
|
//conversion between arma::vec and std:vector
|
||||||
|
std::vector<double> err_std_vector(err.colptr(0), err.colptr(0) + err.n_rows);
|
||||||
|
|
||||||
double rmse = sqrt(arma::mean(err2));
|
double rmse = sqrt(arma::mean(err2));
|
||||||
|
|
||||||
// 3. Mean err and variance
|
// 3. Mean err and variance
|
||||||
double error_mean = arma::mean(err);
|
double error_mean = arma::mean(err);
|
||||||
double error_var = arma::var(err);
|
double error_var = arma::var(err);
|
||||||
|
|
||||||
|
mean_error = error_mean;
|
||||||
|
std_dev_error = sqrt(error_var);
|
||||||
// 4. Peaks
|
// 4. Peaks
|
||||||
double max_error = arma::max(err);
|
double max_error = arma::max(err);
|
||||||
double min_error = arma::min(err);
|
double min_error = arma::min(err);
|
||||||
@ -312,13 +378,16 @@ void GpsL1CADllPllTrackingTest::check_results_acc_carrier_phase(arma::vec& true_
|
|||||||
<< ", mean=" << error_mean
|
<< ", mean=" << error_mean
|
||||||
<< ", stdev=" << sqrt(error_var) << " (max,min)=" << max_error << "," << min_error << " [Hz]" << std::endl;
|
<< ", stdev=" << sqrt(error_var) << " (max,min)=" << max_error << "," << min_error << " [Hz]" << std::endl;
|
||||||
std::cout.precision(ss);
|
std::cout.precision(ss);
|
||||||
|
return err_std_vector;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CADllPllTrackingTest::check_results_codephase(arma::vec& true_time_s,
|
std::vector<double> GpsL1CADllPllTrackingTest::check_results_codephase(arma::vec& true_time_s,
|
||||||
arma::vec& true_value,
|
arma::vec& true_value,
|
||||||
arma::vec& meas_time_s,
|
arma::vec& meas_time_s,
|
||||||
arma::vec& meas_value)
|
arma::vec& meas_value,
|
||||||
|
double& mean_error,
|
||||||
|
double& std_dev_error)
|
||||||
{
|
{
|
||||||
// 1. True value interpolation to match the measurement times
|
// 1. True value interpolation to match the measurement times
|
||||||
arma::vec true_value_interp;
|
arma::vec true_value_interp;
|
||||||
@ -335,6 +404,9 @@ void GpsL1CADllPllTrackingTest::check_results_codephase(arma::vec& true_time_s,
|
|||||||
arma::vec err;
|
arma::vec err;
|
||||||
|
|
||||||
err = meas_value - true_value_interp;
|
err = meas_value - true_value_interp;
|
||||||
|
//conversion between arma::vec and std:vector
|
||||||
|
std::vector<double> err_std_vector(err.colptr(0), err.colptr(0) + err.n_rows);
|
||||||
|
|
||||||
arma::vec err2 = arma::square(err);
|
arma::vec err2 = arma::square(err);
|
||||||
double rmse = sqrt(arma::mean(err2));
|
double rmse = sqrt(arma::mean(err2));
|
||||||
|
|
||||||
@ -342,6 +414,9 @@ void GpsL1CADllPllTrackingTest::check_results_codephase(arma::vec& true_time_s,
|
|||||||
double error_mean = arma::mean(err);
|
double error_mean = arma::mean(err);
|
||||||
double error_var = arma::var(err);
|
double error_var = arma::var(err);
|
||||||
|
|
||||||
|
mean_error = error_mean;
|
||||||
|
std_dev_error = sqrt(error_var);
|
||||||
|
|
||||||
// 4. Peaks
|
// 4. Peaks
|
||||||
double max_error = arma::max(err);
|
double max_error = arma::max(err);
|
||||||
double min_error = arma::min(err);
|
double min_error = arma::min(err);
|
||||||
@ -352,52 +427,174 @@ void GpsL1CADllPllTrackingTest::check_results_codephase(arma::vec& true_time_s,
|
|||||||
<< ", mean=" << error_mean
|
<< ", mean=" << error_mean
|
||||||
<< ", stdev=" << sqrt(error_var) << " (max,min)=" << max_error << "," << min_error << " [Chips]" << std::endl;
|
<< ", stdev=" << sqrt(error_var) << " (max,min)=" << max_error << "," << min_error << " [Chips]" << std::endl;
|
||||||
std::cout.precision(ss);
|
std::cout.precision(ss);
|
||||||
|
return err_std_vector;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
||||||
{
|
{
|
||||||
// Configure the signal generator
|
//*************************************************
|
||||||
configure_generator();
|
//***** STEP 2: Prepare the parameters sweep ******
|
||||||
|
//*************************************************
|
||||||
|
|
||||||
|
std::vector<double> generator_CN0_values;
|
||||||
|
|
||||||
|
|
||||||
|
//data containers for config param sweep
|
||||||
|
std::vector<std::vector<double>> mean_doppler_error_sweep; //swep config param and cn0 sweep
|
||||||
|
std::vector<std::vector<double>> std_dev_doppler_error_sweep; //swep config param and cn0 sweep
|
||||||
|
|
||||||
|
std::vector<std::vector<double>> mean_code_phase_error_sweep; //swep config param and cn0 sweep
|
||||||
|
std::vector<std::vector<double>> std_dev_code_phase_error_sweep; //swep config param and cn0 sweep
|
||||||
|
|
||||||
|
std::vector<std::vector<double>> mean_carrier_phase_error_sweep; //swep config param and cn0 sweep
|
||||||
|
std::vector<std::vector<double>> std_dev_carrier_phase_error_sweep; //swep config param and cn0 sweep
|
||||||
|
|
||||||
|
std::vector<std::vector<double>> trk_valid_timestamp_s_sweep;
|
||||||
|
|
||||||
|
if (FLAGS_CN0_dBHz_start == FLAGS_CN0_dBHz_stop)
|
||||||
|
{
|
||||||
|
generator_CN0_values.push_back(FLAGS_CN0_dBHz_start);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for (double cn0 = FLAGS_CN0_dBHz_start; cn0 > FLAGS_CN0_dBHz_stop; cn0 = cn0 - FLAGS_CN0_dB_step)
|
||||||
|
{
|
||||||
|
generator_CN0_values.push_back(cn0);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int test_satellite_PRN = 0;
|
||||||
|
double acq_delay_samples = 0.0;
|
||||||
|
double acq_doppler_hz = 0.0;
|
||||||
|
tracking_true_obs_reader true_obs_data;
|
||||||
|
|
||||||
|
|
||||||
|
//*********************************************
|
||||||
|
//***** STEP 3: Generate the input signal *****
|
||||||
|
//*********************************************
|
||||||
|
// use generator or use an external capture file
|
||||||
|
if (FLAGS_enable_external_signal_file)
|
||||||
|
{
|
||||||
|
//todo: create and configure an acquisition block and perform an acquisition to obtain the synchronization parameters
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
// Configure the signal generator
|
||||||
|
configure_generator(generator_CN0_values.at(current_cn0_idx), current_cn0_idx);
|
||||||
// Generate signal raw signal samples and observations RINEX file
|
// Generate signal raw signal samples and observations RINEX file
|
||||||
if (FLAGS_disable_generator == false)
|
if (FLAGS_disable_generator == false)
|
||||||
{
|
{
|
||||||
generate_signal();
|
generate_signal();
|
||||||
}
|
}
|
||||||
|
|
||||||
std::chrono::time_point<std::chrono::system_clock> start, end;
|
|
||||||
|
|
||||||
configure_receiver();
|
|
||||||
|
|
||||||
// open true observables log file written by the simulator
|
// open true observables log file written by the simulator
|
||||||
tracking_true_obs_reader true_obs_data;
|
}
|
||||||
int test_satellite_PRN = FLAGS_test_satellite_PRN;
|
}
|
||||||
std::cout << "Testing satellite PRN=" << test_satellite_PRN << std::endl;
|
|
||||||
|
|
||||||
|
// CONFIG PARAM SWEEP LOOP
|
||||||
|
std::vector<double> PLL_wide_bw_values;
|
||||||
|
std::vector<double> DLL_wide_bw_values;
|
||||||
|
|
||||||
|
|
||||||
|
if (FLAGS_PLL_bw_hz_start == FLAGS_PLL_bw_hz_stop)
|
||||||
|
{
|
||||||
|
if (FLAGS_DLL_bw_hz_start == FLAGS_DLL_bw_hz_stop)
|
||||||
|
{
|
||||||
|
//NO PLL/DLL BW sweep
|
||||||
|
PLL_wide_bw_values.push_back(FLAGS_PLL_bw_hz_start);
|
||||||
|
DLL_wide_bw_values.push_back(FLAGS_DLL_bw_hz_start);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//DLL BW Sweep
|
||||||
|
for (double dll_bw = FLAGS_DLL_bw_hz_start; dll_bw > FLAGS_DLL_bw_hz_stop; dll_bw = dll_bw - FLAGS_DLL_bw_hz_step)
|
||||||
|
{
|
||||||
|
PLL_wide_bw_values.push_back(FLAGS_PLL_bw_hz_start);
|
||||||
|
DLL_wide_bw_values.push_back(dll_bw);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//PLL BW Sweep
|
||||||
|
for (double pll_bw = FLAGS_PLL_bw_hz_start; pll_bw > FLAGS_PLL_bw_hz_stop; pll_bw = pll_bw - FLAGS_PLL_bw_hz_step)
|
||||||
|
{
|
||||||
|
PLL_wide_bw_values.push_back(pll_bw);
|
||||||
|
DLL_wide_bw_values.push_back(FLAGS_DLL_bw_hz_start);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int config_idx = 0; config_idx < PLL_wide_bw_values.size(); config_idx++)
|
||||||
|
{
|
||||||
|
//CN0 LOOP
|
||||||
|
// data containers for CN0 sweep
|
||||||
|
std::vector<std::vector<double>> prompt_sweep;
|
||||||
|
std::vector<std::vector<double>> early_sweep;
|
||||||
|
std::vector<std::vector<double>> late_sweep;
|
||||||
|
std::vector<std::vector<double>> promptI_sweep;
|
||||||
|
std::vector<std::vector<double>> promptQ_sweep;
|
||||||
|
std::vector<std::vector<double>> CN0_dBHz_sweep;
|
||||||
|
std::vector<std::vector<double>> trk_timestamp_s_sweep;
|
||||||
|
|
||||||
|
std::vector<std::vector<double>> doppler_error_sweep;
|
||||||
|
std::vector<std::vector<double>> code_phase_error_sweep;
|
||||||
|
std::vector<std::vector<double>> acc_carrier_phase_error_sweep;
|
||||||
|
|
||||||
|
std::vector<double> mean_doppler_error;
|
||||||
|
std::vector<double> std_dev_doppler_error;
|
||||||
|
std::vector<double> mean_code_phase_error;
|
||||||
|
std::vector<double> std_dev_code_phase_error;
|
||||||
|
std::vector<double> mean_carrier_phase_error;
|
||||||
|
std::vector<double> std_dev_carrier_phase_error;
|
||||||
|
|
||||||
|
configure_receiver(PLL_wide_bw_values.at(config_idx),
|
||||||
|
DLL_wide_bw_values.at(config_idx),
|
||||||
|
2.0,
|
||||||
|
1.0,
|
||||||
|
FLAGS_extend_correlation_symbols);
|
||||||
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
//******************************************************************************************
|
||||||
|
//***** Obtain the initial signal sinchronization parameters (emulating an acquisition) ****
|
||||||
|
//******************************************************************************************
|
||||||
|
if (!FLAGS_enable_external_signal_file)
|
||||||
|
{
|
||||||
|
test_satellite_PRN = FLAGS_test_satellite_PRN;
|
||||||
std::string true_obs_file = std::string("./gps_l1_ca_obs_prn");
|
std::string true_obs_file = std::string("./gps_l1_ca_obs_prn");
|
||||||
true_obs_file.append(std::to_string(test_satellite_PRN));
|
true_obs_file.append(std::to_string(test_satellite_PRN));
|
||||||
true_obs_file.append(".dat");
|
true_obs_file.append(".dat");
|
||||||
|
true_obs_data.close_obs_file();
|
||||||
ASSERT_EQ(true_obs_data.open_obs_file(true_obs_file), true) << "Failure opening true observables file";
|
ASSERT_EQ(true_obs_data.open_obs_file(true_obs_file), true) << "Failure opening true observables file";
|
||||||
|
|
||||||
top_block = gr::make_top_block("Tracking test");
|
|
||||||
|
|
||||||
std::shared_ptr<GNSSBlockInterface> trk_ = factory->GetBlock(config, "Tracking_1C", implementation, 1, 1);
|
|
||||||
std::shared_ptr<TrackingInterface> tracking = std::dynamic_pointer_cast<TrackingInterface>(trk_); //std::make_shared<GpsL1CaDllPllCAidTracking>(config.get(), "Tracking_1C", 1, 1);
|
|
||||||
|
|
||||||
boost::shared_ptr<GpsL1CADllPllTrackingTest_msg_rx> msg_rx = GpsL1CADllPllTrackingTest_msg_rx_make();
|
|
||||||
|
|
||||||
// load acquisition data based on the first epoch of the true observations
|
// load acquisition data based on the first epoch of the true observations
|
||||||
ASSERT_EQ(true_obs_data.read_binary_obs(), true)
|
ASSERT_EQ(true_obs_data.read_binary_obs(), true)
|
||||||
<< "Failure reading true tracking dump file." << std::endl
|
<< "Failure reading true tracking dump file." << std::endl
|
||||||
<< "Maybe sat PRN #" + std::to_string(FLAGS_test_satellite_PRN) +
|
<< "Maybe sat PRN #" + std::to_string(FLAGS_test_satellite_PRN) +
|
||||||
" is not available?";
|
" is not available?";
|
||||||
|
std::cout << "Testing satellite PRN=" << test_satellite_PRN << std::endl;
|
||||||
|
std::cout << "Initial Doppler [Hz]=" << true_obs_data.doppler_l1_hz << " Initial code delay [Chips]=" << true_obs_data.prn_delay_chips << std::endl;
|
||||||
|
acq_doppler_hz = true_obs_data.doppler_l1_hz;
|
||||||
|
acq_delay_samples = (GPS_L1_CA_CODE_LENGTH_CHIPS - true_obs_data.prn_delay_chips / GPS_L1_CA_CODE_LENGTH_CHIPS) * static_cast<double>(baseband_sampling_freq) * GPS_L1_CA_CODE_PERIOD;
|
||||||
// restart the epoch counter
|
// restart the epoch counter
|
||||||
true_obs_data.restart();
|
true_obs_data.restart();
|
||||||
|
}
|
||||||
|
|
||||||
std::cout << "Initial Doppler [Hz]=" << true_obs_data.doppler_l1_hz << " Initial code delay [Chips]=" << true_obs_data.prn_delay_chips << std::endl;
|
|
||||||
gnss_synchro.Acq_delay_samples = (GPS_L1_CA_CODE_LENGTH_CHIPS - true_obs_data.prn_delay_chips / GPS_L1_CA_CODE_LENGTH_CHIPS) * static_cast<double>(baseband_sampling_freq) * GPS_L1_CA_CODE_PERIOD;
|
//***** STEP 4: Configure the signal tracking parameters *****
|
||||||
gnss_synchro.Acq_doppler_hz = true_obs_data.doppler_l1_hz;
|
//************************************************************
|
||||||
|
std::chrono::time_point<std::chrono::system_clock> start, end;
|
||||||
|
|
||||||
|
top_block = gr::make_top_block("Tracking test");
|
||||||
|
|
||||||
|
std::shared_ptr<GNSSBlockInterface> trk_ = factory->GetBlock(config, "Tracking_1C", implementation, 1, 1);
|
||||||
|
std::shared_ptr<TrackingInterface> tracking = std::dynamic_pointer_cast<TrackingInterface>(trk_);
|
||||||
|
|
||||||
|
boost::shared_ptr<GpsL1CADllPllTrackingTest_msg_rx> msg_rx = GpsL1CADllPllTrackingTest_msg_rx_make();
|
||||||
|
|
||||||
|
gnss_synchro.Acq_delay_samples = acq_delay_samples;
|
||||||
|
gnss_synchro.Acq_doppler_hz = acq_doppler_hz;
|
||||||
gnss_synchro.Acq_samplestamp_samples = 0;
|
gnss_synchro.Acq_samplestamp_samples = 0;
|
||||||
|
|
||||||
ASSERT_NO_THROW({
|
ASSERT_NO_THROW({
|
||||||
@ -413,7 +610,7 @@ TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
|||||||
}) << "Failure connecting tracking to the top_block.";
|
}) << "Failure connecting tracking to the top_block.";
|
||||||
|
|
||||||
ASSERT_NO_THROW({
|
ASSERT_NO_THROW({
|
||||||
std::string file = "./" + filename_raw_data;
|
std::string file = "./" + filename_raw_data + std::to_string(current_cn0_idx);
|
||||||
const char* file_name = file.c_str();
|
const char* file_name = file.c_str();
|
||||||
gr::blocks::file_source::sptr file_source = gr::blocks::file_source::make(sizeof(int8_t), file_name, false);
|
gr::blocks::file_source::sptr file_source = gr::blocks::file_source::make(sizeof(int8_t), file_name, false);
|
||||||
gr::blocks::interleaved_char_to_complex::sptr gr_interleaved_char_to_complex = gr::blocks::interleaved_char_to_complex::make();
|
gr::blocks::interleaved_char_to_complex::sptr gr_interleaved_char_to_complex = gr::blocks::interleaved_char_to_complex::make();
|
||||||
@ -424,6 +621,10 @@ TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
|||||||
top_block->msg_connect(tracking->get_right_block(), pmt::mp("events"), msg_rx, pmt::mp("events"));
|
top_block->msg_connect(tracking->get_right_block(), pmt::mp("events"), msg_rx, pmt::mp("events"));
|
||||||
}) << "Failure connecting the blocks of tracking test.";
|
}) << "Failure connecting the blocks of tracking test.";
|
||||||
|
|
||||||
|
|
||||||
|
//********************************************************************
|
||||||
|
//***** STEP 5: Perform the signal tracking and read the results *****
|
||||||
|
//********************************************************************
|
||||||
tracking->start_tracking();
|
tracking->start_tracking();
|
||||||
|
|
||||||
EXPECT_NO_THROW({
|
EXPECT_NO_THROW({
|
||||||
@ -432,16 +633,78 @@ TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
|||||||
end = std::chrono::system_clock::now();
|
end = std::chrono::system_clock::now();
|
||||||
}) << "Failure running the top_block.";
|
}) << "Failure running the top_block.";
|
||||||
|
|
||||||
// check results
|
std::chrono::duration<double> elapsed_seconds = end - start;
|
||||||
// load the true values
|
std::cout << "Signal tracking completed in " << elapsed_seconds.count() << " seconds" << std::endl;
|
||||||
long int nepoch = true_obs_data.num_epochs();
|
|
||||||
std::cout << "True observation epochs=" << nepoch << std::endl;
|
|
||||||
|
|
||||||
arma::vec true_timestamp_s = arma::zeros(nepoch, 1);
|
//check results
|
||||||
arma::vec true_acc_carrier_phase_cycles = arma::zeros(nepoch, 1);
|
//load the measured values
|
||||||
arma::vec true_Doppler_Hz = arma::zeros(nepoch, 1);
|
tracking_dump_reader trk_dump;
|
||||||
arma::vec true_prn_delay_chips = arma::zeros(nepoch, 1);
|
ASSERT_EQ(trk_dump.open_obs_file(std::string("./tracking_ch_0.dat")), true)
|
||||||
arma::vec true_tow_s = arma::zeros(nepoch, 1);
|
<< "Failure opening tracking dump file";
|
||||||
|
|
||||||
|
long int n_measured_epochs = trk_dump.num_epochs();
|
||||||
|
std::cout << "Measured observation epochs=" << n_measured_epochs << std::endl;
|
||||||
|
|
||||||
|
arma::vec trk_timestamp_s = arma::zeros(n_measured_epochs, 1);
|
||||||
|
arma::vec trk_acc_carrier_phase_cycles = arma::zeros(n_measured_epochs, 1);
|
||||||
|
arma::vec trk_Doppler_Hz = arma::zeros(n_measured_epochs, 1);
|
||||||
|
arma::vec trk_prn_delay_chips = arma::zeros(n_measured_epochs, 1);
|
||||||
|
|
||||||
|
long int epoch_counter = 0;
|
||||||
|
|
||||||
|
std::vector<double> timestamp_s;
|
||||||
|
std::vector<double> prompt;
|
||||||
|
std::vector<double> early;
|
||||||
|
std::vector<double> late;
|
||||||
|
std::vector<double> promptI;
|
||||||
|
std::vector<double> promptQ;
|
||||||
|
std::vector<double> CN0_dBHz;
|
||||||
|
while (trk_dump.read_binary_obs())
|
||||||
|
{
|
||||||
|
trk_timestamp_s(epoch_counter) = static_cast<double>(trk_dump.PRN_start_sample_count) / static_cast<double>(baseband_sampling_freq);
|
||||||
|
trk_acc_carrier_phase_cycles(epoch_counter) = trk_dump.acc_carrier_phase_rad / GPS_TWO_PI;
|
||||||
|
trk_Doppler_Hz(epoch_counter) = trk_dump.carrier_doppler_hz;
|
||||||
|
double delay_chips = GPS_L1_CA_CODE_LENGTH_CHIPS - GPS_L1_CA_CODE_LENGTH_CHIPS * (fmod((static_cast<double>(trk_dump.PRN_start_sample_count) + trk_dump.aux1) / static_cast<double>(baseband_sampling_freq), 1.0e-3) / 1.0e-3);
|
||||||
|
|
||||||
|
trk_prn_delay_chips(epoch_counter) = delay_chips;
|
||||||
|
|
||||||
|
timestamp_s.push_back(trk_timestamp_s(epoch_counter));
|
||||||
|
prompt.push_back(trk_dump.abs_P);
|
||||||
|
early.push_back(trk_dump.abs_E);
|
||||||
|
late.push_back(trk_dump.abs_L);
|
||||||
|
promptI.push_back(trk_dump.prompt_I);
|
||||||
|
promptQ.push_back(trk_dump.prompt_Q);
|
||||||
|
CN0_dBHz.push_back(trk_dump.CN0_SNV_dB_Hz);
|
||||||
|
|
||||||
|
epoch_counter++;
|
||||||
|
}
|
||||||
|
trk_timestamp_s_sweep.push_back(timestamp_s);
|
||||||
|
prompt_sweep.push_back(prompt);
|
||||||
|
early_sweep.push_back(early);
|
||||||
|
late_sweep.push_back(late);
|
||||||
|
promptI_sweep.push_back(promptI);
|
||||||
|
promptQ_sweep.push_back(promptQ);
|
||||||
|
CN0_dBHz_sweep.push_back(CN0_dBHz);
|
||||||
|
|
||||||
|
//***********************************************************
|
||||||
|
//***** STEP 6: Compare with true values (if available) *****
|
||||||
|
//***********************************************************
|
||||||
|
if (!FLAGS_enable_external_signal_file)
|
||||||
|
{
|
||||||
|
std::vector<double> doppler_error_hz;
|
||||||
|
std::vector<double> code_phase_error_chips;
|
||||||
|
std::vector<double> acc_carrier_phase_hz;
|
||||||
|
try
|
||||||
|
{
|
||||||
|
// load the true values
|
||||||
|
long int n_true_epochs = true_obs_data.num_epochs();
|
||||||
|
std::cout << "True observation epochs=" << n_true_epochs << std::endl;
|
||||||
|
|
||||||
|
arma::vec true_timestamp_s = arma::zeros(n_true_epochs, 1);
|
||||||
|
arma::vec true_acc_carrier_phase_cycles = arma::zeros(n_true_epochs, 1);
|
||||||
|
arma::vec true_Doppler_Hz = arma::zeros(n_true_epochs, 1);
|
||||||
|
arma::vec true_prn_delay_chips = arma::zeros(n_true_epochs, 1);
|
||||||
|
arma::vec true_tow_s = arma::zeros(n_true_epochs, 1);
|
||||||
|
|
||||||
long int epoch_counter = 0;
|
long int epoch_counter = 0;
|
||||||
while (true_obs_data.read_binary_obs())
|
while (true_obs_data.read_binary_obs())
|
||||||
@ -453,49 +716,9 @@ TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
|||||||
true_tow_s(epoch_counter) = true_obs_data.tow;
|
true_tow_s(epoch_counter) = true_obs_data.tow;
|
||||||
epoch_counter++;
|
epoch_counter++;
|
||||||
}
|
}
|
||||||
|
|
||||||
//load the measured values
|
|
||||||
tracking_dump_reader trk_dump;
|
|
||||||
|
|
||||||
ASSERT_EQ(trk_dump.open_obs_file(std::string("./tracking_ch_0.dat")), true)
|
|
||||||
<< "Failure opening tracking dump file";
|
|
||||||
|
|
||||||
nepoch = trk_dump.num_epochs();
|
|
||||||
std::cout << "Measured observation epochs=" << nepoch << std::endl;
|
|
||||||
|
|
||||||
arma::vec trk_timestamp_s = arma::zeros(nepoch, 1);
|
|
||||||
arma::vec trk_acc_carrier_phase_cycles = arma::zeros(nepoch, 1);
|
|
||||||
arma::vec trk_Doppler_Hz = arma::zeros(nepoch, 1);
|
|
||||||
arma::vec trk_prn_delay_chips = arma::zeros(nepoch, 1);
|
|
||||||
|
|
||||||
std::vector<double> prompt;
|
|
||||||
std::vector<double> early;
|
|
||||||
std::vector<double> late;
|
|
||||||
std::vector<double> promptI;
|
|
||||||
std::vector<double> promptQ;
|
|
||||||
std::vector<double> CN0_dBHz;
|
|
||||||
|
|
||||||
epoch_counter = 0;
|
|
||||||
while (trk_dump.read_binary_obs())
|
|
||||||
{
|
|
||||||
trk_timestamp_s(epoch_counter) = static_cast<double>(trk_dump.PRN_start_sample_count) / static_cast<double>(baseband_sampling_freq);
|
|
||||||
trk_acc_carrier_phase_cycles(epoch_counter) = trk_dump.acc_carrier_phase_rad / GPS_TWO_PI;
|
|
||||||
trk_Doppler_Hz(epoch_counter) = trk_dump.carrier_doppler_hz;
|
|
||||||
|
|
||||||
double delay_chips = GPS_L1_CA_CODE_LENGTH_CHIPS - GPS_L1_CA_CODE_LENGTH_CHIPS * (fmod((static_cast<double>(trk_dump.PRN_start_sample_count) + trk_dump.aux1) / static_cast<double>(baseband_sampling_freq), 1.0e-3) / 1.0e-3);
|
|
||||||
|
|
||||||
trk_prn_delay_chips(epoch_counter) = delay_chips;
|
|
||||||
epoch_counter++;
|
|
||||||
prompt.push_back(trk_dump.abs_P);
|
|
||||||
early.push_back(trk_dump.abs_E);
|
|
||||||
late.push_back(trk_dump.abs_L);
|
|
||||||
promptI.push_back(trk_dump.prompt_I);
|
|
||||||
promptQ.push_back(trk_dump.prompt_Q);
|
|
||||||
CN0_dBHz.push_back(trk_dump.CN0_SNV_dB_Hz);
|
|
||||||
}
|
|
||||||
|
|
||||||
// Align initial measurements and cut the tracking pull-in transitory
|
// Align initial measurements and cut the tracking pull-in transitory
|
||||||
double pull_in_offset_s = 1.0;
|
double pull_in_offset_s = 1.0;
|
||||||
|
|
||||||
arma::uvec initial_meas_point = arma::find(trk_timestamp_s >= (true_timestamp_s(0) + pull_in_offset_s), 1, "first");
|
arma::uvec initial_meas_point = arma::find(trk_timestamp_s >= (true_timestamp_s(0) + pull_in_offset_s), 1, "first");
|
||||||
|
|
||||||
trk_timestamp_s = trk_timestamp_s.subvec(initial_meas_point(0), trk_timestamp_s.size() - 1);
|
trk_timestamp_s = trk_timestamp_s.subvec(initial_meas_point(0), trk_timestamp_s.size() - 1);
|
||||||
@ -503,13 +726,58 @@ TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
|||||||
trk_Doppler_Hz = trk_Doppler_Hz.subvec(initial_meas_point(0), trk_Doppler_Hz.size() - 1);
|
trk_Doppler_Hz = trk_Doppler_Hz.subvec(initial_meas_point(0), trk_Doppler_Hz.size() - 1);
|
||||||
trk_prn_delay_chips = trk_prn_delay_chips.subvec(initial_meas_point(0), trk_prn_delay_chips.size() - 1);
|
trk_prn_delay_chips = trk_prn_delay_chips.subvec(initial_meas_point(0), trk_prn_delay_chips.size() - 1);
|
||||||
|
|
||||||
check_results_doppler(true_timestamp_s, true_Doppler_Hz, trk_timestamp_s, trk_Doppler_Hz);
|
|
||||||
check_results_codephase(true_timestamp_s, true_prn_delay_chips, trk_timestamp_s, trk_prn_delay_chips);
|
|
||||||
check_results_acc_carrier_phase(true_timestamp_s, true_acc_carrier_phase_cycles, trk_timestamp_s, trk_acc_carrier_phase_cycles);
|
|
||||||
|
|
||||||
std::chrono::duration<double> elapsed_seconds = end - start;
|
double mean_error;
|
||||||
std::cout << "Signal tracking completed in " << elapsed_seconds.count() * 1e6 << " microseconds" << std::endl;
|
double std_dev_error;
|
||||||
|
|
||||||
|
doppler_error_hz = check_results_doppler(true_timestamp_s, true_Doppler_Hz, trk_timestamp_s, trk_Doppler_Hz, mean_error, std_dev_error);
|
||||||
|
mean_doppler_error.push_back(mean_error);
|
||||||
|
std_dev_doppler_error.push_back(std_dev_error);
|
||||||
|
|
||||||
|
code_phase_error_chips = check_results_codephase(true_timestamp_s, true_prn_delay_chips, trk_timestamp_s, trk_prn_delay_chips, mean_error, std_dev_error);
|
||||||
|
mean_code_phase_error.push_back(mean_error);
|
||||||
|
std_dev_code_phase_error.push_back(std_dev_error);
|
||||||
|
|
||||||
|
acc_carrier_phase_hz = check_results_acc_carrier_phase(true_timestamp_s, true_acc_carrier_phase_cycles, trk_timestamp_s, trk_acc_carrier_phase_cycles, mean_error, std_dev_error);
|
||||||
|
mean_carrier_phase_error.push_back(mean_error);
|
||||||
|
std_dev_carrier_phase_error.push_back(std_dev_error);
|
||||||
|
|
||||||
|
//save tracking measurement timestamps to std::vector
|
||||||
|
std::vector<double> vector_trk_timestamp_s(trk_timestamp_s.colptr(0), trk_timestamp_s.colptr(0) + trk_timestamp_s.n_rows);
|
||||||
|
trk_valid_timestamp_s_sweep.push_back(vector_trk_timestamp_s);
|
||||||
|
|
||||||
|
doppler_error_sweep.push_back(doppler_error_hz);
|
||||||
|
code_phase_error_sweep.push_back(code_phase_error_chips);
|
||||||
|
acc_carrier_phase_error_sweep.push_back(acc_carrier_phase_hz);
|
||||||
|
}
|
||||||
|
catch (const std::exception& ex)
|
||||||
|
{
|
||||||
|
std::cout << "Tracking output could not be used, possible loss of lock " << ex.what() << std::endl;
|
||||||
|
|
||||||
|
std::vector<double> vector_trk_timestamp_s;
|
||||||
|
trk_valid_timestamp_s_sweep.push_back(vector_trk_timestamp_s);
|
||||||
|
doppler_error_sweep.push_back(doppler_error_hz);
|
||||||
|
code_phase_error_sweep.push_back(code_phase_error_chips);
|
||||||
|
acc_carrier_phase_error_sweep.push_back(acc_carrier_phase_hz);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
} //CN0 LOOP
|
||||||
|
|
||||||
|
if (!FLAGS_enable_external_signal_file)
|
||||||
|
{
|
||||||
|
mean_doppler_error_sweep.push_back(mean_doppler_error);
|
||||||
|
std_dev_doppler_error_sweep.push_back(std_dev_doppler_error);
|
||||||
|
mean_code_phase_error_sweep.push_back(mean_code_phase_error);
|
||||||
|
std_dev_code_phase_error_sweep.push_back(std_dev_code_phase_error);
|
||||||
|
mean_carrier_phase_error_sweep.push_back(mean_carrier_phase_error);
|
||||||
|
std_dev_carrier_phase_error_sweep.push_back(std_dev_carrier_phase_error);
|
||||||
|
}
|
||||||
|
|
||||||
|
std::cout << "A\n\n\n";
|
||||||
|
//********************************
|
||||||
|
//***** STEP 7: Plot results *****
|
||||||
|
//********************************
|
||||||
if (FLAGS_plot_gps_l1_tracking_test == true)
|
if (FLAGS_plot_gps_l1_tracking_test == true)
|
||||||
{
|
{
|
||||||
const std::string gnuplot_executable(FLAGS_gnuplot_executable);
|
const std::string gnuplot_executable(FLAGS_gnuplot_executable);
|
||||||
@ -527,50 +795,204 @@ TEST_F(GpsL1CADllPllTrackingTest, ValidationOfResults)
|
|||||||
boost::filesystem::path dir = p.parent_path();
|
boost::filesystem::path dir = p.parent_path();
|
||||||
std::string gnuplot_path = dir.native();
|
std::string gnuplot_path = dir.native();
|
||||||
Gnuplot::set_GNUPlotPath(gnuplot_path);
|
Gnuplot::set_GNUPlotPath(gnuplot_path);
|
||||||
|
unsigned int decimate = static_cast<unsigned int>(FLAGS_plot_decimate);
|
||||||
|
|
||||||
std::vector<double> timevec;
|
if (FLAGS_plot_extra)
|
||||||
double t = 0.0;
|
{
|
||||||
for (auto it = prompt.begin(); it != prompt.end(); it++)
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
{
|
{
|
||||||
timevec.push_back(t);
|
|
||||||
t = t + GPS_L1_CA_CODE_PERIOD;
|
|
||||||
}
|
|
||||||
Gnuplot g1("linespoints");
|
Gnuplot g1("linespoints");
|
||||||
g1.set_title("GPS L1 C/A signal tracking correlators' output (satellite PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
g1.showonscreen(); // window output
|
||||||
|
g1.set_title(std::to_string(generator_CN0_values.at(current_cn0_idx)) + " dB-Hz, " + "PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_idx)) + "," + std::to_string(DLL_wide_bw_values.at(config_idx)) + " Hz" + "GPS L1 C/A (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
g1.set_grid();
|
g1.set_grid();
|
||||||
g1.set_xlabel("Time [s]");
|
g1.set_xlabel("Time [s]");
|
||||||
g1.set_ylabel("Correlators' output");
|
g1.set_ylabel("Correlators' output");
|
||||||
g1.cmd("set key box opaque");
|
//g1.cmd("set key box opaque");
|
||||||
unsigned int decimate = static_cast<unsigned int>(FLAGS_plot_decimate);
|
g1.plot_xy(trk_timestamp_s_sweep.at(current_cn0_idx), prompt_sweep.at(current_cn0_idx), "Prompt", decimate);
|
||||||
g1.plot_xy(timevec, prompt, "Prompt", decimate);
|
g1.plot_xy(trk_timestamp_s_sweep.at(current_cn0_idx), early_sweep.at(current_cn0_idx), "Early", decimate);
|
||||||
g1.plot_xy(timevec, early, "Early", decimate);
|
g1.plot_xy(trk_timestamp_s_sweep.at(current_cn0_idx), late_sweep.at(current_cn0_idx), "Late", decimate);
|
||||||
g1.plot_xy(timevec, late, "Late", decimate);
|
g1.set_legend();
|
||||||
g1.savetops("Correlators_outputs");
|
g1.savetops("Correlators_outputs" + std::to_string(generator_CN0_values.at(current_cn0_idx)));
|
||||||
g1.savetopdf("Correlators_outputs", 18);
|
g1.savetopdf("Correlators_outputs" + std::to_string(generator_CN0_values.at(current_cn0_idx)), 18);
|
||||||
g1.showonscreen(); // window output
|
}
|
||||||
|
|
||||||
Gnuplot g2("points");
|
Gnuplot g2("points");
|
||||||
g2.set_title("Constellation diagram (satellite PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
g2.showonscreen(); // window output
|
||||||
|
g2.set_multiplot(ceil(static_cast<float>(generator_CN0_values.size()) / 2.0),
|
||||||
|
ceil(static_cast<float>(generator_CN0_values.size()) / 2));
|
||||||
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
g2.reset_plot();
|
||||||
|
g2.set_title(std::to_string(generator_CN0_values.at(current_cn0_idx)) + " dB-Hz Constellation " + "PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_idx)) + "," + std::to_string(DLL_wide_bw_values.at(config_idx)) + " Hz" + "GPS L1 C/A (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
g2.set_grid();
|
g2.set_grid();
|
||||||
g2.set_xlabel("Inphase");
|
g2.set_xlabel("Inphase");
|
||||||
g2.set_ylabel("Quadrature");
|
g2.set_ylabel("Quadrature");
|
||||||
g2.cmd("set size ratio -1");
|
//g2.cmd("set size ratio -1");
|
||||||
g2.plot_xy(promptI, promptQ);
|
g2.plot_xy(promptI_sweep.at(current_cn0_idx), promptQ_sweep.at(current_cn0_idx));
|
||||||
|
}
|
||||||
|
g2.unset_multiplot();
|
||||||
g2.savetops("Constellation");
|
g2.savetops("Constellation");
|
||||||
g2.savetopdf("Constellation", 18);
|
g2.savetopdf("Constellation", 18);
|
||||||
g2.showonscreen(); // window output
|
|
||||||
|
|
||||||
Gnuplot g3("linespoints");
|
Gnuplot g3("linespoints");
|
||||||
g3.set_title("GPS L1 C/A tracking CN0 output (satellite PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
g3.set_title("GPS L1 C/A tracking CN0 output (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
g3.set_grid();
|
g3.set_grid();
|
||||||
g3.set_xlabel("Time [s]");
|
g3.set_xlabel("Time [s]");
|
||||||
g3.set_ylabel("Reported CN0 [dB-Hz]");
|
g3.set_ylabel("Reported CN0 [dB-Hz]");
|
||||||
g3.cmd("set key box opaque");
|
g3.cmd("set key box opaque");
|
||||||
g3.plot_xy(timevec, CN0_dBHz, "Prompt", decimate);
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
g3.plot_xy(trk_timestamp_s_sweep.at(current_cn0_idx), CN0_dBHz_sweep.at(current_cn0_idx),
|
||||||
|
std::to_string(static_cast<int>(round(generator_CN0_values.at(current_cn0_idx)))) + "[dB-Hz]", decimate);
|
||||||
|
}
|
||||||
|
g3.set_legend();
|
||||||
g3.savetops("CN0_output");
|
g3.savetops("CN0_output");
|
||||||
g3.savetopdf("CN0_output", 18);
|
g3.savetopdf("CN0_output", 18);
|
||||||
g3.showonscreen(); // window output
|
g3.showonscreen(); // window output
|
||||||
}
|
}
|
||||||
|
|
||||||
|
std::cout << "B\n\n\n";
|
||||||
|
//PLOT ERROR FIGURES (only if it is used the signal generator)
|
||||||
|
if (!FLAGS_enable_external_signal_file)
|
||||||
|
{
|
||||||
|
Gnuplot g4("points");
|
||||||
|
g4.showonscreen(); // window output
|
||||||
|
g4.set_multiplot(ceil(static_cast<float>(generator_CN0_values.size()) / 2.0),
|
||||||
|
ceil(static_cast<float>(generator_CN0_values.size()) / 2));
|
||||||
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
g4.reset_plot();
|
||||||
|
g4.set_title(std::to_string(static_cast<int>(round(generator_CN0_values.at(current_cn0_idx)))) + "[dB-Hz] Doppler error " + "PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_idx)) + "," + std::to_string(DLL_wide_bw_values.at(config_idx)) + " Hz (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
|
g4.set_grid();
|
||||||
|
//g4.cmd("set key box opaque");
|
||||||
|
g4.set_xlabel("Time [s]");
|
||||||
|
g4.set_ylabel("Dopper error [Hz]");
|
||||||
|
g4.plot_xy(trk_valid_timestamp_s_sweep.at(current_cn0_idx), doppler_error_sweep.at(current_cn0_idx),
|
||||||
|
std::to_string(static_cast<int>(round(generator_CN0_values.at(current_cn0_idx)))) + "[dB-Hz]", decimate);
|
||||||
|
//g4.set_legend();
|
||||||
|
}
|
||||||
|
g4.unset_multiplot();
|
||||||
|
g4.savetops("Doppler_error_output");
|
||||||
|
g4.savetopdf("Doppler_error_output", 18);
|
||||||
|
|
||||||
|
Gnuplot g5("points");
|
||||||
|
g5.set_title("Code delay error, PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_idx)) + "," + std::to_string(DLL_wide_bw_values.at(config_idx)) + " Hz (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
|
g5.set_grid();
|
||||||
|
g5.set_xlabel("Time [s]");
|
||||||
|
g5.set_ylabel("Code delay error [Chips]");
|
||||||
|
g5.cmd("set key box opaque");
|
||||||
|
|
||||||
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
g5.plot_xy(trk_valid_timestamp_s_sweep.at(current_cn0_idx), code_phase_error_sweep.at(current_cn0_idx),
|
||||||
|
std::to_string(static_cast<int>(round(generator_CN0_values.at(current_cn0_idx)))) + "[dB-Hz]", decimate);
|
||||||
|
}
|
||||||
|
g5.set_legend();
|
||||||
|
g5.savetops("Code_error_output");
|
||||||
|
g5.savetopdf("Code_error_output", 18);
|
||||||
|
g5.showonscreen(); // window output
|
||||||
|
|
||||||
|
Gnuplot g6("points");
|
||||||
|
g6.set_title("Accumulated carrier phase error, PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_idx)) + "," + std::to_string(DLL_wide_bw_values.at(config_idx)) + " Hz (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
|
g6.set_grid();
|
||||||
|
g6.set_xlabel("Time [s]");
|
||||||
|
g6.set_ylabel("Accumulated carrier phase error [Cycles]");
|
||||||
|
g6.cmd("set key box opaque");
|
||||||
|
|
||||||
|
for (int current_cn0_idx = 0; current_cn0_idx < generator_CN0_values.size(); current_cn0_idx++)
|
||||||
|
{
|
||||||
|
g6.plot_xy(trk_valid_timestamp_s_sweep.at(current_cn0_idx), acc_carrier_phase_error_sweep.at(current_cn0_idx),
|
||||||
|
std::to_string(static_cast<int>(round(generator_CN0_values.at(current_cn0_idx)))) + "[dB-Hz]", decimate);
|
||||||
|
}
|
||||||
|
g6.set_legend();
|
||||||
|
g6.savetops("Carrier_phase_error_output");
|
||||||
|
g6.savetopdf("Carrier_phase_error_output", 18);
|
||||||
|
g6.showonscreen(); // window output
|
||||||
|
}
|
||||||
|
}
|
||||||
|
catch (const GnuplotException& ge)
|
||||||
|
{
|
||||||
|
std::cout << ge.what() << std::endl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
if (FLAGS_plot_gps_l1_tracking_test == true)
|
||||||
|
{
|
||||||
|
const std::string gnuplot_executable(FLAGS_gnuplot_executable);
|
||||||
|
if (gnuplot_executable.empty())
|
||||||
|
{
|
||||||
|
std::cout << "WARNING: Although the flag plot_gps_l1_tracking_test has been set to TRUE," << std::endl;
|
||||||
|
std::cout << "gnuplot has not been found in your system." << std::endl;
|
||||||
|
std::cout << "Test results will not be plotted." << std::endl;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
try
|
||||||
|
{
|
||||||
|
if (generator_CN0_values.size() > 1)
|
||||||
|
{
|
||||||
|
//plot metrics
|
||||||
|
|
||||||
|
Gnuplot g7("linespoints");
|
||||||
|
g7.set_title("Doppler error metrics (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
|
g7.set_grid();
|
||||||
|
g7.set_xlabel("CN0 [dB-Hz]");
|
||||||
|
g7.set_ylabel("Doppler error [Hz]");
|
||||||
|
g7.set_pointsize(2);
|
||||||
|
g7.cmd("set termoption lw 2");
|
||||||
|
g7.cmd("set key box opaque");
|
||||||
|
for (int config_sweep_idx = 0; config_sweep_idx < mean_doppler_error_sweep.size(); config_sweep_idx++)
|
||||||
|
{
|
||||||
|
g7.plot_xy_err(generator_CN0_values,
|
||||||
|
mean_doppler_error_sweep.at(config_sweep_idx),
|
||||||
|
std_dev_doppler_error_sweep.at(config_sweep_idx),
|
||||||
|
"PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_sweep_idx)) +
|
||||||
|
+"," + std::to_string(DLL_wide_bw_values.at(config_sweep_idx)) + " Hz");
|
||||||
|
}
|
||||||
|
g7.savetops("Doppler_error_metrics");
|
||||||
|
g7.savetopdf("Doppler_error_metrics", 18);
|
||||||
|
|
||||||
|
Gnuplot g8("linespoints");
|
||||||
|
g8.set_title("Accumulated carrier phase error metrics (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
|
g8.set_grid();
|
||||||
|
g8.set_xlabel("CN0 [dB-Hz]");
|
||||||
|
g8.set_ylabel("Accumulated Carrier Phase error [Cycles]");
|
||||||
|
g8.cmd("set key box opaque");
|
||||||
|
g8.cmd("set termoption lw 2");
|
||||||
|
g8.set_pointsize(2);
|
||||||
|
for (int config_sweep_idx = 0; config_sweep_idx < mean_doppler_error_sweep.size(); config_sweep_idx++)
|
||||||
|
{
|
||||||
|
g8.plot_xy_err(generator_CN0_values,
|
||||||
|
mean_carrier_phase_error_sweep.at(config_sweep_idx),
|
||||||
|
std_dev_carrier_phase_error_sweep.at(config_sweep_idx),
|
||||||
|
"PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_sweep_idx)) +
|
||||||
|
+"," + std::to_string(DLL_wide_bw_values.at(config_sweep_idx)) + " Hz");
|
||||||
|
}
|
||||||
|
g8.savetops("Carrier_error_metrics");
|
||||||
|
g8.savetopdf("Carrier_error_metrics", 18);
|
||||||
|
|
||||||
|
Gnuplot g9("linespoints");
|
||||||
|
g9.set_title("Code Phase error metrics (PRN #" + std::to_string(FLAGS_test_satellite_PRN) + ")");
|
||||||
|
g9.set_grid();
|
||||||
|
g9.set_xlabel("CN0 [dB-Hz]");
|
||||||
|
g9.set_ylabel("Code Phase error [Chips]");
|
||||||
|
g9.cmd("set key box opaque");
|
||||||
|
g9.cmd("set termoption lw 2");
|
||||||
|
g9.set_pointsize(2);
|
||||||
|
for (int config_sweep_idx = 0; config_sweep_idx < mean_doppler_error_sweep.size(); config_sweep_idx++)
|
||||||
|
{
|
||||||
|
g9.plot_xy_err(generator_CN0_values,
|
||||||
|
mean_code_phase_error_sweep.at(config_sweep_idx),
|
||||||
|
std_dev_code_phase_error_sweep.at(config_sweep_idx),
|
||||||
|
"PLL/DLL BW: " + std::to_string(PLL_wide_bw_values.at(config_sweep_idx)) +
|
||||||
|
+"," + std::to_string(DLL_wide_bw_values.at(config_sweep_idx)) + " Hz");
|
||||||
|
}
|
||||||
|
g9.savetops("Code_error_metrics");
|
||||||
|
g9.savetopdf("Code_error_metrics", 18);
|
||||||
|
}
|
||||||
|
}
|
||||||
catch (const GnuplotException& ge)
|
catch (const GnuplotException& ge)
|
||||||
{
|
{
|
||||||
std::cout << ge.what() << std::endl;
|
std::cout << ge.what() << std::endl;
|
||||||
|
@ -33,6 +33,8 @@ file = 'acq';
|
|||||||
|
|
||||||
sat = 7;
|
sat = 7;
|
||||||
|
|
||||||
|
channel = 0;
|
||||||
|
execution = 1;
|
||||||
% Signal:
|
% Signal:
|
||||||
% 1 GPS L1
|
% 1 GPS L1
|
||||||
% 2 GPS L2M
|
% 2 GPS L2M
|
||||||
@ -77,7 +79,7 @@ switch(signal_type)
|
|||||||
system = 'R';
|
system = 'R';
|
||||||
signal = '1G';
|
signal = '1G';
|
||||||
end
|
end
|
||||||
filename = [path file '_' system '_' signal '_sat_' num2str(sat) '.mat'];
|
filename = [path file '_' system '_' signal '_ch_' num2str(channel) '_' num2str(execution) '_sat_' num2str(sat) '.mat'];
|
||||||
load(filename);
|
load(filename);
|
||||||
[n_fft n_dop_bins] = size(grid);
|
[n_fft n_dop_bins] = size(grid);
|
||||||
[d_max f_max] = find(grid == max(max(grid)));
|
[d_max f_max] = find(grid == max(max(grid)));
|
||||||
|
18
src/utils/matlab/plot_tracking_quality_indicators.m
Normal file
18
src/utils/matlab/plot_tracking_quality_indicators.m
Normal file
@ -0,0 +1,18 @@
|
|||||||
|
%plot tracking quality indicators
|
||||||
|
figure;
|
||||||
|
hold on;
|
||||||
|
title('Carrier lock test output for all the channels');
|
||||||
|
for n=1:1:length(GNSS_tracking)
|
||||||
|
plot(GNSS_tracking(n).carrier_lock_test)
|
||||||
|
plotnames{n}=['SV ' num2str(round(mean(GNSS_tracking(n).PRN)))];
|
||||||
|
end
|
||||||
|
legend(plotnames);
|
||||||
|
|
||||||
|
figure;
|
||||||
|
hold on;
|
||||||
|
title('Carrier CN0 output for all the channels');
|
||||||
|
for n=1:1:length(GNSS_tracking)
|
||||||
|
plot(GNSS_tracking(n).CN0_SNV_dB_Hz)
|
||||||
|
plotnames{n}=['SV ' num2str(round(mean(GNSS_tracking(n).PRN)))];
|
||||||
|
end
|
||||||
|
legend(plotnames);
|
Loading…
Reference in New Issue
Block a user