Updated PCI IDs to latest snapshot.
[tangerine.git] / workbench / network / stacks / AROSTCP / dhcp / common / conflex.c
blob904abb067d74cd7085892275b19300b61c3cb058
1 /* conflex.c
3 Lexical scanner for dhcpd config file... */
5 /*
6 * Copyright (c) 2004-2005 by Internet Systems Consortium, Inc. ("ISC")
7 * Copyright (c) 1995-2003 by Internet Software Consortium
9 * Permission to use, copy, modify, and distribute this software for any
10 * purpose with or without fee is hereby granted, provided that the above
11 * copyright notice and this permission notice appear in all copies.
13 * THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
14 * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
15 * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
16 * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
17 * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
18 * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
19 * OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
21 * Internet Systems Consortium, Inc.
22 * 950 Charter Street
23 * Redwood City, CA 94063
24 * <info@isc.org>
25 * http://www.isc.org/
27 * This software has been written for Internet Systems Consortium
28 * by Ted Lemon in cooperation with Vixie Enterprises and Nominum, Inc.
29 * To learn more about Internet Systems Consortium, see
30 * ``http://www.isc.org/''. To learn more about Vixie Enterprises,
31 * see ``http://www.vix.com''. To learn more about Nominum, Inc., see
32 * ``http://www.nominum.com''.
35 #ifndef lint
36 static char copyright[] =
37 "$Id$ Copyright (c) 2004-2005 Internet Systems Consortium. All rights reserved.\n";
38 #endif /* not lint */
40 #include "dhcpd.h"
41 #include <ctype.h>
43 static int get_char PROTO ((struct parse *));
44 static enum dhcp_token get_token PROTO ((struct parse *));
45 static void skip_to_eol PROTO ((struct parse *));
46 static enum dhcp_token read_string PROTO ((struct parse *));
47 static enum dhcp_token read_number PROTO ((int, struct parse *));
48 static enum dhcp_token read_num_or_name PROTO ((int, struct parse *));
49 static enum dhcp_token intern PROTO ((char *, enum dhcp_token));
51 isc_result_t new_parse (cfile, file, inbuf, buflen, name, eolp)
52 struct parse **cfile;
53 int file;
54 char *inbuf;
55 unsigned buflen;
56 const char *name;
57 int eolp;
59 struct parse *tmp;
61 tmp = dmalloc (sizeof (struct parse), MDL);
62 if (!tmp)
63 return ISC_R_NOMEMORY;
64 memset (tmp, 0, sizeof *tmp);
66 tmp -> token = 0;
67 tmp -> tlname = name;
68 tmp -> lpos = tmp -> line = 1;
69 tmp -> cur_line = tmp -> line1;
70 tmp -> prev_line = tmp -> line2;
71 tmp -> token_line = tmp -> cur_line;
72 tmp -> cur_line [0] = tmp -> prev_line [0] = 0;
73 tmp -> warnings_occurred = 0;
74 tmp -> file = file;
75 tmp -> eol_token = eolp;
77 tmp -> bufix = 0;
78 tmp -> buflen = buflen;
79 if (inbuf) {
80 tmp -> bufsiz = 0;
81 tmp -> inbuf = inbuf;
82 } else {
83 tmp -> inbuf = dmalloc (8192, MDL);
84 if (!tmp -> inbuf) {
85 dfree (tmp, MDL);
86 return ISC_R_NOMEMORY;
88 tmp -> bufsiz = 8192;
91 *cfile = tmp;
92 return ISC_R_SUCCESS;
95 isc_result_t end_parse (cfile)
96 struct parse **cfile;
98 if ((*cfile) -> bufsiz)
99 dfree ((*cfile) -> inbuf, MDL);
100 dfree (*cfile, MDL);
101 *cfile = (struct parse *)0;
102 return ISC_R_SUCCESS;
105 static int get_char (cfile)
106 struct parse *cfile;
108 /* My kingdom for WITH... */
109 int c;
111 if (cfile -> bufix == cfile -> buflen) {
112 if (cfile -> file != -1) {
113 cfile -> buflen =
114 read (cfile -> file,
115 cfile -> inbuf, cfile -> bufsiz);
116 if (cfile -> buflen == 0) {
117 c = EOF;
118 cfile -> bufix = 0;
119 } else if (cfile -> buflen < 0) {
120 c = EOF;
121 cfile -> bufix = cfile -> buflen = 0;
122 } else {
123 c = cfile -> inbuf [0];
124 cfile -> bufix = 1;
126 } else
127 c = EOF;
128 } else {
129 c = cfile -> inbuf [cfile -> bufix];
130 cfile -> bufix++;
133 if (!cfile -> ugflag) {
134 if (c == EOL) {
135 if (cfile -> cur_line == cfile -> line1) {
136 cfile -> cur_line = cfile -> line2;
137 cfile -> prev_line = cfile -> line1;
138 } else {
139 cfile -> cur_line = cfile -> line1;
140 cfile -> prev_line = cfile -> line2;
142 cfile -> line++;
143 cfile -> lpos = 1;
144 cfile -> cur_line [0] = 0;
145 } else if (c != EOF) {
146 if (cfile -> lpos <= 80) {
147 cfile -> cur_line [cfile -> lpos - 1] = c;
148 cfile -> cur_line [cfile -> lpos] = 0;
150 cfile -> lpos++;
152 } else
153 cfile -> ugflag = 0;
154 return c;
157 static enum dhcp_token get_token (cfile)
158 struct parse *cfile;
160 int c;
161 enum dhcp_token ttok;
162 static char tb [2];
163 int l, p, u;
165 do {
166 l = cfile -> line;
167 p = cfile -> lpos;
168 u = cfile -> ugflag;
170 c = get_char (cfile);
171 #ifdef OLD_LEXER
172 if (c == '\n' && p == 1 && !u
173 && cfile -> comment_index < sizeof cfile -> comments)
174 cfile -> comments [cfile -> comment_index++] = '\n';
175 #endif
177 if (!(c == '\n' && cfile -> eol_token)
178 && isascii (c) && isspace (c))
179 continue;
180 if (c == '#') {
181 #ifdef OLD_LEXER
182 if (cfile -> comment_index < sizeof cfile -> comments)
183 cfile -> comments [cfile -> comment_index++] = '#';
184 #endif
185 skip_to_eol (cfile);
186 continue;
188 if (c == '"') {
189 cfile -> lexline = l;
190 cfile -> lexchar = p;
191 ttok = read_string (cfile);
192 break;
194 if ((isascii (c) && isdigit (c)) || c == '-') {
195 cfile -> lexline = l;
196 cfile -> lexchar = p;
197 ttok = read_number (c, cfile);
198 break;
199 } else if (isascii (c) && isalpha (c)) {
200 cfile -> lexline = l;
201 cfile -> lexchar = p;
202 ttok = read_num_or_name (c, cfile);
203 break;
204 } else if (c == EOF) {
205 ttok = END_OF_FILE;
206 cfile -> tlen = 0;
207 break;
208 } else {
209 cfile -> lexline = l;
210 cfile -> lexchar = p;
211 tb [0] = c;
212 tb [1] = 0;
213 cfile -> tval = tb;
214 cfile -> tlen = 1;
215 ttok = c;
216 break;
218 } while (1);
219 return ttok;
222 enum dhcp_token next_token (rval, rlen, cfile)
223 const char **rval;
224 unsigned *rlen;
225 struct parse *cfile;
227 int rv;
229 if (cfile -> token) {
230 if (cfile -> lexline != cfile -> tline)
231 cfile -> token_line = cfile -> cur_line;
232 cfile -> lexchar = cfile -> tlpos;
233 cfile -> lexline = cfile -> tline;
234 rv = cfile -> token;
235 cfile -> token = 0;
236 } else {
237 rv = get_token (cfile);
238 cfile -> token_line = cfile -> cur_line;
240 if (rval)
241 *rval = cfile -> tval;
242 if (rlen)
243 *rlen = cfile -> tlen;
244 #ifdef DEBUG_TOKENS
245 fprintf (stderr, "%s:%d ", cfile -> tval, rv);
246 #endif
247 return rv;
250 enum dhcp_token peek_token (rval, rlen, cfile)
251 const char **rval;
252 unsigned int *rlen;
253 struct parse *cfile;
255 int x;
257 if (!cfile -> token) {
258 cfile -> tlpos = cfile -> lexchar;
259 cfile -> tline = cfile -> lexline;
260 cfile -> token = get_token (cfile);
261 if (cfile -> lexline != cfile -> tline)
262 cfile -> token_line = cfile -> prev_line;
264 x = cfile -> lexchar;
265 cfile -> lexchar = cfile -> tlpos;
266 cfile -> tlpos = x;
268 x = cfile -> lexline;
269 cfile -> lexline = cfile -> tline;
270 cfile -> tline = x;
272 if (rval)
273 *rval = cfile -> tval;
274 if (rlen)
275 *rlen = cfile -> tlen;
276 #ifdef DEBUG_TOKENS
277 fprintf (stderr, "(%s:%d) ", cfile -> tval, cfile -> token);
278 #endif
279 return cfile -> token;
282 static void skip_to_eol (cfile)
283 struct parse *cfile;
285 int c;
286 do {
287 c = get_char (cfile);
288 if (c == EOF)
289 return;
290 #ifdef OLD_LEXER
291 if (cfile -> comment_index < sizeof (cfile -> comments))
292 comments [cfile -> comment_index++] = c;
293 #endif
294 if (c == EOL) {
295 return;
297 } while (1);
300 static enum dhcp_token read_string (cfile)
301 struct parse *cfile;
303 int i;
304 int bs = 0;
305 int c;
306 int value = 0;
307 int hex = 0;
309 for (i = 0; i < sizeof cfile -> tokbuf; i++) {
310 again:
311 c = get_char (cfile);
312 if (c == EOF) {
313 parse_warn (cfile, "eof in string constant");
314 break;
316 if (bs == 1) {
317 switch (c) {
318 case 't':
319 cfile -> tokbuf [i] = '\t';
320 break;
321 case 'r':
322 cfile -> tokbuf [i] = '\r';
323 break;
324 case 'n':
325 cfile -> tokbuf [i] = '\n';
326 break;
327 case 'b':
328 cfile -> tokbuf [i] = '\b';
329 break;
330 case '0':
331 case '1':
332 case '2':
333 case '3':
334 hex = 0;
335 value = c - '0';
336 ++bs;
337 goto again;
338 case 'x':
339 hex = 1;
340 value = 0;
341 ++bs;
342 goto again;
343 default:
344 cfile -> tokbuf [i] = c;
345 bs = 0;
346 break;
348 bs = 0;
349 } else if (bs > 1) {
350 if (hex) {
351 if (c >= '0' && c <= '9') {
352 value = value * 16 + (c - '0');
353 } else if (c >= 'a' && c <= 'f') {
354 value = value * 16 + (c - 'a' + 10);
355 } else if (c >= 'A' && c <= 'F') {
356 value = value * 16 + (c - 'A' + 10);
357 } else {
358 parse_warn (cfile,
359 "invalid hex digit: %x",
361 bs = 0;
362 continue;
364 if (++bs == 4) {
365 cfile -> tokbuf [i] = value;
366 bs = 0;
367 } else
368 goto again;
369 } else {
370 if (c >= '0' && c <= '9') {
371 value = value * 8 + (c - '0');
372 } else {
373 if (value != 0) {
374 parse_warn (cfile,
375 "invalid octal digit %x",
377 continue;
378 } else
379 cfile -> tokbuf [i] = 0;
380 bs = 0;
382 if (++bs == 4) {
383 cfile -> tokbuf [i] = value;
384 bs = 0;
385 } else
386 goto again;
388 } else if (c == '\\') {
389 bs = 1;
390 goto again;
391 } else if (c == '"')
392 break;
393 else
394 cfile -> tokbuf [i] = c;
396 /* Normally, I'd feel guilty about this, but we're talking about
397 strings that'll fit in a DHCP packet here... */
398 if (i == sizeof cfile -> tokbuf) {
399 parse_warn (cfile,
400 "string constant larger than internal buffer");
401 --i;
403 cfile -> tokbuf [i] = 0;
404 cfile -> tlen = i;
405 cfile -> tval = cfile -> tokbuf;
406 return STRING;
409 static enum dhcp_token read_number (c, cfile)
410 int c;
411 struct parse *cfile;
413 #ifdef OLD_LEXER
414 int seenx = 0;
415 #endif
416 int i = 0;
417 int token = NUMBER;
419 cfile -> tokbuf [i++] = c;
420 for (; i < sizeof cfile -> tokbuf; i++) {
421 c = get_char (cfile);
423 #ifndef OLD_LEXER
424 /* Promote NUMBER -> NUMBER_OR_NAME -> NAME, never demote.
425 * Except in the case of '0x' syntax hex, which gets called
426 * a NAME at '0x', and returned to NUMBER_OR_NAME once it's
427 * verified to be at least 0xf or less.
429 switch(isascii(c) ? token : BREAK) {
430 case NUMBER:
431 if(isdigit(c))
432 break;
433 /* FALLTHROUGH */
434 case NUMBER_OR_NAME:
435 if(isxdigit(c)) {
436 token = NUMBER_OR_NAME;
437 break;
439 /* FALLTHROUGH */
440 case NAME:
441 if((i == 2) && isxdigit(c) &&
442 (cfile->tokbuf[0] == '0') &&
443 ((cfile->tokbuf[1] == 'x') ||
444 (cfile->tokbuf[1] == 'X'))) {
445 token = NUMBER_OR_NAME;
446 break;
447 } else if(((c == '-') || (c == '_') || isalnum(c))) {
448 token = NAME;
449 break;
451 /* FALLTHROUGH */
452 case BREAK:
453 /* At this point c is either EOF or part of the next
454 * token. If not EOF, rewind the file one byte so
455 * the next token is read from there.
457 if(c != EOF) {
458 cfile->bufix--;
459 cfile->ugflag = 1;
461 goto end_read;
463 default:
464 log_fatal("read_number():%s:%d: impossible case", MDL);
466 #else /* OLD_LEXER */
467 if (!seenx && (c == 'x') {
468 seenx = 1;
469 } else if (!isascii (c) || !isxdigit (c)) {
470 if (c != EOF) {
471 cfile -> bufix--;
472 cfile -> ugflag = 1;
474 break;
476 #endif /* OLD_LEXER */
478 cfile -> tokbuf [i] = c;
481 if (i == sizeof cfile -> tokbuf) {
482 parse_warn (cfile,
483 "numeric token larger than internal buffer");
484 --i;
487 end_read:
488 cfile -> tokbuf [i] = 0;
489 cfile -> tlen = i;
490 cfile -> tval = cfile -> tokbuf;
492 return token;
495 static enum dhcp_token read_num_or_name (c, cfile)
496 int c;
497 struct parse *cfile;
499 int i = 0;
500 enum dhcp_token rv = NUMBER_OR_NAME;
501 cfile -> tokbuf [i++] = c;
502 for (; i < sizeof cfile -> tokbuf; i++) {
503 c = get_char (cfile);
504 if (!isascii (c) ||
505 (c != '-' && c != '_' && !isalnum (c))) {
506 if (c != EOF) {
507 cfile -> bufix--;
508 cfile -> ugflag = 1;
510 break;
512 if (!isxdigit (c))
513 rv = NAME;
514 cfile -> tokbuf [i] = c;
516 if (i == sizeof cfile -> tokbuf) {
517 parse_warn (cfile, "token larger than internal buffer");
518 --i;
520 cfile -> tokbuf [i] = 0;
521 cfile -> tlen = i;
522 cfile -> tval = cfile -> tokbuf;
523 return intern (cfile -> tval, rv);
526 static enum dhcp_token intern (atom, dfv)
527 char *atom;
528 enum dhcp_token dfv;
530 if (!isascii (atom [0]))
531 return dfv;
533 switch (tolower (atom [0])) {
534 case '-':
535 if (atom [1] == 0)
536 return MINUS;
537 break;
539 case 'a':
540 if (!strncasecmp (atom + 1, "uth", 3)) {
541 if (!strncasecmp (atom + 3, "uthenticat", 10)) {
542 if (!strcasecmp (atom + 13, "ed"))
543 return AUTHENTICATED;
544 if (!strcasecmp (atom + 13, "ion"))
545 return AUTHENTICATION;
546 break;
548 if (!strcasecmp (atom + 1, "uthoritative"))
549 return AUTHORITATIVE;
550 break;
552 if (!strcasecmp (atom + 1, "nd"))
553 return AND;
554 if (!strcasecmp (atom + 1, "ppend"))
555 return APPEND;
556 if (!strcasecmp (atom + 1, "llow"))
557 return ALLOW;
558 if (!strcasecmp (atom + 1, "lias"))
559 return ALIAS;
560 if (!strcasecmp (atom + 1, "lgorithm"))
561 return ALGORITHM;
562 if (!strcasecmp (atom + 1, "bandoned"))
563 return TOKEN_ABANDONED;
564 if (!strcasecmp (atom + 1, "dd"))
565 return TOKEN_ADD;
566 if (!strcasecmp (atom + 1, "ll"))
567 return ALL;
568 if (!strcasecmp (atom + 1, "t"))
569 return AT;
570 if (!strcasecmp (atom + 1, "rray"))
571 return ARRAY;
572 if (!strcasecmp (atom + 1, "ddress"))
573 return ADDRESS;
574 if (!strcasecmp (atom + 1, "ctive"))
575 return TOKEN_ACTIVE;
576 break;
577 case 'b':
578 if (!strcasecmp (atom + 1, "ackup"))
579 return TOKEN_BACKUP;
580 if (!strcasecmp (atom + 1, "ootp"))
581 return TOKEN_BOOTP;
582 if (!strcasecmp (atom + 1, "inding"))
583 return BINDING;
584 if (!strcasecmp (atom + 1, "inary-to-ascii"))
585 return BINARY_TO_ASCII;
586 if (!strcasecmp (atom + 1, "ackoff-cutoff"))
587 return BACKOFF_CUTOFF;
588 if (!strcasecmp (atom + 1, "ooting"))
589 return BOOTING;
590 if (!strcasecmp (atom + 1, "oot-unknown-clients"))
591 return BOOT_UNKNOWN_CLIENTS;
592 if (!strcasecmp (atom + 1, "reak"))
593 return BREAK;
594 if (!strcasecmp (atom + 1, "illing"))
595 return BILLING;
596 if (!strcasecmp (atom + 1, "oolean"))
597 return BOOLEAN;
598 if (!strcasecmp (atom + 1, "alance"))
599 return BALANCE;
600 if (!strcasecmp (atom + 1, "ound"))
601 return BOUND;
602 break;
603 case 'c':
604 if (!strcasecmp (atom + 1, "ase"))
605 return CASE;
606 if (!strcasecmp (atom + 1, "ommit"))
607 return COMMIT;
608 if (!strcasecmp (atom + 1, "ode"))
609 return CODE;
610 if (!strcasecmp (atom + 1, "onfig-option"))
611 return CONFIG_OPTION;
612 if (!strcasecmp (atom + 1, "heck"))
613 return CHECK;
614 if (!strcasecmp (atom + 1, "lass"))
615 return CLASS;
616 if (!strcasecmp (atom + 1, "lose"))
617 return TOKEN_CLOSE;
618 if (!strcasecmp (atom + 1, "reate"))
619 return TOKEN_CREATE;
620 if (!strcasecmp (atom + 1, "iaddr"))
621 return CIADDR;
622 if (!strncasecmp (atom + 1, "lient", 5)) {
623 if (!strcasecmp (atom + 6, "-identifier"))
624 return CLIENT_IDENTIFIER;
625 if (!strcasecmp (atom + 6, "-hostname"))
626 return CLIENT_HOSTNAME;
627 if (!strcasecmp (atom + 6, "-state"))
628 return CLIENT_STATE;
629 if (!strcasecmp (atom + 6, "-updates"))
630 return CLIENT_UPDATES;
631 if (!strcasecmp (atom + 6, "s"))
632 return CLIENTS;
634 if (!strcasecmp (atom + 1, "oncat"))
635 return CONCAT;
636 if (!strcasecmp (atom + 1, "onnect"))
637 return CONNECT;
638 if (!strcasecmp (atom + 1, "ommunications-interrupted"))
639 return COMMUNICATIONS_INTERRUPTED;
640 if (!strcasecmp (atom + 1, "ltt"))
641 return CLTT;
642 break;
643 case 'd':
644 if (!strcasecmp (atom + 1, "ns-update"))
645 return DNS_UPDATE;
646 if (!strcasecmp (atom + 1, "ns-delete"))
647 return DNS_DELETE;
648 if (!strcasecmp (atom + 1, "omain"))
649 return DOMAIN;
650 if (!strcasecmp (atom + 1, "omain-name"))
651 return DOMAIN_NAME;
652 if (!strcasecmp (atom + 1, "o-forward-update"))
653 return DO_FORWARD_UPDATE;
654 if (!strcasecmp (atom + 1, "ebug"))
655 return TOKEN_DEBUG;
656 if (!strcasecmp (atom + 1, "eny"))
657 return DENY;
658 if (!strcasecmp (atom + 1, "eleted"))
659 return TOKEN_DELETED;
660 if (!strcasecmp (atom + 1, "elete"))
661 return TOKEN_DELETE;
662 if (!strncasecmp (atom + 1, "efault", 6)) {
663 if (!atom [7])
664 return DEFAULT;
665 if (!strcasecmp (atom + 7, "-lease-time"))
666 return DEFAULT_LEASE_TIME;
667 break;
669 if (!strncasecmp (atom + 1, "ynamic", 6)) {
670 if (!atom [7])
671 return DYNAMIC;
672 if (!strncasecmp (atom + 7, "-bootp", 6)) {
673 if (!atom [13])
674 return DYNAMIC_BOOTP;
675 if (!strcasecmp (atom + 13, "-lease-cutoff"))
676 return DYNAMIC_BOOTP_LEASE_CUTOFF;
677 if (!strcasecmp (atom + 13, "-lease-length"))
678 return DYNAMIC_BOOTP_LEASE_LENGTH;
679 break;
682 if (!strcasecmp (atom + 1, "uplicates"))
683 return DUPLICATES;
684 if (!strcasecmp (atom + 1, "eclines"))
685 return DECLINES;
686 if (!strncasecmp (atom + 1, "efine", 5)) {
687 if (!strcasecmp (atom + 6, "d"))
688 return DEFINED;
689 if (!atom [6])
690 return DEFINE;
692 break;
693 case 'e':
694 if (isascii (atom [1]) && tolower (atom [1]) == 'x') {
695 if (!strcasecmp (atom + 2, "tract-int"))
696 return EXTRACT_INT;
697 if (!strcasecmp (atom + 2, "ists"))
698 return EXISTS;
699 if (!strcasecmp (atom + 2, "piry"))
700 return EXPIRY;
701 if (!strcasecmp (atom + 2, "pire"))
702 return EXPIRE;
703 if (!strcasecmp (atom + 2, "pired"))
704 return TOKEN_EXPIRED;
706 if (!strcasecmp (atom + 1, "ncode-int"))
707 return ENCODE_INT;
708 if (!strcasecmp (atom + 1, "thernet"))
709 return ETHERNET;
710 if (!strcasecmp (atom + 1, "nds"))
711 return ENDS;
712 if (!strncasecmp (atom + 1, "ls", 2)) {
713 if (!strcasecmp (atom + 3, "e"))
714 return ELSE;
715 if (!strcasecmp (atom + 3, "if"))
716 return ELSIF;
717 break;
719 if (!strcasecmp (atom + 1, "rror"))
720 return ERROR;
721 if (!strcasecmp (atom + 1, "val"))
722 return EVAL;
723 if (!strcasecmp (atom + 1, "ncapsulate"))
724 return ENCAPSULATE;
725 break;
726 case 'f':
727 if (!strcasecmp (atom + 1, "atal"))
728 return FATAL;
729 if (!strcasecmp (atom + 1, "ilename"))
730 return FILENAME;
731 if (!strcasecmp (atom + 1, "ixed-address"))
732 return FIXED_ADDR;
733 if (!strcasecmp (atom + 1, "ddi"))
734 return FDDI;
735 if (!strcasecmp (atom + 1, "ormerr"))
736 return NS_FORMERR;
737 if (!strcasecmp (atom + 1, "unction"))
738 return FUNCTION;
739 if (!strcasecmp (atom + 1, "ailover"))
740 return FAILOVER;
741 if (!strcasecmp (atom + 1, "ree"))
742 return TOKEN_FREE;
743 break;
744 case 'g':
745 if (!strcasecmp (atom + 1, "iaddr"))
746 return GIADDR;
747 if (!strcasecmp (atom + 1, "roup"))
748 return GROUP;
749 if (!strcasecmp (atom + 1, "et-lease-hostnames"))
750 return GET_LEASE_HOSTNAMES;
751 break;
752 case 'h':
753 if (!strcasecmp (atom + 1, "ba"))
754 return HBA;
755 if (!strcasecmp (atom + 1, "ost"))
756 return HOST;
757 if (!strcasecmp (atom + 1, "ost-decl-name"))
758 return HOST_DECL_NAME;
759 if (!strcasecmp (atom + 1, "ardware"))
760 return HARDWARE;
761 if (!strcasecmp (atom + 1, "ostname"))
762 return HOSTNAME;
763 if (!strcasecmp (atom + 1, "elp"))
764 return TOKEN_HELP;
765 break;
766 case 'i':
767 if (!strcasecmp (atom + 1, "nclude"))
768 return INCLUDE;
769 if (!strcasecmp (atom + 1, "nteger"))
770 return INTEGER;
771 if (!strcasecmp (atom + 1, "nfinite"))
772 return INFINITE;
773 if (!strcasecmp (atom + 1, "nfo"))
774 return INFO;
775 if (!strcasecmp (atom + 1, "p-address"))
776 return IP_ADDRESS;
777 if (!strcasecmp (atom + 1, "nitial-interval"))
778 return INITIAL_INTERVAL;
779 if (!strcasecmp (atom + 1, "nterface"))
780 return INTERFACE;
781 if (!strcasecmp (atom + 1, "dentifier"))
782 return IDENTIFIER;
783 if (!strcasecmp (atom + 1, "f"))
784 return IF;
785 if (!strcasecmp (atom + 1, "s"))
786 return IS;
787 if (!strcasecmp (atom + 1, "gnore"))
788 return IGNORE;
789 break;
790 case 'k':
791 if (!strncasecmp (atom + 1, "nown", 4)) {
792 if (!strcasecmp (atom + 5, "-clients"))
793 return KNOWN_CLIENTS;
794 if (!atom[5])
795 return KNOWN;
796 break;
798 if (!strcasecmp (atom + 1, "ey"))
799 return KEY;
800 break;
801 case 'l':
802 if (!strcasecmp (atom + 1, "ease"))
803 return LEASE;
804 if (!strcasecmp (atom + 1, "eased-address"))
805 return LEASED_ADDRESS;
806 if (!strcasecmp (atom + 1, "ease-time"))
807 return LEASE_TIME;
808 if (!strcasecmp (atom + 1, "imit"))
809 return LIMIT;
810 if (!strcasecmp (atom + 1, "et"))
811 return LET;
812 if (!strcasecmp (atom + 1, "oad"))
813 return LOAD;
814 if (!strcasecmp (atom + 1, "og"))
815 return LOG;
816 break;
817 case 'm':
818 if (!strncasecmp (atom + 1, "ax", 2)) {
819 if (!atom [3])
820 return TOKEN_MAX;
821 if (!strcasecmp (atom + 3, "-lease-time"))
822 return MAX_LEASE_TIME;
823 if (!strcasecmp (atom + 3, "-transmit-idle"))
824 return MAX_TRANSMIT_IDLE;
825 if (!strcasecmp (atom + 3, "-response-delay"))
826 return MAX_RESPONSE_DELAY;
827 if (!strcasecmp (atom + 3, "-unacked-updates"))
828 return MAX_UNACKED_UPDATES;
830 if (!strncasecmp (atom + 1, "in-", 3)) {
831 if (!strcasecmp (atom + 4, "lease-time"))
832 return MIN_LEASE_TIME;
833 if (!strcasecmp (atom + 4, "secs"))
834 return MIN_SECS;
835 break;
837 if (!strncasecmp (atom + 1, "edi", 3)) {
838 if (!strcasecmp (atom + 4, "a"))
839 return MEDIA;
840 if (!strcasecmp (atom + 4, "um"))
841 return MEDIUM;
842 break;
844 if (!strcasecmp (atom + 1, "atch"))
845 return MATCH;
846 if (!strcasecmp (atom + 1, "embers"))
847 return MEMBERS;
848 if (!strcasecmp (atom + 1, "y"))
849 return MY;
850 if (!strcasecmp (atom + 1, "clt"))
851 return MCLT;
852 break;
853 case 'n':
854 if (!strcasecmp (atom + 1, "ormal"))
855 return NORMAL;
856 if (!strcasecmp (atom + 1, "ameserver"))
857 return NAMESERVER;
858 if (!strcasecmp (atom + 1, "etmask"))
859 return NETMASK;
860 if (!strcasecmp (atom + 1, "ever"))
861 return NEVER;
862 if (!strcasecmp (atom + 1, "ext-server"))
863 return NEXT_SERVER;
864 if (!strcasecmp (atom + 1, "ot"))
865 return TOKEN_NOT;
866 if (!strcasecmp (atom + 1, "o"))
867 return NO;
868 if (!strcasecmp (atom + 1, "s-update"))
869 return NS_UPDATE;
870 if (!strcasecmp (atom + 1, "oerror"))
871 return NS_NOERROR;
872 if (!strcasecmp (atom + 1, "otauth"))
873 return NS_NOTAUTH;
874 if (!strcasecmp (atom + 1, "otimp"))
875 return NS_NOTIMP;
876 if (!strcasecmp (atom + 1, "otzone"))
877 return NS_NOTZONE;
878 if (!strcasecmp (atom + 1, "xdomain"))
879 return NS_NXDOMAIN;
880 if (!strcasecmp (atom + 1, "xrrset"))
881 return NS_NXRRSET;
882 if (!strcasecmp (atom + 1, "ull"))
883 return TOKEN_NULL;
884 if (!strcasecmp (atom + 1, "ext"))
885 return TOKEN_NEXT;
886 if (!strcasecmp (atom + 1, "ew"))
887 return TOKEN_NEW;
888 break;
889 case 'o':
890 if (!strcasecmp (atom + 1, "mapi"))
891 return OMAPI;
892 if (!strcasecmp (atom + 1, "r"))
893 return OR;
894 if (!strcasecmp (atom + 1, "n"))
895 return ON;
896 if (!strcasecmp (atom + 1, "pen"))
897 return TOKEN_OPEN;
898 if (!strcasecmp (atom + 1, "ption"))
899 return OPTION;
900 if (!strcasecmp (atom + 1, "ne-lease-per-client"))
901 return ONE_LEASE_PER_CLIENT;
902 if (!strcasecmp (atom + 1, "f"))
903 return OF;
904 if (!strcasecmp (atom + 1, "wner"))
905 return OWNER;
906 break;
907 case 'p':
908 if (!strcasecmp (atom + 1, "repend"))
909 return PREPEND;
910 if (!strcasecmp (atom + 1, "acket"))
911 return PACKET;
912 if (!strcasecmp (atom + 1, "ool"))
913 return POOL;
914 if (!strcasecmp (atom + 1, "seudo"))
915 return PSEUDO;
916 if (!strcasecmp (atom + 1, "eer"))
917 return PEER;
918 if (!strcasecmp (atom + 1, "rimary"))
919 return PRIMARY;
920 if (!strncasecmp (atom + 1, "artner", 6)) {
921 if (!atom [7])
922 return PARTNER;
923 if (!strcasecmp (atom + 7, "-down"))
924 return PARTNER_DOWN;
926 if (!strcasecmp (atom + 1, "ort"))
927 return PORT;
928 if (!strcasecmp (atom + 1, "otential-conflict"))
929 return POTENTIAL_CONFLICT;
930 if (!strcasecmp (atom + 1, "ick-first-value") ||
931 !strcasecmp (atom + 1, "ick"))
932 return PICK;
933 if (!strcasecmp (atom + 1, "aused"))
934 return PAUSED;
935 break;
936 case 'r':
937 if (!strcasecmp (atom + 1, "esolution-interrupted"))
938 return RESOLUTION_INTERRUPTED;
939 if (!strcasecmp (atom + 1, "ange"))
940 return RANGE;
941 if (!strcasecmp (atom + 1, "ecover"))
942 return RECOVER;
943 if (!strcasecmp (atom + 1, "ecover-done"))
944 return RECOVER_DONE;
945 if (!strcasecmp (atom + 1, "ecover-wait"))
946 return RECOVER_WAIT;
947 if (!strcasecmp (atom + 1, "econtact-interval"))
948 return RECONTACT_INTERVAL;
949 if (!strcasecmp (atom + 1, "equest"))
950 return REQUEST;
951 if (!strcasecmp (atom + 1, "equire"))
952 return REQUIRE;
953 if (!strcasecmp (atom + 1, "equire"))
954 return REQUIRE;
955 if (!strcasecmp (atom + 1, "etry"))
956 return RETRY;
957 if (!strcasecmp (atom + 1, "eturn"))
958 return RETURN;
959 if (!strcasecmp (atom + 1, "enew"))
960 return RENEW;
961 if (!strcasecmp (atom + 1, "ebind"))
962 return REBIND;
963 if (!strcasecmp (atom + 1, "eboot"))
964 return REBOOT;
965 if (!strcasecmp (atom + 1, "eject"))
966 return REJECT;
967 if (!strcasecmp (atom + 1, "everse"))
968 return REVERSE;
969 if (!strcasecmp (atom + 1, "elease"))
970 return RELEASE;
971 if (!strcasecmp (atom + 1, "efused"))
972 return NS_REFUSED;
973 if (!strcasecmp (atom + 1, "eleased"))
974 return TOKEN_RELEASED;
975 if (!strcasecmp (atom + 1, "eset"))
976 return TOKEN_RESET;
977 if (!strcasecmp (atom + 1, "eserved"))
978 return TOKEN_RESERVED;
979 if (!strcasecmp (atom + 1, "emove"))
980 return REMOVE;
981 if (!strcasecmp (atom + 1, "efresh"))
982 return REFRESH;
983 break;
984 case 's':
985 if (!strcasecmp (atom + 1, "tate"))
986 return STATE;
987 if (!strcasecmp (atom + 1, "ecret"))
988 return SECRET;
989 if (!strcasecmp (atom + 1, "ervfail"))
990 return NS_SERVFAIL;
991 if (!strcasecmp (atom + 1, "witch"))
992 return SWITCH;
993 if (!strcasecmp (atom + 1, "igned"))
994 return SIGNED;
995 if (!strcasecmp (atom + 1, "tring"))
996 return STRING_TOKEN;
997 if (!strcasecmp (atom + 1, "uffix"))
998 return SUFFIX;
999 if (!strcasecmp (atom + 1, "earch"))
1000 return SEARCH;
1001 if (!strcasecmp (atom + 1, "tarts"))
1002 return STARTS;
1003 if (!strcasecmp (atom + 1, "iaddr"))
1004 return SIADDR;
1005 if (!strcasecmp (atom + 1, "hared-network"))
1006 return SHARED_NETWORK;
1007 if (!strcasecmp (atom + 1, "econdary"))
1008 return SECONDARY;
1009 if (!strcasecmp (atom + 1, "erver-name"))
1010 return SERVER_NAME;
1011 if (!strcasecmp (atom + 1, "erver-identifier"))
1012 return SERVER_IDENTIFIER;
1013 if (!strcasecmp (atom + 1, "erver"))
1014 return SERVER;
1015 if (!strcasecmp (atom + 1, "elect-timeout"))
1016 return SELECT_TIMEOUT;
1017 if (!strcasecmp (atom + 1, "elect"))
1018 return SELECT;
1019 if (!strcasecmp (atom + 1, "end"))
1020 return SEND;
1021 if (!strcasecmp (atom + 1, "cript"))
1022 return SCRIPT;
1023 if (!strcasecmp (atom + 1, "upersede"))
1024 return SUPERSEDE;
1025 if (!strncasecmp (atom + 1, "ub", 2)) {
1026 if (!strcasecmp (atom + 3, "string"))
1027 return SUBSTRING;
1028 if (!strcasecmp (atom + 3, "net"))
1029 return SUBNET;
1030 if (!strcasecmp (atom + 3, "class"))
1031 return SUBCLASS;
1032 break;
1034 if (!strcasecmp (atom + 1, "pawn"))
1035 return SPAWN;
1036 if (!strcasecmp (atom + 1, "pace"))
1037 return SPACE;
1038 if (!strcasecmp (atom + 1, "tatic"))
1039 return _STATIC;
1040 if (!strcasecmp (atom + 1, "plit"))
1041 return SPLIT;
1042 if (!strcasecmp (atom + 1, "et"))
1043 return TOKEN_SET;
1044 if (!strcasecmp (atom + 1, "econds"))
1045 return SECONDS;
1046 if (!strcasecmp (atom + 1, "hutdown"))
1047 return SHUTDOWN;
1048 if (!strcasecmp (atom + 1, "tartup"))
1049 return STARTUP;
1050 break;
1051 case 't':
1052 if (!strcasecmp (atom + 1, "imestamp"))
1053 return TIMESTAMP;
1054 if (!strcasecmp (atom + 1, "imeout"))
1055 return TIMEOUT;
1056 if (!strcasecmp (atom + 1, "oken-ring"))
1057 return TOKEN_RING;
1058 if (!strcasecmp (atom + 1, "ext"))
1059 return _TEXT;
1060 if (!strcasecmp (atom + 1, "stp"))
1061 return TSTP;
1062 if (!strcasecmp (atom + 1, "sfp"))
1063 return TSFP;
1064 if (!strcasecmp (atom + 1, "ransmission"))
1065 return TRANSMISSION;
1066 break;
1067 case 'u':
1068 if (!strcasecmp (atom + 1, "nset"))
1069 return UNSET;
1070 if (!strcasecmp (atom + 1, "nsigned"))
1071 return UNSIGNED;
1072 if (!strcasecmp (atom + 1, "id"))
1073 return UID;
1074 if (!strncasecmp (atom + 1, "se", 2)) {
1075 if (!strcasecmp (atom + 3, "r-class"))
1076 return USER_CLASS;
1077 if (!strcasecmp (atom + 3, "-host-decl-names"))
1078 return USE_HOST_DECL_NAMES;
1079 if (!strcasecmp (atom + 3,
1080 "-lease-addr-for-default-route"))
1081 return USE_LEASE_ADDR_FOR_DEFAULT_ROUTE;
1082 break;
1084 if (!strncasecmp (atom + 1, "nknown", 6)) {
1085 if (!strcasecmp (atom + 7, "-clients"))
1086 return UNKNOWN_CLIENTS;
1087 if (!strcasecmp (atom + 7, "-state"))
1088 return UNKNOWN_STATE;
1089 if (!atom [7])
1090 return UNKNOWN;
1091 break;
1093 if (!strcasecmp (atom + 1, "nauthenticated"))
1094 return AUTHENTICATED;
1095 if (!strcasecmp (atom + 1, "pdated-dns-rr"))
1096 return UPDATED_DNS_RR;
1097 if (!strcasecmp (atom + 1, "pdate"))
1098 return UPDATE;
1099 break;
1100 case 'v':
1101 if (!strcasecmp (atom + 1, "endor-class"))
1102 return VENDOR_CLASS;
1103 if (!strcasecmp (atom + 1, "endor"))
1104 return VENDOR;
1105 break;
1106 case 'w':
1107 if (!strcasecmp (atom + 1, "ith"))
1108 return WITH;
1109 break;
1110 case 'y':
1111 if (!strcasecmp (atom + 1, "iaddr"))
1112 return YIADDR;
1113 if (!strcasecmp (atom + 1, "xdomain"))
1114 return NS_YXDOMAIN;
1115 if (!strcasecmp (atom + 1, "xrrset"))
1116 return NS_YXRRSET;
1117 break;
1118 case 'z':
1119 if (!strcasecmp (atom + 1, "one"))
1120 return ZONE;
1121 break;
1123 return dfv;