OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 the V8 project authors. All rights reserved. |
2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
4 | 4 |
5 #include <sstream> | 5 #include <sstream> |
6 | 6 |
7 #include "src/v8.h" | 7 #include "src/v8.h" |
8 | 8 |
9 #include "src/accessors.h" | 9 #include "src/accessors.h" |
10 #include "src/allocation-site-scopes.h" | 10 #include "src/allocation-site-scopes.h" |
(...skipping 1790 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1801 // but any JSFunction knows its context immediately. | 1801 // but any JSFunction knows its context immediately. |
1802 function = JSFunction::cast(this); | 1802 function = JSFunction::cast(this); |
1803 } else { | 1803 } else { |
1804 function = JSFunction::cast(constructor); | 1804 function = JSFunction::cast(constructor); |
1805 } | 1805 } |
1806 | 1806 |
1807 return function->context()->native_context(); | 1807 return function->context()->native_context(); |
1808 } | 1808 } |
1809 | 1809 |
1810 | 1810 |
1811 void JSObject::EnqueueChangeRecord(Handle<JSObject> object, | 1811 MaybeHandle<Object> JSObject::EnqueueChangeRecord(Handle<JSObject> object, |
1812 const char* type_str, | 1812 const char* type_str, |
1813 Handle<Name> name, | 1813 Handle<Name> name, |
1814 Handle<Object> old_value) { | 1814 Handle<Object> old_value) { |
1815 DCHECK(!object->IsJSGlobalProxy()); | 1815 DCHECK(!object->IsJSGlobalProxy()); |
1816 DCHECK(!object->IsJSGlobalObject()); | 1816 DCHECK(!object->IsJSGlobalObject()); |
1817 Isolate* isolate = object->GetIsolate(); | 1817 Isolate* isolate = object->GetIsolate(); |
1818 HandleScope scope(isolate); | 1818 HandleScope scope(isolate); |
1819 Handle<String> type = isolate->factory()->InternalizeUtf8String(type_str); | 1819 Handle<String> type = isolate->factory()->InternalizeUtf8String(type_str); |
1820 Handle<Object> args[] = { type, object, name, old_value }; | 1820 Handle<Object> args[] = { type, object, name, old_value }; |
1821 int argc = name.is_null() ? 2 : old_value->IsTheHole() ? 3 : 4; | 1821 int argc = name.is_null() ? 2 : old_value->IsTheHole() ? 3 : 4; |
1822 | 1822 |
1823 Execution::Call(isolate, | 1823 return Execution::Call(isolate, |
1824 Handle<JSFunction>(isolate->observers_notify_change()), | 1824 Handle<JSFunction>(isolate->observers_notify_change()), |
1825 isolate->factory()->undefined_value(), | 1825 isolate->factory()->undefined_value(), argc, args); |
1826 argc, args).Assert(); | |
1827 } | 1826 } |
1828 | 1827 |
1829 | 1828 |
1830 const char* Representation::Mnemonic() const { | 1829 const char* Representation::Mnemonic() const { |
1831 switch (kind_) { | 1830 switch (kind_) { |
1832 case kNone: return "v"; | 1831 case kNone: return "v"; |
1833 case kTagged: return "t"; | 1832 case kTagged: return "t"; |
1834 case kSmi: return "s"; | 1833 case kSmi: return "s"; |
1835 case kDouble: return "d"; | 1834 case kDouble: return "d"; |
1836 case kInteger32: return "i"; | 1835 case kInteger32: return "i"; |
(...skipping 1086 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2923 if (strict_mode != STRICT) return value; | 2922 if (strict_mode != STRICT) return value; |
2924 | 2923 |
2925 Handle<Object> args[] = {it->name(), it->GetReceiver()}; | 2924 Handle<Object> args[] = {it->name(), it->GetReceiver()}; |
2926 THROW_NEW_ERROR(it->isolate(), | 2925 THROW_NEW_ERROR(it->isolate(), |
2927 NewTypeError("strict_read_only_property", | 2926 NewTypeError("strict_read_only_property", |
2928 HandleVector(args, arraysize(args))), | 2927 HandleVector(args, arraysize(args))), |
2929 Object); | 2928 Object); |
2930 } | 2929 } |
2931 | 2930 |
2932 | 2931 |
2933 Handle<Object> Object::SetDataProperty(LookupIterator* it, | 2932 MaybeHandle<Object> Object::SetDataProperty(LookupIterator* it, |
2934 Handle<Object> value) { | 2933 Handle<Object> value) { |
2935 // Proxies are handled on the WithHandler path. Other non-JSObjects cannot | 2934 // Proxies are handled on the WithHandler path. Other non-JSObjects cannot |
2936 // have own properties. | 2935 // have own properties. |
2937 Handle<JSObject> receiver = Handle<JSObject>::cast(it->GetReceiver()); | 2936 Handle<JSObject> receiver = Handle<JSObject>::cast(it->GetReceiver()); |
2938 | 2937 |
2939 // Store on the holder which may be hidden behind the receiver. | 2938 // Store on the holder which may be hidden behind the receiver. |
2940 DCHECK(it->HolderIsReceiverOrHiddenPrototype()); | 2939 DCHECK(it->HolderIsReceiverOrHiddenPrototype()); |
2941 | 2940 |
2942 // Old value for the observation change record. | 2941 // Old value for the observation change record. |
2943 // Fetch before transforming the object since the encoding may become | 2942 // Fetch before transforming the object since the encoding may become |
2944 // incompatible with what's cached in |it|. | 2943 // incompatible with what's cached in |it|. |
2945 bool is_observed = | 2944 bool is_observed = |
2946 receiver->map()->is_observed() && | 2945 receiver->map()->is_observed() && |
2947 !it->name().is_identical_to(it->factory()->hidden_string()); | 2946 !it->name().is_identical_to(it->factory()->hidden_string()); |
2948 MaybeHandle<Object> maybe_old; | 2947 MaybeHandle<Object> maybe_old; |
2949 if (is_observed) maybe_old = it->GetDataValue(); | 2948 if (is_observed) maybe_old = it->GetDataValue(); |
2950 | 2949 |
2951 // Possibly migrate to the most up-to-date map that will be able to store | 2950 // Possibly migrate to the most up-to-date map that will be able to store |
2952 // |value| under it->name(). | 2951 // |value| under it->name(). |
2953 it->PrepareForDataProperty(value); | 2952 it->PrepareForDataProperty(value); |
2954 | 2953 |
2955 // Write the property value. | 2954 // Write the property value. |
2956 it->WriteDataValue(value); | 2955 it->WriteDataValue(value); |
2957 | 2956 |
2958 // Send the change record if there are observers. | 2957 // Send the change record if there are observers. |
2959 if (is_observed && !value->SameValue(*maybe_old.ToHandleChecked())) { | 2958 if (is_observed && !value->SameValue(*maybe_old.ToHandleChecked())) { |
2960 JSObject::EnqueueChangeRecord(receiver, "update", it->name(), | 2959 RETURN_ON_EXCEPTION(it->isolate(), JSObject::EnqueueChangeRecord( |
2961 maybe_old.ToHandleChecked()); | 2960 receiver, "update", it->name(), |
| 2961 maybe_old.ToHandleChecked()), |
| 2962 Object); |
2962 } | 2963 } |
2963 | 2964 |
2964 return value; | 2965 return value; |
2965 } | 2966 } |
2966 | 2967 |
2967 | 2968 |
2968 MaybeHandle<Object> Object::AddDataProperty(LookupIterator* it, | 2969 MaybeHandle<Object> Object::AddDataProperty(LookupIterator* it, |
2969 Handle<Object> value, | 2970 Handle<Object> value, |
2970 PropertyAttributes attributes, | 2971 PropertyAttributes attributes, |
2971 StrictMode strict_mode, | 2972 StrictMode strict_mode, |
(...skipping 30 matching lines...) Expand all Loading... |
3002 it->InternalizeName(); | 3003 it->InternalizeName(); |
3003 JSObject::AddSlowProperty(receiver, it->name(), value, attributes); | 3004 JSObject::AddSlowProperty(receiver, it->name(), value, attributes); |
3004 } else { | 3005 } else { |
3005 // Write the property value. | 3006 // Write the property value. |
3006 it->WriteDataValue(value); | 3007 it->WriteDataValue(value); |
3007 } | 3008 } |
3008 | 3009 |
3009 // Send the change record if there are observers. | 3010 // Send the change record if there are observers. |
3010 if (receiver->map()->is_observed() && | 3011 if (receiver->map()->is_observed() && |
3011 !it->name().is_identical_to(it->factory()->hidden_string())) { | 3012 !it->name().is_identical_to(it->factory()->hidden_string())) { |
3012 JSObject::EnqueueChangeRecord(receiver, "add", it->name(), | 3013 RETURN_ON_EXCEPTION(it->isolate(), JSObject::EnqueueChangeRecord( |
3013 it->factory()->the_hole_value()); | 3014 receiver, "add", it->name(), |
| 3015 it->factory()->the_hole_value()), |
| 3016 Object); |
3014 } | 3017 } |
3015 | 3018 |
3016 return value; | 3019 return value; |
3017 } | 3020 } |
3018 | 3021 |
3019 | 3022 |
3020 MaybeHandle<Object> JSObject::SetElementWithCallbackSetterInPrototypes( | 3023 MaybeHandle<Object> JSObject::SetElementWithCallbackSetterInPrototypes( |
3021 Handle<JSObject> object, | 3024 Handle<JSObject> object, |
3022 uint32_t index, | 3025 uint32_t index, |
3023 Handle<Object> value, | 3026 Handle<Object> value, |
(...skipping 828 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3852 if (details.attributes() == attributes) { | 3855 if (details.attributes() == attributes) { |
3853 // Regular property update if the attributes match. | 3856 // Regular property update if the attributes match. |
3854 if (is_observed && !old_value->SameValue(*value)) { | 3857 if (is_observed && !old_value->SameValue(*value)) { |
3855 // If we are setting the prototype of a function and are | 3858 // If we are setting the prototype of a function and are |
3856 // observed, don't send change records because the prototype | 3859 // observed, don't send change records because the prototype |
3857 // handles that itself. | 3860 // handles that itself. |
3858 if (!object->IsJSFunction() || | 3861 if (!object->IsJSFunction() || |
3859 !Name::Equals(it.isolate()->factory()->prototype_string(), | 3862 !Name::Equals(it.isolate()->factory()->prototype_string(), |
3860 name) || | 3863 name) || |
3861 !Handle<JSFunction>::cast(object)->should_have_prototype()) { | 3864 !Handle<JSFunction>::cast(object)->should_have_prototype()) { |
3862 EnqueueChangeRecord(object, "update", name, old_value); | 3865 RETURN_ON_EXCEPTION( |
| 3866 it.isolate(), |
| 3867 EnqueueChangeRecord(object, "update", name, old_value), |
| 3868 Object); |
3863 } | 3869 } |
3864 } | 3870 } |
3865 return value; | 3871 return value; |
3866 } | 3872 } |
3867 | 3873 |
3868 // Reconfigure the accessor if attributes mismatch. | 3874 // Reconfigure the accessor if attributes mismatch. |
3869 Handle<ExecutableAccessorInfo> new_data = Accessors::CloneAccessor( | 3875 Handle<ExecutableAccessorInfo> new_data = Accessors::CloneAccessor( |
3870 it.isolate(), Handle<ExecutableAccessorInfo>::cast(accessors)); | 3876 it.isolate(), Handle<ExecutableAccessorInfo>::cast(accessors)); |
3871 new_data->set_property_attributes(attributes); | 3877 new_data->set_property_attributes(attributes); |
3872 // By clearing the setter we don't have to introduce a lookup to | 3878 // By clearing the setter we don't have to introduce a lookup to |
3873 // the setter, simply make it unavailable to reflect the | 3879 // the setter, simply make it unavailable to reflect the |
3874 // attributes. | 3880 // attributes. |
3875 if (attributes & READ_ONLY) new_data->clear_setter(); | 3881 if (attributes & READ_ONLY) new_data->clear_setter(); |
3876 SetPropertyCallback(object, name, new_data, attributes); | 3882 SetPropertyCallback(object, name, new_data, attributes); |
3877 if (is_observed) { | 3883 if (is_observed) { |
3878 if (old_value->SameValue(*value)) { | 3884 if (old_value->SameValue(*value)) { |
3879 old_value = it.isolate()->factory()->the_hole_value(); | 3885 old_value = it.isolate()->factory()->the_hole_value(); |
3880 } | 3886 } |
3881 EnqueueChangeRecord(object, "reconfigure", name, old_value); | 3887 RETURN_ON_EXCEPTION( |
| 3888 it.isolate(), |
| 3889 EnqueueChangeRecord(object, "reconfigure", name, old_value), |
| 3890 Object); |
3882 } | 3891 } |
3883 return value; | 3892 return value; |
3884 } | 3893 } |
3885 | 3894 |
3886 it.ReconfigureDataProperty(value, attributes); | 3895 it.ReconfigureDataProperty(value, attributes); |
3887 it.PrepareForDataProperty(value); | 3896 it.PrepareForDataProperty(value); |
3888 it.WriteDataValue(value); | 3897 it.WriteDataValue(value); |
3889 | 3898 |
3890 if (is_observed) { | 3899 if (is_observed) { |
3891 if (old_value->SameValue(*value)) { | 3900 if (old_value->SameValue(*value)) { |
3892 old_value = it.isolate()->factory()->the_hole_value(); | 3901 old_value = it.isolate()->factory()->the_hole_value(); |
3893 } | 3902 } |
3894 EnqueueChangeRecord(object, "reconfigure", name, old_value); | 3903 RETURN_ON_EXCEPTION( |
| 3904 it.isolate(), |
| 3905 EnqueueChangeRecord(object, "reconfigure", name, old_value), |
| 3906 Object); |
3895 } | 3907 } |
3896 | 3908 |
3897 return value; | 3909 return value; |
3898 } | 3910 } |
3899 | 3911 |
3900 case LookupIterator::DATA: { | 3912 case LookupIterator::DATA: { |
3901 PropertyDetails details = it.property_details(); | 3913 PropertyDetails details = it.property_details(); |
3902 Handle<Object> old_value = it.isolate()->factory()->the_hole_value(); | 3914 Handle<Object> old_value = it.isolate()->factory()->the_hole_value(); |
3903 // Regular property update if the attributes match. | 3915 // Regular property update if the attributes match. |
3904 if (details.attributes() == attributes) { | 3916 if (details.attributes() == attributes) { |
3905 return SetDataProperty(&it, value); | 3917 return SetDataProperty(&it, value); |
3906 } | 3918 } |
3907 // Reconfigure the data property if the attributes mismatch. | 3919 // Reconfigure the data property if the attributes mismatch. |
3908 if (is_observed) old_value = it.GetDataValue(); | 3920 if (is_observed) old_value = it.GetDataValue(); |
3909 | 3921 |
3910 it.ReconfigureDataProperty(value, attributes); | 3922 it.ReconfigureDataProperty(value, attributes); |
3911 it.PrepareForDataProperty(value); | 3923 it.PrepareForDataProperty(value); |
3912 it.WriteDataValue(value); | 3924 it.WriteDataValue(value); |
3913 | 3925 |
3914 if (is_observed) { | 3926 if (is_observed) { |
3915 if (old_value->SameValue(*value)) { | 3927 if (old_value->SameValue(*value)) { |
3916 old_value = it.isolate()->factory()->the_hole_value(); | 3928 old_value = it.isolate()->factory()->the_hole_value(); |
3917 } | 3929 } |
3918 EnqueueChangeRecord(object, "reconfigure", name, old_value); | 3930 RETURN_ON_EXCEPTION( |
| 3931 it.isolate(), |
| 3932 EnqueueChangeRecord(object, "reconfigure", name, old_value), |
| 3933 Object); |
3919 } | 3934 } |
3920 | 3935 |
3921 return value; | 3936 return value; |
3922 } | 3937 } |
3923 } | 3938 } |
3924 } | 3939 } |
3925 | 3940 |
3926 return AddDataProperty(&it, value, attributes, STRICT, | 3941 return AddDataProperty(&it, value, attributes, STRICT, |
3927 CERTAINLY_NOT_STORE_FROM_KEYED); | 3942 CERTAINLY_NOT_STORE_FROM_KEYED); |
3928 } | 3943 } |
(...skipping 952 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4881 maybe_result = object->GetElementsAccessor()->Delete(object, index, mode); | 4896 maybe_result = object->GetElementsAccessor()->Delete(object, index, mode); |
4882 } | 4897 } |
4883 Handle<Object> result; | 4898 Handle<Object> result; |
4884 ASSIGN_RETURN_ON_EXCEPTION(isolate, result, maybe_result, Object); | 4899 ASSIGN_RETURN_ON_EXCEPTION(isolate, result, maybe_result, Object); |
4885 | 4900 |
4886 if (should_enqueue_change_record) { | 4901 if (should_enqueue_change_record) { |
4887 Maybe<bool> maybe = HasOwnElement(object, index); | 4902 Maybe<bool> maybe = HasOwnElement(object, index); |
4888 if (!maybe.has_value) return MaybeHandle<Object>(); | 4903 if (!maybe.has_value) return MaybeHandle<Object>(); |
4889 if (!maybe.value) { | 4904 if (!maybe.value) { |
4890 Handle<String> name = factory->Uint32ToString(index); | 4905 Handle<String> name = factory->Uint32ToString(index); |
4891 EnqueueChangeRecord(object, "delete", name, old_value); | 4906 RETURN_ON_EXCEPTION( |
| 4907 isolate, EnqueueChangeRecord(object, "delete", name, old_value), |
| 4908 Object); |
4892 } | 4909 } |
4893 } | 4910 } |
4894 | 4911 |
4895 return result; | 4912 return result; |
4896 } | 4913 } |
4897 | 4914 |
4898 | 4915 |
4899 MaybeHandle<Object> JSObject::DeleteProperty(Handle<JSObject> object, | 4916 MaybeHandle<Object> JSObject::DeleteProperty(Handle<JSObject> object, |
4900 Handle<Name> name, | 4917 Handle<Name> name, |
4901 DeleteMode delete_mode) { | 4918 DeleteMode delete_mode) { |
(...skipping 65 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
4967 if (!holder.is_identical_to(object) && | 4984 if (!holder.is_identical_to(object) && |
4968 !(object->IsJSGlobalProxy() && holder->IsJSGlobalObject())) { | 4985 !(object->IsJSGlobalProxy() && holder->IsJSGlobalObject())) { |
4969 return it.isolate()->factory()->true_value(); | 4986 return it.isolate()->factory()->true_value(); |
4970 } | 4987 } |
4971 NormalizeProperties(holder, mode, 0); | 4988 NormalizeProperties(holder, mode, 0); |
4972 Handle<Object> result = | 4989 Handle<Object> result = |
4973 DeleteNormalizedProperty(holder, name, delete_mode); | 4990 DeleteNormalizedProperty(holder, name, delete_mode); |
4974 ReoptimizeIfPrototype(holder); | 4991 ReoptimizeIfPrototype(holder); |
4975 | 4992 |
4976 if (is_observed) { | 4993 if (is_observed) { |
4977 EnqueueChangeRecord(object, "delete", name, old_value); | 4994 RETURN_ON_EXCEPTION( |
| 4995 it.isolate(), |
| 4996 EnqueueChangeRecord(object, "delete", name, old_value), Object); |
4978 } | 4997 } |
4979 | 4998 |
4980 return result; | 4999 return result; |
4981 } | 5000 } |
4982 } | 5001 } |
4983 } | 5002 } |
4984 | 5003 |
4985 return it.isolate()->factory()->true_value(); | 5004 return it.isolate()->factory()->true_value(); |
4986 } | 5005 } |
4987 | 5006 |
(...skipping 196 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5184 // Do a map transition, other objects with this map may still | 5203 // Do a map transition, other objects with this map may still |
5185 // be extensible. | 5204 // be extensible. |
5186 // TODO(adamk): Extend the NormalizedMapCache to handle non-extensible maps. | 5205 // TODO(adamk): Extend the NormalizedMapCache to handle non-extensible maps. |
5187 Handle<Map> new_map = Map::Copy(handle(object->map())); | 5206 Handle<Map> new_map = Map::Copy(handle(object->map())); |
5188 | 5207 |
5189 new_map->set_is_extensible(false); | 5208 new_map->set_is_extensible(false); |
5190 JSObject::MigrateToMap(object, new_map); | 5209 JSObject::MigrateToMap(object, new_map); |
5191 DCHECK(!object->map()->is_extensible()); | 5210 DCHECK(!object->map()->is_extensible()); |
5192 | 5211 |
5193 if (object->map()->is_observed()) { | 5212 if (object->map()->is_observed()) { |
5194 EnqueueChangeRecord(object, "preventExtensions", Handle<Name>(), | 5213 RETURN_ON_EXCEPTION( |
5195 isolate->factory()->the_hole_value()); | 5214 isolate, |
| 5215 EnqueueChangeRecord(object, "preventExtensions", Handle<Name>(), |
| 5216 isolate->factory()->the_hole_value()), |
| 5217 Object); |
5196 } | 5218 } |
5197 return object; | 5219 return object; |
5198 } | 5220 } |
5199 | 5221 |
5200 | 5222 |
5201 template<typename Dictionary> | 5223 template<typename Dictionary> |
5202 static void FreezeDictionary(Dictionary* dictionary) { | 5224 static void FreezeDictionary(Dictionary* dictionary) { |
5203 int capacity = dictionary->Capacity(); | 5225 int capacity = dictionary->Capacity(); |
5204 for (int i = 0; i < capacity; i++) { | 5226 for (int i = 0; i < capacity; i++) { |
5205 Object* k = dictionary->KeyAt(i); | 5227 Object* k = dictionary->KeyAt(i); |
(...skipping 952 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
6158 if (!getter->IsNull()) { | 6180 if (!getter->IsNull()) { |
6159 it.TransitionToAccessorProperty(ACCESSOR_GETTER, getter, attributes); | 6181 it.TransitionToAccessorProperty(ACCESSOR_GETTER, getter, attributes); |
6160 } | 6182 } |
6161 if (!setter->IsNull()) { | 6183 if (!setter->IsNull()) { |
6162 it.TransitionToAccessorProperty(ACCESSOR_SETTER, setter, attributes); | 6184 it.TransitionToAccessorProperty(ACCESSOR_SETTER, setter, attributes); |
6163 } | 6185 } |
6164 } | 6186 } |
6165 | 6187 |
6166 if (is_observed) { | 6188 if (is_observed) { |
6167 const char* type = preexists ? "reconfigure" : "add"; | 6189 const char* type = preexists ? "reconfigure" : "add"; |
6168 EnqueueChangeRecord(object, type, name, old_value); | 6190 RETURN_ON_EXCEPTION( |
| 6191 isolate, EnqueueChangeRecord(object, type, name, old_value), Object); |
6169 } | 6192 } |
6170 | 6193 |
6171 return isolate->factory()->undefined_value(); | 6194 return isolate->factory()->undefined_value(); |
6172 } | 6195 } |
6173 | 6196 |
6174 | 6197 |
6175 MaybeHandle<Object> JSObject::SetAccessor(Handle<JSObject> object, | 6198 MaybeHandle<Object> JSObject::SetAccessor(Handle<JSObject> object, |
6176 Handle<AccessorInfo> info) { | 6199 Handle<AccessorInfo> info) { |
6177 Isolate* isolate = object->GetIsolate(); | 6200 Isolate* isolate = object->GetIsolate(); |
6178 Factory* factory = isolate->factory(); | 6201 Factory* factory = isolate->factory(); |
(...skipping 5048 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
11227 | 11250 |
11228 CHECK(array->length()->ToArrayIndex(&new_length)); | 11251 CHECK(array->length()->ToArrayIndex(&new_length)); |
11229 if (old_length == new_length) return hresult; | 11252 if (old_length == new_length) return hresult; |
11230 | 11253 |
11231 BeginPerformSplice(array); | 11254 BeginPerformSplice(array); |
11232 | 11255 |
11233 for (int i = 0; i < indices.length(); ++i) { | 11256 for (int i = 0; i < indices.length(); ++i) { |
11234 // For deletions where the property was an accessor, old_values[i] | 11257 // For deletions where the property was an accessor, old_values[i] |
11235 // will be the hole, which instructs EnqueueChangeRecord to elide | 11258 // will be the hole, which instructs EnqueueChangeRecord to elide |
11236 // the "oldValue" property. | 11259 // the "oldValue" property. |
11237 JSObject::EnqueueChangeRecord( | 11260 RETURN_ON_EXCEPTION( |
11238 array, "delete", isolate->factory()->Uint32ToString(indices[i]), | 11261 isolate, |
11239 old_values[i]); | 11262 JSObject::EnqueueChangeRecord( |
| 11263 array, "delete", isolate->factory()->Uint32ToString(indices[i]), |
| 11264 old_values[i]), |
| 11265 Object); |
11240 } | 11266 } |
11241 JSObject::EnqueueChangeRecord( | 11267 RETURN_ON_EXCEPTION(isolate, |
11242 array, "update", isolate->factory()->length_string(), | 11268 JSObject::EnqueueChangeRecord( |
11243 old_length_handle); | 11269 array, "update", isolate->factory()->length_string(), |
| 11270 old_length_handle), |
| 11271 Object); |
11244 | 11272 |
11245 EndPerformSplice(array); | 11273 EndPerformSplice(array); |
11246 | 11274 |
11247 uint32_t index = Min(old_length, new_length); | 11275 uint32_t index = Min(old_length, new_length); |
11248 uint32_t add_count = new_length > old_length ? new_length - old_length : 0; | 11276 uint32_t add_count = new_length > old_length ? new_length - old_length : 0; |
11249 uint32_t delete_count = new_length < old_length ? old_length - new_length : 0; | 11277 uint32_t delete_count = new_length < old_length ? old_length - new_length : 0; |
11250 Handle<JSArray> deleted = isolate->factory()->NewJSArray(0); | 11278 Handle<JSArray> deleted = isolate->factory()->NewJSArray(0); |
11251 if (delete_count > 0) { | 11279 if (delete_count > 0) { |
11252 for (int i = indices.length() - 1; i >= 0; i--) { | 11280 for (int i = indices.length() - 1; i >= 0; i--) { |
11253 // Skip deletions where the property was an accessor, leaving holes | 11281 // Skip deletions where the property was an accessor, leaving holes |
(...skipping 1187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
12441 !old_length_handle->SameValue( | 12469 !old_length_handle->SameValue( |
12442 Handle<JSArray>::cast(object)->length())) { | 12470 Handle<JSArray>::cast(object)->length())) { |
12443 new_length_handle = handle(Handle<JSArray>::cast(object)->length(), | 12471 new_length_handle = handle(Handle<JSArray>::cast(object)->length(), |
12444 isolate); | 12472 isolate); |
12445 uint32_t old_length = 0; | 12473 uint32_t old_length = 0; |
12446 uint32_t new_length = 0; | 12474 uint32_t new_length = 0; |
12447 CHECK(old_length_handle->ToArrayIndex(&old_length)); | 12475 CHECK(old_length_handle->ToArrayIndex(&old_length)); |
12448 CHECK(new_length_handle->ToArrayIndex(&new_length)); | 12476 CHECK(new_length_handle->ToArrayIndex(&new_length)); |
12449 | 12477 |
12450 BeginPerformSplice(Handle<JSArray>::cast(object)); | 12478 BeginPerformSplice(Handle<JSArray>::cast(object)); |
12451 EnqueueChangeRecord(object, "add", name, old_value); | 12479 RETURN_ON_EXCEPTION( |
12452 EnqueueChangeRecord(object, "update", isolate->factory()->length_string(), | 12480 isolate, EnqueueChangeRecord(object, "add", name, old_value), Object); |
12453 old_length_handle); | 12481 RETURN_ON_EXCEPTION( |
| 12482 isolate, EnqueueChangeRecord(object, "update", |
| 12483 isolate->factory()->length_string(), |
| 12484 old_length_handle), |
| 12485 Object); |
12454 EndPerformSplice(Handle<JSArray>::cast(object)); | 12486 EndPerformSplice(Handle<JSArray>::cast(object)); |
12455 Handle<JSArray> deleted = isolate->factory()->NewJSArray(0); | 12487 Handle<JSArray> deleted = isolate->factory()->NewJSArray(0); |
12456 EnqueueSpliceRecord(Handle<JSArray>::cast(object), old_length, deleted, | 12488 EnqueueSpliceRecord(Handle<JSArray>::cast(object), old_length, deleted, |
12457 new_length - old_length); | 12489 new_length - old_length); |
12458 } else { | 12490 } else { |
12459 EnqueueChangeRecord(object, "add", name, old_value); | 12491 RETURN_ON_EXCEPTION( |
| 12492 isolate, EnqueueChangeRecord(object, "add", name, old_value), Object); |
12460 } | 12493 } |
12461 } else if (old_value->IsTheHole()) { | 12494 } else if (old_value->IsTheHole()) { |
12462 EnqueueChangeRecord(object, "reconfigure", name, old_value); | 12495 RETURN_ON_EXCEPTION( |
| 12496 isolate, EnqueueChangeRecord(object, "reconfigure", name, old_value), |
| 12497 Object); |
12463 } else { | 12498 } else { |
12464 Handle<Object> new_value = | 12499 Handle<Object> new_value = |
12465 Object::GetElement(isolate, object, index).ToHandleChecked(); | 12500 Object::GetElement(isolate, object, index).ToHandleChecked(); |
12466 bool value_changed = !old_value->SameValue(*new_value); | 12501 bool value_changed = !old_value->SameValue(*new_value); |
12467 if (old_attributes != new_attributes) { | 12502 if (old_attributes != new_attributes) { |
12468 if (!value_changed) old_value = isolate->factory()->the_hole_value(); | 12503 if (!value_changed) old_value = isolate->factory()->the_hole_value(); |
12469 EnqueueChangeRecord(object, "reconfigure", name, old_value); | 12504 RETURN_ON_EXCEPTION( |
| 12505 isolate, EnqueueChangeRecord(object, "reconfigure", name, old_value), |
| 12506 Object); |
12470 } else if (value_changed) { | 12507 } else if (value_changed) { |
12471 EnqueueChangeRecord(object, "update", name, old_value); | 12508 RETURN_ON_EXCEPTION( |
| 12509 isolate, EnqueueChangeRecord(object, "update", name, old_value), |
| 12510 Object); |
12472 } | 12511 } |
12473 } | 12512 } |
12474 | 12513 |
12475 return result; | 12514 return result; |
12476 } | 12515 } |
12477 | 12516 |
12478 | 12517 |
12479 MaybeHandle<Object> JSObject::SetElementWithoutInterceptor( | 12518 MaybeHandle<Object> JSObject::SetElementWithoutInterceptor( |
12480 Handle<JSObject> object, | 12519 Handle<JSObject> object, |
12481 uint32_t index, | 12520 uint32_t index, |
(...skipping 3911 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
16393 Handle<DependentCode> codes = | 16432 Handle<DependentCode> codes = |
16394 DependentCode::Insert(handle(cell->dependent_code(), info->isolate()), | 16433 DependentCode::Insert(handle(cell->dependent_code(), info->isolate()), |
16395 DependentCode::kPropertyCellChangedGroup, | 16434 DependentCode::kPropertyCellChangedGroup, |
16396 info->object_wrapper()); | 16435 info->object_wrapper()); |
16397 if (*codes != cell->dependent_code()) cell->set_dependent_code(*codes); | 16436 if (*codes != cell->dependent_code()) cell->set_dependent_code(*codes); |
16398 info->dependencies(DependentCode::kPropertyCellChangedGroup)->Add( | 16437 info->dependencies(DependentCode::kPropertyCellChangedGroup)->Add( |
16399 cell, info->zone()); | 16438 cell, info->zone()); |
16400 } | 16439 } |
16401 | 16440 |
16402 } } // namespace v8::internal | 16441 } } // namespace v8::internal |
OLD | NEW |