| Index: src/runtime.cc
|
| diff --git a/src/runtime.cc b/src/runtime.cc
|
| index 0c15f60f30677bc02c172b4f6929e5ac559273cd..f7b6ad4487cafc7cca2123ca7f331e87b802e795 100644
|
| --- a/src/runtime.cc
|
| +++ b/src/runtime.cc
|
| @@ -789,6 +789,7 @@ static MaybeObject* Runtime_GetOwnProperty(Arguments args) {
|
| case JSObject::FAST_ELEMENT: {
|
| elms->set(IS_ACCESSOR_INDEX, Heap::false_value());
|
| Handle<Object> value = GetElement(obj, index);
|
| + RETURN_IF_EMPTY_HANDLE(value);
|
| elms->set(VALUE_INDEX, *value);
|
| elms->set(WRITABLE_INDEX, Heap::true_value());
|
| elms->set(ENUMERABLE_INDEX, Heap::true_value());
|
| @@ -826,6 +827,7 @@ static MaybeObject* Runtime_GetOwnProperty(Arguments args) {
|
| // This is a data property.
|
| elms->set(IS_ACCESSOR_INDEX, Heap::false_value());
|
| Handle<Object> value = GetElement(obj, index);
|
| + ASSERT(!value.is_null());
|
| elms->set(VALUE_INDEX, *value);
|
| elms->set(WRITABLE_INDEX, Heap::ToBoolean(!details.IsReadOnly()));
|
| break;
|
| @@ -1469,7 +1471,7 @@ static MaybeObject* Runtime_InitializeConstContextSlot(Arguments args) {
|
| // The holder is an arguments object.
|
| ASSERT((attributes & READ_ONLY) == 0);
|
| Handle<JSObject> arguments(Handle<JSObject>::cast(holder));
|
| - SetElement(arguments, index, value);
|
| + RETURN_IF_EMPTY_HANDLE(SetElement(arguments, index, value));
|
| }
|
| return *value;
|
| }
|
| @@ -8384,8 +8386,9 @@ static void CollectElementIndices(Handle<JSObject> object,
|
| * with the element index and the element's value.
|
| * Afterwards it increments the base-index of the visitor by the array
|
| * length.
|
| + * Returns false if any access threw an exception, otherwise true.
|
| */
|
| -static void IterateElements(Handle<JSArray> receiver,
|
| +static bool IterateElements(Handle<JSArray> receiver,
|
| ArrayConcatVisitor* visitor) {
|
| uint32_t length = static_cast<uint32_t>(receiver->length()->Number());
|
| switch (receiver->GetElementsKind()) {
|
| @@ -8404,6 +8407,7 @@ static void IterateElements(Handle<JSArray> receiver,
|
| // Call GetElement on receiver, not its prototype, or getters won't
|
| // have the correct receiver.
|
| element_value = GetElement(receiver, j);
|
| + if (element_value.is_null()) return false;
|
| visitor->visit(j, element_value);
|
| }
|
| }
|
| @@ -8422,6 +8426,7 @@ static void IterateElements(Handle<JSArray> receiver,
|
| HandleScope loop_scope;
|
| uint32_t index = indices[j];
|
| Handle<Object> element = GetElement(receiver, index);
|
| + if (element.is_null()) return false;
|
| visitor->visit(index, element);
|
| // Skip to next different index (i.e., omit duplicates).
|
| do {
|
| @@ -8478,6 +8483,7 @@ static void IterateElements(Handle<JSArray> receiver,
|
| break;
|
| }
|
| visitor->increase_index_offset(length);
|
| + return true;
|
| }
|
|
|
|
|
| @@ -8559,7 +8565,9 @@ static MaybeObject* Runtime_ArrayConcat(Arguments args) {
|
| Handle<Object> obj(elements->get(i));
|
| if (obj->IsJSArray()) {
|
| Handle<JSArray> array = Handle<JSArray>::cast(obj);
|
| - IterateElements(array, &visitor);
|
| + if (!IterateElements(array, &visitor)) {
|
| + return Failure::Exception();
|
| + }
|
| } else {
|
| visitor.visit(0, obj);
|
| visitor.increase_index_offset(1);
|
| @@ -8657,10 +8665,12 @@ static MaybeObject* Runtime_SwapElements(Arguments args) {
|
|
|
| Handle<JSObject> jsobject = Handle<JSObject>::cast(object);
|
| Handle<Object> tmp1 = GetElement(jsobject, index1);
|
| + RETURN_IF_EMPTY_HANDLE(tmp1);
|
| Handle<Object> tmp2 = GetElement(jsobject, index2);
|
| + RETURN_IF_EMPTY_HANDLE(tmp2);
|
|
|
| - SetElement(jsobject, index1, tmp2);
|
| - SetElement(jsobject, index2, tmp1);
|
| + RETURN_IF_EMPTY_HANDLE(SetElement(jsobject, index1, tmp2));
|
| + RETURN_IF_EMPTY_HANDLE(SetElement(jsobject, index2, tmp1));
|
|
|
| return Heap::undefined_value();
|
| }
|
| @@ -11266,7 +11276,8 @@ static MaybeObject* Runtime_CollectStackTrace(Arguments args) {
|
|
|
| limit = Max(limit, 0); // Ensure that limit is not negative.
|
| int initial_size = Min(limit, 10);
|
| - Handle<JSArray> result = Factory::NewJSArray(initial_size * 4);
|
| + Handle<FixedArray> elements =
|
| + Factory::NewFixedArrayWithHoles(initial_size * 4);
|
|
|
| StackFrameIterator iter;
|
| // If the caller parameter is a function we skip frames until we're
|
| @@ -11282,27 +11293,30 @@ static MaybeObject* Runtime_CollectStackTrace(Arguments args) {
|
| List<FrameSummary> frames(3); // Max 2 levels of inlining.
|
| frame->Summarize(&frames);
|
| for (int i = frames.length() - 1; i >= 0; i--) {
|
| + if (cursor + 4 > elements->length()) {
|
| + int new_capacity = JSObject::NewElementsCapacity(elements->length());
|
| + Handle<FixedArray> new_elements =
|
| + Factory::NewFixedArrayWithHoles(new_capacity);
|
| + for (int i = 0; i < cursor; i++) {
|
| + new_elements->set(i, elements->get(i));
|
| + }
|
| + elements = new_elements;
|
| + }
|
| + ASSERT(cursor + 4 <= elements->length());
|
| +
|
| Handle<Object> recv = frames[i].receiver();
|
| Handle<JSFunction> fun = frames[i].function();
|
| Handle<Code> code = frames[i].code();
|
| Handle<Smi> offset(Smi::FromInt(frames[i].offset()));
|
| - FixedArray* elements = FixedArray::cast(result->elements());
|
| - if (cursor + 3 < elements->length()) {
|
| - elements->set(cursor++, *recv);
|
| - elements->set(cursor++, *fun);
|
| - elements->set(cursor++, *code);
|
| - elements->set(cursor++, *offset);
|
| - } else {
|
| - SetElement(result, cursor++, recv);
|
| - SetElement(result, cursor++, fun);
|
| - SetElement(result, cursor++, code);
|
| - SetElement(result, cursor++, offset);
|
| - }
|
| + elements->set(cursor++, *recv);
|
| + elements->set(cursor++, *fun);
|
| + elements->set(cursor++, *code);
|
| + elements->set(cursor++, *offset);
|
| }
|
| }
|
| iter.Advance();
|
| }
|
| -
|
| + Handle<JSArray> result = Factory::NewJSArrayWithElements(elements);
|
| result->set_length(Smi::FromInt(cursor));
|
| return *result;
|
| }
|
| @@ -11467,7 +11481,13 @@ static MaybeObject* Runtime_MessageGetScript(Arguments args) {
|
| static MaybeObject* Runtime_ListNatives(Arguments args) {
|
| ASSERT(args.length() == 0);
|
| HandleScope scope;
|
| - Handle<JSArray> result = Factory::NewJSArray(0);
|
| +#define COUNT_ENTRY(Name, argc, ressize) + 1
|
| + int entry_count = 0
|
| + RUNTIME_FUNCTION_LIST(COUNT_ENTRY)
|
| + INLINE_FUNCTION_LIST(COUNT_ENTRY)
|
| + INLINE_RUNTIME_FUNCTION_LIST(COUNT_ENTRY);
|
| +#undef COUNT_ENTRY
|
| + Handle<FixedArray> elements = Factory::NewFixedArray(entry_count);
|
| int index = 0;
|
| bool inline_runtime_functions = false;
|
| #define ADD_ENTRY(Name, argc, ressize) \
|
| @@ -11482,10 +11502,11 @@ static MaybeObject* Runtime_ListNatives(Arguments args) {
|
| name = Factory::NewStringFromAscii( \
|
| Vector<const char>(#Name, StrLength(#Name))); \
|
| } \
|
| - Handle<JSArray> pair = Factory::NewJSArray(0); \
|
| - SetElement(pair, 0, name); \
|
| - SetElement(pair, 1, Handle<Smi>(Smi::FromInt(argc))); \
|
| - SetElement(result, index++, pair); \
|
| + Handle<FixedArray> pair_elements = Factory::NewFixedArray(2); \
|
| + pair_elements->set(0, *name); \
|
| + pair_elements->set(1, Smi::FromInt(argc)); \
|
| + Handle<JSArray> pair = Factory::NewJSArrayWithElements(pair_elements); \
|
| + elements->set(index++, *pair); \
|
| }
|
| inline_runtime_functions = false;
|
| RUNTIME_FUNCTION_LIST(ADD_ENTRY)
|
| @@ -11493,6 +11514,8 @@ static MaybeObject* Runtime_ListNatives(Arguments args) {
|
| INLINE_FUNCTION_LIST(ADD_ENTRY)
|
| INLINE_RUNTIME_FUNCTION_LIST(ADD_ENTRY)
|
| #undef ADD_ENTRY
|
| + ASSERT_EQ(index, entry_count);
|
| + Handle<JSArray> result = Factory::NewJSArrayWithElements(elements);
|
| return *result;
|
| }
|
| #endif
|
|
|