/*
* CDDL HEADER START
*
* The contents of this file are subject to the terms of the
* Common Development and Distribution License, Version 1.0 only
* (the "License"). You may not use this file except in compliance
* with the License.
*
* You can obtain a copy of the license at usr/src/OPENSOLARIS.LICENSE
* See the License for the specific language governing permissions
* and limitations under the License.
*
* When distributing Covered Code, include this CDDL HEADER in each
* file and include the License file at usr/src/OPENSOLARIS.LICENSE.
* If applicable, add the following below this CDDL HEADER, with the
* fields enclosed by brackets "[]" replaced with your own identifying
* information: Portions Copyright [yyyy] [name of copyright owner]
*
* CDDL HEADER END
*/
/*
* Copyright 2005 Sun Microsystems, Inc. All rights reserved.
* Use is subject to license terms.
*/
#pragma ident "%Z%%M% %I% %E% SMI"
#include <fcntl.h>
#include <sys/sysmacros.h>
#include <netdb.h>
#include <stdio.h>
#include <string.h>
#include <tzfile.h>
#include "snoop.h"
#include "ntp.h"
/*
* In verbose mode, how many octets of the control-mode data payload
* are displayed per line of output. The value 64 fits well on an
* 80-column screen and, as a power of 2, is easily correlated to
* hexadecimal output.
*/
extern char *dlc_header;
static char *show_leap(int);
static char *show_mode(int);
static double s_fixed_to_double(struct s_fixedpt *);
static char *iso_date_time(time_t);
static char *show_operation(int);
int
{
unsigned int i, j, macbytes;
unsigned int proto_version;
unsigned int datalen;
unsigned int sofar = 0;
char *datap;
union ntp_pkt_buf {
union ntpc_buf {
} ntpc_msg;
union ntpp_buf {
} ntpp_msg;
} fragbuf;
/*
* Copying packet contents into a local buffer avoids
* problems of interpretation if the packet is truncated.
*/
case MODE_SYM_ACT:
case MODE_SYM_PAS:
case MODE_CLIENT:
case MODE_SERVER:
case MODE_BROADCAST:
(void) sprintf(get_sum_line(),
"NTP %s [st=%hd] (%s)",
break;
case MODE_CONTROL:
(void) sprintf(get_sum_line(),
"NTP %s "
break;
default:
(void) sprintf(get_sum_line(),
"NTP %s",
break;
}
}
show_space();
case MODE_SYM_ACT:
case MODE_SYM_PAS:
case MODE_CLIENT:
case MODE_SERVER:
case MODE_BROADCAST:
dlc_header, 1),
"Leap = 0x%x (%s)",
dlc_header, 1),
dlc_header, 1),
"Mode = %hu (%s)",
dlc_header, 1),
"Stratum = %d (%s)",
"secondary reference");
dlc_header, 1),
"Precision = %d seconds",
dlc_header, 1),
"Synchronizing distance = 0x%04x.%04x (%f)",
dlc_header, 1),
"Synchronizing dispersion = 0x%04x.%04x (%f)",
1), "Reference time = 0x%08lx.%08lx (%s)",
"Originate time = 0x%08lx.%08lx (%s)",
"Receive time = 0x%08lx.%08lx (%s)",
"Transmit time = 0x%08lx.%08lx (%s)",
if (proto_version > 3 ||
/*
* A newer protocol version we can't parse,
* or v3 packet with no valid authentication.
*/
break;
}
dlc_header, 1),
for (i = 0, j = 0; i < macbytes; i++) {
}
hbuf[j] = '\0';
dlc_header, 1),
break;
case MODE_CONTROL:
/* NTP Control Message, mode 6 */
dlc_header, 1),
"Leap = 0x%x (%s)",
dlc_header, 1),
dlc_header, 1),
"Mode = %hu (%s)",
dlc_header, 1),
"Flags and operation code = 0x%02x",
dlc_header, 1),
" %s",
"request"));
dlc_header, 1),
" %s",
"success"));
dlc_header, 1),
" %s",
"no more"));
dlc_header, 1),
" ...x xxxx = %hd (%s)",
dlc_header, 1),
"Sequence = %hu",
dlc_header, 1),
"Status = 0x%04hx",
dlc_header, 1),
"Assoc ID = %hu",
dlc_header, 1),
"Data offset = %hu",
dlc_header, 1),
"Data bytes = %hu",
if (datalen == 0) {
break;
} else if (datalen > NTPC_DATA_MAXLEN) {
}
show_space();
do {
dlc_header, 1),
"\"%s\"",
}
show_trailer();
break;
case MODE_PRIVATE:
/* NTP Private Message, mode 7 */
" %s",
"request"));
" %s",
dlc_header, 1),
dlc_header, 1),
" %s",
"unauthenticated"));
dlc_header, 1),
" .xxx xxxx = %hu (sequence number)",
break;
default:
/* Unknown mode */
break;
}
}
return (fraglen);
}
char *
{
switch (leap) {
case NO_WARNING: return ("OK");
case PLUS_SEC: return ("add a second (61 seconds)");
case MINUS_SEC: return ("minus a second (59 seconds)");
case ALARM: return ("alarm condition (clock unsynchronized)");
default: return ("unknown");
}
}
char *
{
switch (mode) {
case MODE_UNSPEC: return ("unspecified");
case MODE_SYM_ACT: return ("symmetric active");
case MODE_SYM_PAS: return ("symmetric passive");
case MODE_CLIENT: return ("client");
case MODE_SERVER: return ("server");
case MODE_BROADCAST: return ("broadcast");
case MODE_CONTROL: return ("control");
case MODE_PRIVATE: return ("private");
default: return ("unknown");
}
}
char *
{
extern char *inet_ntoa();
switch (mode) {
case 0:
case 1:
break;
default:
break;
}
return (buff);
}
/*
* Here we have to worry about the high order bit being signed
*/
double
{
double a;
a = a / 65536.0; /* shift dec point over by 16 bits */
a = -a;
} else {
a = a / 65536.0; /* shift dec point over by 16 bits */
}
return (a);
}
/*
* Consistent with RFC-3339, ISO 8601.
*/
char *
{
return (tbuf);
}
/*
* The base of NTP timestamps is 1900-01-01 00:00:00.00000
*/
char *
{
unsigned long fracsec;
buff[0] = '\0';
return (buff);
}
return (buff);
}
char *
{
switch (op) {
case CTL_OP_UNSPEC: return ("unspecified");
case CTL_OP_READSTAT: return ("read stats");
case CTL_OP_READVAR: return ("read var");
case CTL_OP_WRITEVAR: return ("write var");
case CTL_OP_READCLOCK: return ("read clock");
case CTL_OP_WRITECLOCK: return ("write clock");
case CTL_OP_SETTRAP: return ("set trap");
case CTL_OP_ASYNCMSG: return ("async msg");
case CTL_OP_UNSETTRAP: return ("unset trap");
default: return ("unknown");
}
}