Mercurial > hg > truffle
comparison src/share/vm/utilities/hashtable.cpp @ 14702:d4dd5204c0aa
Merge
author | ehelin |
---|---|
date | Fri, 14 Mar 2014 13:27:18 +0100 |
parents | 3c6ae9109a86 |
children | 92aa6797d639 |
comparison
equal
deleted
inserted
replaced
14701:d3ef21095134 | 14702:d4dd5204c0aa |
---|---|
23 */ | 23 */ |
24 | 24 |
25 #include "precompiled.hpp" | 25 #include "precompiled.hpp" |
26 #include "classfile/altHashing.hpp" | 26 #include "classfile/altHashing.hpp" |
27 #include "classfile/javaClasses.hpp" | 27 #include "classfile/javaClasses.hpp" |
28 #include "code/dependencies.hpp" | |
29 #include "memory/allocation.inline.hpp" | 28 #include "memory/allocation.inline.hpp" |
30 #include "memory/filemap.hpp" | 29 #include "memory/filemap.hpp" |
31 #include "memory/resourceArea.hpp" | 30 #include "memory/resourceArea.hpp" |
32 #include "oops/oop.inline.hpp" | 31 #include "oops/oop.inline.hpp" |
33 #include "runtime/safepoint.hpp" | 32 #include "runtime/safepoint.hpp" |
351 } | 350 } |
352 | 351 |
353 #endif | 352 #endif |
354 | 353 |
355 | 354 |
356 template<class T, class M> GenericHashtable<T, M>::GenericHashtable(int size, bool C_heap, MEMFLAGS memflag) { | |
357 assert(size > 0, " Invalid hashtable size"); | |
358 _size = size; | |
359 _C_heap = C_heap; | |
360 _memflag = memflag; | |
361 // Perform subtype-specific resource allocation | |
362 _items = (C_heap) ? NEW_C_HEAP_ARRAY(T*, size, memflag) : NEW_RESOURCE_ARRAY(T*, size); | |
363 memset(_items, 0, sizeof(T*) * size); | |
364 | |
365 DEBUG_ONLY(_num_items = 0;) | |
366 } | |
367 | |
368 template<class T, class M> GenericHashtable<T, M>::~GenericHashtable() { | |
369 if (on_C_heap()) { | |
370 // Check backing array | |
371 for (int i = 0; i < size(); i++) { | |
372 T* item = head(i); | |
373 // Delete all items in linked list | |
374 while (item != NULL) { | |
375 T* next_item = item->next(); | |
376 delete item; | |
377 DEBUG_ONLY(_num_items--); | |
378 item = next_item; | |
379 } | |
380 } | |
381 FREE_C_HEAP_ARRAY(T*, _items, _memflag); | |
382 _items = NULL; | |
383 assert (_num_items == 0, "Not all memory released"); | |
384 } | |
385 } | |
386 | |
387 /** | |
388 * Return a pointer to the item 'I' that is stored in the hashtable for | |
389 * which match_item->equals(I) == true. If no such item is found, NULL | |
390 * is returned. | |
391 */ | |
392 template<class T, class F> T* GenericHashtable<T, F>::contains(T* match_item) { | |
393 if (match_item != NULL) { | |
394 int idx = index(match_item); | |
395 return contains_impl(match_item, idx); | |
396 } | |
397 return NULL; | |
398 } | |
399 | |
400 /** | |
401 * Add item to the hashtable. Return 'true' if the item was added | |
402 * and false otherwise. | |
403 */ | |
404 template<class T, class F> bool GenericHashtable<T, F>::add(T* item) { | |
405 if (item != NULL) { | |
406 int idx = index(item); | |
407 T* found_item = contains_impl(item, idx); | |
408 if (found_item == NULL) { | |
409 T* list_head = head(idx); | |
410 item->set_next(list_head); | |
411 item->set_prev(NULL); | |
412 | |
413 if (list_head != NULL) { | |
414 list_head->set_prev(item); | |
415 } | |
416 set_head(item, idx); | |
417 DEBUG_ONLY(_num_items++); | |
418 return true; | |
419 } | |
420 } | |
421 return false; | |
422 } | |
423 | |
424 /** | |
425 * Removes an item 'I' from the hashtable, if present. 'I' is removed, if | |
426 * match_item->equals(I) == true. Removing an item from the hashtable does | |
427 * not free memory. | |
428 */ | |
429 template<class T, class F> T* GenericHashtable<T, F>::remove(T* match_item) { | |
430 if (match_item != NULL) { | |
431 int idx = index(match_item); | |
432 T* found_item = contains_impl(match_item, idx); | |
433 if (found_item != NULL) { | |
434 // Remove item from linked list | |
435 T* prev = found_item->prev(); | |
436 T* next = found_item->next(); | |
437 if (prev != NULL) { | |
438 prev->set_next(next); | |
439 } else { | |
440 set_head(next, idx); | |
441 } | |
442 if (next != NULL) { | |
443 next->set_prev(prev); | |
444 } | |
445 | |
446 DEBUG_ONLY(_num_items--); | |
447 return found_item; | |
448 } | |
449 } | |
450 return NULL; | |
451 } | |
452 | |
453 | |
454 template<class T, class F> T* GenericHashtable<T, F>::contains_impl(T* item, int idx) { | |
455 T* current_item = head(idx); | |
456 while (current_item != NULL) { | |
457 if (current_item->equals(item)) { | |
458 return current_item; | |
459 } | |
460 current_item = current_item->next(); | |
461 } | |
462 return NULL; | |
463 } | |
464 | |
465 | |
466 // Explicitly instantiate these types | 355 // Explicitly instantiate these types |
467 template class Hashtable<ConstantPool*, mtClass>; | 356 template class Hashtable<ConstantPool*, mtClass>; |
468 template class Hashtable<Symbol*, mtSymbol>; | 357 template class Hashtable<Symbol*, mtSymbol>; |
469 template class Hashtable<Klass*, mtClass>; | 358 template class Hashtable<Klass*, mtClass>; |
470 template class Hashtable<oop, mtClass>; | 359 template class Hashtable<oop, mtClass>; |
480 template class BasicHashtableEntry<mtCode>; | 369 template class BasicHashtableEntry<mtCode>; |
481 template class BasicHashtable<mtClass>; | 370 template class BasicHashtable<mtClass>; |
482 template class BasicHashtable<mtSymbol>; | 371 template class BasicHashtable<mtSymbol>; |
483 template class BasicHashtable<mtCode>; | 372 template class BasicHashtable<mtCode>; |
484 template class BasicHashtable<mtInternal>; | 373 template class BasicHashtable<mtInternal>; |
485 | |
486 template class GenericHashtable<DependencySignature, ResourceObj>; |