< prev index next >

src/hotspot/cpu/x86/c1_LIRAssembler_x86.cpp

Print this page




2538     }
2539 #endif // _LP64
2540   }
2541 }
2542 
2543 
2544 // we assume that rax, and rdx can be overwritten
2545 void LIR_Assembler::arithmetic_idiv(LIR_Code code, LIR_Opr left, LIR_Opr right, LIR_Opr temp, LIR_Opr result, CodeEmitInfo* info) {
2546 
2547   assert(left->is_single_cpu(),   "left must be register");
2548   assert(right->is_single_cpu() || right->is_constant(),  "right must be register or constant");
2549   assert(result->is_single_cpu(), "result must be register");
2550 
2551   //  assert(left->destroys_register(), "check");
2552   //  assert(right->destroys_register(), "check");
2553 
2554   Register lreg = left->as_register();
2555   Register dreg = result->as_register();
2556 
2557   if (right->is_constant()) {
2558     int divisor = right->as_constant_ptr()->as_jint();
2559     assert(divisor > 0 && is_power_of_2(divisor), "must be");
2560     if (code == lir_idiv) {
2561       assert(lreg == rax, "must be rax,");
2562       assert(temp->as_register() == rdx, "tmp register must be rdx");
2563       __ cdql(); // sign extend into rdx:rax
2564       if (divisor == 2) {
2565         __ subl(lreg, rdx);
2566       } else {
2567         __ andl(rdx, divisor - 1);
2568         __ addl(lreg, rdx);
2569       }
2570       __ sarl(lreg, log2_intptr(divisor));
2571       move_regs(lreg, dreg);
2572     } else if (code == lir_irem) {
2573       Label done;
2574       __ mov(dreg, lreg);
2575       __ andl(dreg, 0x80000000 | (divisor - 1));
2576       __ jcc(Assembler::positive, done);
2577       __ decrement(dreg);
2578       __ orl(dreg, ~(divisor - 1));
2579       __ increment(dreg);
2580       __ bind(done);
2581     } else {
2582       ShouldNotReachHere();
2583     }
2584   } else {
2585     Register rreg = right->as_register();
2586     assert(lreg == rax, "left register must be rax,");
2587     assert(rreg != rdx, "right register must not be rdx");
2588     assert(temp->as_register() == rdx, "tmp register must be rdx");
2589 
2590     move_regs(lreg, rax);




2538     }
2539 #endif // _LP64
2540   }
2541 }
2542 
2543 
2544 // we assume that rax, and rdx can be overwritten
2545 void LIR_Assembler::arithmetic_idiv(LIR_Code code, LIR_Opr left, LIR_Opr right, LIR_Opr temp, LIR_Opr result, CodeEmitInfo* info) {
2546 
2547   assert(left->is_single_cpu(),   "left must be register");
2548   assert(right->is_single_cpu() || right->is_constant(),  "right must be register or constant");
2549   assert(result->is_single_cpu(), "result must be register");
2550 
2551   //  assert(left->destroys_register(), "check");
2552   //  assert(right->destroys_register(), "check");
2553 
2554   Register lreg = left->as_register();
2555   Register dreg = result->as_register();
2556 
2557   if (right->is_constant()) {
2558     jint divisor = right->as_constant_ptr()->as_jint();
2559     assert(divisor > 0 && is_power_of_2(divisor), "must be");
2560     if (code == lir_idiv) {
2561       assert(lreg == rax, "must be rax,");
2562       assert(temp->as_register() == rdx, "tmp register must be rdx");
2563       __ cdql(); // sign extend into rdx:rax
2564       if (divisor == 2) {
2565         __ subl(lreg, rdx);
2566       } else {
2567         __ andl(rdx, divisor - 1);
2568         __ addl(lreg, rdx);
2569       }
2570       __ sarl(lreg, log2_jint(divisor));
2571       move_regs(lreg, dreg);
2572     } else if (code == lir_irem) {
2573       Label done;
2574       __ mov(dreg, lreg);
2575       __ andl(dreg, 0x80000000 | (divisor - 1));
2576       __ jcc(Assembler::positive, done);
2577       __ decrement(dreg);
2578       __ orl(dreg, ~(divisor - 1));
2579       __ increment(dreg);
2580       __ bind(done);
2581     } else {
2582       ShouldNotReachHere();
2583     }
2584   } else {
2585     Register rreg = right->as_register();
2586     assert(lreg == rax, "left register must be rax,");
2587     assert(rreg != rdx, "right register must not be rdx");
2588     assert(temp->as_register() == rdx, "tmp register must be rdx");
2589 
2590     move_regs(lreg, rax);


< prev index next >