diff options
| author | Andrew Kelley <superjoe30@gmail.com> | 2016-04-20 11:58:01 -0700 |
|---|---|---|
| committer | Andrew Kelley <superjoe30@gmail.com> | 2016-04-20 11:58:01 -0700 |
| commit | 6acc354957752e2cfa8d67bdd0e4c3b42f9be3c3 (patch) | |
| tree | df6c6511e3ded50d1be9d59940d093a3470b93b4 /src | |
| parent | a25307c0a1b45d0c7b83158349fbc57626baf656 (diff) | |
| download | zig-6acc354957752e2cfa8d67bdd0e4c3b42f9be3c3.tar.gz zig-6acc354957752e2cfa8d67bdd0e4c3b42f9be3c3.zip | |
for loop: add ability to get pointer to elem var
see #51
Diffstat (limited to 'src')
| -rw-r--r-- | src/all_types.hpp | 1 | ||||
| -rw-r--r-- | src/analyze.cpp | 9 | ||||
| -rw-r--r-- | src/codegen.cpp | 11 | ||||
| -rw-r--r-- | src/eval.cpp | 4 | ||||
| -rw-r--r-- | src/parser.cpp | 9 |
5 files changed, 29 insertions, 5 deletions
diff --git a/src/all_types.hpp b/src/all_types.hpp index 830b8db31d..af6a40bde9 100644 --- a/src/all_types.hpp +++ b/src/all_types.hpp @@ -508,6 +508,7 @@ struct AstNodeForExpr { Expr resolved_expr; VariableTableEntry *elem_var; VariableTableEntry *index_var; + bool elem_is_ptr; }; struct AstNodeSwitchExpr { diff --git a/src/analyze.cpp b/src/analyze.cpp index 083f4bd2cd..7556597726 100644 --- a/src/analyze.cpp +++ b/src/analyze.cpp @@ -3567,6 +3567,13 @@ static TypeTableEntry *analyze_for_expr(CodeGen *g, ImportTableEntry *import, Bl child_type = g->builtin_types.entry_invalid; } + TypeTableEntry *var_type; + if (node->data.for_expr.elem_is_ptr) { + var_type = get_pointer_to_type(g, child_type, false); + } else { + var_type = child_type; + } + BlockContext *child_context = new_block_context(node, context); child_context->parent_loop_node = node; @@ -3574,7 +3581,7 @@ static TypeTableEntry *analyze_for_expr(CodeGen *g, ImportTableEntry *import, Bl elem_var_node->block_context = child_context; Buf *elem_var_name = &elem_var_node->data.symbol_expr.symbol; node->data.for_expr.elem_var = add_local_var(g, elem_var_node, import, child_context, elem_var_name, - child_type, true, nullptr); + var_type, true, nullptr); AstNode *index_var_node = node->data.for_expr.index_node; if (index_var_node) { diff --git a/src/codegen.cpp b/src/codegen.cpp index 65720f6d59..80eb4b2089 100644 --- a/src/codegen.cpp +++ b/src/codegen.cpp @@ -2427,9 +2427,14 @@ static LLVMValueRef gen_for_expr(CodeGen *g, AstNode *node) { LLVMPositionBuilderAtEnd(g->builder, body_block); LLVMValueRef elem_ptr = gen_array_elem_ptr(g, node, array_val, array_type, index_val); - LLVMValueRef elem_val = handle_is_ptr(child_type) ? elem_ptr : LLVMBuildLoad(g->builder, elem_ptr, ""); - gen_assign_raw(g, node, BinOpTypeAssign, elem_var->value_ref, elem_val, - elem_var->type, child_type); + + LLVMValueRef elem_val; + if (node->data.for_expr.elem_is_ptr) { + elem_val = elem_ptr; + } else { + elem_val = handle_is_ptr(child_type) ? elem_ptr : LLVMBuildLoad(g->builder, elem_ptr, ""); + } + gen_assign_raw(g, node, BinOpTypeAssign, elem_var->value_ref, elem_val, elem_var->type, child_type); gen_var_debug_decl(g, elem_var); g->break_block_stack.append(end_block); g->continue_block_stack.append(continue_block); diff --git a/src/eval.cpp b/src/eval.cpp index 1fa8f4995e..190f271546 100644 --- a/src/eval.cpp +++ b/src/eval.cpp @@ -812,6 +812,10 @@ static bool eval_for_expr(EvalFn *ef, AstNode *node, ConstExprValue *out_val) { assert(elem_node->type == NodeTypeSymbol); Buf *elem_var_name = &elem_node->data.symbol_expr.symbol; + if (node->data.for_expr.elem_is_ptr) { + zig_panic("TODO"); + } + Buf *index_var_name = nullptr; if (index_node) { assert(index_node->type == NodeTypeSymbol); diff --git a/src/parser.cpp b/src/parser.cpp index 37b062e522..29a65521d7 100644 --- a/src/parser.cpp +++ b/src/parser.cpp @@ -1932,7 +1932,7 @@ static AstNode *ast_parse_symbol(ParseContext *pc, int *token_index) { } /* -ForExpression = "for" "(" Expression ")" option("|" "Symbol" option("," "Symbol") "|") Expression +ForExpression = "for" "(" Expression ")" option("|" option("*") "Symbol" option("," "Symbol") "|") Expression */ static AstNode *ast_parse_for_expr(ParseContext *pc, int *token_index, bool mandatory) { Token *token = &pc->tokens->at(*token_index); @@ -1955,6 +1955,13 @@ static AstNode *ast_parse_for_expr(ParseContext *pc, int *token_index, bool mand Token *maybe_bar = &pc->tokens->at(*token_index); if (maybe_bar->id == TokenIdBinOr) { *token_index += 1; + + Token *maybe_star = &pc->tokens->at(*token_index); + if (maybe_star->id == TokenIdStar) { + *token_index += 1; + node->data.for_expr.elem_is_ptr = true; + } + node->data.for_expr.elem_node = ast_parse_symbol(pc, token_index); Token *maybe_comma = &pc->tokens->at(*token_index); |
