/* Handle the constant pool of the Java(TM) Virtual Machine.
Copyright (C) 1997, 1998, 1999, 2000, 2001, 2003, 2004, 2005, 2006,
- 2007, 2008 Free Software Foundation, Inc.
+ 2007, 2008, 2010 Free Software Foundation, Inc.
This file is part of GCC.
#include "jcf.h"
#include "tree.h"
#include "java-tree.h"
+#include "diagnostic-core.h"
#include "toplev.h"
#include "ggc.h"
if (cpool->data == NULL)
{
cpool->capacity = 100;
- cpool->tags = GGC_CNEWVEC (uint8, cpool->capacity);
- cpool->data = GGC_CNEWVEC (union cpool_entry, cpool->capacity);
+ cpool->tags = (uint8 *) ggc_alloc_cleared_atomic (sizeof (uint8)
+ * cpool->capacity);
+ cpool->data = ggc_alloc_cleared_vec_cpool_entry (sizeof
+ (union cpool_entry),
+ cpool->capacity);
cpool->count = 1;
}
if (index >= cpool->capacity)
if (cpool == NULL)
{
- cpool = GGC_CNEW (struct CPool);
+ cpool = ggc_alloc_cleared_CPool ();
TYPE_CPOOL (klass) = cpool;
}
return cpool;
thinks the type is incomplete. */
layout_type (type);
- decl = build_decl (VAR_DECL, decl_name, type);
+ decl = build_decl (input_location, VAR_DECL, decl_name, type);
TREE_STATIC (decl) = 1;
IDENTIFIER_GLOBAL_VALUE (decl_name) = decl;
}
CPool *outgoing_cpool = cpool_for_class (current_class);
tree tags_value, data_value;
tree cons;
- tree tags_list = NULL_TREE;
- tree data_list = NULL_TREE;
+ VEC(constructor_elt,gc) *v = NULL;
int i;
+ VEC(constructor_elt,gc) *tags = NULL;
+ VEC(constructor_elt,gc) *data = NULL;
+ constructor_elt *t = NULL;
+ constructor_elt *d = NULL;
+ if (outgoing_cpool->count > 0)
+ {
+ int c = outgoing_cpool->count;
+ VEC_safe_grow_cleared (constructor_elt, gc, tags, c);
+ VEC_safe_grow_cleared (constructor_elt, gc, data, c);
+ t = VEC_index (constructor_elt, tags, c-1);
+ d = VEC_index (constructor_elt, data, c-1);
+ }
+
+#define CONSTRUCTOR_PREPEND_VALUE(E, V) E->value = V, E--
for (i = outgoing_cpool->count; --i > 0; )
switch (outgoing_cpool->tags[i] & ~CONSTANT_LazyFlag)
{
FIXME: This is a kludge. The field we're initializing is
not a scalar but a union, and that's how we should
represent it in the compiler. We should fix this. */
- if (BYTES_BIG_ENDIAN && POINTER_SIZE > 32)
- temp <<= POINTER_SIZE - 32;
-
- tags_list
- = tree_cons (NULL_TREE, get_tag_node (outgoing_cpool->tags[i]),
- tags_list);
- data_list
- = tree_cons (NULL_TREE,
- fold_convert (ptr_type_node,
- (build_int_cst (NULL_TREE, temp))),
- data_list);
+ if (BYTES_BIG_ENDIAN)
+ temp <<= ((POINTER_SIZE > 32) ? POINTER_SIZE - 32 : 0);
+
+ CONSTRUCTOR_PREPEND_VALUE (t, get_tag_node (outgoing_cpool->tags[i]));
+ CONSTRUCTOR_PREPEND_VALUE (d,
+ fold_convert (ptr_type_node,
+ (build_int_cst (NULL_TREE,
+ temp))));
}
break;
case CONSTANT_String:
case CONSTANT_Unicode:
case CONSTANT_Utf8:
- tags_list
- = tree_cons (NULL_TREE, get_tag_node (outgoing_cpool->tags[i]),
- tags_list);
- data_list
- = tree_cons (NULL_TREE, build_utf8_ref (outgoing_cpool->data[i].t),
- data_list);
+ CONSTRUCTOR_PREPEND_VALUE (t, get_tag_node (outgoing_cpool->tags[i]));
+ CONSTRUCTOR_PREPEND_VALUE (d, build_utf8_ref (outgoing_cpool->data[i].t));
break;
default:
gcc_assert (false);
}
+#undef CONSTRUCTOR_PREPEND_VALUE
+
if (outgoing_cpool->count > 0)
{
tree data_decl, tags_decl, tags_type;
tree max_index = build_int_cst (sizetype, outgoing_cpool->count - 1);
tree index_type = build_index_type (max_index);
+ tree tem;
/* Add dummy 0'th element of constant pool. */
- tags_list = tree_cons (NULL_TREE, get_tag_node (0), tags_list);
- data_list = tree_cons (NULL_TREE, null_pointer_node, data_list);
+ gcc_assert (t == VEC_address (constructor_elt, tags));
+ gcc_assert (d == VEC_address (constructor_elt, data));
+ t->value = get_tag_node (0);
+ d->value = null_pointer_node;
+ /* Change the type of the decl to have the proper array size.
+ ??? Make sure to transition the old type-pointer-to list to this
+ new type to not invalidate all build address expressions. */
data_decl = build_constant_data_ref (false);
+ tem = TYPE_POINTER_TO (TREE_TYPE (data_decl));
+ if (!tem)
+ tem = build_pointer_type (TREE_TYPE (data_decl));
+ TYPE_POINTER_TO (TREE_TYPE (data_decl)) = NULL_TREE;
TREE_TYPE (data_decl) = build_array_type (ptr_type_node, index_type);
- DECL_INITIAL (data_decl) = build_constructor_from_list
- (TREE_TYPE (data_decl), data_list);
+ TYPE_POINTER_TO (TREE_TYPE (data_decl)) = tem;
+ DECL_INITIAL (data_decl) = build_constructor (TREE_TYPE (data_decl), data);
DECL_SIZE (data_decl) = TYPE_SIZE (TREE_TYPE (data_decl));
DECL_SIZE_UNIT (data_decl) = TYPE_SIZE_UNIT (TREE_TYPE (data_decl));
rest_of_decl_compilation (data_decl, 1, 0);
data_value = build_address_of (data_decl);
tags_type = build_array_type (unsigned_byte_type_node, index_type);
- tags_decl = build_decl (VAR_DECL, mangled_classname ("_CT_",
+ tags_decl = build_decl (input_location,
+ VAR_DECL, mangled_classname ("_CT_",
current_class),
tags_type);
TREE_STATIC (tags_decl) = 1;
- DECL_INITIAL (tags_decl) = build_constructor_from_list
- (tags_type, tags_list);
+ DECL_INITIAL (tags_decl) = build_constructor (tags_type, tags);
rest_of_decl_compilation (tags_decl, 1, 0);
tags_value = build_address_of (tags_decl);
}
data_value = null_pointer_node;
tags_value = null_pointer_node;
}
- START_RECORD_CONSTRUCTOR (cons, constants_type_node);
- PUSH_FIELD_VALUE (cons, "size",
+ START_RECORD_CONSTRUCTOR (v, constants_type_node);
+ PUSH_FIELD_VALUE (v, "size",
build_int_cst (NULL_TREE, outgoing_cpool->count));
- PUSH_FIELD_VALUE (cons, "tags", tags_value);
- PUSH_FIELD_VALUE (cons, "data", data_value);
- FINISH_RECORD_CONSTRUCTOR (cons);
+ PUSH_FIELD_VALUE (v, "tags", tags_value);
+ PUSH_FIELD_VALUE (v, "data", data_value);
+ FINISH_RECORD_CONSTRUCTOR (cons, v, constants_type_node);
return cons;
}