* Various options for isc_lex_gettoken().
*/
-#define ISC_LEXOPT_EOL 0x01 /*%< Want end-of-line token. */
-#define ISC_LEXOPT_EOF 0x02 /*%< Want end-of-file token. */
-#define ISC_LEXOPT_INITIALWS 0x04 /*%< Want initial whitespace. */
-#define ISC_LEXOPT_NUMBER 0x08 /*%< Recognize numbers. */
-#define ISC_LEXOPT_QSTRING 0x10 /*%< Recognize qstrings. */
+#define ISC_LEXOPT_EOL 0x0001 /*%< Want end-of-line token. */
+#define ISC_LEXOPT_EOF 0x0002 /*%< Want end-of-file token. */
+#define ISC_LEXOPT_INITIALWS 0x0004 /*%< Want initial whitespace. */
+#define ISC_LEXOPT_NUMBER 0x0008 /*%< Recognize numbers. */
+#define ISC_LEXOPT_QSTRING 0x0010 /*%< Recognize qstrings. */
/*@}*/
/*@{*/
* the paren count is > 0. To use this option, '(' and ')' must be special
* characters.
*/
-#define ISC_LEXOPT_DNSMULTILINE 0x20 /*%< Handle '(' and ')'. */
-#define ISC_LEXOPT_NOMORE 0x40 /*%< Want "no more" token. */
-
-#define ISC_LEXOPT_CNUMBER 0x80 /*%< Recognize octal and hex. */
-#define ISC_LEXOPT_ESCAPE 0x100 /*%< Recognize escapes. */
-#define ISC_LEXOPT_QSTRINGMULTILINE 0x200 /*%< Allow multiline "" strings */
-#define ISC_LEXOPT_OCTAL 0x400 /*%< Expect a octal number. */
-#define ISC_LEXOPT_BTEXT 0x800 /*%< Bracketed text. */
+#define ISC_LEXOPT_DNSMULTILINE 0x0020 /*%< Handle '(' and ')'. */
+#define ISC_LEXOPT_NOMORE 0x0040 /*%< Want "no more" token. */
+
+#define ISC_LEXOPT_CNUMBER 0x0080 /*%< Recognize octal and hex. */
+#define ISC_LEXOPT_ESCAPE 0x0100 /*%< Recognize escapes. */
+#define ISC_LEXOPT_QSTRINGMULTILINE 0x0200 /*%< Allow multiline "" strings */
+#define ISC_LEXOPT_OCTAL 0x0400 /*%< Expect a octal number. */
+#define ISC_LEXOPT_BTEXT 0x0800 /*%< Bracketed text. */
+#define ISC_LEXOPT_VPAIR 0x1000 /*%< Recognize value pair. */
+#define ISC_LEXOPT_QVPAIR 0x2000 /*%< Recognize quoted value pair. */
/*@}*/
/*@{*/
/*!
isc_tokentype_initialws = 6,
isc_tokentype_special = 7,
isc_tokentype_nomore = 8,
- isc_tokentype_btext = 8
+ isc_tokentype_btext = 9,
+ isc_tokentype_vpair = 10,
+ isc_tokentype_qvpair = 11,
} isc_tokentype_t;
typedef union {
lexstate_ccommentend,
lexstate_eatline,
lexstate_qstring,
- lexstate_btext
+ lexstate_btext,
+ lexstate_vpair,
+ lexstate_vpairstart,
+ lexstate_qvpair,
} lexstate;
#define IWSEOL (ISC_LEXOPT_INITIALWS | ISC_LEXOPT_EOL)
remaining--;
break;
case lexstate_string:
+ if (!escaped && c == '=' &&
+ (options & ISC_LEXOPT_VPAIR) != 0) {
+ INSIST(remaining > 0U);
+ *curr++ = c;
+ *curr = '\0';
+ remaining--;
+ state = lexstate_vpairstart;
+ break;
+ }
+ /* FALLTHROUGH */
+ case lexstate_vpairstart:
+ if (state == lexstate_vpairstart) {
+ if (c == '"' &&
+ (options & ISC_LEXOPT_QVPAIR) != 0) {
+ INSIST(remaining > 0U);
+ no_comments = true;
+ state = lexstate_qvpair;
+ break;
+ }
+ state = lexstate_vpair;
+ }
+ /* FALLTHROUGH */
+ case lexstate_vpair:
/*
* EOF needs to be checked before lex->specials[c]
* as lex->specials[EOF] is not a good idea.
result = source->result;
goto done;
}
- tokenp->type = isc_tokentype_string;
+ if (escaped && c == EOF) {
+ result = ISC_R_UNEXPECTEDEND;
+ goto done;
+ }
+ tokenp->type = (state == lexstate_string)
+ ? isc_tokentype_string
+ : isc_tokentype_vpair;
tokenp->value.as_textregion.base = lex->data;
tokenp->value.as_textregion.length =
(unsigned int)(lex->max_token -
}
break;
case lexstate_qstring:
+ case lexstate_qvpair:
if (c == EOF) {
result = ISC_R_UNEXPECTEDEND;
goto done;
INSIST(prev != NULL);
*prev = '"';
} else {
- tokenp->type = isc_tokentype_qstring;
+ tokenp->type =
+ (state == lexstate_qstring)
+ ? isc_tokentype_qstring
+ : isc_tokentype_qvpair;
tokenp->value.as_textregion.base =
lex->data;
tokenp->value.as_textregion.length =
ISC_LEXOPT_DNSMULTILINE | ISC_LEXOPT_ESCAPE;
isc_result_t result;
- if (expect == isc_tokentype_qstring) {
+ if (expect == isc_tokentype_vpair) {
+ options |= ISC_LEXOPT_VPAIR;
+ } else if (expect == isc_tokentype_qvpair) {
+ options |= ISC_LEXOPT_VPAIR;
+ options |= ISC_LEXOPT_QVPAIR;
+ } else if (expect == isc_tokentype_qstring) {
options |= ISC_LEXOPT_QSTRING;
} else if (expect == isc_tokentype_number) {
options |= ISC_LEXOPT_NUMBER;
return (ISC_R_SUCCESS);
}
if (token->type == isc_tokentype_string &&
- expect == isc_tokentype_qstring) {
+ (expect == isc_tokentype_qstring || expect == isc_tokentype_qvpair))
+ {
+ return (ISC_R_SUCCESS);
+ }
+ if (token->type == isc_tokentype_vpair &&
+ expect == isc_tokentype_qvpair) {
return (ISC_R_SUCCESS);
}
if (token->type != expect) {