os/graphics/fbs/fontandbitmapserver/sfbs/HASHMAP.CPP
author sl
Tue, 10 Jun 2014 14:32:02 +0200
changeset 1 260cb5ec6c19
permissions -rw-r--r--
Update contrib.
     1 // HASHMAP.CPP
     2 //
     3 // This file holds the class methods for the CHashMap
     4 // A hash function for hash table lookup.  Assumes input data length is a multiple of 8-bits.
     5 // 
     6 // The original hash function was sourced from http://burtleburtle.net/bob/hash/index.html
     7 // "By Bob Jenkins, 1996.  bob_jenkins@burtleburtle.net.  You may use this code any way you wish, 
     8 // private, educational, or commercial.  It's free."
     9 // portions Copyright (c) 1995 - 2010 Nokia Corporation and/or its subsidiary(-ies).
    10 //
    11 
    12 #include "SERVER.H"
    13 
    14 CHashMap::CHashMap() :
    15 	iTableSize(sizeof(iHashTable)/sizeof(CSharedBitmapObject*)),
    16 	iMask(iTableSize-1)
    17 	{
    18 	}
    19 	
    20 
    21 CHashMap::~CHashMap()
    22 	{
    23 	for (TInt i=0; i<iTableSize; i++)
    24 		{
    25 		__ASSERT_DEBUG(iHashTable[i]==NULL, User::Invariant());
    26 		}
    27 	}
    28 
    29 
    30 /* This function inserts a pointer to the CSharedBitmapObject into the hashmap.
    31 The hashmap does not acquire ownership of the CSharedBitmapObject.
    32 The key used for insertion is a pre-existing member of the CSharedBitmapObject.
    33 The caller must ensure the key does not already exist in the hashmap prior to calling this function.
    34 
    35 @param aBmpObj The CSharedBitmapObject to insert.
    36 @param aHash The hash of the key of the CSharedBitmapObject.  This is provided for performance reasons explained in CFbTop::ShareBitmap.
    37 @internalComponent
    38 */
    39 void CHashMap::Insert(CSharedBitmapObject& aBmpObj, TUint aHash)
    40 	{
    41 	__ASSERT_DEBUG(aHash==Hash(*(aBmpObj.iKey)), User::Invariant());     // Verify the hash value
    42 	__ASSERT_DEBUG(!Lookup(*(aBmpObj.iKey), aHash), User::Invariant());  // Duplicate keys are not allowed
    43 	
    44 	const TUint index = aHash & iMask;
    45 
    46 	// Insert aBmpObj at head of list
    47 	aBmpObj.iNext = iHashTable[index];
    48 	iHashTable[index] = &aBmpObj;
    49 	}
    50 
    51 
    52 /* This function looks up a CSharedBitmapObject in the hashmap using a key.
    53 Lookup is case sensitive.
    54 
    55 @param aKey The key of the CSharedBitmapObject to be found.
    56 @param aHash The hash of the key.  This is provided for performance reasons explained in CFbTop::ShareBitmap.
    57 @return A pointer to the CSharedBitmapObject if the key is found.  NULL otherwise.
    58 @internalComponent
    59 */
    60 CSharedBitmapObject* CHashMap::Lookup(const TDesC& aKey, TUint aHash) const
    61 	{
    62 	const TUint index = aHash & iMask;
    63 
    64 	for (CSharedBitmapObject* n=iHashTable[index]; n!=NULL; n=n->iNext) // n walks the links of the linked list.
    65 		{
    66 		if (n->iKey->Length()==aKey.Length() && !n->iKey->Compare(aKey))
    67 			{
    68 			return n;  // Key found
    69 			}
    70 		}
    71 
    72 	return NULL;   // Key not found
    73 	}
    74 
    75 
    76 /* Removes a specific object from the hashmap.
    77 The object is discovered using its key and address.
    78 This function does not destroy the object.
    79 
    80 @param aBmpObj The specific CSharedBitmapObject to be removed.
    81 @return KErrNone if the object is found and removed.  An standard error otherwise.
    82 @internalComponent
    83 */
    84 TInt CHashMap::Remove(const CSharedBitmapObject& aBmpObj)
    85 	{
    86 	const TUint hash = Hash(*(aBmpObj.iKey));
    87 	const TUint index = hash & iMask;
    88 
    89 	for (CSharedBitmapObject** n=&iHashTable[index]; *n!=NULL; n=&((*n)->iNext))  // *n walks the links of the linked list.
    90 		{
    91 		if (&aBmpObj==*n)
    92 			{
    93 			*n = aBmpObj.iNext;  // Key found.  The link that was pointing to aBmpObj nows points to the successor of aBmpObj.
    94 			return KErrNone;
    95 			}	
    96 		}
    97 
    98 	return KErrNotFound;
    99 	}
   100 
   101 
   102 // Utility macro for the hash function
   103 #define mix(a,b,c) \
   104 { \
   105   a -= b; a -= c; a ^= (c>>13); \
   106   b -= c; b -= a; b ^= (a<<8);  \
   107   c -= a; c -= b; c ^= (b>>13); \
   108   a -= b; a -= c; a ^= (c>>12); \
   109   b -= c; b -= a; b ^= (a<<16); \
   110   c -= a; c -= b; c ^= (b>>5);  \
   111   a -= b; a -= c; a ^= (c>>3);  \
   112   b -= c; b -= a; b ^= (a<<10); \
   113   c -= a; c -= b; c ^= (b>>15); \
   114 }
   115 
   116 /* A hash function for hash table lookup.
   117 Assumes input data length is a multiple of 8-bits.
   118 
   119 The original hash function was sourced from
   120 http://burtleburtle.net/bob/hash/index.html
   121 "By Bob Jenkins, 1996.  bob_jenkins@burtleburtle.net.  You may use this
   122 code any way you wish, private, educational, or commercial.  It's free."
   123 
   124 TUint CHashMap::Hash(const TDesC8& aKey)
   125 	{
   126 	const TUint8* k = aKey.Ptr();
   127 	const TUint length = aKey.Length();
   128 	const TUint initval = 0;
   129 
   130 	TUint len = length;
   131 	TUint a = 0x9e3779b9;
   132 	TUint b = 0x9e3779b9;
   133 	TUint c = initval;
   134 
   135 	while (len >= 12)
   136 		{
   137 		a += (k[0] + ((TUint)k[1]<<8) + ((TUint)k[2] <<16) + ((TUint)k[3] <<24));
   138 		b += (k[4] + ((TUint)k[5]<<8) + ((TUint)k[6] <<16) + ((TUint)k[7] <<24));
   139 		c += (k[8] + ((TUint)k[9]<<8) + ((TUint)k[10]<<16) + ((TUint)k[11]<<24));
   140 		mix(a,b,c);
   141 		k += 12; len -= 12;
   142 		}
   143 
   144 	c += length;
   145 	switch(len)
   146 		{
   147 		case 11: c+=((TUint)k[10]<<24);
   148 		case 10: c+=((TUint)k[9]<<16);
   149 		case 9 : c+=((TUint)k[8]<<8);
   150       // the first byte of c is reserved for the length
   151 		case 8 : b+=((TUint)k[7]<<24);
   152 		case 7 : b+=((TUint)k[6]<<16);
   153 		case 6 : b+=((TUint)k[5]<<8);
   154 		case 5 : b+=k[4];
   155 		case 4 : a+=((TUint)k[3]<<24);
   156 		case 3 : a+=((TUint)k[2]<<16);
   157 		case 2 : a+=((TUint)k[1]<<8);
   158 		case 1 : a+=k[0];
   159      // case 0: nothing left to add
   160 		}
   161 	mix(a,b,c);
   162 
   163 	return c;
   164 	}
   165 	
   166 */
   167 
   168 
   169 /* A hash function for hash table lookup.
   170 Assumes input data length is a multiple of 16-bits.
   171 @param aKey The data to be hashed
   172 @return The hash value
   173 @internalComponent
   174 */
   175 TUint CHashMap::Hash(const TDesC16& aKey)
   176 	{
   177 	const TUint16* k = aKey.Ptr();
   178 	const TUint length = aKey.Length();
   179 	const TUint initval = 0;
   180 
   181 	TUint len = length;
   182 	TUint a = 0x9e3779b9;
   183 	TUint b = 0x9e3779b9;
   184 	TUint c = initval;
   185 
   186 	while (len >= 6)
   187 		{
   188 		a += (k[0] + ((TUint)k[1]<<16));
   189 		b += (k[2] + ((TUint)k[3]<<16));
   190 		c += (k[4] + ((TUint)k[5]<<16));
   191 		mix(a,b,c);
   192 		k += 6; len -= 6;
   193 		}
   194 
   195 	c += length;
   196 	switch(len)
   197 		{
   198 		case 5 : c+=((TUint)k[4]<<16);
   199       // the first byte of c is reserved for the length
   200 		case 4 : b+=((TUint)k[3]<<16);
   201 		case 3 : b+=k[2];
   202 		case 2 : a+=((TUint)k[1]<<16);
   203 		case 1 : a+=k[0];
   204      // case 0: nothing left to add
   205 		}
   206 	mix(a,b,c);
   207 
   208 	return c;
   209 	}