blob: 10a79719cb15c1a3377cd7013948772e2303d01e [file] [log] [blame]
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
#ifdef WSPACE_CONCURRENT_GC_STATS
#include "wspace_alloc.h"
#include "wspace_mark_sweep.h"
#include "wspace_verify.h"
#include "gc_ms.h"
#include "../gen/gen.h"
#include "../thread/collector.h"
#include "../finalizer_weakref/finalizer_weakref.h"
#include "../common/fix_repointed_refs.h"
#include "../common/gc_concurrent.h"
static unsigned int total_object_num = 0;
static unsigned int total_live_obj_num = 0;
static unsigned int total_float_obj_num = 0;
static unsigned int total_live_new_obj_num = 0;
static unsigned int total_float_new_obj_num = 0;
static Chunk_Header_Basic *volatile next_chunk_for_scanning;
static void wspace_init_chunk_for_scanning(Wspace *wspace)
{
next_chunk_for_scanning = (Chunk_Header_Basic*)space_heap_start((Space*)wspace);
}
static void normal_chunk_scanning(Chunk_Header *chunk)
{
chunk->slot_index = 0;
//chunk_depad_last_index_word(chunk);
unsigned int alloc_num = chunk->alloc_num;
assert(alloc_num);
if(alloc_num == chunk->slot_num){ /* Filled with objects */
unsigned int slot_size = chunk->slot_size;
Partial_Reveal_Object *p_obj = (Partial_Reveal_Object*)slot_index_to_addr(chunk, 0);
for(unsigned int i = alloc_num; i--;){
total_object_num ++;
if(obj_is_marked_in_vt(p_obj)){
total_live_obj_num ++;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_live_new_obj_num ++;
}
}else{
total_float_obj_num ++;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_float_new_obj_num ++;
}
}
p_obj = (Partial_Reveal_Object*)((POINTER_SIZE_INT)p_obj + slot_size);
}
} else { /* Chunk is not full */
while(alloc_num){
Partial_Reveal_Object *p_obj = next_alloc_slot_in_chunk(chunk);
total_object_num ++;
if(obj_is_marked_in_vt(p_obj)){
total_live_obj_num ++;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_live_new_obj_num ++;
}
}else{
total_float_obj_num ++;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_float_new_obj_num ++;
}
}
assert(p_obj);
--alloc_num;
}
}
if(chunk->alloc_num != chunk->slot_num){
//chunk_pad_last_index_word(chunk, cur_alloc_mask);
pfc_reset_slot_index(chunk);
}
}
static void abnormal_chunk_scanning(Chunk_Header *chunk)
{
Partial_Reveal_Object* p_obj = (Partial_Reveal_Object*)chunk->base;
total_object_num ++;
if(obj_is_marked_in_vt(p_obj)){
total_live_obj_num ++;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_live_new_obj_num ++;
}
}else{
total_float_obj_num ++;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_float_new_obj_num ++;
}
}
}
void wspace_scan_heap(GC* gc)
{
Wspace *wspace = gc_get_wspace(gc);
total_object_num = 0;
total_live_obj_num = 0;
total_float_obj_num = 0;
total_live_new_obj_num = 0;
total_float_new_obj_num = 0;
wspace_init_chunk_for_scanning(wspace);
Chunk_Header_Basic *chunk = wspace_grab_next_chunk(wspace, &next_chunk_for_scanning, FALSE);
while(chunk){
if(chunk->status & CHUNK_NORMAL)
normal_chunk_scanning((Chunk_Header*)chunk);
else if(chunk->status & CHUNK_ABNORMAL)
abnormal_chunk_scanning((Chunk_Header*)chunk);
chunk = wspace_grab_next_chunk(wspace, &next_chunk_for_scanning, FALSE);
}
printf("total_object_num: %d \n", total_object_num);
printf("total_live_obj_num: %d \n", total_live_obj_num);
printf("total_float_obj_num: %d \n", total_float_obj_num);
printf("total_live_new_obj_num: %d \n", total_live_new_obj_num);
printf("total_float_new_obj_num: %d \n", total_float_new_obj_num);
}
static void normal_chunk_clear(Chunk_Header *chunk)
{
chunk->slot_index = 0;
//chunk_depad_last_index_word(chunk);
unsigned int alloc_num = chunk->alloc_num;
assert(alloc_num);
if(alloc_num == chunk->slot_num){ /* Filled with objects */
unsigned int slot_size = chunk->slot_size;
Partial_Reveal_Object *p_obj = (Partial_Reveal_Object*)slot_index_to_addr(chunk, 0);
for(unsigned int i = alloc_num; i--;){
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
}
}
} else { /* Chunk is not full */
while(alloc_num){
Partial_Reveal_Object *p_obj = next_alloc_slot_in_chunk(chunk);
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
total_live_new_obj_num ++;
}
assert(p_obj);
--alloc_num;
}
}
if(chunk->alloc_num != chunk->slot_num){
//chunk_pad_last_index_word(chunk, cur_alloc_mask);
pfc_reset_slot_index(chunk);
}
}
static void abnormal_chunk_clear(Chunk_Header *chunk)
{
Partial_Reveal_Object* p_obj = (Partial_Reveal_Object*)chunk->base;
if(p_obj->obj_info & NEW_OBJ_MASK){
p_obj->obj_info &= ~NEW_OBJ_MASK;
}
}
void wspace_clear_heap(GC* gc)
{
Wspace *wspace = gc_get_wspace(gc);
wspace_init_chunk_for_scanning(wspace);
Chunk_Header_Basic *chunk = wspace_grab_next_chunk(wspace, &next_chunk_for_scanning, FALSE);
while(chunk){
if(chunk->status & CHUNK_NORMAL)
normal_chunk_clear((Chunk_Header*)chunk);
else if(chunk->status & CHUNK_ABNORMAL)
abnormal_chunk_clear((Chunk_Header*)chunk);
chunk = wspace_grab_next_chunk(wspace, &next_chunk_for_scanning, FALSE);
}
}
#endif