@@ -3260,23 +3260,28 @@ void TypeRawPtr::dump2( Dict &d, uint depth, outputStream *st ) const {
3260
3260
// Convenience common pre-built type.
3261
3261
const TypeOopPtr *TypeOopPtr::BOTTOM;
3262
3262
3263
- TypeInterfaces::TypeInterfaces ()
3264
- : Type(Interfaces), _list(Compile::current()->type_arena(), 0, 0, nullptr ),
3263
+ TypeInterfaces::TypeInterfaces (ciInstanceKlass** interfaces_base, int nb_interfaces )
3264
+ : Type(Interfaces), _interfaces(interfaces_base, nb_interfaces ),
3265
3265
_hash(0 ), _exact_klass(nullptr ) {
3266
- DEBUG_ONLY (_initialized = true );
3267
- }
3268
-
3269
- TypeInterfaces::TypeInterfaces (GrowableArray<ciInstanceKlass*>* interfaces)
3270
- : Type(Interfaces), _list(Compile::current()->type_arena(), interfaces->length(), 0, nullptr),
3271
- _hash(0 ), _exact_klass(nullptr ) {
3272
- for (int i = 0 ; i < interfaces->length (); i++) {
3273
- add (interfaces->at (i));
3274
- }
3266
+ _interfaces.sort (compare);
3275
3267
initialize ();
3276
3268
}
3277
3269
3278
3270
const TypeInterfaces* TypeInterfaces::make (GrowableArray<ciInstanceKlass*>* interfaces) {
3279
- TypeInterfaces* result = (interfaces == nullptr ) ? new TypeInterfaces () : new TypeInterfaces (interfaces);
3271
+ // hashcons() can only delete the last thing that was allocated: to
3272
+ // make sure all memory for the newly created TypeInterfaces can be
3273
+ // freed if an identical one exists, allocate space for the array of
3274
+ // interfaces right after the TypeInterfaces object so that they
3275
+ // form a contiguous piece of memory.
3276
+ int nb_interfaces = interfaces == nullptr ? 0 : interfaces->length ();
3277
+ size_t total_size = sizeof (TypeInterfaces) + nb_interfaces * sizeof (ciInstanceKlass*);
3278
+
3279
+ void * allocated_mem = operator new (total_size);
3280
+ ciInstanceKlass** interfaces_base = (ciInstanceKlass**)((char *)allocated_mem + sizeof (TypeInterfaces));
3281
+ for (int i = 0 ; i < nb_interfaces; ++i) {
3282
+ interfaces_base[i] = interfaces->at (i);
3283
+ }
3284
+ TypeInterfaces* result = ::new (allocated_mem) TypeInterfaces (interfaces_base, nb_interfaces);
3280
3285
return (const TypeInterfaces*)result->hashcons ();
3281
3286
}
3282
3287
@@ -3295,20 +3300,18 @@ int TypeInterfaces::compare(ciInstanceKlass* const& k1, ciInstanceKlass* const&
3295
3300
return 0 ;
3296
3301
}
3297
3302
3298
- void TypeInterfaces::add (ciInstanceKlass* interface) {
3299
- assert (interface->is_interface (), " for interfaces only" );
3300
- _list.insert_sorted <compare>(interface);
3301
- verify ();
3303
+ int TypeInterfaces::compare (ciInstanceKlass** k1, ciInstanceKlass** k2) {
3304
+ return compare (*k1, *k2);
3302
3305
}
3303
3306
3304
3307
bool TypeInterfaces::eq (const Type* t) const {
3305
3308
const TypeInterfaces* other = (const TypeInterfaces*)t;
3306
- if (_list .length () != other->_list .length ()) {
3309
+ if (_interfaces .length () != other->_interfaces .length ()) {
3307
3310
return false ;
3308
3311
}
3309
- for (int i = 0 ; i < _list .length (); i++) {
3310
- ciKlass* k1 = _list .at (i);
3311
- ciKlass* k2 = other->_list .at (i);
3312
+ for (int i = 0 ; i < _interfaces .length (); i++) {
3313
+ ciKlass* k1 = _interfaces .at (i);
3314
+ ciKlass* k2 = other->_interfaces .at (i);
3312
3315
if (!k1->equals (k2)) {
3313
3316
return false ;
3314
3317
}
@@ -3319,12 +3322,12 @@ bool TypeInterfaces::eq(const Type* t) const {
3319
3322
bool TypeInterfaces::eq (ciInstanceKlass* k) const {
3320
3323
assert (k->is_loaded (), " should be loaded" );
3321
3324
GrowableArray<ciInstanceKlass *>* interfaces = k->transitive_interfaces ();
3322
- if (_list .length () != interfaces->length ()) {
3325
+ if (_interfaces .length () != interfaces->length ()) {
3323
3326
return false ;
3324
3327
}
3325
3328
for (int i = 0 ; i < interfaces->length (); i++) {
3326
3329
bool found = false ;
3327
- _list .find_sorted <ciInstanceKlass*, compare>(interfaces->at (i), found);
3330
+ _interfaces .find_sorted <ciInstanceKlass*, compare>(interfaces->at (i), found);
3328
3331
if (!found) {
3329
3332
return false ;
3330
3333
}
@@ -3344,8 +3347,8 @@ const Type* TypeInterfaces::xdual() const {
3344
3347
3345
3348
void TypeInterfaces::compute_hash () {
3346
3349
uint hash = 0 ;
3347
- for (int i = 0 ; i < _list .length (); i++) {
3348
- ciKlass* k = _list .at (i);
3350
+ for (int i = 0 ; i < _interfaces .length (); i++) {
3351
+ ciKlass* k = _interfaces .at (i);
3349
3352
hash += k->hash ();
3350
3353
}
3351
3354
_hash = hash;
@@ -3356,13 +3359,13 @@ static int compare_interfaces(ciInstanceKlass** k1, ciInstanceKlass** k2) {
3356
3359
}
3357
3360
3358
3361
void TypeInterfaces::dump (outputStream* st) const {
3359
- if (_list .length () == 0 ) {
3362
+ if (_interfaces .length () == 0 ) {
3360
3363
return ;
3361
3364
}
3362
3365
ResourceMark rm;
3363
3366
st->print (" (" );
3364
3367
GrowableArray<ciInstanceKlass*> interfaces;
3365
- interfaces.appendAll (&_list );
3368
+ interfaces.appendAll (&_interfaces );
3366
3369
// Sort the interfaces so they are listed in the same order from one run to the other of the same compilation
3367
3370
interfaces.sort (compare_interfaces);
3368
3371
for (int i = 0 ; i < interfaces.length (); i++) {
@@ -3377,9 +3380,9 @@ void TypeInterfaces::dump(outputStream* st) const {
3377
3380
3378
3381
#ifdef ASSERT
3379
3382
void TypeInterfaces::verify () const {
3380
- for (int i = 1 ; i < _list .length (); i++) {
3381
- ciInstanceKlass* k1 = _list .at (i-1 );
3382
- ciInstanceKlass* k2 = _list .at (i);
3383
+ for (int i = 1 ; i < _interfaces .length (); i++) {
3384
+ ciInstanceKlass* k1 = _interfaces .at (i-1 );
3385
+ ciInstanceKlass* k2 = _interfaces .at (i);
3383
3386
assert (compare (k2, k1) > 0 , " should be ordered" );
3384
3387
assert (k1 != k2, " no duplicate" );
3385
3388
}
@@ -3390,38 +3393,38 @@ const TypeInterfaces* TypeInterfaces::union_with(const TypeInterfaces* other) co
3390
3393
GrowableArray<ciInstanceKlass*> result_list;
3391
3394
int i = 0 ;
3392
3395
int j = 0 ;
3393
- while (i < _list .length () || j < other->_list .length ()) {
3394
- while (i < _list .length () &&
3395
- (j >= other->_list .length () ||
3396
- compare (_list .at (i), other->_list .at (j)) < 0 )) {
3397
- result_list.push (_list .at (i));
3396
+ while (i < _interfaces .length () || j < other->_interfaces .length ()) {
3397
+ while (i < _interfaces .length () &&
3398
+ (j >= other->_interfaces .length () ||
3399
+ compare (_interfaces .at (i), other->_interfaces .at (j)) < 0 )) {
3400
+ result_list.push (_interfaces .at (i));
3398
3401
i++;
3399
3402
}
3400
- while (j < other->_list .length () &&
3401
- (i >= _list .length () ||
3402
- compare (other->_list .at (j), _list .at (i)) < 0 )) {
3403
- result_list.push (other->_list .at (j));
3403
+ while (j < other->_interfaces .length () &&
3404
+ (i >= _interfaces .length () ||
3405
+ compare (other->_interfaces .at (j), _interfaces .at (i)) < 0 )) {
3406
+ result_list.push (other->_interfaces .at (j));
3404
3407
j++;
3405
3408
}
3406
- if (i < _list .length () &&
3407
- j < other->_list .length () &&
3408
- _list .at (i) == other->_list .at (j)) {
3409
- result_list.push (_list .at (i));
3409
+ if (i < _interfaces .length () &&
3410
+ j < other->_interfaces .length () &&
3411
+ _interfaces .at (i) == other->_interfaces .at (j)) {
3412
+ result_list.push (_interfaces .at (i));
3410
3413
i++;
3411
3414
j++;
3412
3415
}
3413
3416
}
3414
3417
const TypeInterfaces* result = TypeInterfaces::make (&result_list);
3415
3418
#ifdef ASSERT
3416
3419
result->verify ();
3417
- for (int i = 0 ; i < _list .length (); i++) {
3418
- assert (result->_list .contains (_list .at (i)), " missing" );
3420
+ for (int i = 0 ; i < _interfaces .length (); i++) {
3421
+ assert (result->_interfaces .contains (_interfaces .at (i)), " missing" );
3419
3422
}
3420
- for (int i = 0 ; i < other->_list .length (); i++) {
3421
- assert (result->_list .contains (other->_list .at (i)), " missing" );
3423
+ for (int i = 0 ; i < other->_interfaces .length (); i++) {
3424
+ assert (result->_interfaces .contains (other->_interfaces .at (i)), " missing" );
3422
3425
}
3423
- for (int i = 0 ; i < result->_list .length (); i++) {
3424
- assert (_list .contains (result->_list .at (i)) || other->_list .contains (result->_list .at (i)), " missing" );
3426
+ for (int i = 0 ; i < result->_interfaces .length (); i++) {
3427
+ assert (_interfaces .contains (result->_interfaces .at (i)) || other->_interfaces .contains (result->_interfaces .at (i)), " missing" );
3425
3428
}
3426
3429
#endif
3427
3430
return result;
@@ -3431,36 +3434,36 @@ const TypeInterfaces* TypeInterfaces::intersection_with(const TypeInterfaces* ot
3431
3434
GrowableArray<ciInstanceKlass*> result_list;
3432
3435
int i = 0 ;
3433
3436
int j = 0 ;
3434
- while (i < _list .length () || j < other->_list .length ()) {
3435
- while (i < _list .length () &&
3436
- (j >= other->_list .length () ||
3437
- compare (_list .at (i), other->_list .at (j)) < 0 )) {
3437
+ while (i < _interfaces .length () || j < other->_interfaces .length ()) {
3438
+ while (i < _interfaces .length () &&
3439
+ (j >= other->_interfaces .length () ||
3440
+ compare (_interfaces .at (i), other->_interfaces .at (j)) < 0 )) {
3438
3441
i++;
3439
3442
}
3440
- while (j < other->_list .length () &&
3441
- (i >= _list .length () ||
3442
- compare (other->_list .at (j), _list .at (i)) < 0 )) {
3443
+ while (j < other->_interfaces .length () &&
3444
+ (i >= _interfaces .length () ||
3445
+ compare (other->_interfaces .at (j), _interfaces .at (i)) < 0 )) {
3443
3446
j++;
3444
3447
}
3445
- if (i < _list .length () &&
3446
- j < other->_list .length () &&
3447
- _list .at (i) == other->_list .at (j)) {
3448
- result_list.push (_list .at (i));
3448
+ if (i < _interfaces .length () &&
3449
+ j < other->_interfaces .length () &&
3450
+ _interfaces .at (i) == other->_interfaces .at (j)) {
3451
+ result_list.push (_interfaces .at (i));
3449
3452
i++;
3450
3453
j++;
3451
3454
}
3452
3455
}
3453
3456
const TypeInterfaces* result = TypeInterfaces::make (&result_list);
3454
3457
#ifdef ASSERT
3455
3458
result->verify ();
3456
- for (int i = 0 ; i < _list .length (); i++) {
3457
- assert (!other->_list .contains (_list .at (i)) || result->_list .contains (_list .at (i)), " missing" );
3459
+ for (int i = 0 ; i < _interfaces .length (); i++) {
3460
+ assert (!other->_interfaces .contains (_interfaces .at (i)) || result->_interfaces .contains (_interfaces .at (i)), " missing" );
3458
3461
}
3459
- for (int i = 0 ; i < other->_list .length (); i++) {
3460
- assert (!_list .contains (other->_list .at (i)) || result->_list .contains (other->_list .at (i)), " missing" );
3462
+ for (int i = 0 ; i < other->_interfaces .length (); i++) {
3463
+ assert (!_interfaces .contains (other->_interfaces .at (i)) || result->_interfaces .contains (other->_interfaces .at (i)), " missing" );
3461
3464
}
3462
- for (int i = 0 ; i < result->_list .length (); i++) {
3463
- assert (_list .contains (result->_list .at (i)) && other->_list .contains (result->_list .at (i)), " missing" );
3465
+ for (int i = 0 ; i < result->_interfaces .length (); i++) {
3466
+ assert (_interfaces .contains (result->_interfaces .at (i)) && other->_interfaces .contains (result->_interfaces .at (i)), " missing" );
3464
3467
}
3465
3468
#endif
3466
3469
return result;
@@ -3473,13 +3476,13 @@ ciInstanceKlass* TypeInterfaces::exact_klass() const {
3473
3476
}
3474
3477
3475
3478
void TypeInterfaces::compute_exact_klass () {
3476
- if (_list .length () == 0 ) {
3479
+ if (_interfaces .length () == 0 ) {
3477
3480
_exact_klass = nullptr ;
3478
3481
return ;
3479
3482
}
3480
3483
ciInstanceKlass* res = nullptr ;
3481
- for (int i = 0 ; i < _list .length (); i++) {
3482
- ciInstanceKlass* interface = _list .at (i);
3484
+ for (int i = 0 ; i < _interfaces .length (); i++) {
3485
+ ciInstanceKlass* interface = _interfaces .at (i);
3483
3486
if (eq (interface)) {
3484
3487
assert (res == nullptr , " " );
3485
3488
res = interface;
@@ -3490,8 +3493,8 @@ void TypeInterfaces::compute_exact_klass() {
3490
3493
3491
3494
#ifdef ASSERT
3492
3495
void TypeInterfaces::verify_is_loaded () const {
3493
- for (int i = 0 ; i < _list .length (); i++) {
3494
- ciKlass* interface = _list .at (i);
3496
+ for (int i = 0 ; i < _interfaces .length (); i++) {
3497
+ ciKlass* interface = _interfaces .at (i);
3495
3498
assert (interface->is_loaded (), " Interface not loaded" );
3496
3499
}
3497
3500
}
0 commit comments