hotspot/src/share/vm/code/relocInfo.cpp
changeset 46530 7b915076588f
parent 45325 2cded43c8842
parent 46469 f0f38f5ac34f
child 46630 75aa3e39d02c
equal deleted inserted replaced
45420:036dbf8b3817 46530:7b915076588f
   189   const int n = CodeBuffer::SECT_CONSTS;
   189   const int n = CodeBuffer::SECT_CONSTS;
   190   return section_start(n) <= addr() && addr() < section_end(n);
   190   return section_start(n) <= addr() && addr() < section_end(n);
   191 }
   191 }
   192 
   192 
   193 
   193 
   194 static inline int num_cards(int code_size) {
       
   195   return (code_size-1) / indexCardSize;
       
   196 }
       
   197 
       
   198 
       
   199 int RelocIterator::locs_and_index_size(int code_size, int locs_size) {
       
   200   if (!UseRelocIndex)  return locs_size;   // no index
       
   201   code_size = round_to(code_size, oopSize);
       
   202   locs_size = round_to(locs_size, oopSize);
       
   203   int index_size = num_cards(code_size) * sizeof(RelocIndexEntry);
       
   204   // format of indexed relocs:
       
   205   //   relocation_begin:   relocInfo ...
       
   206   //   index:              (addr,reloc#) ...
       
   207   //                       indexSize           :relocation_end
       
   208   return locs_size + index_size + BytesPerInt;
       
   209 }
       
   210 
       
   211 
       
   212 void RelocIterator::create_index(relocInfo* dest_begin, int dest_count, relocInfo* dest_end) {
       
   213   address relocation_begin = (address)dest_begin;
       
   214   address relocation_end   = (address)dest_end;
       
   215   int     total_size       = relocation_end - relocation_begin;
       
   216   int     locs_size        = dest_count * sizeof(relocInfo);
       
   217   if (!UseRelocIndex) {
       
   218     Copy::fill_to_bytes(relocation_begin + locs_size, total_size-locs_size, 0);
       
   219     return;
       
   220   }
       
   221   int     index_size       = total_size - locs_size - BytesPerInt;      // find out how much space is left
       
   222   int     ncards           = index_size / sizeof(RelocIndexEntry);
       
   223   assert(total_size == locs_size + index_size + BytesPerInt, "checkin'");
       
   224   assert(index_size >= 0 && index_size % sizeof(RelocIndexEntry) == 0, "checkin'");
       
   225   jint*   index_size_addr  = (jint*)relocation_end - 1;
       
   226 
       
   227   assert(sizeof(jint) == BytesPerInt, "change this code");
       
   228 
       
   229   *index_size_addr = index_size;
       
   230   if (index_size != 0) {
       
   231     assert(index_size > 0, "checkin'");
       
   232 
       
   233     RelocIndexEntry* index = (RelocIndexEntry *)(relocation_begin + locs_size);
       
   234     assert(index == (RelocIndexEntry*)index_size_addr - ncards, "checkin'");
       
   235 
       
   236     // walk over the relocations, and fill in index entries as we go
       
   237     RelocIterator iter;
       
   238     const address    initial_addr    = NULL;
       
   239     relocInfo* const initial_current = dest_begin - 1;  // biased by -1 like elsewhere
       
   240 
       
   241     iter._code    = NULL;
       
   242     iter._addr    = initial_addr;
       
   243     iter._limit   = (address)(intptr_t)(ncards * indexCardSize);
       
   244     iter._current = initial_current;
       
   245     iter._end     = dest_begin + dest_count;
       
   246 
       
   247     int i = 0;
       
   248     address next_card_addr = (address)indexCardSize;
       
   249     int addr_offset = 0;
       
   250     int reloc_offset = 0;
       
   251     while (true) {
       
   252       // Checkpoint the iterator before advancing it.
       
   253       addr_offset  = iter._addr    - initial_addr;
       
   254       reloc_offset = iter._current - initial_current;
       
   255       if (!iter.next())  break;
       
   256       while (iter.addr() >= next_card_addr) {
       
   257         index[i].addr_offset  = addr_offset;
       
   258         index[i].reloc_offset = reloc_offset;
       
   259         i++;
       
   260         next_card_addr += indexCardSize;
       
   261       }
       
   262     }
       
   263     while (i < ncards) {
       
   264       index[i].addr_offset  = addr_offset;
       
   265       index[i].reloc_offset = reloc_offset;
       
   266       i++;
       
   267     }
       
   268   }
       
   269 }
       
   270 
       
   271 
       
   272 void RelocIterator::set_limits(address begin, address limit) {
   194 void RelocIterator::set_limits(address begin, address limit) {
   273   int index_size = 0;
       
   274   if (UseRelocIndex && _code != NULL) {
       
   275     index_size = ((jint*)_end)[-1];
       
   276     _end = (relocInfo*)( (address)_end - index_size - BytesPerInt );
       
   277   }
       
   278 
       
   279   _limit = limit;
   195   _limit = limit;
   280 
   196 
   281   // the limit affects this next stuff:
   197   // the limit affects this next stuff:
   282   if (begin != NULL) {
   198   if (begin != NULL) {
   283 #ifdef ASSERT
       
   284     // In ASSERT mode we do not actually use the index, but simply
       
   285     // check that its contents would have led us to the right answer.
       
   286     address addrCheck = _addr;
       
   287     relocInfo* infoCheck = _current;
       
   288 #endif // ASSERT
       
   289     if (index_size > 0) {
       
   290       // skip ahead
       
   291       RelocIndexEntry* index       = (RelocIndexEntry*)_end;
       
   292       RelocIndexEntry* index_limit = (RelocIndexEntry*)((address)index + index_size);
       
   293       assert(_addr == _code->code_begin(), "_addr must be unadjusted");
       
   294       int card = (begin - _addr) / indexCardSize;
       
   295       if (card > 0) {
       
   296         if (index+card-1 < index_limit)  index += card-1;
       
   297         else                             index = index_limit - 1;
       
   298 #ifdef ASSERT
       
   299         addrCheck = _addr    + index->addr_offset;
       
   300         infoCheck = _current + index->reloc_offset;
       
   301 #else
       
   302         // Advance the iterator immediately to the last valid state
       
   303         // for the previous card.  Calling "next" will then advance
       
   304         // it to the first item on the required card.
       
   305         _addr    += index->addr_offset;
       
   306         _current += index->reloc_offset;
       
   307 #endif // ASSERT
       
   308       }
       
   309     }
       
   310 
       
   311     relocInfo* backup;
   199     relocInfo* backup;
   312     address    backup_addr;
   200     address    backup_addr;
   313     while (true) {
   201     while (true) {
   314       backup      = _current;
   202       backup      = _current;
   315       backup_addr = _addr;
   203       backup_addr = _addr;
   316 #ifdef ASSERT
       
   317       if (backup == infoCheck) {
       
   318         assert(backup_addr == addrCheck, "must match"); addrCheck = NULL; infoCheck = NULL;
       
   319       } else {
       
   320         assert(addrCheck == NULL || backup_addr <= addrCheck, "must not pass addrCheck");
       
   321       }
       
   322 #endif // ASSERT
       
   323       if (!next() || addr() >= begin) break;
   204       if (!next() || addr() >= begin) break;
   324     }
   205     }
   325     assert(addrCheck == NULL || addrCheck == backup_addr, "must have matched addrCheck");
       
   326     assert(infoCheck == NULL || infoCheck == backup,      "must have matched infoCheck");
       
   327     // At this point, either we are at the first matching record,
   206     // At this point, either we are at the first matching record,
   328     // or else there is no such record, and !has_current().
   207     // or else there is no such record, and !has_current().
   329     // In either case, revert to the immediatly preceding state.
   208     // In either case, revert to the immediatly preceding state.
   330     _current = backup;
   209     _current = backup;
   331     _addr    = backup_addr;
   210     _addr    = backup_addr;