Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(46)

Side by Side Diff: src/objects.cc

Issue 2087823002: Optionally invoke an interceptor on failed access checks (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: updates Created 4 years, 5 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/objects.h ('k') | src/objects-debug.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2015 the V8 project authors. All rights reserved. 1 // Copyright 2015 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/objects.h" 5 #include "src/objects.h"
6 6
7 #include <cmath> 7 #include <cmath>
8 #include <iomanip> 8 #include <iomanip>
9 #include <sstream> 9 #include <sstream>
10 10
(...skipping 1339 matching lines...) Expand 10 before | Expand all | Expand 10 after
1350 } else if (it->state() == LookupIterator::INTERCEPTOR) { 1350 } else if (it->state() == LookupIterator::INTERCEPTOR) {
1351 if (it->GetInterceptor()->all_can_read()) return true; 1351 if (it->GetInterceptor()->all_can_read()) return true;
1352 } else if (it->state() == LookupIterator::JSPROXY) { 1352 } else if (it->state() == LookupIterator::JSPROXY) {
1353 // Stop lookupiterating. And no, AllCanNotRead. 1353 // Stop lookupiterating. And no, AllCanNotRead.
1354 return false; 1354 return false;
1355 } 1355 }
1356 } 1356 }
1357 return false; 1357 return false;
1358 } 1358 }
1359 1359
1360 namespace {
1361
1362 MaybeHandle<Object> GetPropertyWithInterceptorInternal(
1363 LookupIterator* it, Handle<InterceptorInfo> interceptor, bool* done) {
1364 *done = false;
1365 Isolate* isolate = it->isolate();
1366 // Make sure that the top context does not change when doing callbacks or
1367 // interceptor calls.
1368 AssertNoContextChange ncc(isolate);
1369
1370 if (interceptor->getter()->IsUndefined(isolate)) {
1371 return isolate->factory()->undefined_value();
1372 }
1373
1374 Handle<JSObject> holder = it->GetHolder<JSObject>();
1375 Handle<Object> result;
1376 Handle<Object> receiver = it->GetReceiver();
1377 if (!receiver->IsJSReceiver()) {
1378 ASSIGN_RETURN_ON_EXCEPTION(
1379 isolate, receiver, Object::ConvertReceiver(isolate, receiver), Object);
1380 }
1381 PropertyCallbackArguments args(isolate, interceptor->data(), *receiver,
1382 *holder, Object::DONT_THROW);
1383
1384 if (it->IsElement()) {
1385 uint32_t index = it->index();
1386 v8::IndexedPropertyGetterCallback getter =
1387 v8::ToCData<v8::IndexedPropertyGetterCallback>(interceptor->getter());
1388 result = args.Call(getter, index);
1389 } else {
1390 Handle<Name> name = it->name();
1391 DCHECK(!name->IsPrivate());
1392
1393 if (name->IsSymbol() && !interceptor->can_intercept_symbols()) {
1394 return isolate->factory()->undefined_value();
1395 }
1396
1397 v8::GenericNamedPropertyGetterCallback getter =
1398 v8::ToCData<v8::GenericNamedPropertyGetterCallback>(
1399 interceptor->getter());
1400 result = args.Call(getter, name);
1401 }
1402
1403 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object);
1404 if (result.is_null()) return isolate->factory()->undefined_value();
1405 *done = true;
1406 // Rebox handle before return
1407 return handle(*result, isolate);
1408 }
1409
1410 Maybe<PropertyAttributes> GetPropertyAttributesWithInterceptorInternal(
1411 LookupIterator* it, Handle<InterceptorInfo> interceptor) {
1412 Isolate* isolate = it->isolate();
1413 // Make sure that the top context does not change when doing
1414 // callbacks or interceptor calls.
1415 AssertNoContextChange ncc(isolate);
1416 HandleScope scope(isolate);
1417
1418 Handle<JSObject> holder = it->GetHolder<JSObject>();
1419 if (!it->IsElement() && it->name()->IsSymbol() &&
1420 !interceptor->can_intercept_symbols()) {
1421 return Just(ABSENT);
1422 }
1423 Handle<Object> receiver = it->GetReceiver();
1424 if (!receiver->IsJSReceiver()) {
1425 ASSIGN_RETURN_ON_EXCEPTION_VALUE(isolate, receiver,
1426 Object::ConvertReceiver(isolate, receiver),
1427 Nothing<PropertyAttributes>());
1428 }
1429 PropertyCallbackArguments args(isolate, interceptor->data(), *receiver,
1430 *holder, Object::DONT_THROW);
1431 if (!interceptor->query()->IsUndefined(isolate)) {
1432 Handle<Object> result;
1433 if (it->IsElement()) {
1434 uint32_t index = it->index();
1435 v8::IndexedPropertyQueryCallback query =
1436 v8::ToCData<v8::IndexedPropertyQueryCallback>(interceptor->query());
1437 result = args.Call(query, index);
1438 } else {
1439 Handle<Name> name = it->name();
1440 DCHECK(!name->IsPrivate());
1441 v8::GenericNamedPropertyQueryCallback query =
1442 v8::ToCData<v8::GenericNamedPropertyQueryCallback>(
1443 interceptor->query());
1444 result = args.Call(query, name);
1445 }
1446 if (!result.is_null()) {
1447 int32_t value;
1448 CHECK(result->ToInt32(&value));
1449 return Just(static_cast<PropertyAttributes>(value));
1450 }
1451 } else if (!interceptor->getter()->IsUndefined(isolate)) {
1452 // TODO(verwaest): Use GetPropertyWithInterceptor?
1453 Handle<Object> result;
1454 if (it->IsElement()) {
1455 uint32_t index = it->index();
1456 v8::IndexedPropertyGetterCallback getter =
1457 v8::ToCData<v8::IndexedPropertyGetterCallback>(interceptor->getter());
1458 result = args.Call(getter, index);
1459 } else {
1460 Handle<Name> name = it->name();
1461 DCHECK(!name->IsPrivate());
1462 v8::GenericNamedPropertyGetterCallback getter =
1463 v8::ToCData<v8::GenericNamedPropertyGetterCallback>(
1464 interceptor->getter());
1465 result = args.Call(getter, name);
1466 }
1467 if (!result.is_null()) return Just(DONT_ENUM);
1468 }
1469
1470 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(isolate, Nothing<PropertyAttributes>());
1471 return Just(ABSENT);
1472 }
1473
1474 Maybe<bool> SetPropertyWithInterceptorInternal(
1475 LookupIterator* it, Handle<InterceptorInfo> interceptor,
1476 Object::ShouldThrow should_throw, Handle<Object> value) {
1477 Isolate* isolate = it->isolate();
1478 // Make sure that the top context does not change when doing callbacks or
1479 // interceptor calls.
1480 AssertNoContextChange ncc(isolate);
1481
1482 if (interceptor->setter()->IsUndefined(isolate)) return Just(false);
1483
1484 Handle<JSObject> holder = it->GetHolder<JSObject>();
1485 bool result;
1486 Handle<Object> receiver = it->GetReceiver();
1487 if (!receiver->IsJSReceiver()) {
1488 ASSIGN_RETURN_ON_EXCEPTION_VALUE(isolate, receiver,
1489 Object::ConvertReceiver(isolate, receiver),
1490 Nothing<bool>());
1491 }
1492 PropertyCallbackArguments args(isolate, interceptor->data(), *receiver,
1493 *holder, should_throw);
1494
1495 if (it->IsElement()) {
1496 uint32_t index = it->index();
1497 v8::IndexedPropertySetterCallback setter =
1498 v8::ToCData<v8::IndexedPropertySetterCallback>(interceptor->setter());
1499 // TODO(neis): In the future, we may want to actually return the
1500 // interceptor's result, which then should be a boolean.
1501 result = !args.Call(setter, index, value).is_null();
1502 } else {
1503 Handle<Name> name = it->name();
1504 DCHECK(!name->IsPrivate());
1505
1506 if (name->IsSymbol() && !interceptor->can_intercept_symbols()) {
1507 return Just(false);
1508 }
1509
1510 v8::GenericNamedPropertySetterCallback setter =
1511 v8::ToCData<v8::GenericNamedPropertySetterCallback>(
1512 interceptor->setter());
1513 result = !args.Call(setter, name, value).is_null();
1514 }
1515
1516 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(it->isolate(), Nothing<bool>());
1517 return Just(result);
1518 }
1519
1520 } // namespace
1360 1521
1361 MaybeHandle<Object> JSObject::GetPropertyWithFailedAccessCheck( 1522 MaybeHandle<Object> JSObject::GetPropertyWithFailedAccessCheck(
1362 LookupIterator* it) { 1523 LookupIterator* it) {
1524 Isolate* isolate = it->isolate();
1363 Handle<JSObject> checked = it->GetHolder<JSObject>(); 1525 Handle<JSObject> checked = it->GetHolder<JSObject>();
1364 while (AllCanRead(it)) { 1526 Handle<InterceptorInfo> interceptor =
1365 if (it->state() == LookupIterator::ACCESSOR) { 1527 it->GetInterceptorForFailedAccessCheck();
1366 return GetPropertyWithAccessor(it); 1528 if (interceptor.is_null()) {
1529 while (AllCanRead(it)) {
1530 if (it->state() == LookupIterator::ACCESSOR) {
1531 return GetPropertyWithAccessor(it);
1532 }
1533 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state());
1534 bool done;
1535 Handle<Object> result;
1536 ASSIGN_RETURN_ON_EXCEPTION(isolate, result,
1537 GetPropertyWithInterceptor(it, &done), Object);
1538 if (done) return result;
1367 } 1539 }
1368 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state()); 1540 } else {
1541 MaybeHandle<Object> result;
1369 bool done; 1542 bool done;
1370 Handle<Object> result; 1543 result = GetPropertyWithInterceptorInternal(it, interceptor, &done);
1371 ASSIGN_RETURN_ON_EXCEPTION(it->isolate(), result, 1544 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object);
1372 GetPropertyWithInterceptor(it, &done), Object);
1373 if (done) return result; 1545 if (done) return result;
1374 } 1546 }
1375 1547
1376 // Cross-Origin [[Get]] of Well-Known Symbols does not throw, and returns 1548 // Cross-Origin [[Get]] of Well-Known Symbols does not throw, and returns
1377 // undefined. 1549 // undefined.
1378 Handle<Name> name = it->GetName(); 1550 Handle<Name> name = it->GetName();
1379 if (name->IsSymbol() && Symbol::cast(*name)->is_well_known_symbol()) { 1551 if (name->IsSymbol() && Symbol::cast(*name)->is_well_known_symbol()) {
1380 return it->factory()->undefined_value(); 1552 return it->factory()->undefined_value();
1381 } 1553 }
1382 1554
1383 it->isolate()->ReportFailedAccessCheck(checked); 1555 isolate->ReportFailedAccessCheck(checked);
1384 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(it->isolate(), Object); 1556 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object);
1385 return it->factory()->undefined_value(); 1557 return it->factory()->undefined_value();
1386 } 1558 }
1387 1559
1388 1560
1389 Maybe<PropertyAttributes> JSObject::GetPropertyAttributesWithFailedAccessCheck( 1561 Maybe<PropertyAttributes> JSObject::GetPropertyAttributesWithFailedAccessCheck(
1390 LookupIterator* it) { 1562 LookupIterator* it) {
1563 Isolate* isolate = it->isolate();
1391 Handle<JSObject> checked = it->GetHolder<JSObject>(); 1564 Handle<JSObject> checked = it->GetHolder<JSObject>();
1392 while (AllCanRead(it)) { 1565 Handle<InterceptorInfo> interceptor =
1393 if (it->state() == LookupIterator::ACCESSOR) { 1566 it->GetInterceptorForFailedAccessCheck();
1394 return Just(it->property_attributes()); 1567 if (interceptor.is_null()) {
1568 while (AllCanRead(it)) {
1569 if (it->state() == LookupIterator::ACCESSOR) {
1570 return Just(it->property_attributes());
1571 }
1572 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state());
1573 auto result = GetPropertyAttributesWithInterceptor(it);
1574 if (isolate->has_scheduled_exception()) break;
1575 if (result.IsJust() && result.FromJust() != ABSENT) return result;
1395 } 1576 }
1396 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state()); 1577 } else {
1397 auto result = GetPropertyAttributesWithInterceptor(it); 1578 Maybe<PropertyAttributes> result =
1398 if (it->isolate()->has_scheduled_exception()) break; 1579 GetPropertyAttributesWithInterceptorInternal(it, interceptor);
1399 if (result.IsJust() && result.FromJust() != ABSENT) return result; 1580 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(isolate, Nothing<PropertyAttributes>());
1581 if (result.FromMaybe(ABSENT) != ABSENT) return result;
1400 } 1582 }
1401 it->isolate()->ReportFailedAccessCheck(checked); 1583 isolate->ReportFailedAccessCheck(checked);
1402 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(it->isolate(), 1584 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(isolate, Nothing<PropertyAttributes>());
1403 Nothing<PropertyAttributes>());
1404 return Just(ABSENT); 1585 return Just(ABSENT);
1405 } 1586 }
1406 1587
1407 1588
1408 // static 1589 // static
1409 bool JSObject::AllCanWrite(LookupIterator* it) { 1590 bool JSObject::AllCanWrite(LookupIterator* it) {
1410 for (; it->IsFound() && it->state() != LookupIterator::JSPROXY; it->Next()) { 1591 for (; it->IsFound() && it->state() != LookupIterator::JSPROXY; it->Next()) {
1411 if (it->state() == LookupIterator::ACCESSOR) { 1592 if (it->state() == LookupIterator::ACCESSOR) {
1412 Handle<Object> accessors = it->GetAccessors(); 1593 Handle<Object> accessors = it->GetAccessors();
1413 if (accessors->IsAccessorInfo()) { 1594 if (accessors->IsAccessorInfo()) {
1414 if (AccessorInfo::cast(*accessors)->all_can_write()) return true; 1595 if (AccessorInfo::cast(*accessors)->all_can_write()) return true;
1415 } 1596 }
1416 } 1597 }
1417 } 1598 }
1418 return false; 1599 return false;
1419 } 1600 }
1420 1601
1421 1602
1422 Maybe<bool> JSObject::SetPropertyWithFailedAccessCheck( 1603 Maybe<bool> JSObject::SetPropertyWithFailedAccessCheck(
1423 LookupIterator* it, Handle<Object> value, ShouldThrow should_throw) { 1604 LookupIterator* it, Handle<Object> value, ShouldThrow should_throw) {
1605 Isolate* isolate = it->isolate();
1424 Handle<JSObject> checked = it->GetHolder<JSObject>(); 1606 Handle<JSObject> checked = it->GetHolder<JSObject>();
1425 if (AllCanWrite(it)) { 1607 Handle<InterceptorInfo> interceptor =
1426 return SetPropertyWithAccessor(it, value, should_throw); 1608 it->GetInterceptorForFailedAccessCheck();
1609 if (interceptor.is_null()) {
1610 if (AllCanWrite(it)) {
1611 return SetPropertyWithAccessor(it, value, should_throw);
1612 }
1613 } else {
1614 Maybe<bool> result = SetPropertyWithInterceptorInternal(
1615 it, interceptor, should_throw, value);
1616 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(isolate, Nothing<bool>());
1617 if (result.IsJust()) return result;
1427 } 1618 }
1428 1619
1429 it->isolate()->ReportFailedAccessCheck(checked); 1620 isolate->ReportFailedAccessCheck(checked);
1430 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(it->isolate(), Nothing<bool>()); 1621 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(isolate, Nothing<bool>());
1431 return Just(true); 1622 return Just(true);
1432 } 1623 }
1433 1624
1434 1625
1435 void JSObject::SetNormalizedProperty(Handle<JSObject> object, 1626 void JSObject::SetNormalizedProperty(Handle<JSObject> object,
1436 Handle<Name> name, 1627 Handle<Name> name,
1437 Handle<Object> value, 1628 Handle<Object> value,
1438 PropertyDetails details) { 1629 PropertyDetails details) {
1439 DCHECK(!object->HasFastProperties()); 1630 DCHECK(!object->HasFastProperties());
1440 if (!name->IsUniqueName()) { 1631 if (!name->IsUniqueName()) {
(...skipping 2769 matching lines...) Expand 10 before | Expand all | Expand 10 after
4210 4401
4211 4402
4212 // static 4403 // static
4213 Handle<Map> Map::Update(Handle<Map> map) { 4404 Handle<Map> Map::Update(Handle<Map> map) {
4214 if (!map->is_deprecated()) return map; 4405 if (!map->is_deprecated()) return map;
4215 return ReconfigureProperty(map, -1, kData, NONE, Representation::None(), 4406 return ReconfigureProperty(map, -1, kData, NONE, Representation::None(),
4216 FieldType::None(map->GetIsolate()), 4407 FieldType::None(map->GetIsolate()),
4217 ALLOW_IN_DESCRIPTOR); 4408 ALLOW_IN_DESCRIPTOR);
4218 } 4409 }
4219 4410
4220
4221 Maybe<bool> JSObject::SetPropertyWithInterceptor(LookupIterator* it, 4411 Maybe<bool> JSObject::SetPropertyWithInterceptor(LookupIterator* it,
4222 ShouldThrow should_throw, 4412 ShouldThrow should_throw,
4223 Handle<Object> value) { 4413 Handle<Object> value) {
4224 Isolate* isolate = it->isolate();
4225 // Make sure that the top context does not change when doing callbacks or
4226 // interceptor calls.
4227 AssertNoContextChange ncc(isolate);
4228
4229 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state()); 4414 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state());
4230 Handle<InterceptorInfo> interceptor(it->GetInterceptor()); 4415 return SetPropertyWithInterceptorInternal(it, it->GetInterceptor(),
4231 if (interceptor->setter()->IsUndefined(isolate)) return Just(false); 4416 should_throw, value);
4232
4233 Handle<JSObject> holder = it->GetHolder<JSObject>();
4234 bool result;
4235 Handle<Object> receiver = it->GetReceiver();
4236 if (!receiver->IsJSReceiver()) {
4237 ASSIGN_RETURN_ON_EXCEPTION_VALUE(isolate, receiver,
4238 Object::ConvertReceiver(isolate, receiver),
4239 Nothing<bool>());
4240 }
4241 PropertyCallbackArguments args(isolate, interceptor->data(), *receiver,
4242 *holder, should_throw);
4243
4244 if (it->IsElement()) {
4245 uint32_t index = it->index();
4246 v8::IndexedPropertySetterCallback setter =
4247 v8::ToCData<v8::IndexedPropertySetterCallback>(interceptor->setter());
4248 // TODO(neis): In the future, we may want to actually return the
4249 // interceptor's result, which then should be a boolean.
4250 result = !args.Call(setter, index, value).is_null();
4251 } else {
4252 Handle<Name> name = it->name();
4253 DCHECK(!name->IsPrivate());
4254
4255 if (name->IsSymbol() && !interceptor->can_intercept_symbols()) {
4256 return Just(false);
4257 }
4258
4259 v8::GenericNamedPropertySetterCallback setter =
4260 v8::ToCData<v8::GenericNamedPropertySetterCallback>(
4261 interceptor->setter());
4262 result = !args.Call(setter, name, value).is_null();
4263 }
4264
4265 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(it->isolate(), Nothing<bool>());
4266 return Just(result);
4267 } 4417 }
4268 4418
4269
4270 MaybeHandle<Object> Object::SetProperty(Handle<Object> object, 4419 MaybeHandle<Object> Object::SetProperty(Handle<Object> object,
4271 Handle<Name> name, Handle<Object> value, 4420 Handle<Name> name, Handle<Object> value,
4272 LanguageMode language_mode, 4421 LanguageMode language_mode,
4273 StoreFromKeyed store_mode) { 4422 StoreFromKeyed store_mode) {
4274 LookupIterator it(object, name); 4423 LookupIterator it(object, name);
4275 MAYBE_RETURN_NULL(SetProperty(&it, value, language_mode, store_mode)); 4424 MAYBE_RETURN_NULL(SetProperty(&it, value, language_mode, store_mode));
4276 return value; 4425 return value;
4277 } 4426 }
4278 4427
4279 4428
(...skipping 1238 matching lines...) Expand 10 before | Expand all | Expand 10 after
5518 5667
5519 MaybeHandle<Object> JSObject::DefinePropertyOrElementIgnoreAttributes( 5668 MaybeHandle<Object> JSObject::DefinePropertyOrElementIgnoreAttributes(
5520 Handle<JSObject> object, Handle<Name> name, Handle<Object> value, 5669 Handle<JSObject> object, Handle<Name> name, Handle<Object> value,
5521 PropertyAttributes attributes) { 5670 PropertyAttributes attributes) {
5522 Isolate* isolate = object->GetIsolate(); 5671 Isolate* isolate = object->GetIsolate();
5523 LookupIterator it = LookupIterator::PropertyOrElement( 5672 LookupIterator it = LookupIterator::PropertyOrElement(
5524 isolate, object, name, object, LookupIterator::OWN); 5673 isolate, object, name, object, LookupIterator::OWN);
5525 return DefineOwnPropertyIgnoreAttributes(&it, value, attributes); 5674 return DefineOwnPropertyIgnoreAttributes(&it, value, attributes);
5526 } 5675 }
5527 5676
5528
5529 Maybe<PropertyAttributes> JSObject::GetPropertyAttributesWithInterceptor( 5677 Maybe<PropertyAttributes> JSObject::GetPropertyAttributesWithInterceptor(
5530 LookupIterator* it) { 5678 LookupIterator* it) {
5531 Isolate* isolate = it->isolate(); 5679 return GetPropertyAttributesWithInterceptorInternal(it, it->GetInterceptor());
5532 // Make sure that the top context does not change when doing
5533 // callbacks or interceptor calls.
5534 AssertNoContextChange ncc(isolate);
5535 HandleScope scope(isolate);
5536
5537 Handle<JSObject> holder = it->GetHolder<JSObject>();
5538 Handle<InterceptorInfo> interceptor(it->GetInterceptor());
5539 if (!it->IsElement() && it->name()->IsSymbol() &&
5540 !interceptor->can_intercept_symbols()) {
5541 return Just(ABSENT);
5542 }
5543 Handle<Object> receiver = it->GetReceiver();
5544 if (!receiver->IsJSReceiver()) {
5545 ASSIGN_RETURN_ON_EXCEPTION_VALUE(isolate, receiver,
5546 Object::ConvertReceiver(isolate, receiver),
5547 Nothing<PropertyAttributes>());
5548 }
5549 PropertyCallbackArguments args(isolate, interceptor->data(), *receiver,
5550 *holder, Object::DONT_THROW);
5551 if (!interceptor->query()->IsUndefined(isolate)) {
5552 Handle<Object> result;
5553 if (it->IsElement()) {
5554 uint32_t index = it->index();
5555 v8::IndexedPropertyQueryCallback query =
5556 v8::ToCData<v8::IndexedPropertyQueryCallback>(interceptor->query());
5557 result = args.Call(query, index);
5558 } else {
5559 Handle<Name> name = it->name();
5560 DCHECK(!name->IsPrivate());
5561 v8::GenericNamedPropertyQueryCallback query =
5562 v8::ToCData<v8::GenericNamedPropertyQueryCallback>(
5563 interceptor->query());
5564 result = args.Call(query, name);
5565 }
5566 if (!result.is_null()) {
5567 int32_t value;
5568 CHECK(result->ToInt32(&value));
5569 return Just(static_cast<PropertyAttributes>(value));
5570 }
5571 } else if (!interceptor->getter()->IsUndefined(isolate)) {
5572 // TODO(verwaest): Use GetPropertyWithInterceptor?
5573 Handle<Object> result;
5574 if (it->IsElement()) {
5575 uint32_t index = it->index();
5576 v8::IndexedPropertyGetterCallback getter =
5577 v8::ToCData<v8::IndexedPropertyGetterCallback>(interceptor->getter());
5578 result = args.Call(getter, index);
5579 } else {
5580 Handle<Name> name = it->name();
5581 DCHECK(!name->IsPrivate());
5582 v8::GenericNamedPropertyGetterCallback getter =
5583 v8::ToCData<v8::GenericNamedPropertyGetterCallback>(
5584 interceptor->getter());
5585 result = args.Call(getter, name);
5586 }
5587 if (!result.is_null()) return Just(DONT_ENUM);
5588 }
5589
5590 RETURN_VALUE_IF_SCHEDULED_EXCEPTION(isolate, Nothing<PropertyAttributes>());
5591 return Just(ABSENT);
5592 } 5680 }
5593 5681
5594
5595 Maybe<PropertyAttributes> JSReceiver::GetPropertyAttributes( 5682 Maybe<PropertyAttributes> JSReceiver::GetPropertyAttributes(
5596 LookupIterator* it) { 5683 LookupIterator* it) {
5597 for (; it->IsFound(); it->Next()) { 5684 for (; it->IsFound(); it->Next()) {
5598 switch (it->state()) { 5685 switch (it->state()) {
5599 case LookupIterator::NOT_FOUND: 5686 case LookupIterator::NOT_FOUND:
5600 case LookupIterator::TRANSITION: 5687 case LookupIterator::TRANSITION:
5601 UNREACHABLE(); 5688 UNREACHABLE();
5602 case LookupIterator::JSPROXY: 5689 case LookupIterator::JSPROXY:
5603 return JSProxy::GetPropertyAttributes(it); 5690 return JSProxy::GetPropertyAttributes(it);
5604 case LookupIterator::INTERCEPTOR: { 5691 case LookupIterator::INTERCEPTOR: {
(...skipping 9846 matching lines...) Expand 10 before | Expand all | Expand 10 after
15451 if (this->IsKey(isolate, k)) { 15538 if (this->IsKey(isolate, k)) {
15452 elements->set(pos++, this->ValueAt(i), mode); 15539 elements->set(pos++, this->ValueAt(i), mode);
15453 } 15540 }
15454 } 15541 }
15455 DCHECK(pos == elements->length()); 15542 DCHECK(pos == elements->length());
15456 } 15543 }
15457 15544
15458 15545
15459 MaybeHandle<Object> JSObject::GetPropertyWithInterceptor(LookupIterator* it, 15546 MaybeHandle<Object> JSObject::GetPropertyWithInterceptor(LookupIterator* it,
15460 bool* done) { 15547 bool* done) {
15461 *done = false;
15462 Isolate* isolate = it->isolate();
15463 // Make sure that the top context does not change when doing callbacks or
15464 // interceptor calls.
15465 AssertNoContextChange ncc(isolate);
15466
15467 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state()); 15548 DCHECK_EQ(LookupIterator::INTERCEPTOR, it->state());
15468 Handle<InterceptorInfo> interceptor = it->GetInterceptor(); 15549 return GetPropertyWithInterceptorInternal(it, it->GetInterceptor(), done);
15469 if (interceptor->getter()->IsUndefined(isolate)) {
15470 return isolate->factory()->undefined_value();
15471 }
15472
15473 Handle<JSObject> holder = it->GetHolder<JSObject>();
15474 Handle<Object> result;
15475 Handle<Object> receiver = it->GetReceiver();
15476 if (!receiver->IsJSReceiver()) {
15477 ASSIGN_RETURN_ON_EXCEPTION(
15478 isolate, receiver, Object::ConvertReceiver(isolate, receiver), Object);
15479 }
15480 PropertyCallbackArguments args(isolate, interceptor->data(), *receiver,
15481 *holder, Object::DONT_THROW);
15482
15483 if (it->IsElement()) {
15484 uint32_t index = it->index();
15485 v8::IndexedPropertyGetterCallback getter =
15486 v8::ToCData<v8::IndexedPropertyGetterCallback>(interceptor->getter());
15487 result = args.Call(getter, index);
15488 } else {
15489 Handle<Name> name = it->name();
15490 DCHECK(!name->IsPrivate());
15491
15492 if (name->IsSymbol() && !interceptor->can_intercept_symbols()) {
15493 return isolate->factory()->undefined_value();
15494 }
15495
15496 v8::GenericNamedPropertyGetterCallback getter =
15497 v8::ToCData<v8::GenericNamedPropertyGetterCallback>(
15498 interceptor->getter());
15499 result = args.Call(getter, name);
15500 }
15501
15502 RETURN_EXCEPTION_IF_SCHEDULED_EXCEPTION(isolate, Object);
15503 if (result.is_null()) return isolate->factory()->undefined_value();
15504 *done = true;
15505 // Rebox handle before return
15506 return handle(*result, isolate);
15507 } 15550 }
15508 15551
15509
15510 Maybe<bool> JSObject::HasRealNamedProperty(Handle<JSObject> object, 15552 Maybe<bool> JSObject::HasRealNamedProperty(Handle<JSObject> object,
15511 Handle<Name> name) { 15553 Handle<Name> name) {
15512 LookupIterator it = LookupIterator::PropertyOrElement( 15554 LookupIterator it = LookupIterator::PropertyOrElement(
15513 name->GetIsolate(), object, name, LookupIterator::OWN_SKIP_INTERCEPTOR); 15555 name->GetIsolate(), object, name, LookupIterator::OWN_SKIP_INTERCEPTOR);
15514 return HasProperty(&it); 15556 return HasProperty(&it);
15515 } 15557 }
15516 15558
15517 15559
15518 Maybe<bool> JSObject::HasRealElementProperty(Handle<JSObject> object, 15560 Maybe<bool> JSObject::HasRealElementProperty(Handle<JSObject> object,
15519 uint32_t index) { 15561 uint32_t index) {
(...skipping 3336 matching lines...) Expand 10 before | Expand all | Expand 10 after
18856 void PropertyCell::SetValueWithInvalidation(Handle<PropertyCell> cell, 18898 void PropertyCell::SetValueWithInvalidation(Handle<PropertyCell> cell,
18857 Handle<Object> new_value) { 18899 Handle<Object> new_value) {
18858 if (cell->value() != *new_value) { 18900 if (cell->value() != *new_value) {
18859 cell->set_value(*new_value); 18901 cell->set_value(*new_value);
18860 Isolate* isolate = cell->GetIsolate(); 18902 Isolate* isolate = cell->GetIsolate();
18861 cell->dependent_code()->DeoptimizeDependentCodeGroup( 18903 cell->dependent_code()->DeoptimizeDependentCodeGroup(
18862 isolate, DependentCode::kPropertyCellChangedGroup); 18904 isolate, DependentCode::kPropertyCellChangedGroup);
18863 } 18905 }
18864 } 18906 }
18865 18907
18908 // static
18909 AccessCheckInfo* AccessCheckInfo::Get(Isolate* isolate,
18910 Handle<JSObject> receiver) {
18911 DisallowHeapAllocation no_gc;
18912 DCHECK(receiver->map()->is_access_check_needed());
18913 Object* maybe_constructor = receiver->map()->GetConstructor();
18914 // Might happen for a detached context.
18915 if (!maybe_constructor->IsJSFunction()) return nullptr;
18916 JSFunction* constructor = JSFunction::cast(maybe_constructor);
18917 // Might happen for the debug context.
18918 if (!constructor->shared()->IsApiFunction()) return nullptr;
18919
18920 Object* data_obj =
18921 constructor->shared()->get_api_func_data()->access_check_info();
18922 if (data_obj->IsUndefined(isolate)) return nullptr;
18923
18924 return AccessCheckInfo::cast(data_obj);
18925 }
18926
18866 } // namespace internal 18927 } // namespace internal
18867 } // namespace v8 18928 } // namespace v8
OLDNEW
« no previous file with comments | « src/objects.h ('k') | src/objects-debug.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698