--- a/hotspot/src/share/vm/opto/type.cpp Wed Jun 23 09:40:11 2010 -0700
+++ b/hotspot/src/share/vm/opto/type.cpp Mon Jun 28 10:52:50 2010 -0700
@@ -182,6 +182,8 @@
return t->hash();
}
+#define SMALLINT ((juint)3) // a value too insignificant to consider widening
+
//--------------------------Initialize_shared----------------------------------
void Type::Initialize_shared(Compile* current) {
// This method does not need to be locked because the first system
@@ -240,6 +242,7 @@
assert( TypeInt::CC_GT == TypeInt::ONE, "types must match for CmpL to work" );
assert( TypeInt::CC_EQ == TypeInt::ZERO, "types must match for CmpL to work" );
assert( TypeInt::CC_GE == TypeInt::BOOL, "types must match for CmpL to work" );
+ assert( (juint)(TypeInt::CC->_hi - TypeInt::CC->_lo) <= SMALLINT, "CC is truly small");
TypeLong::MINUS_1 = TypeLong::make(-1); // -1
TypeLong::ZERO = TypeLong::make( 0); // 0
@@ -1054,16 +1057,21 @@
return (TypeInt*)(new TypeInt(lo,lo,WidenMin))->hashcons();
}
-#define SMALLINT ((juint)3) // a value too insignificant to consider widening
-
-const TypeInt *TypeInt::make( jint lo, jint hi, int w ) {
+static int normalize_int_widen( jint lo, jint hi, int w ) {
// Certain normalizations keep us sane when comparing types.
// The 'SMALLINT' covers constants and also CC and its relatives.
- assert(CC == NULL || (juint)(CC->_hi - CC->_lo) <= SMALLINT, "CC is truly small");
if (lo <= hi) {
- if ((juint)(hi - lo) <= SMALLINT) w = Type::WidenMin;
- if ((juint)(hi - lo) >= max_juint) w = Type::WidenMax; // plain int
+ if ((juint)(hi - lo) <= SMALLINT) w = Type::WidenMin;
+ if ((juint)(hi - lo) >= max_juint) w = Type::WidenMax; // TypeInt::INT
+ } else {
+ if ((juint)(lo - hi) <= SMALLINT) w = Type::WidenMin;
+ if ((juint)(lo - hi) >= max_juint) w = Type::WidenMin; // dual TypeInt::INT
}
+ return w;
+}
+
+const TypeInt *TypeInt::make( jint lo, jint hi, int w ) {
+ w = normalize_int_widen(lo, hi, w);
return (TypeInt*)(new TypeInt(lo,hi,w))->hashcons();
}
@@ -1103,14 +1111,14 @@
// Expand covered set
const TypeInt *r = t->is_int();
- // (Avoid TypeInt::make, to avoid the argument normalizations it enforces.)
- return (new TypeInt( MIN2(_lo,r->_lo), MAX2(_hi,r->_hi), MAX2(_widen,r->_widen) ))->hashcons();
+ return make( MIN2(_lo,r->_lo), MAX2(_hi,r->_hi), MAX2(_widen,r->_widen) );
}
//------------------------------xdual------------------------------------------
// Dual: reverse hi & lo; flip widen
const Type *TypeInt::xdual() const {
- return new TypeInt(_hi,_lo,WidenMax-_widen);
+ int w = normalize_int_widen(_hi,_lo, WidenMax-_widen);
+ return new TypeInt(_hi,_lo,w);
}
//------------------------------widen------------------------------------------
@@ -1202,7 +1210,7 @@
//-----------------------------filter------------------------------------------
const Type *TypeInt::filter( const Type *kills ) const {
const TypeInt* ft = join(kills)->isa_int();
- if (ft == NULL || ft->_lo > ft->_hi)
+ if (ft == NULL || ft->empty())
return Type::TOP; // Canonical empty value
if (ft->_widen < this->_widen) {
// Do not allow the value of kill->_widen to affect the outcome.
@@ -1304,13 +1312,21 @@
return (TypeLong*)(new TypeLong(lo,lo,WidenMin))->hashcons();
}
-const TypeLong *TypeLong::make( jlong lo, jlong hi, int w ) {
+static int normalize_long_widen( jlong lo, jlong hi, int w ) {
// Certain normalizations keep us sane when comparing types.
- // The '1' covers constants.
+ // The 'SMALLINT' covers constants.
if (lo <= hi) {
- if ((julong)(hi - lo) <= SMALLINT) w = Type::WidenMin;
- if ((julong)(hi - lo) >= max_julong) w = Type::WidenMax; // plain long
+ if ((julong)(hi - lo) <= SMALLINT) w = Type::WidenMin;
+ if ((julong)(hi - lo) >= max_julong) w = Type::WidenMax; // TypeLong::LONG
+ } else {
+ if ((julong)(lo - hi) <= SMALLINT) w = Type::WidenMin;
+ if ((julong)(lo - hi) >= max_julong) w = Type::WidenMin; // dual TypeLong::LONG
}
+ return w;
+}
+
+const TypeLong *TypeLong::make( jlong lo, jlong hi, int w ) {
+ w = normalize_long_widen(lo, hi, w);
return (TypeLong*)(new TypeLong(lo,hi,w))->hashcons();
}
@@ -1351,14 +1367,14 @@
// Expand covered set
const TypeLong *r = t->is_long(); // Turn into a TypeLong
- // (Avoid TypeLong::make, to avoid the argument normalizations it enforces.)
- return (new TypeLong( MIN2(_lo,r->_lo), MAX2(_hi,r->_hi), MAX2(_widen,r->_widen) ))->hashcons();
+ return make( MIN2(_lo,r->_lo), MAX2(_hi,r->_hi), MAX2(_widen,r->_widen) );
}
//------------------------------xdual------------------------------------------
// Dual: reverse hi & lo; flip widen
const Type *TypeLong::xdual() const {
- return new TypeLong(_hi,_lo,WidenMax-_widen);
+ int w = normalize_long_widen(_hi,_lo, WidenMax-_widen);
+ return new TypeLong(_hi,_lo,w);
}
//------------------------------widen------------------------------------------
@@ -1453,7 +1469,7 @@
//-----------------------------filter------------------------------------------
const Type *TypeLong::filter( const Type *kills ) const {
const TypeLong* ft = join(kills)->isa_long();
- if (ft == NULL || ft->_lo > ft->_hi)
+ if (ft == NULL || ft->empty())
return Type::TOP; // Canonical empty value
if (ft->_widen < this->_widen) {
// Do not allow the value of kill->_widen to affect the outcome.