2407 bne( CCR0, retry); // stXcx_ sets CCR0
2408 }
2409 }
2410
2411 #if INCLUDE_RTM_OPT
2412
2413 // Update rtm_counters based on abort status
2414 // input: abort_status
2415 // rtm_counters (RTMLockingCounters*)
2416 void MacroAssembler::rtm_counters_update(Register abort_status, Register rtm_counters_Reg) {
2417 // Mapping to keep PreciseRTMLockingStatistics similar to x86.
2418 // x86 ppc (! means inverted, ? means not the same)
2419 // 0 31 Set if abort caused by XABORT instruction.
2420 // 1 ! 7 If set, the transaction may succeed on a retry. This bit is always clear if bit 0 is set.
2421 // 2 13 Set if another logical processor conflicted with a memory address that was part of the transaction that aborted.
2422 // 3 10 Set if an internal buffer overflowed.
2423 // 4 ?12 Set if a debug breakpoint was hit.
2424 // 5 ?32 Set if an abort occurred during execution of a nested transaction.
2425 const int tm_failure_bit[] = {Assembler::tm_tabort, // Note: Seems like signal handler sets this, too.
2426 Assembler::tm_failure_persistent, // inverted: transient
2427 Assembler::tm_trans_cf,
2428 Assembler::tm_footprint_of,
2429 Assembler::tm_non_trans_cf,
2430 Assembler::tm_suspended};
2431 const bool tm_failure_inv[] = {false, true, false, false, false, false};
2432 assert(sizeof(tm_failure_bit)/sizeof(int) == RTMLockingCounters::ABORT_STATUS_LIMIT, "adapt mapping!");
2433
2434 const Register addr_Reg = R0;
2435 // Keep track of offset to where rtm_counters_Reg had pointed to.
2436 int counters_offs = RTMLockingCounters::abort_count_offset();
2437 addi(addr_Reg, rtm_counters_Reg, counters_offs);
2438 const Register temp_Reg = rtm_counters_Reg;
2439
2440 //atomic_inc_ptr(addr_Reg, temp_Reg); We don't increment atomically
2441 ldx(temp_Reg, addr_Reg);
2442 addi(temp_Reg, temp_Reg, 1);
2443 stdx(temp_Reg, addr_Reg);
2444
2445 if (PrintPreciseRTMLockingStatistics) {
2446 int counters_offs_delta = RTMLockingCounters::abortX_count_offset() - counters_offs;
2447
2448 //mftexasr(abort_status); done by caller
2449 for (int i = 0; i < RTMLockingCounters::ABORT_STATUS_LIMIT; i++) {
2450 counters_offs += counters_offs_delta;
2451 li(temp_Reg, counters_offs_delta); // can't use addi with R0
2452 add(addr_Reg, addr_Reg, temp_Reg); // point to next counter
2453 counters_offs_delta = sizeof(uintx);
2454
2455 Label check_abort;
2456 rldicr_(temp_Reg, abort_status, tm_failure_bit[i], 0);
2457 if (tm_failure_inv[i]) {
2458 bne(CCR0, check_abort);
2459 } else {
2460 beq(CCR0, check_abort);
2461 }
2462 //atomic_inc_ptr(addr_Reg, temp_Reg); We don't increment atomically
2463 ldx(temp_Reg, addr_Reg);
2464 addi(temp_Reg, temp_Reg, 1);
2465 stdx(temp_Reg, addr_Reg);
2466 bind(check_abort);
2467 }
2468 }
2469 li(temp_Reg, -counters_offs); // can't use addi with R0
2470 add(rtm_counters_Reg, addr_Reg, temp_Reg); // restore
2471 }
2472
2473 // Branch if (random & (count-1) != 0), count is 2^n
2474 // tmp and CR0 are killed
2475 void MacroAssembler::branch_on_random_using_tb(Register tmp, int count, Label& brLabel) {
2476 mftb(tmp);
|
2407 bne( CCR0, retry); // stXcx_ sets CCR0
2408 }
2409 }
2410
2411 #if INCLUDE_RTM_OPT
2412
2413 // Update rtm_counters based on abort status
2414 // input: abort_status
2415 // rtm_counters (RTMLockingCounters*)
2416 void MacroAssembler::rtm_counters_update(Register abort_status, Register rtm_counters_Reg) {
2417 // Mapping to keep PreciseRTMLockingStatistics similar to x86.
2418 // x86 ppc (! means inverted, ? means not the same)
2419 // 0 31 Set if abort caused by XABORT instruction.
2420 // 1 ! 7 If set, the transaction may succeed on a retry. This bit is always clear if bit 0 is set.
2421 // 2 13 Set if another logical processor conflicted with a memory address that was part of the transaction that aborted.
2422 // 3 10 Set if an internal buffer overflowed.
2423 // 4 ?12 Set if a debug breakpoint was hit.
2424 // 5 ?32 Set if an abort occurred during execution of a nested transaction.
2425 const int tm_failure_bit[] = {Assembler::tm_tabort, // Note: Seems like signal handler sets this, too.
2426 Assembler::tm_failure_persistent, // inverted: transient
2427 Assembler::tm_non_trans_cf,
2428 Assembler::tm_footprint_of,
2429 Assembler::tm_non_trans_cf, // TODO: verify correctness
2430 Assembler::tm_transaction_level};
2431 const bool tm_failure_inv[] = {false, true, false, false, false, false};
2432 assert(sizeof(tm_failure_bit)/sizeof(int) == RTMLockingCounters::ABORT_STATUS_LIMIT, "adapt mapping!");
2433
2434 const Register addr_Reg = R0;
2435 // Keep track of offset to where rtm_counters_Reg had pointed to.
2436 int counters_offs = RTMLockingCounters::abort_count_offset();
2437 addi(addr_Reg, rtm_counters_Reg, counters_offs);
2438 const Register temp_Reg = rtm_counters_Reg;
2439
2440 //atomic_inc_ptr(addr_Reg, temp_Reg); We don't increment atomically
2441 ldx(temp_Reg, addr_Reg);
2442 addi(temp_Reg, temp_Reg, 1);
2443 stdx(temp_Reg, addr_Reg);
2444
2445 if (PrintPreciseRTMLockingStatistics) {
2446 int counters_offs_delta = RTMLockingCounters::abortX_count_offset() - counters_offs;
2447
2448 //mftexasr(abort_status); done by caller
2449 for (int i = 0; i < RTMLockingCounters::ABORT_STATUS_LIMIT; i++) {
2450 counters_offs += counters_offs_delta;
2451 li(temp_Reg, counters_offs_delta); // can't use addi with R0
2452 add(addr_Reg, addr_Reg, temp_Reg); // point to next counter
2453 counters_offs_delta = sizeof(uintx);
2454
2455 Label check_abort;
2456
2457 if (tm_failure_bit[i] == Assembler::tm_transaction_level) {
2458 // Extract 11 bits
2459 rldicr_(temp_Reg, abort_status, tm_failure_bit[i], 11);
2460 } else {
2461 // Extract 1 bit
2462 rldicr_(temp_Reg, abort_status, tm_failure_bit[i], 0);
2463 }
2464
2465 if (tm_failure_inv[i]) {
2466 bne(CCR0, check_abort);
2467 } else {
2468 beq(CCR0, check_abort);
2469 }
2470 //atomic_inc_ptr(addr_Reg, temp_Reg); We don't increment atomically
2471 ldx(temp_Reg, addr_Reg);
2472 addi(temp_Reg, temp_Reg, 1);
2473 stdx(temp_Reg, addr_Reg);
2474 bind(check_abort);
2475 }
2476 }
2477 li(temp_Reg, -counters_offs); // can't use addi with R0
2478 add(rtm_counters_Reg, addr_Reg, temp_Reg); // restore
2479 }
2480
2481 // Branch if (random & (count-1) != 0), count is 2^n
2482 // tmp and CR0 are killed
2483 void MacroAssembler::branch_on_random_using_tb(Register tmp, int count, Label& brLabel) {
2484 mftb(tmp);
|