1/* 2 * ntp_request.c - respond to information requests 3 */ 4 5#ifdef HAVE_CONFIG_H 6# include <config.h> 7#endif 8 9#include "ntpd.h" 10#include "ntp_io.h" 11#include "ntp_request.h" 12#include "ntp_control.h" 13#include "ntp_refclock.h" 14#include "ntp_if.h" 15#include "ntp_stdlib.h" 16#include "ntp_assert.h" 17 18#include <stdio.h> 19#include <stddef.h> 20#include <signal.h> 21#ifdef HAVE_NETINET_IN_H 22#include <netinet/in.h> 23#endif 24#include <arpa/inet.h> 25 26#include "recvbuff.h" 27 28#ifdef KERNEL_PLL 29#include "ntp_syscall.h" 30#endif /* KERNEL_PLL */ 31 32/* 33 * Structure to hold request procedure information 34 */ 35#define NOAUTH 0 36#define AUTH 1 37 38#define NO_REQUEST (-1) 39/* 40 * Because we now have v6 addresses in the messages, we need to compensate 41 * for the larger size. Therefore, we introduce the alternate size to 42 * keep us friendly with older implementations. A little ugly. 43 */ 44static int client_v6_capable = 0; /* the client can handle longer messages */ 45 46#define v6sizeof(type) (client_v6_capable ? sizeof(type) : v4sizeof(type)) 47 48struct req_proc { 49 short request_code; /* defined request code */ 50 short needs_auth; /* true when authentication needed */ 51 short sizeofitem; /* size of request data item (older size)*/ 52 short v6_sizeofitem; /* size of request data item (new size)*/ 53 void (*handler) (sockaddr_u *, struct interface *, 54 struct req_pkt *); /* routine to handle request */ 55}; 56 57/* 58 * Universal request codes 59 */ 60static struct req_proc univ_codes[] = { 61 { NO_REQUEST, NOAUTH, 0, 0 } 62}; 63 64static void req_ack (sockaddr_u *, struct interface *, struct req_pkt *, int); 65static char * prepare_pkt (sockaddr_u *, struct interface *, 66 struct req_pkt *, size_t); 67static char * more_pkt (void); 68static void flush_pkt (void); 69static void peer_list (sockaddr_u *, struct interface *, struct req_pkt *); 70static void peer_list_sum (sockaddr_u *, struct interface *, struct req_pkt *); 71static void peer_info (sockaddr_u *, struct interface *, struct req_pkt *); 72static void peer_stats (sockaddr_u *, struct interface *, struct req_pkt *); 73static void sys_info (sockaddr_u *, struct interface *, struct req_pkt *); 74static void sys_stats (sockaddr_u *, struct interface *, struct req_pkt *); 75static void mem_stats (sockaddr_u *, struct interface *, struct req_pkt *); 76static void io_stats (sockaddr_u *, struct interface *, struct req_pkt *); 77static void timer_stats (sockaddr_u *, struct interface *, struct req_pkt *); 78static void loop_info (sockaddr_u *, struct interface *, struct req_pkt *); 79static void do_conf (sockaddr_u *, struct interface *, struct req_pkt *); 80static void do_unconf (sockaddr_u *, struct interface *, struct req_pkt *); 81static void set_sys_flag (sockaddr_u *, struct interface *, struct req_pkt *); 82static void clr_sys_flag (sockaddr_u *, struct interface *, struct req_pkt *); 83static void setclr_flags (sockaddr_u *, struct interface *, struct req_pkt *, u_long); 84static void list_restrict (sockaddr_u *, struct interface *, struct req_pkt *); 85static void do_resaddflags (sockaddr_u *, struct interface *, struct req_pkt *); 86static void do_ressubflags (sockaddr_u *, struct interface *, struct req_pkt *); 87static void do_unrestrict (sockaddr_u *, struct interface *, struct req_pkt *); 88static void do_restrict (sockaddr_u *, struct interface *, struct req_pkt *, int); 89static void mon_getlist_0 (sockaddr_u *, struct interface *, struct req_pkt *); 90static void mon_getlist_1 (sockaddr_u *, struct interface *, struct req_pkt *); 91static void reset_stats (sockaddr_u *, struct interface *, struct req_pkt *); 92static void reset_peer (sockaddr_u *, struct interface *, struct req_pkt *); 93static void do_key_reread (sockaddr_u *, struct interface *, struct req_pkt *); 94static void trust_key (sockaddr_u *, struct interface *, struct req_pkt *); 95static void untrust_key (sockaddr_u *, struct interface *, struct req_pkt *); 96static void do_trustkey (sockaddr_u *, struct interface *, struct req_pkt *, u_long); 97static void get_auth_info (sockaddr_u *, struct interface *, struct req_pkt *); 98static void reset_auth_stats (void); 99static void req_get_traps (sockaddr_u *, struct interface *, struct req_pkt *); 100static void req_set_trap (sockaddr_u *, struct interface *, struct req_pkt *); 101static void req_clr_trap (sockaddr_u *, struct interface *, struct req_pkt *); 102static void do_setclr_trap (sockaddr_u *, struct interface *, struct req_pkt *, int); 103static void set_request_keyid (sockaddr_u *, struct interface *, struct req_pkt *); 104static void set_control_keyid (sockaddr_u *, struct interface *, struct req_pkt *); 105static void get_ctl_stats (sockaddr_u *, struct interface *, struct req_pkt *); 106static void get_if_stats (sockaddr_u *, struct interface *, struct req_pkt *); 107static void do_if_reload (sockaddr_u *, struct interface *, struct req_pkt *); 108#ifdef KERNEL_PLL 109static void get_kernel_info (sockaddr_u *, struct interface *, struct req_pkt *); 110#endif /* KERNEL_PLL */ 111#ifdef REFCLOCK 112static void get_clock_info (sockaddr_u *, struct interface *, struct req_pkt *); 113static void set_clock_fudge (sockaddr_u *, struct interface *, struct req_pkt *); 114#endif /* REFCLOCK */ 115#ifdef REFCLOCK 116static void get_clkbug_info (sockaddr_u *, struct interface *, struct req_pkt *); 117#endif /* REFCLOCK */ 118 119/* 120 * ntpd request codes 121 */ 122static struct req_proc ntp_codes[] = { 123 { REQ_PEER_LIST, NOAUTH, 0, 0, peer_list }, 124 { REQ_PEER_LIST_SUM, NOAUTH, 0, 0, peer_list_sum }, 125 { REQ_PEER_INFO, NOAUTH, v4sizeof(struct info_peer_list), 126 sizeof(struct info_peer_list), peer_info}, 127 { REQ_PEER_STATS, NOAUTH, v4sizeof(struct info_peer_list), 128 sizeof(struct info_peer_list), peer_stats}, 129 { REQ_SYS_INFO, NOAUTH, 0, 0, sys_info }, 130 { REQ_SYS_STATS, NOAUTH, 0, 0, sys_stats }, 131 { REQ_IO_STATS, NOAUTH, 0, 0, io_stats }, 132 { REQ_MEM_STATS, NOAUTH, 0, 0, mem_stats }, 133 { REQ_LOOP_INFO, NOAUTH, 0, 0, loop_info }, 134 { REQ_TIMER_STATS, NOAUTH, 0, 0, timer_stats }, 135 { REQ_CONFIG, AUTH, v4sizeof(struct conf_peer), 136 sizeof(struct conf_peer), do_conf }, 137 { REQ_UNCONFIG, AUTH, v4sizeof(struct conf_unpeer), 138 sizeof(struct conf_unpeer), do_unconf }, 139 { REQ_SET_SYS_FLAG, AUTH, sizeof(struct conf_sys_flags), 140 sizeof(struct conf_sys_flags), set_sys_flag }, 141 { REQ_CLR_SYS_FLAG, AUTH, sizeof(struct conf_sys_flags), 142 sizeof(struct conf_sys_flags), clr_sys_flag }, 143 { REQ_GET_RESTRICT, NOAUTH, 0, 0, list_restrict }, 144 { REQ_RESADDFLAGS, AUTH, v4sizeof(struct conf_restrict), 145 sizeof(struct conf_restrict), do_resaddflags }, 146 { REQ_RESSUBFLAGS, AUTH, v4sizeof(struct conf_restrict), 147 sizeof(struct conf_restrict), do_ressubflags }, 148 { REQ_UNRESTRICT, AUTH, v4sizeof(struct conf_restrict), 149 sizeof(struct conf_restrict), do_unrestrict }, 150 { REQ_MON_GETLIST, NOAUTH, 0, 0, mon_getlist_0 }, 151 { REQ_MON_GETLIST_1, NOAUTH, 0, 0, mon_getlist_1 }, 152 { REQ_RESET_STATS, AUTH, sizeof(struct reset_flags), 0, reset_stats }, 153 { REQ_RESET_PEER, AUTH, v4sizeof(struct conf_unpeer), 154 sizeof(struct conf_unpeer), reset_peer }, 155 { REQ_REREAD_KEYS, AUTH, 0, 0, do_key_reread }, 156 { REQ_TRUSTKEY, AUTH, sizeof(u_long), sizeof(u_long), trust_key }, 157 { REQ_UNTRUSTKEY, AUTH, sizeof(u_long), sizeof(u_long), untrust_key }, 158 { REQ_AUTHINFO, NOAUTH, 0, 0, get_auth_info }, 159 { REQ_TRAPS, NOAUTH, 0, 0, req_get_traps }, 160 { REQ_ADD_TRAP, AUTH, v4sizeof(struct conf_trap), 161 sizeof(struct conf_trap), req_set_trap }, 162 { REQ_CLR_TRAP, AUTH, v4sizeof(struct conf_trap), 163 sizeof(struct conf_trap), req_clr_trap }, 164 { REQ_REQUEST_KEY, AUTH, sizeof(u_long), sizeof(u_long), 165 set_request_keyid }, 166 { REQ_CONTROL_KEY, AUTH, sizeof(u_long), sizeof(u_long), 167 set_control_keyid }, 168 { REQ_GET_CTLSTATS, NOAUTH, 0, 0, get_ctl_stats }, 169#ifdef KERNEL_PLL 170 { REQ_GET_KERNEL, NOAUTH, 0, 0, get_kernel_info }, 171#endif 172#ifdef REFCLOCK 173 { REQ_GET_CLOCKINFO, NOAUTH, sizeof(u_int32), sizeof(u_int32), 174 get_clock_info }, 175 { REQ_SET_CLKFUDGE, AUTH, sizeof(struct conf_fudge), 176 sizeof(struct conf_fudge), set_clock_fudge }, 177 { REQ_GET_CLKBUGINFO, NOAUTH, sizeof(u_int32), sizeof(u_int32), 178 get_clkbug_info }, 179#endif 180 { REQ_IF_STATS, AUTH, 0, 0, get_if_stats }, 181 { REQ_IF_RELOAD, AUTH, 0, 0, do_if_reload }, 182 183 { NO_REQUEST, NOAUTH, 0, 0, 0 } 184}; 185 186 187/* 188 * Authentication keyid used to authenticate requests. Zero means we 189 * don't allow writing anything. 190 */ 191keyid_t info_auth_keyid; 192 193/* 194 * Statistic counters to keep track of requests and responses. 195 */ 196u_long numrequests; /* number of requests we've received */ 197u_long numresppkts; /* number of resp packets sent with data */ 198 199u_long errorcounter[INFO_ERR_AUTH+1]; /* lazy way to count errors, indexed */ 200/* by the error code */ 201 202/* 203 * A hack. To keep the authentication module clear of ntp-ism's, we 204 * include a time reset variable for its stats here. 205 */ 206static u_long auth_timereset; 207 208/* 209 * Response packet used by these routines. Also some state information 210 * so that we can handle packet formatting within a common set of 211 * subroutines. Note we try to enter data in place whenever possible, 212 * but the need to set the more bit correctly means we occasionally 213 * use the extra buffer and copy. 214 */ 215static struct resp_pkt rpkt; 216static int reqver; 217static int seqno; 218static int nitems; 219static int itemsize; 220static int databytes; 221static char exbuf[RESP_DATA_SIZE]; 222static int usingexbuf; 223static sockaddr_u *toaddr; 224static struct interface *frominter; 225 226/* 227 * init_request - initialize request data 228 */ 229void 230init_request (void) 231{ 232 int i; 233 234 numrequests = 0; 235 numresppkts = 0; 236 auth_timereset = 0; 237 info_auth_keyid = 0; /* by default, can't do this */ 238 239 for (i = 0; i < sizeof(errorcounter)/sizeof(errorcounter[0]); i++) 240 errorcounter[i] = 0; 241} 242 243 244/* 245 * req_ack - acknowledge request with no data 246 */ 247static void 248req_ack( 249 sockaddr_u *srcadr, 250 struct interface *inter, 251 struct req_pkt *inpkt, 252 int errcode 253 ) 254{ 255 /* 256 * fill in the fields 257 */ 258 rpkt.rm_vn_mode = RM_VN_MODE(RESP_BIT, 0, reqver); 259 rpkt.auth_seq = AUTH_SEQ(0, 0); 260 rpkt.implementation = inpkt->implementation; 261 rpkt.request = inpkt->request; 262 rpkt.err_nitems = ERR_NITEMS(errcode, 0); 263 rpkt.mbz_itemsize = MBZ_ITEMSIZE(0); 264 265 /* 266 * send packet and bump counters 267 */ 268 sendpkt(srcadr, inter, -1, (struct pkt *)&rpkt, RESP_HEADER_SIZE); 269 errorcounter[errcode]++; 270} 271 272 273/* 274 * prepare_pkt - prepare response packet for transmission, return pointer 275 * to storage for data item. 276 */ 277static char * 278prepare_pkt( 279 sockaddr_u *srcadr, 280 struct interface *inter, 281 struct req_pkt *pkt, 282 size_t structsize 283 ) 284{ 285 DPRINTF(4, ("request: preparing pkt\n")); 286 287 /* 288 * Fill in the implementation, request and itemsize fields 289 * since these won't change. 290 */ 291 rpkt.implementation = pkt->implementation; 292 rpkt.request = pkt->request; 293 rpkt.mbz_itemsize = MBZ_ITEMSIZE(structsize); 294 295 /* 296 * Compute the static data needed to carry on. 297 */ 298 toaddr = srcadr; 299 frominter = inter; 300 seqno = 0; 301 nitems = 0; 302 itemsize = structsize; 303 databytes = 0; 304 usingexbuf = 0; 305 306 /* 307 * return the beginning of the packet buffer. 308 */ 309 return &rpkt.data[0]; 310} 311 312 313/* 314 * more_pkt - return a data pointer for a new item. 315 */ 316static char * 317more_pkt(void) 318{ 319 /* 320 * If we were using the extra buffer, send the packet. 321 */ 322 if (usingexbuf) { 323 DPRINTF(3, ("request: sending pkt\n")); 324 rpkt.rm_vn_mode = RM_VN_MODE(RESP_BIT, MORE_BIT, reqver); 325 rpkt.auth_seq = AUTH_SEQ(0, seqno); 326 rpkt.err_nitems = htons((u_short)nitems); 327 sendpkt(toaddr, frominter, -1, (struct pkt *)&rpkt, 328 RESP_HEADER_SIZE + databytes); 329 numresppkts++; 330 331 /* 332 * Copy data out of exbuf into the packet. 333 */ 334 memcpy(&rpkt.data[0], exbuf, (unsigned)itemsize); 335 seqno++; 336 databytes = 0; 337 nitems = 0; 338 usingexbuf = 0; 339 } 340 341 databytes += itemsize; 342 nitems++; 343 if (databytes + itemsize <= RESP_DATA_SIZE) { 344 DPRINTF(4, ("request: giving him more data\n")); 345 /* 346 * More room in packet. Give him the 347 * next address. 348 */ 349 return &rpkt.data[databytes]; 350 } else { 351 /* 352 * No room in packet. Give him the extra 353 * buffer unless this was the last in the sequence. 354 */ 355 DPRINTF(4, ("request: into extra buffer\n")); 356 if (seqno == MAXSEQ) 357 return NULL; 358 else { 359 usingexbuf = 1; 360 return exbuf; 361 } 362 } 363} 364 365 366/* 367 * flush_pkt - we're done, return remaining information. 368 */ 369static void 370flush_pkt(void) 371{ 372 DPRINTF(3, ("request: flushing packet, %d items\n", nitems)); 373 /* 374 * Must send the last packet. If nothing in here and nothing 375 * has been sent, send an error saying no data to be found. 376 */ 377 if (seqno == 0 && nitems == 0) 378 req_ack(toaddr, frominter, (struct req_pkt *)&rpkt, 379 INFO_ERR_NODATA); 380 else { 381 rpkt.rm_vn_mode = RM_VN_MODE(RESP_BIT, 0, reqver); 382 rpkt.auth_seq = AUTH_SEQ(0, seqno); 383 rpkt.err_nitems = htons((u_short)nitems); 384 sendpkt(toaddr, frominter, -1, (struct pkt *)&rpkt, 385 RESP_HEADER_SIZE+databytes); 386 numresppkts++; 387 } 388} 389 390 391 392/* 393 * Given a buffer, return the packet mode 394 */ 395int 396get_packet_mode(struct recvbuf *rbufp) 397{ 398 struct req_pkt *inpkt = (struct req_pkt *)&rbufp->recv_pkt; 399 return (INFO_MODE(inpkt->rm_vn_mode)); 400} 401 402 403/* 404 * process_private - process private mode (7) packets 405 */ 406void 407process_private( 408 struct recvbuf *rbufp, 409 int mod_okay 410 ) 411{ 412 static u_long quiet_until; 413 struct req_pkt *inpkt; 414 struct req_pkt_tail *tailinpkt; 415 sockaddr_u *srcadr; 416 struct interface *inter; 417 struct req_proc *proc; 418 int ec; 419 short temp_size; 420 l_fp ftmp; 421 double dtemp; 422 size_t recv_len; 423 size_t noslop_len; 424 size_t mac_len; 425 426 /* 427 * Initialize pointers, for convenience 428 */ 429 recv_len = rbufp->recv_length; 430 inpkt = (struct req_pkt *)&rbufp->recv_pkt; 431 srcadr = &rbufp->recv_srcadr; 432 inter = rbufp->dstadr; 433 434 DPRINTF(3, ("process_private: impl %d req %d\n", 435 inpkt->implementation, inpkt->request)); 436 437 /* 438 * Do some sanity checks on the packet. Return a format 439 * error if it fails. 440 */ 441 ec = 0; 442 if ( (++ec, ISRESPONSE(inpkt->rm_vn_mode)) 443 || (++ec, ISMORE(inpkt->rm_vn_mode)) 444 || (++ec, INFO_VERSION(inpkt->rm_vn_mode) > NTP_VERSION) 445 || (++ec, INFO_VERSION(inpkt->rm_vn_mode) < NTP_OLDVERSION) 446 || (++ec, INFO_SEQ(inpkt->auth_seq) != 0) 447 || (++ec, INFO_ERR(inpkt->err_nitems) != 0) 448 || (++ec, INFO_MBZ(inpkt->mbz_itemsize) != 0) 449 || (++ec, rbufp->recv_length < REQ_LEN_HDR) 450 ) { 451 NLOG(NLOG_SYSEVENT) 452 if (current_time >= quiet_until) { 453 msyslog(LOG_ERR, 454 "process_private: drop test %d" 455 " failed, pkt from %s", 456 ec, stoa(srcadr)); 457 quiet_until = current_time + 60; 458 } 459 return; 460 } 461 462 reqver = INFO_VERSION(inpkt->rm_vn_mode); 463 464 /* 465 * Get the appropriate procedure list to search. 466 */ 467 if (inpkt->implementation == IMPL_UNIV) 468 proc = univ_codes; 469 else if ((inpkt->implementation == IMPL_XNTPD) || 470 (inpkt->implementation == IMPL_XNTPD_OLD)) 471 proc = ntp_codes; 472 else { 473 req_ack(srcadr, inter, inpkt, INFO_ERR_IMPL); 474 return; 475 } 476 477 /* 478 * Search the list for the request codes. If it isn't one 479 * we know, return an error. 480 */ 481 while (proc->request_code != NO_REQUEST) { 482 if (proc->request_code == (short) inpkt->request) 483 break; 484 proc++; 485 } 486 if (proc->request_code == NO_REQUEST) { 487 req_ack(srcadr, inter, inpkt, INFO_ERR_REQ); 488 return; 489 } 490 491 DPRINTF(4, ("found request in tables\n")); 492 493 /* 494 * If we need data, check to see if we have some. If we 495 * don't, check to see that there is none (picky, picky). 496 */ 497 498 /* This part is a bit tricky, we want to be sure that the size 499 * returned is either the old or the new size. We also can find 500 * out if the client can accept both types of messages this way. 501 * 502 * Handle the exception of REQ_CONFIG. It can have two data sizes. 503 */ 504 temp_size = INFO_ITEMSIZE(inpkt->mbz_itemsize); 505 if ((temp_size != proc->sizeofitem && 506 temp_size != proc->v6_sizeofitem) && 507 !(inpkt->implementation == IMPL_XNTPD && 508 inpkt->request == REQ_CONFIG && 509 temp_size == sizeof(struct old_conf_peer))) { 510 DPRINTF(3, ("process_private: wrong item size, received %d, should be %d or %d\n", 511 temp_size, proc->sizeofitem, proc->v6_sizeofitem)); 512 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 513 return; 514 } 515 if ((proc->sizeofitem != 0) && 516 ((size_t)(temp_size * INFO_NITEMS(inpkt->err_nitems)) > 517 (recv_len - REQ_LEN_HDR))) { 518 DPRINTF(3, ("process_private: not enough data\n")); 519 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 520 return; 521 } 522 523 switch (inpkt->implementation) { 524 case IMPL_XNTPD: 525 client_v6_capable = 1; 526 break; 527 case IMPL_XNTPD_OLD: 528 client_v6_capable = 0; 529 break; 530 default: 531 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 532 return; 533 } 534 535 /* 536 * If we need to authenticate, do so. Note that an 537 * authenticatable packet must include a mac field, must 538 * have used key info_auth_keyid and must have included 539 * a time stamp in the appropriate field. The time stamp 540 * must be within INFO_TS_MAXSKEW of the receive 541 * time stamp. 542 */ 543 if (proc->needs_auth && sys_authenticate) { 544 545 if (recv_len < (REQ_LEN_HDR + 546 (INFO_ITEMSIZE(inpkt->mbz_itemsize) * 547 INFO_NITEMS(inpkt->err_nitems)) + 548 REQ_TAIL_MIN)) { 549 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 550 return; 551 } 552 553 /* 554 * For 16-octet digests, regardless of itemsize and 555 * nitems, authenticated requests are a fixed size 556 * with the timestamp, key ID, and digest located 557 * at the end of the packet. Because the key ID 558 * determining the digest size precedes the digest, 559 * for larger digests the fixed size request scheme 560 * is abandoned and the timestamp, key ID, and digest 561 * are located relative to the start of the packet, 562 * with the digest size determined by the packet size. 563 */ 564 noslop_len = REQ_LEN_HDR 565 + INFO_ITEMSIZE(inpkt->mbz_itemsize) * 566 INFO_NITEMS(inpkt->err_nitems) 567 + sizeof(inpkt->tstamp); 568 /* 32-bit alignment */ 569 noslop_len = (noslop_len + 3) & ~3; 570 if (recv_len > (noslop_len + MAX_MAC_LEN)) 571 mac_len = 20; 572 else 573 mac_len = recv_len - noslop_len; 574 575 tailinpkt = (void *)((char *)inpkt + recv_len - 576 (mac_len + sizeof(inpkt->tstamp))); 577 578 /* 579 * If this guy is restricted from doing this, don't let 580 * him. If the wrong key was used, or packet doesn't 581 * have mac, return. 582 */ 583 if (!INFO_IS_AUTH(inpkt->auth_seq) || !info_auth_keyid 584 || ntohl(tailinpkt->keyid) != info_auth_keyid) { 585 DPRINTF(5, ("failed auth %d info_auth_keyid %u pkt keyid %u maclen %u\n", 586 INFO_IS_AUTH(inpkt->auth_seq), 587 info_auth_keyid, 588 ntohl(tailinpkt->keyid), mac_len)); 589#ifdef DEBUG 590 msyslog(LOG_DEBUG, 591 "process_private: failed auth %d info_auth_keyid %u pkt keyid %u maclen %u\n", 592 INFO_IS_AUTH(inpkt->auth_seq), 593 info_auth_keyid, 594 ntohl(tailinpkt->keyid), mac_len); 595#endif 596 req_ack(srcadr, inter, inpkt, INFO_ERR_AUTH); 597 return; 598 } 599 if (recv_len > REQ_LEN_NOMAC + MAX_MAC_LEN) { 600 DPRINTF(5, ("bad pkt length %d\n", recv_len)); 601 msyslog(LOG_ERR, 602 "process_private: bad pkt length %d", 603 recv_len); 604 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 605 return; 606 } 607 if (!mod_okay || !authhavekey(info_auth_keyid)) { 608 DPRINTF(5, ("failed auth mod_okay %d\n", 609 mod_okay)); 610#ifdef DEBUG 611 msyslog(LOG_DEBUG, 612 "process_private: failed auth mod_okay %d\n", 613 mod_okay); 614#endif 615 req_ack(srcadr, inter, inpkt, INFO_ERR_AUTH); 616 return; 617 } 618 619 /* 620 * calculate absolute time difference between xmit time stamp 621 * and receive time stamp. If too large, too bad. 622 */ 623 NTOHL_FP(&tailinpkt->tstamp, &ftmp); 624 L_SUB(&ftmp, &rbufp->recv_time); 625 LFPTOD(&ftmp, dtemp); 626 if (fabs(dtemp) > INFO_TS_MAXSKEW) { 627 /* 628 * He's a loser. Tell him. 629 */ 630 DPRINTF(5, ("xmit/rcv timestamp delta %g > INFO_TS_MAXSKEW %g\n", 631 dtemp, INFO_TS_MAXSKEW)); 632 req_ack(srcadr, inter, inpkt, INFO_ERR_AUTH); 633 return; 634 } 635 636 /* 637 * So far so good. See if decryption works out okay. 638 */ 639 if (!authdecrypt(info_auth_keyid, (u_int32 *)inpkt, 640 recv_len - mac_len, mac_len)) { 641 DPRINTF(5, ("authdecrypt failed\n")); 642 req_ack(srcadr, inter, inpkt, INFO_ERR_AUTH); 643 return; 644 } 645 } 646 647 DPRINTF(3, ("process_private: all okay, into handler\n")); 648 /* 649 * Packet is okay. Call the handler to send him data. 650 */ 651 (proc->handler)(srcadr, inter, inpkt); 652} 653 654 655/* 656 * peer_list - send a list of the peers 657 */ 658static void 659peer_list( 660 sockaddr_u *srcadr, 661 struct interface *inter, 662 struct req_pkt *inpkt 663 ) 664{ 665 register struct info_peer_list *ip; 666 register struct peer *pp; 667 register int i; 668 register int skip = 0; 669 670 ip = (struct info_peer_list *)prepare_pkt(srcadr, inter, inpkt, 671 v6sizeof(struct info_peer_list)); 672 for (i = 0; i < NTP_HASH_SIZE && ip != 0; i++) { 673 pp = peer_hash[i]; 674 while (pp != 0 && ip != 0) { 675 if (IS_IPV6(&pp->srcadr)) { 676 if (client_v6_capable) { 677 ip->addr6 = SOCK_ADDR6(&pp->srcadr); 678 ip->v6_flag = 1; 679 skip = 0; 680 } else { 681 skip = 1; 682 break; 683 } 684 } else { 685 ip->addr = NSRCADR(&pp->srcadr); 686 if (client_v6_capable) 687 ip->v6_flag = 0; 688 skip = 0; 689 } 690 691 if(!skip) { 692 ip->port = NSRCPORT(&pp->srcadr); 693 ip->hmode = pp->hmode; 694 ip->flags = 0; 695 if (pp->flags & FLAG_CONFIG) 696 ip->flags |= INFO_FLAG_CONFIG; 697 if (pp == sys_peer) 698 ip->flags |= INFO_FLAG_SYSPEER; 699 if (pp->status == CTL_PST_SEL_SYNCCAND) 700 ip->flags |= INFO_FLAG_SEL_CANDIDATE; 701 if (pp->status >= CTL_PST_SEL_SYSPEER) 702 ip->flags |= INFO_FLAG_SHORTLIST; 703 ip = (struct info_peer_list *)more_pkt(); 704 } 705 pp = pp->next; 706 } 707 } 708 flush_pkt(); 709} 710 711 712/* 713 * peer_list_sum - return extended peer list 714 */ 715static void 716peer_list_sum( 717 sockaddr_u *srcadr, 718 struct interface *inter, 719 struct req_pkt *inpkt 720 ) 721{ 722 register struct info_peer_summary *ips; 723 register struct peer *pp; 724 register int i; 725 l_fp ltmp; 726 register int skip; 727 728#ifdef DEBUG 729 if (debug > 2) 730 printf("wants peer list summary\n"); 731#endif 732 ips = (struct info_peer_summary *)prepare_pkt(srcadr, inter, inpkt, 733 v6sizeof(struct info_peer_summary)); 734 for (i = 0; i < NTP_HASH_SIZE && ips != 0; i++) { 735 pp = peer_hash[i]; 736 while (pp != 0 && ips != 0) { 737#ifdef DEBUG 738 if (debug > 3) 739 printf("sum: got one\n"); 740#endif 741 /* 742 * Be careful here not to return v6 peers when we 743 * want only v4. 744 */ 745 if (IS_IPV6(&pp->srcadr)) { 746 if (client_v6_capable) { 747 ips->srcadr6 = SOCK_ADDR6(&pp->srcadr); 748 ips->v6_flag = 1; 749 if (pp->dstadr) 750 ips->dstadr6 = SOCK_ADDR6(&pp->dstadr->sin); 751 else 752 memset(&ips->dstadr6, 0, sizeof(ips->dstadr6)); 753 skip = 0; 754 } else { 755 skip = 1; 756 break; 757 } 758 } else { 759 ips->srcadr = NSRCADR(&pp->srcadr); 760 if (client_v6_capable) 761 ips->v6_flag = 0; 762 763 if (pp->dstadr) { 764 if (!pp->processed) 765 ips->dstadr = NSRCADR(&pp->dstadr->sin); 766 else { 767 if (MDF_BCAST == pp->cast_flags) 768 ips->dstadr = NSRCADR(&pp->dstadr->bcast); 769 else if (pp->cast_flags) { 770 ips->dstadr = NSRCADR(&pp->dstadr->sin); 771 if (!ips->dstadr) 772 ips->dstadr = NSRCADR(&pp->dstadr->bcast); 773 } 774 } 775 } else 776 ips->dstadr = 0; 777 778 skip = 0; 779 } 780 781 if (!skip){ 782 ips->srcport = NSRCPORT(&pp->srcadr); 783 ips->stratum = pp->stratum; 784 ips->hpoll = pp->hpoll; 785 ips->ppoll = pp->ppoll; 786 ips->reach = pp->reach; 787 ips->flags = 0; 788 if (pp == sys_peer) 789 ips->flags |= INFO_FLAG_SYSPEER; 790 if (pp->flags & FLAG_CONFIG) 791 ips->flags |= INFO_FLAG_CONFIG; 792 if (pp->flags & FLAG_REFCLOCK) 793 ips->flags |= INFO_FLAG_REFCLOCK; 794 if (pp->flags & FLAG_PREFER) 795 ips->flags |= INFO_FLAG_PREFER; 796 if (pp->flags & FLAG_BURST) 797 ips->flags |= INFO_FLAG_BURST; 798 if (pp->status == CTL_PST_SEL_SYNCCAND) 799 ips->flags |= INFO_FLAG_SEL_CANDIDATE; 800 if (pp->status >= CTL_PST_SEL_SYSPEER) 801 ips->flags |= INFO_FLAG_SHORTLIST; 802 ips->hmode = pp->hmode; 803 ips->delay = HTONS_FP(DTOFP(pp->delay)); 804 DTOLFP(pp->offset, <mp); 805 HTONL_FP(<mp, &ips->offset); 806 ips->dispersion = HTONS_FP(DTOUFP(SQRT(pp->disp))); 807 } 808 pp = pp->next; 809 ips = (struct info_peer_summary *)more_pkt(); 810 } 811 } 812 flush_pkt(); 813} 814 815 816/* 817 * peer_info - send information for one or more peers 818 */ 819static void 820peer_info ( 821 sockaddr_u *srcadr, 822 struct interface *inter, 823 struct req_pkt *inpkt 824 ) 825{ 826 register struct info_peer_list *ipl; 827 register struct peer *pp; 828 register struct info_peer *ip; 829 register int items; 830 register int i, j; 831 sockaddr_u addr; 832 extern struct peer *sys_peer; 833 l_fp ltmp; 834 835 items = INFO_NITEMS(inpkt->err_nitems); 836 ipl = (struct info_peer_list *) inpkt->data; 837 838 ip = (struct info_peer *)prepare_pkt(srcadr, inter, inpkt, 839 v6sizeof(struct info_peer)); 840 while (items-- > 0 && ip != 0) { 841 ZERO_SOCK(&addr); 842 NSRCPORT(&addr) = ipl->port; 843 if (client_v6_capable && ipl->v6_flag) { 844 AF(&addr) = AF_INET6; 845 SOCK_ADDR6(&addr) = ipl->addr6; 846 } else { 847 AF(&addr) = AF_INET; 848 NSRCADR(&addr) = ipl->addr; 849 } 850#ifdef ISC_PLATFORM_HAVESALEN 851 addr.sas.ss_len = SOCKLEN(&addr); 852#endif 853 ipl++; 854 if ((pp = findexistingpeer(&addr, (struct peer *)0, -1)) == 0) 855 continue; 856 if (IS_IPV6(srcadr)) { 857 if (pp->dstadr) 858 ip->dstadr6 = 859 (MDF_BCAST == pp->cast_flags) 860 ? SOCK_ADDR6(&pp->dstadr->bcast) 861 : SOCK_ADDR6(&pp->dstadr->sin); 862 else 863 memset(&ip->dstadr6, 0, sizeof(ip->dstadr6)); 864 865 ip->srcadr6 = SOCK_ADDR6(&pp->srcadr); 866 ip->v6_flag = 1; 867 } else { 868 if (pp->dstadr) { 869 if (!pp->processed) 870 ip->dstadr = NSRCADR(&pp->dstadr->sin); 871 else { 872 if (MDF_BCAST == pp->cast_flags) 873 ip->dstadr = NSRCADR(&pp->dstadr->bcast); 874 else if (pp->cast_flags) { 875 ip->dstadr = NSRCADR(&pp->dstadr->sin); 876 if (!ip->dstadr) 877 ip->dstadr = NSRCADR(&pp->dstadr->bcast); 878 } 879 } 880 } else 881 ip->dstadr = 0; 882 883 ip->srcadr = NSRCADR(&pp->srcadr); 884 if (client_v6_capable) 885 ip->v6_flag = 0; 886 } 887 ip->srcport = NSRCPORT(&pp->srcadr); 888 ip->flags = 0; 889 if (pp == sys_peer) 890 ip->flags |= INFO_FLAG_SYSPEER; 891 if (pp->flags & FLAG_CONFIG) 892 ip->flags |= INFO_FLAG_CONFIG; 893 if (pp->flags & FLAG_REFCLOCK) 894 ip->flags |= INFO_FLAG_REFCLOCK; 895 if (pp->flags & FLAG_PREFER) 896 ip->flags |= INFO_FLAG_PREFER; 897 if (pp->flags & FLAG_BURST) 898 ip->flags |= INFO_FLAG_BURST; 899 if (pp->status == CTL_PST_SEL_SYNCCAND) 900 ip->flags |= INFO_FLAG_SEL_CANDIDATE; 901 if (pp->status >= CTL_PST_SEL_SYSPEER) 902 ip->flags |= INFO_FLAG_SHORTLIST; 903 ip->leap = pp->leap; 904 ip->hmode = pp->hmode; 905 ip->keyid = pp->keyid; 906 ip->stratum = pp->stratum; 907 ip->ppoll = pp->ppoll; 908 ip->hpoll = pp->hpoll; 909 ip->precision = pp->precision; 910 ip->version = pp->version; 911 ip->reach = pp->reach; 912 ip->unreach = (u_char) pp->unreach; 913 ip->flash = (u_char)pp->flash; 914 ip->flash2 = (u_short) pp->flash; 915 ip->estbdelay = HTONS_FP(DTOFP(pp->delay)); 916 ip->ttl = pp->ttl; 917 ip->associd = htons(pp->associd); 918 ip->rootdelay = HTONS_FP(DTOUFP(pp->rootdelay)); 919 ip->rootdispersion = HTONS_FP(DTOUFP(pp->rootdisp)); 920 ip->refid = pp->refid; 921 HTONL_FP(&pp->reftime, &ip->reftime); 922 HTONL_FP(&pp->aorg, &ip->org); 923 HTONL_FP(&pp->rec, &ip->rec); 924 HTONL_FP(&pp->xmt, &ip->xmt); 925 j = pp->filter_nextpt - 1; 926 for (i = 0; i < NTP_SHIFT; i++, j--) { 927 if (j < 0) 928 j = NTP_SHIFT-1; 929 ip->filtdelay[i] = HTONS_FP(DTOFP(pp->filter_delay[j])); 930 DTOLFP(pp->filter_offset[j], <mp); 931 HTONL_FP(<mp, &ip->filtoffset[i]); 932 ip->order[i] = (u_char)((pp->filter_nextpt+NTP_SHIFT-1) 933 - pp->filter_order[i]); 934 if (ip->order[i] >= NTP_SHIFT) 935 ip->order[i] -= NTP_SHIFT; 936 } 937 DTOLFP(pp->offset, <mp); 938 HTONL_FP(<mp, &ip->offset); 939 ip->delay = HTONS_FP(DTOFP(pp->delay)); 940 ip->dispersion = HTONS_FP(DTOUFP(SQRT(pp->disp))); 941 ip->selectdisp = HTONS_FP(DTOUFP(SQRT(pp->jitter))); 942 ip = (struct info_peer *)more_pkt(); 943 } 944 flush_pkt(); 945} 946 947 948/* 949 * peer_stats - send statistics for one or more peers 950 */ 951static void 952peer_stats ( 953 sockaddr_u *srcadr, 954 struct interface *inter, 955 struct req_pkt *inpkt 956 ) 957{ 958 register struct info_peer_list *ipl; 959 register struct peer *pp; 960 register struct info_peer_stats *ip; 961 register int items; 962 sockaddr_u addr; 963 extern struct peer *sys_peer; 964 965#ifdef DEBUG 966 if (debug) 967 printf("peer_stats: called\n"); 968#endif 969 items = INFO_NITEMS(inpkt->err_nitems); 970 ipl = (struct info_peer_list *) inpkt->data; 971 ip = (struct info_peer_stats *)prepare_pkt(srcadr, inter, inpkt, 972 v6sizeof(struct info_peer_stats)); 973 while (items-- > 0 && ip != 0) { 974 memset((char *)&addr, 0, sizeof(addr)); 975 NSRCPORT(&addr) = ipl->port; 976 if (client_v6_capable && ipl->v6_flag) { 977 AF(&addr) = AF_INET6; 978 SOCK_ADDR6(&addr) = ipl->addr6; 979 } else { 980 AF(&addr) = AF_INET; 981 NSRCADR(&addr) = ipl->addr; 982 } 983#ifdef ISC_PLATFORM_HAVESALEN 984 addr.sas.ss_len = SOCKLEN(&addr); 985#endif 986 DPRINTF(1, ("peer_stats: looking for %s, %d, %d\n", 987 stoa(&addr), ipl->port, NSRCPORT(&addr))); 988 989 ipl = (struct info_peer_list *)((char *)ipl + 990 INFO_ITEMSIZE(inpkt->mbz_itemsize)); 991 992 if ((pp = findexistingpeer(&addr, (struct peer *)0, -1)) == NULL) 993 continue; 994 995 DPRINTF(1, ("peer_stats: found %s\n", stoa(&addr))); 996 997 if (IS_IPV4(&pp->srcadr)) { 998 if (pp->dstadr) { 999 if (!pp->processed) 1000 ip->dstadr = NSRCADR(&pp->dstadr->sin); 1001 else { 1002 if (MDF_BCAST == pp->cast_flags) 1003 ip->dstadr = NSRCADR(&pp->dstadr->bcast); 1004 else if (pp->cast_flags) { 1005 ip->dstadr = NSRCADR(&pp->dstadr->sin); 1006 if (!ip->dstadr) 1007 ip->dstadr = NSRCADR(&pp->dstadr->bcast); 1008 } 1009 } 1010 } else 1011 ip->dstadr = 0; 1012 1013 ip->srcadr = NSRCADR(&pp->srcadr); 1014 if (client_v6_capable) 1015 ip->v6_flag = 0; 1016 } else { 1017 if (pp->dstadr) 1018 ip->dstadr6 = 1019 (MDF_BCAST == pp->cast_flags) 1020 ? SOCK_ADDR6(&pp->dstadr->bcast) 1021 : SOCK_ADDR6(&pp->dstadr->sin); 1022 else 1023 memset(&ip->dstadr6, 0, sizeof(ip->dstadr6)); 1024 1025 ip->srcadr6 = SOCK_ADDR6(&pp->srcadr); 1026 ip->v6_flag = 1; 1027 } 1028 ip->srcport = NSRCPORT(&pp->srcadr); 1029 ip->flags = 0; 1030 if (pp == sys_peer) 1031 ip->flags |= INFO_FLAG_SYSPEER; 1032 if (pp->flags & FLAG_CONFIG) 1033 ip->flags |= INFO_FLAG_CONFIG; 1034 if (pp->flags & FLAG_REFCLOCK) 1035 ip->flags |= INFO_FLAG_REFCLOCK; 1036 if (pp->flags & FLAG_PREFER) 1037 ip->flags |= INFO_FLAG_PREFER; 1038 if (pp->flags & FLAG_BURST) 1039 ip->flags |= INFO_FLAG_BURST; 1040 if (pp->flags & FLAG_IBURST) 1041 ip->flags |= INFO_FLAG_IBURST; 1042 if (pp->status == CTL_PST_SEL_SYNCCAND) 1043 ip->flags |= INFO_FLAG_SEL_CANDIDATE; 1044 if (pp->status >= CTL_PST_SEL_SYSPEER) 1045 ip->flags |= INFO_FLAG_SHORTLIST; 1046 ip->flags = htons(ip->flags); 1047 ip->timereceived = htonl((u_int32)(current_time - pp->timereceived)); 1048 ip->timetosend = htonl(pp->nextdate - current_time); 1049 ip->timereachable = htonl((u_int32)(current_time - pp->timereachable)); 1050 ip->sent = htonl((u_int32)(pp->sent)); 1051 ip->processed = htonl((u_int32)(pp->processed)); 1052 ip->badauth = htonl((u_int32)(pp->badauth)); 1053 ip->bogusorg = htonl((u_int32)(pp->bogusorg)); 1054 ip->oldpkt = htonl((u_int32)(pp->oldpkt)); 1055 ip->seldisp = htonl((u_int32)(pp->seldisptoolarge)); 1056 ip->selbroken = htonl((u_int32)(pp->selbroken)); 1057 ip->candidate = pp->status; 1058 ip = (struct info_peer_stats *)more_pkt(); 1059 } 1060 flush_pkt(); 1061} 1062 1063 1064/* 1065 * sys_info - return system info 1066 */ 1067static void 1068sys_info( 1069 sockaddr_u *srcadr, 1070 struct interface *inter, 1071 struct req_pkt *inpkt 1072 ) 1073{ 1074 register struct info_sys *is; 1075 1076 is = (struct info_sys *)prepare_pkt(srcadr, inter, inpkt, 1077 v6sizeof(struct info_sys)); 1078 1079 if (sys_peer) { 1080 if (IS_IPV4(&sys_peer->srcadr)) { 1081 is->peer = NSRCADR(&sys_peer->srcadr); 1082 if (client_v6_capable) 1083 is->v6_flag = 0; 1084 } else if (client_v6_capable) { 1085 is->peer6 = SOCK_ADDR6(&sys_peer->srcadr); 1086 is->v6_flag = 1; 1087 } 1088 is->peer_mode = sys_peer->hmode; 1089 } else { 1090 is->peer = 0; 1091 if (client_v6_capable) { 1092 is->v6_flag = 0; 1093 } 1094 is->peer_mode = 0; 1095 } 1096 1097 is->leap = sys_leap; 1098 is->stratum = sys_stratum; 1099 is->precision = sys_precision; 1100 is->rootdelay = htonl(DTOFP(sys_rootdelay)); 1101 is->rootdispersion = htonl(DTOUFP(sys_rootdisp)); 1102 is->frequency = htonl(DTOFP(sys_jitter)); 1103 is->stability = htonl(DTOUFP(clock_stability)); 1104 is->refid = sys_refid; 1105 HTONL_FP(&sys_reftime, &is->reftime); 1106 1107 is->poll = sys_poll; 1108 1109 is->flags = 0; 1110 if (sys_authenticate) 1111 is->flags |= INFO_FLAG_AUTHENTICATE; 1112 if (sys_bclient) 1113 is->flags |= INFO_FLAG_BCLIENT; 1114#ifdef REFCLOCK 1115 if (cal_enable) 1116 is->flags |= INFO_FLAG_CAL; 1117#endif /* REFCLOCK */ 1118 if (kern_enable) 1119 is->flags |= INFO_FLAG_KERNEL; 1120 if (mon_enabled != MON_OFF) 1121 is->flags |= INFO_FLAG_MONITOR; 1122 if (ntp_enable) 1123 is->flags |= INFO_FLAG_NTP; 1124 if (pps_enable) 1125 is->flags |= INFO_FLAG_PPS_SYNC; 1126 if (stats_control) 1127 is->flags |= INFO_FLAG_FILEGEN; 1128 is->bdelay = HTONS_FP(DTOFP(sys_bdelay)); 1129 HTONL_UF(sys_authdelay.l_f, &is->authdelay); 1130 (void) more_pkt(); 1131 flush_pkt(); 1132} 1133 1134 1135/* 1136 * sys_stats - return system statistics 1137 */ 1138static void 1139sys_stats( 1140 sockaddr_u *srcadr, 1141 struct interface *inter, 1142 struct req_pkt *inpkt 1143 ) 1144{ 1145 register struct info_sys_stats *ss; 1146 1147 /* 1148 * Importations from the protocol module 1149 */ 1150 ss = (struct info_sys_stats *)prepare_pkt(srcadr, inter, inpkt, 1151 sizeof(struct info_sys_stats)); 1152 ss->timeup = htonl((u_int32)current_time); 1153 ss->timereset = htonl((u_int32)(current_time - sys_stattime)); 1154 ss->denied = htonl((u_int32)sys_restricted); 1155 ss->oldversionpkt = htonl((u_int32)sys_oldversion); 1156 ss->newversionpkt = htonl((u_int32)sys_newversion); 1157 ss->unknownversion = htonl((u_int32)sys_declined); 1158 ss->badlength = htonl((u_int32)sys_badlength); 1159 ss->processed = htonl((u_int32)sys_processed); 1160 ss->badauth = htonl((u_int32)sys_badauth); 1161 ss->limitrejected = htonl((u_int32)sys_limitrejected); 1162 ss->received = htonl((u_int32)sys_received); 1163 (void) more_pkt(); 1164 flush_pkt(); 1165} 1166 1167 1168/* 1169 * mem_stats - return memory statistics 1170 */ 1171static void 1172mem_stats( 1173 sockaddr_u *srcadr, 1174 struct interface *inter, 1175 struct req_pkt *inpkt 1176 ) 1177{ 1178 register struct info_mem_stats *ms; 1179 register int i; 1180 1181 /* 1182 * Importations from the peer module 1183 */ 1184 extern int peer_hash_count[NTP_HASH_SIZE]; 1185 extern int peer_free_count; 1186 extern u_long peer_timereset; 1187 extern u_long findpeer_calls; 1188 extern u_long peer_allocations; 1189 extern u_long peer_demobilizations; 1190 extern int total_peer_structs; 1191 1192 ms = (struct info_mem_stats *)prepare_pkt(srcadr, inter, inpkt, 1193 sizeof(struct info_mem_stats)); 1194 1195 ms->timereset = htonl((u_int32)(current_time - peer_timereset)); 1196 ms->totalpeermem = htons((u_short)total_peer_structs); 1197 ms->freepeermem = htons((u_short)peer_free_count); 1198 ms->findpeer_calls = htonl((u_int32)findpeer_calls); 1199 ms->allocations = htonl((u_int32)peer_allocations); 1200 ms->demobilizations = htonl((u_int32)peer_demobilizations); 1201 1202 for (i = 0; i < NTP_HASH_SIZE; i++) { 1203 if (peer_hash_count[i] > 255) 1204 ms->hashcount[i] = 255; 1205 else 1206 ms->hashcount[i] = (u_char)peer_hash_count[i]; 1207 } 1208 1209 (void) more_pkt(); 1210 flush_pkt(); 1211} 1212 1213 1214/* 1215 * io_stats - return io statistics 1216 */ 1217static void 1218io_stats( 1219 sockaddr_u *srcadr, 1220 struct interface *inter, 1221 struct req_pkt *inpkt 1222 ) 1223{ 1224 register struct info_io_stats *io; 1225 1226 /* 1227 * Importations from the io module 1228 */ 1229 extern u_long io_timereset; 1230 1231 io = (struct info_io_stats *)prepare_pkt(srcadr, inter, inpkt, 1232 sizeof(struct info_io_stats)); 1233 1234 io->timereset = htonl((u_int32)(current_time - io_timereset)); 1235 io->totalrecvbufs = htons((u_short) total_recvbuffs()); 1236 io->freerecvbufs = htons((u_short) free_recvbuffs()); 1237 io->fullrecvbufs = htons((u_short) full_recvbuffs()); 1238 io->lowwater = htons((u_short) lowater_additions()); 1239 io->dropped = htonl((u_int32)packets_dropped); 1240 io->ignored = htonl((u_int32)packets_ignored); 1241 io->received = htonl((u_int32)packets_received); 1242 io->sent = htonl((u_int32)packets_sent); 1243 io->notsent = htonl((u_int32)packets_notsent); 1244 io->interrupts = htonl((u_int32)handler_calls); 1245 io->int_received = htonl((u_int32)handler_pkts); 1246 1247 (void) more_pkt(); 1248 flush_pkt(); 1249} 1250 1251 1252/* 1253 * timer_stats - return timer statistics 1254 */ 1255static void 1256timer_stats( 1257 sockaddr_u *srcadr, 1258 struct interface *inter, 1259 struct req_pkt *inpkt 1260 ) 1261{ 1262 register struct info_timer_stats *ts; 1263 1264 /* 1265 * Importations from the timer module 1266 */ 1267 extern u_long timer_timereset; 1268 extern u_long timer_overflows; 1269 extern u_long timer_xmtcalls; 1270 1271 ts = (struct info_timer_stats *)prepare_pkt(srcadr, inter, inpkt, 1272 sizeof(struct info_timer_stats)); 1273 1274 ts->timereset = htonl((u_int32)(current_time - timer_timereset)); 1275 ts->alarms = htonl((u_int32)alarm_overflow); 1276 ts->overflows = htonl((u_int32)timer_overflows); 1277 ts->xmtcalls = htonl((u_int32)timer_xmtcalls); 1278 1279 (void) more_pkt(); 1280 flush_pkt(); 1281} 1282 1283 1284/* 1285 * loop_info - return the current state of the loop filter 1286 */ 1287static void 1288loop_info( 1289 sockaddr_u *srcadr, 1290 struct interface *inter, 1291 struct req_pkt *inpkt 1292 ) 1293{ 1294 register struct info_loop *li; 1295 l_fp ltmp; 1296 1297 /* 1298 * Importations from the loop filter module 1299 */ 1300 extern double last_offset; 1301 extern double drift_comp; 1302 extern int tc_counter; 1303 extern u_long sys_epoch; 1304 1305 li = (struct info_loop *)prepare_pkt(srcadr, inter, inpkt, 1306 sizeof(struct info_loop)); 1307 1308 DTOLFP(last_offset, <mp); 1309 HTONL_FP(<mp, &li->last_offset); 1310 DTOLFP(drift_comp * 1e6, <mp); 1311 HTONL_FP(<mp, &li->drift_comp); 1312 li->compliance = htonl((u_int32)(tc_counter)); 1313 li->watchdog_timer = htonl((u_int32)(current_time - sys_epoch)); 1314 1315 (void) more_pkt(); 1316 flush_pkt(); 1317} 1318 1319 1320/* 1321 * do_conf - add a peer to the configuration list 1322 */ 1323static void 1324do_conf( 1325 sockaddr_u *srcadr, 1326 struct interface *inter, 1327 struct req_pkt *inpkt 1328 ) 1329{ 1330 static u_long soonest_ifrescan_time = 0; 1331 int items; 1332 u_int fl; 1333 struct conf_peer *cp; 1334 struct conf_peer temp_cp; 1335 sockaddr_u peeraddr; 1336 1337 /* 1338 * Do a check of everything to see that it looks 1339 * okay. If not, complain about it. Note we are 1340 * very picky here. 1341 */ 1342 items = INFO_NITEMS(inpkt->err_nitems); 1343 cp = (struct conf_peer *)inpkt->data; 1344 memset(&temp_cp, 0, sizeof(struct conf_peer)); 1345 memcpy(&temp_cp, (char *)cp, INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1346 1347#if 0 /* paranoid checking - these are done in newpeer() */ 1348 fl = 0; 1349 while (items-- > 0 && !fl) { 1350 if (((temp_cp.version) > NTP_VERSION) 1351 || ((temp_cp.version) < NTP_OLDVERSION)) 1352 fl = 1; 1353 if (temp_cp.hmode != MODE_ACTIVE 1354 && temp_cp.hmode != MODE_CLIENT 1355 && temp_cp.hmode != MODE_BROADCAST) 1356 fl = 1; 1357 if (temp_cp.flags & ~(CONF_FLAG_PREFER | CONF_FLAG_BURST | 1358 CONF_FLAG_IBURST | CONF_FLAG_SKEY)) 1359 fl = 1; 1360 cp = (struct conf_peer *) 1361 ((char *)cp + INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1362 } 1363 1364 if (fl) { 1365 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 1366 return; 1367 } 1368#endif /* end paranoid checking */ 1369 1370 /* 1371 * Looks okay, try it out 1372 */ 1373 items = INFO_NITEMS(inpkt->err_nitems); 1374 cp = (struct conf_peer *)inpkt->data; 1375 1376 while (items-- > 0) { 1377 memset(&temp_cp, 0, sizeof(struct conf_peer)); 1378 memcpy(&temp_cp, (char *)cp, INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1379 ZERO_SOCK(&peeraddr); 1380 1381 fl = 0; 1382 if (temp_cp.flags & CONF_FLAG_PREFER) 1383 fl |= FLAG_PREFER; 1384 if (temp_cp.flags & CONF_FLAG_BURST) 1385 fl |= FLAG_BURST; 1386 if (temp_cp.flags & CONF_FLAG_IBURST) 1387 fl |= FLAG_IBURST; 1388#ifdef OPENSSL 1389 if (temp_cp.flags & CONF_FLAG_SKEY) 1390 fl |= FLAG_SKEY; 1391#endif /* OPENSSL */ 1392 if (client_v6_capable && temp_cp.v6_flag != 0) { 1393 AF(&peeraddr) = AF_INET6; 1394 SOCK_ADDR6(&peeraddr) = temp_cp.peeraddr6; 1395 } else { 1396 AF(&peeraddr) = AF_INET; 1397 NSRCADR(&peeraddr) = temp_cp.peeraddr; 1398 /* 1399 * Make sure the address is valid 1400 */ 1401 if (!ISREFCLOCKADR(&peeraddr) && 1402 ISBADADR(&peeraddr)) { 1403 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 1404 return; 1405 } 1406 1407 } 1408 NSRCPORT(&peeraddr) = htons(NTP_PORT); 1409#ifdef ISC_PLATFORM_HAVESALEN 1410 peeraddr.sas.ss_len = SOCKLEN(&peeraddr); 1411#endif 1412 1413 /* XXX W2DO? minpoll/maxpoll arguments ??? */ 1414 if (peer_config(&peeraddr, (struct interface *)0, 1415 temp_cp.hmode, temp_cp.version, temp_cp.minpoll, 1416 temp_cp.maxpoll, fl, temp_cp.ttl, temp_cp.keyid, 1417 NULL, temp_cp.keystr) == 0) { 1418 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 1419 return; 1420 } 1421#if TARGET_OS_EMBEDDED 1422 awake_timer = current_time; 1423#endif 1424 /* 1425 * ntp_intres.c uses REQ_CONFIG/doconf() to add each 1426 * server after its name is resolved. If we have been 1427 * disconnected from the network, it may notice the 1428 * network has returned and add the first server while 1429 * the relevant interface is still disabled, awaiting 1430 * the next interface rescan. To get things moving 1431 * more quickly, trigger an interface scan now, except 1432 * if we have done so in the last half minute. 1433 */ 1434 if (soonest_ifrescan_time < current_time) { 1435 soonest_ifrescan_time = current_time + 30; 1436 timer_interfacetimeout(current_time); 1437 DPRINTF(1, ("do_conf triggering interface rescan\n")); 1438 } 1439 1440 cp = (struct conf_peer *) 1441 ((char *)cp + INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1442 } 1443 1444 req_ack(srcadr, inter, inpkt, INFO_OKAY); 1445} 1446 1447#if 0 1448/* XXX */ 1449/* 1450 * dns_a - Snarf DNS info for an association ID 1451 */ 1452static void 1453dns_a( 1454 sockaddr_u *srcadr, 1455 struct interface *inter, 1456 struct req_pkt *inpkt 1457 ) 1458{ 1459 register struct info_dns_assoc *dp; 1460 register int items; 1461 struct sockaddr_in peeraddr; 1462 1463 /* 1464 * Do a check of everything to see that it looks 1465 * okay. If not, complain about it. Note we are 1466 * very picky here. 1467 */ 1468 items = INFO_NITEMS(inpkt->err_nitems); 1469 dp = (struct info_dns_assoc *)inpkt->data; 1470 1471 /* 1472 * Looks okay, try it out 1473 */ 1474 items = INFO_NITEMS(inpkt->err_nitems); 1475 dp = (struct info_dns_assoc *)inpkt->data; 1476 memset((char *)&peeraddr, 0, sizeof(struct sockaddr_in)); 1477 peeraddr.sin_family = AF_INET; 1478 peeraddr.sin_port = htons(NTP_PORT); 1479 1480 /* 1481 * Make sure the address is valid 1482 */ 1483 if (!ISREFCLOCKADR(&peeraddr) && ISBADADR(&peeraddr)) { 1484 msyslog(LOG_ERR, "dns_a: !ISREFCLOCKADR && ISBADADR"); 1485 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 1486 return; 1487 } 1488 1489 while (items-- > 0) { 1490 associd_t associd; 1491 size_t hnl; 1492 struct peer *peer; 1493 int bogon = 0; 1494 1495 associd = dp->associd; 1496 peer = findpeerbyassoc(associd); 1497 if (peer == 0 || peer->flags & FLAG_REFCLOCK) { 1498 msyslog(LOG_ERR, "dns_a: %s", 1499 (peer == 0) 1500 ? "peer == 0" 1501 : "peer->flags & FLAG_REFCLOCK"); 1502 ++bogon; 1503 } 1504 peeraddr.sin_addr.s_addr = dp->peeraddr; 1505 for (hnl = 0; dp->hostname[hnl] && hnl < sizeof dp->hostname; ++hnl) ; 1506 if (hnl >= sizeof dp->hostname) { 1507 msyslog(LOG_ERR, "dns_a: hnl (%ld) >= %ld", 1508 (long)hnl, (long)sizeof dp->hostname); 1509 ++bogon; 1510 } 1511 1512 msyslog(LOG_INFO, "dns_a: <%s> for %s, AssocID %d, bogon %d", 1513 dp->hostname, 1514 stoa((sockaddr_u *)&peeraddr), associd, 1515 bogon); 1516 1517 if (bogon) { 1518 /* If it didn't work */ 1519 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 1520 return; 1521 } else { 1522#if 0 1523#ifdef PUBKEY 1524 crypto_public(peer, dp->hostname); 1525#endif /* PUBKEY */ 1526#endif 1527 } 1528 1529 dp++; 1530 } 1531 1532 req_ack(srcadr, inter, inpkt, INFO_OKAY); 1533} 1534#endif /* 0 */ 1535 1536/* 1537 * do_unconf - remove a peer from the configuration list 1538 */ 1539static void 1540do_unconf( 1541 sockaddr_u *srcadr, 1542 struct interface *inter, 1543 struct req_pkt *inpkt 1544 ) 1545{ 1546 register struct conf_unpeer *cp; 1547 struct conf_unpeer temp_cp; 1548 register int items; 1549 register struct peer *peer; 1550 sockaddr_u peeraddr; 1551 int bad, found; 1552 1553 /* 1554 * This is a bit unstructured, but I like to be careful. 1555 * We check to see that every peer exists and is actually 1556 * configured. If so, we remove them. If not, we return 1557 * an error. 1558 */ 1559 items = INFO_NITEMS(inpkt->err_nitems); 1560 cp = (struct conf_unpeer *)inpkt->data; 1561 1562 bad = 0; 1563 while (items-- > 0 && !bad) { 1564 memset(&temp_cp, 0, sizeof(temp_cp)); 1565 ZERO_SOCK(&peeraddr); 1566 memcpy(&temp_cp, cp, INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1567 if (client_v6_capable && temp_cp.v6_flag) { 1568 AF(&peeraddr) = AF_INET6; 1569 SOCK_ADDR6(&peeraddr) = temp_cp.peeraddr6; 1570 } else { 1571 AF(&peeraddr) = AF_INET; 1572 NSRCADR(&peeraddr) = temp_cp.peeraddr; 1573 } 1574 SET_PORT(&peeraddr, NTP_PORT); 1575#ifdef ISC_PLATFORM_HAVESALEN 1576 peeraddr.sas.ss_len = SOCKLEN(&peeraddr); 1577#endif 1578 found = 0; 1579 peer = NULL; 1580 1581 DPRINTF(1, ("searching for %s\n", stoa(&peeraddr))); 1582 1583 while (!found) { 1584 peer = findexistingpeer(&peeraddr, peer, -1); 1585 if (!peer) 1586 break; 1587 if (peer->flags & FLAG_CONFIG) 1588 found = 1; 1589 } 1590 if (!found) 1591 bad = 1; 1592 cp = (struct conf_unpeer *) 1593 ((char *)cp + INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1594 } 1595 1596 if (bad) { 1597 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 1598 return; 1599 } 1600 1601 /* 1602 * Now do it in earnest. 1603 */ 1604 1605 items = INFO_NITEMS(inpkt->err_nitems); 1606 cp = (struct conf_unpeer *)inpkt->data; 1607 1608 while (items-- > 0) { 1609 memset(&temp_cp, 0, sizeof(temp_cp)); 1610 memset(&peeraddr, 0, sizeof(peeraddr)); 1611 memcpy(&temp_cp, cp, INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1612 if (client_v6_capable && temp_cp.v6_flag) { 1613 AF(&peeraddr) = AF_INET6; 1614 SOCK_ADDR6(&peeraddr) = temp_cp.peeraddr6; 1615 } else { 1616 AF(&peeraddr) = AF_INET; 1617 NSRCADR(&peeraddr) = temp_cp.peeraddr; 1618 } 1619 SET_PORT(&peeraddr, NTP_PORT); 1620#ifdef ISC_PLATFORM_HAVESALEN 1621 peeraddr.sas.ss_len = SOCKLEN(&peeraddr); 1622#endif 1623 found = 0; 1624 peer = NULL; 1625 1626 while (!found) { 1627 peer = findexistingpeer(&peeraddr, peer, -1); 1628 if (!peer) 1629 break; 1630 if (peer->flags & FLAG_CONFIG) 1631 found = 1; 1632 } 1633 NTP_INSIST(found); 1634 NTP_INSIST(peer); 1635 1636 peer_clear(peer, "GONE"); 1637 unpeer(peer); 1638 1639 cp = (struct conf_unpeer *) 1640 ((char *)cp + INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1641 } 1642 1643 req_ack(srcadr, inter, inpkt, INFO_OKAY); 1644} 1645 1646 1647/* 1648 * set_sys_flag - set system flags 1649 */ 1650static void 1651set_sys_flag( 1652 sockaddr_u *srcadr, 1653 struct interface *inter, 1654 struct req_pkt *inpkt 1655 ) 1656{ 1657 setclr_flags(srcadr, inter, inpkt, 1); 1658} 1659 1660 1661/* 1662 * clr_sys_flag - clear system flags 1663 */ 1664static void 1665clr_sys_flag( 1666 sockaddr_u *srcadr, 1667 struct interface *inter, 1668 struct req_pkt *inpkt 1669 ) 1670{ 1671 setclr_flags(srcadr, inter, inpkt, 0); 1672} 1673 1674 1675/* 1676 * setclr_flags - do the grunge work of flag setting/clearing 1677 */ 1678static void 1679setclr_flags( 1680 sockaddr_u *srcadr, 1681 struct interface *inter, 1682 struct req_pkt *inpkt, 1683 u_long set 1684 ) 1685{ 1686 register u_int flags; 1687 int prev_kern_enable; 1688 1689 prev_kern_enable = kern_enable; 1690 if (INFO_NITEMS(inpkt->err_nitems) > 1) { 1691 msyslog(LOG_ERR, "setclr_flags: err_nitems > 1"); 1692 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 1693 return; 1694 } 1695 1696 flags = ((struct conf_sys_flags *)inpkt->data)->flags; 1697 flags = ntohl(flags); 1698 1699 if (flags & ~(SYS_FLAG_BCLIENT | SYS_FLAG_PPS | 1700 SYS_FLAG_NTP | SYS_FLAG_KERNEL | SYS_FLAG_MONITOR | 1701 SYS_FLAG_FILEGEN | SYS_FLAG_AUTH | SYS_FLAG_CAL)) { 1702 msyslog(LOG_ERR, "setclr_flags: extra flags: %#x", 1703 flags & ~(SYS_FLAG_BCLIENT | SYS_FLAG_PPS | 1704 SYS_FLAG_NTP | SYS_FLAG_KERNEL | 1705 SYS_FLAG_MONITOR | SYS_FLAG_FILEGEN | 1706 SYS_FLAG_AUTH | SYS_FLAG_CAL)); 1707 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 1708 return; 1709 } 1710 1711 if (flags & SYS_FLAG_BCLIENT) 1712 proto_config(PROTO_BROADCLIENT, set, 0., NULL); 1713 if (flags & SYS_FLAG_PPS) 1714 proto_config(PROTO_PPS, set, 0., NULL); 1715 if (flags & SYS_FLAG_NTP) 1716 proto_config(PROTO_NTP, set, 0., NULL); 1717 if (flags & SYS_FLAG_KERNEL) 1718 proto_config(PROTO_KERNEL, set, 0., NULL); 1719 if (flags & SYS_FLAG_MONITOR) 1720 proto_config(PROTO_MONITOR, set, 0., NULL); 1721 if (flags & SYS_FLAG_FILEGEN) 1722 proto_config(PROTO_FILEGEN, set, 0., NULL); 1723 if (flags & SYS_FLAG_AUTH) 1724 proto_config(PROTO_AUTHENTICATE, set, 0., NULL); 1725 if (flags & SYS_FLAG_CAL) 1726 proto_config(PROTO_CAL, set, 0., NULL); 1727 req_ack(srcadr, inter, inpkt, INFO_OKAY); 1728 1729 /* Reset the kernel ntp parameters if the kernel flag changed. */ 1730 if (prev_kern_enable && !kern_enable) 1731 loop_config(LOOP_KERN_CLEAR, 0.0); 1732 if (!prev_kern_enable && kern_enable) 1733 loop_config(LOOP_DRIFTCOMP, drift_comp); 1734} 1735 1736 1737/* 1738 * list_restrict - return the restrict list 1739 */ 1740static void 1741list_restrict( 1742 sockaddr_u *srcadr, 1743 struct interface *inter, 1744 struct req_pkt *inpkt 1745 ) 1746{ 1747 register struct info_restrict *ir; 1748 register struct restrictlist *rl; 1749 register struct restrictlist6 *rl6; 1750 1751#ifdef DEBUG 1752 if (debug > 2) 1753 printf("wants restrict list summary\n"); 1754#endif 1755 1756 ir = (struct info_restrict *)prepare_pkt(srcadr, inter, inpkt, 1757 v6sizeof(struct info_restrict)); 1758 1759 for (rl = restrictlist; rl != 0 && ir != 0; rl = rl->next) { 1760 ir->addr = htonl(rl->addr); 1761 if (client_v6_capable) 1762 ir->v6_flag = 0; 1763 ir->mask = htonl(rl->mask); 1764 ir->count = htonl((u_int32)rl->count); 1765 ir->flags = htons(rl->flags); 1766 ir->mflags = htons(rl->mflags); 1767 ir = (struct info_restrict *)more_pkt(); 1768 } 1769 if (client_v6_capable) 1770 for (rl6 = restrictlist6; rl6 != 0 && ir != 0; rl6 = rl6->next) { 1771 ir->addr6 = rl6->addr6; 1772 ir->mask6 = rl6->mask6; 1773 ir->v6_flag = 1; 1774 ir->count = htonl((u_int32)rl6->count); 1775 ir->flags = htons(rl6->flags); 1776 ir->mflags = htons(rl6->mflags); 1777 ir = (struct info_restrict *)more_pkt(); 1778 } 1779 flush_pkt(); 1780} 1781 1782 1783 1784/* 1785 * do_resaddflags - add flags to a restrict entry (or create one) 1786 */ 1787static void 1788do_resaddflags( 1789 sockaddr_u *srcadr, 1790 struct interface *inter, 1791 struct req_pkt *inpkt 1792 ) 1793{ 1794 do_restrict(srcadr, inter, inpkt, RESTRICT_FLAGS); 1795} 1796 1797 1798 1799/* 1800 * do_ressubflags - remove flags from a restrict entry 1801 */ 1802static void 1803do_ressubflags( 1804 sockaddr_u *srcadr, 1805 struct interface *inter, 1806 struct req_pkt *inpkt 1807 ) 1808{ 1809 do_restrict(srcadr, inter, inpkt, RESTRICT_UNFLAG); 1810} 1811 1812 1813/* 1814 * do_unrestrict - remove a restrict entry from the list 1815 */ 1816static void 1817do_unrestrict( 1818 sockaddr_u *srcadr, 1819 struct interface *inter, 1820 struct req_pkt *inpkt 1821 ) 1822{ 1823 do_restrict(srcadr, inter, inpkt, RESTRICT_REMOVE); 1824} 1825 1826 1827/* 1828 * do_restrict - do the dirty stuff of dealing with restrictions 1829 */ 1830static void 1831do_restrict( 1832 sockaddr_u *srcadr, 1833 struct interface *inter, 1834 struct req_pkt *inpkt, 1835 int op 1836 ) 1837{ 1838 register struct conf_restrict *cr; 1839 register int items; 1840 sockaddr_u matchaddr; 1841 sockaddr_u matchmask; 1842 int bad; 1843 1844 /* 1845 * Do a check of the flags to make sure that only 1846 * the NTPPORT flag is set, if any. If not, complain 1847 * about it. Note we are very picky here. 1848 */ 1849 items = INFO_NITEMS(inpkt->err_nitems); 1850 cr = (struct conf_restrict *)inpkt->data; 1851 1852 bad = 0; 1853 cr->flags = ntohs(cr->flags); 1854 cr->mflags = ntohs(cr->mflags); 1855 while (items-- > 0 && !bad) { 1856 if (cr->mflags & ~(RESM_NTPONLY)) 1857 bad |= 1; 1858 if (cr->flags & ~(RES_ALLFLAGS)) 1859 bad |= 2; 1860 if (cr->mask != htonl(INADDR_ANY)) { 1861 if (client_v6_capable && cr->v6_flag != 0) { 1862 if (IN6_IS_ADDR_UNSPECIFIED(&cr->addr6)) 1863 bad |= 4; 1864 } else 1865 if (cr->addr == htonl(INADDR_ANY)) 1866 bad |= 8; 1867 } 1868 cr = (struct conf_restrict *)((char *)cr + 1869 INFO_ITEMSIZE(inpkt->mbz_itemsize)); 1870 } 1871 1872 if (bad) { 1873 msyslog(LOG_ERR, "do_restrict: bad = %#x", bad); 1874 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 1875 return; 1876 } 1877 1878 /* 1879 * Looks okay, try it out 1880 */ 1881 items = INFO_NITEMS(inpkt->err_nitems); 1882 cr = (struct conf_restrict *)inpkt->data; 1883 ZERO_SOCK(&matchaddr); 1884 ZERO_SOCK(&matchmask); 1885 1886 while (items-- > 0) { 1887 if (client_v6_capable && cr->v6_flag) { 1888 AF(&matchaddr) = AF_INET6; 1889 AF(&matchmask) = AF_INET6; 1890 SOCK_ADDR6(&matchaddr) = cr->addr6; 1891 SOCK_ADDR6(&matchmask) = cr->mask6; 1892 } else { 1893 AF(&matchaddr) = AF_INET; 1894 AF(&matchmask) = AF_INET; 1895 NSRCADR(&matchaddr) = cr->addr; 1896 NSRCADR(&matchmask) = cr->mask; 1897 } 1898 hack_restrict(op, &matchaddr, &matchmask, cr->mflags, 1899 cr->flags); 1900 cr++; 1901 } 1902 1903 req_ack(srcadr, inter, inpkt, INFO_OKAY); 1904} 1905 1906 1907/* 1908 * mon_getlist - return monitor data 1909 */ 1910static void 1911mon_getlist_0( 1912 sockaddr_u *srcadr, 1913 struct interface *inter, 1914 struct req_pkt *inpkt 1915 ) 1916{ 1917 register struct info_monitor *im; 1918 register struct mon_data *md; 1919 extern struct mon_data mon_mru_list; 1920 extern int mon_enabled; 1921 1922#ifdef DEBUG 1923 if (debug > 2) 1924 printf("wants monitor 0 list\n"); 1925#endif 1926 if (!mon_enabled) { 1927 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 1928 return; 1929 } 1930 im = (struct info_monitor *)prepare_pkt(srcadr, inter, inpkt, 1931 v6sizeof(struct info_monitor)); 1932 for (md = mon_mru_list.mru_next; md != &mon_mru_list && im != 0; 1933 md = md->mru_next) { 1934 im->lasttime = htonl((u_int32)((current_time - 1935 md->firsttime) / md->count)); 1936 im->firsttime = htonl((u_int32)(current_time - md->lasttime)); 1937 im->restr = htonl((u_int32)md->flags); 1938 im->count = htonl((u_int32)(md->count)); 1939 if (IS_IPV6(&md->rmtadr)) { 1940 if (!client_v6_capable) 1941 continue; 1942 im->addr6 = SOCK_ADDR6(&md->rmtadr); 1943 im->v6_flag = 1; 1944 } else { 1945 im->addr = NSRCADR(&md->rmtadr); 1946 if (client_v6_capable) 1947 im->v6_flag = 0; 1948 } 1949 im->port = md->rmtport; 1950 im->mode = md->mode; 1951 im->version = md->version; 1952 im = (struct info_monitor *)more_pkt(); 1953 } 1954 flush_pkt(); 1955} 1956 1957/* 1958 * mon_getlist - return monitor data 1959 */ 1960static void 1961mon_getlist_1( 1962 sockaddr_u *srcadr, 1963 struct interface *inter, 1964 struct req_pkt *inpkt 1965 ) 1966{ 1967 register struct info_monitor_1 *im; 1968 register struct mon_data *md; 1969 extern struct mon_data mon_mru_list; 1970 extern int mon_enabled; 1971 1972 if (!mon_enabled) { 1973 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 1974 return; 1975 } 1976 im = (struct info_monitor_1 *)prepare_pkt(srcadr, inter, inpkt, 1977 v6sizeof(struct info_monitor_1)); 1978 for (md = mon_mru_list.mru_next; md != &mon_mru_list && im != 0; 1979 md = md->mru_next) { 1980 im->lasttime = htonl((u_int32)((current_time - 1981 md->firsttime) / md->count)); 1982 im->firsttime = htonl((u_int32)(current_time - md->lasttime)); 1983 im->restr = htonl((u_int32)md->flags); 1984 im->count = htonl((u_int32)md->count); 1985 if (IS_IPV6(&md->rmtadr)) { 1986 if (!client_v6_capable) 1987 continue; 1988 im->addr6 = SOCK_ADDR6(&md->rmtadr); 1989 im->v6_flag = 1; 1990 im->daddr6 = SOCK_ADDR6(&md->interface->sin); 1991 } else { 1992 im->addr = NSRCADR(&md->rmtadr); 1993 if (client_v6_capable) 1994 im->v6_flag = 0; 1995 if (MDF_BCAST == md->cast_flags) 1996 im->daddr = NSRCADR(&md->interface->bcast); 1997 else if (md->cast_flags) { 1998 im->daddr = NSRCADR(&md->interface->sin); 1999 if (!im->daddr) 2000 im->daddr = NSRCADR(&md->interface->bcast); 2001 } else 2002 im->daddr = 4; 2003 } 2004 im->flags = htonl(md->cast_flags); 2005 im->port = md->rmtport; 2006 im->mode = md->mode; 2007 im->version = md->version; 2008 im = (struct info_monitor_1 *)more_pkt(); 2009 } 2010 flush_pkt(); 2011} 2012 2013/* 2014 * Module entry points and the flags they correspond with 2015 */ 2016struct reset_entry { 2017 int flag; /* flag this corresponds to */ 2018 void (*handler) (void); /* routine to handle request */ 2019}; 2020 2021struct reset_entry reset_entries[] = { 2022 { RESET_FLAG_ALLPEERS, peer_all_reset }, 2023 { RESET_FLAG_IO, io_clr_stats }, 2024 { RESET_FLAG_SYS, proto_clr_stats }, 2025 { RESET_FLAG_MEM, peer_clr_stats }, 2026 { RESET_FLAG_TIMER, timer_clr_stats }, 2027 { RESET_FLAG_AUTH, reset_auth_stats }, 2028 { RESET_FLAG_CTL, ctl_clr_stats }, 2029 { 0, 0 } 2030}; 2031 2032/* 2033 * reset_stats - reset statistic counters here and there 2034 */ 2035static void 2036reset_stats( 2037 sockaddr_u *srcadr, 2038 struct interface *inter, 2039 struct req_pkt *inpkt 2040 ) 2041{ 2042 u_long flags; 2043 struct reset_entry *rent; 2044 2045 if (INFO_NITEMS(inpkt->err_nitems) > 1) { 2046 msyslog(LOG_ERR, "reset_stats: err_nitems > 1"); 2047 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 2048 return; 2049 } 2050 2051 flags = ((struct reset_flags *)inpkt->data)->flags; 2052 flags = ntohl(flags); 2053 2054 if (flags & ~RESET_ALLFLAGS) { 2055 msyslog(LOG_ERR, "reset_stats: reset leaves %#lx", 2056 flags & ~RESET_ALLFLAGS); 2057 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 2058 return; 2059 } 2060 2061 for (rent = reset_entries; rent->flag != 0; rent++) { 2062 if (flags & rent->flag) 2063 (rent->handler)(); 2064 } 2065 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2066} 2067 2068 2069/* 2070 * reset_peer - clear a peer's statistics 2071 */ 2072static void 2073reset_peer( 2074 sockaddr_u *srcadr, 2075 struct interface *inter, 2076 struct req_pkt *inpkt 2077 ) 2078{ 2079 struct conf_unpeer *cp; 2080 int items; 2081 struct peer *peer; 2082 sockaddr_u peeraddr; 2083 int bad; 2084 2085 /* 2086 * We check first to see that every peer exists. If not, 2087 * we return an error. 2088 */ 2089 2090 items = INFO_NITEMS(inpkt->err_nitems); 2091 cp = (struct conf_unpeer *)inpkt->data; 2092 2093 bad = 0; 2094 while (items-- > 0 && !bad) { 2095 ZERO_SOCK(&peeraddr); 2096 if (client_v6_capable && cp->v6_flag) { 2097 AF(&peeraddr) = AF_INET6; 2098 SOCK_ADDR6(&peeraddr) = cp->peeraddr6; 2099 } else { 2100 AF(&peeraddr) = AF_INET; 2101 NSRCADR(&peeraddr) = cp->peeraddr; 2102 } 2103 2104#ifdef ISC_PLATFORM_HAVESALEN 2105 peeraddr.sas.ss_len = SOCKLEN(&peeraddr); 2106#endif 2107 peer = findexistingpeer(&peeraddr, NULL, -1); 2108 if (NULL == peer) 2109 bad++; 2110 cp = (struct conf_unpeer *)((char *)cp + 2111 INFO_ITEMSIZE(inpkt->mbz_itemsize)); 2112 } 2113 2114 if (bad) { 2115 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2116 return; 2117 } 2118 2119 /* 2120 * Now do it in earnest. 2121 */ 2122 2123 items = INFO_NITEMS(inpkt->err_nitems); 2124 cp = (struct conf_unpeer *)inpkt->data; 2125 while (items-- > 0) { 2126 ZERO_SOCK(&peeraddr); 2127 if (client_v6_capable && cp->v6_flag) { 2128 AF(&peeraddr) = AF_INET6; 2129 SOCK_ADDR6(&peeraddr) = cp->peeraddr6; 2130 } else { 2131 AF(&peeraddr) = AF_INET; 2132 NSRCADR(&peeraddr) = cp->peeraddr; 2133 } 2134 SET_PORT(&peeraddr, 123); 2135#ifdef ISC_PLATFORM_HAVESALEN 2136 peeraddr.sas.ss_len = SOCKLEN(&peeraddr); 2137#endif 2138 peer = findexistingpeer(&peeraddr, NULL, -1); 2139 while (peer != NULL) { 2140 peer_reset(peer); 2141 peer = findexistingpeer(&peeraddr, peer, -1); 2142 } 2143 cp = (struct conf_unpeer *)((char *)cp + 2144 INFO_ITEMSIZE(inpkt->mbz_itemsize)); 2145 } 2146 2147 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2148} 2149 2150 2151/* 2152 * do_key_reread - reread the encryption key file 2153 */ 2154static void 2155do_key_reread( 2156 sockaddr_u *srcadr, 2157 struct interface *inter, 2158 struct req_pkt *inpkt 2159 ) 2160{ 2161 rereadkeys(); 2162 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2163} 2164 2165 2166/* 2167 * trust_key - make one or more keys trusted 2168 */ 2169static void 2170trust_key( 2171 sockaddr_u *srcadr, 2172 struct interface *inter, 2173 struct req_pkt *inpkt 2174 ) 2175{ 2176 do_trustkey(srcadr, inter, inpkt, 1); 2177} 2178 2179 2180/* 2181 * untrust_key - make one or more keys untrusted 2182 */ 2183static void 2184untrust_key( 2185 sockaddr_u *srcadr, 2186 struct interface *inter, 2187 struct req_pkt *inpkt 2188 ) 2189{ 2190 do_trustkey(srcadr, inter, inpkt, 0); 2191} 2192 2193 2194/* 2195 * do_trustkey - make keys either trustable or untrustable 2196 */ 2197static void 2198do_trustkey( 2199 sockaddr_u *srcadr, 2200 struct interface *inter, 2201 struct req_pkt *inpkt, 2202 u_long trust 2203 ) 2204{ 2205 register u_long *kp; 2206 register int items; 2207 2208 items = INFO_NITEMS(inpkt->err_nitems); 2209 kp = (u_long *)inpkt->data; 2210 while (items-- > 0) { 2211 authtrust(*kp, trust); 2212 kp++; 2213 } 2214 2215 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2216} 2217 2218 2219/* 2220 * get_auth_info - return some stats concerning the authentication module 2221 */ 2222static void 2223get_auth_info( 2224 sockaddr_u *srcadr, 2225 struct interface *inter, 2226 struct req_pkt *inpkt 2227 ) 2228{ 2229 register struct info_auth *ia; 2230 2231 /* 2232 * Importations from the authentication module 2233 */ 2234 extern u_long authnumkeys; 2235 extern int authnumfreekeys; 2236 extern u_long authkeylookups; 2237 extern u_long authkeynotfound; 2238 extern u_long authencryptions; 2239 extern u_long authdecryptions; 2240 extern u_long authkeyuncached; 2241 extern u_long authkeyexpired; 2242 2243 ia = (struct info_auth *)prepare_pkt(srcadr, inter, inpkt, 2244 sizeof(struct info_auth)); 2245 2246 ia->numkeys = htonl((u_int32)authnumkeys); 2247 ia->numfreekeys = htonl((u_int32)authnumfreekeys); 2248 ia->keylookups = htonl((u_int32)authkeylookups); 2249 ia->keynotfound = htonl((u_int32)authkeynotfound); 2250 ia->encryptions = htonl((u_int32)authencryptions); 2251 ia->decryptions = htonl((u_int32)authdecryptions); 2252 ia->keyuncached = htonl((u_int32)authkeyuncached); 2253 ia->expired = htonl((u_int32)authkeyexpired); 2254 ia->timereset = htonl((u_int32)(current_time - auth_timereset)); 2255 2256 (void) more_pkt(); 2257 flush_pkt(); 2258} 2259 2260 2261 2262/* 2263 * reset_auth_stats - reset the authentication stat counters. Done here 2264 * to keep ntp-isms out of the authentication module 2265 */ 2266static void 2267reset_auth_stats(void) 2268{ 2269 /* 2270 * Importations from the authentication module 2271 */ 2272 extern u_long authkeylookups; 2273 extern u_long authkeynotfound; 2274 extern u_long authencryptions; 2275 extern u_long authdecryptions; 2276 extern u_long authkeyuncached; 2277 2278 authkeylookups = 0; 2279 authkeynotfound = 0; 2280 authencryptions = 0; 2281 authdecryptions = 0; 2282 authkeyuncached = 0; 2283 auth_timereset = current_time; 2284} 2285 2286 2287/* 2288 * req_get_traps - return information about current trap holders 2289 */ 2290static void 2291req_get_traps( 2292 sockaddr_u *srcadr, 2293 struct interface *inter, 2294 struct req_pkt *inpkt 2295 ) 2296{ 2297 register struct info_trap *it; 2298 register struct ctl_trap *tr; 2299 register int i; 2300 2301 /* 2302 * Imported from the control module 2303 */ 2304 extern struct ctl_trap ctl_trap[]; 2305 extern int num_ctl_traps; 2306 2307 if (num_ctl_traps == 0) { 2308 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2309 return; 2310 } 2311 2312 it = (struct info_trap *)prepare_pkt(srcadr, inter, inpkt, 2313 v6sizeof(struct info_trap)); 2314 2315 for (i = 0, tr = ctl_trap; i < CTL_MAXTRAPS; i++, tr++) { 2316 if (tr->tr_flags & TRAP_INUSE) { 2317 if (IS_IPV4(&tr->tr_addr)) { 2318 if (tr->tr_localaddr == any_interface) 2319 it->local_address = 0; 2320 else 2321 it->local_address 2322 = NSRCADR(&tr->tr_localaddr->sin); 2323 it->trap_address = NSRCADR(&tr->tr_addr); 2324 if (client_v6_capable) 2325 it->v6_flag = 0; 2326 } else { 2327 if (!client_v6_capable) 2328 continue; 2329 it->local_address6 2330 = SOCK_ADDR6(&tr->tr_localaddr->sin); 2331 it->trap_address6 = SOCK_ADDR6(&tr->tr_addr); 2332 it->v6_flag = 1; 2333 } 2334 it->trap_port = NSRCPORT(&tr->tr_addr); 2335 it->sequence = htons(tr->tr_sequence); 2336 it->settime = htonl((u_int32)(current_time - tr->tr_settime)); 2337 it->origtime = htonl((u_int32)(current_time - tr->tr_origtime)); 2338 it->resets = htonl((u_int32)tr->tr_resets); 2339 it->flags = htonl((u_int32)tr->tr_flags); 2340 it = (struct info_trap *)more_pkt(); 2341 } 2342 } 2343 flush_pkt(); 2344} 2345 2346 2347/* 2348 * req_set_trap - configure a trap 2349 */ 2350static void 2351req_set_trap( 2352 sockaddr_u *srcadr, 2353 struct interface *inter, 2354 struct req_pkt *inpkt 2355 ) 2356{ 2357 do_setclr_trap(srcadr, inter, inpkt, 1); 2358} 2359 2360 2361 2362/* 2363 * req_clr_trap - unconfigure a trap 2364 */ 2365static void 2366req_clr_trap( 2367 sockaddr_u *srcadr, 2368 struct interface *inter, 2369 struct req_pkt *inpkt 2370 ) 2371{ 2372 do_setclr_trap(srcadr, inter, inpkt, 0); 2373} 2374 2375 2376 2377/* 2378 * do_setclr_trap - do the grunge work of (un)configuring a trap 2379 */ 2380static void 2381do_setclr_trap( 2382 sockaddr_u *srcadr, 2383 struct interface *inter, 2384 struct req_pkt *inpkt, 2385 int set 2386 ) 2387{ 2388 register struct conf_trap *ct; 2389 register struct interface *linter; 2390 int res; 2391 sockaddr_u laddr; 2392 2393 /* 2394 * Prepare sockaddr 2395 */ 2396 ZERO_SOCK(&laddr); 2397 AF(&laddr) = AF(srcadr); 2398 SET_PORT(&laddr, NTP_PORT); 2399 2400 /* 2401 * Restrict ourselves to one item only. This eliminates 2402 * the error reporting problem. 2403 */ 2404 if (INFO_NITEMS(inpkt->err_nitems) > 1) { 2405 msyslog(LOG_ERR, "do_setclr_trap: err_nitems > 1"); 2406 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 2407 return; 2408 } 2409 ct = (struct conf_trap *)inpkt->data; 2410 2411 /* 2412 * Look for the local interface. If none, use the default. 2413 */ 2414 if (ct->local_address == 0) { 2415 linter = any_interface; 2416 } else { 2417 if (IS_IPV4(&laddr)) 2418 NSRCADR(&laddr) = ct->local_address; 2419 else 2420 SOCK_ADDR6(&laddr) = ct->local_address6; 2421 linter = findinterface(&laddr); 2422 if (NULL == linter) { 2423 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2424 return; 2425 } 2426 } 2427 2428 if (IS_IPV4(&laddr)) 2429 NSRCADR(&laddr) = ct->trap_address; 2430 else 2431 SOCK_ADDR6(&laddr) = ct->trap_address6; 2432 if (ct->trap_port) 2433 NSRCPORT(&laddr) = ct->trap_port; 2434 else 2435 SET_PORT(&laddr, TRAPPORT); 2436 2437 if (set) { 2438 res = ctlsettrap(&laddr, linter, 0, 2439 INFO_VERSION(inpkt->rm_vn_mode)); 2440 } else { 2441 res = ctlclrtrap(&laddr, linter, 0); 2442 } 2443 2444 if (!res) { 2445 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2446 } else { 2447 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2448 } 2449 return; 2450} 2451 2452 2453 2454/* 2455 * set_request_keyid - set the keyid used to authenticate requests 2456 */ 2457static void 2458set_request_keyid( 2459 sockaddr_u *srcadr, 2460 struct interface *inter, 2461 struct req_pkt *inpkt 2462 ) 2463{ 2464 keyid_t keyid; 2465 2466 /* 2467 * Restrict ourselves to one item only. 2468 */ 2469 if (INFO_NITEMS(inpkt->err_nitems) > 1) { 2470 msyslog(LOG_ERR, "set_request_keyid: err_nitems > 1"); 2471 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 2472 return; 2473 } 2474 2475 keyid = ntohl(*((u_int32 *)(inpkt->data))); 2476 info_auth_keyid = keyid; 2477 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2478} 2479 2480 2481 2482/* 2483 * set_control_keyid - set the keyid used to authenticate requests 2484 */ 2485static void 2486set_control_keyid( 2487 sockaddr_u *srcadr, 2488 struct interface *inter, 2489 struct req_pkt *inpkt 2490 ) 2491{ 2492 keyid_t keyid; 2493 extern keyid_t ctl_auth_keyid; 2494 2495 /* 2496 * Restrict ourselves to one item only. 2497 */ 2498 if (INFO_NITEMS(inpkt->err_nitems) > 1) { 2499 msyslog(LOG_ERR, "set_control_keyid: err_nitems > 1"); 2500 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 2501 return; 2502 } 2503 2504 keyid = ntohl(*((u_int32 *)(inpkt->data))); 2505 ctl_auth_keyid = keyid; 2506 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2507} 2508 2509 2510 2511/* 2512 * get_ctl_stats - return some stats concerning the control message module 2513 */ 2514static void 2515get_ctl_stats( 2516 sockaddr_u *srcadr, 2517 struct interface *inter, 2518 struct req_pkt *inpkt 2519 ) 2520{ 2521 register struct info_control *ic; 2522 2523 /* 2524 * Importations from the control module 2525 */ 2526 extern u_long ctltimereset; 2527 extern u_long numctlreq; 2528 extern u_long numctlbadpkts; 2529 extern u_long numctlresponses; 2530 extern u_long numctlfrags; 2531 extern u_long numctlerrors; 2532 extern u_long numctltooshort; 2533 extern u_long numctlinputresp; 2534 extern u_long numctlinputfrag; 2535 extern u_long numctlinputerr; 2536 extern u_long numctlbadoffset; 2537 extern u_long numctlbadversion; 2538 extern u_long numctldatatooshort; 2539 extern u_long numctlbadop; 2540 extern u_long numasyncmsgs; 2541 2542 ic = (struct info_control *)prepare_pkt(srcadr, inter, inpkt, 2543 sizeof(struct info_control)); 2544 2545 ic->ctltimereset = htonl((u_int32)(current_time - ctltimereset)); 2546 ic->numctlreq = htonl((u_int32)numctlreq); 2547 ic->numctlbadpkts = htonl((u_int32)numctlbadpkts); 2548 ic->numctlresponses = htonl((u_int32)numctlresponses); 2549 ic->numctlfrags = htonl((u_int32)numctlfrags); 2550 ic->numctlerrors = htonl((u_int32)numctlerrors); 2551 ic->numctltooshort = htonl((u_int32)numctltooshort); 2552 ic->numctlinputresp = htonl((u_int32)numctlinputresp); 2553 ic->numctlinputfrag = htonl((u_int32)numctlinputfrag); 2554 ic->numctlinputerr = htonl((u_int32)numctlinputerr); 2555 ic->numctlbadoffset = htonl((u_int32)numctlbadoffset); 2556 ic->numctlbadversion = htonl((u_int32)numctlbadversion); 2557 ic->numctldatatooshort = htonl((u_int32)numctldatatooshort); 2558 ic->numctlbadop = htonl((u_int32)numctlbadop); 2559 ic->numasyncmsgs = htonl((u_int32)numasyncmsgs); 2560 2561 (void) more_pkt(); 2562 flush_pkt(); 2563} 2564 2565 2566#ifdef KERNEL_PLL 2567/* 2568 * get_kernel_info - get kernel pll/pps information 2569 */ 2570static void 2571get_kernel_info( 2572 sockaddr_u *srcadr, 2573 struct interface *inter, 2574 struct req_pkt *inpkt 2575 ) 2576{ 2577 register struct info_kernel *ik; 2578 struct timex ntx; 2579 2580 if (!pll_control) { 2581 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2582 return; 2583 } 2584 2585 memset((char *)&ntx, 0, sizeof(ntx)); 2586 if (ntp_adjtime(&ntx) < 0) 2587 msyslog(LOG_ERR, "get_kernel_info: ntp_adjtime() failed: %m"); 2588 ik = (struct info_kernel *)prepare_pkt(srcadr, inter, inpkt, 2589 sizeof(struct info_kernel)); 2590 2591 /* 2592 * pll variables 2593 */ 2594 ik->offset = htonl((u_int32)ntx.offset); 2595 ik->freq = htonl((u_int32)ntx.freq); 2596 ik->maxerror = htonl((u_int32)ntx.maxerror); 2597 ik->esterror = htonl((u_int32)ntx.esterror); 2598 ik->status = htons(ntx.status); 2599 ik->constant = htonl((u_int32)ntx.constant); 2600 ik->precision = htonl((u_int32)ntx.precision); 2601 ik->tolerance = htonl((u_int32)ntx.tolerance); 2602 2603 /* 2604 * pps variables 2605 */ 2606 ik->ppsfreq = htonl((u_int32)ntx.ppsfreq); 2607 ik->jitter = htonl((u_int32)ntx.jitter); 2608 ik->shift = htons(ntx.shift); 2609 ik->stabil = htonl((u_int32)ntx.stabil); 2610 ik->jitcnt = htonl((u_int32)ntx.jitcnt); 2611 ik->calcnt = htonl((u_int32)ntx.calcnt); 2612 ik->errcnt = htonl((u_int32)ntx.errcnt); 2613 ik->stbcnt = htonl((u_int32)ntx.stbcnt); 2614 2615 (void) more_pkt(); 2616 flush_pkt(); 2617} 2618#endif /* KERNEL_PLL */ 2619 2620 2621#ifdef REFCLOCK 2622/* 2623 * get_clock_info - get info about a clock 2624 */ 2625static void 2626get_clock_info( 2627 sockaddr_u *srcadr, 2628 struct interface *inter, 2629 struct req_pkt *inpkt 2630 ) 2631{ 2632 register struct info_clock *ic; 2633 register u_int32 *clkaddr; 2634 register int items; 2635 struct refclockstat clock_stat; 2636 sockaddr_u addr; 2637 l_fp ltmp; 2638 2639 ZERO_SOCK(&addr); 2640 AF(&addr) = AF_INET; 2641#ifdef ISC_PLATFORM_HAVESALEN 2642 addr.sas.ss_len = SOCKLEN(&addr); 2643#endif 2644 SET_PORT(&addr, NTP_PORT); 2645 items = INFO_NITEMS(inpkt->err_nitems); 2646 clkaddr = (u_int32 *) inpkt->data; 2647 2648 ic = (struct info_clock *)prepare_pkt(srcadr, inter, inpkt, 2649 sizeof(struct info_clock)); 2650 2651 while (items-- > 0) { 2652 NSRCADR(&addr) = *clkaddr++; 2653 if (!ISREFCLOCKADR(&addr) || 2654 findexistingpeer(&addr, NULL, -1) == NULL) { 2655 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2656 return; 2657 } 2658 2659 clock_stat.kv_list = (struct ctl_var *)0; 2660 2661 refclock_control(&addr, NULL, &clock_stat); 2662 2663 ic->clockadr = NSRCADR(&addr); 2664 ic->type = clock_stat.type; 2665 ic->flags = clock_stat.flags; 2666 ic->lastevent = clock_stat.lastevent; 2667 ic->currentstatus = clock_stat.currentstatus; 2668 ic->polls = htonl((u_int32)clock_stat.polls); 2669 ic->noresponse = htonl((u_int32)clock_stat.noresponse); 2670 ic->badformat = htonl((u_int32)clock_stat.badformat); 2671 ic->baddata = htonl((u_int32)clock_stat.baddata); 2672 ic->timestarted = htonl((u_int32)clock_stat.timereset); 2673 DTOLFP(clock_stat.fudgetime1, <mp); 2674 HTONL_FP(<mp, &ic->fudgetime1); 2675 DTOLFP(clock_stat.fudgetime2, <mp); 2676 HTONL_FP(<mp, &ic->fudgetime2); 2677 ic->fudgeval1 = htonl((u_int32)clock_stat.fudgeval1); 2678 ic->fudgeval2 = htonl((u_int32)clock_stat.fudgeval2); 2679 2680 free_varlist(clock_stat.kv_list); 2681 2682 ic = (struct info_clock *)more_pkt(); 2683 } 2684 flush_pkt(); 2685} 2686 2687 2688 2689/* 2690 * set_clock_fudge - get a clock's fudge factors 2691 */ 2692static void 2693set_clock_fudge( 2694 sockaddr_u *srcadr, 2695 struct interface *inter, 2696 struct req_pkt *inpkt 2697 ) 2698{ 2699 register struct conf_fudge *cf; 2700 register int items; 2701 struct refclockstat clock_stat; 2702 sockaddr_u addr; 2703 l_fp ltmp; 2704 2705 ZERO_SOCK(&addr); 2706 memset((char *)&clock_stat, 0, sizeof clock_stat); 2707 items = INFO_NITEMS(inpkt->err_nitems); 2708 cf = (struct conf_fudge *) inpkt->data; 2709 2710 while (items-- > 0) { 2711 AF(&addr) = AF_INET; 2712 NSRCADR(&addr) = cf->clockadr; 2713#ifdef ISC_PLATFORM_HAVESALEN 2714 addr.sas.ss_len = SOCKLEN(&addr); 2715#endif 2716 SET_PORT(&addr, NTP_PORT); 2717 if (!ISREFCLOCKADR(&addr) || 2718 findexistingpeer(&addr, NULL, -1) == 0) { 2719 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2720 return; 2721 } 2722 2723 switch(ntohl(cf->which)) { 2724 case FUDGE_TIME1: 2725 NTOHL_FP(&cf->fudgetime, <mp); 2726 LFPTOD(<mp, clock_stat.fudgetime1); 2727 clock_stat.haveflags = CLK_HAVETIME1; 2728 break; 2729 case FUDGE_TIME2: 2730 NTOHL_FP(&cf->fudgetime, <mp); 2731 LFPTOD(<mp, clock_stat.fudgetime2); 2732 clock_stat.haveflags = CLK_HAVETIME2; 2733 break; 2734 case FUDGE_VAL1: 2735 clock_stat.fudgeval1 = ntohl(cf->fudgeval_flags); 2736 clock_stat.haveflags = CLK_HAVEVAL1; 2737 break; 2738 case FUDGE_VAL2: 2739 clock_stat.fudgeval2 = ntohl(cf->fudgeval_flags); 2740 clock_stat.haveflags = CLK_HAVEVAL2; 2741 break; 2742 case FUDGE_FLAGS: 2743 clock_stat.flags = (u_char) (ntohl(cf->fudgeval_flags) & 0xf); 2744 clock_stat.haveflags = 2745 (CLK_HAVEFLAG1|CLK_HAVEFLAG2|CLK_HAVEFLAG3|CLK_HAVEFLAG4); 2746 break; 2747 default: 2748 msyslog(LOG_ERR, "set_clock_fudge: default!"); 2749 req_ack(srcadr, inter, inpkt, INFO_ERR_FMT); 2750 return; 2751 } 2752 2753 refclock_control(&addr, &clock_stat, (struct refclockstat *)0); 2754 } 2755 2756 req_ack(srcadr, inter, inpkt, INFO_OKAY); 2757} 2758#endif 2759 2760#ifdef REFCLOCK 2761/* 2762 * get_clkbug_info - get debugging info about a clock 2763 */ 2764static void 2765get_clkbug_info( 2766 sockaddr_u *srcadr, 2767 struct interface *inter, 2768 struct req_pkt *inpkt 2769 ) 2770{ 2771 register int i; 2772 register struct info_clkbug *ic; 2773 register u_int32 *clkaddr; 2774 register int items; 2775 struct refclockbug bug; 2776 sockaddr_u addr; 2777 2778 ZERO_SOCK(&addr); 2779 AF(&addr) = AF_INET; 2780#ifdef ISC_PLATFORM_HAVESALEN 2781 addr.sas.ss_len = SOCKLEN(&addr); 2782#endif 2783 SET_PORT(&addr, NTP_PORT); 2784 items = INFO_NITEMS(inpkt->err_nitems); 2785 clkaddr = (u_int32 *) inpkt->data; 2786 2787 ic = (struct info_clkbug *)prepare_pkt(srcadr, inter, inpkt, 2788 sizeof(struct info_clkbug)); 2789 2790 while (items-- > 0) { 2791 NSRCADR(&addr) = *clkaddr++; 2792 if (!ISREFCLOCKADR(&addr) || 2793 findexistingpeer(&addr, NULL, -1) == 0) { 2794 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2795 return; 2796 } 2797 2798 memset((char *)&bug, 0, sizeof bug); 2799 refclock_buginfo(&addr, &bug); 2800 if (bug.nvalues == 0 && bug.ntimes == 0) { 2801 req_ack(srcadr, inter, inpkt, INFO_ERR_NODATA); 2802 return; 2803 } 2804 2805 ic->clockadr = NSRCADR(&addr); 2806 i = bug.nvalues; 2807 if (i > NUMCBUGVALUES) 2808 i = NUMCBUGVALUES; 2809 ic->nvalues = (u_char)i; 2810 ic->svalues = htons((u_short) (bug.svalues & ((1<<i)-1))); 2811 while (--i >= 0) 2812 ic->values[i] = htonl(bug.values[i]); 2813 2814 i = bug.ntimes; 2815 if (i > NUMCBUGTIMES) 2816 i = NUMCBUGTIMES; 2817 ic->ntimes = (u_char)i; 2818 ic->stimes = htonl(bug.stimes); 2819 while (--i >= 0) { 2820 HTONL_FP(&bug.times[i], &ic->times[i]); 2821 } 2822 2823 ic = (struct info_clkbug *)more_pkt(); 2824 } 2825 flush_pkt(); 2826} 2827#endif 2828 2829/* 2830 * receiver of interface structures 2831 */ 2832static void 2833fill_info_if_stats(void *data, interface_info_t *interface_info) 2834{ 2835 struct info_if_stats **ifsp = (struct info_if_stats **)data; 2836 struct info_if_stats *ifs = *ifsp; 2837 struct interface *interface = interface_info->interface; 2838 2839 memset(ifs, 0, sizeof(*ifs)); 2840 2841 if (IS_IPV6(&interface->sin)) { 2842 if (!client_v6_capable) { 2843 return; 2844 } 2845 ifs->v6_flag = 1; 2846 ifs->unaddr.addr6 = SOCK_ADDR6(&interface->sin); 2847 ifs->unbcast.addr6 = SOCK_ADDR6(&interface->bcast); 2848 ifs->unmask.addr6 = SOCK_ADDR6(&interface->mask); 2849 } else { 2850 ifs->v6_flag = 0; 2851 ifs->unaddr.addr = SOCK_ADDR4(&interface->sin); 2852 ifs->unbcast.addr = SOCK_ADDR4(&interface->bcast); 2853 ifs->unmask.addr = SOCK_ADDR4(&interface->mask); 2854 } 2855 ifs->v6_flag = htonl(ifs->v6_flag); 2856 strncpy(ifs->name, interface->name, sizeof(ifs->name)); 2857 ifs->family = htons(interface->family); 2858 ifs->flags = htonl(interface->flags); 2859 ifs->last_ttl = htonl(interface->last_ttl); 2860 ifs->num_mcast = htonl(interface->num_mcast); 2861 ifs->received = htonl(interface->received); 2862 ifs->sent = htonl(interface->sent); 2863 ifs->notsent = htonl(interface->notsent); 2864 ifs->scopeid = htonl(interface->scopeid); 2865 /* ifindex was always zero, now no longer in struct interface */ 2866 ifs->ifindex = 0; 2867 ifs->ifnum = htonl(interface->ifnum); 2868 ifs->uptime = htonl(current_time - interface->starttime); 2869 ifs->ignore_packets = interface->ignore_packets; 2870 ifs->peercnt = htonl(interface->peercnt); 2871 ifs->action = interface_info->action; 2872 2873 *ifsp = (struct info_if_stats *)more_pkt(); 2874} 2875 2876/* 2877 * get_if_stats - get interface statistics 2878 */ 2879static void 2880get_if_stats( 2881 sockaddr_u *srcadr, 2882 struct interface *inter, 2883 struct req_pkt *inpkt 2884 ) 2885{ 2886 struct info_if_stats *ifs; 2887 2888 DPRINTF(3, ("wants interface statistics\n")); 2889 2890 ifs = (struct info_if_stats *)prepare_pkt(srcadr, inter, inpkt, 2891 v6sizeof(struct info_if_stats)); 2892 2893 interface_enumerate(fill_info_if_stats, &ifs); 2894 2895 flush_pkt(); 2896} 2897 2898static void 2899do_if_reload( 2900 sockaddr_u *srcadr, 2901 struct interface *inter, 2902 struct req_pkt *inpkt 2903 ) 2904{ 2905 struct info_if_stats *ifs; 2906 2907 DPRINTF(3, ("wants interface reload\n")); 2908 2909 ifs = (struct info_if_stats *)prepare_pkt(srcadr, inter, inpkt, 2910 v6sizeof(struct info_if_stats)); 2911 2912 interface_update(fill_info_if_stats, &ifs); 2913 2914 flush_pkt(); 2915} 2916 2917