mirror of
https://github.com/gnss-sdr/gnss-sdr
synced 2024-09-29 07:20:51 +00:00
Some code cleaning
git-svn-id: https://svn.code.sf.net/p/gnss-sdr/code/trunk@120 64b25241-fba3-4117-9849-534c7e92360d
This commit is contained in:
parent
dab517aff0
commit
bc62d8d5be
@ -58,10 +58,10 @@ GpsL1CaPvt::GpsL1CaPvt(ConfigurationInterface* configuration,
|
|||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
|
|
||||||
int averaging_depth;
|
int averaging_depth;
|
||||||
averaging_depth=configuration->property(role + ".averaging_depth", 10);
|
averaging_depth = configuration->property(role + ".averaging_depth", 10);
|
||||||
|
|
||||||
bool flag_averaging;
|
bool flag_averaging;
|
||||||
flag_averaging=configuration->property(role + ".flag_averaging", false);
|
flag_averaging = configuration->property(role + ".flag_averaging", false);
|
||||||
|
|
||||||
dump_ = configuration->property(role + ".dump", false);
|
dump_ = configuration->property(role + ".dump", false);
|
||||||
dump_filename_ = configuration->property(role + ".dump_filename", default_dump_filename);
|
dump_filename_ = configuration->property(role + ".dump_filename", default_dump_filename);
|
||||||
@ -73,7 +73,7 @@ GpsL1CaPvt::GpsL1CaPvt(ConfigurationInterface* configuration,
|
|||||||
|
|
||||||
pvt_->set_navigation_queue(&global_gps_nav_msg_queue);
|
pvt_->set_navigation_queue(&global_gps_nav_msg_queue);
|
||||||
|
|
||||||
DLOG(INFO) << "global navigation message queue assigned to pvt ("<< pvt_->unique_id() << ")";
|
DLOG(INFO) << "global navigation message queue assigned to pvt (" << pvt_->unique_id() << ")";
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -98,8 +98,8 @@ bool pseudoranges_pairCompare_min( std::pair<int,gnss_pseudorange> a, std::pair<
|
|||||||
|
|
||||||
|
|
||||||
int gps_l1_ca_pvt_cc::general_work (int noutput_items, gr_vector_int &ninput_items,
|
int gps_l1_ca_pvt_cc::general_work (int noutput_items, gr_vector_int &ninput_items,
|
||||||
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items) {
|
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items)
|
||||||
|
{
|
||||||
d_sample_counter++;
|
d_sample_counter++;
|
||||||
|
|
||||||
std::map<int,gnss_pseudorange> gnss_pseudoranges_map;
|
std::map<int,gnss_pseudorange> gnss_pseudoranges_map;
|
||||||
|
@ -40,26 +40,26 @@ using google::LogMessage;
|
|||||||
gps_l1_ca_ls_pvt::gps_l1_ca_ls_pvt(int nchannels,std::string dump_filename, bool flag_dump_to_file)
|
gps_l1_ca_ls_pvt::gps_l1_ca_ls_pvt(int nchannels,std::string dump_filename, bool flag_dump_to_file)
|
||||||
{
|
{
|
||||||
// init empty ephemeris for all the available GNSS channels
|
// init empty ephemeris for all the available GNSS channels
|
||||||
d_nchannels=nchannels;
|
d_nchannels = nchannels;
|
||||||
d_ephemeris=new gps_navigation_message[nchannels];
|
d_ephemeris = new gps_navigation_message[nchannels];
|
||||||
d_dump_filename=dump_filename;
|
d_dump_filename = dump_filename;
|
||||||
d_flag_dump_enabled=flag_dump_to_file;
|
d_flag_dump_enabled = flag_dump_to_file;
|
||||||
d_averaging_depth=0;
|
d_averaging_depth = 0;
|
||||||
|
|
||||||
// ############# ENABLE DATA FILE LOG #################
|
// ############# ENABLE DATA FILE LOG #################
|
||||||
if (d_flag_dump_enabled==true)
|
if (d_flag_dump_enabled == true)
|
||||||
{
|
{
|
||||||
if (d_dump_file.is_open()==false)
|
if (d_dump_file.is_open() == false)
|
||||||
{
|
{
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
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::out | std::ios::binary);
|
d_dump_file.open(d_dump_filename.c_str(), std::ios::out | std::ios::binary);
|
||||||
std::cout<<"PVT lib dump enabled Log file: "<<d_dump_filename.c_str()<<std::endl;
|
std::cout << "PVT lib dump enabled Log file: "<< d_dump_filename.c_str() << std::endl;
|
||||||
}
|
}
|
||||||
catch (std::ifstream::failure e)
|
catch (std::ifstream::failure e)
|
||||||
{
|
{
|
||||||
std::cout << "Exception opening PVT lib dump file "<<e.what()<<"\r\n";
|
std::cout << "Exception opening PVT lib dump file "<< e.what() << std::endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -68,7 +68,7 @@ gps_l1_ca_ls_pvt::gps_l1_ca_ls_pvt(int nchannels,std::string dump_filename, bool
|
|||||||
|
|
||||||
void gps_l1_ca_ls_pvt::set_averaging_depth(int depth)
|
void gps_l1_ca_ls_pvt::set_averaging_depth(int depth)
|
||||||
{
|
{
|
||||||
d_averaging_depth=depth;
|
d_averaging_depth = depth;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -100,16 +100,16 @@ arma::vec gps_l1_ca_ls_pvt::e_r_corr(double traveltime, arma::vec X_sat)
|
|||||||
omegatau = OMEGA_EARTH_DOT * traveltime;
|
omegatau = OMEGA_EARTH_DOT * traveltime;
|
||||||
|
|
||||||
//--- Make a rotation matrix -----------------------------------------------
|
//--- Make a rotation matrix -----------------------------------------------
|
||||||
arma::mat R3=arma::zeros(3,3);
|
arma::mat R3 = arma::zeros(3,3);
|
||||||
R3(0, 0)= cos(omegatau);
|
R3(0, 0) = cos(omegatau);
|
||||||
R3(0, 1)= sin(omegatau);
|
R3(0, 1) = sin(omegatau);
|
||||||
R3(0, 2)= 0.0;
|
R3(0, 2) = 0.0;
|
||||||
R3(1, 0)=-sin(omegatau);
|
R3(1, 0) = -sin(omegatau);
|
||||||
R3(1, 1)= cos(omegatau);
|
R3(1, 1) = cos(omegatau);
|
||||||
R3(1, 2)=0.0;
|
R3(1, 2) = 0.0;
|
||||||
R3(2, 0)= 0.0;
|
R3(2, 0) = 0.0;
|
||||||
R3(2, 1)= 0.0;
|
R3(2, 1) = 0.0;
|
||||||
R3(2, 2)= 1;
|
R3(2, 2) = 1;
|
||||||
//--- Do the rotation ------------------------------------------------------
|
//--- Do the rotation ------------------------------------------------------
|
||||||
arma::vec X_sat_rot;
|
arma::vec X_sat_rot;
|
||||||
X_sat_rot = R3 * X_sat;
|
X_sat_rot = R3 * X_sat;
|
||||||
@ -144,18 +144,18 @@ arma::vec gps_l1_ca_ls_pvt::leastSquarePos(arma::mat satpos, arma::vec obs, arma
|
|||||||
arma::mat omc;
|
arma::mat omc;
|
||||||
arma::mat az;
|
arma::mat az;
|
||||||
arma::mat el;
|
arma::mat el;
|
||||||
A=arma::zeros(nmbOfSatellites,4);
|
A=arma::zeros(nmbOfSatellites, 4);
|
||||||
omc=arma::zeros(nmbOfSatellites,1);
|
omc=arma::zeros(nmbOfSatellites, 1);
|
||||||
az=arma::zeros(1,nmbOfSatellites);
|
az=arma::zeros(1, nmbOfSatellites);
|
||||||
el=arma::zeros(1,nmbOfSatellites);
|
el=arma::zeros(1, nmbOfSatellites);
|
||||||
for (int i = 0; i < nmbOfSatellites; i++)
|
for (int i = 0; i < nmbOfSatellites; i++)
|
||||||
{
|
{
|
||||||
for (int j = 0; j < 4; j++)
|
for (int j = 0; j < 4; j++)
|
||||||
{
|
{
|
||||||
A(i,j)=0.0; //Armadillo
|
A(i, j) = 0.0; //Armadillo
|
||||||
}
|
}
|
||||||
omc(i, 0)=0.0;
|
omc(i, 0) = 0.0;
|
||||||
az(0, i)=0.0;
|
az(0, i)= 0.0;
|
||||||
}
|
}
|
||||||
el = az;
|
el = az;
|
||||||
|
|
||||||
@ -174,7 +174,7 @@ arma::vec gps_l1_ca_ls_pvt::leastSquarePos(arma::mat satpos, arma::vec obs, arma
|
|||||||
if (iter == 0)
|
if (iter == 0)
|
||||||
{
|
{
|
||||||
//--- Initialize variables at the first iteration --------------
|
//--- Initialize variables at the first iteration --------------
|
||||||
Rot_X=X.col(i); //Armadillo
|
Rot_X = X.col(i); //Armadillo
|
||||||
trop = 0.0;
|
trop = 0.0;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -194,10 +194,10 @@ arma::vec gps_l1_ca_ls_pvt::leastSquarePos(arma::mat satpos, arma::vec obs, arma
|
|||||||
|
|
||||||
//--- Construct the A matrix ---------------------------------------
|
//--- Construct the A matrix ---------------------------------------
|
||||||
//Armadillo
|
//Armadillo
|
||||||
A(i,0)=(-(Rot_X(0) - pos(0))) / obs(i);
|
A(i,0) = (-(Rot_X(0) - pos(0))) / obs(i);
|
||||||
A(i,1)=(-(Rot_X(1) - pos(1))) / obs(i);
|
A(i,1) = (-(Rot_X(1) - pos(1))) / obs(i);
|
||||||
A(i,2)=(-(Rot_X(2) - pos(2))) / obs(i);
|
A(i,2) = (-(Rot_X(2) - pos(2))) / obs(i);
|
||||||
A(i,3)=1.0;
|
A(i,3) = 1.0;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -208,7 +208,7 @@ arma::vec gps_l1_ca_ls_pvt::leastSquarePos(arma::mat satpos, arma::vec obs, arma
|
|||||||
//}
|
//}
|
||||||
|
|
||||||
//--- Find position update ---------------------------------------------
|
//--- Find position update ---------------------------------------------
|
||||||
x = arma::solve(w*A,w*omc); // Armadillo
|
x = arma::solve(w*A, w*omc); // Armadillo
|
||||||
|
|
||||||
//--- Apply position update --------------------------------------------
|
//--- Apply position update --------------------------------------------
|
||||||
pos = pos + x;
|
pos = pos + x;
|
||||||
@ -221,9 +221,9 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
{
|
{
|
||||||
std::map<int,gnss_pseudorange>::iterator gnss_pseudoranges_iter;
|
std::map<int,gnss_pseudorange>::iterator gnss_pseudoranges_iter;
|
||||||
|
|
||||||
arma::mat W=arma::eye(d_nchannels,d_nchannels); //channels weights matrix
|
arma::mat W = arma::eye(d_nchannels,d_nchannels); //channels weights matrix
|
||||||
arma::vec obs=arma::zeros(d_nchannels); // pseudoranges observation vector
|
arma::vec obs = arma::zeros(d_nchannels); // pseudoranges observation vector
|
||||||
arma::mat satpos=arma::zeros(3,d_nchannels); //satellite positions matrix
|
arma::mat satpos = arma::zeros(3,d_nchannels); //satellite positions matrix
|
||||||
|
|
||||||
int GPS_week = 0;
|
int GPS_week = 0;
|
||||||
double GPS_corrected_time = 0;
|
double GPS_corrected_time = 0;
|
||||||
@ -232,15 +232,15 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
int valid_obs=0; //valid observations counter
|
int valid_obs=0; //valid observations counter
|
||||||
for (int i=0; i<d_nchannels; i++)
|
for (int i=0; i<d_nchannels; i++)
|
||||||
{
|
{
|
||||||
if (d_ephemeris[i].satellite_validation()==true)
|
if (d_ephemeris[i].satellite_validation() == true)
|
||||||
{
|
{
|
||||||
gnss_pseudoranges_iter=gnss_pseudoranges_map.find(d_ephemeris[i].i_satellite_PRN);
|
gnss_pseudoranges_iter = gnss_pseudoranges_map.find(d_ephemeris[i].i_satellite_PRN);
|
||||||
if (gnss_pseudoranges_iter!=gnss_pseudoranges_map.end())
|
if (gnss_pseudoranges_iter != gnss_pseudoranges_map.end())
|
||||||
{
|
{
|
||||||
/*!
|
/*!
|
||||||
* \todo Place here the satellite CN0 (power level, or weight factor)
|
* \todo Place here the satellite CN0 (power level, or weight factor)
|
||||||
*/
|
*/
|
||||||
W(i,i)=1;
|
W(i,i) = 1;
|
||||||
// compute the GPS master clock
|
// compute the GPS master clock
|
||||||
// d_ephemeris[i].master_clock(GPS_current_time); ?????
|
// d_ephemeris[i].master_clock(GPS_current_time); ?????
|
||||||
|
|
||||||
@ -248,31 +248,31 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
GPS_corrected_time = d_ephemeris[i].sv_clock_correction(GPS_current_time);
|
GPS_corrected_time = d_ephemeris[i].sv_clock_correction(GPS_current_time);
|
||||||
GPS_week = d_ephemeris[i].i_GPS_week;
|
GPS_week = d_ephemeris[i].i_GPS_week;
|
||||||
|
|
||||||
utc =d_ephemeris[i].utc_time(GPS_corrected_time);
|
utc = d_ephemeris[i].utc_time(GPS_corrected_time);
|
||||||
|
|
||||||
// compute the satellite current ECEF position
|
// compute the satellite current ECEF position
|
||||||
d_ephemeris[i].satellitePosition(GPS_corrected_time);
|
d_ephemeris[i].satellitePosition(GPS_corrected_time);
|
||||||
|
|
||||||
satpos(0,i)=d_ephemeris[i].d_satpos_X;
|
satpos(0,i) = d_ephemeris[i].d_satpos_X;
|
||||||
satpos(1,i)=d_ephemeris[i].d_satpos_Y;
|
satpos(1,i) = d_ephemeris[i].d_satpos_Y;
|
||||||
satpos(2,i)=d_ephemeris[i].d_satpos_Z;
|
satpos(2,i) = d_ephemeris[i].d_satpos_Z;
|
||||||
LOG_AT_LEVEL(INFO)<<"ECEF satellite SV ID="<<d_ephemeris[i].i_satellite_PRN<<" X="<<d_ephemeris[i].d_satpos_X
|
LOG_AT_LEVEL(INFO) << "ECEF satellite SV ID=" << d_ephemeris[i].i_satellite_PRN <<" X=" << d_ephemeris[i].d_satpos_X
|
||||||
<<" [m] Y="<<d_ephemeris[i].d_satpos_Y<<" [m] Z="<<d_ephemeris[i].d_satpos_Z<<" [m]\r\n";
|
<< " [m] Y=" << d_ephemeris[i].d_satpos_Y << " [m] Z=" << d_ephemeris[i].d_satpos_Z << " [m]" << std::endl;
|
||||||
obs(i)=gnss_pseudoranges_iter->second.pseudorange_m+d_ephemeris[i].d_satClkCorr*GPS_C_m_s;
|
obs(i) = gnss_pseudoranges_iter->second.pseudorange_m + d_ephemeris[i].d_satClkCorr*GPS_C_m_s;
|
||||||
valid_obs++;
|
valid_obs++;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// no valid pseudorange for the current channel
|
// no valid pseudorange for the current channel
|
||||||
W(i,i)=0; // channel de-activated
|
W(i,i) = 0; // channel de-activated
|
||||||
obs(i)=1; // to avoid algorithm problems (divide by zero)
|
obs(i) = 1; // to avoid algorithm problems (divide by zero)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// no valid ephemeris for the current channel
|
// no valid ephemeris for the current channel
|
||||||
W(i,i)=0; // channel de-activated
|
W(i,i) = 0; // channel de-activated
|
||||||
obs(i)=1; // to avoid algorithm problems (divide by zero)
|
obs(i) = 1; // to avoid algorithm problems (divide by zero)
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
std::cout<<"PVT: valid observations="<<valid_obs<<std::endl;
|
std::cout<<"PVT: valid observations="<<valid_obs<<std::endl;
|
||||||
@ -280,43 +280,43 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
{
|
{
|
||||||
arma::vec mypos;
|
arma::vec mypos;
|
||||||
mypos=leastSquarePos(satpos,obs,W);
|
mypos=leastSquarePos(satpos,obs,W);
|
||||||
LOG_AT_LEVEL(INFO) << "Position at TOW="<<GPS_current_time<<" in ECEF (X,Y,Z) = " << mypos << std::endl;
|
LOG_AT_LEVEL(INFO) << "Position at TOW="<< GPS_current_time << " in ECEF (X,Y,Z) = " << mypos << std::endl;
|
||||||
cart2geo(mypos(0), mypos(1), mypos(2), 4);
|
cart2geo(mypos(0), mypos(1), mypos(2), 4);
|
||||||
|
|
||||||
// Compute UTC time and print PVT solution
|
// Compute UTC time and print PVT solution
|
||||||
boost::posix_time::time_duration t = boost::posix_time::seconds(utc + 604800*(double)GPS_week);
|
boost::posix_time::time_duration t = boost::posix_time::seconds(utc + 604800*(double)GPS_week);
|
||||||
boost::posix_time::ptime p_time(boost::gregorian::date(1999,8,22),t);
|
boost::posix_time::ptime p_time(boost::gregorian::date(1999, 8, 22), t);
|
||||||
std::cout << "Position at "<<boost::posix_time::to_simple_string(p_time)<<" is Lat = " << d_latitude_d << " [deg] Long = "<< d_longitude_d <<" [deg] Height= "<<d_height_m<<" [m]" <<std::endl;
|
std::cout << "Position at " << boost::posix_time::to_simple_string(p_time) <<" is Lat = " << d_latitude_d << " [deg] Long = " << d_longitude_d << " [deg] Height= " << d_height_m << " [m]" << std::endl;
|
||||||
// ######## LOG FILE #########
|
// ######## LOG FILE #########
|
||||||
if(d_flag_dump_enabled==true)
|
if(d_flag_dump_enabled == true)
|
||||||
{
|
{
|
||||||
// MULTIPLEXED FILE RECORDING - Record results to file
|
// MULTIPLEXED FILE RECORDING - Record results to file
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
double tmp_double;
|
double tmp_double;
|
||||||
// PVT GPS time
|
// PVT GPS time
|
||||||
tmp_double=GPS_current_time;
|
tmp_double = GPS_current_time;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// ECEF User Position East [m]
|
// ECEF User Position East [m]
|
||||||
tmp_double=mypos(0);
|
tmp_double = mypos(0);
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// ECEF User Position North [m]
|
// ECEF User Position North [m]
|
||||||
tmp_double=mypos(1);
|
tmp_double = mypos(1);
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// ECEF User Position Up [m]
|
// ECEF User Position Up [m]
|
||||||
tmp_double=mypos(2);
|
tmp_double = mypos(2);
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// User clock offset [s]
|
// User clock offset [s]
|
||||||
tmp_double=mypos(3);
|
tmp_double = mypos(3);
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// GEO user position Latitude [deg]
|
// GEO user position Latitude [deg]
|
||||||
tmp_double=d_latitude_d;
|
tmp_double = d_latitude_d;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// GEO user position Longitude [deg]
|
// GEO user position Longitude [deg]
|
||||||
tmp_double=d_longitude_d;
|
tmp_double = d_longitude_d;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
// GEO user position Height [m]
|
// GEO user position Height [m]
|
||||||
tmp_double=d_height_m;
|
tmp_double = d_height_m;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
}
|
}
|
||||||
catch (std::ifstream::failure e)
|
catch (std::ifstream::failure e)
|
||||||
@ -326,9 +326,9 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
}
|
}
|
||||||
|
|
||||||
// MOVING AVERAGE PVT
|
// MOVING AVERAGE PVT
|
||||||
if (flag_averaging==true)
|
if (flag_averaging == true)
|
||||||
{
|
{
|
||||||
if (d_hist_longitude_d.size()==(unsigned int)d_averaging_depth)
|
if (d_hist_longitude_d.size() == (unsigned int)d_averaging_depth)
|
||||||
{
|
{
|
||||||
// Pop oldest value
|
// Pop oldest value
|
||||||
d_hist_longitude_d.pop_back();
|
d_hist_longitude_d.pop_back();
|
||||||
@ -339,18 +339,18 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
d_hist_latitude_d.push_front(d_latitude_d);
|
d_hist_latitude_d.push_front(d_latitude_d);
|
||||||
d_hist_height_m.push_front(d_height_m);
|
d_hist_height_m.push_front(d_height_m);
|
||||||
|
|
||||||
d_avg_latitude_d=0;
|
d_avg_latitude_d = 0;
|
||||||
d_avg_longitude_d=0;
|
d_avg_longitude_d = 0;
|
||||||
d_avg_height_m=0;
|
d_avg_height_m = 0;
|
||||||
for (unsigned int i=0;i<d_hist_longitude_d.size();i++)
|
for (unsigned int i=0; i<d_hist_longitude_d.size(); i++)
|
||||||
{
|
{
|
||||||
d_avg_latitude_d=d_avg_latitude_d+d_hist_latitude_d.at(i);
|
d_avg_latitude_d = d_avg_latitude_d + d_hist_latitude_d.at(i);
|
||||||
d_avg_longitude_d=d_avg_longitude_d+d_hist_longitude_d.at(i);
|
d_avg_longitude_d = d_avg_longitude_d + d_hist_longitude_d.at(i);
|
||||||
d_avg_height_m=d_avg_height_m+d_hist_height_m.at(i);
|
d_avg_height_m = d_avg_height_m + d_hist_height_m.at(i);
|
||||||
}
|
}
|
||||||
d_avg_latitude_d=d_avg_latitude_d/(double)d_averaging_depth;
|
d_avg_latitude_d = d_avg_latitude_d / (double)d_averaging_depth;
|
||||||
d_avg_longitude_d=d_avg_longitude_d/(double)d_averaging_depth;
|
d_avg_longitude_d = d_avg_longitude_d / (double)d_averaging_depth;
|
||||||
d_avg_height_m=d_avg_height_m/(double)d_averaging_depth;
|
d_avg_height_m = d_avg_height_m / (double)d_averaging_depth;
|
||||||
return true; //indicates that the returned position is valid
|
return true; //indicates that the returned position is valid
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -361,9 +361,9 @@ bool gps_l1_ca_ls_pvt::get_PVT(std::map<int,gnss_pseudorange> gnss_pseudoranges_
|
|||||||
d_hist_latitude_d.push_front(d_latitude_d);
|
d_hist_latitude_d.push_front(d_latitude_d);
|
||||||
d_hist_height_m.push_front(d_height_m);
|
d_hist_height_m.push_front(d_height_m);
|
||||||
|
|
||||||
d_avg_latitude_d=d_latitude_d;
|
d_avg_latitude_d = d_latitude_d;
|
||||||
d_avg_longitude_d=d_longitude_d;
|
d_avg_longitude_d = d_longitude_d;
|
||||||
d_avg_height_m=d_height_m;
|
d_avg_height_m = d_height_m;
|
||||||
return false;//indicates that the returned position is not valid yet
|
return false;//indicates that the returned position is not valid yet
|
||||||
// output the average, although it will not have the full historic available
|
// output the average, although it will not have the full historic available
|
||||||
// d_avg_latitude_d=0;
|
// d_avg_latitude_d=0;
|
||||||
@ -411,11 +411,11 @@ void gps_l1_ca_ls_pvt::cart2geo(double X, double Y, double Z, int elipsoid_selec
|
|||||||
double lambda;
|
double lambda;
|
||||||
lambda = atan2(Y,X);
|
lambda = atan2(Y,X);
|
||||||
double ex2;
|
double ex2;
|
||||||
ex2 = (2-f[elipsoid_selection])*f[elipsoid_selection]/((1-f[elipsoid_selection])*(1-f[elipsoid_selection]));
|
ex2 = (2 - f[elipsoid_selection]) * f[elipsoid_selection] / ((1 - f[elipsoid_selection])*(1 -f[elipsoid_selection]));
|
||||||
double c;
|
double c;
|
||||||
c = a[elipsoid_selection]*sqrt(1+ex2);
|
c = a[elipsoid_selection] * sqrt(1+ex2);
|
||||||
double phi;
|
double phi;
|
||||||
phi = atan(Z/((sqrt(X*X+Y*Y)*(1-(2-f[elipsoid_selection]))*f[elipsoid_selection])));
|
phi = atan(Z / ((sqrt(X*X + Y*Y)*(1 - (2 - f[elipsoid_selection])) * f[elipsoid_selection])));
|
||||||
|
|
||||||
double h = 0.1;
|
double h = 0.1;
|
||||||
double oldh = 0;
|
double oldh = 0;
|
||||||
@ -424,19 +424,19 @@ void gps_l1_ca_ls_pvt::cart2geo(double X, double Y, double Z, int elipsoid_selec
|
|||||||
do
|
do
|
||||||
{
|
{
|
||||||
oldh = h;
|
oldh = h;
|
||||||
N = c/sqrt(1+ex2*(cos(phi)*cos(phi)));
|
N = c / sqrt(1 + ex2 * (cos(phi) * cos(phi)));
|
||||||
phi = atan(Z/((sqrt(X*X+Y*Y)*(1-(2-f[elipsoid_selection])*f[elipsoid_selection]*N/(N+h)))));
|
phi = atan(Z / ((sqrt(X*X + Y*Y) * (1 - (2 -f[elipsoid_selection]) * f[elipsoid_selection] *N / (N + h) ))));
|
||||||
h = sqrt(X*X+Y*Y)/cos(phi)-N;
|
h = sqrt(X*X + Y*Y) / cos(phi) - N;
|
||||||
iterations = iterations + 1;
|
iterations = iterations + 1;
|
||||||
if (iterations > 100)
|
if (iterations > 100)
|
||||||
{
|
{
|
||||||
std::cout<<"Failed to approximate h with desired precision. h-oldh= "<<h-oldh<<std::endl;
|
std::cout << "Failed to approximate h with desired precision. h-oldh= " << h-oldh << std::endl;
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
while (abs(h-oldh) > 1.0e-12);
|
while (abs(h - oldh) > 1.0e-12);
|
||||||
d_latitude_d = phi*180.0/GPS_PI;
|
d_latitude_d = phi * 180.0 / GPS_PI;
|
||||||
d_longitude_d = lambda*180/GPS_PI;
|
d_longitude_d = lambda * 180 / GPS_PI;
|
||||||
d_height_m = h;
|
d_height_m = h;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -45,31 +45,31 @@ bool kml_printer::set_headers(std::string filename)
|
|||||||
kml_file.open(filename.c_str());
|
kml_file.open(filename.c_str());
|
||||||
if (kml_file.is_open())
|
if (kml_file.is_open())
|
||||||
{
|
{
|
||||||
DLOG(INFO)<<"KML printer writing on "<<filename.c_str();
|
DLOG(INFO) << "KML printer writing on " << filename.c_str();
|
||||||
kml_file<<"<?xml version=\"1.0\" encoding=\"UTF-8\"?>\r\n"
|
kml_file << "<?xml version=\"1.0\" encoding=\"UTF-8\"?>" << std::endl
|
||||||
<<"<kml xmlns=\"http://www.opengis.net/kml/2.2\">\r\n"
|
<< "<kml xmlns=\"http://www.opengis.net/kml/2.2\">" << std::endl
|
||||||
<<" <Document>\r\n"
|
<< " <Document>" << std::endl
|
||||||
<<" <name>GNSS Track</name>\r\n"
|
<< " <name>GNSS Track</name>" << std::endl
|
||||||
<<" <description>GNSS-SDR Receiver position log file created at "<<asctime (timeinfo)
|
<< " <description>GNSS-SDR Receiver position log file created at " << asctime (timeinfo)
|
||||||
<<" </description>\r\n"
|
<< " </description>" << std::endl
|
||||||
<<"<Style id=\"yellowLineGreenPoly\">\r\n"
|
<< "<Style id=\"yellowLineGreenPoly\">" << std::endl
|
||||||
<<" <LineStyle>\r\n"
|
<< " <LineStyle>" << std::endl
|
||||||
<<" <color>7f00ffff</color>\r\n"
|
<< " <color>7f00ffff</color>" << std::endl
|
||||||
<<" <width>1</width>\r\n"
|
<< " <width>1</width>" << std::endl
|
||||||
<<" </LineStyle>\r\n"
|
<< " </LineStyle>" << std::endl
|
||||||
<<"<PolyStyle>\r\n"
|
<< "<PolyStyle>" << std::endl
|
||||||
<<" <color>7f00ff00</color>\r\n"
|
<< " <color>7f00ff00</color>" << std::endl
|
||||||
<<"</PolyStyle>\r\n"
|
<< "</PolyStyle>" << std::endl
|
||||||
<<"</Style>\r\n"
|
<< "</Style>" << std::endl
|
||||||
<<"<Placemark>\r\n"
|
<< "<Placemark>" << std::endl
|
||||||
<<"<name>GNSS-SDR PVT</name>\r\n"
|
<< "<name>GNSS-SDR PVT</name>" << std::endl
|
||||||
<<"<description>GNSS-SDR position log</description>\r\n"
|
<< "<description>GNSS-SDR position log</description>" << std::endl
|
||||||
<<"<styleUrl>#yellowLineGreenPoly</styleUrl>\r\n"
|
<< "<styleUrl>#yellowLineGreenPoly</styleUrl>" << std::endl
|
||||||
<<"<LineString>\r\n"
|
<< "<LineString>" << std::endl
|
||||||
<<"<extrude>0</extrude>\r\n"
|
<< "<extrude>0</extrude>" << std::endl
|
||||||
<<"<tessellate>1</tessellate>\r\n"
|
<< "<tessellate>1</tessellate>" << std::endl
|
||||||
<<"<altitudeMode>absolute</altitudeMode>\r\n"
|
<< "<altitudeMode>absolute</altitudeMode>" << std::endl
|
||||||
<<"<coordinates>\r\n";
|
<< "<coordinates>" << std::endl;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -84,7 +84,7 @@ bool kml_printer::print_position(gps_l1_ca_ls_pvt* position,bool print_average_v
|
|||||||
double latitude;
|
double latitude;
|
||||||
double longitude;
|
double longitude;
|
||||||
double height;
|
double height;
|
||||||
if (print_average_values==false)
|
if (print_average_values == false)
|
||||||
{
|
{
|
||||||
latitude=position->d_latitude_d;
|
latitude=position->d_latitude_d;
|
||||||
longitude=position->d_longitude_d;
|
longitude=position->d_longitude_d;
|
||||||
@ -96,9 +96,10 @@ bool kml_printer::print_position(gps_l1_ca_ls_pvt* position,bool print_average_v
|
|||||||
longitude=position->d_avg_longitude_d;
|
longitude=position->d_avg_longitude_d;
|
||||||
height=position->d_avg_height_m;
|
height=position->d_avg_height_m;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (kml_file.is_open())
|
if (kml_file.is_open())
|
||||||
{
|
{
|
||||||
kml_file<<longitude<<","<<latitude<<","<<height<<"\r\n";
|
kml_file << longitude << "," << latitude << "," << height << std::endl;
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
@ -111,10 +112,10 @@ bool kml_printer::close_file()
|
|||||||
{
|
{
|
||||||
if (kml_file.is_open())
|
if (kml_file.is_open())
|
||||||
{
|
{
|
||||||
kml_file<<"</coordinates>\r\n"
|
kml_file<<"</coordinates>" << std::endl
|
||||||
<<"</LineString>\r\n"
|
<<"</LineString>" << std::endl
|
||||||
<<"</Placemark>\r\n"
|
<<"</Placemark>" << std::endl
|
||||||
<<"</Document>\r\n"
|
<<"</Document>" << std::endl
|
||||||
<<"</kml>";
|
<<"</kml>";
|
||||||
kml_file.close();
|
kml_file.close();
|
||||||
return true;
|
return true;
|
||||||
|
@ -264,12 +264,12 @@ std::string Rinex_Printer::getLocalTime()
|
|||||||
|
|
||||||
std::stringstream strmHour;
|
std::stringstream strmHour;
|
||||||
int utc_hour = pt_tm.tm_hour;
|
int utc_hour = pt_tm.tm_hour;
|
||||||
if (utc_hour<10) strmHour << "0"; // two digits for hours
|
if (utc_hour < 10) strmHour << "0"; // two digits for hours
|
||||||
strmHour << utc_hour;
|
strmHour << utc_hour;
|
||||||
|
|
||||||
std::stringstream strmMin;
|
std::stringstream strmMin;
|
||||||
int utc_minute = pt_tm.tm_min;
|
int utc_minute = pt_tm.tm_min;
|
||||||
if (utc_minute<10) strmMin << "0"; // two digits for minutes
|
if (utc_minute < 10) strmMin << "0"; // two digits for minutes
|
||||||
strmMin << utc_minute;
|
strmMin << utc_minute;
|
||||||
|
|
||||||
if (version == 2)
|
if (version == 2)
|
||||||
@ -371,7 +371,7 @@ void Rinex_Printer::rinex_nav_header(std::ofstream& out, gps_navigation_message
|
|||||||
// -------- Line COMMENT
|
// -------- Line COMMENT
|
||||||
line.clear();
|
line.clear();
|
||||||
line += Rinex_Printer::leftJustify("See http://gnss-sdr.org", 60);
|
line += Rinex_Printer::leftJustify("See http://gnss-sdr.org", 60);
|
||||||
line += Rinex_Printer::leftJustify("COMMENT",20);
|
line += Rinex_Printer::leftJustify("COMMENT", 20);
|
||||||
Rinex_Printer::lengthCheck(line);
|
Rinex_Printer::lengthCheck(line);
|
||||||
out << line << std::endl;
|
out << line << std::endl;
|
||||||
|
|
||||||
@ -547,7 +547,7 @@ void Rinex_Printer::log_rinex_nav(std::ofstream& out, gps_navigation_message nav
|
|||||||
line += satelliteSystem["GPS"];
|
line += satelliteSystem["GPS"];
|
||||||
if (nav_msg.i_satellite_PRN < 10) line += std::string("0");
|
if (nav_msg.i_satellite_PRN < 10) line += std::string("0");
|
||||||
line += boost::lexical_cast<std::string>(nav_msg.i_satellite_PRN);
|
line += boost::lexical_cast<std::string>(nav_msg.i_satellite_PRN);
|
||||||
std::string year (timestring,0,4);
|
std::string year (timestring, 0, 4);
|
||||||
line += std::string(1, ' ');
|
line += std::string(1, ' ');
|
||||||
line += year;
|
line += year;
|
||||||
line += std::string(1, ' ');
|
line += std::string(1, ' ');
|
||||||
@ -932,13 +932,13 @@ void Rinex_Printer::rinex_obs_header(std::ofstream& out, gps_navigation_message
|
|||||||
std::string hour (timestring, 9, 2);
|
std::string hour (timestring, 9, 2);
|
||||||
std::string minutes (timestring, 11, 2);
|
std::string minutes (timestring, 11, 2);
|
||||||
double utc_t = nav_msg.utc_time(nav_msg.sv_clock_correction(nav_msg.d_TOW));
|
double utc_t = nav_msg.utc_time(nav_msg.sv_clock_correction(nav_msg.d_TOW));
|
||||||
double seconds = fmod(utc_t,60);
|
double seconds = fmod(utc_t, 60);
|
||||||
line += Rinex_Printer::rightJustify(year, 6);
|
line += Rinex_Printer::rightJustify(year, 6);
|
||||||
line += Rinex_Printer::rightJustify(month, 6);
|
line += Rinex_Printer::rightJustify(month, 6);
|
||||||
line += Rinex_Printer::rightJustify(day, 6);
|
line += Rinex_Printer::rightJustify(day, 6);
|
||||||
line += Rinex_Printer::rightJustify(hour, 6);
|
line += Rinex_Printer::rightJustify(hour, 6);
|
||||||
line += Rinex_Printer::rightJustify(minutes, 6);
|
line += Rinex_Printer::rightJustify(minutes, 6);
|
||||||
line += Rinex_Printer::rightJustify(asString(seconds,7), 13);
|
line += Rinex_Printer::rightJustify(asString(seconds, 7), 13);
|
||||||
line += Rinex_Printer::rightJustify(std::string("GPS"), 8);
|
line += Rinex_Printer::rightJustify(std::string("GPS"), 8);
|
||||||
line += std::string(9, ' ');
|
line += std::string(9, ' ');
|
||||||
line += Rinex_Printer::leftJustify("TIME OF FIRST OBS", 20);
|
line += Rinex_Printer::leftJustify("TIME OF FIRST OBS", 20);
|
||||||
@ -965,7 +965,7 @@ void Rinex_Printer::log_rinex_obs(std::ofstream& out, gps_navigation_message nav
|
|||||||
if (version == 2)
|
if (version == 2)
|
||||||
{
|
{
|
||||||
line += "OBSERVATION DATA FILE FOR VERSION 2.11 STILL NOT IMPLEMENTED";
|
line += "OBSERVATION DATA FILE FOR VERSION 2.11 STILL NOT IMPLEMENTED";
|
||||||
line += std::string(80-line.size(), ' ');
|
line += std::string(80 - line.size(), ' ');
|
||||||
Rinex_Printer::lengthCheck(line);
|
Rinex_Printer::lengthCheck(line);
|
||||||
out << line << std::endl;
|
out << line << std::endl;
|
||||||
}
|
}
|
||||||
@ -995,7 +995,7 @@ void Rinex_Printer::log_rinex_obs(std::ofstream& out, gps_navigation_message nav
|
|||||||
|
|
||||||
line += std::string(1, ' ');
|
line += std::string(1, ' ');
|
||||||
double utc_t = nav_msg.utc_time(nav_msg.sv_clock_correction(nav_msg.d_TOW));
|
double utc_t = nav_msg.utc_time(nav_msg.sv_clock_correction(nav_msg.d_TOW));
|
||||||
line += Rinex_Printer::asString(fmod(utc_t,60), 7);
|
line += Rinex_Printer::asString(fmod(utc_t, 60), 7);
|
||||||
line += std::string(2, ' ');
|
line += std::string(2, ' ');
|
||||||
// Epoch flag 0: OK 1: power failure between previous and current epoch <1: Special event
|
// Epoch flag 0: OK 1: power failure between previous and current epoch <1: Special event
|
||||||
line += std::string(1, '0');
|
line += std::string(1, '0');
|
||||||
@ -1051,7 +1051,7 @@ void Rinex_Printer::log_rinex_obs(std::ofstream& out, gps_navigation_message nav
|
|||||||
{
|
{
|
||||||
lineObs += Rinex_Printer::rightJustify(Rinex_Printer::asString<short>(ssi), 1);
|
lineObs += Rinex_Printer::rightJustify(Rinex_Printer::asString<short>(ssi), 1);
|
||||||
}
|
}
|
||||||
if (lineObs.size()<80) lineObs += std::string(80 - lineObs.size(), ' ');
|
if (lineObs.size() < 80) lineObs += std::string(80 - lineObs.size(), ' ');
|
||||||
out << lineObs << std::endl;
|
out << lineObs << std::endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -72,6 +72,7 @@ Channel::Channel(ConfigurationInterface *configuration, unsigned int channel,
|
|||||||
|
|
||||||
repeat_ = configuration->property("Acquisition" + boost::lexical_cast<
|
repeat_ = configuration->property("Acquisition" + boost::lexical_cast<
|
||||||
std::string>(channel_) + ".repeat_satellite", false);
|
std::string>(channel_) + ".repeat_satellite", false);
|
||||||
|
|
||||||
DLOG(INFO) << "Channel " << channel_ << " satellite repeat = " << repeat_
|
DLOG(INFO) << "Channel " << channel_ << " satellite repeat = " << repeat_
|
||||||
<< std::endl;
|
<< std::endl;
|
||||||
|
|
||||||
@ -139,8 +140,8 @@ void Channel::disconnect(gr_top_block_sptr top_block)
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
top_block->disconnect(acq_->get_right_block(), 0, trk_->get_left_block(),0);
|
top_block->disconnect(acq_->get_right_block(), 0, trk_->get_left_block(), 0);
|
||||||
top_block->disconnect(trk_->get_right_block(), 0, nav_->get_left_block(),0);
|
top_block->disconnect(trk_->get_right_block(), 0, nav_->get_left_block(), 0);
|
||||||
|
|
||||||
acq_->disconnect(top_block);
|
acq_->disconnect(top_block);
|
||||||
trk_->disconnect(top_block);
|
trk_->disconnect(top_block);
|
||||||
@ -160,7 +161,6 @@ gr_basic_block_sptr Channel::get_left_block()
|
|||||||
|
|
||||||
gr_basic_block_sptr Channel::get_right_block()
|
gr_basic_block_sptr Channel::get_right_block()
|
||||||
{
|
{
|
||||||
|
|
||||||
return nav_->get_right_block();
|
return nav_->get_right_block();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -34,33 +34,26 @@
|
|||||||
#include <glog/log_severity.h>
|
#include <glog/log_severity.h>
|
||||||
#include <glog/logging.h>
|
#include <glog/logging.h>
|
||||||
|
|
||||||
struct Ev_gps_channel_start_acquisition: sc::event<
|
struct Ev_gps_channel_start_acquisition: sc::event<Ev_gps_channel_start_acquisition>
|
||||||
Ev_gps_channel_start_acquisition>
|
|
||||||
{};
|
{};
|
||||||
|
|
||||||
struct Ev_gps_channel_valid_acquisition: sc::event<
|
struct Ev_gps_channel_valid_acquisition: sc::event<Ev_gps_channel_valid_acquisition>
|
||||||
Ev_gps_channel_valid_acquisition>
|
|
||||||
{};
|
{};
|
||||||
|
|
||||||
struct Ev_gps_channel_failed_acquisition_repeat: sc::event<
|
struct Ev_gps_channel_failed_acquisition_repeat: sc::event<Ev_gps_channel_failed_acquisition_repeat>
|
||||||
Ev_gps_channel_failed_acquisition_repeat>
|
|
||||||
{};
|
{};
|
||||||
|
|
||||||
struct Ev_gps_channel_failed_acquisition_no_repeat: sc::event<
|
struct Ev_gps_channel_failed_acquisition_no_repeat: sc::event<Ev_gps_channel_failed_acquisition_no_repeat>
|
||||||
Ev_gps_channel_failed_acquisition_no_repeat>
|
|
||||||
{};
|
{};
|
||||||
|
|
||||||
struct Ev_gps_channel_failed_tracking: sc::event<
|
struct Ev_gps_channel_failed_tracking: sc::event<Ev_gps_channel_failed_tracking>
|
||||||
Ev_gps_channel_failed_tracking>
|
|
||||||
{};
|
{};
|
||||||
|
|
||||||
struct gps_channel_idle_fsm_S0: public sc::state<gps_channel_idle_fsm_S0,
|
struct gps_channel_idle_fsm_S0: public sc::state<gps_channel_idle_fsm_S0,GpsL1CaChannelFsm>
|
||||||
GpsL1CaChannelFsm>
|
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
// sc::transition(event, next state)
|
// sc::transition(event, next state)
|
||||||
typedef sc::transition<Ev_gps_channel_start_acquisition,
|
typedef sc::transition<Ev_gps_channel_start_acquisition, gps_channel_acquiring_fsm_S1> reactions;
|
||||||
gps_channel_acquiring_fsm_S1> reactions;
|
|
||||||
gps_channel_idle_fsm_S0(my_context ctx) :
|
gps_channel_idle_fsm_S0(my_context ctx) :
|
||||||
my_base(ctx)
|
my_base(ctx)
|
||||||
{
|
{
|
||||||
@ -68,72 +61,74 @@ public:
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct gps_channel_acquiring_fsm_S1: public sc::state<
|
|
||||||
gps_channel_acquiring_fsm_S1, GpsL1CaChannelFsm>
|
struct gps_channel_acquiring_fsm_S1: public sc::state<gps_channel_acquiring_fsm_S1, GpsL1CaChannelFsm>
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef mpl::list<sc::transition<
|
typedef mpl::list<sc::transition<Ev_gps_channel_failed_acquisition_no_repeat, gps_channel_waiting_fsm_S3>,
|
||||||
Ev_gps_channel_failed_acquisition_no_repeat,
|
sc::transition<Ev_gps_channel_failed_acquisition_repeat, gps_channel_acquiring_fsm_S1>,
|
||||||
gps_channel_waiting_fsm_S3>, sc::transition<
|
sc::transition<Ev_gps_channel_valid_acquisition, gps_channel_tracking_fsm_S2> >reactions;
|
||||||
Ev_gps_channel_failed_acquisition_repeat,
|
|
||||||
gps_channel_acquiring_fsm_S1>, sc::transition<
|
|
||||||
Ev_gps_channel_valid_acquisition, gps_channel_tracking_fsm_S2> >
|
|
||||||
reactions;
|
|
||||||
|
|
||||||
gps_channel_acquiring_fsm_S1(my_context ctx) :
|
gps_channel_acquiring_fsm_S1(my_context ctx) : my_base(ctx)
|
||||||
my_base(ctx)
|
|
||||||
{
|
{
|
||||||
//std::cout << "Enter Channel_Acq_S1 " << std::endl;
|
//std::cout << "Enter Channel_Acq_S1 " << std::endl;
|
||||||
context<GpsL1CaChannelFsm> ().start_acquisition();
|
context<GpsL1CaChannelFsm> ().start_acquisition();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct gps_channel_tracking_fsm_S2: public sc::state<
|
|
||||||
gps_channel_tracking_fsm_S2, GpsL1CaChannelFsm>
|
|
||||||
|
struct gps_channel_tracking_fsm_S2: public sc::state<gps_channel_tracking_fsm_S2, GpsL1CaChannelFsm>
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef sc::transition<Ev_gps_channel_failed_tracking,
|
typedef sc::transition<Ev_gps_channel_failed_tracking, gps_channel_acquiring_fsm_S1> reactions;
|
||||||
gps_channel_acquiring_fsm_S1> reactions;
|
|
||||||
|
|
||||||
gps_channel_tracking_fsm_S2(my_context ctx) :
|
gps_channel_tracking_fsm_S2(my_context ctx) : my_base(ctx)
|
||||||
my_base(ctx)
|
|
||||||
{
|
{
|
||||||
//std::cout << "Enter Channel_tracking_S2 " << std::endl;
|
//std::cout << "Enter Channel_tracking_S2 " << std::endl;
|
||||||
context<GpsL1CaChannelFsm> ().start_tracking();
|
context<GpsL1CaChannelFsm> ().start_tracking();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
struct gps_channel_waiting_fsm_S3: public sc::state<
|
|
||||||
gps_channel_waiting_fsm_S3, GpsL1CaChannelFsm>
|
|
||||||
|
struct gps_channel_waiting_fsm_S3: public sc::state<gps_channel_waiting_fsm_S3, GpsL1CaChannelFsm>
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
typedef sc::transition<Ev_gps_channel_start_acquisition,
|
typedef sc::transition<Ev_gps_channel_start_acquisition, gps_channel_acquiring_fsm_S1> reactions;
|
||||||
gps_channel_acquiring_fsm_S1> reactions;
|
|
||||||
|
|
||||||
gps_channel_waiting_fsm_S3(my_context ctx) :
|
gps_channel_waiting_fsm_S3(my_context ctx) : my_base(ctx)
|
||||||
my_base(ctx)
|
|
||||||
{
|
{
|
||||||
//std::cout << "Enter Channel_waiting_S3 " << std::endl;
|
//std::cout << "Enter Channel_waiting_S3 " << std::endl;
|
||||||
context<GpsL1CaChannelFsm> ().request_satellite();
|
context<GpsL1CaChannelFsm> ().request_satellite();
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
GpsL1CaChannelFsm::GpsL1CaChannelFsm()
|
GpsL1CaChannelFsm::GpsL1CaChannelFsm()
|
||||||
{
|
{
|
||||||
initiate(); //start the FSM
|
initiate(); //start the FSM
|
||||||
}
|
}
|
||||||
|
|
||||||
GpsL1CaChannelFsm::GpsL1CaChannelFsm(AcquisitionInterface *acquisition) :
|
|
||||||
acq_(acquisition)
|
|
||||||
|
|
||||||
|
GpsL1CaChannelFsm::GpsL1CaChannelFsm(AcquisitionInterface *acquisition) : acq_(acquisition)
|
||||||
{
|
{
|
||||||
initiate(); //start the FSM
|
initiate(); //start the FSM
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::Event_gps_start_acquisition()
|
void GpsL1CaChannelFsm::Event_gps_start_acquisition()
|
||||||
{
|
{
|
||||||
this->process_event(Ev_gps_channel_start_acquisition());
|
this->process_event(Ev_gps_channel_start_acquisition());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::Event_gps_valid_acquisition()
|
void GpsL1CaChannelFsm::Event_gps_valid_acquisition()
|
||||||
{
|
{
|
||||||
this->process_event(Ev_gps_channel_valid_acquisition());
|
this->process_event(Ev_gps_channel_valid_acquisition());
|
||||||
@ -144,40 +139,56 @@ void GpsL1CaChannelFsm::Event_gps_failed_acquisition_repeat()
|
|||||||
this->process_event(Ev_gps_channel_failed_acquisition_repeat());
|
this->process_event(Ev_gps_channel_failed_acquisition_repeat());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::Event_gps_failed_acquisition_no_repeat()
|
void GpsL1CaChannelFsm::Event_gps_failed_acquisition_no_repeat()
|
||||||
{
|
{
|
||||||
this->process_event(Ev_gps_channel_failed_acquisition_no_repeat());
|
this->process_event(Ev_gps_channel_failed_acquisition_no_repeat());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::Event_gps_failed_tracking()
|
void GpsL1CaChannelFsm::Event_gps_failed_tracking()
|
||||||
{
|
{
|
||||||
this->process_event(Ev_gps_channel_failed_tracking());
|
this->process_event(Ev_gps_channel_failed_tracking());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::set_acquisition(AcquisitionInterface *acquisition)
|
void GpsL1CaChannelFsm::set_acquisition(AcquisitionInterface *acquisition)
|
||||||
{
|
{
|
||||||
acq_ = acquisition;
|
acq_ = acquisition;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::set_tracking(TrackingInterface *tracking)
|
void GpsL1CaChannelFsm::set_tracking(TrackingInterface *tracking)
|
||||||
{
|
{
|
||||||
trk_ = tracking;
|
trk_ = tracking;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::set_queue(gr_msg_queue_sptr queue)
|
void GpsL1CaChannelFsm::set_queue(gr_msg_queue_sptr queue)
|
||||||
{
|
{
|
||||||
queue_ = queue;
|
queue_ = queue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::set_channel(unsigned int channel)
|
void GpsL1CaChannelFsm::set_channel(unsigned int channel)
|
||||||
{
|
{
|
||||||
channel_ = channel;
|
channel_ = channel;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::start_acquisition()
|
void GpsL1CaChannelFsm::start_acquisition()
|
||||||
{
|
{
|
||||||
acq_->reset();
|
acq_->reset();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::start_tracking()
|
void GpsL1CaChannelFsm::start_tracking()
|
||||||
{
|
{
|
||||||
LOG_AT_LEVEL(INFO) << "Channel " << channel_
|
LOG_AT_LEVEL(INFO) << "Channel " << channel_
|
||||||
@ -193,6 +204,8 @@ void GpsL1CaChannelFsm::start_tracking()
|
|||||||
trk_->start_tracking();
|
trk_->start_tracking();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void GpsL1CaChannelFsm::request_satellite()
|
void GpsL1CaChannelFsm::request_satellite()
|
||||||
{
|
{
|
||||||
ControlMessageFactory* cmf = new ControlMessageFactory();
|
ControlMessageFactory* cmf = new ControlMessageFactory();
|
||||||
@ -201,6 +214,5 @@ void GpsL1CaChannelFsm::request_satellite()
|
|||||||
queue_->handle(cmf->GetQueueMessage(channel_, 0));
|
queue_->handle(cmf->GetQueueMessage(channel_, 0));
|
||||||
}
|
}
|
||||||
delete cmf;
|
delete cmf;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -55,14 +55,14 @@ GpsL1CaObservables::GpsL1CaObservables(ConfigurationInterface* configuration,
|
|||||||
{
|
{
|
||||||
|
|
||||||
int output_rate_ms;
|
int output_rate_ms;
|
||||||
output_rate_ms=configuration->property(role + ".output_rate_ms", 500);
|
output_rate_ms = configuration->property(role + ".output_rate_ms", 500);
|
||||||
|
|
||||||
std::string default_dump_filename = "./observables.dat";
|
std::string default_dump_filename = "./observables.dat";
|
||||||
|
|
||||||
DLOG(INFO) << "role " << role;
|
DLOG(INFO) << "role " << role;
|
||||||
|
|
||||||
bool flag_averaging;
|
bool flag_averaging;
|
||||||
flag_averaging=configuration->property(role + ".flag_averaging", false);
|
flag_averaging = configuration->property(role + ".flag_averaging", false);
|
||||||
|
|
||||||
dump_ = configuration->property(role + ".dump", false);
|
dump_ = configuration->property(role + ".dump", false);
|
||||||
dump_filename_ = configuration->property(role + ".dump_filename", default_dump_filename);
|
dump_filename_ = configuration->property(role + ".dump_filename", default_dump_filename);
|
||||||
|
@ -61,23 +61,23 @@ gps_l1_ca_observables_cc::gps_l1_ca_observables_cc(unsigned int nchannels, gr_ms
|
|||||||
d_queue = queue;
|
d_queue = queue;
|
||||||
d_dump = dump;
|
d_dump = dump;
|
||||||
d_nchannels = nchannels;
|
d_nchannels = nchannels;
|
||||||
d_output_rate_ms=output_rate_ms;
|
d_output_rate_ms = output_rate_ms;
|
||||||
d_history_prn_delay_ms= new std::deque<double>[d_nchannels];
|
d_history_prn_delay_ms = new std::deque<double>[d_nchannels];
|
||||||
d_dump_filename=dump_filename;
|
d_dump_filename = dump_filename;
|
||||||
d_flag_averaging=flag_averaging;
|
d_flag_averaging = flag_averaging;
|
||||||
|
|
||||||
// ############# ENABLE DATA FILE LOG #################
|
// ############# ENABLE DATA FILE LOG #################
|
||||||
if (d_dump==true)
|
if (d_dump == true)
|
||||||
{
|
{
|
||||||
if (d_dump_file.is_open()==false)
|
if (d_dump_file.is_open() == false)
|
||||||
{
|
{
|
||||||
try {
|
try {
|
||||||
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::out | std::ios::binary);
|
d_dump_file.open(d_dump_filename.c_str(), std::ios::out | std::ios::binary);
|
||||||
std::cout<<"Observables dump enabled Log file: "<<d_dump_filename.c_str()<<std::endl;
|
std::cout << "Observables dump enabled Log file: " << d_dump_filename.c_str() << std::endl;
|
||||||
}
|
}
|
||||||
catch (std::ifstream::failure e) {
|
catch (std::ifstream::failure e) {
|
||||||
std::cout << "Exception opening observables dump file "<<e.what()<<"\r\n";
|
std::cout << "Exception opening observables dump file " << e.what() << std::endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -103,7 +103,7 @@ bool pairCompare_double( std::pair<int,double> a, std::pair<int,double> b)
|
|||||||
void clearQueue( std::deque<double> &q )
|
void clearQueue( std::deque<double> &q )
|
||||||
{
|
{
|
||||||
std::deque<double> empty;
|
std::deque<double> empty;
|
||||||
std::swap( q, empty );
|
std::swap(q, empty);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -127,18 +127,18 @@ int gps_l1_ca_observables_cc::general_work (int noutput_items, gr_vector_int &ni
|
|||||||
double pseudoranges_timestamp_ms;
|
double pseudoranges_timestamp_ms;
|
||||||
double traveltime_ms;
|
double traveltime_ms;
|
||||||
double pseudorange_m;
|
double pseudorange_m;
|
||||||
int history_shift=0;
|
int history_shift = 0;
|
||||||
double delta_timestamp_ms;
|
double delta_timestamp_ms;
|
||||||
double min_delta_timestamp_ms;
|
double min_delta_timestamp_ms;
|
||||||
double actual_min_prn_delay_ms;
|
double actual_min_prn_delay_ms;
|
||||||
double current_prn_delay_ms;
|
double current_prn_delay_ms;
|
||||||
|
|
||||||
int pseudoranges_reference_sat_ID=0;
|
int pseudoranges_reference_sat_ID = 0;
|
||||||
unsigned int pseudoranges_reference_sat_channel_ID=0;
|
unsigned int pseudoranges_reference_sat_channel_ID = 0;
|
||||||
|
|
||||||
d_sample_counter++; //count for the processed samples
|
d_sample_counter++; //count for the processed samples
|
||||||
|
|
||||||
bool flag_history_ok=true; //flag to indicate that all the queues have filled their timestamp history
|
bool flag_history_ok = true; //flag to indicate that all the queues have filled their timestamp history
|
||||||
/*
|
/*
|
||||||
* 1. Read the GNSS SYNCHRO objects from available channels to obtain the preamble timestamp, current PRN start time and accumulated carrier phase
|
* 1. Read the GNSS SYNCHRO objects from available channels to obtain the preamble timestamp, current PRN start time and accumulated carrier phase
|
||||||
*/
|
*/
|
||||||
@ -146,12 +146,12 @@ int gps_l1_ca_observables_cc::general_work (int noutput_items, gr_vector_int &ni
|
|||||||
{
|
{
|
||||||
if (in[i][0].valid_word) //if this channel have valid word
|
if (in[i][0].valid_word) //if this channel have valid word
|
||||||
{
|
{
|
||||||
gps_words.insert(std::pair<int,gnss_synchro>(in[i][0].channel_ID,in[i][0])); //record the word structure in a map for pseudoranges
|
gps_words.insert(std::pair<int,gnss_synchro>(in[i][0].channel_ID, in[i][0])); //record the word structure in a map for pseudoranges
|
||||||
// RECORD PRN start timestamps history
|
// RECORD PRN start timestamps history
|
||||||
if (d_history_prn_delay_ms[i].size()<MAX_TOA_DELAY_MS)
|
if (d_history_prn_delay_ms[i].size()<MAX_TOA_DELAY_MS)
|
||||||
{
|
{
|
||||||
d_history_prn_delay_ms[i].push_front(in[i][0].prn_delay_ms);
|
d_history_prn_delay_ms[i].push_front(in[i][0].prn_delay_ms);
|
||||||
flag_history_ok=false; // at least one channel need more samples
|
flag_history_ok = false; // at least one channel need more samples
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -167,34 +167,34 @@ int gps_l1_ca_observables_cc::general_work (int noutput_items, gr_vector_int &ni
|
|||||||
*/
|
*/
|
||||||
for (unsigned int i=0; i<d_nchannels ; i++)
|
for (unsigned int i=0; i<d_nchannels ; i++)
|
||||||
{
|
{
|
||||||
current_gnss_pseudorange.valid=false;
|
current_gnss_pseudorange.valid = false;
|
||||||
current_gnss_pseudorange.SV_ID=0;
|
current_gnss_pseudorange.SV_ID = 0;
|
||||||
current_gnss_pseudorange.pseudorange_m=0;
|
current_gnss_pseudorange.pseudorange_m = 0;
|
||||||
current_gnss_pseudorange.timestamp_ms=0;
|
current_gnss_pseudorange.timestamp_ms = 0;
|
||||||
*out[i]=current_gnss_pseudorange;
|
*out[i] = current_gnss_pseudorange;
|
||||||
}
|
}
|
||||||
/*
|
/*
|
||||||
* 2. Compute RAW pseudorranges: Use only the valid channels (channels that are tracking a satellite)
|
* 2. Compute RAW pseudorranges: Use only the valid channels (channels that are tracking a satellite)
|
||||||
*/
|
*/
|
||||||
if(gps_words.size()>0 and flag_history_ok==true)
|
if(gps_words.size() > 0 and flag_history_ok == true)
|
||||||
{
|
{
|
||||||
/*
|
/*
|
||||||
* 2.1 find the minimum preamble timestamp (nearest satellite, will be the reference)
|
* 2.1 find the minimum preamble timestamp (nearest satellite, will be the reference)
|
||||||
*/
|
*/
|
||||||
// The nearest satellite, first preamble to arrive
|
// The nearest satellite, first preamble to arrive
|
||||||
gps_words_iter=min_element(gps_words.begin(),gps_words.end(),pairCompare_gnss_synchro);
|
gps_words_iter = min_element(gps_words.begin(), gps_words.end(), pairCompare_gnss_synchro);
|
||||||
min_preamble_delay_ms=gps_words_iter->second.preamble_delay_ms; //[ms]
|
min_preamble_delay_ms = gps_words_iter->second.preamble_delay_ms; //[ms]
|
||||||
|
|
||||||
pseudoranges_reference_sat_ID=gps_words_iter->second.satellite_PRN; // it is the reference!
|
pseudoranges_reference_sat_ID = gps_words_iter->second.satellite_PRN; // it is the reference!
|
||||||
pseudoranges_reference_sat_channel_ID=gps_words_iter->second.channel_ID;
|
pseudoranges_reference_sat_channel_ID = gps_words_iter->second.channel_ID;
|
||||||
|
|
||||||
// The farthest satellite, last preamble to arrive
|
// The farthest satellite, last preamble to arrive
|
||||||
gps_words_iter=max_element(gps_words.begin(),gps_words.end(),pairCompare_gnss_synchro);
|
gps_words_iter = max_element(gps_words.begin(), gps_words.end(), pairCompare_gnss_synchro);
|
||||||
max_preamble_delay_ms=gps_words_iter->second.preamble_delay_ms;
|
max_preamble_delay_ms = gps_words_iter->second.preamble_delay_ms;
|
||||||
min_delta_timestamp_ms=gps_words_iter->second.prn_delay_ms-max_preamble_delay_ms; //[ms]
|
min_delta_timestamp_ms = gps_words_iter->second.prn_delay_ms - max_preamble_delay_ms; //[ms]
|
||||||
|
|
||||||
// check if this is a valid set of observations
|
// check if this is a valid set of observations
|
||||||
if ((max_preamble_delay_ms-min_preamble_delay_ms)<MAX_TOA_DELAY_MS)
|
if ((max_preamble_delay_ms - min_preamble_delay_ms) < MAX_TOA_DELAY_MS)
|
||||||
{
|
{
|
||||||
// Now we have to determine were we are in time, compared with the last preamble! -> we select the corresponding history
|
// Now we have to determine were we are in time, compared with the last preamble! -> we select the corresponding history
|
||||||
/*!
|
/*!
|
||||||
@ -204,10 +204,10 @@ int gps_l1_ca_observables_cc::general_work (int noutput_items, gr_vector_int &ni
|
|||||||
// find again the minimum CURRENT minimum preamble time, taking into account the preamble timeshift
|
// find again the minimum CURRENT minimum preamble time, taking into account the preamble timeshift
|
||||||
for(gps_words_iter = gps_words.begin(); gps_words_iter != gps_words.end(); gps_words_iter++)
|
for(gps_words_iter = gps_words.begin(); gps_words_iter != gps_words.end(); gps_words_iter++)
|
||||||
{
|
{
|
||||||
delta_timestamp_ms=(gps_words_iter->second.prn_delay_ms-gps_words_iter->second.preamble_delay_ms)-min_delta_timestamp_ms;
|
delta_timestamp_ms = (gps_words_iter->second.prn_delay_ms - gps_words_iter->second.preamble_delay_ms) - min_delta_timestamp_ms;
|
||||||
history_shift=round(delta_timestamp_ms);
|
history_shift = round(delta_timestamp_ms);
|
||||||
//std::cout<<"history_shift="<<history_shift<<"\r\n";
|
//std::cout<<"history_shift="<<history_shift<<"\r\n";
|
||||||
current_prn_timestamps_ms.insert(std::pair<int,double>(gps_words_iter->second.channel_ID,d_history_prn_delay_ms[gps_words_iter->second.channel_ID][history_shift]));
|
current_prn_timestamps_ms.insert(std::pair<int,double>(gps_words_iter->second.channel_ID, d_history_prn_delay_ms[gps_words_iter->second.channel_ID][history_shift]));
|
||||||
// debug: preamble position test
|
// debug: preamble position test
|
||||||
//if ((d_history_prn_delay_ms[gps_words_iter->second.channel_ID][history_shift]-gps_words_iter->second.preamble_delay_ms)<0.1)
|
//if ((d_history_prn_delay_ms[gps_words_iter->second.channel_ID][history_shift]-gps_words_iter->second.preamble_delay_ms)<0.1)
|
||||||
//{std::cout<<"ch "<<gps_words_iter->second.channel_ID<<" current_prn_time-last_preamble_prn_time="<<
|
//{std::cout<<"ch "<<gps_words_iter->second.channel_ID<<" current_prn_time-last_preamble_prn_time="<<
|
||||||
@ -221,13 +221,12 @@ int gps_l1_ca_observables_cc::general_work (int noutput_items, gr_vector_int &ni
|
|||||||
//{
|
//{
|
||||||
//std::cout<<"PREAMBLE NAVIGATION NOW!\r\n";
|
//std::cout<<"PREAMBLE NAVIGATION NOW!\r\n";
|
||||||
//d_sample_counter=0;
|
//d_sample_counter=0;
|
||||||
|
|
||||||
//}
|
//}
|
||||||
current_prn_timestamps_ms_iter=min_element(current_prn_timestamps_ms.begin(),current_prn_timestamps_ms.end(),pairCompare_double);
|
current_prn_timestamps_ms_iter = min_element(current_prn_timestamps_ms.begin(), current_prn_timestamps_ms.end(), pairCompare_double);
|
||||||
|
|
||||||
actual_min_prn_delay_ms=current_prn_timestamps_ms_iter->second;
|
actual_min_prn_delay_ms = current_prn_timestamps_ms_iter->second;
|
||||||
|
|
||||||
pseudoranges_timestamp_ms=actual_min_prn_delay_ms; //save the shortest pseudorange timestamp to compute the current GNSS timestamp
|
pseudoranges_timestamp_ms = actual_min_prn_delay_ms; //save the shortest pseudorange timestamp to compute the current GNSS timestamp
|
||||||
/*
|
/*
|
||||||
* 2.2 compute the pseudoranges
|
* 2.2 compute the pseudoranges
|
||||||
*/
|
*/
|
||||||
@ -236,53 +235,54 @@ int gps_l1_ca_observables_cc::general_work (int noutput_items, gr_vector_int &ni
|
|||||||
{
|
{
|
||||||
// #### compute the pseudorange for this satellite ###
|
// #### compute the pseudorange for this satellite ###
|
||||||
|
|
||||||
current_prn_delay_ms=current_prn_timestamps_ms.at(gps_words_iter->second.channel_ID);
|
current_prn_delay_ms = current_prn_timestamps_ms.at(gps_words_iter->second.channel_ID);
|
||||||
traveltime_ms=current_prn_delay_ms-actual_min_prn_delay_ms+GPS_STARTOFFSET_ms; //[ms]
|
traveltime_ms = current_prn_delay_ms - actual_min_prn_delay_ms + GPS_STARTOFFSET_ms; //[ms]
|
||||||
//std::cout<<"delta_time_ms="<<current_prn_delay_ms-actual_min_prn_delay_ms<<"\r\n";
|
//std::cout<<"delta_time_ms="<<current_prn_delay_ms-actual_min_prn_delay_ms<<"\r\n";
|
||||||
pseudorange_m=traveltime_ms*GPS_C_m_ms; // [m]
|
pseudorange_m = traveltime_ms*GPS_C_m_ms; // [m]
|
||||||
|
|
||||||
// update the pseudorange object
|
// update the pseudorange object
|
||||||
current_gnss_pseudorange.pseudorange_m=pseudorange_m;
|
current_gnss_pseudorange.pseudorange_m = pseudorange_m;
|
||||||
current_gnss_pseudorange.timestamp_ms=pseudoranges_timestamp_ms;
|
current_gnss_pseudorange.timestamp_ms = pseudoranges_timestamp_ms;
|
||||||
current_gnss_pseudorange.SV_ID=gps_words_iter->second.satellite_PRN;
|
current_gnss_pseudorange.SV_ID = gps_words_iter->second.satellite_PRN;
|
||||||
current_gnss_pseudorange.valid=true;
|
current_gnss_pseudorange.valid = true;
|
||||||
// #### write the pseudorrange block output for this satellite ###
|
// #### write the pseudorrange block output for this satellite ###
|
||||||
*out[gps_words_iter->second.channel_ID]=current_gnss_pseudorange;
|
*out[gps_words_iter->second.channel_ID] = current_gnss_pseudorange;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(d_dump==true) {
|
if(d_dump == true) {
|
||||||
// MULTIPLEXED FILE RECORDING - Record results to file
|
// MULTIPLEXED FILE RECORDING - Record results to file
|
||||||
try {
|
try {
|
||||||
double tmp_double;
|
double tmp_double;
|
||||||
for (unsigned int i=0; i<d_nchannels ; i++)
|
for (unsigned int i=0; i<d_nchannels ; i++)
|
||||||
{
|
{
|
||||||
tmp_double=in[i][0].preamble_delay_ms;
|
tmp_double = in[i][0].preamble_delay_ms;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
tmp_double=in[i][0].prn_delay_ms;
|
tmp_double = in[i][0].prn_delay_ms;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
tmp_double=out[i][0].pseudorange_m;
|
tmp_double = out[i][0].pseudorange_m;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
tmp_double=out[i][0].timestamp_ms;
|
tmp_double = out[i][0].timestamp_ms;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
tmp_double=out[i][0].SV_ID;
|
tmp_double = out[i][0].SV_ID;
|
||||||
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
d_dump_file.write((char*)&tmp_double, sizeof(double));
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
catch (std::ifstream::failure e) {
|
catch (std::ifstream::failure e)
|
||||||
std::cout << "Exception writing observables dump file "<<e.what()<<"\r\n";
|
{
|
||||||
|
std::cout << "Exception writing observables dump file "<< e.what() << std::endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
consume_each(1); //one by one
|
consume_each(1); //one by one
|
||||||
|
|
||||||
if ((d_sample_counter%d_output_rate_ms)==0)
|
if ((d_sample_counter % d_output_rate_ms) == 0)
|
||||||
{
|
{
|
||||||
return 1; //Output the observables
|
return 1; //Output the observables
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
return 0;//hold on
|
return 0; //hold on
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -58,16 +58,18 @@ gps_l1_ca_make_telemetry_decoder_cc(unsigned int satellite, long if_freq, long f
|
|||||||
fs_in, vector_length, queue, dump));
|
fs_in, vector_length, queue, dump));
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_telemetry_decoder_cc::forecast (int noutput_items,
|
|
||||||
gr_vector_int &ninput_items_required)
|
|
||||||
|
void gps_l1_ca_telemetry_decoder_cc::forecast (int noutput_items, gr_vector_int &ninput_items_required)
|
||||||
{
|
{
|
||||||
for (unsigned i = 0; i < 3; i++)
|
for (unsigned i = 0; i < 3; i++)
|
||||||
{
|
{
|
||||||
ninput_items_required[i] =d_samples_per_bit*8; //set the required sample history
|
ninput_items_required[i] = d_samples_per_bit*8; //set the required sample history
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
gps_l1_ca_telemetry_decoder_cc::gps_l1_ca_telemetry_decoder_cc(unsigned int satellite, long if_freq, long fs_in, unsigned
|
gps_l1_ca_telemetry_decoder_cc::gps_l1_ca_telemetry_decoder_cc(unsigned int satellite, long if_freq, long fs_in, unsigned
|
||||||
int vector_length, gr_msg_queue_sptr queue, bool dump) :
|
int vector_length, gr_msg_queue_sptr queue, bool dump) :
|
||||||
gr_block ("gps_navigation_cc", gr_make_io_signature (5, 5, sizeof(double)),
|
gr_block ("gps_navigation_cc", gr_make_io_signature (5, 5, sizeof(double)),
|
||||||
@ -78,61 +80,60 @@ gps_l1_ca_telemetry_decoder_cc::gps_l1_ca_telemetry_decoder_cc(unsigned int sate
|
|||||||
d_dump = dump;
|
d_dump = dump;
|
||||||
d_satellite = satellite;
|
d_satellite = satellite;
|
||||||
d_vector_length = vector_length;
|
d_vector_length = vector_length;
|
||||||
d_samples_per_bit=20; // it is exactly 1000*(1/50)=20
|
d_samples_per_bit = 20; // it is exactly 1000*(1/50)=20
|
||||||
d_fs_in=fs_in;
|
d_fs_in = fs_in;
|
||||||
d_preamble_duration_seconds=(1.0/(float)GPS_CA_TELEMETRY_RATE_BITS_SECOND)*(float)GPS_CA_PREAMBLE_LENGTH_BITS;
|
d_preamble_duration_seconds = (1.0/(float)GPS_CA_TELEMETRY_RATE_BITS_SECOND)*(float)GPS_CA_PREAMBLE_LENGTH_BITS;
|
||||||
//std::cout<<"d_preamble_duration_seconds="<<d_preamble_duration_seconds<<"\r\n";
|
//std::cout<<"d_preamble_duration_seconds="<<d_preamble_duration_seconds<<"\r\n";
|
||||||
// set the preamble
|
// set the preamble
|
||||||
unsigned short int preambles_bits[8]=GPS_PREAMBLE;
|
unsigned short int preambles_bits[8] = GPS_PREAMBLE;
|
||||||
|
|
||||||
memcpy((unsigned short int*)this->d_preambles_bits, (unsigned short int*)preambles_bits, 8* sizeof(unsigned short int));
|
memcpy((unsigned short int*)this->d_preambles_bits, (unsigned short int*)preambles_bits, 8*sizeof(unsigned short int));
|
||||||
|
|
||||||
// preamble bits to sampled symbols
|
// preamble bits to sampled symbols
|
||||||
d_preambles_symbols=(signed int*)malloc(sizeof(signed int)*8*d_samples_per_bit);
|
d_preambles_symbols = (signed int*)malloc(sizeof(signed int)*8*d_samples_per_bit);
|
||||||
int n=0;
|
int n = 0;
|
||||||
for (int i=0;i<8;i++)
|
for (int i=0; i<8; i++)
|
||||||
{
|
{
|
||||||
for (unsigned int j=0;j<d_samples_per_bit;j++)
|
for (unsigned int j=0; j<d_samples_per_bit; j++)
|
||||||
{
|
{
|
||||||
if (d_preambles_bits[i]==1)
|
if (d_preambles_bits[i] == 1)
|
||||||
{
|
{
|
||||||
d_preambles_symbols[n]=1;
|
d_preambles_symbols[n] = 1;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
d_preambles_symbols[n]=-1;
|
d_preambles_symbols[n] = -1;
|
||||||
}
|
}
|
||||||
n++;
|
n++;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
d_sample_counter=0;
|
d_sample_counter = 0;
|
||||||
d_preamble_code_phase_seconds=0;
|
d_preamble_code_phase_seconds = 0;
|
||||||
d_stat=0;
|
d_stat = 0;
|
||||||
d_preamble_index=0;
|
d_preamble_index = 0;
|
||||||
d_symbol_accumulator_counter=0;
|
d_symbol_accumulator_counter = 0;
|
||||||
d_frame_bit_index=0;
|
d_frame_bit_index = 0;
|
||||||
|
|
||||||
d_flag_frame_sync=false;
|
d_flag_frame_sync = false;
|
||||||
d_GPS_frame_4bytes=0;
|
d_GPS_frame_4bytes = 0;
|
||||||
d_prev_GPS_frame_4bytes=0;
|
d_prev_GPS_frame_4bytes = 0;
|
||||||
d_flag_parity=false;
|
d_flag_parity = false;
|
||||||
|
|
||||||
//set_history(d_samples_per_bit*8); // At least a history of 8 bits are needed to correlate with the preamble
|
//set_history(d_samples_per_bit*8); // At least a history of 8 bits are needed to correlate with the preamble
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
gps_l1_ca_telemetry_decoder_cc::~gps_l1_ca_telemetry_decoder_cc()
|
gps_l1_ca_telemetry_decoder_cc::~gps_l1_ca_telemetry_decoder_cc()
|
||||||
{
|
{
|
||||||
delete d_preambles_symbols;
|
delete d_preambles_symbols;
|
||||||
d_dump_file.close();
|
d_dump_file.close();
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
bool gps_l1_ca_telemetry_decoder_cc::gps_word_parityCheck(unsigned int gpsword)
|
bool gps_l1_ca_telemetry_decoder_cc::gps_word_parityCheck(unsigned int gpsword)
|
||||||
{
|
{
|
||||||
unsigned int d1,d2,d3,d4,d5,d6,d7,t,parity;
|
unsigned int d1, d2, d3, d4, d5, d6, d7, t, parity;
|
||||||
|
|
||||||
/* XOR as many bits in parallel as possible. The magic constants pick
|
/* XOR as many bits in parallel as possible. The magic constants pick
|
||||||
up bits which are to be XOR'ed together to implement the GPS parity
|
up bits which are to be XOR'ed together to implement the GPS parity
|
||||||
@ -150,19 +151,19 @@ bool gps_l1_ca_telemetry_decoder_cc::gps_word_parityCheck(unsigned int gpsword)
|
|||||||
t = d1 ^ d2 ^ d3 ^ d4 ^ d5 ^ d6 ^ d7;
|
t = d1 ^ d2 ^ d3 ^ d4 ^ d5 ^ d6 ^ d7;
|
||||||
|
|
||||||
// Now XOR the 5 6-bit fields together to produce the 6-bit final result.
|
// Now XOR the 5 6-bit fields together to produce the 6-bit final result.
|
||||||
|
|
||||||
parity = t ^ _lrotl(t,6) ^ _lrotl(t,12) ^ _lrotl(t,18) ^ _lrotl(t,24);
|
parity = t ^ _lrotl(t,6) ^ _lrotl(t,12) ^ _lrotl(t,18) ^ _lrotl(t,24);
|
||||||
parity = parity & 0x3F;
|
parity = parity & 0x3F;
|
||||||
if (parity == (gpsword&0x3F))
|
if (parity == (gpsword&0x3F)) return(true);
|
||||||
return(true);
|
else return(false);
|
||||||
else
|
|
||||||
return(false);
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_int &ninput_items,
|
int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_int &ninput_items,
|
||||||
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items) {
|
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items)
|
||||||
int corr_value=0;
|
{
|
||||||
|
int corr_value = 0;
|
||||||
int preamble_diff;
|
int preamble_diff;
|
||||||
|
|
||||||
gnss_synchro gps_synchro; //structure to save the synchronization information
|
gnss_synchro gps_synchro; //structure to save the synchronization information
|
||||||
@ -198,15 +199,15 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
// }
|
// }
|
||||||
// TODO Optimize me!
|
// TODO Optimize me!
|
||||||
//******* preamble correlation ********
|
//******* preamble correlation ********
|
||||||
for (unsigned int i=0;i<d_samples_per_bit*8;i++)
|
for (unsigned int i=0; i<d_samples_per_bit*8; i++)
|
||||||
{
|
{
|
||||||
if (in[1][i] < 0) // symbols clipping
|
if (in[1][i] < 0) // symbols clipping
|
||||||
{
|
{
|
||||||
corr_value-=d_preambles_symbols[i];
|
corr_value -= d_preambles_symbols[i];
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
corr_value+=d_preambles_symbols[i];
|
corr_value += d_preambles_symbols[i];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
d_flag_preamble=false;
|
d_flag_preamble=false;
|
||||||
@ -214,45 +215,45 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
if (abs(corr_value)>=160)
|
if (abs(corr_value)>=160)
|
||||||
{
|
{
|
||||||
//TODO: Rewrite with state machine
|
//TODO: Rewrite with state machine
|
||||||
if (d_stat==0)
|
if (d_stat == 0)
|
||||||
{
|
{
|
||||||
d_GPS_FSM.Event_gps_word_preamble();
|
d_GPS_FSM.Event_gps_word_preamble();
|
||||||
d_preamble_index=d_sample_counter;//record the preamble sample stamp
|
d_preamble_index = d_sample_counter;//record the preamble sample stamp
|
||||||
std::cout<<"Preamble detection for SAT "<<d_satellite<<std::endl;
|
std::cout << "Preamble detection for SAT " << d_satellite<< std::endl;
|
||||||
d_symbol_accumulator=0; //sync the symbol to bits integrator
|
d_symbol_accumulator = 0; //sync the symbol to bits integrator
|
||||||
d_symbol_accumulator_counter=0;
|
d_symbol_accumulator_counter = 0;
|
||||||
d_frame_bit_index=8;
|
d_frame_bit_index = 8;
|
||||||
d_stat=1; // enter into frame pre-detection status
|
d_stat = 1; // enter into frame pre-detection status
|
||||||
}
|
}
|
||||||
else if (d_stat==1) //check 6 seconds of preample separation
|
else if (d_stat == 1) //check 6 seconds of preample separation
|
||||||
{
|
{
|
||||||
preamble_diff=abs(d_sample_counter-d_preamble_index);
|
preamble_diff=abs(d_sample_counter-d_preamble_index);
|
||||||
if (abs(preamble_diff-6000)<1)
|
if (abs(preamble_diff - 6000) < 1)
|
||||||
{
|
{
|
||||||
d_GPS_FSM.Event_gps_word_preamble();
|
d_GPS_FSM.Event_gps_word_preamble();
|
||||||
d_flag_preamble=true;
|
d_flag_preamble = true;
|
||||||
d_preamble_index=d_sample_counter;//record the preamble sample stamp (t_P)
|
d_preamble_index = d_sample_counter;//record the preamble sample stamp (t_P)
|
||||||
d_preamble_time_seconds=in[2][0]-d_preamble_duration_seconds; //record the PRN start sample index associated to the preamble
|
d_preamble_time_seconds = in[2][0] - d_preamble_duration_seconds; //record the PRN start sample index associated to the preamble
|
||||||
d_preamble_code_phase_seconds=in[4][0];
|
d_preamble_code_phase_seconds = in[4][0];
|
||||||
|
|
||||||
if (!d_flag_frame_sync)
|
if (!d_flag_frame_sync)
|
||||||
{
|
{
|
||||||
d_flag_frame_sync=true;
|
d_flag_frame_sync = true;
|
||||||
std::cout<<" Frame sync SAT "<<d_satellite<<" with preamble start at "<<d_preamble_time_seconds<<" [s]"<<std::endl;
|
std::cout <<" Frame sync SAT " << d_satellite << " with preamble start at " << d_preamble_time_seconds << " [s]" << std::endl;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
if (d_stat==1)
|
if (d_stat == 1)
|
||||||
{
|
{
|
||||||
preamble_diff=d_sample_counter-d_preamble_index;
|
preamble_diff = d_sample_counter - d_preamble_index;
|
||||||
if (preamble_diff>6001)
|
if (preamble_diff > 6001)
|
||||||
{
|
{
|
||||||
std::cout<<"Lost of frame sync SAT "<<this->d_satellite<<" preamble_diff= "<<preamble_diff<<std::endl;
|
std::cout << "Lost of frame sync SAT " << this->d_satellite << " preamble_diff= " << preamble_diff << std::endl;
|
||||||
d_stat=0; //lost of frame sync
|
d_stat = 0; //lost of frame sync
|
||||||
d_flag_frame_sync=false;
|
d_flag_frame_sync = false;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -261,22 +262,22 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
//d_preamble_phase-=in[3][0];
|
//d_preamble_phase-=in[3][0];
|
||||||
//******* SYMBOL TO BIT *******
|
//******* SYMBOL TO BIT *******
|
||||||
|
|
||||||
d_symbol_accumulator+=in[1][d_samples_per_bit*8-1]; // accumulate the input value in d_symbol_accumulator
|
d_symbol_accumulator += in[1][d_samples_per_bit*8 - 1]; // accumulate the input value in d_symbol_accumulator
|
||||||
d_symbol_accumulator_counter++;
|
d_symbol_accumulator_counter++;
|
||||||
if (d_symbol_accumulator_counter==20)
|
if (d_symbol_accumulator_counter == 20)
|
||||||
{
|
{
|
||||||
if (d_symbol_accumulator>0)
|
if (d_symbol_accumulator > 0)
|
||||||
{ //symbol to bit
|
{ //symbol to bit
|
||||||
d_GPS_frame_4bytes+=1; //insert the telemetry bit in LSB
|
d_GPS_frame_4bytes +=1; //insert the telemetry bit in LSB
|
||||||
}
|
}
|
||||||
d_symbol_accumulator=0;
|
d_symbol_accumulator = 0;
|
||||||
d_symbol_accumulator_counter=0;
|
d_symbol_accumulator_counter = 0;
|
||||||
|
|
||||||
//******* bits to words ******
|
//******* bits to words ******
|
||||||
d_frame_bit_index++;
|
d_frame_bit_index++;
|
||||||
if (d_frame_bit_index==30)
|
if (d_frame_bit_index == 30)
|
||||||
{
|
{
|
||||||
d_frame_bit_index=0;
|
d_frame_bit_index = 0;
|
||||||
//parity check
|
//parity check
|
||||||
//Each word in wordbuff is composed of:
|
//Each word in wordbuff is composed of:
|
||||||
// Bits 0 to 29 = the GPS data word
|
// Bits 0 to 29 = the GPS data word
|
||||||
@ -284,11 +285,11 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
// prepare the extended frame [-2 -1 0 ... 30]
|
// prepare the extended frame [-2 -1 0 ... 30]
|
||||||
if (d_prev_GPS_frame_4bytes & 0x00000001)
|
if (d_prev_GPS_frame_4bytes & 0x00000001)
|
||||||
{
|
{
|
||||||
d_GPS_frame_4bytes=d_GPS_frame_4bytes|0x40000000;
|
d_GPS_frame_4bytes = d_GPS_frame_4bytes|0x40000000;
|
||||||
}
|
}
|
||||||
if (d_prev_GPS_frame_4bytes & 0x00000002)
|
if (d_prev_GPS_frame_4bytes & 0x00000002)
|
||||||
{
|
{
|
||||||
d_GPS_frame_4bytes=d_GPS_frame_4bytes|0x80000000;
|
d_GPS_frame_4bytes = d_GPS_frame_4bytes|0x80000000;
|
||||||
}
|
}
|
||||||
/* Check that the 2 most recently logged words pass parity. Have to first
|
/* Check that the 2 most recently logged words pass parity. Have to first
|
||||||
invert the data bits according to bit 30 of the previous word. */
|
invert the data bits according to bit 30 of the previous word. */
|
||||||
@ -299,17 +300,17 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
if (gps_l1_ca_telemetry_decoder_cc::gps_word_parityCheck(d_GPS_frame_4bytes))
|
if (gps_l1_ca_telemetry_decoder_cc::gps_word_parityCheck(d_GPS_frame_4bytes))
|
||||||
{
|
{
|
||||||
memcpy(&d_GPS_FSM.d_GPS_frame_4bytes,&d_GPS_frame_4bytes,sizeof(char)*4);
|
memcpy(&d_GPS_FSM.d_GPS_frame_4bytes,&d_GPS_frame_4bytes,sizeof(char)*4);
|
||||||
d_GPS_FSM.d_preamble_time_ms=d_preamble_time_seconds*1000.0;
|
d_GPS_FSM.d_preamble_time_ms = d_preamble_time_seconds*1000.0;
|
||||||
d_GPS_FSM.Event_gps_word_valid();
|
d_GPS_FSM.Event_gps_word_valid();
|
||||||
d_flag_parity=true;
|
d_flag_parity = true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
d_GPS_FSM.Event_gps_word_invalid();
|
d_GPS_FSM.Event_gps_word_invalid();
|
||||||
d_flag_parity=false;
|
d_flag_parity = false;
|
||||||
}
|
}
|
||||||
d_prev_GPS_frame_4bytes=d_GPS_frame_4bytes; // save the actual frame
|
d_prev_GPS_frame_4bytes = d_GPS_frame_4bytes; // save the actual frame
|
||||||
d_GPS_frame_4bytes=d_GPS_frame_4bytes & 0;
|
d_GPS_frame_4bytes = d_GPS_frame_4bytes & 0;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -320,15 +321,15 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
// output the frame
|
// output the frame
|
||||||
consume_each(1); //one by one
|
consume_each(1); //one by one
|
||||||
|
|
||||||
gps_synchro.valid_word=(d_flag_frame_sync==true and d_flag_parity==true);
|
gps_synchro.valid_word = (d_flag_frame_sync == true and d_flag_parity == true);
|
||||||
gps_synchro.flag_preamble=d_flag_preamble;
|
gps_synchro.flag_preamble = d_flag_preamble;
|
||||||
gps_synchro.preamble_delay_ms=d_preamble_time_seconds*1000.0;
|
gps_synchro.preamble_delay_ms = d_preamble_time_seconds*1000.0;
|
||||||
gps_synchro.prn_delay_ms=(in[2][0]-d_preamble_duration_seconds)*1000.0;
|
gps_synchro.prn_delay_ms = (in[2][0] - d_preamble_duration_seconds)*1000.0;
|
||||||
gps_synchro.preamble_code_phase_ms=d_preamble_code_phase_seconds*1000.0;
|
gps_synchro.preamble_code_phase_ms = d_preamble_code_phase_seconds*1000.0;
|
||||||
gps_synchro.preamble_code_phase_correction_ms=(in[4][0]-d_preamble_code_phase_seconds)*1000.0;
|
gps_synchro.preamble_code_phase_correction_ms = (in[4][0] - d_preamble_code_phase_seconds)*1000.0;
|
||||||
gps_synchro.satellite_PRN=d_satellite;
|
gps_synchro.satellite_PRN = d_satellite;
|
||||||
gps_synchro.channel_ID=d_channel;
|
gps_synchro.channel_ID = d_channel;
|
||||||
*out[0]=gps_synchro;
|
*out[0] = gps_synchro;
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -336,14 +337,14 @@ int gps_l1_ca_telemetry_decoder_cc::general_work (int noutput_items, gr_vector_i
|
|||||||
void gps_l1_ca_telemetry_decoder_cc::set_satellite(int satellite)
|
void gps_l1_ca_telemetry_decoder_cc::set_satellite(int satellite)
|
||||||
{
|
{
|
||||||
d_satellite = satellite;
|
d_satellite = satellite;
|
||||||
d_GPS_FSM.i_satellite_PRN=satellite;
|
d_GPS_FSM.i_satellite_PRN = satellite;
|
||||||
LOG_AT_LEVEL(INFO) << "Navigation Satellite set to " << d_satellite;
|
LOG_AT_LEVEL(INFO) << "Navigation Satellite set to " << d_satellite;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_telemetry_decoder_cc::set_channel(int channel)
|
void gps_l1_ca_telemetry_decoder_cc::set_channel(int channel)
|
||||||
{
|
{
|
||||||
d_channel = channel;
|
d_channel = channel;
|
||||||
d_GPS_FSM.i_channel_ID=channel;
|
d_GPS_FSM.i_channel_ID = channel;
|
||||||
LOG_AT_LEVEL(INFO) << "Navigation channel set to " << channel;
|
LOG_AT_LEVEL(INFO) << "Navigation channel set to " << channel;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -64,205 +64,221 @@ using google::LogMessage;
|
|||||||
|
|
||||||
gps_l1_ca_dll_pll_tracking_cc_sptr
|
gps_l1_ca_dll_pll_tracking_cc_sptr
|
||||||
gps_l1_ca_dll_pll_make_tracking_cc(unsigned int satellite, long if_freq, long fs_in, unsigned
|
gps_l1_ca_dll_pll_make_tracking_cc(unsigned int satellite, long if_freq, long fs_in, unsigned
|
||||||
int vector_length, gr_msg_queue_sptr queue, bool dump, std::string dump_filename, float pll_bw_hz, float dll_bw_hz, float early_late_space_chips) {
|
int vector_length, gr_msg_queue_sptr queue, bool dump, std::string dump_filename, float pll_bw_hz, float dll_bw_hz, float early_late_space_chips)
|
||||||
|
{
|
||||||
return gps_l1_ca_dll_pll_tracking_cc_sptr(new gps_l1_ca_dll_pll_tracking_cc(satellite, if_freq,
|
return gps_l1_ca_dll_pll_tracking_cc_sptr(new gps_l1_ca_dll_pll_tracking_cc(satellite, if_freq,
|
||||||
fs_in, vector_length, queue, dump, dump_filename, pll_bw_hz, dll_bw_hz, early_late_space_chips));
|
fs_in, vector_length, queue, dump, dump_filename, pll_bw_hz, dll_bw_hz, early_late_space_chips));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::forecast (int noutput_items,
|
void gps_l1_ca_dll_pll_tracking_cc::forecast (int noutput_items,
|
||||||
gr_vector_int &ninput_items_required){
|
gr_vector_int &ninput_items_required)
|
||||||
ninput_items_required[0] =(int)d_vector_length*2; //set the required available samples in each call
|
{
|
||||||
|
ninput_items_required[0] = (int)d_vector_length*2; //set the required available samples in each call
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
gps_l1_ca_dll_pll_tracking_cc::gps_l1_ca_dll_pll_tracking_cc(unsigned int satellite, long if_freq, long fs_in, unsigned
|
gps_l1_ca_dll_pll_tracking_cc::gps_l1_ca_dll_pll_tracking_cc(unsigned int satellite, long if_freq, long fs_in, unsigned
|
||||||
int vector_length, gr_msg_queue_sptr queue, bool dump, std::string dump_filename, float pll_bw_hz, float dll_bw_hz, float early_late_space_chips) :
|
int vector_length, gr_msg_queue_sptr queue, bool dump, std::string dump_filename, float pll_bw_hz, float dll_bw_hz, float early_late_space_chips) :
|
||||||
gr_block ("gps_l1_ca_dll_pll_tracking_cc", gr_make_io_signature (1, 1, sizeof(gr_complex)),
|
gr_block ("gps_l1_ca_dll_pll_tracking_cc", gr_make_io_signature (1, 1, sizeof(gr_complex)),
|
||||||
gr_make_io_signature(5, 5, sizeof(double))) {
|
gr_make_io_signature(5, 5, sizeof(double)))
|
||||||
|
{
|
||||||
|
|
||||||
//gr_sync_decimator ("gps_l1_ca_dll_pll_tracking_cc", gr_make_io_signature (1, 1, sizeof(gr_complex)),
|
//gr_sync_decimator ("gps_l1_ca_dll_pll_tracking_cc", gr_make_io_signature (1, 1, sizeof(gr_complex)),
|
||||||
// gr_make_io_signature(3, 3, sizeof(float)),vector_length) {
|
// gr_make_io_signature(3, 3, sizeof(float)),vector_length) {
|
||||||
// initialize internal vars
|
// initialize internal vars
|
||||||
d_queue = queue;
|
d_queue = queue;
|
||||||
d_dump = dump;
|
d_dump = dump;
|
||||||
d_satellite = satellite;
|
d_satellite = satellite;
|
||||||
d_if_freq = if_freq;
|
d_if_freq = if_freq;
|
||||||
d_fs_in = fs_in;
|
d_fs_in = fs_in;
|
||||||
d_vector_length = vector_length;
|
d_vector_length = vector_length;
|
||||||
d_dump_filename =dump_filename;
|
d_dump_filename = dump_filename;
|
||||||
|
|
||||||
// Initialize tracking ==========================================
|
// Initialize tracking ==========================================
|
||||||
|
|
||||||
d_code_loop_filter.set_DLL_BW(dll_bw_hz);
|
d_code_loop_filter.set_DLL_BW(dll_bw_hz);
|
||||||
d_carrier_loop_filter.set_PLL_BW(pll_bw_hz);
|
d_carrier_loop_filter.set_PLL_BW(pll_bw_hz);
|
||||||
|
|
||||||
//--- DLL variables --------------------------------------------------------
|
//--- DLL variables --------------------------------------------------------
|
||||||
d_early_late_spc_chips = early_late_space_chips; // Define early-late offset (in chips)
|
d_early_late_spc_chips = early_late_space_chips; // Define early-late offset (in chips)
|
||||||
|
|
||||||
// Initialization of local code replica
|
// Initialization of local code replica
|
||||||
// Get space for a vector with the C/A code replica sampled 1x/chip
|
// Get space for a vector with the C/A code replica sampled 1x/chip
|
||||||
d_ca_code=new gr_complex[(int)GPS_L1_CA_CODE_LENGTH_CHIPS+2];
|
d_ca_code = new gr_complex[(int)GPS_L1_CA_CODE_LENGTH_CHIPS + 2];
|
||||||
|
|
||||||
// Get space for the resampled early / prompt / late local replicas
|
// Get space for the resampled early / prompt / late local replicas
|
||||||
d_early_code= new gr_complex[d_vector_length*2];
|
d_early_code = new gr_complex[d_vector_length*2];
|
||||||
d_prompt_code=new gr_complex[d_vector_length*2];
|
d_prompt_code = new gr_complex[d_vector_length*2];
|
||||||
d_late_code=new gr_complex[d_vector_length*2];
|
d_late_code = new gr_complex[d_vector_length*2];
|
||||||
|
|
||||||
// space for carrier wipeoff and signal baseband vectors
|
// space for carrier wipeoff and signal baseband vectors
|
||||||
d_carr_sign=new gr_complex[d_vector_length*2];
|
d_carr_sign = new gr_complex[d_vector_length*2];
|
||||||
|
|
||||||
//--- Perform initializations ------------------------------
|
//--- Perform initializations ------------------------------
|
||||||
// define initial code frequency basis of NCO
|
// define initial code frequency basis of NCO
|
||||||
d_code_freq_hz = GPS_L1_CA_CODE_RATE_HZ;
|
d_code_freq_hz = GPS_L1_CA_CODE_RATE_HZ;
|
||||||
// define residual code phase (in chips)
|
// define residual code phase (in chips)
|
||||||
d_rem_code_phase_samples = 0.0;
|
d_rem_code_phase_samples = 0.0;
|
||||||
// define residual carrier phase
|
// define residual carrier phase
|
||||||
d_rem_carr_phase_rad = 0.0;
|
d_rem_carr_phase_rad = 0.0;
|
||||||
|
|
||||||
// sample synchronization
|
// sample synchronization
|
||||||
d_sample_counter=0;
|
d_sample_counter = 0;
|
||||||
d_sample_counter_seconds=0;
|
d_sample_counter_seconds = 0;
|
||||||
d_acq_sample_stamp=0;
|
d_acq_sample_stamp = 0;
|
||||||
|
|
||||||
d_enable_tracking=false;
|
d_enable_tracking = false;
|
||||||
d_pull_in=false;
|
d_pull_in = false;
|
||||||
d_last_seg=0;
|
d_last_seg = 0;
|
||||||
|
|
||||||
d_current_prn_length_samples=(int)d_vector_length;
|
d_current_prn_length_samples = (int)d_vector_length;
|
||||||
|
|
||||||
// CN0 estimation and lock detector buffers
|
// CN0 estimation and lock detector buffers
|
||||||
d_cn0_estimation_counter=0;
|
d_cn0_estimation_counter = 0;
|
||||||
d_Prompt_buffer=new gr_complex[CN0_ESTIMATION_SAMPLES];
|
d_Prompt_buffer = new gr_complex[CN0_ESTIMATION_SAMPLES];
|
||||||
d_carrier_lock_test=1;
|
d_carrier_lock_test = 1;
|
||||||
d_CN0_SNV_dB_Hz=0;
|
d_CN0_SNV_dB_Hz = 0;
|
||||||
d_carrier_lock_fail_counter=0;
|
d_carrier_lock_fail_counter = 0;
|
||||||
d_carrier_lock_threshold=5;
|
d_carrier_lock_threshold = 5;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::start_tracking(){
|
void gps_l1_ca_dll_pll_tracking_cc::start_tracking()
|
||||||
/*
|
{
|
||||||
* correct the code phase according to the delay between acq and trk
|
/*
|
||||||
*/
|
* correct the code phase according to the delay between acq and trk
|
||||||
unsigned long int acq_trk_diff_samples;
|
*/
|
||||||
float acq_trk_diff_seconds;
|
unsigned long int acq_trk_diff_samples;
|
||||||
acq_trk_diff_samples=d_sample_counter-d_acq_sample_stamp;//-d_vector_length;
|
float acq_trk_diff_seconds;
|
||||||
std::cout<<"acq_trk_diff_samples="<<acq_trk_diff_samples<<"\r\n";
|
acq_trk_diff_samples = d_sample_counter - d_acq_sample_stamp;//-d_vector_length;
|
||||||
acq_trk_diff_seconds=(float)acq_trk_diff_samples/(float)d_fs_in;
|
std::cout << "acq_trk_diff_samples=" << acq_trk_diff_samples << std::endl;
|
||||||
//doppler effect
|
acq_trk_diff_seconds = (float)acq_trk_diff_samples / (float)d_fs_in;
|
||||||
// Fd=(C/(C+Vr))*F
|
//doppler effect
|
||||||
float radial_velocity;
|
// Fd=(C/(C+Vr))*F
|
||||||
radial_velocity=(GPS_L1_FREQ_HZ+d_acq_carrier_doppler_hz)/GPS_L1_FREQ_HZ;
|
float radial_velocity;
|
||||||
// new chip and prn sequence periods based on acq Doppler
|
radial_velocity = (GPS_L1_FREQ_HZ + d_acq_carrier_doppler_hz)/GPS_L1_FREQ_HZ;
|
||||||
float T_chip_mod_seconds;
|
// new chip and prn sequence periods based on acq Doppler
|
||||||
float T_prn_mod_seconds;
|
float T_chip_mod_seconds;
|
||||||
float T_prn_mod_samples;
|
float T_prn_mod_seconds;
|
||||||
d_code_freq_hz=radial_velocity*GPS_L1_CA_CODE_RATE_HZ;
|
float T_prn_mod_samples;
|
||||||
T_chip_mod_seconds=1/d_code_freq_hz;
|
d_code_freq_hz = radial_velocity * GPS_L1_CA_CODE_RATE_HZ;
|
||||||
T_prn_mod_seconds=T_chip_mod_seconds*GPS_L1_CA_CODE_LENGTH_CHIPS;
|
T_chip_mod_seconds = 1/d_code_freq_hz;
|
||||||
T_prn_mod_samples=T_prn_mod_seconds*(float)d_fs_in;
|
T_prn_mod_seconds = T_chip_mod_seconds * GPS_L1_CA_CODE_LENGTH_CHIPS;
|
||||||
|
T_prn_mod_samples = T_prn_mod_seconds * (float)d_fs_in;
|
||||||
|
|
||||||
|
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
||||||
|
d_next_prn_length_samples = round(T_prn_mod_samples);
|
||||||
|
#else
|
||||||
|
d_next_prn_length_samples = std::round(T_prn_mod_samples);
|
||||||
|
#endif
|
||||||
|
|
||||||
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
float T_prn_true_seconds = GPS_L1_CA_CODE_LENGTH_CHIPS / GPS_L1_CA_CODE_RATE_HZ;
|
||||||
d_next_prn_length_samples=round(T_prn_mod_samples);
|
float T_prn_true_samples = T_prn_true_seconds * (float)d_fs_in;
|
||||||
#else
|
|
||||||
d_next_prn_length_samples=std::round(T_prn_mod_samples);
|
|
||||||
#endif
|
|
||||||
|
|
||||||
|
|
||||||
float T_prn_true_seconds = GPS_L1_CA_CODE_LENGTH_CHIPS/GPS_L1_CA_CODE_RATE_HZ;
|
|
||||||
float T_prn_true_samples = T_prn_true_seconds*(float)d_fs_in;
|
|
||||||
float T_prn_diff_seconds;
|
float T_prn_diff_seconds;
|
||||||
T_prn_diff_seconds=T_prn_true_seconds-T_prn_mod_seconds;
|
T_prn_diff_seconds = T_prn_true_seconds - T_prn_mod_seconds;
|
||||||
float N_prn_diff;
|
float N_prn_diff;
|
||||||
N_prn_diff=acq_trk_diff_seconds/T_prn_true_seconds;
|
N_prn_diff = acq_trk_diff_seconds / T_prn_true_seconds;
|
||||||
float corrected_acq_phase_samples,delay_correction_samples;
|
float corrected_acq_phase_samples, delay_correction_samples;
|
||||||
corrected_acq_phase_samples=fmod((d_acq_code_phase_samples+T_prn_diff_seconds*N_prn_diff*(float)d_fs_in),T_prn_true_samples);
|
corrected_acq_phase_samples = fmod((d_acq_code_phase_samples + T_prn_diff_seconds * N_prn_diff * (float)d_fs_in), T_prn_true_samples);
|
||||||
if (corrected_acq_phase_samples<0)
|
if (corrected_acq_phase_samples < 0)
|
||||||
{
|
{
|
||||||
corrected_acq_phase_samples=T_prn_mod_samples+corrected_acq_phase_samples;
|
corrected_acq_phase_samples = T_prn_mod_samples + corrected_acq_phase_samples;
|
||||||
}
|
}
|
||||||
delay_correction_samples=d_acq_code_phase_samples-corrected_acq_phase_samples;
|
delay_correction_samples = d_acq_code_phase_samples - corrected_acq_phase_samples;
|
||||||
|
|
||||||
d_acq_code_phase_samples=corrected_acq_phase_samples;
|
d_acq_code_phase_samples = corrected_acq_phase_samples;
|
||||||
|
|
||||||
d_carrier_doppler_hz=d_acq_carrier_doppler_hz;
|
d_carrier_doppler_hz = d_acq_carrier_doppler_hz;
|
||||||
// DLL/PLL filter initialization
|
// DLL/PLL filter initialization
|
||||||
d_carrier_loop_filter.initialize(d_carrier_doppler_hz); //initialize the carrier filter
|
d_carrier_loop_filter.initialize(d_carrier_doppler_hz); //initialize the carrier filter
|
||||||
d_code_loop_filter.initialize(d_acq_code_phase_samples); //initialize the code filter
|
d_code_loop_filter.initialize(d_acq_code_phase_samples); //initialize the code filter
|
||||||
|
|
||||||
// generate local reference ALWAYS starting at chip 1 (1 sample per chip)
|
// generate local reference ALWAYS starting at chip 1 (1 sample per chip)
|
||||||
code_gen_conplex(&d_ca_code[1],d_satellite,0);
|
code_gen_conplex(&d_ca_code[1], d_satellite, 0);
|
||||||
d_ca_code[0]=d_ca_code[(int)GPS_L1_CA_CODE_LENGTH_CHIPS];
|
d_ca_code[0] = d_ca_code[(int)GPS_L1_CA_CODE_LENGTH_CHIPS];
|
||||||
d_ca_code[(int)GPS_L1_CA_CODE_LENGTH_CHIPS+1]=d_ca_code[1];
|
d_ca_code[(int)GPS_L1_CA_CODE_LENGTH_CHIPS + 1] = d_ca_code[1];
|
||||||
|
|
||||||
d_carrier_lock_fail_counter=0;
|
d_carrier_lock_fail_counter = 0;
|
||||||
d_rem_code_phase_samples=0;
|
d_rem_code_phase_samples = 0;
|
||||||
d_rem_carr_phase_rad=0;
|
d_rem_carr_phase_rad = 0;
|
||||||
d_rem_code_phase_samples=0;
|
d_rem_code_phase_samples = 0;
|
||||||
d_next_rem_code_phase_samples=0;
|
d_next_rem_code_phase_samples = 0;
|
||||||
d_acc_carrier_phase_rad=0;
|
d_acc_carrier_phase_rad = 0;
|
||||||
|
|
||||||
d_code_phase_samples = d_acq_code_phase_samples;
|
d_code_phase_samples = d_acq_code_phase_samples;
|
||||||
|
|
||||||
// DEBUG OUTPUT
|
// DEBUG OUTPUT
|
||||||
std::cout<<"Tracking start on channel "<<d_channel<<" for satellite ID* "<< this->d_satellite<< std::endl;
|
std::cout << "Tracking start on channel " << d_channel << " for satellite ID* " << this->d_satellite << std::endl;
|
||||||
DLOG(INFO) << "Start tracking for satellite "<<this->d_satellite<<" received ";
|
DLOG(INFO) << "Start tracking for satellite "<< this->d_satellite << " received" << std::endl;
|
||||||
|
|
||||||
// enable tracking
|
// enable tracking
|
||||||
d_pull_in=true;
|
d_pull_in = true;
|
||||||
d_enable_tracking=true;
|
d_enable_tracking = true;
|
||||||
|
|
||||||
std::cout<<"PULL-IN Doppler [Hz]= "<<d_carrier_doppler_hz<<" Code Phase correction [samples]="<<delay_correction_samples<<" PULL-IN Code Phase [samples]= "<<d_acq_code_phase_samples<<"\r\n";
|
|
||||||
|
|
||||||
|
std::cout << "PULL-IN Doppler [Hz]=" << d_carrier_doppler_hz << " Code Phase correction [samples]=" << delay_correction_samples << " PULL-IN Code Phase [samples]=" << d_acq_code_phase_samples << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::update_local_code()
|
void gps_l1_ca_dll_pll_tracking_cc::update_local_code()
|
||||||
{
|
{
|
||||||
float tcode_chips;
|
float tcode_chips;
|
||||||
float rem_code_phase_chips;
|
float rem_code_phase_chips;
|
||||||
int associated_chip_index;
|
int associated_chip_index;
|
||||||
int code_length_chips=(int)GPS_L1_CA_CODE_LENGTH_CHIPS;
|
int code_length_chips = (int)GPS_L1_CA_CODE_LENGTH_CHIPS;
|
||||||
// unified loop for E, P, L code vectors
|
// unified loop for E, P, L code vectors
|
||||||
rem_code_phase_chips=d_rem_code_phase_samples*(d_code_freq_hz/d_fs_in);
|
rem_code_phase_chips = d_rem_code_phase_samples * (d_code_freq_hz / d_fs_in);
|
||||||
tcode_chips=-rem_code_phase_chips;
|
tcode_chips = -rem_code_phase_chips;
|
||||||
for (int i=0;i<d_current_prn_length_samples;i++)
|
for (int i=0; i<d_current_prn_length_samples; i++)
|
||||||
{
|
{
|
||||||
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
||||||
associated_chip_index=1+round(fmod(tcode_chips-d_early_late_spc_chips,code_length_chips));
|
associated_chip_index = 1 + round(fmod(tcode_chips - d_early_late_spc_chips, code_length_chips));
|
||||||
d_early_code[i] = d_ca_code[associated_chip_index];
|
d_early_code[i] = d_ca_code[associated_chip_index];
|
||||||
associated_chip_index = 1+round(fmod(tcode_chips, code_length_chips));
|
associated_chip_index = 1 + round(fmod(tcode_chips, code_length_chips));
|
||||||
d_prompt_code[i] = d_ca_code[associated_chip_index];
|
d_prompt_code[i] = d_ca_code[associated_chip_index];
|
||||||
associated_chip_index = 1+round(fmod(tcode_chips+d_early_late_spc_chips, code_length_chips));
|
associated_chip_index = 1 + round(fmod(tcode_chips+d_early_late_spc_chips, code_length_chips));
|
||||||
d_late_code[i] = d_ca_code[associated_chip_index];
|
d_late_code[i] = d_ca_code[associated_chip_index];
|
||||||
tcode_chips=tcode_chips+d_code_phase_step_chips;
|
tcode_chips = tcode_chips + d_code_phase_step_chips;
|
||||||
#else
|
#else
|
||||||
associated_chip_index=1+std::round(fmod(tcode_chips-d_early_late_spc_chips,code_length_chips));
|
associated_chip_index = 1 + std::round(fmod(tcode_chips - d_early_late_spc_chips, code_length_chips));
|
||||||
d_early_code[i] = d_ca_code[associated_chip_index];
|
d_early_code[i] = d_ca_code[associated_chip_index];
|
||||||
associated_chip_index = 1+std::round(fmod(tcode_chips, code_length_chips));
|
associated_chip_index = 1 + std::round(fmod(tcode_chips, code_length_chips));
|
||||||
d_prompt_code[i] = d_ca_code[associated_chip_index];
|
d_prompt_code[i] = d_ca_code[associated_chip_index];
|
||||||
associated_chip_index = 1+std::round(fmod(tcode_chips+d_early_late_spc_chips, code_length_chips));
|
associated_chip_index = 1 + std::round(fmod(tcode_chips+d_early_late_spc_chips, code_length_chips));
|
||||||
d_late_code[i] = d_ca_code[associated_chip_index];
|
d_late_code[i] = d_ca_code[associated_chip_index];
|
||||||
tcode_chips=tcode_chips+d_code_phase_step_chips;
|
tcode_chips = tcode_chips + d_code_phase_step_chips;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::update_local_carrier()
|
void gps_l1_ca_dll_pll_tracking_cc::update_local_carrier()
|
||||||
{
|
{
|
||||||
float phase_rad, phase_step_rad;
|
float phase_rad, phase_step_rad;
|
||||||
|
|
||||||
phase_step_rad = (float)TWO_PI*d_carrier_doppler_hz/(float)d_fs_in;
|
phase_step_rad = (float)TWO_PI*d_carrier_doppler_hz / (float)d_fs_in;
|
||||||
phase_rad=d_rem_carr_phase_rad;
|
phase_rad = d_rem_carr_phase_rad;
|
||||||
for(int i = 0; i < d_current_prn_length_samples; i++) {
|
for(int i = 0; i < d_current_prn_length_samples; i++)
|
||||||
d_carr_sign[i] = gr_complex(cos(phase_rad),sin(phase_rad));
|
{
|
||||||
|
d_carr_sign[i] = gr_complex(cos(phase_rad), sin(phase_rad));
|
||||||
phase_rad += phase_step_rad;
|
phase_rad += phase_step_rad;
|
||||||
}
|
}
|
||||||
d_rem_carr_phase_rad=fmod(phase_rad,TWO_PI);
|
d_rem_carr_phase_rad = fmod(phase_rad, TWO_PI);
|
||||||
d_acc_carrier_phase_rad=d_acc_carrier_phase_rad+d_rem_carr_phase_rad;
|
d_acc_carrier_phase_rad = d_acc_carrier_phase_rad + d_rem_carr_phase_rad;
|
||||||
}
|
}
|
||||||
|
|
||||||
gps_l1_ca_dll_pll_tracking_cc::~gps_l1_ca_dll_pll_tracking_cc() {
|
|
||||||
d_dump_file.close();
|
|
||||||
|
|
||||||
|
gps_l1_ca_dll_pll_tracking_cc::~gps_l1_ca_dll_pll_tracking_cc()
|
||||||
|
{
|
||||||
|
d_dump_file.close();
|
||||||
delete[] d_ca_code;
|
delete[] d_ca_code;
|
||||||
delete[] d_early_code;
|
delete[] d_early_code;
|
||||||
delete[] d_prompt_code;
|
delete[] d_prompt_code;
|
||||||
@ -271,318 +287,357 @@ gps_l1_ca_dll_pll_tracking_cc::~gps_l1_ca_dll_pll_tracking_cc() {
|
|||||||
delete[] d_Prompt_buffer;
|
delete[] d_Prompt_buffer;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
/* Tracking signal processing
|
/* Tracking signal processing
|
||||||
* Notice that this is a class derived from gr_sync_decimator, so each of the ninput_items has vector_length samples
|
* Notice that this is a class derived from gr_sync_decimator, so each of the ninput_items has vector_length samples
|
||||||
*/
|
*/
|
||||||
|
|
||||||
int gps_l1_ca_dll_pll_tracking_cc::general_work (int noutput_items, gr_vector_int &ninput_items,
|
int gps_l1_ca_dll_pll_tracking_cc::general_work (int noutput_items, gr_vector_int &ninput_items,
|
||||||
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items) {
|
gr_vector_const_void_star &input_items, gr_vector_void_star &output_items)
|
||||||
|
{
|
||||||
|
|
||||||
// if ((unsigned int)ninput_items[0]<(d_vector_length*2))
|
// if ((unsigned int)ninput_items[0]<(d_vector_length*2))
|
||||||
// {
|
// {
|
||||||
// std::cout<<"End of signal detected\r\n";
|
// std::cout<<"End of signal detected\r\n";
|
||||||
// const int samples_available = ninput_items[0];
|
// const int samples_available = ninput_items[0];
|
||||||
// consume_each(samples_available);
|
// consume_each(samples_available);
|
||||||
// return 0;
|
// return 0;
|
||||||
// }
|
// }
|
||||||
|
|
||||||
// process vars
|
// process vars
|
||||||
float carr_error;
|
float carr_error;
|
||||||
float carr_nco;
|
float carr_nco;
|
||||||
float code_error;
|
float code_error;
|
||||||
float code_nco;
|
float code_nco;
|
||||||
d_Early=gr_complex(0,0);
|
d_Early = gr_complex(0,0);
|
||||||
d_Prompt=gr_complex(0,0);
|
d_Prompt = gr_complex(0,0);
|
||||||
d_Late=gr_complex(0,0);
|
d_Late = gr_complex(0,0);
|
||||||
|
|
||||||
if (d_enable_tracking==true){
|
if (d_enable_tracking==true){
|
||||||
/*
|
/*
|
||||||
* Receiver signal alignment
|
* Receiver signal alignment
|
||||||
*/
|
*/
|
||||||
if (d_pull_in==true)
|
if (d_pull_in==true)
|
||||||
{
|
{
|
||||||
int samples_offset;
|
int samples_offset;
|
||||||
|
|
||||||
// 28/11/2011 ACQ to TRK transition BUG CORRECTION
|
// 28/11/2011 ACQ to TRK transition BUG CORRECTION
|
||||||
float acq_trk_shif_correction_samples;
|
float acq_trk_shif_correction_samples;
|
||||||
int acq_to_trk_delay_samples;
|
int acq_to_trk_delay_samples;
|
||||||
acq_to_trk_delay_samples=d_sample_counter-d_acq_sample_stamp;
|
acq_to_trk_delay_samples = d_sample_counter - d_acq_sample_stamp;
|
||||||
acq_trk_shif_correction_samples=d_next_prn_length_samples-fmod((float)acq_to_trk_delay_samples,(float)d_next_prn_length_samples);
|
acq_trk_shif_correction_samples = d_next_prn_length_samples - fmod((float)acq_to_trk_delay_samples, (float)d_next_prn_length_samples);
|
||||||
//std::cout<<"acq_trk_shif_correction="<<acq_trk_shif_correction_samples<<"\r\n";
|
//std::cout<<"acq_trk_shif_correction="<<acq_trk_shif_correction_samples<<"\r\n";
|
||||||
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
||||||
samples_offset=round(d_acq_code_phase_samples+acq_trk_shif_correction_samples);
|
samples_offset=round(d_acq_code_phase_samples + acq_trk_shif_correction_samples);
|
||||||
#else
|
#else
|
||||||
samples_offset=std::round(d_acq_code_phase_samples+acq_trk_shif_correction_samples);
|
samples_offset=std::round(d_acq_code_phase_samples + acq_trk_shif_correction_samples);
|
||||||
#endif
|
#endif
|
||||||
// /todo: Check if the sample counter sent to the next block as a time reference should be incremented AFTER sended or BEFORE
|
// /todo: Check if the sample counter sent to the next block as a time reference should be incremented AFTER sended or BEFORE
|
||||||
d_sample_counter_seconds = d_sample_counter_seconds + (((double)samples_offset)/(double)d_fs_in);
|
d_sample_counter_seconds = d_sample_counter_seconds + (((double)samples_offset) / (double)d_fs_in);
|
||||||
d_sample_counter=d_sample_counter+samples_offset; //count for the processed samples
|
d_sample_counter =d_sample_counter + samples_offset; //count for the processed samples
|
||||||
d_pull_in=false;
|
d_pull_in = false;
|
||||||
//std::cout<<" samples_offset="<<samples_offset<<"\r\n";
|
//std::cout<<" samples_offset="<<samples_offset<<"\r\n";
|
||||||
consume_each(samples_offset); //shift input to perform alignement with local replica
|
consume_each(samples_offset); //shift input to perform alignement with local replica
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
const gr_complex* in = (gr_complex*) input_items[0]; //PRN start block alignement
|
const gr_complex* in = (gr_complex*) input_items[0]; //PRN start block alignement
|
||||||
double **out = (double **) &output_items[0];
|
double **out = (double **) &output_items[0];
|
||||||
// check for samples consistency
|
|
||||||
for(int i=0;i<d_current_prn_length_samples;i++) {
|
|
||||||
if (std::isnan(in[i].real())==true or std::isnan(in[i].imag())==true)// or std::isinf(in[i].real())==true or std::isinf(in[i].imag())==true)
|
|
||||||
{
|
|
||||||
const int samples_available= ninput_items[0];
|
|
||||||
d_sample_counter=d_sample_counter+samples_available;
|
|
||||||
LOG_AT_LEVEL(WARNING) << "Detected NaN samples at sample number "<<d_sample_counter;
|
|
||||||
consume_each(samples_available);
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
// Update the prn length based on code freq (variable) and
|
|
||||||
// sampling frequency (fixed)
|
|
||||||
// variable code PRN sample block size
|
|
||||||
d_current_prn_length_samples=d_next_prn_length_samples;
|
|
||||||
|
|
||||||
update_local_code();
|
// check for samples consistency
|
||||||
update_local_carrier();
|
for(int i=0; i<d_current_prn_length_samples; i++) {
|
||||||
|
if (std::isnan(in[i].real()) == true or std::isnan(in[i].imag()) == true)// or std::isinf(in[i].real())==true or std::isinf(in[i].imag())==true)
|
||||||
|
{
|
||||||
|
const int samples_available = ninput_items[0];
|
||||||
|
d_sample_counter = d_sample_counter + samples_available;
|
||||||
|
LOG_AT_LEVEL(WARNING) << "Detected NaN samples at sample number "<< d_sample_counter << std::endl;
|
||||||
|
consume_each(samples_available);
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
// Update the prn length based on code freq (variable) and
|
||||||
|
// sampling frequency (fixed)
|
||||||
|
// variable code PRN sample block size
|
||||||
|
d_current_prn_length_samples = d_next_prn_length_samples;
|
||||||
|
|
||||||
gr_complex bb_signal_sample(0,0);
|
update_local_code();
|
||||||
|
update_local_carrier();
|
||||||
|
|
||||||
// perform Early, Prompt and Late correlation
|
gr_complex bb_signal_sample(0,0);
|
||||||
/*!
|
|
||||||
* \todo Use SIMD-enabled correlators
|
|
||||||
*/
|
|
||||||
for(int i=0;i<d_current_prn_length_samples;i++) {
|
|
||||||
//Perform the carrier wipe-off
|
|
||||||
bb_signal_sample = in[i] * d_carr_sign[i];
|
|
||||||
// Now get early, late, and prompt values for each
|
|
||||||
d_Early += bb_signal_sample*d_early_code[i];
|
|
||||||
d_Prompt += bb_signal_sample*d_prompt_code[i];
|
|
||||||
d_Late += bb_signal_sample*d_late_code[i];
|
|
||||||
}
|
|
||||||
// Compute PLL error and update carrier NCO -
|
|
||||||
carr_error=pll_cloop_two_quadrant_atan(d_Prompt)/ (float)TWO_PI;
|
|
||||||
// Implement carrier loop filter and generate NCO command
|
|
||||||
carr_nco=d_carrier_loop_filter.get_carrier_nco(carr_error);
|
|
||||||
// Modify carrier freq based on NCO command
|
|
||||||
d_carrier_doppler_hz = d_acq_carrier_doppler_hz + carr_nco;
|
|
||||||
|
|
||||||
// Compute DLL error and update code NCO
|
// perform Early, Prompt and Late correlation
|
||||||
code_error=dll_nc_e_minus_l_normalized(d_Early,d_Late);
|
/*!
|
||||||
// Implement code loop filter and generate NCO command
|
* \todo Use SIMD-enabled correlators
|
||||||
code_nco=d_code_loop_filter.get_code_nco(code_error);
|
*/
|
||||||
// Modify code freq based on NCO command
|
for(int i=0; i<d_current_prn_length_samples; i++) {
|
||||||
d_code_freq_hz = GPS_L1_CA_CODE_RATE_HZ - code_nco;
|
//Perform the carrier wipe-off
|
||||||
|
bb_signal_sample = in[i] * d_carr_sign[i];
|
||||||
|
// Now get early, late, and prompt values for each
|
||||||
|
d_Early += bb_signal_sample * d_early_code[i];
|
||||||
|
d_Prompt += bb_signal_sample * d_prompt_code[i];
|
||||||
|
d_Late += bb_signal_sample * d_late_code[i];
|
||||||
|
}
|
||||||
|
|
||||||
// Update the phasestep based on code freq (variable) and
|
// Compute PLL error and update carrier NCO -
|
||||||
// sampling frequency (fixed)
|
carr_error = pll_cloop_two_quadrant_atan(d_Prompt) / (float)TWO_PI;
|
||||||
d_code_phase_step_chips = d_code_freq_hz / (float)d_fs_in; //[chips]
|
// Implement carrier loop filter and generate NCO command
|
||||||
// variable code PRN sample block size
|
carr_nco = d_carrier_loop_filter.get_carrier_nco(carr_error);
|
||||||
float T_chip_seconds;
|
// Modify carrier freq based on NCO command
|
||||||
float T_prn_seconds;
|
d_carrier_doppler_hz = d_acq_carrier_doppler_hz + carr_nco;
|
||||||
float T_prn_samples;
|
|
||||||
float K_blk_samples;
|
|
||||||
T_chip_seconds=1/d_code_freq_hz;
|
|
||||||
T_prn_seconds=T_chip_seconds*GPS_L1_CA_CODE_LENGTH_CHIPS;
|
|
||||||
T_prn_samples=T_prn_seconds*d_fs_in;
|
|
||||||
d_rem_code_phase_samples=d_next_rem_code_phase_samples;
|
|
||||||
K_blk_samples=T_prn_samples+d_rem_code_phase_samples;
|
|
||||||
|
|
||||||
// Update the current PRN delay (code phase in samples)
|
// Compute DLL error and update code NCO
|
||||||
float T_prn_true_seconds = GPS_L1_CA_CODE_LENGTH_CHIPS/GPS_L1_CA_CODE_RATE_HZ;
|
code_error = dll_nc_e_minus_l_normalized(d_Early, d_Late);
|
||||||
float T_prn_true_samples = T_prn_true_seconds*(float)d_fs_in;
|
// Implement code loop filter and generate NCO command
|
||||||
d_code_phase_samples=d_code_phase_samples+T_prn_samples-T_prn_true_samples;
|
code_nco = d_code_loop_filter.get_code_nco(code_error);
|
||||||
if (d_code_phase_samples<0)
|
// Modify code freq based on NCO command
|
||||||
{
|
d_code_freq_hz = GPS_L1_CA_CODE_RATE_HZ - code_nco;
|
||||||
d_code_phase_samples=T_prn_true_samples+d_code_phase_samples;
|
|
||||||
}
|
|
||||||
|
|
||||||
d_code_phase_samples=fmod(d_code_phase_samples,T_prn_true_samples);
|
// Update the phasestep based on code freq (variable) and
|
||||||
|
// sampling frequency (fixed)
|
||||||
|
d_code_phase_step_chips = d_code_freq_hz / (float)d_fs_in; //[chips]
|
||||||
|
// variable code PRN sample block size
|
||||||
|
float T_chip_seconds;
|
||||||
|
float T_prn_seconds;
|
||||||
|
float T_prn_samples;
|
||||||
|
float K_blk_samples;
|
||||||
|
T_chip_seconds = 1 / d_code_freq_hz;
|
||||||
|
T_prn_seconds = T_chip_seconds * GPS_L1_CA_CODE_LENGTH_CHIPS;
|
||||||
|
T_prn_samples = T_prn_seconds * d_fs_in;
|
||||||
|
d_rem_code_phase_samples = d_next_rem_code_phase_samples;
|
||||||
|
K_blk_samples = T_prn_samples + d_rem_code_phase_samples;
|
||||||
|
|
||||||
|
// Update the current PRN delay (code phase in samples)
|
||||||
|
float T_prn_true_seconds = GPS_L1_CA_CODE_LENGTH_CHIPS / GPS_L1_CA_CODE_RATE_HZ;
|
||||||
|
float T_prn_true_samples = T_prn_true_seconds * (float)d_fs_in;
|
||||||
|
d_code_phase_samples = d_code_phase_samples + T_prn_samples - T_prn_true_samples;
|
||||||
|
if (d_code_phase_samples < 0)
|
||||||
|
{
|
||||||
|
d_code_phase_samples = T_prn_true_samples + d_code_phase_samples;
|
||||||
|
}
|
||||||
|
|
||||||
|
d_code_phase_samples = fmod(d_code_phase_samples, T_prn_true_samples);
|
||||||
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
#ifdef GNSS_SDR_USE_BOOST_ROUND
|
||||||
d_next_prn_length_samples=round(K_blk_samples); //round to a discrete samples
|
d_next_prn_length_samples = round(K_blk_samples); //round to a discrete samples
|
||||||
#else
|
#else
|
||||||
d_next_prn_length_samples=std::round(K_blk_samples); //round to a discrete samples
|
d_next_prn_length_samples = std::round(K_blk_samples); //round to a discrete samples
|
||||||
#endif
|
#endif
|
||||||
d_next_rem_code_phase_samples=K_blk_samples-d_next_prn_length_samples; //rounding error
|
d_next_rem_code_phase_samples = K_blk_samples - d_next_prn_length_samples; //rounding error
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \todo Improve the lock detection algorithm!
|
* \todo Improve the lock detection algorithm!
|
||||||
*/
|
*/
|
||||||
// ####### CN0 ESTIMATION AND LOCK DETECTORS ######
|
// ####### CN0 ESTIMATION AND LOCK DETECTORS ######
|
||||||
if (d_cn0_estimation_counter<CN0_ESTIMATION_SAMPLES)
|
if (d_cn0_estimation_counter < CN0_ESTIMATION_SAMPLES)
|
||||||
{
|
{
|
||||||
// fill buffer with prompt correlator output values
|
// fill buffer with prompt correlator output values
|
||||||
d_Prompt_buffer[d_cn0_estimation_counter]=d_Prompt;
|
d_Prompt_buffer[d_cn0_estimation_counter] = d_Prompt;
|
||||||
d_cn0_estimation_counter++;
|
d_cn0_estimation_counter++;
|
||||||
}else{
|
}
|
||||||
d_cn0_estimation_counter=0;
|
else
|
||||||
d_CN0_SNV_dB_Hz=gps_l1_ca_CN0_SNV(d_Prompt_buffer, CN0_ESTIMATION_SAMPLES,d_fs_in);
|
{
|
||||||
d_carrier_lock_test=carrier_lock_detector(d_Prompt_buffer,CN0_ESTIMATION_SAMPLES);
|
d_cn0_estimation_counter = 0;
|
||||||
// ###### TRACKING UNLOCK NOTIFICATION #####
|
d_CN0_SNV_dB_Hz = gps_l1_ca_CN0_SNV(d_Prompt_buffer, CN0_ESTIMATION_SAMPLES, d_fs_in);
|
||||||
int tracking_message;
|
d_carrier_lock_test = carrier_lock_detector(d_Prompt_buffer, CN0_ESTIMATION_SAMPLES);
|
||||||
if (d_carrier_lock_test<d_carrier_lock_threshold or d_carrier_lock_test>MINIMUM_VALID_CN0)
|
// ###### TRACKING UNLOCK NOTIFICATION #####
|
||||||
{
|
int tracking_message;
|
||||||
d_carrier_lock_fail_counter++;
|
if (d_carrier_lock_test < d_carrier_lock_threshold or d_carrier_lock_test > MINIMUM_VALID_CN0)
|
||||||
}else{
|
{
|
||||||
if (d_carrier_lock_fail_counter>0) d_carrier_lock_fail_counter--;
|
d_carrier_lock_fail_counter++;
|
||||||
}
|
}
|
||||||
if (d_carrier_lock_fail_counter>MAXIMUM_LOCK_FAIL_COUNTER)
|
else
|
||||||
{
|
{
|
||||||
std::cout<<"Channel "<<d_channel << " loss of lock!\r\n";
|
if (d_carrier_lock_fail_counter > 0) d_carrier_lock_fail_counter--;
|
||||||
tracking_message=3; //loss of lock
|
}
|
||||||
d_channel_internal_queue->push(tracking_message);
|
if (d_carrier_lock_fail_counter > MAXIMUM_LOCK_FAIL_COUNTER)
|
||||||
d_carrier_lock_fail_counter=0;
|
{
|
||||||
d_enable_tracking=false; // TODO: check if disabling tracking is consistent with the channel state machine
|
std::cout << "Channel " << d_channel << " loss of lock!" << std::endl ;
|
||||||
|
tracking_message = 3; //loss of lock
|
||||||
|
d_channel_internal_queue->push(tracking_message);
|
||||||
|
d_carrier_lock_fail_counter = 0;
|
||||||
|
d_enable_tracking = false; // TODO: check if disabling tracking is consistent with the channel state machine
|
||||||
|
|
||||||
}
|
}
|
||||||
//std::cout<<"d_carrier_lock_fail_counter"<<d_carrier_lock_fail_counter<<"\r\n";
|
//std::cout<<"d_carrier_lock_fail_counter"<<d_carrier_lock_fail_counter<<"\r\n";
|
||||||
}
|
}
|
||||||
|
|
||||||
/*!
|
/*!
|
||||||
* \todo Output the CN0
|
* \todo Output the CN0
|
||||||
*/
|
*/
|
||||||
// ########### Output the tracking data to navigation and PVT ##########
|
// ########### Output the tracking data to navigation and PVT ##########
|
||||||
// Output channel 0: Prompt correlator output Q
|
// Output channel 0: Prompt correlator output Q
|
||||||
*out[0]=(double)d_Prompt.real();
|
*out[0] = (double)d_Prompt.real();
|
||||||
// Output channel 1: Prompt correlator output I
|
// Output channel 1: Prompt correlator output I
|
||||||
*out[1]=(double)d_Prompt.imag();
|
*out[1] = (double)d_Prompt.imag();
|
||||||
// Output channel 2: PRN absolute delay [s]
|
// Output channel 2: PRN absolute delay [s]
|
||||||
*out[2]=d_sample_counter_seconds;
|
*out[2] = d_sample_counter_seconds;
|
||||||
// Output channel 3: d_acc_carrier_phase_rad [rad]
|
// Output channel 3: d_acc_carrier_phase_rad [rad]
|
||||||
*out[3]=(double)d_acc_carrier_phase_rad;
|
*out[3] = (double)d_acc_carrier_phase_rad;
|
||||||
// Output channel 4: PRN code phase [s]
|
// Output channel 4: PRN code phase [s]
|
||||||
*out[4]=(double)d_code_phase_samples*(1/(float)d_fs_in);
|
*out[4] = (double)d_code_phase_samples * (1 / (float)d_fs_in);
|
||||||
|
|
||||||
// ########## DEBUG OUTPUT
|
// ########## DEBUG OUTPUT
|
||||||
/*!
|
/*!
|
||||||
* \todo The stop timer has to be moved to the signal source!
|
* \todo The stop timer has to be moved to the signal source!
|
||||||
*/
|
*/
|
||||||
// debug: Second counter in channel 0
|
// debug: Second counter in channel 0
|
||||||
if (d_channel==0)
|
if (d_channel == 0)
|
||||||
{
|
{
|
||||||
if (floor(d_sample_counter/d_fs_in)!=d_last_seg)
|
if (floor(d_sample_counter / d_fs_in) != d_last_seg)
|
||||||
{
|
{
|
||||||
d_last_seg=floor(d_sample_counter/d_fs_in);
|
d_last_seg = floor(d_sample_counter / d_fs_in);
|
||||||
std::cout<<"Current input signal time="<<d_last_seg<<" [s]"<<std::endl;
|
std::cout << "Current input signal time=" << d_last_seg << " [s]" << std::endl;
|
||||||
std::cout<<"Tracking CH "<<d_channel<<" CN0="<<d_CN0_SNV_dB_Hz<<" [dB-Hz]"<<std::endl;
|
std::cout << "Tracking CH " << d_channel << " CN0=" << d_CN0_SNV_dB_Hz << " [dB-Hz]" << std::endl;
|
||||||
//std::cout<<"TRK CH "<<d_channel<<" Carrier_lock_test="<<d_carrier_lock_test<< std::endl;
|
//std::cout<<"TRK CH "<<d_channel<<" Carrier_lock_test="<<d_carrier_lock_test<< std::endl;
|
||||||
//if (d_last_seg==5) d_carrier_lock_fail_counter=500; //DEBUG: force unlock!
|
//if (d_last_seg==5) d_carrier_lock_fail_counter=500; //DEBUG: force unlock!
|
||||||
}
|
}
|
||||||
}else
|
}
|
||||||
{
|
else
|
||||||
if (floor(d_sample_counter/d_fs_in)!=d_last_seg)
|
{
|
||||||
{
|
if (floor(d_sample_counter / d_fs_in) != d_last_seg)
|
||||||
d_last_seg=floor(d_sample_counter/d_fs_in);
|
{
|
||||||
std::cout<<"Tracking CH "<<d_channel<<" CN0="<<d_CN0_SNV_dB_Hz<<" [dB-Hz]"<<std::endl;
|
d_last_seg = floor(d_sample_counter / d_fs_in);
|
||||||
//std::cout<<"TRK CH "<<d_channel<<" Carrier_lock_test="<<d_carrier_lock_test<< std::endl;
|
std::cout << "Tracking CH "<< d_channel << " CN0=" << d_CN0_SNV_dB_Hz << " [dB-Hz]" << std::endl;
|
||||||
}
|
//std::cout<<"TRK CH "<<d_channel<<" Carrier_lock_test="<<d_carrier_lock_test<< std::endl;
|
||||||
}
|
}
|
||||||
}else{
|
}
|
||||||
double **out = (double **) &output_items[0]; //block output streams pointer
|
}
|
||||||
*out[0]=0;
|
else
|
||||||
*out[1]=0;
|
{
|
||||||
*out[2]=0;
|
double **out = (double **) &output_items[0]; //block output streams pointer
|
||||||
*out[3]=0;
|
*out[0] = 0;
|
||||||
*out[4]=0;
|
*out[1] = 0;
|
||||||
}
|
*out[2] = 0;
|
||||||
|
*out[3] = 0;
|
||||||
|
*out[4] = 0;
|
||||||
|
}
|
||||||
|
|
||||||
if(d_dump) {
|
if(d_dump) {
|
||||||
// MULTIPLEXED FILE RECORDING - Record results to file
|
// MULTIPLEXED FILE RECORDING - Record results to file
|
||||||
float prompt_I;
|
float prompt_I;
|
||||||
float prompt_Q;
|
float prompt_Q;
|
||||||
float tmp_E,tmp_P,tmp_L;
|
float tmp_E, tmp_P, tmp_L;
|
||||||
float tmp_float;
|
float tmp_float;
|
||||||
prompt_I=d_Prompt.imag();
|
prompt_I = d_Prompt.imag();
|
||||||
prompt_Q=d_Prompt.real();
|
prompt_Q = d_Prompt.real();
|
||||||
tmp_E=std::abs<float>(d_Early);
|
tmp_E = std::abs<float>(d_Early);
|
||||||
tmp_P=std::abs<float>(d_Prompt);
|
tmp_P = std::abs<float>(d_Prompt);
|
||||||
tmp_L=std::abs<float>(d_Late);
|
tmp_L = std::abs<float>(d_Late);
|
||||||
try {
|
try
|
||||||
// EPR
|
{
|
||||||
d_dump_file.write((char*)&tmp_E, sizeof(float));
|
// EPR
|
||||||
d_dump_file.write((char*)&tmp_P, sizeof(float));
|
d_dump_file.write((char*)&tmp_E, sizeof(float));
|
||||||
d_dump_file.write((char*)&tmp_L, sizeof(float));
|
d_dump_file.write((char*)&tmp_P, sizeof(float));
|
||||||
// PROMPT I and Q (to analyze navigation symbols)
|
d_dump_file.write((char*)&tmp_L, sizeof(float));
|
||||||
d_dump_file.write((char*)&prompt_I, sizeof(float));
|
// PROMPT I and Q (to analyze navigation symbols)
|
||||||
d_dump_file.write((char*)&prompt_Q, sizeof(float));
|
d_dump_file.write((char*)&prompt_I, sizeof(float));
|
||||||
// PRN start sample stamp
|
d_dump_file.write((char*)&prompt_Q, sizeof(float));
|
||||||
//tmp_float=(float)d_sample_counter;
|
// PRN start sample stamp
|
||||||
d_dump_file.write((char*)&d_sample_counter, sizeof(unsigned long int));
|
//tmp_float=(float)d_sample_counter;
|
||||||
// accumulated carrier phase
|
d_dump_file.write((char*)&d_sample_counter, sizeof(unsigned long int));
|
||||||
d_dump_file.write((char*)&d_acc_carrier_phase_rad, sizeof(float));
|
// accumulated carrier phase
|
||||||
|
d_dump_file.write((char*)&d_acc_carrier_phase_rad, sizeof(float));
|
||||||
|
|
||||||
// carrier and code frequency
|
// carrier and code frequency
|
||||||
d_dump_file.write((char*)&d_carrier_doppler_hz, sizeof(float));
|
d_dump_file.write((char*)&d_carrier_doppler_hz, sizeof(float));
|
||||||
d_dump_file.write((char*)&d_code_freq_hz, sizeof(float));
|
d_dump_file.write((char*)&d_code_freq_hz, sizeof(float));
|
||||||
|
|
||||||
//PLL commands
|
//PLL commands
|
||||||
d_dump_file.write((char*)&carr_error, sizeof(float));
|
d_dump_file.write((char*)&carr_error, sizeof(float));
|
||||||
d_dump_file.write((char*)&carr_nco, sizeof(float));
|
d_dump_file.write((char*)&carr_nco, sizeof(float));
|
||||||
|
|
||||||
//DLL commands
|
//DLL commands
|
||||||
d_dump_file.write((char*)&code_error, sizeof(float));
|
d_dump_file.write((char*)&code_error, sizeof(float));
|
||||||
d_dump_file.write((char*)&code_nco, sizeof(float));
|
d_dump_file.write((char*)&code_nco, sizeof(float));
|
||||||
|
|
||||||
// CN0 and carrier lock test
|
// CN0 and carrier lock test
|
||||||
d_dump_file.write((char*)&d_CN0_SNV_dB_Hz, sizeof(float));
|
d_dump_file.write((char*)&d_CN0_SNV_dB_Hz, sizeof(float));
|
||||||
d_dump_file.write((char*)&d_carrier_lock_test, sizeof(float));
|
d_dump_file.write((char*)&d_carrier_lock_test, sizeof(float));
|
||||||
|
|
||||||
// AUX vars (for debug purposes)
|
// AUX vars (for debug purposes)
|
||||||
tmp_float=0;
|
tmp_float=0;
|
||||||
d_dump_file.write((char*)&tmp_float, sizeof(float));
|
d_dump_file.write((char*)&tmp_float, sizeof(float));
|
||||||
d_dump_file.write((char*)&d_sample_counter_seconds, sizeof(double));
|
d_dump_file.write((char*)&d_sample_counter_seconds, sizeof(double));
|
||||||
}
|
}
|
||||||
catch (std::ifstream::failure e) {
|
catch (std::ifstream::failure e)
|
||||||
std::cout << "Exception writing trk dump file "<<e.what()<<"\r\n";
|
{
|
||||||
}
|
std::cout << "Exception writing trk dump file " << e.what() << std::endl;
|
||||||
}
|
}
|
||||||
|
}
|
||||||
|
|
||||||
consume_each(d_current_prn_length_samples); // this is necesary in gr_block derivates
|
consume_each(d_current_prn_length_samples); // this is necesary in gr_block derivates
|
||||||
d_sample_counter_seconds = d_sample_counter_seconds + (((double)d_current_prn_length_samples)/(double)d_fs_in);
|
d_sample_counter_seconds = d_sample_counter_seconds + ( ((double)d_current_prn_length_samples) / (double)d_fs_in );
|
||||||
d_sample_counter+=d_current_prn_length_samples; //count for the processed samples
|
d_sample_counter += d_current_prn_length_samples; //count for the processed samples
|
||||||
return 1; //output tracking result ALWAYS even in the case of d_enable_tracking==false
|
return 1; //output tracking result ALWAYS even in the case of d_enable_tracking==false
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::set_acq_code_phase(float code_phase) {
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
void gps_l1_ca_dll_pll_tracking_cc::set_acq_code_phase(float code_phase)
|
||||||
|
{
|
||||||
d_acq_code_phase_samples = code_phase;
|
d_acq_code_phase_samples = code_phase;
|
||||||
LOG_AT_LEVEL(INFO) << "Tracking code phase set to " << d_acq_code_phase_samples;
|
LOG_AT_LEVEL(INFO) << "Tracking code phase set to " << d_acq_code_phase_samples;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::set_acq_doppler(float doppler) {
|
|
||||||
|
|
||||||
|
|
||||||
|
void gps_l1_ca_dll_pll_tracking_cc::set_acq_doppler(float doppler)
|
||||||
|
{
|
||||||
d_acq_carrier_doppler_hz = doppler;
|
d_acq_carrier_doppler_hz = doppler;
|
||||||
LOG_AT_LEVEL(INFO) << "Tracking carrier doppler set to " << d_acq_carrier_doppler_hz;
|
LOG_AT_LEVEL(INFO) << "Tracking carrier doppler set to " << d_acq_carrier_doppler_hz;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::set_satellite(unsigned int satellite) {
|
|
||||||
|
|
||||||
|
void gps_l1_ca_dll_pll_tracking_cc::set_satellite(unsigned int satellite)
|
||||||
|
{
|
||||||
d_satellite = satellite;
|
d_satellite = satellite;
|
||||||
LOG_AT_LEVEL(INFO) << "Tracking Satellite set to " << d_satellite;
|
LOG_AT_LEVEL(INFO) << "Tracking Satellite set to " << d_satellite;
|
||||||
}
|
}
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::set_channel(unsigned int channel) {
|
void gps_l1_ca_dll_pll_tracking_cc::set_channel(unsigned int channel)
|
||||||
d_channel = channel;
|
{
|
||||||
LOG_AT_LEVEL(INFO) << "Tracking Channel set to " << d_channel;
|
d_channel = channel;
|
||||||
// ############# ENABLE DATA FILE LOG #################
|
LOG_AT_LEVEL(INFO) << "Tracking Channel set to " << d_channel;
|
||||||
if (d_dump==true)
|
// ############# ENABLE DATA FILE LOG #################
|
||||||
{
|
if (d_dump==true)
|
||||||
if (d_dump_file.is_open()==false)
|
{
|
||||||
{
|
if (d_dump_file.is_open()==false)
|
||||||
try {
|
{
|
||||||
d_dump_filename.append(boost::lexical_cast<std::string>(d_channel));
|
try
|
||||||
d_dump_filename.append(".dat");
|
{
|
||||||
d_dump_file.exceptions ( std::ifstream::failbit | std::ifstream::badbit );
|
d_dump_filename.append(boost::lexical_cast<std::string>(d_channel));
|
||||||
d_dump_file.open(d_dump_filename.c_str(), std::ios::out | std::ios::binary);
|
d_dump_filename.append(".dat");
|
||||||
std::cout<<"Tracking dump enabled on channel "<<d_channel<<" Log file: "<<d_dump_filename.c_str()<<std::endl;
|
d_dump_file.exceptions (std::ifstream::failbit | std::ifstream::badbit);
|
||||||
}
|
d_dump_file.open(d_dump_filename.c_str(), std::ios::out | std::ios::binary);
|
||||||
catch (std::ifstream::failure e) {
|
std::cout << "Tracking dump enabled on channel " << d_channel << " Log file: " << d_dump_filename.c_str() << std::endl;
|
||||||
std::cout << "channel "<<d_channel <<" Exception opening trk dump file "<<e.what()<<"\r\n";
|
}
|
||||||
}
|
catch (std::ifstream::failure e)
|
||||||
}
|
{
|
||||||
}
|
std::cout << "channel "<< d_channel << " Exception opening trk dump file " << e.what() << std::endl;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::set_acq_sample_stamp(unsigned long int sample_stamp)
|
void gps_l1_ca_dll_pll_tracking_cc::set_acq_sample_stamp(unsigned long int sample_stamp)
|
||||||
{
|
{
|
||||||
d_acq_sample_stamp = sample_stamp;
|
d_acq_sample_stamp = sample_stamp;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void gps_l1_ca_dll_pll_tracking_cc::set_channel_queue(concurrent_queue<int> *channel_internal_queue)
|
void gps_l1_ca_dll_pll_tracking_cc::set_channel_queue(concurrent_queue<int> *channel_internal_queue)
|
||||||
{
|
{
|
||||||
d_channel_internal_queue = channel_internal_queue;
|
d_channel_internal_queue = channel_internal_queue;
|
||||||
|
@ -70,22 +70,22 @@ float gps_l1_ca_CN0_SNV(gr_complex* Prompt_buffer, int length, long fs_in)
|
|||||||
//SNR_SNV(count)=Psig/(Ptot-Psig);
|
//SNR_SNV(count)=Psig/(Ptot-Psig);
|
||||||
//CN0_SNV_dB=10*log10(SNR_SNV)+10*log10(BW)-10*log10(PRN_length);
|
//CN0_SNV_dB=10*log10(SNR_SNV)+10*log10(BW)-10*log10(PRN_length);
|
||||||
float SNR, SNR_dB_Hz;
|
float SNR, SNR_dB_Hz;
|
||||||
float tmp_abs_I,tmp_abs_Q;
|
float tmp_abs_I, tmp_abs_Q;
|
||||||
float Psig,Ptot;
|
float Psig, Ptot;
|
||||||
//float M2,M4;
|
//float M2,M4;
|
||||||
Psig=0;
|
Psig = 0;
|
||||||
Ptot=0;
|
Ptot = 0;
|
||||||
for (int i=0;i<length;i++)
|
for (int i=0; i<length; i++)
|
||||||
{
|
{
|
||||||
tmp_abs_I=std::abs(Prompt_buffer[i].imag());
|
tmp_abs_I = std::abs(Prompt_buffer[i].imag());
|
||||||
tmp_abs_Q=std::abs(Prompt_buffer[i].real());
|
tmp_abs_Q = std::abs(Prompt_buffer[i].real());
|
||||||
Psig+=tmp_abs_I;
|
Psig += tmp_abs_I;
|
||||||
Ptot+=Prompt_buffer[i].imag()*Prompt_buffer[i].imag()+Prompt_buffer[i].real()*Prompt_buffer[i].real();
|
Ptot += Prompt_buffer[i].imag()*Prompt_buffer[i].imag() + Prompt_buffer[i].real()*Prompt_buffer[i].real();
|
||||||
}
|
}
|
||||||
Psig=Psig/(float)length;
|
Psig = Psig / (float)length;
|
||||||
Psig=Psig*Psig;
|
Psig = Psig*Psig;
|
||||||
SNR=Psig/(Ptot/(float)length-Psig);
|
SNR = Psig / (Ptot / (float)length - Psig);
|
||||||
SNR_dB_Hz=10*log10(SNR)+10*log10(fs_in/2)-10*log10(GPS_L1_CA_CODE_LENGTH_CHIPS);
|
SNR_dB_Hz = 10*log10(SNR) + 10*log10(fs_in/2) - 10*log10(GPS_L1_CA_CODE_LENGTH_CHIPS);
|
||||||
return SNR_dB_Hz;
|
return SNR_dB_Hz;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -109,26 +109,25 @@ float carrier_lock_detector(gr_complex* Prompt_buffer, int length)
|
|||||||
//NBD=sum(abs(imag(x((n-N+1):n))))^2 + sum(abs(real(x((n-N+1):n))))^2;
|
//NBD=sum(abs(imag(x((n-N+1):n))))^2 + sum(abs(real(x((n-N+1):n))))^2;
|
||||||
//NBP=sum(imag(x((n-N+1):n)).^2) - sum(real(x((n-N+1):n)).^2);
|
//NBP=sum(imag(x((n-N+1):n)).^2) - sum(real(x((n-N+1):n)).^2);
|
||||||
//LOCK(count)=NBD/NBP;
|
//LOCK(count)=NBD/NBP;
|
||||||
float tmp_abs_I,tmp_abs_Q;
|
float tmp_abs_I, tmp_abs_Q;
|
||||||
float tmp_sum_abs_I,tmp_sum_abs_Q;
|
float tmp_sum_abs_I, tmp_sum_abs_Q;
|
||||||
float tmp_sum_sqr_I,tmp_sum_sqr_Q;
|
float tmp_sum_sqr_I, tmp_sum_sqr_Q;
|
||||||
tmp_sum_abs_I=0;
|
tmp_sum_abs_I=0;
|
||||||
tmp_sum_abs_Q=0;
|
tmp_sum_abs_Q=0;
|
||||||
tmp_sum_sqr_I=0;
|
tmp_sum_sqr_I=0;
|
||||||
tmp_sum_sqr_Q=0;
|
tmp_sum_sqr_Q=0;
|
||||||
float NBD,NBP;
|
float NBD,NBP;
|
||||||
for (int i=0;i<length;i++)
|
for (int i=0; i<length; i++)
|
||||||
{
|
{
|
||||||
tmp_abs_I=std::abs(Prompt_buffer[i].imag());
|
tmp_abs_I = std::abs(Prompt_buffer[i].imag());
|
||||||
tmp_abs_Q=std::abs(Prompt_buffer[i].real());
|
tmp_abs_Q = std::abs(Prompt_buffer[i].real());
|
||||||
tmp_sum_abs_I+=tmp_abs_I;
|
tmp_sum_abs_I += tmp_abs_I;
|
||||||
tmp_sum_abs_Q+=tmp_abs_Q;
|
tmp_sum_abs_Q += tmp_abs_Q;
|
||||||
tmp_sum_sqr_I+=(Prompt_buffer[i].imag()*Prompt_buffer[i].imag());
|
tmp_sum_sqr_I += (Prompt_buffer[i].imag()*Prompt_buffer[i].imag());
|
||||||
tmp_sum_sqr_Q+=(Prompt_buffer[i].real()*Prompt_buffer[i].real());
|
tmp_sum_sqr_Q += (Prompt_buffer[i].real()*Prompt_buffer[i].real());
|
||||||
}
|
}
|
||||||
NBD=tmp_sum_abs_I*tmp_sum_abs_I+tmp_sum_abs_Q*tmp_sum_abs_Q;
|
NBD = tmp_sum_abs_I*tmp_sum_abs_I + tmp_sum_abs_Q*tmp_sum_abs_Q;
|
||||||
NBP=tmp_sum_sqr_I-tmp_sum_sqr_Q;
|
NBP = tmp_sum_sqr_I - tmp_sum_sqr_Q;
|
||||||
return NBD/NBP;
|
return NBD/NBP;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -38,7 +38,8 @@
|
|||||||
#include "tracking_2nd_DLL_filter.h"
|
#include "tracking_2nd_DLL_filter.h"
|
||||||
|
|
||||||
|
|
||||||
void tracking_2nd_DLL_filter::calculate_lopp_coef(float* tau1,float* tau2, float lbw, float zeta, float k){
|
void tracking_2nd_DLL_filter::calculate_lopp_coef(float* tau1,float* tau2, float lbw, float zeta, float k)
|
||||||
|
{
|
||||||
// Solve natural frequency
|
// Solve natural frequency
|
||||||
float Wn;
|
float Wn;
|
||||||
Wn = lbw*8*zeta / (4*zeta*zeta + 1);
|
Wn = lbw*8*zeta / (4*zeta*zeta + 1);
|
||||||
@ -47,20 +48,26 @@ void tracking_2nd_DLL_filter::calculate_lopp_coef(float* tau1,float* tau2, float
|
|||||||
*tau2 = (2.0 * zeta) / Wn;
|
*tau2 = (2.0 * zeta) / Wn;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void tracking_2nd_DLL_filter::set_DLL_BW(float dll_bw_hz)
|
void tracking_2nd_DLL_filter::set_DLL_BW(float dll_bw_hz)
|
||||||
{
|
{
|
||||||
//Calculate filter coefficient values
|
//Calculate filter coefficient values
|
||||||
d_dllnoisebandwidth=dll_bw_hz;
|
d_dllnoisebandwidth =dll_bw_hz;
|
||||||
calculate_lopp_coef(&d_tau1_code, &d_tau2_code, d_dllnoisebandwidth, d_dlldampingratio,1.0);// Calculate filter coefficient values
|
calculate_lopp_coef(&d_tau1_code, &d_tau2_code, d_dllnoisebandwidth, d_dlldampingratio, 1.0);// Calculate filter coefficient values
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
void tracking_2nd_DLL_filter::initialize(float d_acq_code_phase_samples)
|
void tracking_2nd_DLL_filter::initialize(float d_acq_code_phase_samples)
|
||||||
{
|
{
|
||||||
// code tracking loop parameters
|
// code tracking loop parameters
|
||||||
d_old_code_nco = 0.0;
|
d_old_code_nco = 0.0;
|
||||||
d_old_code_error = 0.0;
|
d_old_code_error = 0.0;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
float tracking_2nd_DLL_filter::get_code_nco(float DLL_discriminator)
|
float tracking_2nd_DLL_filter::get_code_nco(float DLL_discriminator)
|
||||||
{
|
{
|
||||||
float code_nco;
|
float code_nco;
|
||||||
@ -70,13 +77,14 @@ float tracking_2nd_DLL_filter::get_code_nco(float DLL_discriminator)
|
|||||||
return code_nco;
|
return code_nco;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
tracking_2nd_DLL_filter::tracking_2nd_DLL_filter ()
|
tracking_2nd_DLL_filter::tracking_2nd_DLL_filter ()
|
||||||
{
|
{
|
||||||
d_pdi_code = 0.001;// Summation interval for code
|
d_pdi_code = 0.001;// Summation interval for code
|
||||||
d_dlldampingratio=0.7;
|
d_dlldampingratio = 0.7;
|
||||||
}
|
}
|
||||||
|
|
||||||
tracking_2nd_DLL_filter::~tracking_2nd_DLL_filter ()
|
tracking_2nd_DLL_filter::~tracking_2nd_DLL_filter ()
|
||||||
{
|
{}
|
||||||
|
|
||||||
}
|
|
||||||
|
@ -47,9 +47,9 @@
|
|||||||
float fll_four_quadrant_atan(gr_complex prompt_s1, gr_complex prompt_s2,float t1, float t2)
|
float fll_four_quadrant_atan(gr_complex prompt_s1, gr_complex prompt_s2,float t1, float t2)
|
||||||
{
|
{
|
||||||
float cross,dot;
|
float cross,dot;
|
||||||
dot=prompt_s1.imag()*prompt_s2.imag()+prompt_s1.real()*prompt_s2.real();
|
dot = prompt_s1.imag()*prompt_s2.imag() + prompt_s1.real()*prompt_s2.real();
|
||||||
cross=prompt_s1.imag()*prompt_s2.real()-prompt_s2.imag()*prompt_s1.real();
|
cross = prompt_s1.imag()*prompt_s2.real() - prompt_s2.imag()*prompt_s1.real();
|
||||||
return atan2(cross,dot)/(t2-t1);
|
return atan2(cross, dot) / (t2-t1);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -62,7 +62,7 @@ float fll_four_quadrant_atan(gr_complex prompt_s1, gr_complex prompt_s2,float t1
|
|||||||
*/
|
*/
|
||||||
float pll_four_quadrant_atan(gr_complex prompt_s1)
|
float pll_four_quadrant_atan(gr_complex prompt_s1)
|
||||||
{
|
{
|
||||||
return atan2(prompt_s1.real(),prompt_s1.imag());
|
return atan2(prompt_s1.real(), prompt_s1.imag());
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -75,11 +75,13 @@ float pll_four_quadrant_atan(gr_complex prompt_s1)
|
|||||||
*/
|
*/
|
||||||
float pll_cloop_two_quadrant_atan(gr_complex prompt_s1)
|
float pll_cloop_two_quadrant_atan(gr_complex prompt_s1)
|
||||||
{
|
{
|
||||||
if (prompt_s1.imag()!=0.0)
|
if (prompt_s1.imag() != 0.0)
|
||||||
{
|
{
|
||||||
return atan(prompt_s1.real()/prompt_s1.imag());
|
return atan(prompt_s1.real() / prompt_s1.imag());
|
||||||
}else{
|
}
|
||||||
return 0;
|
else
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -95,7 +97,7 @@ float pll_cloop_two_quadrant_atan(gr_complex prompt_s1)
|
|||||||
float dll_nc_e_minus_l_normalized(gr_complex early_s1, gr_complex late_s1)
|
float dll_nc_e_minus_l_normalized(gr_complex early_s1, gr_complex late_s1)
|
||||||
{
|
{
|
||||||
float P_early, P_late;
|
float P_early, P_late;
|
||||||
P_early=std::abs(early_s1);
|
P_early = std::abs(early_s1);
|
||||||
P_late=std::abs(late_s1);
|
P_late = std::abs(late_s1);
|
||||||
return (P_early-P_late)/((P_early+P_late));
|
return (P_early - P_late) / ((P_early + P_late));
|
||||||
}
|
}
|
||||||
|
@ -39,59 +39,59 @@
|
|||||||
|
|
||||||
void gps_navigation_message::reset()
|
void gps_navigation_message::reset()
|
||||||
{
|
{
|
||||||
d_TOW=0;
|
d_TOW = 0;
|
||||||
d_IODE_SF2=0;
|
d_IODE_SF2 = 0;
|
||||||
d_IODE_SF3=0;
|
d_IODE_SF3 = 0;
|
||||||
d_Crs=0;
|
d_Crs = 0;
|
||||||
d_Delta_n=0;
|
d_Delta_n = 0;
|
||||||
d_M_0=0;
|
d_M_0 = 0;
|
||||||
d_Cuc=0;
|
d_Cuc = 0;
|
||||||
d_e_eccentricity=0;
|
d_e_eccentricity = 0;
|
||||||
d_Cus=0;
|
d_Cus = 0;
|
||||||
d_sqrt_A=0;
|
d_sqrt_A = 0;
|
||||||
d_Toe=0;
|
d_Toe = 0;
|
||||||
d_Toc=0;
|
d_Toc = 0;
|
||||||
d_Cic=0;
|
d_Cic = 0;
|
||||||
d_OMEGA0=0;
|
d_OMEGA0 = 0;
|
||||||
d_Cis=0;
|
d_Cis = 0;
|
||||||
d_i_0=0;
|
d_i_0 = 0;
|
||||||
d_Crc=0;
|
d_Crc = 0;
|
||||||
d_OMEGA=0;
|
d_OMEGA = 0;
|
||||||
d_OMEGA_DOT=0;
|
d_OMEGA_DOT = 0;
|
||||||
d_IDOT=0;
|
d_IDOT = 0;
|
||||||
i_code_on_L2=0;
|
i_code_on_L2 = 0;
|
||||||
i_GPS_week=0;
|
i_GPS_week = 0;
|
||||||
b_L2_P_data_flag=false;
|
b_L2_P_data_flag = false;
|
||||||
i_SV_accuracy=0;
|
i_SV_accuracy = 0;
|
||||||
i_SV_health=0;
|
i_SV_health = 0;
|
||||||
d_TGD=0;
|
d_TGD = 0;
|
||||||
d_IODC=-1;
|
d_IODC = -1;
|
||||||
i_AODO=0;
|
i_AODO = 0;
|
||||||
|
|
||||||
b_fit_interval_flag=false;
|
b_fit_interval_flag = false;
|
||||||
d_spare1=0;
|
d_spare1 = 0;
|
||||||
d_spare2=0;
|
d_spare2 = 0;
|
||||||
|
|
||||||
d_A_f0=0;
|
d_A_f0 = 0;
|
||||||
d_A_f1=0;
|
d_A_f1 = 0;
|
||||||
d_A_f2=0;
|
d_A_f2 = 0;
|
||||||
|
|
||||||
//clock terms
|
//clock terms
|
||||||
//d_master_clock=0;
|
//d_master_clock=0;
|
||||||
d_dtr=0;
|
d_dtr = 0;
|
||||||
d_satClkCorr=0;
|
d_satClkCorr = 0;
|
||||||
|
|
||||||
// satellite positions
|
// satellite positions
|
||||||
d_satpos_X=0;
|
d_satpos_X = 0;
|
||||||
d_satpos_Y=0;
|
d_satpos_Y = 0;
|
||||||
d_satpos_Z=0;
|
d_satpos_Z = 0;
|
||||||
|
|
||||||
// info
|
// info
|
||||||
i_channel_ID=0;
|
i_channel_ID = 0;
|
||||||
i_satellite_PRN=0;
|
i_satellite_PRN = 0;
|
||||||
|
|
||||||
// time synchro
|
// time synchro
|
||||||
d_subframe1_timestamp_ms=0;
|
d_subframe1_timestamp_ms = 0;
|
||||||
|
|
||||||
// flags
|
// flags
|
||||||
b_alert_flag = false;
|
b_alert_flag = false;
|
||||||
@ -100,35 +100,35 @@ void gps_navigation_message::reset()
|
|||||||
|
|
||||||
|
|
||||||
// Ionosphere and UTC
|
// Ionosphere and UTC
|
||||||
d_alpha0=0;
|
d_alpha0 = 0;
|
||||||
d_alpha1=0;
|
d_alpha1 = 0;
|
||||||
d_alpha2=0;
|
d_alpha2 = 0;
|
||||||
d_alpha3=0;
|
d_alpha3 = 0;
|
||||||
d_beta0=0;
|
d_beta0 = 0;
|
||||||
d_beta1=0;
|
d_beta1 = 0;
|
||||||
d_beta2=0;
|
d_beta2 = 0;
|
||||||
d_beta3=0;
|
d_beta3 = 0;
|
||||||
d_A1=0;
|
d_A1 = 0;
|
||||||
d_A0=0;
|
d_A0 = 0;
|
||||||
d_t_OT=0;
|
d_t_OT = 0;
|
||||||
i_WN_T=0;
|
i_WN_T = 0;
|
||||||
d_DeltaT_LS=0;
|
d_DeltaT_LS = 0;
|
||||||
i_WN_LSF=0;
|
i_WN_LSF = 0;
|
||||||
i_DN=0;
|
i_DN = 0;
|
||||||
d_DeltaT_LSF=0;
|
d_DeltaT_LSF= 0;
|
||||||
|
|
||||||
//Almanac
|
//Almanac
|
||||||
d_Toa = 0;
|
d_Toa = 0;
|
||||||
i_WN_A = 0;
|
i_WN_A = 0;
|
||||||
for (int i=1; i < 32; i++ )
|
for (int i=1; i < 32; i++ )
|
||||||
{
|
{
|
||||||
almanacHealth[i]=0;
|
almanacHealth[i] = 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Satellite velocity
|
// Satellite velocity
|
||||||
d_satvel_X=0;
|
d_satvel_X = 0;
|
||||||
d_satvel_Y=0;
|
d_satvel_Y = 0;
|
||||||
d_satvel_Z=0;
|
d_satvel_Z = 0;
|
||||||
|
|
||||||
//Plane A (info from http://www.navcen.uscg.gov/?Do=constellationStatus)
|
//Plane A (info from http://www.navcen.uscg.gov/?Do=constellationStatus)
|
||||||
satelliteBlock[9] = "IIA";
|
satelliteBlock[9] = "IIA";
|
||||||
@ -182,8 +182,8 @@ gps_navigation_message::gps_navigation_message()
|
|||||||
void gps_navigation_message::print_gps_word_bytes(unsigned int GPS_word)
|
void gps_navigation_message::print_gps_word_bytes(unsigned int GPS_word)
|
||||||
{
|
{
|
||||||
std::cout << " Word =";
|
std::cout << " Word =";
|
||||||
std::cout<<std::bitset<32>(GPS_word);
|
std::cout << std::bitset<32>(GPS_word);
|
||||||
std::cout<<std::endl;
|
std::cout << std::endl;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -192,13 +192,13 @@ bool gps_navigation_message::read_navigation_bool(std::bitset<GPS_SUBFRAME_BITS>
|
|||||||
{
|
{
|
||||||
bool value;
|
bool value;
|
||||||
|
|
||||||
if (bits[GPS_SUBFRAME_BITS-slices[0].position]==1)
|
if (bits[GPS_SUBFRAME_BITS - slices[0].position] == 1)
|
||||||
{
|
{
|
||||||
value=true;
|
value = true;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
value=false;
|
value = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
return value;
|
return value;
|
||||||
@ -212,15 +212,15 @@ unsigned long int gps_navigation_message::read_navigation_unsigned(std::bitset<G
|
|||||||
{
|
{
|
||||||
unsigned long int value;
|
unsigned long int value;
|
||||||
|
|
||||||
value=0;
|
value = 0;
|
||||||
for (int i=0;i<num_of_slices;i++)
|
for (int i=0; i<num_of_slices; i++)
|
||||||
{
|
{
|
||||||
for (int j=0;j<slices[i].length;j++)
|
for (int j=0; j<slices[i].length; j++)
|
||||||
{
|
{
|
||||||
value<<=1; //shift left
|
value <<= 1; //shift left
|
||||||
if (bits[GPS_SUBFRAME_BITS-slices[i].position-j]==1)
|
if (bits[GPS_SUBFRAME_BITS - slices[i].position - j] == 1)
|
||||||
{
|
{
|
||||||
value+=1; // insert the bit
|
value += 1; // insert the bit
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -234,22 +234,25 @@ unsigned long int gps_navigation_message::read_navigation_unsigned(std::bitset<G
|
|||||||
|
|
||||||
signed long int gps_navigation_message::read_navigation_signed(std::bitset<GPS_SUBFRAME_BITS> bits, const bits_slice *slices, int num_of_slices)
|
signed long int gps_navigation_message::read_navigation_signed(std::bitset<GPS_SUBFRAME_BITS> bits, const bits_slice *slices, int num_of_slices)
|
||||||
{
|
{
|
||||||
signed long int value=0;
|
signed long int value = 0;
|
||||||
|
|
||||||
// read the MSB and perform the sign extension
|
// read the MSB and perform the sign extension
|
||||||
if (bits[GPS_SUBFRAME_BITS-slices[0].position]==1)
|
if (bits[GPS_SUBFRAME_BITS-slices[0].position]==1)
|
||||||
{
|
{
|
||||||
value^=0xFFFFFFFF;
|
value^=0xFFFFFFFF;
|
||||||
}else{
|
|
||||||
value&=0;
|
|
||||||
}
|
}
|
||||||
for (int i=0;i<num_of_slices;i++)
|
else
|
||||||
{
|
{
|
||||||
for (int j=0;j<slices[i].length;j++)
|
value&=0;
|
||||||
|
}
|
||||||
|
|
||||||
|
for (int i=0; i<num_of_slices; i++)
|
||||||
|
{
|
||||||
|
for (int j=0; j<slices[i].length; j++)
|
||||||
{
|
{
|
||||||
value<<=1; //shift left
|
value<<=1; //shift left
|
||||||
value&=0xFFFFFFFE; //reset the corresponding bit
|
value&=0xFFFFFFFE; //reset the corresponding bit
|
||||||
if (bits[GPS_SUBFRAME_BITS-slices[i].position-j]==1)
|
if (bits[GPS_SUBFRAME_BITS - slices[i].position-j] == 1)
|
||||||
{
|
{
|
||||||
value+=1; // insert the bit
|
value+=1; // insert the bit
|
||||||
}
|
}
|
||||||
@ -270,10 +273,11 @@ double gps_navigation_message::check_t(double time)
|
|||||||
if (time > half_week)
|
if (time > half_week)
|
||||||
{
|
{
|
||||||
corrTime = time - 2*half_week;
|
corrTime = time - 2*half_week;
|
||||||
}else if (time < -half_week)
|
}
|
||||||
{
|
else if (time < -half_week)
|
||||||
corrTime = time + 2*half_week;
|
{
|
||||||
}
|
corrTime = time + 2*half_week;
|
||||||
|
}
|
||||||
return corrTime;
|
return corrTime;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -314,25 +318,25 @@ void gps_navigation_message::satellitePosition(double transmitTime)
|
|||||||
// Find satellite's position ----------------------------------------------
|
// Find satellite's position ----------------------------------------------
|
||||||
|
|
||||||
// Restore semi-major axis
|
// Restore semi-major axis
|
||||||
a = d_sqrt_A*d_sqrt_A;
|
a = d_sqrt_A*d_sqrt_A;
|
||||||
|
|
||||||
// Time from ephemeris reference epoch
|
// Time from ephemeris reference epoch
|
||||||
tk = check_t(transmitTime - d_Toe);
|
tk = check_t(transmitTime - d_Toe);
|
||||||
|
|
||||||
// Computed mean motion
|
// Computed mean motion
|
||||||
n0 = sqrt(GM / (a*a*a));
|
n0 = sqrt(GM / (a*a*a));
|
||||||
|
|
||||||
// Corrected mean motion
|
// Corrected mean motion
|
||||||
n = n0 + d_Delta_n;
|
n = n0 + d_Delta_n;
|
||||||
|
|
||||||
// Mean anomaly
|
// Mean anomaly
|
||||||
M = d_M_0 + n * tk;
|
M = d_M_0 + n * tk;
|
||||||
|
|
||||||
// Reduce mean anomaly to between 0 and 2pi
|
// Reduce mean anomaly to between 0 and 2pi
|
||||||
M = fmod((M + 2*GPS_PI),(2*GPS_PI));
|
M = fmod((M + 2*GPS_PI),(2*GPS_PI));
|
||||||
|
|
||||||
// Initial guess of eccentric anomaly
|
// Initial guess of eccentric anomaly
|
||||||
E = M;
|
E = M;
|
||||||
|
|
||||||
// --- Iteratively compute eccentric anomaly ----------------------------
|
// --- Iteratively compute eccentric anomaly ----------------------------
|
||||||
for (int ii = 1;ii<20;ii++)
|
for (int ii = 1;ii<20;ii++)
|
||||||
@ -351,8 +355,8 @@ void gps_navigation_message::satellitePosition(double transmitTime)
|
|||||||
d_dtr = F * d_e_eccentricity * d_sqrt_A * sin(E);
|
d_dtr = F * d_e_eccentricity * d_sqrt_A * sin(E);
|
||||||
|
|
||||||
// Compute the true anomaly
|
// Compute the true anomaly
|
||||||
double tmp_Y=sqrt(1.0 - d_e_eccentricity*d_e_eccentricity) * sin(E);
|
double tmp_Y = sqrt(1.0 - d_e_eccentricity*d_e_eccentricity) * sin(E);
|
||||||
double tmp_X=cos(E)-d_e_eccentricity;
|
double tmp_X = cos(E) - d_e_eccentricity;
|
||||||
nu = atan2(tmp_Y, tmp_X);
|
nu = atan2(tmp_Y, tmp_X);
|
||||||
|
|
||||||
// Compute angle phi (argument of Latitude)
|
// Compute angle phi (argument of Latitude)
|
||||||
@ -362,7 +366,7 @@ void gps_navigation_message::satellitePosition(double transmitTime)
|
|||||||
phi = fmod((phi),(2*GPS_PI));
|
phi = fmod((phi),(2*GPS_PI));
|
||||||
|
|
||||||
// Correct argument of latitude
|
// Correct argument of latitude
|
||||||
u = phi + d_Cuc * cos(2*phi) + d_Cus * sin(2*phi);
|
u = phi + d_Cuc * cos(2*phi) + d_Cus * sin(2*phi);
|
||||||
|
|
||||||
// Correct radius
|
// Correct radius
|
||||||
r = a * (1 - d_e_eccentricity*cos(E)) + d_Crc * cos(2*phi) + d_Crs * sin(2*phi);
|
r = a * (1 - d_e_eccentricity*cos(E)) + d_Crc * cos(2*phi) + d_Crs * sin(2*phi);
|
||||||
@ -403,11 +407,6 @@ void gps_navigation_message::satellitePosition(double transmitTime)
|
|||||||
d_satvel_X = - Omega_dot * (cos(u) * r + sin(u) * r * cos(i)) + d_satpos_X * cos(Omega) - d_satpos_Y * cos(i) * sin(Omega);
|
d_satvel_X = - Omega_dot * (cos(u) * r + sin(u) * r * cos(i)) + d_satpos_X * cos(Omega) - d_satpos_Y * cos(i) * sin(Omega);
|
||||||
d_satvel_Y = Omega_dot * (cos(u) * r * cos(Omega) - sin(u) * r * cos(i) * sin(Omega)) + d_satpos_X * sin(Omega) + d_satpos_Y * cos(i) * cos(Omega);
|
d_satvel_Y = Omega_dot * (cos(u) * r * cos(Omega) - sin(u) * r * cos(i) * sin(Omega)) + d_satpos_X * sin(Omega) + d_satpos_Y * cos(i) * cos(Omega);
|
||||||
d_satvel_Z = d_satpos_Y * sin(i);
|
d_satvel_Z = d_satpos_Y * sin(i);
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -422,9 +421,9 @@ void gps_navigation_message::satellitePosition(double transmitTime)
|
|||||||
|
|
||||||
int gps_navigation_message::subframe_decoder(char *subframe)
|
int gps_navigation_message::subframe_decoder(char *subframe)
|
||||||
{
|
{
|
||||||
int subframe_ID=0;
|
int subframe_ID = 0;
|
||||||
int SV_data_ID=0;
|
int SV_data_ID = 0;
|
||||||
int SV_page=0;
|
int SV_page = 0;
|
||||||
//double tmp_TOW;
|
//double tmp_TOW;
|
||||||
|
|
||||||
unsigned int gps_word;
|
unsigned int gps_word;
|
||||||
@ -432,13 +431,13 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
// UNPACK BYTES TO BITS AND REMOVE THE CRC REDUNDANCE
|
// UNPACK BYTES TO BITS AND REMOVE THE CRC REDUNDANCE
|
||||||
std::bitset<GPS_SUBFRAME_BITS> subframe_bits;
|
std::bitset<GPS_SUBFRAME_BITS> subframe_bits;
|
||||||
std::bitset<GPS_WORD_BITS+2> word_bits;
|
std::bitset<GPS_WORD_BITS+2> word_bits;
|
||||||
for (int i=0;i<10;i++)
|
for (int i=0; i<10; i++)
|
||||||
{
|
{
|
||||||
memcpy(&gps_word,&subframe[i*4],sizeof(char)*4);
|
memcpy(&gps_word,&subframe[i*4], sizeof(char)*4);
|
||||||
word_bits=std::bitset<(GPS_WORD_BITS+2)>(gps_word);
|
word_bits = std::bitset<(GPS_WORD_BITS+2)>(gps_word);
|
||||||
for (int j=0;j<GPS_WORD_BITS;j++)
|
for (int j=0; j<GPS_WORD_BITS; j++)
|
||||||
{
|
{
|
||||||
subframe_bits[GPS_WORD_BITS*(9-i)+j]=word_bits[j];
|
subframe_bits[GPS_WORD_BITS*(9-i) + j] = word_bits[j];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -451,11 +450,12 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
print_gps_word_bytes(gps_word);
|
print_gps_word_bytes(gps_word);
|
||||||
}
|
}
|
||||||
*/
|
*/
|
||||||
subframe_ID=(int)read_navigation_unsigned(subframe_bits,SUBFRAME_ID,num_of_slices(SUBFRAME_ID));
|
subframe_ID = (int)read_navigation_unsigned(subframe_bits, SUBFRAME_ID, num_of_slices(SUBFRAME_ID));
|
||||||
//std::cout<<"subframe ID="<<subframe_ID<<std::endl;
|
//std::cout<<"subframe ID="<<subframe_ID<<std::endl;
|
||||||
|
|
||||||
// Decode all 5 sub-frames
|
// Decode all 5 sub-frames
|
||||||
switch (subframe_ID){
|
switch (subframe_ID)
|
||||||
|
{
|
||||||
//--- Decode the sub-frame id ------------------------------------------
|
//--- Decode the sub-frame id ------------------------------------------
|
||||||
// ICD (IS-GPS-200E Appendix II). http://www.losangeles.af.mil/shared/media/document/AFD-100813-045.pdf
|
// ICD (IS-GPS-200E Appendix II). http://www.losangeles.af.mil/shared/media/document/AFD-100813-045.pdf
|
||||||
case 1:
|
case 1:
|
||||||
@ -466,7 +466,7 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
// subframe and we need the TOW of the first subframe in this data block
|
// subframe and we need the TOW of the first subframe in this data block
|
||||||
// (the variable subframe at this point contains bits of the last subframe).
|
// (the variable subframe at this point contains bits of the last subframe).
|
||||||
//TOW = bin2dec(subframe(31:47)) * 6 - 30;
|
//TOW = bin2dec(subframe(31:47)) * 6 - 30;
|
||||||
d_TOW = (double)read_navigation_unsigned(subframe_bits,TOW,num_of_slices(TOW));
|
d_TOW = (double)read_navigation_unsigned(subframe_bits, TOW, num_of_slices(TOW));
|
||||||
d_TOW = d_TOW*6-6; //we are in the first subframe (the transmitted TOW is the start time of the next subframe, thus we need to substract one subframe (6 seconds)) !
|
d_TOW = d_TOW*6-6; //we are in the first subframe (the transmitted TOW is the start time of the next subframe, thus we need to substract one subframe (6 seconds)) !
|
||||||
|
|
||||||
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
||||||
@ -474,22 +474,22 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
||||||
|
|
||||||
// It contains WN, SV clock corrections, health and accuracy
|
// It contains WN, SV clock corrections, health and accuracy
|
||||||
i_GPS_week = (int)read_navigation_unsigned(subframe_bits,GPS_WEEK,num_of_slices(GPS_WEEK));
|
i_GPS_week = (int)read_navigation_unsigned(subframe_bits, GPS_WEEK, num_of_slices(GPS_WEEK));
|
||||||
i_SV_accuracy = (int)read_navigation_unsigned(subframe_bits,SV_ACCURACY,num_of_slices(SV_ACCURACY)); // (20.3.3.3.1.3)
|
i_SV_accuracy = (int)read_navigation_unsigned(subframe_bits, SV_ACCURACY, num_of_slices(SV_ACCURACY)); // (20.3.3.3.1.3)
|
||||||
i_SV_health = (int)read_navigation_unsigned(subframe_bits,SV_HEALTH,num_of_slices(SV_HEALTH));
|
i_SV_health = (int)read_navigation_unsigned(subframe_bits, SV_HEALTH, num_of_slices(SV_HEALTH));
|
||||||
|
|
||||||
b_L2_P_data_flag = read_navigation_bool(subframe_bits,L2_P_DATA_FLAG); //
|
b_L2_P_data_flag = read_navigation_bool(subframe_bits, L2_P_DATA_FLAG); //
|
||||||
i_code_on_L2 = (int)read_navigation_unsigned(subframe_bits,CA_OR_P_ON_L2,num_of_slices(CA_OR_P_ON_L2));
|
i_code_on_L2 = (int)read_navigation_unsigned(subframe_bits, CA_OR_P_ON_L2, num_of_slices(CA_OR_P_ON_L2));
|
||||||
d_TGD = (double)read_navigation_signed(subframe_bits,T_GD,num_of_slices(T_GD));
|
d_TGD = (double)read_navigation_signed(subframe_bits, T_GD, num_of_slices(T_GD));
|
||||||
d_TGD = d_TGD*T_GD_LSB;
|
d_TGD = d_TGD*T_GD_LSB;
|
||||||
d_IODC = (double)read_navigation_unsigned(subframe_bits,IODC,num_of_slices(IODC));
|
d_IODC = (double)read_navigation_unsigned(subframe_bits, IODC, num_of_slices(IODC));
|
||||||
d_Toc = (double)read_navigation_unsigned(subframe_bits,T_OC,num_of_slices(T_OC));
|
d_Toc = (double)read_navigation_unsigned(subframe_bits, T_OC, num_of_slices(T_OC));
|
||||||
d_Toc = d_Toc*T_OC_LSB;
|
d_Toc = d_Toc*T_OC_LSB;
|
||||||
d_A_f0 = (double)read_navigation_signed(subframe_bits,A_F0,num_of_slices(A_F0));
|
d_A_f0 = (double)read_navigation_signed(subframe_bits, A_F0, num_of_slices(A_F0));
|
||||||
d_A_f0 = d_A_f0*A_F0_LSB;
|
d_A_f0 = d_A_f0*A_F0_LSB;
|
||||||
d_A_f1 = (double)read_navigation_signed(subframe_bits,A_F1,num_of_slices(A_F1));
|
d_A_f1 = (double)read_navigation_signed(subframe_bits, A_F1, num_of_slices(A_F1));
|
||||||
d_A_f1 = d_A_f1*A_F1_LSB;
|
d_A_f1 = d_A_f1*A_F1_LSB;
|
||||||
d_A_f2 = (double)read_navigation_signed(subframe_bits,A_F2,num_of_slices(A_F2));
|
d_A_f2 = (double)read_navigation_signed(subframe_bits, A_F2, num_of_slices(A_F2));
|
||||||
d_A_f2 = d_A_f2*A_F2_LSB;
|
d_A_f2 = d_A_f2*A_F2_LSB;
|
||||||
|
|
||||||
|
|
||||||
@ -511,26 +511,26 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
||||||
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
||||||
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
||||||
d_IODE_SF2 = (double)read_navigation_unsigned(subframe_bits,IODE_SF2,num_of_slices(IODE_SF2));
|
d_IODE_SF2 = (double)read_navigation_unsigned(subframe_bits, IODE_SF2, num_of_slices(IODE_SF2));
|
||||||
d_Crs = (double)read_navigation_signed(subframe_bits,C_RS,num_of_slices(C_RS));
|
d_Crs = (double)read_navigation_signed(subframe_bits, C_RS, num_of_slices(C_RS));
|
||||||
d_Crs =d_Crs * C_RS_LSB;
|
d_Crs = d_Crs * C_RS_LSB;
|
||||||
d_Delta_n = (double)read_navigation_signed(subframe_bits,DELTA_N,num_of_slices(DELTA_N));
|
d_Delta_n = (double)read_navigation_signed(subframe_bits, DELTA_N, num_of_slices(DELTA_N));
|
||||||
d_Delta_n = d_Delta_n * DELTA_N_LSB;
|
d_Delta_n = d_Delta_n * DELTA_N_LSB;
|
||||||
d_M_0 = (double)read_navigation_signed(subframe_bits,M_0,num_of_slices(M_0));
|
d_M_0 = (double)read_navigation_signed(subframe_bits, M_0, num_of_slices(M_0));
|
||||||
d_M_0 = d_M_0 * M_0_LSB;
|
d_M_0 = d_M_0 * M_0_LSB;
|
||||||
d_Cuc = (double)read_navigation_signed(subframe_bits,C_UC,num_of_slices(C_UC));
|
d_Cuc = (double)read_navigation_signed(subframe_bits, C_UC, num_of_slices(C_UC));
|
||||||
d_Cuc = d_Cuc * C_UC_LSB;
|
d_Cuc = d_Cuc * C_UC_LSB;
|
||||||
d_e_eccentricity = (double)read_navigation_unsigned(subframe_bits,E,num_of_slices(E));
|
d_e_eccentricity = (double)read_navigation_unsigned(subframe_bits, E, num_of_slices(E));
|
||||||
d_e_eccentricity = d_e_eccentricity * E_LSB;
|
d_e_eccentricity = d_e_eccentricity * E_LSB;
|
||||||
d_Cus = (double)read_navigation_signed(subframe_bits,C_US,num_of_slices(C_US));
|
d_Cus = (double)read_navigation_signed(subframe_bits, C_US, num_of_slices(C_US));
|
||||||
d_Cus = d_Cus * C_US_LSB;
|
d_Cus = d_Cus * C_US_LSB;
|
||||||
d_sqrt_A = (double)read_navigation_unsigned(subframe_bits,SQRT_A,num_of_slices(SQRT_A));
|
d_sqrt_A = (double)read_navigation_unsigned(subframe_bits, SQRT_A, num_of_slices(SQRT_A));
|
||||||
d_sqrt_A = d_sqrt_A * SQRT_A_LSB;
|
d_sqrt_A = d_sqrt_A * SQRT_A_LSB;
|
||||||
d_Toe = (double)read_navigation_unsigned(subframe_bits,T_OE,num_of_slices(T_OE));
|
d_Toe = (double)read_navigation_unsigned(subframe_bits, T_OE, num_of_slices(T_OE));
|
||||||
d_Toe = d_Toe * T_OE_LSB;
|
d_Toe = d_Toe * T_OE_LSB;
|
||||||
b_fit_interval_flag = read_navigation_bool(subframe_bits, FIT_INTERVAL_FLAG);
|
b_fit_interval_flag = read_navigation_bool(subframe_bits, FIT_INTERVAL_FLAG);
|
||||||
|
|
||||||
i_AODO = (int)read_navigation_unsigned(subframe_bits,AODO,num_of_slices(AODO));
|
i_AODO = (int)read_navigation_unsigned(subframe_bits, AODO, num_of_slices(AODO));
|
||||||
i_AODO = i_AODO * AODO_LSB;
|
i_AODO = i_AODO * AODO_LSB;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@ -551,22 +551,22 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
||||||
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
||||||
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
||||||
d_Cic = (double)read_navigation_signed(subframe_bits,C_IC,num_of_slices(C_IC));
|
d_Cic = (double)read_navigation_signed(subframe_bits, C_IC, num_of_slices(C_IC));
|
||||||
d_Cic = d_Cic * C_IC_LSB;
|
d_Cic = d_Cic * C_IC_LSB;
|
||||||
d_OMEGA0 = (double)read_navigation_signed(subframe_bits,OMEGA_0,num_of_slices(OMEGA_0));
|
d_OMEGA0 = (double)read_navigation_signed(subframe_bits, OMEGA_0, num_of_slices(OMEGA_0));
|
||||||
d_OMEGA0 = d_OMEGA0 * OMEGA_0_LSB;
|
d_OMEGA0 = d_OMEGA0 * OMEGA_0_LSB;
|
||||||
d_Cis = (double)read_navigation_signed(subframe_bits,C_IS,num_of_slices(C_IS));
|
d_Cis = (double)read_navigation_signed(subframe_bits, C_IS, num_of_slices(C_IS));
|
||||||
d_Cis = d_Cis * C_IS_LSB;
|
d_Cis = d_Cis * C_IS_LSB;
|
||||||
d_i_0 = (double)read_navigation_signed(subframe_bits,I_0,num_of_slices(I_0));
|
d_i_0 = (double)read_navigation_signed(subframe_bits, I_0, num_of_slices(I_0));
|
||||||
d_i_0 = d_i_0 * I_0_LSB;
|
d_i_0 = d_i_0 * I_0_LSB;
|
||||||
d_Crc = (double)read_navigation_signed(subframe_bits,C_RC,num_of_slices(C_RC));
|
d_Crc = (double)read_navigation_signed(subframe_bits, C_RC, num_of_slices(C_RC));
|
||||||
d_Crc = d_Crc * C_RC_LSB;
|
d_Crc = d_Crc * C_RC_LSB;
|
||||||
d_OMEGA = (double)read_navigation_signed(subframe_bits,OMEGA,num_of_slices(OMEGA));
|
d_OMEGA = (double)read_navigation_signed(subframe_bits, OMEGA, num_of_slices(OMEGA));
|
||||||
d_OMEGA = d_OMEGA * OMEGA_LSB;
|
d_OMEGA = d_OMEGA * OMEGA_LSB;
|
||||||
d_OMEGA_DOT = (double)read_navigation_signed(subframe_bits,OMEGA_DOT,num_of_slices(OMEGA_DOT));
|
d_OMEGA_DOT = (double)read_navigation_signed(subframe_bits, OMEGA_DOT, num_of_slices(OMEGA_DOT));
|
||||||
d_OMEGA_DOT = d_OMEGA_DOT * OMEGA_DOT_LSB;
|
d_OMEGA_DOT = d_OMEGA_DOT * OMEGA_DOT_LSB;
|
||||||
d_IODE_SF3 = (double)read_navigation_unsigned(subframe_bits,IODE_SF3,num_of_slices(IODE_SF3));
|
d_IODE_SF3 = (double)read_navigation_unsigned(subframe_bits, IODE_SF3, num_of_slices(IODE_SF3));
|
||||||
d_IDOT = (double)read_navigation_signed(subframe_bits,I_DOT,num_of_slices(I_DOT));
|
d_IDOT = (double)read_navigation_signed(subframe_bits, I_DOT, num_of_slices(I_DOT));
|
||||||
d_IDOT = d_IDOT*I_DOT_LSB;
|
d_IDOT = d_IDOT*I_DOT_LSB;
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@ -587,8 +587,8 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
||||||
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
||||||
|
|
||||||
SV_data_ID = (int)read_navigation_unsigned(subframe_bits,SV_DATA_ID,num_of_slices(SV_DATA_ID));
|
SV_data_ID = (int)read_navigation_unsigned(subframe_bits, SV_DATA_ID, num_of_slices(SV_DATA_ID));
|
||||||
SV_page = (int)read_navigation_unsigned(subframe_bits,SV_PAGE,num_of_slices(SV_PAGE));
|
SV_page = (int)read_navigation_unsigned(subframe_bits, SV_PAGE, num_of_slices(SV_PAGE));
|
||||||
|
|
||||||
if (SV_page == 13)
|
if (SV_page == 13)
|
||||||
{
|
{
|
||||||
@ -598,51 +598,47 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
if (SV_page == 18)
|
if (SV_page == 18)
|
||||||
{
|
{
|
||||||
// Page 18 - Ionospheric and UTC data
|
// Page 18 - Ionospheric and UTC data
|
||||||
|
d_alpha0 = (double)read_navigation_signed(subframe_bits, ALPHA_0, num_of_slices(ALPHA_0));
|
||||||
d_alpha0 = (double)read_navigation_signed(subframe_bits, ALPHA_0,num_of_slices(ALPHA_0));
|
|
||||||
d_alpha0 = d_alpha0 * ALPHA_0_LSB;
|
d_alpha0 = d_alpha0 * ALPHA_0_LSB;
|
||||||
d_alpha1 = (double)read_navigation_signed(subframe_bits, ALPHA_1,num_of_slices(ALPHA_1));
|
d_alpha1 = (double)read_navigation_signed(subframe_bits, ALPHA_1, num_of_slices(ALPHA_1));
|
||||||
d_alpha1 = d_alpha1 * ALPHA_1_LSB;
|
d_alpha1 = d_alpha1 * ALPHA_1_LSB;
|
||||||
d_alpha2 = (double)read_navigation_signed(subframe_bits, ALPHA_2,num_of_slices(ALPHA_2));
|
d_alpha2 = (double)read_navigation_signed(subframe_bits, ALPHA_2, num_of_slices(ALPHA_2));
|
||||||
d_alpha2 = d_alpha2 * ALPHA_2_LSB;
|
d_alpha2 = d_alpha2 * ALPHA_2_LSB;
|
||||||
d_alpha3 = (double)read_navigation_signed(subframe_bits, ALPHA_3,num_of_slices(ALPHA_3));
|
d_alpha3 = (double)read_navigation_signed(subframe_bits, ALPHA_3, num_of_slices(ALPHA_3));
|
||||||
d_alpha3 = d_alpha3 * ALPHA_3_LSB;
|
d_alpha3 = d_alpha3 * ALPHA_3_LSB;
|
||||||
d_beta0 = (double)read_navigation_signed(subframe_bits, BETA_0,num_of_slices(BETA_0));
|
d_beta0 = (double)read_navigation_signed(subframe_bits, BETA_0, num_of_slices(BETA_0));
|
||||||
d_beta0 = d_beta0 * BETA_0_LSB;
|
d_beta0 = d_beta0 * BETA_0_LSB;
|
||||||
d_beta1 = (double)read_navigation_signed(subframe_bits, BETA_1,num_of_slices(BETA_1));
|
d_beta1 = (double)read_navigation_signed(subframe_bits, BETA_1, num_of_slices(BETA_1));
|
||||||
d_beta1 = d_beta1 * BETA_1_LSB;
|
d_beta1 = d_beta1 * BETA_1_LSB;
|
||||||
d_beta2 = (double)read_navigation_signed(subframe_bits, BETA_2,num_of_slices(BETA_2));
|
d_beta2 = (double)read_navigation_signed(subframe_bits, BETA_2, num_of_slices(BETA_2));
|
||||||
d_beta2 = d_beta2 * BETA_2_LSB;
|
d_beta2 = d_beta2 * BETA_2_LSB;
|
||||||
d_beta3 = (double)read_navigation_signed(subframe_bits, BETA_3,num_of_slices(BETA_3));
|
d_beta3 = (double)read_navigation_signed(subframe_bits, BETA_3, num_of_slices(BETA_3));
|
||||||
d_beta3 = d_beta3 * BETA_3_LSB;
|
d_beta3 = d_beta3 * BETA_3_LSB;
|
||||||
d_A1 = (double)read_navigation_signed(subframe_bits, A_1,num_of_slices(A_1));
|
d_A1 = (double)read_navigation_signed(subframe_bits, A_1, num_of_slices(A_1));
|
||||||
d_A1 = d_A1 * A_1_LSB;
|
d_A1 = d_A1 * A_1_LSB;
|
||||||
d_A0 = (double)read_navigation_signed(subframe_bits, A_0,num_of_slices(A_0));
|
d_A0 = (double)read_navigation_signed(subframe_bits, A_0, num_of_slices(A_0));
|
||||||
d_A0 = d_A0 * A_0_LSB;
|
d_A0 = d_A0 * A_0_LSB;
|
||||||
d_t_OT = (double)read_navigation_unsigned(subframe_bits, T_OT,num_of_slices(T_OT));
|
d_t_OT = (double)read_navigation_unsigned(subframe_bits, T_OT,num_of_slices(T_OT));
|
||||||
d_t_OT = d_t_OT * T_OT_LSB;
|
d_t_OT = d_t_OT * T_OT_LSB;
|
||||||
i_WN_T = (int)read_navigation_unsigned(subframe_bits, WN_T,num_of_slices(WN_T));
|
i_WN_T = (int)read_navigation_unsigned(subframe_bits, WN_T, num_of_slices(WN_T));
|
||||||
d_DeltaT_LS = (double)read_navigation_signed(subframe_bits, DELTAT_LS,num_of_slices(DELTAT_LS));
|
d_DeltaT_LS = (double)read_navigation_signed(subframe_bits, DELTAT_LS, num_of_slices(DELTAT_LS));
|
||||||
i_WN_LSF = (int)read_navigation_unsigned(subframe_bits, WN_LSF,num_of_slices(WN_LSF));
|
i_WN_LSF = (int)read_navigation_unsigned(subframe_bits, WN_LSF, num_of_slices(WN_LSF));
|
||||||
i_DN = (int)read_navigation_unsigned(subframe_bits, DN,num_of_slices(DN));; // Right-justified ?
|
i_DN = (int)read_navigation_unsigned(subframe_bits, DN, num_of_slices(DN));; // Right-justified ?
|
||||||
d_DeltaT_LSF = (double)read_navigation_signed(subframe_bits, DELTAT_LSF,num_of_slices(DELTAT_LSF));
|
d_DeltaT_LSF = (double)read_navigation_signed(subframe_bits, DELTAT_LSF, num_of_slices(DELTAT_LSF));
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
if (SV_page == 25)
|
if (SV_page == 25)
|
||||||
{
|
{
|
||||||
// Page 25 Anti-Spoofing, SV config and almanac health (PRN: 25-32)
|
// Page 25 Anti-Spoofing, SV config and almanac health (PRN: 25-32)
|
||||||
//! \TODO Read Anti-Spoofing, SV config
|
//! \TODO Read Anti-Spoofing, SV config
|
||||||
almanacHealth[25] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV25,num_of_slices(HEALTH_SV25));
|
almanacHealth[25] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV25, num_of_slices(HEALTH_SV25));
|
||||||
almanacHealth[26] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV26,num_of_slices(HEALTH_SV26));
|
almanacHealth[26] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV26, num_of_slices(HEALTH_SV26));
|
||||||
almanacHealth[27] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV27,num_of_slices(HEALTH_SV27));
|
almanacHealth[27] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV27, num_of_slices(HEALTH_SV27));
|
||||||
almanacHealth[28] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV28,num_of_slices(HEALTH_SV28));
|
almanacHealth[28] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV28, num_of_slices(HEALTH_SV28));
|
||||||
almanacHealth[29] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV29,num_of_slices(HEALTH_SV29));
|
almanacHealth[29] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV29, num_of_slices(HEALTH_SV29));
|
||||||
almanacHealth[30] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV30,num_of_slices(HEALTH_SV30));
|
almanacHealth[30] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV30, num_of_slices(HEALTH_SV30));
|
||||||
almanacHealth[31] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV31,num_of_slices(HEALTH_SV31));
|
almanacHealth[31] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV31, num_of_slices(HEALTH_SV31));
|
||||||
almanacHealth[32] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV32,num_of_slices(HEALTH_SV32));
|
almanacHealth[32] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV32, num_of_slices(HEALTH_SV32));
|
||||||
|
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
break;
|
break;
|
||||||
@ -651,8 +647,8 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
b_integrity_status_flag = read_navigation_bool(subframe_bits, INTEGRITY_STATUS_FLAG);
|
||||||
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
b_alert_flag = read_navigation_bool(subframe_bits, ALERT_FLAG);
|
||||||
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
b_antispoofing_flag = read_navigation_bool(subframe_bits, ANTI_SPOOFING_FLAG);
|
||||||
SV_data_ID = (int)read_navigation_unsigned(subframe_bits,SV_DATA_ID,num_of_slices(SV_DATA_ID));
|
SV_data_ID = (int)read_navigation_unsigned(subframe_bits, SV_DATA_ID, num_of_slices(SV_DATA_ID));
|
||||||
SV_page = (int)read_navigation_unsigned(subframe_bits,SV_PAGE,num_of_slices(SV_PAGE));
|
SV_page = (int)read_navigation_unsigned(subframe_bits, SV_PAGE, num_of_slices(SV_PAGE));
|
||||||
|
|
||||||
if (SV_page < 25)
|
if (SV_page < 25)
|
||||||
{
|
{
|
||||||
@ -664,30 +660,30 @@ int gps_navigation_message::subframe_decoder(char *subframe)
|
|||||||
d_Toa = d_Toa * T_OA_LSB;
|
d_Toa = d_Toa * T_OA_LSB;
|
||||||
i_WN_A = (int)read_navigation_unsigned(subframe_bits,WN_A,num_of_slices(WN_A));
|
i_WN_A = (int)read_navigation_unsigned(subframe_bits,WN_A,num_of_slices(WN_A));
|
||||||
|
|
||||||
almanacHealth[1] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV1,num_of_slices(HEALTH_SV1));
|
almanacHealth[1] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV1, num_of_slices(HEALTH_SV1));
|
||||||
almanacHealth[2] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV2,num_of_slices(HEALTH_SV2));
|
almanacHealth[2] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV2, num_of_slices(HEALTH_SV2));
|
||||||
almanacHealth[3] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV3,num_of_slices(HEALTH_SV3));
|
almanacHealth[3] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV3, num_of_slices(HEALTH_SV3));
|
||||||
almanacHealth[4] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV4,num_of_slices(HEALTH_SV4));
|
almanacHealth[4] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV4, num_of_slices(HEALTH_SV4));
|
||||||
almanacHealth[5] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV5,num_of_slices(HEALTH_SV5));
|
almanacHealth[5] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV5, num_of_slices(HEALTH_SV5));
|
||||||
almanacHealth[6] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV6,num_of_slices(HEALTH_SV6));
|
almanacHealth[6] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV6, num_of_slices(HEALTH_SV6));
|
||||||
almanacHealth[7] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV7,num_of_slices(HEALTH_SV7));
|
almanacHealth[7] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV7, num_of_slices(HEALTH_SV7));
|
||||||
almanacHealth[8] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV8,num_of_slices(HEALTH_SV8));
|
almanacHealth[8] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV8, num_of_slices(HEALTH_SV8));
|
||||||
almanacHealth[9] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV9,num_of_slices(HEALTH_SV9));
|
almanacHealth[9] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV9, num_of_slices(HEALTH_SV9));
|
||||||
almanacHealth[10] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV10,num_of_slices(HEALTH_SV10));
|
almanacHealth[10] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV10, num_of_slices(HEALTH_SV10));
|
||||||
almanacHealth[11] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV11,num_of_slices(HEALTH_SV11));
|
almanacHealth[11] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV11, num_of_slices(HEALTH_SV11));
|
||||||
almanacHealth[12] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV12,num_of_slices(HEALTH_SV12));
|
almanacHealth[12] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV12, num_of_slices(HEALTH_SV12));
|
||||||
almanacHealth[13] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV13,num_of_slices(HEALTH_SV13));
|
almanacHealth[13] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV13, num_of_slices(HEALTH_SV13));
|
||||||
almanacHealth[14] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV14,num_of_slices(HEALTH_SV14));
|
almanacHealth[14] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV14, num_of_slices(HEALTH_SV14));
|
||||||
almanacHealth[15] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV15,num_of_slices(HEALTH_SV15));
|
almanacHealth[15] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV15, num_of_slices(HEALTH_SV15));
|
||||||
almanacHealth[16] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV16,num_of_slices(HEALTH_SV16));
|
almanacHealth[16] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV16, num_of_slices(HEALTH_SV16));
|
||||||
almanacHealth[17] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV17,num_of_slices(HEALTH_SV17));
|
almanacHealth[17] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV17, num_of_slices(HEALTH_SV17));
|
||||||
almanacHealth[18] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV18,num_of_slices(HEALTH_SV18));
|
almanacHealth[18] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV18, num_of_slices(HEALTH_SV18));
|
||||||
almanacHealth[19] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV19,num_of_slices(HEALTH_SV19));
|
almanacHealth[19] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV19, num_of_slices(HEALTH_SV19));
|
||||||
almanacHealth[20] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV20,num_of_slices(HEALTH_SV20));
|
almanacHealth[20] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV20, num_of_slices(HEALTH_SV20));
|
||||||
almanacHealth[21] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV21,num_of_slices(HEALTH_SV21));
|
almanacHealth[21] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV21, num_of_slices(HEALTH_SV21));
|
||||||
almanacHealth[22] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV22,num_of_slices(HEALTH_SV22));
|
almanacHealth[22] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV22, num_of_slices(HEALTH_SV22));
|
||||||
almanacHealth[23] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV23,num_of_slices(HEALTH_SV23));
|
almanacHealth[23] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV23, num_of_slices(HEALTH_SV23));
|
||||||
almanacHealth[24] = (int)read_navigation_unsigned(subframe_bits,HEALTH_SV24,num_of_slices(HEALTH_SV24));
|
almanacHealth[24] = (int)read_navigation_unsigned(subframe_bits, HEALTH_SV24, num_of_slices(HEALTH_SV24));
|
||||||
|
|
||||||
}
|
}
|
||||||
break;
|
break;
|
||||||
@ -706,7 +702,7 @@ double gps_navigation_message::utc_time(double gpstime_corrected)
|
|||||||
double Delta_t_UTC = d_DeltaT_LS + d_A0 + d_A1 * (gpstime_corrected - d_t_OT + 604800 *(double)(i_GPS_week - i_WN_T));
|
double Delta_t_UTC = d_DeltaT_LS + d_A0 + d_A1 * (gpstime_corrected - d_t_OT + 604800 *(double)(i_GPS_week - i_WN_T));
|
||||||
|
|
||||||
// Determine if the effectivity time of the leap second event is in the past
|
// Determine if the effectivity time of the leap second event is in the past
|
||||||
int weeksToLeapSecondEvent = i_WN_LSF-i_GPS_week;
|
int weeksToLeapSecondEvent = i_WN_LSF - i_GPS_week;
|
||||||
|
|
||||||
if ((weeksToLeapSecondEvent) >= 0) // is not in the past
|
if ((weeksToLeapSecondEvent) >= 0) // is not in the past
|
||||||
{
|
{
|
||||||
@ -715,13 +711,13 @@ double gps_navigation_message::utc_time(double gpstime_corrected)
|
|||||||
|
|
||||||
if (weeksToLeapSecondEvent > 0)
|
if (weeksToLeapSecondEvent > 0)
|
||||||
{
|
{
|
||||||
t_utc_daytime=fmod(gpstime_corrected-Delta_t_UTC,86400);
|
t_utc_daytime = fmod(gpstime_corrected - Delta_t_UTC, 86400);
|
||||||
}
|
}
|
||||||
else //we are in the same week than the leap second event
|
else //we are in the same week than the leap second event
|
||||||
{
|
{
|
||||||
|
|
||||||
|
|
||||||
if (abs(gpstime_corrected-secondOfLeapSecondEvent) > 21600)
|
if (abs(gpstime_corrected - secondOfLeapSecondEvent) > 21600)
|
||||||
{
|
{
|
||||||
/* 20.3.3.5.2.4a
|
/* 20.3.3.5.2.4a
|
||||||
* Whenever the effectivity time indicated by the WN_LSF and the DN values
|
* Whenever the effectivity time indicated by the WN_LSF and the DN values
|
||||||
@ -731,7 +727,7 @@ double gps_navigation_message::utc_time(double gpstime_corrected)
|
|||||||
* the UTC/GPS-time relationship is given by
|
* the UTC/GPS-time relationship is given by
|
||||||
*/
|
*/
|
||||||
|
|
||||||
t_utc_daytime=fmod(gpstime_corrected-Delta_t_UTC,86400);
|
t_utc_daytime = fmod(gpstime_corrected - Delta_t_UTC, 86400);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -742,15 +738,15 @@ double gps_navigation_message::utc_time(double gpstime_corrected)
|
|||||||
* transition is provided by the following expression for UTC:
|
* transition is provided by the following expression for UTC:
|
||||||
*/
|
*/
|
||||||
|
|
||||||
int W = fmod(gpstime_corrected-Delta_t_UTC-43200,86400)+43200;
|
int W = fmod(gpstime_corrected - Delta_t_UTC - 43200, 86400) + 43200;
|
||||||
t_utc_daytime =fmod(W,86400+d_DeltaT_LSF-d_DeltaT_LS);
|
t_utc_daytime = fmod(W, 86400 + d_DeltaT_LSF - d_DeltaT_LS);
|
||||||
|
|
||||||
//implement something to handle a leap second event!
|
//implement something to handle a leap second event!
|
||||||
}
|
}
|
||||||
if ( (gpstime_corrected - secondOfLeapSecondEvent ) > 21600)
|
if ( (gpstime_corrected - secondOfLeapSecondEvent) > 21600)
|
||||||
{
|
{
|
||||||
Delta_t_UTC = d_DeltaT_LSF + d_A0 + d_A1 * (gpstime_corrected - d_t_OT + 604800 *(double)(i_GPS_week - i_WN_T));
|
Delta_t_UTC = d_DeltaT_LSF + d_A0 + d_A1 * (gpstime_corrected - d_t_OT + 604800*(double)(i_GPS_week - i_WN_T));
|
||||||
t_utc_daytime=fmod(gpstime_corrected-Delta_t_UTC,86400);
|
t_utc_daytime = fmod(gpstime_corrected - Delta_t_UTC, 86400);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -762,13 +758,12 @@ double gps_navigation_message::utc_time(double gpstime_corrected)
|
|||||||
* and the userÕs current time does not fall in the time span as given above
|
* and the userÕs current time does not fall in the time span as given above
|
||||||
* in 20.3.3.5.2.4b,*/
|
* in 20.3.3.5.2.4b,*/
|
||||||
Delta_t_UTC = d_DeltaT_LSF + d_A0 + d_A1 * (gpstime_corrected - d_t_OT + 604800 *(double)(i_GPS_week - i_WN_T));
|
Delta_t_UTC = d_DeltaT_LSF + d_A0 + d_A1 * (gpstime_corrected - d_t_OT + 604800 *(double)(i_GPS_week - i_WN_T));
|
||||||
t_utc_daytime=fmod(gpstime_corrected-Delta_t_UTC,86400);
|
t_utc_daytime = fmod(gpstime_corrected - Delta_t_UTC, 86400);
|
||||||
}
|
}
|
||||||
|
|
||||||
double secondsOfWeekBeforeToday= 43200*floor(gpstime_corrected/43200);
|
double secondsOfWeekBeforeToday= 43200 * floor(gpstime_corrected / 43200);
|
||||||
t_utc = secondsOfWeekBeforeToday+t_utc_daytime;
|
t_utc = secondsOfWeekBeforeToday + t_utc_daytime;
|
||||||
return t_utc;
|
return t_utc;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -785,7 +780,7 @@ bool gps_navigation_message::satellite_validation()
|
|||||||
// and check if the data have been filled (!=0)
|
// and check if the data have been filled (!=0)
|
||||||
if (d_IODE_SF2 == d_IODE_SF3 and d_IODC == d_IODE_SF2 and d_IODC!=-1)
|
if (d_IODE_SF2 == d_IODE_SF3 and d_IODC == d_IODE_SF2 and d_IODC!=-1)
|
||||||
{
|
{
|
||||||
flag_data_valid=true;
|
flag_data_valid = true;
|
||||||
}
|
}
|
||||||
return flag_data_valid;
|
return flag_data_valid;
|
||||||
}
|
}
|
||||||
|
@ -180,9 +180,9 @@ public:
|
|||||||
double d_DeltaT_LSF; //!< Scheduled future or recent past (relative to NAV message upload) value of the delta time due to leap seconds [s]
|
double d_DeltaT_LSF; //!< Scheduled future or recent past (relative to NAV message upload) value of the delta time due to leap seconds [s]
|
||||||
|
|
||||||
// Satellite velocity
|
// Satellite velocity
|
||||||
double d_satvel_X;
|
double d_satvel_X; //!< Earth-fixed velocity coordinate x of the satellite [m]
|
||||||
double d_satvel_Y;
|
double d_satvel_Y; //!< Earth-fixed velocity coordinate y of the satellite [m]
|
||||||
double d_satvel_Z;
|
double d_satvel_Z; //!< Earth-fixed velocity coordinate z of the satellite [m]
|
||||||
|
|
||||||
// public functions
|
// public functions
|
||||||
void reset();
|
void reset();
|
||||||
|
Loading…
Reference in New Issue
Block a user