From 29988a24e20841afa3292c116aecd7a04dafc00c Mon Sep 17 00:00:00 2001 From: Thomas Markwalder Date: Thu, 14 Apr 2022 07:21:12 -0400 Subject: [#2272] Added split function to expression syntax doc/sphinx/arm/classify.rst Documented new split() function src/lib/eval/eval_messages.cc b/src/lib/eval/eval_messages.* New debug log messges src/lib/eval/lexer.ll src/lib/eval/parser.yy added split parsing src/lib/eval/tests/token_unittest.cc Added tests for split() src/lib/eval/token.* Added TokenSplit class --- src/lib/eval/eval_messages.cc | 8 + src/lib/eval/eval_messages.h | 4 + src/lib/eval/eval_messages.mes | 23 + src/lib/eval/lexer.cc | 385 ++++---- src/lib/eval/lexer.ll | 3 +- src/lib/eval/location.hh | 132 +-- src/lib/eval/parser.cc | 1625 ++++++++++++++++------------------ src/lib/eval/parser.h | 1086 +++++++++-------------- src/lib/eval/parser.yy | 14 +- src/lib/eval/tests/token_unittest.cc | 154 +++- src/lib/eval/token.cc | 90 +- src/lib/eval/token.h | 46 +- 12 files changed, 1819 insertions(+), 1751 deletions(-) (limited to 'src/lib/eval') diff --git a/src/lib/eval/eval_messages.cc b/src/lib/eval/eval_messages.cc index d70cd2e8c0..7dfeba1fd8 100644 --- a/src/lib/eval/eval_messages.cc +++ b/src/lib/eval/eval_messages.cc @@ -27,6 +27,10 @@ extern const isc::log::MessageID EVAL_DEBUG_PKT4 = "EVAL_DEBUG_PKT4"; extern const isc::log::MessageID EVAL_DEBUG_PKT6 = "EVAL_DEBUG_PKT6"; extern const isc::log::MessageID EVAL_DEBUG_RELAY6 = "EVAL_DEBUG_RELAY6"; extern const isc::log::MessageID EVAL_DEBUG_RELAY6_RANGE = "EVAL_DEBUG_RELAY6_RANGE"; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT = "EVAL_DEBUG_SPLIT"; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT_DELIM_EMPTY = "EVAL_DEBUG_SPLIT_DELIM_EMPTY"; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT_EMPTY = "EVAL_DEBUG_SPLIT_EMPTY"; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE = "EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE"; extern const isc::log::MessageID EVAL_DEBUG_STRING = "EVAL_DEBUG_STRING"; extern const isc::log::MessageID EVAL_DEBUG_SUBSTRING = "EVAL_DEBUG_SUBSTRING"; extern const isc::log::MessageID EVAL_DEBUG_SUBSTRING_EMPTY = "EVAL_DEBUG_SUBSTRING_EMPTY"; @@ -75,6 +79,10 @@ const char* values[] = { "EVAL_DEBUG_PKT6", "Pushing PKT6 field %1 with value %2", "EVAL_DEBUG_RELAY6", "Pushing PKT6 relay field %1 nest %2 with value %3", "EVAL_DEBUG_RELAY6_RANGE", "Pushing PKT6 relay field %1 nest %2 with value %3", + "EVAL_DEBUG_SPLIT", "Popping field %1, delimiters %2, string %3, pushing result %4", + "EVAL_DEBUG_SPLIT_DELIM_EMPTY", "Popping field %1, delimiters %2, string %3, pushing result %4", + "EVAL_DEBUG_SPLIT_EMPTY", "Popping field %1, delimiters %2, string %3, pushing result %4", + "EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE", "Popping field %1, delimiters %2, string %3, pushing result %4", "EVAL_DEBUG_STRING", "Pushing text string %1", "EVAL_DEBUG_SUBSTRING", "Popping length %1, start %2, string %3 pushing result %4", "EVAL_DEBUG_SUBSTRING_EMPTY", "Popping length %1, start %2, string %3 pushing result %4", diff --git a/src/lib/eval/eval_messages.h b/src/lib/eval/eval_messages.h index 5b7173423b..6353ab21b6 100644 --- a/src/lib/eval/eval_messages.h +++ b/src/lib/eval/eval_messages.h @@ -28,6 +28,10 @@ extern const isc::log::MessageID EVAL_DEBUG_PKT4; extern const isc::log::MessageID EVAL_DEBUG_PKT6; extern const isc::log::MessageID EVAL_DEBUG_RELAY6; extern const isc::log::MessageID EVAL_DEBUG_RELAY6_RANGE; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT_DELIM_EMPTY; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT_EMPTY; +extern const isc::log::MessageID EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE; extern const isc::log::MessageID EVAL_DEBUG_STRING; extern const isc::log::MessageID EVAL_DEBUG_SUBSTRING; extern const isc::log::MessageID EVAL_DEBUG_SUBSTRING_EMPTY; diff --git a/src/lib/eval/eval_messages.mes b/src/lib/eval/eval_messages.mes index d89b79fcb1..bc2483a4a6 100644 --- a/src/lib/eval/eval_messages.mes +++ b/src/lib/eval/eval_messages.mes @@ -261,3 +261,26 @@ and vendor option was not found. This debug message indicates that the expression has been evaluated to said value. This message is mostly useful during debugging of the client classification expressions. + +% EVAL_DEBUG_SPLIT_EMPTY Popping field %1, delimiters %2, string %3, pushing result %4 +This debug message indicates that the string popped from the stack was empty +and so the result will also be empty. The field, deli meter string, and string are +still popped from the stack and the result is still pushed. + +% EVAL_DEBUG_SPLIT_DELIM_EMPTY Popping field %1, delimiters %2, string %3, pushing result %4 +This debug message indicates that the deli meter string popped from the stack was empty +and so the result will also be empty. The field, deli meter string, and string are +still popped from the stack and the result is still pushed. + +% EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE Popping field %1, delimiters %2, string %3, pushing result %4 +This debug message indicates that the field is either less than one or larger +than the number of fields in the string popped from the stack. the result will +be empty. The field, deli meter string, and string are still popped from the +stack and the result is still pushed. + +% EVAL_DEBUG_SPLIT Popping field %1, delimiters %2, string %3, pushing result %4 +This debug message indicates that three values are being popped from +the value stack and a result is being pushed onto the value stack. The +values being popped are the field, delimiter_string and string and the +result is the extracted field. The resulting string is pushed onto +the stack. The strings are displayed in hex. diff --git a/src/lib/eval/lexer.cc b/src/lib/eval/lexer.cc index 82c5b416b0..5855ede9a6 100644 --- a/src/lib/eval/lexer.cc +++ b/src/lib/eval/lexer.cc @@ -710,8 +710,8 @@ static void yynoreturn yy_fatal_error ( const char* msg ); /* %% [3.0] code to copy yytext_ptr to yytext[] goes here, if %array \ */\ (yy_c_buf_p) = yy_cp; /* %% [4.0] data tables for the DFA and the user's section 1 definitions go here */ -#define YY_NUM_RULES 62 -#define YY_END_OF_BUFFER 63 +#define YY_NUM_RULES 63 +#define YY_END_OF_BUFFER 64 /* This struct is not used in this scanner, but its presence is necessary. */ struct yy_trans_info @@ -719,38 +719,38 @@ struct yy_trans_info flex_int32_t yy_verify; flex_int32_t yy_nxt; }; -static const flex_int16_t yy_accept[275] = +static const flex_int16_t yy_accept[279] = { 0, - 0, 0, 63, 61, 1, 2, 61, 54, 55, 59, - 60, 58, 61, 53, 5, 5, 61, 61, 61, 61, - 56, 57, 61, 61, 61, 61, 61, 61, 61, 61, - 61, 61, 61, 61, 61, 61, 61, 61, 61, 61, + 0, 0, 64, 62, 1, 2, 62, 55, 56, 60, + 61, 59, 62, 54, 5, 5, 62, 62, 62, 62, + 57, 58, 62, 62, 62, 62, 62, 62, 62, 62, + 62, 62, 62, 62, 62, 62, 62, 62, 62, 62, 1, 2, 0, 3, 5, 0, 5, 0, 0, 0, 0, 7, 8, 0, 0, 0, 0, 6, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 51, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 4, 7, 0, 38, 50, 0, 0, - - 0, 20, 0, 0, 0, 15, 0, 0, 0, 0, - 0, 21, 0, 23, 0, 0, 49, 0, 0, 17, - 0, 0, 19, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 35, 0, 0, 0, 0, 24, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 22, 30, 0, 0, 0, 14, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 25, 18, + 52, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 4, 7, 0, 39, 51, 0, + + 0, 0, 20, 0, 0, 0, 15, 0, 0, 0, + 0, 0, 21, 0, 23, 0, 0, 50, 0, 0, + 17, 0, 0, 0, 19, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 35, 0, 0, 0, 0, + 24, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 22, 30, 0, 0, 0, 0, 14, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 26, 39, 0, 16, 27, 0, 40, 0, 0, 0, - - 0, 52, 0, 9, 0, 10, 11, 29, 0, 0, - 0, 0, 0, 33, 28, 7, 0, 0, 0, 0, - 0, 0, 0, 31, 0, 0, 32, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 13, 12, 0, - 0, 0, 0, 0, 0, 0, 41, 0, 0, 0, - 37, 0, 0, 0, 0, 42, 36, 0, 0, 43, - 0, 0, 0, 0, 44, 45, 0, 0, 46, 0, - 47, 48, 34, 0 + 0, 25, 18, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 38, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 26, 40, 0, 16, 27, 0, + + 41, 0, 0, 0, 0, 53, 0, 9, 0, 10, + 11, 29, 0, 0, 0, 0, 0, 33, 28, 7, + 0, 0, 0, 0, 0, 0, 0, 31, 0, 0, + 32, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 13, 12, 0, 0, 0, 0, 0, 0, 0, + 42, 0, 0, 0, 37, 0, 0, 0, 0, 43, + 36, 0, 0, 44, 0, 0, 0, 0, 45, 46, + 0, 0, 47, 0, 48, 49, 34, 0 } ; static const YY_CHAR yy_ec[256] = @@ -794,128 +794,129 @@ static const YY_CHAR yy_meta[50] = 1, 1, 1, 1, 1, 1, 1, 1, 1 } ; -static const flex_int16_t yy_base[284] = +static const flex_int16_t yy_base[288] = { 0, - 0, 0, 379, 380, 376, 374, 372, 380, 380, 380, - 380, 380, 0, 380, 39, 36, 355, 353, 86, 124, - 380, 380, 35, 38, 34, 37, 337, 48, 43, 58, - 63, 331, 22, 60, 339, 115, 116, 334, 337, 332, - 365, 363, 361, 380, 0, 0, 121, 344, 343, 0, - 342, 0, 380, 147, 160, 0, 0, 380, 330, 322, - 328, 330, 317, 311, 310, 309, 317, 324, 303, 318, - 300, 132, 303, 307, 306, 315, 305, 309, 297, 296, - 0, 308, 294, 300, 309, 306, 306, 286, 305, 292, - 291, 302, 318, 0, 0, 285, 0, 0, 296, 296, - - 297, 0, 292, 279, 291, 277, 280, 277, 288, 279, - 152, 0, 279, 0, 286, 269, 0, 277, 269, 150, - 283, 279, 0, 265, 263, 267, 261, 274, 273, 0, - 258, 271, 273, 0, 257, 254, 267, 252, 0, 264, - 263, 250, 275, 278, 246, 262, 257, 239, 246, 258, - 0, 0, 236, 253, 238, 0, 238, 157, 240, 249, - 268, 237, 234, 231, 233, 230, 230, 229, 0, 0, - 239, 225, 224, 227, 236, 223, 223, 224, 232, 159, - 219, 218, 224, 241, 244, 212, 213, 212, 0, 209, - 0, 0, 210, 0, 0, 216, 0, 210, 209, 204, - - 217, 0, 215, 0, 215, 0, 0, 0, 209, 213, - 198, 197, 200, 230, 0, 0, 207, 202, 197, 191, - 190, 202, 190, 0, 189, 191, 0, 189, 188, 183, - 176, 179, 182, 186, 176, 173, 156, 0, 0, 169, - 156, 155, 167, 160, 152, 164, 0, 147, 146, 148, - 0, 160, 159, 142, 161, 0, 0, 143, 142, 0, - 137, 136, 138, 138, 0, 0, 136, 135, 0, 130, - 0, 0, 0, 380, 206, 143, 209, 107, 212, 215, - 219, 78, 77 + 0, 0, 383, 384, 380, 378, 376, 384, 384, 384, + 384, 384, 0, 384, 39, 36, 359, 357, 86, 124, + 384, 384, 35, 38, 34, 37, 341, 48, 43, 58, + 63, 335, 22, 60, 343, 122, 116, 338, 341, 336, + 369, 367, 365, 384, 0, 0, 121, 348, 347, 0, + 346, 0, 384, 147, 158, 0, 0, 384, 334, 326, + 332, 334, 321, 315, 314, 313, 321, 328, 307, 322, + 304, 119, 307, 311, 310, 319, 309, 313, 301, 300, + 0, 312, 298, 304, 313, 302, 309, 309, 289, 308, + 295, 294, 305, 321, 0, 0, 288, 0, 0, 299, + + 299, 300, 0, 295, 282, 294, 280, 283, 280, 291, + 282, 157, 0, 282, 0, 289, 272, 0, 280, 272, + 159, 286, 282, 276, 0, 267, 265, 269, 263, 276, + 275, 0, 260, 273, 275, 0, 259, 256, 269, 254, + 0, 266, 265, 252, 277, 280, 248, 264, 259, 241, + 248, 260, 0, 0, 238, 255, 240, 239, 0, 239, + 166, 241, 250, 269, 238, 235, 232, 234, 231, 231, + 230, 0, 0, 240, 226, 225, 228, 237, 224, 224, + 225, 233, 162, 220, 0, 219, 225, 242, 245, 213, + 214, 213, 0, 210, 0, 0, 211, 0, 0, 217, + + 0, 211, 210, 205, 218, 0, 216, 0, 216, 0, + 0, 0, 210, 214, 199, 198, 201, 231, 0, 0, + 208, 203, 198, 192, 191, 203, 191, 0, 190, 192, + 0, 190, 189, 184, 160, 180, 183, 192, 193, 192, + 175, 0, 0, 188, 176, 175, 187, 180, 172, 184, + 0, 167, 166, 168, 0, 180, 179, 162, 176, 0, + 0, 147, 144, 0, 140, 139, 138, 138, 0, 0, + 129, 126, 0, 123, 0, 0, 0, 384, 190, 162, + 193, 107, 196, 199, 203, 78, 77 } ; -static const flex_int16_t yy_def[284] = +static const flex_int16_t yy_def[288] = { 0, - 274, 1, 274, 274, 274, 274, 275, 274, 274, 274, - 274, 274, 276, 274, 274, 15, 277, 274, 274, 19, - 274, 274, 19, 19, 19, 19, 20, 20, 20, 20, + 278, 1, 278, 278, 278, 278, 279, 278, 278, 278, + 278, 278, 280, 278, 278, 15, 281, 278, 278, 19, + 278, 278, 19, 19, 19, 19, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 274, 274, 275, 274, 276, 278, 15, 277, 279, 280, - 277, 281, 274, 274, 20, 19, 20, 274, 19, 20, + 278, 278, 279, 278, 280, 282, 15, 281, 283, 284, + 281, 285, 278, 278, 20, 19, 20, 278, 19, 20, 20, 20, 20, 19, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 278, 280, 281, 19, 20, 20, 20, 20, + 20, 20, 20, 282, 284, 285, 19, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 20, 282, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, + 20, 286, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 282, 20, 20, 20, 20, 20, 20, 20, 20, 20, + 20, 20, 20, 286, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 20, 20, 20, 283, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, + 20, 20, 287, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 20, 283, 20, 20, 20, 20, + 20, 20, 20, 20, 20, 20, 20, 20, 20, 287, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, 20, - 20, 20, 20, 0, 274, 274, 274, 274, 274, 274, - 274, 274, 274 + 20, 20, 20, 20, 20, 20, 20, 0, 278, 278, + 278, 278, 278, 278, 278, 278, 278 } ; -static const flex_int16_t yy_nxt[430] = +static const flex_int16_t yy_nxt[434] = { 0, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15, 16, 16, 16, 16, 16, 16, 16, 17, 18, 19, 20, 20, 21, 22, 4, 23, 19, 24, 25, 26, 19, 27, 28, 29, 20, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 20, 40, 46, - 47, 47, 47, 47, 47, 47, 47, 47, 48, 274, + 47, 47, 47, 47, 47, 47, 47, 47, 48, 278, 49, 64, 50, 80, 81, 59, 49, 49, 49, 49, 49, 49, 60, 62, 61, 72, 66, 65, 63, 69, - 216, 161, 73, 274, 67, 70, 50, 54, 54, 74, + 220, 164, 73, 278, 67, 70, 50, 54, 54, 74, 76, 82, 71, 75, 77, 55, 83, 56, 56, 56, 56, 56, 56, 56, 56, 48, 78, 56, 57, 57, - 93, 58, 55, 56, 56, 56, 56, 56, 56, 57, + 94, 58, 55, 56, 56, 56, 56, 56, 56, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, 57, - 57, 57, 57, 274, 274, 57, 45, 88, 54, 54, - 85, 57, 57, 57, 57, 57, 57, 86, 89, 109, - 87, 274, 274, 110, 143, 151, 144, 152, 274, 184, - 145, 185, 58, 273, 206, 186, 207, 274, 274, 272, - 271, 270, 269, 268, 267, 274, 266, 265, 264, 263, - 262, 261, 260, 259, 258, 257, 256, 255, 254, 253, - - 252, 274, 251, 250, 249, 244, 43, 248, 43, 43, - 43, 43, 51, 51, 51, 49, 49, 49, 94, 247, - 94, 95, 95, 95, 95, 246, 245, 243, 242, 241, - 240, 239, 238, 237, 236, 235, 234, 233, 232, 231, - 230, 229, 228, 227, 226, 225, 224, 223, 222, 221, - 220, 219, 218, 217, 215, 214, 213, 212, 211, 210, - 209, 208, 205, 204, 203, 202, 201, 200, 199, 198, - 197, 196, 195, 194, 193, 192, 191, 190, 189, 188, - 187, 183, 182, 181, 180, 179, 178, 177, 176, 175, - 174, 173, 172, 171, 170, 169, 168, 167, 166, 165, - - 164, 163, 162, 160, 159, 158, 157, 156, 155, 154, - 153, 150, 149, 148, 147, 146, 142, 141, 140, 139, - 138, 137, 136, 135, 134, 133, 132, 131, 130, 129, - 128, 127, 126, 125, 124, 123, 122, 121, 120, 119, - 118, 117, 116, 115, 114, 113, 112, 111, 108, 107, - 106, 105, 104, 103, 102, 101, 100, 99, 98, 97, - 96, 52, 48, 52, 44, 42, 41, 92, 91, 90, - 84, 79, 68, 53, 52, 44, 42, 41, 274, 3, - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274 + 57, 57, 57, 278, 278, 57, 110, 89, 54, 54, + 111, 57, 57, 57, 57, 57, 57, 85, 90, 278, + 278, 278, 278, 86, 87, 45, 277, 88, 278, 145, + 276, 146, 58, 275, 153, 147, 154, 210, 188, 211, + 189, 274, 273, 278, 190, 278, 272, 271, 270, 248, + 43, 269, 43, 43, 43, 43, 51, 51, 51, 49, + + 49, 49, 95, 268, 95, 96, 96, 96, 96, 267, + 266, 265, 264, 263, 262, 261, 260, 259, 258, 257, + 256, 255, 254, 253, 252, 251, 250, 249, 247, 246, + 245, 244, 243, 242, 241, 240, 239, 238, 237, 236, + 235, 234, 233, 232, 231, 230, 229, 228, 227, 226, + 225, 224, 223, 222, 221, 219, 218, 217, 216, 215, + 214, 213, 212, 209, 208, 207, 206, 205, 204, 203, + 202, 201, 200, 199, 198, 197, 196, 195, 194, 193, + 192, 191, 187, 186, 185, 184, 183, 182, 181, 180, + 179, 178, 177, 176, 175, 174, 173, 172, 171, 170, + + 169, 168, 167, 166, 165, 163, 162, 161, 160, 159, + 158, 157, 156, 155, 152, 151, 150, 149, 148, 144, + 143, 142, 141, 140, 139, 138, 137, 136, 135, 134, + 133, 132, 131, 130, 129, 128, 127, 126, 125, 124, + 123, 122, 121, 120, 119, 118, 117, 116, 115, 114, + 113, 112, 109, 108, 107, 106, 105, 104, 103, 102, + 101, 100, 99, 98, 97, 52, 48, 52, 44, 42, + 41, 93, 92, 91, 84, 79, 68, 53, 52, 44, + 42, 41, 278, 3, 278, 278, 278, 278, 278, 278, + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278 } ; -static const flex_int16_t yy_chk[430] = +static const flex_int16_t yy_chk[434] = { 0, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, @@ -925,54 +926,55 @@ static const flex_int16_t yy_chk[430] = 15, 15, 15, 15, 15, 15, 15, 15, 15, 16, 15, 25, 15, 33, 33, 23, 15, 15, 15, 15, 15, 15, 23, 24, 23, 29, 26, 25, 24, 28, - 283, 282, 29, 16, 26, 28, 15, 19, 19, 30, + 287, 286, 29, 16, 26, 28, 15, 19, 19, 30, 31, 34, 28, 30, 31, 19, 34, 19, 19, 19, 19, 19, 19, 19, 19, 19, 31, 19, 19, 19, - 278, 19, 19, 19, 19, 19, 19, 19, 19, 19, + 282, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 19, 20, 20, 20, 20, 20, - 20, 20, 20, 20, 47, 20, 276, 37, 54, 54, - 36, 20, 20, 20, 20, 20, 20, 36, 37, 72, - 36, 55, 55, 72, 111, 120, 111, 120, 47, 158, - 111, 158, 54, 270, 180, 158, 180, 231, 231, 268, - 267, 264, 263, 262, 261, 55, 259, 258, 255, 254, - 253, 252, 250, 249, 248, 246, 245, 244, 243, 242, - - 241, 231, 240, 237, 236, 231, 275, 235, 275, 275, - 275, 275, 277, 277, 277, 279, 279, 279, 280, 234, - 280, 281, 281, 281, 281, 233, 232, 230, 229, 228, - 226, 225, 223, 222, 221, 220, 219, 218, 217, 214, - 213, 212, 211, 210, 209, 205, 203, 201, 200, 199, - 198, 196, 193, 190, 188, 187, 186, 185, 184, 183, - 182, 181, 179, 178, 177, 176, 175, 174, 173, 172, - 171, 168, 167, 166, 165, 164, 163, 162, 161, 160, - 159, 157, 155, 154, 153, 150, 149, 148, 147, 146, - 145, 144, 143, 142, 141, 140, 138, 137, 136, 135, - - 133, 132, 131, 129, 128, 127, 126, 125, 124, 122, - 121, 119, 118, 116, 115, 113, 110, 109, 108, 107, - 106, 105, 104, 103, 101, 100, 99, 96, 93, 92, - 91, 90, 89, 88, 87, 86, 85, 84, 83, 82, - 80, 79, 78, 77, 76, 75, 74, 73, 71, 70, - 69, 68, 67, 66, 65, 64, 63, 62, 61, 60, - 59, 51, 49, 48, 43, 42, 41, 40, 39, 38, - 35, 32, 27, 18, 17, 7, 6, 5, 3, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274, 274, - 274, 274, 274, 274, 274, 274, 274, 274, 274 + 20, 20, 20, 20, 47, 20, 72, 37, 54, 54, + 72, 20, 20, 20, 20, 20, 20, 36, 37, 55, + 55, 235, 235, 36, 36, 280, 274, 36, 47, 112, + 272, 112, 54, 271, 121, 112, 121, 183, 161, 183, + 161, 268, 267, 55, 161, 235, 266, 265, 263, 235, + 279, 262, 279, 279, 279, 279, 281, 281, 281, 283, + + 283, 283, 284, 259, 284, 285, 285, 285, 285, 258, + 257, 256, 254, 253, 252, 250, 249, 248, 247, 246, + 245, 244, 241, 240, 239, 238, 237, 236, 234, 233, + 232, 230, 229, 227, 226, 225, 224, 223, 222, 221, + 218, 217, 216, 215, 214, 213, 209, 207, 205, 204, + 203, 202, 200, 197, 194, 192, 191, 190, 189, 188, + 187, 186, 184, 182, 181, 180, 179, 178, 177, 176, + 175, 174, 171, 170, 169, 168, 167, 166, 165, 164, + 163, 162, 160, 158, 157, 156, 155, 152, 151, 150, + 149, 148, 147, 146, 145, 144, 143, 142, 140, 139, + + 138, 137, 135, 134, 133, 131, 130, 129, 128, 127, + 126, 124, 123, 122, 120, 119, 117, 116, 114, 111, + 110, 109, 108, 107, 106, 105, 104, 102, 101, 100, + 97, 94, 93, 92, 91, 90, 89, 88, 87, 86, + 85, 84, 83, 82, 80, 79, 78, 77, 76, 75, + 74, 73, 71, 70, 69, 68, 67, 66, 65, 64, + 63, 62, 61, 60, 59, 51, 49, 48, 43, 42, + 41, 40, 39, 38, 35, 32, 27, 18, 17, 7, + 6, 5, 3, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278, 278, 278, 278, 278, 278, 278, 278, + 278, 278, 278 } ; /* Table of booleans, true if rule could match eol. */ -static const flex_int32_t yy_rule_can_match_eol[63] = +static const flex_int32_t yy_rule_can_match_eol[64] = { 0, 0, 1, 0, 0, 0, 1, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, }; + 0, 0, 0, 0, }; static yy_state_type yy_last_accepting_state; static char *yy_last_accepting_cpos; @@ -980,7 +982,7 @@ static char *yy_last_accepting_cpos; extern int yy_flex_debug; int yy_flex_debug = 1; -static const flex_int16_t yy_rule_linenum[62] = +static const flex_int16_t yy_rule_linenum[63] = { 0, 106, 111, 117, 127, 133, 151, 175, 189, 190, 191, 192, 193, 194, 195, 196, 197, 198, 199, 200, 201, @@ -988,7 +990,7 @@ static const flex_int16_t yy_rule_linenum[62] = 212, 213, 214, 215, 216, 217, 218, 219, 220, 221, 222, 223, 224, 225, 226, 227, 228, 229, 230, 231, 232, 233, 234, 235, 236, 237, 238, 239, 240, 241, - 242 + 242, 243 } ; /* The intent behind this definition is that it'll catch @@ -1000,7 +1002,7 @@ static const flex_int16_t yy_rule_linenum[62] = #define YY_RESTORE_YY_MORE_OFFSET char *yytext; #line 1 "lexer.ll" -/* Copyright (C) 2015-2021 Internet Systems Consortium, Inc. ("ISC") +/* Copyright (C) 2015-2022 Internet Systems Consortium, Inc. ("ISC") This Source Code Form is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this @@ -1039,7 +1041,7 @@ namespace { /* To avoid the call to exit... oops! */ #define YY_FATAL_ERROR(msg) isc::eval::EvalContext::fatal(msg) -#line 1042 "lexer.cc" +#line 1044 "lexer.cc" /* noyywrap disables automatic rewinding for the next file to parse. Since we always parse only a single string, there's no need to do any wraps. And using yywrap requires linking with -lfl, which provides the default yywrap @@ -1064,8 +1066,8 @@ namespace { by moving it ahead by yyleng bytes. yyleng specifies the length of the currently matched token. */ #define YY_USER_ACTION loc.columns(evalleng); -#line 1067 "lexer.cc" -#line 1068 "lexer.cc" +#line 1069 "lexer.cc" +#line 1070 "lexer.cc" #define INITIAL 0 @@ -1364,7 +1366,7 @@ YY_DECL -#line 1367 "lexer.cc" +#line 1369 "lexer.cc" while ( /*CONSTCOND*/1 ) /* loops until end-of-file is reached */ { @@ -1393,13 +1395,13 @@ yy_match: while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; - if ( yy_current_state >= 275 ) + if ( yy_current_state >= 279 ) yy_c = yy_meta[yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + yy_c]; ++yy_cp; } - while ( yy_current_state != 274 ); + while ( yy_current_state != 278 ); yy_cp = (yy_last_accepting_cpos); yy_current_state = (yy_last_accepting_state); @@ -1428,13 +1430,13 @@ do_action: /* This label is used only to access EOF actions. */ { if ( yy_act == 0 ) fprintf( stderr, "--scanner backing up\n" ); - else if ( yy_act < 62 ) + else if ( yy_act < 63 ) fprintf( stderr, "--accepting rule at line %ld (\"%s\")\n", (long)yy_rule_linenum[yy_act], yytext ); - else if ( yy_act == 62 ) + else if ( yy_act == 63 ) fprintf( stderr, "--accepting default rule (\"%s\")\n", yytext ); - else if ( yy_act == 63 ) + else if ( yy_act == 64 ) fprintf( stderr, "--(end of buffer or a NUL)\n" ); else fprintf( stderr, "--EOF (start condition %d)\n", YY_START ); @@ -1713,133 +1715,138 @@ return isc::eval::EvalParser::make_SUBSTRING(loc); case 38: YY_RULE_SETUP #line 219 "lexer.ll" -return isc::eval::EvalParser::make_ALL(loc); +return isc::eval::EvalParser::make_SPLIT(loc); YY_BREAK case 39: YY_RULE_SETUP #line 220 "lexer.ll" -return isc::eval::EvalParser::make_CONCAT(loc); +return isc::eval::EvalParser::make_ALL(loc); YY_BREAK case 40: YY_RULE_SETUP #line 221 "lexer.ll" -return isc::eval::EvalParser::make_IFELSE(loc); +return isc::eval::EvalParser::make_CONCAT(loc); YY_BREAK case 41: YY_RULE_SETUP #line 222 "lexer.ll" -return isc::eval::EvalParser::make_TOHEXSTRING(loc); +return isc::eval::EvalParser::make_IFELSE(loc); YY_BREAK case 42: YY_RULE_SETUP #line 223 "lexer.ll" -return isc::eval::EvalParser::make_ADDRTOTEXT(loc); +return isc::eval::EvalParser::make_TOHEXSTRING(loc); YY_BREAK case 43: YY_RULE_SETUP #line 224 "lexer.ll" -return isc::eval::EvalParser::make_INT8TOTEXT(loc); +return isc::eval::EvalParser::make_ADDRTOTEXT(loc); YY_BREAK case 44: YY_RULE_SETUP #line 225 "lexer.ll" -return isc::eval::EvalParser::make_INT16TOTEXT(loc); +return isc::eval::EvalParser::make_INT8TOTEXT(loc); YY_BREAK case 45: YY_RULE_SETUP #line 226 "lexer.ll" -return isc::eval::EvalParser::make_INT32TOTEXT(loc); +return isc::eval::EvalParser::make_INT16TOTEXT(loc); YY_BREAK case 46: YY_RULE_SETUP #line 227 "lexer.ll" -return isc::eval::EvalParser::make_UINT8TOTEXT(loc); +return isc::eval::EvalParser::make_INT32TOTEXT(loc); YY_BREAK case 47: YY_RULE_SETUP #line 228 "lexer.ll" -return isc::eval::EvalParser::make_UINT16TOTEXT(loc); +return isc::eval::EvalParser::make_UINT8TOTEXT(loc); YY_BREAK case 48: YY_RULE_SETUP #line 229 "lexer.ll" -return isc::eval::EvalParser::make_UINT32TOTEXT(loc); +return isc::eval::EvalParser::make_UINT16TOTEXT(loc); YY_BREAK case 49: YY_RULE_SETUP #line 230 "lexer.ll" -return isc::eval::EvalParser::make_NOT(loc); +return isc::eval::EvalParser::make_UINT32TOTEXT(loc); YY_BREAK case 50: YY_RULE_SETUP #line 231 "lexer.ll" -return isc::eval::EvalParser::make_AND(loc); +return isc::eval::EvalParser::make_NOT(loc); YY_BREAK case 51: YY_RULE_SETUP #line 232 "lexer.ll" -return isc::eval::EvalParser::make_OR(loc); +return isc::eval::EvalParser::make_AND(loc); YY_BREAK case 52: YY_RULE_SETUP #line 233 "lexer.ll" -return isc::eval::EvalParser::make_MEMBER(loc); +return isc::eval::EvalParser::make_OR(loc); YY_BREAK case 53: YY_RULE_SETUP #line 234 "lexer.ll" -return isc::eval::EvalParser::make_DOT(loc); +return isc::eval::EvalParser::make_MEMBER(loc); YY_BREAK case 54: YY_RULE_SETUP #line 235 "lexer.ll" -return isc::eval::EvalParser::make_LPAREN(loc); +return isc::eval::EvalParser::make_DOT(loc); YY_BREAK case 55: YY_RULE_SETUP #line 236 "lexer.ll" -return isc::eval::EvalParser::make_RPAREN(loc); +return isc::eval::EvalParser::make_LPAREN(loc); YY_BREAK case 56: YY_RULE_SETUP #line 237 "lexer.ll" -return isc::eval::EvalParser::make_LBRACKET(loc); +return isc::eval::EvalParser::make_RPAREN(loc); YY_BREAK case 57: YY_RULE_SETUP #line 238 "lexer.ll" -return isc::eval::EvalParser::make_RBRACKET(loc); +return isc::eval::EvalParser::make_LBRACKET(loc); YY_BREAK case 58: YY_RULE_SETUP #line 239 "lexer.ll" -return isc::eval::EvalParser::make_COMA(loc); +return isc::eval::EvalParser::make_RBRACKET(loc); YY_BREAK case 59: YY_RULE_SETUP #line 240 "lexer.ll" -return isc::eval::EvalParser::make_ANY(loc); +return isc::eval::EvalParser::make_COMA(loc); YY_BREAK case 60: YY_RULE_SETUP #line 241 "lexer.ll" -return isc::eval::EvalParser::make_PLUS(loc); +return isc::eval::EvalParser::make_ANY(loc); YY_BREAK case 61: YY_RULE_SETUP #line 242 "lexer.ll" +return isc::eval::EvalParser::make_PLUS(loc); + YY_BREAK +case 62: +YY_RULE_SETUP +#line 243 "lexer.ll" driver.error (loc, "Invalid character: " + std::string(evaltext)); YY_BREAK case YY_STATE_EOF(INITIAL): -#line 243 "lexer.ll" +#line 244 "lexer.ll" return isc::eval::EvalParser::make_END(loc); YY_BREAK -case 62: +case 63: YY_RULE_SETUP -#line 244 "lexer.ll" +#line 245 "lexer.ll" ECHO; YY_BREAK -#line 1842 "lexer.cc" +#line 1849 "lexer.cc" case YY_END_OF_BUFFER: { @@ -2158,7 +2165,7 @@ static int yy_get_next_buffer (void) while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; - if ( yy_current_state >= 275 ) + if ( yy_current_state >= 279 ) yy_c = yy_meta[yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + yy_c]; @@ -2191,11 +2198,11 @@ static int yy_get_next_buffer (void) while ( yy_chk[yy_base[yy_current_state] + yy_c] != yy_current_state ) { yy_current_state = (int) yy_def[yy_current_state]; - if ( yy_current_state >= 275 ) + if ( yy_current_state >= 279 ) yy_c = yy_meta[yy_c]; } yy_current_state = yy_nxt[yy_base[yy_current_state] + yy_c]; - yy_is_jam = (yy_current_state == 274); + yy_is_jam = (yy_current_state == 278); return yy_is_jam ? 0 : yy_current_state; } @@ -2951,7 +2958,7 @@ void yyfree (void * ptr ) /* %ok-for-header */ -#line 244 "lexer.ll" +#line 245 "lexer.ll" using namespace isc::eval; diff --git a/src/lib/eval/lexer.ll b/src/lib/eval/lexer.ll index 12a0bf8655..3c376c2426 100644 --- a/src/lib/eval/lexer.ll +++ b/src/lib/eval/lexer.ll @@ -1,4 +1,4 @@ -/* Copyright (C) 2015-2021 Internet Systems Consortium, Inc. ("ISC") +/* Copyright (C) 2015-2022 Internet Systems Consortium, Inc. ("ISC") This Source Code Form is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this @@ -215,6 +215,7 @@ addr6 [0-9a-fA-F]*\:[0-9a-fA-F]*\:[0-9a-fA-F:.]* "data" return isc::eval::EvalParser::make_DATA(loc); "enterprise" return isc::eval::EvalParser::make_ENTERPRISE(loc); "substring" return isc::eval::EvalParser::make_SUBSTRING(loc); +"split" return isc::eval::EvalParser::make_SPLIT(loc); "all" return isc::eval::EvalParser::make_ALL(loc); "concat" return isc::eval::EvalParser::make_CONCAT(loc); "ifelse" return isc::eval::EvalParser::make_IFELSE(loc); diff --git a/src/lib/eval/location.hh b/src/lib/eval/location.hh index 5bde47985a..92a70a09df 100644 --- a/src/lib/eval/location.hh +++ b/src/lib/eval/location.hh @@ -1,8 +1,8 @@ -// A Bison parser, made by GNU Bison 3.8.2. +// A Bison parser, made by GNU Bison 3.3.1. // Locations for Bison parsers in C++ -// Copyright (C) 2002-2015, 2018-2021 Free Software Foundation, Inc. +// Copyright (C) 2002-2015, 2018-2019 Free Software Foundation, Inc. // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -15,7 +15,7 @@ // GNU General Public License for more details. // You should have received a copy of the GNU General Public License -// along with this program. If not, see . +// along with this program. If not, see . // As a special exception, you may create a larger work that contains // part or all of the Bison parser skeleton and distribute that work @@ -38,6 +38,7 @@ #ifndef YY_EVAL_LOCATION_HH_INCLUDED # define YY_EVAL_LOCATION_HH_INCLUDED +# include // std::max # include # include @@ -53,23 +54,17 @@ # endif # endif -#line 14 "parser.yy" +#line 14 "parser.yy" // location.cc:339 namespace isc { namespace eval { -#line 59 "location.hh" - +#line 60 "location.hh" // location.cc:339 /// A point in a source file. class position { public: - /// Type for file name. - typedef const std::string filename_type; - /// Type for line and column numbers. - typedef int counter_type; - /// Construct a position. - explicit position (filename_type* f = YY_NULLPTR, - counter_type l = 1, - counter_type c = 1) + explicit position (std::string* f = YY_NULLPTR, + unsigned l = 1u, + unsigned c = 1u) : filename (f) , line (l) , column (c) @@ -77,9 +72,9 @@ namespace isc { namespace eval { /// Initialization. - void initialize (filename_type* fn = YY_NULLPTR, - counter_type l = 1, - counter_type c = 1) + void initialize (std::string* fn = YY_NULLPTR, + unsigned l = 1u, + unsigned c = 1u) { filename = fn; line = l; @@ -89,40 +84,41 @@ namespace isc { namespace eval { /** \name Line and Column related manipulators ** \{ */ /// (line related) Advance to the COUNT next lines. - void lines (counter_type count = 1) + void lines (int count = 1) { if (count) { - column = 1; + column = 1u; line = add_ (line, count, 1); } } /// (column related) Advance to the COUNT next columns. - void columns (counter_type count = 1) + void columns (int count = 1) { column = add_ (column, count, 1); } /** \} */ /// File name to which this position refers. - filename_type* filename; + std::string* filename; /// Current line number. - counter_type line; + unsigned line; /// Current column number. - counter_type column; + unsigned column; private: /// Compute max (min, lhs+rhs). - static counter_type add_ (counter_type lhs, counter_type rhs, counter_type min) + static unsigned add_ (unsigned lhs, int rhs, int min) { - return lhs + rhs < min ? min : lhs + rhs; + return static_cast (std::max (min, + static_cast (lhs) + rhs)); } }; /// Add \a width columns, in place. inline position& - operator+= (position& res, position::counter_type width) + operator+= (position& res, int width) { res.columns (width); return res; @@ -130,25 +126,43 @@ namespace isc { namespace eval { /// Add \a width columns. inline position - operator+ (position res, position::counter_type width) + operator+ (position res, int width) { return res += width; } /// Subtract \a width columns, in place. inline position& - operator-= (position& res, position::counter_type width) + operator-= (position& res, int width) { return res += -width; } /// Subtract \a width columns. inline position - operator- (position res, position::counter_type width) + operator- (position res, int width) { return res -= width; } + /// Compare two position objects. + inline bool + operator== (const position& pos1, const position& pos2) + { + return (pos1.line == pos2.line + && pos1.column == pos2.column + && (pos1.filename == pos2.filename + || (pos1.filename && pos2.filename + && *pos1.filename == *pos2.filename))); + } + + /// Compare two position objects. + inline bool + operator!= (const position& pos1, const position& pos2) + { + return !(pos1 == pos2); + } + /** \brief Intercept output stream redirection. ** \param ostr the destination output stream ** \param pos a reference to the position to redirect @@ -166,10 +180,6 @@ namespace isc { namespace eval { class location { public: - /// Type for file name. - typedef position::filename_type filename_type; - /// Type for line and column numbers. - typedef position::counter_type counter_type; /// Construct a location from \a b to \a e. location (const position& b, const position& e) @@ -184,18 +194,18 @@ namespace isc { namespace eval { {} /// Construct a 0-width location in \a f, \a l, \a c. - explicit location (filename_type* f, - counter_type l = 1, - counter_type c = 1) + explicit location (std::string* f, + unsigned l = 1u, + unsigned c = 1u) : begin (f, l, c) , end (f, l, c) {} /// Initialization. - void initialize (filename_type* f = YY_NULLPTR, - counter_type l = 1, - counter_type c = 1) + void initialize (std::string* f = YY_NULLPTR, + unsigned l = 1u, + unsigned c = 1u) { begin.initialize (f, l, c); end = begin; @@ -211,13 +221,13 @@ namespace isc { namespace eval { } /// Extend the current location to the COUNT next columns. - void columns (counter_type count = 1) + void columns (int count = 1) { end += count; } /// Extend the current location to the COUNT next lines. - void lines (counter_type count = 1) + void lines (int count = 1) { end.lines (count); } @@ -232,49 +242,57 @@ namespace isc { namespace eval { }; /// Join two locations, in place. - inline location& - operator+= (location& res, const location& end) + inline location& operator+= (location& res, const location& end) { res.end = end.end; return res; } /// Join two locations. - inline location - operator+ (location res, const location& end) + inline location operator+ (location res, const location& end) { return res += end; } /// Add \a width columns to the end position, in place. - inline location& - operator+= (location& res, location::counter_type width) + inline location& operator+= (location& res, int width) { res.columns (width); return res; } /// Add \a width columns to the end position. - inline location - operator+ (location res, location::counter_type width) + inline location operator+ (location res, int width) { return res += width; } /// Subtract \a width columns to the end position, in place. - inline location& - operator-= (location& res, location::counter_type width) + inline location& operator-= (location& res, int width) { return res += -width; } /// Subtract \a width columns to the end position. - inline location - operator- (location res, location::counter_type width) + inline location operator- (location res, int width) { return res -= width; } + /// Compare two location objects. + inline bool + operator== (const location& loc1, const location& loc2) + { + return loc1.begin == loc2.begin && loc1.end == loc2.end; + } + + /// Compare two location objects. + inline bool + operator!= (const location& loc1, const location& loc2) + { + return !(loc1 == loc2); + } + /** \brief Intercept output stream redirection. ** \param ostr the destination output stream ** \param loc a reference to the location to redirect @@ -285,8 +303,7 @@ namespace isc { namespace eval { std::basic_ostream& operator<< (std::basic_ostream& ostr, const location& loc) { - location::counter_type end_col - = 0 < loc.end.column ? loc.end.column - 1 : 0; + unsigned end_col = 0 < loc.end.column ? loc.end.column - 1 : 0; ostr << loc.begin; if (loc.end.filename && (!loc.begin.filename @@ -299,8 +316,7 @@ namespace isc { namespace eval { return ostr; } -#line 14 "parser.yy" +#line 14 "parser.yy" // location.cc:339 } } // isc::eval -#line 305 "location.hh" - +#line 322 "location.hh" // location.cc:339 #endif // !YY_EVAL_LOCATION_HH_INCLUDED diff --git a/src/lib/eval/parser.cc b/src/lib/eval/parser.cc index a4d4079a32..ae942c0c37 100644 --- a/src/lib/eval/parser.cc +++ b/src/lib/eval/parser.cc @@ -1,8 +1,8 @@ -// A Bison parser, made by GNU Bison 3.8.2. +// A Bison parser, made by GNU Bison 3.3.1. // Skeleton implementation for Bison LALR(1) parsers in C++ -// Copyright (C) 2002-2015, 2018-2021 Free Software Foundation, Inc. +// Copyright (C) 2002-2015, 2018-2019 Free Software Foundation, Inc. // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -15,7 +15,7 @@ // GNU General Public License for more details. // You should have received a copy of the GNU General Public License -// along with this program. If not, see . +// along with this program. If not, see . // As a special exception, you may create a larger work that contains // part or all of the Bison parser skeleton and distribute that work @@ -30,9 +30,8 @@ // This special exception was added by the Free Software Foundation in // version 2.2 of Bison. -// DO NOT RELY ON FEATURES THAT ARE NOT DOCUMENTED in the manual, -// especially those whose name start with YY_ or yy_. They are -// private implementation details that can be changed or removed. +// Undocumented macros, especially those whose name start with YY_, +// are private implementation details. Do not rely on them. // Take the name prefix into account. @@ -44,11 +43,11 @@ // Unqualified %code blocks. -#line 33 "parser.yy" +#line 33 "parser.yy" // lalr1.cc:435 # include "eval_context.h" -#line 52 "parser.cc" +#line 51 "parser.cc" // lalr1.cc:435 #ifndef YY_ @@ -63,7 +62,6 @@ # endif #endif - // Whether we are compiled with exception support. #ifndef YY_EXCEPTIONS # if defined __GNUC__ && !defined __EXCEPTIONS @@ -94,6 +92,9 @@ # endif +// Suppress unused-variable warnings by "using" E. +#define YYUSE(E) ((void) (E)) + // Enable debugging if requested. #if EVALDEBUG @@ -119,13 +120,13 @@ # define YY_STACK_PRINT() \ do { \ if (yydebug_) \ - yy_stack_print_ (); \ + yystack_print_ (); \ } while (false) #else // !EVALDEBUG # define YYCDEBUG if (false) std::cerr -# define YY_SYMBOL_PRINT(Title, Symbol) YY_USE (Symbol) +# define YY_SYMBOL_PRINT(Title, Symbol) YYUSE (Symbol) # define YY_REDUCE_PRINT(Rule) static_cast (0) # define YY_STACK_PRINT() static_cast (0) @@ -139,17 +140,57 @@ #define YYERROR goto yyerrorlab #define YYRECOVERING() (!!yyerrstatus_) -#line 14 "parser.yy" +#line 14 "parser.yy" // lalr1.cc:510 namespace isc { namespace eval { -#line 145 "parser.cc" +#line 146 "parser.cc" // lalr1.cc:510 + + /* Return YYSTR after stripping away unnecessary quotes and + backslashes, so that it's suitable for yyerror. The heuristic is + that double-quoting is unnecessary unless the string contains an + apostrophe, a comma, or backslash (other than backslash-backslash). + YYSTR is taken from yytname. */ + std::string + EvalParser::yytnamerr_ (const char *yystr) + { + if (*yystr == '"') + { + std::string yyr; + char const *yyp = yystr; + + for (;;) + switch (*++yyp) + { + case '\'': + case ',': + goto do_not_strip_quotes; + + case '\\': + if (*++yyp != '\\') + goto do_not_strip_quotes; + else + goto append; + + append: + default: + yyr += *yyp; + break; + + case '"': + return yyr; + } + do_not_strip_quotes: ; + } + + return yystr; + } + /// Build a parser object. EvalParser::EvalParser (EvalContext& ctx_yyarg) + : #if EVALDEBUG - : yydebug_ (false), + yydebug_ (false), yycdebug_ (&std::cerr), -#else - : #endif ctx (ctx_yyarg) {} @@ -160,9 +201,9 @@ namespace isc { namespace eval { EvalParser::syntax_error::~syntax_error () YY_NOEXCEPT YY_NOTHROW {} - /*---------. - | symbol. | - `---------*/ + /*---------------. + | Symbol types. | + `---------------*/ @@ -192,13 +233,13 @@ namespace isc { namespace eval { : state (s) {} - EvalParser::symbol_kind_type - EvalParser::by_state::kind () const YY_NOEXCEPT + EvalParser::symbol_number_type + EvalParser::by_state::type_get () const YY_NOEXCEPT { if (state == empty_state) - return symbol_kind::S_YYEMPTY; + return empty_symbol; else - return YY_CAST (symbol_kind_type, yystos_[+state]); + return yystos_[state]; } EvalParser::stack_symbol_type::stack_symbol_type () @@ -207,47 +248,47 @@ namespace isc { namespace eval { EvalParser::stack_symbol_type::stack_symbol_type (YY_RVREF (stack_symbol_type) that) : super_type (YY_MOVE (that.state), YY_MOVE (that.location)) { - switch (that.kind ()) + switch (that.type_get ()) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type value.YY_MOVE_OR_COPY< TokenOption::RepresentationType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field value.YY_MOVE_OR_COPY< TokenPkt4::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field value.YY_MOVE_OR_COPY< TokenPkt6::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata value.YY_MOVE_OR_COPY< TokenPkt::MetadataType > (YY_MOVE (that.value)); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field value.YY_MOVE_OR_COPY< TokenRelay6Field::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level value.YY_MOVE_OR_COPY< int8_t > (YY_MOVE (that.value)); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" value.YY_MOVE_OR_COPY< std::string > (YY_MOVE (that.value)); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code value.YY_MOVE_OR_COPY< uint16_t > (YY_MOVE (that.value)); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id value.YY_MOVE_OR_COPY< uint32_t > (YY_MOVE (that.value)); break; @@ -264,47 +305,47 @@ namespace isc { namespace eval { EvalParser::stack_symbol_type::stack_symbol_type (state_type s, YY_MOVE_REF (symbol_type) that) : super_type (s, YY_MOVE (that.location)) { - switch (that.kind ()) + switch (that.type_get ()) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type value.move< TokenOption::RepresentationType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field value.move< TokenPkt4::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field value.move< TokenPkt6::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata value.move< TokenPkt::MetadataType > (YY_MOVE (that.value)); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field value.move< TokenRelay6Field::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level value.move< int8_t > (YY_MOVE (that.value)); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" value.move< std::string > (YY_MOVE (that.value)); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code value.move< uint16_t > (YY_MOVE (that.value)); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id value.move< uint32_t > (YY_MOVE (that.value)); break; @@ -313,111 +354,55 @@ namespace isc { namespace eval { } // that is emptied. - that.kind_ = symbol_kind::S_YYEMPTY; + that.type = empty_symbol; } #if YY_CPLUSPLUS < 201103L - EvalParser::stack_symbol_type& - EvalParser::stack_symbol_type::operator= (const stack_symbol_type& that) - { - state = that.state; - switch (that.kind ()) - { - case symbol_kind::S_option_repr_type: // option_repr_type - value.copy< TokenOption::RepresentationType > (that.value); - break; - - case symbol_kind::S_pkt4_field: // pkt4_field - value.copy< TokenPkt4::FieldType > (that.value); - break; - - case symbol_kind::S_pkt6_field: // pkt6_field - value.copy< TokenPkt6::FieldType > (that.value); - break; - - case symbol_kind::S_pkt_metadata: // pkt_metadata - value.copy< TokenPkt::MetadataType > (that.value); - break; - - case symbol_kind::S_relay6_field: // relay6_field - value.copy< TokenRelay6Field::FieldType > (that.value); - break; - - case symbol_kind::S_nest_level: // nest_level - value.copy< int8_t > (that.value); - break; - - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" - value.copy< std::string > (that.value); - break; - - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code - value.copy< uint16_t > (that.value); - break; - - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id - value.copy< uint32_t > (that.value); - break; - - default: - break; - } - - location = that.location; - return *this; - } - EvalParser::stack_symbol_type& EvalParser::stack_symbol_type::operator= (stack_symbol_type& that) { state = that.state; - switch (that.kind ()) + switch (that.type_get ()) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type value.move< TokenOption::RepresentationType > (that.value); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field value.move< TokenPkt4::FieldType > (that.value); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field value.move< TokenPkt6::FieldType > (that.value); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata value.move< TokenPkt::MetadataType > (that.value); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field value.move< TokenRelay6Field::FieldType > (that.value); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level value.move< int8_t > (that.value); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" value.move< std::string > (that.value); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code value.move< uint16_t > (that.value); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id value.move< uint32_t > (that.value); break; @@ -443,115 +428,117 @@ namespace isc { namespace eval { #if EVALDEBUG template void - EvalParser::yy_print_ (std::ostream& yyo, const basic_symbol& yysym) const + EvalParser::yy_print_ (std::ostream& yyo, + const basic_symbol& yysym) const { std::ostream& yyoutput = yyo; - YY_USE (yyoutput); + YYUSE (yyoutput); + symbol_number_type yytype = yysym.type_get (); +#if defined __GNUC__ && ! defined __clang__ && ! defined __ICC && __GNUC__ * 100 + __GNUC_MINOR__ <= 408 + // Avoid a (spurious) G++ 4.8 warning about "array subscript is + // below array bounds". if (yysym.empty ()) - yyo << "empty symbol"; - else - { - symbol_kind_type yykind = yysym.kind (); - yyo << (yykind < YYNTOKENS ? "token" : "nterm") - << ' ' << yysym.name () << " (" - << yysym.location << ": "; - switch (yykind) - { - case symbol_kind::S_STRING: // "constant string" -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < std::string > (); } -#line 464 "parser.cc" + std::abort (); +#endif + yyo << (yytype < yyntokens_ ? "token" : "nterm") + << ' ' << yytname_[yytype] << " (" + << yysym.location << ": "; + switch (yytype) + { + case 59: // "constant string" +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < std::string > (); } +#line 452 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_INTEGER: // "integer" -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < std::string > (); } -#line 470 "parser.cc" + case 60: // "integer" +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < std::string > (); } +#line 458 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_HEXSTRING: // "constant hexstring" -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < std::string > (); } -#line 476 "parser.cc" + case 61: // "constant hexstring" +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < std::string > (); } +#line 464 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_OPTION_NAME: // "option name" -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < std::string > (); } -#line 482 "parser.cc" + case 62: // "option name" +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < std::string > (); } +#line 470 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_IP_ADDRESS: // "ip address" -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < std::string > (); } -#line 488 "parser.cc" + case 63: // "ip address" +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < std::string > (); } +#line 476 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_integer_expr: // integer_expr -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < uint32_t > (); } -#line 494 "parser.cc" + case 69: // integer_expr +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < uint32_t > (); } +#line 482 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_option_code: // option_code -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < uint16_t > (); } -#line 500 "parser.cc" + case 70: // option_code +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < uint16_t > (); } +#line 488 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_sub_option_code: // sub_option_code -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < uint16_t > (); } -#line 506 "parser.cc" + case 71: // sub_option_code +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < uint16_t > (); } +#line 494 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_option_repr_type: // option_repr_type -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < TokenOption::RepresentationType > (); } -#line 512 "parser.cc" + case 72: // option_repr_type +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < TokenOption::RepresentationType > (); } +#line 500 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_nest_level: // nest_level -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < int8_t > (); } -#line 518 "parser.cc" + case 73: // nest_level +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < int8_t > (); } +#line 506 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_pkt_metadata: // pkt_metadata -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < TokenPkt::MetadataType > (); } -#line 524 "parser.cc" + case 74: // pkt_metadata +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < TokenPkt::MetadataType > (); } +#line 512 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_enterprise_id: // enterprise_id -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < uint32_t > (); } -#line 530 "parser.cc" + case 75: // enterprise_id +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < uint32_t > (); } +#line 518 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_pkt4_field: // pkt4_field -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < TokenPkt4::FieldType > (); } -#line 536 "parser.cc" + case 76: // pkt4_field +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < TokenPkt4::FieldType > (); } +#line 524 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_pkt6_field: // pkt6_field -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < TokenPkt6::FieldType > (); } -#line 542 "parser.cc" + case 77: // pkt6_field +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < TokenPkt6::FieldType > (); } +#line 530 "parser.cc" // lalr1.cc:676 break; - case symbol_kind::S_relay6_field: // relay6_field -#line 121 "parser.yy" - { yyoutput << yysym.value.template as < TokenRelay6Field::FieldType > (); } -#line 548 "parser.cc" + case 78: // relay6_field +#line 122 "parser.yy" // lalr1.cc:676 + { yyoutput << yysym.value.template as < TokenRelay6Field::FieldType > (); } +#line 536 "parser.cc" // lalr1.cc:676 break; default: break; } - yyo << ')'; - } + yyo << ')'; } #endif @@ -575,7 +562,7 @@ namespace isc { namespace eval { } void - EvalParser::yypop_ (int n) YY_NOEXCEPT + EvalParser::yypop_ (int n) { yystack_.pop (n); } @@ -610,21 +597,21 @@ namespace isc { namespace eval { EvalParser::state_type EvalParser::yy_lr_goto_state_ (state_type yystate, int yysym) { - int yyr = yypgoto_[yysym - YYNTOKENS] + yystate; + int yyr = yypgoto_[yysym - yyntokens_] + yystate; if (0 <= yyr && yyr <= yylast_ && yycheck_[yyr] == yystate) return yytable_[yyr]; else - return yydefgoto_[yysym - YYNTOKENS]; + return yydefgoto_[yysym - yyntokens_]; } bool - EvalParser::yy_pact_value_is_default_ (int yyvalue) YY_NOEXCEPT + EvalParser::yy_pact_value_is_default_ (int yyvalue) { return yyvalue == yypact_ninf_; } bool - EvalParser::yy_table_value_is_error_ (int yyvalue) YY_NOEXCEPT + EvalParser::yy_table_value_is_error_ (int yyvalue) { return yyvalue == yytable_ninf_; } @@ -638,6 +625,7 @@ namespace isc { namespace eval { int EvalParser::parse () { + // State. int yyn; /// Length of the RHS of the rule being reduced. int yylen = 0; @@ -673,8 +661,7 @@ namespace isc { namespace eval { | yynewstate -- push a new symbol on the stack. | `-----------------------------------------------*/ yynewstate: - YYCDEBUG << "Entering state " << int (yystack_[0].state) << '\n'; - YY_STACK_PRINT (); + YYCDEBUG << "Entering state " << yystack_[0].state << '\n'; // Accept? if (yystack_[0].state == yyfinal_) @@ -688,14 +675,14 @@ namespace isc { namespace eval { `-----------*/ yybackup: // Try to take a decision without lookahead. - yyn = yypact_[+yystack_[0].state]; + yyn = yypact_[yystack_[0].state]; if (yy_pact_value_is_default_ (yyn)) goto yydefault; // Read a lookahead token. if (yyla.empty ()) { - YYCDEBUG << "Reading a token\n"; + YYCDEBUG << "Reading a token: "; #if YY_EXCEPTIONS try #endif // YY_EXCEPTIONS @@ -714,23 +701,11 @@ namespace isc { namespace eval { } YY_SYMBOL_PRINT ("Next token is", yyla); - if (yyla.kind () == symbol_kind::S_YYerror) - { - // The scanner already issued an error message, process directly - // to error recovery. But do not keep the error token as - // lookahead, it is too special and may lead us to an endless - // loop in error recovery. */ - yyla.kind_ = symbol_kind::S_YYUNDEF; - goto yyerrlab1; - } - /* If the proper action on seeing token YYLA.TYPE is to reduce or to detect an error, take that action. */ - yyn += yyla.kind (); - if (yyn < 0 || yylast_ < yyn || yycheck_[yyn] != yyla.kind ()) - { - goto yydefault; - } + yyn += yyla.type_get (); + if (yyn < 0 || yylast_ < yyn || yycheck_[yyn] != yyla.type_get ()) + goto yydefault; // Reduce or error. yyn = yytable_[yyn]; @@ -747,7 +722,7 @@ namespace isc { namespace eval { --yyerrstatus_; // Shift the lookahead token. - yypush_ ("Shifting", state_type (yyn), YY_MOVE (yyla)); + yypush_ ("Shifting", yyn, YY_MOVE (yyla)); goto yynewstate; @@ -755,7 +730,7 @@ namespace isc { namespace eval { | yydefault -- do the default action for the current state. | `-----------------------------------------------------------*/ yydefault: - yyn = yydefact_[+yystack_[0].state]; + yyn = yydefact_[yystack_[0].state]; if (yyn == 0) goto yyerrlab; goto yyreduce; @@ -774,45 +749,45 @@ namespace isc { namespace eval { when using variants. */ switch (yyr1_[yyn]) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type yylhs.value.emplace< TokenOption::RepresentationType > (); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field yylhs.value.emplace< TokenPkt4::FieldType > (); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field yylhs.value.emplace< TokenPkt6::FieldType > (); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata yylhs.value.emplace< TokenPkt::MetadataType > (); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field yylhs.value.emplace< TokenRelay6Field::FieldType > (); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level yylhs.value.emplace< int8_t > (); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" yylhs.value.emplace< std::string > (); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code yylhs.value.emplace< uint16_t > (); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id yylhs.value.emplace< uint32_t > (); break; @@ -836,63 +811,63 @@ namespace isc { namespace eval { { switch (yyn) { - case 6: // bool_expr: "not" bool_expr -#line 141 "parser.yy" - { + case 6: +#line 142 "parser.yy" // lalr1.cc:919 + { TokenPtr neg(new TokenNot()); ctx.expression.push_back(neg); } -#line 846 "parser.cc" +#line 821 "parser.cc" // lalr1.cc:919 break; - case 7: // bool_expr: bool_expr "and" bool_expr -#line 146 "parser.yy" - { + case 7: +#line 147 "parser.yy" // lalr1.cc:919 + { TokenPtr neg(new TokenAnd()); ctx.expression.push_back(neg); } -#line 855 "parser.cc" +#line 830 "parser.cc" // lalr1.cc:919 break; - case 8: // bool_expr: bool_expr "or" bool_expr -#line 151 "parser.yy" - { + case 8: +#line 152 "parser.yy" // lalr1.cc:919 + { TokenPtr neg(new TokenOr()); ctx.expression.push_back(neg); } -#line 864 "parser.cc" +#line 839 "parser.cc" // lalr1.cc:919 break; - case 9: // bool_expr: string_expr "==" string_expr -#line 156 "parser.yy" - { + case 9: +#line 157 "parser.yy" // lalr1.cc:919 + { TokenPtr eq(new TokenEqual()); ctx.expression.push_back(eq); } -#line 873 "parser.cc" +#line 848 "parser.cc" // lalr1.cc:919 break; - case 10: // bool_expr: "option" "[" option_code "]" "." "exists" -#line 161 "parser.yy" - { + case 10: +#line 162 "parser.yy" // lalr1.cc:919 + { TokenPtr opt(new TokenOption(yystack_[3].value.as < uint16_t > (), TokenOption::EXISTS)); ctx.expression.push_back(opt); } -#line 882 "parser.cc" +#line 857 "parser.cc" // lalr1.cc:919 break; - case 11: // bool_expr: "option" "[" option_code "]" "." "option" "[" sub_option_code "]" "." "exists" -#line 166 "parser.yy" - { + case 11: +#line 167 "parser.yy" // lalr1.cc:919 + { TokenPtr opt(new TokenSubOption(yystack_[8].value.as < uint16_t > (), yystack_[3].value.as < uint16_t > (), TokenOption::EXISTS)); ctx.expression.push_back(opt); } -#line 891 "parser.cc" +#line 866 "parser.cc" // lalr1.cc:919 break; - case 12: // bool_expr: "relay4" "[" sub_option_code "]" "." "exists" -#line 171 "parser.yy" - { + case 12: +#line 172 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V4: { @@ -911,12 +886,12 @@ namespace isc { namespace eval { error(yystack_[5].location, "relay4 can only be used in DHCPv4."); } } -#line 915 "parser.cc" +#line 890 "parser.cc" // lalr1.cc:919 break; - case 13: // bool_expr: "relay6" "[" nest_level "]" "." "option" "[" sub_option_code "]" "." "exists" -#line 191 "parser.yy" - { + case 13: +#line 192 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V6: { @@ -929,12 +904,12 @@ namespace isc { namespace eval { error(yystack_[10].location, "relay6 can only be used in DHCPv6."); } } -#line 933 "parser.cc" +#line 908 "parser.cc" // lalr1.cc:919 break; - case 14: // bool_expr: "vendor-class" "[" enterprise_id "]" "." "exists" -#line 205 "parser.yy" - { + case 14: +#line 206 "parser.yy" // lalr1.cc:919 + { // Expression: vendor-class[1234].exists // // This token will find option 124 (DHCPv4) or 16 (DHCPv6), @@ -942,12 +917,12 @@ namespace isc { namespace eval { TokenPtr exist(new TokenVendorClass(ctx.getUniverse(), yystack_[3].value.as < uint32_t > (), TokenOption::EXISTS)); ctx.expression.push_back(exist); } -#line 946 "parser.cc" +#line 921 "parser.cc" // lalr1.cc:919 break; - case 15: // bool_expr: "vendor" "[" enterprise_id "]" "." "exists" -#line 214 "parser.yy" - { + case 15: +#line 215 "parser.yy" // lalr1.cc:919 + { // Expression: vendor[1234].exists // // This token will find option 125 (DHCPv4) or 17 (DHCPv6), @@ -955,12 +930,12 @@ namespace isc { namespace eval { TokenPtr exist(new TokenVendor(ctx.getUniverse(), yystack_[3].value.as < uint32_t > (), TokenOption::EXISTS)); ctx.expression.push_back(exist); } -#line 959 "parser.cc" +#line 934 "parser.cc" // lalr1.cc:919 break; - case 16: // bool_expr: "vendor" "[" enterprise_id "]" "." "option" "[" sub_option_code "]" "." "exists" -#line 223 "parser.yy" - { + case 16: +#line 224 "parser.yy" // lalr1.cc:919 + { // Expression vendor[1234].option[123].exists // // This token will check if specified vendor option @@ -969,12 +944,12 @@ namespace isc { namespace eval { TokenPtr exist(new TokenVendor(ctx.getUniverse(), yystack_[8].value.as < uint32_t > (), TokenOption::EXISTS, yystack_[3].value.as < uint16_t > ())); ctx.expression.push_back(exist); } -#line 973 "parser.cc" +#line 948 "parser.cc" // lalr1.cc:919 break; - case 17: // bool_expr: "member" "(" "constant string" ")" -#line 233 "parser.yy" - { + case 17: +#line 234 "parser.yy" // lalr1.cc:919 + { // Expression member('foo') // // This token will check if the packet is a member of @@ -988,57 +963,57 @@ namespace isc { namespace eval { TokenPtr member(new TokenMember(cc)); ctx.expression.push_back(member); } -#line 992 "parser.cc" +#line 967 "parser.cc" // lalr1.cc:919 break; - case 18: // string_expr: "constant string" -#line 250 "parser.yy" - { + case 18: +#line 251 "parser.yy" // lalr1.cc:919 + { TokenPtr str(new TokenString(yystack_[0].value.as < std::string > ())); ctx.expression.push_back(str); } -#line 1001 "parser.cc" +#line 976 "parser.cc" // lalr1.cc:919 break; - case 19: // string_expr: "constant hexstring" -#line 255 "parser.yy" - { + case 19: +#line 256 "parser.yy" // lalr1.cc:919 + { TokenPtr hex(new TokenHexString(yystack_[0].value.as < std::string > ())); ctx.expression.push_back(hex); } -#line 1010 "parser.cc" +#line 985 "parser.cc" // lalr1.cc:919 break; - case 20: // string_expr: "ip address" -#line 260 "parser.yy" - { + case 20: +#line 261 "parser.yy" // lalr1.cc:919 + { TokenPtr ip(new TokenIpAddress(yystack_[0].value.as < std::string > ())); ctx.expression.push_back(ip); } -#line 1019 "parser.cc" +#line 994 "parser.cc" // lalr1.cc:919 break; - case 21: // string_expr: "option" "[" option_code "]" "." option_repr_type -#line 265 "parser.yy" - { + case 21: +#line 266 "parser.yy" // lalr1.cc:919 + { TokenPtr opt(new TokenOption(yystack_[3].value.as < uint16_t > (), yystack_[0].value.as < TokenOption::RepresentationType > ())); ctx.expression.push_back(opt); } -#line 1028 "parser.cc" +#line 1003 "parser.cc" // lalr1.cc:919 break; - case 22: // string_expr: "option" "[" option_code "]" "." "option" "[" sub_option_code "]" "." option_repr_type -#line 270 "parser.yy" - { + case 22: +#line 271 "parser.yy" // lalr1.cc:919 + { TokenPtr opt(new TokenSubOption(yystack_[8].value.as < uint16_t > (), yystack_[3].value.as < uint16_t > (), yystack_[0].value.as < TokenOption::RepresentationType > ())); ctx.expression.push_back(opt); } -#line 1037 "parser.cc" +#line 1012 "parser.cc" // lalr1.cc:919 break; - case 23: // string_expr: "relay4" "[" sub_option_code "]" "." option_repr_type -#line 275 "parser.yy" - { + case 23: +#line 276 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V4: { @@ -1057,12 +1032,12 @@ namespace isc { namespace eval { error(yystack_[5].location, "relay4 can only be used in DHCPv4."); } } -#line 1061 "parser.cc" +#line 1036 "parser.cc" // lalr1.cc:919 break; - case 24: // string_expr: "relay6" "[" nest_level "]" "." "option" "[" sub_option_code "]" "." option_repr_type -#line 296 "parser.yy" - { + case 24: +#line 297 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V6: { @@ -1075,21 +1050,21 @@ namespace isc { namespace eval { error(yystack_[10].location, "relay6 can only be used in DHCPv6."); } } -#line 1079 "parser.cc" +#line 1054 "parser.cc" // lalr1.cc:919 break; - case 25: // string_expr: "pkt" "." pkt_metadata -#line 311 "parser.yy" - { + case 25: +#line 312 "parser.yy" // lalr1.cc:919 + { TokenPtr pkt_metadata(new TokenPkt(yystack_[0].value.as < TokenPkt::MetadataType > ())); ctx.expression.push_back(pkt_metadata); } -#line 1088 "parser.cc" +#line 1063 "parser.cc" // lalr1.cc:919 break; - case 26: // string_expr: "pkt4" "." pkt4_field -#line 316 "parser.yy" - { + case 26: +#line 317 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V4: { @@ -1102,12 +1077,12 @@ namespace isc { namespace eval { error(yystack_[2].location, "pkt4 can only be used in DHCPv4."); } } -#line 1106 "parser.cc" +#line 1081 "parser.cc" // lalr1.cc:919 break; - case 27: // string_expr: "pkt6" "." pkt6_field -#line 330 "parser.yy" - { + case 27: +#line 331 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V6: { @@ -1120,12 +1095,12 @@ namespace isc { namespace eval { error(yystack_[2].location, "pkt6 can only be used in DHCPv6."); } } -#line 1124 "parser.cc" +#line 1099 "parser.cc" // lalr1.cc:919 break; - case 28: // string_expr: "relay6" "[" nest_level "]" "." relay6_field -#line 344 "parser.yy" - { + case 28: +#line 345 "parser.yy" // lalr1.cc:919 + { switch (ctx.getUniverse()) { case Option::V6: { @@ -1138,120 +1113,129 @@ namespace isc { namespace eval { error(yystack_[5].location, "relay6 can only be used in DHCPv6."); } } -#line 1142 "parser.cc" +#line 1117 "parser.cc" // lalr1.cc:919 break; - case 29: // string_expr: "substring" "(" string_expr "," start_expr "," length_expr ")" -#line 359 "parser.yy" - { + case 29: +#line 360 "parser.yy" // lalr1.cc:919 + { TokenPtr sub(new TokenSubstring()); ctx.expression.push_back(sub); } -#line 1151 "parser.cc" +#line 1126 "parser.cc" // lalr1.cc:919 + break; + + case 30: +#line 365 "parser.yy" // lalr1.cc:919 + { + TokenPtr split(new TokenSplit()); + ctx.expression.push_back(split); + } +#line 1135 "parser.cc" // lalr1.cc:919 break; - case 30: // string_expr: "concat" "(" string_expr "," string_expr ")" -#line 364 "parser.yy" - { + case 31: +#line 370 "parser.yy" // lalr1.cc:919 + { TokenPtr conc(new TokenConcat()); ctx.expression.push_back(conc); } -#line 1160 "parser.cc" +#line 1144 "parser.cc" // lalr1.cc:919 break; - case 31: // string_expr: string_expr "+" string_expr -#line 369 "parser.yy" - { + case 32: +#line 375 "parser.yy" // lalr1.cc:919 + { TokenPtr conc(new TokenConcat()); ctx.expression.push_back(conc); } -#line 1169 "parser.cc" +#line 1153 "parser.cc" // lalr1.cc:919 break; - case 32: // string_expr: "ifelse" "(" bool_expr "," string_expr "," string_expr ")" -#line 374 "parser.yy" - { + case 33: +#line 380 "parser.yy" // lalr1.cc:919 + { TokenPtr cond(new TokenIfElse()); ctx.expression.push_back(cond); } -#line 1178 "parser.cc" +#line 1162 "parser.cc" // lalr1.cc:919 break; - case 33: // string_expr: "hexstring" "(" string_expr "," string_expr ")" -#line 379 "parser.yy" - { + case 34: +#line 385 "parser.yy" // lalr1.cc:919 + { TokenPtr tohex(new TokenToHexString()); ctx.expression.push_back(tohex); } -#line 1187 "parser.cc" +#line 1171 "parser.cc" // lalr1.cc:919 break; - case 34: // string_expr: "addrtotext" "(" string_expr ")" -#line 384 "parser.yy" - { + case 35: +#line 390 "parser.yy" // lalr1.cc:919 + { TokenPtr addrtotext(new TokenIpAddressToText()); ctx.expression.push_back(addrtotext); } -#line 1196 "parser.cc" +#line 1180 "parser.cc" // lalr1.cc:919 break; - case 35: // string_expr: "int8totext" "(" string_expr ")" -#line 389 "parser.yy" - { + case 36: +#line 395 "parser.yy" // lalr1.cc:919 + { TokenPtr int8totext(new TokenInt8ToText()); ctx.expression.push_back(int8totext); } -#line 1205 "parser.cc" +#line 1189 "parser.cc" // lalr1.cc:919 break; - case 36: // string_expr: "int16totext" "(" string_expr ")" -#line 394 "parser.yy" - { + case 37: +#line 400 "parser.yy" // lalr1.cc:919 + { TokenPtr int16totext(new TokenInt16ToText()); ctx.expression.push_back(int16totext); } -#line 1214 "parser.cc" +#line 1198 "parser.cc" // lalr1.cc:919 break; - case 37: // string_expr: "int32totext" "(" string_expr ")" -#line 399 "parser.yy" - { + case 38: +#line 405 "parser.yy" // lalr1.cc:919 + { TokenPtr int32totext(new TokenInt32ToText()); ctx.expression.push_back(int32totext); } -#line 1223 "parser.cc" +#line 1207 "parser.cc" // lalr1.cc:919 break; - case 38: // string_expr: "uint8totext" "(" string_expr ")" -#line 404 "parser.yy" - { + case 39: +#line 410 "parser.yy" // lalr1.cc:919 + { TokenPtr uint8totext(new TokenUInt8ToText()); ctx.expression.push_back(uint8totext); } -#line 1232 "parser.cc" +#line 1216 "parser.cc" // lalr1.cc:919 break; - case 39: // string_expr: "uint16totext" "(" string_expr ")" -#line 409 "parser.yy" - { + case 40: +#line 415 "parser.yy" // lalr1.cc:919 + { TokenPtr uint16totext(new TokenUInt16ToText()); ctx.expression.push_back(uint16totext); } -#line 1241 "parser.cc" +#line 1225 "parser.cc" // lalr1.cc:919 break; - case 40: // string_expr: "uint32totext" "(" string_expr ")" -#line 414 "parser.yy" - { + case 41: +#line 420 "parser.yy" // lalr1.cc:919 + { TokenPtr uint32totext(new TokenUInt32ToText()); ctx.expression.push_back(uint32totext); } -#line 1250 "parser.cc" +#line 1234 "parser.cc" // lalr1.cc:919 break; - case 41: // string_expr: "vendor" "." "enterprise" -#line 419 "parser.yy" - { + case 42: +#line 425 "parser.yy" // lalr1.cc:919 + { // expression: vendor.enterprise // // This token will return enterprise-id number of @@ -1259,12 +1243,12 @@ namespace isc { namespace eval { TokenPtr vendor(new TokenVendor(ctx.getUniverse(), 0, TokenVendor::ENTERPRISE_ID)); ctx.expression.push_back(vendor); } -#line 1263 "parser.cc" +#line 1247 "parser.cc" // lalr1.cc:919 break; - case 42: // string_expr: "vendor-class" "." "enterprise" -#line 428 "parser.yy" - { + case 43: +#line 434 "parser.yy" // lalr1.cc:919 + { // expression: vendor-class.enterprise // // This token will return enterprise-id number of @@ -1273,12 +1257,12 @@ namespace isc { namespace eval { TokenVendor::ENTERPRISE_ID)); ctx.expression.push_back(vendor); } -#line 1277 "parser.cc" +#line 1261 "parser.cc" // lalr1.cc:919 break; - case 43: // string_expr: "vendor" "[" enterprise_id "]" "." "option" "[" sub_option_code "]" "." option_repr_type -#line 438 "parser.yy" - { + case 44: +#line 444 "parser.yy" // lalr1.cc:919 + { // This token will search for vendor option with // specified enterprise-id. If found, will search // for specified suboption and finally will return @@ -1286,12 +1270,12 @@ namespace isc { namespace eval { TokenPtr opt(new TokenVendor(ctx.getUniverse(), yystack_[8].value.as < uint32_t > (), yystack_[0].value.as < TokenOption::RepresentationType > (), yystack_[3].value.as < uint16_t > ())); ctx.expression.push_back(opt); } -#line 1290 "parser.cc" +#line 1274 "parser.cc" // lalr1.cc:919 break; - case 44: // string_expr: "vendor-class" "[" enterprise_id "]" "." "data" -#line 447 "parser.yy" - { + case 45: +#line 453 "parser.yy" // lalr1.cc:919 + { // expression: vendor-class[1234].data // // Vendor class option does not have suboptions, @@ -1303,12 +1287,12 @@ namespace isc { namespace eval { TokenVendor::DATA, 0)); ctx.expression.push_back(vendor_class); } -#line 1307 "parser.cc" +#line 1291 "parser.cc" // lalr1.cc:919 break; - case 45: // string_expr: "vendor-class" "[" enterprise_id "]" "." "data" "[" "integer" "]" -#line 460 "parser.yy" - { + case 46: +#line 466 "parser.yy" // lalr1.cc:919 + { // expression: vendor-class[1234].data[5] // // Vendor class option does not have suboptions, @@ -1320,256 +1304,264 @@ namespace isc { namespace eval { TokenVendor::DATA, index)); ctx.expression.push_back(vendor_class); } -#line 1324 "parser.cc" +#line 1308 "parser.cc" // lalr1.cc:919 break; - case 46: // string_expr: integer_expr -#line 473 "parser.yy" - { + case 47: +#line 479 "parser.yy" // lalr1.cc:919 + { TokenPtr integer(new TokenInteger(yystack_[0].value.as < uint32_t > ())); ctx.expression.push_back(integer); } -#line 1333 "parser.cc" +#line 1317 "parser.cc" // lalr1.cc:919 break; - case 48: // integer_expr: "integer" -#line 481 "parser.yy" - { + case 49: +#line 487 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < uint32_t > () = ctx.convertUint32(yystack_[0].value.as < std::string > (), yystack_[0].location); } -#line 1341 "parser.cc" +#line 1325 "parser.cc" // lalr1.cc:919 break; - case 49: // option_code: "integer" -#line 487 "parser.yy" - { + case 50: +#line 493 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < uint16_t > () = ctx.convertOptionCode(yystack_[0].value.as < std::string > (), yystack_[0].location); } -#line 1349 "parser.cc" +#line 1333 "parser.cc" // lalr1.cc:919 break; - case 50: // option_code: "option name" -#line 491 "parser.yy" - { + case 51: +#line 497 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < uint16_t > () = ctx.convertOptionName(yystack_[0].value.as < std::string > (), yystack_[0].location); } -#line 1357 "parser.cc" +#line 1341 "parser.cc" // lalr1.cc:919 break; - case 51: // sub_option_code: "integer" -#line 497 "parser.yy" - { + case 52: +#line 503 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < uint16_t > () = ctx.convertOptionCode(yystack_[0].value.as < std::string > (), yystack_[0].location); } -#line 1365 "parser.cc" +#line 1349 "parser.cc" // lalr1.cc:919 break; - case 52: // option_repr_type: "text" -#line 503 "parser.yy" - { + case 53: +#line 509 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenOption::RepresentationType > () = TokenOption::TEXTUAL; } -#line 1373 "parser.cc" +#line 1357 "parser.cc" // lalr1.cc:919 break; - case 53: // option_repr_type: "hex" -#line 507 "parser.yy" - { + case 54: +#line 513 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenOption::RepresentationType > () = TokenOption::HEXADECIMAL; } -#line 1381 "parser.cc" +#line 1365 "parser.cc" // lalr1.cc:919 break; - case 54: // nest_level: "integer" -#line 513 "parser.yy" - { + case 55: +#line 519 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < int8_t > () = ctx.convertNestLevelNumber(yystack_[0].value.as < std::string > (), yystack_[0].location); } -#line 1389 "parser.cc" +#line 1373 "parser.cc" // lalr1.cc:919 break; - case 55: // pkt_metadata: "iface" -#line 522 "parser.yy" - { + case 56: +#line 528 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt::MetadataType > () = TokenPkt::IFACE; } -#line 1397 "parser.cc" +#line 1381 "parser.cc" // lalr1.cc:919 break; - case 56: // pkt_metadata: "src" -#line 526 "parser.yy" - { + case 57: +#line 532 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt::MetadataType > () = TokenPkt::SRC; } -#line 1405 "parser.cc" +#line 1389 "parser.cc" // lalr1.cc:919 break; - case 57: // pkt_metadata: "dst" -#line 530 "parser.yy" - { + case 58: +#line 536 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt::MetadataType > () = TokenPkt::DST; } -#line 1413 "parser.cc" +#line 1397 "parser.cc" // lalr1.cc:919 break; - case 58: // pkt_metadata: "len" -#line 534 "parser.yy" - { + case 59: +#line 540 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt::MetadataType > () = TokenPkt::LEN; } -#line 1421 "parser.cc" +#line 1405 "parser.cc" // lalr1.cc:919 break; - case 59: // enterprise_id: "integer" -#line 540 "parser.yy" - { + case 60: +#line 546 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < uint32_t > () = ctx.convertUint32(yystack_[0].value.as < std::string > (), yystack_[0].location); } -#line 1429 "parser.cc" +#line 1413 "parser.cc" // lalr1.cc:919 break; - case 60: // enterprise_id: "*" -#line 544 "parser.yy" - { + case 61: +#line 550 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < uint32_t > () = 0; } -#line 1437 "parser.cc" +#line 1421 "parser.cc" // lalr1.cc:919 break; - case 61: // pkt4_field: "mac" -#line 550 "parser.yy" - { + case 62: +#line 556 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::CHADDR; } -#line 1445 "parser.cc" +#line 1429 "parser.cc" // lalr1.cc:919 break; - case 62: // pkt4_field: "hlen" -#line 554 "parser.yy" - { + case 63: +#line 560 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::HLEN; } -#line 1453 "parser.cc" +#line 1437 "parser.cc" // lalr1.cc:919 break; - case 63: // pkt4_field: "htype" -#line 558 "parser.yy" - { + case 64: +#line 564 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::HTYPE; } -#line 1461 "parser.cc" +#line 1445 "parser.cc" // lalr1.cc:919 break; - case 64: // pkt4_field: "ciaddr" -#line 562 "parser.yy" - { + case 65: +#line 568 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::CIADDR; } -#line 1469 "parser.cc" +#line 1453 "parser.cc" // lalr1.cc:919 break; - case 65: // pkt4_field: "giaddr" -#line 566 "parser.yy" - { + case 66: +#line 572 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::GIADDR; } -#line 1477 "parser.cc" +#line 1461 "parser.cc" // lalr1.cc:919 break; - case 66: // pkt4_field: "yiaddr" -#line 570 "parser.yy" - { + case 67: +#line 576 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::YIADDR; } -#line 1485 "parser.cc" +#line 1469 "parser.cc" // lalr1.cc:919 break; - case 67: // pkt4_field: "siaddr" -#line 574 "parser.yy" - { + case 68: +#line 580 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::SIADDR; } -#line 1493 "parser.cc" +#line 1477 "parser.cc" // lalr1.cc:919 break; - case 68: // pkt4_field: "msgtype" -#line 578 "parser.yy" - { + case 69: +#line 584 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::MSGTYPE; } -#line 1501 "parser.cc" +#line 1485 "parser.cc" // lalr1.cc:919 break; - case 69: // pkt4_field: "transid" -#line 582 "parser.yy" - { + case 70: +#line 588 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt4::FieldType > () = TokenPkt4::TRANSID; } -#line 1509 "parser.cc" +#line 1493 "parser.cc" // lalr1.cc:919 break; - case 70: // pkt6_field: "msgtype" -#line 588 "parser.yy" - { + case 71: +#line 594 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt6::FieldType > () = TokenPkt6::MSGTYPE; } -#line 1517 "parser.cc" +#line 1501 "parser.cc" // lalr1.cc:919 break; - case 71: // pkt6_field: "transid" -#line 592 "parser.yy" - { + case 72: +#line 598 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenPkt6::FieldType > () = TokenPkt6::TRANSID; } -#line 1525 "parser.cc" +#line 1509 "parser.cc" // lalr1.cc:919 break; - case 72: // relay6_field: "peeraddr" -#line 598 "parser.yy" - { + case 73: +#line 604 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenRelay6Field::FieldType > () = TokenRelay6Field::PEERADDR; } -#line 1533 "parser.cc" +#line 1517 "parser.cc" // lalr1.cc:919 break; - case 73: // relay6_field: "linkaddr" -#line 602 "parser.yy" - { + case 74: +#line 608 "parser.yy" // lalr1.cc:919 + { yylhs.value.as < TokenRelay6Field::FieldType > () = TokenRelay6Field::LINKADDR; } -#line 1541 "parser.cc" +#line 1525 "parser.cc" // lalr1.cc:919 break; - case 74: // start_expr: "integer" -#line 608 "parser.yy" - { + case 75: +#line 614 "parser.yy" // lalr1.cc:919 + { TokenPtr str(new TokenString(yystack_[0].value.as < std::string > ())); ctx.expression.push_back(str); } -#line 1550 "parser.cc" +#line 1534 "parser.cc" // lalr1.cc:919 break; - case 75: // length_expr: "integer" -#line 615 "parser.yy" - { + case 76: +#line 621 "parser.yy" // lalr1.cc:919 + { TokenPtr str(new TokenString(yystack_[0].value.as < std::string > ())); ctx.expression.push_back(str); } -#line 1559 "parser.cc" +#line 1543 "parser.cc" // lalr1.cc:919 break; - case 76: // length_expr: "all" -#line 620 "parser.yy" - { + case 77: +#line 626 "parser.yy" // lalr1.cc:919 + { TokenPtr str(new TokenString("all")); ctx.expression.push_back(str); } -#line 1568 "parser.cc" +#line 1552 "parser.cc" // lalr1.cc:919 break; + case 78: +#line 632 "parser.yy" // lalr1.cc:919 + { + TokenPtr str(new TokenString(yystack_[0].value.as < std::string > ())); + ctx.expression.push_back(str); + } +#line 1561 "parser.cc" // lalr1.cc:919 + break; -#line 1572 "parser.cc" +#line 1565 "parser.cc" // lalr1.cc:919 default: break; } @@ -1585,6 +1577,7 @@ namespace isc { namespace eval { YY_SYMBOL_PRINT ("-> $$ =", yylhs); yypop_ (yylen); yylen = 0; + YY_STACK_PRINT (); // Shift the result of the reduction. yypush_ (YY_NULLPTR, YY_MOVE (yylhs)); @@ -1600,9 +1593,7 @@ namespace isc { namespace eval { if (!yyerrstatus_) { ++yynerrs_; - context yyctx (*this, yyla); - std::string msg = yysyntax_error_ (yyctx); - error (yyla.location, YY_MOVE (msg)); + error (yyla.location, yysyntax_error_ (yystack_[0].state, yyla)); } @@ -1613,7 +1604,7 @@ namespace isc { namespace eval { error, discard it. */ // Return failure if at end of input. - if (yyla.kind () == symbol_kind::S_YYEOF) + if (yyla.type_get () == yyeof_) YYABORT; else if (!yyla.empty ()) { @@ -1639,7 +1630,6 @@ namespace isc { namespace eval { this YYERROR. */ yypop_ (yylen); yylen = 0; - YY_STACK_PRINT (); goto yyerrlab1; @@ -1648,39 +1638,37 @@ namespace isc { namespace eval { `-------------------------------------------------------------*/ yyerrlab1: yyerrstatus_ = 3; // Each real token shifted decrements this. - // Pop stack until we find a state that shifts the error token. - for (;;) - { - yyn = yypact_[+yystack_[0].state]; - if (!yy_pact_value_is_default_ (yyn)) - { - yyn += symbol_kind::S_YYerror; - if (0 <= yyn && yyn <= yylast_ - && yycheck_[yyn] == symbol_kind::S_YYerror) - { - yyn = yytable_[yyn]; - if (0 < yyn) - break; - } - } - - // Pop the current state because it cannot handle the error token. - if (yystack_.size () == 1) - YYABORT; - - yyerror_range[1].location = yystack_[0].location; - yy_destroy_ ("Error: popping", yystack_[0]); - yypop_ (); - YY_STACK_PRINT (); - } { stack_symbol_type error_token; + for (;;) + { + yyn = yypact_[yystack_[0].state]; + if (!yy_pact_value_is_default_ (yyn)) + { + yyn += yyterror_; + if (0 <= yyn && yyn <= yylast_ && yycheck_[yyn] == yyterror_) + { + yyn = yytable_[yyn]; + if (0 < yyn) + break; + } + } + + // Pop the current state because it cannot handle the error token. + if (yystack_.size () == 1) + YYABORT; + + yyerror_range[1].location = yystack_[0].location; + yy_destroy_ ("Error: popping", yystack_[0]); + yypop_ (); + YY_STACK_PRINT (); + } yyerror_range[2].location = yyla.location; YYLLOC_DEFAULT (error_token.location, yyerror_range, 2); // Shift the error token. - error_token.state = state_type (yyn); + error_token.state = yyn; yypush_ ("Shifting", YY_MOVE (error_token)); } goto yynewstate; @@ -1712,7 +1700,6 @@ namespace isc { namespace eval { /* Do not reclaim the symbols of the rule whose action triggered this YYABORT or YYACCEPT. */ yypop_ (yylen); - YY_STACK_PRINT (); while (1 < yystack_.size ()) { yy_destroy_ ("Cleanup: popping", yystack_[0]); @@ -1746,103 +1733,18 @@ namespace isc { namespace eval { error (yyexc.location, yyexc.what ()); } - /* Return YYSTR after stripping away unnecessary quotes and - backslashes, so that it's suitable for yyerror. The heuristic is - that double-quoting is unnecessary unless the string contains an - apostrophe, a comma, or backslash (other than backslash-backslash). - YYSTR is taken from yytname. */ - std::string - EvalParser::yytnamerr_ (const char *yystr) - { - if (*yystr == '"') - { - std::string yyr; - char const *yyp = yystr; - - for (;;) - switch (*++yyp) - { - case '\'': - case ',': - goto do_not_strip_quotes; - - case '\\': - if (*++yyp != '\\') - goto do_not_strip_quotes; - else - goto append; - - append: - default: - yyr += *yyp; - break; - - case '"': - return yyr; - } - do_not_strip_quotes: ; - } - - return yystr; - } - + // Generate an error message. std::string - EvalParser::symbol_name (symbol_kind_type yysymbol) - { - return yytnamerr_ (yytname_[yysymbol]); - } - - - - // EvalParser::context. - EvalParser::context::context (const EvalParser& yyparser, const symbol_type& yyla) - : yyparser_ (yyparser) - , yyla_ (yyla) - {} - - int - EvalParser::context::expected_tokens (symbol_kind_type yyarg[], int yyargn) const + EvalParser::yysyntax_error_ (state_type yystate, const symbol_type& yyla) const { - // Actual number of expected tokens - int yycount = 0; - - const int yyn = yypact_[+yyparser_.yystack_[0].state]; - if (!yy_pact_value_is_default_ (yyn)) - { - /* Start YYX at -YYN if negative to avoid negative indexes in - YYCHECK. In other words, skip the first -YYN actions for - this state because they are default actions. */ - const int yyxbegin = yyn < 0 ? -yyn : 0; - // Stay within bounds of both yycheck and yytname. - const int yychecklim = yylast_ - yyn + 1; - const int yyxend = yychecklim < YYNTOKENS ? yychecklim : YYNTOKENS; - for (int yyx = yyxbegin; yyx < yyxend; ++yyx) - if (yycheck_[yyx + yyn] == yyx && yyx != symbol_kind::S_YYerror - && !yy_table_value_is_error_ (yytable_[yyx + yyn])) - { - if (!yyarg) - ++yycount; - else if (yycount == yyargn) - return 0; - else - yyarg[yycount++] = YY_CAST (symbol_kind_type, yyx); - } - } - - if (yyarg && yycount == 0 && 0 < yyargn) - yyarg[0] = symbol_kind::S_YYEMPTY; - return yycount; - } - - - - - + // Number of reported tokens (one for the "unexpected", one per + // "expected"). + size_t yycount = 0; + // Its maximum. + enum { YYERROR_VERBOSE_ARGS_MAXIMUM = 5 }; + // Arguments of yyformat. + char const *yyarg[YYERROR_VERBOSE_ARGS_MAXIMUM]; - int - EvalParser::yy_syntax_error_arguments_ (const context& yyctx, - symbol_kind_type yyarg[], int yyargn) const - { /* There are many possibilities here to consider: - If this state is a consistent state with a default action, then the only way this function was invoked is if the default action @@ -1861,32 +1763,41 @@ namespace isc { namespace eval { - Of course, the expected token list depends on states to have correct lookahead information, and it depends on the parser not to perform extra reductions after fetching a lookahead from the - scanner and before detecting a syntax error. Thus, state merging - (from LALR or IELR) and default reductions corrupt the expected - token list. However, the list is correct for canonical LR with - one exception: it will still contain any token that will not be - accepted due to an error action in a later state. + scanner and before detecting a syntax error. Thus, state + merging (from LALR or IELR) and default reductions corrupt the + expected token list. However, the list is correct for + canonical LR with one exception: it will still contain any + token that will not be accepted due to an error action in a + later state. */ - - if (!yyctx.lookahead ().empty ()) + if (!yyla.empty ()) { - if (yyarg) - yyarg[0] = yyctx.token (); - int yyn = yyctx.expected_tokens (yyarg ? yyarg + 1 : yyarg, yyargn - 1); - return yyn + 1; + int yytoken = yyla.type_get (); + yyarg[yycount++] = yytname_[yytoken]; + int yyn = yypact_[yystate]; + if (!yy_pact_value_is_default_ (yyn)) + { + /* Start YYX at -YYN if negative to avoid negative indexes in + YYCHECK. In other words, skip the first -YYN actions for + this state because they are default actions. */ + int yyxbegin = yyn < 0 ? -yyn : 0; + // Stay within bounds of both yycheck and yytname. + int yychecklim = yylast_ - yyn + 1; + int yyxend = yychecklim < yyntokens_ ? yychecklim : yyntokens_; + for (int yyx = yyxbegin; yyx < yyxend; ++yyx) + if (yycheck_[yyx + yyn] == yyx && yyx != yyterror_ + && !yy_table_value_is_error_ (yytable_[yyx + yyn])) + { + if (yycount == YYERROR_VERBOSE_ARGS_MAXIMUM) + { + yycount = 1; + break; + } + else + yyarg[yycount++] = yytname_[yyx]; + } + } } - return 0; - } - - // Generate an error message. - std::string - EvalParser::yysyntax_error_ (const context& yyctx) const - { - // Its maximum. - enum { YYARGS_MAX = 5 }; - // Arguments of yyformat. - symbol_kind_type yyarg[YYARGS_MAX]; - int yycount = yy_syntax_error_arguments_ (yyctx, yyarg, YYARGS_MAX); char const* yyformat = YY_NULLPTR; switch (yycount) @@ -1907,11 +1818,11 @@ namespace isc { namespace eval { std::string yyres; // Argument number. - std::ptrdiff_t yyi = 0; + size_t yyi = 0; for (char const* yyp = yyformat; *yyp; ++yyp) if (yyp[0] == '%' && yyp[1] == 's' && yyi < yycount) { - yyres += symbol_name (yyarg[yyi++]); + yyres += yytnamerr_ (yyarg[yyi++]); ++yyp; } else @@ -1920,259 +1831,264 @@ namespace isc { namespace eval { } - const short EvalParser::yypact_ninf_ = -149; + const short EvalParser::yypact_ninf_ = -156; const signed char EvalParser::yytable_ninf_ = -1; const short EvalParser::yypact_[] = { - -16, 103, 149, 66, 103, 103, 87, 101, 102, 21, - 114, 121, 150, 161, 171, 178, 181, 195, 196, 203, - 210, 211, 212, 152, 72, 124, -149, -149, -149, -149, - -149, 12, 39, -149, 149, 201, 202, 204, 165, 170, - 180, -149, 126, -1, -149, -34, 162, 163, 168, 98, - 51, 149, 149, 103, 149, 149, 149, 149, 149, 149, - 149, 149, 43, -38, 169, -38, 172, 103, 103, 149, - 149, 0, -34, 162, 163, -38, -38, -149, -149, -149, - -149, 207, -149, 209, -149, 213, 216, -149, -149, -149, - -149, -149, -149, -149, -149, -149, -149, -149, -149, -149, - -149, -149, 69, 166, 29, 167, 1, 4, 5, 6, - 7, 10, 13, -149, -149, -149, -149, -149, 214, -149, - 215, -149, -149, 222, 180, -149, 217, 218, 219, 220, - 221, 223, 224, 225, -149, 173, 149, 149, 149, -149, - -149, -149, -149, -149, -149, -149, 226, 227, 228, 229, - 230, 231, 232, 76, 91, 77, -149, 233, 22, 174, - 24, 9, 11, 79, 138, 90, 184, 241, 236, -149, - -149, -149, -149, -149, -149, 237, -149, -149, -149, -13, - -149, 149, -149, -149, 238, 239, -149, 240, 242, 243, - 162, 162, -149, -149, 235, 26, 197, 162, 162, 162, - 162, 244, 245, -149, -149, 246, 247, 248, 249, 250, - 251, 253, -149, 254, 255, 256, 257, 148, 153, 158, - 138, 138, 138, -149, -149, -149, -149, -149, -149 + 43, 109, 156, 20, 109, 109, 73, 94, 98, 90, + 79, 111, 133, 142, 157, 168, 177, 180, 185, 189, + 190, 192, 211, 219, 207, 112, 131, -156, -156, -156, + -156, -156, 135, 29, -156, 156, 210, 212, 213, 161, + 164, 187, -156, 104, 0, -156, -34, 169, 170, 172, + 82, 52, 156, 156, 156, 109, 156, 156, 156, 156, + 156, 156, 156, 156, 113, -39, 176, -39, 178, 109, + 109, 156, 156, 1, -34, 169, 170, -39, -39, -156, + -156, -156, -156, 217, -156, 220, -156, 221, 231, -156, + -156, -156, -156, -156, -156, -156, -156, -156, -156, -156, + -156, -156, -156, -156, 147, 150, 173, 10, 174, 2, + 3, 5, 6, 7, 14, 23, -156, -156, -156, -156, + -156, 222, -156, 223, -156, -156, 234, 187, -156, 225, + 226, 227, 228, 229, 230, 232, 233, -156, 186, 156, + 156, 156, 156, -156, -156, -156, -156, -156, -156, -156, + 235, 236, 237, 238, 239, 240, 241, 16, 4, 78, + -156, 214, 181, 25, 184, 26, 11, 77, 80, 188, + 81, 193, 250, 245, -156, -156, -156, -156, -156, -156, + 246, -156, -156, -156, -17, 202, -156, 156, -156, -156, + 248, 249, -156, 251, 252, 253, 169, 169, -156, -156, + 261, -156, 265, 28, 215, 169, 169, 169, 169, 254, + 255, -156, -156, -156, 256, 257, 258, 260, 262, 263, + 264, -156, 266, 267, 268, 269, 97, 106, 155, 188, + 188, 188, -156, -156, -156, -156, -156, -156 }; - const signed char + const unsigned char EvalParser::yydefact_[] = { 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 18, 48, 19, 20, - 2, 4, 0, 46, 0, 0, 0, 0, 0, 0, - 3, 1, 0, 0, 6, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 18, 49, 19, + 20, 2, 4, 0, 47, 0, 0, 0, 0, 0, + 0, 3, 1, 0, 0, 6, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 0, 0, 0, 5, + 48, 50, 51, 0, 52, 0, 55, 0, 0, 56, + 57, 58, 59, 25, 62, 63, 64, 65, 66, 67, + 68, 69, 70, 26, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 0, 0, 71, 72, 27, 61, + 60, 0, 43, 0, 42, 7, 8, 9, 32, 0, + 0, 0, 0, 0, 0, 0, 0, 17, 0, 0, + 0, 0, 0, 35, 36, 37, 38, 39, 40, 41, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 5, 47, 49, - 50, 0, 51, 0, 54, 0, 0, 55, 56, 57, - 58, 25, 61, 62, 63, 64, 65, 66, 67, 68, - 69, 26, 0, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 70, 71, 27, 60, 59, 0, 42, - 0, 41, 7, 8, 9, 31, 0, 0, 0, 0, - 0, 0, 0, 0, 17, 0, 0, 0, 0, 34, - 35, 36, 37, 38, 39, 40, 0, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 74, 0, 0, 0, - 0, 0, 0, 0, 0, 0, 0, 0, 0, 52, - 53, 10, 21, 12, 23, 0, 72, 73, 28, 0, - 30, 0, 33, 14, 44, 0, 15, 0, 0, 0, - 0, 0, 76, 75, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 29, 32, 0, 0, 0, 0, 0, - 0, 0, 45, 0, 0, 0, 0, 0, 0, 0, - 0, 0, 0, 11, 22, 13, 24, 16, 43 + 75, 0, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 0, 0, 53, 54, 10, 21, 12, 23, + 0, 73, 74, 28, 0, 0, 31, 0, 34, 14, + 45, 0, 15, 0, 0, 0, 0, 0, 77, 76, + 0, 78, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 29, 30, 33, 0, 0, 0, 0, 0, 0, + 0, 46, 0, 0, 0, 0, 0, 0, 0, 0, + 0, 0, 11, 22, 13, 24, 16, 44 }; const short EvalParser::yypgoto_[] = { - -149, -149, -149, 8, -2, -149, 187, -72, -148, 193, - -149, -42, -149, -149, -149, -149, -149 + -156, -156, -156, 8, -2, -156, 203, -74, -155, 206, + -156, -29, -156, -156, -156, -156, -156, -156 }; - const unsigned char + const short EvalParser::yydefgoto_[] = { - 0, 3, 30, 31, 32, 33, 81, 83, 172, 85, - 91, 118, 101, 115, 178, 157, 194 + -1, 3, 31, 32, 33, 34, 83, 85, 177, 87, + 93, 121, 103, 118, 183, 161, 200, 202 }; const unsigned char EvalParser::yytable_[] = { - 40, 127, 43, 78, 78, 139, 174, 69, 140, 141, - 142, 143, 42, 44, 144, 116, 174, 145, 67, 68, - 185, 117, 192, 120, 48, 79, 180, 80, 182, 183, - 204, 186, 71, 129, 130, 67, 68, 70, 70, 70, - 1, 2, 70, 70, 70, 70, 193, 69, 70, 102, - 103, 70, 105, 106, 107, 108, 109, 110, 111, 112, - 70, 104, 70, 184, 70, 137, 41, 124, 125, 224, - 226, 228, 224, 226, 228, 122, 123, 70, 92, 93, - 94, 95, 96, 97, 98, 168, 175, 63, 187, 64, - 176, 177, 113, 114, 169, 170, 171, 169, 170, 188, - 99, 100, 45, 176, 177, 135, 4, 70, 5, 169, - 170, 173, 6, 7, 8, 9, 46, 47, 201, 202, - 87, 88, 89, 90, 10, 206, 207, 208, 209, 11, - 77, 49, 67, 68, 158, 159, 160, 12, 50, 65, - 13, 66, 14, 15, 16, 17, 18, 19, 20, 21, - 22, 23, 34, 51, 24, 25, 169, 170, 35, 36, - 37, 26, 27, 28, 52, 29, 169, 170, 223, 62, - 10, 169, 170, 225, 53, 11, 169, 170, 227, 195, - 75, 54, 64, 12, 55, 76, 13, 66, 14, 15, - 16, 17, 18, 19, 20, 21, 22, 23, 56, 57, - 38, 39, 136, 138, 70, 70, 58, 26, 27, 28, - 181, 29, 70, 59, 60, 61, 72, 73, 70, 74, - 134, 82, 84, 131, 119, 132, 86, 121, 67, 133, - 146, 147, 156, 148, 149, 150, 151, 152, 184, 203, - 153, 154, 155, 161, 162, 163, 164, 165, 166, 167, - 189, 190, 191, 196, 197, 198, 205, 199, 200, 126, - 210, 211, 212, 213, 214, 215, 216, 128, 217, 179, - 218, 219, 220, 221, 222 + 41, 130, 44, 179, 80, 80, 143, 144, 71, 145, + 146, 147, 43, 45, 179, 119, 69, 70, 148, 198, + 42, 120, 174, 175, 178, 173, 81, 149, 82, 186, + 188, 189, 213, 73, 174, 175, 176, 71, 123, 72, + 72, 72, 72, 199, 72, 72, 72, 141, 132, 133, + 104, 105, 106, 72, 108, 109, 110, 111, 112, 113, + 114, 115, 72, 107, 72, 72, 190, 72, 72, 127, + 128, 233, 235, 237, 233, 235, 237, 125, 126, 94, + 95, 96, 97, 98, 99, 100, 191, 180, 46, 193, + 194, 181, 182, 49, 181, 182, 50, 192, 174, 175, + 1, 2, 101, 102, 89, 90, 91, 92, 79, 47, + 69, 70, 4, 48, 5, 174, 175, 232, 6, 7, + 8, 9, 209, 210, 174, 175, 234, 65, 51, 66, + 10, 215, 216, 217, 218, 11, 52, 162, 163, 164, + 165, 69, 70, 12, 13, 53, 67, 14, 68, 15, + 16, 17, 18, 19, 20, 21, 22, 23, 24, 35, + 54, 25, 26, 116, 117, 36, 37, 38, 27, 28, + 29, 55, 30, 174, 175, 236, 77, 10, 66, 78, + 56, 68, 11, 57, 138, 203, 72, 139, 58, 72, + 12, 13, 59, 60, 14, 61, 15, 16, 17, 18, + 19, 20, 21, 22, 23, 24, 174, 175, 39, 40, + 140, 142, 72, 72, 62, 27, 28, 29, 185, 30, + 72, 187, 63, 72, 64, 74, 72, 75, 76, 84, + 86, 88, 122, 134, 124, 137, 135, 136, 150, 151, + 69, 152, 153, 154, 155, 156, 160, 157, 190, 158, + 159, 184, 166, 167, 168, 169, 170, 171, 172, 195, + 196, 197, 201, 204, 205, 211, 206, 207, 208, 212, + 219, 220, 221, 222, 223, 214, 224, 129, 225, 0, + 226, 227, 131, 228, 229, 230, 231 }; - const unsigned char + const short EvalParser::yycheck_[] = { - 2, 73, 4, 4, 4, 4, 154, 8, 4, 4, - 4, 4, 4, 5, 4, 53, 164, 4, 6, 7, - 9, 59, 35, 65, 3, 59, 4, 61, 4, 20, - 4, 20, 34, 75, 76, 6, 7, 38, 38, 38, - 56, 57, 38, 38, 38, 38, 59, 8, 38, 51, - 52, 38, 54, 55, 56, 57, 58, 59, 60, 61, - 38, 53, 38, 54, 38, 36, 0, 69, 70, 217, - 218, 219, 220, 221, 222, 67, 68, 38, 27, 28, - 29, 30, 31, 32, 33, 9, 9, 15, 9, 17, - 13, 14, 49, 50, 18, 19, 20, 18, 19, 9, - 49, 50, 15, 13, 14, 36, 3, 38, 5, 18, - 19, 20, 9, 10, 11, 12, 15, 15, 190, 191, - 22, 23, 24, 25, 21, 197, 198, 199, 200, 26, - 4, 17, 6, 7, 136, 137, 138, 34, 17, 15, - 37, 17, 39, 40, 41, 42, 43, 44, 45, 46, - 47, 48, 3, 3, 51, 52, 18, 19, 9, 10, - 11, 58, 59, 60, 3, 62, 18, 19, 20, 17, - 21, 18, 19, 20, 3, 26, 18, 19, 20, 181, - 15, 3, 17, 34, 3, 15, 37, 17, 39, 40, - 41, 42, 43, 44, 45, 46, 47, 48, 3, 3, - 51, 52, 36, 36, 38, 38, 3, 58, 59, 60, - 36, 62, 38, 3, 3, 3, 15, 15, 38, 15, - 4, 59, 59, 16, 55, 16, 58, 55, 6, 16, - 16, 16, 59, 16, 16, 16, 16, 16, 54, 4, - 17, 17, 17, 17, 17, 17, 17, 17, 17, 17, - 9, 15, 15, 15, 15, 15, 59, 15, 15, 72, - 16, 16, 16, 16, 16, 16, 16, 74, 17, 36, - 17, 17, 17, 17, 17 + 2, 75, 4, 158, 4, 4, 4, 4, 8, 4, + 4, 4, 4, 5, 169, 54, 6, 7, 4, 36, + 0, 60, 18, 19, 20, 9, 60, 4, 62, 4, + 4, 20, 4, 35, 18, 19, 20, 8, 67, 39, + 39, 39, 39, 60, 39, 39, 39, 37, 77, 78, + 52, 53, 54, 39, 56, 57, 58, 59, 60, 61, + 62, 63, 39, 55, 39, 39, 55, 39, 39, 71, + 72, 226, 227, 228, 229, 230, 231, 69, 70, 27, + 28, 29, 30, 31, 32, 33, 9, 9, 15, 9, + 9, 13, 14, 3, 13, 14, 17, 20, 18, 19, + 57, 58, 50, 51, 22, 23, 24, 25, 4, 15, + 6, 7, 3, 15, 5, 18, 19, 20, 9, 10, + 11, 12, 196, 197, 18, 19, 20, 15, 17, 17, + 21, 205, 206, 207, 208, 26, 3, 139, 140, 141, + 142, 6, 7, 34, 35, 3, 15, 38, 17, 40, + 41, 42, 43, 44, 45, 46, 47, 48, 49, 3, + 3, 52, 53, 50, 51, 9, 10, 11, 59, 60, + 61, 3, 63, 18, 19, 20, 15, 21, 17, 15, + 3, 17, 26, 3, 37, 187, 39, 37, 3, 39, + 34, 35, 3, 3, 38, 3, 40, 41, 42, 43, + 44, 45, 46, 47, 48, 49, 18, 19, 52, 53, + 37, 37, 39, 39, 3, 59, 60, 61, 37, 63, + 39, 37, 3, 39, 17, 15, 39, 15, 15, 60, + 60, 59, 56, 16, 56, 4, 16, 16, 16, 16, + 6, 16, 16, 16, 16, 16, 60, 17, 55, 17, + 17, 37, 17, 17, 17, 17, 17, 17, 17, 9, + 15, 15, 60, 15, 15, 4, 15, 15, 15, 4, + 16, 16, 16, 16, 16, 60, 16, 74, 16, -1, + 17, 17, 76, 17, 17, 17, 17 }; - const signed char + const unsigned char EvalParser::yystos_[] = { - 0, 56, 57, 64, 3, 5, 9, 10, 11, 12, - 21, 26, 34, 37, 39, 40, 41, 42, 43, 44, - 45, 46, 47, 48, 51, 52, 58, 59, 60, 62, - 65, 66, 67, 68, 3, 9, 10, 11, 51, 52, - 67, 0, 66, 67, 66, 15, 15, 15, 3, 17, - 17, 3, 3, 3, 3, 3, 3, 3, 3, 3, - 3, 3, 17, 15, 17, 15, 17, 6, 7, 8, - 38, 67, 15, 15, 15, 15, 15, 4, 4, 59, - 61, 69, 59, 70, 59, 72, 58, 22, 23, 24, - 25, 73, 27, 28, 29, 30, 31, 32, 33, 49, - 50, 75, 67, 67, 66, 67, 67, 67, 67, 67, - 67, 67, 67, 49, 50, 76, 53, 59, 74, 55, - 74, 55, 66, 66, 67, 67, 69, 70, 72, 74, - 74, 16, 16, 16, 4, 36, 36, 36, 36, 4, - 4, 4, 4, 4, 4, 4, 16, 16, 16, 16, - 16, 16, 16, 17, 17, 17, 59, 78, 67, 67, - 67, 17, 17, 17, 17, 17, 17, 17, 9, 18, - 19, 20, 71, 20, 71, 9, 13, 14, 77, 36, - 4, 36, 4, 20, 54, 9, 20, 9, 9, 9, - 15, 15, 35, 59, 79, 67, 15, 15, 15, 15, - 15, 70, 70, 4, 4, 59, 70, 70, 70, 70, + 0, 57, 58, 65, 3, 5, 9, 10, 11, 12, + 21, 26, 34, 35, 38, 40, 41, 42, 43, 44, + 45, 46, 47, 48, 49, 52, 53, 59, 60, 61, + 63, 66, 67, 68, 69, 3, 9, 10, 11, 52, + 53, 68, 0, 67, 68, 67, 15, 15, 15, 3, + 17, 17, 3, 3, 3, 3, 3, 3, 3, 3, + 3, 3, 3, 3, 17, 15, 17, 15, 17, 6, + 7, 8, 39, 68, 15, 15, 15, 15, 15, 4, + 4, 60, 62, 70, 60, 71, 60, 73, 59, 22, + 23, 24, 25, 74, 27, 28, 29, 30, 31, 32, + 33, 50, 51, 76, 68, 68, 68, 67, 68, 68, + 68, 68, 68, 68, 68, 68, 50, 51, 77, 54, + 60, 75, 56, 75, 56, 67, 67, 68, 68, 70, + 71, 73, 75, 75, 16, 16, 16, 4, 37, 37, + 37, 37, 37, 4, 4, 4, 4, 4, 4, 4, 16, 16, 16, 16, 16, 16, 16, 17, 17, 17, - 17, 17, 17, 20, 71, 20, 71, 20, 71 + 60, 79, 68, 68, 68, 68, 17, 17, 17, 17, + 17, 17, 17, 9, 18, 19, 20, 72, 20, 72, + 9, 13, 14, 78, 37, 37, 4, 37, 4, 20, + 55, 9, 20, 9, 9, 9, 15, 15, 36, 60, + 80, 60, 81, 68, 15, 15, 15, 15, 15, 71, + 71, 4, 4, 4, 60, 71, 71, 71, 71, 16, + 16, 16, 16, 16, 16, 16, 17, 17, 17, 17, + 17, 17, 20, 72, 20, 72, 20, 72 }; - const signed char + const unsigned char EvalParser::yyr1_[] = { - 0, 63, 64, 64, 65, 66, 66, 66, 66, 66, - 66, 66, 66, 66, 66, 66, 66, 66, 67, 67, - 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 67, 67, 67, 67, 67, 67, - 67, 67, 67, 67, 67, 67, 67, 67, 68, 69, - 69, 70, 71, 71, 72, 73, 73, 73, 73, 74, - 74, 75, 75, 75, 75, 75, 75, 75, 75, 75, - 76, 76, 77, 77, 78, 79, 79 + 0, 64, 65, 65, 66, 67, 67, 67, 67, 67, + 67, 67, 67, 67, 67, 67, 67, 67, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, 68, 68, + 68, 68, 68, 68, 68, 68, 68, 68, 68, 69, + 70, 70, 71, 72, 72, 73, 74, 74, 74, 74, + 75, 75, 76, 76, 76, 76, 76, 76, 76, 76, + 76, 77, 77, 78, 78, 79, 80, 80, 81 }; - const signed char + const unsigned char EvalParser::yyr2_[] = { 0, 2, 2, 2, 1, 3, 2, 3, 3, 3, 6, 11, 6, 11, 6, 6, 11, 4, 1, 1, 1, 6, 11, 6, 11, 3, 3, 3, 6, 8, - 6, 3, 8, 6, 4, 4, 4, 4, 4, 4, - 4, 3, 3, 11, 6, 9, 1, 3, 1, 1, + 8, 6, 3, 8, 6, 4, 4, 4, 4, 4, + 4, 4, 3, 3, 11, 6, 9, 1, 3, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, 1, - 1, 1, 1, 1, 1, 1, 1 + 1, 1, 1, 1, 1, 1, 1, 1, 1 }; -#if EVALDEBUG || 1 + // YYTNAME[SYMBOL-NUM] -- String name of the symbol SYMBOL-NUM. - // First, the terminals, then, starting at \a YYNTOKENS, nonterminals. + // First, the terminals, then, starting at \a yyntokens_, nonterminals. const char* const EvalParser::yytname_[] = { - "\"end of file\"", "error", "\"invalid token\"", "\"(\"", "\")\"", - "\"not\"", "\"and\"", "\"or\"", "\"==\"", "\"option\"", "\"relay4\"", - "\"relay6\"", "\"member\"", "\"peeraddr\"", "\"linkaddr\"", "\"[\"", - "\"]\"", "\".\"", "\"text\"", "\"hex\"", "\"exists\"", "\"pkt\"", - "\"iface\"", "\"src\"", "\"dst\"", "\"len\"", "\"pkt4\"", "\"mac\"", - "\"hlen\"", "\"htype\"", "\"ciaddr\"", "\"giaddr\"", "\"yiaddr\"", - "\"siaddr\"", "\"substring\"", "\"all\"", "\",\"", "\"concat\"", "\"+\"", - "\"ifelse\"", "\"hexstring\"", "\"addrtotext\"", "\"int8totext\"", - "\"int16totext\"", "\"int32totext\"", "\"uint8totext\"", - "\"uint16totext\"", "\"uint32totext\"", "\"pkt6\"", "\"msgtype\"", - "\"transid\"", "\"vendor-class\"", "\"vendor\"", "\"*\"", "\"data\"", - "\"enterprise\"", "\"top-level bool\"", "\"top-level string\"", - "\"constant string\"", "\"integer\"", "\"constant hexstring\"", - "\"option name\"", "\"ip address\"", "$accept", "start", "expression", - "bool_expr", "string_expr", "integer_expr", "option_code", - "sub_option_code", "option_repr_type", "nest_level", "pkt_metadata", - "enterprise_id", "pkt4_field", "pkt6_field", "relay6_field", - "start_expr", "length_expr", YY_NULLPTR + "\"end of file\"", "error", "$undefined", "\"(\"", "\")\"", "\"not\"", + "\"and\"", "\"or\"", "\"==\"", "\"option\"", "\"relay4\"", "\"relay6\"", + "\"member\"", "\"peeraddr\"", "\"linkaddr\"", "\"[\"", "\"]\"", "\".\"", + "\"text\"", "\"hex\"", "\"exists\"", "\"pkt\"", "\"iface\"", "\"src\"", + "\"dst\"", "\"len\"", "\"pkt4\"", "\"mac\"", "\"hlen\"", "\"htype\"", + "\"ciaddr\"", "\"giaddr\"", "\"yiaddr\"", "\"siaddr\"", "\"substring\"", + "\"split\"", "\"all\"", "\",\"", "\"concat\"", "\"+\"", "\"ifelse\"", + "\"hexstring\"", "\"addrtotext\"", "\"int8totext\"", "\"int16totext\"", + "\"int32totext\"", "\"uint8totext\"", "\"uint16totext\"", + "\"uint32totext\"", "\"pkt6\"", "\"msgtype\"", "\"transid\"", + "\"vendor-class\"", "\"vendor\"", "\"*\"", "\"data\"", "\"enterprise\"", + "\"top-level bool\"", "\"top-level string\"", "\"constant string\"", + "\"integer\"", "\"constant hexstring\"", "\"option name\"", + "\"ip address\"", "$accept", "start", "expression", "bool_expr", + "string_expr", "integer_expr", "option_code", "sub_option_code", + "option_repr_type", "nest_level", "pkt_metadata", "enterprise_id", + "pkt4_field", "pkt6_field", "relay6_field", "start_expr", "length_expr", + "int_expr", YY_NULLPTR }; -#endif - #if EVALDEBUG - const short + const unsigned short EvalParser::yyrline_[] = { - 0, 130, 130, 131, 136, 139, 140, 145, 150, 155, - 160, 165, 170, 190, 204, 213, 222, 232, 249, 254, - 259, 264, 269, 274, 295, 310, 315, 329, 343, 358, - 363, 368, 373, 378, 383, 388, 393, 398, 403, 408, - 413, 418, 427, 437, 446, 459, 472, 477, 480, 486, - 490, 496, 502, 506, 512, 521, 525, 529, 533, 539, - 543, 549, 553, 557, 561, 565, 569, 573, 577, 581, - 587, 591, 597, 601, 607, 614, 619 + 0, 131, 131, 132, 137, 140, 141, 146, 151, 156, + 161, 166, 171, 191, 205, 214, 223, 233, 250, 255, + 260, 265, 270, 275, 296, 311, 316, 330, 344, 359, + 364, 369, 374, 379, 384, 389, 394, 399, 404, 409, + 414, 419, 424, 433, 443, 452, 465, 478, 483, 486, + 492, 496, 502, 508, 512, 518, 527, 531, 535, 539, + 545, 549, 555, 559, 563, 567, 571, 575, 579, 583, + 587, 593, 597, 603, 607, 613, 620, 625, 631 }; + // Print the state stack on the debug stream. void - EvalParser::yy_stack_print_ () const + EvalParser::yystack_print_ () { *yycdebug_ << "Stack now"; for (stack_type::const_iterator i = yystack_.begin (), i_end = yystack_.end (); i != i_end; ++i) - *yycdebug_ << ' ' << int (i->state); + *yycdebug_ << ' ' << i->state; *yycdebug_ << '\n'; } + // Report on the debug stream that the rule \a yyrule is going to be reduced. void - EvalParser::yy_reduce_print_ (int yyrule) const + EvalParser::yy_reduce_print_ (int yyrule) { - int yylno = yyrline_[yyrule]; + unsigned yylno = yyrline_[yyrule]; int yynrhs = yyr2_[yyrule]; // Print the symbols being reduced, and their result. *yycdebug_ << "Reducing stack by rule " << yyrule - 1 @@ -2185,11 +2101,10 @@ namespace isc { namespace eval { #endif // EVALDEBUG -#line 14 "parser.yy" +#line 14 "parser.yy" // lalr1.cc:1242 } } // isc::eval -#line 2191 "parser.cc" - -#line 626 "parser.yy" +#line 2107 "parser.cc" // lalr1.cc:1242 +#line 638 "parser.yy" // lalr1.cc:1243 void isc::eval::EvalParser::error(const location_type& loc, diff --git a/src/lib/eval/parser.h b/src/lib/eval/parser.h index 0ff5185efe..6b361e17ec 100644 --- a/src/lib/eval/parser.h +++ b/src/lib/eval/parser.h @@ -1,8 +1,8 @@ -// A Bison parser, made by GNU Bison 3.8.2. +// A Bison parser, made by GNU Bison 3.3.1. // Skeleton interface for Bison LALR(1) parsers in C++ -// Copyright (C) 2002-2015, 2018-2021 Free Software Foundation, Inc. +// Copyright (C) 2002-2015, 2018-2019 Free Software Foundation, Inc. // This program is free software: you can redistribute it and/or modify // it under the terms of the GNU General Public License as published by @@ -15,7 +15,7 @@ // GNU General Public License for more details. // You should have received a copy of the GNU General Public License -// along with this program. If not, see . +// along with this program. If not, see . // As a special exception, you may create a larger work that contains // part or all of the Bison parser skeleton and distribute that work @@ -38,14 +38,13 @@ // C++ LALR(1) parser skeleton written by Akim Demaille. -// DO NOT RELY ON FEATURES THAT ARE NOT DOCUMENTED in the manual, -// especially those whose name start with YY_ or yy_. They are -// private implementation details that can be changed or removed. +// Undocumented macros, especially those whose name start with YY_, +// are private implementation details. Do not rely on them. #ifndef YY_EVAL_PARSER_H_INCLUDED # define YY_EVAL_PARSER_H_INCLUDED -// "%code requires" blocks. -#line 17 "parser.yy" +// // "%code requires" blocks. +#line 17 "parser.yy" // lalr1.cc:401 #include #include @@ -56,7 +55,7 @@ using namespace isc::dhcp; using namespace isc::eval; -#line 60 "parser.h" +#line 59 "parser.h" // lalr1.cc:401 # include # include // std::abort @@ -103,48 +102,44 @@ using namespace isc::eval; #endif # include "location.hh" #include -#ifndef EVAL_ASSERT +#ifndef YYASSERT # include -# define EVAL_ASSERT assert +# define YYASSERT assert #endif -#ifndef YY_ATTRIBUTE_PURE -# if defined __GNUC__ && 2 < __GNUC__ + (96 <= __GNUC_MINOR__) -# define YY_ATTRIBUTE_PURE __attribute__ ((__pure__)) +#ifndef YY_ATTRIBUTE +# if (defined __GNUC__ \ + && (2 < __GNUC__ || (__GNUC__ == 2 && 96 <= __GNUC_MINOR__))) \ + || defined __SUNPRO_C && 0x5110 <= __SUNPRO_C +# define YY_ATTRIBUTE(Spec) __attribute__(Spec) # else -# define YY_ATTRIBUTE_PURE +# define YY_ATTRIBUTE(Spec) /* empty */ # endif #endif +#ifndef YY_ATTRIBUTE_PURE +# define YY_ATTRIBUTE_PURE YY_ATTRIBUTE ((__pure__)) +#endif + #ifndef YY_ATTRIBUTE_UNUSED -# if defined __GNUC__ && 2 < __GNUC__ + (7 <= __GNUC_MINOR__) -# define YY_ATTRIBUTE_UNUSED __attribute__ ((__unused__)) -# else -# define YY_ATTRIBUTE_UNUSED -# endif +# define YY_ATTRIBUTE_UNUSED YY_ATTRIBUTE ((__unused__)) #endif /* Suppress unused-variable warnings by "using" E. */ #if ! defined lint || defined __GNUC__ -# define YY_USE(E) ((void) (E)) +# define YYUSE(E) ((void) (E)) #else -# define YY_USE(E) /* empty */ +# define YYUSE(E) /* empty */ #endif +#if defined __GNUC__ && ! defined __ICC && 407 <= __GNUC__ * 100 + __GNUC_MINOR__ /* Suppress an incorrect diagnostic about yylval being uninitialized. */ -#if defined __GNUC__ && ! defined __ICC && 406 <= __GNUC__ * 100 + __GNUC_MINOR__ -# if __GNUC__ * 100 + __GNUC_MINOR__ < 407 -# define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN \ - _Pragma ("GCC diagnostic push") \ - _Pragma ("GCC diagnostic ignored \"-Wuninitialized\"") -# else -# define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN \ - _Pragma ("GCC diagnostic push") \ - _Pragma ("GCC diagnostic ignored \"-Wuninitialized\"") \ +# define YY_IGNORE_MAYBE_UNINITIALIZED_BEGIN \ + _Pragma ("GCC diagnostic push") \ + _Pragma ("GCC diagnostic ignored \"-Wuninitialized\"")\ _Pragma ("GCC diagnostic ignored \"-Wmaybe-uninitialized\"") -# endif -# define YY_IGNORE_MAYBE_UNINITIALIZED_END \ +# define YY_IGNORE_MAYBE_UNINITIALIZED_END \ _Pragma ("GCC diagnostic pop") #else # define YY_INITIAL_VALUE(Value) Value @@ -157,27 +152,6 @@ using namespace isc::eval; # define YY_INITIAL_VALUE(Value) /* Nothing. */ #endif -#if defined __cplusplus && defined __GNUC__ && ! defined __ICC && 6 <= __GNUC__ -# define YY_IGNORE_USELESS_CAST_BEGIN \ - _Pragma ("GCC diagnostic push") \ - _Pragma ("GCC diagnostic ignored \"-Wuseless-cast\"") -# define YY_IGNORE_USELESS_CAST_END \ - _Pragma ("GCC diagnostic pop") -#endif -#ifndef YY_IGNORE_USELESS_CAST_BEGIN -# define YY_IGNORE_USELESS_CAST_BEGIN -# define YY_IGNORE_USELESS_CAST_END -#endif - -# ifndef YY_CAST -# ifdef __cplusplus -# define YY_CAST(Type, Val) static_cast (Val) -# define YY_REINTERPRET_CAST(Type, Val) reinterpret_cast (Val) -# else -# define YY_CAST(Type, Val) ((Type) (Val)) -# define YY_REINTERPRET_CAST(Type, Val) ((Type) (Val)) -# endif -# endif # ifndef YY_NULLPTR # if defined __cplusplus # if 201103L <= __cplusplus @@ -203,10 +177,9 @@ using namespace isc::eval; # endif /* ! defined YYDEBUG */ #endif /* ! defined EVALDEBUG */ -#line 14 "parser.yy" +#line 14 "parser.yy" // lalr1.cc:401 namespace isc { namespace eval { -#line 209 "parser.h" - +#line 183 "parser.h" // lalr1.cc:401 @@ -214,49 +187,37 @@ namespace isc { namespace eval { class EvalParser { public: -#ifdef EVALSTYPE -# ifdef __GNUC__ -# pragma GCC message "bison: do not #define EVALSTYPE in C++, use %define api.value.type" -# endif - typedef EVALSTYPE value_type; -#else +#ifndef EVALSTYPE /// A buffer to store and retrieve objects. /// /// Sort of a variant, but does not keep track of the nature /// of the stored data, since that knowledge is available /// via the current parser state. - class value_type + class semantic_type { public: /// Type of *this. - typedef value_type self_type; + typedef semantic_type self_type; /// Empty construction. - value_type () YY_NOEXCEPT - : yyraw_ () + semantic_type () YY_NOEXCEPT + : yybuffer_ () , yytypeid_ (YY_NULLPTR) {} /// Construct and fill. template - value_type (YY_RVREF (T) t) + semantic_type (YY_RVREF (T) t) : yytypeid_ (&typeid (T)) { - EVAL_ASSERT (sizeof (T) <= size); + YYASSERT (sizeof (T) <= size); new (yyas_ ()) T (YY_MOVE (t)); } -#if 201103L <= YY_CPLUSPLUS - /// Non copyable. - value_type (const self_type&) = delete; - /// Non copyable. - self_type& operator= (const self_type&) = delete; -#endif - /// Destruction, allowed only if empty. - ~value_type () YY_NOEXCEPT + ~semantic_type () YY_NOEXCEPT { - EVAL_ASSERT (!yytypeid_); + YYASSERT (!yytypeid_); } # if 201103L <= YY_CPLUSPLUS @@ -265,8 +226,8 @@ namespace isc { namespace eval { T& emplace (U&&... u) { - EVAL_ASSERT (!yytypeid_); - EVAL_ASSERT (sizeof (T) <= size); + YYASSERT (!yytypeid_); + YYASSERT (sizeof (T) <= size); yytypeid_ = & typeid (T); return *new (yyas_ ()) T (std::forward (u)...); } @@ -276,8 +237,8 @@ namespace isc { namespace eval { T& emplace () { - EVAL_ASSERT (!yytypeid_); - EVAL_ASSERT (sizeof (T) <= size); + YYASSERT (!yytypeid_); + YYASSERT (sizeof (T) <= size); yytypeid_ = & typeid (T); return *new (yyas_ ()) T (); } @@ -287,8 +248,8 @@ namespace isc { namespace eval { T& emplace (const T& t) { - EVAL_ASSERT (!yytypeid_); - EVAL_ASSERT (sizeof (T) <= size); + YYASSERT (!yytypeid_); + YYASSERT (sizeof (T) <= size); yytypeid_ = & typeid (T); return *new (yyas_ ()) T (t); } @@ -317,9 +278,9 @@ namespace isc { namespace eval { T& as () YY_NOEXCEPT { - EVAL_ASSERT (yytypeid_); - EVAL_ASSERT (*yytypeid_ == typeid (T)); - EVAL_ASSERT (sizeof (T) <= size); + YYASSERT (yytypeid_); + YYASSERT (*yytypeid_ == typeid (T)); + YYASSERT (sizeof (T) <= size); return *yyas_ (); } @@ -328,9 +289,9 @@ namespace isc { namespace eval { const T& as () const YY_NOEXCEPT { - EVAL_ASSERT (yytypeid_); - EVAL_ASSERT (*yytypeid_ == typeid (T)); - EVAL_ASSERT (sizeof (T) <= size); + YYASSERT (yytypeid_); + YYASSERT (*yytypeid_ == typeid (T)); + YYASSERT (sizeof (T) <= size); return *yyas_ (); } @@ -346,8 +307,8 @@ namespace isc { namespace eval { void swap (self_type& that) YY_NOEXCEPT { - EVAL_ASSERT (yytypeid_); - EVAL_ASSERT (*yytypeid_ == *that.yytypeid_); + YYASSERT (yytypeid_); + YYASSERT (*yytypeid_ == *that.yytypeid_); std::swap (as (), that.as ()); } @@ -396,19 +357,16 @@ namespace isc { namespace eval { } private: -#if YY_CPLUSPLUS < 201103L - /// Non copyable. - value_type (const self_type&); - /// Non copyable. + /// Prohibit blind copies. self_type& operator= (const self_type&); -#endif + semantic_type (const self_type&); /// Accessor to raw memory as \a T. template T* yyas_ () YY_NOEXCEPT { - void *yyp = yyraw_; + void *yyp = yybuffer_.yyraw; return static_cast (yyp); } @@ -417,7 +375,7 @@ namespace isc { namespace eval { const T* yyas_ () const YY_NOEXCEPT { - const void *yyp = yyraw_; + const void *yyp = yybuffer_.yyraw; return static_cast (yyp); } @@ -465,19 +423,18 @@ namespace isc { namespace eval { union { /// Strongest alignment constraints. - long double yyalign_me_; + long double yyalign_me; /// A buffer large enough to store any of the semantic values. - char yyraw_[size]; - }; + char yyraw[size]; + } yybuffer_; /// Whether the content is built: if defined, the name of the stored type. const std::type_info *yytypeid_; }; +#else + typedef EVALSTYPE semantic_type; #endif - /// Backward compatibility (Bison 3.8). - typedef value_type semantic_type; - /// Symbol locations. typedef location location_type; @@ -499,186 +456,92 @@ namespace isc { namespace eval { location_type location; }; - /// Token kinds. + /// Tokens. struct token { - enum token_kind_type - { - TOKEN_EVALEMPTY = -2, - TOKEN_END = 0, // "end of file" - TOKEN_EVALerror = 256, // error - TOKEN_EVALUNDEF = 257, // "invalid token" - TOKEN_LPAREN = 258, // "(" - TOKEN_RPAREN = 259, // ")" - TOKEN_NOT = 260, // "not" - TOKEN_AND = 261, // "and" - TOKEN_OR = 262, // "or" - TOKEN_EQUAL = 263, // "==" - TOKEN_OPTION = 264, // "option" - TOKEN_RELAY4 = 265, // "relay4" - TOKEN_RELAY6 = 266, // "relay6" - TOKEN_MEMBER = 267, // "member" - TOKEN_PEERADDR = 268, // "peeraddr" - TOKEN_LINKADDR = 269, // "linkaddr" - TOKEN_LBRACKET = 270, // "[" - TOKEN_RBRACKET = 271, // "]" - TOKEN_DOT = 272, // "." - TOKEN_TEXT = 273, // "text" - TOKEN_HEX = 274, // "hex" - TOKEN_EXISTS = 275, // "exists" - TOKEN_PKT = 276, // "pkt" - TOKEN_IFACE = 277, // "iface" - TOKEN_SRC = 278, // "src" - TOKEN_DST = 279, // "dst" - TOKEN_LEN = 280, // "len" - TOKEN_PKT4 = 281, // "pkt4" - TOKEN_CHADDR = 282, // "mac" - TOKEN_HLEN = 283, // "hlen" - TOKEN_HTYPE = 284, // "htype" - TOKEN_CIADDR = 285, // "ciaddr" - TOKEN_GIADDR = 286, // "giaddr" - TOKEN_YIADDR = 287, // "yiaddr" - TOKEN_SIADDR = 288, // "siaddr" - TOKEN_SUBSTRING = 289, // "substring" - TOKEN_ALL = 290, // "all" - TOKEN_COMA = 291, // "," - TOKEN_CONCAT = 292, // "concat" - TOKEN_PLUS = 293, // "+" - TOKEN_IFELSE = 294, // "ifelse" - TOKEN_TOHEXSTRING = 295, // "hexstring" - TOKEN_ADDRTOTEXT = 296, // "addrtotext" - TOKEN_INT8TOTEXT = 297, // "int8totext" - TOKEN_INT16TOTEXT = 298, // "int16totext" - TOKEN_INT32TOTEXT = 299, // "int32totext" - TOKEN_UINT8TOTEXT = 300, // "uint8totext" - TOKEN_UINT16TOTEXT = 301, // "uint16totext" - TOKEN_UINT32TOTEXT = 302, // "uint32totext" - TOKEN_PKT6 = 303, // "pkt6" - TOKEN_MSGTYPE = 304, // "msgtype" - TOKEN_TRANSID = 305, // "transid" - TOKEN_VENDOR_CLASS = 306, // "vendor-class" - TOKEN_VENDOR = 307, // "vendor" - TOKEN_ANY = 308, // "*" - TOKEN_DATA = 309, // "data" - TOKEN_ENTERPRISE = 310, // "enterprise" - TOKEN_TOPLEVEL_BOOL = 311, // "top-level bool" - TOKEN_TOPLEVEL_STRING = 312, // "top-level string" - TOKEN_STRING = 313, // "constant string" - TOKEN_INTEGER = 314, // "integer" - TOKEN_HEXSTRING = 315, // "constant hexstring" - TOKEN_OPTION_NAME = 316, // "option name" - TOKEN_IP_ADDRESS = 317 // "ip address" + enum yytokentype + { + TOKEN_END = 0, + TOKEN_LPAREN = 258, + TOKEN_RPAREN = 259, + TOKEN_NOT = 260, + TOKEN_AND = 261, + TOKEN_OR = 262, + TOKEN_EQUAL = 263, + TOKEN_OPTION = 264, + TOKEN_RELAY4 = 265, + TOKEN_RELAY6 = 266, + TOKEN_MEMBER = 267, + TOKEN_PEERADDR = 268, + TOKEN_LINKADDR = 269, + TOKEN_LBRACKET = 270, + TOKEN_RBRACKET = 271, + TOKEN_DOT = 272, + TOKEN_TEXT = 273, + TOKEN_HEX = 274, + TOKEN_EXISTS = 275, + TOKEN_PKT = 276, + TOKEN_IFACE = 277, + TOKEN_SRC = 278, + TOKEN_DST = 279, + TOKEN_LEN = 280, + TOKEN_PKT4 = 281, + TOKEN_CHADDR = 282, + TOKEN_HLEN = 283, + TOKEN_HTYPE = 284, + TOKEN_CIADDR = 285, + TOKEN_GIADDR = 286, + TOKEN_YIADDR = 287, + TOKEN_SIADDR = 288, + TOKEN_SUBSTRING = 289, + TOKEN_SPLIT = 290, + TOKEN_ALL = 291, + TOKEN_COMA = 292, + TOKEN_CONCAT = 293, + TOKEN_PLUS = 294, + TOKEN_IFELSE = 295, + TOKEN_TOHEXSTRING = 296, + TOKEN_ADDRTOTEXT = 297, + TOKEN_INT8TOTEXT = 298, + TOKEN_INT16TOTEXT = 299, + TOKEN_INT32TOTEXT = 300, + TOKEN_UINT8TOTEXT = 301, + TOKEN_UINT16TOTEXT = 302, + TOKEN_UINT32TOTEXT = 303, + TOKEN_PKT6 = 304, + TOKEN_MSGTYPE = 305, + TOKEN_TRANSID = 306, + TOKEN_VENDOR_CLASS = 307, + TOKEN_VENDOR = 308, + TOKEN_ANY = 309, + TOKEN_DATA = 310, + TOKEN_ENTERPRISE = 311, + TOKEN_TOPLEVEL_BOOL = 312, + TOKEN_TOPLEVEL_STRING = 313, + TOKEN_STRING = 314, + TOKEN_INTEGER = 315, + TOKEN_HEXSTRING = 316, + TOKEN_OPTION_NAME = 317, + TOKEN_IP_ADDRESS = 318 }; - /// Backward compatibility alias (Bison 3.6). - typedef token_kind_type yytokentype; }; - /// Token kind, as returned by yylex. - typedef token::token_kind_type token_kind_type; + /// (External) token type, as returned by yylex. + typedef token::yytokentype token_type; - /// Backward compatibility alias (Bison 3.6). - typedef token_kind_type token_type; + /// Symbol type: an internal symbol number. + typedef int symbol_number_type; - /// Symbol kinds. - struct symbol_kind - { - enum symbol_kind_type - { - YYNTOKENS = 63, ///< Number of tokens. - S_YYEMPTY = -2, - S_YYEOF = 0, // "end of file" - S_YYerror = 1, // error - S_YYUNDEF = 2, // "invalid token" - S_LPAREN = 3, // "(" - S_RPAREN = 4, // ")" - S_NOT = 5, // "not" - S_AND = 6, // "and" - S_OR = 7, // "or" - S_EQUAL = 8, // "==" - S_OPTION = 9, // "option" - S_RELAY4 = 10, // "relay4" - S_RELAY6 = 11, // "relay6" - S_MEMBER = 12, // "member" - S_PEERADDR = 13, // "peeraddr" - S_LINKADDR = 14, // "linkaddr" - S_LBRACKET = 15, // "[" - S_RBRACKET = 16, // "]" - S_DOT = 17, // "." - S_TEXT = 18, // "text" - S_HEX = 19, // "hex" - S_EXISTS = 20, // "exists" - S_PKT = 21, // "pkt" - S_IFACE = 22, // "iface" - S_SRC = 23, // "src" - S_DST = 24, // "dst" - S_LEN = 25, // "len" - S_PKT4 = 26, // "pkt4" - S_CHADDR = 27, // "mac" - S_HLEN = 28, // "hlen" - S_HTYPE = 29, // "htype" - S_CIADDR = 30, // "ciaddr" - S_GIADDR = 31, // "giaddr" - S_YIADDR = 32, // "yiaddr" - S_SIADDR = 33, // "siaddr" - S_SUBSTRING = 34, // "substring" - S_ALL = 35, // "all" - S_COMA = 36, // "," - S_CONCAT = 37, // "concat" - S_PLUS = 38, // "+" - S_IFELSE = 39, // "ifelse" - S_TOHEXSTRING = 40, // "hexstring" - S_ADDRTOTEXT = 41, // "addrtotext" - S_INT8TOTEXT = 42, // "int8totext" - S_INT16TOTEXT = 43, // "int16totext" - S_INT32TOTEXT = 44, // "int32totext" - S_UINT8TOTEXT = 45, // "uint8totext" - S_UINT16TOTEXT = 46, // "uint16totext" - S_UINT32TOTEXT = 47, // "uint32totext" - S_PKT6 = 48, // "pkt6" - S_MSGTYPE = 49, // "msgtype" - S_TRANSID = 50, // "transid" - S_VENDOR_CLASS = 51, // "vendor-class" - S_VENDOR = 52, // "vendor" - S_ANY = 53, // "*" - S_DATA = 54, // "data" - S_ENTERPRISE = 55, // "enterprise" - S_TOPLEVEL_BOOL = 56, // "top-level bool" - S_TOPLEVEL_STRING = 57, // "top-level string" - S_STRING = 58, // "constant string" - S_INTEGER = 59, // "integer" - S_HEXSTRING = 60, // "constant hexstring" - S_OPTION_NAME = 61, // "option name" - S_IP_ADDRESS = 62, // "ip address" - S_YYACCEPT = 63, // $accept - S_start = 64, // start - S_expression = 65, // expression - S_bool_expr = 66, // bool_expr - S_string_expr = 67, // string_expr - S_integer_expr = 68, // integer_expr - S_option_code = 69, // option_code - S_sub_option_code = 70, // sub_option_code - S_option_repr_type = 71, // option_repr_type - S_nest_level = 72, // nest_level - S_pkt_metadata = 73, // pkt_metadata - S_enterprise_id = 74, // enterprise_id - S_pkt4_field = 75, // pkt4_field - S_pkt6_field = 76, // pkt6_field - S_relay6_field = 77, // relay6_field - S_start_expr = 78, // start_expr - S_length_expr = 79 // length_expr - }; - }; + /// The symbol type number to denote an empty symbol. + enum { empty_symbol = -2 }; - /// (Internal) symbol kind. - typedef symbol_kind::symbol_kind_type symbol_kind_type; - - /// The number of tokens. - static const symbol_kind_type YYNTOKENS = symbol_kind::YYNTOKENS; + /// Internal symbol number for tokens (subsumed by symbol_number_type). + typedef unsigned char token_number_type; /// A complete symbol. /// - /// Expects its Base type to provide access to the symbol kind - /// via kind (). + /// Expects its Base type to provide access to the symbol type + /// via type_get (). /// /// Provide access to semantic value and location. template @@ -688,73 +551,20 @@ namespace isc { namespace eval { typedef Base super_type; /// Default constructor. - basic_symbol () YY_NOEXCEPT + basic_symbol () : value () , location () {} #if 201103L <= YY_CPLUSPLUS /// Move constructor. - basic_symbol (basic_symbol&& that) - : Base (std::move (that)) - , value () - , location (std::move (that.location)) - { - switch (this->kind ()) - { - case symbol_kind::S_option_repr_type: // option_repr_type - value.move< TokenOption::RepresentationType > (std::move (that.value)); - break; - - case symbol_kind::S_pkt4_field: // pkt4_field - value.move< TokenPkt4::FieldType > (std::move (that.value)); - break; - - case symbol_kind::S_pkt6_field: // pkt6_field - value.move< TokenPkt6::FieldType > (std::move (that.value)); - break; - - case symbol_kind::S_pkt_metadata: // pkt_metadata - value.move< TokenPkt::MetadataType > (std::move (that.value)); - break; - - case symbol_kind::S_relay6_field: // relay6_field - value.move< TokenRelay6Field::FieldType > (std::move (that.value)); - break; - - case symbol_kind::S_nest_level: // nest_level - value.move< int8_t > (std::move (that.value)); - break; - - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" - value.move< std::string > (std::move (that.value)); - break; - - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code - value.move< uint16_t > (std::move (that.value)); - break; - - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id - value.move< uint32_t > (std::move (that.value)); - break; - - default: - break; - } - - } + basic_symbol (basic_symbol&& that); #endif /// Copy constructor. basic_symbol (const basic_symbol& that); - /// Constructors for typed symbols. + /// Constructor for valueless symbols, and symbols from each type. #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, location_type&& l) : Base (t) @@ -766,7 +576,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, TokenOption::RepresentationType&& v, location_type&& l) : Base (t) @@ -780,7 +589,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, TokenPkt4::FieldType&& v, location_type&& l) : Base (t) @@ -794,7 +602,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, TokenPkt6::FieldType&& v, location_type&& l) : Base (t) @@ -808,7 +615,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, TokenPkt::MetadataType&& v, location_type&& l) : Base (t) @@ -822,7 +628,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, TokenRelay6Field::FieldType&& v, location_type&& l) : Base (t) @@ -836,7 +641,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, int8_t&& v, location_type&& l) : Base (t) @@ -850,7 +654,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, std::string&& v, location_type&& l) : Base (t) @@ -864,7 +667,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, uint16_t&& v, location_type&& l) : Base (t) @@ -878,7 +680,6 @@ namespace isc { namespace eval { , location (l) {} #endif - #if 201103L <= YY_CPLUSPLUS basic_symbol (typename Base::kind_type t, uint32_t&& v, location_type&& l) : Base (t) @@ -899,63 +700,61 @@ namespace isc { namespace eval { clear (); } - - /// Destroy contents, and record that is empty. - void clear () YY_NOEXCEPT + void clear () { // User destructor. - symbol_kind_type yykind = this->kind (); + symbol_number_type yytype = this->type_get (); basic_symbol& yysym = *this; (void) yysym; - switch (yykind) + switch (yytype) { default: break; } - // Value type destructor. -switch (yykind) + // Type destructor. +switch (yytype) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type value.template destroy< TokenOption::RepresentationType > (); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field value.template destroy< TokenPkt4::FieldType > (); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field value.template destroy< TokenPkt6::FieldType > (); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata value.template destroy< TokenPkt::MetadataType > (); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field value.template destroy< TokenRelay6Field::FieldType > (); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level value.template destroy< int8_t > (); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" value.template destroy< std::string > (); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code value.template destroy< uint16_t > (); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id value.template destroy< uint32_t > (); break; @@ -966,15 +765,6 @@ switch (yykind) Base::clear (); } - /// The user-facing name of this symbol. - std::string name () const YY_NOEXCEPT - { - return EvalParser::symbol_name (this->kind ()); - } - - /// Backward compatibility (Bison 3.6). - symbol_kind_type type_get () const YY_NOEXCEPT; - /// Whether empty. bool empty () const YY_NOEXCEPT; @@ -982,7 +772,7 @@ switch (yykind) void move (basic_symbol& s); /// The semantic value. - value_type value; + semantic_type value; /// The location. location_type location; @@ -995,96 +785,86 @@ switch (yykind) }; /// Type access provider for token (enum) based symbols. - struct by_kind + struct by_type { - /// The symbol kind as needed by the constructor. - typedef token_kind_type kind_type; - /// Default constructor. - by_kind () YY_NOEXCEPT; + by_type (); #if 201103L <= YY_CPLUSPLUS /// Move constructor. - by_kind (by_kind&& that) YY_NOEXCEPT; + by_type (by_type&& that); #endif /// Copy constructor. - by_kind (const by_kind& that) YY_NOEXCEPT; - - /// Constructor from (external) token numbers. - by_kind (kind_type t) YY_NOEXCEPT; + by_type (const by_type& that); + /// The symbol type as needed by the constructor. + typedef token_type kind_type; + /// Constructor from (external) token numbers. + by_type (kind_type t); /// Record that this symbol is empty. - void clear () YY_NOEXCEPT; + void clear (); - /// Steal the symbol kind from \a that. - void move (by_kind& that); + /// Steal the symbol type from \a that. + void move (by_type& that); /// The (internal) type number (corresponding to \a type). /// \a empty when empty. - symbol_kind_type kind () const YY_NOEXCEPT; + symbol_number_type type_get () const YY_NOEXCEPT; - /// Backward compatibility (Bison 3.6). - symbol_kind_type type_get () const YY_NOEXCEPT; + /// The token. + token_type token () const YY_NOEXCEPT; - /// The symbol kind. - /// \a S_YYEMPTY when empty. - symbol_kind_type kind_; + /// The symbol type. + /// \a empty_symbol when empty. + /// An int, not token_number_type, to be able to store empty_symbol. + int type; }; - /// Backward compatibility for a private implementation detail (Bison 3.6). - typedef by_kind by_type; - /// "External" symbols: returned by the scanner. - struct symbol_type : basic_symbol + struct symbol_type : basic_symbol { /// Superclass. - typedef basic_symbol super_type; + typedef basic_symbol super_type; /// Empty symbol. - symbol_type () YY_NOEXCEPT {} + symbol_type () {} /// Constructor for valueless symbols, and symbols from each type. #if 201103L <= YY_CPLUSPLUS symbol_type (int tok, location_type l) - : super_type (token_kind_type (tok), std::move (l)) + : super_type(token_type (tok), std::move (l)) + { + YYASSERT (tok == token::TOKEN_END || tok == token::TOKEN_LPAREN || tok == token::TOKEN_RPAREN || tok == token::TOKEN_NOT || tok == token::TOKEN_AND || tok == token::TOKEN_OR || tok == token::TOKEN_EQUAL || tok == token::TOKEN_OPTION || tok == token::TOKEN_RELAY4 || tok == token::TOKEN_RELAY6 || tok == token::TOKEN_MEMBER || tok == token::TOKEN_PEERADDR || tok == token::TOKEN_LINKADDR || tok == token::TOKEN_LBRACKET || tok == token::TOKEN_RBRACKET || tok == token::TOKEN_DOT || tok == token::TOKEN_TEXT || tok == token::TOKEN_HEX || tok == token::TOKEN_EXISTS || tok == token::TOKEN_PKT || tok == token::TOKEN_IFACE || tok == token::TOKEN_SRC || tok == token::TOKEN_DST || tok == token::TOKEN_LEN || tok == token::TOKEN_PKT4 || tok == token::TOKEN_CHADDR || tok == token::TOKEN_HLEN || tok == token::TOKEN_HTYPE || tok == token::TOKEN_CIADDR || tok == token::TOKEN_GIADDR || tok == token::TOKEN_YIADDR || tok == token::TOKEN_SIADDR || tok == token::TOKEN_SUBSTRING || tok == token::TOKEN_SPLIT || tok == token::TOKEN_ALL || tok == token::TOKEN_COMA || tok == token::TOKEN_CONCAT || tok == token::TOKEN_PLUS || tok == token::TOKEN_IFELSE || tok == token::TOKEN_TOHEXSTRING || tok == token::TOKEN_ADDRTOTEXT || tok == token::TOKEN_INT8TOTEXT || tok == token::TOKEN_INT16TOTEXT || tok == token::TOKEN_INT32TOTEXT || tok == token::TOKEN_UINT8TOTEXT || tok == token::TOKEN_UINT16TOTEXT || tok == token::TOKEN_UINT32TOTEXT || tok == token::TOKEN_PKT6 || tok == token::TOKEN_MSGTYPE || tok == token::TOKEN_TRANSID || tok == token::TOKEN_VENDOR_CLASS || tok == token::TOKEN_VENDOR || tok == token::TOKEN_ANY || tok == token::TOKEN_DATA || tok == token::TOKEN_ENTERPRISE || tok == token::TOKEN_TOPLEVEL_BOOL || tok == token::TOKEN_TOPLEVEL_STRING); + } #else symbol_type (int tok, const location_type& l) - : super_type (token_kind_type (tok), l) -#endif + : super_type(token_type (tok), l) { -#if !defined _MSC_VER || defined __clang__ - EVAL_ASSERT (tok == token::TOKEN_END - || (token::TOKEN_EVALerror <= tok && tok <= token::TOKEN_TOPLEVEL_STRING)); -#endif + YYASSERT (tok == token::TOKEN_END || tok == token::TOKEN_LPAREN || tok == token::TOKEN_RPAREN || tok == token::TOKEN_NOT || tok == token::TOKEN_AND || tok == token::TOKEN_OR || tok == token::TOKEN_EQUAL || tok == token::TOKEN_OPTION || tok == token::TOKEN_RELAY4 || tok == token::TOKEN_RELAY6 || tok == token::TOKEN_MEMBER || tok == token::TOKEN_PEERADDR || tok == token::TOKEN_LINKADDR || tok == token::TOKEN_LBRACKET || tok == token::TOKEN_RBRACKET || tok == token::TOKEN_DOT || tok == token::TOKEN_TEXT || tok == token::TOKEN_HEX || tok == token::TOKEN_EXISTS || tok == token::TOKEN_PKT || tok == token::TOKEN_IFACE || tok == token::TOKEN_SRC || tok == token::TOKEN_DST || tok == token::TOKEN_LEN || tok == token::TOKEN_PKT4 || tok == token::TOKEN_CHADDR || tok == token::TOKEN_HLEN || tok == token::TOKEN_HTYPE || tok == token::TOKEN_CIADDR || tok == token::TOKEN_GIADDR || tok == token::TOKEN_YIADDR || tok == token::TOKEN_SIADDR || tok == token::TOKEN_SUBSTRING || tok == token::TOKEN_SPLIT || tok == token::TOKEN_ALL || tok == token::TOKEN_COMA || tok == token::TOKEN_CONCAT || tok == token::TOKEN_PLUS || tok == token::TOKEN_IFELSE || tok == token::TOKEN_TOHEXSTRING || tok == token::TOKEN_ADDRTOTEXT || tok == token::TOKEN_INT8TOTEXT || tok == token::TOKEN_INT16TOTEXT || tok == token::TOKEN_INT32TOTEXT || tok == token::TOKEN_UINT8TOTEXT || tok == token::TOKEN_UINT16TOTEXT || tok == token::TOKEN_UINT32TOTEXT || tok == token::TOKEN_PKT6 || tok == token::TOKEN_MSGTYPE || tok == token::TOKEN_TRANSID || tok == token::TOKEN_VENDOR_CLASS || tok == token::TOKEN_VENDOR || tok == token::TOKEN_ANY || tok == token::TOKEN_DATA || tok == token::TOKEN_ENTERPRISE || tok == token::TOKEN_TOPLEVEL_BOOL || tok == token::TOKEN_TOPLEVEL_STRING); } +#endif #if 201103L <= YY_CPLUSPLUS symbol_type (int tok, std::string v, location_type l) - : super_type (token_kind_type (tok), std::move (v), std::move (l)) + : super_type(token_type (tok), std::move (v), std::move (l)) + { + YYASSERT (tok == token::TOKEN_STRING || tok == token::TOKEN_INTEGER || tok == token::TOKEN_HEXSTRING || tok == token::TOKEN_OPTION_NAME || tok == token::TOKEN_IP_ADDRESS); + } #else symbol_type (int tok, const std::string& v, const location_type& l) - : super_type (token_kind_type (tok), v, l) -#endif + : super_type(token_type (tok), v, l) { -#if !defined _MSC_VER || defined __clang__ - EVAL_ASSERT ((token::TOKEN_STRING <= tok && tok <= token::TOKEN_IP_ADDRESS)); -#endif + YYASSERT (tok == token::TOKEN_STRING || tok == token::TOKEN_INTEGER || tok == token::TOKEN_HEXSTRING || tok == token::TOKEN_OPTION_NAME || tok == token::TOKEN_IP_ADDRESS); } +#endif }; /// Build a parser object. EvalParser (EvalContext& ctx_yyarg); virtual ~EvalParser (); -#if 201103L <= YY_CPLUSPLUS - /// Non copyable. - EvalParser (const EvalParser&) = delete; - /// Non copyable. - EvalParser& operator= (const EvalParser&) = delete; -#endif - /// Parse. An alias for parse (). /// \returns 0 iff parsing succeeded. int operator() (); @@ -1115,11 +895,7 @@ switch (yykind) /// Report a syntax error. void error (const syntax_error& err); - /// The user-facing name of the symbol whose (internal) number is - /// YYSYMBOL. No bounds checking. - static std::string symbol_name (symbol_kind_type yysymbol); - - // Implementation of make_symbol for each token kind. + // Implementation of make_symbol for each symbol type. #if 201103L <= YY_CPLUSPLUS static symbol_type @@ -1135,36 +911,6 @@ switch (yykind) return symbol_type (token::TOKEN_END, l); } #endif -#if 201103L <= YY_CPLUSPLUS - static - symbol_type - make_EVALerror (location_type l) - { - return symbol_type (token::TOKEN_EVALerror, std::move (l)); - } -#else - static - symbol_type - make_EVALerror (const location_type& l) - { - return symbol_type (token::TOKEN_EVALerror, l); - } -#endif -#if 201103L <= YY_CPLUSPLUS - static - symbol_type - make_EVALUNDEF (location_type l) - { - return symbol_type (token::TOKEN_EVALUNDEF, std::move (l)); - } -#else - static - symbol_type - make_EVALUNDEF (const location_type& l) - { - return symbol_type (token::TOKEN_EVALUNDEF, l); - } -#endif #if 201103L <= YY_CPLUSPLUS static symbol_type @@ -1645,6 +1391,21 @@ switch (yykind) return symbol_type (token::TOKEN_SUBSTRING, l); } #endif +#if 201103L <= YY_CPLUSPLUS + static + symbol_type + make_SPLIT (location_type l) + { + return symbol_type (token::TOKEN_SPLIT, std::move (l)); + } +#else + static + symbol_type + make_SPLIT (const location_type& l) + { + return symbol_type (token::TOKEN_SPLIT, l); + } +#endif #if 201103L <= YY_CPLUSPLUS static symbol_type @@ -2067,119 +1828,93 @@ switch (yykind) #endif - class context - { - public: - context (const EvalParser& yyparser, const symbol_type& yyla); - const symbol_type& lookahead () const YY_NOEXCEPT { return yyla_; } - symbol_kind_type token () const YY_NOEXCEPT { return yyla_.kind (); } - const location_type& location () const YY_NOEXCEPT { return yyla_.location; } - - /// Put in YYARG at most YYARGN of the expected tokens, and return the - /// number of tokens stored in YYARG. If YYARG is null, return the - /// number of expected tokens (guaranteed to be less than YYNTOKENS). - int expected_tokens (symbol_kind_type yyarg[], int yyargn) const; - - private: - const EvalParser& yyparser_; - const symbol_type& yyla_; - }; - private: -#if YY_CPLUSPLUS < 201103L - /// Non copyable. + /// This class is not copyable. EvalParser (const EvalParser&); - /// Non copyable. EvalParser& operator= (const EvalParser&); -#endif - - /// Stored state numbers (used for stacks). - typedef unsigned char state_type; - - /// The arguments of the error message. - int yy_syntax_error_arguments_ (const context& yyctx, - symbol_kind_type yyarg[], int yyargn) const; + /// State numbers. + typedef int state_type; /// Generate an error message. - /// \param yyctx the context in which the error occurred. - virtual std::string yysyntax_error_ (const context& yyctx) const; + /// \param yystate the state where the error occurred. + /// \param yyla the lookahead token. + virtual std::string yysyntax_error_ (state_type yystate, + const symbol_type& yyla) const; + /// Compute post-reduction state. /// \param yystate the current state /// \param yysym the nonterminal to push on the stack - static state_type yy_lr_goto_state_ (state_type yystate, int yysym); + state_type yy_lr_goto_state_ (state_type yystate, int yysym); /// Whether the given \c yypact_ value indicates a defaulted state. /// \param yyvalue the value to check - static bool yy_pact_value_is_default_ (int yyvalue) YY_NOEXCEPT; + static bool yy_pact_value_is_default_ (int yyvalue); /// Whether the given \c yytable_ value indicates a syntax error. /// \param yyvalue the value to check - static bool yy_table_value_is_error_ (int yyvalue) YY_NOEXCEPT; + static bool yy_table_value_is_error_ (int yyvalue); static const short yypact_ninf_; static const signed char yytable_ninf_; - /// Convert a scanner token kind \a t to a symbol kind. - /// In theory \a t should be a token_kind_type, but character literals - /// are valid, yet not members of the token_kind_type enum. - static symbol_kind_type yytranslate_ (int t) YY_NOEXCEPT; - - /// Convert the symbol name \a n to a form suitable for a diagnostic. - static std::string yytnamerr_ (const char *yystr); + /// Convert a scanner token number \a t to a symbol number. + static token_number_type yytranslate_ (token_type t); - /// For a symbol, its name in clear. - static const char* const yytname_[]; + // Tables. + // YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing + // STATE-NUM. + static const short yypact_[]; + // YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM. + // Performed when YYTABLE does not specify something else to do. Zero + // means the default is an error. + static const unsigned char yydefact_[]; - // Tables. - // YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing - // STATE-NUM. - static const short yypact_[]; + // YYPGOTO[NTERM-NUM]. + static const short yypgoto_[]; - // YYDEFACT[STATE-NUM] -- Default reduction number in state STATE-NUM. - // Performed when YYTABLE does not specify something else to do. Zero - // means the default is an error. - static const signed char yydefact_[]; + // YYDEFGOTO[NTERM-NUM]. + static const short yydefgoto_[]; - // YYPGOTO[NTERM-NUM]. - static const short yypgoto_[]; + // YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM. If + // positive, shift that token. If negative, reduce the rule whose + // number is the opposite. If YYTABLE_NINF, syntax error. + static const unsigned char yytable_[]; - // YYDEFGOTO[NTERM-NUM]. - static const unsigned char yydefgoto_[]; + static const short yycheck_[]; - // YYTABLE[YYPACT[STATE-NUM]] -- What to do in state STATE-NUM. If - // positive, shift that token. If negative, reduce the rule whose - // number is the opposite. If YYTABLE_NINF, syntax error. - static const unsigned char yytable_[]; + // YYSTOS[STATE-NUM] -- The (internal number of the) accessing + // symbol of state STATE-NUM. + static const unsigned char yystos_[]; - static const unsigned char yycheck_[]; + // YYR1[YYN] -- Symbol number of symbol that rule YYN derives. + static const unsigned char yyr1_[]; - // YYSTOS[STATE-NUM] -- The symbol kind of the accessing symbol of - // state STATE-NUM. - static const signed char yystos_[]; + // YYR2[YYN] -- Number of symbols on the right hand side of rule YYN. + static const unsigned char yyr2_[]; - // YYR1[RULE-NUM] -- Symbol kind of the left-hand side of rule RULE-NUM. - static const signed char yyr1_[]; - // YYR2[RULE-NUM] -- Number of symbols on the right-hand side of rule RULE-NUM. - static const signed char yyr2_[]; + /// Convert the symbol name \a n to a form suitable for a diagnostic. + static std::string yytnamerr_ (const char *n); + /// For a symbol, its name in clear. + static const char* const yytname_[]; #if EVALDEBUG - // YYRLINE[YYN] -- Source line where rule number YYN was defined. - static const short yyrline_[]; + // YYRLINE[YYN] -- Source line where rule number YYN was defined. + static const unsigned short yyrline_[]; /// Report on the debug stream that the rule \a r is going to be reduced. - virtual void yy_reduce_print_ (int r) const; + virtual void yy_reduce_print_ (int r); /// Print the state stack on the debug stream. - virtual void yy_stack_print_ () const; + virtual void yystack_print_ (); /// Debugging level. int yydebug_; /// Debug stream. std::ostream* yycdebug_; - /// \brief Display a symbol kind, value and location. + /// \brief Display a symbol type, value and location. /// \param yyo The output stream. /// \param yysym The symbol. template @@ -2200,7 +1935,7 @@ switch (yykind) /// Default constructor. by_state () YY_NOEXCEPT; - /// The symbol kind as needed by the constructor. + /// The symbol type as needed by the constructor. typedef state_type kind_type; /// Constructor. @@ -2212,16 +1947,15 @@ switch (yykind) /// Record that this symbol is empty. void clear () YY_NOEXCEPT; - /// Steal the symbol kind from \a that. + /// Steal the symbol type from \a that. void move (by_state& that); - /// The symbol kind (corresponding to \a state). - /// \a symbol_kind::S_YYEMPTY when empty. - symbol_kind_type kind () const YY_NOEXCEPT; + /// The (internal) type number (corresponding to \a state). + /// \a empty_symbol when empty. + symbol_number_type type_get () const YY_NOEXCEPT; /// The state number used to denote an empty symbol. - /// We use the initial state, as it does not have a value. - enum { empty_state = 0 }; + enum { empty_state = -1 }; /// The state. /// \a empty when empty. @@ -2243,10 +1977,6 @@ switch (yykind) /// Assignment, needed by push_back by some old implementations. /// Moves the contents of that. stack_symbol_type& operator= (stack_symbol_type& that); - - /// Assignment, needed by push_back by other implementations. - /// Needed by some other old implementations. - stack_symbol_type& operator= (const stack_symbol_type& that); #endif }; @@ -2256,38 +1986,48 @@ switch (yykind) { public: // Hide our reversed order. - typedef typename S::iterator iterator; - typedef typename S::const_iterator const_iterator; + typedef typename S::reverse_iterator iterator; + typedef typename S::const_reverse_iterator const_iterator; typedef typename S::size_type size_type; - typedef typename std::ptrdiff_t index_type; - stack (size_type n = 200) YY_NOEXCEPT + stack (size_type n = 200) : seq_ (n) {} -#if 201103L <= YY_CPLUSPLUS - /// Non copyable. - stack (const stack&) = delete; - /// Non copyable. - stack& operator= (const stack&) = delete; -#endif + /// Random access. + /// + /// Index 0 returns the topmost element. + T& + operator[] (size_type i) + { + return seq_[size () - 1 - i]; + } + + /// Random access. + /// + /// Index 0 returns the topmost element. + T& + operator[] (int i) + { + return operator[] (size_type (i)); + } /// Random access. /// /// Index 0 returns the topmost element. const T& - operator[] (index_type i) const + operator[] (size_type i) const { - return seq_[size_type (size () - 1 - i)]; + return seq_[size () - 1 - i]; } /// Random access. /// /// Index 0 returns the topmost element. - T& - operator[] (index_type i) + const T& + operator[] (int i) const { - return seq_[size_type (size () - 1 - i)]; + return operator[] (size_type (i)); } /// Steal the contents of \a t. @@ -2302,7 +2042,7 @@ switch (yykind) /// Pop elements from the stack. void - pop (std::ptrdiff_t n = 1) YY_NOEXCEPT + pop (int n = 1) YY_NOEXCEPT { for (; 0 < n; --n) seq_.pop_back (); @@ -2316,53 +2056,49 @@ switch (yykind) } /// Number of elements on the stack. - index_type + size_type size () const YY_NOEXCEPT { - return index_type (seq_.size ()); + return seq_.size (); } /// Iterator on top of the stack (going downwards). const_iterator begin () const YY_NOEXCEPT { - return seq_.begin (); + return seq_.rbegin (); } /// Bottom of the stack. const_iterator end () const YY_NOEXCEPT { - return seq_.end (); + return seq_.rend (); } /// Present a slice of the top of a stack. class slice { public: - slice (const stack& stack, index_type range) YY_NOEXCEPT + slice (const stack& stack, int range) : stack_ (stack) , range_ (range) {} const T& - operator[] (index_type i) const + operator[] (int i) const { return stack_[range_ - i]; } private: const stack& stack_; - index_type range_; + int range_; }; private: -#if YY_CPLUSPLUS < 201103L - /// Non copyable. stack (const stack&); - /// Non copyable. stack& operator= (const stack&); -#endif /// The wrapped container. S seq_; }; @@ -2390,30 +2126,33 @@ switch (yykind) void yypush_ (const char* m, state_type s, YY_MOVE_REF (symbol_type) sym); /// Pop \a n symbols from the stack. - void yypop_ (int n = 1) YY_NOEXCEPT; + void yypop_ (int n = 1); /// Constants. enum { - yylast_ = 274, ///< Last index in yytable_. - yynnts_ = 17, ///< Number of nonterminal symbols. - yyfinal_ = 41 ///< Termination state number. + yyeof_ = 0, + yylast_ = 286, ///< Last index in yytable_. + yynnts_ = 18, ///< Number of nonterminal symbols. + yyfinal_ = 42, ///< Termination state number. + yyterror_ = 1, + yyerrcode_ = 256, + yyntokens_ = 64 ///< Number of tokens. }; // User arguments. EvalContext& ctx; - }; inline - EvalParser::symbol_kind_type - EvalParser::yytranslate_ (int t) YY_NOEXCEPT + EvalParser::token_number_type + EvalParser::yytranslate_ (token_type t) { // YYTRANSLATE[TOKEN-NUM] -- Symbol number corresponding to // TOKEN-NUM as returned by yylex. static - const signed char + const token_number_type translate_table[] = { 0, 2, 2, 2, 2, 2, 2, 2, 2, 2, @@ -2447,67 +2186,125 @@ switch (yykind) 25, 26, 27, 28, 29, 30, 31, 32, 33, 34, 35, 36, 37, 38, 39, 40, 41, 42, 43, 44, 45, 46, 47, 48, 49, 50, 51, 52, 53, 54, - 55, 56, 57, 58, 59, 60, 61, 62 + 55, 56, 57, 58, 59, 60, 61, 62, 63 }; - // Last valid token kind. - const int code_max = 317; + const unsigned user_token_number_max_ = 318; + const token_number_type undef_token_ = 2; - if (t <= 0) - return symbol_kind::S_YYEOF; - else if (t <= code_max) - return static_cast (translate_table[t]); + if (static_cast (t) <= yyeof_) + return yyeof_; + else if (static_cast (t) <= user_token_number_max_) + return translate_table[t]; else - return symbol_kind::S_YYUNDEF; + return undef_token_; } // basic_symbol. +#if 201103L <= YY_CPLUSPLUS + template + EvalParser::basic_symbol::basic_symbol (basic_symbol&& that) + : Base (std::move (that)) + , value () + , location (std::move (that.location)) + { + switch (this->type_get ()) + { + case 72: // option_repr_type + value.move< TokenOption::RepresentationType > (std::move (that.value)); + break; + + case 76: // pkt4_field + value.move< TokenPkt4::FieldType > (std::move (that.value)); + break; + + case 77: // pkt6_field + value.move< TokenPkt6::FieldType > (std::move (that.value)); + break; + + case 74: // pkt_metadata + value.move< TokenPkt::MetadataType > (std::move (that.value)); + break; + + case 78: // relay6_field + value.move< TokenRelay6Field::FieldType > (std::move (that.value)); + break; + + case 73: // nest_level + value.move< int8_t > (std::move (that.value)); + break; + + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" + value.move< std::string > (std::move (that.value)); + break; + + case 70: // option_code + case 71: // sub_option_code + value.move< uint16_t > (std::move (that.value)); + break; + + case 69: // integer_expr + case 75: // enterprise_id + value.move< uint32_t > (std::move (that.value)); + break; + + default: + break; + } + + } +#endif + template EvalParser::basic_symbol::basic_symbol (const basic_symbol& that) : Base (that) , value () , location (that.location) { - switch (this->kind ()) + switch (this->type_get ()) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type value.copy< TokenOption::RepresentationType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field value.copy< TokenPkt4::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field value.copy< TokenPkt6::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata value.copy< TokenPkt::MetadataType > (YY_MOVE (that.value)); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field value.copy< TokenRelay6Field::FieldType > (YY_MOVE (that.value)); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level value.copy< int8_t > (YY_MOVE (that.value)); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" value.copy< std::string > (YY_MOVE (that.value)); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code value.copy< uint16_t > (YY_MOVE (that.value)); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id value.copy< uint32_t > (YY_MOVE (that.value)); break; @@ -2519,20 +2316,11 @@ switch (yykind) - - template - EvalParser::symbol_kind_type - EvalParser::basic_symbol::type_get () const YY_NOEXCEPT - { - return this->kind (); - } - - template bool EvalParser::basic_symbol::empty () const YY_NOEXCEPT { - return this->kind () == symbol_kind::S_YYEMPTY; + return Base::type_get () == empty_symbol; } template @@ -2540,47 +2328,47 @@ switch (yykind) EvalParser::basic_symbol::move (basic_symbol& s) { super_type::move (s); - switch (this->kind ()) + switch (this->type_get ()) { - case symbol_kind::S_option_repr_type: // option_repr_type + case 72: // option_repr_type value.move< TokenOption::RepresentationType > (YY_MOVE (s.value)); break; - case symbol_kind::S_pkt4_field: // pkt4_field + case 76: // pkt4_field value.move< TokenPkt4::FieldType > (YY_MOVE (s.value)); break; - case symbol_kind::S_pkt6_field: // pkt6_field + case 77: // pkt6_field value.move< TokenPkt6::FieldType > (YY_MOVE (s.value)); break; - case symbol_kind::S_pkt_metadata: // pkt_metadata + case 74: // pkt_metadata value.move< TokenPkt::MetadataType > (YY_MOVE (s.value)); break; - case symbol_kind::S_relay6_field: // relay6_field + case 78: // relay6_field value.move< TokenRelay6Field::FieldType > (YY_MOVE (s.value)); break; - case symbol_kind::S_nest_level: // nest_level + case 73: // nest_level value.move< int8_t > (YY_MOVE (s.value)); break; - case symbol_kind::S_STRING: // "constant string" - case symbol_kind::S_INTEGER: // "integer" - case symbol_kind::S_HEXSTRING: // "constant hexstring" - case symbol_kind::S_OPTION_NAME: // "option name" - case symbol_kind::S_IP_ADDRESS: // "ip address" + case 59: // "constant string" + case 60: // "integer" + case 61: // "constant hexstring" + case 62: // "option name" + case 63: // "ip address" value.move< std::string > (YY_MOVE (s.value)); break; - case symbol_kind::S_option_code: // option_code - case symbol_kind::S_sub_option_code: // sub_option_code + case 70: // option_code + case 71: // sub_option_code value.move< uint16_t > (YY_MOVE (s.value)); break; - case symbol_kind::S_integer_expr: // integer_expr - case symbol_kind::S_enterprise_id: // enterprise_id + case 69: // integer_expr + case 75: // enterprise_id value.move< uint32_t > (YY_MOVE (s.value)); break; @@ -2591,67 +2379,77 @@ switch (yykind) location = YY_MOVE (s.location); } - // by_kind. + // by_type. inline - EvalParser::by_kind::by_kind () YY_NOEXCEPT - : kind_ (symbol_kind::S_YYEMPTY) + EvalParser::by_type::by_type () + : type (empty_symbol) {} #if 201103L <= YY_CPLUSPLUS inline - EvalParser::by_kind::by_kind (by_kind&& that) YY_NOEXCEPT - : kind_ (that.kind_) + EvalParser::by_type::by_type (by_type&& that) + : type (that.type) { that.clear (); } #endif inline - EvalParser::by_kind::by_kind (const by_kind& that) YY_NOEXCEPT - : kind_ (that.kind_) + EvalParser::by_type::by_type (const by_type& that) + : type (that.type) {} inline - EvalParser::by_kind::by_kind (token_kind_type t) YY_NOEXCEPT - : kind_ (yytranslate_ (t)) + EvalParser::by_type::by_type (token_type t) + : type (yytranslate_ (t)) {} - - inline void - EvalParser::by_kind::clear () YY_NOEXCEPT + EvalParser::by_type::clear () { - kind_ = symbol_kind::S_YYEMPTY; + type = empty_symbol; } inline void - EvalParser::by_kind::move (by_kind& that) + EvalParser::by_type::move (by_type& that) { - kind_ = that.kind_; + type = that.type; that.clear (); } inline - EvalParser::symbol_kind_type - EvalParser::by_kind::kind () const YY_NOEXCEPT + int + EvalParser::by_type::type_get () const YY_NOEXCEPT { - return kind_; + return type; } - inline - EvalParser::symbol_kind_type - EvalParser::by_kind::type_get () const YY_NOEXCEPT + EvalParser::token_type + EvalParser::by_type::token () const YY_NOEXCEPT { - return this->kind (); + // YYTOKNUM[NUM] -- (External) token number corresponding to the + // (internal) symbol number NUM (which must be that of a token). */ + static + const unsigned short + yytoken_number_[] = + { + 0, 256, 257, 258, 259, 260, 261, 262, 263, 264, + 265, 266, 267, 268, 269, 270, 271, 272, 273, 274, + 275, 276, 277, 278, 279, 280, 281, 282, 283, 284, + 285, 286, 287, 288, 289, 290, 291, 292, 293, 294, + 295, 296, 297, 298, 299, 300, 301, 302, 303, 304, + 305, 306, 307, 308, 309, 310, 311, 312, 313, 314, + 315, 316, 317, 318 + }; + return token_type (yytoken_number_[type]); } - -#line 14 "parser.yy" +#line 14 "parser.yy" // lalr1.cc:401 } } // isc::eval -#line 2655 "parser.h" +#line 2453 "parser.h" // lalr1.cc:401 diff --git a/src/lib/eval/parser.yy b/src/lib/eval/parser.yy index 6a5ffd6a52..d762e66b09 100644 --- a/src/lib/eval/parser.yy +++ b/src/lib/eval/parser.yy @@ -1,4 +1,4 @@ -/* Copyright (C) 2015-2021 Internet Systems Consortium, Inc. ("ISC") +/* Copyright (C) 2015-2022 Internet Systems Consortium, Inc. ("ISC") This Source Code Form is subject to the terms of the Mozilla Public License, v. 2.0. If a copy of the MPL was not distributed with this @@ -70,6 +70,7 @@ using namespace isc::eval; YIADDR "yiaddr" SIADDR "siaddr" SUBSTRING "substring" + SPLIT "split" ALL "all" COMA "," CONCAT "concat" @@ -360,6 +361,11 @@ string_expr : STRING TokenPtr sub(new TokenSubstring()); ctx.expression.push_back(sub); } + | SPLIT "(" string_expr "," string_expr "," int_expr ")" + { + TokenPtr split(new TokenSplit()); + ctx.expression.push_back(split); + } | CONCAT "(" string_expr "," string_expr ")" { TokenPtr conc(new TokenConcat()); @@ -622,6 +628,12 @@ length_expr : INTEGER ctx.expression.push_back(str); } ; +int_expr : INTEGER + { + TokenPtr str(new TokenString($1)); + ctx.expression.push_back(str); + } + ; %% void diff --git a/src/lib/eval/tests/token_unittest.cc b/src/lib/eval/tests/token_unittest.cc index 620372ac92..a7d798a9f0 100644 --- a/src/lib/eval/tests/token_unittest.cc +++ b/src/lib/eval/tests/token_unittest.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2015-2019,2021 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2015-2022 Internet Systems Consortium, Inc. ("ISC") // // This Source Code Form is subject to the terms of the Mozilla Public // License, v. 2.0. If a copy of the MPL was not distributed with this @@ -20,6 +20,9 @@ #include #include +#include +#include +#include #include #include #include @@ -255,6 +258,45 @@ public: } } + /// @brief Verify that the split eval works properly + /// + /// This function takes the parameters and sets up the value + /// stack then executes the eval and checks the results. + /// + /// @param test_string The string to operate on + /// @param test_delimiters The string of delimiter characters to split upon + /// @param test_field The field number of the desired field + /// @param result_string The expected result of the eval + /// @param should_throw The eval will throw + void verifySplitEval(const std::string& test_string, + const std::string& test_delimeters, + const std::string& test_field, + const std::string& result_string, + bool should_throw = false) { + // create the token + ASSERT_NO_THROW(t_.reset(new TokenSplit())); + + // push values on stack + values_.push(test_string); + values_.push(test_delimeters); + values_.push(test_field); + + // evaluate the token + if (should_throw) { + EXPECT_THROW(t_->evaluate(*pkt4_, values_), EvalTypeError); + ASSERT_EQ(0, values_.size()); + } else { + EXPECT_NO_THROW(t_->evaluate(*pkt4_, values_)); + + // verify results + ASSERT_EQ(1, values_.size()); + EXPECT_EQ(result_string, values_.top()); + + // remove result + values_.pop(); + } + } + /// @brief Creates vendor-option with specified value and adds it to packet /// /// This method creates specified vendor option, removes any existing @@ -3324,4 +3366,114 @@ TEST_F(TokenTest, integer) { testInteger(encode(4294967295), 4294967295); } +// Verify TokenSplit::eval, single delimeter. +TEST_F(TokenTest, split) { + // Get the whole string + std::string input(".two.three..five."); + std::string delims("."); + + // Empty input string should yield empty result. + verifySplitEval("", delims, "1", ""); + + // Empty delimiters string should original string result. + verifySplitEval(input, "", "1", input); + + // Field number less than one yield empty result. + verifySplitEval(input, delims, "0", ""); + + // Now get each field in succession. + verifySplitEval(input, delims, "1", ""); + verifySplitEval(input, delims, "2", "two"); + verifySplitEval(input, delims, "3", "three"); + verifySplitEval(input, delims, "4", ""); + verifySplitEval(input, delims, "5", "five"); + verifySplitEval(input, delims, "6", ""); + + // Too large of a field should yield empty result. + verifySplitEval(input, delims, "7", ""); + + // A string without delimiters returns as field 1. + verifySplitEval("just_one", delims, "1", "just_one"); + + // Check that the debug output was correct. Add the strings + // to the test vector in the class and then call checkFile + // for comparison + addString("EVAL_DEBUG_SPLIT_EMPTY Popping field 1, delimiters .," + " string , pushing result 0x"); + addString("EVAL_DEBUG_SPLIT_DELIM_EMPTY Popping field 1, delimiters ," + " string .two.three..five., pushing result 0x2E74776F2E74687265652E2E666976652E"); + addString("EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE Popping field 0, delimiters .," + " string .two.three..five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 1, delimiters .," + " string .two.three..five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 2, delimiters .," + " string .two.three..five., pushing result 0x74776F"); + addString("EVAL_DEBUG_SPLIT Popping field 3, delimiters .," + " string .two.three..five., pushing result 0x7468726565"); + addString("EVAL_DEBUG_SPLIT Popping field 4, delimiters .," + " string .two.three..five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 5, delimiters .," + " string .two.three..five., pushing result 0x66697665"); + addString("EVAL_DEBUG_SPLIT Popping field 6, delimiters .," + " string .two.three..five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE Popping field 7, delimiters .," + " string .two.three..five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 1, delimiters .," + " string just_one, pushing result 0x6A7573745F6F6E65"); + EXPECT_TRUE(checkFile()); +} + +// Verify TokenSplit::eval with more than one delimeter. +TEST_F(TokenTest, splitMultipleDelims) { + // Get the whole string + std::string input(".two:three.:five."); + std::string delims(".:"); + + // Empty input string should yield empty result. + verifySplitEval("", delims, "1", ""); + + // Too small of a field should yield empty result. + verifySplitEval(input, delims, "0", ""); + + // Now get each field in succession. + verifySplitEval(input, delims, "1", ""); + verifySplitEval(input, delims, "2", "two"); + verifySplitEval(input, delims, "3", "three"); + verifySplitEval(input, delims, "4", ""); + verifySplitEval(input, delims, "5", "five"); + verifySplitEval(input, delims, "6", ""); + + // Too large of a field should yield empty result. + verifySplitEval(input, delims, "7", ""); + + // A string without delimiters returns as field 1. + verifySplitEval("just_one", delims, "1", "just_one"); + + // Check that the debug output was correct. Add the strings + // to the test vector in the class and then call checkFile + // for comparison + + addString("EVAL_DEBUG_SPLIT_EMPTY Popping field 1, delimiters .:," + " string , pushing result 0x"); + addString("EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE Popping field 0, delimiters .:," + " string .two:three.:five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 1, delimiters .:," + " string .two:three.:five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 2, delimiters .:," + " string .two:three.:five., pushing result 0x74776F"); + addString("EVAL_DEBUG_SPLIT Popping field 3, delimiters .:," + " string .two:three.:five., pushing result 0x7468726565"); + addString("EVAL_DEBUG_SPLIT Popping field 4, delimiters .:," + " string .two:three.:five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 5, delimiters .:," + " string .two:three.:five., pushing result 0x66697665"); + addString("EVAL_DEBUG_SPLIT Popping field 6, delimiters .:," + " string .two:three.:five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE Popping field 7, delimiters .:," + " string .two:three.:five., pushing result 0x"); + addString("EVAL_DEBUG_SPLIT Popping field 1, delimiters .:," + " string just_one, pushing result 0x6A7573745F6F6E65"); + EXPECT_TRUE(checkFile()); +} + }; diff --git a/src/lib/eval/token.cc b/src/lib/eval/token.cc index bec3c66c06..0784301583 100644 --- a/src/lib/eval/token.cc +++ b/src/lib/eval/token.cc @@ -1,4 +1,4 @@ -// Copyright (C) 2015-2021 Internet Systems Consortium, Inc. ("ISC") +// Copyright (C) 2015-2022 Internet Systems Consortium, Inc. ("ISC") // // This Source Code Form is subject to the terms of the Mozilla Public // License, v. 2.0. If a copy of the MPL was not distributed with this @@ -19,6 +19,10 @@ #include #include #include + +#include +#include + #include #include #include @@ -775,6 +779,90 @@ TokenSubstring::evaluate(Pkt& /*pkt*/, ValueStack& values) { .arg(toHex(values.top())); } +void +TokenSplit::evaluate(Pkt& /*pkt*/, ValueStack& values) { + if (values.size() < 3) { + isc_throw(EvalBadStack, "Incorrect stack order. Expected at least " + "3 values for split operator, got " << values.size()); + } + + // Pop the parameters. + string field_str = values.top(); + values.pop(); + string delim_str = values.top(); + values.pop(); + string string_str = values.top(); + values.pop(); + + // If we have no string to start with we push an empty string and leave + if (string_str.empty()) { + values.push(""); + + // Log what we popped and pushed + LOG_DEBUG(eval_logger, EVAL_DBG_STACK, EVAL_DEBUG_SPLIT_EMPTY) + .arg(field_str) + .arg(delim_str) + .arg(string_str) + .arg("0x"); + return; + } + + // Convert the starting position and length from strings to numbers + // the length may also be "all" in which case simply make it the + // length of the string. + // If we have a problem push an empty string and leave + int field; + try { + field = boost::lexical_cast(field_str); + } catch (const boost::bad_lexical_cast&) { + isc_throw(EvalTypeError, "the parameter '" << field_str + << "' for the field field for split " + << "couldn't be converted to an integer."); + } + + // If we have no string to start with we push an empty string and leave + if (delim_str.empty()) { + values.push(string_str); + + // Log what we popped and pushed + LOG_DEBUG(eval_logger, EVAL_DBG_STACK, EVAL_DEBUG_SPLIT_DELIM_EMPTY) + .arg(field_str) + .arg(delim_str) + .arg(string_str) + .arg(toHex(values.top())); + return; + } + + // Split the string into fields. + std::vector fields; + boost::split(fields, string_str, boost::is_any_of(delim_str), + boost::algorithm::token_compress_off); + + // Range check the field. + if (field < 1 || field > fields.size()) { + // Push an empty string if field is out of range. + values.push(""); + + // Log what we popped and pushed + LOG_DEBUG(eval_logger, EVAL_DBG_STACK, EVAL_DEBUG_SPLIT_FIELD_OUT_OF_RANGE) + .arg(field_str) + .arg(delim_str) + .arg(string_str) + .arg("0x"); + return; + } + + // Push the desired field. + values.push(fields[field - 1]); + + // Log what we popped and pushed + LOG_DEBUG(eval_logger, EVAL_DBG_STACK, EVAL_DEBUG_SPLIT) + .arg(field_str) + .arg(delim_str) + .arg(string_str) + .arg(toHex(values.top())); +} + void TokenConcat::evaluate(Pkt& /*pkt*/, ValueStack& values) { if (values.size() < 2) { diff --git a/src/lib/eval/token.h b/src/lib/eval/token.h index 9185cbc2b9..71a3d724b8 100644 --- a/src/lib/eval/token.h +++ b/src/lib/eval/token.h @@ -453,7 +453,7 @@ protected: /// encapsulation /// /// This represents a reference to a given option similar to TokenOption -/// but from within the information from a relay. In the expresssion +/// but from within the information from a relay. In the expression /// relay6[nest-level].option[option-code], nest-level indicates which /// of the relays to examine and option-code which option to extract. /// @@ -795,6 +795,50 @@ public: void evaluate(Pkt& pkt, ValueStack& values); }; +class TokenSplit : public Token { +public: + /// @brief Constructor (does nothing) + TokenSplit() {} + + /// @brief Extract a field from a delimited string + /// + /// Evaluation does not use packet information. It requires at least + /// three values to be present on the stack. It will consume the top + /// three values on the stack as parameters and push the resulting substring + /// onto the stack. From the top it expects the values on the stack as: + /// - field + /// - delims + /// - str + /// + /// str is the string to split. If it is empty, an empty + /// string is pushed onto the value stack. + /// delims is string of character delimiters by which to split str. If it is + /// empty the entire value of str will be pushed on onto the value stack. + /// field is the field number (starting at 1) of the desired field. If it is + /// out of range an empty string is pushed on the the value stack. + /// + /// The following examples all use the base string "one.two..four" and shows + /// the value returned for a given field: + /// ``` + /// field => value + /// -------------- + /// - 0 => "" + /// - 1 => "one" + /// - 2 => "two" + /// - 3 => "" + /// - 4 => "four" + /// - 5 => "" + /// ``` + /// + /// @throw EvalBadStack if there are less than 3 values on stack + /// @throw EvalTypeError if field is not a number + /// + /// @param pkt (unused) + /// @param values - stack of values (3 arguments will be popped, 1 result + /// will be pushed) + void evaluate(Pkt& pkt, ValueStack& values); +}; + /// @brief Token that represents concat operator (concatenates two other tokens) /// /// For example in the sub-expression "concat('foo','bar')" the result -- cgit v1.2.3