1. Added support for object printing for release mode using the

objectprint=on (defaults to off) option (which defines OBJECT_PRINT).
2. Added the ability to print objects to a specified file instead of
   just stdout.
3. Added a use_verbose_printer flag (true by default) to allow some
   object printouts to be less verbose when the flag is false.
4. Fixed a bug in VSNPrintF() where it can potentially write into an
   empty char vector.

Patch by Mark Lam from Hewlett-Packard Development Company, LP

Review URL: http://codereview.chromium.org/5998001


git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@6080 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
sgjesse@chromium.org 2010-12-20 10:38:19 +00:00
parent c91f5606d0
commit e21d76a0e3
23 changed files with 977 additions and 521 deletions

View File

@ -108,11 +108,14 @@ LIBRARY_FLAGS = {
'CPPDEFINES': ['V8_INTERPRETED_REGEXP']
},
'mode:debug': {
'CPPDEFINES': ['V8_ENABLE_CHECKS']
'CPPDEFINES': ['V8_ENABLE_CHECKS', 'OBJECT_PRINT']
},
'vmstate:on': {
'CPPDEFINES': ['ENABLE_VMSTATE_TRACKING'],
},
'objectprint:on': {
'CPPDEFINES': ['OBJECT_PRINT'],
},
'protectheap:on': {
'CPPDEFINES': ['ENABLE_VMSTATE_TRACKING', 'ENABLE_HEAP_PROTECTION'],
},
@ -711,6 +714,11 @@ SIMPLE_OPTIONS = {
'default': 'off',
'help': 'enable VM state tracking'
},
'objectprint': {
'values': ['on', 'off'],
'default': 'off',
'help': 'enable object printing'
},
'protectheap': {
'values': ['on', 'off'],
'default': 'off',

View File

@ -230,7 +230,8 @@ SOURCES = {
'mode:release': [],
'mode:debug': [
'objects-debug.cc', 'prettyprinter.cc', 'regexp-macro-assembler-tracer.cc'
]
],
'objectprint:on': ['objects-debug.cc']
}

View File

@ -467,34 +467,35 @@ const char* RelocInfo::RelocModeName(RelocInfo::Mode rmode) {
}
void RelocInfo::Print() {
PrintF("%p %s", pc_, RelocModeName(rmode_));
void RelocInfo::Print(FILE* out) {
PrintF(out, "%p %s", pc_, RelocModeName(rmode_));
if (IsComment(rmode_)) {
PrintF(" (%s)", reinterpret_cast<char*>(data_));
PrintF(out, " (%s)", reinterpret_cast<char*>(data_));
} else if (rmode_ == EMBEDDED_OBJECT) {
PrintF(" (");
target_object()->ShortPrint();
PrintF(")");
PrintF(out, " (");
target_object()->ShortPrint(out);
PrintF(out, ")");
} else if (rmode_ == EXTERNAL_REFERENCE) {
ExternalReferenceEncoder ref_encoder;
PrintF(" (%s) (%p)",
PrintF(out, " (%s) (%p)",
ref_encoder.NameOfAddress(*target_reference_address()),
*target_reference_address());
} else if (IsCodeTarget(rmode_)) {
Code* code = Code::GetCodeFromTargetAddress(target_address());
PrintF(" (%s) (%p)", Code::Kind2String(code->kind()), target_address());
PrintF(out, " (%s) (%p)", Code::Kind2String(code->kind()),
target_address());
} else if (IsPosition(rmode_)) {
PrintF(" (%" V8_PTR_PREFIX "d)", data());
PrintF(out, " (%" V8_PTR_PREFIX "d)", data());
} else if (rmode_ == RelocInfo::RUNTIME_ENTRY) {
// Depotimization bailouts are stored as runtime entries.
int id = Deoptimizer::GetDeoptimizationId(
target_address(), Deoptimizer::EAGER);
if (id != Deoptimizer::kNotDeoptimizationEntry) {
PrintF(" (deoptimization bailout %d)", id);
PrintF(out, " (deoptimization bailout %d)", id);
}
}
PrintF("\n");
PrintF(out, "\n");
}
#endif // ENABLE_DISASSEMBLER

View File

@ -322,7 +322,7 @@ class RelocInfo BASE_EMBEDDED {
#ifdef ENABLE_DISASSEMBLER
// Printing
static const char* RelocModeName(Mode rmode);
void Print();
void Print(FILE* out);
#endif // ENABLE_DISASSEMBLER
#ifdef DEBUG
// Debugging

View File

@ -1096,7 +1096,7 @@ int Translation::NumberOfOperandsFor(Opcode opcode) {
}
#ifdef DEBUG
#ifdef OBJECT_PRINT
const char* Translation::StringFor(Opcode opcode) {
switch (opcode) {

View File

@ -476,7 +476,7 @@ class Translation BASE_EMBEDDED {
static int NumberOfOperandsFor(Opcode opcode);
#ifdef DEBUG
#ifdef OBJECT_PRINT
static const char* StringFor(Opcode opcode);
#endif

View File

@ -296,6 +296,9 @@ DEFINE_int(max_map_space_pages, MapSpace::kMaxMapPageIndex - 1,
DEFINE_bool(h, false, "print this message")
DEFINE_bool(new_snapshot, true, "use new snapshot implementation")
// objects.cc
DEFINE_bool(use_verbose_printer, true, "allows verbose printing")
// parser.cc
DEFINE_bool(allow_natives_syntax, false, "allow natives syntax")

File diff suppressed because it is too large Load Diff

View File

@ -553,11 +553,11 @@ Object* Object::GetPrototype() {
}
void Object::ShortPrint() {
void Object::ShortPrint(FILE* out) {
HeapStringAllocator allocator;
StringStream accumulator(&allocator);
ShortPrint(&accumulator);
accumulator.OutputToStdOut();
accumulator.OutputToFile(out);
}
@ -572,8 +572,8 @@ void Object::ShortPrint(StringStream* accumulator) {
}
void Smi::SmiPrint() {
PrintF("%d", value());
void Smi::SmiPrint(FILE* out) {
PrintF(out, "%d", value());
}
@ -587,8 +587,8 @@ void Failure::FailurePrint(StringStream* accumulator) {
}
void Failure::FailurePrint() {
PrintF("Failure(%p)", reinterpret_cast<void*>(value()));
void Failure::FailurePrint(FILE* out) {
PrintF(out, "Failure(%p)", reinterpret_cast<void*>(value()));
}
@ -1141,8 +1141,8 @@ Object* HeapNumber::HeapNumberToBoolean() {
}
void HeapNumber::HeapNumberPrint() {
PrintF("%.16g", Number());
void HeapNumber::HeapNumberPrint(FILE* out) {
PrintF(out, "%.16g", Number());
}
@ -5467,9 +5467,9 @@ Object* JSFunction::SetInstanceClassName(String* name) {
}
void JSFunction::PrintName() {
void JSFunction::PrintName(FILE* out) {
SmartPointer<char> name = shared()->DebugName()->ToCString();
PrintF("%s", *name);
PrintF(out, "%s", *name);
}
@ -5999,18 +5999,18 @@ Map* Code::FindFirstMap() {
#ifdef ENABLE_DISASSEMBLER
#ifdef DEBUG
#ifdef OBJECT_PRINT
void DeoptimizationInputData::DeoptimizationInputDataPrint() {
void DeoptimizationInputData::DeoptimizationInputDataPrint(FILE* out) {
disasm::NameConverter converter;
int deopt_count = DeoptCount();
PrintF("Deoptimization Input Data (deopt points = %d)\n", deopt_count);
PrintF(out, "Deoptimization Input Data (deopt points = %d)\n", deopt_count);
if (0 == deopt_count) return;
PrintF("%6s %6s %6s %12s\n", "index", "ast id", "argc", "commands");
PrintF(out, "%6s %6s %6s %12s\n", "index", "ast id", "argc", "commands");
for (int i = 0; i < deopt_count; i++) {
int command_count = 0;
PrintF("%6d %6d %6d",
PrintF(out, "%6d %6d %6d",
i, AstId(i)->value(), ArgumentsStackHeight(i)->value());
int translation_index = TranslationIndex(i)->value();
TranslationIterator iterator(TranslationByteArray(), translation_index);
@ -6019,7 +6019,8 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
ASSERT(Translation::BEGIN == opcode);
int frame_count = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF(" %s {count=%d}\n", Translation::StringFor(opcode), frame_count);
PrintF(out, " %s {count=%d}\n", Translation::StringFor(opcode),
frame_count);
}
for (int i = 0; i < frame_count; ++i) {
@ -6031,10 +6032,10 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
JSFunction::cast(LiteralArray()->get(function_id));
unsigned height = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("%24s %s {ast_id=%d, function=",
PrintF(out, "%24s %s {ast_id=%d, function=",
"", Translation::StringFor(opcode), ast_id);
function->PrintName();
PrintF(", height=%u}\n", height);
function->PrintName(out);
PrintF(out, ", height=%u}\n", height);
}
// Size of translation is height plus all incoming arguments including
@ -6044,13 +6045,13 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
for (int j = 0; j < size; ++j) {
opcode = static_cast<Translation::Opcode>(iterator.Next());
if (FLAG_print_code_verbose) {
PrintF("%24s %s ", "", Translation::StringFor(opcode));
PrintF(out, "%24s %s ", "", Translation::StringFor(opcode));
}
if (opcode == Translation::DUPLICATE) {
opcode = static_cast<Translation::Opcode>(iterator.Next());
if (FLAG_print_code_verbose) {
PrintF("%s ", Translation::StringFor(opcode));
PrintF(out, "%s ", Translation::StringFor(opcode));
}
--j; // Two commands share the same frame index.
}
@ -6065,7 +6066,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::REGISTER: {
int reg_code = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{input=%s}", converter.NameOfCPURegister(reg_code));
PrintF(out, "{input=%s}", converter.NameOfCPURegister(reg_code));
}
break;
}
@ -6073,7 +6074,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::INT32_REGISTER: {
int reg_code = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{input=%s}", converter.NameOfCPURegister(reg_code));
PrintF(out, "{input=%s}", converter.NameOfCPURegister(reg_code));
}
break;
}
@ -6081,7 +6082,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::DOUBLE_REGISTER: {
int reg_code = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{input=%s}",
PrintF(out, "{input=%s}",
DoubleRegister::AllocationIndexToString(reg_code));
}
break;
@ -6090,7 +6091,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::STACK_SLOT: {
int input_slot_index = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{input=%d}", input_slot_index);
PrintF(out, "{input=%d}", input_slot_index);
}
break;
}
@ -6098,7 +6099,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::INT32_STACK_SLOT: {
int input_slot_index = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{input=%d}", input_slot_index);
PrintF(out, "{input=%d}", input_slot_index);
}
break;
}
@ -6106,7 +6107,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::DOUBLE_STACK_SLOT: {
int input_slot_index = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{input=%d}", input_slot_index);
PrintF(out, "{input=%d}", input_slot_index);
}
break;
}
@ -6114,7 +6115,7 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::LITERAL: {
unsigned literal_index = iterator.Next();
if (FLAG_print_code_verbose) {
PrintF("{literal_id=%u}", literal_index);
PrintF(out, "{literal_id=%u}", literal_index);
}
break;
}
@ -6122,16 +6123,16 @@ void DeoptimizationInputData::DeoptimizationInputDataPrint() {
case Translation::ARGUMENTS_OBJECT:
break;
}
if (FLAG_print_code_verbose) PrintF("\n");
if (FLAG_print_code_verbose) PrintF(out, "\n");
}
}
if (!FLAG_print_code_verbose) PrintF(" %12d\n", command_count);
if (!FLAG_print_code_verbose) PrintF(out, " %12d\n", command_count);
}
}
void DeoptimizationOutputData::DeoptimizationOutputDataPrint() {
PrintF("Deoptimization Output Data (deopt points = %d)\n",
void DeoptimizationOutputData::DeoptimizationOutputDataPrint(FILE* out) {
PrintF(out, "Deoptimization Output Data (deopt points = %d)\n",
this->DeoptPoints());
if (this->DeoptPoints() == 0) return;
@ -6202,56 +6203,56 @@ const char* Code::PropertyType2String(PropertyType type) {
}
void Code::Disassemble(const char* name) {
PrintF("kind = %s\n", Kind2String(kind()));
void Code::Disassemble(const char* name, FILE* out) {
PrintF(out, "kind = %s\n", Kind2String(kind()));
if (is_inline_cache_stub()) {
PrintF("ic_state = %s\n", ICState2String(ic_state()));
PrintF("ic_in_loop = %d\n", ic_in_loop() == IN_LOOP);
PrintF(out, "ic_state = %s\n", ICState2String(ic_state()));
PrintF(out, "ic_in_loop = %d\n", ic_in_loop() == IN_LOOP);
if (ic_state() == MONOMORPHIC) {
PrintF("type = %s\n", PropertyType2String(type()));
PrintF(out, "type = %s\n", PropertyType2String(type()));
}
}
if ((name != NULL) && (name[0] != '\0')) {
PrintF("name = %s\n", name);
PrintF(out, "name = %s\n", name);
}
if (kind() == OPTIMIZED_FUNCTION) {
PrintF("stack_slots = %d\n", stack_slots());
PrintF(out, "stack_slots = %d\n", stack_slots());
}
PrintF("Instructions (size = %d)\n", instruction_size());
Disassembler::Decode(NULL, this);
PrintF("\n");
PrintF(out, "Instructions (size = %d)\n", instruction_size());
Disassembler::Decode(out, this);
PrintF(out, "\n");
#ifdef DEBUG
if (kind() == FUNCTION) {
DeoptimizationOutputData* data =
DeoptimizationOutputData::cast(this->deoptimization_data());
data->DeoptimizationOutputDataPrint();
data->DeoptimizationOutputDataPrint(out);
} else if (kind() == OPTIMIZED_FUNCTION) {
DeoptimizationInputData* data =
DeoptimizationInputData::cast(this->deoptimization_data());
data->DeoptimizationInputDataPrint();
data->DeoptimizationInputDataPrint(out);
}
PrintF("\n");
#endif
if (kind() == OPTIMIZED_FUNCTION) {
SafepointTable table(this);
PrintF("Safepoints (size = %u)\n", table.size());
PrintF(out, "Safepoints (size = %u)\n", table.size());
for (unsigned i = 0; i < table.length(); i++) {
unsigned pc_offset = table.GetPcOffset(i);
PrintF("%p %4d ", (instruction_start() + pc_offset), pc_offset);
PrintF(out, "%p %4d ", (instruction_start() + pc_offset), pc_offset);
table.PrintEntry(i);
PrintF(" (sp -> fp)");
PrintF(out, " (sp -> fp)");
int deoptimization_index = table.GetDeoptimizationIndex(i);
if (deoptimization_index != Safepoint::kNoDeoptimizationIndex) {
PrintF(" %6d", deoptimization_index);
PrintF(out, " %6d", deoptimization_index);
} else {
PrintF(" <none>");
PrintF(out, " <none>");
}
PrintF("\n");
PrintF(out, "\n");
}
PrintF("\n");
PrintF(out, "\n");
} else if (kind() == FUNCTION) {
unsigned offset = stack_check_table_start();
// If there is no stack check table, the "table start" will at or after
@ -6260,19 +6261,19 @@ void Code::Disassemble(const char* name) {
unsigned* address =
reinterpret_cast<unsigned*>(instruction_start() + offset);
unsigned length = address[0];
PrintF("Stack checks (size = %u)\n", length);
PrintF("ast_id pc_offset\n");
PrintF(out, "Stack checks (size = %u)\n", length);
PrintF(out, "ast_id pc_offset\n");
for (unsigned i = 0; i < length; ++i) {
unsigned index = (2 * i) + 1;
PrintF("%6u %9u\n", address[index], address[index + 1]);
PrintF(out, "%6u %9u\n", address[index], address[index + 1]);
}
PrintF("\n");
PrintF(out, "\n");
}
}
PrintF("RelocInfo (size = %d)\n", relocation_size());
for (RelocIterator it(this); !it.done(); it.next()) it.rinfo()->Print();
PrintF("\n");
for (RelocIterator it(this); !it.done(); it.next()) it.rinfo()->Print(out);
PrintF(out, "\n");
}
#endif // ENABLE_DISASSEMBLER
@ -7421,22 +7422,22 @@ bool JSObject::ShouldConvertToFastElements() {
// class. This requires us to have the template functions put
// together, so even though this function belongs in objects-debug.cc,
// we keep it here instead to satisfy certain compilers.
#ifdef DEBUG
#ifdef OBJECT_PRINT
template<typename Shape, typename Key>
void Dictionary<Shape, Key>::Print() {
void Dictionary<Shape, Key>::Print(FILE* out) {
int capacity = HashTable<Shape, Key>::Capacity();
for (int i = 0; i < capacity; i++) {
Object* k = HashTable<Shape, Key>::KeyAt(i);
if (HashTable<Shape, Key>::IsKey(k)) {
PrintF(" ");
PrintF(out, " ");
if (k->IsString()) {
String::cast(k)->StringPrint();
String::cast(k)->StringPrint(out);
} else {
k->ShortPrint();
k->ShortPrint(out);
}
PrintF(": ");
ValueAt(i)->ShortPrint();
PrintF("\n");
PrintF(out, ": ");
ValueAt(i)->ShortPrint(out);
PrintF(out, "\n");
}
}
}

View File

@ -607,10 +607,18 @@ class MaybeObject BASE_EMBEDDED {
return reinterpret_cast<Object*>(this);
}
#ifdef DEBUG
#ifdef OBJECT_PRINT
// Prints this object with details.
void Print();
void PrintLn();
inline void Print() {
Print(stdout);
};
inline void PrintLn() {
PrintLn(stdout);
}
void Print(FILE* out);
void PrintLn(FILE* out);
#endif
#ifdef DEBUG
// Verifies the object.
void Verify();
#endif
@ -762,7 +770,10 @@ class Object : public MaybeObject {
#endif
// Prints this object without details.
void ShortPrint();
inline void ShortPrint() {
ShortPrint(stdout);
}
void ShortPrint(FILE* out);
// Prints this object without details to a message accumulator.
void ShortPrint(StringStream* accumulator);
@ -801,7 +812,10 @@ class Smi: public Object {
static inline Smi* cast(Object* object);
// Dispatched behavior.
void SmiPrint();
inline void SmiPrint() {
SmiPrint(stdout);
}
void SmiPrint(FILE* out);
void SmiPrint(StringStream* accumulator);
#ifdef DEBUG
void SmiVerify();
@ -870,7 +884,10 @@ class Failure: public MaybeObject {
static inline Failure* cast(MaybeObject* object);
// Dispatched behavior.
void FailurePrint();
inline void FailurePrint() {
FailurePrint(stdout);
}
void FailurePrint(FILE* out);
void FailurePrint(StringStream* accumulator);
#ifdef DEBUG
void FailureVerify();
@ -1099,14 +1116,23 @@ class HeapObject: public Object {
// Dispatched behavior.
void HeapObjectShortPrint(StringStream* accumulator);
#ifdef OBJECT_PRINT
inline void HeapObjectPrint() {
HeapObjectPrint(stdout);
}
void HeapObjectPrint(FILE* out);
#endif
#ifdef DEBUG
void HeapObjectPrint();
void HeapObjectVerify();
inline void VerifyObjectField(int offset);
inline void VerifySmiField(int offset);
#endif
void PrintHeader(const char* id);
#ifdef OBJECT_PRINT
void PrintHeader(FILE* out, const char* id);
#endif
#ifdef DEBUG
// Verify a pointer is a valid HeapObject pointer that points to object
// areas in the heap.
static void VerifyHeapPointer(Object* p);
@ -1189,7 +1215,10 @@ class HeapNumber: public HeapObject {
// Dispatched behavior.
Object* HeapNumberToBoolean();
void HeapNumberPrint();
inline void HeapNumberPrint() {
HeapNumberPrint(stdout);
}
void HeapNumberPrint(FILE* out);
void HeapNumberPrint(StringStream* accumulator);
#ifdef DEBUG
void HeapNumberVerify();
@ -1649,12 +1678,28 @@ class JSObject: public HeapObject {
// Dispatched behavior.
void JSObjectShortPrint(StringStream* accumulator);
#ifdef OBJECT_PRINT
inline void JSObjectPrint() {
JSObjectPrint(stdout);
}
void JSObjectPrint(FILE* out);
#endif
#ifdef DEBUG
void JSObjectPrint();
void JSObjectVerify();
void PrintProperties();
void PrintElements();
#endif
#ifdef OBJECT_PRINT
inline void PrintProperties() {
PrintProperties(stdout);
}
void PrintProperties(FILE* out);
inline void PrintElements() {
PrintElements(stdout);
}
void PrintElements(FILE* out);
#endif
#ifdef DEBUG
// Structure for collecting spill information about JSObjects.
class SpillInformation {
public:
@ -1835,8 +1880,13 @@ class FixedArray: public HeapObject {
static const int kMaxLength = (kMaxSize - kHeaderSize) / kPointerSize;
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void FixedArrayPrint() {
FixedArrayPrint(stdout);
}
void FixedArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void FixedArrayPrint();
void FixedArrayVerify();
// Checks if two FixedArrays have identical contents.
bool IsEqualTo(FixedArray* other);
@ -2012,10 +2062,15 @@ class DescriptorArray: public FixedArray {
static const int kEnumCacheBridgeCacheOffset =
kEnumCacheBridgeEnumOffset + kPointerSize;
#ifdef DEBUG
#ifdef OBJECT_PRINT
// Print all the descriptors.
void PrintDescriptors();
inline void PrintDescriptors() {
PrintDescriptors(stdout);
}
void PrintDescriptors(FILE* out);
#endif
#ifdef DEBUG
// Is the descriptor array sorted and without duplicates?
bool IsSortedNoDuplicates();
@ -2396,8 +2451,11 @@ class Dictionary: public HashTable<Shape, Key> {
// Ensure enough space for n additional elements.
MUST_USE_RESULT MaybeObject* EnsureCapacity(int n, Key key);
#ifdef DEBUG
void Print();
#ifdef OBJECT_PRINT
inline void Print() {
Print(stdout);
}
void Print(FILE* out);
#endif
// Returns the key (slow).
Object* SlowReverseLookup(Object* value);
@ -2619,8 +2677,13 @@ class ByteArray: public HeapObject {
inline int ByteArraySize() {
return SizeFor(this->length());
}
#ifdef OBJECT_PRINT
inline void ByteArrayPrint() {
ByteArrayPrint(stdout);
}
void ByteArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ByteArrayPrint();
void ByteArrayVerify();
#endif
@ -2669,8 +2732,13 @@ class PixelArray: public HeapObject {
// Casting.
static inline PixelArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void PixelArrayPrint() {
PixelArrayPrint(stdout);
}
void PixelArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void PixelArrayPrint();
void PixelArrayVerify();
#endif // DEBUG
@ -2741,8 +2809,13 @@ class ExternalByteArray: public ExternalArray {
// Casting.
static inline ExternalByteArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalByteArrayPrint() {
ExternalByteArrayPrint(stdout);
}
void ExternalByteArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalByteArrayPrint();
void ExternalByteArrayVerify();
#endif // DEBUG
@ -2764,8 +2837,13 @@ class ExternalUnsignedByteArray: public ExternalArray {
// Casting.
static inline ExternalUnsignedByteArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalUnsignedByteArrayPrint() {
ExternalUnsignedByteArrayPrint(stdout);
}
void ExternalUnsignedByteArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalUnsignedByteArrayPrint();
void ExternalUnsignedByteArrayVerify();
#endif // DEBUG
@ -2787,8 +2865,13 @@ class ExternalShortArray: public ExternalArray {
// Casting.
static inline ExternalShortArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalShortArrayPrint() {
ExternalShortArrayPrint(stdout);
}
void ExternalShortArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalShortArrayPrint();
void ExternalShortArrayVerify();
#endif // DEBUG
@ -2810,8 +2893,13 @@ class ExternalUnsignedShortArray: public ExternalArray {
// Casting.
static inline ExternalUnsignedShortArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalUnsignedShortArrayPrint() {
ExternalUnsignedShortArrayPrint(stdout);
}
void ExternalUnsignedShortArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalUnsignedShortArrayPrint();
void ExternalUnsignedShortArrayVerify();
#endif // DEBUG
@ -2833,8 +2921,13 @@ class ExternalIntArray: public ExternalArray {
// Casting.
static inline ExternalIntArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalIntArrayPrint() {
ExternalIntArrayPrint(stdout);
}
void ExternalIntArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalIntArrayPrint();
void ExternalIntArrayVerify();
#endif // DEBUG
@ -2856,8 +2949,13 @@ class ExternalUnsignedIntArray: public ExternalArray {
// Casting.
static inline ExternalUnsignedIntArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalUnsignedIntArrayPrint() {
ExternalUnsignedIntArrayPrint(stdout);
}
void ExternalUnsignedIntArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalUnsignedIntArrayPrint();
void ExternalUnsignedIntArrayVerify();
#endif // DEBUG
@ -2879,8 +2977,13 @@ class ExternalFloatArray: public ExternalArray {
// Casting.
static inline ExternalFloatArray* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ExternalFloatArrayPrint() {
ExternalFloatArrayPrint(stdout);
}
void ExternalFloatArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void ExternalFloatArrayPrint();
void ExternalFloatArrayVerify();
#endif // DEBUG
@ -2960,8 +3063,8 @@ class DeoptimizationInputData: public FixedArray {
// Casting.
static inline DeoptimizationInputData* cast(Object* obj);
#ifdef DEBUG
void DeoptimizationInputDataPrint();
#ifdef OBJECT_PRINT
void DeoptimizationInputDataPrint(FILE* out);
#endif
private:
@ -2999,8 +3102,8 @@ class DeoptimizationOutputData: public FixedArray {
// Casting.
static inline DeoptimizationOutputData* cast(Object* obj);
#ifdef DEBUG
void DeoptimizationOutputDataPrint();
#ifdef OBJECT_PRINT
void DeoptimizationOutputDataPrint(FILE* out);
#endif
};
@ -3049,7 +3152,10 @@ class Code: public HeapObject {
static const char* Kind2String(Kind kind);
static const char* ICState2String(InlineCacheState state);
static const char* PropertyType2String(PropertyType type);
void Disassemble(const char* name);
inline void Disassemble(const char* name) {
Disassemble(name, stdout);
}
void Disassemble(const char* name, FILE* out);
#endif // ENABLE_DISASSEMBLER
// [instruction_size]: Size of the native instructions
@ -3242,8 +3348,13 @@ class Code: public HeapObject {
template<typename StaticVisitor>
inline void CodeIterateBody();
#ifdef OBJECT_PRINT
inline void CodePrint() {
CodePrint(stdout);
}
void CodePrint(FILE* out);
#endif
#ifdef DEBUG
void CodePrint();
void CodeVerify();
#endif
@ -3531,8 +3642,13 @@ class Map: public HeapObject {
void ClearNonLiveTransitions(Object* real_prototype);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void MapPrint() {
MapPrint(stdout);
}
void MapPrint(FILE* out);
#endif
#ifdef DEBUG
void MapPrint();
void MapVerify();
void SharedMapVerify();
#endif
@ -3688,8 +3804,13 @@ class Script: public Struct {
// resource is accessible. Otherwise, always return true.
inline bool HasValidSource();
#ifdef OBJECT_PRINT
inline void ScriptPrint() {
ScriptPrint(stdout);
}
void ScriptPrint(FILE* out);
#endif
#ifdef DEBUG
void ScriptPrint();
void ScriptVerify();
#endif
@ -4052,8 +4173,13 @@ class SharedFunctionInfo: public HeapObject {
// Dispatched behavior.
// Set max_length to -1 for unlimited length.
void SourceCodePrint(StringStream* accumulator, int max_length);
#ifdef OBJECT_PRINT
inline void SharedFunctionInfoPrint() {
SharedFunctionInfoPrint(stdout);
}
void SharedFunctionInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void SharedFunctionInfoPrint();
void SharedFunctionInfoVerify();
#endif
@ -4285,7 +4411,10 @@ class JSFunction: public JSObject {
DECL_ACCESSORS(next_function_link, Object)
// Prints the name of the function using PrintF.
void PrintName();
inline void PrintName() {
PrintName(stdout);
}
void PrintName(FILE* out);
// Casting.
static inline JSFunction* cast(Object* obj);
@ -4295,8 +4424,13 @@ class JSFunction: public JSObject {
void JSFunctionIterateBody(int object_size, ObjectVisitor* v);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void JSFunctionPrint() {
JSFunctionPrint(stdout);
}
void JSFunctionPrint(FILE* out);
#endif
#ifdef DEBUG
void JSFunctionPrint();
void JSFunctionVerify();
#endif
@ -4345,8 +4479,13 @@ class JSGlobalProxy : public JSObject {
static inline JSGlobalProxy* cast(Object* obj);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void JSGlobalProxyPrint() {
JSGlobalProxyPrint(stdout);
}
void JSGlobalProxyPrint(FILE* out);
#endif
#ifdef DEBUG
void JSGlobalProxyPrint();
void JSGlobalProxyVerify();
#endif
@ -4416,8 +4555,13 @@ class JSGlobalObject: public GlobalObject {
static inline JSGlobalObject* cast(Object* obj);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void JSGlobalObjectPrint() {
JSGlobalObjectPrint(stdout);
}
void JSGlobalObjectPrint(FILE* out);
#endif
#ifdef DEBUG
void JSGlobalObjectPrint();
void JSGlobalObjectVerify();
#endif
@ -4445,8 +4589,13 @@ class JSBuiltinsObject: public GlobalObject {
static inline JSBuiltinsObject* cast(Object* obj);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void JSBuiltinsObjectPrint() {
JSBuiltinsObjectPrint(stdout);
}
void JSBuiltinsObjectPrint(FILE* out);
#endif
#ifdef DEBUG
void JSBuiltinsObjectPrint();
void JSBuiltinsObjectVerify();
#endif
@ -4483,8 +4632,13 @@ class JSValue: public JSObject {
static inline JSValue* cast(Object* obj);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void JSValuePrint() {
JSValuePrint(stdout);
}
void JSValuePrint(FILE* out);
#endif
#ifdef DEBUG
void JSValuePrint();
void JSValueVerify();
#endif
@ -4673,8 +4827,13 @@ class CodeCache: public Struct {
static inline CodeCache* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void CodeCachePrint() {
CodeCachePrint(stdout);
}
void CodeCachePrint(FILE* out);
#endif
#ifdef DEBUG
void CodeCachePrint();
void CodeCacheVerify();
#endif
@ -4975,8 +5134,13 @@ class String: public HeapObject {
// Dispatched behavior.
void StringShortPrint(StringStream* accumulator);
#ifdef OBJECT_PRINT
inline void StringPrint() {
StringPrint(stdout);
}
void StringPrint(FILE* out);
#endif
#ifdef DEBUG
void StringPrint();
void StringVerify();
#endif
inline bool IsFlat();
@ -5531,7 +5695,12 @@ class JSGlobalPropertyCell: public HeapObject {
#ifdef DEBUG
void JSGlobalPropertyCellVerify();
void JSGlobalPropertyCellPrint();
#endif
#ifdef OBJECT_PRINT
inline void JSGlobalPropertyCellPrint() {
JSGlobalPropertyCellPrint(stdout);
}
void JSGlobalPropertyCellPrint(FILE* out);
#endif
// Layout description.
@ -5566,8 +5735,13 @@ class Proxy: public HeapObject {
template<typename StaticVisitor>
inline void ProxyIterateBody();
#ifdef OBJECT_PRINT
inline void ProxyPrint() {
ProxyPrint(stdout);
}
void ProxyPrint(FILE* out);
#endif
#ifdef DEBUG
void ProxyPrint();
void ProxyVerify();
#endif
@ -5616,8 +5790,13 @@ class JSArray: public JSObject {
inline void EnsureSize(int minimum_size_of_backing_fixed_array);
// Dispatched behavior.
#ifdef OBJECT_PRINT
inline void JSArrayPrint() {
JSArrayPrint(stdout);
}
void JSArrayPrint(FILE* out);
#endif
#ifdef DEBUG
void JSArrayPrint();
void JSArrayVerify();
#endif
@ -5688,8 +5867,13 @@ class AccessorInfo: public Struct {
static inline AccessorInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void AccessorInfoPrint() {
AccessorInfoPrint(stdout);
}
void AccessorInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void AccessorInfoPrint();
void AccessorInfoVerify();
#endif
@ -5719,8 +5903,13 @@ class AccessCheckInfo: public Struct {
static inline AccessCheckInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void AccessCheckInfoPrint() {
AccessCheckInfoPrint(stdout);
}
void AccessCheckInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void AccessCheckInfoPrint();
void AccessCheckInfoVerify();
#endif
@ -5745,8 +5934,13 @@ class InterceptorInfo: public Struct {
static inline InterceptorInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void InterceptorInfoPrint() {
InterceptorInfoPrint(stdout);
}
void InterceptorInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void InterceptorInfoPrint();
void InterceptorInfoVerify();
#endif
@ -5770,8 +5964,13 @@ class CallHandlerInfo: public Struct {
static inline CallHandlerInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void CallHandlerInfoPrint() {
CallHandlerInfoPrint(stdout);
}
void CallHandlerInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void CallHandlerInfoPrint();
void CallHandlerInfoVerify();
#endif
@ -5827,8 +6026,13 @@ class FunctionTemplateInfo: public TemplateInfo {
static inline FunctionTemplateInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void FunctionTemplateInfoPrint() {
FunctionTemplateInfoPrint(stdout);
}
void FunctionTemplateInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void FunctionTemplateInfoPrint();
void FunctionTemplateInfoVerify();
#endif
@ -5870,8 +6074,13 @@ class ObjectTemplateInfo: public TemplateInfo {
static inline ObjectTemplateInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void ObjectTemplateInfoPrint() {
ObjectTemplateInfoPrint(stdout);
}
void ObjectTemplateInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void ObjectTemplateInfoPrint();
void ObjectTemplateInfoVerify();
#endif
@ -5889,8 +6098,13 @@ class SignatureInfo: public Struct {
static inline SignatureInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void SignatureInfoPrint() {
SignatureInfoPrint(stdout);
}
void SignatureInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void SignatureInfoPrint();
void SignatureInfoVerify();
#endif
@ -5909,8 +6123,13 @@ class TypeSwitchInfo: public Struct {
static inline TypeSwitchInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void TypeSwitchInfoPrint() {
TypeSwitchInfoPrint(stdout);
}
void TypeSwitchInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void TypeSwitchInfoPrint();
void TypeSwitchInfoVerify();
#endif
@ -5956,8 +6175,13 @@ class DebugInfo: public Struct {
static inline DebugInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void DebugInfoPrint() {
DebugInfoPrint(stdout);
}
void DebugInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void DebugInfoPrint();
void DebugInfoVerify();
#endif
@ -6009,8 +6233,13 @@ class BreakPointInfo: public Struct {
static inline BreakPointInfo* cast(Object* obj);
#ifdef OBJECT_PRINT
inline void BreakPointInfoPrint() {
BreakPointInfoPrint(stdout);
}
void BreakPointInfoPrint(FILE* out);
#endif
#ifdef DEBUG
void BreakPointInfoPrint();
void BreakPointInfoVerify();
#endif

View File

@ -128,6 +128,19 @@ void OS::VPrint(const char* format, va_list args) {
}
void OS::FPrint(FILE* out, const char* format, ...) {
va_list args;
va_start(args, format);
VFPrint(out, format, args);
va_end(args);
}
void OS::VFPrint(FILE* out, const char* format, va_list args) {
vfprintf(out, format, args);
}
// Print error message to console.
void OS::PrintError(const char* format, ...) {
// Minimalistic implementation for bootstrapping.

View File

@ -142,6 +142,23 @@ void OS::VPrint(const char* format, va_list args) {
}
void OS::FPrint(FILE* out, const char* format, ...) {
va_list args;
va_start(args, format);
VFPrint(out, format, args);
va_end(args);
}
void OS::VFPrint(FILE* out, const char* format, va_list args) {
#if defined(ANDROID)
LOG_PRI_VA(ANDROID_LOG_INFO, LOG_TAG, format, args);
#else
vfprintf(out, format, args);
#endif
}
void OS::PrintError(const char* format, ...) {
va_list args;
va_start(args, format);
@ -173,7 +190,9 @@ int OS::VSNPrintF(Vector<char> str,
va_list args) {
int n = vsnprintf(str.start(), str.length(), format, args);
if (n < 0 || n >= str.length()) {
str[str.length() - 1] = '\0';
// If the length is zero, the assignment fails.
if (str.length() > 0)
str[str.length() - 1] = '\0';
return -1;
} else {
return n;

View File

@ -688,6 +688,19 @@ void OS::VPrint(const char* format, va_list args) {
}
void OS::FPrint(FILE* out, const char* format, ...) {
va_list args;
va_start(args, format);
VFPrint(out, format, args);
va_end(args);
}
void OS::VFPrint(FILE* out, const char* format, va_list args) {
VPrintHelper(out, format, args);
}
// Print error message to console.
void OS::PrintError(const char* format, ...) {
va_list args;
@ -716,7 +729,8 @@ int OS::VSNPrintF(Vector<char> str, const char* format, va_list args) {
// Make sure to zero-terminate the string if the output was
// truncated or if there was an error.
if (n < 0 || n >= str.length()) {
str[str.length() - 1] = '\0';
if (str.length() > 0)
str[str.length() - 1] = '\0';
return -1;
} else {
return n;

View File

@ -184,6 +184,10 @@ class OS {
static void Print(const char* format, ...);
static void VPrint(const char* format, va_list args);
// Print output to a file. This is mostly used for debugging output.
static void FPrint(FILE* out, const char* format, ...);
static void VFPrint(FILE* out, const char* format, va_list args);
// Print error output to console. This is mostly used for error message
// output. On platforms that has standard terminal output, the output
// should go to stderr.

View File

@ -31,62 +31,62 @@ namespace v8 {
namespace internal {
#ifdef DEBUG
void LookupResult::Print() {
#ifdef OBJECT_PRINT
void LookupResult::Print(FILE* out) {
if (!IsFound()) {
PrintF("Not Found\n");
PrintF(out, "Not Found\n");
return;
}
PrintF("LookupResult:\n");
PrintF(" -cacheable = %s\n", IsCacheable() ? "true" : "false");
PrintF(" -attributes = %x\n", GetAttributes());
PrintF(out, "LookupResult:\n");
PrintF(out, " -cacheable = %s\n", IsCacheable() ? "true" : "false");
PrintF(out, " -attributes = %x\n", GetAttributes());
switch (type()) {
case NORMAL:
PrintF(" -type = normal\n");
PrintF(" -entry = %d", GetDictionaryEntry());
PrintF(out, " -type = normal\n");
PrintF(out, " -entry = %d", GetDictionaryEntry());
break;
case MAP_TRANSITION:
PrintF(" -type = map transition\n");
PrintF(" -map:\n");
GetTransitionMap()->Print();
PrintF("\n");
PrintF(out, " -type = map transition\n");
PrintF(out, " -map:\n");
GetTransitionMap()->Print(out);
PrintF(out, "\n");
break;
case CONSTANT_FUNCTION:
PrintF(" -type = constant function\n");
PrintF(" -function:\n");
GetConstantFunction()->Print();
PrintF("\n");
PrintF(out, " -type = constant function\n");
PrintF(out, " -function:\n");
GetConstantFunction()->Print(out);
PrintF(out, "\n");
break;
case FIELD:
PrintF(" -type = field\n");
PrintF(" -index = %d", GetFieldIndex());
PrintF("\n");
PrintF(out, " -type = field\n");
PrintF(out, " -index = %d", GetFieldIndex());
PrintF(out, "\n");
break;
case CALLBACKS:
PrintF(" -type = call backs\n");
PrintF(" -callback object:\n");
GetCallbackObject()->Print();
PrintF(out, " -type = call backs\n");
PrintF(out, " -callback object:\n");
GetCallbackObject()->Print(out);
break;
case INTERCEPTOR:
PrintF(" -type = lookup interceptor\n");
PrintF(out, " -type = lookup interceptor\n");
break;
case CONSTANT_TRANSITION:
PrintF(" -type = constant property transition\n");
PrintF(out, " -type = constant property transition\n");
break;
case NULL_DESCRIPTOR:
PrintF(" =type = null descriptor\n");
PrintF(out, " =type = null descriptor\n");
break;
}
}
void Descriptor::Print() {
PrintF("Descriptor ");
GetKey()->ShortPrint();
PrintF(" @ ");
GetValue()->ShortPrint();
PrintF(" %d\n", GetDetails().index());
void Descriptor::Print(FILE* out) {
PrintF(out, "Descriptor ");
GetKey()->ShortPrint(out);
PrintF(out, " @ ");
GetValue()->ShortPrint(out);
PrintF(out, " %d\n", GetDetails().index());
}

View File

@ -60,8 +60,8 @@ class Descriptor BASE_EMBEDDED {
Object* GetValue() { return value_; }
PropertyDetails GetDetails() { return details_; }
#ifdef DEBUG
void Print();
#ifdef OBJECT_PRINT
void Print(FILE* out);
#endif
void SetEnumerationIndex(int index) {
@ -310,8 +310,8 @@ class LookupResult BASE_EMBEDDED {
return GetValue();
}
#ifdef DEBUG
void Print();
#ifdef OBJECT_PRINT
void Print(FILE* out);
#endif
Object* GetValue() {

View File

@ -264,7 +264,7 @@ void StringStream::Log() {
}
void StringStream::OutputToStdOut() {
void StringStream::OutputToFile(FILE* out) {
// Dump the output to stdout, but make sure to break it up into
// manageable chunks to avoid losing parts of the output in the OS
// printing code. This is a problem on Windows in particular; see
@ -273,10 +273,10 @@ void StringStream::OutputToStdOut() {
for (unsigned next; (next = position + 2048) < length_; position = next) {
char save = buffer_[next];
buffer_[next] = '\0';
internal::PrintF("%s", &buffer_[position]);
internal::PrintF(out, "%s", &buffer_[position]);
buffer_[next] = save;
}
internal::PrintF("%s", &buffer_[position]);
internal::PrintF(out, "%s", &buffer_[position]);
}

View File

@ -138,7 +138,8 @@ class StringStream {
FmtElm arg3);
// Getting the message out.
void OutputToStdOut();
void OutputToFile(FILE* out);
void OutputToStdOut() { OutputToFile(stdout); }
void Log();
Handle<String> ToString();
SmartPointer<const char> ToCString() const;

View File

@ -45,8 +45,16 @@ void PrintF(const char* format, ...) {
}
void Flush() {
fflush(stdout);
void PrintF(FILE* out, const char* format, ...) {
va_list arguments;
va_start(arguments, format);
OS::VFPrint(out, format, arguments);
va_end(arguments);
}
void Flush(FILE* out) {
fflush(out);
}

View File

@ -42,18 +42,26 @@ namespace internal {
// so it works on MacOSX.
#if defined(__MACH__) && defined(__APPLE__)
#define PRINTF_CHECKING
#define FPRINTF_CHECKING
#else // MacOsX.
#define PRINTF_CHECKING __attribute__ ((format (printf, 1, 2)))
#define FPRINTF_CHECKING __attribute__ ((format (printf, 2, 3)))
#endif
#else
#define PRINTF_CHECKING
#define FPRINTF_CHECKING
#endif
// Our version of printf().
void PRINTF_CHECKING PrintF(const char* format, ...);
void FPRINTF_CHECKING PrintF(FILE* out, const char* format, ...);
// Our version of fflush.
void Flush();
void Flush(FILE* out);
inline void Flush() {
Flush(stdout);
}
// Read a line of characters after printing the prompt to stdout. The resulting

View File

@ -70,7 +70,8 @@
'DEBUG',
'_DEBUG',
'ENABLE_DISASSEMBLER',
'V8_ENABLE_CHECKS'
'V8_ENABLE_CHECKS',
'OBJECT_PRINT',
],
'msvs_settings': {
'VCCLCompilerTool': {

View File

@ -1850,6 +1850,7 @@
DEBUG,
ENABLE_LOGGING_AND_PROFILING,
V8_ENABLE_CHECKS,
OBJECT_PRINT,
ENABLE_VMSTATE_TRACKING,
);
GCC_SYMBOLS_PRIVATE_EXTERN = YES;
@ -1914,6 +1915,7 @@
V8_TARGET_ARCH_IA32,
DEBUG,
V8_ENABLE_CHECKS,
OBJECT_PRINT,
ENABLE_DEBUGGER_SUPPORT,
);
HEADER_SEARCH_PATHS = ../src;
@ -1976,6 +1978,7 @@
V8_TARGET_ARCH_IA32,
DEBUG,
V8_ENABLE_CHECKS,
OBJECT_PRINT,
ENABLE_DEBUGGER_SUPPORT,
);
HEADER_SEARCH_PATHS = ../src;

View File

@ -7,7 +7,7 @@
<Tool
Name="VCCLCompilerTool"
Optimization="0"
PreprocessorDefinitions="DEBUG;_DEBUG;ENABLE_DISASSEMBLER;V8_ENABLE_CHECKS"
PreprocessorDefinitions="DEBUG;_DEBUG;ENABLE_DISASSEMBLER;V8_ENABLE_CHECKS,OBJECT_PRINT"
RuntimeLibrary="1"
/>
<Tool