cmdmon: add offset command
Add a new command to modify the offset option of NTP sources and reference clocks.
This commit is contained in:
parent
719c6f6a8a
commit
ad37c409c9
7 changed files with 99 additions and 10 deletions
11
candm.h
11
candm.h
|
@ -110,7 +110,8 @@
|
||||||
#define REQ_RELOAD_SOURCES 70
|
#define REQ_RELOAD_SOURCES 70
|
||||||
#define REQ_DOFFSET2 71
|
#define REQ_DOFFSET2 71
|
||||||
#define REQ_MODIFY_SELECTOPTS 72
|
#define REQ_MODIFY_SELECTOPTS 72
|
||||||
#define N_REQUEST_TYPES 73
|
#define REQ_MODIFY_OFFSET 73
|
||||||
|
#define N_REQUEST_TYPES 74
|
||||||
|
|
||||||
/* Structure used to exchange timespecs independent of time_t size */
|
/* Structure used to exchange timespecs independent of time_t size */
|
||||||
typedef struct {
|
typedef struct {
|
||||||
|
@ -390,6 +391,13 @@ typedef struct {
|
||||||
int32_t EOR;
|
int32_t EOR;
|
||||||
} REQ_Modify_SelectOpts;
|
} REQ_Modify_SelectOpts;
|
||||||
|
|
||||||
|
typedef struct {
|
||||||
|
IPAddr address;
|
||||||
|
uint32_t ref_id;
|
||||||
|
Float new_offset;
|
||||||
|
int32_t EOR;
|
||||||
|
} REQ_Modify_Offset;
|
||||||
|
|
||||||
/* ================================================== */
|
/* ================================================== */
|
||||||
|
|
||||||
#define PKT_TYPE_CMD_REQUEST 1
|
#define PKT_TYPE_CMD_REQUEST 1
|
||||||
|
@ -497,6 +505,7 @@ typedef struct {
|
||||||
REQ_AuthData auth_data;
|
REQ_AuthData auth_data;
|
||||||
REQ_SelectData select_data;
|
REQ_SelectData select_data;
|
||||||
REQ_Modify_SelectOpts modify_select_opts;
|
REQ_Modify_SelectOpts modify_select_opts;
|
||||||
|
REQ_Modify_Offset modify_offset;
|
||||||
} data; /* Command specific parameters */
|
} data; /* Command specific parameters */
|
||||||
|
|
||||||
/* Padding used to prevent traffic amplification. It only defines the
|
/* Padding used to prevent traffic amplification. It only defines the
|
||||||
|
|
59
client.c
59
client.c
|
@ -344,6 +344,24 @@ parse_source_address(char *word, IPAddr *address)
|
||||||
|
|
||||||
/* ================================================== */
|
/* ================================================== */
|
||||||
|
|
||||||
|
static int
|
||||||
|
parse_source_address_or_refid(char *s, IPAddr *address, uint32_t *ref_id)
|
||||||
|
{
|
||||||
|
address->family = IPADDR_UNSPEC;
|
||||||
|
*ref_id = 0;
|
||||||
|
|
||||||
|
/* Don't allow hostnames to avoid conflicts with reference IDs */
|
||||||
|
if (UTI_StringToIdIP(s, address) || UTI_StringToIP(s, address))
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
if (CPS_ParseRefid(s, ref_id) > 0)
|
||||||
|
return 1;
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ================================================== */
|
||||||
|
|
||||||
static int
|
static int
|
||||||
read_mask_address(char *line, IPAddr *mask, IPAddr *address)
|
read_mask_address(char *line, IPAddr *mask, IPAddr *address)
|
||||||
{
|
{
|
||||||
|
@ -1031,6 +1049,7 @@ give_help(void)
|
||||||
"selectopts <address|refid> <+|-options>\0Modify selection options\0"
|
"selectopts <address|refid> <+|-options>\0Modify selection options\0"
|
||||||
"reselect\0Force reselecting synchronisation source\0"
|
"reselect\0Force reselecting synchronisation source\0"
|
||||||
"reselectdist <dist>\0Modify reselection distance\0"
|
"reselectdist <dist>\0Modify reselection distance\0"
|
||||||
|
"offset <address|refid> <offset>\0Modify offset correction\0"
|
||||||
"\0\0"
|
"\0\0"
|
||||||
"NTP sources:\0\0"
|
"NTP sources:\0\0"
|
||||||
"activity\0Check how many NTP sources are online/offline\0"
|
"activity\0Check how many NTP sources are online/offline\0"
|
||||||
|
@ -1141,7 +1160,8 @@ command_name_generator(const char *text, int state)
|
||||||
"clients", "cmdaccheck", "cmdallow", "cmddeny", "cyclelogs", "delete",
|
"clients", "cmdaccheck", "cmdallow", "cmddeny", "cyclelogs", "delete",
|
||||||
"deny", "dns", "dump", "exit", "help", "keygen", "local", "makestep",
|
"deny", "dns", "dump", "exit", "help", "keygen", "local", "makestep",
|
||||||
"manual", "maxdelay", "maxdelaydevratio", "maxdelayratio", "maxpoll",
|
"manual", "maxdelay", "maxdelaydevratio", "maxdelayratio", "maxpoll",
|
||||||
"maxupdateskew", "minpoll", "minstratum", "ntpdata", "offline", "online", "onoffline",
|
"maxupdateskew", "minpoll", "minstratum", "ntpdata",
|
||||||
|
"offline", "offset", "online", "onoffline",
|
||||||
"polltarget", "quit", "refresh", "rekey", "reload", "reselect", "reselectdist", "reset",
|
"polltarget", "quit", "refresh", "rekey", "reload", "reselect", "reselectdist", "reset",
|
||||||
"retries", "rtcdata", "selectdata", "selectopts", "serverstats", "settime",
|
"retries", "rtcdata", "selectdata", "selectopts", "serverstats", "settime",
|
||||||
"shutdown", "smoothing", "smoothtime", "sourcename", "sources", "sourcestats",
|
"shutdown", "smoothing", "smoothtime", "sourcename", "sources", "sourcestats",
|
||||||
|
@ -2858,6 +2878,34 @@ process_cmd_activity(const char *line)
|
||||||
|
|
||||||
/* ================================================== */
|
/* ================================================== */
|
||||||
|
|
||||||
|
static int
|
||||||
|
process_cmd_offset(CMD_Request *msg, char *line)
|
||||||
|
{
|
||||||
|
uint32_t ref_id;
|
||||||
|
IPAddr ip_addr;
|
||||||
|
double offset;
|
||||||
|
char *src;
|
||||||
|
|
||||||
|
src = line;
|
||||||
|
line = CPS_SplitWord(line);
|
||||||
|
|
||||||
|
if (!parse_source_address_or_refid(src, &ip_addr, &ref_id) ||
|
||||||
|
sscanf(line, "%lf", &offset) != 1) {
|
||||||
|
LOG(LOGS_ERR, "Invalid syntax for offset command");
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
|
||||||
|
UTI_IPHostToNetwork(&ip_addr, &msg->data.modify_offset.address);
|
||||||
|
msg->data.modify_offset.ref_id = htonl(ref_id);
|
||||||
|
msg->data.modify_offset.new_offset = UTI_FloatHostToNetwork(offset);
|
||||||
|
|
||||||
|
msg->command = htons(REQ_MODIFY_OFFSET);
|
||||||
|
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* ================================================== */
|
||||||
|
|
||||||
static int
|
static int
|
||||||
process_cmd_reselectdist(CMD_Request *msg, char *line)
|
process_cmd_reselectdist(CMD_Request *msg, char *line)
|
||||||
{
|
{
|
||||||
|
@ -2939,16 +2987,11 @@ process_cmd_selectopts(CMD_Request *msg, char *line)
|
||||||
|
|
||||||
src = line;
|
src = line;
|
||||||
line = CPS_SplitWord(line);
|
line = CPS_SplitWord(line);
|
||||||
ref_id = 0;
|
|
||||||
|
|
||||||
/* Don't allow hostnames to avoid conflicts with reference IDs */
|
if (!parse_source_address_or_refid(src, &ip_addr, &ref_id)) {
|
||||||
if (!UTI_StringToIdIP(src, &ip_addr) && !UTI_StringToIP(src, &ip_addr)) {
|
|
||||||
ip_addr.family = IPADDR_UNSPEC;
|
|
||||||
if (CPS_ParseRefid(src, &ref_id) == 0) {
|
|
||||||
LOG(LOGS_ERR, "Invalid syntax for selectopts command");
|
LOG(LOGS_ERR, "Invalid syntax for selectopts command");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
|
|
||||||
mask = options = 0;
|
mask = options = 0;
|
||||||
|
|
||||||
|
@ -3249,6 +3292,8 @@ process_line(char *line)
|
||||||
ret = process_cmd_ntpdata(line);
|
ret = process_cmd_ntpdata(line);
|
||||||
} else if (!strcmp(command, "offline")) {
|
} else if (!strcmp(command, "offline")) {
|
||||||
do_normal_submit = process_cmd_offline(&tx_message, line);
|
do_normal_submit = process_cmd_offline(&tx_message, line);
|
||||||
|
} else if (!strcmp(command, "offset")) {
|
||||||
|
do_normal_submit = process_cmd_offset(&tx_message, line);
|
||||||
} else if (!strcmp(command, "online")) {
|
} else if (!strcmp(command, "online")) {
|
||||||
do_normal_submit = process_cmd_online(&tx_message, line);
|
do_normal_submit = process_cmd_online(&tx_message, line);
|
||||||
} else if (!strcmp(command, "onoffline")) {
|
} else if (!strcmp(command, "onoffline")) {
|
||||||
|
|
23
cmdmon.c
23
cmdmon.c
|
@ -145,6 +145,7 @@ static const char permissions[] = {
|
||||||
PERMIT_AUTH, /* RELOAD_SOURCES */
|
PERMIT_AUTH, /* RELOAD_SOURCES */
|
||||||
PERMIT_AUTH, /* DOFFSET2 */
|
PERMIT_AUTH, /* DOFFSET2 */
|
||||||
PERMIT_AUTH, /* MODIFY_SELECTOPTS */
|
PERMIT_AUTH, /* MODIFY_SELECTOPTS */
|
||||||
|
PERMIT_AUTH, /* MODIFY_OFFSET */
|
||||||
};
|
};
|
||||||
|
|
||||||
/* ================================================== */
|
/* ================================================== */
|
||||||
|
@ -1418,6 +1419,24 @@ handle_modify_selectopts(CMD_Request *rx_message, CMD_Reply *tx_message)
|
||||||
tx_message->status = htons(STT_NOSUCHSOURCE);
|
tx_message->status = htons(STT_NOSUCHSOURCE);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/* ================================================== */
|
||||||
|
|
||||||
|
static void
|
||||||
|
handle_modify_offset(CMD_Request *rx_message, CMD_Reply *tx_message)
|
||||||
|
{
|
||||||
|
uint32_t ref_id;
|
||||||
|
IPAddr ip_addr;
|
||||||
|
double offset;
|
||||||
|
|
||||||
|
UTI_IPNetworkToHost(&rx_message->data.modify_offset.address, &ip_addr);
|
||||||
|
ref_id = ntohl(rx_message->data.modify_offset.ref_id);
|
||||||
|
offset = UTI_FloatNetworkToHost(rx_message->data.modify_offset.new_offset);
|
||||||
|
|
||||||
|
if ((ip_addr.family != IPADDR_UNSPEC && !NSR_ModifyOffset(&ip_addr, offset)) ||
|
||||||
|
(ip_addr.family == IPADDR_UNSPEC && !RCL_ModifyOffset(ref_id, offset)))
|
||||||
|
tx_message->status = htons(STT_NOSUCHSOURCE);
|
||||||
|
}
|
||||||
|
|
||||||
/* ================================================== */
|
/* ================================================== */
|
||||||
/* Read a packet and process it */
|
/* Read a packet and process it */
|
||||||
|
|
||||||
|
@ -1818,6 +1837,10 @@ read_from_cmd_socket(int sock_fd, int event, void *anything)
|
||||||
handle_modify_selectopts(&rx_message, &tx_message);
|
handle_modify_selectopts(&rx_message, &tx_message);
|
||||||
break;
|
break;
|
||||||
|
|
||||||
|
case REQ_MODIFY_OFFSET:
|
||||||
|
handle_modify_offset(&rx_message, &tx_message);
|
||||||
|
break;
|
||||||
|
|
||||||
default:
|
default:
|
||||||
DEBUG_LOG("Unhandled command %d", rx_command);
|
DEBUG_LOG("Unhandled command %d", rx_command);
|
||||||
tx_message.status = htons(STT_FAILED);
|
tx_message.status = htons(STT_FAILED);
|
||||||
|
|
|
@ -556,6 +556,13 @@ The *reselectdist* command sets the reselection distance. It is equivalent to
|
||||||
the <<chrony.conf.adoc#reselectdist,*reselectdist*>> directive in the
|
the <<chrony.conf.adoc#reselectdist,*reselectdist*>> directive in the
|
||||||
configuration file.
|
configuration file.
|
||||||
|
|
||||||
|
[[offset]]*offset* _address|refid_ _offset_::
|
||||||
|
The *offset* command modifies the offset correction of an NTP source specified
|
||||||
|
by IP address (or the _ID#XXXXXXXXXX_ identifier used for unknown addresses),
|
||||||
|
or a reference clock specified by reference ID as a string. It is equivalent to
|
||||||
|
the *offset* option in the <<chrony.conf.adoc#server,*server*>> or
|
||||||
|
<<chrony.conf.adoc#refclock,*refclock*>> directive respectively.
|
||||||
|
|
||||||
=== NTP sources
|
=== NTP sources
|
||||||
|
|
||||||
[[activity]]*activity*::
|
[[activity]]*activity*::
|
||||||
|
|
|
@ -130,6 +130,7 @@ static const struct request_length request_lengths[] = {
|
||||||
REQ_LENGTH_ENTRY(null, null), /* RELOAD_SOURCES */
|
REQ_LENGTH_ENTRY(null, null), /* RELOAD_SOURCES */
|
||||||
REQ_LENGTH_ENTRY(doffset, null), /* DOFFSET2 */
|
REQ_LENGTH_ENTRY(doffset, null), /* DOFFSET2 */
|
||||||
REQ_LENGTH_ENTRY(modify_select_opts, null), /* MODIFY_SELECTOPTS */
|
REQ_LENGTH_ENTRY(modify_select_opts, null), /* MODIFY_SELECTOPTS */
|
||||||
|
REQ_LENGTH_ENTRY(modify_offset, null), /* MODIFY_OFFSET */
|
||||||
};
|
};
|
||||||
|
|
||||||
static const uint16_t reply_lengths[] = {
|
static const uint16_t reply_lengths[] = {
|
||||||
|
|
|
@ -165,6 +165,7 @@ for chronyc_conf in \
|
||||||
"offline" \
|
"offline" \
|
||||||
"offline 255.255.255.0/1.2.3.0" \
|
"offline 255.255.255.0/1.2.3.0" \
|
||||||
"offline 1.2.3.0/24" \
|
"offline 1.2.3.0/24" \
|
||||||
|
"offset 1.2.3.4 1.0" \
|
||||||
"online" \
|
"online" \
|
||||||
"online 1.2.3.0/24" \
|
"online 1.2.3.0/24" \
|
||||||
"onoffline" \
|
"onoffline" \
|
||||||
|
@ -351,6 +352,7 @@ maxpoll 192.168.123.1 5
|
||||||
maxupdateskew 192.168.123.1 10.0
|
maxupdateskew 192.168.123.1 10.0
|
||||||
minpoll 192.168.123.1 3
|
minpoll 192.168.123.1 3
|
||||||
minstratum 192.168.123.1 1
|
minstratum 192.168.123.1 1
|
||||||
|
offset 192.168.123.1 -1.0
|
||||||
polltarget 192.168.123.1 10
|
polltarget 192.168.123.1 10
|
||||||
selectopts 192.168.123.1 +trust +prefer -require
|
selectopts 192.168.123.1 +trust +prefer -require
|
||||||
selectdata
|
selectdata
|
||||||
|
@ -375,6 +377,7 @@ check_chronyc_output "^200 OK
|
||||||
200 OK
|
200 OK
|
||||||
200 OK
|
200 OK
|
||||||
200 OK
|
200 OK
|
||||||
|
200 OK
|
||||||
S Name/IP Address Auth COpts EOpts Last Score Interval Leap
|
S Name/IP Address Auth COpts EOpts Last Score Interval Leap
|
||||||
=======================================================================
|
=======================================================================
|
||||||
M node1\.net1\.clk N \-PT\-\- \-PT\-\- 0 1\.0 \+0ns \+0ns \?
|
M node1\.net1\.clk N \-PT\-\- \-PT\-\- 0 1\.0 \+0ns \+0ns \?
|
||||||
|
|
|
@ -28,6 +28,7 @@ for command in \
|
||||||
"local" \
|
"local" \
|
||||||
"online" \
|
"online" \
|
||||||
"onoffline" \
|
"onoffline" \
|
||||||
|
"offset $server 0.0" \
|
||||||
"maxdelay $server 1e-1" \
|
"maxdelay $server 1e-1" \
|
||||||
"maxdelaydevratio $server 5.0" \
|
"maxdelaydevratio $server 5.0" \
|
||||||
"maxdelayratio $server 3.0" \
|
"maxdelayratio $server 3.0" \
|
||||||
|
|
Loading…
Reference in a new issue