Back to index

lightning-sunbird  0.9+nobinonly
Public Member Functions | Static Public Member Functions | Private Types | Private Member Functions | Static Private Member Functions | Private Attributes
xptiInterfaceInfoManager Class Reference

#include <xptiprivate.h>

Inheritance diagram for xptiInterfaceInfoManager:
Inheritance graph
[legend]
Collaboration diagram for xptiInterfaceInfoManager:
Collaboration graph
[legend]

List of all members.

Public Member Functions

xptiWorkingSetGetWorkingSet ()
PRFileDescGetOpenLogFile ()
PRFileDescSetOpenLogFile (PRFileDesc *fd)
PRBool LoadFile (const xptiTypelib &aTypelibRecord, xptiWorkingSet *aWorkingSet=nsnull)
PRBool GetApplicationDir (nsILocalFile **aDir)
PRBool GetCloneOfManifestLocation (nsILocalFile **aDir)
void GetSearchPath (nsISupportsArray **aSearchPath)
void addAdditionalManager (in nsIInterfaceInfoManager manager)
void removeAdditionalManager (in nsIInterfaceInfoManager manager)
PRBool hasAdditionalManagers ()
nsISimpleEnumerator enumerateAdditionalManagers ()
nsIInterfaceInfo getInfoForIID (in nsIIDPtr iid)
nsIInterfaceInfo getInfoForName (in string name)
nsIIDPtr getIIDForName (in string name)
string getNameForIID (in nsIIDPtr iid)
nsIEnumerator enumerateInterfaces ()
void autoRegisterInterfaces ()
nsIEnumerator enumerateInterfacesWhoseNamesStartWith (in string prefix)

Static Public Member Functions

static xptiInterfaceInfoManagerGetInterfaceInfoManagerNoAddRef ()
static void FreeInterfaceInfoManager ()
static PRLockGetResolveLock (xptiInterfaceInfoManager *self=nsnull)
static PRLockGetAutoRegLock (xptiInterfaceInfoManager *self=nsnull)
static PRMonitorGetInfoMonitor (xptiInterfaceInfoManager *self=nsnull)
static void WriteToLog (const char *fmt,...)

Private Types

enum  AutoRegMode { NO_FILES_CHANGED = 0, FILES_ADDED_ONLY, FULL_VALIDATION_REQUIRED }

Private Member Functions

NS_DECL_ISUPPORTS
NS_DECL_NSIINTERFACEINFOMANAGER
NS_DECL_NSIINTERFACEINFOSUPERMANAGER
PRBool 
FoundZipEntry (const char *entryName, int index, XPTHeader *header, xptiWorkingSet *aWorkingSet)
 ~xptiInterfaceInfoManager ()
 xptiInterfaceInfoManager ()
 xptiInterfaceInfoManager (nsISupportsArray *aSearchPath)
PRBool IsValid ()
PRBool BuildFileList (nsISupportsArray *aSearchPath, nsISupportsArray **aFileList)
nsILocalFile ** BuildOrderedFileArray (nsISupportsArray *aSearchPath, nsISupportsArray *aFileList, xptiWorkingSet *aWorkingSet)
XPTHeaderReadXPTFile (nsILocalFile *aFile, xptiWorkingSet *aWorkingSet)
AutoRegMode DetermineAutoRegStrategy (nsISupportsArray *aSearchPath, nsISupportsArray *aFileList, xptiWorkingSet *aWorkingSet)
PRBool AddOnlyNewFilesFromFileList (nsISupportsArray *aSearchPath, nsISupportsArray *aFileList, xptiWorkingSet *aWorkingSet)
PRBool DoFullValidationMergeFromFileList (nsISupportsArray *aSearchPath, nsISupportsArray *aFileList, xptiWorkingSet *aWorkingSet)
PRBool VerifyAndAddEntryIfNew (xptiWorkingSet *aWorkingSet, XPTInterfaceDirectoryEntry *iface, const xptiTypelib &typelibRecord, xptiInterfaceEntry **entryAdded)
PRBool MergeWorkingSets (xptiWorkingSet *aDestWorkingSet, xptiWorkingSet *aSrcWorkingSet)
void LogStats ()
PRBool DEBUG_DumpFileList (nsISupportsArray *aFileList)
PRBool DEBUG_DumpFileArray (nsILocalFile **aFileArray, PRUint32 count)
PRBool DEBUG_DumpFileListInWorkingSet (xptiWorkingSet *aWorkingSet)

Static Private Member Functions

static PRBool BuildFileSearchPath (nsISupportsArray **aPath)

Private Attributes

xptiWorkingSet mWorkingSet
nsCOMPtr< nsILocalFilemStatsLogFile
nsCOMPtr< nsILocalFilemAutoRegLogFile
PRFileDescmOpenLogFile
PRLockmResolveLock
PRLockmAutoRegLock
PRMonitormInfoMonitor
PRLockmAdditionalManagersLock
nsSupportsArray mAdditionalManagers
nsCOMPtr< nsISupportsArraymSearchPath

Detailed Description

Definition at line 860 of file xptiprivate.h.


Member Enumeration Documentation

Enumerator:
NO_FILES_CHANGED 
FILES_ADDED_ONLY 
FULL_VALIDATION_REQUIRED 

Definition at line 914 of file xptiprivate.h.


Constructor & Destructor Documentation

Definition at line 161 of file xptiInterfaceInfoManager.cpp.

{
    // We only do this on shutdown of the service.
    mWorkingSet.InvalidateInterfaceInfos();

    if(mResolveLock)
        PR_DestroyLock(mResolveLock);
    if(mAutoRegLock)
        PR_DestroyLock(mAutoRegLock);
    if(mInfoMonitor)
        nsAutoMonitor::DestroyMonitor(mInfoMonitor);
    if(mAdditionalManagersLock)
        PR_DestroyLock(mAdditionalManagersLock);

    gInterfaceInfoManager = nsnull;
#ifdef DEBUG
    xptiInterfaceInfo::DEBUG_ShutdownNotification();
    gCallCount = 0;
#endif
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 119 of file xptiInterfaceInfoManager.cpp.

    :   mWorkingSet(aSearchPath),
        mOpenLogFile(nsnull),
        mResolveLock(PR_NewLock()),
        mAutoRegLock(PR_NewLock()),
        mInfoMonitor(nsAutoMonitor::NewMonitor("xptiInfoMonitor")),
        mAdditionalManagersLock(PR_NewLock()),
        mSearchPath(aSearchPath)
{
    const char* statsFilename = PR_GetEnv("MOZILLA_XPTI_STATS");
    if(statsFilename)
    {
        mStatsLogFile = do_CreateInstance(NS_LOCAL_FILE_CONTRACTID);         
        if(mStatsLogFile && 
           NS_SUCCEEDED(mStatsLogFile->InitWithNativePath(nsDependentCString(statsFilename))))
        {
            printf("* Logging xptinfo stats to: %s\n", statsFilename);
        }
        else
        {
            printf("* Failed to create xptinfo stats file: %s\n", statsFilename);
            mStatsLogFile = nsnull;
        }
    }

    const char* autoRegFilename = PR_GetEnv("MOZILLA_XPTI_REGLOG");
    if(autoRegFilename)
    {
        mAutoRegLogFile = do_CreateInstance(NS_LOCAL_FILE_CONTRACTID);         
        if(mAutoRegLogFile && 
           NS_SUCCEEDED(mAutoRegLogFile->InitWithNativePath(nsDependentCString(autoRegFilename))))
        {
            printf("* Logging xptinfo autoreg to: %s\n", autoRegFilename);
        }
        else
        {
            printf("* Failed to create xptinfo autoreg file: %s\n", autoRegFilename);
            mAutoRegLogFile = nsnull;
        }
    }
}

Here is the call graph for this function:


Member Function Documentation

PRBool xptiInterfaceInfoManager::AddOnlyNewFilesFromFileList ( nsISupportsArray aSearchPath,
nsISupportsArray aFileList,
xptiWorkingSet aWorkingSet 
) [private]

Definition at line 892 of file xptiInterfaceInfoManager.cpp.

{
    nsILocalFile** orderedFileArray;
    PRUint32 countOfFilesInFileList;
    PRUint32 i;

    NS_ASSERTION(aFileList, "loser!");
    NS_ASSERTION(aWorkingSet, "loser!");
    NS_ASSERTION(aWorkingSet->IsValid(), "loser!");

    if(NS_FAILED(aFileList->Count(&countOfFilesInFileList)))
        return PR_FALSE;
    NS_ASSERTION(countOfFilesInFileList, "loser!");
    NS_ASSERTION(countOfFilesInFileList > aWorkingSet->GetFileCount(), "loser!");

    orderedFileArray = BuildOrderedFileArray(aSearchPath, aFileList, aWorkingSet);

    if(!orderedFileArray)
        return PR_FALSE;

    // Make enough space in aWorkingset for additions to xptiFile array.

    if(!aWorkingSet->ExtendFileArray(countOfFilesInFileList))   
        return PR_FALSE;

    // For each file that is not already in our working set, add any valid 
    // interfaces that don't conflict with previous interfaces added.
    for(i = 0; i < countOfFilesInFileList; i++)
    {
        nsILocalFile* file = orderedFileArray[i];

        nsCAutoString name;
        PRInt64 size;
        PRInt64 date;
        PRUint32 dir;
        if(NS_FAILED(file->GetFileSize(&size)) ||
           NS_FAILED(file->GetLastModifiedTime(&date)) ||
           NS_FAILED(file->GetNativeLeafName(name)) ||
           !aWorkingSet->FindDirectoryOfFile(file, &dir))
        {
            return PR_FALSE;
        }    
    

        if(xptiWorkingSet::NOT_FOUND != aWorkingSet->FindFile(dir, name.get()))
        {
            // This file was found in the working set, so skip it.       
            continue;
        }

        LOG_AUTOREG(("  finding interfaces in new file: %s\n", name.get()));

        xptiFile fileRecord;
        fileRecord = xptiFile(nsInt64(size), nsInt64(date), dir,
                              name.get(), aWorkingSet);

        if(xptiFileType::IsXPT(fileRecord.GetName()))
        {
            XPTHeader* header = ReadXPTFile(file, aWorkingSet);
            if(!header)
            {
                // XXX do something!
                NS_ERROR("");    
                continue;
            }

    
            xptiTypelib typelibRecord;
            typelibRecord.Init(aWorkingSet->GetFileCount());
    
            PRBool AddedFile = PR_FALSE;

            if(header->major_version >= XPT_MAJOR_INCOMPATIBLE_VERSION)
            {
                NS_ASSERTION(!header->num_interfaces,"bad libxpt");
                LOG_AUTOREG(("      file is version %d.%d  Type file of version %d.0 or higher can not be read.\n", (int)header->major_version, (int)header->minor_version, (int)XPT_MAJOR_INCOMPATIBLE_VERSION));
            }

            for(PRUint16 k = 0; k < header->num_interfaces; k++)
            {
                xptiInterfaceEntry* entry = nsnull;
    
                if(!VerifyAndAddEntryIfNew(aWorkingSet,
                                           header->interface_directory + k,
                                           typelibRecord,
                                           &entry))
                    return PR_FALSE;    
    
                if(!entry)
                    continue;
                
                // If this is the first interface we found for this file then
                // setup the fileRecord for the header and infos.
                if(!AddedFile)
                {
                    if(!fileRecord.SetHeader(header, aWorkingSet))
                    {
                        // XXX that would be bad.
                        return PR_FALSE;    
                    }
                    AddedFile = PR_TRUE;
                }
                fileRecord.GetGuts()->SetEntryAt(k, entry);
            }
            
            // This will correspond to typelibRecord above.
            aWorkingSet->AppendFile(fileRecord);
        }
        else // its another kind of archive
        {
            nsCOMPtr<nsIXPTLoader> loader =
                do_GetService(NS_ZIPLOADER_CONTRACTID);
            
            if (loader) {
                nsresult rv;
                
                nsCOMPtr<nsIXPTLoaderSink> sink =
                    new xptiZipLoaderSink(this, aWorkingSet);
                if (!sink)
                    return PR_FALSE;
                
                rv = loader->EnumerateEntries(file, sink);
                if (NS_FAILED(rv))
                    return PR_FALSE;
                // This will correspond to typelibRecord used in
                // xptiInterfaceInfoManager::FoundEntry.
                aWorkingSet->AppendFile(fileRecord);
            } else {
                NS_WARNING("Could not load XPT Zip loader");
            }
        }
    }

    return PR_TRUE;
}        

Here is the call graph for this function:

PRBool xptiInterfaceInfoManager::BuildFileList ( nsISupportsArray aSearchPath,
nsISupportsArray **  aFileList 
) [private]

Definition at line 302 of file xptiInterfaceInfoManager.cpp.

{
    NS_ASSERTION(aFileList, "loser!");
    
    nsresult rv;

    nsCOMPtr<nsISupportsArray> fileList = 
        do_CreateInstance(NS_SUPPORTSARRAY_CONTRACTID);
    if(!fileList)
        return PR_FALSE;

    PRUint32 pathCount;
    if(NS_FAILED(aSearchPath->Count(&pathCount)))
        return PR_FALSE;

    for(PRUint32 i = 0; i < pathCount; i++)
    {
        nsCOMPtr<nsILocalFile> dir;
        rv = xptiCloneElementAsLocalFile(aSearchPath, i, getter_AddRefs(dir));
        if(NS_FAILED(rv) || !dir)
            return PR_FALSE;

        nsCOMPtr<nsISimpleEnumerator> entries;
        rv = dir->GetDirectoryEntries(getter_AddRefs(entries));
        if(NS_FAILED(rv) || !entries)
            continue;

        PRUint32 count = 0;
        PRBool hasMore;
        while(NS_SUCCEEDED(entries->HasMoreElements(&hasMore)) && hasMore)
        {
            nsCOMPtr<nsISupports> sup;
            entries->GetNext(getter_AddRefs(sup));
            if(!sup)
                return PR_FALSE;
            nsCOMPtr<nsILocalFile> file = do_QueryInterface(sup);
            if(!file)
                return PR_FALSE;

            PRBool isFile;
            if(NS_FAILED(file->IsFile(&isFile)) || !isFile)
            {
                continue;
            }
     
            nsCAutoString name;
            if(NS_FAILED(file->GetNativeLeafName(name)))
                return PR_FALSE;

            if(xptiFileType::IsUnknown(name.get()))
                continue;

            LOG_AUTOREG(("found file: %s\n", name.get()));

            if(!fileList->InsertElementAt(file, count))
                return PR_FALSE;
            ++count;
        }
    }

    NS_ADDREF(*aFileList = fileList); 
    return PR_TRUE;
}

Here is the call graph for this function:

Definition at line 226 of file xptiInterfaceInfoManager.cpp.

{
#ifdef DEBUG
    NS_ASSERTION(!gCallCount++, "Expected only one call!");
#endif

    nsCOMPtr<nsISupportsArray> searchPath;
    NS_NewISupportsArray(getter_AddRefs(searchPath));
    if(!searchPath)
        return PR_FALSE;
    
    nsCOMPtr<nsILocalFile> compDir;

    // Always put components directory first

    if(NS_FAILED(GetDirectoryFromDirService(NS_XPCOM_COMPONENT_DIR, 
                                            getter_AddRefs(compDir))) ||
       !searchPath->AppendElement(compDir))
    {
        return PR_FALSE;
    }

    // Add additional plugins dirs
    // No error checking here since this is optional in some embeddings
    
    // Add the GRE's component directory to searchPath if the 
    // application is using an GRE.
    // An application indicates that it's using an GRE by returning
    // a valid nsIFile via it's directory service provider interface.
    //
    // Please see http://www.mozilla.org/projects/embedding/MRE.html
    // for more info. on GREs
    //
    nsCOMPtr<nsILocalFile> greComponentDirectory;
    nsresult rv = GetDirectoryFromDirService(NS_GRE_COMPONENT_DIR, 
                                    getter_AddRefs(greComponentDirectory));
    if(NS_SUCCEEDED(rv) && greComponentDirectory)
    {
        // make sure we only append a directory if its a different one
        PRBool equalsCompDir = PR_FALSE;
        greComponentDirectory->Equals(compDir, &equalsCompDir);

        if(!equalsCompDir)
            searchPath->AppendElement(greComponentDirectory);
    }

    (void)AppendFromDirServiceList(NS_XPCOM_COMPONENT_DIR_LIST, searchPath);
    (void)AppendFromDirServiceList(NS_APP_PLUGINS_DIR_LIST, searchPath);

    NS_ADDREF(*aPath = searchPath);
    return PR_TRUE;
}

Here is the call graph for this function:

Here is the caller graph for this function:

nsILocalFile ** xptiInterfaceInfoManager::BuildOrderedFileArray ( nsISupportsArray aSearchPath,
nsISupportsArray aFileList,
xptiWorkingSet aWorkingSet 
) [private]

Definition at line 721 of file xptiInterfaceInfoManager.cpp.

{
    // We want to end up with a file list that starts with the files from
    // aWorkingSet (but only those that are in aFileList) in the order in 
    // which they appeared in aWorkingSet-> Following those files will be those
    // files in aFileList which are not in aWorkingSet-> These additional
    // files will be ordered by file size (larger first) but all .xpt files
    // will preceed all zipfile of those files not already in the working set.
    // To do this we will do a fancy sort on a copy of aFileList.

    nsILocalFile** orderedFileList = nsnull;
    PRUint32 countOfFilesInFileList;
    PRUint32 i;

    NS_ASSERTION(aFileList, "loser!");
    NS_ASSERTION(aWorkingSet, "loser!");
    NS_ASSERTION(aWorkingSet->IsValid(), "loser!");

    if(NS_FAILED(aFileList->Count(&countOfFilesInFileList)) || 
       0 == countOfFilesInFileList)
        return nsnull;

    orderedFileList = (nsILocalFile**) 
        XPT_MALLOC(aWorkingSet->GetStructArena(),
                   sizeof(nsILocalFile*) * countOfFilesInFileList);
    
    if(!orderedFileList)
        return nsnull;

    // fill our list for sorting
    for(i = 0; i < countOfFilesInFileList; ++i)
    {
        nsCOMPtr<nsILocalFile> file;
        aFileList->QueryElementAt(i, NS_GET_IID(nsILocalFile), getter_AddRefs(file));
        NS_ASSERTION(file, "loser!");

        // Intentionally NOT addref'd cuz we know these are pinned in aFileList.
        orderedFileList[i] = file.get();
    }

    // sort the filelist

    SortData sortData = {aSearchPath, aWorkingSet};
    NS_QuickSort(orderedFileList, countOfFilesInFileList, sizeof(nsILocalFile*),
                 xptiSortFileList, &sortData);
     
    return orderedFileList;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 1589 of file xptiInterfaceInfoManager.cpp.

{
    // dump the sorted list
    for(PRUint32 i = 0; i < count; ++i)
    {
        nsILocalFile* file = aFileArray[i];
    
        nsCAutoString name;
        if(NS_FAILED(file->GetNativeLeafName(name)))
            return PR_FALSE;

        printf("found file: %s\n", name.get());
    }        
    return PR_TRUE;        
}        

Here is the call graph for this function:

Definition at line 1553 of file xptiInterfaceInfoManager.cpp.

{
    PRUint32 count;

    if(NS_FAILED(aFileList->Count(&count)))
        return PR_FALSE;
    
    for(PRUint32 i = 0; i < count; i++)
    {
        nsCOMPtr<nsIFile> file;
        aFileList->QueryElementAt(i, NS_GET_IID(nsILocalFile), getter_AddRefs(file));
        if(!file)
            return PR_FALSE;

        nsCAutoString name;
        if(NS_FAILED(file->GetNativeLeafName(name)))
            return PR_FALSE;

        printf("* found %s\n", name.get());
    }
    return PR_TRUE;
}

Here is the call graph for this function:

Definition at line 1577 of file xptiInterfaceInfoManager.cpp.

{
    for(PRUint16 i = 0; i < aWorkingSet->GetFileCount(); ++i)
    {
        xptiFile& record = aWorkingSet->GetFileAt(i);
    
        printf("! has %s\n", record.GetName());
    }        
    return PR_TRUE;
}        

Here is the call graph for this function:

Definition at line 773 of file xptiInterfaceInfoManager.cpp.

{
    NS_ASSERTION(aFileList, "loser!");
    NS_ASSERTION(aWorkingSet, "loser!");
    NS_ASSERTION(aWorkingSet->IsValid(), "loser!");

    PRUint32 countOfFilesInWorkingSet = aWorkingSet->GetFileCount();
    PRUint32 countOfFilesInFileList;
    PRUint32 i;
    PRUint32 k;

    if(0 == countOfFilesInWorkingSet)
    {
        // Loading manifest might have failed. Better safe...     
        return FULL_VALIDATION_REQUIRED;
    }

    if(NS_FAILED(aFileList->Count(&countOfFilesInFileList)))
    {
        NS_ERROR("unexpected!");
        return FULL_VALIDATION_REQUIRED;
    }       

    if(countOfFilesInFileList == countOfFilesInWorkingSet)
    {
        // try to determine if *no* files are new or changed.
     
        PRBool same = PR_TRUE;
        for(i = 0; i < countOfFilesInFileList && same; ++i)
        {
            nsCOMPtr<nsILocalFile> file;
            aFileList->QueryElementAt(i, NS_GET_IID(nsILocalFile), getter_AddRefs(file));
            NS_ASSERTION(file, "loser!");

            PRInt64 size;
            PRInt64 date;
            nsCAutoString name;
            PRUint32 directory;

            if(NS_FAILED(file->GetFileSize(&size)) ||
               NS_FAILED(file->GetLastModifiedTime(&date)) ||
               NS_FAILED(file->GetNativeLeafName(name)) ||
               !aWorkingSet->FindDirectoryOfFile(file, &directory))
            {
                NS_ERROR("unexpected!");
                return FULL_VALIDATION_REQUIRED;
            }    

            for(k = 0; k < countOfFilesInWorkingSet; ++k)
            {
                xptiFile& target = aWorkingSet->GetFileAt(k);
                
                if(directory == target.GetDirectory() &&
                   name.Equals(target.GetName()))
                {
                    if(nsInt64(size) != target.GetSize() ||
                       nsInt64(date) != target.GetDate())
                        same = PR_FALSE;
                    break;        
                }
            }
            // failed to find our file in the workingset?
            if(k == countOfFilesInWorkingSet)
                same = PR_FALSE;
        }
        if(same)
            return NO_FILES_CHANGED;
    }
    else if(countOfFilesInFileList > countOfFilesInWorkingSet)
    {
        // try to determine if the only changes are additional new files
        // XXX Wimping out and doing this as a separate walk through the lists.

        PRBool same = PR_TRUE;

        for(i = 0; i < countOfFilesInWorkingSet && same; ++i)
        {
            xptiFile& target = aWorkingSet->GetFileAt(i);
            
            for(k = 0; k < countOfFilesInFileList; ++k)
            {
                nsCOMPtr<nsILocalFile> file;
                aFileList->QueryElementAt(k, NS_GET_IID(nsILocalFile), getter_AddRefs(file));
                NS_ASSERTION(file, "loser!");
                
                nsCAutoString name;
                PRInt64 size;
                PRInt64 date;
                if(NS_FAILED(file->GetFileSize(&size)) ||
                   NS_FAILED(file->GetLastModifiedTime(&date)) ||
                   NS_FAILED(file->GetNativeLeafName(name)))
                {
                    NS_ERROR("unexpected!");
                    return FULL_VALIDATION_REQUIRED;
                }    
            
                PRBool sameName = name.Equals(target.GetName());
                if(sameName)
                {
                    if(nsInt64(size) != target.GetSize() ||
                       nsInt64(date) != target.GetDate())
                        same = PR_FALSE;
                    break;        
                }
            }
            // failed to find our file in the file list?
            if(k == countOfFilesInFileList)
                same = PR_FALSE;
        }
        if(same)
            return FILES_ADDED_ONLY;
    }

    return FULL_VALIDATION_REQUIRED; 
}

Here is the call graph for this function:

Definition at line 1031 of file xptiInterfaceInfoManager.cpp.

{
    nsILocalFile** orderedFileArray;
    PRUint32 countOfFilesInFileList;
    PRUint32 i;

    NS_ASSERTION(aFileList, "loser!");

    if(!aWorkingSet->IsValid())
        return PR_FALSE;

    if(NS_FAILED(aFileList->Count(&countOfFilesInFileList)))
        return PR_FALSE;

    if(!countOfFilesInFileList)
    {
        // maybe there are no xpt files to register.  
        // a minimal install would have this case.
        return PR_TRUE;
    }

    orderedFileArray = BuildOrderedFileArray(aSearchPath, aFileList, aWorkingSet);

    if(!orderedFileArray)
        return PR_FALSE;

    // DEBUG_DumpFileArray(orderedFileArray, countOfFilesInFileList);

    // Make space in aWorkingset for a new xptiFile array.

    if(!aWorkingSet->NewFileArray(countOfFilesInFileList))   
        return PR_FALSE;

    aWorkingSet->ClearZipItems();
    aWorkingSet->ClearHashTables();

    // For each file, add any valid interfaces that don't conflict with 
    // previous interfaces added.
    for(i = 0; i < countOfFilesInFileList; i++)
    {
        nsILocalFile* file = orderedFileArray[i];

        nsCAutoString name;
        PRInt64 size;
        PRInt64 date;
        PRUint32 dir;
        if(NS_FAILED(file->GetFileSize(&size)) ||
           NS_FAILED(file->GetLastModifiedTime(&date)) ||
           NS_FAILED(file->GetNativeLeafName(name)) ||
           !aWorkingSet->FindDirectoryOfFile(file, &dir))
        {
            return PR_FALSE;
        }    

        LOG_AUTOREG(("  finding interfaces in file: %s\n", name.get()));
    
        xptiFile fileRecord;
        fileRecord = xptiFile(nsInt64(size), nsInt64(date), dir,
                              name.get(), aWorkingSet);

//        printf("* found %s\n", fileRecord.GetName());


        if(xptiFileType::IsXPT(fileRecord.GetName()))
        {
            XPTHeader* header = ReadXPTFile(file, aWorkingSet);
            if(!header)
            {
                // XXX do something!
                NS_ERROR("Unable to read an XPT file, turn logging on to see which file");    
                LOG_AUTOREG(("      unable to read file\n"));
                continue;
            }
    
            xptiTypelib typelibRecord;
            typelibRecord.Init(aWorkingSet->GetFileCount());
    
            PRBool AddedFile = PR_FALSE;

            if(header->major_version >= XPT_MAJOR_INCOMPATIBLE_VERSION)
            {
                NS_ASSERTION(!header->num_interfaces,"bad libxpt");
                LOG_AUTOREG(("      file is version %d.%d  Type file of version %d.0 or higher can not be read.\n", (int)header->major_version, (int)header->minor_version, (int)XPT_MAJOR_INCOMPATIBLE_VERSION));
            }

            for(PRUint16 k = 0; k < header->num_interfaces; k++)
            {
                xptiInterfaceEntry* entry = nsnull;
    
                if(!VerifyAndAddEntryIfNew(aWorkingSet,
                                           header->interface_directory + k,
                                           typelibRecord,
                                           &entry))
                    return PR_FALSE;    
    
                if(!entry)
                    continue;
                
                // If this is the first interface we found for this file then
                // setup the fileRecord for the header and infos.
                if(!AddedFile)
                {
                    if(!fileRecord.SetHeader(header, aWorkingSet))
                    {
                        // XXX that would be bad.
                        return PR_FALSE;    
                    }
                    AddedFile = PR_TRUE;
                }
                fileRecord.GetGuts()->SetEntryAt(k, entry);
            }
            
            // This will correspond to typelibRecord above.
            aWorkingSet->AppendFile(fileRecord);
        }

        else
        {
            nsCOMPtr<nsIXPTLoader> loader =
                do_GetService(NS_ZIPLOADER_CONTRACTID);
            
            if (loader) {
                nsresult rv;
                
                nsCOMPtr<nsIXPTLoaderSink> sink =
                    new xptiZipLoaderSink(this, aWorkingSet);
                if (!sink)
                    return PR_FALSE;
                
                rv = loader->EnumerateEntries(file, sink);
                if (NS_FAILED(rv))
                    return PR_FALSE;
                // This will correspond to typelibRecord used in
                // xptiInterfaceInfoManager::FoundEntry.
                aWorkingSet->AppendFile(fileRecord);
            } else {
                NS_WARNING("Could not load XPT Zip loader");
            }
        }
    }
    return PR_TRUE;
}        

Here is the call graph for this function:

PRBool xptiInterfaceInfoManager::FoundZipEntry ( const char *  entryName,
int  index,
XPTHeader header,
xptiWorkingSet aWorkingSet 
) [private]

Definition at line 1197 of file xptiInterfaceInfoManager.cpp.

{

    NS_ASSERTION(entryName, "loser!");
    NS_ASSERTION(header, "loser!");
    NS_ASSERTION(aWorkingSet, "loser!");

    int countOfInterfacesAddedForItem = 0;
    xptiZipItem zipItemRecord(entryName, aWorkingSet);
    
    LOG_AUTOREG(("    finding interfaces in file: %s\n", entryName));

    if(header->major_version >= XPT_MAJOR_INCOMPATIBLE_VERSION)
    {
        NS_ASSERTION(!header->num_interfaces,"bad libxpt");
        LOG_AUTOREG(("      file is version %d.%d. Type file of version %d.0 or higher can not be read.\n", (int)header->major_version, (int)header->minor_version, (int)XPT_MAJOR_INCOMPATIBLE_VERSION));
    }

    if(!header->num_interfaces)
    {
        // We are not interested in files without interfaces.
        return PR_TRUE;
    }
    
    xptiTypelib typelibRecord;
    typelibRecord.Init(aWorkingSet->GetFileCount(),
                       aWorkingSet->GetZipItemCount());

    for(PRUint16 k = 0; k < header->num_interfaces; k++)
    {
        xptiInterfaceEntry* entry = nsnull;
    
        if(!VerifyAndAddEntryIfNew(aWorkingSet,
                                   header->interface_directory + k,
                                   typelibRecord,
                                   &entry))
            return PR_FALSE;    
    
        if(!entry)
            continue;

        // If this is the first interface we found for this item
        // then setup the zipItemRecord for the header and infos.
        if(!countOfInterfacesAddedForItem)
        {
            // XXX fix this!
            if(!zipItemRecord.SetHeader(header, aWorkingSet))
            {
                // XXX that would be bad.
                return PR_FALSE;    
            }
        }

        // zipItemRecord.GetGuts()->SetEntryAt(k, entry);
        ++countOfInterfacesAddedForItem;
    }   

    if(countOfInterfacesAddedForItem)
    {
        if(!aWorkingSet->GetZipItemFreeSpace())
        {
            if(!aWorkingSet->ExtendZipItemArray(
                aWorkingSet->GetZipItemCount() + 20))
            {        
                // out of space!
                return PR_FALSE;    
            }
        }
        aWorkingSet->AppendZipItem(zipItemRecord);
    } 
    return PR_TRUE;
}

Here is the call graph for this function:

Definition at line 101 of file xptiInterfaceInfoManager.cpp.

{
    if(gInterfaceInfoManager)
        gInterfaceInfoManager->LogStats();

    NS_IF_RELEASE(gInterfaceInfoManager);
}

Here is the caller graph for this function:

Definition at line 295 of file xptiInterfaceInfoManager.cpp.

{
    // We *trust* that this will not change!
    return NS_SUCCEEDED(GetDirectoryFromDirService(NS_XPCOM_CURRENT_PROCESS_DIR, aDir));
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 897 of file xptiprivate.h.

        {if(!self && !(self = GetInterfaceInfoManagerNoAddRef())) 
            return nsnull;
         return self->mAutoRegLock;}

Here is the call graph for this function:

Definition at line 280 of file xptiInterfaceInfoManager.cpp.

{
    // We *trust* that this will not change!
    nsCOMPtr<nsILocalFile> lf;
    nsresult rv = GetDirectoryFromDirService(NS_XPCOM_XPTI_REGISTRY_FILE, 
                                             getter_AddRefs(lf));

    if (NS_FAILED(rv)) return PR_FALSE;

    rv = xptiCloneLocalFile(lf, aFile);
    if (NS_FAILED(rv)) return PR_FALSE;
    return PR_TRUE;
}

Here is the call graph for this function:

Here is the caller graph for this function:

nsIIDPtr nsIInterfaceInfoManager::getIIDForName ( in string  name) [inherited]

Definition at line 902 of file xptiprivate.h.

        {if(!self && !(self = GetInterfaceInfoManagerNoAddRef())) 
            return nsnull;
         return self->mInfoMonitor;}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 59 of file xptiInterfaceInfoManager.cpp.

{
    if(!gInterfaceInfoManager)
    {
        nsCOMPtr<nsISupportsArray> searchPath;
        BuildFileSearchPath(getter_AddRefs(searchPath));
        if(!searchPath)
        {
            NS_ERROR("can't get xpt search path!");    
            return nsnull;
        }

        gInterfaceInfoManager = new xptiInterfaceInfoManager(searchPath);
        if(gInterfaceInfoManager)
            NS_ADDREF(gInterfaceInfoManager);
        if(!gInterfaceInfoManager->IsValid())
        {
            NS_RELEASE(gInterfaceInfoManager);
        }
        else
        {
            PRBool mustAutoReg = 
                    !xptiManifest::Read(gInterfaceInfoManager, 
                                        &gInterfaceInfoManager->mWorkingSet);
#ifdef DEBUG
            {
            // This sets what will be returned by GetOpenLogFile().
            xptiAutoLog autoLog(gInterfaceInfoManager, 
                                gInterfaceInfoManager->mAutoRegLogFile, PR_TRUE);
            LOG_AUTOREG(("debug build forced autoreg after %s load of manifest\n", mustAutoReg ? "FAILED" : "successful"));
        
            mustAutoReg = PR_TRUE;
            }
#endif // DEBUG
            if(mustAutoReg)
                gInterfaceInfoManager->AutoRegisterInterfaces();
        }
    }
    return gInterfaceInfoManager;
}

Here is the call graph for this function:

Here is the caller graph for this function:

string nsIInterfaceInfoManager::getNameForIID ( in nsIIDPtr  iid) [inherited]

Definition at line 879 of file xptiprivate.h.

{return mOpenLogFile;}

Here is the caller graph for this function:

Definition at line 892 of file xptiprivate.h.

        {if(!self && !(self = GetInterfaceInfoManagerNoAddRef())) 
            return nsnull;
         return self->mResolveLock;}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 889 of file xptiprivate.h.

        {NS_ADDREF(*aSearchPath = mSearchPath);}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 878 of file xptiprivate.h.

{return &mWorkingSet;}

Here is the caller graph for this function:

Definition at line 110 of file xptiInterfaceInfoManager.cpp.

Here is the call graph for this function:

PRBool xptiInterfaceInfoManager::LoadFile ( const xptiTypelib aTypelibRecord,
xptiWorkingSet aWorkingSet = nsnull 
)

Definition at line 438 of file xptiInterfaceInfoManager.cpp.

{
    if(!aWorkingSet)
        aWorkingSet = &mWorkingSet;

    if(!aWorkingSet->IsValid())
        return PR_FALSE;

    xptiFile* fileRecord = &aWorkingSet->GetFileAt(aTypelibRecord.GetFileIndex());
    xptiZipItem* zipItem = nsnull;

    nsCOMPtr<nsILocalFile> file;
    if(NS_FAILED(aWorkingSet->GetCloneOfDirectoryAt(fileRecord->GetDirectory(),
                                    getter_AddRefs(file))) || !file)
        return PR_FALSE;

    if(NS_FAILED(file->AppendNative(nsDependentCString(fileRecord->GetName()))))
        return PR_FALSE;

    XPTHeader* header;

    if(aTypelibRecord.IsZip())
    {
        zipItem = &aWorkingSet->GetZipItemAt(aTypelibRecord.GetZipItemIndex());
        
        // See the big comment below in the 'non-zip' case...
        if(zipItem->GetGuts())
        {
            NS_ERROR("Trying to load an xpt file from a zip twice");    
            
            // Force an autoreg on next run
            (void) xptiManifest::Delete(this);

            return PR_FALSE;
        }
        
        LOG_LOAD(("# loading zip item %s::%s\n", fileRecord->GetName(), zipItem->GetName()));
        
        nsCOMPtr<nsIXPTLoader> loader =
            do_GetService(NS_ZIPLOADER_CONTRACTID);

        if (loader) {
            nsresult rv;
            
            nsCOMPtr<nsIInputStream> stream;
            rv = loader->LoadEntry(file, zipItem->GetName(),
                                   getter_AddRefs(stream));

            if (NS_FAILED(rv))
                return PR_FALSE;
            
            header =
                xptiZipLoader::ReadXPTFileFromInputStream(stream, aWorkingSet);
        } else {
            header = nsnull;
            NS_WARNING("Could not load XPT Zip loader");
        }
    } 
    else
    {
        // The file would only have guts already if we previously failed to 
        // find an interface info in a file where the manifest claimed it was 
        // going to be. 
        //
        // Normally, when the file gets loaded (and the guts set) then all 
        // interfaces would also be resolved. So, if we are here again for
        // the same file then there must have been some interface that was 
        // expected but not present. Now we are explicitly trying to find it
        // and it isn't going to be there this time either.
        //
        // This is an assertion style error in a DEBUG build because it shows 
        // that we failed to detect this in autoreg. For release builds (where
        // autoreg is not run on every startup) it is just bad. But by returning
        // PR_FALSE we mark this interface as RESOLVE_FAILED and get on with 
        // things without crashing or anything.
        //
        // We don't want to do an autoreg here because this is too much of an 
        // edge case (and in that odd case it might autoreg multiple times if
        // many interfaces had been removed). But, by deleting the manifest we 
        // force the system to get it right on the next run.
        
        if(fileRecord->GetGuts())
        {
            NS_ERROR("Trying to load an xpt file twice");    
            
            // Force an autoreg on next run
            (void) xptiManifest::Delete(this);

            return PR_FALSE;
        }

        LOG_LOAD(("^ loading file %s\n", fileRecord->GetName()));
        header = ReadXPTFile(file, aWorkingSet);
    } 

    if(!header)
        return PR_FALSE;


    if(aTypelibRecord.IsZip())
    {
        // This also allocs zipItem.GetGuts() used below.
        if(!zipItem->SetHeader(header, aWorkingSet))
            return PR_FALSE;
    }
    else
    {
        // This also allocs fileRecord.GetGuts() used below.
        if(!fileRecord->SetHeader(header, aWorkingSet))
            return PR_FALSE;
    }

    // For each interface in the header we want to find the xptiInterfaceInfo
    // object and set its resolution info.

    for(PRUint16 i = 0; i < header->num_interfaces; i++)
    {
        static const nsID zeroIID =
            { 0x0, 0x0, 0x0, { 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0, 0x0 } };

        XPTInterfaceDirectoryEntry* iface = header->interface_directory + i;
        
        xptiHashEntry* hashEntry;

        if(!iface->iid.Equals(zeroIID))
        {
            hashEntry = (xptiHashEntry*)
                PL_DHashTableOperate(aWorkingSet->mIIDTable, 
                                     &iface->iid, PL_DHASH_LOOKUP);
        }
        else
        {
            hashEntry = (xptiHashEntry*)
                PL_DHashTableOperate(aWorkingSet->mNameTable, 
                                     iface->name, PL_DHASH_LOOKUP);
        }

        xptiInterfaceEntry* entry = 
            PL_DHASH_ENTRY_IS_FREE(hashEntry) ? nsnull : hashEntry->value;

        if(!entry)
        {
            // This one is just not resolved anywhere!
            continue;    
        }

        if(aTypelibRecord.IsZip())
            zipItem->GetGuts()->SetEntryAt(i, entry);
        else
            fileRecord->GetGuts()->SetEntryAt(i, entry);

        XPTInterfaceDescriptor* descriptor = iface->interface_descriptor;

        if(descriptor && aTypelibRecord.Equals(entry->GetTypelibRecord()))
            entry->PartiallyResolveLocked(descriptor, aWorkingSet);
    }
    return PR_TRUE;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 1658 of file xptiInterfaceInfoManager.cpp.

{
    PRUint32 i;
    
    // This sets what will be returned by GetOpenLogFile().
    xptiAutoLog autoLog(this, mStatsLogFile, PR_FALSE);

    PRFileDesc* fd = GetOpenLogFile();
    if(!fd)
        return;

    // Show names of xpt (only) files from which at least one interface 
    // was resolved.

    PRUint32 fileCount = mWorkingSet.GetFileCount();
    for(i = 0; i < fileCount; ++i)
    {
        xptiFile& f = mWorkingSet.GetFileAt(i);
        if(f.GetGuts())
            PR_fprintf(fd, "xpti used file: %s\n", f.GetName());
    }

    PR_fprintf(fd, "\n");

    // Show names of xptfiles loaded from zips from which at least 
    // one interface was resolved.

    PRUint32 zipItemCount = mWorkingSet.GetZipItemCount();
    for(i = 0; i < zipItemCount; ++i)
    {
        xptiZipItem& zi = mWorkingSet.GetZipItemAt(i);
        if(zi.GetGuts())                           
            PR_fprintf(fd, "xpti used file from zip: %s\n", zi.GetName());
    }

    PR_fprintf(fd, "\n");

    // Show name of each interface that was fully resolved and the name
    // of the file and (perhaps) zip from which it was loaded.

    PL_DHashTableEnumerate(mWorkingSet.mNameTable, 
                           xpti_ResolvedFileNameLogger, this);

} 

Here is the call graph for this function:

PRBool xptiInterfaceInfoManager::MergeWorkingSets ( xptiWorkingSet aDestWorkingSet,
xptiWorkingSet aSrcWorkingSet 
) [private]

Definition at line 1432 of file xptiInterfaceInfoManager.cpp.

{

    PRUint32 i;

    // Combine file lists.

    PRUint32 originalFileCount = aDestWorkingSet->GetFileCount();
    PRUint32 additionalFileCount = aSrcWorkingSet->GetFileCount();

    // Create a new array big enough to hold both lists and copy existing files

    if(additionalFileCount)
    {
        if(!aDestWorkingSet->ExtendFileArray(originalFileCount +
                                             additionalFileCount))
            return PR_FALSE;
    
        // Now we are where we started, but we know we have enough space.
    
        // Prepare offset array for later fixups. 
        // NOTE: Storing with dest, but alloc'ing from src. This is intentional.
        aDestWorkingSet->mFileMergeOffsetMap = (PRUint32*)
            XPT_CALLOC(aSrcWorkingSet->GetStructArena(),
                       additionalFileCount * sizeof(PRUint32)); 
        if(!aDestWorkingSet->mFileMergeOffsetMap)
            return PR_FALSE;
    }

    for(i = 0; i < additionalFileCount; ++i)
    {
        xptiFile& srcFile = aSrcWorkingSet->GetFileAt(i);
        PRUint32 k;
        for(k = 0; k < originalFileCount; ++k)
        {
            // If file (with same name, date, and time) is in both lists
            // then reuse that record.
            xptiFile& destFile = aDestWorkingSet->GetFileAt(k);
            if(srcFile.Equals(destFile))
            {
                aDestWorkingSet->mFileMergeOffsetMap[i] = k - i;
                break;    
            }
        }
        if(k == originalFileCount)
        {
            // No match found, tack it on the end.

            PRUint32 newIndex = aDestWorkingSet->GetFileCount();

            aDestWorkingSet->AppendFile(xptiFile(srcFile, aDestWorkingSet));

            // Fixup the merge offset map.
            aDestWorkingSet->mFileMergeOffsetMap[i] = newIndex - i;
        }
    }

    // Combine ZipItem lists.

    PRUint32 originalZipItemCount = aDestWorkingSet->GetZipItemCount();
    PRUint32 additionalZipItemCount = aSrcWorkingSet->GetZipItemCount();

    // Create a new array big enough to hold both lists and copy existing ZipItems

    if(additionalZipItemCount)
    {
        if(!aDestWorkingSet->ExtendZipItemArray(originalZipItemCount +
                                                additionalZipItemCount))
            return PR_FALSE;
    
        // Now we are where we started, but we know we have enough space.
    
        // Prepare offset array for later fixups. 
        // NOTE: Storing with dest, but alloc'ing from src. This is intentional.
        aDestWorkingSet->mZipItemMergeOffsetMap = (PRUint32*)
            XPT_CALLOC(aSrcWorkingSet->GetStructArena(),
                       additionalZipItemCount * sizeof(PRUint32)); 
        if(!aDestWorkingSet->mZipItemMergeOffsetMap)
            return PR_FALSE;
    }

    for(i = 0; i < additionalZipItemCount; ++i)
    {
        xptiZipItem& srcZipItem = aSrcWorkingSet->GetZipItemAt(i);
        PRUint32 k;
        for(k = 0; k < originalZipItemCount; ++k)
        {
            // If ZipItem (with same name) is in both lists
            // then reuse that record.
            xptiZipItem& destZipItem = aDestWorkingSet->GetZipItemAt(k);
            if(srcZipItem.Equals(destZipItem))
            {
                aDestWorkingSet->mZipItemMergeOffsetMap[i] = k - i;
                break;    
            }
        }
        if(k == originalZipItemCount)
        {
            // No match found, tack it on the end.

            PRUint32 newIndex = aDestWorkingSet->GetZipItemCount();

            aDestWorkingSet->AppendZipItem(
                    xptiZipItem(srcZipItem, aDestWorkingSet));

            // Fixup the merge offset map.
            aDestWorkingSet->mZipItemMergeOffsetMap[i] = newIndex - i;
        }
    }

    // Migrate xptiInterfaceInfos

    TwoWorkingSets sets(aSrcWorkingSet, aDestWorkingSet);

    PL_DHashTableEnumerate(aSrcWorkingSet->mNameTable, xpti_Merger, &sets);

    return PR_TRUE;
}        

Here is the call graph for this function:

XPTHeader * xptiInterfaceInfoManager::ReadXPTFile ( nsILocalFile aFile,
xptiWorkingSet aWorkingSet 
) [private]

Definition at line 368 of file xptiInterfaceInfoManager.cpp.

{
    NS_ASSERTION(aFile, "loser!");

    XPTHeader *header = nsnull;
    char *whole = nsnull;
    PRFileDesc*   fd = nsnull;
    XPTState *state = nsnull;
    XPTCursor cursor;
    PRInt32 flen;
    PRInt64 fileSize;
    
    PRBool saveFollowLinks;
    aFile->GetFollowLinks(&saveFollowLinks);
    aFile->SetFollowLinks(PR_TRUE);

    if(NS_FAILED(aFile->GetFileSize(&fileSize)) || !(flen = nsInt64(fileSize)))
    {
        aFile->SetFollowLinks(saveFollowLinks);
        return nsnull;
    }

    whole = new char[flen];
    if (!whole)
    {
        aFile->SetFollowLinks(saveFollowLinks);
        return nsnull;
    }

    // all exits from on here should be via 'goto out' 

    if(NS_FAILED(aFile->OpenNSPRFileDesc(PR_RDONLY, 0444, &fd)) || !fd)
    {
        goto out;
    }

    if(flen > PR_Read(fd, whole, flen))
    {
        goto out;
    }

    if(!(state = XPT_NewXDRState(XPT_DECODE, whole, flen)))
    {
        goto out;
    }
    
    if(!XPT_MakeCursor(state, XPT_HEADER, 0, &cursor))
    {
        goto out;
    }
    
    if (!XPT_DoHeader(aWorkingSet->GetStructArena(), &cursor, &header))
    {
        header = nsnull;
        goto out;
    }

 out:
    if(fd)
        PR_Close(fd);
    if(state)
        XPT_DestroyXDRState(state);
    if(whole)
        delete [] whole;
    aFile->SetFollowLinks(saveFollowLinks);
    return header;
}

Here is the call graph for this function:

Here is the caller graph for this function:

Definition at line 880 of file xptiprivate.h.

        {PRFileDesc* temp = mOpenLogFile; mOpenLogFile = fd; return temp;}

Here is the caller graph for this function:

PRBool xptiInterfaceInfoManager::VerifyAndAddEntryIfNew ( xptiWorkingSet aWorkingSet,
XPTInterfaceDirectoryEntry iface,
const xptiTypelib typelibRecord,
xptiInterfaceEntry **  entryAdded 
) [private]

Definition at line 1274 of file xptiInterfaceInfoManager.cpp.

{
    NS_ASSERTION(iface, "loser!");
    NS_ASSERTION(entryAdded, "loser!");

    *entryAdded = nsnull;

    if(!iface->interface_descriptor)
    {
        // Not resolved, ignore this one.
        // XXX full logging might note this...
        return PR_TRUE;
    }
    
    xptiHashEntry* hashEntry = (xptiHashEntry*)
        PL_DHashTableOperate(aWorkingSet->mIIDTable, &iface->iid, PL_DHASH_LOOKUP);

    xptiInterfaceEntry* entry = 
        PL_DHASH_ENTRY_IS_FREE(hashEntry) ? nsnull : hashEntry->value;
    
    if(entry)
    {
        // XXX validate this info to find possible inconsistencies
        LOG_AUTOREG(("      ignoring repeated interface: %s\n", iface->name));
        return PR_TRUE;
    }
    
    // Build a new xptiInterfaceEntry object and hook it up. 

    entry = xptiInterfaceEntry::NewEntry(iface->name, strlen(iface->name),
                                         iface->iid,
                                         typelibRecord, aWorkingSet);
    if(!entry)
    {
        // XXX bad!
        return PR_FALSE;    
    }

    //XXX  We should SetHeader too as part of the validation, no?
    entry->SetScriptableFlag(XPT_ID_IS_SCRIPTABLE(iface->interface_descriptor->flags));

    // Add our entry to the iid hashtable.

    hashEntry = (xptiHashEntry*)
        PL_DHashTableOperate(aWorkingSet->mNameTable, 
                             entry->GetTheName(), PL_DHASH_ADD);
    if(hashEntry)
        hashEntry->value = entry;
    
    // Add our entry to the name hashtable.

    hashEntry = (xptiHashEntry*)
        PL_DHashTableOperate(aWorkingSet->mIIDTable, 
                             entry->GetTheIID(), PL_DHASH_ADD);
    if(hashEntry)
        hashEntry->value = entry;
    
    *entryAdded = entry;

    LOG_AUTOREG(("      added interface: %s\n", iface->name));

    return PR_TRUE;
}

Here is the call graph for this function:

Here is the caller graph for this function:

void xptiInterfaceInfoManager::WriteToLog ( const char *  fmt,
  ... 
) [static]

Definition at line 1610 of file xptiInterfaceInfoManager.cpp.

{
    if(!gInterfaceInfoManager)
        return;

    PRFileDesc* fd = gInterfaceInfoManager->GetOpenLogFile();
    if(fd)
    {
        va_list ap;
        va_start(ap, fmt);
        PR_vfprintf(fd, fmt, ap);
        va_end(ap);
    }
}        

Member Data Documentation

Definition at line 968 of file xptiprivate.h.

Definition at line 967 of file xptiprivate.h.

Definition at line 965 of file xptiprivate.h.

Definition at line 962 of file xptiprivate.h.

Definition at line 966 of file xptiprivate.h.

Definition at line 963 of file xptiprivate.h.

Definition at line 964 of file xptiprivate.h.

Definition at line 969 of file xptiprivate.h.

Definition at line 961 of file xptiprivate.h.

Definition at line 960 of file xptiprivate.h.


The documentation for this class was generated from the following files: