diff options
Diffstat (limited to 'Source/DirectFB/lib/fusion/shm/shm_internal.h')
-rwxr-xr-x | Source/DirectFB/lib/fusion/shm/shm_internal.h | 264 |
1 files changed, 264 insertions, 0 deletions
diff --git a/Source/DirectFB/lib/fusion/shm/shm_internal.h b/Source/DirectFB/lib/fusion/shm/shm_internal.h new file mode 100755 index 0000000..3e282a5 --- /dev/null +++ b/Source/DirectFB/lib/fusion/shm/shm_internal.h @@ -0,0 +1,264 @@ +/* + (c) Copyright 2001-2009 The world wide DirectFB Open Source Community (directfb.org) + (c) Copyright 2000-2004 Convergence (integrated media) GmbH + + All rights reserved. + + Written by Denis Oliver Kropp <dok@directfb.org>, + Andreas Hundt <andi@fischlustig.de>, + Sven Neumann <neo@directfb.org>, + Ville Syrjälä <syrjala@sci.fi> and + Claudio Ciccani <klan@users.sf.net>. + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the + Free Software Foundation, Inc., 59 Temple Place - Suite 330, + Boston, MA 02111-1307, USA. +*/ + +#ifndef __FUSION__SHM__SHM_INTERNAL_H__ +#define __FUSION__SHM__SHM_INTERNAL_H__ + +#include <limits.h> + +#include <direct/list.h> + +#include <fusion/build.h> +#include <fusion/lock.h> + + +#define FUSION_SHM_MAX_POOLS 24 +#define FUSION_SHM_TMPFS_PATH_NAME_LEN 64 + + +typedef struct __shmalloc_heap shmalloc_heap; + + +/* + * Local pool data. + */ +struct __Fusion_FusionSHMPool { + int magic; + + bool attached; /* Indicates usage of this entry in the static pool array. */ + + FusionSHM *shm; /* Back pointer to local SHM data. */ + + FusionSHMPoolShared *shared; /* Pointer to shared pool data. */ + + int pool_id; /* The pool's ID within the world. */ + + int fd; /* File descriptor of shared memory file. */ + char *filename; /* Name of the shared memory file. */ +}; + +/* + * Shared pool data. + */ +struct __Fusion_FusionSHMPoolShared { + int magic; + + bool debug; /* Debug allocations in this pool? */ + + int index; /* Index within the static pool array. */ + bool active; /* Indicates usage of this entry in the static pool array. */ + + FusionSHMShared *shm; /* Back pointer to shared SHM data. */ + + int max_size; /* Maximum possible size of the shared memory. */ + int pool_id; /* The pool's ID within the world. */ + void *addr_base; /* Virtual starting address of shared memory. */ + + FusionSkirmish lock; /* Lock for this pool. */ + + shmalloc_heap *heap; /* The actual heap information ported from libc5. */ + + char *name; /* Name of the pool (allocated in the pool). */ + + DirectLink *allocs; /* Used for debugging. */ +}; + + +/* + * Local SHM data. + */ +struct __Fusion_FusionSHM { + int magic; + + FusionWorld *world; /* Back pointer to local world data. */ + + FusionSHMShared *shared; /* Pointer to shared SHM data. */ + + FusionSHMPool pools[FUSION_SHM_MAX_POOLS]; /* Local data of all pools. */ + + DirectSignalHandler *signal_handler; +}; + +/* + * Shared SHM data. + */ +struct __Fusion_FusionSHMShared { + int magic; + + FusionWorldShared *world; /* Back pointer to shared world data. */ + + FusionSkirmish lock; /* Lock for list of pools. */ + + int num_pools; /* Number of active pools. */ + FusionSHMPoolShared pools[FUSION_SHM_MAX_POOLS]; /* Shared data of all pools. */ + + char tmpfs[FUSION_SHM_TMPFS_PATH_NAME_LEN]; +}; + + + +/* The allocator divides the heap into blocks of fixed size; large + requests receive one or more whole blocks, and small requests + receive a fragment of a block. Fragment sizes are powers of two, + and all fragments of a block are the same size. When all the + fragments in a block have been freed, the block itself is freed. */ +#define INT_BIT (CHAR_BIT * sizeof(int)) +#define BLOCKLOG (INT_BIT > 16 ? 12 : 9) +#define BLOCKSIZE (1 << BLOCKLOG) +#define BLOCKIFY(SIZE) (((SIZE) + BLOCKSIZE - 1) / BLOCKSIZE) +#define BLOCKALIGN(SIZE) (((SIZE) + BLOCKSIZE - 1) & ~(BLOCKSIZE - 1)) + +/* Number of contiguous free blocks allowed to build up at the end of + memory before they will be returned to the system. */ +#define FINAL_FREE_BLOCKS 8 + +/* Address to block number and vice versa. */ +#define BLOCK(A) (((char *) (A) - heap->heapbase) / BLOCKSIZE + 1) +#define ADDRESS(B) ((void *) (((B) - 1) * BLOCKSIZE + heap->heapbase)) + + +/* Data structure giving per-block information. */ +typedef union { + + /* Heap information for a busy block. */ + struct { + + /* Zero for a large block, or positive giving the + logarithm to the base two of the fragment size. */ + int type; + + union { + struct { + size_t nfree; /* Free fragments in a fragmented block. */ + size_t first; /* First free fragment of the block. */ + } frag; + + /* Size (in blocks) of a large cluster. */ + size_t size; + } info; + } busy; + + /* Heap information for a free block + (that may be the first of a free cluster). */ + struct { + size_t size; /* Size (in blocks) of a free cluster. */ + size_t next; /* Index of next free cluster. */ + size_t prev; /* Index of previous free cluster. */ + } free; +} shmalloc_info; + +/* Doubly linked lists of free fragments. */ +struct list { + struct list *next; + struct list *prev; +}; + + +#define SHMEMDESC_FUNC_NAME_LENGTH 48 +#define SHMEMDESC_FILE_NAME_LENGTH 24 + +/* Used for debugging. */ +typedef struct { + DirectLink link; + + const void *mem; + size_t bytes; + char func[SHMEMDESC_FUNC_NAME_LENGTH]; + char file[SHMEMDESC_FILE_NAME_LENGTH]; + unsigned int line; + + FusionID fid; +} SHMemDesc; + + +struct __shmalloc_heap { + int magic; + + /* Pointer to first block of the heap. */ + char *heapbase; + + /* Block information table indexed by block number giving per-block information. */ + shmalloc_info *heapinfo; + + /* Number of info entries. */ + size_t heapsize; + + /* Current search index for the heap table. */ + size_t heapindex; + + /* Limit of valid info table indices. */ + size_t heaplimit; + +#if 1 /* Adapted from Mike */ + /* Count of large blocks allocated for each fragment size. */ + int fragblocks[BLOCKLOG]; +#endif + + /* Free list headers for each fragment size. */ + struct list fraghead[BLOCKLOG]; + + /* Instrumentation. */ + size_t chunks_used; + size_t bytes_used; + size_t chunks_free; + size_t bytes_free; + + /* Total size of heap in bytes. */ + int size; + + /* Back pointer to shared memory pool. */ + FusionSHMPoolShared *pool; +}; + + +void *_fusion_shmalloc (shmalloc_heap *heap, size_t __size); + +void *_fusion_shrealloc (shmalloc_heap *heap, void *__ptr, size_t __size); + +void _fusion_shfree (shmalloc_heap *heap, void *__ptr); + + +DirectResult __shmalloc_init_heap( FusionSHM *shm, + const char *filename, + void *addr_base, + int space, + int *ret_fd, + int *ret_size ); + +DirectResult __shmalloc_join_heap( FusionSHM *shm, + const char *filename, + void *addr_base, + int size, + int *ret_fd ); + +void *__shmalloc_brk ( shmalloc_heap *heap, + int increment ); + + +#endif + |