258 259 void generate() { 260 NativeSignatureIterator::iterate(); 261 } 262 }; 263 264 bool OopMapCacheEntry::verify_mask(CellTypeState* vars, CellTypeState* stack, int max_locals, int stack_top) { 265 // Check mask includes map 266 VerifyClosure blk(this); 267 iterate_oop(&blk); 268 if (blk.failed()) return false; 269 270 // Check if map is generated correctly 271 // (Use ?: operator to make sure all 'true' & 'false' are represented exactly the same so we can use == afterwards) 272 Log(interpreter, oopmap) logv; 273 LogStream st(logv.trace()); 274 275 st.print("Locals (%d): ", max_locals); 276 for(int i = 0; i < max_locals; i++) { 277 bool v1 = is_oop(i) ? true : false; 278 bool v2 = vars[i].is_reference() || vars[i].is_valuetype() ? true : false; 279 assert(v1 == v2, "locals oop mask generation error"); 280 st.print("%d", v1 ? 1 : 0); 281 } 282 st.cr(); 283 284 st.print("Stack (%d): ", stack_top); 285 for(int j = 0; j < stack_top; j++) { 286 bool v1 = is_oop(max_locals + j) ? true : false; 287 bool v2 = stack[j].is_reference() || stack[j].is_valuetype( )? true : false; 288 assert(v1 == v2, "stack oop mask generation error"); 289 st.print("%d", v1 ? 1 : 0); 290 } 291 st.cr(); 292 return true; 293 } 294 295 void OopMapCacheEntry::allocate_bit_mask() { 296 if (mask_size() > small_mask_limit) { 297 assert(_bit_mask[0] == 0, "bit mask should be new or just flushed"); 298 _bit_mask[0] = (intptr_t) 299 NEW_C_HEAP_ARRAY(uintptr_t, mask_word_size(), mtClass); 300 } 301 } 302 303 void OopMapCacheEntry::deallocate_bit_mask() { 304 if (mask_size() > small_mask_limit && _bit_mask[0] != 0) { 305 assert(!Thread::current()->resource_area()->contains((void*)_bit_mask[0]), 306 "This bit mask should not be in the resource area"); 307 FREE_C_HEAP_ARRAY(uintptr_t, _bit_mask[0]); 349 // compute bits 350 int word_index = 0; 351 uintptr_t value = 0; 352 uintptr_t mask = 1; 353 354 CellTypeState* cell = vars; 355 for (int entry_index = 0; entry_index < n_entries; entry_index++, mask <<= bits_per_entry, cell++) { 356 // store last word 357 if (mask == 0) { 358 bit_mask()[word_index++] = value; 359 value = 0; 360 mask = 1; 361 } 362 363 // switch to stack when done with locals 364 if (entry_index == max_locals) { 365 cell = stack; 366 } 367 368 // set oop bit 369 // Note: the interpreter handles value types with oops too 370 if ( cell->is_reference() || cell->is_valuetype()) { 371 value |= (mask << oop_bit_number ); 372 } 373 374 // set dead bit 375 if (!cell->is_live()) { 376 value |= (mask << dead_bit_number); 377 assert(!cell->is_reference() && !cell->is_valuetype(), "dead value marked as oop"); 378 } 379 } 380 381 // make sure last word is stored 382 bit_mask()[word_index] = value; 383 384 // verify bit mask 385 assert(verify_mask(vars, stack, max_locals, stack_top), "mask could not be verified"); 386 } 387 388 void OopMapCacheEntry::flush() { 389 deallocate_bit_mask(); 390 initialize(); 391 } 392 393 394 // Implementation of OopMapCache 395 396 void InterpreterOopMap::resource_copy(OopMapCacheEntry* from) { 397 assert(_resource_allocate_bit_mask, | 258 259 void generate() { 260 NativeSignatureIterator::iterate(); 261 } 262 }; 263 264 bool OopMapCacheEntry::verify_mask(CellTypeState* vars, CellTypeState* stack, int max_locals, int stack_top) { 265 // Check mask includes map 266 VerifyClosure blk(this); 267 iterate_oop(&blk); 268 if (blk.failed()) return false; 269 270 // Check if map is generated correctly 271 // (Use ?: operator to make sure all 'true' & 'false' are represented exactly the same so we can use == afterwards) 272 Log(interpreter, oopmap) logv; 273 LogStream st(logv.trace()); 274 275 st.print("Locals (%d): ", max_locals); 276 for(int i = 0; i < max_locals; i++) { 277 bool v1 = is_oop(i) ? true : false; 278 bool v2 = vars[i].is_reference(); 279 assert(v1 == v2, "locals oop mask generation error"); 280 st.print("%d", v1 ? 1 : 0); 281 } 282 st.cr(); 283 284 st.print("Stack (%d): ", stack_top); 285 for(int j = 0; j < stack_top; j++) { 286 bool v1 = is_oop(max_locals + j) ? true : false; 287 bool v2 = stack[j].is_reference(); 288 assert(v1 == v2, "stack oop mask generation error"); 289 st.print("%d", v1 ? 1 : 0); 290 } 291 st.cr(); 292 return true; 293 } 294 295 void OopMapCacheEntry::allocate_bit_mask() { 296 if (mask_size() > small_mask_limit) { 297 assert(_bit_mask[0] == 0, "bit mask should be new or just flushed"); 298 _bit_mask[0] = (intptr_t) 299 NEW_C_HEAP_ARRAY(uintptr_t, mask_word_size(), mtClass); 300 } 301 } 302 303 void OopMapCacheEntry::deallocate_bit_mask() { 304 if (mask_size() > small_mask_limit && _bit_mask[0] != 0) { 305 assert(!Thread::current()->resource_area()->contains((void*)_bit_mask[0]), 306 "This bit mask should not be in the resource area"); 307 FREE_C_HEAP_ARRAY(uintptr_t, _bit_mask[0]); 349 // compute bits 350 int word_index = 0; 351 uintptr_t value = 0; 352 uintptr_t mask = 1; 353 354 CellTypeState* cell = vars; 355 for (int entry_index = 0; entry_index < n_entries; entry_index++, mask <<= bits_per_entry, cell++) { 356 // store last word 357 if (mask == 0) { 358 bit_mask()[word_index++] = value; 359 value = 0; 360 mask = 1; 361 } 362 363 // switch to stack when done with locals 364 if (entry_index == max_locals) { 365 cell = stack; 366 } 367 368 // set oop bit 369 if (cell->is_reference()) { 370 value |= (mask << oop_bit_number ); 371 } 372 373 // set dead bit 374 if (!cell->is_live()) { 375 value |= (mask << dead_bit_number); 376 assert(!cell->is_reference(), "dead value marked as oop"); 377 } 378 } 379 380 // make sure last word is stored 381 bit_mask()[word_index] = value; 382 383 // verify bit mask 384 assert(verify_mask(vars, stack, max_locals, stack_top), "mask could not be verified"); 385 } 386 387 void OopMapCacheEntry::flush() { 388 deallocate_bit_mask(); 389 initialize(); 390 } 391 392 393 // Implementation of OopMapCache 394 395 void InterpreterOopMap::resource_copy(OopMapCacheEntry* from) { 396 assert(_resource_allocate_bit_mask, |