65 lines
1.2 KiB
C
65 lines
1.2 KiB
C
|
|
#include "ctx.h"
|
||
|
|
|
||
|
|
#include <ivy/lang/ast.h>
|
||
|
|
|
||
|
|
bool parse_fstring(struct ivy_parser *parser, struct ivy_ast_node **out)
|
||
|
|
{
|
||
|
|
if (!parse_str_start(parser)) {
|
||
|
|
parse_trace(parser, "expected STR_START");
|
||
|
|
return false;
|
||
|
|
}
|
||
|
|
|
||
|
|
struct ivy_ast_fstring_node *fstring = create_node(IVY_AST_FSTRING);
|
||
|
|
bool ok = true;
|
||
|
|
|
||
|
|
while (1) {
|
||
|
|
if (parse_str_end(parser)) {
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
struct ivy_token *tok = NULL;
|
||
|
|
if (parse_string(parser, &tok)) {
|
||
|
|
struct ivy_ast_string_node *string
|
||
|
|
= create_node(IVY_AST_STRING);
|
||
|
|
string->n_value = tok;
|
||
|
|
fx_queue_push_back(
|
||
|
|
&fstring->n_value, &string->n_base.n_entry);
|
||
|
|
continue;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (parse_symbol(parser, IVY_SYM_LEFT_BRACE)) {
|
||
|
|
struct ivy_ast_node *expr = NULL;
|
||
|
|
if (!parse_expr(parser, EXPR_PARSE_NORMAL, &expr)) {
|
||
|
|
parse_trace(
|
||
|
|
parser,
|
||
|
|
"invalid expression in fstring");
|
||
|
|
ok = false;
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (!parse_symbol(parser, IVY_SYM_RIGHT_BRACE)) {
|
||
|
|
parse_trace(
|
||
|
|
parser,
|
||
|
|
"expected `}` after expression in "
|
||
|
|
"fstring");
|
||
|
|
ok = false;
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
fx_queue_push_back(&fstring->n_value, &expr->n_entry);
|
||
|
|
continue;
|
||
|
|
}
|
||
|
|
|
||
|
|
parse_trace(parser, "unexpected token in fstring");
|
||
|
|
ok = false;
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (!ok) {
|
||
|
|
return ok;
|
||
|
|
}
|
||
|
|
|
||
|
|
*out = generic_node(fstring);
|
||
|
|
return ok;
|
||
|
|
}
|