Got rid of some trivial warnings (nested comments and tokens after #endif).
/*
* Copyright (c) 2007 Nokia Corporation and/or its subsidiary(-ies).
* All rights reserved.
* This component and the accompanying materials are made available
* under the terms of "Eclipse Public License v1.0"
* which accompanies this distribution, and is available
* at the URL "http://www.eclipse.org/legal/epl-v10.html".
*
* Initial Contributors:
* Nokia Corporation - initial contribution.
*
* Contributors:
*
* Description: Holds the contact information in memory. It maintains a
* master array of all contacts. It also has 10 pools corresponding
* to each key id in the keyboard. Based on numeric key char of
* first char of firstname/ lastname a contact is added to one of the
* pools. Implements MDataStoreObserver interface functions to
* add/ remove contacts.
*
*/
// INCLUDE FILES
#include <MVPbkContactLink.h>
#include "CPsData.h"
#include "CPcsCache.h"
#include "CPcsDebug.h"
#include "CWords.h"
#include "CPcsAlgorithm1Utils.h"
// ============================== MEMBER FUNCTIONS ============================
// ----------------------------------------------------------------------------
// CPcsCache::NewL
// Two Phase Construction
// ----------------------------------------------------------------------------
CPcsCache* CPcsCache::NewL(TDesC& aURI, CPcsKeyMap& aKeyMap, TUint8 aUriId)
{
PRINT ( _L("Enter CPcsCache::NewL") );
CPcsCache* instance= new ( ELeave ) CPcsCache();
CleanupStack::PushL( instance );
instance->ConstructL(aURI, aKeyMap, aUriId);
CleanupStack::Pop( instance );
PRINT ( _L("End CPcsCache::NewL") );
return instance;
}
// ----------------------------------------------------------------------------
// CPcsCache::CPcsCache
// Constructor
// ----------------------------------------------------------------------------
CPcsCache::CPcsCache()
{
PRINT ( _L("Enter CPcsCache::CPcsCache") );
PRINT ( _L("End CPcsCache::CPcsCache") );
}
// ----------------------------------------------------------------------------
// CPcsCache::ConstructL
// 2nd Phase Constructor
// ----------------------------------------------------------------------------
void CPcsCache::ConstructL(TDesC& aURI, CPcsKeyMap& aKeyMap, TUint8 aUriId)
{
PRINT ( _L("Enter CPcsCache::ConstructL") );
iURI = aURI.AllocL();
iUriId = aUriId;
//Update the caching status for this cache
iCacheStatus = ECachingNotStarted;
keyMap = &aKeyMap;
// Populate keyArr
for(TInt i= 0; i <aKeyMap.PoolCount();i++ )
{
RPointerArray<CPcsPoolElement> *keyMap = new (ELeave) RPointerArray<CPcsPoolElement>(1);
keyArr.InsertL(keyMap,i);
}
PRINT ( _L("End CPcsCache::ConstructL") );
}
// ----------------------------------------------------------------------------
// CPcsCache::~CPcsCache
// Destructor
// ----------------------------------------------------------------------------
CPcsCache::~CPcsCache()
{
PRINT ( _L("Enter CPcsCache::~CPcsCache") );
if ( iURI )
delete iURI;
// Loop thru cache info and free and the data elements
THashMapIter<TInt, TInt> iter(cacheInfo);
do
{
TInt* id = const_cast<TInt*>(iter.NextKey());
if ( id == NULL )
break;
TInt* poolMap = iter.CurrentValue();
if ( poolMap == NULL )
{
continue;
}
CPsData *data = NULL;
for ( int keyIndex = 0; keyIndex < keyArr.Count(); keyIndex++ )
{
TBool present = GetPoolMap(*poolMap, keyIndex);
if ( ! present )
{
continue;
}
RPointerArray<CPcsPoolElement> tmpKeyMap = *(keyArr[keyIndex]);
for ( int arrayIndex = 0;
arrayIndex < tmpKeyMap.Count();
arrayIndex++ )
{
CPcsPoolElement *element = tmpKeyMap[arrayIndex];
TInt localId = element->GetPsData()->Id();
if ( *id == localId )
{
data = element->GetPsData();
delete element;
keyArr[keyIndex]->Remove(arrayIndex);
}
}
};
// Remove this element from master pool
for ( int arrayIndex = 0;
arrayIndex < masterPool.Count();
arrayIndex++ )
{
CPsData *dataElement = masterPool[arrayIndex];
TInt localId = dataElement->Id();
if ( *id == localId )
{
masterPool.Remove(arrayIndex);
}
}
if( data )
{
delete data;
}
}
while (1);
for(TInt i= 0; i <keyArr.Count();i++ )
{
keyArr[i]->ResetAndDestroy();
delete keyArr[i];
keyArr[i] = NULL;
}
masterPool.ResetAndDestroy();
cacheInfo.Close();
keyArr.Reset();
iDataFields.Reset();
iSortOrder.Reset();
iIndexOrder.Reset();
PRINT ( _L("End CPcsCache::~CPcsCache") );
}
// ----------------------------------------------------------------------------
// CPcsCache::GetContactsForKeyL
// Get list of pool elements specific to a pool
// ----------------------------------------------------------------------------
void CPcsCache::GetContactsForKeyL(TInt aKeyId, RPointerArray<CPcsPoolElement>& aData)
{
PRINT ( _L("Enter CPcsCache::GetContactsForKeyL") );
RPointerArray<CPcsPoolElement> arr = *keyArr[aKeyId];
for ( int i = 0; i < arr.Count(); i++ )
{
CPcsPoolElement* value = arr[i];
aData.AppendL(value);
}
PRINT ( _L("End CPcsCache::GetContactsForKeyL") );
}
// ----------------------------------------------------------------------------
// CPcsCache::GetAllContentsL
// Get all data elements in this cache
// ----------------------------------------------------------------------------
void CPcsCache::GetAllContentsL(RPointerArray<CPsData>& aData)
{
PRINT ( _L("Enter CPcsCache::GetAllContentsL") );
for ( int i = 0; i < masterPool.Count(); i++ )
{
CPsData* value = masterPool[i];
aData.AppendL(value);
}
PRINT ( _L("End CPcsCache::GetAllContentsL") );
}
// ----------------------------------------------------------------------------
// CPcsCache::AddToPool
// Adds a contact to cache
// ----------------------------------------------------------------------------
void CPcsCache::AddToPoolL(TInt& aPoolMap, CPsData& aData)
{
// Temp hash to remember the location of pool elements
// First TInt = Pool
// Second TInt = Location in the pool
// Required for memory optimization so that more than one pool
// element doesn't get added for the same data
RHashMap<TInt, TInt> elementHash;
TLinearOrder<CPcsPoolElement> rule( CPcsPoolElement::CompareByData );
// Parse thru each data element
for ( int dataIndex = 0; dataIndex < aData.DataElementCount(); dataIndex++ )
{
// Stores first key for each word
RArray<TUint> firstKey;
// Recover the first character
if ( aData.Data(dataIndex) && aData.Data(dataIndex)->Length() != 0 )
{
// Split the data into words
CWords* words = CWords::NewLC(*aData.Data(dataIndex));
// Store the first numeric key for each word
for ( int i = 0; i < words->MdcaCount(); i++ )
{
TChar firstChar = (words->MdcaPoint(i))[0];
firstKey.Append(firstChar);
}
CleanupStack::PopAndDestroy(words);
}
for ( TInt wordIndex = 0; wordIndex < firstKey.Count(); wordIndex++ )
{
TInt arrayIndex =keyMap->PoolIdForCharacter(firstKey[wordIndex]);
CPcsPoolElement* element = NULL;
// Check if an element already exists in the pool for this data
TInt* loc = NULL;
loc = elementHash.Find(arrayIndex);
if ( loc != NULL )
{
// Exists. Then recover ...
RPointerArray<CPcsPoolElement> tmpKeyMap = *(keyArr[arrayIndex]);
element = tmpKeyMap[*loc];
}
if ( element == NULL ) // Pool element doesn't exist. Create new ...
{
element = CPcsPoolElement::NewL(aData);
element->ClearDataMatchAttribute();
element->SetDataMatch(dataIndex);
// Insert to pool
keyArr[arrayIndex]->InsertInOrderAllowRepeatsL(element, rule);
TInt index = keyArr[arrayIndex]->FindInOrderL(element, rule);
// Set the bit for this pool
SetPoolMap(aPoolMap, arrayIndex);
// Store the array index in the temp hash
elementHash.InsertL(arrayIndex, index );
}
else // Pool element exists. Just alter the data match attribute
{
element->SetDataMatch(dataIndex);
// Set the bit for this pool
SetPoolMap(aPoolMap, arrayIndex);
}
} // for 2 loop
firstKey.Reset();
} // for 1 loop
elementHash.Close();
}
// ---------------------------------------------------------------------
// CPcsCache::AddToCacheL
//
// ---------------------------------------------------------------------
void CPcsCache::AddToCacheL( CPsData& aData )
{
// Protect against duplicate items getting added
if ( cacheInfo.Find(aData.Id()) != NULL )
{
return;
}
// Include this element in the pool
TInt poolMap = 0;
AddToPoolL(poolMap, aData);
cacheInfo.InsertL(aData.Id(), poolMap);
// Include this element in master pool
TLinearOrder<CPsData> rule( CPcsAlgorithm1Utils::CompareDataBySortOrderL );
masterPool.InsertInOrderAllowRepeatsL(&aData, rule);
}
// ---------------------------------------------------------------------
// CPcsCache::RemoveContactL
//
// ---------------------------------------------------------------------
void CPcsCache::RemoveFromCacheL( TInt aItemId )
{
CPsData *data = NULL;
TInt* poolMap = cacheInfo.Find(aItemId);
if ( poolMap == NULL )
{
return;
}
// Remove this element from pools
for ( int keyIndex = 0; keyIndex < keyArr.Count(); keyIndex++ )
{
TBool present = GetPoolMap(*poolMap, keyIndex);
if ( ! present )
{
continue;
}
RPointerArray<CPcsPoolElement> tmpKeyMap = *(keyArr[keyIndex]);
for ( int arrayIndex = 0;
arrayIndex < tmpKeyMap.Count();
arrayIndex++ )
{
CPcsPoolElement *element = tmpKeyMap[arrayIndex];
TInt id = element->GetPsData()->Id();
if ( id == aItemId )
{
data = element->GetPsData();
delete element;
keyArr[keyIndex]->Remove(arrayIndex);
}
}
};
// Remove this element from master pool
for ( int arrayIndex = 0;
arrayIndex < masterPool.Count();
arrayIndex++ )
{
CPsData *dataElement = masterPool[arrayIndex];
TInt id = dataElement->Id();
if ( id == aItemId )
{
masterPool.Remove(arrayIndex);
}
}
// Delete data
if ( data )
{
delete data;
data = NULL;
}
// Clear up cache information
cacheInfo.Remove(aItemId);
}
// ---------------------------------------------------------------------
// CPcsCache::RemoveAllFromCacheL
//
// ---------------------------------------------------------------------
void CPcsCache::RemoveAllFromCacheL()
{
PRINT ( _L("Enter CPcsCache::RemoveAllFromCacheL") );
for(TInt i= 0; i <keyArr.Count();i++ )
{
keyArr[i]->ResetAndDestroy();
}
masterPool.ResetAndDestroy();
cacheInfo.Close();
PRINT ( _L("End CPcsCache::RemoveAllFromCacheL") );
}
// ---------------------------------------------------------------------
// CPcsCache::SetPoolMap
//
// ---------------------------------------------------------------------
void CPcsCache::SetPoolMap(TInt& aPoolMap, TInt arrayIndex)
{
TReal val;
Math::Pow(val, 2, arrayIndex);
aPoolMap |= (TInt)val;
}
// ---------------------------------------------------------------------
// CPcsCache::GetPoolMap
//
// ---------------------------------------------------------------------
TBool CPcsCache::GetPoolMap(TInt& aPoolMap, TInt arrayIndex)
{
TReal val;
Math::Pow(val, 2, arrayIndex);
return (aPoolMap & (TInt)val);
}
// ---------------------------------------------------------------------
// CPcsCache::GetURI
//
// ---------------------------------------------------------------------
TDesC& CPcsCache::GetURI()
{
return (*iURI);
}
// ---------------------------------------------------------------------
// CPcsCache::SetDataFields
//
// ---------------------------------------------------------------------
void CPcsCache::SetDataFields(RArray<TInt>& aDataFields)
{
for (TInt i(0); i < aDataFields.Count(); i++)
{
iDataFields.Append(aDataFields[i]);
}
}
// ---------------------------------------------------------------------
// CPcsCache::GetDataFields
//
// ---------------------------------------------------------------------
void CPcsCache::GetDataFields(RArray<TInt>& aDataFields)
{
for (TInt i(0); i < iDataFields.Count(); i++)
{
aDataFields.Append(iDataFields[i]);
}
}
// ---------------------------------------------------------------------
// CPcsCache::UpdateCacheStatus
//
// ---------------------------------------------------------------------
void CPcsCache::UpdateCacheStatus(TInt aStatus)
{
iCacheStatus = aStatus;
}
// ---------------------------------------------------------------------
// CPcsCache::GetCacheStatus
//
// ---------------------------------------------------------------------
TInt CPcsCache::GetCacheStatus()
{
return iCacheStatus;
}
// ---------------------------------------------------------------------
// CPcsCache::GetUriId
//
// ---------------------------------------------------------------------
TUint8 CPcsCache::GetUriId()
{
return iUriId;
}
// ---------------------------------------------------------------------
// CPcsCache::GetUri
//
// ---------------------------------------------------------------------
HBufC* CPcsCache::GetUri()
{
return iURI;
}
// ---------------------------------------------------------------------
// CPcsCache::SetSortOrder
//
// ---------------------------------------------------------------------
void CPcsCache::SetSortOrder(RArray<TInt>& aSortOrder)
{
PRINT ( _L("Enter CPcsCache::SetSortOrder") );
iSortOrder.Reset();
for (TInt i(0); i < aSortOrder.Count(); i++)
{
iSortOrder.Append(aSortOrder[i]);
}
ComputeIndexOrder();
PRINT ( _L("End CPcsCache::SetSortOrder") );
}
// ---------------------------------------------------------------------
// CPcsCache::GetSortOrder
//
// ---------------------------------------------------------------------
void CPcsCache::GetSortOrder(RArray<TInt>& aSortOrder)
{
aSortOrder.Reset();
for (TInt i(0); i < iSortOrder.Count(); i++)
{
aSortOrder.Append(iSortOrder[i]);
}
}
// ---------------------------------------------------------------------
// CPcsCache::GetIndexOrder
//
// ---------------------------------------------------------------------
void CPcsCache::GetIndexOrder(RArray<TInt>& aIndexOrder)
{
aIndexOrder.Reset();
for (TInt i(0); i < iIndexOrder.Count(); i++)
{
aIndexOrder.Append(iIndexOrder[i]);
}
}
// ---------------------------------------------------------------------
// CPcsCache::ComputeIndexOrder
//
// ---------------------------------------------------------------------
void CPcsCache::ComputeIndexOrder()
{
iIndexOrder.Reset();
for ( int i = 0; i < iSortOrder.Count(); i++ )
{
for ( int j = 0; j < iDataFields.Count(); j++ )
{
if ( iSortOrder[i] == iDataFields[j] )
{
iIndexOrder.Append(j);
break;
}
}
}
}
// ---------------------------------------------------------------------
// CPcsCache::ResortdataInPools
//
// ---------------------------------------------------------------------
void CPcsCache::ResortdataInPoolsL()
{
// copy masterPool data into masterPoolBackup
for (TInt i = 0; i < masterPool.Count(); i++ )
{
masterPoolBackup.Append( masterPool[i] );
}
//Now reset the key array
for (TInt i = 0; i < keyArr.Count(); i++ )
{
keyArr[i]->ResetAndDestroy();
}
masterPool.Reset();
cacheInfo.Close();
//now add data again from the masterPoolBackup
for (TInt i = 0; i < masterPoolBackup.Count(); i++ )
{
CPsData* temp = static_cast<CPsData*>(masterPoolBackup[i]);
AddToCacheL( *temp );
}
masterPoolBackup.Reset();
}
// End of file