Version 3.12.15
Added PRESERVE_ASCII_NULL option to String::WriteAscii. (issue 2252)
Added dependency to HLoadKeyed* instructions to prevent invalid hoisting. (Chromium issue 137768)
Enabled building d8 for Android on Mac.
Interpret negative hexadecimal literals as NaN. (issue 2240)
Expose counters in javascript when using --track-gc-object-stats.
Enabled building and testing V8 on Android IA.
Added --trace-parse flag to parser.
Performance and stability improvements on all platforms.
git-svn-id: http://v8.googlecode.com/svn/trunk@12180 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
diff --git a/src/objects-inl.h b/src/objects-inl.h
index feca271..f4e0767 100644
--- a/src/objects-inl.h
+++ b/src/objects-inl.h
@@ -1952,12 +1952,12 @@
// Perform a linear search in this fixed array. len is the number of entry
// indices that are valid.
template<typename T>
-int LinearSearch(T* array, SearchMode mode, String* name, int len) {
+int LinearSearch(T* array, String* name, int len) {
uint32_t hash = name->Hash();
for (int number = 0; number < len; number++) {
String* entry = array->GetKey(number);
uint32_t current_hash = entry->Hash();
- if (mode == EXPECT_SORTED && current_hash > hash) break;
+ if (current_hash > hash) break;
if (current_hash == hash && name->Equals(entry)) return number;
}
return T::kNotFound;
@@ -1975,7 +1975,7 @@
// Fast case: do linear search for small arrays.
const int kMaxElementsForLinearSearch = 8;
if (StringShape(name).IsSymbol() && nof < kMaxElementsForLinearSearch) {
- return LinearSearch(array, EXPECT_SORTED, name, nof);
+ return LinearSearch(array, name, nof);
}
// Slow case: perform binary search.
@@ -2110,13 +2110,26 @@
}
-void DescriptorArray::Append(Descriptor* desc,
- const WhitenessWitness& witness) {
- int descriptor_number = NumberOfSetDescriptors();
+int DescriptorArray::Append(Descriptor* desc,
+ const WhitenessWitness& witness,
+ int number_of_set_descriptors) {
+ int descriptor_number = number_of_set_descriptors;
int enumeration_index = descriptor_number + 1;
desc->SetEnumerationIndex(enumeration_index);
+
+ uint32_t hash = desc->GetKey()->Hash();
+
+ for (; descriptor_number > 0; --descriptor_number) {
+ String* key = GetKey(descriptor_number - 1);
+ if (key->Hash() <= hash) break;
+ Object* value = GetValue(descriptor_number - 1);
+ PropertyDetails details = GetDetails(descriptor_number - 1);
+ Descriptor moved_descriptor(key, value, details);
+ Set(descriptor_number, &moved_descriptor, witness);
+ }
+
Set(descriptor_number, desc, witness);
- SetLastAdded(descriptor_number);
+ return descriptor_number;
}
@@ -2434,9 +2447,10 @@
}
-void SlicedString::set_parent(String* parent) {
+void SlicedString::set_parent(String* parent, WriteBarrierMode mode) {
ASSERT(parent->IsSeqString() || parent->IsExternalString());
WRITE_FIELD(this, kParentOffset, parent);
+ CONDITIONAL_WRITE_BARRIER(GetHeap(), this, kParentOffset, parent, mode);
}
@@ -2940,16 +2954,12 @@
void Map::set_function_with_prototype(bool value) {
- if (value) {
- set_bit_field3(bit_field3() | (1 << kFunctionWithPrototype));
- } else {
- set_bit_field3(bit_field3() & ~(1 << kFunctionWithPrototype));
- }
+ set_bit_field3(FunctionWithPrototype::update(bit_field3(), value));
}
bool Map::function_with_prototype() {
- return ((1 << kFunctionWithPrototype) & bit_field3()) != 0;
+ return FunctionWithPrototype::decode(bit_field3());
}
@@ -2994,15 +3004,11 @@
void Map::set_is_shared(bool value) {
- if (value) {
- set_bit_field3(bit_field3() | (1 << kIsShared));
- } else {
- set_bit_field3(bit_field3() & ~(1 << kIsShared));
- }
+ set_bit_field3(IsShared::update(bit_field3(), value));
}
bool Map::is_shared() {
- return ((1 << kIsShared) & bit_field3()) != 0;
+ return IsShared::decode(bit_field3());
}
@@ -3488,6 +3494,40 @@
}
+void Map::InitializeDescriptors(DescriptorArray* descriptors) {
+ int len = descriptors->number_of_descriptors();
+ ASSERT(len <= DescriptorArray::kMaxNumberOfDescriptors);
+ SLOW_ASSERT(descriptors->IsSortedNoDuplicates());
+
+#ifdef DEBUG
+ bool used_indices[DescriptorArray::kMaxNumberOfDescriptors];
+ for (int i = 0; i < len; ++i) used_indices[i] = false;
+
+ // Ensure that all enumeration indexes between 1 and length occur uniquely in
+ // the descriptor array.
+ for (int i = 0; i < len; ++i) {
+ int enum_index = descriptors->GetDetails(i).index() -
+ PropertyDetails::kInitialIndex;
+ ASSERT(0 <= enum_index && enum_index < len);
+ ASSERT(!used_indices[enum_index]);
+ used_indices[enum_index] = true;
+ }
+#endif
+
+ set_instance_descriptors(descriptors);
+
+ for (int i = 0; i < len; ++i) {
+ if (descriptors->GetDetails(i).index() == len) {
+ SetLastAdded(i);
+ break;
+ }
+ }
+
+ ASSERT(len == 0 ||
+ len == descriptors->GetDetails(LastAdded()).index());
+}
+
+
SMI_ACCESSORS(Map, bit_field3, kBitField3Offset)
@@ -3507,6 +3547,14 @@
}
+void Map::AppendDescriptor(Descriptor* desc,
+ const DescriptorArray::WhitenessWitness& witness) {
+ DescriptorArray* descriptors = instance_descriptors();
+ int set_descriptors = NumberOfSetDescriptors();
+ int new_last_added = descriptors->Append(desc, witness, set_descriptors);
+ SetLastAdded(new_last_added);
+}
+
Object* Map::GetBackPointer() {
Object* object = READ_FIELD(this, kInstanceDescriptorsOrBackPointerOffset);
@@ -4202,6 +4250,18 @@
}
+bool JSFunction::IsMarkedForParallelRecompilation() {
+ return code() ==
+ GetIsolate()->builtins()->builtin(Builtins::kParallelRecompile);
+}
+
+
+bool JSFunction::IsInRecompileQueue() {
+ return code() == GetIsolate()->builtins()->builtin(
+ Builtins::kInRecompileQueue);
+}
+
+
Code* JSFunction::code() {
return Code::cast(unchecked_code());
}