src/share/vm/c1/c1_Compilation.cpp

Thu, 02 Dec 2010 17:21:12 -0800

author
iveresov
date
Thu, 02 Dec 2010 17:21:12 -0800
changeset 2349
5ddfcf4b079e
parent 2314
f95d63e2154a
child 2421
2f9d59b0fa5c
permissions
-rw-r--r--

7003554: (tiered) assert(is_null_object() || handle() != NULL) failed: cannot embed null pointer
Summary: C1 with profiling doesn't check whether the MDO has been really allocated, which can silently fail if the perm gen is full. The solution is to check if the allocation failed and bailout out of inlining or compilation.
Reviewed-by: kvn, never

duke@435 1 /*
trims@1907 2 * Copyright (c) 1999, 2010, Oracle and/or its affiliates. All rights reserved.
duke@435 3 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
duke@435 4 *
duke@435 5 * This code is free software; you can redistribute it and/or modify it
duke@435 6 * under the terms of the GNU General Public License version 2 only, as
duke@435 7 * published by the Free Software Foundation.
duke@435 8 *
duke@435 9 * This code is distributed in the hope that it will be useful, but WITHOUT
duke@435 10 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
duke@435 11 * FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
duke@435 12 * version 2 for more details (a copy is included in the LICENSE file that
duke@435 13 * accompanied this code).
duke@435 14 *
duke@435 15 * You should have received a copy of the GNU General Public License version
duke@435 16 * 2 along with this work; if not, write to the Free Software Foundation,
duke@435 17 * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
duke@435 18 *
trims@1907 19 * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
trims@1907 20 * or visit www.oracle.com if you need additional information or have any
trims@1907 21 * questions.
duke@435 22 *
duke@435 23 */
duke@435 24
stefank@2314 25 #include "precompiled.hpp"
stefank@2314 26 #include "c1/c1_CFGPrinter.hpp"
stefank@2314 27 #include "c1/c1_Compilation.hpp"
stefank@2314 28 #include "c1/c1_IR.hpp"
stefank@2314 29 #include "c1/c1_LIRAssembler.hpp"
stefank@2314 30 #include "c1/c1_LinearScan.hpp"
stefank@2314 31 #include "c1/c1_MacroAssembler.hpp"
stefank@2314 32 #include "c1/c1_ValueMap.hpp"
stefank@2314 33 #include "c1/c1_ValueStack.hpp"
stefank@2314 34 #include "code/debugInfoRec.hpp"
duke@435 35
duke@435 36
duke@435 37 typedef enum {
duke@435 38 _t_compile,
duke@435 39 _t_setup,
duke@435 40 _t_optimizeIR,
duke@435 41 _t_buildIR,
duke@435 42 _t_emit_lir,
duke@435 43 _t_linearScan,
duke@435 44 _t_lirGeneration,
duke@435 45 _t_lir_schedule,
duke@435 46 _t_codeemit,
duke@435 47 _t_codeinstall,
duke@435 48 max_phase_timers
duke@435 49 } TimerName;
duke@435 50
duke@435 51 static const char * timer_name[] = {
duke@435 52 "compile",
duke@435 53 "setup",
duke@435 54 "optimizeIR",
duke@435 55 "buildIR",
duke@435 56 "emit_lir",
duke@435 57 "linearScan",
duke@435 58 "lirGeneration",
duke@435 59 "lir_schedule",
duke@435 60 "codeemit",
duke@435 61 "codeinstall"
duke@435 62 };
duke@435 63
duke@435 64 static elapsedTimer timers[max_phase_timers];
duke@435 65 static int totalInstructionNodes = 0;
duke@435 66
duke@435 67 class PhaseTraceTime: public TraceTime {
duke@435 68 private:
duke@435 69 JavaThread* _thread;
duke@435 70
duke@435 71 public:
duke@435 72 PhaseTraceTime(TimerName timer):
duke@435 73 TraceTime("", &timers[timer], CITime || CITimeEach, Verbose) {
duke@435 74 }
duke@435 75 };
duke@435 76
duke@435 77 // Implementation of Compilation
duke@435 78
duke@435 79
duke@435 80 #ifndef PRODUCT
duke@435 81
duke@435 82 void Compilation::maybe_print_current_instruction() {
duke@435 83 if (_current_instruction != NULL && _last_instruction_printed != _current_instruction) {
duke@435 84 _last_instruction_printed = _current_instruction;
duke@435 85 _current_instruction->print_line();
duke@435 86 }
duke@435 87 }
duke@435 88 #endif // PRODUCT
duke@435 89
duke@435 90
duke@435 91 DebugInformationRecorder* Compilation::debug_info_recorder() const {
duke@435 92 return _env->debug_info();
duke@435 93 }
duke@435 94
duke@435 95
duke@435 96 Dependencies* Compilation::dependency_recorder() const {
duke@435 97 return _env->dependencies();
duke@435 98 }
duke@435 99
duke@435 100
duke@435 101 void Compilation::initialize() {
duke@435 102 // Use an oop recorder bound to the CI environment.
duke@435 103 // (The default oop recorder is ignorant of the CI.)
duke@435 104 OopRecorder* ooprec = new OopRecorder(_env->arena());
duke@435 105 _env->set_oop_recorder(ooprec);
duke@435 106 _env->set_debug_info(new DebugInformationRecorder(ooprec));
duke@435 107 debug_info_recorder()->set_oopmaps(new OopMapSet());
duke@435 108 _env->set_dependencies(new Dependencies(_env));
duke@435 109 }
duke@435 110
duke@435 111
duke@435 112 void Compilation::build_hir() {
duke@435 113 CHECK_BAILOUT();
duke@435 114
duke@435 115 // setup ir
duke@435 116 _hir = new IR(this, method(), osr_bci());
duke@435 117 if (!_hir->is_valid()) {
duke@435 118 bailout("invalid parsing");
duke@435 119 return;
duke@435 120 }
duke@435 121
duke@435 122 #ifndef PRODUCT
duke@435 123 if (PrintCFGToFile) {
duke@435 124 CFGPrinter::print_cfg(_hir, "After Generation of HIR", true, false);
duke@435 125 }
duke@435 126 #endif
duke@435 127
duke@435 128 #ifndef PRODUCT
duke@435 129 if (PrintCFG || PrintCFG0) { tty->print_cr("CFG after parsing"); _hir->print(true); }
duke@435 130 if (PrintIR || PrintIR0 ) { tty->print_cr("IR after parsing"); _hir->print(false); }
duke@435 131 #endif
duke@435 132
duke@435 133 _hir->verify();
duke@435 134
duke@435 135 if (UseC1Optimizations) {
duke@435 136 NEEDS_CLEANUP
duke@435 137 // optimization
duke@435 138 PhaseTraceTime timeit(_t_optimizeIR);
duke@435 139
duke@435 140 _hir->optimize();
duke@435 141 }
duke@435 142
duke@435 143 _hir->verify();
duke@435 144
duke@435 145 _hir->split_critical_edges();
duke@435 146
duke@435 147 #ifndef PRODUCT
duke@435 148 if (PrintCFG || PrintCFG1) { tty->print_cr("CFG after optimizations"); _hir->print(true); }
duke@435 149 if (PrintIR || PrintIR1 ) { tty->print_cr("IR after optimizations"); _hir->print(false); }
duke@435 150 #endif
duke@435 151
duke@435 152 _hir->verify();
duke@435 153
duke@435 154 // compute block ordering for code generation
duke@435 155 // the control flow must not be changed from here on
duke@435 156 _hir->compute_code();
duke@435 157
duke@435 158 if (UseGlobalValueNumbering) {
duke@435 159 ResourceMark rm;
duke@435 160 int instructions = Instruction::number_of_instructions();
duke@435 161 GlobalValueNumbering gvn(_hir);
duke@435 162 assert(instructions == Instruction::number_of_instructions(),
duke@435 163 "shouldn't have created an instructions");
duke@435 164 }
duke@435 165
duke@435 166 // compute use counts after global value numbering
duke@435 167 _hir->compute_use_counts();
duke@435 168
duke@435 169 #ifndef PRODUCT
duke@435 170 if (PrintCFG || PrintCFG2) { tty->print_cr("CFG before code generation"); _hir->code()->print(true); }
duke@435 171 if (PrintIR || PrintIR2 ) { tty->print_cr("IR before code generation"); _hir->code()->print(false, true); }
duke@435 172 #endif
duke@435 173
duke@435 174 _hir->verify();
duke@435 175 }
duke@435 176
duke@435 177
duke@435 178 void Compilation::emit_lir() {
duke@435 179 CHECK_BAILOUT();
duke@435 180
duke@435 181 LIRGenerator gen(this, method());
duke@435 182 {
duke@435 183 PhaseTraceTime timeit(_t_lirGeneration);
duke@435 184 hir()->iterate_linear_scan_order(&gen);
duke@435 185 }
duke@435 186
duke@435 187 CHECK_BAILOUT();
duke@435 188
duke@435 189 {
duke@435 190 PhaseTraceTime timeit(_t_linearScan);
duke@435 191
duke@435 192 LinearScan* allocator = new LinearScan(hir(), &gen, frame_map());
duke@435 193 set_allocator(allocator);
duke@435 194 // Assign physical registers to LIR operands using a linear scan algorithm.
duke@435 195 allocator->do_linear_scan();
duke@435 196 CHECK_BAILOUT();
duke@435 197
duke@435 198 _max_spills = allocator->max_spills();
duke@435 199 }
duke@435 200
duke@435 201 if (BailoutAfterLIR) {
duke@435 202 if (PrintLIR && !bailed_out()) {
duke@435 203 print_LIR(hir()->code());
duke@435 204 }
duke@435 205 bailout("Bailing out because of -XX:+BailoutAfterLIR");
duke@435 206 }
duke@435 207 }
duke@435 208
duke@435 209
duke@435 210 void Compilation::emit_code_epilog(LIR_Assembler* assembler) {
duke@435 211 CHECK_BAILOUT();
duke@435 212
twisti@1639 213 CodeOffsets* code_offsets = assembler->offsets();
twisti@1639 214
duke@435 215 // generate code or slow cases
duke@435 216 assembler->emit_slow_case_stubs();
duke@435 217 CHECK_BAILOUT();
duke@435 218
duke@435 219 // generate exception adapters
duke@435 220 assembler->emit_exception_entries(exception_info_list());
duke@435 221 CHECK_BAILOUT();
duke@435 222
twisti@1639 223 // Generate code for exception handler.
twisti@1639 224 code_offsets->set_value(CodeOffsets::Exceptions, assembler->emit_exception_handler());
duke@435 225 CHECK_BAILOUT();
twisti@1639 226
twisti@1639 227 // Generate code for deopt handler.
twisti@1639 228 code_offsets->set_value(CodeOffsets::Deopt, assembler->emit_deopt_handler());
twisti@1639 229 CHECK_BAILOUT();
twisti@1639 230
twisti@2046 231 // Emit the MethodHandle deopt handler code (if required).
twisti@2046 232 if (has_method_handle_invokes()) {
twisti@2046 233 // We can use the same code as for the normal deopt handler, we
twisti@2046 234 // just need a different entry point address.
twisti@2046 235 code_offsets->set_value(CodeOffsets::DeoptMH, assembler->emit_deopt_handler());
twisti@2046 236 CHECK_BAILOUT();
twisti@2046 237 }
duke@435 238
never@1813 239 // Emit the handler to remove the activation from the stack and
never@1813 240 // dispatch to the caller.
never@1813 241 offsets()->set_value(CodeOffsets::UnwindHandler, assembler->emit_unwind_handler());
never@1813 242
duke@435 243 // done
duke@435 244 masm()->flush();
duke@435 245 }
duke@435 246
duke@435 247
iveresov@1939 248 void Compilation::setup_code_buffer(CodeBuffer* code, int call_stub_estimate) {
iveresov@1939 249 // Preinitialize the consts section to some large size:
iveresov@1939 250 int locs_buffer_size = 20 * (relocInfo::length_limit + sizeof(relocInfo));
iveresov@1939 251 char* locs_buffer = NEW_RESOURCE_ARRAY(char, locs_buffer_size);
iveresov@1939 252 code->insts()->initialize_shared_locs((relocInfo*)locs_buffer,
iveresov@1939 253 locs_buffer_size / sizeof(relocInfo));
iveresov@1939 254 code->initialize_consts_size(Compilation::desired_max_constant_size());
iveresov@1972 255 // Call stubs + two deopt handlers (regular and MH) + exception handler
iveresov@1939 256 code->initialize_stubs_size((call_stub_estimate * LIR_Assembler::call_stub_size) +
iveresov@1939 257 LIR_Assembler::exception_handler_size +
iveresov@1972 258 2 * LIR_Assembler::deopt_handler_size);
iveresov@1939 259 }
iveresov@1939 260
iveresov@1939 261
duke@435 262 int Compilation::emit_code_body() {
duke@435 263 // emit code
iveresov@1939 264 setup_code_buffer(code(), allocator()->num_calls());
duke@435 265 code()->initialize_oop_recorder(env()->oop_recorder());
duke@435 266
duke@435 267 _masm = new C1_MacroAssembler(code());
duke@435 268 _masm->set_oop_recorder(env()->oop_recorder());
duke@435 269
duke@435 270 LIR_Assembler lir_asm(this);
duke@435 271
duke@435 272 lir_asm.emit_code(hir()->code());
duke@435 273 CHECK_BAILOUT_(0);
duke@435 274
duke@435 275 emit_code_epilog(&lir_asm);
duke@435 276 CHECK_BAILOUT_(0);
duke@435 277
duke@435 278 generate_exception_handler_table();
duke@435 279
duke@435 280 #ifndef PRODUCT
duke@435 281 if (PrintExceptionHandlers && Verbose) {
duke@435 282 exception_handler_table()->print();
duke@435 283 }
duke@435 284 #endif /* PRODUCT */
duke@435 285
duke@435 286 return frame_map()->framesize();
duke@435 287 }
duke@435 288
duke@435 289
duke@435 290 int Compilation::compile_java_method() {
duke@435 291 assert(!method()->is_native(), "should not reach here");
duke@435 292
duke@435 293 if (BailoutOnExceptionHandlers) {
duke@435 294 if (method()->has_exception_handlers()) {
duke@435 295 bailout("linear scan can't handle exception handlers");
duke@435 296 }
duke@435 297 }
duke@435 298
duke@435 299 CHECK_BAILOUT_(no_frame_size);
duke@435 300
iveresov@2349 301 if (is_profiling() && !method()->ensure_method_data()) {
iveresov@2349 302 BAILOUT_("mdo allocation failed", no_frame_size);
iveresov@2138 303 }
iveresov@2138 304
duke@435 305 {
duke@435 306 PhaseTraceTime timeit(_t_buildIR);
iveresov@2138 307 build_hir();
duke@435 308 }
duke@435 309 if (BailoutAfterHIR) {
duke@435 310 BAILOUT_("Bailing out because of -XX:+BailoutAfterHIR", no_frame_size);
duke@435 311 }
duke@435 312
duke@435 313
duke@435 314 {
duke@435 315 PhaseTraceTime timeit(_t_emit_lir);
duke@435 316
duke@435 317 _frame_map = new FrameMap(method(), hir()->number_of_locks(), MAX2(4, hir()->max_stack()));
duke@435 318 emit_lir();
duke@435 319 }
duke@435 320 CHECK_BAILOUT_(no_frame_size);
duke@435 321
duke@435 322 {
duke@435 323 PhaseTraceTime timeit(_t_codeemit);
duke@435 324 return emit_code_body();
duke@435 325 }
duke@435 326 }
duke@435 327
duke@435 328 void Compilation::install_code(int frame_size) {
duke@435 329 // frame_size is in 32-bit words so adjust it intptr_t words
duke@435 330 assert(frame_size == frame_map()->framesize(), "must match");
duke@435 331 assert(in_bytes(frame_map()->framesize_in_bytes()) % sizeof(intptr_t) == 0, "must be at least pointer aligned");
duke@435 332 _env->register_method(
duke@435 333 method(),
duke@435 334 osr_bci(),
duke@435 335 &_offsets,
duke@435 336 in_bytes(_frame_map->sp_offset_for_orig_pc()),
duke@435 337 code(),
duke@435 338 in_bytes(frame_map()->framesize_in_bytes()) / sizeof(intptr_t),
duke@435 339 debug_info_recorder()->_oopmaps,
duke@435 340 exception_handler_table(),
duke@435 341 implicit_exception_table(),
duke@435 342 compiler(),
duke@435 343 _env->comp_level(),
never@1832 344 true,
duke@435 345 has_unsafe_access()
duke@435 346 );
duke@435 347 }
duke@435 348
duke@435 349
duke@435 350 void Compilation::compile_method() {
duke@435 351 // setup compilation
duke@435 352 initialize();
duke@435 353
duke@435 354 if (!method()->can_be_compiled()) {
duke@435 355 // Prevent race condition 6328518.
duke@435 356 // This can happen if the method is obsolete or breakpointed.
duke@435 357 bailout("Bailing out because method is not compilable");
duke@435 358 return;
duke@435 359 }
duke@435 360
kvn@1215 361 if (_env->jvmti_can_hotswap_or_post_breakpoint()) {
duke@435 362 // We can assert evol_method because method->can_be_compiled is true.
duke@435 363 dependency_recorder()->assert_evol_method(method());
duke@435 364 }
duke@435 365
duke@435 366 if (method()->break_at_execute()) {
duke@435 367 BREAKPOINT;
duke@435 368 }
duke@435 369
duke@435 370 #ifndef PRODUCT
duke@435 371 if (PrintCFGToFile) {
duke@435 372 CFGPrinter::print_compilation(this);
duke@435 373 }
duke@435 374 #endif
duke@435 375
duke@435 376 // compile method
duke@435 377 int frame_size = compile_java_method();
duke@435 378
duke@435 379 // bailout if method couldn't be compiled
duke@435 380 // Note: make sure we mark the method as not compilable!
duke@435 381 CHECK_BAILOUT();
duke@435 382
duke@435 383 if (InstallMethods) {
duke@435 384 // install code
duke@435 385 PhaseTraceTime timeit(_t_codeinstall);
duke@435 386 install_code(frame_size);
duke@435 387 }
duke@435 388 totalInstructionNodes += Instruction::number_of_instructions();
duke@435 389 }
duke@435 390
duke@435 391
duke@435 392 void Compilation::generate_exception_handler_table() {
duke@435 393 // Generate an ExceptionHandlerTable from the exception handler
duke@435 394 // information accumulated during the compilation.
duke@435 395 ExceptionInfoList* info_list = exception_info_list();
duke@435 396
duke@435 397 if (info_list->length() == 0) {
duke@435 398 return;
duke@435 399 }
duke@435 400
duke@435 401 // allocate some arrays for use by the collection code.
duke@435 402 const int num_handlers = 5;
duke@435 403 GrowableArray<intptr_t>* bcis = new GrowableArray<intptr_t>(num_handlers);
duke@435 404 GrowableArray<intptr_t>* scope_depths = new GrowableArray<intptr_t>(num_handlers);
duke@435 405 GrowableArray<intptr_t>* pcos = new GrowableArray<intptr_t>(num_handlers);
duke@435 406
duke@435 407 for (int i = 0; i < info_list->length(); i++) {
duke@435 408 ExceptionInfo* info = info_list->at(i);
duke@435 409 XHandlers* handlers = info->exception_handlers();
duke@435 410
duke@435 411 // empty the arrays
duke@435 412 bcis->trunc_to(0);
duke@435 413 scope_depths->trunc_to(0);
duke@435 414 pcos->trunc_to(0);
duke@435 415
duke@435 416 for (int i = 0; i < handlers->length(); i++) {
duke@435 417 XHandler* handler = handlers->handler_at(i);
duke@435 418 assert(handler->entry_pco() != -1, "must have been generated");
duke@435 419
duke@435 420 int e = bcis->find(handler->handler_bci());
duke@435 421 if (e >= 0 && scope_depths->at(e) == handler->scope_count()) {
duke@435 422 // two different handlers are declared to dispatch to the same
duke@435 423 // catch bci. During parsing we created edges for each
duke@435 424 // handler but we really only need one. The exception handler
duke@435 425 // table will also get unhappy if we try to declare both since
duke@435 426 // it's nonsensical. Just skip this handler.
duke@435 427 continue;
duke@435 428 }
duke@435 429
duke@435 430 bcis->append(handler->handler_bci());
duke@435 431 if (handler->handler_bci() == -1) {
duke@435 432 // insert a wildcard handler at scope depth 0 so that the
duke@435 433 // exception lookup logic with find it.
duke@435 434 scope_depths->append(0);
duke@435 435 } else {
duke@435 436 scope_depths->append(handler->scope_count());
duke@435 437 }
duke@435 438 pcos->append(handler->entry_pco());
duke@435 439
duke@435 440 // stop processing once we hit a catch any
duke@435 441 if (handler->is_catch_all()) {
duke@435 442 assert(i == handlers->length() - 1, "catch all must be last handler");
duke@435 443 }
duke@435 444 }
duke@435 445 exception_handler_table()->add_subtable(info->pco(), bcis, scope_depths, pcos);
duke@435 446 }
duke@435 447 }
duke@435 448
duke@435 449
iveresov@1939 450 Compilation::Compilation(AbstractCompiler* compiler, ciEnv* env, ciMethod* method,
iveresov@1939 451 int osr_bci, BufferBlob* buffer_blob)
duke@435 452 : _compiler(compiler)
duke@435 453 , _env(env)
duke@435 454 , _method(method)
duke@435 455 , _osr_bci(osr_bci)
duke@435 456 , _hir(NULL)
duke@435 457 , _max_spills(-1)
duke@435 458 , _frame_map(NULL)
duke@435 459 , _masm(NULL)
duke@435 460 , _has_exception_handlers(false)
duke@435 461 , _has_fpu_code(true) // pessimistic assumption
iveresov@2138 462 , _would_profile(false)
duke@435 463 , _has_unsafe_access(false)
twisti@2046 464 , _has_method_handle_invokes(false)
duke@435 465 , _bailout_msg(NULL)
duke@435 466 , _exception_info_list(NULL)
duke@435 467 , _allocator(NULL)
iveresov@1939 468 , _next_id(0)
iveresov@1939 469 , _next_block_id(0)
twisti@2103 470 , _code(buffer_blob)
duke@435 471 , _current_instruction(NULL)
duke@435 472 #ifndef PRODUCT
duke@435 473 , _last_instruction_printed(NULL)
duke@435 474 #endif // PRODUCT
duke@435 475 {
duke@435 476 PhaseTraceTime timeit(_t_compile);
duke@435 477 _arena = Thread::current()->resource_area();
iveresov@1939 478 _env->set_compiler_data(this);
duke@435 479 _exception_info_list = new ExceptionInfoList();
duke@435 480 _implicit_exception_table.set_size(0);
duke@435 481 compile_method();
iveresov@2306 482 if (bailed_out()) {
iveresov@2306 483 _env->record_method_not_compilable(bailout_msg(), !TieredCompilation);
iveresov@2306 484 if (is_profiling()) {
iveresov@2306 485 // Compilation failed, create MDO, which would signal the interpreter
iveresov@2306 486 // to start profiling on its own.
iveresov@2349 487 _method->ensure_method_data();
iveresov@2306 488 }
iveresov@2306 489 } else if (is_profiling() && _would_profile) {
iveresov@2349 490 ciMethodData *md = method->method_data_or_null();
iveresov@2349 491 assert(md != NULL, "Sanity");
iveresov@2138 492 md->set_would_profile(_would_profile);
iveresov@2138 493 }
duke@435 494 }
duke@435 495
duke@435 496 Compilation::~Compilation() {
iveresov@1939 497 _env->set_compiler_data(NULL);
duke@435 498 }
duke@435 499
duke@435 500
duke@435 501 void Compilation::add_exception_handlers_for_pco(int pco, XHandlers* exception_handlers) {
duke@435 502 #ifndef PRODUCT
duke@435 503 if (PrintExceptionHandlers && Verbose) {
duke@435 504 tty->print_cr(" added exception scope for pco %d", pco);
duke@435 505 }
duke@435 506 #endif
duke@435 507 // Note: we do not have program counters for these exception handlers yet
duke@435 508 exception_info_list()->push(new ExceptionInfo(pco, exception_handlers));
duke@435 509 }
duke@435 510
duke@435 511
duke@435 512 void Compilation::notice_inlined_method(ciMethod* method) {
duke@435 513 _env->notice_inlined_method(method);
duke@435 514 }
duke@435 515
duke@435 516
duke@435 517 void Compilation::bailout(const char* msg) {
duke@435 518 assert(msg != NULL, "bailout message must exist");
duke@435 519 if (!bailed_out()) {
duke@435 520 // keep first bailout message
duke@435 521 if (PrintBailouts) tty->print_cr("compilation bailout: %s", msg);
duke@435 522 _bailout_msg = msg;
duke@435 523 }
duke@435 524 }
duke@435 525
duke@435 526
duke@435 527 void Compilation::print_timers() {
duke@435 528 // tty->print_cr(" Native methods : %6.3f s, Average : %2.3f", CompileBroker::_t_native_compilation.seconds(), CompileBroker::_t_native_compilation.seconds() / CompileBroker::_total_native_compile_count);
duke@435 529 float total = timers[_t_setup].seconds() + timers[_t_buildIR].seconds() + timers[_t_emit_lir].seconds() + timers[_t_lir_schedule].seconds() + timers[_t_codeemit].seconds() + timers[_t_codeinstall].seconds();
duke@435 530
duke@435 531
duke@435 532 tty->print_cr(" Detailed C1 Timings");
duke@435 533 tty->print_cr(" Setup time: %6.3f s (%4.1f%%)", timers[_t_setup].seconds(), (timers[_t_setup].seconds() / total) * 100.0);
duke@435 534 tty->print_cr(" Build IR: %6.3f s (%4.1f%%)", timers[_t_buildIR].seconds(), (timers[_t_buildIR].seconds() / total) * 100.0);
duke@435 535 tty->print_cr(" Optimize: %6.3f s (%4.1f%%)", timers[_t_optimizeIR].seconds(), (timers[_t_optimizeIR].seconds() / total) * 100.0);
duke@435 536 tty->print_cr(" Emit LIR: %6.3f s (%4.1f%%)", timers[_t_emit_lir].seconds(), (timers[_t_emit_lir].seconds() / total) * 100.0);
duke@435 537 tty->print_cr(" LIR Gen: %6.3f s (%4.1f%%)", timers[_t_lirGeneration].seconds(), (timers[_t_lirGeneration].seconds() / total) * 100.0);
duke@435 538 tty->print_cr(" Linear Scan: %6.3f s (%4.1f%%)", timers[_t_linearScan].seconds(), (timers[_t_linearScan].seconds() / total) * 100.0);
duke@435 539 NOT_PRODUCT(LinearScan::print_timers(timers[_t_linearScan].seconds()));
duke@435 540 tty->print_cr(" LIR Schedule: %6.3f s (%4.1f%%)", timers[_t_lir_schedule].seconds(), (timers[_t_lir_schedule].seconds() / total) * 100.0);
duke@435 541 tty->print_cr(" Code Emission: %6.3f s (%4.1f%%)", timers[_t_codeemit].seconds(), (timers[_t_codeemit].seconds() / total) * 100.0);
duke@435 542 tty->print_cr(" Code Installation: %6.3f s (%4.1f%%)", timers[_t_codeinstall].seconds(), (timers[_t_codeinstall].seconds() / total) * 100.0);
duke@435 543 tty->print_cr(" Instruction Nodes: %6d nodes", totalInstructionNodes);
duke@435 544
duke@435 545 NOT_PRODUCT(LinearScan::print_statistics());
duke@435 546 }
duke@435 547
duke@435 548
duke@435 549 #ifndef PRODUCT
duke@435 550 void Compilation::compile_only_this_method() {
duke@435 551 ResourceMark rm;
duke@435 552 fileStream stream(fopen("c1_compile_only", "wt"));
duke@435 553 stream.print_cr("# c1 compile only directives");
duke@435 554 compile_only_this_scope(&stream, hir()->top_scope());
duke@435 555 }
duke@435 556
duke@435 557
duke@435 558 void Compilation::compile_only_this_scope(outputStream* st, IRScope* scope) {
duke@435 559 st->print("CompileOnly=");
duke@435 560 scope->method()->holder()->name()->print_symbol_on(st);
duke@435 561 st->print(".");
duke@435 562 scope->method()->name()->print_symbol_on(st);
duke@435 563 st->cr();
duke@435 564 }
duke@435 565
duke@435 566
duke@435 567 void Compilation::exclude_this_method() {
duke@435 568 fileStream stream(fopen(".hotspot_compiler", "at"));
duke@435 569 stream.print("exclude ");
duke@435 570 method()->holder()->name()->print_symbol_on(&stream);
duke@435 571 stream.print(" ");
duke@435 572 method()->name()->print_symbol_on(&stream);
duke@435 573 stream.cr();
duke@435 574 stream.cr();
duke@435 575 }
duke@435 576 #endif

mercurial