summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorMichal Klocek <michal.klocek@qt.io>2017-05-16 13:04:46 +0200
committerMichal Klocek <michal.klocek@qt.io>2017-07-19 11:04:27 +0000
commit9966a98c2c90603a7ed3c7bd61609d441b782116 (patch)
tree5483359e4b97b23ea55117b38a0a2c3e7b812f4f
parent2c15cc053c4bbb8a3ad3bf9b52c0502cd0a632f8 (diff)
[Backport] CVE-2017-5054
Merged: [runtime] Ensure that canonical empty dictionaries reallocate upon addition. Revision: 17ac7c5f4d712c914030e1fb7247d2083b04b929 BUG=chromium:699166 LOG=N NOTRY=true NOPRESUBMIT=true NOTREECHECKS=true Reviewed-on: https://chromium-review.googlesource.com/456703 Reviewed-by: Igor Sheludko <ishell@chromium.org> Cr-Commit-Position: refs/branch-heads/5.8@{#35} Cr-Branched-From: eda659cc5e307f20ac1ad542ba12ab32eaf4c7ef-refs/heads/5.8.283@{#1} Cr-Branched-From: 4310cd02d2160b1457baed81a2f40063eb264a21-refs/heads/master@{#43429} Change-Id: Icb1453cc24519319992629b13846cb46d7e9fc85 Reviewed-by: Allan Sandfeld Jensen <allan.jensen@qt.io>
-rw-r--r--chromium/v8/src/heap/heap.cc4
-rw-r--r--chromium/v8/src/objects.cc26
-rw-r--r--chromium/v8/src/objects.h7
3 files changed, 34 insertions, 3 deletions
diff --git a/chromium/v8/src/heap/heap.cc b/chromium/v8/src/heap/heap.cc
index 7983d478973..f93adb8b6b8 100644
--- a/chromium/v8/src/heap/heap.cc
+++ b/chromium/v8/src/heap/heap.cc
@@ -2753,7 +2753,7 @@ void Heap::CreateInitialObjects() {
set_intrinsic_function_names(*intrinsic_names);
Handle<NameDictionary> empty_properties_dictionary =
- NameDictionary::New(isolate(), 0, TENURED);
+ NameDictionary::NewEmpty(isolate(), TENURED);
empty_properties_dictionary->SetRequiresCopyOnCapacityChange();
set_empty_properties_dictionary(*empty_properties_dictionary);
@@ -2850,7 +2850,7 @@ void Heap::CreateInitialObjects() {
set_script_list(Smi::FromInt(0));
Handle<SeededNumberDictionary> slow_element_dictionary =
- SeededNumberDictionary::New(isolate(), 0, TENURED);
+ SeededNumberDictionary::NewEmpty(isolate(), TENURED);
slow_element_dictionary->set_requires_slow_elements();
set_empty_slow_element_dictionary(*slow_element_dictionary);
diff --git a/chromium/v8/src/objects.cc b/chromium/v8/src/objects.cc
index 5601768da28..9b463de1805 100644
--- a/chromium/v8/src/objects.cc
+++ b/chromium/v8/src/objects.cc
@@ -17082,7 +17082,13 @@ Handle<Derived> HashTable<Derived, Shape, Key>::New(
if (capacity > HashTable::kMaxCapacity) {
v8::internal::Heap::FatalProcessOutOfMemory("invalid table size", true);
}
+ return New(isolate, capacity, pretenure);
+}
+template <typename Derived, typename Shape, typename Key>
+Handle<Derived> HashTable<Derived, Shape, Key>::New(Isolate* isolate,
+ int capacity,
+ PretenureFlag pretenure) {
Factory* factory = isolate->factory();
int length = EntryToIndex(capacity);
Handle<FixedArray> array = factory->NewFixedArray(length, pretenure);
@@ -17095,7 +17101,6 @@ Handle<Derived> HashTable<Derived, Shape, Key>::New(
return table;
}
-
// Find entry for key otherwise return kNotFound.
template <typename Derived, typename Shape>
int NameDictionaryBase<Derived, Shape>::FindEntry(Handle<Name> key) {
@@ -17363,6 +17368,10 @@ template Handle<SeededNumberDictionary>
Dictionary<SeededNumberDictionary, SeededNumberDictionaryShape, uint32_t>::
New(Isolate*, int at_least_space_for, PretenureFlag pretenure);
+template Handle<SeededNumberDictionary>
+Dictionary<SeededNumberDictionary, SeededNumberDictionaryShape,
+ uint32_t>::NewEmpty(Isolate*, PretenureFlag pretenure);
+
template Handle<UnseededNumberDictionary>
Dictionary<UnseededNumberDictionary, UnseededNumberDictionaryShape, uint32_t>::
New(Isolate*, int at_least_space_for, PretenureFlag pretenure);
@@ -17371,6 +17380,10 @@ template Handle<NameDictionary>
Dictionary<NameDictionary, NameDictionaryShape, Handle<Name> >::
New(Isolate*, int n, PretenureFlag pretenure);
+template Handle<NameDictionary>
+Dictionary<NameDictionary, NameDictionaryShape, Handle<Name>>::NewEmpty(
+ Isolate*, PretenureFlag pretenure);
+
template Handle<GlobalDictionary>
Dictionary<GlobalDictionary, GlobalDictionaryShape, Handle<Name> >::New(
Isolate*, int n, PretenureFlag pretenure);
@@ -18154,6 +18167,17 @@ Handle<FixedArray> Dictionary<Derived, Shape, Key>::BuildIterationIndicesArray(
template <typename Derived, typename Shape, typename Key>
+Handle<Derived> Dictionary<Derived, Shape, Key>::NewEmpty(
+ Isolate* isolate, PretenureFlag pretenure) {
+ Handle<Derived> dict = DerivedHashTable::New(isolate, 1, pretenure);
+ // Attempt to add one element to the empty dictionary must cause reallocation.
+ DCHECK(!dict->HasSufficientCapacityToAdd(1));
+ // Initialize the next enumeration index.
+ dict->SetNextEnumerationIndex(PropertyDetails::kInitialIndex);
+ return dict;
+}
+
+template <typename Derived, typename Shape, typename Key>
Handle<FixedArray>
Dictionary<Derived, Shape, Key>::GenerateNewEnumerationIndices(
Handle<Derived> dictionary) {
diff --git a/chromium/v8/src/objects.h b/chromium/v8/src/objects.h
index d737a18fe9f..151ab523ddf 100644
--- a/chromium/v8/src/objects.h
+++ b/chromium/v8/src/objects.h
@@ -3199,6 +3199,9 @@ class HashTable : public HashTableBase {
protected:
friend class ObjectHashTable;
+ MUST_USE_RESULT static Handle<Derived> New(Isolate* isolate, int capacity,
+ PretenureFlag pretenure);
+
// Find the entry at which to insert element with the given key that
// has the given hash value.
uint32_t FindInsertionEntry(uint32_t hash);
@@ -3415,6 +3418,10 @@ class Dictionary: public HashTable<Derived, Shape, Key> {
int at_least_space_for,
PretenureFlag pretenure = NOT_TENURED);
+ // Creates an dictionary with minimal possible capacity.
+ MUST_USE_RESULT static Handle<Derived> NewEmpty(
+ Isolate* isolate, PretenureFlag pretenure = NOT_TENURED);
+
// Ensures that a new dictionary is created when the capacity is checked.
void SetRequiresCopyOnCapacityChange();