@@ -63,6 +63,7 @@ int mysql_yylex(union MYSQL_YYSTYPE* yylval_param, yyscan_t yyscanner, MysqlPars
6363/* TOKEN_FIELDS is already declared */
6464/* TOKEN_FULL is already declared */
6565%token TOKEN_BEGIN TOKEN_COMMIT /* Added for BEGIN/COMMIT */
66+ %token TOKEN_IS TOKEN_NULL_KEYWORD TOKEN_NOT /* Added for IS NULL / IS NOT NULL */
6667
6768
6869%token <str_val> TOKEN_QUIT
@@ -113,11 +114,11 @@ int mysql_yylex(union MYSQL_YYSTYPE* yylval_param, yyscan_t yyscanner, MysqlPars
113114%type <node_val> values_clause value_row_list value_row expression_list
114115
115116// Precedence
116- %left TOKEN_OR // Assuming OR might be added
117+ %left TOKEN_OR
117118%left TOKEN_AND
118- %right TOKEN_NOT // Assuming NOT might be added
119+ %right TOKEN_NOT // For logical NOT
119120
120- %left TOKEN_EQUAL TOKEN_LESS TOKEN_GREATER TOKEN_LESS_EQUAL TOKEN_GREATER_EQUAL TOKEN_NOT_EQUAL
121+ %left TOKEN_EQUAL TOKEN_LESS TOKEN_GREATER TOKEN_LESS_EQUAL TOKEN_GREATER_EQUAL TOKEN_NOT_EQUAL TOKEN_IS // Added TOKEN_IS
121122
122123%left TOKEN_PLUS TOKEN_MINUS
123124%left TOKEN_ASTERISK TOKEN_DIVIDE
@@ -1210,10 +1211,18 @@ expression_placeholder:
12101211 }
12111212 | expression_placeholder comparison_operator expression_placeholder {
12121213 $$ = new MysqlParser::AstNode(MysqlParser::NodeType::NODE_COMPARISON_EXPRESSION, $2->value);
1213- delete $2; // $2 is operator node, its value copied
1214+ delete $2;
12141215 $$->addChild($1);
12151216 $$->addChild($3);
12161217 }
1218+ | expression_placeholder TOKEN_IS TOKEN_NULL_KEYWORD { // Covers `expr IS NULL`
1219+ $$ = new MysqlParser::AstNode(MysqlParser::NodeType::NODE_IS_NULL_EXPRESSION);
1220+ $$->addChild($1); // The expression part
1221+ }
1222+ | expression_placeholder TOKEN_IS TOKEN_NOT TOKEN_NULL_KEYWORD { // Covers `expr IS NOT NULL`
1223+ $$ = new MysqlParser::AstNode(MysqlParser::NodeType::NODE_IS_NOT_NULL_EXPRESSION);
1224+ $$->addChild($1); // The expression part
1225+ }
12171226 | match_against_expression { $$ = $1; }
12181227 ;
12191228
@@ -1227,7 +1236,7 @@ simple_expression:
12271236 | TOKEN_DEFAULT { $$ = new MysqlParser::AstNode(MysqlParser::NodeType::NODE_KEYWORD, "DEFAULT"); }
12281237 | aggregate_function_call { $$ = $1; }
12291238 | function_call_placeholder {$$ = $1; }
1230- | TOKEN_LPAREN expression_placeholder TOKEN_RPAREN { $$ = $2; }
1239+ | TOKEN_LPAREN expression_placeholder TOKEN_RPAREN { $$ = $2; } // Important for `(expr IS NOT NULL)`
12311240 | simple_expression TOKEN_PLUS simple_expression {
12321241 $$ = new MysqlParser::AstNode(MysqlParser::NodeType::NODE_OPERATOR, "+");
12331242 $$->addChild($1); $$->addChild($3);
@@ -1333,3 +1342,4 @@ opt_expression_placeholder_list:
13331342// }
13341343// The default yyerror or the one provided by %define parse.error verbose should be sufficient.
13351344// If you need custom error formatting or location tracking, you'd define mysql_yyerror here.
1345+
0 commit comments