if (PREF_NOERROR == pPref->CreateChildList("ldap_1", &oldChildren))
PRUint32 prefCount; err = pPref->GetChildList("ldap_1", &prefCount, &oldChildren); if (NS_SUCCEEDED(err))
nsresult DIR_GetServerPreferences(nsVoidArray** list){    nsresult err = NS_OK;    nsCOMPtr<nsIPref> pPref(do_GetService(NS_PREF_CONTRACTID, &err));     if (NS_FAILED(err) || !pPref) 		return NS_ERROR_FAILURE;	PRInt32 position = 1;	PRInt32 version = -1;	char *oldChildren = nsnull;	PRBool savePrefs = PR_FALSE;	PRBool migrating = PR_FALSE;	nsVoidArray *oldList = nsnull;	nsVoidArray *obsoleteList = nsnull;	nsVoidArray *newList = nsnull;	PRInt32 i, j, count;	/* Update the ldap list version and see if there are old prefs to migrate. */	if (pPref->GetIntPref(PREF_LDAP_VERSION_NAME, &version) == PREF_NOERROR)	{		if (version < kPreviousListVersion)		{			pPref->SetIntPref(PREF_LDAP_VERSION_NAME, kCurrentListVersion);			/* Look to see if there's an old-style "ldap_1" tree in prefs */			if (PREF_NOERROR == pPref->CreateChildList("ldap_1", &oldChildren))			{				if (PL_strlen(oldChildren))				{					migrating = PR_TRUE;					position = dir_GetPrefsFrom40Branch(&oldList);				}				PR_Free(oldChildren);			}		}	}	/* Find the new-style "ldap_2.servers" tree in prefs */	err = dir_GetPrefsFrom45Branch(&newList, migrating ? &obsoleteList : nsnull);	/* Merge the new tree onto the old tree, old on top, new at bottom */	if (NS_SUCCEEDED(err) && oldList && newList)	{		DIR_Server *newServer;		/* Walk through the new list looking for servers that are duplicates of		 * ones in the old list.  Mark any duplicates for non-inclusion in the		 * final list.		 */		PRInt32 newCount = newList->Count();		for (i = 0; i < newCount; i++)		{			newServer = (DIR_Server *)newList->ElementAt(i);			if (nsnull != newServer)			{				DIR_Server *oldServer;				PRInt32 oldCount = oldList->Count();				for (j = 0; j < oldCount; j++)				{					oldServer = (DIR_Server *)oldList->ElementAt(j);					if (nsnull != oldServer)					{						/* Don't add servers which are in the old list and don't add a						 * second personal address book.						 */						if (   dir_AreServersSame(newServer, oldServer, PR_FALSE)							|| (   oldServer->dirType == PABDirectory								&& newServer->dirType == PABDirectory								&& oldServer->isOffline == PR_FALSE								&& newServer->isOffline == PR_FALSE))						{							/* Copy any new prefs out of the new server.							 */							PR_FREEIF(oldServer->prefName);                            oldServer->prefName  = nsCRT::strdup(newServer->prefName);							/* since the pref name has now been set, we can generate a proper							   file name in case we don't have one already */							if (!oldServer->fileName || !*oldServer->fileName)								DIR_SetServerFileName(oldServer, nsnull); 															oldServer->flags     = newServer->flags;							/* Mark the new version of the server as one not to be moved							 * to the final list.							 */							newServer->position = 0;							break;						}					}				}			}		}		/* Walk throught the new list again.  This time delete duplicates and		 * move the rest to the old (final) list.		 */		count = newList->Count();		for (i = count - 1; i >= 0; i--)		{			newServer = (DIR_Server *)newList->ElementAt(i);			if (!dir_IsServerDeleted(newServer))			{				/* Make sure new servers are placed after old servers, but				 * keep them in relative order.				 */				if (!DIR_TestFlag(newServer, DIR_POSITION_LOCKED))				{					/* The server at position 2 (i.e. Netcenter) must be left					 * at position 2.					 */					if (newServer->position > 2) 						newServer->position += position;				}				oldList->AppendElement(newServer);			}			else			{				DIR_DecrementServerRefCount(newServer);			}		}		newList->Clear();		DIR_DeleteServerList(newList);		*list = oldList;		savePrefs = PR_TRUE;	}	else		*list = newList;	/* Remove any obsolete servers from the list.	 * Note that we only remove obsolete servers when we are migrating.  We	 * don't do it otherwise because that would keep users from manually	 * re-adding these servers (which they should be allowed to do).	 */	if (NS_SUCCEEDED(err) && obsoleteList)	{		DIR_Server *obsoleteServer;		nsVoidArray *walkObsoleteList = obsoleteList;				count = walkObsoleteList->Count();		for (i = 0; i < count;i++)		{			if (nsnull != (obsoleteServer = (DIR_Server *)walkObsoleteList->ElementAt(i)))			{				DIR_Server *existingServer;				nsVoidArray *walkExistingList = *list;				PRInt32 existCount = walkExistingList->Count();				for (j = 0; j < existCount;j++)				{					existingServer = (DIR_Server *)walkExistingList->ElementAt(j);					if (nsnull != existingServer)					{						if (dir_AreServersSame(existingServer, obsoleteServer, PR_FALSE))						{							savePrefs = PR_TRUE;							DIR_DecrementServerRefCount(existingServer);							(*list)->RemoveElement(existingServer);							break;						}					}				}			}		}	}	if (obsoleteList)		DIR_DeleteServerList(obsoleteList);	if (version < kCurrentListVersion)	{		pPref->SetIntPref(PREF_LDAP_VERSION_NAME, kCurrentListVersion);		// see if we have the ab upgrader.  if so, skip this, since we		// will be migrating.		nsresult rv;		nsCOMPtr <nsIAbUpgrader> abUpgrader = do_GetService(NS_AB4xUPGRADER_CONTRACTID, &rv);  		if (NS_FAILED(rv) || !abUpgrader) {      // if we can upgrade, don't touch the 4.x pab.      // if we can't, move the 4.x pab aside			dir_ConvertToMabFileName();		}	}	/* Write the merged list so we get it next time we ask */	if (savePrefs)		DIR_SaveServerPreferences(*list);	return err;}