1995-11-29 07:40:04 +00:00
|
|
|
/* conflex.c
|
|
|
|
|
|
|
|
Lexical scanner for dhcpd config file... */
|
|
|
|
|
|
|
|
/*
|
2007-05-19 19:16:28 +00:00
|
|
|
* Copyright (c) 2004-2007 by Internet Systems Consortium, Inc. ("ISC")
|
2005-03-17 20:15:29 +00:00
|
|
|
* Copyright (c) 1995-2003 by Internet Software Consortium
|
1995-11-29 07:40:04 +00:00
|
|
|
*
|
2005-03-17 20:15:29 +00:00
|
|
|
* Permission to use, copy, modify, and distribute this software for any
|
|
|
|
* purpose with or without fee is hereby granted, provided that the above
|
|
|
|
* copyright notice and this permission notice appear in all copies.
|
1995-11-29 07:40:04 +00:00
|
|
|
*
|
2005-03-17 20:15:29 +00:00
|
|
|
* THE SOFTWARE IS PROVIDED "AS IS" AND ISC DISCLAIMS ALL WARRANTIES
|
|
|
|
* WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF
|
|
|
|
* MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL ISC BE LIABLE FOR
|
|
|
|
* ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES
|
|
|
|
* WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN
|
|
|
|
* ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT
|
|
|
|
* OF OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE.
|
1995-11-29 07:40:04 +00:00
|
|
|
*
|
2005-03-17 20:15:29 +00:00
|
|
|
* Internet Systems Consortium, Inc.
|
|
|
|
* 950 Charter Street
|
|
|
|
* Redwood City, CA 94063
|
|
|
|
* <info@isc.org>
|
|
|
|
* http://www.isc.org/
|
2000-03-17 04:00:32 +00:00
|
|
|
*
|
2005-03-17 20:15:29 +00:00
|
|
|
* This software has been written for Internet Systems Consortium
|
2000-03-17 04:00:32 +00:00
|
|
|
* by Ted Lemon in cooperation with Vixie Enterprises and Nominum, Inc.
|
2005-03-17 20:15:29 +00:00
|
|
|
* To learn more about Internet Systems Consortium, see
|
2000-03-17 04:00:32 +00:00
|
|
|
* ``http://www.isc.org/''. To learn more about Vixie Enterprises,
|
|
|
|
* see ``http://www.vix.com''. To learn more about Nominum, Inc., see
|
|
|
|
* ``http://www.nominum.com''.
|
1995-11-29 07:40:04 +00:00
|
|
|
*/
|
|
|
|
|
|
|
|
#include "dhcpd.h"
|
|
|
|
#include <ctype.h>
|
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
static int get_char PROTO ((struct parse *));
|
2007-08-29 18:09:35 +00:00
|
|
|
static void unget_char(struct parse *, int);
|
1999-10-01 03:13:43 +00:00
|
|
|
static void skip_to_eol PROTO ((struct parse *));
|
2007-06-20 10:38:55 +00:00
|
|
|
static enum dhcp_token read_whitespace(int c, struct parse *cfile);
|
1999-10-01 03:13:43 +00:00
|
|
|
static enum dhcp_token read_string PROTO ((struct parse *));
|
|
|
|
static enum dhcp_token read_number PROTO ((int, struct parse *));
|
|
|
|
static enum dhcp_token read_num_or_name PROTO ((int, struct parse *));
|
2007-07-13 06:43:43 +00:00
|
|
|
static enum dhcp_token intern PROTO ((char *, enum dhcp_token));
|
1995-11-29 07:40:04 +00:00
|
|
|
|
2001-05-02 06:32:54 +00:00
|
|
|
isc_result_t new_parse (cfile, file, inbuf, buflen, name, eolp)
|
1999-10-01 03:13:43 +00:00
|
|
|
struct parse **cfile;
|
|
|
|
int file;
|
|
|
|
char *inbuf;
|
1999-10-07 06:36:35 +00:00
|
|
|
unsigned buflen;
|
|
|
|
const char *name;
|
2001-05-02 06:32:54 +00:00
|
|
|
int eolp;
|
1999-10-01 03:13:43 +00:00
|
|
|
{
|
|
|
|
struct parse *tmp;
|
1996-08-28 01:26:34 +00:00
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
tmp = dmalloc(sizeof(struct parse), MDL);
|
|
|
|
if (tmp == NULL) {
|
1999-10-01 03:13:43 +00:00
|
|
|
return ISC_R_NOMEMORY;
|
2007-06-20 10:38:55 +00:00
|
|
|
}
|
1996-08-28 01:26:34 +00:00
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
/*
|
|
|
|
* We don't need to initialize things to zero here, since
|
|
|
|
* dmalloc() returns memory that is set to zero.
|
|
|
|
*/
|
|
|
|
/* tmp->token = 0; */
|
|
|
|
/* tmp->warnings_occurred = 0; */
|
|
|
|
/* tmp->bufix = 0; */
|
|
|
|
/* tmp->saved_state = NULL; */
|
2007-05-23 15:29:49 +00:00
|
|
|
tmp->tlname = name;
|
|
|
|
tmp->lpos = tmp -> line = 1;
|
2007-06-20 10:38:55 +00:00
|
|
|
tmp->cur_line = tmp->line1;
|
|
|
|
tmp->prev_line = tmp->line2;
|
|
|
|
tmp->token_line = tmp->cur_line;
|
|
|
|
tmp->cur_line[0] = tmp->prev_line[0] = 0;
|
2007-05-23 15:29:49 +00:00
|
|
|
tmp->file = file;
|
|
|
|
tmp->eol_token = eolp;
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
if (inbuf != NULL) {
|
2007-05-23 15:29:49 +00:00
|
|
|
tmp->inbuf = inbuf;
|
|
|
|
tmp->buflen = buflen;
|
|
|
|
tmp->bufsiz = 0;
|
1999-10-01 03:13:43 +00:00
|
|
|
} else {
|
2007-05-23 15:29:49 +00:00
|
|
|
struct stat sb;
|
|
|
|
|
|
|
|
if (fstat(file, &sb) < 0)
|
|
|
|
return ISC_R_IOERROR;
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
tmp->bufsiz = tmp->buflen = (size_t)sb.st_size;
|
2007-05-23 15:29:49 +00:00
|
|
|
tmp->inbuf = mmap(NULL, tmp->bufsiz, PROT_READ, MAP_SHARED,
|
|
|
|
file, 0);
|
|
|
|
|
|
|
|
if (tmp->inbuf == MAP_FAILED) {
|
|
|
|
return ISC_R_IOERROR;
|
1999-10-01 03:13:43 +00:00
|
|
|
}
|
|
|
|
}
|
|
|
|
|
|
|
|
*cfile = tmp;
|
|
|
|
return ISC_R_SUCCESS;
|
|
|
|
}
|
|
|
|
|
|
|
|
isc_result_t end_parse (cfile)
|
|
|
|
struct parse **cfile;
|
1996-08-27 09:39:17 +00:00
|
|
|
{
|
2006-02-24 23:16:32 +00:00
|
|
|
/* "Memory" config files have no file. */
|
2007-05-23 15:29:49 +00:00
|
|
|
if ((*cfile)->file != -1) {
|
|
|
|
munmap((*cfile)->inbuf, (*cfile)->bufsiz);
|
2006-02-24 23:16:32 +00:00
|
|
|
close((*cfile)->file);
|
2007-05-23 15:29:49 +00:00
|
|
|
}
|
2007-06-20 10:38:55 +00:00
|
|
|
|
|
|
|
if ((*cfile)->saved_state != NULL) {
|
|
|
|
dfree((*cfile)->saved_state, MDL);
|
|
|
|
}
|
2007-05-23 15:29:49 +00:00
|
|
|
|
2006-02-24 23:16:32 +00:00
|
|
|
dfree(*cfile, MDL);
|
|
|
|
*cfile = NULL;
|
1999-10-01 03:13:43 +00:00
|
|
|
return ISC_R_SUCCESS;
|
1996-08-27 09:39:17 +00:00
|
|
|
}
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
/*
|
|
|
|
* Save the current state of the parser.
|
|
|
|
*
|
|
|
|
* Only one state may be saved. Any previous saved state is
|
|
|
|
* lost.
|
|
|
|
*/
|
|
|
|
isc_result_t
|
|
|
|
save_parse_state(struct parse *cfile) {
|
|
|
|
/*
|
|
|
|
* Free any previous saved state.
|
|
|
|
*/
|
|
|
|
if (cfile->saved_state != NULL) {
|
|
|
|
dfree(cfile->saved_state, MDL);
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Save our current state.
|
|
|
|
*/
|
|
|
|
cfile->saved_state = dmalloc(sizeof(struct parse), MDL);
|
|
|
|
if (cfile->saved_state == NULL) {
|
|
|
|
return ISC_R_NOMEMORY;
|
|
|
|
}
|
|
|
|
memcpy(cfile->saved_state, cfile, sizeof(*cfile));
|
|
|
|
return ISC_R_SUCCESS;
|
|
|
|
}
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Return the parser to the previous saved state.
|
|
|
|
*
|
|
|
|
* You must call save_parse_state() before calling
|
|
|
|
* restore_parse_state(), but you can call restore_parse_state() any
|
|
|
|
* number of times after that.
|
|
|
|
*/
|
|
|
|
isc_result_t
|
|
|
|
restore_parse_state(struct parse *cfile) {
|
|
|
|
struct parse *saved_state;
|
|
|
|
|
|
|
|
if (cfile->saved_state == NULL) {
|
|
|
|
return ISC_R_NOTYET;
|
|
|
|
}
|
|
|
|
|
|
|
|
saved_state = cfile->saved_state;
|
|
|
|
memcpy(cfile, saved_state, sizeof(*cfile));
|
|
|
|
cfile->saved_state = saved_state;
|
|
|
|
return ISC_R_SUCCESS;
|
|
|
|
}
|
|
|
|
|
1995-11-29 07:40:04 +00:00
|
|
|
static int get_char (cfile)
|
1999-10-01 03:13:43 +00:00
|
|
|
struct parse *cfile;
|
1995-11-29 07:40:04 +00:00
|
|
|
{
|
1999-10-01 03:13:43 +00:00
|
|
|
/* My kingdom for WITH... */
|
|
|
|
int c;
|
|
|
|
|
2007-05-23 15:29:49 +00:00
|
|
|
if (cfile->bufix == cfile->buflen)
|
|
|
|
c = EOF;
|
|
|
|
else {
|
|
|
|
c = cfile->inbuf [cfile->bufix];
|
|
|
|
cfile->bufix++;
|
1999-10-01 03:13:43 +00:00
|
|
|
}
|
|
|
|
|
2007-05-23 15:29:49 +00:00
|
|
|
if (!cfile->ugflag) {
|
1995-11-29 07:40:04 +00:00
|
|
|
if (c == EOL) {
|
2007-05-23 15:29:49 +00:00
|
|
|
if (cfile->cur_line == cfile->line1) {
|
|
|
|
cfile->cur_line = cfile->line2;
|
|
|
|
cfile->prev_line = cfile->line1;
|
1996-08-28 01:26:34 +00:00
|
|
|
} else {
|
2007-05-23 15:29:49 +00:00
|
|
|
cfile->cur_line = cfile->line1;
|
|
|
|
cfile->prev_line = cfile->line2;
|
1996-08-28 01:26:34 +00:00
|
|
|
}
|
2007-05-23 15:29:49 +00:00
|
|
|
cfile->line++;
|
|
|
|
cfile->lpos = 1;
|
|
|
|
cfile->cur_line [0] = 0;
|
1996-08-28 01:26:34 +00:00
|
|
|
} else if (c != EOF) {
|
2007-05-23 15:29:49 +00:00
|
|
|
if (cfile->lpos <= 80) {
|
|
|
|
cfile->cur_line [cfile->lpos - 1] = c;
|
|
|
|
cfile->cur_line [cfile->lpos] = 0;
|
1996-08-28 01:26:34 +00:00
|
|
|
}
|
2007-05-23 15:29:49 +00:00
|
|
|
cfile->lpos++;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
|
|
|
} else
|
2007-05-23 15:29:49 +00:00
|
|
|
cfile->ugflag = 0;
|
1995-11-29 07:40:04 +00:00
|
|
|
return c;
|
|
|
|
}
|
|
|
|
|
2007-08-29 15:56:56 +00:00
|
|
|
/*
|
|
|
|
* Return a character to our input buffer.
|
|
|
|
*/
|
2007-08-29 18:09:35 +00:00
|
|
|
static void
|
2007-08-29 15:56:56 +00:00
|
|
|
unget_char(struct parse *cfile, int c) {
|
|
|
|
if (c != EOF) {
|
|
|
|
cfile->bufix--;
|
|
|
|
cfile->ugflag = 1; /* do not put characters into
|
|
|
|
our error buffer on the next
|
|
|
|
call to get_char() */
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
/*
|
|
|
|
* GENERAL NOTE ABOUT TOKENS
|
|
|
|
*
|
|
|
|
* We normally only want non-whitespace tokens. There are some
|
|
|
|
* circumstances where we *do* want to see whitespace (for example
|
|
|
|
* when parsing IPv6 addresses).
|
|
|
|
*
|
|
|
|
* Generally we use the next_token() function to read tokens. This
|
2007-07-13 06:43:43 +00:00
|
|
|
* in turn calls get_next_token, which does *not* return tokens for
|
2007-06-20 10:38:55 +00:00
|
|
|
* whitespace. Rather, it skips these.
|
|
|
|
*
|
|
|
|
* When we need to see whitespace, we us next_raw_token(), which also
|
|
|
|
* returns the WHITESPACE token.
|
|
|
|
*
|
|
|
|
* The peek_token() and peek_raw_token() functions work as expected.
|
|
|
|
*
|
|
|
|
* Warning: if you invoke peek_token(), then if there is a whitespace
|
|
|
|
* token, it will be lost, and subsequent use of next_raw_token() or
|
|
|
|
* peek_raw_token() will NOT see it.
|
|
|
|
*/
|
|
|
|
|
|
|
|
static enum dhcp_token
|
|
|
|
get_raw_token(struct parse *cfile) {
|
1995-11-29 07:40:04 +00:00
|
|
|
int c;
|
1999-04-08 17:46:15 +00:00
|
|
|
enum dhcp_token ttok;
|
1996-02-06 20:25:56 +00:00
|
|
|
static char tb [2];
|
2007-08-29 21:58:32 +00:00
|
|
|
int l, p;
|
1995-11-29 07:40:04 +00:00
|
|
|
|
|
|
|
do {
|
1999-10-01 03:13:43 +00:00
|
|
|
l = cfile -> line;
|
|
|
|
p = cfile -> lpos;
|
1996-08-27 09:39:17 +00:00
|
|
|
|
1995-11-29 07:40:04 +00:00
|
|
|
c = get_char (cfile);
|
2007-06-20 10:38:55 +00:00
|
|
|
if (!((c == '\n') && cfile->eol_token) &&
|
|
|
|
isascii(c) && isspace(c)) {
|
|
|
|
ttok = read_whitespace(c, cfile);
|
|
|
|
break;
|
|
|
|
}
|
1995-11-29 07:40:04 +00:00
|
|
|
if (c == '#') {
|
|
|
|
skip_to_eol (cfile);
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
if (c == '"') {
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> lexline = l;
|
|
|
|
cfile -> lexchar = p;
|
1995-11-29 07:40:04 +00:00
|
|
|
ttok = read_string (cfile);
|
|
|
|
break;
|
|
|
|
}
|
1996-03-16 17:50:30 +00:00
|
|
|
if ((isascii (c) && isdigit (c)) || c == '-') {
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> lexline = l;
|
|
|
|
cfile -> lexchar = p;
|
1995-11-29 07:40:04 +00:00
|
|
|
ttok = read_number (c, cfile);
|
|
|
|
break;
|
|
|
|
} else if (isascii (c) && isalpha (c)) {
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> lexline = l;
|
|
|
|
cfile -> lexchar = p;
|
1996-08-29 09:13:41 +00:00
|
|
|
ttok = read_num_or_name (c, cfile);
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
2001-03-01 18:17:09 +00:00
|
|
|
} else if (c == EOF) {
|
|
|
|
ttok = END_OF_FILE;
|
2001-03-17 00:47:39 +00:00
|
|
|
cfile -> tlen = 0;
|
2001-03-01 18:17:09 +00:00
|
|
|
break;
|
1995-11-29 07:40:04 +00:00
|
|
|
} else {
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> lexline = l;
|
|
|
|
cfile -> lexchar = p;
|
1996-02-06 20:25:56 +00:00
|
|
|
tb [0] = c;
|
|
|
|
tb [1] = 0;
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tval = tb;
|
2001-03-17 00:47:39 +00:00
|
|
|
cfile -> tlen = 1;
|
1995-11-29 07:40:04 +00:00
|
|
|
ttok = c;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
} while (1);
|
|
|
|
return ttok;
|
|
|
|
}
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
/*
|
|
|
|
* The get_next_token() function consumes the next token and
|
|
|
|
* returns it to the caller.
|
|
|
|
*
|
|
|
|
* Since the code is almost the same for "normal" and "raw"
|
|
|
|
* input, we pass a flag to alter the way it works.
|
|
|
|
*/
|
|
|
|
|
|
|
|
static enum dhcp_token
|
|
|
|
get_next_token(const char **rval, unsigned *rlen,
|
|
|
|
struct parse *cfile, isc_boolean_t raw) {
|
1995-11-29 07:40:04 +00:00
|
|
|
int rv;
|
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
if (cfile -> token) {
|
|
|
|
if (cfile -> lexline != cfile -> tline)
|
|
|
|
cfile -> token_line = cfile -> cur_line;
|
|
|
|
cfile -> lexchar = cfile -> tlpos;
|
|
|
|
cfile -> lexline = cfile -> tline;
|
|
|
|
rv = cfile -> token;
|
|
|
|
cfile -> token = 0;
|
1995-11-29 07:40:04 +00:00
|
|
|
} else {
|
2007-06-20 10:38:55 +00:00
|
|
|
rv = get_raw_token(cfile);
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> token_line = cfile -> cur_line;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
2007-06-20 10:38:55 +00:00
|
|
|
|
|
|
|
if (!raw) {
|
|
|
|
while (rv == WHITESPACE) {
|
|
|
|
rv = get_raw_token(cfile);
|
|
|
|
cfile->token_line = cfile->cur_line;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
|
1995-11-29 07:40:04 +00:00
|
|
|
if (rval)
|
1999-10-01 03:13:43 +00:00
|
|
|
*rval = cfile -> tval;
|
2001-03-17 00:47:39 +00:00
|
|
|
if (rlen)
|
|
|
|
*rlen = cfile -> tlen;
|
1996-02-06 20:25:56 +00:00
|
|
|
#ifdef DEBUG_TOKENS
|
1999-10-01 03:13:43 +00:00
|
|
|
fprintf (stderr, "%s:%d ", cfile -> tval, rv);
|
1996-02-06 20:25:56 +00:00
|
|
|
#endif
|
1995-11-29 07:40:04 +00:00
|
|
|
return rv;
|
|
|
|
}
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Get the next token from cfile and return it.
|
|
|
|
*
|
|
|
|
* If rval is non-NULL, set the pointer it contains to
|
|
|
|
* the contents of the token.
|
|
|
|
*
|
|
|
|
* If rlen is non-NULL, set the integer it contains to
|
|
|
|
* the length of the token.
|
|
|
|
*/
|
|
|
|
|
|
|
|
enum dhcp_token
|
|
|
|
next_token(const char **rval, unsigned *rlen, struct parse *cfile) {
|
|
|
|
return get_next_token(rval, rlen, cfile, ISC_FALSE);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
* The same as the next_token() function above, but will return space
|
|
|
|
* as the WHITESPACE token.
|
|
|
|
*/
|
|
|
|
|
|
|
|
enum dhcp_token
|
|
|
|
next_raw_token(const char **rval, unsigned *rlen, struct parse *cfile) {
|
|
|
|
return get_next_token(rval, rlen, cfile, ISC_TRUE);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
* The do_peek_token() function checks the next token without
|
|
|
|
* consuming it, and returns it to the caller.
|
|
|
|
*
|
|
|
|
* Since the code is almost the same for "normal" and "raw"
|
|
|
|
* input, we pass a flag to alter the way it works. (See the
|
|
|
|
* warning in the GENERAL NOTES ABOUT TOKENS above though.)
|
|
|
|
*/
|
|
|
|
|
|
|
|
enum dhcp_token
|
|
|
|
do_peek_token(const char **rval, unsigned int *rlen,
|
|
|
|
struct parse *cfile, isc_boolean_t raw) {
|
1996-08-27 09:39:17 +00:00
|
|
|
int x;
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
if (!cfile->token || (!raw && (cfile->token == WHITESPACE))) {
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tlpos = cfile -> lexchar;
|
|
|
|
cfile -> tline = cfile -> lexline;
|
2007-06-20 10:38:55 +00:00
|
|
|
|
|
|
|
do {
|
|
|
|
cfile->token = get_raw_token(cfile);
|
|
|
|
} while (!raw && (cfile->token == WHITESPACE));
|
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
if (cfile -> lexline != cfile -> tline)
|
|
|
|
cfile -> token_line = cfile -> prev_line;
|
|
|
|
|
|
|
|
x = cfile -> lexchar;
|
|
|
|
cfile -> lexchar = cfile -> tlpos;
|
|
|
|
cfile -> tlpos = x;
|
|
|
|
|
|
|
|
x = cfile -> lexline;
|
|
|
|
cfile -> lexline = cfile -> tline;
|
|
|
|
cfile -> tline = x;
|
1996-08-27 09:39:17 +00:00
|
|
|
}
|
1995-11-29 07:40:04 +00:00
|
|
|
if (rval)
|
1999-10-01 03:13:43 +00:00
|
|
|
*rval = cfile -> tval;
|
2001-03-17 00:47:39 +00:00
|
|
|
if (rlen)
|
|
|
|
*rlen = cfile -> tlen;
|
1996-02-06 20:25:56 +00:00
|
|
|
#ifdef DEBUG_TOKENS
|
1999-10-01 03:13:43 +00:00
|
|
|
fprintf (stderr, "(%s:%d) ", cfile -> tval, cfile -> token);
|
1996-02-06 20:25:56 +00:00
|
|
|
#endif
|
1999-10-01 03:13:43 +00:00
|
|
|
return cfile -> token;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Get the next token from cfile and return it, leaving it for a
|
|
|
|
* subsequent call to next_token().
|
|
|
|
*
|
|
|
|
* Note that it WILL consume whitespace tokens.
|
|
|
|
*
|
|
|
|
* If rval is non-NULL, set the pointer it contains to
|
|
|
|
* the contents of the token.
|
|
|
|
*
|
|
|
|
* If rlen is non-NULL, set the integer it contains to
|
|
|
|
* the length of the token.
|
|
|
|
*/
|
|
|
|
|
|
|
|
enum dhcp_token
|
|
|
|
peek_token(const char **rval, unsigned *rlen, struct parse *cfile) {
|
|
|
|
return do_peek_token(rval, rlen, cfile, ISC_FALSE);
|
|
|
|
}
|
|
|
|
|
|
|
|
|
|
|
|
/*
|
|
|
|
* The same as the peek_token() function above, but will return space
|
|
|
|
* as the WHITESPACE token.
|
|
|
|
*/
|
|
|
|
|
|
|
|
enum dhcp_token
|
|
|
|
peek_raw_token(const char **rval, unsigned *rlen, struct parse *cfile) {
|
|
|
|
return do_peek_token(rval, rlen, cfile, ISC_TRUE);
|
|
|
|
}
|
|
|
|
|
1995-11-29 07:40:04 +00:00
|
|
|
static void skip_to_eol (cfile)
|
1999-10-01 03:13:43 +00:00
|
|
|
struct parse *cfile;
|
1995-11-29 07:40:04 +00:00
|
|
|
{
|
|
|
|
int c;
|
|
|
|
do {
|
|
|
|
c = get_char (cfile);
|
|
|
|
if (c == EOF)
|
|
|
|
return;
|
|
|
|
if (c == EOL) {
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
} while (1);
|
|
|
|
}
|
|
|
|
|
2007-06-20 10:38:55 +00:00
|
|
|
static enum dhcp_token
|
|
|
|
read_whitespace(int c, struct parse *cfile) {
|
|
|
|
int ofs;
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Read as much whitespace as we have available.
|
|
|
|
*/
|
|
|
|
ofs = 0;
|
|
|
|
do {
|
|
|
|
cfile->tokbuf[ofs++] = c;
|
|
|
|
c = get_char(cfile);
|
|
|
|
} while (!((c == '\n') && cfile->eol_token) &&
|
|
|
|
isascii(c) && isspace(c));
|
|
|
|
|
|
|
|
/*
|
|
|
|
* Put the last (non-whitespace) character back.
|
|
|
|
*/
|
2007-08-29 15:56:56 +00:00
|
|
|
unget_char(cfile, c);
|
2007-06-20 10:38:55 +00:00
|
|
|
|
|
|
|
/*
|
|
|
|
* Return our token.
|
|
|
|
*/
|
|
|
|
cfile->tokbuf[ofs] = '\0';
|
|
|
|
cfile->tlen = ofs;
|
|
|
|
cfile->tval = cfile->tokbuf;
|
|
|
|
return WHITESPACE;
|
|
|
|
}
|
|
|
|
|
1999-04-08 17:46:15 +00:00
|
|
|
static enum dhcp_token read_string (cfile)
|
1999-10-01 03:13:43 +00:00
|
|
|
struct parse *cfile;
|
1995-11-29 07:40:04 +00:00
|
|
|
{
|
|
|
|
int i;
|
|
|
|
int bs = 0;
|
|
|
|
int c;
|
2005-03-17 20:15:29 +00:00
|
|
|
int value = 0;
|
|
|
|
int hex = 0;
|
1995-11-29 07:40:04 +00:00
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
for (i = 0; i < sizeof cfile -> tokbuf; i++) {
|
2000-01-05 17:59:12 +00:00
|
|
|
again:
|
1995-11-29 07:40:04 +00:00
|
|
|
c = get_char (cfile);
|
|
|
|
if (c == EOF) {
|
1999-10-01 03:13:43 +00:00
|
|
|
parse_warn (cfile, "eof in string constant");
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
|
|
|
}
|
2000-01-05 17:59:12 +00:00
|
|
|
if (bs == 1) {
|
|
|
|
switch (c) {
|
|
|
|
case 't':
|
|
|
|
cfile -> tokbuf [i] = '\t';
|
|
|
|
break;
|
|
|
|
case 'r':
|
|
|
|
cfile -> tokbuf [i] = '\r';
|
|
|
|
break;
|
|
|
|
case 'n':
|
|
|
|
cfile -> tokbuf [i] = '\n';
|
|
|
|
break;
|
|
|
|
case 'b':
|
|
|
|
cfile -> tokbuf [i] = '\b';
|
|
|
|
break;
|
|
|
|
case '0':
|
|
|
|
case '1':
|
|
|
|
case '2':
|
|
|
|
case '3':
|
|
|
|
hex = 0;
|
|
|
|
value = c - '0';
|
|
|
|
++bs;
|
|
|
|
goto again;
|
|
|
|
case 'x':
|
|
|
|
hex = 1;
|
|
|
|
value = 0;
|
|
|
|
++bs;
|
|
|
|
goto again;
|
|
|
|
default:
|
|
|
|
cfile -> tokbuf [i] = c;
|
|
|
|
bs = 0;
|
|
|
|
break;
|
|
|
|
}
|
1995-11-29 07:40:04 +00:00
|
|
|
bs = 0;
|
2000-01-05 17:59:12 +00:00
|
|
|
} else if (bs > 1) {
|
|
|
|
if (hex) {
|
|
|
|
if (c >= '0' && c <= '9') {
|
|
|
|
value = value * 16 + (c - '0');
|
|
|
|
} else if (c >= 'a' && c <= 'f') {
|
|
|
|
value = value * 16 + (c - 'a' + 10);
|
|
|
|
} else if (c >= 'A' && c <= 'F') {
|
|
|
|
value = value * 16 + (c - 'A' + 10);
|
|
|
|
} else {
|
|
|
|
parse_warn (cfile,
|
|
|
|
"invalid hex digit: %x",
|
|
|
|
c);
|
|
|
|
bs = 0;
|
|
|
|
continue;
|
|
|
|
}
|
|
|
|
if (++bs == 4) {
|
|
|
|
cfile -> tokbuf [i] = value;
|
|
|
|
bs = 0;
|
|
|
|
} else
|
|
|
|
goto again;
|
|
|
|
} else {
|
2007-07-03 09:51:58 +00:00
|
|
|
if (c >= '0' && c <= '7') {
|
2000-01-05 17:59:12 +00:00
|
|
|
value = value * 8 + (c - '0');
|
|
|
|
} else {
|
|
|
|
if (value != 0) {
|
|
|
|
parse_warn (cfile,
|
|
|
|
"invalid octal digit %x",
|
|
|
|
c);
|
|
|
|
continue;
|
|
|
|
} else
|
|
|
|
cfile -> tokbuf [i] = 0;
|
|
|
|
bs = 0;
|
|
|
|
}
|
|
|
|
if (++bs == 4) {
|
|
|
|
cfile -> tokbuf [i] = value;
|
|
|
|
bs = 0;
|
|
|
|
} else
|
|
|
|
goto again;
|
|
|
|
}
|
|
|
|
} else if (c == '\\') {
|
1995-11-29 07:40:04 +00:00
|
|
|
bs = 1;
|
2000-01-05 17:59:12 +00:00
|
|
|
goto again;
|
|
|
|
} else if (c == '"')
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
|
|
|
else
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i] = c;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
|
|
|
/* Normally, I'd feel guilty about this, but we're talking about
|
|
|
|
strings that'll fit in a DHCP packet here... */
|
1999-10-01 03:13:43 +00:00
|
|
|
if (i == sizeof cfile -> tokbuf) {
|
|
|
|
parse_warn (cfile,
|
|
|
|
"string constant larger than internal buffer");
|
1995-11-29 07:40:04 +00:00
|
|
|
--i;
|
|
|
|
}
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i] = 0;
|
2001-03-17 00:47:39 +00:00
|
|
|
cfile -> tlen = i;
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tval = cfile -> tokbuf;
|
1995-11-29 07:40:04 +00:00
|
|
|
return STRING;
|
|
|
|
}
|
|
|
|
|
1999-04-08 17:46:15 +00:00
|
|
|
static enum dhcp_token read_number (c, cfile)
|
1995-11-29 07:40:04 +00:00
|
|
|
int c;
|
1999-10-01 03:13:43 +00:00
|
|
|
struct parse *cfile;
|
1995-11-29 07:40:04 +00:00
|
|
|
{
|
|
|
|
int i = 0;
|
1996-08-28 01:26:34 +00:00
|
|
|
int token = NUMBER;
|
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i++] = c;
|
|
|
|
for (; i < sizeof cfile -> tokbuf; i++) {
|
1995-11-29 07:40:04 +00:00
|
|
|
c = get_char (cfile);
|
2005-03-17 20:15:29 +00:00
|
|
|
|
|
|
|
/* Promote NUMBER -> NUMBER_OR_NAME -> NAME, never demote.
|
|
|
|
* Except in the case of '0x' syntax hex, which gets called
|
|
|
|
* a NAME at '0x', and returned to NUMBER_OR_NAME once it's
|
|
|
|
* verified to be at least 0xf or less.
|
|
|
|
*/
|
|
|
|
switch(isascii(c) ? token : BREAK) {
|
|
|
|
case NUMBER:
|
|
|
|
if(isdigit(c))
|
|
|
|
break;
|
|
|
|
/* FALLTHROUGH */
|
|
|
|
case NUMBER_OR_NAME:
|
|
|
|
if(isxdigit(c)) {
|
|
|
|
token = NUMBER_OR_NAME;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
/* FALLTHROUGH */
|
|
|
|
case NAME:
|
|
|
|
if((i == 2) && isxdigit(c) &&
|
|
|
|
(cfile->tokbuf[0] == '0') &&
|
|
|
|
((cfile->tokbuf[1] == 'x') ||
|
|
|
|
(cfile->tokbuf[1] == 'X'))) {
|
|
|
|
token = NUMBER_OR_NAME;
|
|
|
|
break;
|
|
|
|
} else if(((c == '-') || (c == '_') || isalnum(c))) {
|
|
|
|
token = NAME;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
/* FALLTHROUGH */
|
|
|
|
case BREAK:
|
|
|
|
/* At this point c is either EOF or part of the next
|
|
|
|
* token. If not EOF, rewind the file one byte so
|
|
|
|
* the next token is read from there.
|
|
|
|
*/
|
2007-08-29 15:56:56 +00:00
|
|
|
unget_char(cfile, c);
|
2005-03-17 20:15:29 +00:00
|
|
|
goto end_read;
|
|
|
|
|
|
|
|
default:
|
|
|
|
log_fatal("read_number():%s:%d: impossible case", MDL);
|
|
|
|
}
|
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i] = c;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
2005-03-17 20:15:29 +00:00
|
|
|
|
1999-10-01 03:13:43 +00:00
|
|
|
if (i == sizeof cfile -> tokbuf) {
|
|
|
|
parse_warn (cfile,
|
|
|
|
"numeric token larger than internal buffer");
|
1995-11-29 07:40:04 +00:00
|
|
|
--i;
|
|
|
|
}
|
2005-03-17 20:15:29 +00:00
|
|
|
|
|
|
|
end_read:
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i] = 0;
|
2001-03-17 00:47:39 +00:00
|
|
|
cfile -> tlen = i;
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tval = cfile -> tokbuf;
|
2005-03-17 20:15:29 +00:00
|
|
|
|
1996-08-28 01:26:34 +00:00
|
|
|
return token;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
|
|
|
|
1999-04-08 17:46:15 +00:00
|
|
|
static enum dhcp_token read_num_or_name (c, cfile)
|
1995-11-29 07:40:04 +00:00
|
|
|
int c;
|
1999-10-01 03:13:43 +00:00
|
|
|
struct parse *cfile;
|
1995-11-29 07:40:04 +00:00
|
|
|
{
|
|
|
|
int i = 0;
|
1999-04-08 17:46:15 +00:00
|
|
|
enum dhcp_token rv = NUMBER_OR_NAME;
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i++] = c;
|
|
|
|
for (; i < sizeof cfile -> tokbuf; i++) {
|
1995-11-29 07:40:04 +00:00
|
|
|
c = get_char (cfile);
|
|
|
|
if (!isascii (c) ||
|
|
|
|
(c != '-' && c != '_' && !isalnum (c))) {
|
2007-08-29 15:56:56 +00:00
|
|
|
unget_char(cfile, c);
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!isxdigit (c))
|
1996-08-29 09:13:41 +00:00
|
|
|
rv = NAME;
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i] = c;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
1999-10-01 03:13:43 +00:00
|
|
|
if (i == sizeof cfile -> tokbuf) {
|
|
|
|
parse_warn (cfile, "token larger than internal buffer");
|
1995-11-29 07:40:04 +00:00
|
|
|
--i;
|
|
|
|
}
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tokbuf [i] = 0;
|
2001-03-17 00:47:39 +00:00
|
|
|
cfile -> tlen = i;
|
1999-10-01 03:13:43 +00:00
|
|
|
cfile -> tval = cfile -> tokbuf;
|
2007-07-13 06:43:43 +00:00
|
|
|
return intern(cfile->tval, rv);
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
|
|
|
|
2007-07-13 06:43:43 +00:00
|
|
|
static enum dhcp_token
|
|
|
|
intern(char *atom, enum dhcp_token dfv) {
|
|
|
|
if (!isascii(atom[0]))
|
1996-05-22 08:05:19 +00:00
|
|
|
return dfv;
|
|
|
|
|
2007-07-13 06:43:43 +00:00
|
|
|
switch (tolower((unsigned char)atom[0])) {
|
2000-02-15 19:40:34 +00:00
|
|
|
case '-':
|
|
|
|
if (atom [1] == 0)
|
|
|
|
return MINUS;
|
|
|
|
break;
|
|
|
|
|
1997-02-22 08:29:24 +00:00
|
|
|
case 'a':
|
1999-03-09 23:39:41 +00:00
|
|
|
if (!strncasecmp (atom + 1, "uth", 3)) {
|
|
|
|
if (!strncasecmp (atom + 3, "uthenticat", 10)) {
|
|
|
|
if (!strcasecmp (atom + 13, "ed"))
|
|
|
|
return AUTHENTICATED;
|
|
|
|
if (!strcasecmp (atom + 13, "ion"))
|
|
|
|
return AUTHENTICATION;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp (atom + 1, "uthoritative"))
|
|
|
|
return AUTHORITATIVE;
|
|
|
|
break;
|
|
|
|
}
|
1998-04-20 18:02:40 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nd"))
|
|
|
|
return AND;
|
1997-05-09 07:57:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ppend"))
|
|
|
|
return APPEND;
|
1997-02-22 08:29:24 +00:00
|
|
|
if (!strcasecmp (atom + 1, "llow"))
|
|
|
|
return ALLOW;
|
1997-02-22 12:25:32 +00:00
|
|
|
if (!strcasecmp (atom + 1, "lias"))
|
|
|
|
return ALIAS;
|
2000-04-06 22:38:52 +00:00
|
|
|
if (!strcasecmp (atom + 1, "lgorithm"))
|
|
|
|
return ALGORITHM;
|
2007-08-23 16:06:09 +00:00
|
|
|
if (!strcasecmp (atom + 1, "lso"))
|
|
|
|
return TOKEN_ALSO;
|
1997-03-06 19:27:57 +00:00
|
|
|
if (!strcasecmp (atom + 1, "bandoned"))
|
2000-06-02 21:27:21 +00:00
|
|
|
return TOKEN_ABANDONED;
|
1998-06-25 02:54:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "dd"))
|
1999-07-01 18:41:30 +00:00
|
|
|
return TOKEN_ADD;
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ll"))
|
|
|
|
return ALL;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "t"))
|
|
|
|
return AT;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "rray"))
|
|
|
|
return ARRAY;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ddress"))
|
|
|
|
return ADDRESS;
|
2000-06-02 21:27:21 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ctive"))
|
|
|
|
return TOKEN_ACTIVE;
|
2006-02-24 23:16:32 +00:00
|
|
|
if (!strcasecmp (atom + 1, "tsfp"))
|
|
|
|
return ATSFP;
|
2007-10-31 19:13:33 +00:00
|
|
|
if (!strcasecmp (atom + 1, "fter"))
|
|
|
|
return AFTER;
|
1997-02-22 08:29:24 +00:00
|
|
|
break;
|
1996-08-27 09:39:17 +00:00
|
|
|
case 'b':
|
2000-06-02 21:27:21 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ackup"))
|
|
|
|
return TOKEN_BACKUP;
|
|
|
|
if (!strcasecmp (atom + 1, "ootp"))
|
|
|
|
return TOKEN_BOOTP;
|
|
|
|
if (!strcasecmp (atom + 1, "inding"))
|
|
|
|
return BINDING;
|
1999-07-06 16:49:59 +00:00
|
|
|
if (!strcasecmp (atom + 1, "inary-to-ascii"))
|
|
|
|
return BINARY_TO_ASCII;
|
1997-03-29 01:25:10 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ackoff-cutoff"))
|
|
|
|
return BACKOFF_CUTOFF;
|
1997-02-22 08:29:24 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ooting"))
|
|
|
|
return BOOTING;
|
1996-08-27 09:39:17 +00:00
|
|
|
if (!strcasecmp (atom + 1, "oot-unknown-clients"))
|
|
|
|
return BOOT_UNKNOWN_CLIENTS;
|
1998-06-25 02:54:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "reak"))
|
|
|
|
return BREAK;
|
1998-11-11 07:50:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "illing"))
|
|
|
|
return BILLING;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "oolean"))
|
|
|
|
return BOOLEAN;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "alance"))
|
|
|
|
return BALANCE;
|
2000-12-05 07:12:18 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ound"))
|
|
|
|
return BOUND;
|
1998-06-25 02:54:29 +00:00
|
|
|
break;
|
1996-02-06 20:25:56 +00:00
|
|
|
case 'c':
|
2000-01-08 01:27:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ase"))
|
|
|
|
return CASE;
|
1999-07-16 21:34:14 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ommit"))
|
|
|
|
return COMMIT;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ode"))
|
|
|
|
return CODE;
|
1999-07-16 21:34:14 +00:00
|
|
|
if (!strcasecmp (atom + 1, "onfig-option"))
|
|
|
|
return CONFIG_OPTION;
|
1998-04-20 18:02:40 +00:00
|
|
|
if (!strcasecmp (atom + 1, "heck"))
|
|
|
|
return CHECK;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "lass"))
|
|
|
|
return CLASS;
|
2001-02-27 01:15:38 +00:00
|
|
|
if (!strcasecmp (atom + 1, "lose"))
|
|
|
|
return TOKEN_CLOSE;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ompressed"))
|
|
|
|
return COMPRESSED;
|
2001-02-27 01:15:38 +00:00
|
|
|
if (!strcasecmp (atom + 1, "reate"))
|
|
|
|
return TOKEN_CREATE;
|
1996-02-21 12:11:09 +00:00
|
|
|
if (!strcasecmp (atom + 1, "iaddr"))
|
|
|
|
return CIADDR;
|
1999-02-25 23:30:43 +00:00
|
|
|
if (!strncasecmp (atom + 1, "lient", 5)) {
|
|
|
|
if (!strcasecmp (atom + 6, "-identifier"))
|
|
|
|
return CLIENT_IDENTIFIER;
|
|
|
|
if (!strcasecmp (atom + 6, "-hostname"))
|
|
|
|
return CLIENT_HOSTNAME;
|
2000-11-28 22:11:52 +00:00
|
|
|
if (!strcasecmp (atom + 6, "-state"))
|
|
|
|
return CLIENT_STATE;
|
2001-01-11 23:13:27 +00:00
|
|
|
if (!strcasecmp (atom + 6, "-updates"))
|
|
|
|
return CLIENT_UPDATES;
|
1999-02-25 23:30:43 +00:00
|
|
|
if (!strcasecmp (atom + 6, "s"))
|
|
|
|
return CLIENTS;
|
|
|
|
}
|
2001-05-02 06:32:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "oncat"))
|
1999-05-06 20:13:31 +00:00
|
|
|
return CONCAT;
|
2001-05-02 06:32:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "onnect"))
|
|
|
|
return CONNECT;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ommunications-interrupted"))
|
|
|
|
return COMMUNICATIONS_INTERRUPTED;
|
2000-05-04 18:58:16 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ltt"))
|
|
|
|
return CLTT;
|
1996-02-06 20:25:56 +00:00
|
|
|
break;
|
1996-02-21 15:16:18 +00:00
|
|
|
case 'd':
|
2006-06-06 16:35:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "b-time-format"))
|
|
|
|
return DB_TIME_FORMAT;
|
1999-07-19 01:15:22 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ns-update"))
|
|
|
|
return DNS_UPDATE;
|
1999-10-06 01:00:07 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ns-delete"))
|
|
|
|
return DNS_DELETE;
|
1997-05-09 07:57:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "omain"))
|
|
|
|
return DOMAIN;
|
2006-07-22 02:24:16 +00:00
|
|
|
if (!strncasecmp (atom + 1, "omain-", 6)) {
|
|
|
|
if (!strcasecmp(atom + 7, "name"))
|
|
|
|
return DOMAIN_NAME;
|
|
|
|
if (!strcasecmp(atom + 7, "list"))
|
|
|
|
return DOMAIN_LIST;
|
|
|
|
}
|
2005-03-17 20:15:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "o-forward-update"))
|
|
|
|
return DO_FORWARD_UPDATE;
|
2000-08-22 21:51:39 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ebug"))
|
|
|
|
return TOKEN_DEBUG;
|
1997-02-22 08:29:24 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eny"))
|
|
|
|
return DENY;
|
1999-09-09 23:25:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eleted"))
|
2000-06-02 21:27:21 +00:00
|
|
|
return TOKEN_DELETED;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "elete"))
|
|
|
|
return TOKEN_DELETE;
|
1997-02-22 08:29:24 +00:00
|
|
|
if (!strncasecmp (atom + 1, "efault", 6)) {
|
|
|
|
if (!atom [7])
|
|
|
|
return DEFAULT;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 7, "-duid"))
|
|
|
|
return DEFAULT_DUID;
|
1997-02-22 08:29:24 +00:00
|
|
|
if (!strcasecmp (atom + 7, "-lease-time"))
|
|
|
|
return DEFAULT_LEASE_TIME;
|
|
|
|
break;
|
|
|
|
}
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!strncasecmp (atom + 1, "ynamic", 6)) {
|
|
|
|
if (!atom [7])
|
|
|
|
return DYNAMIC;
|
|
|
|
if (!strncasecmp (atom + 7, "-bootp", 6)) {
|
|
|
|
if (!atom [13])
|
|
|
|
return DYNAMIC_BOOTP;
|
|
|
|
if (!strcasecmp (atom + 13, "-lease-cutoff"))
|
|
|
|
return DYNAMIC_BOOTP_LEASE_CUTOFF;
|
|
|
|
if (!strcasecmp (atom + 13, "-lease-length"))
|
|
|
|
return DYNAMIC_BOOTP_LEASE_LENGTH;
|
|
|
|
break;
|
|
|
|
}
|
1996-08-27 09:39:17 +00:00
|
|
|
}
|
1999-10-20 20:55:48 +00:00
|
|
|
if (!strcasecmp (atom + 1, "uplicates"))
|
|
|
|
return DUPLICATES;
|
1999-10-21 02:33:40 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eclines"))
|
|
|
|
return DECLINES;
|
2000-02-15 19:40:34 +00:00
|
|
|
if (!strncasecmp (atom + 1, "efine", 5)) {
|
|
|
|
if (!strcasecmp (atom + 6, "d"))
|
|
|
|
return DEFINED;
|
|
|
|
if (!atom [6])
|
|
|
|
return DEFINE;
|
|
|
|
}
|
1996-02-21 15:16:18 +00:00
|
|
|
break;
|
1996-02-06 20:25:56 +00:00
|
|
|
case 'e':
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii (atom [1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 'x') {
|
1998-10-17 13:34:31 +00:00
|
|
|
if (!strcasecmp (atom + 2, "tract-int"))
|
|
|
|
return EXTRACT_INT;
|
|
|
|
if (!strcasecmp (atom + 2, "ists"))
|
|
|
|
return EXISTS;
|
1999-10-01 03:33:44 +00:00
|
|
|
if (!strcasecmp (atom + 2, "piry"))
|
|
|
|
return EXPIRY;
|
|
|
|
if (!strcasecmp (atom + 2, "pire"))
|
|
|
|
return EXPIRE;
|
2000-06-02 21:27:21 +00:00
|
|
|
if (!strcasecmp (atom + 2, "pired"))
|
|
|
|
return TOKEN_EXPIRED;
|
1998-10-17 13:34:31 +00:00
|
|
|
}
|
1999-10-20 20:55:48 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ncode-int"))
|
1999-10-01 03:33:44 +00:00
|
|
|
return ENCODE_INT;
|
2006-06-06 16:35:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "poch"))
|
|
|
|
return EPOCH;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "thernet"))
|
|
|
|
return ETHERNET;
|
|
|
|
if (!strcasecmp (atom + 1, "nds"))
|
|
|
|
return ENDS;
|
1998-06-25 02:54:29 +00:00
|
|
|
if (!strncasecmp (atom + 1, "ls", 2)) {
|
|
|
|
if (!strcasecmp (atom + 3, "e"))
|
|
|
|
return ELSE;
|
|
|
|
if (!strcasecmp (atom + 3, "if"))
|
|
|
|
return ELSIF;
|
|
|
|
break;
|
|
|
|
}
|
2000-08-22 21:51:39 +00:00
|
|
|
if (!strcasecmp (atom + 1, "rror"))
|
|
|
|
return ERROR;
|
2000-01-25 01:03:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "val"))
|
|
|
|
return EVAL;
|
2000-10-10 22:05:53 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ncapsulate"))
|
|
|
|
return ENCAPSULATE;
|
2006-07-31 22:19:51 +00:00
|
|
|
if (!strcasecmp(atom + 1, "xecute"))
|
|
|
|
return EXECUTE;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom+1, "n")) {
|
|
|
|
return EN;
|
|
|
|
}
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
|
|
|
case 'f':
|
2000-08-22 21:51:39 +00:00
|
|
|
if (!strcasecmp (atom + 1, "atal"))
|
|
|
|
return FATAL;
|
1995-11-29 07:40:04 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ilename"))
|
|
|
|
return FILENAME;
|
|
|
|
if (!strcasecmp (atom + 1, "ixed-address"))
|
|
|
|
return FIXED_ADDR;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ixed-address6"))
|
|
|
|
return FIXED_ADDR6;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ddi"))
|
|
|
|
return FDDI;
|
2000-01-08 01:27:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ormerr"))
|
|
|
|
return NS_FORMERR;
|
2000-02-15 19:40:34 +00:00
|
|
|
if (!strcasecmp (atom + 1, "unction"))
|
|
|
|
return FUNCTION;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ailover"))
|
|
|
|
return FAILOVER;
|
2000-06-02 21:27:21 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ree"))
|
|
|
|
return TOKEN_FREE;
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
1996-02-21 12:11:09 +00:00
|
|
|
case 'g':
|
|
|
|
if (!strcasecmp (atom + 1, "iaddr"))
|
|
|
|
return GIADDR;
|
1996-08-27 09:39:17 +00:00
|
|
|
if (!strcasecmp (atom + 1, "roup"))
|
|
|
|
return GROUP;
|
1996-08-29 23:02:40 +00:00
|
|
|
if (!strcasecmp (atom + 1, "et-lease-hostnames"))
|
|
|
|
return GET_LEASE_HOSTNAMES;
|
1996-02-21 12:11:09 +00:00
|
|
|
break;
|
1996-02-06 20:25:56 +00:00
|
|
|
case 'h':
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ash"))
|
|
|
|
return HASH;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ba"))
|
|
|
|
return HBA;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ost"))
|
|
|
|
return HOST;
|
1999-07-16 21:34:14 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ost-decl-name"))
|
|
|
|
return HOST_DECL_NAME;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ost-identifier"))
|
|
|
|
return HOST_IDENTIFIER;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ardware"))
|
|
|
|
return HARDWARE;
|
1997-10-29 18:32:53 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ostname"))
|
|
|
|
return HOSTNAME;
|
2001-02-27 01:15:38 +00:00
|
|
|
if (!strcasecmp (atom + 1, "elp"))
|
|
|
|
return TOKEN_HELP;
|
1996-02-06 20:25:56 +00:00
|
|
|
break;
|
1997-02-18 14:32:30 +00:00
|
|
|
case 'i':
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom+1, "a-na"))
|
|
|
|
return IA_NA;
|
|
|
|
if (!strcasecmp(atom+1, "aaddr"))
|
|
|
|
return IAADDR;
|
2000-05-16 23:03:49 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nclude"))
|
|
|
|
return INCLUDE;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nteger"))
|
|
|
|
return INTEGER;
|
1999-09-08 01:47:46 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nfinite"))
|
|
|
|
return INFINITE;
|
2000-08-22 21:51:39 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nfo"))
|
|
|
|
return INFO;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "p-address"))
|
|
|
|
return IP_ADDRESS;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp (atom + 1, "p6-address"))
|
|
|
|
return IP6_ADDRESS;
|
1997-03-29 01:25:10 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nitial-interval"))
|
|
|
|
return INITIAL_INTERVAL;
|
1997-02-18 14:32:30 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nterface"))
|
|
|
|
return INTERFACE;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "dentifier"))
|
|
|
|
return IDENTIFIER;
|
1998-06-25 02:54:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "f"))
|
|
|
|
return IF;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "s"))
|
|
|
|
return IS;
|
1999-10-21 03:08:00 +00:00
|
|
|
if (!strcasecmp (atom + 1, "gnore"))
|
|
|
|
return IGNORE;
|
1997-02-18 14:32:30 +00:00
|
|
|
break;
|
1998-11-09 02:45:37 +00:00
|
|
|
case 'k':
|
2005-03-17 20:15:29 +00:00
|
|
|
if (!strncasecmp (atom + 1, "nown", 4)) {
|
|
|
|
if (!strcasecmp (atom + 5, "-clients"))
|
|
|
|
return KNOWN_CLIENTS;
|
|
|
|
if (!atom[5])
|
|
|
|
return KNOWN;
|
|
|
|
break;
|
|
|
|
}
|
2000-04-06 22:38:52 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ey"))
|
|
|
|
return KEY;
|
1998-11-09 02:45:37 +00:00
|
|
|
break;
|
1996-02-06 20:25:56 +00:00
|
|
|
case 'l':
|
2006-05-11 16:31:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "case"))
|
|
|
|
return LCASE;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ease"))
|
|
|
|
return LEASE;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ease6"))
|
|
|
|
return LEASE6;
|
1999-07-06 16:49:59 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eased-address"))
|
|
|
|
return LEASED_ADDRESS;
|
1999-07-19 15:32:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ease-time"))
|
1999-07-19 01:15:22 +00:00
|
|
|
return LEASE_TIME;
|
2006-07-25 13:26:00 +00:00
|
|
|
if (!strcasecmp(atom + 1, "easequery"))
|
|
|
|
return LEASEQUERY;
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ength"))
|
|
|
|
return LENGTH;
|
1998-11-11 07:50:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "imit"))
|
|
|
|
return LIMIT;
|
2000-01-25 01:03:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "et"))
|
|
|
|
return LET;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "oad"))
|
|
|
|
return LOAD;
|
2006-06-06 16:35:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ocal"))
|
|
|
|
return LOCAL;
|
2000-08-22 21:51:39 +00:00
|
|
|
if (!strcasecmp (atom + 1, "og"))
|
|
|
|
return LOG;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom+1, "lt")) {
|
|
|
|
return LLT;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom+1, "l")) {
|
|
|
|
return LL;
|
|
|
|
}
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
1996-02-21 15:16:18 +00:00
|
|
|
case 'm':
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strncasecmp (atom + 1, "ax", 2)) {
|
|
|
|
if (!atom [3])
|
|
|
|
return TOKEN_MAX;
|
2006-06-16 19:26:45 +00:00
|
|
|
if (!strcasecmp (atom + 3, "-balance"))
|
|
|
|
return MAX_BALANCE;
|
2006-08-04 10:59:33 +00:00
|
|
|
if (!strncasecmp (atom + 3, "-lease-", 7)) {
|
2006-06-16 19:26:45 +00:00
|
|
|
if (!strcasecmp(atom + 10, "misbalance"))
|
|
|
|
return MAX_LEASE_MISBALANCE;
|
|
|
|
if (!strcasecmp(atom + 10, "ownership"))
|
|
|
|
return MAX_LEASE_OWNERSHIP;
|
|
|
|
if (!strcasecmp(atom + 10, "time"))
|
|
|
|
return MAX_LEASE_TIME;
|
|
|
|
}
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 3, "-life"))
|
|
|
|
return MAX_LIFE;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 3, "-transmit-idle"))
|
1999-02-14 18:42:06 +00:00
|
|
|
return MAX_TRANSMIT_IDLE;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 3, "-response-delay"))
|
1999-02-14 18:42:06 +00:00
|
|
|
return MAX_RESPONSE_DELAY;
|
2000-05-01 17:25:36 +00:00
|
|
|
if (!strcasecmp (atom + 3, "-unacked-updates"))
|
2000-01-05 17:59:12 +00:00
|
|
|
return MAX_UNACKED_UPDATES;
|
1999-02-14 18:42:06 +00:00
|
|
|
}
|
1998-04-09 04:28:20 +00:00
|
|
|
if (!strncasecmp (atom + 1, "in-", 3)) {
|
2006-06-16 19:26:45 +00:00
|
|
|
if (!strcasecmp (atom + 4, "balance"))
|
|
|
|
return MIN_BALANCE;
|
1998-04-09 04:28:20 +00:00
|
|
|
if (!strcasecmp (atom + 4, "lease-time"))
|
|
|
|
return MIN_LEASE_TIME;
|
|
|
|
if (!strcasecmp (atom + 4, "secs"))
|
|
|
|
return MIN_SECS;
|
|
|
|
break;
|
|
|
|
}
|
1997-02-22 08:29:24 +00:00
|
|
|
if (!strncasecmp (atom + 1, "edi", 3)) {
|
|
|
|
if (!strcasecmp (atom + 4, "a"))
|
|
|
|
return MEDIA;
|
|
|
|
if (!strcasecmp (atom + 4, "um"))
|
|
|
|
return MEDIUM;
|
|
|
|
break;
|
|
|
|
}
|
1998-06-25 02:54:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "atch"))
|
|
|
|
return MATCH;
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!strcasecmp (atom + 1, "embers"))
|
|
|
|
return MEMBERS;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "y"))
|
|
|
|
return MY;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "clt"))
|
|
|
|
return MCLT;
|
1996-02-21 15:16:18 +00:00
|
|
|
break;
|
|
|
|
case 'n':
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ormal"))
|
|
|
|
return NORMAL;
|
1997-05-09 07:57:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ameserver"))
|
|
|
|
return NAMESERVER;
|
1996-02-21 15:16:18 +00:00
|
|
|
if (!strcasecmp (atom + 1, "etmask"))
|
|
|
|
return NETMASK;
|
1999-09-08 01:47:46 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ever"))
|
|
|
|
return NEVER;
|
1996-08-27 09:39:17 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ext-server"))
|
|
|
|
return NEXT_SERVER;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ot"))
|
|
|
|
return TOKEN_NOT;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "o"))
|
2007-06-08 14:58:20 +00:00
|
|
|
return TOKEN_NO;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "s-update"))
|
|
|
|
return NS_UPDATE;
|
2000-01-08 01:27:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "oerror"))
|
|
|
|
return NS_NOERROR;
|
|
|
|
if (!strcasecmp (atom + 1, "otauth"))
|
|
|
|
return NS_NOTAUTH;
|
|
|
|
if (!strcasecmp (atom + 1, "otimp"))
|
|
|
|
return NS_NOTIMP;
|
|
|
|
if (!strcasecmp (atom + 1, "otzone"))
|
|
|
|
return NS_NOTZONE;
|
|
|
|
if (!strcasecmp (atom + 1, "xdomain"))
|
|
|
|
return NS_NXDOMAIN;
|
|
|
|
if (!strcasecmp (atom + 1, "xrrset"))
|
|
|
|
return NS_NXRRSET;
|
|
|
|
if (!strcasecmp (atom + 1, "ull"))
|
|
|
|
return TOKEN_NULL;
|
2000-06-02 21:27:21 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ext"))
|
|
|
|
return TOKEN_NEXT;
|
2001-01-16 22:50:05 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ew"))
|
|
|
|
return TOKEN_NEW;
|
1996-02-21 15:16:18 +00:00
|
|
|
break;
|
1995-11-29 07:40:04 +00:00
|
|
|
case 'o':
|
2000-06-24 06:17:55 +00:00
|
|
|
if (!strcasecmp (atom + 1, "mapi"))
|
|
|
|
return OMAPI;
|
1998-04-20 18:02:40 +00:00
|
|
|
if (!strcasecmp (atom + 1, "r"))
|
|
|
|
return OR;
|
1999-07-16 21:34:14 +00:00
|
|
|
if (!strcasecmp (atom + 1, "n"))
|
|
|
|
return ON;
|
2001-02-27 01:15:38 +00:00
|
|
|
if (!strcasecmp (atom + 1, "pen"))
|
|
|
|
return TOKEN_OPEN;
|
1995-11-29 07:40:04 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ption"))
|
|
|
|
return OPTION;
|
1996-08-28 01:26:34 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ne-lease-per-client"))
|
|
|
|
return ONE_LEASE_PER_CLIENT;
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!strcasecmp (atom + 1, "f"))
|
|
|
|
return OF;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "wner"))
|
|
|
|
return OWNER;
|
1996-08-28 01:26:34 +00:00
|
|
|
break;
|
|
|
|
case 'p':
|
1997-05-09 07:57:54 +00:00
|
|
|
if (!strcasecmp (atom + 1, "repend"))
|
|
|
|
return PREPEND;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 1, "referred-life"))
|
|
|
|
return PREFERRED_LIFE;
|
1996-08-28 01:26:34 +00:00
|
|
|
if (!strcasecmp (atom + 1, "acket"))
|
|
|
|
return PACKET;
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ool"))
|
|
|
|
return POOL;
|
|
|
|
if (!strcasecmp (atom + 1, "seudo"))
|
|
|
|
return PSEUDO;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eer"))
|
|
|
|
return PEER;
|
|
|
|
if (!strcasecmp (atom + 1, "rimary"))
|
|
|
|
return PRIMARY;
|
|
|
|
if (!strncasecmp (atom + 1, "artner", 6)) {
|
|
|
|
if (!atom [7])
|
|
|
|
return PARTNER;
|
|
|
|
if (!strcasecmp (atom + 7, "-down"))
|
|
|
|
return PARTNER_DOWN;
|
|
|
|
}
|
|
|
|
if (!strcasecmp (atom + 1, "ort"))
|
|
|
|
return PORT;
|
|
|
|
if (!strcasecmp (atom + 1, "otential-conflict"))
|
|
|
|
return POTENTIAL_CONFLICT;
|
2000-01-25 01:03:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ick-first-value") ||
|
|
|
|
!strcasecmp (atom + 1, "ick"))
|
|
|
|
return PICK;
|
2000-08-31 04:39:41 +00:00
|
|
|
if (!strcasecmp (atom + 1, "aused"))
|
|
|
|
return PAUSED;
|
1995-11-29 07:40:04 +00:00
|
|
|
break;
|
1996-02-06 20:25:56 +00:00
|
|
|
case 'r':
|
2000-08-24 18:20:47 +00:00
|
|
|
if (!strcasecmp (atom + 1, "esolution-interrupted"))
|
|
|
|
return RESOLUTION_INTERRUPTED;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ange"))
|
|
|
|
return RANGE;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 1, "ange6")) {
|
|
|
|
return RANGE6;
|
|
|
|
}
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ecover"))
|
|
|
|
return RECOVER;
|
2000-08-31 04:39:41 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ecover-done"))
|
|
|
|
return RECOVER_DONE;
|
2001-04-20 18:07:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ecover-wait"))
|
|
|
|
return RECOVER_WAIT;
|
2000-12-05 07:12:18 +00:00
|
|
|
if (!strcasecmp (atom + 1, "econtact-interval"))
|
|
|
|
return RECONTACT_INTERVAL;
|
1997-02-18 14:32:30 +00:00
|
|
|
if (!strcasecmp (atom + 1, "equest"))
|
|
|
|
return REQUEST;
|
|
|
|
if (!strcasecmp (atom + 1, "equire"))
|
|
|
|
return REQUIRE;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strcasecmp (atom + 1, "equire"))
|
|
|
|
return REQUIRE;
|
1997-02-18 14:32:30 +00:00
|
|
|
if (!strcasecmp (atom + 1, "etry"))
|
|
|
|
return RETRY;
|
2000-08-28 19:36:39 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eturn"))
|
|
|
|
return RETURN;
|
1997-02-18 14:32:30 +00:00
|
|
|
if (!strcasecmp (atom + 1, "enew"))
|
|
|
|
return RENEW;
|
|
|
|
if (!strcasecmp (atom + 1, "ebind"))
|
|
|
|
return REBIND;
|
1997-03-05 06:33:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eboot"))
|
|
|
|
return REBOOT;
|
1997-06-02 22:30:52 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eject"))
|
|
|
|
return REJECT;
|
1999-07-06 16:49:59 +00:00
|
|
|
if (!strcasecmp (atom + 1, "everse"))
|
|
|
|
return REVERSE;
|
1999-07-16 21:34:14 +00:00
|
|
|
if (!strcasecmp (atom + 1, "elease"))
|
|
|
|
return RELEASE;
|
2000-01-08 01:27:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "efused"))
|
|
|
|
return NS_REFUSED;
|
2000-06-02 21:27:21 +00:00
|
|
|
if (!strcasecmp (atom + 1, "eleased"))
|
|
|
|
return TOKEN_RELEASED;
|
|
|
|
if (!strcasecmp (atom + 1, "eset"))
|
|
|
|
return TOKEN_RESET;
|
|
|
|
if (!strcasecmp (atom + 1, "eserved"))
|
|
|
|
return TOKEN_RESERVED;
|
2001-05-17 19:04:09 +00:00
|
|
|
if (!strcasecmp (atom + 1, "emove"))
|
|
|
|
return REMOVE;
|
2001-06-27 00:31:20 +00:00
|
|
|
if (!strcasecmp (atom + 1, "efresh"))
|
|
|
|
return REFRESH;
|
1996-02-06 20:25:56 +00:00
|
|
|
break;
|
|
|
|
case 's':
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "cript"))
|
|
|
|
return SCRIPT;
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 'e') {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 2, "arch"))
|
|
|
|
return SEARCH;
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[2]) &&
|
|
|
|
tolower((unsigned char)atom[2]) == 'c') {
|
2006-08-04 10:59:33 +00:00
|
|
|
if (!strncasecmp(atom + 3, "ond", 3)) {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 6, "ary"))
|
|
|
|
return SECONDARY;
|
|
|
|
if (!strcasecmp(atom + 6, "s"))
|
|
|
|
return SECONDS;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 3, "ret"))
|
|
|
|
return SECRET;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strncasecmp(atom + 2, "lect", 4)) {
|
|
|
|
if (atom[6] == '\0')
|
|
|
|
return SELECT;
|
|
|
|
if (!strcasecmp(atom + 6, "-timeout"))
|
|
|
|
return SELECT_TIMEOUT;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 2, "nd"))
|
|
|
|
return SEND;
|
|
|
|
if (!strncasecmp(atom + 2, "rv", 2)) {
|
|
|
|
if (!strncasecmp(atom + 4, "er", 2)) {
|
|
|
|
if (atom[6] == '\0')
|
2007-06-08 14:58:20 +00:00
|
|
|
return TOKEN_SERVER;
|
2006-06-01 20:23:18 +00:00
|
|
|
if (atom[6] == '-') {
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 7,
|
|
|
|
"duid"))
|
|
|
|
return SERVER_DUID;
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 7,
|
|
|
|
"name"))
|
|
|
|
return SERVER_NAME;
|
|
|
|
if (!strcasecmp(atom + 7,
|
|
|
|
"identifier"))
|
|
|
|
return SERVER_IDENTIFIER;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 4, "fail"))
|
|
|
|
return NS_SERVFAIL;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 2, "t"))
|
|
|
|
return TOKEN_SET;
|
1998-06-25 02:54:29 +00:00
|
|
|
break;
|
|
|
|
}
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 'h') {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 2, "ared-network"))
|
|
|
|
return SHARED_NETWORK;
|
|
|
|
if (!strcasecmp(atom + 2, "utdown"))
|
|
|
|
return SHUTDOWN;
|
|
|
|
break;
|
|
|
|
}
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 'i') {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 2, "addr"))
|
|
|
|
return SIADDR;
|
|
|
|
if (!strcasecmp(atom + 2, "gned"))
|
|
|
|
return SIGNED;
|
|
|
|
if (!strcasecmp(atom + 2, "ze"))
|
|
|
|
return SIZE;
|
|
|
|
break;
|
|
|
|
}
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 'p') {
|
|
|
|
if (isascii(atom[2]) &&
|
|
|
|
tolower((unsigned char)atom[2]) == 'a') {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 3, "ce"))
|
|
|
|
return SPACE;
|
|
|
|
if (!strcasecmp(atom + 3, "wn"))
|
|
|
|
return SPAWN;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 2, "lit"))
|
|
|
|
return SPLIT;
|
|
|
|
break;
|
|
|
|
}
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 't') {
|
|
|
|
if (isascii(atom[2]) &&
|
|
|
|
tolower((unsigned char)atom[2]) == 'a') {
|
2006-08-02 22:36:00 +00:00
|
|
|
if(!strncasecmp(atom + 3, "rt", 2)) {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 5, "s"))
|
|
|
|
return STARTS;
|
|
|
|
if (!strcasecmp(atom + 5, "up"))
|
|
|
|
return STARTUP;
|
|
|
|
break;
|
|
|
|
}
|
2006-08-02 22:36:00 +00:00
|
|
|
if (isascii(atom[3]) &&
|
2007-07-13 06:43:43 +00:00
|
|
|
tolower((unsigned char)atom[3]) == 't') {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 4, "e"))
|
|
|
|
return STATE;
|
|
|
|
if (!strcasecmp(atom + 4, "ic"))
|
|
|
|
return STATIC;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 2, "ring"))
|
|
|
|
return STRING_TOKEN;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strncasecmp(atom + 1, "ub", 2)) {
|
|
|
|
if (!strcasecmp(atom + 3, "class"))
|
|
|
|
return SUBCLASS;
|
|
|
|
if (!strcasecmp(atom + 3, "net"))
|
|
|
|
return SUBNET;
|
2007-05-08 23:05:22 +00:00
|
|
|
if (!strcasecmp(atom + 3, "net6"))
|
|
|
|
return SUBNET6;
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 3, "string"))
|
|
|
|
return SUBSTRING;
|
|
|
|
break;
|
|
|
|
}
|
2007-07-13 06:43:43 +00:00
|
|
|
if (isascii(atom[1]) &&
|
|
|
|
tolower((unsigned char)atom[1]) == 'u') {
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 2, "ffix"))
|
|
|
|
return SUFFIX;
|
|
|
|
if (!strcasecmp(atom + 2, "persede"))
|
|
|
|
return SUPERSEDE;
|
|
|
|
}
|
|
|
|
if (!strcasecmp(atom + 1, "witch"))
|
|
|
|
return SWITCH;
|
1996-02-06 20:25:56 +00:00
|
|
|
break;
|
|
|
|
case 't':
|
1996-05-22 08:05:19 +00:00
|
|
|
if (!strcasecmp (atom + 1, "imestamp"))
|
1996-02-06 20:25:56 +00:00
|
|
|
return TIMESTAMP;
|
1997-02-18 14:32:30 +00:00
|
|
|
if (!strcasecmp (atom + 1, "imeout"))
|
|
|
|
return TIMEOUT;
|
1996-08-27 09:39:17 +00:00
|
|
|
if (!strcasecmp (atom + 1, "oken-ring"))
|
|
|
|
return TOKEN_RING;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ext"))
|
|
|
|
return TEXT;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "stp"))
|
|
|
|
return TSTP;
|
|
|
|
if (!strcasecmp (atom + 1, "sfp"))
|
|
|
|
return TSFP;
|
2001-01-25 08:20:24 +00:00
|
|
|
if (!strcasecmp (atom + 1, "ransmission"))
|
|
|
|
return TRANSMISSION;
|
1996-02-06 20:25:56 +00:00
|
|
|
break;
|
|
|
|
case 'u':
|
2006-05-11 16:31:29 +00:00
|
|
|
if (!strcasecmp (atom + 1, "case"))
|
|
|
|
return UCASE;
|
2000-01-25 01:03:36 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nset"))
|
|
|
|
return UNSET;
|
1999-03-25 21:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 1, "nsigned"))
|
|
|
|
return UNSIGNED;
|
1996-02-06 20:25:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "id"))
|
|
|
|
return UID;
|
1999-02-14 18:42:06 +00:00
|
|
|
if (!strncasecmp (atom + 1, "se", 2)) {
|
|
|
|
if (!strcasecmp (atom + 3, "r-class"))
|
|
|
|
return USER_CLASS;
|
|
|
|
if (!strcasecmp (atom + 3, "-host-decl-names"))
|
|
|
|
return USE_HOST_DECL_NAMES;
|
|
|
|
if (!strcasecmp (atom + 3,
|
|
|
|
"-lease-addr-for-default-route"))
|
|
|
|
return USE_LEASE_ADDR_FOR_DEFAULT_ROUTE;
|
|
|
|
break;
|
|
|
|
}
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!strncasecmp (atom + 1, "nknown", 6)) {
|
|
|
|
if (!strcasecmp (atom + 7, "-clients"))
|
|
|
|
return UNKNOWN_CLIENTS;
|
2000-05-03 05:56:28 +00:00
|
|
|
if (!strcasecmp (atom + 7, "-state"))
|
|
|
|
return UNKNOWN_STATE;
|
1998-11-09 02:45:37 +00:00
|
|
|
if (!atom [7])
|
|
|
|
return UNKNOWN;
|
|
|
|
break;
|
|
|
|
}
|
|
|
|
if (!strcasecmp (atom + 1, "nauthenticated"))
|
2007-12-15 10:59:37 +00:00
|
|
|
return UNAUTHENTICATED;
|
1999-10-05 19:43:44 +00:00
|
|
|
if (!strcasecmp (atom + 1, "pdated-dns-rr"))
|
|
|
|
return UPDATED_DNS_RR;
|
2000-01-05 17:59:12 +00:00
|
|
|
if (!strcasecmp (atom + 1, "pdate"))
|
|
|
|
return UPDATE;
|
1996-02-29 18:06:29 +00:00
|
|
|
break;
|
|
|
|
case 'v':
|
|
|
|
if (!strcasecmp (atom + 1, "endor-class"))
|
|
|
|
return VENDOR_CLASS;
|
2000-10-10 22:05:53 +00:00
|
|
|
if (!strcasecmp (atom + 1, "endor"))
|
|
|
|
return VENDOR;
|
1996-02-06 20:25:56 +00:00
|
|
|
break;
|
1998-06-25 02:54:29 +00:00
|
|
|
case 'w':
|
|
|
|
if (!strcasecmp (atom + 1, "ith"))
|
|
|
|
return WITH;
|
2006-06-01 20:23:18 +00:00
|
|
|
if (!strcasecmp(atom + 1, "idth"))
|
|
|
|
return WIDTH;
|
1998-06-25 02:54:29 +00:00
|
|
|
break;
|
1996-02-21 12:11:09 +00:00
|
|
|
case 'y':
|
|
|
|
if (!strcasecmp (atom + 1, "iaddr"))
|
|
|
|
return YIADDR;
|
2000-01-08 01:27:56 +00:00
|
|
|
if (!strcasecmp (atom + 1, "xdomain"))
|
|
|
|
return NS_YXDOMAIN;
|
|
|
|
if (!strcasecmp (atom + 1, "xrrset"))
|
|
|
|
return NS_YXRRSET;
|
1996-02-21 12:11:09 +00:00
|
|
|
break;
|
2000-03-06 20:08:05 +00:00
|
|
|
case 'z':
|
|
|
|
if (!strcasecmp (atom + 1, "one"))
|
|
|
|
return ZONE;
|
|
|
|
break;
|
1995-11-29 07:40:04 +00:00
|
|
|
}
|
|
|
|
return dfv;
|
|
|
|
}
|