/* IBM_PROLOG_BEGIN_TAG                                                   */
/* This is an automatically generated prolog.                             */
/*                                                                        */
/* bos72Q src/bos/kernel/sys/malloc.h 1.28.1.4                            */
/*                                                                        */
/* Licensed Materials - Property of IBM                                   */
/*                                                                        */
/* COPYRIGHT International Business Machines Corp. 1989,2019              */
/* All Rights Reserved                                                    */
/*                                                                        */
/* US Government Users Restricted Rights - Use, duplication or            */
/* disclosure restricted by GSA ADP Schedule Contract with IBM Corp.      */
/*                                                                        */
/* IBM_PROLOG_END_TAG                                                     */
/* @(#)33	1.28.1.4  src/bos/kernel/sys/malloc.h, sysalloc, bos72Q, q2019_13A4 2/5/19 09:32:13 */
/*
 * COMPONENT_NAME: (LIBCGEN) Standard C Library General Functions
 *
 * ORIGINS: 27
 *
 */
#ifndef _H_SYS_MALLOC
#define _H_SYS_MALLOC

#include <sys/types.h>

typedef	void *	heapaddr_t;

#include <sys/processor.h>
#include <sys/ras.h>

#ifdef __cplusplus
extern "C" {
#endif

/*
 * The heap attribute structure used with the heap_create() interface
 */
typedef struct heapattr {
    eye_catch8b_t       hpa_eyec; 	/* eye catcher 			*/
    short               hpa_version;	/* structure is versioned 	*/
    long                hpa_flags;	/* flags 			*/
    void *		hpa_heapaddr;   /* heap addresss 		*/
    size_t              hpa_heapsize;	/* size in bytes		*/
    size_t              hpa_limit;	/* barrier independent from size*/
    long                hpa_debug_level;/* how much debug ? 		*/
    uint                hpa_kkey;	/* kernel key requested 	*/
} heapattr_t;


/*
 * hpa_flags specifications
 */
#define HPA_PAGED       0x0001          /* heap returns pageable memory */
#define HPA_PINNED      0x0002          /* heap returns pinned memory 	*/
#define HPA_SHARED      0x0004          /* returned unique descriptor is
                                              backed by common sub-heap */
#define HPA_PRIVATE     0x0008          /* isolated sub heap 		*/
#define HPA_RELEASE     0x0010          /* pass HEAP_RELEASE to init_heap */
#ifdef _KERNSYS				
#define HPA_DISABLED_XMFREE	0x0020	/* allow disabled xmfree() on */
					/* private heap */	
#endif
#define HPA_NO_CACHE	0x0040		/* Do not cache freed memory on
					 * per-cpu free lists.
					 */

#define HPA_VERSION     0x0001          /* structure version 		*/
#define HPA_INVALID_HEAP	(void *)-1
#define HPA_DEFAULT_DEBUG	0
#define EYEC_HEAPATTR		__EYEC8('H','E','A','P','A','T','T','R')


#ifdef _KERNEL
#ifndef _NO_PROTO
/* 
 * init_heap initializes an area of memory as a heap. The
 * origin address, area, must be page aligned.  The size
 * is in bytes and need not be page aligned.  The minimum size
 * heap is log2 pagesize-3,  which for 4096 pages is 9 pages.
 * heaps are normally expected to be large.  The maximum
 * heap size is 2**32 XXX.  Heaps may cross segment boudaries, 
 * including the 2**31 boundary.
 *
 * heapp is NULL when initializing a new heap.  If heapp is
 * provided, init_heap returns the heapaddr of the alternate
 * heap for the given heap.  In this case, area and size are ignored
 *
 * Heaps are managed internally with relative addresses.  Thus a segment
 * may be made addressable at different locations and heap calls used
 * to allocate and free storage.  Each call will use the current virtual
 * address of the heap and data.
 */

/*
 * This interface should not be used by kernel extensions to create
 * heaps after release 5.4.  The create_heap() interface should be
 * used instead so that storage keys can be specified.
 */

heapaddr_t
init_heap(caddr_t area,uint32long64_t size,heapaddr_t heapp);

kerrno_t
heap_create(heapattr_t  *heapattr,
            heapaddr_t  *heapptr);

kerrno_t
heap_destroy(heapaddr_t heapptr,
             long       flags);

kerrno_t
heap_modify(heapaddr_t  heapptr,
            long        command,
            long        argument);

/*
 * allocate size bytes.  align specifies the required alignment.  However,
 * all allocations are aligned at least to the next largest power of 2.
 * if size < PGSIZE and to a page otherwise - so align can be safely 
 * specified as 0.
 *
 * It is a committed feature of the architecture that align 0 will always return
 * allignment to the next power of two, independent of implementation.
 * xmalloc does NOT clear storage which is allocated - initialize it yourself!
 */
void *
xmalloc(uint32long64_t size,uint align,heapaddr_t heapp);

/*
 * Same as xmalloc above, but allocate storage on a particular memory domain.
 * If passed an invalid srad number or non NUMA style heap, xmalloc_srad will
 * fail.
 */
void *
xmalloc_srad(long req_size,uint align,heapaddr_t heapp,sradid_t srad);

/*
 * free a previously allocated piece of storage.  addr must be an address
 * returned by xmalloc.  
 */
int
xmfree(void * addr,heapaddr_t heapp);

/* interrupt level support for xmfree operations.  Can fail for some storage */
int
xmfree_interrupt(void * addr,heapaddr_t heapp);

int
xmdbg_query(void);

#else	/* no proto */

heapaddr_t
init_heap();

kerrno_t
heap_create();

kerrno_t
heap_destroy();

kerrno_t
heap_modify();

void *
xmalloc();

void *
xmalloc_srad();

int
xmfree();

int
xmdbg_query();

#endif


/* Commands for heap_modify */
#define XMHM_DEBUG_LEVEL 0x1    /* argument is new debug level */
#define XMHM_HEAP_LIMIT  0x2    /* argument is new heap limit  */
#define XMHM_HEAP_PSIZE  0x3    /* Heap always returns default page size */

/* kerrnos for heap_create(), heap_modify(), and heap_destroy */

                                        /* 0x96518001/0xEEEE000096518001 */
#define EINVAL_HEAP_CREATE              KERROR(EINVAL, sysalloc_BLOCK_00, 1)

                                        /* 0x96518002/0xEEEE000096518002 */
#define ENOMEM_HEAP_CREATE              KERROR(EINVAL, sysalloc_BLOCK_00, 2)

                                        /* 0x96518003/0xEEEE000096518003 */
#define EINVAL_HEAP_DESTROY             KERROR(EINVAL, sysalloc_BLOCK_00, 3)

                                        /* 0x96518004/0xEEEE000096518004 */
#define EINVAL_HEAP_MODIFY              KERROR(EINVAL, sysalloc_BLOCK_00, 4)

                                        /* 0x96518005/0xEEEE000096518005 */
#define EBUSY_HEAP_DESTROY              KERROR(EINVAL,  sysalloc_BLOCK_00, 5)


/* 
 * xmalloc debug/MODS query routine. possible return values are listed below.
 * Currently there are only two options: off and full. This may or may not
 * change in future releases.
 */
#define XMDBG_OFF  0
#define XMDBG_FULL 1 

#ifndef _NO_PROTO
int
xmdbg_query(void);
#else
int
xmdbg_query();
#endif

/* 
 * N.B. these symbols are now heapaddr_t's - so the correct calls are
 * as in the defines below.  Calls which pass &kernel_heap and &pinned_heap
 * will be (at least temporarally) supported - but please fix your code
 */

#ifndef __KDB_USER

#define palloc(x,y)	xmalloc( x, y, kernel_heap )
#define malloc(x)	xmalloc( x, 0, kernel_heap )
#define free(x)		xmfree( x, kernel_heap )

#endif /* __KDB_USER */

#endif /* _KERNEL */

extern heapaddr_t kernel_heap;
extern heapaddr_t pinned_heap;

#ifdef __cplusplus
}
#endif

#endif /* _H_SYS_MALLOC */
