Back to index

lightning-sunbird  0.9+nobinonly
Defines | Functions | Variables
stubborn.c File Reference
#include "gc_priv.h"

Go to the source code of this file.

Defines

#define GENERAL_MALLOC(lb, k)   (GC_PTR)GC_clear_stack(GC_generic_malloc((word)lb, k))
#define INIT_SIZE   10
#define ADD_CHANGING(p)

Functions

ptr_t GC_clear_stack ()
void GC_stubborn_init ()
GC_bool GC_compact_changing_list ()
void GC_change_stubborn (GC_PTR p)
void GC_end_stubborn_change (GC_PTR p)
GC_PTR GC_malloc_stubborn (size_t lb)
void GC_read_changed ()
GC_bool GC_page_was_changed (struct hblk *h)
void GC_clean_changing_list ()

Variables

GC_PTRGC_changing_list_start
GC_PTRGC_changing_list_current
GC_PTRGC_changing_list_limit

Define Documentation

Value:

Definition at line 109 of file stubborn.c.

#define GENERAL_MALLOC (   lb,
 
)    (GC_PTR)GC_clear_stack(GC_generic_malloc((word)lb, k))

Definition at line 24 of file stubborn.c.

#define INIT_SIZE   10

Function Documentation

Definition at line 122 of file stubborn.c.

Here is the caller graph for this function:

Definition at line 265 of file stubborn.c.

{
    register GC_PTR * p = GC_changing_list_start;
    register GC_PTR q;
    register ptr_t r;
    register unsigned long count = 0;
    register unsigned long dropped_count = 0;
    
    if (p == 0) /* initializing */ return;
    for (; p <= GC_changing_list_current; p++) {
        if ((q = *p) != 0) {
            count++;
            r = (ptr_t)GC_base(q);
            if (r == 0 || !GC_is_marked(r)) {
                *p = 0;
                dropped_count++;
           }
        }
    }
#   ifdef PRINTSTATS
      if (count > 0) {
        GC_printf2("%lu entries in changing list: reclaimed %lu\n",
                  (unsigned long)count, (unsigned long)dropped_count);
      }
#   endif
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 76 of file stubborn.c.

{
    register GC_PTR *p, *q;
    register word count = 0;
    word old_size = (char **)GC_changing_list_limit
                  - (char **)GC_changing_list_start+1;
                  /* The casts are needed as a workaround for an Amiga bug */
    register word new_size = old_size;
    GC_PTR * new_list;
    
    for (p = GC_changing_list_start; p < GC_changing_list_limit; p++) {
        if (*p != 0) count++;
    }
    if (2 * count > old_size) new_size = 2 * count;
    new_list = (GC_PTR *)
              GC_generic_malloc_inner(
                            new_size * sizeof(GC_PTR), PTRFREE);
              /* PTRFREE is a lie.  But we don't want the collector to  */
              /* consider these.  We do want the list itself to be      */
              /* collectable.                                           */
    if (new_list == 0) return(FALSE);
    BZERO(new_list, new_size * sizeof(GC_PTR));
    q = new_list;
    for (p = GC_changing_list_start; p < GC_changing_list_limit; p++) {
        if (*p != 0) *q++ = *p;
    }
    GC_changing_list_start = new_list;
    GC_changing_list_limit = new_list + new_size - 1;
    GC_changing_list_current = q;
    return(TRUE);
}

Here is the call graph for this function:

Definition at line 134 of file stubborn.c.

{
#   ifdef THREADS
      register VOLATILE GC_PTR * my_current = GC_changing_list_current;
#   else
      register GC_PTR * my_current = GC_changing_list_current;
#   endif
    register GC_bool tried_quick;
    DCL_LOCK_STATE;
    
    if (*my_current == p) {
        /* Hopefully the normal case.                                 */
        /* Compaction could not have been running when we started.    */
        *my_current = 0;
#      ifdef THREADS
          if (my_current == GC_changing_list_current) {
            /* Compaction can't have run in the interim.       */
            /* We got away with the quick and dirty approach.   */
            return;
          }
          tried_quick = TRUE;
#      else
         return;
#      endif
    } else {
        tried_quick = FALSE;
    }
    DISABLE_SIGNALS();
    LOCK();
    my_current = GC_changing_list_current;
    for (; my_current >= GC_changing_list_start; my_current--) {
        if (*my_current == p) {
            *my_current = 0;
            UNLOCK();
            ENABLE_SIGNALS();
            return;
        }
    }
    if (!tried_quick) {
        GC_err_printf1("Bad arg to GC_end_stubborn_change: 0x%lx\n",
                     (unsigned long)p);
        ABORT("Bad arg to GC_end_stubborn_change");
    }
    UNLOCK();
    ENABLE_SIGNALS();
}

Here is the caller graph for this function:

GC_PTR GC_malloc_stubborn ( size_t  lb)

Definition at line 189 of file stubborn.c.

{
register ptr_t op;
register ptr_t *opp;
register word lw;
ptr_t result;
DCL_LOCK_STATE;

    if( SMALL_OBJ(lb) ) {
#       ifdef MERGE_SIZES
         lw = GC_size_map[lb];
#      else
         lw = ALIGNED_WORDS(lb);
#       endif
       opp = &(GC_sobjfreelist[lw]);
       FASTLOCK();
        if( !FASTLOCK_SUCCEEDED() || (op = *opp) == 0 ) {
            FASTUNLOCK();
            result = GC_generic_malloc((word)lb, STUBBORN);
            goto record;
        }
        *opp = obj_link(op);
        obj_link(op) = 0;
        GC_words_allocd += lw;
        result = (GC_PTR) op;
        ADD_CHANGING(result);
        FASTUNLOCK();
        return((GC_PTR)result);
   } else {
       result = (GC_PTR)
              GC_generic_malloc((word)lb, STUBBORN);
   }
record:
   DISABLE_SIGNALS();
   LOCK();
   ADD_CHANGING(result);
   UNLOCK();
   ENABLE_SIGNALS();
   return((GC_PTR)GC_clear_stack(result));
}

Here is the call graph for this function:

Here is the caller graph for this function:

GC_bool GC_page_was_changed ( struct hblk h)

Definition at line 255 of file stubborn.c.

Definition at line 235 of file stubborn.c.

{
    register GC_PTR * p = GC_changing_list_start;
    register GC_PTR q;
    register struct hblk * h;
    register word index;
    
    if (p == 0) /* initializing */ return;
    BCOPY(GC_changed_pages, GC_prev_changed_pages,
          (sizeof GC_changed_pages));
    BZERO(GC_changed_pages, (sizeof GC_changed_pages));
    for (; p <= GC_changing_list_current; p++) {
        if ((q = *p) != 0) {
            h = HBLKPTR(q);
            index = PHT_HASH(h);
            set_pht_entry_from_index(GC_changed_pages, index);
        }
    }
}

Here is the caller graph for this function:

Definition at line 48 of file stubborn.c.

{
#   define INIT_SIZE 10

    GC_changing_list_start = (GC_PTR *)
                     GC_generic_malloc_inner(
                            (word)(INIT_SIZE * sizeof(GC_PTR)),
                            PTRFREE);
    BZERO(GC_changing_list_start,
         INIT_SIZE * sizeof(GC_PTR));
    if (GC_changing_list_start == 0) {
        GC_err_printf0("Insufficient space to start up\n");
        ABORT("GC_stubborn_init: put of space");
    }
    GC_changing_list_current = GC_changing_list_start;
    GC_changing_list_limit = GC_changing_list_start + INIT_SIZE - 1;
    * GC_changing_list_limit = 0;
}

Here is the call graph for this function:

Here is the caller graph for this function:


Variable Documentation

Definition at line 37 of file stubborn.c.

Definition at line 42 of file stubborn.c.

Definition at line 32 of file stubborn.c.