xref: /inferno-os/libfreetype/ftutil.c (revision 37da2899f40661e3e9631e497da8dc59b971cbd0)
1*37da2899SCharles.Forsyth /***************************************************************************/
2*37da2899SCharles.Forsyth /*                                                                         */
3*37da2899SCharles.Forsyth /*  ftutil.c                                                               */
4*37da2899SCharles.Forsyth /*                                                                         */
5*37da2899SCharles.Forsyth /*    FreeType utility file for memory and list management (body).         */
6*37da2899SCharles.Forsyth /*                                                                         */
7*37da2899SCharles.Forsyth /*  Copyright 2002 by                                                      */
8*37da2899SCharles.Forsyth /*  David Turner, Robert Wilhelm, and Werner Lemberg.                      */
9*37da2899SCharles.Forsyth /*                                                                         */
10*37da2899SCharles.Forsyth /*  This file is part of the FreeType project, and may only be used,       */
11*37da2899SCharles.Forsyth /*  modified, and distributed under the terms of the FreeType project      */
12*37da2899SCharles.Forsyth /*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     */
13*37da2899SCharles.Forsyth /*  this file you indicate that you have read the license and              */
14*37da2899SCharles.Forsyth /*  understand and accept it fully.                                        */
15*37da2899SCharles.Forsyth /*                                                                         */
16*37da2899SCharles.Forsyth /***************************************************************************/
17*37da2899SCharles.Forsyth 
18*37da2899SCharles.Forsyth 
19*37da2899SCharles.Forsyth #include <ft2build.h>
20*37da2899SCharles.Forsyth #include FT_INTERNAL_DEBUG_H
21*37da2899SCharles.Forsyth #include FT_INTERNAL_MEMORY_H
22*37da2899SCharles.Forsyth #include FT_LIST_H
23*37da2899SCharles.Forsyth 
24*37da2899SCharles.Forsyth 
25*37da2899SCharles.Forsyth   /*************************************************************************/
26*37da2899SCharles.Forsyth   /*                                                                       */
27*37da2899SCharles.Forsyth   /* The macro FT_COMPONENT is used in trace mode.  It is an implicit      */
28*37da2899SCharles.Forsyth   /* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log  */
29*37da2899SCharles.Forsyth   /* messages during execution.                                            */
30*37da2899SCharles.Forsyth   /*                                                                       */
31*37da2899SCharles.Forsyth #undef  FT_COMPONENT
32*37da2899SCharles.Forsyth #define FT_COMPONENT  trace_memory
33*37da2899SCharles.Forsyth 
34*37da2899SCharles.Forsyth 
35*37da2899SCharles.Forsyth   /*************************************************************************/
36*37da2899SCharles.Forsyth   /*************************************************************************/
37*37da2899SCharles.Forsyth   /*************************************************************************/
38*37da2899SCharles.Forsyth   /*****                                                               *****/
39*37da2899SCharles.Forsyth   /*****                                                               *****/
40*37da2899SCharles.Forsyth   /*****               M E M O R Y   M A N A G E M E N T               *****/
41*37da2899SCharles.Forsyth   /*****                                                               *****/
42*37da2899SCharles.Forsyth   /*****                                                               *****/
43*37da2899SCharles.Forsyth   /*************************************************************************/
44*37da2899SCharles.Forsyth   /*************************************************************************/
45*37da2899SCharles.Forsyth   /*************************************************************************/
46*37da2899SCharles.Forsyth 
47*37da2899SCharles.Forsyth   /* documentation is in ftmemory.h */
48*37da2899SCharles.Forsyth 
49*37da2899SCharles.Forsyth   FT_BASE_DEF( FT_Error )
FT_Alloc(FT_Memory memory,FT_Long size,void ** P)50*37da2899SCharles.Forsyth   FT_Alloc( FT_Memory  memory,
51*37da2899SCharles.Forsyth             FT_Long    size,
52*37da2899SCharles.Forsyth             void*     *P )
53*37da2899SCharles.Forsyth   {
54*37da2899SCharles.Forsyth     FT_ASSERT( P != 0 );
55*37da2899SCharles.Forsyth 
56*37da2899SCharles.Forsyth     if ( size > 0 )
57*37da2899SCharles.Forsyth     {
58*37da2899SCharles.Forsyth       *P = memory->alloc( memory, size );
59*37da2899SCharles.Forsyth       if ( !*P )
60*37da2899SCharles.Forsyth       {
61*37da2899SCharles.Forsyth         FT_ERROR(( "FT_Alloc:" ));
62*37da2899SCharles.Forsyth         FT_ERROR(( " Out of memory? (%ld requested)\n",
63*37da2899SCharles.Forsyth                    size ));
64*37da2899SCharles.Forsyth 
65*37da2899SCharles.Forsyth         return FT_Err_Out_Of_Memory;
66*37da2899SCharles.Forsyth       }
67*37da2899SCharles.Forsyth       FT_MEM_ZERO( *P, size );
68*37da2899SCharles.Forsyth     }
69*37da2899SCharles.Forsyth     else
70*37da2899SCharles.Forsyth       *P = NULL;
71*37da2899SCharles.Forsyth 
72*37da2899SCharles.Forsyth     FT_TRACE7(( "FT_Alloc:" ));
73*37da2899SCharles.Forsyth     FT_TRACE7(( " size = %ld, block = 0x%08p, ref = 0x%08p\n",
74*37da2899SCharles.Forsyth                 size, *P, P ));
75*37da2899SCharles.Forsyth 
76*37da2899SCharles.Forsyth     return FT_Err_Ok;
77*37da2899SCharles.Forsyth   }
78*37da2899SCharles.Forsyth 
79*37da2899SCharles.Forsyth 
80*37da2899SCharles.Forsyth   /* documentation is in ftmemory.h */
81*37da2899SCharles.Forsyth 
82*37da2899SCharles.Forsyth   FT_BASE_DEF( FT_Error )
FT_Realloc(FT_Memory memory,FT_Long current,FT_Long size,void ** P)83*37da2899SCharles.Forsyth   FT_Realloc( FT_Memory  memory,
84*37da2899SCharles.Forsyth               FT_Long    current,
85*37da2899SCharles.Forsyth               FT_Long    size,
86*37da2899SCharles.Forsyth               void**     P )
87*37da2899SCharles.Forsyth   {
88*37da2899SCharles.Forsyth     void*  Q;
89*37da2899SCharles.Forsyth 
90*37da2899SCharles.Forsyth 
91*37da2899SCharles.Forsyth     FT_ASSERT( P != 0 );
92*37da2899SCharles.Forsyth 
93*37da2899SCharles.Forsyth     /* if the original pointer is NULL, call FT_Alloc() */
94*37da2899SCharles.Forsyth     if ( !*P )
95*37da2899SCharles.Forsyth       return FT_Alloc( memory, size, P );
96*37da2899SCharles.Forsyth 
97*37da2899SCharles.Forsyth     /* if the new block if zero-sized, clear the current one */
98*37da2899SCharles.Forsyth     if ( size <= 0 )
99*37da2899SCharles.Forsyth     {
100*37da2899SCharles.Forsyth       FT_Free( memory, P );
101*37da2899SCharles.Forsyth       return FT_Err_Ok;
102*37da2899SCharles.Forsyth     }
103*37da2899SCharles.Forsyth 
104*37da2899SCharles.Forsyth     Q = memory->realloc( memory, current, size, *P );
105*37da2899SCharles.Forsyth     if ( !Q )
106*37da2899SCharles.Forsyth       goto Fail;
107*37da2899SCharles.Forsyth 
108*37da2899SCharles.Forsyth     if ( size > current )
109*37da2899SCharles.Forsyth       FT_MEM_ZERO( (char*)Q + current, size - current );
110*37da2899SCharles.Forsyth 
111*37da2899SCharles.Forsyth     *P = Q;
112*37da2899SCharles.Forsyth     return FT_Err_Ok;
113*37da2899SCharles.Forsyth 
114*37da2899SCharles.Forsyth   Fail:
115*37da2899SCharles.Forsyth     FT_ERROR(( "FT_Realloc:" ));
116*37da2899SCharles.Forsyth     FT_ERROR(( " Failed (current %ld, requested %ld)\n",
117*37da2899SCharles.Forsyth                current, size ));
118*37da2899SCharles.Forsyth     return FT_Err_Out_Of_Memory;
119*37da2899SCharles.Forsyth   }
120*37da2899SCharles.Forsyth 
121*37da2899SCharles.Forsyth 
122*37da2899SCharles.Forsyth   /* documentation is in ftmemory.h */
123*37da2899SCharles.Forsyth 
124*37da2899SCharles.Forsyth   FT_BASE_DEF( void )
FT_Free(FT_Memory memory,void ** P)125*37da2899SCharles.Forsyth   FT_Free( FT_Memory  memory,
126*37da2899SCharles.Forsyth            void**     P )
127*37da2899SCharles.Forsyth   {
128*37da2899SCharles.Forsyth     FT_TRACE7(( "FT_Free:" ));
129*37da2899SCharles.Forsyth     FT_TRACE7(( " Freeing block 0x%08p, ref 0x%08p\n",
130*37da2899SCharles.Forsyth                 P, P ? *P : (void*)0 ));
131*37da2899SCharles.Forsyth 
132*37da2899SCharles.Forsyth     if ( P && *P )
133*37da2899SCharles.Forsyth     {
134*37da2899SCharles.Forsyth       memory->free( memory, *P );
135*37da2899SCharles.Forsyth       *P = 0;
136*37da2899SCharles.Forsyth     }
137*37da2899SCharles.Forsyth   }
138*37da2899SCharles.Forsyth 
139*37da2899SCharles.Forsyth 
140*37da2899SCharles.Forsyth   /*************************************************************************/
141*37da2899SCharles.Forsyth   /*************************************************************************/
142*37da2899SCharles.Forsyth   /*************************************************************************/
143*37da2899SCharles.Forsyth   /*****                                                               *****/
144*37da2899SCharles.Forsyth   /*****                                                               *****/
145*37da2899SCharles.Forsyth   /*****            D O U B L Y   L I N K E D   L I S T S              *****/
146*37da2899SCharles.Forsyth   /*****                                                               *****/
147*37da2899SCharles.Forsyth   /*****                                                               *****/
148*37da2899SCharles.Forsyth   /*************************************************************************/
149*37da2899SCharles.Forsyth   /*************************************************************************/
150*37da2899SCharles.Forsyth   /*************************************************************************/
151*37da2899SCharles.Forsyth 
152*37da2899SCharles.Forsyth #undef  FT_COMPONENT
153*37da2899SCharles.Forsyth #define FT_COMPONENT  trace_list
154*37da2899SCharles.Forsyth 
155*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
156*37da2899SCharles.Forsyth 
157*37da2899SCharles.Forsyth   FT_EXPORT_DEF( FT_ListNode )
FT_List_Find(FT_List list,void * data)158*37da2899SCharles.Forsyth   FT_List_Find( FT_List  list,
159*37da2899SCharles.Forsyth                 void*    data )
160*37da2899SCharles.Forsyth   {
161*37da2899SCharles.Forsyth     FT_ListNode  cur;
162*37da2899SCharles.Forsyth 
163*37da2899SCharles.Forsyth 
164*37da2899SCharles.Forsyth     cur = list->head;
165*37da2899SCharles.Forsyth     while ( cur )
166*37da2899SCharles.Forsyth     {
167*37da2899SCharles.Forsyth       if ( cur->data == data )
168*37da2899SCharles.Forsyth         return cur;
169*37da2899SCharles.Forsyth 
170*37da2899SCharles.Forsyth       cur = cur->next;
171*37da2899SCharles.Forsyth     }
172*37da2899SCharles.Forsyth 
173*37da2899SCharles.Forsyth     return (FT_ListNode)0;
174*37da2899SCharles.Forsyth   }
175*37da2899SCharles.Forsyth 
176*37da2899SCharles.Forsyth 
177*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
178*37da2899SCharles.Forsyth 
179*37da2899SCharles.Forsyth   FT_EXPORT_DEF( void )
FT_List_Add(FT_List list,FT_ListNode node)180*37da2899SCharles.Forsyth   FT_List_Add( FT_List      list,
181*37da2899SCharles.Forsyth                FT_ListNode  node )
182*37da2899SCharles.Forsyth   {
183*37da2899SCharles.Forsyth     FT_ListNode  before = list->tail;
184*37da2899SCharles.Forsyth 
185*37da2899SCharles.Forsyth 
186*37da2899SCharles.Forsyth     node->next = 0;
187*37da2899SCharles.Forsyth     node->prev = before;
188*37da2899SCharles.Forsyth 
189*37da2899SCharles.Forsyth     if ( before )
190*37da2899SCharles.Forsyth       before->next = node;
191*37da2899SCharles.Forsyth     else
192*37da2899SCharles.Forsyth       list->head = node;
193*37da2899SCharles.Forsyth 
194*37da2899SCharles.Forsyth     list->tail = node;
195*37da2899SCharles.Forsyth   }
196*37da2899SCharles.Forsyth 
197*37da2899SCharles.Forsyth 
198*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
199*37da2899SCharles.Forsyth 
200*37da2899SCharles.Forsyth   FT_EXPORT_DEF( void )
FT_List_Insert(FT_List list,FT_ListNode node)201*37da2899SCharles.Forsyth   FT_List_Insert( FT_List      list,
202*37da2899SCharles.Forsyth                   FT_ListNode  node )
203*37da2899SCharles.Forsyth   {
204*37da2899SCharles.Forsyth     FT_ListNode  after = list->head;
205*37da2899SCharles.Forsyth 
206*37da2899SCharles.Forsyth 
207*37da2899SCharles.Forsyth     node->next = after;
208*37da2899SCharles.Forsyth     node->prev = 0;
209*37da2899SCharles.Forsyth 
210*37da2899SCharles.Forsyth     if ( !after )
211*37da2899SCharles.Forsyth       list->tail = node;
212*37da2899SCharles.Forsyth     else
213*37da2899SCharles.Forsyth       after->prev = node;
214*37da2899SCharles.Forsyth 
215*37da2899SCharles.Forsyth     list->head = node;
216*37da2899SCharles.Forsyth   }
217*37da2899SCharles.Forsyth 
218*37da2899SCharles.Forsyth 
219*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
220*37da2899SCharles.Forsyth 
221*37da2899SCharles.Forsyth   FT_EXPORT_DEF( void )
FT_List_Remove(FT_List list,FT_ListNode node)222*37da2899SCharles.Forsyth   FT_List_Remove( FT_List      list,
223*37da2899SCharles.Forsyth                   FT_ListNode  node )
224*37da2899SCharles.Forsyth   {
225*37da2899SCharles.Forsyth     FT_ListNode  before, after;
226*37da2899SCharles.Forsyth 
227*37da2899SCharles.Forsyth 
228*37da2899SCharles.Forsyth     before = node->prev;
229*37da2899SCharles.Forsyth     after  = node->next;
230*37da2899SCharles.Forsyth 
231*37da2899SCharles.Forsyth     if ( before )
232*37da2899SCharles.Forsyth       before->next = after;
233*37da2899SCharles.Forsyth     else
234*37da2899SCharles.Forsyth       list->head = after;
235*37da2899SCharles.Forsyth 
236*37da2899SCharles.Forsyth     if ( after )
237*37da2899SCharles.Forsyth       after->prev = before;
238*37da2899SCharles.Forsyth     else
239*37da2899SCharles.Forsyth       list->tail = before;
240*37da2899SCharles.Forsyth   }
241*37da2899SCharles.Forsyth 
242*37da2899SCharles.Forsyth 
243*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
244*37da2899SCharles.Forsyth 
245*37da2899SCharles.Forsyth   FT_EXPORT_DEF( void )
FT_List_Up(FT_List list,FT_ListNode node)246*37da2899SCharles.Forsyth   FT_List_Up( FT_List      list,
247*37da2899SCharles.Forsyth               FT_ListNode  node )
248*37da2899SCharles.Forsyth   {
249*37da2899SCharles.Forsyth     FT_ListNode  before, after;
250*37da2899SCharles.Forsyth 
251*37da2899SCharles.Forsyth 
252*37da2899SCharles.Forsyth     before = node->prev;
253*37da2899SCharles.Forsyth     after  = node->next;
254*37da2899SCharles.Forsyth 
255*37da2899SCharles.Forsyth     /* check whether we are already on top of the list */
256*37da2899SCharles.Forsyth     if ( !before )
257*37da2899SCharles.Forsyth       return;
258*37da2899SCharles.Forsyth 
259*37da2899SCharles.Forsyth     before->next = after;
260*37da2899SCharles.Forsyth 
261*37da2899SCharles.Forsyth     if ( after )
262*37da2899SCharles.Forsyth       after->prev = before;
263*37da2899SCharles.Forsyth     else
264*37da2899SCharles.Forsyth       list->tail = before;
265*37da2899SCharles.Forsyth 
266*37da2899SCharles.Forsyth     node->prev       = 0;
267*37da2899SCharles.Forsyth     node->next       = list->head;
268*37da2899SCharles.Forsyth     list->head->prev = node;
269*37da2899SCharles.Forsyth     list->head       = node;
270*37da2899SCharles.Forsyth   }
271*37da2899SCharles.Forsyth 
272*37da2899SCharles.Forsyth 
273*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
274*37da2899SCharles.Forsyth 
275*37da2899SCharles.Forsyth   FT_EXPORT_DEF( FT_Error )
FT_List_Iterate(FT_List list,FT_List_Iterator iterator,void * user)276*37da2899SCharles.Forsyth   FT_List_Iterate( FT_List            list,
277*37da2899SCharles.Forsyth                    FT_List_Iterator   iterator,
278*37da2899SCharles.Forsyth                    void*              user )
279*37da2899SCharles.Forsyth   {
280*37da2899SCharles.Forsyth     FT_ListNode  cur   = list->head;
281*37da2899SCharles.Forsyth     FT_Error     error = FT_Err_Ok;
282*37da2899SCharles.Forsyth 
283*37da2899SCharles.Forsyth 
284*37da2899SCharles.Forsyth     while ( cur )
285*37da2899SCharles.Forsyth     {
286*37da2899SCharles.Forsyth       FT_ListNode  next = cur->next;
287*37da2899SCharles.Forsyth 
288*37da2899SCharles.Forsyth 
289*37da2899SCharles.Forsyth       error = iterator( cur, user );
290*37da2899SCharles.Forsyth       if ( error )
291*37da2899SCharles.Forsyth         break;
292*37da2899SCharles.Forsyth 
293*37da2899SCharles.Forsyth       cur = next;
294*37da2899SCharles.Forsyth     }
295*37da2899SCharles.Forsyth 
296*37da2899SCharles.Forsyth     return error;
297*37da2899SCharles.Forsyth   }
298*37da2899SCharles.Forsyth 
299*37da2899SCharles.Forsyth 
300*37da2899SCharles.Forsyth   /* documentation is in ftlist.h */
301*37da2899SCharles.Forsyth 
302*37da2899SCharles.Forsyth   FT_EXPORT_DEF( void )
FT_List_Finalize(FT_List list,FT_List_Destructor destroy,FT_Memory memory,void * user)303*37da2899SCharles.Forsyth   FT_List_Finalize( FT_List             list,
304*37da2899SCharles.Forsyth                     FT_List_Destructor  destroy,
305*37da2899SCharles.Forsyth                     FT_Memory           memory,
306*37da2899SCharles.Forsyth                     void*               user )
307*37da2899SCharles.Forsyth   {
308*37da2899SCharles.Forsyth     FT_ListNode  cur;
309*37da2899SCharles.Forsyth 
310*37da2899SCharles.Forsyth 
311*37da2899SCharles.Forsyth     cur = list->head;
312*37da2899SCharles.Forsyth     while ( cur )
313*37da2899SCharles.Forsyth     {
314*37da2899SCharles.Forsyth       FT_ListNode  next = cur->next;
315*37da2899SCharles.Forsyth       void*        data = cur->data;
316*37da2899SCharles.Forsyth 
317*37da2899SCharles.Forsyth 
318*37da2899SCharles.Forsyth       if ( destroy )
319*37da2899SCharles.Forsyth         destroy( memory, data, user );
320*37da2899SCharles.Forsyth 
321*37da2899SCharles.Forsyth       FT_FREE( cur );
322*37da2899SCharles.Forsyth       cur = next;
323*37da2899SCharles.Forsyth     }
324*37da2899SCharles.Forsyth 
325*37da2899SCharles.Forsyth     list->head = 0;
326*37da2899SCharles.Forsyth     list->tail = 0;
327*37da2899SCharles.Forsyth   }
328*37da2899SCharles.Forsyth 
329*37da2899SCharles.Forsyth 
330*37da2899SCharles.Forsyth /* END */
331