mirror of
https://github.com/rn10950/RetroZilla.git
synced 2024-11-15 04:00:12 +01:00
1021 lines
41 KiB
C++
1021 lines
41 KiB
C++
|
/* ***** BEGIN LICENSE BLOCK *****
|
||
|
* Version: MPL 1.1/GPL 2.0/LGPL 2.1
|
||
|
*
|
||
|
* The contents of this file are subject to the Mozilla Public License Version
|
||
|
* 1.1 (the "License"); you may not use this file except in compliance with
|
||
|
* the License. You may obtain a copy of the License at
|
||
|
* http://www.mozilla.org/MPL/
|
||
|
*
|
||
|
* Software distributed under the License is distributed on an "AS IS" basis,
|
||
|
* WITHOUT WARRANTY OF ANY KIND, either express or implied. See the License
|
||
|
* for the specific language governing rights and limitations under the
|
||
|
* License.
|
||
|
*
|
||
|
* The Original Code is mozilla.org code.
|
||
|
*
|
||
|
* The Initial Developer of the Original Code is
|
||
|
* Netscape Communications Corporation
|
||
|
*
|
||
|
* Portions created by the Initial Developer are Copyright (C) 2002
|
||
|
* the Initial Developer. All Rights Reserved.
|
||
|
*
|
||
|
* Contributor(s):
|
||
|
* Rajiv Dayal <rdayal@netscape.com>
|
||
|
*
|
||
|
* Alternatively, the contents of this file may be used under the terms of
|
||
|
* either the GNU General Public License Version 2 or later (the "GPL"), or
|
||
|
* the GNU Lesser General Public License Version 2.1 or later (the "LGPL"),
|
||
|
* in which case the provisions of the GPL or the LGPL are applicable instead
|
||
|
* of those above. If you wish to allow use of your version of this file only
|
||
|
* under the terms of either the GPL or the LGPL, and not to allow others to
|
||
|
* use your version of this file under the terms of the MPL, indicate your
|
||
|
* decision by deleting the provisions above and replace them with the notice
|
||
|
* and other provisions required by the GPL or the LGPL. If you do not delete
|
||
|
* the provisions above, a recipient may use your version of this file under
|
||
|
* the terms of any one of the MPL, the GPL or the LGPL.
|
||
|
*
|
||
|
* ***** END LICENSE BLOCK ***** */
|
||
|
|
||
|
#include <windows.h>
|
||
|
#include "syncmgr.h"
|
||
|
#include <tchar.h>
|
||
|
#include <time.h>
|
||
|
#include <stdlib.h>
|
||
|
#include <stdio.h>
|
||
|
|
||
|
#include "CondAPI.h"
|
||
|
#include "hslog.h"
|
||
|
#include "MozABConduitSync.h"
|
||
|
#include "MozABConduitRecord.h"
|
||
|
|
||
|
|
||
|
#define MAX_PROD_ID_TEXT 255
|
||
|
#define PERSONAL "Personal"
|
||
|
|
||
|
// Global var
|
||
|
FILE *gFD = NULL; // logging.
|
||
|
|
||
|
CMozABConduitSync::CMozABConduitSync(CSyncProperties& rProps)
|
||
|
{
|
||
|
m_dbHH = NULL;
|
||
|
m_dbPC = NULL;
|
||
|
m_remoteDB = NULL;
|
||
|
m_TotRemoteDBs = rProps.m_nRemoteCount; // Fixed 3/25/99 KRM
|
||
|
m_ConduitHandle = (CONDHANDLE)0;
|
||
|
memcpy(&m_rSyncProperties, &rProps, sizeof(m_rSyncProperties));
|
||
|
memset(&m_SystemInfo, 0, sizeof(m_SystemInfo));
|
||
|
|
||
|
// See if logging is turned on (ie, check env variable "MOZ_CONDUIT_LOG"
|
||
|
// for a logfile like "c:\\temp\\conduitlog.txt").
|
||
|
char *envVar = getenv(ENV_VAR_CONDUTI_LOG);
|
||
|
if(envVar != NULL )
|
||
|
gFD = fopen(envVar, "a+");
|
||
|
}
|
||
|
|
||
|
CMozABConduitSync::~CMozABConduitSync()
|
||
|
{
|
||
|
long retval;
|
||
|
|
||
|
if (m_SystemInfo.m_ProductIdText) {
|
||
|
delete m_SystemInfo.m_ProductIdText;
|
||
|
m_SystemInfo.m_ProductIdText = NULL;
|
||
|
m_SystemInfo.m_AllocedLen = 0;
|
||
|
}
|
||
|
if ((!m_rSyncProperties.m_RemoteDbList) && (m_remoteDB)) {
|
||
|
delete m_remoteDB;
|
||
|
m_remoteDB = NULL;
|
||
|
}
|
||
|
if (m_ConduitHandle) {
|
||
|
retval = SyncUnRegisterConduit(m_ConduitHandle);
|
||
|
m_ConduitHandle = 0;
|
||
|
}
|
||
|
|
||
|
if (gFD)
|
||
|
fclose(gFD);
|
||
|
}
|
||
|
|
||
|
long CMozABConduitSync::Perform(void)
|
||
|
{
|
||
|
long retval = 0;
|
||
|
|
||
|
// Log the start time.
|
||
|
time_t ltime;
|
||
|
time( <ime );
|
||
|
CONDUIT_LOG1(gFD, "\n------------ START OF PALM SYNC ------------ at %s", ctime(<ime));
|
||
|
|
||
|
if (m_rSyncProperties.m_SyncType > eProfileInstall)
|
||
|
return GEN_ERR_BAD_SYNC_TYPE;
|
||
|
|
||
|
if (m_rSyncProperties.m_SyncType == eDoNothing) {
|
||
|
return 0;
|
||
|
}
|
||
|
|
||
|
// Obtain System Information
|
||
|
m_SystemInfo.m_ProductIdText = (BYTE*) new char [MAX_PROD_ID_TEXT]; //deleted in d'ctor
|
||
|
if (!m_SystemInfo.m_ProductIdText)
|
||
|
return GEN_ERR_LOW_MEMORY;
|
||
|
|
||
|
m_SystemInfo.m_AllocedLen = (BYTE) MAX_PROD_ID_TEXT;
|
||
|
retval = SyncReadSystemInfo(m_SystemInfo);
|
||
|
if (retval)
|
||
|
return retval;
|
||
|
|
||
|
// Register this conduit with SyncMgr.DLL for communication to HH
|
||
|
retval = SyncRegisterConduit(m_ConduitHandle);
|
||
|
if (retval) {
|
||
|
CONDUIT_LOG0(gFD, "Failed SyncRegisterConduit.\n");
|
||
|
return retval;
|
||
|
}
|
||
|
|
||
|
for (int iCount=0; iCount < m_TotRemoteDBs && !retval; iCount++) {
|
||
|
retval = GetRemoteDBInfo(iCount);
|
||
|
if (retval) {
|
||
|
retval = 0;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
m_dbHH = new MozABHHManager(GENERIC_FLAG_APPINFO_SUPPORTED | GENERIC_FLAG_CATEGORY_SUPPORTED,
|
||
|
m_remoteDB->m_Name,
|
||
|
m_remoteDB->m_Creator,
|
||
|
m_remoteDB->m_DbType,
|
||
|
m_remoteDB->m_DbFlags,
|
||
|
0,
|
||
|
m_remoteDB->m_CardNum,
|
||
|
m_rSyncProperties.m_SyncType);
|
||
|
if(!m_dbHH) {
|
||
|
CONDUIT_LOG0(gFD, "Failed dbHH.\n");
|
||
|
return GEN_ERR_LOW_MEMORY;
|
||
|
}
|
||
|
|
||
|
m_dbPC = new MozABPCManager();
|
||
|
if(!m_dbPC) {
|
||
|
if (m_dbHH)
|
||
|
delete m_dbHH;
|
||
|
m_dbHH = NULL;
|
||
|
CONDUIT_LOG0(gFD, "Failed dbPC.\n");
|
||
|
return GEN_ERR_LOW_MEMORY;
|
||
|
}
|
||
|
|
||
|
char conduitName[32];
|
||
|
GetConduitName(conduitName, 32);
|
||
|
LogAddFormattedEntry(slSyncStarted, FALSE, "SYNC %s", conduitName);
|
||
|
CONDUIT_LOG1(gFD, "slSyncStarted. SyncType=%d\n", m_rSyncProperties.m_SyncType);
|
||
|
|
||
|
switch (m_rSyncProperties.m_SyncType) {
|
||
|
case eFast:
|
||
|
retval = PerformFastSync();
|
||
|
if ((retval) && (retval == GEN_ERR_CHANGE_SYNC_MODE)){
|
||
|
if (m_rSyncProperties.m_SyncType == eHHtoPC)
|
||
|
retval = CopyHHtoPC();
|
||
|
else if (m_rSyncProperties.m_SyncType == ePCtoHH)
|
||
|
retval = CopyPCtoHH();
|
||
|
}
|
||
|
break;
|
||
|
case eSlow:
|
||
|
retval = PerformSlowSync();
|
||
|
if ((retval) && (retval == GEN_ERR_CHANGE_SYNC_MODE)){
|
||
|
if (m_rSyncProperties.m_SyncType == eHHtoPC)
|
||
|
retval = CopyHHtoPC();
|
||
|
else if (m_rSyncProperties.m_SyncType == ePCtoHH)
|
||
|
retval = CopyPCtoHH();
|
||
|
}
|
||
|
break;
|
||
|
case eHHtoPC:
|
||
|
case eBackup:
|
||
|
retval = CopyHHtoPC();
|
||
|
break;
|
||
|
case eInstall:
|
||
|
case ePCtoHH:
|
||
|
case eProfileInstall:
|
||
|
retval = CopyPCtoHH();
|
||
|
break;
|
||
|
case eDoNothing:
|
||
|
break;
|
||
|
default:
|
||
|
retval = GEN_ERR_SYNC_TYPE_NOT_SUPPORTED;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
if (retval) {
|
||
|
LogAddFormattedEntry(slSyncAborted, FALSE, "retval=%d %s\n", retval, conduitName);
|
||
|
CONDUIT_LOG1(gFD, "Sync finished with errors retval=%d\n", retval);
|
||
|
}
|
||
|
else {
|
||
|
LogAddFormattedEntry(slSyncFinished, FALSE, "%s", conduitName);
|
||
|
CONDUIT_LOG0(gFD, "Sync Finished retval=0\n");
|
||
|
}
|
||
|
|
||
|
// remove the handheld and PC manager
|
||
|
if (m_dbHH)
|
||
|
delete m_dbHH;
|
||
|
m_dbHH = NULL;
|
||
|
if (m_dbPC)
|
||
|
delete m_dbPC;
|
||
|
m_dbPC = NULL;
|
||
|
}
|
||
|
|
||
|
// Log the end time.
|
||
|
time( <ime );
|
||
|
CONDUIT_LOG1(gFD, "------------ END OF PALM SYNC -------------- at %s\n", ctime(<ime));
|
||
|
|
||
|
// Unregister the conduit
|
||
|
long retval2 = 0;
|
||
|
if (m_ConduitHandle) {
|
||
|
retval2 = SyncUnRegisterConduit(m_ConduitHandle);
|
||
|
m_ConduitHandle = 0;
|
||
|
}
|
||
|
|
||
|
if (!retval)
|
||
|
return retval2;
|
||
|
|
||
|
return retval;
|
||
|
}
|
||
|
|
||
|
long CMozABConduitSync::GetRemoteDBInfo(int iIndex)
|
||
|
{
|
||
|
long retval = 0;
|
||
|
if (m_rSyncProperties.m_RemoteDbList) {
|
||
|
m_remoteDB = m_rSyncProperties.m_RemoteDbList[iIndex];
|
||
|
} else {
|
||
|
if (m_remoteDB)
|
||
|
delete m_remoteDB;
|
||
|
|
||
|
m_remoteDB = new CDbList; // deleted in d'ctor
|
||
|
if (m_remoteDB) {
|
||
|
m_remoteDB->m_Creator = m_rSyncProperties.m_Creator;
|
||
|
m_remoteDB->m_DbFlags = eRecord; // todo
|
||
|
m_remoteDB->m_DbType = m_rSyncProperties.m_DbType;
|
||
|
strncpy(m_remoteDB->m_Name, m_rSyncProperties.m_RemoteName[iIndex], sizeof(m_remoteDB->m_Name)-1);
|
||
|
m_remoteDB->m_Name[sizeof(m_remoteDB->m_Name)-1] = '\0';
|
||
|
m_remoteDB->m_Version = 0;
|
||
|
m_remoteDB->m_CardNum = 0;
|
||
|
m_remoteDB->m_ModNumber = 0;
|
||
|
m_remoteDB->m_CreateDate= 0;
|
||
|
m_remoteDB->m_ModDate = 0;
|
||
|
m_remoteDB->m_BackupDate= 0;
|
||
|
} else {
|
||
|
retval = GEN_ERR_LOW_MEMORY;
|
||
|
}
|
||
|
}
|
||
|
return retval;
|
||
|
}
|
||
|
|
||
|
BOOL CMozABConduitSync::CategoryNameMatches(CPString &catName, CPString &cutOffMozABName, BOOL isPAB)
|
||
|
{
|
||
|
if (!catName.CompareNoCase(cutOffMozABName.GetBuffer(0)))
|
||
|
return TRUE;
|
||
|
else
|
||
|
return (isPAB && !catName.CompareNoCase("Personal"));
|
||
|
}
|
||
|
|
||
|
BOOL CMozABConduitSync::CategoryExists(CPString &mozABName, BOOL isPAB)
|
||
|
{
|
||
|
CPCategory * pCategory = m_dbHH->GetFirstCategory();
|
||
|
// Palm only allows 15 chars for category names.
|
||
|
CPString cutOffName;
|
||
|
if (mozABName.Length() > 15)
|
||
|
cutOffName = mozABName.Left(15);
|
||
|
else
|
||
|
cutOffName = mozABName;
|
||
|
while (pCategory)
|
||
|
{
|
||
|
CPString catName(pCategory->GetName());
|
||
|
if (CategoryNameMatches(catName, cutOffName, isPAB))
|
||
|
return TRUE;
|
||
|
// Process next category
|
||
|
pCategory = m_dbHH->GetNextCategory();
|
||
|
}
|
||
|
return FALSE;
|
||
|
}
|
||
|
|
||
|
// this is done in separate thread since the main thread in this DLL
|
||
|
// needs to call SyncYieldCycles(1) atleast once every 7 seconds
|
||
|
DWORD WINAPI DoFastSync(LPVOID lpParameter)
|
||
|
{
|
||
|
CONDUIT_LOG0(gFD, "-- SYNC DoFastSync --\n");
|
||
|
|
||
|
CMozABConduitSync * sync = (CMozABConduitSync * ) lpParameter;
|
||
|
if(!sync || !sync->m_dbHH)
|
||
|
return 0;
|
||
|
|
||
|
BOOL initialHHSync = (sync->m_rSyncProperties.m_FirstDevice == eHH);
|
||
|
if (initialHHSync) // if HH has been reset, copy everything on pc to hh.
|
||
|
return sync->CopyPCtoHH();
|
||
|
|
||
|
long retval=0;
|
||
|
BOOL success = FALSE;
|
||
|
|
||
|
DWORD mozABCount=0;
|
||
|
LONG * mozCatIndexList = NULL; // freed by MSCOM/Mozilla
|
||
|
CPString ** mozABNameList = NULL; // freed by MSCOM/Mozilla
|
||
|
CPString ** mozABUrlList = NULL; // freed by MSCOM/Mozilla
|
||
|
BOOL * mozDirFlagsList = NULL; // freed by MSCOM/Mozilla
|
||
|
BOOL neverDidPalmSyncBefore = TRUE; // 1st time palm sync?
|
||
|
DWORD mozABIndex;
|
||
|
|
||
|
retval = sync->m_dbHH->OpenDB(FALSE);
|
||
|
if (!retval)
|
||
|
retval = sync->m_dbHH->LoadCategories();
|
||
|
|
||
|
CONDUIT_LOG0(gFD, "Getting moz AB List ... ");
|
||
|
if(!retval)
|
||
|
retval = sync->m_dbPC->GetPCABList(&mozABCount, &mozCatIndexList, &mozABNameList, &mozABUrlList, &mozDirFlagsList);
|
||
|
CONDUIT_LOG1(gFD, "done getting moz AB List. retval = %d\n", retval);
|
||
|
|
||
|
if (retval)
|
||
|
return retval;
|
||
|
|
||
|
// Create an array to help us identify addrbooks that have been deleted on Palm.
|
||
|
DWORD *mozABSeen = (DWORD *) CoTaskMemAlloc(sizeof(DWORD) * mozABCount);
|
||
|
if (!mozABSeen)
|
||
|
return GEN_ERR_LOW_MEMORY;
|
||
|
else
|
||
|
memset(mozABSeen, FALSE, sizeof(DWORD) * mozABCount);
|
||
|
|
||
|
CONDUIT_LOG1(gFD, "first device = %lx\n", sync->m_rSyncProperties.m_FirstDevice);
|
||
|
|
||
|
// See if palm sync was performed before.
|
||
|
for(mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
if (! (mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag))
|
||
|
{
|
||
|
neverDidPalmSyncBefore = FALSE;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// Log moz addrbooks.
|
||
|
for (mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
{
|
||
|
CONDUIT_LOG5(gFD, "Moz AB[%d] category index/synced=%d/%d, name= '%s', url= '%s'\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], ! (mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag),
|
||
|
mozABNameList[mozABIndex]->GetBuffer(0), mozABUrlList[mozABIndex]->GetBuffer(0));
|
||
|
}
|
||
|
|
||
|
// For each category, try to find the corresponding AB in the moz AB list
|
||
|
// and see if it has been synchronized before and take action accordingly.
|
||
|
CPCategory * pCategory = sync->m_dbHH->GetFirstCategory();
|
||
|
while (pCategory)
|
||
|
{
|
||
|
CPalmRecord ** recordListHH = NULL;
|
||
|
DWORD recordCountHH=0;
|
||
|
|
||
|
DWORD catID = pCategory->GetID();
|
||
|
DWORD catIndex = pCategory->GetIndex();
|
||
|
DWORD catFlags = pCategory->GetFlags();
|
||
|
CPString catName(pCategory->GetName());
|
||
|
|
||
|
CONDUIT_LOG3(gFD, "\nProcessing Palm AB '%s' (catIndex/catId) = (%d/%d)... \n", catName.GetBuffer(0), catIndex, catID);
|
||
|
BOOL abRenamed = FALSE;
|
||
|
BOOL foundInABList=FALSE;
|
||
|
for(mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
{
|
||
|
// Palm only allows 15 chars for category names.
|
||
|
CPString cutOffName;
|
||
|
if (mozABNameList[mozABIndex]->Length() > 15)
|
||
|
cutOffName = mozABNameList[mozABIndex]->Left(15);
|
||
|
else
|
||
|
cutOffName = *mozABNameList[mozABIndex];
|
||
|
|
||
|
// if this category has been synchronized before
|
||
|
if(catIndex == mozCatIndexList[mozABIndex])
|
||
|
{
|
||
|
retval = sync->m_dbHH->LoadUpdatedRecordsInCategory(catIndex, &recordListHH, &recordCountHH);
|
||
|
CONDUIT_LOG2(gFD, "Category index = %d, name = '%s' has been synced before\n", catID, catName.GetBuffer(0));
|
||
|
foundInABList = TRUE;
|
||
|
mozABSeen[mozABIndex] = TRUE; // mark it seen
|
||
|
// See if the name has been changed on Palm side. Note that if both
|
||
|
// Palm category and the corresponding moz addrbook are renamed then
|
||
|
// Palm category name takes precedence.
|
||
|
if (!sync->CategoryNameMatches(catName, cutOffName, mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
{
|
||
|
abRenamed = TRUE;
|
||
|
CONDUIT_LOG3(gFD, "Category index = %d, name = '%s' was renamed (from '%s') on Palm so do the same on moz\n",
|
||
|
catID, catName.GetBuffer(0), mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
}
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// if corresponding category exists but not synchronized before
|
||
|
if(sync->CategoryNameMatches(catName, cutOffName, mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
{
|
||
|
retval = sync->m_dbHH->LoadAllRecordsInCategory(catIndex, &recordListHH, &recordCountHH);
|
||
|
CONDUIT_LOG2(gFD, "Category index = %d, name = '%s' has not been synced before\n", catID, catName.GetBuffer(0));
|
||
|
foundInABList = TRUE;
|
||
|
mozABSeen[mozABIndex] = TRUE; // mark it seen
|
||
|
break;
|
||
|
}
|
||
|
} // end of for
|
||
|
|
||
|
if(!retval && foundInABList)
|
||
|
{
|
||
|
CPalmRecord ** recordListPC=NULL;
|
||
|
DWORD recordCountPC=0;
|
||
|
DWORD newRecAddedCount = 0;
|
||
|
DWORD * newRecIDList=NULL;
|
||
|
CONDUIT_LOG1(gFD, " Syncing with moz AB with %d modified Palm record(s) ... ", recordCountHH);
|
||
|
retval = sync->m_dbPC->SynchronizePCAB(catIndex, catID, catName,
|
||
|
recordCountHH, recordListHH,
|
||
|
&recordCountPC, &recordListPC);
|
||
|
CONDUIT_LOG1(gFD, "Done syncing AB. retval=%lx.\n", retval);
|
||
|
|
||
|
// SynchronizePCAB() returns a list of modified moz records so update those on Palm.
|
||
|
if (!retval) {
|
||
|
unsigned long i;
|
||
|
newRecIDList = (DWORD *) calloc(recordCountPC, sizeof(DWORD));
|
||
|
if (recordCountPC > 0)
|
||
|
CONDUIT_LOG1(gFD, " Updating Palm AB with %d modified moz record(s) ...\n", recordCountPC);
|
||
|
for (i=0; i < recordCountPC; i++) {
|
||
|
if(!recordListPC[i])
|
||
|
continue;
|
||
|
CPalmRecord palmRec = *recordListPC[i];
|
||
|
palmRec.SetCategory(catIndex);
|
||
|
if(palmRec.GetAttribs() == ATTR_DELETED)
|
||
|
{
|
||
|
CONDUIT_LOG0(gFD, " - deleting a record\n");
|
||
|
retval = sync->m_dbHH->DeleteARecord(palmRec);
|
||
|
}
|
||
|
else if(palmRec.GetAttribs() == ATTR_MODIFIED)
|
||
|
{
|
||
|
CONDUIT_LOG0(gFD, " - modifying a record\n");
|
||
|
retval = sync->m_dbHH->UpdateARecord(palmRec);
|
||
|
}
|
||
|
else if(palmRec.GetAttribs() == ATTR_NEW) {
|
||
|
CONDUIT_LOG0(gFD, " - adding a record\n");
|
||
|
retval = sync->m_dbHH->AddARecord(palmRec); // should we check existing recs?
|
||
|
if(!retval && (newRecAddedCount < recordCountPC)) {
|
||
|
newRecIDList[newRecAddedCount] = palmRec.GetID();
|
||
|
newRecAddedCount++;
|
||
|
}
|
||
|
}
|
||
|
delete recordListPC[i]; // once done with PC record, delete
|
||
|
}
|
||
|
if (recordCountPC > 0)
|
||
|
CONDUIT_LOG0(gFD, " Done updating Palm AB.\n");
|
||
|
}
|
||
|
// the MozAB is now synchronized
|
||
|
if(!retval)
|
||
|
mozDirFlagsList[mozABIndex] &= ~kFirstTimeSyncDirFlag;
|
||
|
// delete the PC recordList now that palm is updated
|
||
|
if(recordListPC)
|
||
|
free(recordListPC);
|
||
|
// notify Mozilla that sync is done so that memory can be freed
|
||
|
success = retval ? FALSE : TRUE;
|
||
|
|
||
|
if(newRecAddedCount) {
|
||
|
if(newRecAddedCount != recordCountPC)
|
||
|
newRecIDList = (DWORD *) realloc(newRecIDList, newRecAddedCount);
|
||
|
retval = sync->m_dbPC->NotifySyncDone(success, catIndex, newRecAddedCount, newRecIDList);
|
||
|
}
|
||
|
else
|
||
|
retval = sync->m_dbPC->NotifySyncDone(success);
|
||
|
|
||
|
if(newRecIDList)
|
||
|
free(newRecIDList);
|
||
|
|
||
|
// See if it was renamed on palm.
|
||
|
if (abRenamed)
|
||
|
{
|
||
|
// We should not rename personal and collected address books here.
|
||
|
if (! (mozDirFlagsList[mozABIndex] & kIsPabDirFlag) &&
|
||
|
mozABUrlList[mozABIndex]->CompareNoCase(COLLECTED_ADDRBOOK_URL))
|
||
|
{
|
||
|
CONDUIT_LOG0(gFD, " Renaming AB ... ");
|
||
|
retval = sync->m_dbPC->RenamePCAB(catIndex, catName, *mozABUrlList[mozABIndex]);
|
||
|
CONDUIT_LOG1(gFD, "Done renaming AB. retval=%d.\n", retval);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// If this category can't be found in the moz AB list then two cases here:
|
||
|
// 1. If catFlags is not CAT_DIRTY then this category has been deleted
|
||
|
// on moz so remove it from palm side.
|
||
|
// 2. else, if we never did palm sync on moz before then it's a new one
|
||
|
// on palm. So create a new AB in moz with all records in this category
|
||
|
// (even if it's an empty AB).
|
||
|
if(!retval && !foundInABList)
|
||
|
{
|
||
|
if (catFlags != CAT_DIRTY && !neverDidPalmSyncBefore && !initialHHSync)
|
||
|
{
|
||
|
BOOL abDeleted = sync->m_dbPC->PCABDeleted(catName);
|
||
|
if (abDeleted)
|
||
|
{
|
||
|
CONDUIT_LOG2(gFD, "Category index = %d, name = '%s' is removed from moz and needs to be removed from palm\n", catID, catName.GetBuffer(0));
|
||
|
CONDUIT_LOG0(gFD, " Deleting AB from Palm ... ");
|
||
|
retval = sync->m_dbHH->DeleteCategory(catIndex, FALSE);
|
||
|
CONDUIT_LOG1(gFD, "Done deleting AB from Palm. retval=%d.\n", retval);
|
||
|
}
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
CONDUIT_LOG2(gFD, "Category index = %d, name = '%s' is new on palm and needs to be added to moz\n", catID, catName.GetBuffer(0));
|
||
|
retval = sync->m_dbHH->LoadAllRecordsInCategory(catIndex, &recordListHH, &recordCountHH);
|
||
|
CONDUIT_LOG1(gFD, " Creating new moz AB with %d Palm record(s) ... ", recordCountHH);
|
||
|
if(!retval)
|
||
|
retval = sync->m_dbPC->AddRecords(FALSE, catIndex, catName, recordCountHH, recordListHH);
|
||
|
CONDUIT_LOG1(gFD, "Done creating new moz AB. retval=%d.\n", retval);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// delete and free HH records and recordList once synced
|
||
|
if(recordListHH) {
|
||
|
CPalmRecord ** tempRecordListHH = recordListHH;
|
||
|
for(DWORD i=0; i < recordCountHH; i++)
|
||
|
{
|
||
|
if(*tempRecordListHH)
|
||
|
delete *tempRecordListHH;
|
||
|
tempRecordListHH++;
|
||
|
}
|
||
|
free(recordListHH);
|
||
|
}
|
||
|
|
||
|
// Process next category
|
||
|
pCategory = sync->m_dbHH->GetNextCategory();
|
||
|
} // end of while
|
||
|
|
||
|
// Deal with any Moz AB not existing in Palm, ones not sync'ed above,
|
||
|
// and the case where Palm ABs have been deleted.
|
||
|
for(mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
{
|
||
|
if((mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag || neverDidPalmSyncBefore || initialHHSync) && !sync->CategoryExists(*mozABNameList[mozABIndex], mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
{
|
||
|
CONDUIT_LOG3(gFD, "\nMoz AB[%d] category index = %d, name = '%s' doesn't exist on Palm so needs to be added to palm\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
CPalmRecord ** recordListPC=NULL;
|
||
|
DWORD recordCountPC=0;
|
||
|
DWORD * newRecIDList=NULL;
|
||
|
CPCategory cat;
|
||
|
retval = sync->m_dbPC->LoadAllRecords(*mozABNameList[mozABIndex],
|
||
|
&recordCountPC, &recordListPC);
|
||
|
if(!retval)
|
||
|
{
|
||
|
if (! (mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
cat.SetName(mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
else
|
||
|
cat.SetName("Personal");
|
||
|
|
||
|
CONDUIT_LOG1(gFD, " Creating new Palm AB with %d record(s) ... ", recordCountPC);
|
||
|
retval = sync->m_dbHH->AddCategory(cat);
|
||
|
CONDUIT_LOG2(gFD, "Done creating new Palm AB, new category index=%d. retval=%d.\n", cat.GetIndex(), retval);
|
||
|
if(!retval)
|
||
|
{
|
||
|
CONDUIT_LOG1(gFD, " Adding %d record(s) to new Palm AB ... ", recordCountPC);
|
||
|
newRecIDList = (DWORD *) calloc(recordCountPC, sizeof(DWORD));
|
||
|
for (unsigned long i=0; i < recordCountPC; i++)
|
||
|
{
|
||
|
if(!recordListPC[i])
|
||
|
continue;
|
||
|
CPalmRecord palmRec = *recordListPC[i];
|
||
|
palmRec.SetCategory(cat.GetIndex());
|
||
|
retval = sync->m_dbHH->AddARecord(palmRec); // should we check existing recs?
|
||
|
newRecIDList[i] = palmRec.GetID();
|
||
|
delete recordListPC[i]; // delete the record now that it is used
|
||
|
}
|
||
|
CONDUIT_LOG0(gFD, "Done adding new records to new Palm AB.\n");
|
||
|
}
|
||
|
else
|
||
|
CONDUIT_LOG1(gFD, "Creating new Palm AB failed. retval=%d.\n", retval);
|
||
|
}
|
||
|
else
|
||
|
CONDUIT_LOG1(gFD, " Loading moz AB records failed so can't create new Palm AB. retval=%d.\n", retval);
|
||
|
|
||
|
|
||
|
// the MozAB is now synchronized
|
||
|
if(!retval)
|
||
|
mozDirFlagsList[mozABIndex] &= ~kFirstTimeSyncDirFlag;
|
||
|
// delete the recordList now that palm is updated
|
||
|
if(recordListPC)
|
||
|
free(recordListPC);
|
||
|
// notify Mozilla that sync is done so that memory can be freed
|
||
|
if(!retval)
|
||
|
success = TRUE;
|
||
|
else
|
||
|
{
|
||
|
success = FALSE;
|
||
|
recordCountPC=0;
|
||
|
}
|
||
|
retval = sync->m_dbPC->NotifySyncDone(success, cat.GetIndex(), recordCountPC, newRecIDList);
|
||
|
if(newRecIDList)
|
||
|
free(newRecIDList);
|
||
|
|
||
|
// Lastly, update the AB with new category index and mod time.
|
||
|
retval = sync->m_dbPC->UpdatePCABSyncInfo(success ? cat.GetIndex() : -1, *mozABNameList[mozABIndex]);
|
||
|
}
|
||
|
else if (!mozABSeen[mozABIndex] && !neverDidPalmSyncBefore && !initialHHSync)
|
||
|
{
|
||
|
// We should not delete personal and collected address books here. Rather,
|
||
|
// reset the mod time so next time we can sync them back to Palm again.
|
||
|
// Note: make sure the moz addrbook has been synced before to avoid the case
|
||
|
// where early sync failed and we delete this un-synced addrbook by mistake.
|
||
|
if (mozCatIndexList[mozABIndex] > -1 &&
|
||
|
! (mozDirFlagsList[mozABIndex] & kIsPabDirFlag) &&
|
||
|
mozABUrlList[mozABIndex]->CompareNoCase(COLLECTED_ADDRBOOK_URL))
|
||
|
{
|
||
|
CONDUIT_LOG3(gFD, "\nMoz AB[%d] category index = %d, name = '%s' is removed on Palm and needs to be removed from moz\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
CONDUIT_LOG0(gFD, " Deleting AB from moz ... ");
|
||
|
retval = sync->m_dbPC->DeletePCAB(mozCatIndexList[mozABIndex], *mozABNameList[mozABIndex], *mozABUrlList[mozABIndex]);
|
||
|
CONDUIT_LOG1(gFD, "Done deleting AB from moz. retval=%d.\n", retval);
|
||
|
}
|
||
|
else
|
||
|
{
|
||
|
CONDUIT_LOG3(gFD, "\nMoz AB[%d] category index = %d, name = '%s', is removed on Palm but only need to reset sync info on moz\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
// Reset category index and mod time.
|
||
|
CONDUIT_LOG0(gFD, " Resetting AB info on moz ... ");
|
||
|
retval = sync->m_dbPC->UpdatePCABSyncInfo(-1, *mozABNameList[mozABIndex]);
|
||
|
CONDUIT_LOG1(gFD, " Done resetting AB info on moz. retval=%d.\n", retval);
|
||
|
}
|
||
|
}
|
||
|
} // end of mozAB not existing in Palm for loop
|
||
|
|
||
|
// Purge deleted Palm record permanently (in case they were logically deleted).
|
||
|
sync->m_dbHH->PurgeDeletedRecs();
|
||
|
|
||
|
// Free stuff we allocated.
|
||
|
CoTaskMemFree(mozABSeen);
|
||
|
|
||
|
// update category info in HH
|
||
|
sync->m_dbHH->CompactCategoriesToHH();
|
||
|
|
||
|
// close the HH DB once synced
|
||
|
retval = sync->m_dbHH->CloseDB(FALSE);
|
||
|
|
||
|
return retval;
|
||
|
}
|
||
|
|
||
|
long CMozABConduitSync::PerformFastSync()
|
||
|
{
|
||
|
CONDUIT_LOG0(gFD, "-- SYNC Palm -> PerformFastSync --\n");
|
||
|
|
||
|
DWORD ThreadId;
|
||
|
DWORD threadExitCode;
|
||
|
HANDLE hThread = CreateThread(NULL, 0, DoFastSync, this, 0, &ThreadId);
|
||
|
while (WaitForSingleObject(hThread, 1000) == WAIT_TIMEOUT) {
|
||
|
SyncYieldCycles(1); // every sec call this for feedback & keep Palm connection alive
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
// get and return thread's return code if available
|
||
|
BOOL ret = GetExitCodeThread(hThread, &threadExitCode);
|
||
|
if (!ret)
|
||
|
return GetLastError();
|
||
|
// thread failed
|
||
|
CONDUIT_LOG1(gFD, "GetExitCodeThread failed return code = %d\n", threadExitCode);
|
||
|
return threadExitCode;
|
||
|
}
|
||
|
|
||
|
|
||
|
long CMozABConduitSync::PerformSlowSync()
|
||
|
{
|
||
|
// we take care of first time sync in fast sync in an optimized way
|
||
|
return PerformFastSync();
|
||
|
}
|
||
|
|
||
|
long CMozABConduitSync::CopyHHtoPC()
|
||
|
{
|
||
|
long retval=0;
|
||
|
BOOL success = FALSE;
|
||
|
CONDUIT_LOG0(gFD, "-- SYNC Palm -> Destkop --\n");
|
||
|
|
||
|
if(!m_dbHH)
|
||
|
return retval;
|
||
|
|
||
|
DWORD mozABCount=0;
|
||
|
LONG * mozCatIndexList = NULL; // freed by MSCOM/Mozilla
|
||
|
CPString ** mozABNameList = NULL; // freed by MSCOM/Mozilla
|
||
|
CPString ** mozABUrlList = NULL; // freed by MSCOM/Mozilla
|
||
|
BOOL * mozDirFlagsList = NULL; // freed by MSCOM/Mozilla
|
||
|
BOOL neverDidPalmSyncBefore = TRUE; // 1st time palm sync?
|
||
|
DWORD mozABIndex;
|
||
|
|
||
|
retval = m_dbHH->OpenDB(FALSE);
|
||
|
if (!retval)
|
||
|
retval = m_dbHH->LoadCategories();
|
||
|
|
||
|
CONDUIT_LOG0(gFD, "Getting moz AB List ... ");
|
||
|
if(!retval)
|
||
|
retval = m_dbPC->GetPCABList(&mozABCount, &mozCatIndexList, &mozABNameList, &mozABUrlList, &mozDirFlagsList);
|
||
|
|
||
|
CONDUIT_LOG1(gFD, "Done getting moz AB List. retval = %d\n", retval);
|
||
|
if (retval)
|
||
|
return retval;
|
||
|
|
||
|
// Create an array to help us identify addrbooks that have been deleted on Palm.
|
||
|
DWORD *mozABSeen = (DWORD *) CoTaskMemAlloc(sizeof(DWORD) * mozABCount);
|
||
|
if (!mozABSeen)
|
||
|
return GEN_ERR_LOW_MEMORY;
|
||
|
else
|
||
|
memset(mozABSeen, FALSE, sizeof(DWORD) * mozABCount);
|
||
|
|
||
|
// See if palm sync was performed before.
|
||
|
for(mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
if (! (mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag))
|
||
|
{
|
||
|
neverDidPalmSyncBefore = FALSE;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// Log moz addrbooks.
|
||
|
for (mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
{
|
||
|
CONDUIT_LOG5(gFD, "Moz AB[%d] category index/synced=%d/%d, name= '%s', url= '%s'\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], !(mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag),
|
||
|
mozABNameList[mozABIndex]->GetBuffer(0), mozABUrlList[mozABIndex]->GetBuffer(0));
|
||
|
}
|
||
|
|
||
|
// For each category, try to find the corresponding AB in the moz AB list
|
||
|
// and overwrite it with the HH category.
|
||
|
CPCategory * pCategory = m_dbHH->GetFirstCategory();
|
||
|
while (pCategory)
|
||
|
{
|
||
|
CPalmRecord ** recordListHH = NULL;
|
||
|
DWORD recordCountHH=0;
|
||
|
|
||
|
DWORD catID = pCategory->GetID();
|
||
|
DWORD catIndex = pCategory->GetIndex();
|
||
|
DWORD catFlags = pCategory->GetFlags();
|
||
|
CPString catName(pCategory->GetName());
|
||
|
|
||
|
CONDUIT_LOG3(gFD, "\nProcessing Palm AB '%s' (catIndex/catId) = (%d/%d)... \n", catName.GetBuffer(0), catIndex, catID);
|
||
|
BOOL abRenamed = FALSE;
|
||
|
BOOL foundInABList=FALSE;
|
||
|
for(mozABIndex = 0; mozABIndex < mozABCount; mozABIndex++)
|
||
|
{
|
||
|
// Palm only allows 15 chars for category names.
|
||
|
CPString cutOffName;
|
||
|
if (mozABNameList[mozABIndex]->Length() > 15)
|
||
|
cutOffName = mozABNameList[mozABIndex]->Left(15);
|
||
|
else
|
||
|
cutOffName = *mozABNameList[mozABIndex];
|
||
|
|
||
|
// if this category has been synchronized before, check if it has been renamed
|
||
|
if(catIndex == mozCatIndexList[mozABIndex])
|
||
|
{
|
||
|
CONDUIT_LOG4(gFD, "Category index = %d, name = '%s' moz ab name = %s has been synced before uri = %s\n",
|
||
|
catID, catName.GetBuffer(0), mozABNameList[mozABIndex]->GetBuffer(0), mozABUrlList[mozABIndex]->GetBuffer(0));
|
||
|
foundInABList = TRUE;
|
||
|
mozABSeen[mozABIndex] = TRUE; // mark it seen
|
||
|
// See if the name has been changed on Palm side. Note that if both
|
||
|
// Palm category and the corresponding moz addrbook are renamed then
|
||
|
// Palm category name takes precedence.
|
||
|
if (!CategoryNameMatches(catName, cutOffName, mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
{
|
||
|
abRenamed = TRUE;
|
||
|
CONDUIT_LOG3(gFD, "Category index = %d, name = '%s' was renamed (from '%s') on Palm so do the same on moz\n",
|
||
|
catID, catName.GetBuffer(0), mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
}
|
||
|
break;
|
||
|
}
|
||
|
// if corresponding category exists
|
||
|
if (CategoryNameMatches(catName, cutOffName, mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
{
|
||
|
retval = m_dbHH->LoadAllRecordsInCategory(catIndex, &recordListHH, &recordCountHH);
|
||
|
CONDUIT_LOG3(gFD, "Category index = %d, name = '%s' matches moz ab %s\n", catID, catName.GetBuffer(0), mozABUrlList[mozABIndex]->GetBuffer(0));
|
||
|
foundInABList = TRUE;
|
||
|
mozABSeen[mozABIndex] = TRUE; // mark it seen
|
||
|
break;
|
||
|
}
|
||
|
else
|
||
|
CONDUIT_LOG3(gFD, "Category index = %d, name = '%s' doesn't match moz ab %s\n", catID, catName.GetBuffer(0), mozABUrlList[mozABIndex]->GetBuffer(0));
|
||
|
|
||
|
} // end of for
|
||
|
|
||
|
// we've got a matching moz AB. So, just delete all the cards in the Moz AB and copy over all the cards
|
||
|
// in the HH category.
|
||
|
if(!retval && foundInABList)
|
||
|
{
|
||
|
CPalmRecord ** recordListPC=NULL;
|
||
|
DWORD * newRecIDList=NULL;
|
||
|
// retval = m_dbPC->DeletePCAB(mozCatIndexList[mozABIndex], *mozABNameList[mozABIndex], *mozABUrlList[mozABIndex]);
|
||
|
retval = m_dbHH->LoadAllRecordsInCategory(catIndex, &recordListHH, &recordCountHH);
|
||
|
CONDUIT_LOG2(gFD, " Creating new moz AB %s with %d Palm record(s) ... ", mozABNameList[mozABIndex]->GetBuffer(0), recordCountHH);
|
||
|
if(!retval)
|
||
|
retval = m_dbPC->AddRecords(TRUE, catIndex, *mozABNameList[mozABIndex], recordCountHH, recordListHH);
|
||
|
|
||
|
CONDUIT_LOG1(gFD, "Done creating new moz AB. retval=%d.\n", retval);
|
||
|
// the MozAB is now synchronized
|
||
|
if(!retval)
|
||
|
mozDirFlagsList[mozABIndex] &= ~kFirstTimeSyncDirFlag;
|
||
|
// delete the PC recordList now that palm is updated
|
||
|
if(recordListPC)
|
||
|
free(recordListPC);
|
||
|
// notify Mozilla that sync is done so that memory can be freed
|
||
|
success = retval ? FALSE : TRUE;
|
||
|
|
||
|
retval = m_dbPC->NotifySyncDone(success);
|
||
|
|
||
|
if(newRecIDList)
|
||
|
free(newRecIDList);
|
||
|
|
||
|
// See if it was renamed on palm.
|
||
|
if (abRenamed)
|
||
|
{
|
||
|
// We should not rename personal and collected address books here.
|
||
|
if (! (mozDirFlagsList[mozABIndex] & kIsPabDirFlag) &&
|
||
|
mozABUrlList[mozABIndex]->CompareNoCase(COLLECTED_ADDRBOOK_URL))
|
||
|
{
|
||
|
CONDUIT_LOG0(gFD, " Renaming AB ... ");
|
||
|
retval = m_dbPC->RenamePCAB(catIndex, catName, *mozABUrlList[mozABIndex]);
|
||
|
CONDUIT_LOG1(gFD, "Done renaming AB. retval=%d.\n", retval);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
// If this category can't be found in the moz AB list, then
|
||
|
// create a new AB in moz with all records in this category
|
||
|
// (even if it's an empty AB).
|
||
|
if(!retval && !foundInABList)
|
||
|
{
|
||
|
CONDUIT_LOG2(gFD, "Category index = %d, name = '%s' is new on palm and needs to be added to moz\n", catID, catName.GetBuffer(0));
|
||
|
retval = m_dbHH->LoadAllRecordsInCategory(catIndex, &recordListHH, &recordCountHH);
|
||
|
CONDUIT_LOG2(gFD, " Creating new moz AB %s with %d Palm record(s) ... ", catName.GetBuffer(0), recordCountHH);
|
||
|
if(!retval)
|
||
|
{
|
||
|
CPString mozABName;
|
||
|
|
||
|
retval = m_dbPC->AddRecords(FALSE, catIndex, catName, recordCountHH, recordListHH);
|
||
|
}
|
||
|
CONDUIT_LOG2(gFD, "Done creating new moz AB %s - retval=%d.\n", catName.GetBuffer(0), retval);
|
||
|
}
|
||
|
|
||
|
// delete and free HH records and recordList once synced
|
||
|
if(recordListHH)
|
||
|
{
|
||
|
CPalmRecord ** tempRecordListHH = recordListHH;
|
||
|
for(DWORD i=0; i < recordCountHH; i++)
|
||
|
{
|
||
|
delete *tempRecordListHH;
|
||
|
tempRecordListHH++;
|
||
|
}
|
||
|
free(recordListHH);
|
||
|
}
|
||
|
|
||
|
// Process next category
|
||
|
pCategory = m_dbHH->GetNextCategory();
|
||
|
} // end of while
|
||
|
|
||
|
// Free stuff we allocated.
|
||
|
CoTaskMemFree(mozABSeen);
|
||
|
|
||
|
// update category info in HH
|
||
|
m_dbHH->CompactCategoriesToHH();
|
||
|
|
||
|
// close the HH DB once synced
|
||
|
retval = m_dbHH->CloseDB(FALSE);
|
||
|
|
||
|
return retval;
|
||
|
}
|
||
|
|
||
|
long CMozABConduitSync::CopyPCtoHH()
|
||
|
{
|
||
|
long retval=0;
|
||
|
BOOL success = FALSE;
|
||
|
|
||
|
CONDUIT_LOG0(gFD, "-- SYNC Destkop-> Palm --\n");
|
||
|
|
||
|
if(!m_dbHH)
|
||
|
return retval;
|
||
|
|
||
|
DWORD mozABCount=0;
|
||
|
LONG * mozCatIndexList = NULL; // freed by MSCOM/Mozilla
|
||
|
CPString ** mozABNameList = NULL; // freed by MSCOM/Mozilla
|
||
|
CPString ** mozABUrlList = NULL; // freed by MSCOM/Mozilla
|
||
|
BOOL * mozDirFlagsList = NULL; // freed by MSCOM/Mozilla
|
||
|
BOOL neverDidPalmSyncBefore = TRUE; // 1st time palm sync?
|
||
|
DWORD mozABIndex;
|
||
|
|
||
|
retval = m_dbHH->OpenDB(FALSE);
|
||
|
if (!retval)
|
||
|
retval = m_dbHH->LoadCategories();
|
||
|
|
||
|
CONDUIT_LOG0(gFD, "Getting moz AB List ... ");
|
||
|
if(!retval)
|
||
|
retval = m_dbPC->GetPCABList(&mozABCount, &mozCatIndexList, &mozABNameList, &mozABUrlList, &mozDirFlagsList);
|
||
|
|
||
|
if (retval)
|
||
|
return retval;
|
||
|
CONDUIT_LOG0(gFD, "Done getting moz AB List. \n");
|
||
|
|
||
|
// Create an array to help us identify addrbooks that have been deleted on Palm.
|
||
|
DWORD *mozABSeen = (DWORD *) CoTaskMemAlloc(sizeof(DWORD) * mozABCount);
|
||
|
if (!mozABSeen)
|
||
|
return GEN_ERR_LOW_MEMORY;
|
||
|
else
|
||
|
memset(mozABSeen, FALSE, sizeof(DWORD) * mozABCount);
|
||
|
|
||
|
// See if palm sync was performed before.
|
||
|
for(mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
if (! (mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag))
|
||
|
{
|
||
|
neverDidPalmSyncBefore = FALSE;
|
||
|
break;
|
||
|
}
|
||
|
|
||
|
// Log moz addrbooks.
|
||
|
for (mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
{
|
||
|
CONDUIT_LOG5(gFD, "Moz AB[%d] category index/synced=%d/%d, name= '%s', url= '%s'\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], !(mozDirFlagsList[mozABIndex] & kFirstTimeSyncDirFlag),
|
||
|
mozABNameList[mozABIndex]->GetBuffer(0), mozABUrlList[mozABIndex]->GetBuffer(0));
|
||
|
}
|
||
|
|
||
|
// For each category, try to find the corresponding AB in the moz AB list
|
||
|
// and see if it has been synchronized before and take action accordingly.
|
||
|
CPCategory * pCategory = m_dbHH->GetFirstCategory();
|
||
|
while (pCategory)
|
||
|
{
|
||
|
CPalmRecord ** recordListHH = NULL;
|
||
|
DWORD recordCountHH=0;
|
||
|
|
||
|
DWORD catID = pCategory->GetID();
|
||
|
DWORD catIndex = pCategory->GetIndex();
|
||
|
DWORD catFlags = pCategory->GetFlags();
|
||
|
CPString catName(pCategory->GetName());
|
||
|
|
||
|
CONDUIT_LOG3(gFD, "\nProcessing Palm AB '%s' (catIndex/catId) = (%d/%d)... \n", catName.GetBuffer(0), catIndex, catID);
|
||
|
BOOL abRenamed = FALSE;
|
||
|
BOOL foundInABList=FALSE;
|
||
|
|
||
|
retval = m_dbHH->DeleteCategory(catIndex, FALSE); // delete the category - we'll recreate from moz ab.
|
||
|
|
||
|
// Process next category
|
||
|
pCategory = m_dbHH->GetNextCategory();
|
||
|
} // end of while
|
||
|
|
||
|
// Deal with any Moz AB not existing in Palm, ones not sync'ed above,
|
||
|
// and the case where Palm ABs have been deleted.
|
||
|
for(mozABIndex=0; mozABIndex<mozABCount; mozABIndex++)
|
||
|
{
|
||
|
CONDUIT_LOG3(gFD, "\nMoz AB[%d] category index = %d, name = '%s' doesn't exist on Palm so needs to be added to palm\n",
|
||
|
mozABIndex, mozCatIndexList[mozABIndex], mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
CPalmRecord ** recordListPC=NULL;
|
||
|
DWORD recordCountPC=0;
|
||
|
DWORD * newRecIDList=NULL;
|
||
|
CPCategory cat;
|
||
|
retval = m_dbPC->LoadAllRecords(*mozABNameList[mozABIndex],
|
||
|
&recordCountPC, &recordListPC);
|
||
|
if(!retval)
|
||
|
{
|
||
|
if ((mozDirFlagsList[mozABIndex] & kIsPabDirFlag))
|
||
|
cat.SetName("Personal");
|
||
|
else
|
||
|
cat.SetName(mozABNameList[mozABIndex]->GetBuffer(0));
|
||
|
CONDUIT_LOG1(gFD, " Creating new Palm AB with %d record(s) ... ", recordCountPC);
|
||
|
retval = m_dbHH->AddCategory(cat);
|
||
|
CONDUIT_LOG2(gFD, "Done creating new Palm AB, new category index=%d. retval=%d.\n", cat.GetIndex(), retval);
|
||
|
if(!retval) {
|
||
|
CONDUIT_LOG1(gFD, " Adding %d record(s) to new Palm AB ... ", recordCountPC);
|
||
|
newRecIDList = (DWORD *) calloc(recordCountPC, sizeof(DWORD));
|
||
|
for (unsigned long i=0; i < recordCountPC; i++)
|
||
|
{
|
||
|
if(!recordListPC[i])
|
||
|
continue;
|
||
|
CPalmRecord palmRec = *recordListPC[i];
|
||
|
palmRec.SetCategory(cat.GetIndex());
|
||
|
retval = m_dbHH->AddARecord(palmRec); // should we check existing recs?
|
||
|
newRecIDList[i] = palmRec.GetID();
|
||
|
delete recordListPC[i]; // delete the record now that it is used
|
||
|
}
|
||
|
CONDUIT_LOG0(gFD, "Done adding new records to new Palm AB.\n");
|
||
|
}
|
||
|
else
|
||
|
CONDUIT_LOG1(gFD, "Creating new Palm AB failed. retval=%d.\n", retval);
|
||
|
}
|
||
|
else
|
||
|
CONDUIT_LOG1(gFD, " Loading moz AB records failed so can't create new Palm AB. retval=%d.\n", retval);
|
||
|
|
||
|
|
||
|
// delete the recordList now that palm is updated
|
||
|
if(recordListPC)
|
||
|
free(recordListPC);
|
||
|
// notify Mozilla that sync is done so that memory can be freed
|
||
|
if(!retval)
|
||
|
success = TRUE;
|
||
|
else
|
||
|
{
|
||
|
success = FALSE;
|
||
|
recordCountPC=0;
|
||
|
}
|
||
|
retval = m_dbPC->NotifySyncDone(success, cat.GetIndex(), recordCountPC, newRecIDList);
|
||
|
if(newRecIDList)
|
||
|
free(newRecIDList);
|
||
|
|
||
|
// Lastly, update the AB with new category index and mod time.
|
||
|
retval = m_dbPC->UpdatePCABSyncInfo(success ? cat.GetIndex() : -1, *mozABNameList[mozABIndex]);
|
||
|
} // end of mozAB not existing in Palm for loop
|
||
|
|
||
|
// Purge deleted Palm record permanently (in case they were logically deleted).
|
||
|
m_dbHH->PurgeDeletedRecs();
|
||
|
|
||
|
// Free stuff we allocated.
|
||
|
CoTaskMemFree(mozABSeen);
|
||
|
|
||
|
// update category info in HH
|
||
|
m_dbHH->CompactCategoriesToHH();
|
||
|
|
||
|
// close the HH DB once synced
|
||
|
retval = m_dbHH->CloseDB(FALSE);
|
||
|
|
||
|
return retval;
|
||
|
}
|
||
|
|