diff --git a/src/parser/SolsNode.h b/src/parser/SolsNode.h index cbc4075..5e2aef7 100644 --- a/src/parser/SolsNode.h +++ b/src/parser/SolsNode.h @@ -11,7 +11,17 @@ #include "../lexer/SolsToken.h" typedef enum SolsNodeType { - SNT_IDENTIFIER, SNT_LITERAL, SNT_TYPE, SNT_CODE_BLOCK, SNT_OP_ADD, SNT_OP_SUB, SNT_OP_MUL, SNT_OP_DIV, SNT_OP_ADDTO, SNT_OP_SUBTO, SNT_OP_MULTO, SNT_OP_DIVTO, SNT_OP_INCREMENT, SNT_OP_DECREMENT, SNT_OP_SET, SNT_OP_GREATER, SNT_OP_LESSER, SNT_OP_EQUAL, SNT_OP_INEQUAL, SNT_OP_EQGREATER, SNT_OP_EQLESSER, SNT_DEF, SNT_LAMBDA, SNT_FUNCTION_CALL, SNT_RETURN, SNT_USE, SNT_STRUCT, SNT_PUTS, SNT_IF, SNT_WHILE, SNT_NEW, SNT_GROUND, SNT_ROOT + SNT_IDENTIFIER, SNT_LITERAL, SNT_TYPE, + SNT_CODE_BLOCK, + SNT_OP_ADD, SNT_OP_SUB, SNT_OP_MUL, SNT_OP_DIV, + SNT_OP_ADDTO, SNT_OP_SUBTO, SNT_OP_MULTO, SNT_OP_DIVTO, + SNT_OP_INCREMENT, SNT_OP_DECREMENT, + SNT_OP_SET, + SNT_OP_GREATER, SNT_OP_LESSER, SNT_OP_EQUAL, SNT_OP_INEQUAL, SNT_OP_EQGREATER, SNT_OP_EQLESSER, + SNT_DEF, SNT_LAMBDA, SNT_FUNCTION_CALL, SNT_RETURN, + SNT_USE, SNT_STRUCT, + SNT_PUTS, SNT_IF, SNT_WHILE, SNT_NEW, + SNT_GROUND, SNT_ROOT, SNT_EXPR_IN_PAREN } SolsNodeType; struct SolsNode; diff --git a/src/parser/parser.c b/src/parser/parser.c index 2a1cc86..68150ae 100644 --- a/src/parser/parser.c +++ b/src/parser/parser.c @@ -1607,12 +1607,70 @@ static inline ResultType(Nothing, charptr) parseInlineGround(SolsParser* parser) } static inline ResultType(Nothing, charptr) parseOpenParen(SolsParser* parser) { - return Error(Nothing, charptr, "WIP"); + size_t parenCount = 1; + size_t curlyCount = 0; + SolsTokens tokens = ({ + ResultType(SolsTokens, charptr) _result = createSolsTokens(); + if (_result.error) { + return Error(Nothing, charptr, _result.as.error); + } + _result.as.success; + }); + // Collect tokens + for (;;) { + ResultType(SolsToken, Nothing) token = parserConsume(parser); + if (token.error) { + return Error(Nothing, charptr, "Expecting ')'"); + } + bool done = false; + switch (token.as.success.type) { + case STT_OPEN_PAREN: + parenCount++; + break; + case STT_CLOSE_PAREN: + parenCount--; + if (parenCount == 0) { + if (curlyCount == 0) { + done = true; + } else { + return Error(Nothing, charptr, "Expecting '}' before ')'"); + } + } + break; + case STT_OPEN_CURLY: + curlyCount++; + break; + case STT_CLOSE_CURLY: + if (curlyCount == 0) { + return Error(Nothing, charptr, "Extra closing curly brace inside ()"); + } + curlyCount--; + break; + default: + break; + } + if (done) break; + addTokenToSolsTokens(&tokens, token.as.success); + } + // Parse tokens + ResultType(SolsParser, charptr) newParser = createSolsParser(&tokens); + if (newParser.error) { + return Error(Nothing, charptr, newParser.as.error); + } + newParser.as.success.currentParent = &newParser.as.success.output; + ResultType(Nothing, charptr) parsed = parse(&newParser.as.success); + if (parsed.error) { + addToParserErrors(parser, parsed.as.error); + } + // Add node to parent + newParser.as.success.output.type = SNT_EXPR_IN_PAREN; + addChildToSolsNode(parser->currentParent, newParser.as.success.output); + return Success(Nothing, charptr, {}); } static inline ResultType(Nothing, charptr) parseCloseParen(SolsParser* parser) { (void)parser; - return Error(Nothing, charptr, "Extra closing parenthases"); + return Error(Nothing, charptr, "Extra closing parentheses"); } ResultType(Nothing, charptr) parse(SolsParser* parser) {