LCOV - app.info - js/xpconnect/src/XPCMaps.cpp

LCOV - code coverage report
| Current view: | directory - js/xpconnect/src - XPCMaps.cpp (source / functions) |  | Found | Hit | Coverage |
| Test: | app.info | Lines: | 353 | 245 | 69.4 %
| Date: | 2012-07-07 | Functions: | 60 | 53 | 88.3 %

           1                 : /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*-
           2                 :  *
           3                 :  * ***** BEGIN LICENSE BLOCK *****
           4                 :  * Version: MPL 1.1/GPL 2.0/LGPL 2.1
           5                 :  *
           6                 :  * The contents of this file are subject to the Mozilla Public License Version
           7                 :  * 1.1 (the "License"); you may not use this file except in compliance with
           8                 :  * the License. You may obtain a copy of the License at
           9                 :  * http://www.mozilla.org/MPL/
          10                 :  *
          11                 :  * Software distributed under the License is distributed on an "AS IS" basis,
          12                 :  * WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
          13                 :  * for the specific language governing rights and limitations under the
          14                 :  * License.
          15                 :  *
          16                 :  * The Original Code is Mozilla Communicator client code, released
          17                 :  * March 31, 1998.
          18                 :  *
          19                 :  * The Initial Developer of the Original Code is
          20                 :  * Netscape Communications Corporation.
          21                 :  * Portions created by the Initial Developer are Copyright (C) 1998
          22                 :  * the Initial Developer. All Rights Reserved.
          23                 :  *
          24                 :  * Contributor(s):
          25                 :  *   John Bandhauer <jband@netscape.com> (original author)
          26                 :  *
          27                 :  * Alternatively, the contents of this file may be used under the terms of
          28                 :  * either of the GNU General Public License Version 2 or later (the "GPL"),
          29                 :  * or the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
          30                 :  * in which case the provisions of the GPL or the LGPL are applicable instead
          31                 :  * of those above. If you wish to allow use of your version of this file only
          32                 :  * under the terms of either the GPL or the LGPL, and not to allow others to
          33                 :  * use your version of this file under the terms of the MPL, indicate your
          34                 :  * decision by deleting the provisions above and replace them with the notice
          35                 :  * and other provisions required by the GPL or the LGPL. If you do not delete
          36                 :  * the provisions above, a recipient may use your version of this file under
          37                 :  * the terms of any one of the MPL, the GPL or the LGPL.
          38                 :  *
          39                 :  * ***** END LICENSE BLOCK ***** */
          40                 :
          41                 : /* Private maps (hashtables). */
          42                 :
          43                 : #include "xpcprivate.h"
          44                 :
          45                 : #include "jshash.h"
          46                 :
          47                 : /***************************************************************************/
          48                 : // static shared...
          49                 :
          50                 : // Note this is returning the bit pattern of the first part of the nsID, not
          51                 : // the pointer to the nsID.
          52                 :
          53                 : static JSDHashNumber
          54         2918064 : HashIIDPtrKey(JSDHashTable *table, const void *key)
          55                 : {
          56         2918064 :     return *((JSHashNumber*)key);
          57                 : }
          58                 :
          59                 : static JSBool
          60         2523931 : MatchIIDPtrKey(JSDHashTable *table,
          61                 :                const JSDHashEntryHdr *entry,
          62                 :                const void *key)
          63                 : {
          64                 :     return ((const nsID*)key)->
          65         2523931 :                 Equals(*((const nsID*)((JSDHashEntryStub*)entry)->key));
          66                 : }
          67                 :
          68                 : static JSDHashNumber
          69         1281073 : HashNativeKey(JSDHashTable *table, const void *key)
          70                 : {
          71         1281073 :     XPCNativeSetKey* Key = (XPCNativeSetKey*) key;
          72                 :
          73         1281073 :     JSDHashNumber h = 0;
          74                 :
          75                 :     XPCNativeSet*       Set;
          76                 :     XPCNativeInterface* Addition;
          77                 :     PRUint16            Position;
          78                 :
          79         1281073 :     if (Key->IsAKey()) {
          80         1281073 :         Set      = Key->GetBaseSet();
          81         1281073 :         Addition = Key->GetAddition();
          82         1281073 :         Position = Key->GetPosition();
          83                 :     } else {
          84               0 :         Set      = (XPCNativeSet*) Key;
          85               0 :         Addition = nsnull;
          86               0 :         Position = 0;
          87                 :     }
          88                 :
          89         1281073 :     if (!Set) {
          90          988881 :         NS_ASSERTION(Addition, "bad key");
          91                 :         // This would be an XOR like below.
          92                 :         // But "0 ^ x == x". So it does not matter.
          93          988881 :         h = (JSHashNumber) NS_PTR_TO_INT32(Addition) >> 2;
          94                 :     } else {
          95          292192 :         XPCNativeInterface** Current = Set->GetInterfaceArray();
          96          292192 :         PRUint16 count = Set->GetInterfaceCount();
          97          292192 :         if (Addition) {
          98          188048 :             count++;
          99          697757 :             for (PRUint16 i = 0; i < count; i++) {
         100          509709 :                 if (i == Position)
         101          188048 :                     h ^= (JSHashNumber) NS_PTR_TO_INT32(Addition) >> 2;
         102                 :                 else
         103          321661 :                     h ^= (JSHashNumber) NS_PTR_TO_INT32(*(Current++)) >> 2;
         104                 :             }
         105                 :         } else {
         106          420623 :             for (PRUint16 i = 0; i < count; i++)
         107          316479 :                 h ^= (JSHashNumber) NS_PTR_TO_INT32(*(Current++)) >> 2;
         108                 :         }
         109                 :     }
         110                 :
         111         1281073 :     return h;
         112                 : }
         113                 :
         114                 : /***************************************************************************/
         115                 : // implement JSObject2WrappedJSMap...
         116                 :
         117                 : // static
         118                 : JSObject2WrappedJSMap*
         119            1404 : JSObject2WrappedJSMap::newMap(int size)
         120                 : {
         121            1404 :     JSObject2WrappedJSMap* map = new JSObject2WrappedJSMap(size);
         122            1404 :     if (map && map->mTable)
         123            1404 :         return map;
         124               0 :     delete map;
         125               0 :     return nsnull;
         126                 : }
         127                 :
         128            1404 : JSObject2WrappedJSMap::JSObject2WrappedJSMap(int size)
         129                 : {
         130                 :     mTable = JS_NewDHashTable(JS_DHashGetStubOps(), nsnull,
         131            1404 :                               sizeof(Entry), size);
         132            1404 : }
         133                 :
         134            1403 : JSObject2WrappedJSMap::~JSObject2WrappedJSMap()
         135                 : {
         136            1403 :     if (mTable)
         137            1403 :         JS_DHashTableDestroy(mTable);
         138            1403 : }
         139                 :
         140                 : size_t
         141               3 : JSObject2WrappedJSMap::SizeOfIncludingThis(nsMallocSizeOfFun mallocSizeOf)
         142                 : {
         143               3 :     size_t n = 0;
         144               3 :     n += mallocSizeOf(this);
         145               3 :     n += mTable ? JS_DHashTableSizeOfIncludingThis(mTable, SizeOfEntryExcludingThis, mallocSizeOf) : 0;
         146               3 :     return n;
         147                 : }
         148                 :
         149                 : /* static */ size_t
         150              81 : JSObject2WrappedJSMap::SizeOfEntryExcludingThis(JSDHashEntryHdr *hdr,
         151                 :                                                 JSMallocSizeOfFun mallocSizeOf, void *)
         152                 : {
         153              81 :     return mallocSizeOf(((JSObject2WrappedJSMap::Entry*)hdr)->value);
         154                 : }
         155                 :
         156                 : /***************************************************************************/
         157                 : // implement Native2WrappedNativeMap...
         158                 :
         159                 : // static
         160                 : Native2WrappedNativeMap*
         161           15475 : Native2WrappedNativeMap::newMap(int size)
         162                 : {
         163           15475 :     Native2WrappedNativeMap* map = new Native2WrappedNativeMap(size);
         164           15475 :     if (map && map->mTable)
         165           15475 :         return map;
         166               0 :     delete map;
         167               0 :     return nsnull;
         168                 : }
         169                 :
         170           15475 : Native2WrappedNativeMap::Native2WrappedNativeMap(int size)
         171                 : {
         172                 :     mTable = JS_NewDHashTable(JS_DHashGetStubOps(), nsnull,
         173           15475 :                               sizeof(Entry), size);
         174           15475 : }
         175                 :
         176           15471 : Native2WrappedNativeMap::~Native2WrappedNativeMap()
         177                 : {
         178           15471 :     if (mTable)
         179           15471 :         JS_DHashTableDestroy(mTable);
         180           15471 : }
         181                 :
         182                 : size_t
         183              59 : Native2WrappedNativeMap::SizeOfIncludingThis(nsMallocSizeOfFun mallocSizeOf)
         184                 : {
         185              59 :     size_t n = 0;
         186              59 :     n += mallocSizeOf(this);
         187              59 :     n += mTable ? JS_DHashTableSizeOfIncludingThis(mTable, SizeOfEntryExcludingThis, mallocSizeOf) : 0;
         188              59 :     return n;
         189                 : }
         190                 :
         191                 : /* static */ size_t
         192            1865 : Native2WrappedNativeMap::SizeOfEntryExcludingThis(JSDHashEntryHdr *hdr,
         193                 :                                                   JSMallocSizeOfFun mallocSizeOf, void *)
         194                 : {
         195            1865 :     return mallocSizeOf(((Native2WrappedNativeMap::Entry*)hdr)->value);
         196                 : }
         197                 :
         198                 : /***************************************************************************/
         199                 : // implement IID2WrappedJSClassMap...
         200                 :
         201                 : struct JSDHashTableOps IID2WrappedJSClassMap::Entry::sOps =
         202                 : {
         203                 :     JS_DHashAllocTable,
         204                 :     JS_DHashFreeTable,
         205                 :     HashIIDPtrKey,
         206                 :     MatchIIDPtrKey,
         207                 :     JS_DHashMoveEntryStub,
         208                 :     JS_DHashClearEntryStub,
         209                 :     JS_DHashFinalizeStub
         210                 : };
         211                 :
         212                 : // static
         213                 : IID2WrappedJSClassMap*
         214            1404 : IID2WrappedJSClassMap::newMap(int size)
         215                 : {
         216            1404 :     IID2WrappedJSClassMap* map = new IID2WrappedJSClassMap(size);
         217            1404 :     if (map && map->mTable)
         218            1404 :         return map;
         219               0 :     delete map;
         220               0 :     return nsnull;
         221                 : }
         222                 :
         223            1404 : IID2WrappedJSClassMap::IID2WrappedJSClassMap(int size)
         224                 : {
         225            1404 :     mTable = JS_NewDHashTable(&Entry::sOps, nsnull, sizeof(Entry), size);
         226            1404 : }
         227                 :
         228            1403 : IID2WrappedJSClassMap::~IID2WrappedJSClassMap()
         229                 : {
         230            1403 :     if (mTable)
         231            1403 :         JS_DHashTableDestroy(mTable);
         232            1403 : }
         233                 :
         234                 :
         235                 : /***************************************************************************/
         236                 : // implement IID2NativeInterfaceMap...
         237                 :
         238                 : struct JSDHashTableOps IID2NativeInterfaceMap::Entry::sOps =
         239                 : {
         240                 :     JS_DHashAllocTable,
         241                 :     JS_DHashFreeTable,
         242                 :     HashIIDPtrKey,
         243                 :     MatchIIDPtrKey,
         244                 :     JS_DHashMoveEntryStub,
         245                 :     JS_DHashClearEntryStub,
         246                 :     JS_DHashFinalizeStub
         247                 : };
         248                 :
         249                 : // static
         250                 : IID2NativeInterfaceMap*
         251            1404 : IID2NativeInterfaceMap::newMap(int size)
         252                 : {
         253            1404 :     IID2NativeInterfaceMap* map = new IID2NativeInterfaceMap(size);
         254            1404 :     if (map && map->mTable)
         255            1404 :         return map;
         256               0 :     delete map;
         257               0 :     return nsnull;
         258                 : }
         259                 :
         260            1404 : IID2NativeInterfaceMap::IID2NativeInterfaceMap(int size)
         261                 : {
         262            1404 :     mTable = JS_NewDHashTable(&Entry::sOps, nsnull, sizeof(Entry), size);
         263            1404 : }
         264                 :
         265            1403 : IID2NativeInterfaceMap::~IID2NativeInterfaceMap()
         266                 : {
         267            1403 :     if (mTable)
         268            1403 :         JS_DHashTableDestroy(mTable);
         269            1403 : }
         270                 :
         271                 : size_t
         272               3 : IID2NativeInterfaceMap::SizeOfIncludingThis(nsMallocSizeOfFun mallocSizeOf)
         273                 : {
         274               3 :     size_t n = 0;
         275               3 :     n += mallocSizeOf(this);
         276               3 :     n += mTable ? JS_DHashTableSizeOfIncludingThis(mTable, SizeOfEntryExcludingThis, mallocSizeOf) : 0;
         277               3 :     return n;
         278                 : }
         279                 :
         280                 : /* static */ size_t
         281             306 : IID2NativeInterfaceMap::SizeOfEntryExcludingThis(JSDHashEntryHdr *hdr,
         282                 :                                                  JSMallocSizeOfFun mallocSizeOf, void *)
         283                 : {
         284             306 :     XPCNativeInterface *iface = ((IID2NativeInterfaceMap::Entry*)hdr)->value;
         285             306 :     return iface->SizeOfIncludingThis(mallocSizeOf);
         286                 : }
         287                 :
         288                 : /***************************************************************************/
         289                 : // implement ClassInfo2NativeSetMap...
         290                 :
         291                 : // static
         292                 : ClassInfo2NativeSetMap*
         293            1404 : ClassInfo2NativeSetMap::newMap(int size)
         294                 : {
         295            1404 :     ClassInfo2NativeSetMap* map = new ClassInfo2NativeSetMap(size);
         296            1404 :     if (map && map->mTable)
         297            1404 :         return map;
         298               0 :     delete map;
         299               0 :     return nsnull;
         300                 : }
         301                 :
         302            1404 : ClassInfo2NativeSetMap::ClassInfo2NativeSetMap(int size)
         303                 : {
         304                 :     mTable = JS_NewDHashTable(JS_DHashGetStubOps(), nsnull,
         305            1404 :                               sizeof(Entry), size);
         306            1404 : }
         307                 :
         308            1403 : ClassInfo2NativeSetMap::~ClassInfo2NativeSetMap()
         309                 : {
         310            1403 :     if (mTable)
         311            1403 :         JS_DHashTableDestroy(mTable);
         312            1403 : }
         313                 :
         314                 : size_t
         315               3 : ClassInfo2NativeSetMap::ShallowSizeOfIncludingThis(nsMallocSizeOfFun mallocSizeOf)
         316                 : {
         317               3 :     size_t n = 0;
         318               3 :     n += mallocSizeOf(this);
         319                 :     // The second arg is NULL because this is a "shallow" measurement of the map.
         320               3 :     n += mTable ? JS_DHashTableSizeOfIncludingThis(mTable, NULL, mallocSizeOf) : 0;
         321               3 :     return n;
         322                 : }
         323                 :
         324                 : /***************************************************************************/
         325                 : // implement ClassInfo2WrappedNativeProtoMap...
         326                 :
         327                 : // static
         328                 : ClassInfo2WrappedNativeProtoMap*
         329           30950 : ClassInfo2WrappedNativeProtoMap::newMap(int size)
         330                 : {
         331           30950 :     ClassInfo2WrappedNativeProtoMap* map = new ClassInfo2WrappedNativeProtoMap(size);
         332           30950 :     if (map && map->mTable)
         333           30950 :         return map;
         334               0 :     delete map;
         335               0 :     return nsnull;
         336                 : }
         337                 :
         338           30950 : ClassInfo2WrappedNativeProtoMap::ClassInfo2WrappedNativeProtoMap(int size)
         339                 : {
         340                 :     mTable = JS_NewDHashTable(JS_DHashGetStubOps(), nsnull,
         341           30950 :                               sizeof(Entry), size);
         342           30950 : }
         343                 :
         344           30942 : ClassInfo2WrappedNativeProtoMap::~ClassInfo2WrappedNativeProtoMap()
         345                 : {
         346           30942 :     if (mTable)
         347           30942 :         JS_DHashTableDestroy(mTable);
         348           30942 : }
         349                 :
         350                 : size_t
         351             118 : ClassInfo2WrappedNativeProtoMap::SizeOfIncludingThis(nsMallocSizeOfFun mallocSizeOf)
         352                 : {
         353             118 :     size_t n = 0;
         354             118 :     n += mallocSizeOf(this);
         355             118 :     n += mTable ? JS_DHashTableSizeOfIncludingThis(mTable, SizeOfEntryExcludingThis, mallocSizeOf) : 0;
         356             118 :     return n;
         357                 : }
         358                 :
         359                 : /* static */ size_t
         360             469 : ClassInfo2WrappedNativeProtoMap::SizeOfEntryExcludingThis(JSDHashEntryHdr *hdr,
         361                 :                                                           JSMallocSizeOfFun mallocSizeOf, void *)
         362                 : {
         363             469 :     return mallocSizeOf(((ClassInfo2WrappedNativeProtoMap::Entry*)hdr)->value);
         364                 : }
         365                 :
         366                 : /***************************************************************************/
         367                 : // implement NativeSetMap...
         368                 :
         369                 : JSBool
         370         1090535 : NativeSetMap::Entry::Match(JSDHashTable *table,
         371                 :                            const JSDHashEntryHdr *entry,
         372                 :                            const void *key)
         373                 : {
         374         1090535 :     XPCNativeSetKey* Key = (XPCNativeSetKey*) key;
         375                 :
         376                 :     // See the comment in the XPCNativeSetKey declaration in xpcprivate.h.
         377         1090535 :     if (!Key->IsAKey()) {
         378               0 :         XPCNativeSet* Set1 = (XPCNativeSet*) key;
         379               0 :         XPCNativeSet* Set2 = ((Entry*)entry)->key_value;
         380                 :
         381               0 :         if (Set1 == Set2)
         382               0 :             return true;
         383                 :
         384               0 :         PRUint16 count = Set1->GetInterfaceCount();
         385               0 :         if (count != Set2->GetInterfaceCount())
         386               0 :             return false;
         387                 :
         388               0 :         XPCNativeInterface** Current1 = Set1->GetInterfaceArray();
         389               0 :         XPCNativeInterface** Current2 = Set2->GetInterfaceArray();
         390               0 :         for (PRUint16 i = 0; i < count; i++) {
         391               0 :             if (*(Current1++) != *(Current2++))
         392               0 :                 return false;
         393                 :         }
         394                 :
         395               0 :         return true;
         396                 :     }
         397                 :
         398         1090535 :     XPCNativeSet*       SetInTable = ((Entry*)entry)->key_value;
         399         1090535 :     XPCNativeSet*       Set        = Key->GetBaseSet();
         400         1090535 :     XPCNativeInterface* Addition   = Key->GetAddition();
         401                 :
         402         1090535 :     if (!Set) {
         403                 :         // This is a special case to deal with the invariant that says:
         404                 :         // "All sets have exactly one nsISupports interface and it comes first."
         405                 :         // See XPCNativeSet::NewInstance for details.
         406                 :         //
         407                 :         // Though we might have a key that represents only one interface, we
         408                 :         // know that if that one interface were contructed into a set then
         409                 :         // it would end up really being a set with two interfaces (except for
         410                 :         // the case where the one interface happened to be nsISupports).
         411                 :
         412          863997 :         return ((SetInTable->GetInterfaceCount() == 1 &&
         413           69542 :                  SetInTable->GetInterfaceAt(0) == Addition) ||
         414          794455 :                 (SetInTable->GetInterfaceCount() == 2 &&
         415         1727994 :                  SetInTable->GetInterfaceAt(1) == Addition));
         416                 :     }
         417                 :
         418          226538 :     if (!Addition && Set == SetInTable)
         419               0 :         return true;
         420                 :
         421          226538 :     PRUint16 count = Set->GetInterfaceCount() + (Addition ? 1 : 0);
         422          226538 :     if (count != SetInTable->GetInterfaceCount())
         423               0 :         return false;
         424                 :
         425          226538 :     PRUint16 Position = Key->GetPosition();
         426          226538 :     XPCNativeInterface** CurrentInTable = SetInTable->GetInterfaceArray();
         427          226538 :     XPCNativeInterface** Current = Set->GetInterfaceArray();
         428          824920 :     for (PRUint16 i = 0; i < count; i++) {
         429          611111 :         if (Addition && i == Position) {
         430          273612 :             if (Addition != *(CurrentInTable++))
         431               0 :                 return false;
         432                 :         } else {
         433          474305 :             if (*(Current++) != *(CurrentInTable++))
         434           12729 :                 return false;
         435                 :         }
         436                 :     }
         437                 :
         438          213809 :     return true;
         439                 : }
         440                 :
         441                 : struct JSDHashTableOps NativeSetMap::Entry::sOps =
         442                 : {
         443                 :     JS_DHashAllocTable,
         444                 :     JS_DHashFreeTable,
         445                 :     HashNativeKey,
         446                 :     Match,
         447                 :     JS_DHashMoveEntryStub,
         448                 :     JS_DHashClearEntryStub,
         449                 :     JS_DHashFinalizeStub
         450                 : };
         451                 :
         452                 : // static
         453                 : NativeSetMap*
         454            1404 : NativeSetMap::newMap(int size)
         455                 : {
         456            1404 :     NativeSetMap* map = new NativeSetMap(size);
         457            1404 :     if (map && map->mTable)
         458            1404 :         return map;
         459               0 :     delete map;
         460               0 :     return nsnull;
         461                 : }
         462                 :
         463            1404 : NativeSetMap::NativeSetMap(int size)
         464                 : {
         465            1404 :     mTable = JS_NewDHashTable(&Entry::sOps, nsnull, sizeof(Entry), size);
         466            1404 : }
         467                 :
         468            1403 : NativeSetMap::~NativeSetMap()
         469                 : {
         470            1403 :     if (mTable)
         471            1403 :         JS_DHashTableDestroy(mTable);
         472            1403 : }
         473                 :
         474                 : size_t
         475               3 : NativeSetMap::SizeOfIncludingThis(nsMallocSizeOfFun mallocSizeOf)
         476                 : {
         477               3 :     size_t n = 0;
         478               3 :     n += mallocSizeOf(this);
         479               3 :     n += mTable ? JS_DHashTableSizeOfIncludingThis(mTable, SizeOfEntryExcludingThis, mallocSizeOf) : 0;
         480               3 :     return n;
         481                 : }
         482                 :
         483                 : /* static */ size_t
         484             284 : NativeSetMap::SizeOfEntryExcludingThis(JSDHashEntryHdr *hdr, JSMallocSizeOfFun mallocSizeOf, void *)
         485                 : {
         486             284 :     XPCNativeSet *set = ((NativeSetMap::Entry*)hdr)->key_value;
         487             284 :     return set->SizeOfIncludingThis(mallocSizeOf);
         488                 : }
         489                 :
         490                 : /***************************************************************************/
         491                 : // implement IID2ThisTranslatorMap...
         492                 :
         493                 : JSBool
         494            3963 : IID2ThisTranslatorMap::Entry::Match(JSDHashTable *table,
         495                 :                                     const JSDHashEntryHdr *entry,
         496                 :                                     const void *key)
         497                 : {
         498            3963 :     return ((const nsID*)key)->Equals(((Entry*)entry)->key);
         499                 : }
         500                 :
         501                 : void
         502             305 : IID2ThisTranslatorMap::Entry::Clear(JSDHashTable *table, JSDHashEntryHdr *entry)
         503                 : {
         504             305 :     NS_IF_RELEASE(((Entry*)entry)->value);
         505             305 :     memset(entry, 0, table->entrySize);
         506             305 : }
         507                 :
         508                 : struct JSDHashTableOps IID2ThisTranslatorMap::Entry::sOps =
         509                 : {
         510                 :     JS_DHashAllocTable,
         511                 :     JS_DHashFreeTable,
         512                 :     HashIIDPtrKey,
         513                 :     Match,
         514                 :     JS_DHashMoveEntryStub,
         515                 :     Clear,
         516                 :     JS_DHashFinalizeStub
         517                 : };
         518                 :
         519                 : // static
         520                 : IID2ThisTranslatorMap*
         521            1404 : IID2ThisTranslatorMap::newMap(int size)
         522                 : {
         523            1404 :     IID2ThisTranslatorMap* map = new IID2ThisTranslatorMap(size);
         524            1404 :     if (map && map->mTable)
         525            1404 :         return map;
         526               0 :     delete map;
         527               0 :     return nsnull;
         528                 : }
         529                 :
         530            1404 : IID2ThisTranslatorMap::IID2ThisTranslatorMap(int size)
         531                 : {
         532            1404 :     mTable = JS_NewDHashTable(&Entry::sOps, nsnull, sizeof(Entry), size);
         533            1404 : }
         534                 :
         535            1403 : IID2ThisTranslatorMap::~IID2ThisTranslatorMap()
         536                 : {
         537            1403 :     if (mTable)
         538            1403 :         JS_DHashTableDestroy(mTable);
         539            1403 : }
         540                 :
         541                 : /***************************************************************************/
         542                 :
         543                 : JSDHashNumber
         544          249778 : XPCNativeScriptableSharedMap::Entry::Hash(JSDHashTable *table, const void *key)
         545                 : {
         546                 :     JSDHashNumber h;
         547                 :     const unsigned char *s;
         548                 :
         549                 :     XPCNativeScriptableShared* obj =
         550          249778 :         (XPCNativeScriptableShared*) key;
         551                 :
         552                 :     // hash together the flags and the classname string, ignore the interfaces
         553                 :     // bitmap since it's very rare that it's different when flags and classname
         554                 :     // are the same.
         555                 :
         556          249778 :     h = (JSDHashNumber) obj->GetFlags();
         557         3208096 :     for (s = (const unsigned char*) obj->GetJSClass()->name; *s != '\0'; s++)
         558         2958318 :         h = JS_ROTATE_LEFT32(h, 4) ^ *s;
         559          249778 :     return h;
         560                 : }
         561                 :
         562                 : JSBool
         563          228550 : XPCNativeScriptableSharedMap::Entry::Match(JSDHashTable *table,
         564                 :                                            const JSDHashEntryHdr *entry,
         565                 :                                            const void *key)
         566                 : {
         567                 :     XPCNativeScriptableShared* obj1 =
         568          228550 :         ((XPCNativeScriptableSharedMap::Entry*) entry)->key;
         569                 :
         570                 :     XPCNativeScriptableShared* obj2 =
         571          228550 :         (XPCNativeScriptableShared*) key;
         572                 :
         573                 :     // match the flags, the classname string and the interfaces bitmap
         574                 :
         575          457100 :     if (obj1->GetFlags() != obj2->GetFlags() ||
         576          228550 :         obj1->GetInterfacesBitmap() != obj2->GetInterfacesBitmap())
         577               0 :         return false;
         578                 :
         579          228550 :     const char* name1 = obj1->GetJSClass()->name;
         580          228550 :     const char* name2 = obj2->GetJSClass()->name;
         581                 :
         582          228550 :     if (!name1 || !name2)
         583               0 :         return name1 == name2;
         584                 :
         585          228550 :     return 0 == strcmp(name1, name2);
         586                 : }
         587                 :
         588                 : struct JSDHashTableOps XPCNativeScriptableSharedMap::Entry::sOps =
         589                 : {
         590                 :     JS_DHashAllocTable,
         591                 :     JS_DHashFreeTable,
         592                 :     Hash,
         593                 :     Match,
         594                 :     JS_DHashMoveEntryStub,
         595                 :     JS_DHashClearEntryStub,
         596                 :     JS_DHashFinalizeStub
         597                 : };
         598                 :
         599                 : // static
         600                 : XPCNativeScriptableSharedMap*
         601            1404 : XPCNativeScriptableSharedMap::newMap(int size)
         602                 : {
         603                 :     XPCNativeScriptableSharedMap* map =
         604            1404 :         new XPCNativeScriptableSharedMap(size);
         605            1404 :     if (map && map->mTable)
         606            1404 :         return map;
         607               0 :     delete map;
         608               0 :     return nsnull;
         609                 : }
         610                 :
         611            1404 : XPCNativeScriptableSharedMap::XPCNativeScriptableSharedMap(int size)
         612                 : {
         613            1404 :     mTable = JS_NewDHashTable(&Entry::sOps, nsnull, sizeof(Entry), size);
         614            1404 : }
         615                 :
         616            1403 : XPCNativeScriptableSharedMap::~XPCNativeScriptableSharedMap()
         617                 : {
         618            1403 :     if (mTable)
         619            1403 :         JS_DHashTableDestroy(mTable);
         620            1403 : }
         621                 :
         622                 : JSBool
         623          249778 : XPCNativeScriptableSharedMap::GetNewOrUsed(uint32_t flags,
         624                 :                                            char* name,
         625                 :                                            PRUint32 interfacesBitmap,
         626                 :                                            XPCNativeScriptableInfo* si)
         627                 : {
         628          249778 :     NS_PRECONDITION(name,"bad param");
         629          249778 :     NS_PRECONDITION(si,"bad param");
         630                 :
         631          499556 :     XPCNativeScriptableShared key(flags, name, interfacesBitmap);
         632                 :     Entry* entry = (Entry*)
         633          249778 :         JS_DHashTableOperate(mTable, &key, JS_DHASH_ADD);
         634          249778 :     if (!entry)
         635               0 :         return false;
         636                 :
         637          249778 :     XPCNativeScriptableShared* shared = entry->key;
         638                 :
         639          249778 :     if (!shared) {
         640                 :         entry->key = shared =
         641                 :             new XPCNativeScriptableShared(flags, key.TransferNameOwnership(),
         642           42456 :                                           interfacesBitmap);
         643           21228 :         if (!shared)
         644               0 :             return false;
         645           21228 :         shared->PopulateJSClass();
         646                 :     }
         647          249778 :     si->SetScriptableShared(shared);
         648          249778 :     return true;
         649                 : }
         650                 :
         651                 : /***************************************************************************/
         652                 : // implement XPCWrappedNativeProtoMap...
         653                 :
         654                 : // static
         655                 : XPCWrappedNativeProtoMap*
         656            2808 : XPCWrappedNativeProtoMap::newMap(int size)
         657                 : {
         658            2808 :     XPCWrappedNativeProtoMap* map = new XPCWrappedNativeProtoMap(size);
         659            2808 :     if (map && map->mTable)
         660            2808 :         return map;
         661               0 :     delete map;
         662               0 :     return nsnull;
         663                 : }
         664                 :
         665            2808 : XPCWrappedNativeProtoMap::XPCWrappedNativeProtoMap(int size)
         666                 : {
         667                 :     mTable = JS_NewDHashTable(JS_DHashGetStubOps(), nsnull,
         668            2808 :                               sizeof(JSDHashEntryStub), size);
         669            2808 : }
         670                 :
         671            2806 : XPCWrappedNativeProtoMap::~XPCWrappedNativeProtoMap()
         672                 : {
         673            2806 :     if (mTable)
         674            2806 :         JS_DHashTableDestroy(mTable);
         675            2806 : }
         676                 :
         677                 : /***************************************************************************/
         678                 : // implement XPCNativeWrapperMap...
         679                 :
         680                 : // static
         681                 : XPCNativeWrapperMap*
         682            1404 : XPCNativeWrapperMap::newMap(int size)
         683                 : {
         684            1404 :     XPCNativeWrapperMap* map = new XPCNativeWrapperMap(size);
         685            1404 :     if (map && map->mTable)
         686            1404 :         return map;
         687               0 :     delete map;
         688               0 :     return nsnull;
         689                 : }
         690                 :
         691            1404 : XPCNativeWrapperMap::XPCNativeWrapperMap(int size)
         692                 : {
         693                 :     mTable = JS_NewDHashTable(JS_DHashGetStubOps(), nsnull,
         694            1404 :                               sizeof(JSDHashEntryStub), size);
         695            1404 : }
         696                 :
         697            1403 : XPCNativeWrapperMap::~XPCNativeWrapperMap()
         698                 : {
         699            1403 :     if (mTable)
         700            1403 :         JS_DHashTableDestroy(mTable);
         701            1403 : }
         702                 :
         703                 : /***************************************************************************/
         704                 : // implement WrappedNative2WrapperMap...
         705                 :
         706                 : struct JSDHashTableOps
         707                 : WrappedNative2WrapperMap::sOps = {
         708                 :     JS_DHashAllocTable,
         709                 :     JS_DHashFreeTable,
         710                 :     JS_DHashVoidPtrKeyStub,
         711                 :     JS_DHashMatchEntryStub,
         712                 :     MoveLink,
         713                 :     ClearLink,
         714                 :     JS_DHashFinalizeStub,
         715                 :     nsnull
         716                 : };
         717                 :
         718                 : // static
         719                 : void
         720               0 : WrappedNative2WrapperMap::ClearLink(JSDHashTable* table,
         721                 :                                     JSDHashEntryHdr* entry)
         722                 : {
         723               0 :     Entry* e = static_cast<Entry*>(entry);
         724               0 :     e->key = nsnull;
         725               0 :     PR_REMOVE_LINK(&e->value);
         726               0 :     memset(e, 0, sizeof(*e));
         727               0 : }
         728                 :
         729                 : // static
         730                 : void
         731               0 : WrappedNative2WrapperMap::MoveLink(JSDHashTable* table,
         732                 :                                    const JSDHashEntryHdr* from,
         733                 :                                    JSDHashEntryHdr* to)
         734                 : {
         735               0 :     const Entry* oldEntry = static_cast<const Entry*>(from);
         736               0 :     Entry* newEntry = static_cast<Entry*>(to);
         737                 :
         738               0 :     newEntry->key = oldEntry->key;
         739                 :
         740                 :     // Now update the list.
         741               0 :     if (PR_CLIST_IS_EMPTY(&oldEntry->value)) {
         742               0 :         PR_INIT_CLIST(&newEntry->value);
         743               0 :         newEntry->value.obj = oldEntry->value.obj;
         744                 :     } else {
         745               0 :         newEntry->value = oldEntry->value;
         746               0 :         newEntry->value.next->prev = &newEntry->value;
         747               0 :         newEntry->value.prev->next = &newEntry->value;
         748                 :     }
         749               0 : }
         750                 :
         751                 : // static
         752                 : WrappedNative2WrapperMap*
         753               0 : WrappedNative2WrapperMap::newMap(int size)
         754                 : {
         755               0 :     WrappedNative2WrapperMap* map = new WrappedNative2WrapperMap(size);
         756               0 :     if (map && map->mTable)
         757               0 :         return map;
         758               0 :     delete map;
         759               0 :     return nsnull;
         760                 : }
         761                 :
         762               0 : WrappedNative2WrapperMap::WrappedNative2WrapperMap(int size)
         763                 : {
         764               0 :     mTable = JS_NewDHashTable(&sOps, nsnull, sizeof(Entry), size);
         765               0 : }
         766                 :
         767               0 : WrappedNative2WrapperMap::~WrappedNative2WrapperMap()
         768                 : {
         769               0 :     if (mTable)
         770               0 :         JS_DHashTableDestroy(mTable);
         771               0 : }
         772                 :
         773                 : JSObject*
         774               0 : WrappedNative2WrapperMap::Add(WrappedNative2WrapperMap* head,
         775                 :                               JSObject* wrappedObject,
         776                 :                               JSObject* wrapper)
         777                 : {
         778               0 :     NS_PRECONDITION(wrappedObject,"bad param");
         779                 :     Entry* entry = (Entry*)
         780               0 :         JS_DHashTableOperate(mTable, wrappedObject, JS_DHASH_ADD);
         781               0 :     if (!entry)
         782               0 :         return nsnull;
         783               0 :     NS_ASSERTION(!entry->key || this == head, "dangling pointer?");
         784               0 :     entry->key = wrappedObject;
         785               0 :     Link* l = &entry->value;
         786                 :
         787               0 :     NS_ASSERTION(!l->obj, "Uh, how'd this happen?");
         788                 :
         789               0 :     if (!l->next) {
         790                 :         // Initialize the circular list. This case only happens when
         791                 :         // this == head.
         792               0 :         PR_INIT_CLIST(l);
         793                 :     }
         794                 :
         795               0 :     l->obj = wrapper;
         796                 :
         797               0 :     if (this != head) {
         798               0 :         Link* headLink = head->FindLink(wrappedObject);
         799               0 :         if (!headLink) {
         800                 :             Entry* dummy = (Entry*)
         801               0 :                 JS_DHashTableOperate(head->mTable, wrappedObject, JS_DHASH_ADD);
         802               0 :             dummy->key = wrappedObject;
         803               0 :             headLink = &dummy->value;
         804               0 :             PR_INIT_CLIST(headLink);
         805               0 :             headLink->obj = nsnull;
         806                 :         }
         807                 :
         808               0 :         PR_INSERT_BEFORE(l, headLink);
         809                 :     }
         810                 :
         811               0 :     return wrapper;
         812                 : }
         813                 :
         814                 : bool
         815               0 : WrappedNative2WrapperMap::AddLink(JSObject* wrappedObject, Link* oldLink)
         816                 : {
         817                 :     Entry* entry = (Entry*)
         818               0 :         JS_DHashTableOperate(mTable, wrappedObject, JS_DHASH_ADD);
         819               0 :     if (!entry)
         820               0 :         return false;
         821               0 :     NS_ASSERTION(!entry->key, "Eh? What's happening?");
         822               0 :     entry->key = wrappedObject;
         823               0 :     Link* newLink = &entry->value;
         824                 :
         825               0 :     PR_INSERT_LINK(newLink, oldLink);
         826               0 :     PR_REMOVE_AND_INIT_LINK(oldLink);
         827               0 :     newLink->obj = oldLink->obj;
         828                 :
         829               0 :     return true;
         830                 : }
         831                 :
         832                 : /***************************************************************************/
         833                 : // implement JSObject2JSObjectMap...
         834                 :
         835                 : struct JSDHashTableOps
         836                 : JSObject2JSObjectMap::sOps = {
         837                 :     JS_DHashAllocTable,
         838                 :     JS_DHashFreeTable,
         839                 :     JS_DHashVoidPtrKeyStub,
         840                 :     JS_DHashMatchEntryStub,
         841                 :     JS_DHashMoveEntryStub,
         842                 :     JS_DHashClearEntryStub,
         843                 :     JS_DHashFinalizeStub,
         844                 :     nsnull
         845                 : };
         846                 :
         847                 : /***************************************************************************/

Generated by: LCOV version 1.7