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 1758 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1769 return; | 1769 return; |
1770 } | 1770 } |
1771 } | 1771 } |
1772 } | 1772 } |
1773 // One of the strings in the natives cache should match the resource. We | 1773 // One of the strings in the natives cache should match the resource. We |
1774 // can't serialize any other kinds of external strings. | 1774 // can't serialize any other kinds of external strings. |
1775 UNREACHABLE(); | 1775 UNREACHABLE(); |
1776 } | 1776 } |
1777 | 1777 |
1778 | 1778 |
1779 static Code* CloneCodeObject(HeapObject* code) { | |
1780 Address copy = new byte[code->Size()]; | |
1781 OS::MemCopy(copy, code->address(), code->Size()); | |
1782 return Code::cast(HeapObject::FromAddress(copy)); | |
1783 } | |
1784 | |
1785 | |
1786 static void WipeOutCodeHeader(Code* code) { | |
1787 code->set_relocation_info( | |
Benedikt Meurer
2013/11/04 11:25:14
Nit: Can we do better here?
| |
1788 reinterpret_cast<ByteArray*>(Smi::FromInt(0)), SKIP_WRITE_BARRIER); | |
1789 code->set_handler_table( | |
1790 reinterpret_cast<FixedArray*>(Smi::FromInt(0)), SKIP_WRITE_BARRIER); | |
1791 code->set_deoptimization_data( | |
1792 reinterpret_cast<FixedArray*>(Smi::FromInt(0)), SKIP_WRITE_BARRIER); | |
1793 // Do not wipe out e.g. a minor key. | |
1794 if (!code->raw_type_feedback_info()->IsSmi()) { | |
1795 code->InitializeTypeFeedbackInfoNoWriteBarrier(Smi::FromInt(0)); | |
1796 } | |
1797 } | |
1798 | |
1799 | |
1800 static void WipeOutRelocations(Code* code) { | |
1801 int mode_mask = | |
1802 RelocInfo::kCodeTargetMask | | |
1803 RelocInfo::ModeMask(RelocInfo::EMBEDDED_OBJECT) | | |
1804 RelocInfo::ModeMask(RelocInfo::EXTERNAL_REFERENCE) | | |
1805 RelocInfo::ModeMask(RelocInfo::RUNTIME_ENTRY); | |
1806 for (RelocIterator it(code, mode_mask); !it.done(); it.next()) { | |
1807 it.rinfo()->WipeOut(); | |
1808 } | |
1809 } | |
1810 | |
1811 | |
1779 int Serializer::ObjectSerializer::OutputRawData( | 1812 int Serializer::ObjectSerializer::OutputRawData( |
1780 Address up_to, Serializer::ObjectSerializer::ReturnSkip return_skip) { | 1813 Address up_to, Serializer::ObjectSerializer::ReturnSkip return_skip) { |
1781 Address object_start = object_->address(); | 1814 Address object_start = object_->address(); |
1782 Address base = object_start + bytes_processed_so_far_; | 1815 int base = bytes_processed_so_far_; |
1783 int up_to_offset = static_cast<int>(up_to - object_start); | 1816 int up_to_offset = static_cast<int>(up_to - object_start); |
1784 int to_skip = up_to_offset - bytes_processed_so_far_; | 1817 int to_skip = up_to_offset - bytes_processed_so_far_; |
1785 int bytes_to_output = to_skip; | 1818 int bytes_to_output = to_skip; |
1786 bytes_processed_so_far_ += to_skip; | 1819 bytes_processed_so_far_ += to_skip; |
1787 // This assert will fail if the reloc info gives us the target_address_address | 1820 // This assert will fail if the reloc info gives us the target_address_address |
1788 // locations in a non-ascending order. Luckily that doesn't happen. | 1821 // locations in a non-ascending order. Luckily that doesn't happen. |
1789 ASSERT(to_skip >= 0); | 1822 ASSERT(to_skip >= 0); |
1790 bool outputting_code = false; | 1823 bool outputting_code = false; |
1791 if (to_skip != 0 && code_object_ && !code_has_been_output_) { | 1824 if (to_skip != 0 && code_object_ && !code_has_been_output_) { |
1792 // Output the code all at once and fix later. | 1825 // Output the code all at once and fix later. |
1793 bytes_to_output = object_->Size() + to_skip - bytes_processed_so_far_; | 1826 bytes_to_output = object_->Size() + to_skip - bytes_processed_so_far_; |
1794 outputting_code = true; | 1827 outputting_code = true; |
1795 code_has_been_output_ = true; | 1828 code_has_been_output_ = true; |
1796 } | 1829 } |
1797 if (bytes_to_output != 0 && | 1830 if (bytes_to_output != 0 && |
1798 (!code_object_ || outputting_code)) { | 1831 (!code_object_ || outputting_code)) { |
1799 #define RAW_CASE(index) \ | 1832 #define RAW_CASE(index) \ |
1800 if (!outputting_code && bytes_to_output == index * kPointerSize && \ | 1833 if (!outputting_code && bytes_to_output == index * kPointerSize && \ |
1801 index * kPointerSize == to_skip) { \ | 1834 index * kPointerSize == to_skip) { \ |
1802 sink_->PutSection(kRawData + index, "RawDataFixed"); \ | 1835 sink_->PutSection(kRawData + index, "RawDataFixed"); \ |
1803 to_skip = 0; /* This insn already skips. */ \ | 1836 to_skip = 0; /* This insn already skips. */ \ |
1804 } else /* NOLINT */ | 1837 } else /* NOLINT */ |
1805 COMMON_RAW_LENGTHS(RAW_CASE) | 1838 COMMON_RAW_LENGTHS(RAW_CASE) |
1806 #undef RAW_CASE | 1839 #undef RAW_CASE |
1807 { /* NOLINT */ | 1840 { /* NOLINT */ |
1808 // We always end up here if we are outputting the code of a code object. | 1841 // We always end up here if we are outputting the code of a code object. |
1809 sink_->Put(kRawData, "RawData"); | 1842 sink_->Put(kRawData, "RawData"); |
1810 sink_->PutInt(bytes_to_output, "length"); | 1843 sink_->PutInt(bytes_to_output, "length"); |
1811 } | 1844 } |
1845 | |
1846 // To make snapshots reproducible, we need to wipe out all pointers in code. | |
1847 if (code_object_) { | |
1848 Code* code = CloneCodeObject(object_); | |
1849 WipeOutRelocations(code); | |
1850 // We need to wipe out the header fields *after* wiping out the | |
1851 // relocations, because some of these fields are needed for the latter. | |
1852 WipeOutCodeHeader(code); | |
1853 object_start = code->address(); | |
1854 } | |
1855 | |
1856 const char* description = code_object_ ? "Code" : "Byte"; | |
1812 for (int i = 0; i < bytes_to_output; i++) { | 1857 for (int i = 0; i < bytes_to_output; i++) { |
1813 unsigned int data = base[i]; | 1858 sink_->PutSection(object_start[base + i], description); |
1814 sink_->PutSection(data, "Byte"); | |
1815 } | 1859 } |
1860 if (code_object_) delete[] object_start; | |
1816 } | 1861 } |
1817 if (to_skip != 0 && return_skip == kIgnoringReturn) { | 1862 if (to_skip != 0 && return_skip == kIgnoringReturn) { |
1818 sink_->Put(kSkip, "Skip"); | 1863 sink_->Put(kSkip, "Skip"); |
1819 sink_->PutInt(to_skip, "SkipDistance"); | 1864 sink_->PutInt(to_skip, "SkipDistance"); |
1820 to_skip = 0; | 1865 to_skip = 0; |
1821 } | 1866 } |
1822 return to_skip; | 1867 return to_skip; |
1823 } | 1868 } |
1824 | 1869 |
1825 | 1870 |
(...skipping 38 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1864 | 1909 |
1865 bool SnapshotByteSource::AtEOF() { | 1910 bool SnapshotByteSource::AtEOF() { |
1866 if (0u + length_ - position_ > 2 * sizeof(uint32_t)) return false; | 1911 if (0u + length_ - position_ > 2 * sizeof(uint32_t)) return false; |
1867 for (int x = position_; x < length_; x++) { | 1912 for (int x = position_; x < length_; x++) { |
1868 if (data_[x] != SerializerDeserializer::nop()) return false; | 1913 if (data_[x] != SerializerDeserializer::nop()) return false; |
1869 } | 1914 } |
1870 return true; | 1915 return true; |
1871 } | 1916 } |
1872 | 1917 |
1873 } } // namespace v8::internal | 1918 } } // namespace v8::internal |
OLD | NEW |