OLD | NEW |
1 // Copyright 2013 the V8 project authors. All rights reserved. | 1 // Copyright 2013 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/deoptimizer.h" | 5 #include "src/deoptimizer.h" |
6 | 6 |
7 #include "src/accessors.h" | 7 #include "src/accessors.h" |
8 #include "src/ast/prettyprinter.h" | 8 #include "src/ast/prettyprinter.h" |
9 #include "src/codegen.h" | 9 #include "src/codegen.h" |
10 #include "src/disasm.h" | 10 #include "src/disasm.h" |
(...skipping 877 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
888 // Allocate and store the output frame description. | 888 // Allocate and store the output frame description. |
889 int parameter_count = shared->internal_formal_parameter_count() + 1; | 889 int parameter_count = shared->internal_formal_parameter_count() + 1; |
890 FrameDescription* output_frame = new (output_frame_size) | 890 FrameDescription* output_frame = new (output_frame_size) |
891 FrameDescription(output_frame_size, parameter_count); | 891 FrameDescription(output_frame_size, parameter_count); |
892 output_frame->SetFrameType(StackFrame::JAVA_SCRIPT); | 892 output_frame->SetFrameType(StackFrame::JAVA_SCRIPT); |
893 | 893 |
894 CHECK(frame_index >= 0 && frame_index < output_count_); | 894 CHECK(frame_index >= 0 && frame_index < output_count_); |
895 CHECK_NULL(output_[frame_index]); | 895 CHECK_NULL(output_[frame_index]); |
896 output_[frame_index] = output_frame; | 896 output_[frame_index] = output_frame; |
897 | 897 |
898 // The top address for the bottommost output frame can be computed from | 898 // The top address of the frame is computed from the previous frame's top and |
899 // the input frame pointer and the output frame's height. For all | 899 // this frame's size. |
900 // subsequent output frames, it can be computed from the previous one's | |
901 // top address and the current frame's size. | |
902 Register fp_reg = JavaScriptFrame::fp_register(); | |
903 intptr_t top_address; | 900 intptr_t top_address; |
904 if (is_bottommost) { | 901 if (is_bottommost) { |
905 top_address = caller_frame_top_ - output_frame_size; | 902 top_address = caller_frame_top_ - output_frame_size; |
906 } else { | 903 } else { |
907 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; | 904 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; |
908 } | 905 } |
909 output_frame->SetTop(top_address); | 906 output_frame->SetTop(top_address); |
910 | 907 |
911 // Compute the incoming parameter translation. | 908 // Compute the incoming parameter translation. |
912 unsigned output_offset = output_frame_size; | 909 unsigned output_offset = output_frame_size; |
(...skipping 27 matching lines...) Expand all Loading... |
940 // pointer. | 937 // pointer. |
941 output_offset -= kFPOnStackSize; | 938 output_offset -= kFPOnStackSize; |
942 if (is_bottommost) { | 939 if (is_bottommost) { |
943 value = caller_fp_; | 940 value = caller_fp_; |
944 } else { | 941 } else { |
945 value = output_[frame_index - 1]->GetFp(); | 942 value = output_[frame_index - 1]->GetFp(); |
946 } | 943 } |
947 output_frame->SetCallerFp(output_offset, value); | 944 output_frame->SetCallerFp(output_offset, value); |
948 intptr_t fp_value = top_address + output_offset; | 945 intptr_t fp_value = top_address + output_offset; |
949 output_frame->SetFp(fp_value); | 946 output_frame->SetFp(fp_value); |
950 if (is_topmost) output_frame->SetRegister(fp_reg.code(), fp_value); | 947 if (is_topmost) { |
| 948 Register fp_reg = JavaScriptFrame::fp_register(); |
| 949 output_frame->SetRegister(fp_reg.code(), fp_value); |
| 950 } |
951 DebugPrintOutputSlot(value, frame_index, output_offset, "caller's fp\n"); | 951 DebugPrintOutputSlot(value, frame_index, output_offset, "caller's fp\n"); |
952 | 952 |
953 if (FLAG_enable_embedded_constant_pool) { | 953 if (FLAG_enable_embedded_constant_pool) { |
954 // For the bottommost output frame the constant pool pointer can be gotten | 954 // For the bottommost output frame the constant pool pointer can be gotten |
955 // from the input frame. For subsequent output frames, it can be read from | 955 // from the input frame. For subsequent output frames, it can be read from |
956 // the previous frame. | 956 // the previous frame. |
957 output_offset -= kPointerSize; | 957 output_offset -= kPointerSize; |
958 if (is_bottommost) { | 958 if (is_bottommost) { |
959 value = caller_constant_pool_; | 959 value = caller_constant_pool_; |
960 } else { | 960 } else { |
(...skipping 149 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1110 FrameDescription* output_frame = new (output_frame_size) | 1110 FrameDescription* output_frame = new (output_frame_size) |
1111 FrameDescription(output_frame_size, parameter_count); | 1111 FrameDescription(output_frame_size, parameter_count); |
1112 output_frame->SetFrameType(StackFrame::INTERPRETED); | 1112 output_frame->SetFrameType(StackFrame::INTERPRETED); |
1113 | 1113 |
1114 bool is_bottommost = (0 == frame_index); | 1114 bool is_bottommost = (0 == frame_index); |
1115 bool is_topmost = (output_count_ - 1 == frame_index); | 1115 bool is_topmost = (output_count_ - 1 == frame_index); |
1116 CHECK(frame_index >= 0 && frame_index < output_count_); | 1116 CHECK(frame_index >= 0 && frame_index < output_count_); |
1117 CHECK_NULL(output_[frame_index]); | 1117 CHECK_NULL(output_[frame_index]); |
1118 output_[frame_index] = output_frame; | 1118 output_[frame_index] = output_frame; |
1119 | 1119 |
1120 // The top address for the bottommost output frame can be computed from | 1120 // The top address of the frame is computed from the previous frame's top and |
1121 // the input frame pointer and the output frame's height. For all | 1121 // this frame's size. |
1122 // subsequent output frames, it can be computed from the previous one's | |
1123 // top address and the current frame's size. | |
1124 Register fp_reg = InterpretedFrame::fp_register(); | |
1125 intptr_t top_address; | 1122 intptr_t top_address; |
1126 if (is_bottommost) { | 1123 if (is_bottommost) { |
1127 top_address = caller_frame_top_ - output_frame_size; | 1124 top_address = caller_frame_top_ - output_frame_size; |
1128 } else { | 1125 } else { |
1129 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; | 1126 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; |
1130 } | 1127 } |
1131 output_frame->SetTop(top_address); | 1128 output_frame->SetTop(top_address); |
1132 | 1129 |
1133 // Compute the incoming parameter translation. | 1130 // Compute the incoming parameter translation. |
1134 unsigned output_offset = output_frame_size; | 1131 unsigned output_offset = output_frame_size; |
(...skipping 28 matching lines...) Expand all Loading... |
1163 // pointer. | 1160 // pointer. |
1164 output_offset -= kFPOnStackSize; | 1161 output_offset -= kFPOnStackSize; |
1165 if (is_bottommost) { | 1162 if (is_bottommost) { |
1166 value = caller_fp_; | 1163 value = caller_fp_; |
1167 } else { | 1164 } else { |
1168 value = output_[frame_index - 1]->GetFp(); | 1165 value = output_[frame_index - 1]->GetFp(); |
1169 } | 1166 } |
1170 output_frame->SetCallerFp(output_offset, value); | 1167 output_frame->SetCallerFp(output_offset, value); |
1171 intptr_t fp_value = top_address + output_offset; | 1168 intptr_t fp_value = top_address + output_offset; |
1172 output_frame->SetFp(fp_value); | 1169 output_frame->SetFp(fp_value); |
1173 if (is_topmost) output_frame->SetRegister(fp_reg.code(), fp_value); | 1170 if (is_topmost) { |
| 1171 Register fp_reg = InterpretedFrame::fp_register(); |
| 1172 output_frame->SetRegister(fp_reg.code(), fp_value); |
| 1173 } |
1174 DebugPrintOutputSlot(value, frame_index, output_offset, "caller's fp\n"); | 1174 DebugPrintOutputSlot(value, frame_index, output_offset, "caller's fp\n"); |
1175 | 1175 |
1176 if (FLAG_enable_embedded_constant_pool) { | 1176 if (FLAG_enable_embedded_constant_pool) { |
1177 // For the bottommost output frame the constant pool pointer can be gotten | 1177 // For the bottommost output frame the constant pool pointer can be gotten |
1178 // from the input frame. For subsequent output frames, it can be read from | 1178 // from the input frame. For subsequent output frames, it can be read from |
1179 // the previous frame. | 1179 // the previous frame. |
1180 output_offset -= kPointerSize; | 1180 output_offset -= kPointerSize; |
1181 if (is_bottommost) { | 1181 if (is_bottommost) { |
1182 value = caller_constant_pool_; | 1182 value = caller_constant_pool_; |
1183 } else { | 1183 } else { |
(...skipping 143 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1327 int parameter_count = height; | 1327 int parameter_count = height; |
1328 FrameDescription* output_frame = new (output_frame_size) | 1328 FrameDescription* output_frame = new (output_frame_size) |
1329 FrameDescription(output_frame_size, parameter_count); | 1329 FrameDescription(output_frame_size, parameter_count); |
1330 output_frame->SetFrameType(StackFrame::ARGUMENTS_ADAPTOR); | 1330 output_frame->SetFrameType(StackFrame::ARGUMENTS_ADAPTOR); |
1331 | 1331 |
1332 // Arguments adaptor can not be topmost. | 1332 // Arguments adaptor can not be topmost. |
1333 CHECK(frame_index < output_count_ - 1); | 1333 CHECK(frame_index < output_count_ - 1); |
1334 CHECK(output_[frame_index] == NULL); | 1334 CHECK(output_[frame_index] == NULL); |
1335 output_[frame_index] = output_frame; | 1335 output_[frame_index] = output_frame; |
1336 | 1336 |
1337 // The top address of the frame is computed from the previous | 1337 // The top address of the frame is computed from the previous frame's top and |
1338 // frame's top and this frame's size. | 1338 // this frame's size. |
1339 intptr_t top_address; | 1339 intptr_t top_address; |
1340 if (is_bottommost) { | 1340 if (is_bottommost) { |
1341 top_address = caller_frame_top_ - output_frame_size; | 1341 top_address = caller_frame_top_ - output_frame_size; |
1342 } else { | 1342 } else { |
1343 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; | 1343 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; |
1344 } | 1344 } |
1345 output_frame->SetTop(top_address); | 1345 output_frame->SetTop(top_address); |
1346 | 1346 |
1347 // Compute the incoming parameter translation. | 1347 // Compute the incoming parameter translation. |
1348 unsigned output_offset = output_frame_size; | 1348 unsigned output_offset = output_frame_size; |
(...skipping 129 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1478 | 1478 |
1479 if (trace_scope_ != NULL) { | 1479 if (trace_scope_ != NULL) { |
1480 PrintF(trace_scope_->file(), | 1480 PrintF(trace_scope_->file(), |
1481 " dropping caller arguments adaptor frame: offset=%d, " | 1481 " dropping caller arguments adaptor frame: offset=%d, " |
1482 "fp: 0x%08" V8PRIxPTR " -> 0x%08" V8PRIxPTR | 1482 "fp: 0x%08" V8PRIxPTR " -> 0x%08" V8PRIxPTR |
1483 ", " | 1483 ", " |
1484 "caller sp: 0x%08" V8PRIxPTR " -> 0x%08" V8PRIxPTR "\n", | 1484 "caller sp: 0x%08" V8PRIxPTR " -> 0x%08" V8PRIxPTR "\n", |
1485 offset, stack_fp_, new_stack_fp, caller_frame_top_, | 1485 offset, stack_fp_, new_stack_fp, caller_frame_top_, |
1486 new_caller_frame_top); | 1486 new_caller_frame_top); |
1487 } | 1487 } |
1488 stack_fp_ = new_stack_fp; | |
1489 caller_frame_top_ = new_caller_frame_top; | 1488 caller_frame_top_ = new_caller_frame_top; |
1490 caller_fp_ = adaptor_caller_fp; | 1489 caller_fp_ = adaptor_caller_fp; |
1491 caller_pc_ = adaptor_caller_pc; | 1490 caller_pc_ = adaptor_caller_pc; |
1492 } | 1491 } |
1493 | 1492 |
1494 void Deoptimizer::DoComputeConstructStubFrame(TranslatedFrame* translated_frame, | 1493 void Deoptimizer::DoComputeConstructStubFrame(TranslatedFrame* translated_frame, |
1495 int frame_index) { | 1494 int frame_index) { |
1496 TranslatedFrame::iterator value_iterator = translated_frame->begin(); | 1495 TranslatedFrame::iterator value_iterator = translated_frame->begin(); |
1497 int input_index = 0; | 1496 int input_index = 0; |
1498 | 1497 |
(...skipping 15 matching lines...) Expand all Loading... |
1514 // Allocate and store the output frame description. | 1513 // Allocate and store the output frame description. |
1515 FrameDescription* output_frame = | 1514 FrameDescription* output_frame = |
1516 new (output_frame_size) FrameDescription(output_frame_size); | 1515 new (output_frame_size) FrameDescription(output_frame_size); |
1517 output_frame->SetFrameType(StackFrame::CONSTRUCT); | 1516 output_frame->SetFrameType(StackFrame::CONSTRUCT); |
1518 | 1517 |
1519 // Construct stub can not be topmost or bottommost. | 1518 // Construct stub can not be topmost or bottommost. |
1520 DCHECK(frame_index > 0 && frame_index < output_count_ - 1); | 1519 DCHECK(frame_index > 0 && frame_index < output_count_ - 1); |
1521 DCHECK(output_[frame_index] == NULL); | 1520 DCHECK(output_[frame_index] == NULL); |
1522 output_[frame_index] = output_frame; | 1521 output_[frame_index] = output_frame; |
1523 | 1522 |
1524 // The top address of the frame is computed from the previous | 1523 // The top address of the frame is computed from the previous frame's top and |
1525 // frame's top and this frame's size. | 1524 // this frame's size. |
1526 intptr_t top_address; | 1525 intptr_t top_address; |
1527 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; | 1526 top_address = output_[frame_index - 1]->GetTop() - output_frame_size; |
1528 output_frame->SetTop(top_address); | 1527 output_frame->SetTop(top_address); |
1529 | 1528 |
1530 // Compute the incoming parameter translation. | 1529 // Compute the incoming parameter translation. |
1531 int parameter_count = height; | 1530 int parameter_count = height; |
1532 unsigned output_offset = output_frame_size; | 1531 unsigned output_offset = output_frame_size; |
1533 for (int i = 0; i < parameter_count; ++i) { | 1532 for (int i = 0; i < parameter_count; ++i) { |
1534 output_offset -= kPointerSize; | 1533 output_offset -= kPointerSize; |
1535 // The allocated receiver of a construct stub frame is passed as the | 1534 // The allocated receiver of a construct stub frame is passed as the |
(...skipping 264 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
1800 height_in_bytes); | 1799 height_in_bytes); |
1801 } | 1800 } |
1802 | 1801 |
1803 // The stub failure trampoline is a single frame. | 1802 // The stub failure trampoline is a single frame. |
1804 FrameDescription* output_frame = | 1803 FrameDescription* output_frame = |
1805 new (output_frame_size) FrameDescription(output_frame_size); | 1804 new (output_frame_size) FrameDescription(output_frame_size); |
1806 output_frame->SetFrameType(StackFrame::STUB_FAILURE_TRAMPOLINE); | 1805 output_frame->SetFrameType(StackFrame::STUB_FAILURE_TRAMPOLINE); |
1807 CHECK_EQ(frame_index, 0); | 1806 CHECK_EQ(frame_index, 0); |
1808 output_[frame_index] = output_frame; | 1807 output_[frame_index] = output_frame; |
1809 | 1808 |
1810 // The top address for the output frame can be computed from the input | 1809 // The top address of the frame is computed from the previous frame's top and |
1811 // frame pointer and the output frame's height. Subtract space for the | 1810 // this frame's size. |
1812 // context and function slots. | 1811 intptr_t top_address = caller_frame_top_ - output_frame_size; |
1813 Register fp_reg = StubFailureTrampolineFrame::fp_register(); | |
1814 intptr_t top_address = | |
1815 stack_fp_ - StubFailureTrampolineFrameConstants::kFixedFrameSizeFromFp - | |
1816 height_in_bytes; | |
1817 output_frame->SetTop(top_address); | 1812 output_frame->SetTop(top_address); |
1818 | 1813 |
1819 // Set caller's PC (JSFunction continuation). | 1814 // Set caller's PC (JSFunction continuation). |
1820 unsigned output_frame_offset = output_frame_size - kFPOnStackSize; | 1815 unsigned output_frame_offset = output_frame_size - kFPOnStackSize; |
1821 intptr_t value = caller_pc_; | 1816 intptr_t value = caller_pc_; |
1822 output_frame->SetCallerPc(output_frame_offset, value); | 1817 output_frame->SetCallerPc(output_frame_offset, value); |
1823 DebugPrintOutputSlot(value, frame_index, output_frame_offset, | 1818 DebugPrintOutputSlot(value, frame_index, output_frame_offset, |
1824 "caller's pc\n"); | 1819 "caller's pc\n"); |
1825 | 1820 |
1826 // Read caller's FP from the input frame, and set this frame's FP. | 1821 // Read caller's FP from the input frame, and set this frame's FP. |
1827 value = caller_fp_; | 1822 value = caller_fp_; |
1828 output_frame_offset -= kFPOnStackSize; | 1823 output_frame_offset -= kFPOnStackSize; |
1829 output_frame->SetCallerFp(output_frame_offset, value); | 1824 output_frame->SetCallerFp(output_frame_offset, value); |
1830 intptr_t frame_ptr = stack_fp_; | 1825 intptr_t frame_ptr = top_address + output_frame_offset; |
| 1826 Register fp_reg = StubFailureTrampolineFrame::fp_register(); |
1831 output_frame->SetRegister(fp_reg.code(), frame_ptr); | 1827 output_frame->SetRegister(fp_reg.code(), frame_ptr); |
1832 output_frame->SetFp(frame_ptr); | 1828 output_frame->SetFp(frame_ptr); |
1833 DebugPrintOutputSlot(value, frame_index, output_frame_offset, | 1829 DebugPrintOutputSlot(value, frame_index, output_frame_offset, |
1834 "caller's fp\n"); | 1830 "caller's fp\n"); |
1835 | 1831 |
1836 if (FLAG_enable_embedded_constant_pool) { | 1832 if (FLAG_enable_embedded_constant_pool) { |
1837 // Read the caller's constant pool from the input frame. | 1833 // Read the caller's constant pool from the input frame. |
1838 value = caller_constant_pool_; | 1834 value = caller_constant_pool_; |
1839 output_frame_offset -= kPointerSize; | 1835 output_frame_offset -= kPointerSize; |
1840 output_frame->SetCallerConstantPool(output_frame_offset, value); | 1836 output_frame->SetCallerConstantPool(output_frame_offset, value); |
(...skipping 1973 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
3814 CHECK(value_info->IsMaterializedObject()); | 3810 CHECK(value_info->IsMaterializedObject()); |
3815 | 3811 |
3816 value_info->value_ = | 3812 value_info->value_ = |
3817 Handle<Object>(previously_materialized_objects->get(i), isolate_); | 3813 Handle<Object>(previously_materialized_objects->get(i), isolate_); |
3818 } | 3814 } |
3819 } | 3815 } |
3820 } | 3816 } |
3821 | 3817 |
3822 } // namespace internal | 3818 } // namespace internal |
3823 } // namespace v8 | 3819 } // namespace v8 |
OLD | NEW |