29#define PI 3.1415926535897932
30#define D2R (PI / 180.0)
31#define R2D (180.0 / PI)
36#define STD_ZTD_DIST 1E-4
37#define STD_GRAD_DIST 1E-5
38#define STD_VTEC_DIST 1E-3
40#define SQR(x) ((x) * (x))
41#define MAX(x, y) ((x) > (y) ? (x) : (y))
42#define GN(gp) (gp == 1 ? 64 : 16)
59 for (i = 0; i < stat->
nst; i++) {
80 double tow = 0, ecef[3] = {0}, azel[2] = {0}, ion = 0, ztd = {0}, grad[2] = {0}, std[2] = {0};
81 char sat[64] =
"", sys;
82 int prn, week = 0, qflag = 0, rcv = 0,
satno = 0;
88 if (sscanf(buff,
"$POS,%d,%lf,%d,%lf,%lf,%lf", &week, &tow, &qflag, ecef, ecef + 1, ecef + 2) >= 6) {
94 else if (sscanf(buff,
"$ION,%d,%lf,%d,%c%d,%lf,%lf,%lf,%lf", &week, &tow, &qflag, &sys, &prn, azel, azel + 1, &ion,
96 sprintf(sat,
"%c%02d", sys, prn);
108 else if (sscanf(buff,
"$TROP,%d,%lf,%d,%d,%lf,%lf", &week, &tow, &qflag, &rcv, &ztd, std) >= 6) {
117 else if (sscanf(buff,
"$TRPG,%d,%lf,%d,%d,%lf,%lf,%lf,%lf", &week, &tow, &qflag, &rcv, grad, grad + 1, std,
142 trace(NULL, 4,
"input_stat: data=%c,%d\n", data, *nbyte);
153 buff[(*nbyte)++] = data;
173 trace(NULL, 4,
"input_statf:\n");
175 for (i = 0; i < 4096; i++) {
176 if ((data = fgetc(fp)) == EOF) {
179 if ((ret =
input_stat(sstat, (
char)data, buff, nbyte))) {
191extern double posdist(
const double* ecef1,
const double* ecef2) {
194 for (i = 0; i < 3; i++) {
195 r[i] = ecef1[i] - ecef2[i];
200static int get_site(
const stat_t* stat,
const double* llh,
int iontrp,
int* siteno,
double maxdist,
double* dist,
215 for (i = 0; i < nsta; i++) {
225 trace(NULL, 4,
"get_site:targetpos llh=%f,%f,%f site pos llh=%f,%f,%f dist=%f\n", llh[0] *
R2D, llh[1] *
R2D,
226 llh[2], gllh[n][0] *
R2D, gllh[n][1] *
R2D, gllh[n][2], d);
227 if ((dist[n] =
MAX(d / 1E3, 0.1)) > maxdist) {
240 if (tt < -600.0 || tt > 5.) {
244 for (i = 0; i < 3; i++) {
245 trp[i] = trpd->
trp[i];
247 trace(NULL, 4,
"trpd %s %d ion=%f std=%f\n",
time_str(time, 0), i + 1, trp[i], std[i]);
256 for (i = 0; i <
MAXSAT; i++) {
264 ion[i] = iond[i].
ion;
265 std[i] = iond[i].
std;
266 el[i] = iond[i].
azel[1];
267 trace(NULL, 4,
"iond %s sat=%d ion=%f std=%f\n",
time_str(time, 0), i + 1, ion[i], std[i]);
284 const double azel[] = {0.0,
PI / 2.0};
285 double trp_s[3], std_s[3];
289 for (i = 0; i < 3; i++) {
290 trp[i] = std[i] = 0.0;
297 for (i = 0; i < n; i++) {
304 trp_s[0] -=
tropmodel(time, llh_s[i], azel, 0.0);
306 for (j = 0; j < 3; j++) {
308 trp[j] += trp_s[j] / dist[i];
309 wgt[j] += 1.0 / dist[i];
317 for (i = 0; i < 3; i++) {
319 std[i] = sqrt(1.0 / cof[i]);
320 trace(NULL, 3,
"interpolation trp %s %d trp=%f std=%f lat=%.2f lat=%.2f n=%d\n",
time_str(time, 0), i + 1,
321 trp[i], std[i], llh[0] *
R2D, llh[1] *
R2D, n);
324 trp[0] +=
tropmodel(time, llh, azel, 0.0);
343 double* ion,
double* std,
double maxres,
int* nrej,
int* ncnt) {
349 for (i = 0; i <
MAXSAT; i++) {
357 for (i = 0; i < n; i++) {
358 for (j = 0; j <
MAXSAT; j++) {
359 ion_s[i][j] = std_s[j] = el_s[j] = 0.0;
367 for (j = 0; j <
MAXSAT; j++) {
373 if (ion_s[i][j] == 0.0 || eltmp <= 0.0) {
377 ion[j] += ion_s[i][j] / dist[i];
378 wgt[j] += 1.0 / dist[i];
382 for (i = 0; i <
MAXSAT; i++) {
383 if (wgt[i] == 0.0 || (cof[i] <= 0.0)) {
387 std[i] = sqrt(1.0 / cof[i]);
388 trace(NULL, 3,
"interpolation ion %s sat=%d ion=%f std=%f lat=%.2f lat=%.2f n=%d\n",
time_str(time, 0), i + 1,
389 ion[i], std[i], llh[0] *
R2D, llh[1] *
R2D, n);
392 for (i = 0; i < n; i++) {
393 for (j = 0; j <
MAXSAT; j++) {
394 if (ion_s[i][j] == 0.0 || ion[j] == 0.0) {
397 res = ion[j] - ion_s[i][j];
399 if (fabs(res) > maxres) {
420 if (
rtcm->lclblk->tnum == 0 &&
rtcm->lclblk->inum == 0) {
425 for (i = 0; i <
rtcm->lclblk->tnum; i++) {
426 for (j = 0; j <
rtcm->lclblk->tblkinf[i].n; j++) {
428 gp =
rtcm->lclblk->tblkinf[i].gp[j];
432 for (k = 0; k < stat->
nst; k++) {
438 if (k >= stat->
nst) {
446 for (i = 0; i <
rtcm->lclblk->inum; i++) {
447 for (j = 0; j <
rtcm->lclblk->iblkinf[i].n; j++) {
448 gp =
rtcm->lclblk->iblkinf[i].gp[j];
450 gp =
rtcm->lclblk->iblkinf[i].gp[j];
454 for (k = 0; k < stat->
nsi; k++) {
460 if (k >= stat->
nsi) {
double tropmodel(gtime_t time, const double *pos, const double *azel, double humi)
Compute tropospheric delay by standard atmosphere and Saastamoinen.
MRTKLIB Atmosphere Module — Ionospheric and tropospheric models.
void pos2ecef(const double *pos, double *r)
Transform geodetic position to ECEF position.
void ecef2pos(const double *r, double *pos)
Transform ECEF position to geodetic position.
MRTKLIB Coordinates Module — Coordinate transformations and geometry.
double posdist(const double *ecef1, const double *ecef2)
Calculate the Euclidean distance between two ECEF positions.
int corr_trop_distwgt(const stat_t *stat, gtime_t time, const double *llh, double maxdist, double *trp, double *std)
Calculate tropospheric correction using weighted interpolation by distance.
int get_trop_sta(gtime_t time, const trp_t *trpd, double *trp, double *std)
Get tropospheric correction for a point.
int get_iono_sta(gtime_t time, const ion_t *iond, double *ion, double *std, double *el)
Get ionospheric correction for a point.
int input_statf(sstat_t *sstat, FILE *fp, char *buff, int *nbyte)
Fetch next stat message and input a message from file.
int satid2no(const char *id)
int getstano(stat_t *stat, const char *pntname)
Search for a point by name or add a new point if not found.
char * time_str(gtime_t t, int n)
static int decode_stat(sstat_t *sstat, char *buff, int *nbyte)
int corr_iono_distwgt(const stat_t *stat, gtime_t time, const double *llh, const double *el, double maxdist, double *ion, double *std, double maxres, int *nrej, int *ncnt)
Calculate ionospheric correction using weighted interpolation by distance.
static int get_site(const stat_t *stat, const double *llh, int iontrp, int *siteno, double maxdist, double *dist, double gllh[][3])
int block2stat(rtcm_t *rtcm, stat_t *stat)
Convert RTCM3 block data to station statistics.
int input_stat(sstat_t *sstat, const char data, char *buff, int *nbyte)
Stack stat message and synchronize frame with stat preamble.
MRTKLIB MADOCA Local Correction Module — local correction common functions and constants.
double norm(const double *a, int n)
Euclidean norm of vector.
MRTKLIB Matrix Module — Matrix/vector operations and estimation.
int satno(int sys, int prn)
Convert satellite system+prn/slot number to satellite number.
gtime_t gpst2time(int week, double sec)
Convert GPS week/tow to gtime_t.
double timediff(gtime_t t1, gtime_t t2)
Compute time difference (t1 - t2).
void trace(mrtk_ctx_t *ctx, int level, const char *format,...)
Output trace message.
MRTKLIB Trace Module — debug trace and logging functions.
GNSS time representation.
RTCM control struct type.