Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(146)

Side by Side Diff: src/deoptimizer.h

Issue 1210413005: Revert of Unify reading of deoptimization information. (Closed) Base URL: https://chromium.googlesource.com/v8/v8.git@master
Patch Set: Created 5 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « src/arm64/lithium-codegen-arm64.cc ('k') | src/deoptimizer.cc » ('j') | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2012 the V8 project authors. All rights reserved. 1 // Copyright 2012 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 #ifndef V8_DEOPTIMIZER_H_ 5 #ifndef V8_DEOPTIMIZER_H_
6 #define V8_DEOPTIMIZER_H_ 6 #define V8_DEOPTIMIZER_H_
7 7
8 #include "src/v8.h" 8 #include "src/v8.h"
9 9
10 #include "src/allocation.h" 10 #include "src/allocation.h"
11 #include "src/macro-assembler.h" 11 #include "src/macro-assembler.h"
12 12
13 13
14 namespace v8 { 14 namespace v8 {
15 namespace internal { 15 namespace internal {
16 16
17
18 static inline double read_double_value(Address p) {
19 double d;
20 memcpy(&d, p, sizeof(d));
21 return d;
22 }
23
24
17 class FrameDescription; 25 class FrameDescription;
18 class TranslationIterator; 26 class TranslationIterator;
19 class DeoptimizedFrameInfo; 27 class DeoptimizedFrameInfo;
20 class TranslatedState;
21 class RegisterValues;
22
23 class TranslatedValue BASE_EMBEDDED {
24 public:
25 // Allocation-less getter of the value.
26 // Returns heap()->arguments_marker() if allocation would be
27 // necessary to get the value.
28 Object* GetRawValue() const;
29 Handle<Object> GetValue();
30
31 bool IsMaterializedObject() const;
32
33 private:
34 friend class TranslatedState;
35 friend class TranslatedFrame;
36
37 enum Kind {
38 kInvalid,
39 kTagged,
40 kInt32,
41 kUInt32,
42 kBoolBit,
43 kDouble,
44 kCapturedObject, // Object captured by the escape analysis.
45 // The number of nested objects can be obtained
46 // with the DeferredObjectLength() method
47 // (the values of the nested objects follow
48 // this value in the depth-first order.)
49 kDuplicatedObject, // Duplicated object of a deferred object.
50 kArgumentsObject // Arguments object - only used to keep indexing
51 // in sync, it should not be materialized.
52 };
53
54 TranslatedValue(TranslatedState* container, Kind kind)
55 : kind_(kind), container_(container) {}
56 Kind kind() const { return kind_; }
57 void Handlify();
58 int GetChildrenCount() const;
59
60 static TranslatedValue NewArgumentsObject(TranslatedState* container,
61 int length, int object_index);
62 static TranslatedValue NewDeferredObject(TranslatedState* container,
63 int length, int object_index);
64 static TranslatedValue NewDuplicateObject(TranslatedState* container, int id);
65 static TranslatedValue NewDouble(TranslatedState* container, double value);
66 static TranslatedValue NewInt32(TranslatedState* container, int32_t value);
67 static TranslatedValue NewUInt32(TranslatedState* container, uint32_t value);
68 static TranslatedValue NewBool(TranslatedState* container, uint32_t value);
69 static TranslatedValue NewTagged(TranslatedState* container, Object* literal);
70 static TranslatedValue NewInvalid();
71
72 Isolate* isolate() const;
73 void MaterializeSimple();
74
75 Kind kind_;
76 TranslatedState* container_; // This is only needed for materialization of
77 // objects and constructing handles (to get
78 // to the isolate).
79
80 MaybeHandle<Object> value_; // Before handlification, this is always null,
81 // after materialization it is never null,
82 // in between it is only null if the value needs
83 // to be materialized.
84
85 struct MaterializedObjectInfo {
86 int id_;
87 int length_; // Applies only to kArgumentsObject or kCapturedObject kinds.
88 };
89
90 union {
91 // kind kTagged. After handlification it is always nullptr.
92 Object* raw_literal_;
93 // kind is kUInt32 or kBoolBit.
94 uint32_t uint32_value_;
95 // kind is kInt32.
96 int32_t int32_value_;
97 // kind is kDouble
98 double double_value_;
99 // kind is kDuplicatedObject or kArgumentsObject or kCapturedObject.
100 MaterializedObjectInfo materialization_info_;
101 };
102
103 // Checked accessors for the union members.
104 Object* raw_literal() const;
105 int32_t int32_value() const;
106 uint32_t uint32_value() const;
107 double double_value() const;
108 int object_length() const;
109 int object_index() const;
110 };
111
112
113 class TranslatedFrame {
114 public:
115 enum Kind {
116 kFunction,
117 kGetter,
118 kSetter,
119 kArgumentsAdaptor,
120 kConstructStub,
121 kCompiledStub,
122 kInvalid
123 };
124
125 int GetValueCount();
126
127 Kind kind() const { return kind_; }
128 BailoutId node_id() { return node_id_; }
129 JSFunction* raw_function() { return raw_function_; }
130 Handle<JSFunction> function() { return function_; }
131 int height() { return height_; }
132
133 class iterator {
134 public:
135 iterator& operator++() {
136 AdvanceIterator(&position_);
137 return *this;
138 }
139
140 iterator operator++(int) {
141 iterator original(position_);
142 AdvanceIterator(&position_);
143 return original;
144 }
145
146 bool operator==(const iterator& other) const {
147 return position_ == other.position_;
148 }
149 bool operator!=(const iterator& other) const { return !(*this == other); }
150
151 TranslatedValue& operator*() { return (*position_); }
152 TranslatedValue* operator->() { return &(*position_); }
153
154 private:
155 friend TranslatedFrame;
156
157 explicit iterator(std::deque<TranslatedValue>::iterator position)
158 : position_(position) {}
159
160 std::deque<TranslatedValue>::iterator position_;
161 };
162
163 iterator begin() { return iterator(values_.begin()); }
164 iterator end() { return iterator(values_.end()); }
165
166 private:
167 friend class TranslatedState;
168
169 // Constructor static methods.
170 static TranslatedFrame JSFrame(BailoutId node_id, JSFunction* function,
171 int height);
172 static TranslatedFrame AccessorFrame(Kind kind, JSFunction* function);
173 static TranslatedFrame ArgumentsAdaptorFrame(JSFunction* function,
174 int height);
175 static TranslatedFrame ConstructStubFrame(JSFunction* function, int height);
176 static TranslatedFrame CompiledStubFrame(int height, Isolate* isolate) {
177 return TranslatedFrame(kCompiledStub, isolate, nullptr, height);
178 }
179 static TranslatedFrame InvalidFrame() {
180 return TranslatedFrame(kInvalid, nullptr);
181 }
182
183 static void AdvanceIterator(std::deque<TranslatedValue>::iterator* iter);
184
185 TranslatedFrame(Kind kind, Isolate* isolate, JSFunction* function = nullptr,
186 int height = 0)
187 : kind_(kind),
188 node_id_(BailoutId::None()),
189 raw_function_(function),
190 height_(height),
191 isolate_(isolate) {}
192
193
194 void Add(const TranslatedValue& value) { values_.push_back(value); }
195 void Handlify(Isolate* isolate);
196
197 Kind kind_;
198 BailoutId node_id_;
199 JSFunction* raw_function_;
200 Handle<JSFunction> function_;
201 int height_;
202 Isolate* isolate_;
203
204 typedef std::deque<TranslatedValue> ValuesContainer;
205
206 ValuesContainer values_;
207 };
208
209
210 // Auxiliary class for translating deoptimization values.
211 // Typical usage sequence:
212 //
213 // 1. Construct the instance. This will involve reading out the translations
214 // and resolving them to values using the supplied frame pointer and
215 // machine state (registers). This phase is guaranteed not to allocate
216 // and not to use any HandleScope. Any object pointers will be stored raw.
217 //
218 // 2. Handlify pointers. This will convert all the raw pointers to handles.
219 //
220 // 3. Reading out the frame values.
221 //
222 // Note: After the instance is constructed, it is possible to iterate over
223 // the values eagerly.
224
225 class TranslatedState {
226 public:
227 TranslatedState();
228 explicit TranslatedState(JavaScriptFrame* frame);
229
230 void Prepare(bool has_adapted_arguments, Address stack_frame_pointer);
231
232 // Store newly materialized values into the isolate.
233 void StoreMaterializedValuesAndDeopt();
234
235 std::vector<TranslatedFrame>& frames() { return frames_; }
236
237 TranslatedFrame* GetArgumentsInfoFromJSFrameIndex(int jsframe_index,
238 int* arguments_count);
239
240 Isolate* isolate() { return isolate_; }
241
242 void Init(Address input_frame_pointer, JSFunction* input_frame_function,
243 TranslationIterator* iterator, FixedArray* literal_array,
244 RegisterValues* registers, FILE* trace_file);
245
246 private:
247 friend TranslatedValue;
248
249 TranslatedFrame CreateNextTranslatedFrame(TranslationIterator* iterator,
250 FixedArray* literal_array,
251 Address fp,
252 JSFunction* frame_function,
253 FILE* trace_file);
254 TranslatedValue CreateNextTranslatedValue(int frame_index, int value_index,
255 TranslationIterator* iterator,
256 FixedArray* literal_array,
257 Address fp,
258 RegisterValues* registers,
259 FILE* trace_file);
260
261 void UpdateFromPreviouslyMaterializedObjects();
262 Handle<Object> MaterializeAt(int frame_index, int* value_index);
263 Handle<Object> MaterializeObjectAt(int object_index);
264 bool GetAdaptedArguments(Handle<JSObject>* result, int frame_index);
265
266 static int SlotOffsetFp(int slot_index);
267 static Address SlotAddress(Address fp, int slot_index);
268 static uint32_t GetUInt32Slot(Address fp, int slot_index);
269
270 std::vector<TranslatedFrame> frames_;
271 Isolate* isolate_;
272 Address stack_frame_pointer_;
273 bool has_adapted_arguments_;
274
275 struct ObjectPosition {
276 int frame_index_;
277 int value_index_;
278 };
279 std::deque<ObjectPosition> object_positions_;
280 };
281 28
282 template<typename T> 29 template<typename T>
283 class HeapNumberMaterializationDescriptor BASE_EMBEDDED { 30 class HeapNumberMaterializationDescriptor BASE_EMBEDDED {
284 public: 31 public:
285 HeapNumberMaterializationDescriptor(T destination, double value) 32 HeapNumberMaterializationDescriptor(T destination, double value)
286 : destination_(destination), value_(value) { } 33 : destination_(destination), value_(value) { }
287 34
288 T destination() const { return destination_; } 35 T destination() const { return destination_; }
289 double value() const { return value_; } 36 double value() const { return value_; }
290 37
(...skipping 235 matching lines...) Expand 10 before | Expand all | Expand 10 after
526 Isolate* isolate, OptimizedFunctionVisitor* visitor); 273 Isolate* isolate, OptimizedFunctionVisitor* visitor);
527 274
528 // The size in bytes of the code required at a lazy deopt patch site. 275 // The size in bytes of the code required at a lazy deopt patch site.
529 static int patch_size(); 276 static int patch_size();
530 277
531 ~Deoptimizer(); 278 ~Deoptimizer();
532 279
533 void MaterializeHeapObjects(JavaScriptFrameIterator* it); 280 void MaterializeHeapObjects(JavaScriptFrameIterator* it);
534 281
535 void MaterializeHeapNumbersForDebuggerInspectableFrame( 282 void MaterializeHeapNumbersForDebuggerInspectableFrame(
536 int frame_index, int parameter_count, int expression_count, 283 Address parameters_top,
284 uint32_t parameters_size,
285 Address expressions_top,
286 uint32_t expressions_size,
537 DeoptimizedFrameInfo* info); 287 DeoptimizedFrameInfo* info);
538 288
539 static void ComputeOutputFrames(Deoptimizer* deoptimizer); 289 static void ComputeOutputFrames(Deoptimizer* deoptimizer);
540 290
541 291
542 enum GetEntryMode { 292 enum GetEntryMode {
543 CALCULATE_ENTRY_ADDRESS, 293 CALCULATE_ENTRY_ADDRESS,
544 ENSURE_ENTRY_CODE 294 ENSURE_ENTRY_CODE
545 }; 295 };
546 296
(...skipping 78 matching lines...) Expand 10 before | Expand all | Expand 10 after
625 void DoComputeArgumentsAdaptorFrame(TranslationIterator* iterator, 375 void DoComputeArgumentsAdaptorFrame(TranslationIterator* iterator,
626 int frame_index); 376 int frame_index);
627 void DoComputeConstructStubFrame(TranslationIterator* iterator, 377 void DoComputeConstructStubFrame(TranslationIterator* iterator,
628 int frame_index); 378 int frame_index);
629 void DoComputeAccessorStubFrame(TranslationIterator* iterator, 379 void DoComputeAccessorStubFrame(TranslationIterator* iterator,
630 int frame_index, 380 int frame_index,
631 bool is_setter_stub_frame); 381 bool is_setter_stub_frame);
632 void DoComputeCompiledStubFrame(TranslationIterator* iterator, 382 void DoComputeCompiledStubFrame(TranslationIterator* iterator,
633 int frame_index); 383 int frame_index);
634 384
635 void WriteValueToOutput(TranslatedFrame::iterator* iterator, int* input_index, 385 // Translate object, store the result into an auxiliary array
636 int frame_index, unsigned output_offset, 386 // (deferred_objects_tagged_values_).
637 Address output_address_for_materialization = nullptr); 387 void DoTranslateObject(TranslationIterator* iterator,
388 int object_index,
389 int field_index);
390
391 // Translate value, store the result into the given frame slot.
392 void DoTranslateCommand(TranslationIterator* iterator,
393 int frame_index,
394 unsigned output_offset);
395
396 // Translate object, do not store the result anywhere (but do update
397 // the deferred materialization array).
398 void DoTranslateObjectAndSkip(TranslationIterator* iterator);
638 399
639 unsigned ComputeInputFrameSize() const; 400 unsigned ComputeInputFrameSize() const;
640 unsigned ComputeFixedSize(JSFunction* function) const; 401 unsigned ComputeFixedSize(JSFunction* function) const;
641 402
642 unsigned ComputeIncomingArgumentSize(JSFunction* function) const; 403 unsigned ComputeIncomingArgumentSize(JSFunction* function) const;
643 unsigned ComputeOutgoingArgumentSize() const; 404 unsigned ComputeOutgoingArgumentSize() const;
644 405
645 Object* ComputeLiteral(int index) const; 406 Object* ComputeLiteral(int index) const;
646 407
408 void AddObjectStart(intptr_t slot_address, int argc, bool is_arguments);
409 void AddObjectDuplication(intptr_t slot, int object_index);
410 void AddObjectTaggedValue(intptr_t value);
411 void AddObjectDoubleValue(double value);
412 void AddDoubleValue(intptr_t slot_address, double value);
413
414 bool ArgumentsObjectIsAdapted(int object_index) {
415 ObjectMaterializationDescriptor desc = deferred_objects_.at(object_index);
416 int reverse_jsframe_index = jsframe_count_ - desc.jsframe_index() - 1;
417 return jsframe_has_adapted_arguments_[reverse_jsframe_index];
418 }
419
420 Handle<JSFunction> ArgumentsObjectFunction(int object_index) {
421 ObjectMaterializationDescriptor desc = deferred_objects_.at(object_index);
422 int reverse_jsframe_index = jsframe_count_ - desc.jsframe_index() - 1;
423 return jsframe_functions_[reverse_jsframe_index];
424 }
425
426 // Helper function for heap object materialization.
427 Handle<Object> MaterializeNextHeapObject();
428 Handle<Object> MaterializeNextValue();
429
647 static void GenerateDeoptimizationEntries( 430 static void GenerateDeoptimizationEntries(
648 MacroAssembler* masm, int count, BailoutType type); 431 MacroAssembler* masm, int count, BailoutType type);
649 432
650 // Marks all the code in the given context for deoptimization. 433 // Marks all the code in the given context for deoptimization.
651 static void MarkAllCodeForContext(Context* native_context); 434 static void MarkAllCodeForContext(Context* native_context);
652 435
653 // Visit all the known optimized functions in a given context. 436 // Visit all the known optimized functions in a given context.
654 static void VisitAllOptimizedFunctionsForContext( 437 static void VisitAllOptimizedFunctionsForContext(
655 Context* context, OptimizedFunctionVisitor* visitor); 438 Context* context, OptimizedFunctionVisitor* visitor);
656 439
(...skipping 37 matching lines...) Expand 10 before | Expand all | Expand 10 after
694 477
695 // Input frame description. 478 // Input frame description.
696 FrameDescription* input_; 479 FrameDescription* input_;
697 // Number of output frames. 480 // Number of output frames.
698 int output_count_; 481 int output_count_;
699 // Number of output js frames. 482 // Number of output js frames.
700 int jsframe_count_; 483 int jsframe_count_;
701 // Array of output frame descriptions. 484 // Array of output frame descriptions.
702 FrameDescription** output_; 485 FrameDescription** output_;
703 486
487 // Deferred values to be materialized.
488 List<Object*> deferred_objects_tagged_values_;
489 List<HeapNumberMaterializationDescriptor<int> >
490 deferred_objects_double_values_;
491 List<ObjectMaterializationDescriptor> deferred_objects_;
492 List<HeapNumberMaterializationDescriptor<Address> > deferred_heap_numbers_;
493
704 // Key for lookup of previously materialized objects 494 // Key for lookup of previously materialized objects
705 Address stack_fp_; 495 Address stack_fp_;
496 Handle<FixedArray> previously_materialized_objects_;
497 int prev_materialized_count_;
706 498
707 TranslatedState translated_state_; 499 // Output frame information. Only used during heap object materialization.
708 struct ValueToMaterialize { 500 List<Handle<JSFunction> > jsframe_functions_;
709 Address output_slot_address_; 501 List<bool> jsframe_has_adapted_arguments_;
710 TranslatedFrame::iterator value_; 502
711 }; 503 // Materialized objects. Only used during heap object materialization.
712 std::vector<ValueToMaterialize> values_to_materialize_; 504 List<Handle<Object> >* materialized_values_;
505 List<Handle<Object> >* materialized_objects_;
506 int materialization_value_index_;
507 int materialization_object_index_;
713 508
714 #ifdef DEBUG 509 #ifdef DEBUG
715 DisallowHeapAllocation* disallow_heap_allocation_; 510 DisallowHeapAllocation* disallow_heap_allocation_;
716 #endif // DEBUG 511 #endif // DEBUG
717 512
718 CodeTracer::Scope* trace_scope_; 513 CodeTracer::Scope* trace_scope_;
719 514
720 static const int table_entry_size_; 515 static const int table_entry_size_;
721 516
722 friend class FrameDescription; 517 friend class FrameDescription;
723 friend class DeoptimizedFrameInfo; 518 friend class DeoptimizedFrameInfo;
724 }; 519 };
725 520
726 521
727 class RegisterValues { 522 class FrameDescription {
728 public: 523 public:
524 FrameDescription(uint32_t frame_size,
525 JSFunction* function);
526
527 void* operator new(size_t size, uint32_t frame_size) {
528 // Subtracts kPointerSize, as the member frame_content_ already supplies
529 // the first element of the area to store the frame.
530 return malloc(size + frame_size - kPointerSize);
531 }
532
533 // Bug in VS2015 RC, reported fixed in RTM. Microsoft bug: 1153909.
534 #if !defined(_MSC_FULL_VER) || _MSC_FULL_VER != 190022816
535 void operator delete(void* pointer, uint32_t frame_size) {
536 free(pointer);
537 }
538 #endif // _MSC_FULL_VER
539
540 void operator delete(void* description) {
541 free(description);
542 }
543
544 uint32_t GetFrameSize() const {
545 DCHECK(static_cast<uint32_t>(frame_size_) == frame_size_);
546 return static_cast<uint32_t>(frame_size_);
547 }
548
549 JSFunction* GetFunction() const { return function_; }
550
551 unsigned GetOffsetFromSlotIndex(int slot_index);
552
553 intptr_t GetFrameSlot(unsigned offset) {
554 return *GetFrameSlotPointer(offset);
555 }
556
557 double GetDoubleFrameSlot(unsigned offset) {
558 intptr_t* ptr = GetFrameSlotPointer(offset);
559 return read_double_value(reinterpret_cast<Address>(ptr));
560 }
561
562 void SetFrameSlot(unsigned offset, intptr_t value) {
563 *GetFrameSlotPointer(offset) = value;
564 }
565
566 void SetCallerPc(unsigned offset, intptr_t value);
567
568 void SetCallerFp(unsigned offset, intptr_t value);
569
570 void SetCallerConstantPool(unsigned offset, intptr_t value);
571
729 intptr_t GetRegister(unsigned n) const { 572 intptr_t GetRegister(unsigned n) const {
730 #if DEBUG 573 #if DEBUG
731 // This convoluted DCHECK is needed to work around a gcc problem that 574 // This convoluted DCHECK is needed to work around a gcc problem that
732 // improperly detects an array bounds overflow in optimized debug builds 575 // improperly detects an array bounds overflow in optimized debug builds
733 // when using a plain DCHECK. 576 // when using a plain DCHECK.
734 if (n >= arraysize(registers_)) { 577 if (n >= arraysize(registers_)) {
735 DCHECK(false); 578 DCHECK(false);
736 return 0; 579 return 0;
737 } 580 }
738 #endif 581 #endif
739 return registers_[n]; 582 return registers_[n];
740 } 583 }
741 584
742 double GetDoubleRegister(unsigned n) const { 585 double GetDoubleRegister(unsigned n) const {
743 DCHECK(n < arraysize(double_registers_)); 586 DCHECK(n < arraysize(double_registers_));
744 return double_registers_[n]; 587 return double_registers_[n];
745 } 588 }
746 589
747 void SetRegister(unsigned n, intptr_t value) { 590 void SetRegister(unsigned n, intptr_t value) {
748 DCHECK(n < arraysize(registers_)); 591 DCHECK(n < arraysize(registers_));
749 registers_[n] = value; 592 registers_[n] = value;
750 } 593 }
751 594
752 void SetDoubleRegister(unsigned n, double value) { 595 void SetDoubleRegister(unsigned n, double value) {
753 DCHECK(n < arraysize(double_registers_)); 596 DCHECK(n < arraysize(double_registers_));
754 double_registers_[n] = value; 597 double_registers_[n] = value;
755 } 598 }
756 599
757 intptr_t registers_[Register::kNumRegisters];
758 double double_registers_[DoubleRegister::kMaxNumRegisters];
759 };
760
761
762 class FrameDescription {
763 public:
764 FrameDescription(uint32_t frame_size,
765 JSFunction* function);
766
767 void* operator new(size_t size, uint32_t frame_size) {
768 // Subtracts kPointerSize, as the member frame_content_ already supplies
769 // the first element of the area to store the frame.
770 return malloc(size + frame_size - kPointerSize);
771 }
772
773 // Bug in VS2015 RC, reported fixed in RTM. Microsoft bug: 1153909.
774 #if !defined(_MSC_FULL_VER) || _MSC_FULL_VER != 190022816
775 void operator delete(void* pointer, uint32_t frame_size) {
776 free(pointer);
777 }
778 #endif // _MSC_FULL_VER
779
780 void operator delete(void* description) {
781 free(description);
782 }
783
784 uint32_t GetFrameSize() const {
785 DCHECK(static_cast<uint32_t>(frame_size_) == frame_size_);
786 return static_cast<uint32_t>(frame_size_);
787 }
788
789 JSFunction* GetFunction() const { return function_; }
790
791 unsigned GetOffsetFromSlotIndex(int slot_index);
792
793 intptr_t GetFrameSlot(unsigned offset) {
794 return *GetFrameSlotPointer(offset);
795 }
796
797 Address GetFramePointerAddress() {
798 int fp_offset = GetFrameSize() -
799 (ComputeParametersCount() + 1) * kPointerSize -
800 StandardFrameConstants::kCallerSPOffset;
801 return reinterpret_cast<Address>(GetFrameSlotPointer(fp_offset));
802 }
803
804 RegisterValues* GetRegisterValues() { return &register_values_; }
805
806 void SetFrameSlot(unsigned offset, intptr_t value) {
807 *GetFrameSlotPointer(offset) = value;
808 }
809
810 void SetCallerPc(unsigned offset, intptr_t value);
811
812 void SetCallerFp(unsigned offset, intptr_t value);
813
814 void SetCallerConstantPool(unsigned offset, intptr_t value);
815
816 intptr_t GetRegister(unsigned n) const {
817 return register_values_.GetRegister(n);
818 }
819
820 double GetDoubleRegister(unsigned n) const {
821 return register_values_.GetDoubleRegister(n);
822 }
823
824 void SetRegister(unsigned n, intptr_t value) {
825 register_values_.SetRegister(n, value);
826 }
827
828 void SetDoubleRegister(unsigned n, double value) {
829 register_values_.SetDoubleRegister(n, value);
830 }
831
832 intptr_t GetTop() const { return top_; } 600 intptr_t GetTop() const { return top_; }
833 void SetTop(intptr_t top) { top_ = top; } 601 void SetTop(intptr_t top) { top_ = top; }
834 602
835 intptr_t GetPc() const { return pc_; } 603 intptr_t GetPc() const { return pc_; }
836 void SetPc(intptr_t pc) { pc_ = pc; } 604 void SetPc(intptr_t pc) { pc_ = pc; }
837 605
838 intptr_t GetFp() const { return fp_; } 606 intptr_t GetFp() const { return fp_; }
839 void SetFp(intptr_t fp) { fp_ = fp; } 607 void SetFp(intptr_t fp) { fp_ = fp; }
840 608
841 intptr_t GetContext() const { return context_; } 609 intptr_t GetContext() const { return context_; }
(...skipping 18 matching lines...) Expand all
860 // Get a parameter value for an unoptimized frame. 628 // Get a parameter value for an unoptimized frame.
861 Object* GetParameter(int index); 629 Object* GetParameter(int index);
862 630
863 // Get the expression stack height for a unoptimized frame. 631 // Get the expression stack height for a unoptimized frame.
864 unsigned GetExpressionCount(); 632 unsigned GetExpressionCount();
865 633
866 // Get the expression stack value for an unoptimized frame. 634 // Get the expression stack value for an unoptimized frame.
867 Object* GetExpression(int index); 635 Object* GetExpression(int index);
868 636
869 static int registers_offset() { 637 static int registers_offset() {
870 return OFFSET_OF(FrameDescription, register_values_.registers_); 638 return OFFSET_OF(FrameDescription, registers_);
871 } 639 }
872 640
873 static int double_registers_offset() { 641 static int double_registers_offset() {
874 return OFFSET_OF(FrameDescription, register_values_.double_registers_); 642 return OFFSET_OF(FrameDescription, double_registers_);
875 } 643 }
876 644
877 static int frame_size_offset() { 645 static int frame_size_offset() {
878 return OFFSET_OF(FrameDescription, frame_size_); 646 return OFFSET_OF(FrameDescription, frame_size_);
879 } 647 }
880 648
881 static int pc_offset() { 649 static int pc_offset() {
882 return OFFSET_OF(FrameDescription, pc_); 650 return OFFSET_OF(FrameDescription, pc_);
883 } 651 }
884 652
(...skipping 10 matching lines...) Expand all
895 } 663 }
896 664
897 private: 665 private:
898 static const uint32_t kZapUint32 = 0xbeeddead; 666 static const uint32_t kZapUint32 = 0xbeeddead;
899 667
900 // Frame_size_ must hold a uint32_t value. It is only a uintptr_t to 668 // Frame_size_ must hold a uint32_t value. It is only a uintptr_t to
901 // keep the variable-size array frame_content_ of type intptr_t at 669 // keep the variable-size array frame_content_ of type intptr_t at
902 // the end of the structure aligned. 670 // the end of the structure aligned.
903 uintptr_t frame_size_; // Number of bytes. 671 uintptr_t frame_size_; // Number of bytes.
904 JSFunction* function_; 672 JSFunction* function_;
905 RegisterValues register_values_; 673 intptr_t registers_[Register::kNumRegisters];
674 double double_registers_[DoubleRegister::kMaxNumRegisters];
906 intptr_t top_; 675 intptr_t top_;
907 intptr_t pc_; 676 intptr_t pc_;
908 intptr_t fp_; 677 intptr_t fp_;
909 intptr_t context_; 678 intptr_t context_;
910 intptr_t constant_pool_; 679 intptr_t constant_pool_;
911 StackFrame::Type type_; 680 StackFrame::Type type_;
912 Smi* state_; 681 Smi* state_;
913 682
914 // Continuation is the PC where the execution continues after 683 // Continuation is the PC where the execution continues after
915 // deoptimizing. 684 // deoptimizing.
(...skipping 110 matching lines...) Expand 10 before | Expand all | Expand 10 after
1026 zone_(zone) { 795 zone_(zone) {
1027 buffer_->Add(BEGIN, zone); 796 buffer_->Add(BEGIN, zone);
1028 buffer_->Add(frame_count, zone); 797 buffer_->Add(frame_count, zone);
1029 buffer_->Add(jsframe_count, zone); 798 buffer_->Add(jsframe_count, zone);
1030 } 799 }
1031 800
1032 int index() const { return index_; } 801 int index() const { return index_; }
1033 802
1034 // Commands. 803 // Commands.
1035 void BeginJSFrame(BailoutId node_id, int literal_id, unsigned height); 804 void BeginJSFrame(BailoutId node_id, int literal_id, unsigned height);
1036 void BeginCompiledStubFrame(int height); 805 void BeginCompiledStubFrame();
1037 void BeginArgumentsAdaptorFrame(int literal_id, unsigned height); 806 void BeginArgumentsAdaptorFrame(int literal_id, unsigned height);
1038 void BeginConstructStubFrame(int literal_id, unsigned height); 807 void BeginConstructStubFrame(int literal_id, unsigned height);
1039 void BeginGetterStubFrame(int literal_id); 808 void BeginGetterStubFrame(int literal_id);
1040 void BeginSetterStubFrame(int literal_id); 809 void BeginSetterStubFrame(int literal_id);
1041 void BeginArgumentsObject(int args_length); 810 void BeginArgumentsObject(int args_length);
1042 void BeginCapturedObject(int length); 811 void BeginCapturedObject(int length);
1043 void DuplicateObject(int object_index); 812 void DuplicateObject(int object_index);
1044 void StoreRegister(Register reg); 813 void StoreRegister(Register reg);
1045 void StoreInt32Register(Register reg); 814 void StoreInt32Register(Register reg);
1046 void StoreUint32Register(Register reg); 815 void StoreUint32Register(Register reg);
(...skipping 18 matching lines...) Expand all
1065 // A literal id which refers to the JSFunction itself. 834 // A literal id which refers to the JSFunction itself.
1066 static const int kSelfLiteralId = -239; 835 static const int kSelfLiteralId = -239;
1067 836
1068 private: 837 private:
1069 TranslationBuffer* buffer_; 838 TranslationBuffer* buffer_;
1070 int index_; 839 int index_;
1071 Zone* zone_; 840 Zone* zone_;
1072 }; 841 };
1073 842
1074 843
844 class SlotRef BASE_EMBEDDED {
845 public:
846 enum SlotRepresentation {
847 UNKNOWN,
848 TAGGED,
849 INT32,
850 UINT32,
851 BOOLBIT,
852 DOUBLE,
853 LITERAL,
854 DEFERRED_OBJECT, // Object captured by the escape analysis.
855 // The number of nested objects can be obtained
856 // with the DeferredObjectLength() method
857 // (the SlotRefs of the nested objects follow
858 // this SlotRef in the depth-first order.)
859 DUPLICATE_OBJECT, // Duplicated object of a deferred object.
860 ARGUMENTS_OBJECT // Arguments object - only used to keep indexing
861 // in sync, it should not be materialized.
862 };
863
864 SlotRef()
865 : addr_(NULL), representation_(UNKNOWN) { }
866
867 SlotRef(Address addr, SlotRepresentation representation)
868 : addr_(addr), representation_(representation) { }
869
870 SlotRef(Isolate* isolate, Object* literal)
871 : literal_(literal, isolate), representation_(LITERAL) { }
872
873 static SlotRef NewArgumentsObject(int length) {
874 SlotRef slot;
875 slot.representation_ = ARGUMENTS_OBJECT;
876 slot.deferred_object_length_ = length;
877 return slot;
878 }
879
880 static SlotRef NewDeferredObject(int length) {
881 SlotRef slot;
882 slot.representation_ = DEFERRED_OBJECT;
883 slot.deferred_object_length_ = length;
884 return slot;
885 }
886
887 SlotRepresentation Representation() { return representation_; }
888
889 static SlotRef NewDuplicateObject(int id) {
890 SlotRef slot;
891 slot.representation_ = DUPLICATE_OBJECT;
892 slot.duplicate_object_id_ = id;
893 return slot;
894 }
895
896 int GetChildrenCount() {
897 if (representation_ == DEFERRED_OBJECT ||
898 representation_ == ARGUMENTS_OBJECT) {
899 return deferred_object_length_;
900 } else {
901 return 0;
902 }
903 }
904
905 int DuplicateObjectId() { return duplicate_object_id_; }
906
907 Handle<Object> GetValue(Isolate* isolate);
908
909 private:
910 Address addr_;
911 Handle<Object> literal_;
912 SlotRepresentation representation_;
913 int deferred_object_length_;
914 int duplicate_object_id_;
915 };
916
917 class SlotRefValueBuilder BASE_EMBEDDED {
918 public:
919 SlotRefValueBuilder(
920 JavaScriptFrame* frame,
921 int inlined_frame_index,
922 int formal_parameter_count);
923
924 void Prepare(Isolate* isolate);
925 Handle<Object> GetNext(Isolate* isolate, int level);
926 void Finish(Isolate* isolate);
927
928 int args_length() { return args_length_; }
929
930 private:
931 List<Handle<Object> > materialized_objects_;
932 Handle<FixedArray> previously_materialized_objects_;
933 int prev_materialized_count_;
934 Address stack_frame_id_;
935 List<SlotRef> slot_refs_;
936 int current_slot_;
937 int args_length_;
938 int first_slot_index_;
939 bool should_deoptimize_;
940
941 static SlotRef ComputeSlotForNextArgument(
942 Translation::Opcode opcode,
943 TranslationIterator* iterator,
944 DeoptimizationInputData* data,
945 JavaScriptFrame* frame);
946
947 Handle<Object> GetPreviouslyMaterialized(Isolate* isolate, int length);
948
949 static Address SlotAddress(JavaScriptFrame* frame, int slot_index) {
950 if (slot_index >= 0) {
951 const int offset = JavaScriptFrameConstants::kLocal0Offset;
952 return frame->fp() + offset - (slot_index * kPointerSize);
953 } else {
954 const int offset = JavaScriptFrameConstants::kLastParameterOffset;
955 return frame->fp() + offset - ((slot_index + 1) * kPointerSize);
956 }
957 }
958
959 Handle<Object> GetDeferredObject(Isolate* isolate);
960 };
961
1075 class MaterializedObjectStore { 962 class MaterializedObjectStore {
1076 public: 963 public:
1077 explicit MaterializedObjectStore(Isolate* isolate) : isolate_(isolate) { 964 explicit MaterializedObjectStore(Isolate* isolate) : isolate_(isolate) {
1078 } 965 }
1079 966
1080 Handle<FixedArray> Get(Address fp); 967 Handle<FixedArray> Get(Address fp);
1081 void Set(Address fp, Handle<FixedArray> materialized_objects); 968 void Set(Address fp, Handle<FixedArray> materialized_objects);
1082 bool Remove(Address fp); 969 bool Remove(Address fp);
1083 970
1084 private: 971 private:
(...skipping 79 matching lines...) Expand 10 before | Expand all | Expand 10 after
1164 bool has_construct_stub_; 1051 bool has_construct_stub_;
1165 int parameters_count_; 1052 int parameters_count_;
1166 int expression_count_; 1053 int expression_count_;
1167 Object** parameters_; 1054 Object** parameters_;
1168 Object** expression_stack_; 1055 Object** expression_stack_;
1169 int source_position_; 1056 int source_position_;
1170 1057
1171 friend class Deoptimizer; 1058 friend class Deoptimizer;
1172 }; 1059 };
1173 1060
1174 } // namespace internal 1061 } } // namespace v8::internal
1175 } // namespace v8
1176 1062
1177 #endif // V8_DEOPTIMIZER_H_ 1063 #endif // V8_DEOPTIMIZER_H_
OLDNEW
« no previous file with comments | « src/arm64/lithium-codegen-arm64.cc ('k') | src/deoptimizer.cc » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698