sdk-world v2026.11.05
PS2 SDK - world tier (copyleft-allowed, non-essential packages)
Loading...
Searching...
No Matches
ftcmru.h
Go to the documentation of this file.
1/****************************************************************************
2 *
3 * ftcmru.h
4 *
5 * Simple MRU list-cache (specification).
6 *
7 * Copyright (C) 2000-2025 by
8 * David Turner, Robert Wilhelm, and Werner Lemberg.
9 *
10 * This file is part of the FreeType project, and may only be used,
11 * modified, and distributed under the terms of the FreeType project
12 * license, LICENSE.TXT. By continuing to use, modify, or distribute
13 * this file you indicate that you have read the license and
14 * understand and accept it fully.
15 *
16 */
17
18
19 /**************************************************************************
20 *
21 * An MRU is a list that cannot hold more than a certain number of
22 * elements (`max_elements'). All elements in the list are sorted in
23 * least-recently-used order, i.e., the `oldest' element is at the tail
24 * of the list.
25 *
26 * When doing a lookup (either through `Lookup()' or `Lookup_Node()'),
27 * the list is searched for an element with the corresponding key. If
28 * it is found, the element is moved to the head of the list and is
29 * returned.
30 *
31 * If no corresponding element is found, the lookup routine will try to
32 * obtain a new element with the relevant key. If the list is already
33 * full, the oldest element from the list is discarded and replaced by a
34 * new one; a new element is added to the list otherwise.
35 *
36 * Note that it is possible to pre-allocate the element list nodes.
37 * This is handy if `max_elements' is sufficiently small, as it saves
38 * allocations/releases during the lookup process.
39 *
40 */
41
42
47#ifndef FTCMRU_H_
48#define FTCMRU_H_
49
50
51#include <freetype/freetype.h>
53
54#ifdef FREETYPE_H
55#error "freetype.h of FreeType 1 has been loaded!"
56#error "Please fix the directory search order for header files"
57#error "so that freetype.h of FreeType 2 is found first."
58#endif
59
60#define xxFT_DEBUG_ERROR
61#define FTC_INLINE
62
63FT_BEGIN_HEADER
64
65 typedef struct FTC_MruNodeRec_* FTC_MruNode;
66
67 typedef struct FTC_MruNodeRec_
68 {
69 FTC_MruNode next;
70 FTC_MruNode prev;
71
72 } FTC_MruNodeRec;
73
74
75 FT_LOCAL( void )
76 FTC_MruNode_Prepend( FTC_MruNode *plist,
77 FTC_MruNode node );
78
79 FT_LOCAL( void )
80 FTC_MruNode_Up( FTC_MruNode *plist,
81 FTC_MruNode node );
82
83 FT_LOCAL( void )
84 FTC_MruNode_Remove( FTC_MruNode *plist,
85 FTC_MruNode node );
86
87
88 typedef struct FTC_MruListRec_* FTC_MruList;
89
90 typedef struct FTC_MruListClassRec_ const * FTC_MruListClass;
91
92
93 typedef FT_Bool
94 (*FTC_MruNode_CompareFunc)( FTC_MruNode node,
95 FT_Pointer key );
96
97 typedef FT_Error
98 (*FTC_MruNode_InitFunc)( FTC_MruNode node,
99 FT_Pointer key,
100 FT_Pointer data );
101
102 typedef void
103 (*FTC_MruNode_DoneFunc)( FTC_MruNode node,
104 FT_Pointer data );
105
106
107 typedef struct FTC_MruListClassRec_
108 {
109 FT_Offset node_size;
110
111 FTC_MruNode_CompareFunc node_compare;
112 FTC_MruNode_InitFunc node_init;
113 FTC_MruNode_DoneFunc node_done;
114
115 } FTC_MruListClassRec;
116
117
118 typedef struct FTC_MruListRec_
119 {
120 FT_UInt num_nodes;
121 FT_UInt max_nodes;
122 FTC_MruNode nodes;
123 FT_Pointer data;
124 FTC_MruListClassRec clazz;
125 FT_Memory memory;
126
127 } FTC_MruListRec;
128
129
130 FT_LOCAL( void )
131 FTC_MruList_Init( FTC_MruList list,
132 FTC_MruListClass clazz,
133 FT_UInt max_nodes,
134 FT_Pointer data,
135 FT_Memory memory );
136
137 FT_LOCAL( void )
138 FTC_MruList_Reset( FTC_MruList list );
139
140
141 FT_LOCAL( void )
142 FTC_MruList_Done( FTC_MruList list );
143
144
145 FT_LOCAL( FT_Error )
146 FTC_MruList_New( FTC_MruList list,
147 FT_Pointer key,
148 FTC_MruNode *anode );
149
150 FT_LOCAL( void )
151 FTC_MruList_Remove( FTC_MruList list,
152 FTC_MruNode node );
153
154 FT_LOCAL( void )
155 FTC_MruList_RemoveSelection( FTC_MruList list,
156 FTC_MruNode_CompareFunc selection,
157 FT_Pointer key );
158
159
160#ifdef FTC_INLINE
161
162#define FTC_MRULIST_LOOKUP_CMP( list, key, compare, node, error ) \
163 FT_BEGIN_STMNT \
164 FTC_MruNode* _pfirst = &(list)->nodes; \
165 FTC_MruNode_CompareFunc _compare = (FTC_MruNode_CompareFunc)(compare); \
166 FTC_MruNode _first, _node; \
167 \
168 \
169 error = FT_Err_Ok; \
170 _first = *(_pfirst); \
171 _node = NULL; \
172 \
173 if ( _first ) \
174 { \
175 _node = _first; \
176 do \
177 { \
178 if ( _compare( _node, (key) ) ) \
179 { \
180 if ( _node != _first ) \
181 FTC_MruNode_Up( _pfirst, _node ); \
182 \
183 node = _node; \
184 goto MruOk_; \
185 } \
186 _node = _node->next; \
187 \
188 } while ( _node != _first); \
189 } \
190 \
191 error = FTC_MruList_New( (list), (key), (FTC_MruNode*)(void*)&(node) ); \
192 MruOk_: \
193 ; \
194 FT_END_STMNT
195
196#define FTC_MRULIST_LOOKUP( list, key, node, error ) \
197 FTC_MRULIST_LOOKUP_CMP( list, key, (list)->clazz.node_compare, node, error )
198
199#else /* !FTC_INLINE */
200
201 FT_LOCAL( FTC_MruNode )
202 FTC_MruList_Find( FTC_MruList list,
203 FT_Pointer key );
204
205 FT_LOCAL( FT_Error )
206 FTC_MruList_Lookup( FTC_MruList list,
207 FT_Pointer key,
208 FTC_MruNode *pnode );
209
210#define FTC_MRULIST_LOOKUP( list, key, node, error ) \
211 error = FTC_MruList_Lookup( (list), (key), (FTC_MruNode*)&(node) )
212
213#endif /* !FTC_INLINE */
214
215
216#define FTC_MRULIST_LOOP( list, node ) \
217 FT_BEGIN_STMNT \
218 FTC_MruNode _first = (list)->nodes; \
219 \
220 \
221 if ( _first ) \
222 { \
223 FTC_MruNode _node = _first; \
224 \
225 \
226 do \
227 { \
228 *(FTC_MruNode*)&(node) = _node;
229
230
231#define FTC_MRULIST_LOOP_END() \
232 _node = _node->next; \
233 \
234 } while ( _node != _first ); \
235 } \
236 FT_END_STMNT
237
238 /* */
239
240FT_END_HEADER
241
242
243#endif /* FTCMRU_H_ */
244
245
246/* END */