OLD | NEW |
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. | 1 // Copyright 2006-2008 the V8 project authors. All rights reserved. |
2 // Redistribution and use in source and binary forms, with or without | 2 // Redistribution and use in source and binary forms, with or without |
3 // modification, are permitted provided that the following conditions are | 3 // modification, are permitted provided that the following conditions are |
4 // met: | 4 // met: |
5 // | 5 // |
6 // * Redistributions of source code must retain the above copyright | 6 // * Redistributions of source code must retain the above copyright |
7 // notice, this list of conditions and the following disclaimer. | 7 // notice, this list of conditions and the following disclaimer. |
8 // * Redistributions in binary form must reproduce the above | 8 // * Redistributions in binary form must reproduce the above |
9 // copyright notice, this list of conditions and the following | 9 // copyright notice, this list of conditions and the following |
10 // disclaimer in the documentation and/or other materials provided | 10 // disclaimer in the documentation and/or other materials provided |
(...skipping 353 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
364 : id_(id), executable_(executable) {} | 364 : id_(id), executable_(executable) {} |
365 | 365 |
366 virtual ~Space() {} | 366 virtual ~Space() {} |
367 | 367 |
368 // Does the space need executable memory? | 368 // Does the space need executable memory? |
369 Executability executable() { return executable_; } | 369 Executability executable() { return executable_; } |
370 | 370 |
371 // Identity used in error reporting. | 371 // Identity used in error reporting. |
372 AllocationSpace identity() { return id_; } | 372 AllocationSpace identity() { return id_; } |
373 | 373 |
374 virtual intptr_t Size() = 0; | 374 virtual int Size() = 0; |
375 | 375 |
376 #ifdef ENABLE_HEAP_PROTECTION | 376 #ifdef ENABLE_HEAP_PROTECTION |
377 // Protect/unprotect the space by marking it read-only/writable. | 377 // Protect/unprotect the space by marking it read-only/writable. |
378 virtual void Protect() = 0; | 378 virtual void Protect() = 0; |
379 virtual void Unprotect() = 0; | 379 virtual void Unprotect() = 0; |
380 #endif | 380 #endif |
381 | 381 |
382 #ifdef DEBUG | 382 #ifdef DEBUG |
383 virtual void Print() = 0; | 383 virtual void Print() = 0; |
384 #endif | 384 #endif |
(...skipping 99 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
484 // induces a constraint on the order of pages in a linked lists. We say that | 484 // induces a constraint on the order of pages in a linked lists. We say that |
485 // pages are linked in the chunk-order if and only if every two consecutive | 485 // pages are linked in the chunk-order if and only if every two consecutive |
486 // pages from the same chunk are consecutive in the linked list. | 486 // pages from the same chunk are consecutive in the linked list. |
487 // | 487 // |
488 | 488 |
489 | 489 |
490 class MemoryAllocator : public AllStatic { | 490 class MemoryAllocator : public AllStatic { |
491 public: | 491 public: |
492 // Initializes its internal bookkeeping structures. | 492 // Initializes its internal bookkeeping structures. |
493 // Max capacity of the total space. | 493 // Max capacity of the total space. |
494 static bool Setup(intptr_t max_capacity); | 494 static bool Setup(int max_capacity); |
495 | 495 |
496 // Deletes valid chunks. | 496 // Deletes valid chunks. |
497 static void TearDown(); | 497 static void TearDown(); |
498 | 498 |
499 // Reserves an initial address range of virtual memory to be split between | 499 // Reserves an initial address range of virtual memory to be split between |
500 // the two new space semispaces, the old space, and the map space. The | 500 // the two new space semispaces, the old space, and the map space. The |
501 // memory is not yet committed or assigned to spaces and split into pages. | 501 // memory is not yet committed or assigned to spaces and split into pages. |
502 // The initial chunk is unmapped when the memory allocator is torn down. | 502 // The initial chunk is unmapped when the memory allocator is torn down. |
503 // This function should only be called when there is not already a reserved | 503 // This function should only be called when there is not already a reserved |
504 // initial chunk (initial_chunk_ should be NULL). It returns the start | 504 // initial chunk (initial_chunk_ should be NULL). It returns the start |
(...skipping 70 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
575 | 575 |
576 static void AddMemoryAllocationCallback(MemoryAllocationCallback callback, | 576 static void AddMemoryAllocationCallback(MemoryAllocationCallback callback, |
577 ObjectSpace space, | 577 ObjectSpace space, |
578 AllocationAction action); | 578 AllocationAction action); |
579 static void RemoveMemoryAllocationCallback( | 579 static void RemoveMemoryAllocationCallback( |
580 MemoryAllocationCallback callback); | 580 MemoryAllocationCallback callback); |
581 static bool MemoryAllocationCallbackRegistered( | 581 static bool MemoryAllocationCallbackRegistered( |
582 MemoryAllocationCallback callback); | 582 MemoryAllocationCallback callback); |
583 | 583 |
584 // Returns the maximum available bytes of heaps. | 584 // Returns the maximum available bytes of heaps. |
585 static intptr_t Available() { | 585 static int Available() { return capacity_ < size_ ? 0 : capacity_ - size_; } |
586 return capacity_ < size_ ? 0 : capacity_ - size_; | |
587 } | |
588 | 586 |
589 // Returns allocated spaces in bytes. | 587 // Returns allocated spaces in bytes. |
590 static intptr_t Size() { return size_; } | 588 static int Size() { return size_; } |
591 | 589 |
592 // Returns allocated executable spaces in bytes. | 590 // Returns allocated executable spaces in bytes. |
593 static intptr_t SizeExecutable() { return size_executable_; } | 591 static int SizeExecutable() { return size_executable_; } |
594 | 592 |
595 // Returns maximum available bytes that the old space can have. | 593 // Returns maximum available bytes that the old space can have. |
596 static intptr_t MaxAvailable() { | 594 static int MaxAvailable() { |
597 return (Available() / Page::kPageSize) * Page::kObjectAreaSize; | 595 return (Available() / Page::kPageSize) * Page::kObjectAreaSize; |
598 } | 596 } |
599 | 597 |
600 // Links two pages. | 598 // Links two pages. |
601 static inline void SetNextPage(Page* prev, Page* next); | 599 static inline void SetNextPage(Page* prev, Page* next); |
602 | 600 |
603 // Returns the next page of a given page. | 601 // Returns the next page of a given page. |
604 static inline Page* GetNextPage(Page* p); | 602 static inline Page* GetNextPage(Page* p); |
605 | 603 |
606 // Checks whether a page belongs to a space. | 604 // Checks whether a page belongs to a space. |
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
644 // 8K * 8K * 16 = 1G bytes. | 642 // 8K * 8K * 16 = 1G bytes. |
645 #ifdef V8_TARGET_ARCH_X64 | 643 #ifdef V8_TARGET_ARCH_X64 |
646 static const int kPagesPerChunk = 32; | 644 static const int kPagesPerChunk = 32; |
647 #else | 645 #else |
648 static const int kPagesPerChunk = 16; | 646 static const int kPagesPerChunk = 16; |
649 #endif | 647 #endif |
650 static const int kChunkSize = kPagesPerChunk * Page::kPageSize; | 648 static const int kChunkSize = kPagesPerChunk * Page::kPageSize; |
651 | 649 |
652 private: | 650 private: |
653 // Maximum space size in bytes. | 651 // Maximum space size in bytes. |
654 static intptr_t capacity_; | 652 static int capacity_; |
655 | 653 |
656 // Allocated space size in bytes. | 654 // Allocated space size in bytes. |
657 static intptr_t size_; | 655 static int size_; |
658 // Allocated executable space size in bytes. | 656 // Allocated executable space size in bytes. |
659 static intptr_t size_executable_; | 657 static int size_executable_; |
660 | 658 |
661 struct MemoryAllocationCallbackRegistration { | 659 struct MemoryAllocationCallbackRegistration { |
662 MemoryAllocationCallbackRegistration(MemoryAllocationCallback callback, | 660 MemoryAllocationCallbackRegistration(MemoryAllocationCallback callback, |
663 ObjectSpace space, | 661 ObjectSpace space, |
664 AllocationAction action) | 662 AllocationAction action) |
665 : callback(callback), space(space), action(action) { | 663 : callback(callback), space(space), action(action) { |
666 } | 664 } |
667 MemoryAllocationCallback callback; | 665 MemoryAllocationCallback callback; |
668 ObjectSpace space; | 666 ObjectSpace space; |
669 AllocationAction action; | 667 AllocationAction action; |
(...skipping 252 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
922 | 920 |
923 // Reset the allocation statistics (ie, available = capacity with no | 921 // Reset the allocation statistics (ie, available = capacity with no |
924 // wasted or allocated bytes). | 922 // wasted or allocated bytes). |
925 void Reset() { | 923 void Reset() { |
926 available_ = capacity_; | 924 available_ = capacity_; |
927 size_ = 0; | 925 size_ = 0; |
928 waste_ = 0; | 926 waste_ = 0; |
929 } | 927 } |
930 | 928 |
931 // Accessors for the allocation statistics. | 929 // Accessors for the allocation statistics. |
932 intptr_t Capacity() { return capacity_; } | 930 int Capacity() { return capacity_; } |
933 intptr_t Available() { return available_; } | 931 int Available() { return available_; } |
934 intptr_t Size() { return size_; } | 932 int Size() { return size_; } |
935 intptr_t Waste() { return waste_; } | 933 int Waste() { return waste_; } |
936 | 934 |
937 // Grow the space by adding available bytes. | 935 // Grow the space by adding available bytes. |
938 void ExpandSpace(int size_in_bytes) { | 936 void ExpandSpace(int size_in_bytes) { |
939 capacity_ += size_in_bytes; | 937 capacity_ += size_in_bytes; |
940 available_ += size_in_bytes; | 938 available_ += size_in_bytes; |
941 } | 939 } |
942 | 940 |
943 // Shrink the space by removing available bytes. | 941 // Shrink the space by removing available bytes. |
944 void ShrinkSpace(int size_in_bytes) { | 942 void ShrinkSpace(int size_in_bytes) { |
945 capacity_ -= size_in_bytes; | 943 capacity_ -= size_in_bytes; |
946 available_ -= size_in_bytes; | 944 available_ -= size_in_bytes; |
947 } | 945 } |
948 | 946 |
949 // Allocate from available bytes (available -> size). | 947 // Allocate from available bytes (available -> size). |
950 void AllocateBytes(int size_in_bytes) { | 948 void AllocateBytes(int size_in_bytes) { |
951 available_ -= size_in_bytes; | 949 available_ -= size_in_bytes; |
952 size_ += size_in_bytes; | 950 size_ += size_in_bytes; |
953 } | 951 } |
954 | 952 |
955 // Free allocated bytes, making them available (size -> available). | 953 // Free allocated bytes, making them available (size -> available). |
956 void DeallocateBytes(intptr_t size_in_bytes) { | 954 void DeallocateBytes(int size_in_bytes) { |
957 size_ -= size_in_bytes; | 955 size_ -= size_in_bytes; |
958 available_ += size_in_bytes; | 956 available_ += size_in_bytes; |
959 } | 957 } |
960 | 958 |
961 // Waste free bytes (available -> waste). | 959 // Waste free bytes (available -> waste). |
962 void WasteBytes(int size_in_bytes) { | 960 void WasteBytes(int size_in_bytes) { |
963 available_ -= size_in_bytes; | 961 available_ -= size_in_bytes; |
964 waste_ += size_in_bytes; | 962 waste_ += size_in_bytes; |
965 } | 963 } |
966 | 964 |
967 // Consider the wasted bytes to be allocated, as they contain filler | 965 // Consider the wasted bytes to be allocated, as they contain filler |
968 // objects (waste -> size). | 966 // objects (waste -> size). |
969 void FillWastedBytes(int size_in_bytes) { | 967 void FillWastedBytes(int size_in_bytes) { |
970 waste_ -= size_in_bytes; | 968 waste_ -= size_in_bytes; |
971 size_ += size_in_bytes; | 969 size_ += size_in_bytes; |
972 } | 970 } |
973 | 971 |
974 private: | 972 private: |
975 intptr_t capacity_; | 973 int capacity_; |
976 intptr_t available_; | 974 int available_; |
977 intptr_t size_; | 975 int size_; |
978 intptr_t waste_; | 976 int waste_; |
979 }; | 977 }; |
980 | 978 |
981 | 979 |
982 class PagedSpace : public Space { | 980 class PagedSpace : public Space { |
983 public: | 981 public: |
984 // Creates a space with a maximum capacity, and an id. | 982 // Creates a space with a maximum capacity, and an id. |
985 PagedSpace(intptr_t max_capacity, | 983 PagedSpace(int max_capacity, AllocationSpace id, Executability executable); |
986 AllocationSpace id, | |
987 Executability executable); | |
988 | 984 |
989 virtual ~PagedSpace() {} | 985 virtual ~PagedSpace() {} |
990 | 986 |
991 // Set up the space using the given address range of virtual memory (from | 987 // Set up the space using the given address range of virtual memory (from |
992 // the memory allocator's initial chunk) if possible. If the block of | 988 // the memory allocator's initial chunk) if possible. If the block of |
993 // addresses is not big enough to contain a single page-aligned page, a | 989 // addresses is not big enough to contain a single page-aligned page, a |
994 // fresh chunk will be allocated. | 990 // fresh chunk will be allocated. |
995 bool Setup(Address start, size_t size); | 991 bool Setup(Address start, size_t size); |
996 | 992 |
997 // Returns true if the space has been successfully set up and not | 993 // Returns true if the space has been successfully set up and not |
(...skipping 30 matching lines...) Expand all Loading... |
1028 | 1024 |
1029 // The limit of allocation for a page in this space. | 1025 // The limit of allocation for a page in this space. |
1030 virtual Address PageAllocationLimit(Page* page) = 0; | 1026 virtual Address PageAllocationLimit(Page* page) = 0; |
1031 | 1027 |
1032 void FlushTopPageWatermark() { | 1028 void FlushTopPageWatermark() { |
1033 AllocationTopPage()->SetCachedAllocationWatermark(top()); | 1029 AllocationTopPage()->SetCachedAllocationWatermark(top()); |
1034 AllocationTopPage()->InvalidateWatermark(true); | 1030 AllocationTopPage()->InvalidateWatermark(true); |
1035 } | 1031 } |
1036 | 1032 |
1037 // Current capacity without growing (Size() + Available() + Waste()). | 1033 // Current capacity without growing (Size() + Available() + Waste()). |
1038 intptr_t Capacity() { return accounting_stats_.Capacity(); } | 1034 int Capacity() { return accounting_stats_.Capacity(); } |
1039 | 1035 |
1040 // Total amount of memory committed for this space. For paged | 1036 // Total amount of memory committed for this space. For paged |
1041 // spaces this equals the capacity. | 1037 // spaces this equals the capacity. |
1042 intptr_t CommittedMemory() { return Capacity(); } | 1038 int CommittedMemory() { return Capacity(); } |
1043 | 1039 |
1044 // Available bytes without growing. | 1040 // Available bytes without growing. |
1045 intptr_t Available() { return accounting_stats_.Available(); } | 1041 int Available() { return accounting_stats_.Available(); } |
1046 | 1042 |
1047 // Allocated bytes in this space. | 1043 // Allocated bytes in this space. |
1048 virtual intptr_t Size() { return accounting_stats_.Size(); } | 1044 virtual int Size() { return accounting_stats_.Size(); } |
1049 | 1045 |
1050 // Wasted bytes due to fragmentation and not recoverable until the | 1046 // Wasted bytes due to fragmentation and not recoverable until the |
1051 // next GC of this space. | 1047 // next GC of this space. |
1052 intptr_t Waste() { return accounting_stats_.Waste(); } | 1048 int Waste() { return accounting_stats_.Waste(); } |
1053 | 1049 |
1054 // Returns the address of the first object in this space. | 1050 // Returns the address of the first object in this space. |
1055 Address bottom() { return first_page_->ObjectAreaStart(); } | 1051 Address bottom() { return first_page_->ObjectAreaStart(); } |
1056 | 1052 |
1057 // Returns the allocation pointer in this space. | 1053 // Returns the allocation pointer in this space. |
1058 Address top() { return allocation_info_.top; } | 1054 Address top() { return allocation_info_.top; } |
1059 | 1055 |
1060 // Allocate the requested number of bytes in the space if possible, return a | 1056 // Allocate the requested number of bytes in the space if possible, return a |
1061 // failure object if not. | 1057 // failure object if not. |
1062 inline Object* AllocateRaw(int size_in_bytes); | 1058 inline Object* AllocateRaw(int size_in_bytes); |
(...skipping 262 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1325 return (reinterpret_cast<uintptr_t>(o) & object_mask_) == object_expected_; | 1321 return (reinterpret_cast<uintptr_t>(o) & object_mask_) == object_expected_; |
1326 } | 1322 } |
1327 | 1323 |
1328 // The offset of an address from the beginning of the space. | 1324 // The offset of an address from the beginning of the space. |
1329 int SpaceOffsetForAddress(Address addr) { | 1325 int SpaceOffsetForAddress(Address addr) { |
1330 return static_cast<int>(addr - low()); | 1326 return static_cast<int>(addr - low()); |
1331 } | 1327 } |
1332 | 1328 |
1333 // If we don't have these here then SemiSpace will be abstract. However | 1329 // If we don't have these here then SemiSpace will be abstract. However |
1334 // they should never be called. | 1330 // they should never be called. |
1335 virtual intptr_t Size() { | 1331 virtual int Size() { |
1336 UNREACHABLE(); | 1332 UNREACHABLE(); |
1337 return 0; | 1333 return 0; |
1338 } | 1334 } |
1339 | 1335 |
1340 virtual bool ReserveSpace(int bytes) { | 1336 virtual bool ReserveSpace(int bytes) { |
1341 UNREACHABLE(); | 1337 UNREACHABLE(); |
1342 return false; | 1338 return false; |
1343 } | 1339 } |
1344 | 1340 |
1345 bool is_committed() { return committed_; } | 1341 bool is_committed() { return committed_; } |
1346 bool Commit(); | 1342 bool Commit(); |
1347 bool Uncommit(); | 1343 bool Uncommit(); |
1348 | 1344 |
1349 #ifdef ENABLE_HEAP_PROTECTION | 1345 #ifdef ENABLE_HEAP_PROTECTION |
1350 // Protect/unprotect the space by marking it read-only/writable. | 1346 // Protect/unprotect the space by marking it read-only/writable. |
1351 virtual void Protect() {} | 1347 virtual void Protect() {} |
1352 virtual void Unprotect() {} | 1348 virtual void Unprotect() {} |
1353 #endif | 1349 #endif |
1354 | 1350 |
1355 #ifdef DEBUG | 1351 #ifdef DEBUG |
1356 virtual void Print(); | 1352 virtual void Print(); |
1357 virtual void Verify(); | 1353 virtual void Verify(); |
1358 #endif | 1354 #endif |
1359 | 1355 |
1360 // Returns the current capacity of the semi space. | 1356 // Returns the current capacity of the semi space. |
1361 intptr_t Capacity() { return capacity_; } | 1357 int Capacity() { return capacity_; } |
1362 | 1358 |
1363 // Returns the maximum capacity of the semi space. | 1359 // Returns the maximum capacity of the semi space. |
1364 int MaximumCapacity() { return maximum_capacity_; } | 1360 int MaximumCapacity() { return maximum_capacity_; } |
1365 | 1361 |
1366 // Returns the initial capacity of the semi space. | 1362 // Returns the initial capacity of the semi space. |
1367 int InitialCapacity() { return initial_capacity_; } | 1363 int InitialCapacity() { return initial_capacity_; } |
1368 | 1364 |
1369 private: | 1365 private: |
1370 // The current and maximum capacity of the space. | 1366 // The current and maximum capacity of the space. |
1371 int capacity_; | 1367 int capacity_; |
(...skipping 96 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1468 // semispace (not necessarily below the allocation pointer). | 1464 // semispace (not necessarily below the allocation pointer). |
1469 bool Contains(Address a) { | 1465 bool Contains(Address a) { |
1470 return (reinterpret_cast<uintptr_t>(a) & address_mask_) | 1466 return (reinterpret_cast<uintptr_t>(a) & address_mask_) |
1471 == reinterpret_cast<uintptr_t>(start_); | 1467 == reinterpret_cast<uintptr_t>(start_); |
1472 } | 1468 } |
1473 bool Contains(Object* o) { | 1469 bool Contains(Object* o) { |
1474 return (reinterpret_cast<uintptr_t>(o) & object_mask_) == object_expected_; | 1470 return (reinterpret_cast<uintptr_t>(o) & object_mask_) == object_expected_; |
1475 } | 1471 } |
1476 | 1472 |
1477 // Return the allocated bytes in the active semispace. | 1473 // Return the allocated bytes in the active semispace. |
1478 virtual intptr_t Size() { return static_cast<int>(top() - bottom()); } | 1474 virtual int Size() { return static_cast<int>(top() - bottom()); } |
1479 | 1475 |
1480 // Return the current capacity of a semispace. | 1476 // Return the current capacity of a semispace. |
1481 intptr_t Capacity() { | 1477 int Capacity() { |
1482 ASSERT(to_space_.Capacity() == from_space_.Capacity()); | 1478 ASSERT(to_space_.Capacity() == from_space_.Capacity()); |
1483 return to_space_.Capacity(); | 1479 return to_space_.Capacity(); |
1484 } | 1480 } |
1485 | 1481 |
1486 // Return the total amount of memory committed for new space. | 1482 // Return the total amount of memory committed for new space. |
1487 intptr_t CommittedMemory() { | 1483 int CommittedMemory() { |
1488 if (from_space_.is_committed()) return 2 * Capacity(); | 1484 if (from_space_.is_committed()) return 2 * Capacity(); |
1489 return Capacity(); | 1485 return Capacity(); |
1490 } | 1486 } |
1491 | 1487 |
1492 // Return the available bytes without growing in the active semispace. | 1488 // Return the available bytes without growing in the active semispace. |
1493 intptr_t Available() { return Capacity() - Size(); } | 1489 int Available() { return Capacity() - Size(); } |
1494 | 1490 |
1495 // Return the maximum capacity of a semispace. | 1491 // Return the maximum capacity of a semispace. |
1496 int MaximumCapacity() { | 1492 int MaximumCapacity() { |
1497 ASSERT(to_space_.MaximumCapacity() == from_space_.MaximumCapacity()); | 1493 ASSERT(to_space_.MaximumCapacity() == from_space_.MaximumCapacity()); |
1498 return to_space_.MaximumCapacity(); | 1494 return to_space_.MaximumCapacity(); |
1499 } | 1495 } |
1500 | 1496 |
1501 // Returns the initial capacity of a semispace. | 1497 // Returns the initial capacity of a semispace. |
1502 intptr_t InitialCapacity() { | 1498 int InitialCapacity() { |
1503 ASSERT(to_space_.InitialCapacity() == from_space_.InitialCapacity()); | 1499 ASSERT(to_space_.InitialCapacity() == from_space_.InitialCapacity()); |
1504 return to_space_.InitialCapacity(); | 1500 return to_space_.InitialCapacity(); |
1505 } | 1501 } |
1506 | 1502 |
1507 // Return the address of the allocation pointer in the active semispace. | 1503 // Return the address of the allocation pointer in the active semispace. |
1508 Address top() { return allocation_info_.top; } | 1504 Address top() { return allocation_info_.top; } |
1509 // Return the address of the first object in the active semispace. | 1505 // Return the address of the first object in the active semispace. |
1510 Address bottom() { return to_space_.low(); } | 1506 Address bottom() { return to_space_.low(); } |
1511 | 1507 |
1512 // Get the age mark of the inactive semispace. | 1508 // Get the age mark of the inactive semispace. |
(...skipping 165 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1678 | 1674 |
1679 // The free list for the old space. | 1675 // The free list for the old space. |
1680 class OldSpaceFreeList BASE_EMBEDDED { | 1676 class OldSpaceFreeList BASE_EMBEDDED { |
1681 public: | 1677 public: |
1682 explicit OldSpaceFreeList(AllocationSpace owner); | 1678 explicit OldSpaceFreeList(AllocationSpace owner); |
1683 | 1679 |
1684 // Clear the free list. | 1680 // Clear the free list. |
1685 void Reset(); | 1681 void Reset(); |
1686 | 1682 |
1687 // Return the number of bytes available on the free list. | 1683 // Return the number of bytes available on the free list. |
1688 intptr_t available() { return available_; } | 1684 int available() { return available_; } |
1689 | 1685 |
1690 // Place a node on the free list. The block of size 'size_in_bytes' | 1686 // Place a node on the free list. The block of size 'size_in_bytes' |
1691 // starting at 'start' is placed on the free list. The return value is the | 1687 // starting at 'start' is placed on the free list. The return value is the |
1692 // number of bytes that have been lost due to internal fragmentation by | 1688 // number of bytes that have been lost due to internal fragmentation by |
1693 // freeing the block. Bookkeeping information will be written to the block, | 1689 // freeing the block. Bookkeeping information will be written to the block, |
1694 // ie, its contents will be destroyed. The start address should be word | 1690 // ie, its contents will be destroyed. The start address should be word |
1695 // aligned, and the size should be a non-zero multiple of the word size. | 1691 // aligned, and the size should be a non-zero multiple of the word size. |
1696 int Free(Address start, int size_in_bytes); | 1692 int Free(Address start, int size_in_bytes); |
1697 | 1693 |
1698 // Allocate a block of size 'size_in_bytes' from the free list. The block | 1694 // Allocate a block of size 'size_in_bytes' from the free list. The block |
(...skipping 81 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1780 | 1776 |
1781 // The free list for the map space. | 1777 // The free list for the map space. |
1782 class FixedSizeFreeList BASE_EMBEDDED { | 1778 class FixedSizeFreeList BASE_EMBEDDED { |
1783 public: | 1779 public: |
1784 FixedSizeFreeList(AllocationSpace owner, int object_size); | 1780 FixedSizeFreeList(AllocationSpace owner, int object_size); |
1785 | 1781 |
1786 // Clear the free list. | 1782 // Clear the free list. |
1787 void Reset(); | 1783 void Reset(); |
1788 | 1784 |
1789 // Return the number of bytes available on the free list. | 1785 // Return the number of bytes available on the free list. |
1790 intptr_t available() { return available_; } | 1786 int available() { return available_; } |
1791 | 1787 |
1792 // Place a node on the free list. The block starting at 'start' (assumed to | 1788 // Place a node on the free list. The block starting at 'start' (assumed to |
1793 // have size object_size_) is placed on the free list. Bookkeeping | 1789 // have size object_size_) is placed on the free list. Bookkeeping |
1794 // information will be written to the block, ie, its contents will be | 1790 // information will be written to the block, ie, its contents will be |
1795 // destroyed. The start address should be word aligned. | 1791 // destroyed. The start address should be word aligned. |
1796 void Free(Address start); | 1792 void Free(Address start); |
1797 | 1793 |
1798 // Allocate a fixed sized block from the free list. The block is unitialized. | 1794 // Allocate a fixed sized block from the free list. The block is unitialized. |
1799 // A failure is returned if no block is available. | 1795 // A failure is returned if no block is available. |
1800 Object* Allocate(); | 1796 Object* Allocate(); |
1801 | 1797 |
1802 private: | 1798 private: |
1803 // Available bytes on the free list. | 1799 // Available bytes on the free list. |
1804 intptr_t available_; | 1800 int available_; |
1805 | 1801 |
1806 // The head of the free list. | 1802 // The head of the free list. |
1807 Address head_; | 1803 Address head_; |
1808 | 1804 |
1809 // The tail of the free list. | 1805 // The tail of the free list. |
1810 Address tail_; | 1806 Address tail_; |
1811 | 1807 |
1812 // The identity of the owning space, for building allocation Failure | 1808 // The identity of the owning space, for building allocation Failure |
1813 // objects. | 1809 // objects. |
1814 AllocationSpace owner_; | 1810 AllocationSpace owner_; |
(...skipping 14 matching lines...) Expand all Loading... |
1829 // The constructor does not allocate pages from OS. | 1825 // The constructor does not allocate pages from OS. |
1830 explicit OldSpace(int max_capacity, | 1826 explicit OldSpace(int max_capacity, |
1831 AllocationSpace id, | 1827 AllocationSpace id, |
1832 Executability executable) | 1828 Executability executable) |
1833 : PagedSpace(max_capacity, id, executable), free_list_(id) { | 1829 : PagedSpace(max_capacity, id, executable), free_list_(id) { |
1834 page_extra_ = 0; | 1830 page_extra_ = 0; |
1835 } | 1831 } |
1836 | 1832 |
1837 // The bytes available on the free list (ie, not above the linear allocation | 1833 // The bytes available on the free list (ie, not above the linear allocation |
1838 // pointer). | 1834 // pointer). |
1839 intptr_t AvailableFree() { return free_list_.available(); } | 1835 int AvailableFree() { return free_list_.available(); } |
1840 | 1836 |
1841 // The limit of allocation for a page in this space. | 1837 // The limit of allocation for a page in this space. |
1842 virtual Address PageAllocationLimit(Page* page) { | 1838 virtual Address PageAllocationLimit(Page* page) { |
1843 return page->ObjectAreaEnd(); | 1839 return page->ObjectAreaEnd(); |
1844 } | 1840 } |
1845 | 1841 |
1846 // Give a block of memory to the space's free list. It might be added to | 1842 // Give a block of memory to the space's free list. It might be added to |
1847 // the free list or accounted as waste. | 1843 // the free list or accounted as waste. |
1848 // If add_to_freelist is false then just accounting stats are updated and | 1844 // If add_to_freelist is false then just accounting stats are updated and |
1849 // no attempt to add area to free list is made. | 1845 // no attempt to add area to free list is made. |
(...skipping 276 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2126 | 2122 |
2127 // Returns the object in this chunk. | 2123 // Returns the object in this chunk. |
2128 inline HeapObject* GetObject(); | 2124 inline HeapObject* GetObject(); |
2129 | 2125 |
2130 // Given a requested size returns the physical size of a chunk to be | 2126 // Given a requested size returns the physical size of a chunk to be |
2131 // allocated. | 2127 // allocated. |
2132 static int ChunkSizeFor(int size_in_bytes); | 2128 static int ChunkSizeFor(int size_in_bytes); |
2133 | 2129 |
2134 // Given a chunk size, returns the object size it can accommodate. Used by | 2130 // Given a chunk size, returns the object size it can accommodate. Used by |
2135 // LargeObjectSpace::Available. | 2131 // LargeObjectSpace::Available. |
2136 static intptr_t ObjectSizeFor(intptr_t chunk_size) { | 2132 static int ObjectSizeFor(int chunk_size) { |
2137 if (chunk_size <= (Page::kPageSize + Page::kObjectStartOffset)) return 0; | 2133 if (chunk_size <= (Page::kPageSize + Page::kObjectStartOffset)) return 0; |
2138 return chunk_size - Page::kPageSize - Page::kObjectStartOffset; | 2134 return chunk_size - Page::kPageSize - Page::kObjectStartOffset; |
2139 } | 2135 } |
2140 | 2136 |
2141 private: | 2137 private: |
2142 // A pointer to the next large object chunk in the space or NULL. | 2138 // A pointer to the next large object chunk in the space or NULL. |
2143 LargeObjectChunk* next_; | 2139 LargeObjectChunk* next_; |
2144 | 2140 |
2145 // The size of this chunk. | 2141 // The size of this chunk. |
2146 size_t size_; | 2142 size_t size_; |
(...skipping 15 matching lines...) Expand all Loading... |
2162 void TearDown(); | 2158 void TearDown(); |
2163 | 2159 |
2164 // Allocates a (non-FixedArray, non-Code) large object. | 2160 // Allocates a (non-FixedArray, non-Code) large object. |
2165 Object* AllocateRaw(int size_in_bytes); | 2161 Object* AllocateRaw(int size_in_bytes); |
2166 // Allocates a large Code object. | 2162 // Allocates a large Code object. |
2167 Object* AllocateRawCode(int size_in_bytes); | 2163 Object* AllocateRawCode(int size_in_bytes); |
2168 // Allocates a large FixedArray. | 2164 // Allocates a large FixedArray. |
2169 Object* AllocateRawFixedArray(int size_in_bytes); | 2165 Object* AllocateRawFixedArray(int size_in_bytes); |
2170 | 2166 |
2171 // Available bytes for objects in this space. | 2167 // Available bytes for objects in this space. |
2172 intptr_t Available() { | 2168 int Available() { |
2173 return LargeObjectChunk::ObjectSizeFor(MemoryAllocator::Available()); | 2169 return LargeObjectChunk::ObjectSizeFor(MemoryAllocator::Available()); |
2174 } | 2170 } |
2175 | 2171 |
2176 virtual intptr_t Size() { | 2172 virtual int Size() { |
2177 return size_; | 2173 return size_; |
2178 } | 2174 } |
2179 | 2175 |
2180 int PageCount() { | 2176 int PageCount() { |
2181 return page_count_; | 2177 return page_count_; |
2182 } | 2178 } |
2183 | 2179 |
2184 // Finds an object for a given address, returns Failure::Exception() | 2180 // Finds an object for a given address, returns Failure::Exception() |
2185 // if it is not found. The function iterates through all objects in this | 2181 // if it is not found. The function iterates through all objects in this |
2186 // space, may be slow. | 2182 // space, may be slow. |
(...skipping 33 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
2220 void ReportStatistics(); | 2216 void ReportStatistics(); |
2221 void CollectCodeStatistics(); | 2217 void CollectCodeStatistics(); |
2222 #endif | 2218 #endif |
2223 // Checks whether an address is in the object area in this space. It | 2219 // Checks whether an address is in the object area in this space. It |
2224 // iterates all objects in the space. May be slow. | 2220 // iterates all objects in the space. May be slow. |
2225 bool SlowContains(Address addr) { return !FindObject(addr)->IsFailure(); } | 2221 bool SlowContains(Address addr) { return !FindObject(addr)->IsFailure(); } |
2226 | 2222 |
2227 private: | 2223 private: |
2228 // The head of the linked list of large object chunks. | 2224 // The head of the linked list of large object chunks. |
2229 LargeObjectChunk* first_chunk_; | 2225 LargeObjectChunk* first_chunk_; |
2230 intptr_t size_; // allocated bytes | 2226 int size_; // allocated bytes |
2231 int page_count_; // number of chunks | 2227 int page_count_; // number of chunks |
2232 | 2228 |
2233 | 2229 |
2234 // Shared implementation of AllocateRaw, AllocateRawCode and | 2230 // Shared implementation of AllocateRaw, AllocateRawCode and |
2235 // AllocateRawFixedArray. | 2231 // AllocateRawFixedArray. |
2236 Object* AllocateRawInternal(int requested_size, | 2232 Object* AllocateRawInternal(int requested_size, |
2237 int object_size, | 2233 int object_size, |
2238 Executability executable); | 2234 Executability executable); |
2239 | 2235 |
2240 friend class LargeObjectIterator; | 2236 friend class LargeObjectIterator; |
(...skipping 15 matching lines...) Expand all Loading... |
2256 | 2252 |
2257 private: | 2253 private: |
2258 LargeObjectChunk* current_; | 2254 LargeObjectChunk* current_; |
2259 HeapObjectCallback size_func_; | 2255 HeapObjectCallback size_func_; |
2260 }; | 2256 }; |
2261 | 2257 |
2262 | 2258 |
2263 } } // namespace v8::internal | 2259 } } // namespace v8::internal |
2264 | 2260 |
2265 #endif // V8_SPACES_H_ | 2261 #endif // V8_SPACES_H_ |
OLD | NEW |