OLD | NEW |
1 // Copyright 2012 the V8 project authors. All rights reserved. | 1 // Copyright 2012 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 1766 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1777 CHECK_EQ(initial_size, static_cast<int>(CcTest::heap()->SizeOfObjects())); | 1777 CHECK_EQ(initial_size, static_cast<int>(CcTest::heap()->SizeOfObjects())); |
1778 | 1778 |
1779 // Waiting for sweeper threads should not change heap size. | 1779 // Waiting for sweeper threads should not change heap size. |
1780 if (collector->sweeping_in_progress()) { | 1780 if (collector->sweeping_in_progress()) { |
1781 collector->EnsureSweepingCompleted(); | 1781 collector->EnsureSweepingCompleted(); |
1782 } | 1782 } |
1783 CHECK_EQ(initial_size, static_cast<int>(CcTest::heap()->SizeOfObjects())); | 1783 CHECK_EQ(initial_size, static_cast<int>(CcTest::heap()->SizeOfObjects())); |
1784 } | 1784 } |
1785 | 1785 |
1786 | 1786 |
| 1787 TEST(TestAlignmentCalculations) { |
| 1788 // Maximum fill amounts should be consistent. |
| 1789 int maximum_double_misalignment = kDoubleSize - kPointerSize; |
| 1790 int max_word_fill = Heap::GetMaximumFillToAlign(kWordAligned); |
| 1791 CHECK_EQ(0, max_word_fill); |
| 1792 int max_double_fill = Heap::GetMaximumFillToAlign(kDoubleAligned); |
| 1793 CHECK_EQ(maximum_double_misalignment, max_double_fill); |
| 1794 int max_double_unaligned_fill = Heap::GetMaximumFillToAlign(kDoubleUnaligned); |
| 1795 CHECK_EQ(maximum_double_misalignment, max_double_unaligned_fill); |
| 1796 |
| 1797 Address base = reinterpret_cast<Address>(NULL); |
| 1798 int fill = 0; |
| 1799 |
| 1800 // Word alignment never requires fill. |
| 1801 fill = Heap::GetFillToAlign(base, kWordAligned); |
| 1802 CHECK_EQ(0, fill); |
| 1803 fill = Heap::GetFillToAlign(base + kPointerSize, kWordAligned); |
| 1804 CHECK_EQ(0, fill); |
| 1805 |
| 1806 // No fill is required when address is double aligned. |
| 1807 fill = Heap::GetFillToAlign(base, kDoubleAligned); |
| 1808 CHECK_EQ(0, fill); |
| 1809 // Fill is required if address is not double aligned. |
| 1810 fill = Heap::GetFillToAlign(base + kPointerSize, kDoubleAligned); |
| 1811 CHECK_EQ(maximum_double_misalignment, fill); |
| 1812 // kDoubleUnaligned has the opposite fill amounts. |
| 1813 fill = Heap::GetFillToAlign(base, kDoubleUnaligned); |
| 1814 CHECK_EQ(maximum_double_misalignment, fill); |
| 1815 fill = Heap::GetFillToAlign(base + kPointerSize, kDoubleUnaligned); |
| 1816 CHECK_EQ(0, fill); |
| 1817 } |
| 1818 |
| 1819 |
| 1820 static HeapObject* NewSpaceAllocateAligned(int size, |
| 1821 AllocationAlignment alignment) { |
| 1822 Heap* heap = CcTest::heap(); |
| 1823 AllocationResult allocation = |
| 1824 heap->new_space()->AllocateRawAligned(size, alignment); |
| 1825 HeapObject* obj = NULL; |
| 1826 allocation.To(&obj); |
| 1827 heap->CreateFillerObjectAt(obj->address(), size); |
| 1828 return obj; |
| 1829 } |
| 1830 |
| 1831 |
| 1832 TEST(TestAlignedAllocation) { |
| 1833 // Double misalignment is 4 on 32-bit platforms, 0 on 64-bit ones. |
| 1834 const intptr_t double_misalignment = kDoubleSize - kPointerSize; |
| 1835 if (double_misalignment) { |
| 1836 Address* top_addr = CcTest::heap()->new_space()->allocation_top_address(); |
| 1837 // Align the top for the first test. |
| 1838 if (!IsAddressAligned(*top_addr, kDoubleAlignment)) |
| 1839 NewSpaceAllocateAligned(kPointerSize, kWordAligned); |
| 1840 |
| 1841 // Allocate a pointer sized object that must be double aligned. |
| 1842 Address start = *top_addr; |
| 1843 HeapObject* obj1 = NewSpaceAllocateAligned(kPointerSize, kDoubleAligned); |
| 1844 CHECK(IsAddressAligned(obj1->address(), kDoubleAlignment)); |
| 1845 // Only the object was allocated. |
| 1846 CHECK_EQ(kPointerSize, *top_addr - start); |
| 1847 // top is now misaligned. |
| 1848 // Allocate a second pointer sized object that must be double aligned. |
| 1849 HeapObject* obj2 = NewSpaceAllocateAligned(kPointerSize, kDoubleAligned); |
| 1850 CHECK(IsAddressAligned(obj2->address(), kDoubleAlignment)); |
| 1851 // There should be a filler object in between the two objects. |
| 1852 CHECK(HeapObject::FromAddress(start + kPointerSize)->IsFiller()); |
| 1853 // Two objects and a filler object were allocated. |
| 1854 CHECK_EQ(2 * kPointerSize + double_misalignment, *top_addr - start); |
| 1855 |
| 1856 // Similarly for kDoubleUnaligned. top is misaligned. |
| 1857 start = *top_addr; |
| 1858 obj1 = NewSpaceAllocateAligned(kPointerSize, kDoubleUnaligned); |
| 1859 CHECK(IsAddressAligned(obj1->address(), kDoubleAlignment, kPointerSize)); |
| 1860 CHECK_EQ(kPointerSize, *top_addr - start); |
| 1861 obj2 = NewSpaceAllocateAligned(kPointerSize, kDoubleUnaligned); |
| 1862 CHECK(IsAddressAligned(obj2->address(), kDoubleAlignment, kPointerSize)); |
| 1863 CHECK(HeapObject::FromAddress(start + kPointerSize)->IsFiller()); |
| 1864 CHECK_EQ(2 * kPointerSize + double_misalignment, *top_addr - start); |
| 1865 } |
| 1866 } |
| 1867 |
| 1868 |
| 1869 // Force allocation to happen from the free list, at a desired misalignment. |
| 1870 static Address SetUpFreeListAllocation(int misalignment) { |
| 1871 Heap* heap = CcTest::heap(); |
| 1872 OldSpace* old_space = heap->old_space(); |
| 1873 Address top = old_space->top(); |
| 1874 // First, allocate enough filler to get the linear area into the desired |
| 1875 // misalignment. |
| 1876 const intptr_t maximum_misalignment = 2 * kPointerSize; |
| 1877 const intptr_t maximum_misalignment_mask = maximum_misalignment - 1; |
| 1878 intptr_t top_alignment = OffsetFrom(top) & maximum_misalignment_mask; |
| 1879 int filler_size = misalignment - static_cast<int>(top_alignment); |
| 1880 if (filler_size < 0) filler_size += maximum_misalignment; |
| 1881 if (filler_size) { |
| 1882 // Create the filler object. |
| 1883 AllocationResult allocation = old_space->AllocateRawUnaligned(filler_size); |
| 1884 HeapObject* obj = NULL; |
| 1885 allocation.To(&obj); |
| 1886 heap->CreateFillerObjectAt(obj->address(), filler_size); |
| 1887 } |
| 1888 top = old_space->top(); |
| 1889 old_space->EmptyAllocationInfo(); |
| 1890 return top; |
| 1891 } |
| 1892 |
| 1893 |
| 1894 static HeapObject* OldSpaceAllocateAligned(int size, |
| 1895 AllocationAlignment alignment) { |
| 1896 Heap* heap = CcTest::heap(); |
| 1897 AllocationResult allocation = |
| 1898 heap->old_space()->AllocateRawAligned(size, alignment); |
| 1899 HeapObject* obj = NULL; |
| 1900 allocation.To(&obj); |
| 1901 heap->CreateFillerObjectAt(obj->address(), size); |
| 1902 return obj; |
| 1903 } |
| 1904 |
| 1905 |
| 1906 // Test the case where allocation must be done from the free list, so filler |
| 1907 // may precede or follow the object. |
| 1908 TEST(TestAlignedOverAllocation) { |
| 1909 // Double misalignment is 4 on 32-bit platforms, 0 on 64-bit ones. |
| 1910 const intptr_t double_misalignment = kDoubleSize - kPointerSize; |
| 1911 if (double_misalignment) { |
| 1912 Address start = SetUpFreeListAllocation(0); |
| 1913 HeapObject* obj1 = OldSpaceAllocateAligned(kPointerSize, kDoubleAligned); |
| 1914 // The object should be aligned, and a filler object should be created. |
| 1915 CHECK(IsAddressAligned(obj1->address(), kDoubleAlignment)); |
| 1916 CHECK(HeapObject::FromAddress(start)->IsFiller() && |
| 1917 HeapObject::FromAddress(start + kPointerSize)->IsFiller()); |
| 1918 // Try the opposite alignment case. |
| 1919 start = SetUpFreeListAllocation(kPointerSize); |
| 1920 HeapObject* obj2 = OldSpaceAllocateAligned(kPointerSize, kDoubleAligned); |
| 1921 CHECK(IsAddressAligned(obj2->address(), kDoubleAlignment)); |
| 1922 CHECK(HeapObject::FromAddress(start)->IsFiller() && |
| 1923 HeapObject::FromAddress(start + kPointerSize)->IsFiller()); |
| 1924 |
| 1925 // Similarly for kDoubleUnaligned. |
| 1926 start = SetUpFreeListAllocation(0); |
| 1927 obj1 = OldSpaceAllocateAligned(kPointerSize, kDoubleUnaligned); |
| 1928 // The object should be aligned, and a filler object should be created. |
| 1929 CHECK(IsAddressAligned(obj1->address(), kDoubleAlignment, kPointerSize)); |
| 1930 CHECK(HeapObject::FromAddress(start)->IsFiller() && |
| 1931 HeapObject::FromAddress(start + kPointerSize)->IsFiller()); |
| 1932 // Try the opposite alignment case. |
| 1933 start = SetUpFreeListAllocation(kPointerSize); |
| 1934 obj2 = OldSpaceAllocateAligned(kPointerSize, kDoubleUnaligned); |
| 1935 CHECK(IsAddressAligned(obj2->address(), kDoubleAlignment, kPointerSize)); |
| 1936 CHECK(HeapObject::FromAddress(start)->IsFiller() && |
| 1937 HeapObject::FromAddress(start + kPointerSize)->IsFiller()); |
| 1938 } |
| 1939 } |
| 1940 |
| 1941 |
1787 TEST(TestSizeOfObjectsVsHeapIteratorPrecision) { | 1942 TEST(TestSizeOfObjectsVsHeapIteratorPrecision) { |
1788 CcTest::InitializeVM(); | 1943 CcTest::InitializeVM(); |
1789 HeapIterator iterator(CcTest::heap()); | 1944 HeapIterator iterator(CcTest::heap()); |
1790 intptr_t size_of_objects_1 = CcTest::heap()->SizeOfObjects(); | 1945 intptr_t size_of_objects_1 = CcTest::heap()->SizeOfObjects(); |
1791 intptr_t size_of_objects_2 = 0; | 1946 intptr_t size_of_objects_2 = 0; |
1792 for (HeapObject* obj = iterator.next(); | 1947 for (HeapObject* obj = iterator.next(); |
1793 obj != NULL; | 1948 obj != NULL; |
1794 obj = iterator.next()) { | 1949 obj = iterator.next()) { |
1795 if (!obj->IsFreeSpace()) { | 1950 if (!obj->IsFreeSpace()) { |
1796 size_of_objects_2 += obj->Size(); | 1951 size_of_objects_2 += obj->Size(); |
(...skipping 3837 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
5634 size_t counter2 = 2000; | 5789 size_t counter2 = 2000; |
5635 tracer->SampleAllocation(time2, counter2, counter2); | 5790 tracer->SampleAllocation(time2, counter2, counter2); |
5636 size_t throughput = tracer->AllocationThroughputInBytesPerMillisecond(100); | 5791 size_t throughput = tracer->AllocationThroughputInBytesPerMillisecond(100); |
5637 CHECK_EQ(2 * (counter2 - counter1) / (time2 - time1), throughput); | 5792 CHECK_EQ(2 * (counter2 - counter1) / (time2 - time1), throughput); |
5638 int time3 = 1000; | 5793 int time3 = 1000; |
5639 size_t counter3 = 30000; | 5794 size_t counter3 = 30000; |
5640 tracer->SampleAllocation(time3, counter3, counter3); | 5795 tracer->SampleAllocation(time3, counter3, counter3); |
5641 throughput = tracer->AllocationThroughputInBytesPerMillisecond(100); | 5796 throughput = tracer->AllocationThroughputInBytesPerMillisecond(100); |
5642 CHECK_EQ(2 * (counter3 - counter1) / (time3 - time1), throughput); | 5797 CHECK_EQ(2 * (counter3 - counter1) / (time3 - time1), throughput); |
5643 } | 5798 } |
OLD | NEW |