X-Git-Url: http://wien.tomnetworks.com/gitweb/?a=blobdiff_plain;f=mono%2Fsgen%2Fsgen-fin-weak-hash.c;h=814b516a272042624a2e9a95a73a86ba5ffc4659;hb=a984f20e232d863a9d3b7848023f78816aa282e7;hp=dd7cca93dbecc2634a3c6dce3ece2278a5d040ca;hpb=58e8a9f85176c9607e605b888ef45db01a0f6997;p=mono.git diff --git a/mono/sgen/sgen-fin-weak-hash.c b/mono/sgen/sgen-fin-weak-hash.c index dd7cca93dbe..814b516a272 100644 --- a/mono/sgen/sgen-fin-weak-hash.c +++ b/mono/sgen/sgen-fin-weak-hash.c @@ -1,5 +1,6 @@ -/* - * sgen-fin-weak-hash.c: Finalizers and weak links. +/** + * \file + * Finalizers and weak links. * * Author: * Paolo Molaro (lupus@ximian.com) @@ -228,7 +229,7 @@ sgen_finalize_in_range (int generation, ScanCopyContext ctx) } /* LOCKING: requires that the GC lock is held */ -static void +static MONO_PERMIT (need (sgen_gc_locked)) void register_for_finalization (GCObject *obj, void *user_data, int generation) { SgenHashTable *hash_table = get_finalize_entry_hash_table (generation); @@ -345,7 +346,7 @@ try_lock_stage_for_processing (int num_entries, volatile gint32 *next_entry) } /* LOCKING: requires that the GC lock is held */ -static void +static MONO_PERMIT (need (sgen_gc_locked)) void process_stage_entries (int num_entries, volatile gint32 *next_entry, StageEntry *entries, void (*process_func) (GCObject*, void*, int)) { int i; @@ -527,7 +528,7 @@ add_stage_entry (int num_entries, volatile gint32 *next_entry, StageEntry *entri } /* LOCKING: requires that the GC lock is held */ -static void +static MONO_PERMIT (need (sgen_gc_locked)) void process_fin_stage_entry (GCObject *obj, void *user_data, int index) { if (ptr_in_nursery (obj)) @@ -557,30 +558,27 @@ sgen_object_register_for_finalization (GCObject *obj, void *user_data) } /* LOCKING: requires that the GC lock is held */ -static int -finalizers_with_predicate (SgenObjectPredicateFunc predicate, void *user_data, GCObject **out_array, int out_size, SgenHashTable *hash_table) +static MONO_PERMIT (need (sgen_gc_locked)) void +finalize_with_predicate (SgenObjectPredicateFunc predicate, void *user_data, SgenHashTable *hash_table) { GCObject *object; gpointer dummy G_GNUC_UNUSED; - int count; - if (no_finalize || !out_size || !out_array) - return 0; - count = 0; + if (no_finalize) + return; SGEN_HASH_TABLE_FOREACH (hash_table, GCObject *, object, gpointer, dummy) { object = tagged_object_get_object (object); if (predicate (object, user_data)) { /* remove and put in out_array */ SGEN_HASH_TABLE_FOREACH_REMOVE (TRUE); - out_array [count ++] = object; - SGEN_LOG (5, "Collecting object for finalization: %p (%s) (%d)", object, sgen_client_vtable_get_name (SGEN_LOAD_VTABLE (object)), sgen_hash_table_num_entries (hash_table)); - if (count == out_size) - return count; - continue; + sgen_queue_finalization_entry (object); + SGEN_LOG (5, "Enqueuing object for finalization: %p (%s) (%d)", object, sgen_client_vtable_get_name (SGEN_LOAD_VTABLE (object)), sgen_hash_table_num_entries (hash_table)); } + + if (sgen_suspend_finalizers) + break; } SGEN_HASH_TABLE_FOREACH_END; - return count; } /** @@ -599,21 +597,14 @@ finalizers_with_predicate (SgenObjectPredicateFunc predicate, void *user_data, G * @out_array me be on the stack, or registered as a root, to allow the GC to know the * objects are still alive. */ -int -sgen_gather_finalizers_if (SgenObjectPredicateFunc predicate, void *user_data, GCObject **out_array, int out_size) +void +sgen_finalize_if (SgenObjectPredicateFunc predicate, void *user_data) { - int result; - LOCK_GC; sgen_process_fin_stage_entries (); - result = finalizers_with_predicate (predicate, user_data, (GCObject**)out_array, out_size, &minor_finalizable_hash); - if (result < out_size) { - result += finalizers_with_predicate (predicate, user_data, (GCObject**)out_array + result, out_size - result, - &major_finalizable_hash); - } + finalize_with_predicate (predicate, user_data, &minor_finalizable_hash); + finalize_with_predicate (predicate, user_data, &major_finalizable_hash); UNLOCK_GC; - - return result; } void