misc/libfreetype/src/cache/ftcmru.h
changeset 9431 0f5961910e27
parent 9357 a501f5ec7b34
parent 9429 7a97a554ac80
child 9433 f0a8ac191839
equal deleted inserted replaced
9357:a501f5ec7b34 9431:0f5961910e27
     1 /***************************************************************************/
       
     2 /*                                                                         */
       
     3 /*  ftcmru.h                                                               */
       
     4 /*                                                                         */
       
     5 /*    Simple MRU list-cache (specification).                               */
       
     6 /*                                                                         */
       
     7 /*  Copyright 2000-2001, 2003, 2004, 2005, 2006, 2010 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 
       
    43 #ifndef __FTCMRU_H__
       
    44 #define __FTCMRU_H__
       
    45 
       
    46 
       
    47 #include <ft2build.h>
       
    48 #include FT_FREETYPE_H
       
    49 
       
    50 #ifdef FREETYPE_H
       
    51 #error "freetype.h of FreeType 1 has been loaded!"
       
    52 #error "Please fix the directory search order for header files"
       
    53 #error "so that freetype.h of FreeType 2 is found first."
       
    54 #endif
       
    55 
       
    56 #define  xxFT_DEBUG_ERROR
       
    57 #define  FTC_INLINE
       
    58 
       
    59 FT_BEGIN_HEADER
       
    60 
       
    61   typedef struct FTC_MruNodeRec_*  FTC_MruNode;
       
    62 
       
    63   typedef struct  FTC_MruNodeRec_
       
    64   {
       
    65     FTC_MruNode  next;
       
    66     FTC_MruNode  prev;
       
    67 
       
    68   } FTC_MruNodeRec;
       
    69 
       
    70 
       
    71   FT_LOCAL( void )
       
    72   FTC_MruNode_Prepend( FTC_MruNode  *plist,
       
    73                        FTC_MruNode   node );
       
    74 
       
    75   FT_LOCAL( void )
       
    76   FTC_MruNode_Up( FTC_MruNode  *plist,
       
    77                   FTC_MruNode   node );
       
    78 
       
    79   FT_LOCAL( void )
       
    80   FTC_MruNode_Remove( FTC_MruNode  *plist,
       
    81                       FTC_MruNode   node );
       
    82 
       
    83 
       
    84   typedef struct FTC_MruListRec_*              FTC_MruList;
       
    85 
       
    86   typedef struct FTC_MruListClassRec_ const *  FTC_MruListClass;
       
    87 
       
    88 
       
    89   typedef FT_Bool
       
    90   (*FTC_MruNode_CompareFunc)( FTC_MruNode  node,
       
    91                               FT_Pointer   key );
       
    92 
       
    93   typedef FT_Error
       
    94   (*FTC_MruNode_InitFunc)( FTC_MruNode  node,
       
    95                            FT_Pointer   key,
       
    96                            FT_Pointer   data );
       
    97 
       
    98   typedef FT_Error
       
    99   (*FTC_MruNode_ResetFunc)( FTC_MruNode  node,
       
   100                             FT_Pointer   key,
       
   101                             FT_Pointer   data );
       
   102 
       
   103   typedef void
       
   104   (*FTC_MruNode_DoneFunc)( FTC_MruNode  node,
       
   105                            FT_Pointer   data );
       
   106 
       
   107 
       
   108   typedef struct  FTC_MruListClassRec_
       
   109   {
       
   110     FT_Offset                node_size;
       
   111     FTC_MruNode_CompareFunc  node_compare;
       
   112     FTC_MruNode_InitFunc     node_init;
       
   113     FTC_MruNode_ResetFunc    node_reset;
       
   114     FTC_MruNode_DoneFunc     node_done;
       
   115 
       
   116   } FTC_MruListClassRec;
       
   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  = FTC_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 
       
   240 FT_END_HEADER
       
   241 
       
   242 
       
   243 #endif /* __FTCMRU_H__ */
       
   244 
       
   245 
       
   246 /* END */