< prev index next >

src/share/vm/gc/cms/parNewGeneration.cpp

Print this page
rev 11971 : [mq]: overflow_list_3


1269   if (ParGCUseLocalOverflow) {
1270     // In the case of compressed oops, we use a private, not-shared
1271     // overflow stack.
1272     par_scan_state->push_on_overflow_stack(from_space_obj);
1273   } else {
1274     assert(!UseCompressedOops, "Error");
1275     // if the object has been forwarded to itself, then we cannot
1276     // use the klass pointer for the linked list.  Instead we have
1277     // to allocate an oopDesc in the C-Heap and use that for the linked list.
1278     // XXX This is horribly inefficient when a promotion failure occurs
1279     // and should be fixed. XXX FIX ME !!!
1280 #ifndef PRODUCT
1281     Atomic::inc_ptr(&_num_par_pushes);
1282     assert(_num_par_pushes > 0, "Tautology");
1283 #endif
1284     if (from_space_obj->forwardee() == from_space_obj) {
1285       oopDesc* listhead = NEW_C_HEAP_ARRAY(oopDesc, 1, mtGC);
1286       listhead->forward_to(from_space_obj);
1287       from_space_obj = listhead;
1288     }
1289     oop observed_overflow_list = _overflow_list;
1290     oop cur_overflow_list;
1291     do {
1292       cur_overflow_list = observed_overflow_list;
1293       if (cur_overflow_list != BUSY) {
1294         from_space_obj->set_klass_to_list_ptr(cur_overflow_list);
1295       } else {
1296         from_space_obj->set_klass_to_list_ptr(NULL);
1297       }
1298       observed_overflow_list =
1299         (oop)Atomic::cmpxchg_ptr(from_space_obj, &_overflow_list, cur_overflow_list);
1300     } while (cur_overflow_list != observed_overflow_list);
1301   }
1302 }
1303 
1304 bool ParNewGeneration::take_from_overflow_list(ParScanThreadState* par_scan_state) {
1305   bool res;
1306 
1307   if (ParGCUseLocalOverflow) {
1308     res = par_scan_state->take_from_overflow_stack();
1309   } else {


1369   size_t i = 1;
1370   oop cur = prefix;
1371   while (i < objsFromOverflow && cur->klass_or_null() != NULL) {
1372     i++; cur = cur->list_ptr_from_klass();
1373   }
1374 
1375   // Reattach remaining (suffix) to overflow list
1376   if (cur->klass_or_null() == NULL) {
1377     // Write back the NULL in lieu of the BUSY we wrote
1378     // above and it is still the same value.
1379     if (_overflow_list == BUSY) {
1380       (void) Atomic::cmpxchg_ptr(NULL, &_overflow_list, BUSY);
1381     }
1382   } else {
1383     assert(cur->klass_or_null() != (Klass*)(address)BUSY, "Error");
1384     oop suffix = cur->list_ptr_from_klass();       // suffix will be put back on global list
1385     cur->set_klass_to_list_ptr(NULL);     // break off suffix
1386     // It's possible that the list is still in the empty(busy) state
1387     // we left it in a short while ago; in that case we may be
1388     // able to place back the suffix.
1389     oop observed_overflow_list = _overflow_list;
1390     oop cur_overflow_list = observed_overflow_list;
1391     bool attached = false;
1392     while (observed_overflow_list == BUSY || observed_overflow_list == NULL) {
1393       observed_overflow_list =
1394         (oop) Atomic::cmpxchg_ptr(suffix, &_overflow_list, cur_overflow_list);
1395       if (cur_overflow_list == observed_overflow_list) {
1396         attached = true;
1397         break;
1398       } else cur_overflow_list = observed_overflow_list;
1399     }
1400     if (!attached) {
1401       // Too bad, someone else got in in between; we'll need to do a splice.
1402       // Find the last item of suffix list
1403       oop last = suffix;
1404       while (last->klass_or_null() != NULL) {
1405         last = last->list_ptr_from_klass();
1406       }
1407       // Atomically prepend suffix to current overflow list
1408       observed_overflow_list = _overflow_list;
1409       do {
1410         cur_overflow_list = observed_overflow_list;
1411         if (cur_overflow_list != BUSY) {
1412           // Do the splice ...
1413           last->set_klass_to_list_ptr(cur_overflow_list);
1414         } else { // cur_overflow_list == BUSY
1415           last->set_klass_to_list_ptr(NULL);
1416         }
1417         observed_overflow_list =
1418           (oop)Atomic::cmpxchg_ptr(suffix, &_overflow_list, cur_overflow_list);
1419       } while (cur_overflow_list != observed_overflow_list);
1420     }
1421   }
1422 
1423   // Push objects on prefix list onto this thread's work queue
1424   assert(prefix != NULL && prefix != BUSY, "program logic");
1425   cur = prefix;
1426   ssize_t n = 0;
1427   while (cur != NULL) {
1428     oop obj_to_push = cur->forwardee();




1269   if (ParGCUseLocalOverflow) {
1270     // In the case of compressed oops, we use a private, not-shared
1271     // overflow stack.
1272     par_scan_state->push_on_overflow_stack(from_space_obj);
1273   } else {
1274     assert(!UseCompressedOops, "Error");
1275     // if the object has been forwarded to itself, then we cannot
1276     // use the klass pointer for the linked list.  Instead we have
1277     // to allocate an oopDesc in the C-Heap and use that for the linked list.
1278     // XXX This is horribly inefficient when a promotion failure occurs
1279     // and should be fixed. XXX FIX ME !!!
1280 #ifndef PRODUCT
1281     Atomic::inc_ptr(&_num_par_pushes);
1282     assert(_num_par_pushes > 0, "Tautology");
1283 #endif
1284     if (from_space_obj->forwardee() == from_space_obj) {
1285       oopDesc* listhead = NEW_C_HEAP_ARRAY(oopDesc, 1, mtGC);
1286       listhead->forward_to(from_space_obj);
1287       from_space_obj = listhead;
1288     }
1289     oop observed_overflow_list = oop(_overflow_list);
1290     oop cur_overflow_list;
1291     do {
1292       cur_overflow_list = observed_overflow_list;
1293       if (cur_overflow_list != BUSY) {
1294         from_space_obj->set_klass_to_list_ptr(cur_overflow_list);
1295       } else {
1296         from_space_obj->set_klass_to_list_ptr(NULL);
1297       }
1298       observed_overflow_list =
1299         (oop)Atomic::cmpxchg_ptr(from_space_obj, &_overflow_list, cur_overflow_list);
1300     } while (cur_overflow_list != observed_overflow_list);
1301   }
1302 }
1303 
1304 bool ParNewGeneration::take_from_overflow_list(ParScanThreadState* par_scan_state) {
1305   bool res;
1306 
1307   if (ParGCUseLocalOverflow) {
1308     res = par_scan_state->take_from_overflow_stack();
1309   } else {


1369   size_t i = 1;
1370   oop cur = prefix;
1371   while (i < objsFromOverflow && cur->klass_or_null() != NULL) {
1372     i++; cur = cur->list_ptr_from_klass();
1373   }
1374 
1375   // Reattach remaining (suffix) to overflow list
1376   if (cur->klass_or_null() == NULL) {
1377     // Write back the NULL in lieu of the BUSY we wrote
1378     // above and it is still the same value.
1379     if (_overflow_list == BUSY) {
1380       (void) Atomic::cmpxchg_ptr(NULL, &_overflow_list, BUSY);
1381     }
1382   } else {
1383     assert(cur->klass_or_null() != (Klass*)(address)BUSY, "Error");
1384     oop suffix = cur->list_ptr_from_klass();       // suffix will be put back on global list
1385     cur->set_klass_to_list_ptr(NULL);     // break off suffix
1386     // It's possible that the list is still in the empty(busy) state
1387     // we left it in a short while ago; in that case we may be
1388     // able to place back the suffix.
1389     oop observed_overflow_list = oop(_overflow_list);
1390     oop cur_overflow_list = observed_overflow_list;
1391     bool attached = false;
1392     while (observed_overflow_list == BUSY || observed_overflow_list == NULL) {
1393       observed_overflow_list =
1394         (oop) Atomic::cmpxchg_ptr(suffix, &_overflow_list, cur_overflow_list);
1395       if (cur_overflow_list == observed_overflow_list) {
1396         attached = true;
1397         break;
1398       } else cur_overflow_list = observed_overflow_list;
1399     }
1400     if (!attached) {
1401       // Too bad, someone else got in in between; we'll need to do a splice.
1402       // Find the last item of suffix list
1403       oop last = suffix;
1404       while (last->klass_or_null() != NULL) {
1405         last = last->list_ptr_from_klass();
1406       }
1407       // Atomically prepend suffix to current overflow list
1408       observed_overflow_list = oop(_overflow_list);
1409       do {
1410         cur_overflow_list = observed_overflow_list;
1411         if (cur_overflow_list != BUSY) {
1412           // Do the splice ...
1413           last->set_klass_to_list_ptr(cur_overflow_list);
1414         } else { // cur_overflow_list == BUSY
1415           last->set_klass_to_list_ptr(NULL);
1416         }
1417         observed_overflow_list =
1418           (oop)Atomic::cmpxchg_ptr(suffix, &_overflow_list, cur_overflow_list);
1419       } while (cur_overflow_list != observed_overflow_list);
1420     }
1421   }
1422 
1423   // Push objects on prefix list onto this thread's work queue
1424   assert(prefix != NULL && prefix != BUSY, "program logic");
1425   cur = prefix;
1426   ssize_t n = 0;
1427   while (cur != NULL) {
1428     oop obj_to_push = cur->forwardee();


< prev index next >