aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorIan Lance Taylor <ian@gcc.gnu.org>2011-02-24 03:37:57 +0000
committerIan Lance Taylor <ian@gcc.gnu.org>2011-02-24 03:37:57 +0000
commitd6007535e639e34b9a73fd3967d1b7f135414386 (patch)
tree0b0ad7c26ccfee825bd23884f0284c3304fd7a5e
parent76ace672dcbf704b27833e25c753298bd08af956 (diff)
downloadgcc-d6007535e639e34b9a73fd3967d1b7f135414386.zip
gcc-d6007535e639e34b9a73fd3967d1b7f135414386.tar.gz
gcc-d6007535e639e34b9a73fd3967d1b7f135414386.tar.bz2
Handle an array of pointers to itself.
From-SVN: r170454
-rw-r--r--gcc/go/gofrontend/types.cc68
-rw-r--r--gcc/go/gofrontend/types.h6
2 files changed, 54 insertions, 20 deletions
diff --git a/gcc/go/gofrontend/types.cc b/gcc/go/gofrontend/types.cc
index 8ce39b7..1e39731 100644
--- a/gcc/go/gofrontend/types.cc
+++ b/gcc/go/gofrontend/types.cc
@@ -4442,33 +4442,59 @@ Array_type::do_get_tree(Gogo* gogo)
if (this->length_ == NULL)
{
tree struct_type = gogo->slice_type_tree(void_type_node);
- return this->fill_in_tree(gogo, struct_type);
+ return this->fill_in_slice_tree(gogo, struct_type);
}
else
{
- tree element_type_tree = this->element_type_->get_tree(gogo);
- tree length_tree = this->get_length_tree(gogo);
- if (element_type_tree == error_mark_node
- || length_tree == error_mark_node)
- return error_mark_node;
+ tree array_type = make_node(ARRAY_TYPE);
+ return this->fill_in_array_tree(gogo, array_type);
+ }
+}
- length_tree = fold_convert(sizetype, length_tree);
+// Fill in the fields for an array type. This is used for named array
+// types.
- // build_index_type takes the maximum index, which is one less
- // than the length.
- tree index_type = build_index_type(fold_build2(MINUS_EXPR, sizetype,
- length_tree,
- size_one_node));
+tree
+Array_type::fill_in_array_tree(Gogo* gogo, tree array_type)
+{
+ gcc_assert(this->length_ != NULL);
- return build_array_type(element_type_tree, index_type);
- }
+ tree element_type_tree = this->element_type_->get_tree(gogo);
+ tree length_tree = this->get_length_tree(gogo);
+ if (element_type_tree == error_mark_node
+ || length_tree == error_mark_node)
+ return error_mark_node;
+
+ length_tree = fold_convert(sizetype, length_tree);
+
+ // build_index_type takes the maximum index, which is one less than
+ // the length.
+ tree index_type = build_index_type(fold_build2(MINUS_EXPR, sizetype,
+ length_tree,
+ size_one_node));
+
+ TREE_TYPE(array_type) = element_type_tree;
+ TYPE_DOMAIN(array_type) = index_type;
+ TYPE_ADDR_SPACE(array_type) = TYPE_ADDR_SPACE(element_type_tree);
+ layout_type(array_type);
+
+ if (TYPE_STRUCTURAL_EQUALITY_P(element_type_tree)
+ || TYPE_STRUCTURAL_EQUALITY_P(index_type))
+ SET_TYPE_STRUCTURAL_EQUALITY(array_type);
+ else if (TYPE_CANONICAL(element_type_tree) != element_type_tree
+ || TYPE_CANONICAL(index_type) != index_type)
+ TYPE_CANONICAL(array_type) =
+ build_array_type(TYPE_CANONICAL(element_type_tree),
+ TYPE_CANONICAL(index_type));
+
+ return array_type;
}
// Fill in the fields for a slice type. This is used for named slice
// types.
tree
-Array_type::fill_in_tree(Gogo* gogo, tree struct_type)
+Array_type::fill_in_slice_tree(Gogo* gogo, tree struct_type)
{
gcc_assert(this->length_ == NULL);
@@ -7129,15 +7155,19 @@ Named_type::do_get_tree(Gogo* gogo)
break;
case TYPE_ARRAY:
+ if (this->named_tree_ != NULL_TREE)
+ return this->named_tree_;
if (!this->is_open_array_type())
- t = Type::get_named_type_tree(gogo, this->type_);
+ {
+ t = make_node(ARRAY_TYPE);
+ this->named_tree_ = t;
+ t = this->type_->array_type()->fill_in_array_tree(gogo, t);
+ }
else
{
- if (this->named_tree_ != NULL_TREE)
- return this->named_tree_;
t = gogo->slice_type_tree(void_type_node);
this->named_tree_ = t;
- t = this->type_->array_type()->fill_in_tree(gogo, t);
+ t = this->type_->array_type()->fill_in_slice_tree(gogo, t);
}
if (t == error_mark_node)
return error_mark_node;
diff --git a/gcc/go/gofrontend/types.h b/gcc/go/gofrontend/types.h
index b9e8caf..b428077 100644
--- a/gcc/go/gofrontend/types.h
+++ b/gcc/go/gofrontend/types.h
@@ -2050,9 +2050,13 @@ class Array_type : public Type
static Array_type*
do_import(Import*);
+ // Fill in the fields for a named array type.
+ tree
+ fill_in_array_tree(Gogo*, tree);
+
// Fill in the fields for a named slice type.
tree
- fill_in_tree(Gogo*, tree);
+ fill_in_slice_tree(Gogo*, tree);
protected:
int