zoukankan      html  css  js  c++  java
  • jvm源码解读--14 defNewGeneration.cpp gc标记复制之后,进行空间清理

    进入Eden()->clean()函数

    void EdenSpace::clear(bool mangle_space) {
      ContiguousSpace::clear(mangle_space);
      set_soft_end(end());
    }

    进入

    void ContiguousSpace::clear(bool mangle_space) {
      set_top(bottom());
      set_saved_mark();
      CompactibleSpace::clear(mangle_space);
    }

    打印对象,这个是eden

    (gdb) p this 
    $154 = (EdenSpace * const) 0x7f4780020328
    (gdb) p * this 
    $155 = (EdenSpace) {
      <ContiguousSpace> = {
        <CompactibleSpace> = {
          <Space> = {
            <CHeapObj<1280u>> = {
              <AllocatedObj> = {
                _vptr.AllocatedObj = 0x7f4788515a90 <vtable for EdenSpace+16>
              }, <No data fields>}, 
            members of Space: 
            _bottom = 0xf3800000, 
            _end = 0xf5600000, 
            _saved_mark_word = 0xf4dccdb8, 
            _preconsumptionDirtyCardClosure = 0x0, 
            _par_seq_tasks = {
              <StackObj> = {
                <AllocatedObj> = {
                  _vptr.AllocatedObj = 0x7f47884fb650 <vtable for SequentialSubTasksDone+16>
                }, <No data fields>}, 
              members of SequentialSubTasksDone: 
              _n_tasks = 0, 
              _n_claimed = 0, 
              _n_threads = 0, 
              _n_completed = 0
            }
          }, 
          members of CompactibleSpace: 
          _compaction_top = 0xf3800000, 
          _next_compaction_space = 0x7f4780020438, 
          _first_dead = 0xf1f1f1f1f1f1f1f1, 
          _end_of_live = 0xf1f1f1f1f1f1f1f1
        }, 
        members of ContiguousSpace: 
        _top = 0xf4dccdb8, 
        _concurrent_iteration_safe_limit = 0xf3800000, 
        _mangler = 0x7f47800203e8
      }, 
      members of EdenSpace: 
      _gen = 0x7f478001f1c8, 
      _soft_end = 0xf5600000
    }

    看实现

    (gdb) p bottom()
    $156 = (HeapWord *) 0xf3800000
    (gdb) p top()
    $157 = (HeapWord *) 0xf4dccdb8

    将top清空

    设置mark

     virtual void set_saved_mark()    { _saved_mark_word = top();    }

    清理完之后的对象

    (gdb) p *this
    $159 = (EdenSpace) {
      <ContiguousSpace> = {
        <CompactibleSpace> = {
          <Space> = {
            <CHeapObj<1280u>> = {
              <AllocatedObj> = {
                _vptr.AllocatedObj = 0x7f4788515a90 <vtable for EdenSpace+16>
              }, <No data fields>}, 
            members of Space: 
            _bottom = 0xf3800000, 
            _end = 0xf5600000, 
            _saved_mark_word = 0xf3800000, 
            _preconsumptionDirtyCardClosure = 0x0, 
            _par_seq_tasks = {
              <StackObj> = {
                <AllocatedObj> = {
                  _vptr.AllocatedObj = 0x7f47884fb650 <vtable for SequentialSubTasksDone+16>
                }, <No data fields>}, 
              members of SequentialSubTasksDone: 
              _n_tasks = 0, 
              _n_claimed = 0, 
              _n_threads = 0, 
              _n_completed = 0
            }
          }, 
          members of CompactibleSpace: 
          _compaction_top = 0xf3800000, 
          _next_compaction_space = 0x7f4780020438, 
          _first_dead = 0xf1f1f1f1f1f1f1f1, 
          _end_of_live = 0xf1f1f1f1f1f1f1f1
        }, 
        members of ContiguousSpace: 
        _top = 0xf3800000, 
        _concurrent_iteration_safe_limit = 0xf3800000, 
        _mangler = 0x7f47800203e8
      }, 
      members of EdenSpace: 
      _gen = 0x7f478001f1c8, 
      _soft_end = 0xf5600000
    }

    接着看

    CompactibleSpace::clear(mangle_space);
    ----------------------------------------------
    void CompactibleSpace::clear(bool mangle_space) {
      Space::clear(mangle_space);
      _compaction_top = bottom();
    }
    ----------------------------------------------
    void Space::clear(bool mangle_space) {
      if (ZapUnusedHeapArea && mangle_space) {
        mangle_unused_area();
      }
    }
    
    -------------------------------------------------
    void ContiguousSpace::mangle_unused_area() {
      mangler()->mangle_unused_area();
    }
    -----------------------------------------------------
    void SpaceMangler::mangle_unused_area() {
      assert(ZapUnusedHeapArea, "Mangling should not be in use");
      // Mangle between top and the high water mark.  Safeguard
      // against the space changing since top_for_allocations was
      // set.
      HeapWord* mangled_end = MIN2(top_for_allocations(), end());
      if (top() < mangled_end) {
        MemRegion mangle_mr(top(), mangled_end);
        SpaceMangler::mangle_region(mangle_mr);
        // Light weight check of mangling.
        check_mangled_unused_area(end());
      }
      // Complete check of unused area which is functional when
      // DEBUG_MANGLING is defined.
      check_mangled_unused_area_complete();
    }

    打印这个spaceMangler对象

    (gdb) p _mangler
    $162 = (GenSpaceMangler *) 0x7f47800203e8
    (gdb) p *_mangler
    $163 = (GenSpaceMangler) {
      <SpaceMangler> = {
        <CHeapObj<1280u>> = {
          <AllocatedObj> = {
            _vptr.AllocatedObj = 0x7f47885163d0 <vtable for GenSpaceMangler+16>
          }, <No data fields>}, 
        members of SpaceMangler: 
        _top_for_allocations = 0xf4dccdb8
      }, 
      members of GenSpaceMangler: 
      _sp = 0x7f4780020328
    }

    查看紫色函数

    (gdb) p end()
    $164 = (HeapWord *) 0xf5600000
    (gdb) p _top_for_allocations
    $165 = (HeapWord *) 0xf4dccdb8

    进入棕色函数

    // Simply mangle the MemRegion mr.
    void SpaceMangler::mangle_region(MemRegion mr) {
      assert(ZapUnusedHeapArea, "Mangling should not be in use");
    #ifdef ASSERT
      if(TraceZapUnusedHeapArea) {
        gclog_or_tty->print("Mangling [0x%x to 0x%x)", mr.start(), mr.end());
      }
      Copy::fill_to_words(mr.start(), mr.word_size(), badHeapWord);
      if(TraceZapUnusedHeapArea) {
        gclog_or_tty->print_cr(" done");
      }
    #endif
    }

    进入函数

      // Fill methods
    
      // Fill word-aligned words, not atomic on each word
      // set_words
      static void fill_to_words(HeapWord* to, size_t count, juint value = 0) {
        assert_params_ok(to, LogHeapWordSize);
        pd_fill_to_words(to, count, value);
      }

    进入

    static void pd_fill_to_words(HeapWord* tohw, size_t count, juint value) {
    #ifdef AMD64
      julong* to = (julong*) tohw;
      julong  v  = ((julong) value << 32) | value;
      while (count-- > 0) {
        *to++ = v;
      }
    #else..无用..
    #endif // AMD64
    }

    看badHeapWord的值

    (gdb) p/x value 
    $171 = 0xbaadbabe

    那么上述过程就是将heap的值全部设置成了0xbaadbabe

    接着就是对from区域

    (gdb) p from()
    $175 = (ContiguousSpace *) 0x7f4780020438

    重要的交换空间

        swap_spaces();

    交换之前

    (gdb) p this 
    $181 = (DefNewGeneration * const) 0x7f478001f1c8
    (gdb) p* this
    $182 = (DefNewGeneration) {
      <Generation> = {
        <CHeapObj<1280u>> = {
          <AllocatedObj> = {
            _vptr.AllocatedObj = 0x7f47884ff590 <vtable for DefNewGeneration+16>
          }, <No data fields>}, 
        members of Generation: 
        _time_of_last_gc = -1012762419733073423, 
        _prev_used_region = {
          _start = 0x0, 
          _word_size = 0
        }, 
        _reserved = {
          _start = 0xf3800000, 
          _word_size = 6553600
        }, 
    ....略部分
      _promo_failure_drain_in_progress = false, 
      _gen_counters = 0x7f4780020638, 
      _eden_counters = 0x7f478000d678, 
      _from_counters = 0x7f4780021888, 
      _to_counters = 0x7f4780021d78, 
      _max_eden_size = 31457280, 
      _max_survivor_size = 10485760, 
      _should_allocate_from_space = false, 
      _eden_space = 0x7f4780020328, 
      _from_space = 0x7f4780020438, 
      _to_space = 0x7f4780020538, 
      _gc_timer = 0x7f4780022268
    }

    代码为

    void DefNewGeneration::swap_spaces() {
      ContiguousSpace* s = from();
      _from_space        = to();
      _to_space          = s;
      eden()->set_next_compaction_space(from());
      // The to-space is normally empty before a compaction so need
      // not be considered.  The exception is during promotion
      // failure handling when to-space can contain live objects.
      from()->set_next_compaction_space(NULL);
    
      if (UsePerfData) {
        CSpaceCounters* c = _from_counters;
        _from_counters = _to_counters;
        _to_counters = c;
      }
    }

    这个函数为  eden()->set_next_compaction_space(from());

      void set_next_compaction_space(CompactibleSpace* csp) {
        _next_compaction_space = csp;
      }

    将eden()的值设置为新的from值,(即原来的from空间已经变为了to空间)

      if (UsePerfData) {
        CSpaceCounters* c = _from_counters;
        _from_counters = _to_counters;
        _to_counters = c;
      }

    设置完成后就结束了

  • 相关阅读:
    ASCII码表记忆规律
    Live Photos原理
    FAAS -- Serverless
    wasm能力检测
    守则
    split分割文件
    个人开源项目:微服务全栈技术学习开源项目,涵盖Java及前端主流技术点
    采用React+Ant Design组件化开发前端界面(一)
    SpringBoot 2.0中SpringWebContext 找不到无法使用的问题解决
    [做全栈攻城狮]程序员带你学习安卓开发-安卓基础之网络编程 大汇总
  • 原文地址:https://www.cnblogs.com/zytcomeon/p/14776435.html
Copyright © 2011-2022 走看看