/* File: "mem.h" */

/* Copyright (c) 1994-2018 by Marc Feeley, All Rights Reserved. */

#ifndef ___MEM_H
#define ___MEM_H


/*
 * Memory allocation parameters:
 *
 * ___MAX_NB_PARMS is the maximum number of formal parameters of procedures.
 *
 * ___MAX_NB_ARGS is the maximum number of arguments (actual parameters)
 * that are passed to procedures.  It must be >= ___MAX_NB_PARMS.
 *
 * ___MAX_NB_FRAME_SLOTS is the maximum number of slots in continuation
 * frames.  It must be >= ___MAX_NB_ARGS.
 *
 * ___MSECTION_SIZE is the size in words of sections that contain
 * movable objects (msections).
 *
 * ___MSECTION_FUDGE is the size in words of the msection fudge area.
 * There is a fudge area at the end of the space reserved for
 * allocating movable objects (heap fudge) and a fudge area at the end
 * of the space reserved for allocating continuation frames (stack
 * fudge).  Instructions in the code generated by the compiler check
 * whether the heap allocation pointer points into the heap fudge area
 * after a bounded number of constant size allocations and whether the
 * frame pointer points into the stack fudge area.  When either of
 * these cases occur, the assignment of space for the heap and stack
 * is adjusted.  If there is less than or equal to ___MSECTION_WASTE
 * words of space left, a garbage collection is triggered.
 * ___MSECTION_FUDGE must be >=
 * ___MAX_NB_FRAME_SLOTS+1+___SUBTYPED_BODY (which is the size of
 * the largest continuation frame).
 *
 * ___MSECTION_BIGGEST is the size in words beyond which an object will
 * be allocated as a still object.  It must be <= ___MSECTION_FUDGE.
 *
 * ___MSECTION_CHUNK is the size in words beyond which a chunk will
 * cause a new chunk to be started.
 *
 * ___MIN_NB_MSECTIONS_PER_PROCESSOR is the minimum number of msections
 * per processor contained in the heap.
 *
 * ___PSECTION_SIZE is the size in words of sections that contain permanent
 * objects (psections).
 *
 * ___PSECTION_WASTE is the maximum number of words that are unused
 * in a psection due to fragmentation.  It must be <= ___PSECTION_SIZE.
 *
 * ___DEFAULT_LIVE_PERCENT is the default percentage of the heap that
 * is live after a GC.  At the end of a GC the heap is resized to reach
 * this percentage.
 *
 * ___MAX_STILL_DEFERRED is the maximum number of words that are
 * allocated per processor to still objects before they are accounted for
 * at the VM level.
 */


#define ___MAX_NB_PARMS         1024
#define ___MAX_NB_ARGS          8192
#define ___MAX_NB_FRAME_SLOTS   8192
#define ___MSECTION_SIZE        131072
#define ___MSECTION_FUDGE       (___MAX_NB_FRAME_SLOTS+1+___SUBTYPED_BODY)
#define ___MSECTION_WASTE       (___MSECTION_FUDGE/16)
#define ___MSECTION_BIGGEST     255
#define ___MSECTION_CHUNK       ___MSECTION_BIGGEST
#define ___MIN_NB_MSECTIONS_PER_PROCESSOR 2
#define ___PSECTION_SIZE        4096
#define ___PSECTION_WASTE       32
#define ___DEFAULT_LIVE_PERCENT 50
#define ___DEFAULT_MIN_HEAP     (1*(1<<20))
#define ___MAX_STILL_DEFERRED   1024


/* 
 * Initial length of symbol table and keyword table.
 */

#define INIT_SYMBOL_TABLE_LENGTH  2048
#define INIT_KEYWORD_TABLE_LENGTH 128


extern ___SCMOBJ ___setup_mem_pstate
   ___P((___processor_state ___ps),
        ());

extern ___SCMOBJ ___setup_mem_vmstate
   ___P((___virtual_machine_state ___vms),
        ());

extern ___SCMOBJ ___setup_mem ___PVOID;

extern void ___cleanup_mem_pstate
   ___P((___processor_state ___ps),
        ());

extern void ___cleanup_mem_vmstate
   ___P((___virtual_machine_state ___vms),
        ());

extern void ___cleanup_mem ___PVOID;


extern ___BOOL ___garbage_collect_pstate
   ___P((___processor_state ___ps,
         ___SIZE_TS requested_words_still),
        ());


#ifdef ___DEBUG_STACK_LIMIT

#define ___stack_limit(ps) ___stack_limit_debug (ps,__LINE__,__FILE__)

extern ___BOOL ___stack_limit_debug
   ___P((___PSD
         int line,
         char *file),
        ());

#else

extern ___BOOL ___stack_limit
   ___P((___PSDNC),
        ());

#endif


extern ___WORD ___stack_overflow_undo_if_possible
   ___P((___PSDNC),
        ());


#ifdef ___DEBUG_HEAP_LIMIT

#define ___heap_limit(ps) ___heap_limit_debug (ps,__LINE__,__FILE__)

extern ___BOOL ___heap_limit_debug
   ___P((___PSD
         int line,
         char *file),
        ());

#else

extern ___BOOL ___heap_limit
   ___P((___PSDNC),
        ());

#endif


extern ___SCMOBJ ___hash_UTF_8_string
   ___P((___UTF_8STRING str),
        ());

extern ___SCMOBJ ___hash_scheme_string
   ___P((___SCMOBJ str),
        ());

extern void ___intern_symkey
   ___P((___SCMOBJ symkey),
        ());

extern ___SCMOBJ ___new_symkey
   ___P((___SCMOBJ name,
         unsigned int subtype),
        ());

extern ___SCMOBJ ___find_symkey_from_UTF_8_string
   ___P((char *str,
         unsigned int subtype),
        ());

extern ___SCMOBJ ___find_symkey_from_scheme_string
   ___P((___SCMOBJ str,
         unsigned int subtype),
        ());

extern ___SCMOBJ ___make_symkey_from_UTF_8_string
   ___P((___UTF_8STRING str,
         unsigned int subtype),
        ());

extern ___SCMOBJ ___make_symkey_from_scheme_string
   ___P((___SCMOBJ str,
         unsigned int subtype),
        ());

extern void ___for_each_symkey
   ___P((unsigned int subtype,
         void (*visit) (___SCMOBJ symkey, void *data),
         void *data),
        ());

#ifdef ___DEBUG_GARBAGE_COLLECT
#define ___USE_find_global_var_bound_to
#else
#ifdef ___DEBUG_HOST_CHANGES
#define ___USE_find_global_var_bound_to
#endif
#endif

#ifdef ___USE_find_global_var_bound_to

extern ___SCMOBJ ___find_global_var_bound_to
   ___P((___SCMOBJ val),
        ());

#endif

extern void ___glo_list_setup ___PVOID;

extern void ___glo_list_add
   ___P((___glo_struct *glo),
        ());

extern ___glo_struct *___glo_list_search_obj
   ___P((___SCMOBJ obj,
         ___BOOL prm),
        ());

extern ___SCMOBJ ___glo_struct_to_global_var
   ___P((___glo_struct *glo),
        ());

extern ___SCMOBJ ___obj_to_global_var
   ___P((___SCMOBJ obj,
         ___BOOL prm),
        ());

extern ___SCMOBJ ___make_global_var
   ___P((___SCMOBJ sym),
        ());

extern ___F64 ___bytes_allocated
   ___P((___PSDNC),
        ());


#endif
