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 <stdlib.h> | 5 #include <stdlib.h> |
6 #include <utility> | 6 #include <utility> |
7 | 7 |
8 #include "src/v8.h" | 8 #include "src/v8.h" |
9 | 9 |
10 #include "src/compilation-cache.h" | 10 #include "src/compilation-cache.h" |
(...skipping 1345 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1356 NONE, Representation::Tagged(), | 1356 NONE, Representation::Tagged(), |
1357 INSERT_TRANSITION).ToHandleChecked(); | 1357 INSERT_TRANSITION).ToHandleChecked(); |
1358 | 1358 |
1359 // Layout descriptors should not be shared with |split_map|. | 1359 // Layout descriptors should not be shared with |split_map|. |
1360 CHECK(map2->owns_descriptors()); | 1360 CHECK(map2->owns_descriptors()); |
1361 CHECK_NE(*split_layout_descriptor, map2->layout_descriptor()); | 1361 CHECK_NE(*split_layout_descriptor, map2->layout_descriptor()); |
1362 CHECK(map2->layout_descriptor()->IsConsistentWithMap(*map2, true)); | 1362 CHECK(map2->layout_descriptor()->IsConsistentWithMap(*map2, true)); |
1363 } | 1363 } |
1364 | 1364 |
1365 | 1365 |
1366 TEST(StoreBufferScanOnScavenge) { | |
1367 CcTest::InitializeVM(); | |
1368 Isolate* isolate = CcTest::i_isolate(); | |
1369 Factory* factory = isolate->factory(); | |
1370 v8::HandleScope scope(CcTest::isolate()); | |
1371 | |
1372 Handle<FieldType> any_type = FieldType::Any(isolate); | |
1373 Handle<Map> map = Map::Create(isolate, 10); | |
1374 map = Map::CopyWithField(map, MakeName("prop", 0), any_type, NONE, | |
1375 Representation::Double(), | |
1376 INSERT_TRANSITION).ToHandleChecked(); | |
1377 | |
1378 // Create object in new space. | |
1379 Handle<JSObject> obj = factory->NewJSObjectFromMap(map, NOT_TENURED); | |
1380 | |
1381 Handle<HeapNumber> heap_number = factory->NewHeapNumber(42.5); | |
1382 obj->WriteToField(0, *heap_number); | |
1383 | |
1384 { | |
1385 // Ensure the object is properly set up. | |
1386 DescriptorArray* descriptors = map->instance_descriptors(); | |
1387 CHECK(descriptors->GetDetails(0).representation().IsDouble()); | |
1388 FieldIndex field_index = FieldIndex::ForDescriptor(*map, 0); | |
1389 CHECK(field_index.is_inobject() && field_index.is_double()); | |
1390 CHECK_EQ(FLAG_unbox_double_fields, map->IsUnboxedDoubleField(field_index)); | |
1391 CHECK_EQ(42.5, GetDoubleFieldValue(*obj, field_index)); | |
1392 } | |
1393 CHECK(isolate->heap()->new_space()->Contains(*obj)); | |
1394 | |
1395 // Trigger GCs so that the newly allocated object moves to old gen. | |
1396 CcTest::heap()->CollectGarbage(i::NEW_SPACE); // in survivor space now | |
1397 CcTest::heap()->CollectGarbage(i::NEW_SPACE); // in old gen now | |
1398 | |
1399 CHECK(isolate->heap()->old_space()->Contains(*obj)); | |
1400 | |
1401 // Create temp object in the new space. | |
1402 Handle<JSArray> temp = factory->NewJSArray(0, FAST_ELEMENTS); | |
1403 CHECK(isolate->heap()->new_space()->Contains(*temp)); | |
1404 | |
1405 // Construct a double value that looks like a pointer to the new space object | |
1406 // and store it into the obj. | |
1407 Address fake_object = reinterpret_cast<Address>(*temp) + kPointerSize; | |
1408 double boom_value = bit_cast<double>(fake_object); | |
1409 | |
1410 FieldIndex field_index = FieldIndex::ForDescriptor(obj->map(), 0); | |
1411 Handle<HeapNumber> boom_number = factory->NewHeapNumber(boom_value, MUTABLE); | |
1412 obj->FastPropertyAtPut(field_index, *boom_number); | |
1413 | |
1414 // Enforce scan on scavenge for the obj's page. | |
1415 MemoryChunk* chunk = MemoryChunk::FromAddress(obj->address()); | |
1416 chunk->set_scan_on_scavenge(true); | |
1417 | |
1418 // Trigger GCs and force evacuation. Should not crash there. | |
1419 CcTest::heap()->CollectAllGarbage(); | |
1420 | |
1421 CHECK_EQ(boom_value, GetDoubleFieldValue(*obj, field_index)); | |
1422 } | |
1423 | |
1424 | |
1425 static void TestWriteBarrier(Handle<Map> map, Handle<Map> new_map, | 1366 static void TestWriteBarrier(Handle<Map> map, Handle<Map> new_map, |
1426 int tagged_descriptor, int double_descriptor, | 1367 int tagged_descriptor, int double_descriptor, |
1427 bool check_tagged_value = true) { | 1368 bool check_tagged_value = true) { |
1428 FLAG_stress_compaction = true; | 1369 FLAG_stress_compaction = true; |
1429 FLAG_manual_evacuation_candidates_selection = true; | 1370 FLAG_manual_evacuation_candidates_selection = true; |
1430 Isolate* isolate = CcTest::i_isolate(); | 1371 Isolate* isolate = CcTest::i_isolate(); |
1431 Factory* factory = isolate->factory(); | 1372 Factory* factory = isolate->factory(); |
1432 Heap* heap = CcTest::heap(); | 1373 Heap* heap = CcTest::heap(); |
1433 PagedSpace* old_space = heap->old_space(); | 1374 PagedSpace* old_space = heap->old_space(); |
1434 | 1375 |
(...skipping 187 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1622 | 1563 |
1623 // TODO(ishell): add respective tests for property kind reconfiguring from | 1564 // TODO(ishell): add respective tests for property kind reconfiguring from |
1624 // accessor field to double, once accessor fields are supported by | 1565 // accessor field to double, once accessor fields are supported by |
1625 // Map::ReconfigureProperty(). | 1566 // Map::ReconfigureProperty(). |
1626 | 1567 |
1627 | 1568 |
1628 // TODO(ishell): add respective tests for fast property removal case once | 1569 // TODO(ishell): add respective tests for fast property removal case once |
1629 // Map::ReconfigureProperty() supports that. | 1570 // Map::ReconfigureProperty() supports that. |
1630 | 1571 |
1631 #endif | 1572 #endif |
OLD | NEW |