expected tokens vararg
This commit is contained in:
parent
6e155817dd
commit
5742e9af6b
34
parser.c
34
parser.c
@ -1,5 +1,6 @@
|
|||||||
#include <stdlib.h>
|
#include <stdlib.h>
|
||||||
#include <stdio.h>
|
#include <stdio.h>
|
||||||
|
#include <stdarg.h>
|
||||||
#include "parser.h"
|
#include "parser.h"
|
||||||
|
|
||||||
/* Vrátí ukazatel na aktuální token */
|
/* Vrátí ukazatel na aktuální token */
|
||||||
@ -42,8 +43,9 @@ static void error_bad_alloc(struct parser *parser) {
|
|||||||
error_printf(&parser->eb, "Out of memory\n");
|
error_printf(&parser->eb, "Out of memory\n");
|
||||||
}
|
}
|
||||||
|
|
||||||
static void error_expected_one_of(struct parser *parser, const int expected[]) {
|
static void error_expected_tokens(struct parser *parser, size_t num_tokens, ...) {
|
||||||
size_t i;
|
size_t i;
|
||||||
|
va_list ap;
|
||||||
|
|
||||||
enum token_type got = get_token(parser)->type;
|
enum token_type got = get_token(parser)->type;
|
||||||
|
|
||||||
@ -56,24 +58,22 @@ static void error_expected_one_of(struct parser *parser, const int expected[]) {
|
|||||||
error_set(&parser->eb, ERR_INVALID_FUNCTION);
|
error_set(&parser->eb, ERR_INVALID_FUNCTION);
|
||||||
error_printf(&parser->eb, "Syntax error - expected ");
|
error_printf(&parser->eb, "Syntax error - expected ");
|
||||||
|
|
||||||
for (i = 0; expected[i] >= 0; ++i) {
|
va_start(ap, num_tokens);
|
||||||
|
for (i = 0; i < num_tokens; ++i) {
|
||||||
|
enum token_type tok = va_arg(ap, enum token_type);
|
||||||
|
|
||||||
if (i > 0)
|
if (i > 0)
|
||||||
error_printf(&parser->eb, ", ");
|
error_printf(&parser->eb, ", ");
|
||||||
|
|
||||||
error_printf(&parser->eb, "%s", lex_token_str(expected[i]));
|
error_printf(&parser->eb, "%s", lex_token_str(tok));
|
||||||
}
|
}
|
||||||
|
va_end(ap);
|
||||||
|
|
||||||
error_printf(&parser->eb, " - but got %s\n", lex_token_str(got));
|
error_printf(&parser->eb, " - but got %s\n", lex_token_str(got));
|
||||||
|
|
||||||
lex_print_position(&parser->lexer, &parser->eb);
|
lex_print_position(&parser->lexer, &parser->eb);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void error_expected_single(struct parser *parser, enum token_type expected) {
|
|
||||||
static int expected_arr[] = { -1, -1 };
|
|
||||||
expected_arr[0] = expected;
|
|
||||||
error_expected_one_of(parser, expected_arr);
|
|
||||||
}
|
|
||||||
|
|
||||||
static struct expr_node* parse_subexpression(struct parser *parser);
|
static struct expr_node* parse_subexpression(struct parser *parser);
|
||||||
int parse_n_expressions(struct parser *parser, struct expr_node **out_nodes, size_t n);
|
int parse_n_expressions(struct parser *parser, struct expr_node **out_nodes, size_t n);
|
||||||
|
|
||||||
@ -81,7 +81,7 @@ static struct expr_node* parse_bracketed(struct parser *parser) {
|
|||||||
struct expr_node* node;
|
struct expr_node* node;
|
||||||
|
|
||||||
if (!accept_token(parser, TOK_LEFT_PAREN)) {
|
if (!accept_token(parser, TOK_LEFT_PAREN)) {
|
||||||
error_expected_single(parser, TOK_LEFT_PAREN);
|
error_expected_tokens(parser, 1, TOK_LEFT_PAREN);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -89,7 +89,7 @@ static struct expr_node* parse_bracketed(struct parser *parser) {
|
|||||||
return NULL;
|
return NULL;
|
||||||
|
|
||||||
if (!accept_token(parser, TOK_RIGHT_PAREN)) {
|
if (!accept_token(parser, TOK_RIGHT_PAREN)) {
|
||||||
error_expected_single(parser, TOK_RIGHT_PAREN);
|
error_expected_tokens(parser, 1, TOK_RIGHT_PAREN);
|
||||||
node_free(node);
|
node_free(node);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@ -128,7 +128,7 @@ static struct expr_node *parse_base(struct parser *parser) {
|
|||||||
next_token(parser);
|
next_token(parser);
|
||||||
|
|
||||||
if (!accept_token(parser, TOK_LEFT_PAREN)) {
|
if (!accept_token(parser, TOK_LEFT_PAREN)) {
|
||||||
error_expected_single(parser, TOK_LEFT_PAREN);
|
error_expected_tokens(parser, 1, TOK_LEFT_PAREN);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -145,7 +145,7 @@ static struct expr_node *parse_base(struct parser *parser) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
if (!accept_token(parser, TOK_RIGHT_PAREN)) {
|
if (!accept_token(parser, TOK_RIGHT_PAREN)) {
|
||||||
error_expected_single(parser, TOK_RIGHT_PAREN);
|
error_expected_tokens(parser, 1, TOK_RIGHT_PAREN);
|
||||||
node_free(node);
|
node_free(node);
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
@ -157,11 +157,7 @@ static struct expr_node *parse_base(struct parser *parser) {
|
|||||||
return parse_bracketed(parser);
|
return parse_bracketed(parser);
|
||||||
}
|
}
|
||||||
|
|
||||||
{
|
error_expected_tokens(parser, 4, TOK_NUMBER, TOK_VARIABLE, TOK_FUNCTION, TOK_LEFT_PAREN);
|
||||||
static const int expected[] = { TOK_NUMBER, TOK_VARIABLE, TOK_FUNCTION, TOK_LEFT_PAREN, -1 };
|
|
||||||
error_expected_one_of(parser, expected);
|
|
||||||
}
|
|
||||||
|
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -317,7 +313,7 @@ int parser_parse_n(struct parser *parser, const char *str, const char *variable_
|
|||||||
|
|
||||||
if (!token_is(parser, TOK_EOF)) {
|
if (!token_is(parser, TOK_EOF)) {
|
||||||
size_t i;
|
size_t i;
|
||||||
error_expected_single(parser, TOK_EOF);
|
error_expected_tokens(parser, 1, TOK_EOF);
|
||||||
|
|
||||||
for (i = 0; i < n; ++i) {
|
for (i = 0; i < n; ++i) {
|
||||||
node_free(out_nodes[i]);
|
node_free(out_nodes[i]);
|
||||||
|
|||||||
Loading…
x
Reference in New Issue
Block a user