diff options
author | Lorry Tar Creator <lorry-tar-importer@baserock.org> | 2015-04-07 08:29:34 +0000 |
---|---|---|
committer | <> | 2015-04-13 18:52:43 +0000 |
commit | b2ccf8dd31d1457ae9f0ae270054117179220370 (patch) | |
tree | 4ccd4a16d5e9ef5869630ba624e822665a6e248c /ntpd/refclock_parse.c | |
parent | bdab5265fcbf3f472545073a23f8999749a9f2b9 (diff) | |
download | ntp-master.tar.gz |
Imported from /home/lorry/working-area/delta_ntp/ntp-4.2.8p2.tar.gz.HEADntp-4.2.8p2master
Diffstat (limited to 'ntpd/refclock_parse.c')
-rw-r--r-- | ntpd/refclock_parse.c | 1226 |
1 files changed, 618 insertions, 608 deletions
diff --git a/ntpd/refclock_parse.c b/ntpd/refclock_parse.c index 052ec3a..195ec39 100644 --- a/ntpd/refclock_parse.c +++ b/ntpd/refclock_parse.c @@ -16,7 +16,7 @@ * SunOS 4.x and SunOS5.x. * * Copyright (c) 1995-2009 by Frank Kardel <kardel <AT> ntp.org> - * Copyright (c) 1989-1994 by Frank Kardel, Friedrich-Alexander Universität Erlangen-Nürnberg, Germany + * Copyright (c) 1989-1994 by Frank Kardel, Friedrich-Alexander Universitaet Erlangen-Nuernberg, Germany * * Redistribution and use in source and binary forms, with or without * modification, are permitted provided that the following conditions @@ -54,36 +54,36 @@ /* * This driver currently provides the support for - * - Meinberg receiver DCF77 PZF 535 (TCXO version) (DCF) - * - Meinberg receiver DCF77 PZF 535 (OCXO version) (DCF) - * - Meinberg receiver DCF77 PZF 509 (DCF) + * - Meinberg receiver DCF77 PZF535 (TCXO version) (DCF) + * - Meinberg receiver DCF77 PZF535 (OCXO version) (DCF) + * - Meinberg receiver DCF77 PZF509 (DCF) * - Meinberg receiver DCF77 AM receivers (e.g. C51) (DCF) * - IGEL CLOCK (DCF) * - ELV DCF7000 (DCF) * - Schmid clock (DCF) * - Conrad DCF77 receiver module (DCF) * - FAU DCF77 NTP receiver (TimeBrick) (DCF) - * - WHARTON 400A Series clock (DCF) + * - WHARTON 400A Series clock (DCF) * - * - Meinberg GPS166/GPS167 (GPS) + * - Meinberg GPS receivers (GPS) * - Trimble (TSIP and TAIP protocol) (GPS) * * - RCC8000 MSF Receiver (MSF) - * - VARITEXT clock (MSF) + * - VARITEXT clock (MSF) */ /* * Meinberg receivers are usually connected via a - * 9600 baud serial line + * 9600/7E1 or 19200/8N1 serial line. * * The Meinberg GPS receivers also have a special NTP time stamp * format. The firmware release is Uni-Erlangen. * * Meinberg generic receiver setup: - * output time code every second - * Baud rate 9600 7E2S + * output time code every second + * Baud rate 9600 7E2S * - * Meinberg GPS16x setup: + * Meinberg GPS receiver setup: * output time code every second * Baudrate 19200 8N1 * @@ -91,7 +91,9 @@ * in Meinberg receivers. * * Special software versions are only sensible for the - * GPS 16x family of receivers. + * oldest GPS receiver, GPS16x. For newer receiver types + * the output string format can be configured at the device, + * and the device name is generally GPSxxx instead of GPS16x. * * Meinberg can be reached via: http://www.meinberg.de/ */ @@ -156,13 +158,13 @@ # endif #endif -#define BUFFER_SIZE(_BUF, _PTR) ((_BUF) + sizeof(_BUF) - (_PTR)) -#define BUFFER_SIZES(_BUF, _PTR, _SZ) ((_BUF) + (_SZ) - (_PTR)) +# define BUFFER_SIZE(_BUF, _PTR) ((int)((_BUF) + sizeof(_BUF) - (_PTR))) +# define BUFFER_SIZES(_BUF, _PTR, _SZ) ((int)((_BUF) + (_SZ) - (_PTR))) /* * document type of PPS interfacing - copy of ifdef mechanism in local_input() */ -#undef PPS_METHOD +#undef PPS_METHOD #ifdef HAVE_PPSAPI #define PPS_METHOD "PPS API" @@ -181,6 +183,18 @@ #endif /* TIOCDCDTIMESTAMP */ #endif /* HAVE_PPSAPI */ +/* + * COND_DEF can be conditionally defined as DEF or 0. If defined as DEF + * then some more parse-specific variables are flagged to be printed with + * "ntpq -c cv <assid>". This can be lengthy, so by default COND_DEF + * should be defined as 0. + */ +#if 0 +# define COND_DEF DEF // enable this for testing +#else +# define COND_DEF 0 // enable this by default +#endif + #include "ntp_io.h" #include "ntp_stdlib.h" @@ -382,7 +396,7 @@ struct parseunit * PARSE io */ bind_t *binding; /* io handling binding */ - + /* * parse state */ @@ -450,23 +464,23 @@ typedef struct poll_info #define DCF_P_ID "DCFp" /* psuedo random phase shift */ #define GPS_ID "GPS" /* GPS receiver */ -#define NOCLOCK_ROOTDELAY 0.0 -#define NOCLOCK_BASEDELAY 0.0 -#define NOCLOCK_DESCRIPTION 0 +#define NOCLOCK_ROOTDELAY 0.0 +#define NOCLOCK_BASEDELAY 0.0 +#define NOCLOCK_DESCRIPTION 0 #define NOCLOCK_MAXUNSYNC 0 #define NOCLOCK_CFLAG 0 #define NOCLOCK_IFLAG 0 #define NOCLOCK_OFLAG 0 #define NOCLOCK_LFLAG 0 -#define NOCLOCK_ID "TILT" -#define NOCLOCK_POLL NO_POLL -#define NOCLOCK_INIT NO_INIT -#define NOCLOCK_END NO_END -#define NOCLOCK_DATA NO_LCLDATA -#define NOCLOCK_FORMAT "" -#define NOCLOCK_TYPE CTL_SST_TS_UNSPEC -#define NOCLOCK_SAMPLES 0 -#define NOCLOCK_KEEP 0 +#define NOCLOCK_ID "TILT" +#define NOCLOCK_POLL NO_POLL +#define NOCLOCK_INIT NO_INIT +#define NOCLOCK_END NO_END +#define NOCLOCK_DATA NO_LCLDATA +#define NOCLOCK_FORMAT "" +#define NOCLOCK_TYPE CTL_SST_TS_UNSPEC +#define NOCLOCK_SAMPLES 0 +#define NOCLOCK_KEEP 0 #define DCF_TYPE CTL_SST_TS_LF #define GPS_TYPE CTL_SST_TS_UHF @@ -536,14 +550,14 @@ typedef struct poll_info #define DCFPZF535OCXO_FORMAT "Meinberg Standard" /* - * Meinberg GPS16X receiver + * Meinberg GPS receivers */ static void gps16x_message (struct parseunit *, parsetime_t *); static int gps16x_poll_init (struct parseunit *); #define GPS16X_ROOTDELAY 0.0 /* nothing here */ #define GPS16X_BASEDELAY 0.001968 /* XXX to be fixed ! 1.968ms +- 104us (oscilloscope) - relative to start (end of STX) */ -#define GPS16X_DESCRIPTION "Meinberg GPS16x receiver" +#define GPS16X_DESCRIPTION "Meinberg GPS receiver" #define GPS16X_MAXUNSYNC 60*60*96 /* only trust clock for 4 days * @ 5e-9df/f we have accumulated * at most an error of 1.73 ms @@ -745,9 +759,9 @@ static void trimbletsip_event (struct parseunit *, int); #define TRIMBLETAIP_INIT trimbletaip_init #define TRIMBLETSIP_INIT trimbletsip_init -#define TRIMBLETAIP_EVENT trimbletaip_event +#define TRIMBLETAIP_EVENT trimbletaip_event -#define TRIMBLETSIP_EVENT trimbletsip_event +#define TRIMBLETSIP_EVENT trimbletsip_event #define TRIMBLETSIP_MESSAGE trimbletsip_message #define TRIMBLETAIP_END 0 @@ -804,7 +818,7 @@ static poll_info_t rcc8000_pollinfo = { RCC_POLLRATE, RCC_POLLCMD, RCC_CMDSIZE } #define RCC8000_KEEP 3 /* - * Hopf Radio clock 6021 Format + * Hopf Radio clock 6021 Format * */ #define HOPF6021_ROOTDELAY 0.0 @@ -1200,7 +1214,7 @@ static struct parse_clockinfo }, { /* mode 12 */ HOPF6021_FLAGS, - NO_POLL, + NO_POLL, NO_INIT, NO_EVENT, NO_END, @@ -1537,7 +1551,7 @@ clear_err( { if (lstate == ERR_ALL) { - int i; + size_t i; for (i = 0; i < ERR_CNT; i++) { @@ -1576,7 +1590,7 @@ list_err( if (do_it) err->err_cnt++; - + if (err->err_stage->err_count && (err->err_cnt >= err->err_stage->err_count)) { @@ -1600,7 +1614,7 @@ list_err( l_mktime(current_time - err->err_started)); err->err_suppressed = 0; } - + return do_it; } @@ -1638,7 +1652,7 @@ mkreadable( if (!hex && /* no binary only */ (*src != '\\') && /* no plain \ */ (*src != '"') && /* no " */ - isprint((int)*src)) /* only printables */ + isprint((unsigned char)*src)) /* only printables */ { /* they are easy... */ *buffer++ = *src++; blen--; @@ -1715,7 +1729,7 @@ static int stream_setfmt (struct parseunit *, parsectl_t *); static int stream_timecode (struct parseunit *, parsectl_t *); static void stream_receive (struct recvbuf *); #endif - + static int local_init (struct parseunit *); static void local_end (struct parseunit *); static int local_nop (struct parseunit *); @@ -1771,6 +1785,16 @@ static bind_t io_bindings[] = }, { (char *)0, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, } }; @@ -1786,7 +1810,7 @@ ppsclock_init( { static char m1[] = "ppsclocd"; static char m2[] = "ppsclock"; - + /* * now push the parse streams module * it will ensure exclusive access to the device @@ -1875,7 +1899,7 @@ stream_setcs( ) { struct strioctl strioc; - + strioc.ic_cmd = PARSEIOC_SETCS; strioc.ic_timout = 0; strioc.ic_dp = (char *)tcl; @@ -1898,7 +1922,7 @@ stream_enable( ) { struct strioctl strioc; - + strioc.ic_cmd = PARSEIOC_ENABLE; strioc.ic_timout = 0; strioc.ic_dp = (char *)0; @@ -1922,7 +1946,7 @@ stream_disable( ) { struct strioctl strioc; - + strioc.ic_cmd = PARSEIOC_DISABLE; strioc.ic_timout = 0; strioc.ic_dp = (char *)0; @@ -1947,7 +1971,7 @@ stream_getfmt( ) { struct strioctl strioc; - + strioc.ic_cmd = PARSEIOC_GETFMT; strioc.ic_timout = 0; strioc.ic_dp = (char *)tcl; @@ -1970,7 +1994,7 @@ stream_setfmt( ) { struct strioctl strioc; - + strioc.ic_cmd = PARSEIOC_SETFMT; strioc.ic_timout = 0; strioc.ic_dp = (char *)tcl; @@ -1995,12 +2019,12 @@ stream_timecode( ) { struct strioctl strioc; - + strioc.ic_cmd = PARSEIOC_TIMECODE; strioc.ic_timout = 0; strioc.ic_dp = (char *)tcl; strioc.ic_len = sizeof (*tcl); - + if (ioctl(parse->generic->io.fd, I_STR, (caddr_t)&strioc) == -1) { ERR(ERR_INTERNAL) @@ -2035,7 +2059,7 @@ stream_receive( return; } clear_err(parse, ERR_BADIO); - + memmove((caddr_t)&parsetime, (caddr_t)rbufp->recv_buffer, sizeof(parsetime_t)); @@ -2201,7 +2225,7 @@ local_input( { struct timespec pps_timeout; pps_info_t pps_info; - + pps_timeout.tv_sec = 0; pps_timeout.tv_nsec = 0; @@ -2222,9 +2246,9 @@ local_input( else pts = pps_info.assert_timestamp; - parse->parseio.parse_dtime.parse_ptime.fp.l_ui = pts.tv_sec + JAN_1970; + parse->parseio.parse_dtime.parse_ptime.fp.l_ui = (uint32_t) (pts.tv_sec + JAN_1970); - dtemp = pts.tv_nsec / 1e9; + dtemp = (double) pts.tv_nsec / 1e9; if (dtemp < 0.) { dtemp += 1; parse->parseio.parse_dtime.parse_ptime.fp.l_ui--; @@ -2233,9 +2257,9 @@ local_input( dtemp -= 1; parse->parseio.parse_dtime.parse_ptime.fp.l_ui++; } - parse->parseio.parse_dtime.parse_ptime.fp.l_uf = dtemp * FRAC; + parse->parseio.parse_dtime.parse_ptime.fp.l_uf = (uint32_t)(dtemp * FRAC); - parse->parseio.parse_dtime.parse_state |= PARSEB_PPS|PARSEB_S_PPS; + parse->parseio.parse_dtime.parse_state |= PARSEB_PPS|PARSEB_S_PPS; #ifdef DEBUG if (debug > 3) { @@ -2277,11 +2301,11 @@ local_input( #else #ifdef TIOCDCDTIMESTAMP struct timeval dcd_time; - + if (ioctl(parse->ppsfd, TIOCDCDTIMESTAMP, &dcd_time) != -1) { l_fp tstmp; - + TVTOTS(&dcd_time, &tstmp); tstmp.l_ui += JAN_1970; L_SUB(&ts.fp, &tstmp); @@ -2403,7 +2427,7 @@ local_receive( return; } clear_err(parse, ERR_BADIO); - + memmove((caddr_t)&parsetime, (caddr_t)rbufp->recv_buffer, sizeof(parsetime_t)); @@ -2452,6 +2476,31 @@ init_iobinding( ** support routines **/ +static NTP_PRINTF(4, 5) char * +ap(char *buffer, size_t len, char *pos, const char *fmt, ...) +{ + va_list va; + int l; + size_t rem = len - (pos - buffer); + + if (rem == 0) + return pos; + + va_start(va, fmt); + l = vsnprintf(pos, rem, fmt, va); + va_end(va); + + if (l != -1) { + rem--; + if (rem >= (size_t)l) + pos += l; + else + pos += rem; + } + + return pos; +} + /*-------------------------------------------------- * convert a flag field to a string */ @@ -2476,11 +2525,11 @@ parsestate( { PARSEB_LEAPADD, "LEAP ADD WARNING" }, { PARSEB_LEAPDEL, "LEAP DELETE WARNING" }, { PARSEB_LEAPSECOND, "LEAP SECOND" }, - { PARSEB_ALTERNATE, "ALTERNATE ANTENNA" }, + { PARSEB_CALLBIT, "CALL BIT" }, { PARSEB_TIMECODE, "TIME CODE" }, { PARSEB_PPS, "PPS" }, { PARSEB_POSITION, "POSITION" }, - { 0 } + { 0, NULL } }; static struct sbits @@ -2493,12 +2542,11 @@ parsestate( { PARSEB_S_PPS, "PPS SIGNAL" }, { PARSEB_S_ANTENNA, "ANTENNA" }, { PARSEB_S_POSITION, "POSITION" }, - { 0 } + { 0, NULL } }; int i; char *s, *t; - *buffer = '\0'; s = t = buffer; @@ -2508,42 +2556,37 @@ parsestate( if (flagstrings[i].bit & lstate) { if (s != t) - strlcpy(t, "; ", BUFFER_SIZES(buffer, t, size)); - if (strlcat(t, flagstrings[i].name, BUFFER_SIZES(buffer, t, size)) < - BUFFER_SIZES(buffer, t, size)) - t += strlen(t); + t = ap(buffer, size, t, "; "); + t = ap(buffer, size, t, "%s", flagstrings[i].name); } i++; } if (lstate & (PARSEB_S_LEAP|PARSEB_S_ANTENNA|PARSEB_S_PPS|PARSEB_S_POSITION)) { - if (s != t && - strlcpy(t, "; ", BUFFER_SIZES(buffer, t, size)) < - BUFFER_SIZES(buffer, t, size)) - t += strlen(t); + if (s != t) + t = ap(buffer, size, t, "; "); + + t = ap(buffer, size, t, "("); - if (strlcpy(t, "(", BUFFER_SIZES(buffer, t, size)) < - BUFFER_SIZES(buffer, t, size)) - s = t = t + strlen(t); + s = t; i = 0; while (sflagstrings[i].bit) { if (sflagstrings[i].bit & lstate) { - if (t != s && - strlcpy(t, "; ", BUFFER_SIZES(buffer, t, size)) < - BUFFER_SIZES(buffer, t, size)) - t += 2; - - if (strlcpy(t, sflagstrings[i].name, BUFFER_SIZES(buffer, t, size)) < - BUFFER_SIZES(buffer, t, size)) - t += strlen(t); + if (t != s) + { + t = ap(buffer, size, t, "; "); + } + + t = ap(buffer, size, t, "%s", + sflagstrings[i].name); } i++; } - strlcpy(t, ")", BUFFER_SIZES(buffer, t, size)); + t = ap(buffer, size, t, ")"); } return buffer; } @@ -2571,10 +2614,12 @@ parsestatus( { CVT_BADDATE, "DATE ILLEGAL" }, { CVT_BADTIME, "TIME ILLEGAL" }, { CVT_ADDITIONAL, "ADDITIONAL DATA" }, - { 0 } + { 0, NULL } }; int i; + char *t; + t = buffer; *buffer = '\0'; i = 0; @@ -2582,9 +2627,9 @@ parsestatus( { if (flagstrings[i].bit & lstate) { - if (buffer[0]) - strlcat(buffer, "; ", size); - strlcat(buffer, flagstrings[i].name, size); + if (t != buffer) + t = ap(buffer, size, t, "; "); + t = ap(buffer, size, t, "%s", flagstrings[i].name); } i++; } @@ -2614,12 +2659,12 @@ clockstatus( { CEVNT_PROP, "PROPAGATION DELAY" }, { CEVNT_BADDATE, "ILLEGAL DATE" }, { CEVNT_BADTIME, "ILLEGAL TIME" }, - { (unsigned)~0L } + { (unsigned)~0L, NULL } }; int i; i = 0; - while (flagstrings[i].value != ~0) + while (flagstrings[i].value != (u_int)~0) { if (flagstrings[i].value == lstate) { @@ -2647,10 +2692,11 @@ l_mktime( char *t; buffer[0] = '\0'; + t = buffer; if ((tmp = delta / (60*60*24)) != 0) { - snprintf(buffer, BUFFER_SIZE(buffer, buffer), "%ldd+", (u_long)tmp); + t = ap(buffer, sizeof(buffer), t, "%ldd+", (u_long)tmp); delta -= tmp * 60*60*24; } @@ -2659,10 +2705,8 @@ l_mktime( m = delta % 60; delta /= 60; - t = buffer + strlen(buffer); - - snprintf(t, BUFFER_SIZE(buffer, t), "%02d:%02d:%02d", - (int)delta, (int)m, (int)s); + t = ap(buffer, sizeof(buffer), t, "%02d:%02d:%02d", + (int)delta, (int)m, (int)s); return buffer; } @@ -2778,7 +2822,7 @@ parse_shutdown( { parse->parse_type->cl_end(parse); } - + /* * cleanup before leaving this world */ @@ -2791,7 +2835,7 @@ parse_shutdown( io_closeclock(&parse->generic->io); free_varlist(parse->kv); - + NLOG(NLOG_CLOCKINFO) /* conditional if clause for conditional syslog */ msyslog(LOG_INFO, "PARSE receiver #%d: reference clock \"%s\" removed", CLK_UNIT(parse->peer), parse->parse_type->cl_description); @@ -2817,14 +2861,14 @@ parse_hardpps( if (CLK_PPS(parse->peer) && (parse->flags & PARSE_PPSKERNEL)) { int i = 0; - if (mode == PARSE_HARDPPS_ENABLE) + if (mode == PARSE_HARDPPS_ENABLE) { if (parse->flags & PARSE_CLEAR) i = PPS_CAPTURECLEAR; else i = PPS_CAPTUREASSERT; } - + if (time_pps_kcbind(parse->atom.handle, PPS_KC_HARDPPS, i, PPS_TSFMT_TSPEC) < 0) { msyslog(LOG_ERR, "PARSE receiver #%d: time_pps_kcbind failed: %m", @@ -2853,9 +2897,9 @@ parse_ppsapi( ) { int cap, mode_ppsoffset; - char *cp; - - parse->flags &= ~PARSE_PPSCLOCK; + const char *cp; + + parse->flags &= (u_char) (~PARSE_PPSCLOCK); /* * collect PPSAPI offset capability - should move into generic handling @@ -2863,7 +2907,7 @@ parse_ppsapi( if (time_pps_getcap(parse->atom.handle, &cap) < 0) { msyslog(LOG_ERR, "PARSE receiver #%d: parse_ppsapi: time_pps_getcap failed: %m", CLK_UNIT(parse->peer)); - + return 0; } @@ -2897,19 +2941,19 @@ parse_ppsapi( CLK_UNIT(parse->peer), cp, cap); mode_ppsoffset = 0; } else { - if (mode_ppsoffset == PPS_OFFSETCLEAR) - { - parse->atom.pps_params.clear_offset.tv_sec = -parse->ppsphaseadjust; - parse->atom.pps_params.clear_offset.tv_nsec = -1e9*(parse->ppsphaseadjust - (long)parse->ppsphaseadjust); + if (mode_ppsoffset == PPS_OFFSETCLEAR) + { + parse->atom.pps_params.clear_offset.tv_sec = (time_t)(-parse->ppsphaseadjust); + parse->atom.pps_params.clear_offset.tv_nsec = (long)(-1e9*(parse->ppsphaseadjust - (double)(long)parse->ppsphaseadjust)); } - + if (mode_ppsoffset == PPS_OFFSETASSERT) - { - parse->atom.pps_params.assert_offset.tv_sec = -parse->ppsphaseadjust; - parse->atom.pps_params.assert_offset.tv_nsec = -1e9*(parse->ppsphaseadjust - (long)parse->ppsphaseadjust); + { + parse->atom.pps_params.assert_offset.tv_sec = (time_t)(-parse->ppsphaseadjust); + parse->atom.pps_params.assert_offset.tv_nsec = (long)(-1e9*(parse->ppsphaseadjust - (double)(long)parse->ppsphaseadjust)); } } - + parse->atom.pps_params.mode |= mode_ppsoffset; if (time_pps_setparams(parse->atom.handle, &parse->atom.pps_params) < 0) { @@ -2961,7 +3005,7 @@ parse_start( type = CLK_TYPE(peer); unit = CLK_UNIT(peer); - if ((type == ~0) || (parse_clockinfo[type].cl_description == (char *)0)) + if ((type == (u_int)~0) || (parse_clockinfo[type].cl_description == (char *)0)) { msyslog(LOG_ERR, "PARSE receiver #%d: parse_start: unsupported clock type %d (max %d)", unit, CLK_REALTYPE(peer), ncltypes-1); @@ -3013,9 +3057,9 @@ parse_start( parse->kv = (struct ctl_var *)0; clear_err(parse, ERR_ALL); - + parse->parse_type = &parse_clockinfo[type]; - + parse->maxunsync = parse->parse_type->cl_maxunsync; parse->generic->fudgetime1 = parse->parse_type->cl_basedelay; @@ -3028,16 +3072,16 @@ parse_start( peer->rootdelay = parse->parse_type->cl_rootdelay; peer->sstclktype = parse->parse_type->cl_type; peer->precision = sys_precision; - + peer->stratum = STRATUM_REFCLOCK; if (peer->stratum <= 1) memmove((char *)&parse->generic->refid, parse->parse_type->cl_id, 4); else parse->generic->refid = htonl(PARSEHSREFID); - + parse->generic->io.fd = fd232; - + parse->peer = peer; /* marks it also as busy */ /* @@ -3080,15 +3124,15 @@ parse_start( } #endif - tio.c_cflag = parse_clockinfo[type].cl_cflag; - tio.c_iflag = parse_clockinfo[type].cl_iflag; - tio.c_oflag = parse_clockinfo[type].cl_oflag; - tio.c_lflag = parse_clockinfo[type].cl_lflag; - + tio.c_cflag = (tcflag_t) parse_clockinfo[type].cl_cflag; + tio.c_iflag = (tcflag_t) parse_clockinfo[type].cl_iflag; + tio.c_oflag = (tcflag_t) parse_clockinfo[type].cl_oflag; + tio.c_lflag = (tcflag_t) parse_clockinfo[type].cl_lflag; + #ifdef HAVE_TERMIOS - if ((cfsetospeed(&tio, parse_clockinfo[type].cl_speed) == -1) || - (cfsetispeed(&tio, parse_clockinfo[type].cl_speed) == -1)) + if ((cfsetospeed(&tio, (speed_t) parse_clockinfo[type].cl_speed) == -1) || + (cfsetispeed(&tio, (speed_t) parse_clockinfo[type].cl_speed) == -1)) { msyslog(LOG_ERR, "PARSE receiver #%d: parse_start: tcset{i,o}speed(&tio, speed): %m", unit); parse_shutdown(CLK_UNIT(parse->peer), peer); /* let our cleaning staff do the work */ @@ -3148,7 +3192,7 @@ parse_start( if (CLK_PPS(parse->peer)) { int i = 1; - + if (ioctl(parse->ppsfd, TIOCSPPS, (caddr_t)&i) == 0) { parse->flags |= PARSE_PPSCLOCK; @@ -3187,7 +3231,7 @@ parse_start( */ parse->generic->io.srcclock = peer; parse->generic->io.datalen = 0; - + parse->binding = init_iobinding(parse); if (parse->binding == (bind_t *)0) @@ -3234,11 +3278,8 @@ parse_start( return 0; /* well, ok - special initialisation broke */ } - tmp_ctl.parseformat.parse_count = strlcpy(tmp_ctl.parseformat.parse_buffer, - parse->parse_type->cl_format, - sizeof(tmp_ctl.parseformat.parse_buffer)); - if (tmp_ctl.parseformat.parse_count >= sizeof(tmp_ctl.parseformat.parse_buffer)) - tmp_ctl.parseformat.parse_count = sizeof(tmp_ctl.parseformat.parse_buffer) - 1; + strlcpy(tmp_ctl.parseformat.parse_buffer, parse->parse_type->cl_format, sizeof(tmp_ctl.parseformat.parse_buffer)); + tmp_ctl.parseformat.parse_count = (u_short) strlen(tmp_ctl.parseformat.parse_buffer); if (!PARSE_SETFMT(parse, &tmp_ctl)) { @@ -3246,7 +3287,7 @@ parse_start( parse_shutdown(CLK_UNIT(parse->peer), peer); /* let our cleaning staff do the work */ return 0; /* well, ok - special initialisation broke */ } - + /* * get rid of all IO accumulated so far */ @@ -3273,7 +3314,7 @@ parse_start( return 0; /* well, ok - special initialisation broke */ } } - + /* * Insert in async io device list. */ @@ -3338,8 +3379,8 @@ parse_ctl( { if (in->haveflags & (CLK_HAVEFLAG1|CLK_HAVEFLAG2|CLK_HAVEFLAG3|CLK_HAVEFLAG4)) { - parse->flags = (parse->flags & ~(CLK_FLAG1|CLK_FLAG2|CLK_FLAG3|CLK_FLAG4)) | - (in->flags & (CLK_FLAG1|CLK_FLAG2|CLK_FLAG3|CLK_FLAG4)); + u_char mask = CLK_FLAG1|CLK_FLAG2|CLK_FLAG3|CLK_FLAG4; + parse->flags = (parse->flags & (u_char)(~mask)) | (in->flags & mask); #if defined(HAVE_PPSAPI) if (CLK_PPS(parse->peer)) { @@ -3347,7 +3388,7 @@ parse_ctl( } #endif } - + if (in->haveflags & CLK_HAVETIME1) { parse->generic->fudgetime1 = in->fudgetime1; @@ -3355,11 +3396,11 @@ parse_ctl( CLK_UNIT(parse->peer), parse->generic->fudgetime1); } - + if (in->haveflags & CLK_HAVETIME2) { parse->generic->fudgetime2 = in->fudgetime2; - if (parse->flags & PARSE_TRUSTTIME) + if (parse->flags & PARSE_TRUSTTIME) { parse->maxunsync = (u_long)ABS(in->fudgetime2); msyslog(LOG_INFO, "PARSE receiver #%d: new trust time %s", @@ -3407,8 +3448,8 @@ parse_poll( */ parse->generic->polls++; - if (parse->pollneeddata && - ((current_time - parse->pollneeddata) > (1<<(max(min(parse->peer->hpoll, parse->peer->ppoll), parse->peer->minpoll))))) + if (parse->pollneeddata && + ((int)(current_time - parse->pollneeddata) > (1<<(max(min(parse->peer->hpoll, parse->peer->ppoll), parse->peer->minpoll))))) { /* * start worrying when exceeding a poll inteval @@ -3416,7 +3457,7 @@ parse_poll( */ parse->lastmissed = current_time; parse_event(parse, CEVNT_TIMEOUT); - + ERR(ERR_NODATA) msyslog(LOG_WARNING, "PARSE receiver #%d: no data from device within poll interval (check receiver / wiring)", CLK_UNIT(parse->peer)); } @@ -3474,7 +3515,7 @@ parse_control( * handle changes */ parse_ctl(parse, in); - + /* * supply data */ @@ -3521,16 +3562,16 @@ parse_control( } start = tt = add_var(&out->kv_list, 128, RO|DEF); - snprintf(tt, 128, "refclock_time=\""); - tt += strlen(tt); + tt = ap(start, 128, tt, "refclock_time=\""); if (parse->timedata.parse_time.fp.l_ui == 0) { - strlcpy(tt, "<UNDEFINED>\"", BUFFER_SIZES(start, tt, 128)); + tt = ap(start, 128, tt, "<UNDEFINED>\""); } else { - snprintf(tt, 128, "%s\"", gmprettydate(&parse->timedata.parse_time.fp)); + tt = ap(start, 128, tt, "%s\"", + gmprettydate(&parse->timedata.parse_time.fp)); } if (!PARSE_GETTIMECODE(parse, &tmpctl)) @@ -3541,8 +3582,7 @@ parse_control( else { start = tt = add_var(&out->kv_list, 512, RO|DEF); - snprintf(tt, 512, "refclock_status=\""); - tt += strlen(tt); + tt = ap(start, 512, tt, "refclock_status=\""); /* * copy PPS flags from last read transaction (informational only) @@ -3550,18 +3590,20 @@ parse_control( tmpctl.parsegettc.parse_state |= parse->timedata.parse_state & (PARSEB_PPS|PARSEB_S_PPS); - (void) parsestate(tmpctl.parsegettc.parse_state, tt, BUFFER_SIZES(start, tt, 512)); + (void)parsestate(tmpctl.parsegettc.parse_state, tt, BUFFER_SIZES(start, tt, 512)); - strlcat(tt, "\"", BUFFER_SIZES(start, tt, 512)); + tt += strlen(tt); + + tt = ap(start, 512, tt, "\""); if (tmpctl.parsegettc.parse_count) mkascii(outstatus+strlen(outstatus), (int)(sizeof(outstatus)- strlen(outstatus) - 1), tmpctl.parsegettc.parse_buffer, (unsigned)(tmpctl.parsegettc.parse_count)); } - + tmpctl.parseformat.parse_format = tmpctl.parsegettc.parse_format; - + if (!PARSE_GETFMT(parse, &tmpctl)) { ERR(ERR_INTERNAL) @@ -3569,11 +3611,19 @@ parse_control( } else { - tt = add_var(&out->kv_list, 80, RO|DEF); - snprintf(tt, 80, "refclock_format=\""); + int count = tmpctl.parseformat.parse_count - 1; + + start = tt = add_var(&out->kv_list, 80, RO|DEF); + tt = ap(start, 80, tt, "refclock_format=\""); - strlcat(tt, tmpctl.parseformat.parse_buffer, 80); - strlcat(tt,"\"", 80); + if (count > 0) { + tt = ap(start, 80, tt, "%*.*s", + count, + count, + tmpctl.parseformat.parse_buffer); + } + + tt = ap(start, 80, tt, "\""); } /* @@ -3581,8 +3631,7 @@ parse_control( */ start = tt = add_var(&out->kv_list, LEN_STATES, RO|DEF); - strlcpy(tt, "refclock_states=\"", LEN_STATES); - tt += strlen(tt); + tt = ap(start, LEN_STATES, tt, "refclock_states=\""); for (i = 0; i <= CEVNT_MAX; i++) { @@ -3597,7 +3646,7 @@ parse_control( percent /= 10; d /= 10; } - + if (d) percent = (percent * 10000) / d; else @@ -3607,36 +3656,37 @@ parse_control( { char item[80]; int count; - + snprintf(item, 80, "%s%s%s: %s (%d.%02d%%)", sum ? "; " : "", (parse->generic->currentstatus == i) ? "*" : "", clockstatus((unsigned int)i), l_mktime(s_time), (int)(percent / 100), (int)(percent % 100)); - if ((count = strlen(item)) < (LEN_STATES - 40 - (tt - start))) + if ((count = (int) strlen(item)) < (LEN_STATES - 40 - (tt - start))) { - strlcpy(tt, item, BUFFER_SIZES(start, tt, LEN_STATES)); - tt += count; + tt = ap(start, LEN_STATES, tt, + "%s", item); } sum += s_time; } } - - snprintf(tt, BUFFER_SIZES(start, tt, LEN_STATES), "; running time: %s\"", l_mktime(sum)); - + + tt = ap(start, LEN_STATES, tt, + "; running time: %s\"", l_mktime(sum)); + tt = add_var(&out->kv_list, 32, RO); snprintf(tt, 32, "refclock_id=\"%s\"", parse->parse_type->cl_id); - + tt = add_var(&out->kv_list, 80, RO); snprintf(tt, 80, "refclock_iomode=\"%s\"", parse->binding->bd_description); tt = add_var(&out->kv_list, 128, RO); snprintf(tt, 128, "refclock_driver_version=\"%s\"", rcsid); - + { struct ctl_var *k; - + k = parse->kv; while (k && !(k->flags & EOV)) { @@ -3644,8 +3694,8 @@ parse_control( k++; } } - - out->lencode = strlen(outstatus); + + out->lencode = (u_short) strlen(outstatus); out->p_lastcode = outstatus; } } @@ -3694,7 +3744,7 @@ parse_process( { l_fp off, rectime, reftime; double fudge; - + /* silence warning: 'off.Ul_i.Xl_i' may be used uninitialized in this function */ ZERO(off); @@ -3707,11 +3757,11 @@ parse_process( (parse->timedata.parse_status != parsetime->parse_status)) { char buffer[400]; - + NLOG(NLOG_CLOCKINFO) /* conditional if clause for conditional syslog */ msyslog(LOG_WARNING, "PARSE receiver #%d: conversion status \"%s\"", CLK_UNIT(parse->peer), parsestatus(parsetime->parse_status, buffer, sizeof(buffer))); - + if ((parsetime->parse_status & CVT_MASK) == CVT_FAIL) { /* @@ -3720,7 +3770,7 @@ parse_process( * the time code might be overwritten by the next packet */ parsectl_t tmpctl; - + if (!PARSE_GETTIMECODE(parse, &tmpctl)) { ERR(ERR_INTERNAL) @@ -3758,7 +3808,7 @@ parse_process( parse->timedata.parse_ptime = parsetime->parse_ptime; } break; /* well, still waiting - timeout is handled at higher levels */ - + case CVT_FAIL: if (parsetime->parse_status & CVT_BADFMT) { @@ -3789,7 +3839,7 @@ parse_process( if (parse->lastformat != parsetime->parse_format) { parsectl_t tmpctl; - + tmpctl.parseformat.parse_format = parsetime->parse_format; if (!PARSE_GETFMT(parse, &tmpctl)) @@ -3817,10 +3867,10 @@ parse_process( /* * something happend - except for PPS events */ - + (void) parsestate(parsetime->parse_state, tmp1, sizeof(tmp1)); (void) parsestate(parse->timedata.parse_state, tmp2, sizeof(tmp2)); - + NLOG(NLOG_CLOCKINFO) /* conditional if clause for conditional syslog */ msyslog(LOG_INFO,"PARSE receiver #%d: STATE CHANGE: %s -> %s", CLK_UNIT(parse->peer), tmp2, tmp1); @@ -3923,12 +3973,12 @@ parse_process( } fudge = parse->generic->fudgetime1; /* standard RS232 Fudgefactor */ - + if (PARSE_TIMECODE(parsetime->parse_state)) { rectime = parsetime->parse_stime.fp; off = reftime = parsetime->parse_time.fp; - + L_SUB(&off, &rectime); /* prepare for PPS adjustments logic */ #ifdef DEBUG @@ -3973,7 +4023,7 @@ parse_process( M_ISGEQ(0, 0x7fffffff, off.l_i, off.l_uf)) { fudge = ppsphaseadjust; /* pick PPS fudge factor */ - + /* * RS232 offsets within [-0.5..0.5[ - take PPS offsets */ @@ -3985,12 +4035,12 @@ parse_process( reftime.l_ui++; reftime.l_uf = 0; - + /* * implied on second offset */ off.l_uf = ~off.l_uf; /* map [0.5..1[ -> [-0.5..0[ */ - off.l_i = (off.l_uf & 0x8000000) ? -1 : 0; /* sign extend */ + off.l_i = (off.l_uf & 0x80000000) ? -1 : 0; /* sign extend */ } else { @@ -4051,7 +4101,7 @@ parse_process( rectime = reftime; L_SUB(&rectime, &off); /* just to keep the ntp interface happy */ - + #ifdef DEBUG if (debug > 3) printf("PARSE receiver #%d: calculated Reftime %s, Recvtime %s\n", @@ -4076,14 +4126,14 @@ parse_process( clear_err(parse, ERR_BADDATA); clear_err(parse, ERR_NODATA); clear_err(parse, ERR_INTERNAL); - + /* * and now stick it into the clock machine * samples are only valid iff lastsync is not too old and * we have seen the clock in sync at least once * after the last time we didn't see an expected data telegram * at startup being not in sync is also bad just like - * POWERUP state unless PARSE_F_POWERUPTRUST is set + * POWERUP state unless PARSE_F_POWERUPTRUST is set * see the clock states section above for more reasoning */ if (((current_time - parse->lastsync) > parse->maxunsync) || @@ -4123,9 +4173,9 @@ parse_process( * only good/trusted samples are interesting */ #ifdef DEBUG - if (debug > 2) - { - printf("PARSE receiver #%d: refclock_process_offset(reftime=%s, rectime=%s, Fudge=%f)\n", + if (debug > 2) + { + printf("PARSE receiver #%d: refclock_process_offset(reftime=%s, rectime=%s, Fudge=%f)\n", CLK_UNIT(parse->peer), prettydate(&reftime), prettydate(&rectime), @@ -4133,7 +4183,7 @@ parse_process( } #endif parse->generic->lastref = reftime; - + refclock_process_offset(parse->generic, reftime, rectime, fudge); #ifdef HAVE_PPSAPI @@ -4141,31 +4191,18 @@ parse_process( * pass PPS information on to PPS clock */ if (PARSE_PPS(parsetime->parse_state) && CLK_PPS(parse->peer)) - { - /* refclock_pps includes fudgetime1 - we keep the RS232 offset in there :-( */ - double savedtime1 = parse->generic->fudgetime1; - - parse->generic->fudgetime1 = fudge; - - if (refclock_pps(parse->peer, &parse->atom, - parse->flags & (CLK_FLAG1|CLK_FLAG2|CLK_FLAG3|CLK_FLAG4))) { - parse->peer->flags |= FLAG_PPS; - } else { - parse->peer->flags &= ~FLAG_PPS; - } - - parse->generic->fudgetime1 = savedtime1; - + { + parse->peer->flags |= (FLAG_PPS | FLAG_TSTAMP_PPS); parse_hardpps(parse, PARSE_HARDPPS_ENABLE); } #endif } else { - parse_hardpps(parse, PARSE_HARDPPS_DISABLE); - parse->peer->flags &= ~FLAG_PPS; + parse_hardpps(parse, PARSE_HARDPPS_DISABLE); + parse->peer->flags &= ~(FLAG_PPS | FLAG_TSTAMP_PPS); } /* - * ready, unless the machine wants a sample or + * ready, unless the machine wants a sample or * we are in fast startup mode (peer->dist > MAXDISTANCE) */ if (!parse->pollneeddata && parse->peer->disp <= MAXDISTANCE) @@ -4177,56 +4214,71 @@ parse_process( refclock_receive(parse->peer); } - + /**=========================================================================== ** special code for special clocks **/ static void mk_utcinfo( - char *t, + char *t, // pointer to the output string buffer int wnt, int wnlsf, int dn, int dtls, int dtlsf, - int size + int size // size of the output string buffer ) { - l_fp leapdate; - char *start = t; - - snprintf(t, size, "current correction %d sec", dtls); - t += strlen(t); - - if (wnlsf < 990) - wnlsf += 1024; - - if (wnt < 990) - wnt += 1024; - - gpstolfp((unsigned short)wnlsf, (unsigned short)dn, 0, &leapdate); - - if ((dtlsf != dtls) && - ((wnlsf - wnt) < 52)) - { - snprintf(t, BUFFER_SIZES(start, t, size), ", next correction %d sec on %s, new GPS-UTC offset %d", - dtlsf - dtls, gmprettydate(&leapdate), dtlsf); - } - else - { - snprintf(t, BUFFER_SIZES(start, t, size), ", last correction on %s", - gmprettydate(&leapdate)); - } + /* + * The week number transmitted by the GPS satellites for the leap date + * is truncated to 8 bits only. If the nearest leap second date is off + * the current date by more than +/- 128 weeks then conversion to a + * calendar date is ambiguous. On the other hand, if a leap second is + * currently being announced (i.e. dtlsf != dtls) then the week number + * wnlsf is close enough, and we can unambiguously determine the date + * for which the leap second is scheduled. + */ + if ( dtlsf != dtls ) + { + time_t t_ls; + struct tm *tm; + int n = 0; + + if (wnlsf < GPSWRAP) + wnlsf += GPSWEEKS; + + if (wnt < GPSWRAP) + wnt += GPSWEEKS; + + t_ls = (time_t) wnlsf * SECSPERWEEK + + (time_t) dn * SECSPERDAY + + GPS_SEC_BIAS - 1; + + tm = gmtime( &t_ls ); + if (tm == NULL) // gmtime() failed + { + snprintf( t, size, "** (gmtime() failed in mk_utcinfo())" ); + return; + } + + n += snprintf( t, size, "UTC offset transition from %is to %is due to leap second %s", + dtls, dtlsf, ( dtls < dtlsf ) ? "insertion" : "deletion" ); + n += snprintf( t + n, size - n, " at UTC midnight at the end of %s, %04i-%02i-%02i", + daynames[tm->tm_wday], tm->tm_year + 1900, tm->tm_mon + 1, tm->tm_mday ); + } + else + snprintf( t, size, "UTC offset parameter: %is, no leap second announced.\n", dtls ); + } #ifdef CLOCK_MEINBERG /**=========================================================================== - ** Meinberg GPS166/GPS167 support + ** Meinberg GPS receiver support **/ /*------------------------------------------------------------ - * gps16x_message - process GPS16x messages + * gps16x_message - process messages from Meinberg GPS receiver */ static void gps16x_message( @@ -4238,12 +4290,12 @@ gps16x_message( { GPS_MSG_HDR header; unsigned char *bufp = (unsigned char *)parsetime->parse_msg + 1; - + #ifdef DEBUG if (debug > 2) { char msgbuffer[600]; - + mkreadable(msgbuffer, sizeof(msgbuffer), (char *)parsetime->parse_msg, parsetime->parse_msglen, 1); printf("PARSE receiver #%d: received message (%d bytes) >%s<\n", CLK_UNIT(parse->peer), @@ -4252,21 +4304,21 @@ gps16x_message( } #endif get_mbg_header(&bufp, &header); - if (header.gps_hdr_csum == mbg_csum(parsetime->parse_msg + 1, 6) && - (header.gps_len == 0 || - (header.gps_len < sizeof(parsetime->parse_msg) && - header.gps_data_csum == mbg_csum(bufp, header.gps_len)))) + if (header.hdr_csum == mbg_csum(parsetime->parse_msg + 1, 6) && + (header.len == 0 || + (header.len < sizeof(parsetime->parse_msg) && + header.data_csum == mbg_csum(bufp, header.len)))) { /* * clean message */ - switch (header.gps_cmd) + switch (header.cmd) { case GPS_SW_REV: { char buffer[64]; SW_REV gps_sw_rev; - + get_mbg_sw_rev(&bufp, &gps_sw_rev); snprintf(buffer, sizeof(buffer), "meinberg_gps_version=\"%x.%02x%s%s\"", (gps_sw_rev.code >> 8) & 0xFF, @@ -4277,54 +4329,56 @@ gps16x_message( } break; - case GPS_STAT: + case GPS_BVAR_STAT: { static struct state { - unsigned short flag; /* status flag */ - unsigned const char *string; /* bit name */ + BVAR_STAT flag; /* status flag */ + const char *string; /* bit name */ } states[] = { - { TM_ANT_DISCONN, (const unsigned char *)"ANTENNA FAULTY" }, - { TM_SYN_FLAG, (const unsigned char *)"NO SYNC SIGNAL" }, - { TM_NO_SYNC, (const unsigned char *)"NO SYNC POWERUP" }, - { TM_NO_POS, (const unsigned char *)"NO POSITION" }, - { 0, (const unsigned char *)"" } + { BVAR_CFGH_INVALID, "Configuration/Health" }, + { BVAR_ALM_NOT_COMPLETE, "Almanachs" }, + { BVAR_UTC_INVALID, "UTC Correction" }, + { BVAR_IONO_INVALID, "Ionospheric Correction" }, + { BVAR_RCVR_POS_INVALID, "Receiver Position" }, + { 0, "" } }; - unsigned short status; + BVAR_STAT status; struct state *s = states; char buffer[512]; char *p, *b; - - status = get_lsb_short(&bufp); - snprintf(buffer, sizeof(buffer), "meinberg_gps_status=\"[0x%04x] ", status); - + + status = (BVAR_STAT) get_lsb_short(&bufp); + p = b = buffer; + p = ap(buffer, sizeof(buffer), p, + "meinberg_gps_status=\"[0x%04x] ", + status); + if (status) { - p = b = buffer + strlen(buffer); + p = ap(buffer, sizeof(buffer), p, "incomplete buffered data: "); + b = p; while (s->flag) { if (status & s->flag) { if (p != b) { - *p++ = ','; - *p++ = ' '; + p = ap(buffer, sizeof(buffer), p, ", "); } - - strlcat(p, (const char *)s->string, sizeof(buffer)); + + p = ap(buffer, sizeof(buffer), p, "%s", (const char *)s->string); } s++; } - - *p++ = '"'; - *p = '\0'; + p = ap(buffer, sizeof(buffer), p, "\""); } else { - strlcat(buffer, "<OK>\"", sizeof(buffer)); + p = ap(buffer, sizeof(buffer), p, "<all buffered data complete>\""); } - + set_var(&parse->kv, buffer, strlen(buffer)+1, RO|DEF); } break; @@ -4333,282 +4387,259 @@ gps16x_message( { XYZ xyz; char buffer[256]; - + get_mbg_xyz(&bufp, xyz); snprintf(buffer, sizeof(buffer), "gps_position(XYZ)=\"%s m, %s m, %s m\"", mfptoa(xyz[XP].l_ui, xyz[XP].l_uf, 1), mfptoa(xyz[YP].l_ui, xyz[YP].l_uf, 1), mfptoa(xyz[ZP].l_ui, xyz[ZP].l_uf, 1)); - + set_var(&parse->kv, buffer, sizeof(buffer), RO|DEF); } break; - + case GPS_POS_LLA: { LLA lla; char buffer[256]; - + get_mbg_lla(&bufp, lla); - + snprintf(buffer, sizeof(buffer), "gps_position(LLA)=\"%s deg, %s deg, %s m\"", mfptoa(lla[LAT].l_ui, lla[LAT].l_uf, 4), - mfptoa(lla[LON].l_ui, lla[LON].l_uf, 4), + mfptoa(lla[LON].l_ui, lla[LON].l_uf, 4), mfptoa(lla[ALT].l_ui, lla[ALT].l_uf, 1)); - + set_var(&parse->kv, buffer, sizeof(buffer), RO|DEF); } break; - + case GPS_TZDL: break; - + case GPS_PORT_PARM: break; - + case GPS_SYNTH: break; - + case GPS_ANT_INFO: { ANT_INFO antinfo; char buffer[512]; - char *p; - + char *p, *q; + get_mbg_antinfo(&bufp, &antinfo); - snprintf(buffer, sizeof(buffer), "meinberg_antenna_status=\""); - p = buffer + strlen(buffer); - + p = buffer; + p = ap(buffer, sizeof(buffer), p, "meinberg_antenna_status=\""); switch (antinfo.status) { - case ANT_INVALID: - strlcat(p, "<OK>", BUFFER_SIZE(buffer, p)); - p += strlen(p); + case ANT_INVALID: // No other fields valid since antenna has not yet been disconnected + p = ap(buffer, sizeof(buffer), + p, "<OK>"); break; - - case ANT_DISCONN: - strlcat(p, "DISCONNECTED since ", BUFFER_SIZE(buffer, p)); + + case ANT_DISCONN: // Antenna is disconnected, tm_reconn and delta_t not yet set + q = ap(buffer, sizeof(buffer), + p, "DISCONNECTED since "); NLOG(NLOG_CLOCKSTATUS) ERR(ERR_BADSTATUS) msyslog(LOG_ERR,"PARSE receiver #%d: ANTENNA FAILURE: %s", CLK_UNIT(parse->peer), p); - - p += strlen(p); - mbg_tm_str(&p, &antinfo.tm_disconn, BUFFER_SIZE(buffer, p)); + + p = q; + mbg_tm_str(&p, &antinfo.tm_disconn, BUFFER_SIZE(buffer, p), 0); *p = '\0'; break; - - case ANT_RECONN: - strlcat(p, "RECONNECTED on ", BUFFER_SIZE(buffer, p)); - p += strlen(p); - mbg_tm_str(&p, &antinfo.tm_reconn, BUFFER_SIZE(buffer, p)); - snprintf(p, BUFFER_SIZE(buffer, p), ", reconnect clockoffset %c%ld.%07ld s, disconnect time ", + + case ANT_RECONN: // Antenna had been disconnect, but receiver sync. after reconnect, so all fields valid + p = ap(buffer, sizeof(buffer), + p, "SYNC AFTER RECONNECT on "); + mbg_tm_str(&p, &antinfo.tm_reconn, BUFFER_SIZE(buffer, p), 0); + p = ap(buffer, sizeof(buffer), + p, ", clock offset at reconnect %c%ld.%07ld s, disconnect time ", (antinfo.delta_t < 0) ? '-' : '+', - ABS(antinfo.delta_t) / 10000, - ABS(antinfo.delta_t) % 10000); - p += strlen(p); - mbg_tm_str(&p, &antinfo.tm_disconn, BUFFER_SIZE(buffer, p)); + (long) ABS(antinfo.delta_t) / 10000, + (long) ABS(antinfo.delta_t) % 10000); + mbg_tm_str(&p, &antinfo.tm_disconn, BUFFER_SIZE(buffer, p), 0); *p = '\0'; break; - + default: - snprintf(p, BUFFER_SIZE(buffer, p), "bad status 0x%04x", antinfo.status); - p += strlen(p); + p = ap(buffer, sizeof(buffer), + p, "bad status 0x%04x", + antinfo.status); break; } - - strlcat(p, "\"", BUFFER_SIZE(buffer, p)); - - set_var(&parse->kv, buffer, strlen(buffer)+1, RO|DEF); + + p = ap(buffer, sizeof(buffer), p, "\""); + + set_var(&parse->kv, buffer, sizeof(buffer), RO|DEF); } break; - + case GPS_UCAP: break; - + case GPS_CFGH: { CFGH cfgh; char buffer[512]; char *p; - + get_mbg_cfgh(&bufp, &cfgh); if (cfgh.valid) { + const char *cp; + uint16_t tmp_val; int i; - + p = buffer; - strlcpy(buffer, "gps_tot_51=\"", BUFFER_SIZE(buffer, p)); - p += strlen(p); + p = ap(buffer, sizeof(buffer), + p, "gps_tot_51=\""); mbg_tgps_str(&p, &cfgh.tot_51, BUFFER_SIZE(buffer, p)); - strlcpy(p, "\"", BUFFER_SIZE(buffer, p)); - set_var(&parse->kv, buffer, strlen(buffer)+1, RO); - + p = ap(buffer, sizeof(buffer), + p, "\""); + set_var(&parse->kv, buffer, sizeof(buffer), RO|COND_DEF); + p = buffer; - strlcpy(buffer, "gps_tot_63=\"", BUFFER_SIZE(buffer, p)); - p += strlen(p); + p = ap(buffer, sizeof(buffer), + p, "gps_tot_63=\""); mbg_tgps_str(&p, &cfgh.tot_63, BUFFER_SIZE(buffer, p)); - strlcpy(p, "\"", BUFFER_SIZE(buffer, p)); - set_var(&parse->kv, buffer, strlen(buffer)+1, RO); - + p = ap(buffer, sizeof(buffer), + p, "\""); + set_var(&parse->kv, buffer, sizeof(buffer), RO|COND_DEF); + p = buffer; - strlcpy(buffer, "gps_t0a=\"", BUFFER_SIZE(buffer, p)); - p += strlen(p); + p = ap(buffer, sizeof(buffer), + p, "gps_t0a=\""); mbg_tgps_str(&p, &cfgh.t0a, BUFFER_SIZE(buffer, p)); - strlcpy(p, "\"", BUFFER_SIZE(buffer, p)); - set_var(&parse->kv, buffer, strlen(buffer)+1, RO); - - for (i = MIN_SVNO; i < MAX_SVNO; i++) + p = ap(buffer, sizeof(buffer), + p, "\""); + set_var(&parse->kv, buffer, sizeof(buffer), RO|COND_DEF); + + for (i = 0; i < N_SVNO_GPS; i++) { p = buffer; - snprintf(p, BUFFER_SIZE(buffer, p), "gps_cfg[%d]=\"[0x%x] ", i, cfgh.cfg[i]); - p += strlen(p); - switch (cfgh.cfg[i] & 0x7) - { - case 0: - strlcpy(p, "BLOCK I", BUFFER_SIZE(buffer, p)); - break; - case 1: - strlcpy(p, "BLOCK II", BUFFER_SIZE(buffer, p)); - break; - default: - strlcpy(p, "bad CFG", BUFFER_SIZE(buffer, p)); - break; - } - strlcat(p, "\"", BUFFER_SIZE(buffer, p)); - set_var(&parse->kv, buffer, strlen(buffer)+1, RO); - - p = buffer; - snprintf(p, BUFFER_SIZE(buffer, p), "gps_health[%d]=\"[0x%x] ", i, cfgh.health[i]); - p += strlen(p); - switch ((cfgh.health[i] >> 5) & 0x7 ) - { - case 0: - strlcpy(p, "OK;", BUFFER_SIZE(buffer, p)); - break; - case 1: - strlcpy(p, "PARITY;", BUFFER_SIZE(buffer, p)); - break; - case 2: - strlcpy(p, "TLM/HOW;", BUFFER_SIZE(buffer, p)); - break; - case 3: - strlcpy(p, "Z-COUNT;", BUFFER_SIZE(buffer, p)); - break; - case 4: - strlcpy(p, "SUBFRAME 1,2,3;", BUFFER_SIZE(buffer, p)); - break; - case 5: - strlcpy(p, "SUBFRAME 4,5;", BUFFER_SIZE(buffer, p)); - break; - case 6: - strlcpy(p, "UPLOAD BAD;", BUFFER_SIZE(buffer, p)); - break; - case 7: - strlcpy(p, "DATA BAD;", BUFFER_SIZE(buffer, p)); - break; + p = ap(buffer, sizeof(buffer), p, "sv_info[%d]=\"PRN%d", i, i + N_SVNO_GPS); + + tmp_val = cfgh.health[i]; /* a 6 bit SV health code */ + p = ap(buffer, sizeof(buffer), p, "; health=0x%02x (", tmp_val); + /* "All Ones" has a special meaning" */ + if (tmp_val == 0x3F) /* satellite is unusable or doesn't even exist */ + cp = "SV UNAVAILABLE"; + else { + /* The MSB contains a summary of the 3 MSBs of the 8 bit health code, + * indicating if the data sent by the satellite is OK or not. */ + p = ap(buffer, sizeof(buffer), p, "DATA %s, ", (tmp_val & 0x20) ? "BAD" : "OK" ); + + /* The 5 LSBs contain the status of the different signals sent by the satellite. */ + switch (tmp_val & 0x1F) + { + case 0x00: cp = "SIGNAL OK"; break; + /* codes 0x01 through 0x1B indicate that one or more + * specific signal components are weak or dead. + * We don't decode this here in detail. */ + case 0x1C: cp = "SV IS TEMP OUT"; break; + case 0x1D: cp = "SV WILL BE TEMP OUT"; break; + default: cp = "TRANSMISSION PROBLEMS"; break; + } } - - p += strlen(p); - - switch (cfgh.health[i] & 0x1F) + p = ap(buffer, sizeof(buffer), p, "%s)", cp ); + + tmp_val = cfgh.cfg[i]; /* a 4 bit SV configuration/type code */ + p = ap(buffer, sizeof(buffer), p, "; cfg=0x%02x (", tmp_val); + switch (tmp_val & 0x7) { - case 0: - strlcpy(p, "SIGNAL OK", BUFFER_SIZE(buffer, p)); - break; - case 0x1C: - strlcpy(p, "SV TEMP OUT", BUFFER_SIZE(buffer, p)); - break; - case 0x1D: - strlcpy(p, "SV WILL BE TEMP OUT", BUFFER_SIZE(buffer, p)); - break; - case 0x1E: - break; - case 0x1F: - strlcpy(p, "MULTIPLE ERRS", BUFFER_SIZE(buffer, p)); - break; - default: - strlcpy(p, "TRANSMISSION PROBLEMS", BUFFER_SIZE(buffer, p)); - break; + case 0x00: cp = "(reserved)"; break; + case 0x01: cp = "BLOCK II/IIA/IIR"; break; + case 0x02: cp = "BLOCK IIR-M"; break; + case 0x03: cp = "BLOCK IIF"; break; + case 0x04: cp = "BLOCK III"; break; + default: cp = "unknown SV type"; break; } - - strlcat(p, "\"", sizeof(buffer)); - set_var(&parse->kv, buffer, strlen(buffer)+1, RO); + p = ap(buffer, sizeof(buffer), p, "%s", cp ); + if (tmp_val & 0x08) /* A-S is on, P-code is encrypted */ + p = ap( buffer, sizeof(buffer), p, ", A-S on" ); + + p = ap(buffer, sizeof(buffer), p, ")\""); + set_var(&parse->kv, buffer, sizeof(buffer), RO|COND_DEF); } } } break; - + case GPS_ALM: break; - + case GPS_EPH: break; - + case GPS_UTC: { UTC utc; char buffer[512]; char *p; - + p = buffer; - + get_mbg_utc(&bufp, &utc); - + if (utc.valid) { - strlcpy(p, "gps_utc_correction=\"", sizeof(buffer)); - p += strlen(p); + p = ap(buffer, sizeof(buffer), p, "gps_utc_correction=\""); mk_utcinfo(p, utc.t0t.wn, utc.WNlsf, utc.DNt, utc.delta_tls, utc.delta_tlsf, BUFFER_SIZE(buffer, p)); - strlcat(p, "\"", BUFFER_SIZE(buffer, p)); + p += strlen(p); + p = ap(buffer, sizeof(buffer), p, "\""); } else { - strlcpy(p, "gps_utc_correction=\"<NO UTC DATA>\"", BUFFER_SIZE(buffer, p)); + p = ap(buffer, sizeof(buffer), p, "gps_utc_correction=\"<NO UTC DATA>\""); } - set_var(&parse->kv, buffer, strlen(buffer)+1, RO|DEF); + set_var(&parse->kv, buffer, sizeof(buffer), RO|DEF); } break; - + case GPS_IONO: break; - + case GPS_ASCII_MSG: { ASCII_MSG gps_ascii_msg; char buffer[128]; - + get_mbg_ascii_msg(&bufp, &gps_ascii_msg); - + if (gps_ascii_msg.valid) { char buffer1[128]; mkreadable(buffer1, sizeof(buffer1), gps_ascii_msg.s, strlen(gps_ascii_msg.s), (int)0); - + snprintf(buffer, sizeof(buffer), "gps_message=\"%s\"", buffer1); } else - strlcpy(buffer, "gps_message=<NONE>", sizeof(buffer)); - - set_var(&parse->kv, buffer, strlen(buffer)+1, RO|DEF); + snprintf(buffer, sizeof(buffer), "gps_message=<NONE>"); + + set_var(&parse->kv, buffer, sizeof(buffer), RO|DEF); } - + break; - + default: break; } } else { - msyslog(LOG_DEBUG, "PARSE receiver #%d: gps16x_message: message checksum error: hdr_csum = 0x%x (expected 0x%lx), data_len = %d, data_csum = 0x%x (expected 0x%lx)", + msyslog(LOG_DEBUG, "PARSE receiver #%d: gps16x_message: message checksum error: hdr_csum = 0x%x (expected 0x%x), " + "data_len = %d, data_csum = 0x%x (expected 0x%x)", CLK_UNIT(parse->peer), - header.gps_hdr_csum, mbg_csum(parsetime->parse_msg + 1, 6), - header.gps_len, - header.gps_data_csum, mbg_csum(bufp, (unsigned)((header.gps_len < sizeof(parsetime->parse_msg)) ? header.gps_len : 0))); + header.hdr_csum, mbg_csum(parsetime->parse_msg + 1, 6), + header.len, + header.data_csum, mbg_csum(bufp, (unsigned)((header.len < sizeof(parsetime->parse_msg)) ? header.len : 0))); } } - + return; } @@ -4621,11 +4652,11 @@ gps16x_poll( ) { struct parseunit *parse = peer->procptr->unitptr; - - static GPS_MSG_HDR sequence[] = + + static GPS_MSG_HDR sequence[] = { { GPS_SW_REV, 0, 0, 0 }, - { GPS_STAT, 0, 0, 0 }, + { GPS_BVAR_STAT, 0, 0, 0 }, { GPS_UTC, 0, 0, 0 }, { GPS_ASCII_MSG, 0, 0, 0 }, { GPS_ANT_INFO, 0, 0, 0 }, @@ -4639,41 +4670,41 @@ gps16x_poll( unsigned char cmd_buffer[64]; unsigned char *outp = cmd_buffer; GPS_MSG_HDR *header; - + if (((poll_info_t *)parse->parse_type->cl_data)->rate) { parse->peer->procptr->nextaction = current_time + ((poll_info_t *)parse->parse_type->cl_data)->rate; } - if (sequence[parse->localstate].gps_cmd == (unsigned short)~0) + if (sequence[parse->localstate].cmd == (unsigned short)~0) parse->localstate = 0; - + header = sequence + parse->localstate++; - + *outp++ = SOH; /* start command */ - + put_mbg_header(&outp, header); outp = cmd_buffer + 1; - - header->gps_hdr_csum = (short)mbg_csum(outp, 6); + + header->hdr_csum = (short)mbg_csum(outp, 6); put_mbg_header(&outp, header); - + #ifdef DEBUG if (debug > 2) { char buffer[128]; - + mkreadable(buffer, sizeof(buffer), (char *)cmd_buffer, (unsigned)(outp - cmd_buffer), 1); printf("PARSE receiver #%d: transmitted message #%ld (%d bytes) >%s<\n", CLK_UNIT(parse->peer), parse->localstate - 1, (int)(outp - cmd_buffer), - buffer); + buffer); } #endif - - rtc = write(parse->generic->io.fd, cmd_buffer, (unsigned long)(outp - cmd_buffer)); - + + rtc = (int) write(parse->generic->io.fd, cmd_buffer, (unsigned long)(outp - cmd_buffer)); + if (rtc < 0) { ERR(ERR_BADIO) @@ -4722,7 +4753,7 @@ gps16x_poll_init( return 1; } #endif /* CLOCK_MEINBERG */ - + /**=========================================================================== ** clock polling support **/ @@ -4735,11 +4766,11 @@ poll_dpoll( struct parseunit *parse ) { - int rtc; + long rtc; const char *ps = ((poll_info_t *)parse->parse_type->cl_data)->string; - int ct = ((poll_info_t *)parse->parse_type->cl_data)->count; + long ct = ((poll_info_t *)parse->parse_type->cl_data)->count; - rtc = write(parse->generic->io.fd, ps, (unsigned long)ct); + rtc = write(parse->generic->io.fd, ps, ct); if (rtc < 0) { ERR(ERR_BADIO) @@ -4749,7 +4780,7 @@ poll_dpoll( if (rtc != ct) { ERR(ERR_BADIO) - msyslog(LOG_ERR, "PARSE receiver #%d: poll_dpoll: failed to send cmd incomplete (%d of %d bytes sent)", CLK_UNIT(parse->peer), rtc, ct); + msyslog(LOG_ERR, "PARSE receiver #%d: poll_dpoll: failed to send cmd incomplete (%ld of %ld bytes sent)", CLK_UNIT(parse->peer), rtc, ct); } clear_err(parse, ERR_BADIO); } @@ -4763,7 +4794,7 @@ poll_poll( ) { struct parseunit *parse = peer->procptr->unitptr; - + if (parse->parse_type->cl_poll) parse->parse_type->cl_poll(parse); @@ -4789,7 +4820,7 @@ poll_init( return 0; } - + /**=========================================================================== ** Trimble support **/ @@ -4819,7 +4850,7 @@ trimbletaip_init( else { tio.c_cc[VEOL] = TRIMBLETAIP_EOL; - + if (TTY_SETATTR(parse->generic->io.fd, &tio) == -1) { msyslog(LOG_ERR, "PARSE receiver #%d: trimbletaip_init: tcsetattr(fd, &tio): %m", CLK_UNIT(parse->peer)); @@ -4838,7 +4869,7 @@ static const char *taipinit[] = { ">FTM00020001<", (char *)0 }; - + static void trimbletaip_event( struct parseunit *parse, @@ -4855,7 +4886,7 @@ trimbletaip_event( iv = taipinit; while (*iv) { - int rtc = write(parse->generic->io.fd, *iv, strlen(*iv)); + int rtc = (int) write(parse->generic->io.fd, *iv, strlen(*iv)); if (rtc < 0) { msyslog(LOG_ERR, "PARSE receiver #%d: trimbletaip_event: failed to send cmd to clock: %m", CLK_UNIT(parse->peer)); @@ -4863,7 +4894,7 @@ trimbletaip_event( } else { - if (rtc != strlen(*iv)) + if (rtc != (int)strlen(*iv)) { msyslog(LOG_ERR, "PARSE receiver #%d: trimbletaip_event: failed to send cmd incomplete (%d of %d bytes sent)", CLK_UNIT(parse->peer), rtc, (int)strlen(*iv)); @@ -4983,19 +5014,19 @@ union uval { float fv; double dv; }; - + struct txbuf { short idx; /* index to first unused byte */ u_char *txt; /* pointer to actual data buffer */ }; -void sendcmd (struct txbuf *buf, int c); -void sendbyte (struct txbuf *buf, int b); -void sendetx (struct txbuf *buf, struct parseunit *parse); -void sendint (struct txbuf *buf, int a); -void sendflt (struct txbuf *buf, double a); - +void sendcmd (struct txbuf *buf, int c); +void sendbyte (struct txbuf *buf, int b); +void sendetx (struct txbuf *buf, struct parseunit *parse); +void sendint (struct txbuf *buf, int a); +void sendflt (struct txbuf *buf, double a); + void sendcmd( struct txbuf *buf, @@ -5007,12 +5038,12 @@ sendcmd( buf->idx = 2; } -void sendcmd (struct txbuf *buf, int c); -void sendbyte (struct txbuf *buf, int b); -void sendetx (struct txbuf *buf, struct parseunit *parse); -void sendint (struct txbuf *buf, int a); -void sendflt (struct txbuf *buf, double a); - +void sendcmd (struct txbuf *buf, int c); +void sendbyte (struct txbuf *buf, int b); +void sendetx (struct txbuf *buf, struct parseunit *parse); +void sendint (struct txbuf *buf, int a); +void sendflt (struct txbuf *buf, double a); + void sendbyte( struct txbuf *buf, @@ -5044,18 +5075,18 @@ sendetx( if (debug > 2) { char buffer[256]; - + mkreadable(buffer, sizeof(buffer), (char *)buf->txt, (unsigned)buf->idx, 1); printf("PARSE receiver #%d: transmitted message (%d bytes) >%s<\n", CLK_UNIT(parse->peer), - buf->idx, buffer); + buf->idx, buffer); } #endif clear_err(parse, ERR_BADIO); } } -void +void sendint( struct txbuf *buf, int a @@ -5075,7 +5106,7 @@ sendflt( int i; union uval uval; - uval.fv = a; + uval.fv = (float) a; #ifdef WORDS_BIGENDIAN for (i=0; i<=3; i++) #else @@ -5107,12 +5138,12 @@ trimbletsip_setup( if (t) t->last_reset = current_time; - + buf.txt = buffer; - + sendcmd(&buf, CMD_CVERSION); /* request software versions */ sendetx(&buf, parse); - + sendcmd(&buf, CMD_COPERPARAM); /* set operating parameters */ sendbyte(&buf, 4); /* static */ sendflt(&buf, 5.0*D2R); /* elevation angle mask = 10 deg XXX */ @@ -5120,25 +5151,25 @@ trimbletsip_setup( sendflt(&buf, 12.0); /* PDOP mask = 12 */ sendflt(&buf, 8.0); /* PDOP switch level = 8 */ sendetx(&buf, parse); - + sendcmd(&buf, CMD_CMODESEL); /* fix mode select */ sendbyte(&buf, 1); /* time transfer mode */ sendetx(&buf, parse); - + sendcmd(&buf, CMD_CMESSAGE); /* request system message */ sendetx(&buf, parse); - + sendcmd(&buf, CMD_CSUPER); /* superpacket fix */ sendbyte(&buf, 0x2); /* binary mode */ sendetx(&buf, parse); - + sendcmd(&buf, CMD_CIOOPTIONS); /* set I/O options */ sendbyte(&buf, TRIM_POS_OPT); /* position output */ sendbyte(&buf, 0x00); /* no velocity output */ sendbyte(&buf, TRIM_TIME_OPT); /* UTC, compute on seconds */ sendbyte(&buf, 0x00); /* no raw measurements */ sendetx(&buf, parse); - + sendcmd(&buf, CMD_CUTCPARAM); /* request UTC correction data */ sendetx(&buf, parse); @@ -5162,7 +5193,7 @@ trimble_check( u_char buffer[256]; struct txbuf buf; buf.txt = buffer; - + if (t) { if (current_time > t->last_msg + TRIMBLETSIP_IDLE_TIME) @@ -5170,18 +5201,18 @@ trimble_check( } poll_poll(parse->peer); /* emit query string and re-arm timer */ - + if (t && t->qtracking) { u_long oldsats = t->ltrack & ~t->ctrack; - + t->qtracking = 0; t->ltrack = t->ctrack; - + if (oldsats) { int i; - + for (i = 0; oldsats; i++) { if (oldsats & (1 << i)) { @@ -5192,7 +5223,7 @@ trimble_check( oldsats &= ~(1 << i); } } - + sendcmd(&buf, CMD_CSTATTRACK); sendbyte(&buf, 0x00); /* current tracking set */ sendetx(&buf, parse); @@ -5207,7 +5238,7 @@ trimbletsip_end( struct parseunit *parse ) { trimble_t *t = parse->localdata; - + if (t) { free(t); @@ -5238,9 +5269,9 @@ trimbletsip_init( if (!parse->localdata) { trimble_t *t; - + t = (trimble_t *)(parse->localdata = emalloc(sizeof(trimble_t))); - + if (t) { memset((char *)t, 0, sizeof(trimble_t)); @@ -5320,7 +5351,7 @@ getflt( ) { union uval uval; - + #ifdef WORDS_BIGENDIAN uval.bd[0] = *bp++; uval.bd[1] = *bp++; @@ -5341,7 +5372,7 @@ getdbl( ) { union uval uval; - + #ifdef WORDS_BIGENDIAN uval.bd[0] = *bp++; uval.bd[1] = *bp++; @@ -5369,7 +5400,7 @@ getshort( unsigned char *p ) { - return get_msb_short(&p); + return (int) get_msb_short(&p); } /*-------------------------------------------------- @@ -5386,7 +5417,7 @@ trimbletsip_message( { unsigned char *buffer = parsetime->parse_msg; unsigned int size = parsetime->parse_msglen; - + if ((size < 4) || (buffer[0] != DLE) || (buffer[size-1] != ETX) || @@ -5394,7 +5425,7 @@ trimbletsip_message( { #ifdef DEBUG if (debug > 2) { - int i; + size_t i; printf("TRIMBLE BAD packet, size %d:\n ", size); for (i = 0; i < size; i++) { @@ -5408,16 +5439,16 @@ trimbletsip_message( } else { - int var_flag; + u_short var_flag; trimble_t *tr = parse->localdata; unsigned int cmd = buffer[1]; char pbuffer[200]; char *t = pbuffer; cmd_info_t *s; - + #ifdef DEBUG if (debug > 3) { - int i; + size_t i; printf("TRIMBLE packet 0x%02x, size %d:\n ", cmd, size); for (i = 0; i < size; i++) { @@ -5430,12 +5461,12 @@ trimbletsip_message( if (tr) tr->last_msg = current_time; - + s = trimble_convert(cmd, trimble_rcmds); - + if (s) { - snprintf(t, BUFFER_SIZE(pbuffer, t), "%s=\"", s->varname); + t = ap(pbuffer, sizeof(pbuffer), t, "%s=\"", s->varname); } else { @@ -5443,47 +5474,43 @@ trimbletsip_message( return; } - var_flag = s->varmode; + var_flag = (u_short) s->varmode; - t += strlen(t); - switch(cmd) { case CMD_RCURTIME: - snprintf(t, BUFFER_SIZE(pbuffer, t), "%f, %d, %f", + t = ap(pbuffer, sizeof(pbuffer), t, "%f, %d, %f", getflt((unsigned char *)&mb(0)), getshort((unsigned char *)&mb(4)), getflt((unsigned char *)&mb(6))); break; - + case CMD_RBEST4: - strlcpy(t, "mode: ", BUFFER_SIZE(pbuffer, t)); - t += strlen(t); + t = ap(pbuffer, sizeof(pbuffer), t, "mode: "); switch (mb(0) & 0xF) { default: - snprintf(t, BUFFER_SIZE(pbuffer, t), "0x%x", mb(0) & 0x7); + t = ap(pbuffer, sizeof(pbuffer), t, + "0x%x", mb(0) & 0x7); break; case 1: - strlcpy(t, "0D", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "0D"); break; - + case 3: - strlcpy(t, "2D", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "2D"); break; - + case 4: - strlcpy(t, "3D", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "3D"); break; } - t += strlen(t); if (mb(0) & 0x10) - strlcpy(t, "-MANUAL, ", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "-MANUAL, "); else - strlcpy(t, "-AUTO, ", BUFFER_SIZE(pbuffer, t)); - t += strlen(t); - - snprintf(t, BUFFER_SIZE(pbuffer, t), "satellites %02d %02d %02d %02d, PDOP %.2f, HDOP %.2f, VDOP %.2f, TDOP %.2f", + t = ap(pbuffer, sizeof(pbuffer), t, "-AUTO, "); + + t = ap(pbuffer, sizeof(pbuffer), t, "satellites %02d %02d %02d %02d, PDOP %.2f, HDOP %.2f, VDOP %.2f, TDOP %.2f", mb(1), mb(2), mb(3), mb(4), getflt((unsigned char *)&mb(5)), getflt((unsigned char *)&mb(9)), @@ -5491,12 +5518,12 @@ trimbletsip_message( getflt((unsigned char *)&mb(17))); break; - + case CMD_RVERSION: - snprintf(t, BUFFER_SIZE(pbuffer, t), "%d.%d (%d/%d/%d)", + t = ap(pbuffer, sizeof(pbuffer), t, "%d.%d (%d/%d/%d)", mb(0)&0xff, mb(1)&0xff, 1900+(mb(4)&0xff), mb(2)&0xff, mb(3)&0xff); break; - + case CMD_RRECVHEALTH: { static const char *msgs[] = @@ -5510,57 +5537,54 @@ trimbletsip_message( "<BIT 6>", "<BIT 7>" }; - + int i, bits; - + switch (mb(0) & 0xFF) { default: - snprintf(t, BUFFER_SIZE(pbuffer, t), "illegal value 0x%02x", mb(0) & 0xFF); + t = ap(pbuffer, sizeof(pbuffer), t, "illegal value 0x%02x", mb(0) & 0xFF); break; case 0x00: - strlcpy(t, "doing position fixes", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "doing position fixes"); break; case 0x01: - strlcpy(t, "no GPS time yet", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "no GPS time yet"); break; case 0x03: - strlcpy(t, "PDOP too high", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "PDOP too high"); break; case 0x08: - strlcpy(t, "no usable satellites", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "no usable satellites"); break; case 0x09: - strlcpy(t, "only ONE usable satellite", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "only ONE usable satellite"); break; case 0x0A: - strlcpy(t, "only TWO usable satellites", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "only TWO usable satellites"); break; case 0x0B: - strlcpy(t, "only THREE usable satellites", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "only THREE usable satellites"); break; case 0x0C: - strlcpy(t, "the chosen satellite is unusable", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "the chosen satellite is unusable"); break; } - t += strlen(t); - bits = mb(1) & 0xFF; - + for (i = 0; i < 8; i++) if (bits & (0x1<<i)) { - snprintf(t, BUFFER_SIZE(pbuffer, t), ", %s", msgs[i]); - t += strlen(t); + t = ap(pbuffer, sizeof(pbuffer), t, ", %s", msgs[i]); } } break; - + case CMD_RMESSAGE: mkreadable(t, (int)BUFFER_SIZE(pbuffer, t), (char *)&mb(0), (unsigned)(size - 2 - (&mb(0) - buffer)), 0); break; - + case CMD_RMACHSTAT: { static const char *msgs[] = @@ -5574,39 +5598,36 @@ trimbletsip_message( "<BIT 6>", "<BIT 7>" }; - + int i, bits; - snprintf(t, BUFFER_SIZE(pbuffer, t), "machine id 0x%02x", mb(0) & 0xFF); - t += strlen(t); - + t = ap(pbuffer, sizeof(pbuffer), t, "machine id 0x%02x", mb(0) & 0xFF); bits = mb(1) & 0xFF; - + for (i = 0; i < 8; i++) if (bits & (0x1<<i)) { - snprintf(t, BUFFER_SIZE(pbuffer, t), ", %s", msgs[i]); - t += strlen(t); + t = ap(pbuffer, sizeof(pbuffer), t, ", %s", msgs[i]); } - snprintf(t, BUFFER_SIZE(pbuffer, t), ", Superpackets %ssupported", (mb(2) & 0xFF) ? "" :"un" ); + t = ap(pbuffer, sizeof(pbuffer), t, ", Superpackets %ssupported", (mb(2) & 0xFF) ? "" :"un" ); } break; - + case CMD_ROPERPARAM: - snprintf(t, BUFFER_SIZE(pbuffer, t), "%2x %.1f %.1f %.1f %.1f", + t = ap(pbuffer, sizeof(pbuffer), t, "%2x %.1f %.1f %.1f %.1f", mb(0), getflt((unsigned char *)&mb(1)), getflt((unsigned char *)&mb(5)), getflt((unsigned char *)&mb(9)), getflt((unsigned char *)&mb(13))); break; - + case CMD_RUTCPARAM: { float t0t = getflt((unsigned char *)&mb(14)); - short wnt = getshort((unsigned char *)&mb(18)); - short dtls = getshort((unsigned char *)&mb(12)); - short wnlsf = getshort((unsigned char *)&mb(20)); - short dn = getshort((unsigned char *)&mb(22)); - short dtlsf = getshort((unsigned char *)&mb(24)); + short wnt = (short) getshort((unsigned char *)&mb(18)); + short dtls = (short) getshort((unsigned char *)&mb(12)); + short wnlsf = (short) getshort((unsigned char *)&mb(20)); + short dn = (short) getshort((unsigned char *)&mb(22)); + short dtlsf = (short) getshort((unsigned char *)&mb(24)); if ((int)t0t != 0) { @@ -5614,19 +5635,19 @@ trimbletsip_message( } else { - strlcpy(t, "<NO UTC DATA>", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "<NO UTC DATA>"); } } break; case CMD_RSAT1BIAS: - snprintf(t, BUFFER_SIZE(pbuffer, t), "%.1fm %.2fm/s at %.1fs", + t = ap(pbuffer, sizeof(pbuffer), t, "%.1fm %.2fm/s at %.1fs", getflt(&mb(0)), getflt(&mb(4)), getflt(&mb(8))); break; case CMD_RIOOPTIONS: { - snprintf(t, BUFFER_SIZE(pbuffer, t), "%02x %02x %02x %02x", + t = ap(pbuffer, sizeof(pbuffer), t, "%02x %02x %02x %02x", mb(0), mb(1), mb(2), mb(3)); if (mb(0) != TRIM_POS_OPT || mb(2) != TRIM_TIME_OPT) @@ -5635,18 +5656,18 @@ trimbletsip_message( } } break; - + case CMD_RSPOSXYZ: { double x = getflt((unsigned char *)&mb(0)); double y = getflt((unsigned char *)&mb(4)); double z = getflt((unsigned char *)&mb(8)); double f = getflt((unsigned char *)&mb(12)); - + if (f > 0.0) - snprintf(t, BUFFER_SIZE(pbuffer, t), "x= %.1fm, y= %.1fm, z= %.1fm, time_of_fix= %f sec", - x, y, z, - f); + t = ap(pbuffer, sizeof(pbuffer), t, "x= %.1fm, y= %.1fm, z= %.1fm, time_of_fix= %f sec", + x, y, z, + f); else return; } @@ -5657,12 +5678,12 @@ trimbletsip_message( double lat = getflt((unsigned char *)&mb(0)); double lng = getflt((unsigned char *)&mb(4)); double f = getflt((unsigned char *)&mb(12)); - + if (f > 0.0) - snprintf(t, BUFFER_SIZE(pbuffer, t), "lat %f %c, long %f %c, alt %.2fm", - ((lat < 0.0) ? (-lat) : (lat))*RTOD, (lat < 0.0 ? 'S' : 'N'), - ((lng < 0.0) ? (-lng) : (lng))*RTOD, (lng < 0.0 ? 'W' : 'E'), - getflt((unsigned char *)&mb(8))); + t = ap(pbuffer, sizeof(pbuffer), t, "lat %f %c, long %f %c, alt %.2fm", + ((lat < 0.0) ? (-lat) : (lat))*RTOD, (lat < 0.0 ? 'S' : 'N'), + ((lng < 0.0) ? (-lng) : (lng))*RTOD, (lng < 0.0 ? 'W' : 'E'), + getflt((unsigned char *)&mb(8))); else return; } @@ -5673,16 +5694,16 @@ trimbletsip_message( double x = getdbl((unsigned char *)&mb(0)); double y = getdbl((unsigned char *)&mb(8)); double z = getdbl((unsigned char *)&mb(16)); - snprintf(t, BUFFER_SIZE(pbuffer, t), "x= %.1fm, y= %.1fm, z= %.1fm", - x, y, z); + t = ap(pbuffer, sizeof(pbuffer), t, "x= %.1fm, y= %.1fm, z= %.1fm", + x, y, z); } break; - + case CMD_RDOUBLELLA: { double lat = getdbl((unsigned char *)&mb(0)); double lng = getdbl((unsigned char *)&mb(8)); - snprintf(t, BUFFER_SIZE(pbuffer, t), "lat %f %c, lon %f %c, alt %.2fm", + t = ap(pbuffer, sizeof(pbuffer), t, "lat %f %c, lon %f %c, alt %.2fm", ((lat < 0.0) ? (-lat) : (lat))*RTOD, (lat < 0.0 ? 'S' : 'N'), ((lng < 0.0) ? (-lng) : (lng))*RTOD, (lng < 0.0 ? 'W' : 'E'), getdbl((unsigned char *)&mb(16))); @@ -5692,44 +5713,39 @@ trimbletsip_message( case CMD_RALLINVIEW: { int i, sats; - - strlcpy(t, "mode: ", BUFFER_SIZE(pbuffer, t)); - t += strlen(t); + + t = ap(pbuffer, sizeof(pbuffer), t, "mode: "); switch (mb(0) & 0x7) { default: - snprintf(t, BUFFER_SIZE(pbuffer, t), "0x%x", mb(0) & 0x7); + t = ap(pbuffer, sizeof(pbuffer), t, "0x%x", mb(0) & 0x7); break; case 3: - strlcpy(t, "2D", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "2D"); break; - + case 4: - strlcpy(t, "3D", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "3D"); break; } - t += strlen(t); if (mb(0) & 0x8) - strlcpy(t, "-MANUAL, ", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "-MANUAL, "); else - strlcpy(t, "-AUTO, ", BUFFER_SIZE(pbuffer, t)); - t += strlen(t); - + t = ap(pbuffer, sizeof(pbuffer), t, "-AUTO, "); + sats = (mb(0)>>4) & 0xF; - - snprintf(t, BUFFER_SIZE(pbuffer, t), "PDOP %.2f, HDOP %.2f, VDOP %.2f, TDOP %.2f, %d satellite%s in view: ", + + t = ap(pbuffer, sizeof(pbuffer), t, "PDOP %.2f, HDOP %.2f, VDOP %.2f, TDOP %.2f, %d satellite%s in view: ", getflt((unsigned char *)&mb(1)), getflt((unsigned char *)&mb(5)), getflt((unsigned char *)&mb(9)), getflt((unsigned char *)&mb(13)), sats, (sats == 1) ? "" : "s"); - t += strlen(t); for (i=0; i < sats; i++) { - snprintf(t, BUFFER_SIZE(pbuffer, t), "%s%02d", i ? ", " : "", mb(17+i)); - t += strlen(t); + t = ap(pbuffer, sizeof(pbuffer), t, "%s%02d", i ? ", " : "", mb(17+i)); if (tr) tr->ctrack |= (1 << (mb(17+i)-1)); } @@ -5740,60 +5756,54 @@ trimbletsip_message( } } break; - + case CMD_RSTATTRACK: { - snprintf(t-2, BUFFER_SIZE(pbuffer, t-2), "[%02d]=\"", mb(0)); /* add index to var name */ - t += strlen(t); - + t = ap(pbuffer, sizeof(pbuffer), t-2, "[%02d]=\"", mb(0)); /* add index to var name */ if (getflt((unsigned char *)&mb(4)) < 0.0) { - strlcpy(t, "<NO MEASUREMENTS>", BUFFER_SIZE(pbuffer, t)); - var_flag &= ~DEF; + t = ap(pbuffer, sizeof(pbuffer), t, "<NO MEASUREMENTS>"); + var_flag &= (u_short)(~DEF); } else - { - snprintf(t, BUFFER_SIZE(pbuffer, t), "ch=%d, acq=%s, eph=%d, signal_level= %5.2f, elevation= %5.2f, azimuth= %6.2f", + { + t = ap(pbuffer, sizeof(pbuffer), t, "ch=%d, acq=%s, eph=%d, signal_level= %5.2f, elevation= %5.2f, azimuth= %6.2f", (mb(1) & 0xFF)>>3, mb(2) ? ((mb(2) == 1) ? "ACQ" : "SRCH") : "NEVER", mb(3), getflt((unsigned char *)&mb(4)), getflt((unsigned char *)&mb(12)) * RTOD, getflt((unsigned char *)&mb(16)) * RTOD); - t += strlen(t); if (mb(20)) { - var_flag &= ~DEF; - strlcpy(t, ", OLD", BUFFER_SIZE(pbuffer, t)); + var_flag &= (u_short)(~DEF); + t = ap(pbuffer, sizeof(pbuffer), t, ", OLD"); } - t += strlen(t); if (mb(22)) { if (mb(22) == 1) - strlcpy(t, ", BAD PARITY", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, ", BAD PARITY"); else if (mb(22) == 2) - strlcpy(t, ", BAD EPH HEALTH", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, ", BAD EPH HEALTH"); } - t += strlen(t); if (mb(23)) - strlcpy(t, ", collecting data", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, ", collecting data"); } } break; - + default: - strlcpy(t, "<UNDECODED>", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "<UNDECODED>"); break; } - t += strlen(t); - strlcpy(t,"\"", BUFFER_SIZE(pbuffer, t)); + t = ap(pbuffer, sizeof(pbuffer), t, "\""); set_var(&parse->kv, pbuffer, sizeof(pbuffer), var_flag); } } - + /**============================================================ ** RAWDCF support **/ |