1 /* $NetBSD: ntp_parser.y,v 1.15 2016/11/22 03:09:30 christos Exp $ */ 2 3 /* ntp_parser.y 4 * 5 * The parser for the NTP configuration file. 6 * 7 * Written By: Sachin Kamboj 8 * University of Delaware 9 * Newark, DE 19711 10 * Copyright (c) 2006 11 */ 12 13 %{ 14 #ifdef HAVE_CONFIG_H 15 # include <config.h> 16 #endif 17 18 #include "ntp.h" 19 #include "ntpd.h" 20 #include "ntp_machine.h" 21 #include "ntp_stdlib.h" 22 #include "ntp_filegen.h" 23 #include "ntp_scanner.h" 24 #include "ntp_config.h" 25 #include "ntp_crypto.h" 26 27 #include "ntpsim.h" /* HMS: Do we really want this all the time? */ 28 /* SK: It might be a good idea to always 29 include the simulator code. That way 30 someone can use the same configuration file 31 for both the simulator and the daemon 32 */ 33 34 #define YYMALLOC emalloc 35 #define YYFREE free 36 #define YYERROR_VERBOSE 37 #define YYMAXDEPTH 1000 /* stop the madness sooner */ 38 void yyerror(const char *msg); 39 40 #ifdef SIM 41 # define ONLY_SIM(a) (a) 42 #else 43 # define ONLY_SIM(a) NULL 44 #endif 45 %} 46 47 /* 48 * Enable generation of token names array even without YYDEBUG. 49 * We access via token_name() defined below. 50 */ 51 %token-table 52 53 %union { 54 char * String; 55 double Double; 56 int Integer; 57 unsigned U_int; 58 gen_fifo * Generic_fifo; 59 attr_val * Attr_val; 60 attr_val_fifo * Attr_val_fifo; 61 int_fifo * Int_fifo; 62 string_fifo * String_fifo; 63 address_node * Address_node; 64 address_fifo * Address_fifo; 65 setvar_node * Set_var; 66 server_info * Sim_server; 67 server_info_fifo * Sim_server_fifo; 68 script_info * Sim_script; 69 script_info_fifo * Sim_script_fifo; 70 } 71 72 /* TERMINALS (do not appear left of colon) */ 73 %token <Integer> T_Abbrev 74 %token <Integer> T_Age 75 %token <Integer> T_All 76 %token <Integer> T_Allan 77 %token <Integer> T_Allpeers 78 %token <Integer> T_Auth 79 %token <Integer> T_Autokey 80 %token <Integer> T_Automax 81 %token <Integer> T_Average 82 %token <Integer> T_Bclient 83 %token <Integer> T_Bcpollbstep 84 %token <Integer> T_Beacon 85 %token <Integer> T_Broadcast 86 %token <Integer> T_Broadcastclient 87 %token <Integer> T_Broadcastdelay 88 %token <Integer> T_Burst 89 %token <Integer> T_Calibrate 90 %token <Integer> T_Ceiling 91 %token <Integer> T_Clockstats 92 %token <Integer> T_Cohort 93 %token <Integer> T_ControlKey 94 %token <Integer> T_Crypto 95 %token <Integer> T_Cryptostats 96 %token <Integer> T_Ctl 97 %token <Integer> T_Day 98 %token <Integer> T_Default 99 %token <Integer> T_Digest 100 %token <Integer> T_Disable 101 %token <Integer> T_Discard 102 %token <Integer> T_Dispersion 103 %token <Double> T_Double /* not a token */ 104 %token <Integer> T_Driftfile 105 %token <Integer> T_Drop 106 %token <Integer> T_Dscp 107 %token <Integer> T_Ellipsis /* "..." not "ellipsis" */ 108 %token <Integer> T_Enable 109 %token <Integer> T_End 110 %token <Integer> T_False 111 %token <Integer> T_File 112 %token <Integer> T_Filegen 113 %token <Integer> T_Filenum 114 %token <Integer> T_Flag1 115 %token <Integer> T_Flag2 116 %token <Integer> T_Flag3 117 %token <Integer> T_Flag4 118 %token <Integer> T_Flake 119 %token <Integer> T_Floor 120 %token <Integer> T_Freq 121 %token <Integer> T_Fudge 122 %token <Integer> T_Host 123 %token <Integer> T_Huffpuff 124 %token <Integer> T_Iburst 125 %token <Integer> T_Ident 126 %token <Integer> T_Ignore 127 %token <Integer> T_Incalloc 128 %token <Integer> T_Incmem 129 %token <Integer> T_Initalloc 130 %token <Integer> T_Initmem 131 %token <Integer> T_Includefile 132 %token <Integer> T_Integer /* not a token */ 133 %token <Integer> T_Interface 134 %token <Integer> T_Intrange /* not a token */ 135 %token <Integer> T_Io 136 %token <Integer> T_Ipv4 137 %token <Integer> T_Ipv4_flag 138 %token <Integer> T_Ipv6 139 %token <Integer> T_Ipv6_flag 140 %token <Integer> T_Kernel 141 %token <Integer> T_Key 142 %token <Integer> T_Keys 143 %token <Integer> T_Keysdir 144 %token <Integer> T_Kod 145 %token <Integer> T_Mssntp 146 %token <Integer> T_Leapfile 147 %token <Integer> T_Leapsmearinterval 148 %token <Integer> T_Limited 149 %token <Integer> T_Link 150 %token <Integer> T_Listen 151 %token <Integer> T_Logconfig 152 %token <Integer> T_Logfile 153 %token <Integer> T_Loopstats 154 %token <Integer> T_Lowpriotrap 155 %token <Integer> T_Manycastclient 156 %token <Integer> T_Manycastserver 157 %token <Integer> T_Mask 158 %token <Integer> T_Maxage 159 %token <Integer> T_Maxclock 160 %token <Integer> T_Maxdepth 161 %token <Integer> T_Maxdist 162 %token <Integer> T_Maxmem 163 %token <Integer> T_Maxpoll 164 %token <Integer> T_Mdnstries 165 %token <Integer> T_Mem 166 %token <Integer> T_Memlock 167 %token <Integer> T_Minclock 168 %token <Integer> T_Mindepth 169 %token <Integer> T_Mindist 170 %token <Integer> T_Minimum 171 %token <Integer> T_Minpoll 172 %token <Integer> T_Minsane 173 %token <Integer> T_Mode 174 %token <Integer> T_Mode7 175 %token <Integer> T_Monitor 176 %token <Integer> T_Month 177 %token <Integer> T_Mru 178 %token <Integer> T_Multicastclient 179 %token <Integer> T_Nic 180 %token <Integer> T_Nolink 181 %token <Integer> T_Nomodify 182 %token <Integer> T_Nomrulist 183 %token <Integer> T_None 184 %token <Integer> T_Nonvolatile 185 %token <Integer> T_Nopeer 186 %token <Integer> T_Noquery 187 %token <Integer> T_Noselect 188 %token <Integer> T_Noserve 189 %token <Integer> T_Notrap 190 %token <Integer> T_Notrust 191 %token <Integer> T_Ntp 192 %token <Integer> T_Ntpport 193 %token <Integer> T_NtpSignDsocket 194 %token <Integer> T_Orphan 195 %token <Integer> T_Orphanwait 196 %token <Integer> T_PCEdigest 197 %token <Integer> T_Panic 198 %token <Integer> T_Peer 199 %token <Integer> T_Peerstats 200 %token <Integer> T_Phone 201 %token <Integer> T_Pid 202 %token <Integer> T_Pidfile 203 %token <Integer> T_Pool 204 %token <Integer> T_Port 205 %token <Integer> T_Preempt 206 %token <Integer> T_Prefer 207 %token <Integer> T_Protostats 208 %token <Integer> T_Pw 209 %token <Integer> T_Randfile 210 %token <Integer> T_Rawstats 211 %token <Integer> T_Refid 212 %token <Integer> T_Requestkey 213 %token <Integer> T_Reset 214 %token <Integer> T_Restrict 215 %token <Integer> T_Revoke 216 %token <Integer> T_Rlimit 217 %token <Integer> T_Saveconfigdir 218 %token <Integer> T_Server 219 %token <Integer> T_Setvar 220 %token <Integer> T_Source 221 %token <Integer> T_Stacksize 222 %token <Integer> T_Statistics 223 %token <Integer> T_Stats 224 %token <Integer> T_Statsdir 225 %token <Integer> T_Step 226 %token <Integer> T_Stepback 227 %token <Integer> T_Stepfwd 228 %token <Integer> T_Stepout 229 %token <Integer> T_Stratum 230 %token <String> T_String /* not a token */ 231 %token <Integer> T_Sys 232 %token <Integer> T_Sysstats 233 %token <Integer> T_Tick 234 %token <Integer> T_Time1 235 %token <Integer> T_Time2 236 %token <Integer> T_Timer 237 %token <Integer> T_Timingstats 238 %token <Integer> T_Tinker 239 %token <Integer> T_Tos 240 %token <Integer> T_Trap 241 %token <Integer> T_True 242 %token <Integer> T_Trustedkey 243 %token <Integer> T_Ttl 244 %token <Integer> T_Type 245 %token <Integer> T_U_int /* Not a token */ 246 %token <Integer> T_UEcrypto 247 %token <Integer> T_UEcryptonak 248 %token <Integer> T_UEdigest 249 %token <Integer> T_Unconfig 250 %token <Integer> T_Unpeer 251 %token <Integer> T_Version 252 %token <Integer> T_WanderThreshold /* Not a token */ 253 %token <Integer> T_Week 254 %token <Integer> T_Wildcard 255 %token <Integer> T_Xleave 256 %token <Integer> T_Year 257 %token <Integer> T_Flag /* Not a token */ 258 %token <Integer> T_EOC 259 260 261 /* NTP Simulator Tokens */ 262 %token <Integer> T_Simulate 263 %token <Integer> T_Beep_Delay 264 %token <Integer> T_Sim_Duration 265 %token <Integer> T_Server_Offset 266 %token <Integer> T_Duration 267 %token <Integer> T_Freq_Offset 268 %token <Integer> T_Wander 269 %token <Integer> T_Jitter 270 %token <Integer> T_Prop_Delay 271 %token <Integer> T_Proc_Delay 272 273 274 275 /*** NON-TERMINALS ***/ 276 %type <Integer> access_control_flag 277 %type <Int_fifo> ac_flag_list 278 %type <Address_node> address 279 %type <Integer> address_fam 280 %type <Address_fifo> address_list 281 %type <Integer> boolean 282 %type <Integer> client_type 283 %type <Integer> counter_set_keyword 284 %type <Int_fifo> counter_set_list 285 %type <Attr_val> crypto_command 286 %type <Attr_val_fifo> crypto_command_list 287 %type <Integer> crypto_str_keyword 288 %type <Attr_val> discard_option 289 %type <Integer> discard_option_keyword 290 %type <Attr_val_fifo> discard_option_list 291 %type <Integer> enable_disable 292 %type <Attr_val> filegen_option 293 %type <Attr_val_fifo> filegen_option_list 294 %type <Integer> filegen_type 295 %type <Attr_val> fudge_factor 296 %type <Integer> fudge_factor_bool_keyword 297 %type <Integer> fudge_factor_dbl_keyword 298 %type <Attr_val_fifo> fudge_factor_list 299 %type <Attr_val_fifo> integer_list 300 %type <Attr_val_fifo> integer_list_range 301 %type <Attr_val> integer_list_range_elt 302 %type <Attr_val> integer_range 303 %type <Integer> nic_rule_action 304 %type <Integer> interface_command 305 %type <Integer> interface_nic 306 %type <Address_node> ip_address 307 %type <Integer> link_nolink 308 %type <Attr_val> log_config_command 309 %type <Attr_val_fifo> log_config_list 310 %type <Integer> misc_cmd_dbl_keyword 311 %type <Integer> misc_cmd_int_keyword 312 %type <Integer> misc_cmd_str_keyword 313 %type <Integer> misc_cmd_str_lcl_keyword 314 %type <Attr_val> mru_option 315 %type <Integer> mru_option_keyword 316 %type <Attr_val_fifo> mru_option_list 317 %type <Integer> nic_rule_class 318 %type <Double> number 319 %type <Attr_val> option 320 %type <Attr_val> option_flag 321 %type <Integer> option_flag_keyword 322 %type <Attr_val_fifo> option_list 323 %type <Attr_val> option_int 324 %type <Integer> option_int_keyword 325 %type <Attr_val> option_str 326 %type <Integer> option_str_keyword 327 %type <Integer> reset_command 328 %type <Integer> rlimit_option_keyword 329 %type <Attr_val> rlimit_option 330 %type <Attr_val_fifo> rlimit_option_list 331 %type <Integer> stat 332 %type <Int_fifo> stats_list 333 %type <String_fifo> string_list 334 %type <Attr_val> system_option 335 %type <Integer> system_option_flag_keyword 336 %type <Integer> system_option_local_flag_keyword 337 %type <Attr_val_fifo> system_option_list 338 %type <Integer> t_default_or_zero 339 %type <Integer> tinker_option_keyword 340 %type <Attr_val> tinker_option 341 %type <Attr_val_fifo> tinker_option_list 342 %type <Attr_val> tos_option 343 %type <Integer> tos_option_dbl_keyword 344 %type <Integer> tos_option_int_keyword 345 %type <Attr_val_fifo> tos_option_list 346 %type <Attr_val> trap_option 347 %type <Attr_val_fifo> trap_option_list 348 %type <Integer> unpeer_keyword 349 %type <Set_var> variable_assign 350 351 /* NTP Simulator non-terminals */ 352 %type <Attr_val> sim_init_statement 353 %type <Attr_val_fifo> sim_init_statement_list 354 %type <Integer> sim_init_keyword 355 %type <Sim_server_fifo> sim_server_list 356 %type <Sim_server> sim_server 357 %type <Double> sim_server_offset 358 %type <Address_node> sim_server_name 359 %type <Sim_script> sim_act 360 %type <Sim_script_fifo> sim_act_list 361 %type <Integer> sim_act_keyword 362 %type <Attr_val_fifo> sim_act_stmt_list 363 %type <Attr_val> sim_act_stmt 364 365 %% 366 367 /* ntp.conf 368 * Configuration File Grammar 369 * -------------------------- 370 */ 371 372 configuration 373 : command_list 374 ; 375 376 command_list 377 : command_list command T_EOC 378 | command T_EOC 379 | error T_EOC 380 { 381 /* I will need to incorporate much more fine grained 382 * error messages. The following should suffice for 383 * the time being. 384 */ 385 struct FILE_INFO * ip_ctx = lex_current(); 386 msyslog(LOG_ERR, 387 "syntax error in %s line %d, column %d", 388 ip_ctx->fname, 389 ip_ctx->errpos.nline, 390 ip_ctx->errpos.ncol); 391 } 392 ; 393 394 command : /* NULL STATEMENT */ 395 | server_command 396 | unpeer_command 397 | other_mode_command 398 | authentication_command 399 | monitoring_command 400 | access_control_command 401 | orphan_mode_command 402 | fudge_command 403 | rlimit_command 404 | system_option_command 405 | tinker_command 406 | miscellaneous_command 407 | simulate_command 408 ; 409 410 /* Server Commands 411 * --------------- 412 */ 413 414 server_command 415 : client_type address option_list 416 { 417 peer_node *my_node; 418 419 my_node = create_peer_node($1, $2, $3); 420 APPEND_G_FIFO(cfgt.peers, my_node); 421 } 422 ; 423 424 client_type 425 : T_Server 426 | T_Pool 427 | T_Peer 428 | T_Broadcast 429 | T_Manycastclient 430 ; 431 432 address 433 : ip_address 434 | address_fam T_String 435 { $$ = create_address_node($2, $1); } 436 ; 437 438 ip_address 439 : T_String 440 { $$ = create_address_node($1, AF_UNSPEC); } 441 ; 442 443 address_fam 444 : T_Ipv4_flag 445 { $$ = AF_INET; } 446 | T_Ipv6_flag 447 { $$ = AF_INET6; } 448 ; 449 450 option_list 451 : /* empty list */ 452 { $$ = NULL; } 453 | option_list option 454 { 455 $$ = $1; 456 APPEND_G_FIFO($$, $2); 457 } 458 ; 459 460 option 461 : option_flag 462 | option_int 463 | option_str 464 ; 465 466 option_flag 467 : option_flag_keyword 468 { $$ = create_attr_ival(T_Flag, $1); } 469 ; 470 471 option_flag_keyword 472 : T_Autokey 473 | T_Burst 474 | T_Iburst 475 | T_Noselect 476 | T_Preempt 477 | T_Prefer 478 | T_True 479 | T_Xleave 480 ; 481 482 option_int 483 : option_int_keyword T_Integer 484 { $$ = create_attr_ival($1, $2); } 485 | option_int_keyword T_U_int 486 { $$ = create_attr_uval($1, $2); } 487 ; 488 489 option_int_keyword 490 : T_Key 491 | T_Minpoll 492 | T_Maxpoll 493 | T_Ttl 494 | T_Mode 495 | T_Version 496 ; 497 498 option_str 499 : option_str_keyword T_String 500 { $$ = create_attr_sval($1, $2); } 501 ; 502 503 option_str_keyword 504 : T_Ident 505 ; 506 507 508 /* unpeer commands 509 * --------------- 510 */ 511 512 unpeer_command 513 : unpeer_keyword address 514 { 515 unpeer_node *my_node; 516 517 my_node = create_unpeer_node($2); 518 if (my_node) 519 APPEND_G_FIFO(cfgt.unpeers, my_node); 520 } 521 ; 522 unpeer_keyword 523 : T_Unconfig 524 | T_Unpeer 525 ; 526 527 528 /* Other Modes 529 * (broadcastclient manycastserver multicastclient) 530 * ------------------------------------------------ 531 */ 532 533 other_mode_command 534 : T_Broadcastclient 535 { cfgt.broadcastclient = 1; } 536 | T_Manycastserver address_list 537 { CONCAT_G_FIFOS(cfgt.manycastserver, $2); } 538 | T_Multicastclient address_list 539 { CONCAT_G_FIFOS(cfgt.multicastclient, $2); } 540 | T_Mdnstries T_Integer 541 { cfgt.mdnstries = $2; } 542 ; 543 544 545 546 /* Authentication Commands 547 * ----------------------- 548 */ 549 550 authentication_command 551 : T_Automax T_Integer 552 { 553 attr_val *atrv; 554 555 atrv = create_attr_ival($1, $2); 556 APPEND_G_FIFO(cfgt.vars, atrv); 557 } 558 | T_ControlKey T_Integer 559 { cfgt.auth.control_key = $2; } 560 | T_Crypto crypto_command_list 561 { 562 cfgt.auth.cryptosw++; 563 CONCAT_G_FIFOS(cfgt.auth.crypto_cmd_list, $2); 564 } 565 | T_Keys T_String 566 { cfgt.auth.keys = $2; } 567 | T_Keysdir T_String 568 { cfgt.auth.keysdir = $2; } 569 | T_Requestkey T_Integer 570 { cfgt.auth.request_key = $2; } 571 | T_Revoke T_Integer 572 { cfgt.auth.revoke = $2; } 573 | T_Trustedkey integer_list_range 574 { 575 cfgt.auth.trusted_key_list = $2; 576 577 // if (!cfgt.auth.trusted_key_list) 578 // cfgt.auth.trusted_key_list = $2; 579 // else 580 // LINK_SLIST(cfgt.auth.trusted_key_list, $2, link); 581 } 582 | T_NtpSignDsocket T_String 583 { cfgt.auth.ntp_signd_socket = $2; } 584 ; 585 586 crypto_command_list 587 : /* empty list */ 588 { $$ = NULL; } 589 | crypto_command_list crypto_command 590 { 591 $$ = $1; 592 APPEND_G_FIFO($$, $2); 593 } 594 ; 595 596 crypto_command 597 : crypto_str_keyword T_String 598 { $$ = create_attr_sval($1, $2); } 599 | T_Revoke T_Integer 600 { 601 $$ = NULL; 602 cfgt.auth.revoke = $2; 603 msyslog(LOG_WARNING, 604 "'crypto revoke %d' is deprecated, " 605 "please use 'revoke %d' instead.", 606 cfgt.auth.revoke, cfgt.auth.revoke); 607 } 608 ; 609 610 crypto_str_keyword 611 : T_Host 612 | T_Ident 613 | T_Pw 614 | T_Randfile 615 | T_Digest 616 ; 617 618 619 /* Orphan Mode Commands 620 * -------------------- 621 */ 622 623 orphan_mode_command 624 : T_Tos tos_option_list 625 { CONCAT_G_FIFOS(cfgt.orphan_cmds, $2); } 626 ; 627 628 tos_option_list 629 : tos_option_list tos_option 630 { 631 $$ = $1; 632 APPEND_G_FIFO($$, $2); 633 } 634 | tos_option 635 { 636 $$ = NULL; 637 APPEND_G_FIFO($$, $1); 638 } 639 ; 640 641 tos_option 642 : tos_option_int_keyword T_Integer 643 { $$ = create_attr_dval($1, (double)$2); } 644 | tos_option_dbl_keyword number 645 { $$ = create_attr_dval($1, $2); } 646 | T_Cohort boolean 647 { $$ = create_attr_dval($1, (double)$2); } 648 ; 649 650 tos_option_int_keyword 651 : T_Bcpollbstep 652 | T_Ceiling 653 | T_Floor 654 | T_Orphan 655 | T_Orphanwait 656 | T_Minsane 657 | T_Beacon 658 ; 659 660 tos_option_dbl_keyword 661 : T_Mindist 662 | T_Maxdist 663 | T_Minclock 664 | T_Maxclock 665 ; 666 667 668 /* Monitoring Commands 669 * ------------------- 670 */ 671 672 monitoring_command 673 : T_Statistics stats_list 674 { CONCAT_G_FIFOS(cfgt.stats_list, $2); } 675 | T_Statsdir T_String 676 { 677 if (lex_from_file()) { 678 cfgt.stats_dir = $2; 679 } else { 680 YYFREE($2); 681 yyerror("statsdir remote configuration ignored"); 682 } 683 } 684 | T_Filegen stat filegen_option_list 685 { 686 filegen_node *fgn; 687 688 fgn = create_filegen_node($2, $3); 689 APPEND_G_FIFO(cfgt.filegen_opts, fgn); 690 } 691 ; 692 693 stats_list 694 : stats_list stat 695 { 696 $$ = $1; 697 APPEND_G_FIFO($$, create_int_node($2)); 698 } 699 | stat 700 { 701 $$ = NULL; 702 APPEND_G_FIFO($$, create_int_node($1)); 703 } 704 ; 705 706 stat 707 : T_Clockstats 708 | T_Cryptostats 709 | T_Loopstats 710 | T_Peerstats 711 | T_Rawstats 712 | T_Sysstats 713 | T_Timingstats 714 | T_Protostats 715 ; 716 717 filegen_option_list 718 : /* empty list */ 719 { $$ = NULL; } 720 | filegen_option_list filegen_option 721 { 722 $$ = $1; 723 APPEND_G_FIFO($$, $2); 724 } 725 ; 726 727 filegen_option 728 : T_File T_String 729 { 730 if (lex_from_file()) { 731 $$ = create_attr_sval($1, $2); 732 } else { 733 $$ = NULL; 734 YYFREE($2); 735 yyerror("filegen file remote config ignored"); 736 } 737 } 738 | T_Type filegen_type 739 { 740 if (lex_from_file()) { 741 $$ = create_attr_ival($1, $2); 742 } else { 743 $$ = NULL; 744 yyerror("filegen type remote config ignored"); 745 } 746 } 747 | link_nolink 748 { 749 const char *err; 750 751 if (lex_from_file()) { 752 $$ = create_attr_ival(T_Flag, $1); 753 } else { 754 $$ = NULL; 755 if (T_Link == $1) 756 err = "filegen link remote config ignored"; 757 else 758 err = "filegen nolink remote config ignored"; 759 yyerror(err); 760 } 761 } 762 | enable_disable 763 { $$ = create_attr_ival(T_Flag, $1); } 764 ; 765 766 link_nolink 767 : T_Link 768 | T_Nolink 769 ; 770 771 enable_disable 772 : T_Enable 773 | T_Disable 774 ; 775 776 filegen_type 777 : T_None 778 | T_Pid 779 | T_Day 780 | T_Week 781 | T_Month 782 | T_Year 783 | T_Age 784 ; 785 786 787 /* Access Control Commands 788 * ----------------------- 789 */ 790 791 access_control_command 792 : T_Discard discard_option_list 793 { 794 CONCAT_G_FIFOS(cfgt.discard_opts, $2); 795 } 796 | T_Mru mru_option_list 797 { 798 CONCAT_G_FIFOS(cfgt.mru_opts, $2); 799 } 800 | T_Restrict address ac_flag_list 801 { 802 restrict_node *rn; 803 804 rn = create_restrict_node($2, NULL, $3, 805 lex_current()->curpos.nline); 806 APPEND_G_FIFO(cfgt.restrict_opts, rn); 807 } 808 | T_Restrict ip_address T_Mask ip_address ac_flag_list 809 { 810 restrict_node *rn; 811 812 rn = create_restrict_node($2, $4, $5, 813 lex_current()->curpos.nline); 814 APPEND_G_FIFO(cfgt.restrict_opts, rn); 815 } 816 | T_Restrict T_Default ac_flag_list 817 { 818 restrict_node *rn; 819 820 rn = create_restrict_node(NULL, NULL, $3, 821 lex_current()->curpos.nline); 822 APPEND_G_FIFO(cfgt.restrict_opts, rn); 823 } 824 | T_Restrict T_Ipv4_flag T_Default ac_flag_list 825 { 826 restrict_node *rn; 827 828 rn = create_restrict_node( 829 create_address_node( 830 estrdup("0.0.0.0"), 831 AF_INET), 832 create_address_node( 833 estrdup("0.0.0.0"), 834 AF_INET), 835 $4, 836 lex_current()->curpos.nline); 837 APPEND_G_FIFO(cfgt.restrict_opts, rn); 838 } 839 | T_Restrict T_Ipv6_flag T_Default ac_flag_list 840 { 841 restrict_node *rn; 842 843 rn = create_restrict_node( 844 create_address_node( 845 estrdup("::"), 846 AF_INET6), 847 create_address_node( 848 estrdup("::"), 849 AF_INET6), 850 $4, 851 lex_current()->curpos.nline); 852 APPEND_G_FIFO(cfgt.restrict_opts, rn); 853 } 854 | T_Restrict T_Source ac_flag_list 855 { 856 restrict_node * rn; 857 858 APPEND_G_FIFO($3, create_int_node($2)); 859 rn = create_restrict_node( 860 NULL, NULL, $3, lex_current()->curpos.nline); 861 APPEND_G_FIFO(cfgt.restrict_opts, rn); 862 } 863 ; 864 865 ac_flag_list 866 : /* empty list is allowed */ 867 { $$ = NULL; } 868 | ac_flag_list access_control_flag 869 { 870 $$ = $1; 871 APPEND_G_FIFO($$, create_int_node($2)); 872 } 873 ; 874 875 access_control_flag 876 : T_Flake 877 | T_Ignore 878 | T_Kod 879 | T_Mssntp 880 | T_Limited 881 | T_Lowpriotrap 882 | T_Nomodify 883 | T_Nomrulist 884 | T_Nopeer 885 | T_Noquery 886 | T_Noserve 887 | T_Notrap 888 | T_Notrust 889 | T_Ntpport 890 | T_Version 891 ; 892 893 discard_option_list 894 : discard_option_list discard_option 895 { 896 $$ = $1; 897 APPEND_G_FIFO($$, $2); 898 } 899 | discard_option 900 { 901 $$ = NULL; 902 APPEND_G_FIFO($$, $1); 903 } 904 ; 905 906 discard_option 907 : discard_option_keyword T_Integer 908 { $$ = create_attr_ival($1, $2); } 909 ; 910 911 discard_option_keyword 912 : T_Average 913 | T_Minimum 914 | T_Monitor 915 ; 916 917 mru_option_list 918 : mru_option_list mru_option 919 { 920 $$ = $1; 921 APPEND_G_FIFO($$, $2); 922 } 923 | mru_option 924 { 925 $$ = NULL; 926 APPEND_G_FIFO($$, $1); 927 } 928 ; 929 930 mru_option 931 : mru_option_keyword T_Integer 932 { $$ = create_attr_ival($1, $2); } 933 ; 934 935 mru_option_keyword 936 : T_Incalloc 937 | T_Incmem 938 | T_Initalloc 939 | T_Initmem 940 | T_Maxage 941 | T_Maxdepth 942 | T_Maxmem 943 | T_Mindepth 944 ; 945 946 /* Fudge Commands 947 * -------------- 948 */ 949 950 fudge_command 951 : T_Fudge address fudge_factor_list 952 { 953 addr_opts_node *aon; 954 955 aon = create_addr_opts_node($2, $3); 956 APPEND_G_FIFO(cfgt.fudge, aon); 957 } 958 ; 959 960 fudge_factor_list 961 : fudge_factor_list fudge_factor 962 { 963 $$ = $1; 964 APPEND_G_FIFO($$, $2); 965 } 966 | fudge_factor 967 { 968 $$ = NULL; 969 APPEND_G_FIFO($$, $1); 970 } 971 ; 972 973 fudge_factor 974 : fudge_factor_dbl_keyword number 975 { $$ = create_attr_dval($1, $2); } 976 | fudge_factor_bool_keyword boolean 977 { $$ = create_attr_ival($1, $2); } 978 | T_Stratum T_Integer 979 { 980 if ($2 >= 0 && $2 <= 16) { 981 $$ = create_attr_ival($1, $2); 982 } else { 983 $$ = NULL; 984 yyerror("fudge factor: stratum value not in [0..16], ignored"); 985 } 986 } 987 | T_Abbrev T_String 988 { $$ = create_attr_sval($1, $2); } 989 | T_Refid T_String 990 { $$ = create_attr_sval($1, $2); } 991 ; 992 993 fudge_factor_dbl_keyword 994 : T_Time1 995 | T_Time2 996 ; 997 998 fudge_factor_bool_keyword 999 : T_Flag1 1000 | T_Flag2 1001 | T_Flag3 1002 | T_Flag4 1003 ; 1004 1005 /* rlimit Commands 1006 * --------------- 1007 */ 1008 1009 rlimit_command 1010 : T_Rlimit rlimit_option_list 1011 { CONCAT_G_FIFOS(cfgt.rlimit, $2); } 1012 ; 1013 1014 rlimit_option_list 1015 : rlimit_option_list rlimit_option 1016 { 1017 $$ = $1; 1018 APPEND_G_FIFO($$, $2); 1019 } 1020 | rlimit_option 1021 { 1022 $$ = NULL; 1023 APPEND_G_FIFO($$, $1); 1024 } 1025 ; 1026 1027 rlimit_option 1028 : rlimit_option_keyword T_Integer 1029 { $$ = create_attr_ival($1, $2); } 1030 ; 1031 1032 rlimit_option_keyword 1033 : T_Memlock 1034 | T_Stacksize 1035 | T_Filenum 1036 ; 1037 1038 1039 /* Command for System Options 1040 * -------------------------- 1041 */ 1042 1043 system_option_command 1044 : T_Enable system_option_list 1045 { CONCAT_G_FIFOS(cfgt.enable_opts, $2); } 1046 | T_Disable system_option_list 1047 { CONCAT_G_FIFOS(cfgt.disable_opts, $2); } 1048 ; 1049 1050 system_option_list 1051 : system_option_list system_option 1052 { 1053 $$ = $1; 1054 APPEND_G_FIFO($$, $2); 1055 } 1056 | system_option 1057 { 1058 $$ = NULL; 1059 APPEND_G_FIFO($$, $1); 1060 } 1061 ; 1062 1063 system_option 1064 : system_option_flag_keyword 1065 { $$ = create_attr_ival(T_Flag, $1); } 1066 | system_option_local_flag_keyword 1067 { 1068 if (lex_from_file()) { 1069 $$ = create_attr_ival(T_Flag, $1); 1070 } else { 1071 char err_str[128]; 1072 1073 $$ = NULL; 1074 snprintf(err_str, sizeof(err_str), 1075 "enable/disable %s remote configuration ignored", 1076 keyword($1)); 1077 yyerror(err_str); 1078 } 1079 } 1080 ; 1081 1082 system_option_flag_keyword 1083 : T_Auth 1084 | T_Bclient 1085 | T_Calibrate 1086 | T_Kernel 1087 | T_Monitor 1088 | T_Ntp 1089 ; 1090 1091 system_option_local_flag_keyword 1092 : T_Mode7 1093 | T_PCEdigest 1094 | T_Stats 1095 | T_UEcrypto 1096 | T_UEcryptonak 1097 | T_UEdigest 1098 ; 1099 1100 /* Tinker Commands 1101 * --------------- 1102 */ 1103 1104 tinker_command 1105 : T_Tinker tinker_option_list 1106 { CONCAT_G_FIFOS(cfgt.tinker, $2); } 1107 ; 1108 1109 tinker_option_list 1110 : tinker_option_list tinker_option 1111 { 1112 $$ = $1; 1113 APPEND_G_FIFO($$, $2); 1114 } 1115 | tinker_option 1116 { 1117 $$ = NULL; 1118 APPEND_G_FIFO($$, $1); 1119 } 1120 ; 1121 1122 tinker_option 1123 : tinker_option_keyword number 1124 { $$ = create_attr_dval($1, $2); } 1125 ; 1126 1127 tinker_option_keyword 1128 : T_Allan 1129 | T_Dispersion 1130 | T_Freq 1131 | T_Huffpuff 1132 | T_Panic 1133 | T_Step 1134 | T_Stepback 1135 | T_Stepfwd 1136 | T_Stepout 1137 | T_Tick 1138 ; 1139 1140 1141 /* Miscellaneous Commands 1142 * ---------------------- 1143 */ 1144 1145 miscellaneous_command 1146 : interface_command 1147 | reset_command 1148 | misc_cmd_dbl_keyword number 1149 { 1150 attr_val *av; 1151 1152 av = create_attr_dval($1, $2); 1153 APPEND_G_FIFO(cfgt.vars, av); 1154 } 1155 | misc_cmd_int_keyword T_Integer 1156 { 1157 attr_val *av; 1158 1159 av = create_attr_ival($1, $2); 1160 APPEND_G_FIFO(cfgt.vars, av); 1161 } 1162 | misc_cmd_str_keyword T_String 1163 { 1164 attr_val *av; 1165 1166 av = create_attr_sval($1, $2); 1167 APPEND_G_FIFO(cfgt.vars, av); 1168 } 1169 | misc_cmd_str_lcl_keyword T_String 1170 { 1171 char error_text[64]; 1172 attr_val *av; 1173 1174 if (lex_from_file()) { 1175 av = create_attr_sval($1, $2); 1176 APPEND_G_FIFO(cfgt.vars, av); 1177 } else { 1178 YYFREE($2); 1179 snprintf(error_text, sizeof(error_text), 1180 "%s remote config ignored", 1181 keyword($1)); 1182 yyerror(error_text); 1183 } 1184 } 1185 | T_Includefile T_String command 1186 { 1187 if (!lex_from_file()) { 1188 YYFREE($2); /* avoid leak */ 1189 yyerror("remote includefile ignored"); 1190 break; 1191 } 1192 if (lex_level() > MAXINCLUDELEVEL) { 1193 fprintf(stderr, "getconfig: Maximum include file level exceeded.\n"); 1194 msyslog(LOG_ERR, "getconfig: Maximum include file level exceeded."); 1195 } else { 1196 const char * path = FindConfig($2); /* might return $2! */ 1197 if (!lex_push_file(path, "r")) { 1198 fprintf(stderr, "getconfig: Couldn't open <%s>\n", path); 1199 msyslog(LOG_ERR, "getconfig: Couldn't open <%s>", path); 1200 } 1201 } 1202 YYFREE($2); /* avoid leak */ 1203 } 1204 | T_End 1205 { lex_flush_stack(); } 1206 | T_Driftfile drift_parm 1207 { /* see drift_parm below for actions */ } 1208 | T_Logconfig log_config_list 1209 { CONCAT_G_FIFOS(cfgt.logconfig, $2); } 1210 | T_Phone string_list 1211 { CONCAT_G_FIFOS(cfgt.phone, $2); } 1212 | T_Setvar variable_assign 1213 { APPEND_G_FIFO(cfgt.setvar, $2); } 1214 | T_Trap ip_address trap_option_list 1215 { 1216 addr_opts_node *aon; 1217 1218 aon = create_addr_opts_node($2, $3); 1219 APPEND_G_FIFO(cfgt.trap, aon); 1220 } 1221 | T_Ttl integer_list 1222 { CONCAT_G_FIFOS(cfgt.ttl, $2); } 1223 ; 1224 1225 misc_cmd_dbl_keyword 1226 : T_Broadcastdelay 1227 | T_Nonvolatile 1228 | T_Tick 1229 ; 1230 1231 misc_cmd_int_keyword 1232 : T_Dscp 1233 ; 1234 1235 misc_cmd_int_keyword 1236 : T_Leapsmearinterval 1237 { 1238 #ifndef LEAP_SMEAR 1239 yyerror("Built without LEAP_SMEAR support."); 1240 #endif 1241 } 1242 ; 1243 1244 misc_cmd_str_keyword 1245 : T_Ident 1246 | T_Leapfile 1247 ; 1248 1249 misc_cmd_str_lcl_keyword 1250 : T_Logfile 1251 | T_Pidfile 1252 | T_Saveconfigdir 1253 ; 1254 1255 drift_parm 1256 : T_String 1257 { 1258 if (lex_from_file()) { 1259 attr_val *av; 1260 av = create_attr_sval(T_Driftfile, $1); 1261 APPEND_G_FIFO(cfgt.vars, av); 1262 } else { 1263 YYFREE($1); 1264 yyerror("driftfile remote configuration ignored"); 1265 } 1266 } 1267 | T_String T_Double 1268 { 1269 if (lex_from_file()) { 1270 attr_val *av; 1271 av = create_attr_sval(T_Driftfile, $1); 1272 APPEND_G_FIFO(cfgt.vars, av); 1273 av = create_attr_dval(T_WanderThreshold, $2); 1274 APPEND_G_FIFO(cfgt.vars, av); 1275 } else { 1276 YYFREE($1); 1277 yyerror("driftfile remote configuration ignored"); 1278 } 1279 } 1280 | /* Null driftfile, indicated by empty string "" */ 1281 { 1282 if (lex_from_file()) { 1283 attr_val *av; 1284 av = create_attr_sval(T_Driftfile, estrdup("")); 1285 APPEND_G_FIFO(cfgt.vars, av); 1286 } else { 1287 yyerror("driftfile remote configuration ignored"); 1288 } 1289 } 1290 ; 1291 1292 variable_assign 1293 : T_String '=' T_String t_default_or_zero 1294 { $$ = create_setvar_node($1, $3, $4); } 1295 ; 1296 1297 t_default_or_zero 1298 : T_Default 1299 | /* empty, no "default" modifier */ 1300 { $$ = 0; } 1301 ; 1302 1303 trap_option_list 1304 : /* empty list */ 1305 { $$ = NULL; } 1306 | trap_option_list trap_option 1307 { 1308 $$ = $1; 1309 APPEND_G_FIFO($$, $2); 1310 } 1311 ; 1312 1313 trap_option 1314 : T_Port T_Integer 1315 { $$ = create_attr_ival($1, $2); } 1316 | T_Interface ip_address 1317 { 1318 $$ = create_attr_sval($1, estrdup($2->address)); 1319 destroy_address_node($2); 1320 } 1321 ; 1322 1323 log_config_list 1324 : log_config_list log_config_command 1325 { 1326 $$ = $1; 1327 APPEND_G_FIFO($$, $2); 1328 } 1329 | log_config_command 1330 { 1331 $$ = NULL; 1332 APPEND_G_FIFO($$, $1); 1333 } 1334 ; 1335 1336 log_config_command 1337 : T_String 1338 { 1339 char prefix; 1340 char * type; 1341 1342 switch ($1[0]) { 1343 1344 case '+': 1345 case '-': 1346 case '=': 1347 prefix = $1[0]; 1348 type = $1 + 1; 1349 break; 1350 1351 default: 1352 prefix = '='; 1353 type = $1; 1354 } 1355 1356 $$ = create_attr_sval(prefix, estrdup(type)); 1357 YYFREE($1); 1358 } 1359 ; 1360 1361 interface_command 1362 : interface_nic nic_rule_action nic_rule_class 1363 { 1364 nic_rule_node *nrn; 1365 1366 nrn = create_nic_rule_node($3, NULL, $2); 1367 APPEND_G_FIFO(cfgt.nic_rules, nrn); 1368 } 1369 | interface_nic nic_rule_action T_String 1370 { 1371 nic_rule_node *nrn; 1372 1373 nrn = create_nic_rule_node(0, $3, $2); 1374 APPEND_G_FIFO(cfgt.nic_rules, nrn); 1375 } 1376 ; 1377 1378 interface_nic 1379 : T_Interface 1380 | T_Nic 1381 ; 1382 1383 nic_rule_class 1384 : T_All 1385 | T_Ipv4 1386 | T_Ipv6 1387 | T_Wildcard 1388 ; 1389 1390 nic_rule_action 1391 : T_Listen 1392 | T_Ignore 1393 | T_Drop 1394 ; 1395 1396 reset_command 1397 : T_Reset counter_set_list 1398 { CONCAT_G_FIFOS(cfgt.reset_counters, $2); } 1399 ; 1400 1401 counter_set_list 1402 : counter_set_list counter_set_keyword 1403 { 1404 $$ = $1; 1405 APPEND_G_FIFO($$, create_int_node($2)); 1406 } 1407 | counter_set_keyword 1408 { 1409 $$ = NULL; 1410 APPEND_G_FIFO($$, create_int_node($1)); 1411 } 1412 ; 1413 1414 counter_set_keyword 1415 : T_Allpeers 1416 | T_Auth 1417 | T_Ctl 1418 | T_Io 1419 | T_Mem 1420 | T_Sys 1421 | T_Timer 1422 ; 1423 1424 1425 1426 /* Miscellaneous Rules 1427 * ------------------- 1428 */ 1429 1430 integer_list 1431 : integer_list T_Integer 1432 { 1433 $$ = $1; 1434 APPEND_G_FIFO($$, create_int_node($2)); 1435 } 1436 | T_Integer 1437 { 1438 $$ = NULL; 1439 APPEND_G_FIFO($$, create_int_node($1)); 1440 } 1441 ; 1442 1443 integer_list_range 1444 : integer_list_range integer_list_range_elt 1445 { 1446 $$ = $1; 1447 APPEND_G_FIFO($$, $2); 1448 } 1449 | integer_list_range_elt 1450 { 1451 $$ = NULL; 1452 APPEND_G_FIFO($$, $1); 1453 } 1454 ; 1455 1456 integer_list_range_elt 1457 : T_Integer 1458 { $$ = create_attr_ival('i', $1); } 1459 | integer_range 1460 ; 1461 1462 integer_range 1463 : '(' T_Integer T_Ellipsis T_Integer ')' 1464 { $$ = create_attr_rangeval('-', $2, $4); } 1465 ; 1466 1467 string_list 1468 : string_list T_String 1469 { 1470 $$ = $1; 1471 APPEND_G_FIFO($$, create_string_node($2)); 1472 } 1473 | T_String 1474 { 1475 $$ = NULL; 1476 APPEND_G_FIFO($$, create_string_node($1)); 1477 } 1478 ; 1479 1480 address_list 1481 : address_list address 1482 { 1483 $$ = $1; 1484 APPEND_G_FIFO($$, $2); 1485 } 1486 | address 1487 { 1488 $$ = NULL; 1489 APPEND_G_FIFO($$, $1); 1490 } 1491 ; 1492 1493 boolean 1494 : T_Integer 1495 { 1496 if ($1 != 0 && $1 != 1) { 1497 yyerror("Integer value is not boolean (0 or 1). Assuming 1"); 1498 $$ = 1; 1499 } else { 1500 $$ = $1; 1501 } 1502 } 1503 | T_True { $$ = 1; } 1504 | T_False { $$ = 0; } 1505 ; 1506 1507 number 1508 : T_Integer { $$ = (double)$1; } 1509 | T_Double 1510 ; 1511 1512 1513 /* Simulator Configuration Commands 1514 * -------------------------------- 1515 */ 1516 1517 simulate_command 1518 : sim_conf_start '{' sim_init_statement_list sim_server_list '}' 1519 { 1520 sim_node *sn; 1521 1522 sn = create_sim_node($3, $4); 1523 APPEND_G_FIFO(cfgt.sim_details, sn); 1524 1525 /* Revert from ; to \n for end-of-command */ 1526 old_config_style = 1; 1527 } 1528 ; 1529 1530 /* The following is a terrible hack to get the configuration file to 1531 * treat newlines as whitespace characters within the simulation. 1532 * This is needed because newlines are significant in the rest of the 1533 * configuration file. 1534 */ 1535 sim_conf_start 1536 : T_Simulate { old_config_style = 0; } 1537 ; 1538 1539 sim_init_statement_list 1540 : sim_init_statement_list sim_init_statement T_EOC 1541 { 1542 $$ = $1; 1543 APPEND_G_FIFO($$, $2); 1544 } 1545 | sim_init_statement T_EOC 1546 { 1547 $$ = NULL; 1548 APPEND_G_FIFO($$, $1); 1549 } 1550 ; 1551 1552 sim_init_statement 1553 : sim_init_keyword '=' number 1554 { $$ = create_attr_dval($1, $3); } 1555 ; 1556 1557 sim_init_keyword 1558 : T_Beep_Delay 1559 | T_Sim_Duration 1560 ; 1561 1562 sim_server_list 1563 : sim_server_list sim_server 1564 { 1565 $$ = $1; 1566 APPEND_G_FIFO($$, $2); 1567 } 1568 | sim_server 1569 { 1570 $$ = NULL; 1571 APPEND_G_FIFO($$, $1); 1572 } 1573 ; 1574 1575 sim_server 1576 : sim_server_name '{' sim_server_offset sim_act_list '}' 1577 { $$ = ONLY_SIM(create_sim_server($1, $3, $4)); } 1578 ; 1579 1580 sim_server_offset 1581 : T_Server_Offset '=' number T_EOC 1582 { $$ = $3; } 1583 ; 1584 1585 sim_server_name 1586 : T_Server '=' address 1587 { $$ = $3; } 1588 ; 1589 1590 sim_act_list 1591 : sim_act_list sim_act 1592 { 1593 $$ = $1; 1594 APPEND_G_FIFO($$, $2); 1595 } 1596 | sim_act 1597 { 1598 $$ = NULL; 1599 APPEND_G_FIFO($$, $1); 1600 } 1601 ; 1602 1603 sim_act 1604 : T_Duration '=' number '{' sim_act_stmt_list '}' 1605 { $$ = ONLY_SIM(create_sim_script_info($3, $5)); } 1606 ; 1607 1608 sim_act_stmt_list 1609 : sim_act_stmt_list sim_act_stmt T_EOC 1610 { 1611 $$ = $1; 1612 APPEND_G_FIFO($$, $2); 1613 } 1614 | sim_act_stmt T_EOC 1615 { 1616 $$ = NULL; 1617 APPEND_G_FIFO($$, $1); 1618 } 1619 ; 1620 1621 sim_act_stmt 1622 : sim_act_keyword '=' number 1623 { $$ = create_attr_dval($1, $3); } 1624 ; 1625 1626 sim_act_keyword 1627 : T_Freq_Offset 1628 | T_Wander 1629 | T_Jitter 1630 | T_Prop_Delay 1631 | T_Proc_Delay 1632 ; 1633 1634 %% 1635 1636 void 1637 yyerror( 1638 const char *msg 1639 ) 1640 { 1641 int retval; 1642 struct FILE_INFO * ip_ctx; 1643 1644 ip_ctx = lex_current(); 1645 ip_ctx->errpos = ip_ctx->tokpos; 1646 1647 msyslog(LOG_ERR, "line %d column %d %s", 1648 ip_ctx->errpos.nline, ip_ctx->errpos.ncol, msg); 1649 if (!lex_from_file()) { 1650 /* Save the error message in the correct buffer */ 1651 retval = snprintf(remote_config.err_msg + remote_config.err_pos, 1652 MAXLINE - remote_config.err_pos, 1653 "column %d %s", 1654 ip_ctx->errpos.ncol, msg); 1655 1656 /* Increment the value of err_pos */ 1657 if (retval > 0) 1658 remote_config.err_pos += retval; 1659 1660 /* Increment the number of errors */ 1661 ++remote_config.no_errors; 1662 } 1663 } 1664 1665 1666 /* 1667 * token_name - convert T_ token integers to text 1668 * example: token_name(T_Server) returns "T_Server" 1669 */ 1670 const char * 1671 token_name( 1672 int token 1673 ) 1674 { 1675 return yytname[YYTRANSLATE(token)]; 1676 } 1677 1678 1679 /* Initial Testing function -- ignore */ 1680 #if 0 1681 int main(int argc, char *argv[]) 1682 { 1683 ip_file = FOPEN(argv[1], "r"); 1684 if (!ip_file) 1685 fprintf(stderr, "ERROR!! Could not open file: %s\n", argv[1]); 1686 yyparse(); 1687 return 0; 1688 } 1689 #endif 1690 1691