00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024 # include "incls/_precompiled.incl"
00025
00026 #ifdef DELTA_COMPILER
00027
00028 # include "incls/_compUtils.cpp.incl"
00029
00030 PerformanceDebugger::PerformanceDebugger(Compiler* c) {
00031 this->c = c; compileReported = false;
00032 blocks = new GrowableArray<BlockPReg*>(5);
00033 reports = new GrowableArray<char*>(5);
00034 str = NULL;
00035 notInlinedBecauseNmethodTooBig = NULL;
00036 }
00037
00038 void PerformanceDebugger::start_report() {
00039 str = new stringStream(256);
00040 report_compile();
00041 }
00042
00043 void PerformanceDebugger::stop_report() {
00044 char* report = str->as_string();
00045 for (int i = reports->length() - 1; i >= 0; i--) {
00046 if (strcmp(reports->at(i), report) == 0) return;
00047 }
00048 std->print(report);
00049 reports->append(report);
00050 str = NULL;
00051 }
00052
00053 void PerformanceDebugger::report_compile() {
00054 if (!compileReported) {
00055 compileReported = true;
00056 std->print("\n*while compiling nmethod for %s:\n", c->key->print_string());
00057 }
00058 }
00059
00060
00061
00062 class Reporter {
00063 PerformanceDebugger* d;
00064 public:
00065 Reporter(PerformanceDebugger* d) { this->d = d; d->start_report(); }
00066 ~Reporter() { d->stop_report(); }
00067 };
00068
00069 void PerformanceDebugger::finish_reporting() {
00070
00071 if (DebugPerformance && notInlinedBecauseNmethodTooBig) {
00072 Reporter r(this);
00073 str->print(" did not inline the following sends because the nmethod was getting too big:");
00074 int len = notInlinedBecauseNmethodTooBig->length();
00075 for (int i = 0; i < min(9, len); i++) {
00076 if (i % 3 == 0) str->print("\n ");
00077 InlinedScope* s = notInlinedBecauseNmethodTooBig->at(i);
00078 str->print("%s ", s->key()->print_string());
00079 }
00080 if (i < len) str->print("\n (%d more sends omitted)\n", len);
00081 str->put('\n');
00082 }
00083 }
00084
00085 void PerformanceDebugger::report_context(InlinedScope* s) {
00086 if (!DebugPerformance) return;
00087 Reporter r(this);
00088 GrowableArray<Expr*>* temps = s->contextTemporaries();
00089 const int len = temps->length();
00090 int nused = 0;
00091 for (int i = 0; i < len; i++) {
00092 PReg* r = temps->at(i)->preg();
00093 if (r->uplevelR() || r->uplevelW() || (r->isBlockPReg() && !r->isUnused())) nused++;
00094 }
00095 if (nused == 0) {
00096 str->print(" could not eliminate context of scope %s (fixable compiler restriction; should be eliminated)\n", s->key()->print_string());
00097 } else {
00098 str->print(" could not eliminate context of scope %s; temp(s) still used: ", s->key()->print_string());
00099 for (int j = 0; j < len; j++) {
00100 PReg* r = temps->at(j)->preg();
00101 if (r->uplevelR() || r->uplevelW()) {
00102 str->print("%d ", j);
00103 } else if (r->isBlockPReg() && !r->isUnused()) {
00104 str->print("%d (non-inlined block)", j);
00105 }
00106 }
00107 str->print("\n");
00108 }
00109 }
00110
00111 void PerformanceDebugger::report_toobig(InlinedScope* s) {
00112 if (!DebugPerformance) return;
00113 report_compile();
00114 if (!notInlinedBecauseNmethodTooBig) notInlinedBecauseNmethodTooBig = new GrowableArray<InlinedScope*>(20);
00115 notInlinedBecauseNmethodTooBig->append(s);
00116 }
00117
00118 void PerformanceDebugger::report_uncommon(bool reoptimizing) {
00119 if (!DebugPerformance) return;
00120 Reporter r(this);
00121 if (reoptimizing) {
00122 str->print(" -- reoptimizing previously compiled 'uncommon' version of nmethod\n");
00123 } else {
00124 str->print(" -- creating 'uncommon' version of nmethod\n");
00125 }
00126 }
00127
00128 void PerformanceDebugger::report_prim_failure(primitive_desc* pd) {
00129
00130 if (!DebugPerformance || theCompiler->is_uncommon_compile()) return;
00131 Reporter r(this);
00132 str->print(" primitive failure of %s not uncommon\n", pd->name());
00133 }
00134
00135 void PerformanceDebugger::report_block(Node* n, BlockPReg* blk, char* what) {
00136 if (!DebugPerformance) return;
00137 if (blocks->contains(blk)) return;
00138 if (blk->method()->is_clean_block()) return;
00139 Reporter r(this);
00140 str->print(" could not eliminate block in ");
00141 blk->method()->home()->selector()->print_symbol_on(str);
00142 str->print(" because it is %s in scope %s at bytecode %d",
00143 what, n->scope()->key()->print_string(), n->bci());
00144 InterpretedIC* ic = n->scope()->method()->ic_at(n->bci());
00145 if (ic) str->print(" (send of %s)", ic->selector()->copy_null_terminated());
00146 str->print("\n");
00147 blocks->append(blk);
00148 }
00149
00150 #endif