[cvs] / xvidcore / src / utils / mem_align.c Repository:
ViewVC logotype

Diff of /xvidcore/src/utils/mem_align.c

Parent Directory Parent Directory | Revision Log Revision Log | View Patch Patch

revision 1.2, Wed Mar 20 00:27:57 2002 UTC revision 1.16, Mon Mar 22 22:36:24 2004 UTC
# Line 1  Line 1 
1    /*****************************************************************************
2     *
3     *  XVID MPEG-4 VIDEO CODEC
4     *  - Aligned Memory Allocator -
5     *
6     *  Copyright(C) 2002-2003 Edouard Gomez <ed.gomez@free.fr>
7     *
8     *  This program is free software ; you can redistribute it and/or modify
9     *  it under the terms of the GNU General Public License as published by
10     *  the Free Software Foundation ; either version 2 of the License, or
11     *  (at your option) any later version.
12     *
13     *  This program is distributed in the hope that it will be useful,
14     *  but WITHOUT ANY WARRANTY ; without even the implied warranty of
15     *  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
16     *  GNU General Public License for more details.
17     *
18     *  You should have received a copy of the GNU General Public License
19     *  along with this program ; if not, write to the Free Software
20     *  Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307 USA
21     *
22     * $Id$
23     *
24     ****************************************************************************/
25    
26  #include <stdlib.h>  #include <stdlib.h>
27  #include <stdio.h>  #include <stdio.h>
28  #include "mem_align.h"  #include "mem_align.h"
29    
30  void *xvid_malloc(size_t size, uint8_t alignment)  /*****************************************************************************
31     * xvid_malloc
32     *
33     * This function allocates 'size' bytes (usable by the user) on the heap and
34     * takes care of the requested 'alignment'.
35     * In order to align the allocated memory block, the xvid_malloc allocates
36     * 'size' bytes + 'alignment' bytes. So try to keep alignment very small
37     * when allocating small pieces of memory.
38     *
39     * NB : a block allocated by xvid_malloc _must_ be freed with xvid_free
40     *      (the libc free will return an error)
41     *
42     * Returned value : - NULL on error
43     *                  - Pointer to the allocated aligned block
44     *
45     ****************************************************************************/
46    
47    void *
48    xvid_malloc(size_t size,
49                            uint8_t alignment)
50  {  {
51    uint8_t *mem_ptr;    uint8_t *mem_ptr;
52    
53    if(alignment == 0)          if (!alignment) {
54    {  
55                    /* We have not to satisfy any alignment */
56            if((mem_ptr = (uint8_t *) malloc(size + 1)) != NULL) {            if((mem_ptr = (uint8_t *) malloc(size + 1)) != NULL) {
57                  *mem_ptr = 0;  
58                  return (void *) mem_ptr++;                          /* Store (mem_ptr - "real allocated memory") in *(mem_ptr-1) */
59            }                          *mem_ptr = (uint8_t)1;
60    
61                            /* Return the mem_ptr pointer */
62                            return ((void *)(mem_ptr+1));
63    }    }
64    else          } else {
   {  
65            uint8_t *tmp;            uint8_t *tmp;
66    
67                    /* Allocate the required size memory + alignment so we
68                     * can realign the data if necessary */
69            if((tmp = (uint8_t *) malloc(size + alignment)) != NULL) {            if((tmp = (uint8_t *) malloc(size + alignment)) != NULL) {
70                  mem_ptr = (uint8_t *) (((uint32_t) tmp / alignment) * alignment + alignment);  
71                  *(mem_ptr - 1) = (alignment - 1) - ((uint32_t) tmp % alignment);                          /* Align the tmp pointer */
72                  return (void *) mem_ptr;                          mem_ptr =
73                                    (uint8_t *) ((ptr_t) (tmp + alignment - 1) &
74                                                             (~(ptr_t) (alignment - 1)));
75    
76                            /* Special case where malloc have already satisfied the alignment
77                             * We must add alignment to mem_ptr because we must store
78                             * (mem_ptr - tmp) in *(mem_ptr-1)
79                             * If we do not add alignment to mem_ptr then *(mem_ptr-1) points
80                             * to a forbidden memory space */
81                            if (mem_ptr == tmp)
82                                    mem_ptr += alignment;
83    
84                            /* (mem_ptr - tmp) is stored in *(mem_ptr-1) so we are able to retrieve
85                             * the real malloc block allocated and free it in xvid_free */
86                            *(mem_ptr - 1) = (uint8_t) (mem_ptr - tmp);
87    
88                            /* Return the aligned pointer */
89                            return ((void *)mem_ptr);
90            }            }
91    }    }
92    
93    return NULL;          return(NULL);
94  }  }
95    
96    /*****************************************************************************
97     * xvid_free
98     *
99     * Free a previously 'xvid_malloc' allocated block. Does not free NULL
100     * references.
101     *
102     * Returned value : None.
103     *
104     ****************************************************************************/
105    
106  void xvid_free(void *mem_ptr)  void
107    xvid_free(void *mem_ptr)
108  {  {
   uint8_t *tmp;  
109    
110    tmp = (uint8_t *) mem_ptr - 1;          uint8_t *ptr;
111    mem_ptr  = tmp - *tmp;  
112            if (mem_ptr == NULL)
113                    return;
114    
115            /* Aligned pointer */
116            ptr = mem_ptr;
117    
118            /* *(ptr - 1) holds the offset to the real allocated block
119             * we sub that offset os we free the real pointer */
120            ptr -= *(ptr - 1);
121    
122    free(mem_ptr);          /* Free the memory */
123            free(ptr);
124  }  }

Legend:
Removed from v.1.2  
changed lines
  Added in v.1.16

No admin address has been configured
ViewVC Help
Powered by ViewVC 1.0.4