hotspot/src/share/vm/oops/markOop.hpp
Print this page
rev 611 : Merge
*** 1,10 ****
#ifdef USE_PRAGMA_IDENT_HDR
#pragma ident "@(#)markOop.hpp 1.66 08/11/24 12:22:54 JVM"
#endif
/*
! * Copyright 1997-2006 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
--- 1,10 ----
#ifdef USE_PRAGMA_IDENT_HDR
#pragma ident "@(#)markOop.hpp 1.66 08/11/24 12:22:54 JVM"
#endif
/*
! * Copyright 1997-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
* under the terms of the GNU General Public License version 2 only, as
* published by the Free Software Foundation.
*** 30,41 ****
// Note that the mark is not a real oop but just a word.
// It is placed in the oop hierarchy for historical reasons.
//
// Bit-format of an object header (most significant first):
//
! //
! // unused:0/25 hash:25/31 age:4 biased_lock:1 lock:2 = 32/64 bits
//
// - hash contains the identity hash value: largest value is
// 31 bits, see os::random(). Also, 64-bit vm's require
// a hash value no bigger than 32 bits because they will not
// properly generate a mask larger than that: see library_call.cpp
--- 30,43 ----
// Note that the mark is not a real oop but just a word.
// It is placed in the oop hierarchy for historical reasons.
//
// Bit-format of an object header (most significant first):
//
! // 32 bits: unused:0 hash:25 age:4 biased_lock:1 lock:2
! // 64 bits: unused:24 hash:31 cms:2 age:4 biased_lock:1 lock:2
! // unused:20 size:35 cms:2 age:4 biased_lock:1 lock:2 (if cms
! // free chunk)
//
// - hash contains the identity hash value: largest value is
// 31 bits, see os::random(). Also, 64-bit vm's require
// a hash value no bigger than 32 bits because they will not
// properly generate a mask larger than that: see library_call.cpp
*** 90,101 ****
public:
// Constants
enum { age_bits = 4,
lock_bits = 2,
biased_lock_bits = 1,
! max_hash_bits = BitsPerOop - age_bits - lock_bits - biased_lock_bits,
hash_bits = max_hash_bits > 31 ? 31 : max_hash_bits,
epoch_bits = 2
};
// The biased locking code currently requires that the age bits be
// contiguous to the lock bits. Class data sharing would prefer the
--- 92,104 ----
public:
// Constants
enum { age_bits = 4,
lock_bits = 2,
biased_lock_bits = 1,
! max_hash_bits = BitsPerWord - age_bits - lock_bits - biased_lock_bits,
hash_bits = max_hash_bits > 31 ? 31 : max_hash_bits,
+ cms_bits = LP64_ONLY(1) NOT_LP64(0),
epoch_bits = 2
};
// The biased locking code currently requires that the age bits be
// contiguous to the lock bits. Class data sharing would prefer the
*** 107,117 ****
// of the biased locking code.
enum { lock_shift = 0,
biased_lock_shift = lock_bits,
age_shift = lock_bits + biased_lock_bits,
! hash_shift = lock_bits + biased_lock_bits + age_bits,
epoch_shift = hash_shift
};
enum { lock_mask = right_n_bits(lock_bits),
lock_mask_in_place = lock_mask << lock_shift,
--- 110,121 ----
// of the biased locking code.
enum { lock_shift = 0,
biased_lock_shift = lock_bits,
age_shift = lock_bits + biased_lock_bits,
! cms_shift = age_shift + age_bits,
! hash_shift = cms_shift + cms_bits,
epoch_shift = hash_shift
};
enum { lock_mask = right_n_bits(lock_bits),
lock_mask_in_place = lock_mask << lock_shift,
*** 119,129 ****
biased_lock_mask_in_place= biased_lock_mask << lock_shift,
biased_lock_bit_in_place = 1 << biased_lock_shift,
age_mask = right_n_bits(age_bits),
age_mask_in_place = age_mask << age_shift,
epoch_mask = right_n_bits(epoch_bits),
! epoch_mask_in_place = epoch_mask << epoch_shift
#ifndef _WIN64
,hash_mask = right_n_bits(hash_bits),
hash_mask_in_place = (address_word)hash_mask << hash_shift
#endif
};
--- 123,135 ----
biased_lock_mask_in_place= biased_lock_mask << lock_shift,
biased_lock_bit_in_place = 1 << biased_lock_shift,
age_mask = right_n_bits(age_bits),
age_mask_in_place = age_mask << age_shift,
epoch_mask = right_n_bits(epoch_bits),
! epoch_mask_in_place = epoch_mask << epoch_shift,
! cms_mask = right_n_bits(cms_bits),
! cms_mask_in_place = cms_mask << cms_shift
#ifndef _WIN64
,hash_mask = right_n_bits(hash_bits),
hash_mask_in_place = (address_word)hash_mask << hash_shift
#endif
};
*** 217,231 ****
// other thread. (They should spin or block instead. The 0 value
// is transient and *should* be short-lived).
static markOop INFLATING() { return (markOop) 0; } // inflate-in-progress
// Should this header be preserved during GC?
! bool must_be_preserved(oop obj_containing_mark) const {
! if (!UseBiasedLocking)
! return (!is_unlocked() || !has_no_hash());
! return must_be_preserved_with_bias(obj_containing_mark);
! }
inline bool must_be_preserved_with_bias(oop obj_containing_mark) const;
// Should this header (including its age bits) be preserved in the
// case of a promotion failure during scavenge?
// Note that we special case this situation. We want to avoid
--- 223,233 ----
// other thread. (They should spin or block instead. The 0 value
// is transient and *should* be short-lived).
static markOop INFLATING() { return (markOop) 0; } // inflate-in-progress
// Should this header be preserved during GC?
! inline bool must_be_preserved(oop obj_containing_mark) const;
inline bool must_be_preserved_with_bias(oop obj_containing_mark) const;
// Should this header (including its age bits) be preserved in the
// case of a promotion failure during scavenge?
// Note that we special case this situation. We want to avoid
*** 241,266 ****
// place in which to call them in any of the scavengers (although
// guarded by appropriate locks we could make one), but the
// observation is that promotion failures are quite rare and
// reducing the number of mark words preserved during them isn't a
// high priority.
! bool must_be_preserved_for_promotion_failure(oop obj_containing_mark) const {
! if (!UseBiasedLocking)
! return (this != prototype());
! return must_be_preserved_with_bias_for_promotion_failure(obj_containing_mark);
! }
inline bool must_be_preserved_with_bias_for_promotion_failure(oop obj_containing_mark) const;
// Should this header be preserved during a scavenge where CMS is
// the old generation?
// (This is basically the same body as must_be_preserved_for_promotion_failure(),
// but takes the klassOop as argument instead)
! bool must_be_preserved_for_cms_scavenge(klassOop klass_of_obj_containing_mark) const {
! if (!UseBiasedLocking)
! return (this != prototype());
! return must_be_preserved_with_bias_for_cms_scavenge(klass_of_obj_containing_mark);
! }
inline bool must_be_preserved_with_bias_for_cms_scavenge(klassOop klass_of_obj_containing_mark) const;
// WARNING: The following routines are used EXCLUSIVELY by
// synchronization functions. They are not really gc safe.
// They must get updated if markOop layout get changed.
--- 243,260 ----
// place in which to call them in any of the scavengers (although
// guarded by appropriate locks we could make one), but the
// observation is that promotion failures are quite rare and
// reducing the number of mark words preserved during them isn't a
// high priority.
! inline bool must_be_preserved_for_promotion_failure(oop obj_containing_mark) const;
inline bool must_be_preserved_with_bias_for_promotion_failure(oop obj_containing_mark) const;
// Should this header be preserved during a scavenge where CMS is
// the old generation?
// (This is basically the same body as must_be_preserved_for_promotion_failure(),
// but takes the klassOop as argument instead)
! inline bool must_be_preserved_for_cms_scavenge(klassOop klass_of_obj_containing_mark) const;
inline bool must_be_preserved_with_bias_for_cms_scavenge(klassOop klass_of_obj_containing_mark) const;
// WARNING: The following routines are used EXCLUSIVELY by
// synchronization functions. They are not really gc safe.
// They must get updated if markOop layout get changed.
*** 361,366 ****
--- 355,396 ----
// Recover address of oop from encoded form used in mark
inline void* decode_pointer() { if (UseBiasedLocking && has_bias_pattern()) return NULL; return clear_lock_bits(); }
// see the definition in markOop.cpp for the gory details
bool should_not_be_cached() const;
+
+ // These markOops indicate cms free chunk blocks and not objects.
+ // In 64 bit, the markOop is set to distinguish them from oops.
+ // These are defined in 32 bit mode for vmStructs.
+ const static uintptr_t cms_free_chunk_pattern = 0x1;
+
+ // Constants for the size field.
+ enum { size_shift = cms_shift + cms_bits,
+ size_bits = 35 // need for compressed oops 32G
+ };
+ // These values are too big for Win64
+ const static uintptr_t size_mask = LP64_ONLY(right_n_bits(size_bits))
+ NOT_LP64(0);
+ const static uintptr_t size_mask_in_place =
+ (address_word)size_mask << size_shift;
+
+ #ifdef _LP64
+ static markOop cms_free_prototype() {
+ return markOop(((intptr_t)prototype() & ~cms_mask_in_place) |
+ ((cms_free_chunk_pattern & cms_mask) << cms_shift));
+ }
+ uintptr_t cms_encoding() const {
+ return mask_bits(value() >> cms_shift, cms_mask);
+ }
+ bool is_cms_free_chunk() const {
+ return is_neutral() &&
+ (cms_encoding() & cms_free_chunk_pattern) == cms_free_chunk_pattern;
+ }
+
+ size_t get_size() const { return (size_t)(value() >> size_shift); }
+ static markOop set_size_and_free(size_t size) {
+ assert((size & ~size_mask) == 0, "shouldn't overflow size field");
+ return markOop(((intptr_t)cms_free_prototype() & ~size_mask_in_place) |
+ (((intptr_t)size & size_mask) << size_shift));
+ }
+ #endif // _LP64
};