diff --git a/src/parser/parser.c b/src/parser/parser.c index 41b5004..542e11a 100644 --- a/src/parser/parser.c +++ b/src/parser/parser.c @@ -13,6 +13,7 @@ #include "assignable/identifier/identifier.h" #include "declaration/declaration.h" #include "dictionary/dictionary.h" +#include "return/return.h" #include "dowrap/dowrap.h" #include "function/function.h" #include "if/if.h" @@ -31,7 +32,7 @@ const char *ValueTypeNames[] = { "string", "assign", "identifier", "number", "if statement", "access", "call", "declaration", "null", "boolean", - "do wrap", "operations", "list", "dictionary", "function"}; + "do wrap", "operations", "list", "dictionary", "function", "return"}; ArErr error_if_finished(char *file, DArray *tokens, size_t *index) { if ((*index) >= tokens->size) { @@ -70,6 +71,8 @@ ParsedValueReturn parse_token_full(char *file, DArray *tokens, size_t *index, switch (token->type) { case TOKEN_IF: return parse_if(file, tokens, index); + case TOKEN_RETURN: + return parse_return(file, tokens, index); default: break; }; @@ -254,5 +257,9 @@ void free_parsed(void *ptr) { break; case AST_FUNCTION: free_function(parsed); + break; + case AST_RETURN: + free_parsed_return(parsed); + break; } } \ No newline at end of file diff --git a/src/parser/parser.h b/src/parser/parser.h index 35bc08e..109cfd3 100644 --- a/src/parser/parser.h +++ b/src/parser/parser.h @@ -48,7 +48,8 @@ typedef enum { AST_OPERATION, AST_LIST, AST_DICTIONARY, - AST_FUNCTION + AST_FUNCTION, + AST_RETURN } ValueType; extern const char *ValueTypeNames[]; diff --git a/src/parser/return/return.c b/src/parser/return/return.c new file mode 100644 index 0000000..72b2e05 --- /dev/null +++ b/src/parser/return/return.c @@ -0,0 +1,49 @@ +/* + * SPDX-FileCopyrightText: 2025 William Bell + * + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +#include "return.h" +#include "../../lexer/token.h" +#include "../../memory.h" +#include "../literals/literals.h" + +ParsedValueReturn parse_return(char *file, DArray *tokens, size_t *index) { + (*index)++; + ParsedValue *parsedValue = checked_malloc(sizeof(ParsedValue)); + ParsedReturn *parsedReturn = checked_malloc(sizeof(ParsedReturn)); + parsedValue->type = AST_RETURN; + parsedValue->data = parsedReturn; + parsedReturn->value = parse_null(); + if (*index >= tokens->size) + return (ParsedValueReturn){no_err, parsedValue}; + Token *token = darray_get(tokens, *index); + if (token->type == TOKEN_NEW_LINE) + return (ParsedValueReturn){no_err, parsedValue}; + ParsedValueReturn value = parse_token(file, tokens, index, true); + if (value.err.exists) { + free_parsed(parsedValue); + free(parsedValue); + return value; + } + if (!value.value) { + free_parsed(parsedValue); + free(parsedValue); + return (ParsedValueReturn){create_err(token->line, token->column, + token->length, file, "Syntax Error", + "expected value"), + NULL}; + } + free_parsed(parsedReturn->value); + free(parsedReturn->value); + parsedReturn->value = value.value; + return (ParsedValueReturn){no_err, parsedValue}; +} + +void free_parsed_return(void *ptr) { + ParsedValue *parsedValue = ptr; + DArray *parsed_return = parsedValue->data; + free_parsed(parsed_return); + free(parsed_return); +} \ No newline at end of file diff --git a/src/parser/return/return.h b/src/parser/return/return.h new file mode 100644 index 0000000..05fb5ee --- /dev/null +++ b/src/parser/return/return.h @@ -0,0 +1,20 @@ +/* + * SPDX-FileCopyrightText: 2025 William Bell + * + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +#ifndef RETURN_H +#define RETURN_H + +#include "../parser.h" + +typedef struct { + ParsedValue * value; +} ParsedReturn; + +ParsedValueReturn parse_return(char *file, DArray *tokens, size_t *index); + +void free_parsed_return(void *ptr); + +#endif // RETURN_H \ No newline at end of file diff --git a/src/translator/declaration/declaration.c b/src/translator/declaration/declaration.c index 89e70a9..e1e8f6d 100644 --- a/src/translator/declaration/declaration.c +++ b/src/translator/declaration/declaration.c @@ -16,6 +16,8 @@ size_t translate_parsed_declaration(Translated *translated, set_registers(translated, 1); size_t first = 0; for (size_t i = 0; i < delcarations.size; i++) { + DArray* old_return_jumps = translated->return_jumps; + translated->return_jumps = NULL; ParsedSingleDeclaration *singleDeclaration = darray_get(&delcarations, i); size_t temp = translate_parsed(translated, singleDeclaration->from); if (i == 0) @@ -33,6 +35,7 @@ size_t translate_parsed_declaration(Translated *translated, singleDeclaration->column, length}; push_instruction_code(translated, translated->source_locations.size); darray_push(&translated->source_locations, &source_locations); + translated->return_jumps = old_return_jumps; } return first; } \ No newline at end of file diff --git a/src/translator/return/return.c b/src/translator/return/return.c new file mode 100644 index 0000000..f8bf8c8 --- /dev/null +++ b/src/translator/return/return.c @@ -0,0 +1,11 @@ +#include "return.h" + +size_t translate_parsed_return(Translated *translated, + ParsedReturn *parsedReturn) { + + size_t first = translate_parsed(translated, parsedReturn->value); + push_instruction_byte(translated, OP_JUMP); + size_t return_up = push_instruction_code(translated, 0); + darray_push(translated->return_jumps, &return_up); + return first; +} \ No newline at end of file diff --git a/src/translator/return/return.h b/src/translator/return/return.h new file mode 100644 index 0000000..4861717 --- /dev/null +++ b/src/translator/return/return.h @@ -0,0 +1,15 @@ +/* + * SPDX-FileCopyrightText: 2025 William Bell + * + * SPDX-License-Identifier: GPL-3.0-or-later + */ + +#ifndef TRANSLATE_RETURN_H +#define TRANSLATE_RETURN_H +#include "../translator.h" +#include "../../parser/return/return.h" + + +size_t translate_parsed_return(Translated *translated, ParsedReturn *parsedReturn); + +#endif // TRANSLATE_RETURN_H \ No newline at end of file diff --git a/src/translator/translator.c b/src/translator/translator.c index c7e9d12..1ec346f 100644 --- a/src/translator/translator.c +++ b/src/translator/translator.c @@ -14,6 +14,7 @@ #include "if/if.h" #include "number/number.h" #include "string/string.h" +#include "return/return.h" #include #include #include @@ -148,6 +149,8 @@ size_t translate_parsed(Translated *translated, ParsedValue *parsedValue) { return translate_parsed_if(translated, (DArray *)parsedValue->data); case AST_DOWRAP: return translate_parsed_dowrap(translated, (DArray *)parsedValue->data); + case AST_RETURN: + return translate_parsed_return(translated, (ParsedReturn *)parsedValue->data); } return 0; } diff --git a/testing.ar b/testing.ar index 12f4433..9b75e3d 100644 --- a/testing.ar +++ b/testing.ar @@ -4,6 +4,6 @@ let y = 1 let term = y -if (let x = let z = y) do - do - x \ No newline at end of file + +let x = do + return x \ No newline at end of file