//============================================================================= //------------------------------Ideal------------------------------------------ // Check for power-of-2 multiply, then try the regular MulNode::Ideal Node *MulLNode::Ideal(PhaseGVN *phase, bool can_reshape) { // Swap constant to right if( in(1)->is_Con() ) { Node *t = in(1); set_req(1,in(2)); set_req(2,t); } else if( !in(2)->is_Con() ) return MulNode::Ideal(phase, can_reshape); // Now we have a constant Node on the right and the constant in con const TypeLong *tl2 = phase->type( in(2) )->isa_long(); if( !tl2 ) return NULL; // Might be top jlong con = tl2->isa_long()->get_con(); if( con == CONST64(0) ) return NULL; // By zero is handled by Value call if( con == CONST64(1) ) return NULL; // By one is handled by Identity call // Check for negative constant; if so negate the final result bool sign_flip = false; if( con < 0 ) { con = -con; sign_flip = true; } // Get low bit; check for being the only bit Node *res = NULL; jlong bit1 = con & -con; // Extract low bit if( bit1 == con ) { // Found a power of 2? res = new (3) LShiftLNode( in(1), phase->intcon(log2_long(bit1)) ); } else { // Check for constant with 2 bits set jlong bit2 = con-bit1; bit2 = bit2 & -bit2; // Extract 2nd bit if( bit2 + bit1 == con ) { // Found all bits in con? Node *n1 = phase->transform( new (3) LShiftLNode( in(1), phase->intcon(log2_long(bit1)) ) ); Node *n2 = phase->transform( new (3) LShiftLNode( in(1), phase->intcon(log2_long(bit2)) ) ); res = new (3) AddLNode( n2, n1 ); } else { // Sleezy: power-of-2 -1. Next time be generic. jlong temp = con + 1; if( temp == (temp & -temp) ) { Node *n1 = phase->transform( new (3) LShiftLNode( in(1), phase->intcon(log2_long(temp)) ) ); res = new (3) SubLNode( n1, in(1) ); } else { return MulNode::Ideal(phase, can_reshape); } } } if( sign_flip ) { // Need to negate result? res = phase->transform(res);// Transform, before making the zero con res = new (3) SubLNode(phase->makecon(TypeLong::ZERO),res); } return res; // Return final result }
void HeapRegion::setup_heap_region_size(uintx min_heap_size) { // region_size in bytes uintx region_size = G1HeapRegionSize; if (FLAG_IS_DEFAULT(G1HeapRegionSize)) { // We base the automatic calculation on the min heap size. This // can be problematic if the spread between min and max is quite // wide, imagine -Xms128m -Xmx32g. But, if we decided it based on // the max size, the region size might be way too large for the // min size. Either way, some users might have to set the region // size manually for some -Xms / -Xmx combos. region_size = MAX2(min_heap_size / TARGET_REGION_NUMBER, (uintx) MIN_REGION_SIZE); } int region_size_log = log2_long((jlong) region_size); // Recalculate the region size to make sure it's a power of // 2. This means that region_size is the largest power of 2 that's // <= what we've calculated so far. region_size = ((uintx)1 << region_size_log); // Now make sure that we don't go over or under our limits. if (region_size < MIN_REGION_SIZE) { region_size = MIN_REGION_SIZE; } else if (region_size > MAX_REGION_SIZE) { region_size = MAX_REGION_SIZE; } // And recalculate the log. region_size_log = log2_long((jlong) region_size); // Now, set up the globals. guarantee(LogOfHRGrainBytes == 0, "we should only set it once"); LogOfHRGrainBytes = region_size_log; guarantee(LogOfHRGrainWords == 0, "we should only set it once"); LogOfHRGrainWords = LogOfHRGrainBytes - LogHeapWordSize; guarantee(GrainBytes == 0, "we should only set it once"); // The cast to int is safe, given that we've bounded region_size by // MIN_REGION_SIZE and MAX_REGION_SIZE. GrainBytes = (int) region_size; guarantee(GrainWords == 0, "we should only set it once"); GrainWords = GrainBytes >> LogHeapWordSize; guarantee(1 << LogOfHRGrainWords == GrainWords, "sanity"); guarantee(CardsPerRegion == 0, "we should only set it once"); CardsPerRegion = GrainBytes >> CardTableModRefBS::card_shift; }
void HeapRegion::setup_heap_region_size(size_t initial_heap_size, size_t max_heap_size) { uintx region_size = G1HeapRegionSize; if (FLAG_IS_DEFAULT(G1HeapRegionSize)) { size_t average_heap_size = (initial_heap_size + max_heap_size) / 2; region_size = MAX2(average_heap_size / TARGET_REGION_NUMBER, (uintx) MIN_REGION_SIZE); } int region_size_log = log2_long((jlong) region_size); // Recalculate the region size to make sure it's a power of // 2. This means that region_size is the largest power of 2 that's // <= what we've calculated so far. region_size = ((uintx)1 << region_size_log); // Now make sure that we don't go over or under our limits. if (region_size < MIN_REGION_SIZE) { region_size = MIN_REGION_SIZE; } else if (region_size > MAX_REGION_SIZE) { region_size = MAX_REGION_SIZE; } // And recalculate the log. region_size_log = log2_long((jlong) region_size); // Now, set up the globals. guarantee(LogOfHRGrainBytes == 0, "we should only set it once"); LogOfHRGrainBytes = region_size_log; guarantee(LogOfHRGrainWords == 0, "we should only set it once"); LogOfHRGrainWords = LogOfHRGrainBytes - LogHeapWordSize; guarantee(GrainBytes == 0, "we should only set it once"); // The cast to int is safe, given that we've bounded region_size by // MIN_REGION_SIZE and MAX_REGION_SIZE. GrainBytes = (size_t)region_size; guarantee(GrainWords == 0, "we should only set it once"); GrainWords = GrainBytes >> LogHeapWordSize; guarantee((size_t) 1 << LogOfHRGrainWords == GrainWords, "sanity"); guarantee(CardsPerRegion == 0, "we should only set it once"); CardsPerRegion = GrainBytes >> CardTableModRefBS::card_shift; }
//* the argument must be exactly a power of 2 inline int exact_log2_long(jlong x) { #ifdef ASSERT if (!is_power_of_2_long(x)) basic_fatal("x must be a power of 2"); #endif return log2_long(x); }
inline void MacroAssembler::round_to(Register r, int modulus) { assert(is_power_of_2_long((jlong)modulus), "must be power of 2"); addi(r, r, modulus-1); clrrdi(r, r, log2_long((jlong)modulus)); }