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
3 // found in the LICENSE file.
4 
5 #include <iomanip>
6 #include <memory>
7 
8 #include "src/common/globals.h"
9 #include "src/compiler/node.h"
10 #include "src/diagnostics/disasm.h"
11 #include "src/diagnostics/disassembler.h"
12 #include "src/heap/heap-inl.h"                // For InOldSpace.
13 #include "src/heap/heap-write-barrier-inl.h"  // For GetIsolateFromWritableObj.
14 #include "src/init/bootstrapper.h"
15 #include "src/interpreter/bytecodes.h"
16 #include "src/objects/all-objects-inl.h"
17 #include "src/objects/code-kind.h"
18 #include "src/regexp/regexp.h"
19 #include "src/snapshot/embedded/embedded-data.h"
20 #include "src/utils/ostreams.h"
21 #include "src/wasm/wasm-code-manager.h"
22 #include "src/wasm/wasm-engine.h"
23 #include "src/wasm/wasm-objects-inl.h"
24 
25 namespace v8 {
26 namespace internal {
27 
28 #ifdef OBJECT_PRINT
29 
Print() const30 void Object::Print() const {
31   // Output into debugger's command window if a debugger is attached.
32   DbgStdoutStream dbg_os;
33   this->Print(dbg_os);
34   dbg_os << std::flush;
35 
36   StdoutStream os;
37   this->Print(os);
38   os << std::flush;
39 }
40 
Print(std::ostream & os) const41 void Object::Print(std::ostream& os) const {  // NOLINT
42   if (IsSmi()) {
43     os << "Smi: " << std::hex << "0x" << Smi::ToInt(*this);
44     os << std::dec << " (" << Smi::ToInt(*this) << ")\n";
45   } else {
46     HeapObject::cast(*this).HeapObjectPrint(os);
47   }
48 }
49 
50 namespace {
51 
PrintHeapObjectHeaderWithoutMap(HeapObject object,std::ostream & os,const char * id)52 void PrintHeapObjectHeaderWithoutMap(HeapObject object, std::ostream& os,
53                                      const char* id) {  // NOLINT
54   os << reinterpret_cast<void*>(object.ptr()) << ": [";
55   if (id != nullptr) {
56     os << id;
57   } else {
58     os << object.map().instance_type();
59   }
60   os << "]";
61   if (ReadOnlyHeap::Contains(object)) {
62     os << " in ReadOnlySpace";
63   } else if (GetHeapFromWritableObject(object)->InOldSpace(object)) {
64     os << " in OldSpace";
65   }
66 }
67 
68 }  // namespace
69 
PrintHeader(std::ostream & os,const char * id)70 void HeapObject::PrintHeader(std::ostream& os, const char* id) {  // NOLINT
71   PrintHeapObjectHeaderWithoutMap(*this, os, id);
72   if (!IsMap()) os << "\n - map: " << Brief(map());
73 }
74 
HeapObjectPrint(std::ostream & os)75 void HeapObject::HeapObjectPrint(std::ostream& os) {  // NOLINT
76   InstanceType instance_type = map().instance_type();
77 
78   if (instance_type < FIRST_NONSTRING_TYPE) {
79     String::cast(*this).StringPrint(os);
80     os << "\n";
81     return;
82   }
83 
84   switch (instance_type) {
85     case FIXED_ARRAY_TYPE:
86       FixedArray::cast(*this).FixedArrayPrint(os);
87       break;
88     case AWAIT_CONTEXT_TYPE:
89     case BLOCK_CONTEXT_TYPE:
90     case CATCH_CONTEXT_TYPE:
91     case DEBUG_EVALUATE_CONTEXT_TYPE:
92     case EVAL_CONTEXT_TYPE:
93     case FUNCTION_CONTEXT_TYPE:
94     case MODULE_CONTEXT_TYPE:
95     case SCRIPT_CONTEXT_TYPE:
96     case WITH_CONTEXT_TYPE:
97     case SCRIPT_CONTEXT_TABLE_TYPE:
98       Context::cast(*this).ContextPrint(os);
99       break;
100     case NATIVE_CONTEXT_TYPE:
101       NativeContext::cast(*this).NativeContextPrint(os);
102       break;
103     case HASH_TABLE_TYPE:
104       ObjectHashTable::cast(*this).ObjectHashTablePrint(os);
105       break;
106     case ORDERED_HASH_MAP_TYPE:
107     case ORDERED_HASH_SET_TYPE:
108     case ORDERED_NAME_DICTIONARY_TYPE:
109     case NAME_DICTIONARY_TYPE:
110     case GLOBAL_DICTIONARY_TYPE:
111     case SIMPLE_NUMBER_DICTIONARY_TYPE:
112       FixedArray::cast(*this).FixedArrayPrint(os);
113       break;
114     case NUMBER_DICTIONARY_TYPE:
115       NumberDictionary::cast(*this).NumberDictionaryPrint(os);
116       break;
117     case EPHEMERON_HASH_TABLE_TYPE:
118       EphemeronHashTable::cast(*this).EphemeronHashTablePrint(os);
119       break;
120     case OBJECT_BOILERPLATE_DESCRIPTION_TYPE:
121       ObjectBoilerplateDescription::cast(*this)
122           .ObjectBoilerplateDescriptionPrint(os);
123       break;
124     case TRANSITION_ARRAY_TYPE:
125       TransitionArray::cast(*this).TransitionArrayPrint(os);
126       break;
127     case CLOSURE_FEEDBACK_CELL_ARRAY_TYPE:
128       ClosureFeedbackCellArray::cast(*this).ClosureFeedbackCellArrayPrint(os);
129       break;
130 
131     case FILLER_TYPE:
132       os << "filler";
133       break;
134     case JS_OBJECT_TYPE:  // fall through
135     case JS_API_OBJECT_TYPE:
136     case JS_SPECIAL_API_OBJECT_TYPE:
137     case JS_CONTEXT_EXTENSION_OBJECT_TYPE:
138     case JS_ERROR_TYPE:
139       JSObject::cast(*this).JSObjectPrint(os);
140       break;
141     case WASM_INSTANCE_OBJECT_TYPE:
142       WasmInstanceObject::cast(*this).WasmInstanceObjectPrint(os);
143       break;
144     case JS_GENERATOR_OBJECT_TYPE:
145       JSGeneratorObject::cast(*this).JSGeneratorObjectPrint(os);
146       break;
147     case CODE_TYPE:
148       Code::cast(*this).CodePrint(os);
149       break;
150     case CODE_DATA_CONTAINER_TYPE:
151       CodeDataContainer::cast(*this).CodeDataContainerPrint(os);
152       break;
153     case JS_SET_KEY_VALUE_ITERATOR_TYPE:
154     case JS_SET_VALUE_ITERATOR_TYPE:
155       JSSetIterator::cast(*this).JSSetIteratorPrint(os);
156       break;
157     case JS_MAP_KEY_ITERATOR_TYPE:
158     case JS_MAP_KEY_VALUE_ITERATOR_TYPE:
159     case JS_MAP_VALUE_ITERATOR_TYPE:
160       JSMapIterator::cast(*this).JSMapIteratorPrint(os);
161       break;
162 #define MAKE_TORQUE_CASE(Name, TYPE)   \
163   case TYPE:                           \
164     Name::cast(*this).Name##Print(os); \
165     break;
166       // Every class that has its fields defined in a .tq file and corresponds
167       // to exactly one InstanceType value is included in the following list.
168       TORQUE_INSTANCE_CHECKERS_SINGLE_FULLY_DEFINED(MAKE_TORQUE_CASE)
169       TORQUE_INSTANCE_CHECKERS_MULTIPLE_FULLY_DEFINED(MAKE_TORQUE_CASE)
170 #undef MAKE_TORQUE_CASE
171 
172     case FOREIGN_TYPE:
173       Foreign::cast(*this).ForeignPrint(os);
174       break;
175     case ALLOCATION_SITE_TYPE:
176       AllocationSite::cast(*this).AllocationSitePrint(os);
177       break;
178     case LOAD_HANDLER_TYPE:
179       LoadHandler::cast(*this).LoadHandlerPrint(os);
180       break;
181     case STORE_HANDLER_TYPE:
182       StoreHandler::cast(*this).StoreHandlerPrint(os);
183       break;
184     case SCOPE_INFO_TYPE:
185       ScopeInfo::cast(*this).ScopeInfoPrint(os);
186       break;
187     case FEEDBACK_METADATA_TYPE:
188       FeedbackMetadata::cast(*this).FeedbackMetadataPrint(os);
189       break;
190     case WEAK_FIXED_ARRAY_TYPE:
191       WeakFixedArray::cast(*this).WeakFixedArrayPrint(os);
192       break;
193     case INTERNALIZED_STRING_TYPE:
194     case EXTERNAL_INTERNALIZED_STRING_TYPE:
195     case ONE_BYTE_INTERNALIZED_STRING_TYPE:
196     case EXTERNAL_ONE_BYTE_INTERNALIZED_STRING_TYPE:
197     case UNCACHED_EXTERNAL_INTERNALIZED_STRING_TYPE:
198     case UNCACHED_EXTERNAL_ONE_BYTE_INTERNALIZED_STRING_TYPE:
199     case STRING_TYPE:
200     case CONS_STRING_TYPE:
201     case EXTERNAL_STRING_TYPE:
202     case SLICED_STRING_TYPE:
203     case THIN_STRING_TYPE:
204     case ONE_BYTE_STRING_TYPE:
205     case CONS_ONE_BYTE_STRING_TYPE:
206     case EXTERNAL_ONE_BYTE_STRING_TYPE:
207     case SLICED_ONE_BYTE_STRING_TYPE:
208     case THIN_ONE_BYTE_STRING_TYPE:
209     case UNCACHED_EXTERNAL_STRING_TYPE:
210     case UNCACHED_EXTERNAL_ONE_BYTE_STRING_TYPE:
211       // TODO(all): Handle these types too.
212       os << "UNKNOWN TYPE " << map().instance_type();
213       UNREACHABLE();
214   }
215 }
216 
ByteArrayPrint(std::ostream & os)217 void ByteArray::ByteArrayPrint(std::ostream& os) {  // NOLINT
218   PrintHeader(os, "ByteArray");
219   os << "\n - length: " << length()
220      << "\n - data-start: " << static_cast<void*>(GetDataStartAddress())
221      << "\n";
222 }
223 
BytecodeArrayPrint(std::ostream & os)224 void BytecodeArray::BytecodeArrayPrint(std::ostream& os) {  // NOLINT
225   PrintHeader(os, "BytecodeArray");
226   os << "\n";
227   Disassemble(os);
228 }
229 
FreeSpacePrint(std::ostream & os)230 void FreeSpace::FreeSpacePrint(std::ostream& os) {  // NOLINT
231   os << "free space, size " << Size() << "\n";
232 }
233 
PrintProperties(std::ostream & os)234 bool JSObject::PrintProperties(std::ostream& os) {  // NOLINT
235   if (HasFastProperties()) {
236     DescriptorArray descs = map().instance_descriptors(kRelaxedLoad);
237     int nof_inobject_properties = map().GetInObjectProperties();
238     for (InternalIndex i : map().IterateOwnDescriptors()) {
239       os << "\n    ";
240       descs.GetKey(i).NamePrint(os);
241       os << ": ";
242       PropertyDetails details = descs.GetDetails(i);
243       switch (details.location()) {
244         case kField: {
245           FieldIndex field_index = FieldIndex::ForDescriptor(map(), i);
246           if (IsUnboxedDoubleField(field_index)) {
247             os << "<unboxed double> " << RawFastDoublePropertyAt(field_index);
248           } else {
249             os << Brief(RawFastPropertyAt(field_index));
250           }
251           break;
252         }
253         case kDescriptor:
254           os << Brief(descs.GetStrongValue(i));
255           break;
256       }
257       os << " ";
258       details.PrintAsFastTo(os, PropertyDetails::kForProperties);
259       if (details.location() == kField) {
260         int field_index = details.field_index();
261         if (field_index < nof_inobject_properties) {
262           os << ", location: in-object";
263         } else {
264           field_index -= nof_inobject_properties;
265           os << ", location: properties[" << field_index << "]";
266         }
267       } else {
268         os << ", location: descriptor";
269       }
270     }
271     return map().NumberOfOwnDescriptors() > 0;
272   } else if (IsJSGlobalObject()) {
273     JSGlobalObject::cast(*this).global_dictionary().Print(os);
274   } else if (V8_DICT_MODE_PROTOTYPES_BOOL) {
275     property_dictionary_ordered().Print(os);
276   } else {
277     property_dictionary().Print(os);
278   }
279   return true;
280 }
281 
282 namespace {
283 
284 template <class T>
IsTheHoleAt(T array,int index)285 bool IsTheHoleAt(T array, int index) {
286   return false;
287 }
288 
289 template <>
IsTheHoleAt(FixedDoubleArray array,int index)290 bool IsTheHoleAt(FixedDoubleArray array, int index) {
291   return array.is_the_hole(index);
292 }
293 
294 template <class T>
GetScalarElement(T array,int index)295 double GetScalarElement(T array, int index) {
296   if (IsTheHoleAt(array, index)) {
297     return std::numeric_limits<double>::quiet_NaN();
298   }
299   return array.get_scalar(index);
300 }
301 
302 template <class T>
DoPrintElements(std::ostream & os,Object object,int length)303 void DoPrintElements(std::ostream& os, Object object, int length) {  // NOLINT
304   const bool print_the_hole = std::is_same<T, FixedDoubleArray>::value;
305   T array = T::cast(object);
306   if (length == 0) return;
307   int previous_index = 0;
308   double previous_value = GetScalarElement(array, 0);
309   double value = 0.0;
310   int i;
311   for (i = 1; i <= length; i++) {
312     if (i < length) value = GetScalarElement(array, i);
313     bool values_are_nan = std::isnan(previous_value) && std::isnan(value);
314     if (i != length && (previous_value == value || values_are_nan) &&
315         IsTheHoleAt(array, i - 1) == IsTheHoleAt(array, i)) {
316       continue;
317     }
318     os << "\n";
319     std::stringstream ss;
320     ss << previous_index;
321     if (previous_index != i - 1) {
322       ss << '-' << (i - 1);
323     }
324     os << std::setw(12) << ss.str() << ": ";
325     if (print_the_hole && IsTheHoleAt(array, i - 1)) {
326       os << "<the_hole>";
327     } else {
328       os << previous_value;
329     }
330     previous_index = i;
331     previous_value = value;
332   }
333 }
334 
335 template <typename ElementType>
PrintTypedArrayElements(std::ostream & os,const ElementType * data_ptr,size_t length,bool is_on_heap)336 void PrintTypedArrayElements(std::ostream& os, const ElementType* data_ptr,
337                              size_t length, bool is_on_heap) {
338   if (length == 0) return;
339   size_t previous_index = 0;
340   if (i::FLAG_mock_arraybuffer_allocator && !is_on_heap) {
341     // Don't try to print data that's not actually allocated.
342     os << "\n    0-" << length << ": <mocked array buffer bytes>";
343     return;
344   }
345 
346   ElementType previous_value = data_ptr[0];
347   ElementType value = 0;
348   for (size_t i = 1; i <= length; i++) {
349     if (i < length) value = data_ptr[i];
350     if (i != length && previous_value == value) {
351       continue;
352     }
353     os << "\n";
354     std::stringstream ss;
355     ss << previous_index;
356     if (previous_index != i - 1) {
357       ss << '-' << (i - 1);
358     }
359     os << std::setw(12) << ss.str() << ": " << +previous_value;
360     previous_index = i;
361     previous_value = value;
362   }
363 }
364 
365 template <typename T>
PrintFixedArrayElements(std::ostream & os,T array)366 void PrintFixedArrayElements(std::ostream& os, T array) {
367   // Print in array notation for non-sparse arrays.
368   Object previous_value = array.length() > 0 ? array.get(0) : Object();
369   Object value;
370   int previous_index = 0;
371   int i;
372   for (i = 1; i <= array.length(); i++) {
373     if (i < array.length()) value = array.get(i);
374     if (previous_value == value && i != array.length()) {
375       continue;
376     }
377     os << "\n";
378     std::stringstream ss;
379     ss << previous_index;
380     if (previous_index != i - 1) {
381       ss << '-' << (i - 1);
382     }
383     os << std::setw(12) << ss.str() << ": " << Brief(previous_value);
384     previous_index = i;
385     previous_value = value;
386   }
387 }
388 
PrintDictionaryElements(std::ostream & os,FixedArrayBase elements)389 void PrintDictionaryElements(std::ostream& os, FixedArrayBase elements) {
390   // Print some internal fields
391   NumberDictionary dict = NumberDictionary::cast(elements);
392   if (dict.requires_slow_elements()) {
393     os << "\n   - requires_slow_elements";
394   } else {
395     os << "\n   - max_number_key: " << dict.max_number_key();
396   }
397   dict.Print(os);
398 }
399 
PrintSloppyArgumentElements(std::ostream & os,ElementsKind kind,SloppyArgumentsElements elements)400 void PrintSloppyArgumentElements(std::ostream& os, ElementsKind kind,
401                                  SloppyArgumentsElements elements) {
402   FixedArray arguments_store = elements.arguments();
403   os << "\n    0: context: " << Brief(elements.context())
404      << "\n    1: arguments_store: " << Brief(arguments_store)
405      << "\n    parameter to context slot map:";
406   for (int i = 0; i < elements.length(); i++) {
407     Object mapped_entry = elements.mapped_entries(i);
408     os << "\n    " << i << ": param(" << i << "): " << Brief(mapped_entry);
409     if (mapped_entry.IsTheHole()) {
410       os << " in the arguments_store[" << i << "]";
411     } else {
412       os << " in the context";
413     }
414   }
415   if (arguments_store.length() == 0) return;
416   os << "\n }"
417      << "\n - arguments_store: " << Brief(arguments_store) << " "
418      << ElementsKindToString(arguments_store.map().elements_kind()) << " {";
419   if (kind == FAST_SLOPPY_ARGUMENTS_ELEMENTS) {
420     PrintFixedArrayElements(os, arguments_store);
421   } else {
422     DCHECK_EQ(kind, SLOW_SLOPPY_ARGUMENTS_ELEMENTS);
423     PrintDictionaryElements(os, arguments_store);
424   }
425 }
426 
PrintEmbedderData(IsolateRoot isolate,std::ostream & os,EmbedderDataSlot slot)427 void PrintEmbedderData(IsolateRoot isolate, std::ostream& os,
428                        EmbedderDataSlot slot) {
429   DisallowHeapAllocation no_gc;
430   Object value = slot.load_tagged();
431   os << Brief(value);
432   void* raw_pointer;
433   if (slot.ToAlignedPointer(isolate, &raw_pointer)) {
434     os << ", aligned pointer: " << raw_pointer;
435   }
436 }
437 
438 }  // namespace
439 
PrintElements(std::ostream & os)440 void JSObject::PrintElements(std::ostream& os) {  // NOLINT
441   // Don't call GetElementsKind, its validation code can cause the printer to
442   // fail when debugging.
443   os << " - elements: " << Brief(elements()) << " {";
444   switch (map().elements_kind()) {
445     case HOLEY_SMI_ELEMENTS:
446     case PACKED_SMI_ELEMENTS:
447     case HOLEY_ELEMENTS:
448     case HOLEY_FROZEN_ELEMENTS:
449     case HOLEY_SEALED_ELEMENTS:
450     case HOLEY_NONEXTENSIBLE_ELEMENTS:
451     case PACKED_ELEMENTS:
452     case PACKED_FROZEN_ELEMENTS:
453     case PACKED_SEALED_ELEMENTS:
454     case PACKED_NONEXTENSIBLE_ELEMENTS:
455     case FAST_STRING_WRAPPER_ELEMENTS: {
456       PrintFixedArrayElements(os, FixedArray::cast(elements()));
457       break;
458     }
459     case HOLEY_DOUBLE_ELEMENTS:
460     case PACKED_DOUBLE_ELEMENTS: {
461       DoPrintElements<FixedDoubleArray>(os, elements(), elements().length());
462       break;
463     }
464 
465 #define PRINT_ELEMENTS(Type, type, TYPE, elementType)                         \
466   case TYPE##_ELEMENTS: {                                                     \
467     size_t length = JSTypedArray::cast(*this).length();                       \
468     bool is_on_heap = JSTypedArray::cast(*this).is_on_heap();                 \
469     const elementType* data_ptr =                                             \
470         static_cast<const elementType*>(JSTypedArray::cast(*this).DataPtr()); \
471     PrintTypedArrayElements<elementType>(os, data_ptr, length, is_on_heap);   \
472     break;                                                                    \
473   }
474       TYPED_ARRAYS(PRINT_ELEMENTS)
475 #undef PRINT_ELEMENTS
476 
477     case DICTIONARY_ELEMENTS:
478     case SLOW_STRING_WRAPPER_ELEMENTS:
479       PrintDictionaryElements(os, elements());
480       break;
481     case FAST_SLOPPY_ARGUMENTS_ELEMENTS:
482     case SLOW_SLOPPY_ARGUMENTS_ELEMENTS:
483       PrintSloppyArgumentElements(os, map().elements_kind(),
484                                   SloppyArgumentsElements::cast(elements()));
485       break;
486     case NO_ELEMENTS:
487       break;
488   }
489   os << "\n }\n";
490 }
491 
JSObjectPrintHeader(std::ostream & os,JSObject obj,const char * id)492 static void JSObjectPrintHeader(std::ostream& os, JSObject obj,
493                                 const char* id) {  // NOLINT
494   Isolate* isolate = obj.GetIsolate();
495   obj.PrintHeader(os, id);
496   // Don't call GetElementsKind, its validation code can cause the printer to
497   // fail when debugging.
498   os << " [";
499   if (obj.HasFastProperties()) {
500     os << "FastProperties";
501   } else {
502     os << "DictionaryProperties";
503   }
504   PrototypeIterator iter(isolate, obj);
505   os << "]\n - prototype: " << Brief(iter.GetCurrent());
506   os << "\n - elements: " << Brief(obj.elements()) << " ["
507      << ElementsKindToString(obj.map().elements_kind());
508   if (obj.elements().IsCowArray()) os << " (COW)";
509   os << "]";
510   Object hash = obj.GetHash();
511   if (hash.IsSmi()) {
512     os << "\n - hash: " << Brief(hash);
513   }
514   if (obj.GetEmbedderFieldCount() > 0) {
515     os << "\n - embedder fields: " << obj.GetEmbedderFieldCount();
516   }
517 }
518 
JSObjectPrintBody(std::ostream & os,JSObject obj,bool print_elements=true)519 static void JSObjectPrintBody(std::ostream& os,
520                               JSObject obj,  // NOLINT
521                               bool print_elements = true) {
522   os << "\n - properties: ";
523   Object properties_or_hash = obj.raw_properties_or_hash();
524   if (!properties_or_hash.IsSmi()) {
525     os << Brief(properties_or_hash);
526   }
527   os << "\n - All own properties (excluding elements): {";
528   if (obj.PrintProperties(os)) os << "\n ";
529   os << "}\n";
530 
531   if (print_elements) {
532     size_t length = obj.IsJSTypedArray() ? JSTypedArray::cast(obj).length()
533                                          : obj.elements().length();
534     if (length > 0) obj.PrintElements(os);
535   }
536   int embedder_fields = obj.GetEmbedderFieldCount();
537   if (embedder_fields > 0) {
538     IsolateRoot isolate = GetIsolateForPtrCompr(obj);
539     os << " - embedder fields = {";
540     for (int i = 0; i < embedder_fields; i++) {
541       os << "\n    ";
542       PrintEmbedderData(isolate, os, EmbedderDataSlot(obj, i));
543     }
544     os << "\n }\n";
545   }
546 }
547 
JSObjectPrint(std::ostream & os)548 void JSObject::JSObjectPrint(std::ostream& os) {  // NOLINT
549   JSObjectPrintHeader(os, *this, nullptr);
550   JSObjectPrintBody(os, *this);
551 }
552 
JSGeneratorObjectPrint(std::ostream & os)553 void JSGeneratorObject::JSGeneratorObjectPrint(std::ostream& os) {  // NOLINT
554   JSObjectPrintHeader(os, *this, "JSGeneratorObject");
555   os << "\n - function: " << Brief(function());
556   os << "\n - context: " << Brief(context());
557   os << "\n - receiver: " << Brief(receiver());
558   if (is_executing() || is_closed()) {
559     os << "\n - input: " << Brief(input_or_debug_pos());
560   } else {
561     DCHECK(is_suspended());
562     os << "\n - debug pos: " << Brief(input_or_debug_pos());
563   }
564   const char* mode = "(invalid)";
565   switch (resume_mode()) {
566     case kNext:
567       mode = ".next()";
568       break;
569     case kReturn:
570       mode = ".return()";
571       break;
572     case kThrow:
573       mode = ".throw()";
574       break;
575   }
576   os << "\n - resume mode: " << mode;
577   os << "\n - continuation: " << continuation();
578   if (is_closed()) os << " (closed)";
579   if (is_executing()) os << " (executing)";
580   if (is_suspended()) os << " (suspended)";
581   if (is_suspended()) {
582     DisallowHeapAllocation no_gc;
583     SharedFunctionInfo fun_info = function().shared();
584     if (fun_info.HasSourceCode()) {
585       Script script = Script::cast(fun_info.script());
586       String script_name = script.name().IsString()
587                                ? String::cast(script.name())
588                                : GetReadOnlyRoots().empty_string();
589 
590       os << "\n - source position: ";
591       // Can't collect source positions here if not available as that would
592       // allocate memory.
593       if (fun_info.HasBytecodeArray() &&
594           fun_info.GetBytecodeArray().HasSourcePositionTable()) {
595         os << source_position();
596         os << " (";
597         script_name.PrintUC16(os);
598         int lin = script.GetLineNumber(source_position()) + 1;
599         int col = script.GetColumnNumber(source_position()) + 1;
600         os << ", lin " << lin;
601         os << ", col " << col;
602       } else {
603         os << "unavailable";
604       }
605       os << ")";
606     }
607   }
608   os << "\n - register file: " << Brief(parameters_and_registers());
609   JSObjectPrintBody(os, *this);
610 }
611 
JSArrayPrint(std::ostream & os)612 void JSArray::JSArrayPrint(std::ostream& os) {  // NOLINT
613   JSObjectPrintHeader(os, *this, "JSArray");
614   os << "\n - length: " << Brief(this->length());
615   JSObjectPrintBody(os, *this);
616 }
617 
JSPromisePrint(std::ostream & os)618 void JSPromise::JSPromisePrint(std::ostream& os) {  // NOLINT
619   JSObjectPrintHeader(os, *this, "JSPromise");
620   os << "\n - status: " << JSPromise::Status(status());
621   if (status() == Promise::kPending) {
622     os << "\n - reactions: " << Brief(reactions());
623   } else {
624     os << "\n - result: " << Brief(result());
625   }
626   os << "\n - has_handler: " << has_handler();
627   os << "\n - handled_hint: " << handled_hint();
628   JSObjectPrintBody(os, *this);
629 }
630 
JSRegExpPrint(std::ostream & os)631 void JSRegExp::JSRegExpPrint(std::ostream& os) {  // NOLINT
632   JSObjectPrintHeader(os, *this, "JSRegExp");
633   os << "\n - data: " << Brief(data());
634   os << "\n - source: " << Brief(source());
635   JSObjectPrintBody(os, *this);
636 }
637 
JSRegExpStringIteratorPrint(std::ostream & os)638 void JSRegExpStringIterator::JSRegExpStringIteratorPrint(
639     std::ostream& os) {  // NOLINT
640   JSObjectPrintHeader(os, *this, "JSRegExpStringIterator");
641   os << "\n - regex: " << Brief(iterating_reg_exp());
642   os << "\n - string: " << Brief(iterated_string());
643   os << "\n - done: " << done();
644   os << "\n - global: " << global();
645   os << "\n - unicode: " << unicode();
646   JSObjectPrintBody(os, *this);
647 }
648 
SymbolPrint(std::ostream & os)649 void Symbol::SymbolPrint(std::ostream& os) {  // NOLINT
650   PrintHeader(os, "Symbol");
651   os << "\n - hash: " << Hash();
652   os << "\n - description: " << Brief(description());
653   if (description().IsUndefined()) {
654     os << " (" << PrivateSymbolToName() << ")";
655   }
656   os << "\n - private: " << is_private();
657 }
658 
DescriptorArrayPrint(std::ostream & os)659 void DescriptorArray::DescriptorArrayPrint(std::ostream& os) {
660   PrintHeader(os, "DescriptorArray");
661   os << "\n - enum_cache: ";
662   if (enum_cache().keys().length() == 0) {
663     os << "empty";
664   } else {
665     os << enum_cache().keys().length();
666     os << "\n   - keys: " << Brief(enum_cache().keys());
667     os << "\n   - indices: " << Brief(enum_cache().indices());
668   }
669   os << "\n - nof slack descriptors: " << number_of_slack_descriptors();
670   os << "\n - nof descriptors: " << number_of_descriptors();
671   int16_t raw_marked = raw_number_of_marked_descriptors();
672   os << "\n - raw marked descriptors: mc epoch "
673      << NumberOfMarkedDescriptors::Epoch::decode(raw_marked) << ", marked "
674      << NumberOfMarkedDescriptors::Marked::decode(raw_marked);
675   PrintDescriptors(os);
676 }
677 
678 namespace {
PrintFixedArrayWithHeader(std::ostream & os,FixedArray array,const char * type)679 void PrintFixedArrayWithHeader(std::ostream& os, FixedArray array,
680                                const char* type) {
681   array.PrintHeader(os, type);
682   os << "\n - length: " << array.length();
683   PrintFixedArrayElements(os, array);
684   os << "\n";
685 }
686 
687 template <typename T>
PrintHashTableWithHeader(std::ostream & os,T table,const char * type)688 void PrintHashTableWithHeader(std::ostream& os, T table, const char* type) {
689   table.PrintHeader(os, type);
690   os << "\n - length: " << table.length();
691   os << "\n - elements: " << table.NumberOfElements();
692   os << "\n - deleted: " << table.NumberOfDeletedElements();
693   os << "\n - capacity: " << table.Capacity();
694 
695   os << "\n - elements: {";
696   for (InternalIndex i : table.IterateEntries()) {
697     os << '\n'
698        << std::setw(12) << i.as_int() << ": " << Brief(table.KeyAt(i)) << " -> "
699        << Brief(table.ValueAt(i));
700   }
701   os << "\n }\n";
702 }
703 
704 template <typename T>
PrintWeakArrayElements(std::ostream & os,T * array)705 void PrintWeakArrayElements(std::ostream& os, T* array) {
706   // Print in array notation for non-sparse arrays.
707   MaybeObject previous_value =
708       array->length() > 0 ? array->Get(0) : MaybeObject(kNullAddress);
709   MaybeObject value;
710   int previous_index = 0;
711   int i;
712   for (i = 1; i <= array->length(); i++) {
713     if (i < array->length()) value = array->Get(i);
714     if (previous_value == value && i != array->length()) {
715       continue;
716     }
717     os << "\n";
718     std::stringstream ss;
719     ss << previous_index;
720     if (previous_index != i - 1) {
721       ss << '-' << (i - 1);
722     }
723     os << std::setw(12) << ss.str() << ": " << Brief(previous_value);
724     previous_index = i;
725     previous_value = value;
726   }
727 }
728 
729 }  // namespace
730 
EmbedderDataArrayPrint(std::ostream & os)731 void EmbedderDataArray::EmbedderDataArrayPrint(std::ostream& os) {
732   IsolateRoot isolate = GetIsolateForPtrCompr(*this);
733   PrintHeader(os, "EmbedderDataArray");
734   os << "\n - length: " << length();
735   EmbedderDataSlot start(*this, 0);
736   EmbedderDataSlot end(*this, length());
737   for (EmbedderDataSlot slot = start; slot < end; ++slot) {
738     os << "\n    ";
739     PrintEmbedderData(isolate, os, slot);
740   }
741   os << "\n";
742 }
743 
FixedArrayPrint(std::ostream & os)744 void FixedArray::FixedArrayPrint(std::ostream& os) {
745   PrintFixedArrayWithHeader(os, *this, "FixedArray");
746 }
747 
748 namespace {
PrintContextWithHeader(std::ostream & os,Context context,const char * type)749 void PrintContextWithHeader(std::ostream& os, Context context,
750                             const char* type) {
751   context.PrintHeader(os, type);
752   os << "\n - length: " << context.length();
753   os << "\n - scope_info: " << Brief(context.scope_info());
754   os << "\n - previous: " << Brief(context.unchecked_previous());
755   os << "\n - native_context: " << Brief(context.native_context());
756   PrintFixedArrayElements(os, context);
757   os << "\n";
758 }
759 }  // namespace
760 
ContextPrint(std::ostream & os)761 void Context::ContextPrint(std::ostream& os) {
762   PrintContextWithHeader(os, *this, "Context");
763 }
764 
NativeContextPrint(std::ostream & os)765 void NativeContext::NativeContextPrint(std::ostream& os) {
766   PrintContextWithHeader(os, *this, "NativeContext");
767   os << " - microtask_queue: " << microtask_queue() << "\n";
768 }
769 
ObjectHashTablePrint(std::ostream & os)770 void ObjectHashTable::ObjectHashTablePrint(std::ostream& os) {
771   PrintHashTableWithHeader(os, *this, "ObjectHashTable");
772 }
773 
NumberDictionaryPrint(std::ostream & os)774 void NumberDictionary::NumberDictionaryPrint(std::ostream& os) {
775   PrintHashTableWithHeader(os, *this, "NumberDictionary");
776 }
777 
EphemeronHashTablePrint(std::ostream & os)778 void EphemeronHashTable::EphemeronHashTablePrint(std::ostream& os) {
779   PrintHashTableWithHeader(os, *this, "EphemeronHashTable");
780 }
781 
ObjectBoilerplateDescriptionPrint(std::ostream & os)782 void ObjectBoilerplateDescription::ObjectBoilerplateDescriptionPrint(
783     std::ostream& os) {
784   PrintFixedArrayWithHeader(os, *this, "ObjectBoilerplateDescription");
785 }
786 
PropertyArrayPrint(std::ostream & os)787 void PropertyArray::PropertyArrayPrint(std::ostream& os) {  // NOLINT
788   PrintHeader(os, "PropertyArray");
789   os << "\n - length: " << length();
790   os << "\n - hash: " << Hash();
791   PrintFixedArrayElements(os, *this);
792   os << "\n";
793 }
794 
FixedDoubleArrayPrint(std::ostream & os)795 void FixedDoubleArray::FixedDoubleArrayPrint(std::ostream& os) {  // NOLINT
796   PrintHeader(os, "FixedDoubleArray");
797   os << "\n - length: " << length();
798   DoPrintElements<FixedDoubleArray>(os, *this, length());
799   os << "\n";
800 }
801 
WeakFixedArrayPrint(std::ostream & os)802 void WeakFixedArray::WeakFixedArrayPrint(std::ostream& os) {
803   PrintHeader(os, "WeakFixedArray");
804   os << "\n - length: " << length() << "\n";
805   PrintWeakArrayElements(os, this);
806   os << "\n";
807 }
808 
WeakArrayListPrint(std::ostream & os)809 void WeakArrayList::WeakArrayListPrint(std::ostream& os) {
810   PrintHeader(os, "WeakArrayList");
811   os << "\n - capacity: " << capacity();
812   os << "\n - length: " << length() << "\n";
813   PrintWeakArrayElements(os, this);
814   os << "\n";
815 }
816 
TransitionArrayPrint(std::ostream & os)817 void TransitionArray::TransitionArrayPrint(std::ostream& os) {  // NOLINT
818   PrintHeader(os, "TransitionArray");
819   PrintInternal(os);
820 }
821 
FeedbackCellPrint(std::ostream & os)822 void FeedbackCell::FeedbackCellPrint(std::ostream& os) {  // NOLINT
823   PrintHeader(os, "FeedbackCell");
824   ReadOnlyRoots roots = GetReadOnlyRoots();
825   if (map() == roots.no_closures_cell_map()) {
826     os << "\n - no closures";
827   } else if (map() == roots.one_closure_cell_map()) {
828     os << "\n - one closure";
829   } else if (map() == roots.many_closures_cell_map()) {
830     os << "\n - many closures";
831   } else {
832     os << "\n - Invalid FeedbackCell map";
833   }
834   os << "\n - value: " << Brief(value());
835   os << "\n - interrupt_budget: " << interrupt_budget();
836   os << "\n";
837 }
838 
Print()839 void FeedbackVectorSpec::Print() {
840   StdoutStream os;
841 
842   FeedbackVectorSpecPrint(os);
843 
844   os << std::flush;
845 }
846 
FeedbackVectorSpecPrint(std::ostream & os)847 void FeedbackVectorSpec::FeedbackVectorSpecPrint(std::ostream& os) {  // NOLINT
848   os << " - slot_count: " << slot_count();
849   if (slot_count() == 0) {
850     os << " (empty)\n";
851     return;
852   }
853 
854   for (int slot = 0; slot < slot_count();) {
855     FeedbackSlotKind kind = GetKind(FeedbackSlot(slot));
856     int entry_size = FeedbackMetadata::GetSlotSize(kind);
857     DCHECK_LT(0, entry_size);
858     os << "\n Slot #" << slot << " " << kind;
859     slot += entry_size;
860   }
861   os << "\n";
862 }
863 
FeedbackMetadataPrint(std::ostream & os)864 void FeedbackMetadata::FeedbackMetadataPrint(std::ostream& os) {
865   PrintHeader(os, "FeedbackMetadata");
866   os << "\n - slot_count: " << slot_count();
867   os << "\n - create_closure_slot_count: " << create_closure_slot_count();
868 
869   FeedbackMetadataIterator iter(*this);
870   while (iter.HasNext()) {
871     FeedbackSlot slot = iter.Next();
872     FeedbackSlotKind kind = iter.kind();
873     os << "\n Slot " << slot << " " << kind;
874   }
875   os << "\n";
876 }
877 
ClosureFeedbackCellArrayPrint(std::ostream & os)878 void ClosureFeedbackCellArray::ClosureFeedbackCellArrayPrint(std::ostream& os) {
879   PrintFixedArrayWithHeader(os, *this, "ClosureFeedbackCellArray");
880 }
881 
FeedbackVectorPrint(std::ostream & os)882 void FeedbackVector::FeedbackVectorPrint(std::ostream& os) {  // NOLINT
883   PrintHeader(os, "FeedbackVector");
884   os << "\n - length: " << length();
885   if (length() == 0) {
886     os << " (empty)\n";
887     return;
888   }
889 
890   os << "\n - shared function info: " << Brief(shared_function_info());
891   if (has_optimized_code()) {
892     os << "\n - optimized code: " << Brief(optimized_code());
893   } else {
894     os << "\n - no optimized code";
895   }
896   os << "\n - optimization marker: " << optimization_marker();
897   os << "\n - optimization tier: " << optimization_tier();
898   os << "\n - invocation count: " << invocation_count();
899   os << "\n - profiler ticks: " << profiler_ticks();
900 
901   FeedbackMetadataIterator iter(metadata());
902   while (iter.HasNext()) {
903     FeedbackSlot slot = iter.Next();
904     FeedbackSlotKind kind = iter.kind();
905 
906     os << "\n - slot " << slot << " " << kind << " ";
907     FeedbackSlotPrint(os, slot);
908 
909     int entry_size = iter.entry_size();
910     if (entry_size > 0) os << " {";
911     for (int i = 0; i < entry_size; i++) {
912       FeedbackSlot slot_with_offset = slot.WithOffset(i);
913       os << "\n     [" << slot_with_offset.ToInt()
914          << "]: " << Brief(Get(slot_with_offset));
915     }
916     if (entry_size > 0) os << "\n  }";
917   }
918   os << "\n";
919 }
920 
FeedbackSlotPrint(std::ostream & os,FeedbackSlot slot)921 void FeedbackVector::FeedbackSlotPrint(std::ostream& os,
922                                        FeedbackSlot slot) {  // NOLINT
923   FeedbackNexus nexus(*this, slot);
924   nexus.Print(os);
925 }
926 
Print(std::ostream & os)927 void FeedbackNexus::Print(std::ostream& os) {  // NOLINT
928   switch (kind()) {
929     case FeedbackSlotKind::kCall:
930     case FeedbackSlotKind::kCloneObject:
931     case FeedbackSlotKind::kHasKeyed:
932     case FeedbackSlotKind::kInstanceOf:
933     case FeedbackSlotKind::kLoadGlobalInsideTypeof:
934     case FeedbackSlotKind::kLoadGlobalNotInsideTypeof:
935     case FeedbackSlotKind::kLoadKeyed:
936     case FeedbackSlotKind::kLoadProperty:
937     case FeedbackSlotKind::kStoreDataPropertyInLiteral:
938     case FeedbackSlotKind::kStoreGlobalSloppy:
939     case FeedbackSlotKind::kStoreGlobalStrict:
940     case FeedbackSlotKind::kStoreInArrayLiteral:
941     case FeedbackSlotKind::kStoreKeyedSloppy:
942     case FeedbackSlotKind::kStoreKeyedStrict:
943     case FeedbackSlotKind::kStoreNamedSloppy:
944     case FeedbackSlotKind::kStoreNamedStrict:
945     case FeedbackSlotKind::kStoreOwnNamed: {
946       os << InlineCacheState2String(ic_state());
947       break;
948     }
949     case FeedbackSlotKind::kBinaryOp: {
950       os << "BinaryOp:" << GetBinaryOperationFeedback();
951       break;
952     }
953     case FeedbackSlotKind::kCompareOp: {
954       os << "CompareOp:" << GetCompareOperationFeedback();
955       break;
956     }
957     case FeedbackSlotKind::kForIn: {
958       os << "ForIn:" << GetForInFeedback();
959       break;
960     }
961     case FeedbackSlotKind::kLiteral:
962     case FeedbackSlotKind::kTypeProfile:
963       break;
964     case FeedbackSlotKind::kInvalid:
965     case FeedbackSlotKind::kKindsNumber:
966       UNREACHABLE();
967   }
968 }
969 
OddballPrint(std::ostream & os)970 void Oddball::OddballPrint(std::ostream& os) {  // NOLINT
971   PrintHeapObjectHeaderWithoutMap(*this, os, "Oddball");
972   os << ": ";
973   String s = to_string();
974   os << s.PrefixForDebugPrint();
975   s.PrintUC16(os);
976   os << s.SuffixForDebugPrint();
977   os << std::endl;
978 }
979 
JSAsyncFunctionObjectPrint(std::ostream & os)980 void JSAsyncFunctionObject::JSAsyncFunctionObjectPrint(
981     std::ostream& os) {  // NOLINT
982   JSGeneratorObjectPrint(os);
983 }
984 
JSAsyncGeneratorObjectPrint(std::ostream & os)985 void JSAsyncGeneratorObject::JSAsyncGeneratorObjectPrint(
986     std::ostream& os) {  // NOLINT
987   JSGeneratorObjectPrint(os);
988 }
989 
JSArgumentsObjectPrint(std::ostream & os)990 void JSArgumentsObject::JSArgumentsObjectPrint(std::ostream& os) {  // NOLINT
991   JSObjectPrint(os);
992 }
993 
JSStringIteratorPrint(std::ostream & os)994 void JSStringIterator::JSStringIteratorPrint(std::ostream& os) {  // NOLINT
995   JSObjectPrintHeader(os, *this, "JSStringIterator");
996   os << "\n - string: " << Brief(string());
997   os << "\n - index: " << index();
998   JSObjectPrintBody(os, *this);
999 }
1000 
JSAsyncFromSyncIteratorPrint(std::ostream & os)1001 void JSAsyncFromSyncIterator::JSAsyncFromSyncIteratorPrint(
1002     std::ostream& os) {  // NOLINT
1003   JSObjectPrintHeader(os, *this, "JSAsyncFromSyncIterator");
1004   os << "\n - sync_iterator: " << Brief(sync_iterator());
1005   os << "\n - next: " << Brief(next());
1006   JSObjectPrintBody(os, *this);
1007 }
1008 
JSPrimitiveWrapperPrint(std::ostream & os)1009 void JSPrimitiveWrapper::JSPrimitiveWrapperPrint(std::ostream& os) {  // NOLINT
1010   JSObjectPrintHeader(os, *this, "JSPrimitiveWrapper");
1011   os << "\n - value: " << Brief(value());
1012   JSObjectPrintBody(os, *this);
1013 }
1014 
JSMessageObjectPrint(std::ostream & os)1015 void JSMessageObject::JSMessageObjectPrint(std::ostream& os) {  // NOLINT
1016   JSObjectPrintHeader(os, *this, "JSMessageObject");
1017   os << "\n - type: " << static_cast<int>(type());
1018   os << "\n - arguments: " << Brief(argument());
1019   os << "\n - start_position: " << start_position();
1020   os << "\n - end_position: " << end_position();
1021   os << "\n - script: " << Brief(script());
1022   os << "\n - stack_frames: " << Brief(stack_frames());
1023   JSObjectPrintBody(os, *this);
1024 }
1025 
StringPrint(std::ostream & os)1026 void String::StringPrint(std::ostream& os) {  // NOLINT
1027   PrintHeapObjectHeaderWithoutMap(*this, os, "String");
1028   os << ": ";
1029   os << PrefixForDebugPrint();
1030   PrintUC16(os, 0, length());
1031   os << SuffixForDebugPrint();
1032 }
1033 
NamePrint(std::ostream & os)1034 void Name::NamePrint(std::ostream& os) {  // NOLINT
1035   if (IsString()) {
1036     String::cast(*this).StringPrint(os);
1037   } else {
1038     os << Brief(*this);
1039   }
1040 }
1041 
1042 static const char* const weekdays[] = {"???", "Sun", "Mon", "Tue",
1043                                        "Wed", "Thu", "Fri", "Sat"};
1044 
JSDatePrint(std::ostream & os)1045 void JSDate::JSDatePrint(std::ostream& os) {  // NOLINT
1046   JSObjectPrintHeader(os, *this, "JSDate");
1047   os << "\n - value: " << Brief(value());
1048   if (!year().IsSmi()) {
1049     os << "\n - time = NaN\n";
1050   } else {
1051     // TODO(svenpanne) Add some basic formatting to our streams.
1052     ScopedVector<char> buf(100);
1053     SNPrintF(buf, "\n - time = %s %04d/%02d/%02d %02d:%02d:%02d\n",
1054              weekdays[weekday().IsSmi() ? Smi::ToInt(weekday()) + 1 : 0],
1055              year().IsSmi() ? Smi::ToInt(year()) : -1,
1056              month().IsSmi() ? Smi::ToInt(month()) : -1,
1057              day().IsSmi() ? Smi::ToInt(day()) : -1,
1058              hour().IsSmi() ? Smi::ToInt(hour()) : -1,
1059              min().IsSmi() ? Smi::ToInt(min()) : -1,
1060              sec().IsSmi() ? Smi::ToInt(sec()) : -1);
1061     os << buf.begin();
1062   }
1063   JSObjectPrintBody(os, *this);
1064 }
1065 
JSProxyPrint(std::ostream & os)1066 void JSProxy::JSProxyPrint(std::ostream& os) {  // NOLINT
1067   PrintHeader(os, "JSProxy");
1068   os << "\n - target: ";
1069   target().ShortPrint(os);
1070   os << "\n - handler: ";
1071   handler().ShortPrint(os);
1072   os << "\n";
1073 }
1074 
JSSetPrint(std::ostream & os)1075 void JSSet::JSSetPrint(std::ostream& os) {  // NOLINT
1076   JSObjectPrintHeader(os, *this, "JSSet");
1077   os << " - table: " << Brief(table());
1078   JSObjectPrintBody(os, *this);
1079 }
1080 
JSMapPrint(std::ostream & os)1081 void JSMap::JSMapPrint(std::ostream& os) {  // NOLINT
1082   JSObjectPrintHeader(os, *this, "JSMap");
1083   os << " - table: " << Brief(table());
1084   JSObjectPrintBody(os, *this);
1085 }
1086 
JSCollectionIteratorPrint(std::ostream & os,const char * name)1087 void JSCollectionIterator::JSCollectionIteratorPrint(
1088     std::ostream& os, const char* name) {  // NOLINT
1089   JSObjectPrintHeader(os, *this, name);
1090   os << "\n - table: " << Brief(table());
1091   os << "\n - index: " << Brief(index());
1092   JSObjectPrintBody(os, *this);
1093 }
1094 
JSSetIteratorPrint(std::ostream & os)1095 void JSSetIterator::JSSetIteratorPrint(std::ostream& os) {  // NOLINT
1096   JSCollectionIteratorPrint(os, "JSSetIterator");
1097 }
1098 
JSMapIteratorPrint(std::ostream & os)1099 void JSMapIterator::JSMapIteratorPrint(std::ostream& os) {  // NOLINT
1100   JSCollectionIteratorPrint(os, "JSMapIterator");
1101 }
1102 
WeakCellPrint(std::ostream & os)1103 void WeakCell::WeakCellPrint(std::ostream& os) {
1104   PrintHeader(os, "WeakCell");
1105   os << "\n - finalization_registry: " << Brief(finalization_registry());
1106   os << "\n - target: " << Brief(target());
1107   os << "\n - holdings: " << Brief(holdings());
1108   os << "\n - prev: " << Brief(prev());
1109   os << "\n - next: " << Brief(next());
1110   os << "\n - unregister_token: " << Brief(unregister_token());
1111   os << "\n - key_list_prev: " << Brief(key_list_prev());
1112   os << "\n - key_list_next: " << Brief(key_list_next());
1113 }
1114 
JSWeakRefPrint(std::ostream & os)1115 void JSWeakRef::JSWeakRefPrint(std::ostream& os) {
1116   JSObjectPrintHeader(os, *this, "JSWeakRef");
1117   os << "\n - target: " << Brief(target());
1118   JSObjectPrintBody(os, *this);
1119 }
1120 
JSFinalizationRegistryPrint(std::ostream & os)1121 void JSFinalizationRegistry::JSFinalizationRegistryPrint(std::ostream& os) {
1122   JSObjectPrintHeader(os, *this, "JSFinalizationRegistry");
1123   os << "\n - native_context: " << Brief(native_context());
1124   os << "\n - cleanup: " << Brief(cleanup());
1125   os << "\n - active_cells: " << Brief(active_cells());
1126   Object active_cell = active_cells();
1127   while (active_cell.IsWeakCell()) {
1128     os << "\n   - " << Brief(active_cell);
1129     active_cell = WeakCell::cast(active_cell).next();
1130   }
1131   os << "\n - cleared_cells: " << Brief(cleared_cells());
1132   Object cleared_cell = cleared_cells();
1133   while (cleared_cell.IsWeakCell()) {
1134     os << "\n   - " << Brief(cleared_cell);
1135     cleared_cell = WeakCell::cast(cleared_cell).next();
1136   }
1137   os << "\n - key_map: " << Brief(key_map());
1138   JSObjectPrintBody(os, *this);
1139 }
1140 
JSWeakMapPrint(std::ostream & os)1141 void JSWeakMap::JSWeakMapPrint(std::ostream& os) {  // NOLINT
1142   JSObjectPrintHeader(os, *this, "JSWeakMap");
1143   os << "\n - table: " << Brief(table());
1144   JSObjectPrintBody(os, *this);
1145 }
1146 
JSWeakSetPrint(std::ostream & os)1147 void JSWeakSet::JSWeakSetPrint(std::ostream& os) {  // NOLINT
1148   JSObjectPrintHeader(os, *this, "JSWeakSet");
1149   os << "\n - table: " << Brief(table());
1150   JSObjectPrintBody(os, *this);
1151 }
1152 
JSArrayBufferPrint(std::ostream & os)1153 void JSArrayBuffer::JSArrayBufferPrint(std::ostream& os) {  // NOLINT
1154   JSObjectPrintHeader(os, *this, "JSArrayBuffer");
1155   os << "\n - backing_store: " << backing_store();
1156   os << "\n - byte_length: " << byte_length();
1157   if (is_external()) os << "\n - external";
1158   if (is_detachable()) os << "\n - detachable";
1159   if (was_detached()) os << "\n - detached";
1160   if (is_shared()) os << "\n - shared";
1161   JSObjectPrintBody(os, *this, !was_detached());
1162 }
1163 
JSTypedArrayPrint(std::ostream & os)1164 void JSTypedArray::JSTypedArrayPrint(std::ostream& os) {  // NOLINT
1165   JSObjectPrintHeader(os, *this, "JSTypedArray");
1166   os << "\n - buffer: " << Brief(buffer());
1167   os << "\n - byte_offset: " << byte_offset();
1168   os << "\n - byte_length: " << byte_length();
1169   os << "\n - length: " << length();
1170   os << "\n - data_ptr: " << DataPtr();
1171   Tagged_t base_ptr = static_cast<Tagged_t>(base_pointer().ptr());
1172   os << "\n   - base_pointer: "
1173      << reinterpret_cast<void*>(static_cast<Address>(base_ptr));
1174   os << "\n   - external_pointer: "
1175      << reinterpret_cast<void*>(external_pointer());
1176   if (!buffer().IsJSArrayBuffer()) {
1177     os << "\n <invalid buffer>\n";
1178     return;
1179   }
1180   if (WasDetached()) os << "\n - detached";
1181   JSObjectPrintBody(os, *this, !WasDetached());
1182 }
1183 
JSArrayIteratorPrint(std::ostream & os)1184 void JSArrayIterator::JSArrayIteratorPrint(std::ostream& os) {  // NOLING
1185   JSObjectPrintHeader(os, *this, "JSArrayIterator");
1186   os << "\n - iterated_object: " << Brief(iterated_object());
1187   os << "\n - next_index: " << Brief(next_index());
1188   os << "\n - kind: " << kind();
1189   JSObjectPrintBody(os, *this);
1190 }
1191 
JSDataViewPrint(std::ostream & os)1192 void JSDataView::JSDataViewPrint(std::ostream& os) {  // NOLINT
1193   JSObjectPrintHeader(os, *this, "JSDataView");
1194   os << "\n - buffer =" << Brief(buffer());
1195   os << "\n - byte_offset: " << byte_offset();
1196   os << "\n - byte_length: " << byte_length();
1197   if (!buffer().IsJSArrayBuffer()) {
1198     os << "\n <invalid buffer>";
1199     return;
1200   }
1201   if (WasDetached()) os << "\n - detached";
1202   JSObjectPrintBody(os, *this, !WasDetached());
1203 }
1204 
JSBoundFunctionPrint(std::ostream & os)1205 void JSBoundFunction::JSBoundFunctionPrint(std::ostream& os) {  // NOLINT
1206   JSObjectPrintHeader(os, *this, "JSBoundFunction");
1207   os << "\n - bound_target_function: " << Brief(bound_target_function());
1208   os << "\n - bound_this: " << Brief(bound_this());
1209   os << "\n - bound_arguments: " << Brief(bound_arguments());
1210   JSObjectPrintBody(os, *this);
1211 }
1212 
JSFunctionPrint(std::ostream & os)1213 void JSFunction::JSFunctionPrint(std::ostream& os) {  // NOLINT
1214   Isolate* isolate = GetIsolate();
1215   JSObjectPrintHeader(os, *this, "Function");
1216   os << "\n - function prototype: ";
1217   if (has_prototype_slot()) {
1218     if (has_prototype()) {
1219       os << Brief(prototype());
1220       if (map().has_non_instance_prototype()) {
1221         os << " (non-instance prototype)";
1222       }
1223     }
1224     os << "\n - initial_map: ";
1225     if (has_initial_map()) os << Brief(initial_map());
1226   } else {
1227     os << "<no-prototype-slot>";
1228   }
1229   os << "\n - shared_info: " << Brief(shared());
1230   os << "\n - name: " << Brief(shared().Name());
1231 
1232   // Print Builtin name for builtin functions
1233   int builtin_index = code().builtin_index();
1234   if (Builtins::IsBuiltinId(builtin_index)) {
1235     os << "\n - builtin: " << isolate->builtins()->name(builtin_index);
1236   }
1237 
1238   os << "\n - formal_parameter_count: "
1239      << shared().internal_formal_parameter_count();
1240   os << "\n - kind: " << shared().kind();
1241   os << "\n - context: " << Brief(context());
1242   os << "\n - code: " << Brief(code());
1243   if (code().kind() == CodeKind::FOR_TESTING) {
1244     os << "\n - FOR_TESTING";
1245   } else if (ActiveTierIsIgnition()) {
1246     os << "\n - interpreted";
1247     if (shared().HasBytecodeArray()) {
1248       os << "\n - bytecode: " << shared().GetBytecodeArray();
1249     }
1250   }
1251   if (WasmExportedFunction::IsWasmExportedFunction(*this)) {
1252     WasmExportedFunction function = WasmExportedFunction::cast(*this);
1253     os << "\n - Wasm instance: " << Brief(function.instance());
1254     os << "\n - Wasm function index: " << function.function_index();
1255   }
1256   if (WasmJSFunction::IsWasmJSFunction(*this)) {
1257     WasmJSFunction function = WasmJSFunction::cast(*this);
1258     os << "\n - Wasm wrapper around: " << Brief(function.GetCallable());
1259   }
1260   shared().PrintSourceCode(os);
1261   JSObjectPrintBody(os, *this);
1262   os << " - feedback vector: ";
1263   if (!shared().HasFeedbackMetadata()) {
1264     os << "feedback metadata is not available in SFI\n";
1265   } else if (has_feedback_vector()) {
1266     feedback_vector().FeedbackVectorPrint(os);
1267   } else {
1268     os << "not available\n";
1269   }
1270 }
1271 
PrintSourceCode(std::ostream & os)1272 void SharedFunctionInfo::PrintSourceCode(std::ostream& os) {
1273   if (HasSourceCode()) {
1274     os << "\n - source code: ";
1275     String source = String::cast(Script::cast(script()).source());
1276     int start = StartPosition();
1277     int length = EndPosition() - start;
1278     std::unique_ptr<char[]> source_string = source.ToCString(
1279         DISALLOW_NULLS, FAST_STRING_TRAVERSAL, start, length, nullptr);
1280     os << source_string.get();
1281   }
1282 }
1283 
SmallOrderedHashSetPrint(std::ostream & os)1284 void SmallOrderedHashSet::SmallOrderedHashSetPrint(std::ostream& os) {
1285   PrintHeader(os, "SmallOrderedHashSet");
1286   // TODO(tebbi): Print all fields.
1287 }
1288 
SmallOrderedHashMapPrint(std::ostream & os)1289 void SmallOrderedHashMap::SmallOrderedHashMapPrint(std::ostream& os) {
1290   PrintHeader(os, "SmallOrderedHashMap");
1291   // TODO(tebbi): Print all fields.
1292 }
1293 
SmallOrderedNameDictionaryPrint(std::ostream & os)1294 void SmallOrderedNameDictionary::SmallOrderedNameDictionaryPrint(
1295     std::ostream& os) {
1296   PrintHeader(os, "SmallOrderedNameDictionary");
1297   // TODO(tebbi): Print all fields.
1298 }
1299 
SharedFunctionInfoPrint(std::ostream & os)1300 void SharedFunctionInfo::SharedFunctionInfoPrint(std::ostream& os) {  // NOLINT
1301   PrintHeader(os, "SharedFunctionInfo");
1302   os << "\n - name: ";
1303   if (HasSharedName()) {
1304     os << Brief(Name());
1305   } else {
1306     os << "<no-shared-name>";
1307   }
1308   if (HasInferredName()) {
1309     os << "\n - inferred name: " << Brief(inferred_name());
1310   }
1311   if (class_scope_has_private_brand()) {
1312     os << "\n - class_scope_has_private_brand";
1313   }
1314   if (has_static_private_methods_or_accessors()) {
1315     os << "\n - has_static_private_methods_or_accessors";
1316   }
1317   os << "\n - kind: " << kind();
1318   os << "\n - syntax kind: " << syntax_kind();
1319   if (needs_home_object()) {
1320     os << "\n - needs_home_object";
1321   }
1322   os << "\n - function_map_index: " << function_map_index();
1323   os << "\n - formal_parameter_count: " << internal_formal_parameter_count();
1324   os << "\n - expected_nof_properties: " << expected_nof_properties();
1325   os << "\n - language_mode: " << language_mode();
1326   os << "\n - data: " << Brief(function_data(kAcquireLoad));
1327   os << "\n - code (from data): ";
1328     os << Brief(GetCode());
1329   PrintSourceCode(os);
1330   // Script files are often large, thus only print their {Brief} representation.
1331   os << "\n - script: " << Brief(script());
1332   os << "\n - function token position: " << function_token_position();
1333   os << "\n - start position: " << StartPosition();
1334   os << "\n - end position: " << EndPosition();
1335   if (HasDebugInfo()) {
1336     os << "\n - debug info: " << Brief(GetDebugInfo());
1337   } else {
1338     os << "\n - no debug info";
1339   }
1340   os << "\n - scope info: " << Brief(scope_info());
1341   if (HasOuterScopeInfo()) {
1342     os << "\n - outer scope info: " << Brief(GetOuterScopeInfo());
1343   }
1344   os << "\n - length: " << length();
1345   os << "\n - feedback_metadata: ";
1346   if (HasFeedbackMetadata()) {
1347     feedback_metadata().FeedbackMetadataPrint(os);
1348   } else {
1349     os << "<none>";
1350   }
1351   os << "\n";
1352 }
1353 
JSGlobalProxyPrint(std::ostream & os)1354 void JSGlobalProxy::JSGlobalProxyPrint(std::ostream& os) {  // NOLINT
1355   JSObjectPrintHeader(os, *this, "JSGlobalProxy");
1356   if (!GetIsolate()->bootstrapper()->IsActive()) {
1357     os << "\n - native context: " << Brief(native_context());
1358   }
1359   JSObjectPrintBody(os, *this);
1360 }
1361 
JSGlobalObjectPrint(std::ostream & os)1362 void JSGlobalObject::JSGlobalObjectPrint(std::ostream& os) {  // NOLINT
1363   JSObjectPrintHeader(os, *this, "JSGlobalObject");
1364   if (!GetIsolate()->bootstrapper()->IsActive()) {
1365     os << "\n - native context: " << Brief(native_context());
1366   }
1367   os << "\n - global proxy: " << Brief(global_proxy());
1368   JSObjectPrintBody(os, *this);
1369 }
1370 
PropertyCellPrint(std::ostream & os)1371 void PropertyCell::PropertyCellPrint(std::ostream& os) {  // NOLINT
1372   PrintHeader(os, "PropertyCell");
1373   os << "\n - name: ";
1374   name().NamePrint(os);
1375   os << "\n - value: " << Brief(value());
1376   os << "\n - details: ";
1377   property_details().PrintAsSlowTo(os);
1378   PropertyCellType cell_type = property_details().cell_type();
1379   os << "\n - cell_type: ";
1380   if (value().IsTheHole()) {
1381     switch (cell_type) {
1382       case PropertyCellType::kUninitialized:
1383         os << "Uninitialized";
1384         break;
1385       case PropertyCellType::kInvalidated:
1386         os << "Invalidated";
1387         break;
1388       default:
1389         os << "??? " << static_cast<int>(cell_type);
1390         break;
1391     }
1392   } else {
1393     switch (cell_type) {
1394       case PropertyCellType::kUndefined:
1395         os << "Undefined";
1396         break;
1397       case PropertyCellType::kConstant:
1398         os << "Constant";
1399         break;
1400       case PropertyCellType::kConstantType:
1401         os << "ConstantType"
1402            << " (";
1403         switch (GetConstantType()) {
1404           case PropertyCellConstantType::kSmi:
1405             os << "Smi";
1406             break;
1407           case PropertyCellConstantType::kStableMap:
1408             os << "StableMap";
1409             break;
1410         }
1411         os << ")";
1412         break;
1413       case PropertyCellType::kMutable:
1414         os << "Mutable";
1415         break;
1416     }
1417   }
1418   os << "\n";
1419 }
1420 
CodePrint(std::ostream & os)1421 void Code::CodePrint(std::ostream& os) {  // NOLINT
1422   PrintHeader(os, "Code");
1423   os << "\n";
1424 #ifdef ENABLE_DISASSEMBLER
1425   Disassemble(nullptr, os, GetIsolate());
1426 #endif
1427 }
1428 
CodeDataContainerPrint(std::ostream & os)1429 void CodeDataContainer::CodeDataContainerPrint(std::ostream& os) {  // NOLINT
1430   PrintHeader(os, "CodeDataContainer");
1431   os << "\n - kind_specific_flags: " << kind_specific_flags();
1432   os << "\n";
1433 }
1434 
ForeignPrint(std::ostream & os)1435 void Foreign::ForeignPrint(std::ostream& os) {  // NOLINT
1436   PrintHeader(os, "Foreign");
1437   os << "\n - foreign address : " << reinterpret_cast<void*>(foreign_address());
1438   os << "\n";
1439 }
1440 
CallbackTaskPrint(std::ostream & os)1441 void CallbackTask::CallbackTaskPrint(std::ostream& os) {  // NOLINT
1442   PrintHeader(os, "CallbackTask");
1443   os << "\n - callback: " << Brief(callback());
1444   os << "\n - data: " << Brief(data());
1445   os << "\n";
1446 }
1447 
CallableTaskPrint(std::ostream & os)1448 void CallableTask::CallableTaskPrint(std::ostream& os) {  // NOLINT
1449   PrintHeader(os, "CallableTask");
1450   os << "\n - context: " << Brief(context());
1451   os << "\n - callable: " << Brief(callable());
1452   os << "\n";
1453 }
1454 
PromiseFulfillReactionJobTaskPrint(std::ostream & os)1455 void PromiseFulfillReactionJobTask::PromiseFulfillReactionJobTaskPrint(
1456     std::ostream& os) {  // NOLINT
1457   PrintHeader(os, "PromiseFulfillReactionJobTask");
1458   os << "\n - argument: " << Brief(argument());
1459   os << "\n - context: " << Brief(context());
1460   os << "\n - handler: " << Brief(handler());
1461   os << "\n - promise_or_capability: " << Brief(promise_or_capability());
1462   os << "\n";
1463 }
1464 
PromiseRejectReactionJobTaskPrint(std::ostream & os)1465 void PromiseRejectReactionJobTask::PromiseRejectReactionJobTaskPrint(
1466     std::ostream& os) {  // NOLINT
1467   PrintHeader(os, "PromiseRejectReactionJobTask");
1468   os << "\n - argument: " << Brief(argument());
1469   os << "\n - context: " << Brief(context());
1470   os << "\n - handler: " << Brief(handler());
1471   os << "\n - promise_or_capability: " << Brief(promise_or_capability());
1472   os << "\n";
1473 }
1474 
PromiseResolveThenableJobTaskPrint(std::ostream & os)1475 void PromiseResolveThenableJobTask::PromiseResolveThenableJobTaskPrint(
1476     std::ostream& os) {  // NOLINT
1477   PrintHeader(os, "PromiseResolveThenableJobTask");
1478   os << "\n - context: " << Brief(context());
1479   os << "\n - promise_to_resolve: " << Brief(promise_to_resolve());
1480   os << "\n - then: " << Brief(then());
1481   os << "\n - thenable: " << Brief(thenable());
1482   os << "\n";
1483 }
1484 
PromiseCapabilityPrint(std::ostream & os)1485 void PromiseCapability::PromiseCapabilityPrint(std::ostream& os) {  // NOLINT
1486   PrintHeader(os, "PromiseCapability");
1487   os << "\n - promise: " << Brief(promise());
1488   os << "\n - resolve: " << Brief(resolve());
1489   os << "\n - reject: " << Brief(reject());
1490   os << "\n";
1491 }
1492 
PromiseReactionPrint(std::ostream & os)1493 void PromiseReaction::PromiseReactionPrint(std::ostream& os) {  // NOLINT
1494   PrintHeader(os, "PromiseReaction");
1495   os << "\n - next: " << Brief(next());
1496   os << "\n - reject_handler: " << Brief(reject_handler());
1497   os << "\n - fulfill_handler: " << Brief(fulfill_handler());
1498   os << "\n - promise_or_capability: " << Brief(promise_or_capability());
1499   os << "\n";
1500 }
1501 
AsyncGeneratorRequestPrint(std::ostream & os)1502 void AsyncGeneratorRequest::AsyncGeneratorRequestPrint(
1503     std::ostream& os) {  // NOLINT
1504   PrintHeader(os, "AsyncGeneratorRequest");
1505   const char* mode = "Invalid!";
1506   switch (resume_mode()) {
1507     case JSGeneratorObject::kNext:
1508       mode = ".next()";
1509       break;
1510     case JSGeneratorObject::kReturn:
1511       mode = ".return()";
1512       break;
1513     case JSGeneratorObject::kThrow:
1514       mode = ".throw()";
1515       break;
1516   }
1517   os << "\n - resume mode: " << mode;
1518   os << "\n - value: " << Brief(value());
1519   os << "\n - next: " << Brief(next());
1520   os << "\n";
1521 }
1522 
SourceTextModuleInfoEntryPrint(std::ostream & os)1523 void SourceTextModuleInfoEntry::SourceTextModuleInfoEntryPrint(
1524     std::ostream& os) {  // NOLINT
1525   PrintHeader(os, "SourceTextModuleInfoEntry");
1526   os << "\n - export_name: " << Brief(export_name());
1527   os << "\n - local_name: " << Brief(local_name());
1528   os << "\n - import_name: " << Brief(import_name());
1529   os << "\n - module_request: " << module_request();
1530   os << "\n - cell_index: " << cell_index();
1531   os << "\n - beg_pos: " << beg_pos();
1532   os << "\n - end_pos: " << end_pos();
1533   os << "\n";
1534 }
1535 
PrintModuleFields(Module module,std::ostream & os)1536 static void PrintModuleFields(Module module, std::ostream& os) {
1537   os << "\n - exports: " << Brief(module.exports());
1538   os << "\n - status: " << module.status();
1539   os << "\n - exception: " << Brief(module.exception());
1540 }
1541 
ModulePrint(std::ostream & os)1542 void Module::ModulePrint(std::ostream& os) {  // NOLINT
1543   if (this->IsSourceTextModule()) {
1544     SourceTextModule::cast(*this).SourceTextModulePrint(os);
1545   } else if (this->IsSyntheticModule()) {
1546     SyntheticModule::cast(*this).SyntheticModulePrint(os);
1547   } else {
1548     UNREACHABLE();
1549   }
1550 }
1551 
SourceTextModulePrint(std::ostream & os)1552 void SourceTextModule::SourceTextModulePrint(std::ostream& os) {  // NOLINT
1553   PrintHeader(os, "SourceTextModule");
1554   PrintModuleFields(*this, os);
1555   os << "\n - origin: " << Brief(script().GetNameOrSourceURL());
1556   os << "\n - code: " << Brief(code());
1557   os << "\n - requested_modules: " << Brief(requested_modules());
1558   os << "\n - script: " << Brief(script());
1559   os << "\n - import_meta: " << Brief(import_meta());
1560   os << "\n";
1561 }
1562 
SyntheticModulePrint(std::ostream & os)1563 void SyntheticModule::SyntheticModulePrint(std::ostream& os) {  // NOLINT
1564   PrintHeader(os, "SyntheticModule");
1565   PrintModuleFields(*this, os);
1566   os << "\n - export_names: " << Brief(export_names());
1567   os << "\n";
1568 }
1569 
JSModuleNamespacePrint(std::ostream & os)1570 void JSModuleNamespace::JSModuleNamespacePrint(std::ostream& os) {  // NOLINT
1571   JSObjectPrintHeader(os, *this, "JSModuleNamespace");
1572   os << "\n - module: " << Brief(module());
1573   JSObjectPrintBody(os, *this);
1574 }
1575 
PrototypeInfoPrint(std::ostream & os)1576 void PrototypeInfo::PrototypeInfoPrint(std::ostream& os) {  // NOLINT
1577   PrintHeader(os, "PrototypeInfo");
1578   os << "\n - module namespace: " << Brief(module_namespace());
1579   os << "\n - prototype users: " << Brief(prototype_users());
1580   os << "\n - registry slot: " << registry_slot();
1581   os << "\n - object create map: " << Brief(object_create_map());
1582   os << "\n - should_be_fast_map: " << should_be_fast_map();
1583   os << "\n";
1584 }
1585 
ClassPositionsPrint(std::ostream & os)1586 void ClassPositions::ClassPositionsPrint(std::ostream& os) {  // NOLINT
1587   PrintHeader(os, "ClassPositions");
1588   os << "\n - start position: " << start();
1589   os << "\n - end position: " << end();
1590   os << "\n";
1591 }
1592 
ArrayBoilerplateDescriptionPrint(std::ostream & os)1593 void ArrayBoilerplateDescription::ArrayBoilerplateDescriptionPrint(
1594     std::ostream& os) {  // NOLINT
1595   PrintHeader(os, "ArrayBoilerplateDescription");
1596   os << "\n - elements kind: " << elements_kind();
1597   os << "\n - constant elements: " << Brief(constant_elements());
1598   os << "\n";
1599 }
1600 
AsmWasmDataPrint(std::ostream & os)1601 void AsmWasmData::AsmWasmDataPrint(std::ostream& os) {  // NOLINT
1602   PrintHeader(os, "AsmWasmData");
1603   os << "\n - native module: " << Brief(managed_native_module());
1604   os << "\n - export_wrappers: " << Brief(export_wrappers());
1605   os << "\n - uses bitset: " << uses_bitset().value();
1606   os << "\n";
1607 }
1608 
WasmTypeInfoPrint(std::ostream & os)1609 void WasmTypeInfo::WasmTypeInfoPrint(std::ostream& os) {  // NOLINT
1610   PrintHeader(os, "WasmTypeInfo");
1611   os << "\n - type address: " << reinterpret_cast<void*>(foreign_address());
1612   os << "\n - parent: " << Brief(parent());
1613   os << "\n";
1614 }
1615 
WasmStructPrint(std::ostream & os)1616 void WasmStruct::WasmStructPrint(std::ostream& os) {  // NOLINT
1617   PrintHeader(os, "WasmStruct");
1618   wasm::StructType* struct_type = type();
1619   os << "\n - fields (" << struct_type->field_count() << "):";
1620   for (uint32_t i = 0; i < struct_type->field_count(); i++) {
1621     wasm::ValueType field = struct_type->field(i);
1622     os << "\n   - " << field.short_name() << ": ";
1623     uint32_t field_offset = struct_type->field_offset(i);
1624     Address field_address = RawField(field_offset).address();
1625     switch (field.kind()) {
1626       case wasm::ValueType::kI32:
1627         os << base::ReadUnalignedValue<int32_t>(field_address);
1628         break;
1629       case wasm::ValueType::kI64:
1630         os << base::ReadUnalignedValue<int64_t>(field_address);
1631         break;
1632       case wasm::ValueType::kF32:
1633         os << base::ReadUnalignedValue<float>(field_address);
1634         break;
1635       case wasm::ValueType::kF64:
1636         os << base::ReadUnalignedValue<double>(field_address);
1637         break;
1638       case wasm::ValueType::kI8:
1639       case wasm::ValueType::kI16:
1640       case wasm::ValueType::kS128:
1641       case wasm::ValueType::kRef:
1642       case wasm::ValueType::kOptRef:
1643       case wasm::ValueType::kRtt:
1644       case wasm::ValueType::kBottom:
1645       case wasm::ValueType::kStmt:
1646         UNIMPLEMENTED();  // TODO(7748): Implement.
1647         break;
1648     }
1649   }
1650   os << "\n";
1651 }
1652 
WasmArrayPrint(std::ostream & os)1653 void WasmArray::WasmArrayPrint(std::ostream& os) {  // NOLINT
1654   PrintHeader(os, "WasmArray");
1655   wasm::ArrayType* array_type = type();
1656   uint32_t len = length();
1657   os << "\n - type: " << array_type->element_type().name();
1658   os << "\n - length: " << len;
1659   Address data_ptr = ptr() + WasmArray::kHeaderSize - kHeapObjectTag;
1660   switch (array_type->element_type().kind()) {
1661     case wasm::ValueType::kI32:
1662       PrintTypedArrayElements(os, reinterpret_cast<int32_t*>(data_ptr), len,
1663                               true);
1664       break;
1665     case wasm::ValueType::kI64:
1666       PrintTypedArrayElements(os, reinterpret_cast<int64_t*>(data_ptr), len,
1667                               true);
1668       break;
1669     case wasm::ValueType::kF32:
1670       PrintTypedArrayElements(os, reinterpret_cast<float*>(data_ptr), len,
1671                               true);
1672       break;
1673     case wasm::ValueType::kF64:
1674       PrintTypedArrayElements(os, reinterpret_cast<double*>(data_ptr), len,
1675                               true);
1676       break;
1677     case wasm::ValueType::kI8:
1678     case wasm::ValueType::kI16:
1679     case wasm::ValueType::kS128:
1680     case wasm::ValueType::kRef:
1681     case wasm::ValueType::kOptRef:
1682     case wasm::ValueType::kRtt:
1683     case wasm::ValueType::kBottom:
1684     case wasm::ValueType::kStmt:
1685       UNIMPLEMENTED();  // TODO(7748): Implement.
1686       break;
1687   }
1688   os << "\n";
1689 }
1690 
WasmExceptionTagPrint(std::ostream & os)1691 void WasmExceptionTag::WasmExceptionTagPrint(std::ostream& os) {  // NOLINT
1692   PrintHeader(os, "WasmExceptionTag");
1693   os << "\n - index: " << index();
1694   os << "\n";
1695 }
1696 
WasmInstanceObjectPrint(std::ostream & os)1697 void WasmInstanceObject::WasmInstanceObjectPrint(std::ostream& os) {  // NOLINT
1698   JSObjectPrintHeader(os, *this, "WasmInstanceObject");
1699   os << "\n - module_object: " << Brief(module_object());
1700   os << "\n - exports_object: " << Brief(exports_object());
1701   os << "\n - native_context: " << Brief(native_context());
1702   if (has_memory_object()) {
1703     os << "\n - memory_object: " << Brief(memory_object());
1704   }
1705   if (has_untagged_globals_buffer()) {
1706     os << "\n - untagged_globals_buffer: " << Brief(untagged_globals_buffer());
1707   }
1708   if (has_tagged_globals_buffer()) {
1709     os << "\n - tagged_globals_buffer: " << Brief(tagged_globals_buffer());
1710   }
1711   if (has_imported_mutable_globals_buffers()) {
1712     os << "\n - imported_mutable_globals_buffers: "
1713        << Brief(imported_mutable_globals_buffers());
1714   }
1715   for (int i = 0; i < tables().length(); i++) {
1716     os << "\n - table " << i << ": " << Brief(tables().get(i));
1717   }
1718   os << "\n - imported_function_refs: " << Brief(imported_function_refs());
1719   if (has_indirect_function_table_refs()) {
1720     os << "\n - indirect_function_table_refs: "
1721        << Brief(indirect_function_table_refs());
1722   }
1723   if (has_managed_native_allocations()) {
1724     os << "\n - managed_native_allocations: "
1725        << Brief(managed_native_allocations());
1726   }
1727   os << "\n - memory_start: " << static_cast<void*>(memory_start());
1728   os << "\n - memory_size: " << memory_size();
1729   os << "\n - memory_mask: " << AsHex(memory_mask());
1730   os << "\n - imported_function_targets: "
1731      << static_cast<void*>(imported_function_targets());
1732   os << "\n - globals_start: " << static_cast<void*>(globals_start());
1733   os << "\n - imported_mutable_globals: "
1734      << static_cast<void*>(imported_mutable_globals());
1735   os << "\n - indirect_function_table_size: " << indirect_function_table_size();
1736   os << "\n - indirect_function_table_sig_ids: "
1737      << static_cast<void*>(indirect_function_table_sig_ids());
1738   os << "\n - indirect_function_table_targets: "
1739      << static_cast<void*>(indirect_function_table_targets());
1740   JSObjectPrintBody(os, *this);
1741   os << "\n";
1742 }
1743 
WasmExportedFunctionDataPrint(std::ostream & os)1744 void WasmExportedFunctionData::WasmExportedFunctionDataPrint(
1745     std::ostream& os) {  // NOLINT
1746   PrintHeader(os, "WasmExportedFunctionData");
1747   os << "\n - wrapper_code: " << Brief(wrapper_code());
1748   os << "\n - instance: " << Brief(instance());
1749   os << "\n - jump_table_offset: " << jump_table_offset();
1750   os << "\n - function_index: " << function_index();
1751   os << "\n";
1752 }
1753 
WasmJSFunctionDataPrint(std::ostream & os)1754 void WasmJSFunctionData::WasmJSFunctionDataPrint(std::ostream& os) {  // NOLINT
1755   PrintHeader(os, "WasmJSFunctionData");
1756   os << "\n - callable: " << Brief(callable());
1757   os << "\n - wrapper_code: " << Brief(wrapper_code());
1758   os << "\n";
1759 }
1760 
WasmModuleObjectPrint(std::ostream & os)1761 void WasmModuleObject::WasmModuleObjectPrint(std::ostream& os) {  // NOLINT
1762   PrintHeader(os, "WasmModuleObject");
1763   os << "\n - module: " << module();
1764   os << "\n - native module: " << native_module();
1765   os << "\n - export wrappers: " << Brief(export_wrappers());
1766   os << "\n - script: " << Brief(script());
1767   os << "\n";
1768 }
1769 
WasmTableObjectPrint(std::ostream & os)1770 void WasmTableObject::WasmTableObjectPrint(std::ostream& os) {  // NOLINT
1771   PrintHeader(os, "WasmTableObject");
1772   os << "\n - elements: " << Brief(elements());
1773   os << "\n - maximum_length: " << Brief(maximum_length());
1774   os << "\n - dispatch_tables: " << Brief(dispatch_tables());
1775   os << "\n - raw_type: " << raw_type();
1776   os << "\n";
1777 }
1778 
WasmGlobalObjectPrint(std::ostream & os)1779 void WasmGlobalObject::WasmGlobalObjectPrint(std::ostream& os) {  // NOLINT
1780   PrintHeader(os, "WasmGlobalObject");
1781   if (type().is_reference_type()) {
1782     os << "\n - tagged_buffer: " << Brief(tagged_buffer());
1783   } else {
1784     os << "\n - untagged_buffer: " << Brief(untagged_buffer());
1785   }
1786   os << "\n - offset: " << offset();
1787   os << "\n - raw_type: " << raw_type();
1788   os << "\n - is_mutable: " << is_mutable();
1789   os << "\n - type: " << type().kind();
1790   os << "\n - is_mutable: " << is_mutable();
1791   os << "\n";
1792 }
1793 
WasmMemoryObjectPrint(std::ostream & os)1794 void WasmMemoryObject::WasmMemoryObjectPrint(std::ostream& os) {  // NOLINT
1795   PrintHeader(os, "WasmMemoryObject");
1796   os << "\n - array_buffer: " << Brief(array_buffer());
1797   os << "\n - maximum_pages: " << maximum_pages();
1798   os << "\n - instances: " << Brief(instances());
1799   os << "\n";
1800 }
1801 
WasmExceptionObjectPrint(std::ostream & os)1802 void WasmExceptionObject::WasmExceptionObjectPrint(
1803     std::ostream& os) {  // NOLINT
1804   PrintHeader(os, "WasmExceptionObject");
1805   os << "\n - serialized_signature: " << Brief(serialized_signature());
1806   os << "\n - exception_tag: " << Brief(exception_tag());
1807   os << "\n";
1808 }
1809 
LoadHandlerPrint(std::ostream & os)1810 void LoadHandler::LoadHandlerPrint(std::ostream& os) {  // NOLINT
1811   PrintHeader(os, "LoadHandler");
1812   // TODO(ishell): implement printing based on handler kind
1813   os << "\n - handler: " << Brief(smi_handler());
1814   os << "\n - validity_cell: " << Brief(validity_cell());
1815   int data_count = data_field_count();
1816   if (data_count >= 1) {
1817     os << "\n - data1: " << Brief(data1());
1818   }
1819   if (data_count >= 2) {
1820     os << "\n - data2: " << Brief(data2());
1821   }
1822   if (data_count >= 3) {
1823     os << "\n - data3: " << Brief(data3());
1824   }
1825   os << "\n";
1826 }
1827 
StoreHandlerPrint(std::ostream & os)1828 void StoreHandler::StoreHandlerPrint(std::ostream& os) {  // NOLINT
1829   PrintHeader(os, "StoreHandler");
1830   // TODO(ishell): implement printing based on handler kind
1831   os << "\n - handler: " << Brief(smi_handler());
1832   os << "\n - validity_cell: " << Brief(validity_cell());
1833   int data_count = data_field_count();
1834   if (data_count >= 1) {
1835     os << "\n - data1: " << Brief(data1());
1836   }
1837   if (data_count >= 2) {
1838     os << "\n - data2: " << Brief(data2());
1839   }
1840   if (data_count >= 3) {
1841     os << "\n - data3: " << Brief(data3());
1842   }
1843   os << "\n";
1844 }
1845 
AccessorPairPrint(std::ostream & os)1846 void AccessorPair::AccessorPairPrint(std::ostream& os) {  // NOLINT
1847   PrintHeader(os, "AccessorPair");
1848   os << "\n - getter: " << Brief(getter());
1849   os << "\n - setter: " << Brief(setter());
1850   os << "\n";
1851 }
1852 
CallHandlerInfoPrint(std::ostream & os)1853 void CallHandlerInfo::CallHandlerInfoPrint(std::ostream& os) {  // NOLINT
1854   PrintHeader(os, "CallHandlerInfo");
1855   os << "\n - callback: " << Brief(callback());
1856   os << "\n - js_callback: " << Brief(js_callback());
1857   os << "\n - data: " << Brief(data());
1858   os << "\n - side_effect_free: "
1859      << (IsSideEffectFreeCallHandlerInfo() ? "true" : "false");
1860   os << "\n";
1861 }
1862 
FunctionTemplateInfoPrint(std::ostream & os)1863 void FunctionTemplateInfo::FunctionTemplateInfoPrint(
1864     std::ostream& os) {  // NOLINT
1865   PrintHeader(os, "FunctionTemplateInfo");
1866   os << "\n - class name: " << Brief(class_name());
1867   os << "\n - tag: " << tag();
1868   os << "\n - serial_number: " << serial_number();
1869   os << "\n - property_list: " << Brief(property_list());
1870   os << "\n - call_code: " << Brief(call_code(kAcquireLoad));
1871   os << "\n - property_accessors: " << Brief(property_accessors());
1872   os << "\n - signature: " << Brief(signature());
1873   os << "\n - cached_property_name: " << Brief(cached_property_name());
1874   os << "\n - undetectable: " << (undetectable() ? "true" : "false");
1875   os << "\n - need_access_check: " << (needs_access_check() ? "true" : "false");
1876   os << "\n - instantiated: " << (instantiated() ? "true" : "false");
1877   os << "\n - rare_data: " << Brief(rare_data());
1878   os << "\n";
1879 }
1880 
WasmIndirectFunctionTablePrint(std::ostream & os)1881 void WasmIndirectFunctionTable::WasmIndirectFunctionTablePrint(
1882     std::ostream& os) {
1883   PrintHeader(os, "WasmIndirectFunctionTable");
1884   os << "\n - size: " << size();
1885   os << "\n - sig_ids: " << static_cast<void*>(sig_ids());
1886   os << "\n - targets: " << static_cast<void*>(targets());
1887   if (has_managed_native_allocations()) {
1888     os << "\n - managed_native_allocations: "
1889        << Brief(managed_native_allocations());
1890   }
1891   os << "\n - refs: " << Brief(refs());
1892   os << "\n";
1893 }
1894 
ObjectTemplateInfoPrint(std::ostream & os)1895 void ObjectTemplateInfo::ObjectTemplateInfoPrint(std::ostream& os) {  // NOLINT
1896   PrintHeader(os, "ObjectTemplateInfo");
1897   os << "\n - tag: " << tag();
1898   os << "\n - serial_number: " << serial_number();
1899   os << "\n - property_list: " << Brief(property_list());
1900   os << "\n - property_accessors: " << Brief(property_accessors());
1901   os << "\n - constructor: " << Brief(constructor());
1902   os << "\n - embedder_field_count: " << embedder_field_count();
1903   os << "\n - immutable_proto: " << (immutable_proto() ? "true" : "false");
1904   os << "\n";
1905 }
1906 
AllocationSitePrint(std::ostream & os)1907 void AllocationSite::AllocationSitePrint(std::ostream& os) {  // NOLINT
1908   PrintHeader(os, "AllocationSite");
1909   if (this->HasWeakNext()) os << "\n - weak_next: " << Brief(weak_next());
1910   os << "\n - dependent code: " << Brief(dependent_code());
1911   os << "\n - nested site: " << Brief(nested_site());
1912   os << "\n - memento found count: "
1913      << Brief(Smi::FromInt(memento_found_count()));
1914   os << "\n - memento create count: "
1915      << Brief(Smi::FromInt(memento_create_count()));
1916   os << "\n - pretenure decision: "
1917      << Brief(Smi::FromInt(pretenure_decision()));
1918   os << "\n - transition_info: ";
1919   if (!PointsToLiteral()) {
1920     ElementsKind kind = GetElementsKind();
1921     os << "Array allocation with ElementsKind " << ElementsKindToString(kind);
1922   } else if (boilerplate().IsJSArray()) {
1923     os << "Array literal with boilerplate " << Brief(boilerplate());
1924   } else {
1925     os << "Object literal with boilerplate " << Brief(boilerplate());
1926   }
1927   os << "\n";
1928 }
1929 
AllocationMementoPrint(std::ostream & os)1930 void AllocationMemento::AllocationMementoPrint(std::ostream& os) {  // NOLINT
1931   PrintHeader(os, "AllocationMemento");
1932   os << "\n - allocation site: ";
1933   if (IsValid()) {
1934     GetAllocationSite().AllocationSitePrint(os);
1935   } else {
1936     os << "<invalid>\n";
1937   }
1938 }
1939 
ScriptPrint(std::ostream & os)1940 void Script::ScriptPrint(std::ostream& os) {  // NOLINT
1941   PrintHeader(os, "Script");
1942   os << "\n - source: " << Brief(source());
1943   os << "\n - name: " << Brief(name());
1944   os << "\n - line_offset: " << line_offset();
1945   os << "\n - column_offset: " << column_offset();
1946   os << "\n - type: " << type();
1947   os << "\n - id: " << id();
1948   os << "\n - context data: " << Brief(context_data());
1949   os << "\n - compilation type: " << compilation_type();
1950   os << "\n - line ends: " << Brief(line_ends());
1951   if (type() == TYPE_WASM) {
1952     if (has_wasm_breakpoint_infos()) {
1953       os << "\n - wasm_breakpoint_infos: " << Brief(wasm_breakpoint_infos());
1954     }
1955   } else {
1956     if (has_eval_from_shared()) {
1957       os << "\n - eval from shared: " << Brief(eval_from_shared());
1958     }
1959     if (is_wrapped()) {
1960       os << "\n - wrapped arguments: " << Brief(wrapped_arguments());
1961     }
1962     os << "\n - eval from position: " << eval_from_position();
1963   }
1964   os << "\n - shared function infos: " << Brief(shared_function_infos());
1965   os << "\n";
1966 }
1967 
1968 #ifdef V8_INTL_SUPPORT
JSV8BreakIteratorPrint(std::ostream & os)1969 void JSV8BreakIterator::JSV8BreakIteratorPrint(std::ostream& os) {  // NOLINT
1970   JSObjectPrintHeader(os, *this, "JSV8BreakIterator");
1971   os << "\n - locale: " << Brief(locale());
1972   os << "\n - break iterator: " << Brief(break_iterator());
1973   os << "\n - unicode string: " << Brief(unicode_string());
1974   os << "\n - bound adopt text: " << Brief(bound_adopt_text());
1975   os << "\n - bound first: " << Brief(bound_first());
1976   os << "\n - bound next: " << Brief(bound_next());
1977   os << "\n - bound current: " << Brief(bound_current());
1978   os << "\n - bound break type: " << Brief(bound_break_type());
1979   os << "\n";
1980 }
1981 
JSCollatorPrint(std::ostream & os)1982 void JSCollator::JSCollatorPrint(std::ostream& os) {  // NOLINT
1983   JSObjectPrintHeader(os, *this, "JSCollator");
1984   os << "\n - icu collator: " << Brief(icu_collator());
1985   os << "\n - bound compare: " << Brief(bound_compare());
1986   JSObjectPrintBody(os, *this);
1987 }
1988 
JSDateTimeFormatPrint(std::ostream & os)1989 void JSDateTimeFormat::JSDateTimeFormatPrint(std::ostream& os) {  // NOLINT
1990   JSObjectPrintHeader(os, *this, "JSDateTimeFormat");
1991   os << "\n - locale: " << Brief(locale());
1992   os << "\n - icu locale: " << Brief(icu_locale());
1993   os << "\n - icu simple date format: " << Brief(icu_simple_date_format());
1994   os << "\n - icu date interval format: " << Brief(icu_date_interval_format());
1995   os << "\n - bound format: " << Brief(bound_format());
1996   os << "\n - hour cycle: " << HourCycleAsString();
1997   JSObjectPrintBody(os, *this);
1998 }
1999 
JSDisplayNamesPrint(std::ostream & os)2000 void JSDisplayNames::JSDisplayNamesPrint(std::ostream& os) {  // NOLINT
2001   JSObjectPrintHeader(os, *this, "JSDisplayNames");
2002   os << "\n - internal: " << Brief(internal());
2003   os << "\n - style: " << StyleAsString();
2004   os << "\n - fallback: " << FallbackAsString();
2005   JSObjectPrintBody(os, *this);
2006 }
2007 
JSListFormatPrint(std::ostream & os)2008 void JSListFormat::JSListFormatPrint(std::ostream& os) {  // NOLINT
2009   JSObjectPrintHeader(os, *this, "JSListFormat");
2010   os << "\n - locale: " << Brief(locale());
2011   os << "\n - style: " << StyleAsString();
2012   os << "\n - type: " << TypeAsString();
2013   os << "\n - icu formatter: " << Brief(icu_formatter());
2014   JSObjectPrintBody(os, *this);
2015 }
2016 
JSLocalePrint(std::ostream & os)2017 void JSLocale::JSLocalePrint(std::ostream& os) {  // NOLINT
2018   JSObjectPrintHeader(os, *this, "JSLocale");
2019   os << "\n - icu locale: " << Brief(icu_locale());
2020   JSObjectPrintBody(os, *this);
2021 }
2022 
JSNumberFormatPrint(std::ostream & os)2023 void JSNumberFormat::JSNumberFormatPrint(std::ostream& os) {  // NOLINT
2024   JSObjectPrintHeader(os, *this, "JSNumberFormat");
2025   os << "\n - locale: " << Brief(locale());
2026   os << "\n - icu_number_formatter: " << Brief(icu_number_formatter());
2027   os << "\n - bound_format: " << Brief(bound_format());
2028   JSObjectPrintBody(os, *this);
2029 }
2030 
JSPluralRulesPrint(std::ostream & os)2031 void JSPluralRules::JSPluralRulesPrint(std::ostream& os) {  // NOLINT
2032   JSObjectPrintHeader(os, *this, "JSPluralRules");
2033   os << "\n - locale: " << Brief(locale());
2034   os << "\n - type: " << TypeAsString();
2035   os << "\n - icu plural rules: " << Brief(icu_plural_rules());
2036   os << "\n - icu_number_formatter: " << Brief(icu_number_formatter());
2037   JSObjectPrintBody(os, *this);
2038 }
2039 
JSRelativeTimeFormatPrint(std::ostream & os)2040 void JSRelativeTimeFormat::JSRelativeTimeFormatPrint(
2041     std::ostream& os) {  // NOLINT
2042   JSObjectPrintHeader(os, *this, "JSRelativeTimeFormat");
2043   os << "\n - locale: " << Brief(locale());
2044   os << "\n - numberingSystem: " << Brief(numberingSystem());
2045   os << "\n - numeric: " << NumericAsString();
2046   os << "\n - icu formatter: " << Brief(icu_formatter());
2047   os << "\n";
2048 }
2049 
JSSegmentIteratorPrint(std::ostream & os)2050 void JSSegmentIterator::JSSegmentIteratorPrint(std::ostream& os) {  // NOLINT
2051   JSObjectPrintHeader(os, *this, "JSSegmentIterator");
2052   os << "\n - icu break iterator: " << Brief(icu_break_iterator());
2053   os << "\n - granularity: " << GranularityAsString(GetIsolate());
2054   os << "\n";
2055 }
2056 
JSSegmenterPrint(std::ostream & os)2057 void JSSegmenter::JSSegmenterPrint(std::ostream& os) {  // NOLINT
2058   JSObjectPrintHeader(os, *this, "JSSegmenter");
2059   os << "\n - locale: " << Brief(locale());
2060   os << "\n - granularity: " << GranularityAsString(GetIsolate());
2061   os << "\n - icu break iterator: " << Brief(icu_break_iterator());
2062   JSObjectPrintBody(os, *this);
2063 }
2064 
JSSegmentsPrint(std::ostream & os)2065 void JSSegments::JSSegmentsPrint(std::ostream& os) {  // NOLINT
2066   JSObjectPrintHeader(os, *this, "JSSegments");
2067   os << "\n - icu break iterator: " << Brief(icu_break_iterator());
2068   os << "\n - unicode string: " << Brief(unicode_string());
2069   os << "\n - granularity: " << GranularityAsString(GetIsolate());
2070   JSObjectPrintBody(os, *this);
2071 }
2072 #endif  // V8_INTL_SUPPORT
2073 
2074 namespace {
PrintScopeInfoList(ScopeInfo scope_info,std::ostream & os,const char * list_name,int nof_internal_slots,int start,int length)2075 void PrintScopeInfoList(ScopeInfo scope_info, std::ostream& os,
2076                         const char* list_name, int nof_internal_slots,
2077                         int start, int length) {
2078   if (length <= 0) return;
2079   int end = start + length;
2080   os << "\n - " << list_name;
2081   if (nof_internal_slots > 0) {
2082     os << " " << start << "-" << end << " [internal slots]";
2083   }
2084   os << " {\n";
2085   for (int i = nof_internal_slots; start < end; ++i, ++start) {
2086     os << "    - " << i << ": ";
2087     String::cast(scope_info.get(start)).ShortPrint(os);
2088     os << "\n";
2089   }
2090   os << "  }";
2091 }
2092 }  // namespace
2093 
ScopeInfoPrint(std::ostream & os)2094 void ScopeInfo::ScopeInfoPrint(std::ostream& os) {  // NOLINT
2095   PrintHeader(os, "ScopeInfo");
2096   if (length() == 0) {
2097     os << "\n - length = 0\n";
2098     return;
2099   }
2100   int flags = Flags();
2101 
2102   os << "\n - parameters: " << ParameterCount();
2103   os << "\n - context locals : " << ContextLocalCount();
2104 
2105   os << "\n - scope type: " << scope_type();
2106   if (SloppyEvalCanExtendVars()) os << "\n - sloppy eval";
2107   os << "\n - language mode: " << language_mode();
2108   if (is_declaration_scope()) os << "\n - declaration scope";
2109   if (HasReceiver()) {
2110     os << "\n - receiver: " << ReceiverVariableBits::decode(flags);
2111   }
2112   if (HasClassBrand()) os << "\n - has class brand";
2113   if (HasSavedClassVariableIndex()) os << "\n - has saved class variable index";
2114   if (HasNewTarget()) os << "\n - needs new target";
2115   if (HasFunctionName()) {
2116     os << "\n - function name(" << FunctionVariableBits::decode(flags) << "): ";
2117     FunctionName().ShortPrint(os);
2118   }
2119   if (IsAsmModule()) os << "\n - asm module";
2120   if (HasSimpleParameters()) os << "\n - simple parameters";
2121   os << "\n - function kind: " << function_kind();
2122   if (HasOuterScopeInfo()) {
2123     os << "\n - outer scope info: " << Brief(OuterScopeInfo());
2124   }
2125   if (HasLocalsBlockList()) {
2126     os << "\n - locals blocklist: " << Brief(LocalsBlockList());
2127   }
2128   if (HasFunctionName()) {
2129     os << "\n - function name: " << Brief(FunctionName());
2130   }
2131   if (HasInferredFunctionName()) {
2132     os << "\n - inferred function name: " << Brief(InferredFunctionName());
2133   }
2134   if (HasContextExtensionSlot()) {
2135     os << "\n - has context extension slot";
2136   }
2137 
2138   if (HasPositionInfo()) {
2139     os << "\n - start position: " << StartPosition();
2140     os << "\n - end position: " << EndPosition();
2141   }
2142   os << "\n - length: " << length();
2143   if (length() > 0) {
2144     PrintScopeInfoList(*this, os, "context slots", Context::MIN_CONTEXT_SLOTS,
2145                        ContextLocalNamesIndex(), ContextLocalCount());
2146     // TODO(neis): Print module stuff if present.
2147   }
2148   os << "\n";
2149 }
2150 
StackTraceFramePrint(std::ostream & os)2151 void StackTraceFrame::StackTraceFramePrint(std::ostream& os) {  // NOLINT
2152   PrintHeader(os, "StackTraceFrame");
2153   os << "\n - frame_index: " << frame_index();
2154   os << "\n - frame_info: " << Brief(frame_info());
2155   os << "\n";
2156 }
2157 
StackFrameInfoPrint(std::ostream & os)2158 void StackFrameInfo::StackFrameInfoPrint(std::ostream& os) {  // NOLINT
2159   PrintHeader(os, "StackFrame");
2160   os << "\n - line_number: " << line_number();
2161   os << "\n - column_number: " << column_number();
2162   os << "\n - script_id: " << script_id();
2163   os << "\n - script_name: " << Brief(script_name());
2164   os << "\n - script_name_or_source_url: "
2165      << Brief(script_name_or_source_url());
2166   os << "\n - function_name: " << Brief(function_name());
2167   os << "\n - is_eval: " << (is_eval() ? "true" : "false");
2168   os << "\n - is_constructor: " << (is_constructor() ? "true" : "false");
2169   os << "\n";
2170 }
2171 
PrintBitMask(std::ostream & os,uint32_t value)2172 static void PrintBitMask(std::ostream& os, uint32_t value) {  // NOLINT
2173   for (int i = 0; i < 32; i++) {
2174     if ((i & 7) == 0) os << " ";
2175     os << (((value & 1) == 0) ? "_" : "x");
2176     value >>= 1;
2177   }
2178 }
2179 
Print()2180 void LayoutDescriptor::Print() {
2181   StdoutStream os;
2182   this->Print(os);
2183   os << std::flush;
2184 }
2185 
ShortPrint(std::ostream & os)2186 void LayoutDescriptor::ShortPrint(std::ostream& os) {
2187   if (IsSmi()) {
2188     // Print tagged value for easy use with "jld" gdb macro.
2189     os << reinterpret_cast<void*>(ptr());
2190   } else {
2191     os << Brief(*this);
2192   }
2193 }
2194 
Print(std::ostream & os)2195 void LayoutDescriptor::Print(std::ostream& os) {  // NOLINT
2196   os << "Layout descriptor: ";
2197   if (IsFastPointerLayout()) {
2198     os << "<all tagged>";
2199   } else if (IsSmi()) {
2200     os << "fast";
2201     PrintBitMask(os, static_cast<uint32_t>(Smi::ToInt(*this)));
2202   } else if (IsOddball() && IsUninitialized()) {
2203     os << "<uninitialized>";
2204   } else {
2205     os << "slow";
2206     int num_words = number_of_layout_words();
2207     for (int i = 0; i < num_words; i++) {
2208       if (i > 0) os << " |";
2209       PrintBitMask(os, get_layout_word(i));
2210     }
2211   }
2212   os << "\n";
2213 }
2214 
PreparseDataPrint(std::ostream & os)2215 void PreparseData::PreparseDataPrint(std::ostream& os) {  // NOLINT
2216   PrintHeader(os, "PreparseData");
2217   os << "\n - data_length: " << data_length();
2218   os << "\n - children_length: " << children_length();
2219   if (data_length() > 0) {
2220     os << "\n - data-start: " << (address() + kDataStartOffset);
2221   }
2222   if (children_length() > 0) {
2223     os << "\n - children-start: " << inner_start_offset();
2224   }
2225   for (int i = 0; i < children_length(); ++i) {
2226     os << "\n - [" << i << "]: " << Brief(get_child(i));
2227   }
2228   os << "\n";
2229 }
2230 
UncompiledDataWithoutPreparseDataPrint(std::ostream & os)2231 void UncompiledDataWithoutPreparseData::UncompiledDataWithoutPreparseDataPrint(
2232     std::ostream& os) {  // NOLINT
2233   PrintHeader(os, "UncompiledDataWithoutPreparseData");
2234   os << "\n - start position: " << start_position();
2235   os << "\n - end position: " << end_position();
2236   os << "\n";
2237 }
2238 
UncompiledDataWithPreparseDataPrint(std::ostream & os)2239 void UncompiledDataWithPreparseData::UncompiledDataWithPreparseDataPrint(
2240     std::ostream& os) {  // NOLINT
2241   PrintHeader(os, "UncompiledDataWithPreparseData");
2242   os << "\n - start position: " << start_position();
2243   os << "\n - end position: " << end_position();
2244   os << "\n - preparse_data: " << Brief(preparse_data());
2245   os << "\n";
2246 }
2247 
InterpreterDataPrint(std::ostream & os)2248 void InterpreterData::InterpreterDataPrint(std::ostream& os) {  // NOLINT
2249   PrintHeader(os, "InterpreterData");
2250   os << "\n - bytecode_array: " << Brief(bytecode_array());
2251   os << "\n - interpreter_trampoline: " << Brief(interpreter_trampoline());
2252   os << "\n";
2253 }
2254 
2255 template <HeapObjectReferenceType kRefType, typename StorageType>
Print()2256 void TaggedImpl<kRefType, StorageType>::Print() {
2257   StdoutStream os;
2258   this->Print(os);
2259   os << std::flush;
2260 }
2261 
2262 template <HeapObjectReferenceType kRefType, typename StorageType>
Print(std::ostream & os)2263 void TaggedImpl<kRefType, StorageType>::Print(std::ostream& os) {
2264   Smi smi;
2265   HeapObject heap_object;
2266   if (ToSmi(&smi)) {
2267     smi.SmiPrint(os);
2268   } else if (IsCleared()) {
2269     os << "[cleared]";
2270   } else if (GetHeapObjectIfWeak(&heap_object)) {
2271     os << "[weak] ";
2272     heap_object.HeapObjectPrint(os);
2273   } else if (GetHeapObjectIfStrong(&heap_object)) {
2274     heap_object.HeapObjectPrint(os);
2275   } else {
2276     UNREACHABLE();
2277   }
2278 }
2279 
HeapNumberPrint(std::ostream & os)2280 void HeapNumber::HeapNumberPrint(std::ostream& os) {
2281   HeapNumberShortPrint(os);
2282   os << "\n";
2283 }
2284 
2285 #endif  // OBJECT_PRINT
2286 
HeapNumberShortPrint(std::ostream & os)2287 void HeapNumber::HeapNumberShortPrint(std::ostream& os) {
2288   static constexpr uint64_t kUint64AllBitsSet =
2289       static_cast<uint64_t>(int64_t{-1});
2290   // Min/max integer values representable by 52 bits of mantissa and 1 sign bit.
2291   static constexpr int64_t kMinSafeInteger =
2292       static_cast<int64_t>(kUint64AllBitsSet << 53);
2293   static constexpr int64_t kMaxSafeInteger = -(kMinSafeInteger + 1);
2294 
2295   double val = value();
2296   if (val == DoubleToInteger(val) &&
2297       val >= static_cast<double>(kMinSafeInteger) &&
2298       val <= static_cast<double>(kMaxSafeInteger)) {
2299     int64_t i = static_cast<int64_t>(val);
2300     os << i << ".0";
2301   } else {
2302     os << val;
2303   }
2304 }
2305 
2306 // TODO(cbruni): remove once the new maptracer is in place.
NameShortPrint()2307 void Name::NameShortPrint() {
2308   if (this->IsString()) {
2309     PrintF("%s", String::cast(*this).ToCString().get());
2310   } else {
2311     DCHECK(this->IsSymbol());
2312     Symbol s = Symbol::cast(*this);
2313     if (s.description().IsUndefined()) {
2314       PrintF("#<%s>", s.PrivateSymbolToName());
2315     } else {
2316       PrintF("<%s>", String::cast(s.description()).ToCString().get());
2317     }
2318   }
2319 }
2320 
2321 // TODO(cbruni): remove once the new maptracer is in place.
NameShortPrint(Vector<char> str)2322 int Name::NameShortPrint(Vector<char> str) {
2323   if (this->IsString()) {
2324     return SNPrintF(str, "%s", String::cast(*this).ToCString().get());
2325   } else {
2326     DCHECK(this->IsSymbol());
2327     Symbol s = Symbol::cast(*this);
2328     if (s.description().IsUndefined()) {
2329       return SNPrintF(str, "#<%s>", s.PrivateSymbolToName());
2330     } else {
2331       return SNPrintF(str, "<%s>",
2332                       String::cast(s.description()).ToCString().get());
2333     }
2334   }
2335 }
2336 
PrintMapDetails(std::ostream & os)2337 void Map::PrintMapDetails(std::ostream& os) {
2338   DisallowHeapAllocation no_gc;
2339   this->MapPrint(os);
2340   instance_descriptors(kRelaxedLoad).PrintDescriptors(os);
2341 }
2342 
MapPrint(std::ostream & os)2343 void Map::MapPrint(std::ostream& os) {  // NOLINT
2344 #ifdef OBJECT_PRINT
2345   PrintHeader(os, "Map");
2346 #else
2347   os << "Map=" << reinterpret_cast<void*>(ptr());
2348 #endif
2349   os << "\n - type: " << instance_type();
2350   os << "\n - instance size: ";
2351   if (instance_size() == kVariableSizeSentinel) {
2352     os << "variable";
2353   } else {
2354     os << instance_size();
2355   }
2356   if (IsJSObjectMap()) {
2357     os << "\n - inobject properties: " << GetInObjectProperties();
2358   }
2359   os << "\n - elements kind: " << ElementsKindToString(elements_kind());
2360   os << "\n - unused property fields: " << UnusedPropertyFields();
2361   os << "\n - enum length: ";
2362   if (EnumLength() == kInvalidEnumCacheSentinel) {
2363     os << "invalid";
2364   } else {
2365     os << EnumLength();
2366   }
2367   if (is_deprecated()) os << "\n - deprecated_map";
2368   if (is_stable()) os << "\n - stable_map";
2369   if (is_migration_target()) os << "\n - migration_target";
2370   if (is_dictionary_map()) os << "\n - dictionary_map";
2371   if (has_named_interceptor()) os << "\n - named_interceptor";
2372   if (has_indexed_interceptor()) os << "\n - indexed_interceptor";
2373   if (may_have_interesting_symbols()) os << "\n - may_have_interesting_symbols";
2374   if (is_undetectable()) os << "\n - undetectable";
2375   if (is_callable()) os << "\n - callable";
2376   if (is_constructor()) os << "\n - constructor";
2377   if (has_prototype_slot()) {
2378     os << "\n - has_prototype_slot";
2379     if (has_non_instance_prototype()) os << " (non-instance prototype)";
2380   }
2381   if (is_access_check_needed()) os << "\n - access_check_needed";
2382   if (!is_extensible()) os << "\n - non-extensible";
2383   if (IsContextMap()) {
2384     os << "\n - native context: " << Brief(native_context());
2385   } else if (is_prototype_map()) {
2386     os << "\n - prototype_map";
2387     os << "\n - prototype info: " << Brief(prototype_info());
2388   } else {
2389     os << "\n - back pointer: " << Brief(GetBackPointer());
2390   }
2391   os << "\n - prototype_validity cell: " << Brief(prototype_validity_cell());
2392   os << "\n - instance descriptors " << (owns_descriptors() ? "(own) " : "")
2393      << "#" << NumberOfOwnDescriptors() << ": "
2394      << Brief(instance_descriptors(kRelaxedLoad));
2395   if (FLAG_unbox_double_fields) {
2396     os << "\n - layout descriptor: ";
2397     layout_descriptor(kAcquireLoad).ShortPrint(os);
2398   }
2399 
2400   // Read-only maps can't have transitions, which is fortunate because we need
2401   // the isolate to iterate over the transitions.
2402   if (!IsReadOnlyHeapObject(*this)) {
2403     Isolate* isolate = GetIsolateFromWritableObject(*this);
2404     DisallowHeapAllocation no_gc;
2405     TransitionsAccessor transitions(isolate, *this, &no_gc);
2406     int nof_transitions = transitions.NumberOfTransitions();
2407     if (nof_transitions > 0) {
2408       os << "\n - transitions #" << nof_transitions << ": ";
2409       HeapObject heap_object;
2410       Smi smi;
2411       if (raw_transitions()->ToSmi(&smi)) {
2412         os << Brief(smi);
2413       } else if (raw_transitions()->GetHeapObject(&heap_object)) {
2414         os << Brief(heap_object);
2415       }
2416 #ifdef OBJECT_PRINT
2417       transitions.PrintTransitions(os);
2418 #endif  // OBJECT_PRINT
2419     }
2420   }
2421   os << "\n - prototype: " << Brief(prototype());
2422   if (!IsContextMap()) {
2423     os << "\n - constructor: " << Brief(GetConstructor());
2424   }
2425   os << "\n - dependent code: " << Brief(dependent_code());
2426   os << "\n - construction counter: " << construction_counter();
2427   os << "\n";
2428 }
2429 
PrintDescriptors(std::ostream & os)2430 void DescriptorArray::PrintDescriptors(std::ostream& os) {
2431   for (InternalIndex i : InternalIndex::Range(number_of_descriptors())) {
2432     Name key = GetKey(i);
2433     os << "\n  [" << i.as_int() << "]: ";
2434 #ifdef OBJECT_PRINT
2435     key.NamePrint(os);
2436 #else
2437     key.ShortPrint(os);
2438 #endif
2439     os << " ";
2440     PrintDescriptorDetails(os, i, PropertyDetails::kPrintFull);
2441   }
2442   os << "\n";
2443 }
2444 
PrintDescriptorDetails(std::ostream & os,InternalIndex descriptor,PropertyDetails::PrintMode mode)2445 void DescriptorArray::PrintDescriptorDetails(std::ostream& os,
2446                                              InternalIndex descriptor,
2447                                              PropertyDetails::PrintMode mode) {
2448   PropertyDetails details = GetDetails(descriptor);
2449   details.PrintAsFastTo(os, mode);
2450   os << " @ ";
2451   switch (details.location()) {
2452     case kField: {
2453       FieldType field_type = GetFieldType(descriptor);
2454       field_type.PrintTo(os);
2455       break;
2456     }
2457     case kDescriptor:
2458       Object value = GetStrongValue(descriptor);
2459       os << Brief(value);
2460       if (value.IsAccessorPair()) {
2461         AccessorPair pair = AccessorPair::cast(value);
2462         os << "(get: " << Brief(pair.getter())
2463            << ", set: " << Brief(pair.setter()) << ")";
2464       }
2465       break;
2466   }
2467 }
2468 
2469 #if defined(DEBUG) || defined(OBJECT_PRINT)
2470 // This method is only meant to be called from gdb for debugging purposes.
2471 // Since the string can also be in two-byte encoding, non-Latin1 characters
2472 // will be ignored in the output.
ToAsciiArray()2473 char* String::ToAsciiArray() {
2474   // Static so that subsequent calls frees previously allocated space.
2475   // This also means that previous results will be overwritten.
2476   static char* buffer = nullptr;
2477   if (buffer != nullptr) delete[] buffer;
2478   buffer = new char[length() + 1];
2479   WriteToFlat(*this, reinterpret_cast<uint8_t*>(buffer), 0, length());
2480   buffer[length()] = 0;
2481   return buffer;
2482 }
2483 
2484 // static
PrintOneTransition(std::ostream & os,Name key,Map target)2485 void TransitionsAccessor::PrintOneTransition(std::ostream& os, Name key,
2486                                              Map target) {
2487   os << "\n     ";
2488 #ifdef OBJECT_PRINT
2489   key.NamePrint(os);
2490 #else
2491   key.ShortPrint(os);
2492 #endif
2493   os << ": ";
2494   ReadOnlyRoots roots = key.GetReadOnlyRoots();
2495   if (key == roots.nonextensible_symbol()) {
2496     os << "(transition to non-extensible)";
2497   } else if (key == roots.sealed_symbol()) {
2498     os << "(transition to sealed)";
2499   } else if (key == roots.frozen_symbol()) {
2500     os << "(transition to frozen)";
2501   } else if (key == roots.elements_transition_symbol()) {
2502     os << "(transition to " << ElementsKindToString(target.elements_kind())
2503        << ")";
2504   } else if (key == roots.strict_function_transition_symbol()) {
2505     os << " (transition to strict function)";
2506   } else {
2507     DCHECK(!IsSpecialTransition(roots, key));
2508     os << "(transition to ";
2509     InternalIndex descriptor = target.LastAdded();
2510     DescriptorArray descriptors = target.instance_descriptors(kRelaxedLoad);
2511     descriptors.PrintDescriptorDetails(os, descriptor,
2512                                        PropertyDetails::kForTransitions);
2513     os << ")";
2514   }
2515   os << " -> " << Brief(target);
2516 }
2517 
PrintInternal(std::ostream & os)2518 void TransitionArray::PrintInternal(std::ostream& os) {
2519   int num_transitions = number_of_transitions();
2520   os << "Transition array #" << num_transitions << ":";
2521   for (int i = 0; i < num_transitions; i++) {
2522     Name key = GetKey(i);
2523     Map target = GetTarget(i);
2524     TransitionsAccessor::PrintOneTransition(os, key, target);
2525   }
2526   os << "\n" << std::flush;
2527 }
2528 
PrintTransitions(std::ostream & os)2529 void TransitionsAccessor::PrintTransitions(std::ostream& os) {  // NOLINT
2530   switch (encoding()) {
2531     case kPrototypeInfo:
2532     case kUninitialized:
2533     case kMigrationTarget:
2534       return;
2535     case kWeakRef: {
2536       Map target = Map::cast(raw_transitions_->GetHeapObjectAssumeWeak());
2537       Name key = GetSimpleTransitionKey(target);
2538       PrintOneTransition(os, key, target);
2539       break;
2540     }
2541     case kFullTransitionArray:
2542       return transitions().PrintInternal(os);
2543   }
2544 }
2545 
PrintTransitionTree()2546 void TransitionsAccessor::PrintTransitionTree() {
2547   StdoutStream os;
2548   os << "map= " << Brief(map_);
2549   DisallowHeapAllocation no_gc;
2550   PrintTransitionTree(os, 0, &no_gc);
2551   os << "\n" << std::flush;
2552 }
2553 
PrintTransitionTree(std::ostream & os,int level,DisallowHeapAllocation * no_gc)2554 void TransitionsAccessor::PrintTransitionTree(std::ostream& os, int level,
2555                                               DisallowHeapAllocation* no_gc) {
2556   ReadOnlyRoots roots = ReadOnlyRoots(isolate_);
2557   int num_transitions = NumberOfTransitions();
2558   if (num_transitions == 0) return;
2559   for (int i = 0; i < num_transitions; i++) {
2560     Name key = GetKey(i);
2561     Map target = GetTarget(i);
2562     os << std::endl
2563        << "  " << level << "/" << i << ":" << std::setw(level * 2 + 2) << " ";
2564     std::stringstream ss;
2565     ss << Brief(target);
2566     os << std::left << std::setw(50) << ss.str() << ": ";
2567 
2568     if (key == roots.nonextensible_symbol()) {
2569       os << "to non-extensible";
2570     } else if (key == roots.sealed_symbol()) {
2571       os << "to sealed ";
2572     } else if (key == roots.frozen_symbol()) {
2573       os << "to frozen";
2574     } else if (key == roots.elements_transition_symbol()) {
2575       os << "to " << ElementsKindToString(target.elements_kind());
2576     } else if (key == roots.strict_function_transition_symbol()) {
2577       os << "to strict function";
2578     } else {
2579 #ifdef OBJECT_PRINT
2580       key.NamePrint(os);
2581 #else
2582       key.ShortPrint(os);
2583 #endif
2584       os << " ";
2585       DCHECK(!IsSpecialTransition(ReadOnlyRoots(isolate_), key));
2586       os << "to ";
2587       InternalIndex descriptor = target.LastAdded();
2588       DescriptorArray descriptors = target.instance_descriptors(kRelaxedLoad);
2589       descriptors.PrintDescriptorDetails(os, descriptor,
2590                                          PropertyDetails::kForTransitions);
2591     }
2592     TransitionsAccessor transitions(isolate_, target, no_gc);
2593     transitions.PrintTransitionTree(os, level + 1, no_gc);
2594   }
2595 }
2596 
PrintTransitions(std::ostream & os)2597 void JSObject::PrintTransitions(std::ostream& os) {  // NOLINT
2598   DisallowHeapAllocation no_gc;
2599   TransitionsAccessor ta(GetIsolate(), map(), &no_gc);
2600   if (ta.NumberOfTransitions() == 0) return;
2601   os << "\n - transitions";
2602   ta.PrintTransitions(os);
2603 }
2604 
2605 #endif  // defined(DEBUG) || defined(OBJECT_PRINT)
2606 }  // namespace internal
2607 }  // namespace v8
2608 
2609 namespace {
2610 
GetObjectFromRaw(void * object)2611 inline i::Object GetObjectFromRaw(void* object) {
2612   i::Address object_ptr = reinterpret_cast<i::Address>(object);
2613 #ifdef V8_COMPRESS_POINTERS
2614   if (RoundDown<i::kPtrComprIsolateRootAlignment>(object_ptr) ==
2615       i::kNullAddress) {
2616     // Try to decompress pointer.
2617     i::Isolate* isolate = i::Isolate::Current();
2618     object_ptr = i::DecompressTaggedAny(isolate->isolate_root(),
2619                                         static_cast<i::Tagged_t>(object_ptr));
2620   }
2621 #endif
2622   return i::Object(object_ptr);
2623 }
2624 
2625 }  // namespace
2626 
2627 //
2628 // The following functions are used by our gdb macros.
2629 //
_v8_internal_Get_Object(void * object)2630 V8_EXPORT_PRIVATE extern i::Object _v8_internal_Get_Object(void* object) {
2631   return GetObjectFromRaw(object);
2632 }
2633 
_v8_internal_Print_Object(void * object)2634 V8_EXPORT_PRIVATE extern void _v8_internal_Print_Object(void* object) {
2635   GetObjectFromRaw(object).Print();
2636 }
2637 
_v8_internal_Print_Code(void * object)2638 V8_EXPORT_PRIVATE extern void _v8_internal_Print_Code(void* object) {
2639   i::Address address = reinterpret_cast<i::Address>(object);
2640   i::Isolate* isolate = i::Isolate::Current();
2641 
2642   {
2643     i::wasm::WasmCodeRefScope scope;
2644     i::wasm::WasmCode* wasm_code =
2645         isolate->wasm_engine()->code_manager()->LookupCode(address);
2646     if (wasm_code) {
2647       i::StdoutStream os;
2648       wasm_code->Disassemble(nullptr, os, address);
2649       return;
2650     }
2651   }
2652 
2653   if (!isolate->heap()->InSpaceSlow(address, i::CODE_SPACE) &&
2654       !isolate->heap()->InSpaceSlow(address, i::LO_SPACE) &&
2655       !i::InstructionStream::PcIsOffHeap(isolate, address) &&
2656       !i::ReadOnlyHeap::Contains(address)) {
2657     i::PrintF(
2658         "%p is not within the current isolate's large object, code, read_only "
2659         "or embedded spaces\n",
2660         object);
2661     return;
2662   }
2663 
2664   i::Code code = isolate->FindCodeObject(address);
2665   if (!code.IsCode()) {
2666     i::PrintF("No code object found containing %p\n", object);
2667     return;
2668   }
2669 #ifdef ENABLE_DISASSEMBLER
2670   i::StdoutStream os;
2671   code.Disassemble(nullptr, os, isolate, address);
2672 #else   // ENABLE_DISASSEMBLER
2673   code.Print();
2674 #endif  // ENABLE_DISASSEMBLER
2675 }
2676 
_v8_internal_Print_LayoutDescriptor(void * object)2677 V8_EXPORT_PRIVATE extern void _v8_internal_Print_LayoutDescriptor(
2678     void* object) {
2679   i::Object o(GetObjectFromRaw(object));
2680   if (!o.IsLayoutDescriptor()) {
2681     printf("Please provide a layout descriptor\n");
2682   } else {
2683     i::LayoutDescriptor::cast(o).Print();
2684   }
2685 }
2686 
_v8_internal_Print_StackTrace()2687 V8_EXPORT_PRIVATE extern void _v8_internal_Print_StackTrace() {
2688   i::Isolate* isolate = i::Isolate::Current();
2689   isolate->PrintStack(stdout);
2690 }
2691 
_v8_internal_Print_TransitionTree(void * object)2692 V8_EXPORT_PRIVATE extern void _v8_internal_Print_TransitionTree(void* object) {
2693   i::Object o(GetObjectFromRaw(object));
2694   if (!o.IsMap()) {
2695     printf("Please provide a valid Map\n");
2696   } else {
2697 #if defined(DEBUG) || defined(OBJECT_PRINT)
2698     i::DisallowHeapAllocation no_gc;
2699     i::Map map = i::Map::unchecked_cast(o);
2700     i::TransitionsAccessor transitions(i::Isolate::Current(), map, &no_gc);
2701     transitions.PrintTransitionTree();
2702 #endif
2703   }
2704 }
2705 
_v8_internal_Node_Print(void * object)2706 V8_EXPORT_PRIVATE extern void _v8_internal_Node_Print(void* object) {
2707   reinterpret_cast<i::compiler::Node*>(object)->Print();
2708 }
2709