diff options
author | A404M <ahmadmahmoudiprogrammer@gmail.com> | 2025-04-14 12:55:08 +0330 |
---|---|---|
committer | A404M <ahmadmahmoudiprogrammer@gmail.com> | 2025-04-14 12:55:08 +0330 |
commit | 038bbfc95cf79e1be48b1926e9893e2a12a3b92a (patch) | |
tree | 7cfcf33b7f431acbb2edb4201dfc30f7e08acf3d /src/runner | |
parent | f6a2a2ed20376f6ba677248b0dcf5d0ddceaeef7 (diff) |
add arrays
Diffstat (limited to 'src/runner')
-rw-r--r-- | src/runner/runner.c | 75 |
1 files changed, 74 insertions, 1 deletions
diff --git a/src/runner/runner.c b/src/runner/runner.c index 2f4b32f..075e3a4 100644 --- a/src/runner/runner.c +++ b/src/runner/runner.c @@ -438,6 +438,7 @@ AstTree *runExpression(AstTree *expr, bool *shouldRet, bool isLeft) { if (!conti) { break; } + astTreeDelete(ret); ret = runExpression(metadata->body, shouldRet, isLeft); } return ret; @@ -1121,6 +1122,7 @@ AstTree *runExpression(AstTree *expr, bool *shouldRet, bool isLeft) { case AST_TREE_TOKEN_VALUE_OBJECT: case AST_TREE_TOKEN_FUNCTION: case AST_TREE_TOKEN_BUILTIN: + case AST_TREE_TOKEN_TYPE_ARRAY: return copyAstTree(expr); case AST_TREE_TOKEN_OPERATOR_ADDRESS: { AstTreeSingleChild *metadata = expr->metadata; @@ -1160,7 +1162,8 @@ AstTree *runExpression(AstTree *expr, bool *shouldRet, bool isLeft) { case AST_TREE_TOKEN_OPERATOR_ACCESS: { AstTreeAccess *metadata = expr->metadata; AstTree *tree = runExpression(metadata->object, shouldRet, true); - if (tree->type->token != AST_TREE_TOKEN_KEYWORD_STRUCT) { + if (tree->type->token != AST_TREE_TOKEN_KEYWORD_STRUCT && + tree->token != AST_TREE_TOKEN_VARIABLE) { UNREACHABLE; } AstTreeVariable *variable = tree->metadata; @@ -1217,6 +1220,76 @@ AstTree *runExpression(AstTree *expr, bool *shouldRet, bool isLeft) { return newAstTree(AST_TREE_TOKEN_OPERATOR_POINTER, newMetadata, copyAstTree(expr->type), expr->str_begin, expr->str_end); } + case AST_TREE_TOKEN_OPERATOR_ARRAY_ACCESS: { + AstTreeBracket *metadata = expr->metadata; + AstTree *operand = runExpression(metadata->operand, shouldRet, true); + + if (operand->token != AST_TREE_TOKEN_VARIABLE) { + UNREACHABLE; + } else if (metadata->parameters.size != 1) { + UNREACHABLE; + } + + AstTree *array_indexNode = + runExpression(metadata->parameters.data[0], shouldRet, false); + + if (array_indexNode->token != AST_TREE_TOKEN_VALUE_INT) { + UNREACHABLE; + } + + AstTreeInt index = *(AstTreeInt *)array_indexNode->metadata; + astTreeDelete(array_indexNode); + + AstTreeVariable *variable = operand->metadata; + astTreeDelete(operand); + if (variable->value->token == AST_TREE_TOKEN_VALUE_UNDEFINED) { + AstTreeBracket *array_type_metadata = variable->type->metadata; + if (array_type_metadata->parameters.size != 1) { + UNREACHABLE; + } + AstTree *arraySize_tree = runExpression( + array_type_metadata->parameters.data[0], shouldRet, false); + if (arraySize_tree->token != AST_TREE_TOKEN_VALUE_INT) { + UNREACHABLE; + } + AstTreeInt array_size = *(AstTreeInt *)arraySize_tree->metadata; + astTreeDelete(arraySize_tree); + + AstTreeObject *newMetadata = a404m_malloc(sizeof(*newMetadata)); + + newMetadata->variables = (AstTreeVariables){ + .data = + a404m_malloc(array_size * sizeof(*newMetadata->variables.data)), + .size = array_size, + }; + + for (size_t i = 0; i < array_size; ++i) { + AstTreeVariable *member = a404m_malloc(sizeof(*member)); + member->name_begin = member->name_end = NULL; + member->isConst = false; + member->type = copyAstTree(array_type_metadata->operand); + member->value = newAstTree( + AST_TREE_TOKEN_VALUE_UNDEFINED, NULL, copyAstTree(member->type), + variable->value->str_begin, variable->value->str_end); + newMetadata->variables.data[i] = member; + } + + runnerVariableSetValue(variable, newAstTree(AST_TREE_TOKEN_VALUE_OBJECT, + newMetadata, + copyAstTree(variable->type), + variable->value->str_begin, + variable->value->str_end)); + } + AstTreeObject *object = variable->value->metadata; + AstTreeVariable *var = object->variables.data[index]; + + if (isLeft) { + return newAstTree(AST_TREE_TOKEN_VARIABLE, var, copyAstTree(var->type), + var->name_begin, var->name_end); + } else { + return copyAstTree(var->value); + } + } case AST_TREE_TOKEN_NONE: } UNREACHABLE; |