/* mem-common.ins
 *
 * This is code that is common to all three implementations of the 
 * memory management library.
 */

#ifndef _MEM_COMMON_INS_
#define _MEM_COMMON_INS_

PVT Addr_t	PageSize;	/* the system page size. */
PVT Addr_t	PageShift;	/* PageSize == (1 << PageShift) */
PVT Addr_t	VMSizeB;	/* The amount of virtual memory allocated */

PVT status_t MapMemory (mem_obj_t *obj, Addr_t szb);
PVT void UnmapMemory (mem_obj_t *obj);


/* InitMemory:
 *
 * Initialize the common stuff.
 *
 */
PVT void InitMemory ()
{
    int		i, j;

    VMSizeB = 0;
    PageSize = GETPAGESIZE();
    for (i = 1, j = 0;  i != PageSize;  i <<= 1, j++)
	continue;
    PageShift = j;

} /* end of InitMemory */


/* MEM_GetVMSize:
 *
 * Return the amount of virtual memory (in K-bytes) allocated to the heap.
 */
long MEM_GetVMSize ()
{
    return (VMSizeB / ONE_K);

} /* end of MEM_GetVMSize */


/* MEM_AllocMemObj:
 * Get a new memory object from the O.S.  Return NIL on failure, otherwise return
 * a pointer to the object descriptor.
 */
mem_obj_t *MEM_AllocMemObj (Word_t szb)
{
    Word_t	alloc_szb;
    mem_obj_t	*obj;

    if ((obj = ALLOC_MEMOBJ()) == NIL(mem_obj_t *)) {
	Error ("unable to malloc chunk descriptor\n");
	return NIL(mem_obj_t *);
    }

    alloc_szb = (szb <= BIBOP_PAGE_SZB) ? BIBOP_PAGE_SZB : RND_MEMOBJ_SZB(szb);

    if (MapMemory (obj, alloc_szb) == FAILURE) {
	FREE_MEMOBJ (obj);
	return NIL(mem_obj_t *);
    }

    VMSizeB += alloc_szb;

    return obj;

} /* end of AllocMemObj */

/* MEM_FreeMemObj:
 */
void MEM_FreeMemObj (mem_obj_t *obj)
{
    if (obj == NIL(mem_obj_t *))
	return;

    UnmapMemory(obj);

    VMSizeB -= obj->sizeB;

    FREE_MEMOBJ (obj);

} /* end of MEM_FreeMemObj */

#endif /* !_MEM_COMMON_INS_ */
