summaryrefslogtreecommitdiff
path: root/gcc/go
diff options
context:
space:
mode:
authorian <ian@138bc75d-0d04-0410-961f-82ee72b054a4>2011-02-24 03:01:22 +0000
committerian <ian@138bc75d-0d04-0410-961f-82ee72b054a4>2011-02-24 03:01:22 +0000
commit746d2e731607a53cbf31444bfda7d6db7eeaf5eb (patch)
tree51d6fb9452fd188f5ba831a740a8e56b7c188709 /gcc/go
parent46ae0691018492affba11b9c95852331a9f8321a (diff)
downloadgcc-746d2e731607a53cbf31444bfda7d6db7eeaf5eb.tar.gz
Don't crash if a map index is used outside of a function.
git-svn-id: svn+ssh://gcc.gnu.org/svn/gcc/trunk@170453 138bc75d-0d04-0410-961f-82ee72b054a4
Diffstat (limited to 'gcc/go')
-rw-r--r--gcc/go/gofrontend/expressions.cc46
1 files changed, 37 insertions, 9 deletions
diff --git a/gcc/go/gofrontend/expressions.cc b/gcc/go/gofrontend/expressions.cc
index e9a26a0da0d..2e31e806478 100644
--- a/gcc/go/gofrontend/expressions.cc
+++ b/gcc/go/gofrontend/expressions.cc
@@ -9888,12 +9888,39 @@ Map_index_expression::get_value_pointer(Translate_context* context,
// We need to pass in a pointer to the key, so stuff it into a
// variable.
- tree tmp = create_tmp_var(TREE_TYPE(index_tree), get_name(index_tree));
- DECL_IGNORED_P(tmp) = 0;
- DECL_INITIAL(tmp) = index_tree;
- tree make_tmp = build1(DECL_EXPR, void_type_node, tmp);
- tree tmpref = fold_convert(const_ptr_type_node, build_fold_addr_expr(tmp));
- TREE_ADDRESSABLE(tmp) = 1;
+ tree tmp;
+ tree make_tmp;
+ if (current_function_decl != NULL)
+ {
+ tmp = create_tmp_var(TREE_TYPE(index_tree), get_name(index_tree));
+ DECL_IGNORED_P(tmp) = 0;
+ DECL_INITIAL(tmp) = index_tree;
+ make_tmp = build1(DECL_EXPR, void_type_node, tmp);
+ TREE_ADDRESSABLE(tmp) = 1;
+ }
+ else
+ {
+ tmp = build_decl(this->location(), VAR_DECL, create_tmp_var_name("M"),
+ TREE_TYPE(index_tree));
+ DECL_EXTERNAL(tmp) = 0;
+ TREE_PUBLIC(tmp) = 0;
+ TREE_STATIC(tmp) = 1;
+ DECL_ARTIFICIAL(tmp) = 1;
+ if (!TREE_CONSTANT(index_tree))
+ make_tmp = fold_build2_loc(this->location(), INIT_EXPR, void_type_node,
+ tmp, index_tree);
+ else
+ {
+ TREE_READONLY(tmp) = 1;
+ TREE_CONSTANT(tmp) = 1;
+ DECL_INITIAL(tmp) = index_tree;
+ make_tmp = NULL_TREE;
+ }
+ rest_of_decl_compilation(tmp, 1, 0);
+ }
+ tree tmpref = fold_convert_loc(this->location(), const_ptr_type_node,
+ build_fold_addr_expr_loc(this->location(),
+ tmp));
static tree map_index_fndecl;
tree call = Gogo::call_builtin(&map_index_fndecl,
@@ -9920,9 +9947,10 @@ Map_index_expression::get_value_pointer(Translate_context* context,
return error_mark_node;
tree ptr_val_type_tree = build_pointer_type(val_type_tree);
- return build2(COMPOUND_EXPR, ptr_val_type_tree,
- make_tmp,
- fold_convert(ptr_val_type_tree, call));
+ tree ret = fold_convert_loc(this->location(), ptr_val_type_tree, call);
+ if (make_tmp != NULL_TREE)
+ ret = build2(COMPOUND_EXPR, ptr_val_type_tree, make_tmp, ret);
+ return ret;
}
// Make a map index expression.