Version 1.2.12.
Added stack traces collection to Error objects accessible through the e.stack property.
Changed RegExp parser to use a recursive data structure instead of stack-based recursion.
Optimized Date object construction and string concatenation.
Improved performance of div, mod, and mul on ARM platforms.
git-svn-id: http://v8.googlecode.com/svn/trunk@2361 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
diff --git a/src/runtime.cc b/src/runtime.cc
index e0eab74..aeda068 100644
--- a/src/runtime.cc
+++ b/src/runtime.cc
@@ -168,7 +168,7 @@
}
}
} else {
- Dictionary* element_dictionary = copy->element_dictionary();
+ NumberDictionary* element_dictionary = copy->element_dictionary();
int capacity = element_dictionary->Capacity();
for (int i = 0; i < capacity; i++) {
Object* k = element_dictionary->KeyAt(i);
@@ -2610,9 +2610,9 @@
}
} else {
// Attempt dictionary lookup.
- Dictionary* dictionary = receiver->property_dictionary();
- int entry = dictionary->FindStringEntry(key);
- if ((entry != Dictionary::kNotFound) &&
+ StringDictionary* dictionary = receiver->property_dictionary();
+ int entry = dictionary->FindEntry(key);
+ if ((entry != StringDictionary::kNotFound) &&
(dictionary->DetailsAt(entry).type() == NORMAL)) {
Object* value = dictionary->ValueAt(entry);
if (receiver->IsGlobalObject()) {
@@ -5136,8 +5136,8 @@
storage_->set(index, *elm);
} else {
- Handle<Dictionary> dict = Handle<Dictionary>::cast(storage_);
- Handle<Dictionary> result =
+ Handle<NumberDictionary> dict = Handle<NumberDictionary>::cast(storage_);
+ Handle<NumberDictionary> result =
Factory::DictionaryAtNumberPut(dict, index, elm);
if (!result.is_identical_to(dict))
storage_ = result;
@@ -5185,7 +5185,7 @@
}
} else {
- Handle<Dictionary> dict(receiver->element_dictionary());
+ Handle<NumberDictionary> dict(receiver->element_dictionary());
uint32_t capacity = dict->Capacity();
for (uint32_t j = 0; j < capacity; j++) {
Handle<Object> k(dict->KeyAt(j));
@@ -5339,7 +5339,7 @@
uint32_t at_least_space_for = estimate_nof_elements +
(estimate_nof_elements >> 2);
storage = Handle<FixedArray>::cast(
- Factory::NewDictionary(at_least_space_for));
+ Factory::NewNumberDictionary(at_least_space_for));
}
Handle<Object> len = Factory::NewNumber(static_cast<double>(result_length));
@@ -5402,7 +5402,7 @@
CONVERT_CHECKED(JSArray, array, args[0]);
HeapObject* elements = array->elements();
if (elements->IsDictionary()) {
- return Smi::FromInt(Dictionary::cast(elements)->NumberOfElements());
+ return Smi::FromInt(NumberDictionary::cast(elements)->NumberOfElements());
} else {
return array->length();
}
@@ -7420,32 +7420,46 @@
// element segments each containing a receiver, function and native
// code offset.
static Object* Runtime_CollectStackTrace(Arguments args) {
- ASSERT_EQ(args.length(), 1);
+ ASSERT_EQ(args.length(), 2);
Object* caller = args[0];
+ CONVERT_NUMBER_CHECKED(int32_t, limit, Int32, args[1]);
+
+ HandleScope scope;
+
+ int initial_size = limit < 10 ? limit : 10;
+ Handle<JSArray> result = Factory::NewJSArray(initial_size * 3);
StackFrameIterator iter;
- int frame_count = 0;
bool seen_caller = false;
- while (!iter.done()) {
- if (ShowFrameInStackTrace(iter.frame(), caller, &seen_caller))
- frame_count++;
- iter.Advance();
- }
- HandleScope scope;
- Handle<JSArray> result = Factory::NewJSArray(frame_count * 3);
- int i = 0;
- seen_caller = false;
- for (iter.Reset(); !iter.done(); iter.Advance()) {
+ int cursor = 0;
+ int frames_seen = 0;
+ while (!iter.done() && frames_seen < limit) {
StackFrame* raw_frame = iter.frame();
if (ShowFrameInStackTrace(raw_frame, caller, &seen_caller)) {
+ frames_seen++;
JavaScriptFrame* frame = JavaScriptFrame::cast(raw_frame);
- result->SetElement(i++, frame->receiver());
- result->SetElement(i++, frame->function());
+ Object* recv = frame->receiver();
+ Object* fun = frame->function();
Address pc = frame->pc();
Address start = frame->code()->address();
- result->SetElement(i++, Smi::FromInt(pc - start));
+ Smi* offset = Smi::FromInt(pc - start);
+ FixedArray* elements = result->elements();
+ if (cursor + 2 < elements->length()) {
+ elements->set(cursor++, recv);
+ elements->set(cursor++, fun);
+ elements->set(cursor++, offset, SKIP_WRITE_BARRIER);
+ } else {
+ HandleScope scope;
+ SetElement(result, cursor++, Handle<Object>(recv));
+ SetElement(result, cursor++, Handle<Object>(fun));
+ SetElement(result, cursor++, Handle<Smi>(offset));
+ }
}
+ iter.Advance();
}
+
+ result->set_length(Smi::FromInt(cursor), SKIP_WRITE_BARRIER);
+
return *result;
}