src/share/vm/gc_implementation/concurrentMarkSweep/promotionInfo.hpp

changeset 1901
a00b51b2dda4
parent 1876
a8127dc669ba
child 1907
c18cbe5936b8
     1.1 --- a/src/share/vm/gc_implementation/concurrentMarkSweep/promotionInfo.hpp	Fri May 14 10:28:46 2010 -0700
     1.2 +++ b/src/share/vm/gc_implementation/concurrentMarkSweep/promotionInfo.hpp	Mon May 17 00:47:28 2010 -0700
     1.3 @@ -1,5 +1,5 @@
     1.4  /*
     1.5 - * Copyright 2001-2009 Sun Microsystems, Inc.  All Rights Reserved.
     1.6 + * Copyright 2010 Sun Microsystems, Inc.  All Rights Reserved.
     1.7   * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
     1.8   *
     1.9   * This code is free software; you can redistribute it and/or modify it
    1.10 @@ -32,30 +32,75 @@
    1.11      displaced_mark = nth_bit(2),        // i.e. 0x4
    1.12      next_mask      = ~(right_n_bits(3)) // i.e. ~(0x7)
    1.13    };
    1.14 -  intptr_t _next;
    1.15 +
    1.16 +  // Below, we want _narrow_next in the "higher" 32 bit slot,
    1.17 +  // whose position will depend on endian-ness of the platform.
    1.18 +  // This is so that there is no interference with the
    1.19 +  // cms_free_bit occupying bit position 7 (lsb == 0)
    1.20 +  // when we are using compressed oops; see FreeChunk::isFree().
    1.21 +  // We cannot move the cms_free_bit down because currently
    1.22 +  // biased locking code assumes that age bits are contiguous
    1.23 +  // with the lock bits. Even if that assumption were relaxed,
    1.24 +  // the least position we could move this bit to would be
    1.25 +  // to bit position 3, which would require 16 byte alignment.
    1.26 +  typedef struct {
    1.27 +#ifdef VM_LITTLE_ENDIAN
    1.28 +    LP64_ONLY(narrowOop _pad;)
    1.29 +              narrowOop _narrow_next;
    1.30 +#else
    1.31 +              narrowOop _narrow_next;
    1.32 +    LP64_ONLY(narrowOop _pad;)
    1.33 +#endif
    1.34 +  } Data;
    1.35 +
    1.36 +  union {
    1.37 +    intptr_t _next;
    1.38 +    Data     _data;
    1.39 +  };
    1.40   public:
    1.41    inline PromotedObject* next() const {
    1.42 -    return (PromotedObject*)(_next & next_mask);
    1.43 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.44 +    PromotedObject* res;
    1.45 +    if (UseCompressedOops) {
    1.46 +      // The next pointer is a compressed oop stored in the top 32 bits
    1.47 +      res = (PromotedObject*)oopDesc::decode_heap_oop(_data._narrow_next);
    1.48 +    } else {
    1.49 +      res = (PromotedObject*)(_next & next_mask);
    1.50 +    }
    1.51 +    assert(oop(res)->is_oop_or_null(true /* ignore mark word */), "Not an oop?");
    1.52 +    return res;
    1.53    }
    1.54    inline void setNext(PromotedObject* x) {
    1.55 -    assert(((intptr_t)x & ~next_mask) == 0,
    1.56 -           "Conflict in bit usage, "
    1.57 -           " or insufficient alignment of objects");
    1.58 -    _next |= (intptr_t)x;
    1.59 +    assert(((intptr_t)x & ~next_mask) == 0, "Conflict in bit usage, "
    1.60 +           "or insufficient alignment of objects");
    1.61 +    if (UseCompressedOops) {
    1.62 +      assert(_data._narrow_next == 0, "Overwrite?");
    1.63 +      _data._narrow_next = oopDesc::encode_heap_oop(oop(x));
    1.64 +    } else {
    1.65 +      _next |= (intptr_t)x;
    1.66 +    }
    1.67 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.68    }
    1.69    inline void setPromotedMark() {
    1.70      _next |= promoted_mask;
    1.71 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.72    }
    1.73    inline bool hasPromotedMark() const {
    1.74 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.75      return (_next & promoted_mask) == promoted_mask;
    1.76    }
    1.77    inline void setDisplacedMark() {
    1.78      _next |= displaced_mark;
    1.79 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.80    }
    1.81    inline bool hasDisplacedMark() const {
    1.82 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.83      return (_next & displaced_mark) != 0;
    1.84    }
    1.85 -  inline void clearNext()        { _next = 0; }
    1.86 +  inline void clearNext()        {
    1.87 +    _next = 0;
    1.88 +    assert(!((FreeChunk*)this)->isFree(), "Error");
    1.89 +  }
    1.90    debug_only(void *next_addr() { return (void *) &_next; })
    1.91  };
    1.92  

mercurial