Commit 681440e2 authored by sgjesse@chromium.org's avatar sgjesse@chromium.org

Handle pre-allocated properties when copying map.

When copying a map always set the descriptor array to describe the pre-allocated properties, even when descriptors are to be dropped.

Added a test which otherwise failed with an assert on ARM in debug mode. The reason for it only surfasing on ARM is that the NewObject runtime function is always used for allocating new JSObjects on ARM.

This change includes a few parts of http://codereview.chromium.org/174392 needed to trigger the error.
Review URL: http://codereview.chromium.org/173469

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@2762 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
parent af6c6a55
......@@ -425,6 +425,13 @@ bool Compiler::CompileLazy(Handle<SharedFunctionInfo> shared,
// Set the expected number of properties for instances.
SetExpectedNofPropertiesFromEstimate(shared, lit->expected_property_count());
// Set the optimication hints after performing lazy compilation, as these are
// not set when the function is set up as a lazily compiled function.
shared->SetThisPropertyAssignmentsInfo(
lit->has_only_this_property_assignments(),
lit->has_only_simple_this_property_assignments(),
*lit->this_property_assignments());
// Check the function has compiled code.
ASSERT(shared->is_compiled());
return true;
......
......@@ -463,6 +463,8 @@ void Map::MapPrint() {
PrintF(" - type: %s\n", TypeToString(instance_type()));
PrintF(" - instance size: %d\n", instance_size());
PrintF(" - inobject properties: %d\n", inobject_properties());
PrintF(" - pre-allocated property fields: %d\n",
pre_allocated_property_fields());
PrintF(" - unused property fields: %d\n", unused_property_fields());
if (is_hidden_prototype()) {
PrintF(" - hidden_prototype\n");
......
......@@ -2923,6 +2923,17 @@ Object* Map::CopyDropDescriptors() {
// Please note instance_type and instance_size are set when allocated.
Map::cast(result)->set_inobject_properties(inobject_properties());
Map::cast(result)->set_unused_property_fields(unused_property_fields());
// If the map has pre-allocated properties always start out with a descriptor
// array describing these properties.
if (pre_allocated_property_fields() > 0) {
ASSERT(constructor()->IsJSFunction());
JSFunction* ctor = JSFunction::cast(constructor());
Map::cast(result)->set_instance_descriptors(
ctor->initial_map()->instance_descriptors());
Map::cast(result)->set_pre_allocated_property_fields(
pre_allocated_property_fields());
}
Map::cast(result)->set_bit_field(bit_field());
Map::cast(result)->set_bit_field2(bit_field2());
Map::cast(result)->ClearCodeCache();
......@@ -4800,7 +4811,6 @@ void SharedFunctionInfo::SetThisPropertyAssignmentsInfo(
bool only_this_property_assignments,
bool only_simple_this_property_assignments,
FixedArray* assignments) {
ASSERT(this_property_assignments()->IsUndefined());
set_compiler_hints(BooleanBit::set(compiler_hints(),
kHasOnlyThisPropertyAssignments,
only_this_property_assignments));
......
......@@ -4373,6 +4373,13 @@ static Object* Runtime_NewObject(Arguments args) {
}
}
// The function should be compiled for the optimization hints to be available.
if (!function->shared()->is_compiled()) {
CompileLazyShared(Handle<SharedFunctionInfo>(function->shared()),
CLEAR_EXCEPTION,
0);
}
bool first_allocation = !function->has_initial_map();
Handle<JSObject> result = Factory::NewJSObject(function);
if (first_allocation) {
......
......@@ -76,3 +76,20 @@ o4_1_1 = new f4(1);
o4_1_2 = new f4(1);
assertArrayEquals(["x", "y"], props(o4_1_1));
assertArrayEquals(["x", "y"], props(o4_1_2));
function g(){
this.x=1
}
o = new g();
assertEquals(1, o.x);
o = new g();
assertEquals(1, o.x);
g.prototype = {y:2}
o = new g();
assertEquals(1, o.x);
assertEquals(2, o.y);
o = new g();
assertEquals(1, o.x);
assertEquals(2, o.y);
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment