| OLD | NEW |
| 1 // Copyright 2014 the V8 project authors. All rights reserved. | 1 // Copyright 2014 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 "src/v8.h" | 5 #include "src/v8.h" |
| 6 | 6 |
| 7 #include "src/arguments.h" | 7 #include "src/arguments.h" |
| 8 #include "src/bootstrapper.h" | 8 #include "src/bootstrapper.h" |
| 9 #include "src/debug.h" | 9 #include "src/debug.h" |
| 10 #include "src/runtime/runtime.h" | 10 #include "src/runtime/runtime.h" |
| (...skipping 231 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 242 } | 242 } |
| 243 | 243 |
| 244 | 244 |
| 245 MaybeHandle<Object> Runtime::GetPrototype(Isolate* isolate, | 245 MaybeHandle<Object> Runtime::GetPrototype(Isolate* isolate, |
| 246 Handle<Object> obj) { | 246 Handle<Object> obj) { |
| 247 // We don't expect access checks to be needed on JSProxy objects. | 247 // We don't expect access checks to be needed on JSProxy objects. |
| 248 DCHECK(!obj->IsAccessCheckNeeded() || obj->IsJSObject()); | 248 DCHECK(!obj->IsAccessCheckNeeded() || obj->IsJSObject()); |
| 249 PrototypeIterator iter(isolate, obj, PrototypeIterator::START_AT_RECEIVER); | 249 PrototypeIterator iter(isolate, obj, PrototypeIterator::START_AT_RECEIVER); |
| 250 do { | 250 do { |
| 251 if (PrototypeIterator::GetCurrent(iter)->IsAccessCheckNeeded() && | 251 if (PrototypeIterator::GetCurrent(iter)->IsAccessCheckNeeded() && |
| 252 !isolate->MayNamedAccess( | 252 !isolate->MayAccess( |
| 253 Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)), | 253 Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)))) { |
| 254 isolate->factory()->proto_string(), v8::ACCESS_GET)) { | |
| 255 isolate->ReportFailedAccessCheck( | 254 isolate->ReportFailedAccessCheck( |
| 256 Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)), | 255 Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter))); |
| 257 v8::ACCESS_GET); | |
| 258 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object); | 256 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object); |
| 259 return isolate->factory()->undefined_value(); | 257 return isolate->factory()->undefined_value(); |
| 260 } | 258 } |
| 261 iter.AdvanceIgnoringProxies(); | 259 iter.AdvanceIgnoringProxies(); |
| 262 if (PrototypeIterator::GetCurrent(iter)->IsJSProxy()) { | 260 if (PrototypeIterator::GetCurrent(iter)->IsJSProxy()) { |
| 263 return PrototypeIterator::GetCurrent(iter); | 261 return PrototypeIterator::GetCurrent(iter); |
| 264 } | 262 } |
| 265 } while (!iter.IsAtEnd(PrototypeIterator::END_AT_NON_HIDDEN)); | 263 } while (!iter.IsAtEnd(PrototypeIterator::END_AT_NON_HIDDEN)); |
| 266 return PrototypeIterator::GetCurrent(iter); | 264 return PrototypeIterator::GetCurrent(iter); |
| 267 } | 265 } |
| (...skipping 22 matching lines...) Expand all Loading... |
| 290 isolate, result, JSObject::SetPrototype(obj, prototype, false)); | 288 isolate, result, JSObject::SetPrototype(obj, prototype, false)); |
| 291 return *result; | 289 return *result; |
| 292 } | 290 } |
| 293 | 291 |
| 294 | 292 |
| 295 RUNTIME_FUNCTION(Runtime_SetPrototype) { | 293 RUNTIME_FUNCTION(Runtime_SetPrototype) { |
| 296 HandleScope scope(isolate); | 294 HandleScope scope(isolate); |
| 297 DCHECK(args.length() == 2); | 295 DCHECK(args.length() == 2); |
| 298 CONVERT_ARG_HANDLE_CHECKED(JSObject, obj, 0); | 296 CONVERT_ARG_HANDLE_CHECKED(JSObject, obj, 0); |
| 299 CONVERT_ARG_HANDLE_CHECKED(Object, prototype, 1); | 297 CONVERT_ARG_HANDLE_CHECKED(Object, prototype, 1); |
| 300 if (obj->IsAccessCheckNeeded() && | 298 if (obj->IsAccessCheckNeeded() && !isolate->MayAccess(obj)) { |
| 301 !isolate->MayNamedAccess(obj, isolate->factory()->proto_string(), | 299 isolate->ReportFailedAccessCheck(obj); |
| 302 v8::ACCESS_SET)) { | |
| 303 isolate->ReportFailedAccessCheck(obj, v8::ACCESS_SET); | |
| 304 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); | 300 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); |
| 305 return isolate->heap()->undefined_value(); | 301 return isolate->heap()->undefined_value(); |
| 306 } | 302 } |
| 307 if (obj->map()->is_observed()) { | 303 if (obj->map()->is_observed()) { |
| 308 Handle<Object> old_value = | 304 Handle<Object> old_value = |
| 309 Object::GetPrototypeSkipHiddenPrototypes(isolate, obj); | 305 Object::GetPrototypeSkipHiddenPrototypes(isolate, obj); |
| 310 Handle<Object> result; | 306 Handle<Object> result; |
| 311 ASSIGN_RETURN_FAILURE_ON_EXCEPTION( | 307 ASSIGN_RETURN_FAILURE_ON_EXCEPTION( |
| 312 isolate, result, JSObject::SetPrototype(obj, prototype, true)); | 308 isolate, result, JSObject::SetPrototype(obj, prototype, true)); |
| 313 | 309 |
| (...skipping 596 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 910 return isolate->heap()->undefined_value(); | 906 return isolate->heap()->undefined_value(); |
| 911 } | 907 } |
| 912 CONVERT_ARG_HANDLE_CHECKED(JSObject, obj, 0); | 908 CONVERT_ARG_HANDLE_CHECKED(JSObject, obj, 0); |
| 913 CONVERT_SMI_ARG_CHECKED(filter_value, 1); | 909 CONVERT_SMI_ARG_CHECKED(filter_value, 1); |
| 914 PropertyAttributes filter = static_cast<PropertyAttributes>(filter_value); | 910 PropertyAttributes filter = static_cast<PropertyAttributes>(filter_value); |
| 915 | 911 |
| 916 // Skip the global proxy as it has no properties and always delegates to the | 912 // Skip the global proxy as it has no properties and always delegates to the |
| 917 // real global object. | 913 // real global object. |
| 918 if (obj->IsJSGlobalProxy()) { | 914 if (obj->IsJSGlobalProxy()) { |
| 919 // Only collect names if access is permitted. | 915 // Only collect names if access is permitted. |
| 920 if (obj->IsAccessCheckNeeded() && | 916 if (obj->IsAccessCheckNeeded() && !isolate->MayAccess(obj)) { |
| 921 !isolate->MayNamedAccess(obj, isolate->factory()->undefined_value(), | 917 isolate->ReportFailedAccessCheck(obj); |
| 922 v8::ACCESS_KEYS)) { | |
| 923 isolate->ReportFailedAccessCheck(obj, v8::ACCESS_KEYS); | |
| 924 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); | 918 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); |
| 925 return *isolate->factory()->NewJSArray(0); | 919 return *isolate->factory()->NewJSArray(0); |
| 926 } | 920 } |
| 927 PrototypeIterator iter(isolate, obj); | 921 PrototypeIterator iter(isolate, obj); |
| 928 obj = Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)); | 922 obj = Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)); |
| 929 } | 923 } |
| 930 | 924 |
| 931 // Find the number of objects making up this. | 925 // Find the number of objects making up this. |
| 932 int length = OwnPrototypeChainLength(*obj); | 926 int length = OwnPrototypeChainLength(*obj); |
| 933 | 927 |
| 934 // Find the number of own properties for each of the objects. | 928 // Find the number of own properties for each of the objects. |
| 935 ScopedVector<int> own_property_count(length); | 929 ScopedVector<int> own_property_count(length); |
| 936 int total_property_count = 0; | 930 int total_property_count = 0; |
| 937 { | 931 { |
| 938 PrototypeIterator iter(isolate, obj, PrototypeIterator::START_AT_RECEIVER); | 932 PrototypeIterator iter(isolate, obj, PrototypeIterator::START_AT_RECEIVER); |
| 939 for (int i = 0; i < length; i++) { | 933 for (int i = 0; i < length; i++) { |
| 940 DCHECK(!iter.IsAtEnd()); | 934 DCHECK(!iter.IsAtEnd()); |
| 941 Handle<JSObject> jsproto = | 935 Handle<JSObject> jsproto = |
| 942 Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)); | 936 Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)); |
| 943 // Only collect names if access is permitted. | 937 // Only collect names if access is permitted. |
| 944 if (jsproto->IsAccessCheckNeeded() && | 938 if (jsproto->IsAccessCheckNeeded() && !isolate->MayAccess(jsproto)) { |
| 945 !isolate->MayNamedAccess(jsproto, | 939 isolate->ReportFailedAccessCheck(jsproto); |
| 946 isolate->factory()->undefined_value(), | |
| 947 v8::ACCESS_KEYS)) { | |
| 948 isolate->ReportFailedAccessCheck(jsproto, v8::ACCESS_KEYS); | |
| 949 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); | 940 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); |
| 950 return *isolate->factory()->NewJSArray(0); | 941 return *isolate->factory()->NewJSArray(0); |
| 951 } | 942 } |
| 952 int n; | 943 int n; |
| 953 n = jsproto->NumberOfOwnProperties(filter); | 944 n = jsproto->NumberOfOwnProperties(filter); |
| 954 own_property_count[i] = n; | 945 own_property_count[i] = n; |
| 955 total_property_count += n; | 946 total_property_count += n; |
| 956 iter.Advance(); | 947 iter.Advance(); |
| 957 } | 948 } |
| 958 } | 949 } |
| (...skipping 128 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1087 | 1078 |
| 1088 | 1079 |
| 1089 RUNTIME_FUNCTION(Runtime_OwnKeys) { | 1080 RUNTIME_FUNCTION(Runtime_OwnKeys) { |
| 1090 HandleScope scope(isolate); | 1081 HandleScope scope(isolate); |
| 1091 DCHECK(args.length() == 1); | 1082 DCHECK(args.length() == 1); |
| 1092 CONVERT_ARG_CHECKED(JSObject, raw_object, 0); | 1083 CONVERT_ARG_CHECKED(JSObject, raw_object, 0); |
| 1093 Handle<JSObject> object(raw_object); | 1084 Handle<JSObject> object(raw_object); |
| 1094 | 1085 |
| 1095 if (object->IsJSGlobalProxy()) { | 1086 if (object->IsJSGlobalProxy()) { |
| 1096 // Do access checks before going to the global object. | 1087 // Do access checks before going to the global object. |
| 1097 if (object->IsAccessCheckNeeded() && | 1088 if (object->IsAccessCheckNeeded() && !isolate->MayAccess(object)) { |
| 1098 !isolate->MayNamedAccess(object, isolate->factory()->undefined_value(), | 1089 isolate->ReportFailedAccessCheck(object); |
| 1099 v8::ACCESS_KEYS)) { | |
| 1100 isolate->ReportFailedAccessCheck(object, v8::ACCESS_KEYS); | |
| 1101 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); | 1090 RETURN_FAILURE_IF_SCHEDULED_EXCEPTION(isolate); |
| 1102 return *isolate->factory()->NewJSArray(0); | 1091 return *isolate->factory()->NewJSArray(0); |
| 1103 } | 1092 } |
| 1104 | 1093 |
| 1105 PrototypeIterator iter(isolate, object); | 1094 PrototypeIterator iter(isolate, object); |
| 1106 // If proxy is detached we simply return an empty array. | 1095 // If proxy is detached we simply return an empty array. |
| 1107 if (iter.IsAtEnd()) return *isolate->factory()->NewJSArray(0); | 1096 if (iter.IsAtEnd()) return *isolate->factory()->NewJSArray(0); |
| 1108 object = Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)); | 1097 object = Handle<JSObject>::cast(PrototypeIterator::GetCurrent(iter)); |
| 1109 } | 1098 } |
| 1110 | 1099 |
| (...skipping 324 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1435 RUNTIME_FUNCTION(Runtime_DefineDataPropertyUnchecked) { | 1424 RUNTIME_FUNCTION(Runtime_DefineDataPropertyUnchecked) { |
| 1436 HandleScope scope(isolate); | 1425 HandleScope scope(isolate); |
| 1437 DCHECK(args.length() == 4); | 1426 DCHECK(args.length() == 4); |
| 1438 CONVERT_ARG_HANDLE_CHECKED(JSObject, js_object, 0); | 1427 CONVERT_ARG_HANDLE_CHECKED(JSObject, js_object, 0); |
| 1439 CONVERT_ARG_HANDLE_CHECKED(Name, name, 1); | 1428 CONVERT_ARG_HANDLE_CHECKED(Name, name, 1); |
| 1440 CONVERT_ARG_HANDLE_CHECKED(Object, obj_value, 2); | 1429 CONVERT_ARG_HANDLE_CHECKED(Object, obj_value, 2); |
| 1441 CONVERT_PROPERTY_ATTRIBUTES_CHECKED(attrs, 3); | 1430 CONVERT_PROPERTY_ATTRIBUTES_CHECKED(attrs, 3); |
| 1442 | 1431 |
| 1443 LookupIterator it(js_object, name, LookupIterator::OWN_SKIP_INTERCEPTOR); | 1432 LookupIterator it(js_object, name, LookupIterator::OWN_SKIP_INTERCEPTOR); |
| 1444 if (it.IsFound() && it.state() == LookupIterator::ACCESS_CHECK) { | 1433 if (it.IsFound() && it.state() == LookupIterator::ACCESS_CHECK) { |
| 1445 if (!isolate->MayNamedAccess(js_object, name, v8::ACCESS_SET)) { | 1434 if (!isolate->MayAccess(js_object)) { |
| 1446 return isolate->heap()->undefined_value(); | 1435 return isolate->heap()->undefined_value(); |
| 1447 } | 1436 } |
| 1448 it.Next(); | 1437 it.Next(); |
| 1449 } | 1438 } |
| 1450 | 1439 |
| 1451 // Take special care when attributes are different and there is already | 1440 // Take special care when attributes are different and there is already |
| 1452 // a property. | 1441 // a property. |
| 1453 if (it.state() == LookupIterator::ACCESSOR) { | 1442 if (it.state() == LookupIterator::ACCESSOR) { |
| 1454 // Use IgnoreAttributes version since a readonly property may be | 1443 // Use IgnoreAttributes version since a readonly property may be |
| 1455 // overridden and SetProperty does not allow this. | 1444 // overridden and SetProperty does not allow this. |
| (...skipping 126 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 1582 CONVERT_PROPERTY_ATTRIBUTES_CHECKED(attrs, 3); | 1571 CONVERT_PROPERTY_ATTRIBUTES_CHECKED(attrs, 3); |
| 1583 | 1572 |
| 1584 RETURN_FAILURE_ON_EXCEPTION( | 1573 RETURN_FAILURE_ON_EXCEPTION( |
| 1585 isolate, | 1574 isolate, |
| 1586 JSObject::DefineAccessor(object, name, isolate->factory()->null_value(), | 1575 JSObject::DefineAccessor(object, name, isolate->factory()->null_value(), |
| 1587 setter, attrs)); | 1576 setter, attrs)); |
| 1588 return isolate->heap()->undefined_value(); | 1577 return isolate->heap()->undefined_value(); |
| 1589 } | 1578 } |
| 1590 } | 1579 } |
| 1591 } // namespace v8::internal | 1580 } // namespace v8::internal |
| OLD | NEW |