pimappservices/calendar/server/src/agssess.cpp
changeset 0 f979ecb2b13e
child 36 9c5b1510919f
child 45 b6db4fd4947b
equal deleted inserted replaced
-1:000000000000 0:f979ecb2b13e
       
     1 // Copyright (c) 1997-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 //
       
    15 
       
    16 #include "agssess.h"
       
    17 
       
    18 #include "agmattachment.h"
       
    19 #include "agscategoryindex.h"
       
    20 #include "agscategorylist.h"
       
    21 #include "agmentry.h"
       
    22 #include "agsiterator.h"
       
    23 #include "agsentrymodel.h"
       
    24 #include "agmpanic.h"
       
    25 #include "agmcategory.h"
       
    26 #include "agmcontent.h"
       
    27 #include "agmserv.h"
       
    28 #include "agsfilemanager.h"
       
    29 #include "agsmain.h"
       
    30 #include "calcommonimpl.h"
       
    31 #include "agmdebug.h"
       
    32 #include "agmtzrules.h"
       
    33 #include "agssortinstance.h"
       
    34 #include "agsinstanceiterator.h"
       
    35 #include "agmsortcriteria.h"
       
    36 #include "agmdate.h"
       
    37 #include "agssort.h"
       
    38 #include "agmcalendarinfo.h"
       
    39 #include "calsessionimpl.h"
       
    40 #include "agmfilechangenotification.h"
       
    41 #ifdef SYMBIAN_SYSTEM_STATE_MANAGEMENT
       
    42 #include "agssystemstateobserver.h"
       
    43 #endif
       
    44 
       
    45 #include <apparc.h>
       
    46 #include <s32file.h>
       
    47 
       
    48 //
       
    49 // CAgnServerSession
       
    50 //
       
    51 
       
    52 const TInt KGranFilteredEntries = 20;
       
    53 const TInt KMaxNumberOfBufferedNotifications = 50;
       
    54 const TInt KGranNotificationBuffer = 64;
       
    55 
       
    56 const TInt KSlot0 = 0;
       
    57 const TInt KSlot1 = 1;
       
    58 const TInt KSlot2 = 2;
       
    59 const TInt KSlot3 = 3;
       
    60 
       
    61 void CleanupCloseAgendaImmediately(TAny* aRef)
       
    62     {
       
    63     if (aRef)
       
    64         {
       
    65         static_cast<CAgnServFile*>(aRef)->CloseAgenda(ETrue);
       
    66         }
       
    67     }
       
    68 
       
    69 TAgnChangeFilter::TAgnChangeFilter(CAgnServerSession& aSession) :
       
    70 	iChangeBroadcastEnabled(ETrue),
       
    71 	iSession(aSession),
       
    72 	iStartTimeUtc(Time::NullTTime()),
       
    73 	iEndTimeUtc(Time::NullTTime()),
       
    74 	iPubSubChangeMadeDuringDisable(ENoChange),
       
    75 	iPubSubEnabled(ETrue)
       
    76 	{
       
    77 	}
       
    78 
       
    79 TBool TAgnChangeFilter::ChangeBroadcastEnabled() const
       
    80 	{
       
    81 	return iChangeBroadcastEnabled;
       
    82 	}
       
    83 	
       
    84 const CAgnServerSession& TAgnChangeFilter::Session() const
       
    85 	{
       
    86 	return iSession;
       
    87 	}
       
    88 
       
    89 void TAgnChangeFilter::SetEnableChangeBroadcast(TBool aBool)
       
    90 	{
       
    91 	iChangeBroadcastEnabled = aBool;
       
    92 	}
       
    93 
       
    94 TBool TAgnChangeFilter::ChangeMadeWhileDisabled() const
       
    95 	{
       
    96 	return iChangeMadeWhileDisabled;
       
    97 	}
       
    98 	
       
    99 void TAgnChangeFilter::SetChangeMadeWhileDisabled(TBool aBool)
       
   100 	{
       
   101 	iChangeMadeWhileDisabled = aBool;	
       
   102 	}
       
   103 
       
   104 void TAgnChangeFilter::SetChangeParameter(const TTime& aStartTime, const TTime& aEndTime, MCalChangeCallBack2::TChangeEntryType aChangeType)
       
   105 	{
       
   106 	iStartTimeUtc = aStartTime;
       
   107 	iEndTimeUtc = aEndTime;
       
   108 	iEntryType = aChangeType;
       
   109 	}
       
   110 
       
   111 TBool TAgnChangeFilter::CheckChangeWithinRangeL(const CAgnRptDef* aRptDef, const TTime& aStartTime, const TTime& aEndTime) const
       
   112 	{
       
   113 	TBool entryInTimeRange = ETrue;
       
   114 	if (aRptDef)
       
   115 		{
       
   116 		TTime nudgedNextTimeUtc;
       
   117 		TBool nextDateExists = aRptDef->NudgeNextInstanceUtcL(iStartTimeUtc, nudgedNextTimeUtc);
       
   118 		if ( ! nextDateExists || nudgedNextTimeUtc > iEndTimeUtc)
       
   119 			{
       
   120 			entryInTimeRange = EFalse;
       
   121 			}
       
   122 		}
       
   123 	else
       
   124 		{
       
   125 		if (iStartTimeUtc > aEndTime || iEndTimeUtc < aStartTime)
       
   126 			{
       
   127 			entryInTimeRange = EFalse;
       
   128 			}
       
   129 		}
       
   130 	return entryInTimeRange;
       
   131 	}
       
   132 			
       
   133 TBool TAgnChangeFilter::IsValidChangeL(const TAgnChange& aChange) const
       
   134 	{
       
   135 	if (aChange.iOperationType != MCalChangeCallBack2::EChangeUndefined)
       
   136 		{
       
   137 		if (iEntryType == MCalChangeCallBack2::EChangeEntryTodo && aChange.iEntryType != CCalEntry::ETodo)
       
   138 			{
       
   139 			return EFalse;
       
   140 			}
       
   141 		if (iEntryType == MCalChangeCallBack2::EChangeEntryEvent && aChange.iEntryType == CCalEntry::ETodo)
       
   142 			{
       
   143 			return EFalse;
       
   144 			}
       
   145 		
       
   146 		// Check the entry is within the time range specified by the filter
       
   147 		// aChange.iRepeatRule gives the repeat data for the newly stored entry. If this operation is an update,
       
   148 		// then aChange.iOriginalRepeatRule gives the repeat data for the old entry.
       
   149 		TBool entryInTimeRange = CheckChangeWithinRangeL(aChange.iRepeatRule, aChange.iStartTimeOfEntryUtc, aChange.iEndTimeOfEntryUtc);
       
   150 		TBool originalEntryInTimeRange = CheckChangeWithinRangeL(aChange.iOriginalRepeatRule, aChange.iOriginalStartTimeUtc, aChange.iOriginalEndTimeUtc);
       
   151 			
       
   152 		if (iEntryType != MCalChangeCallBack2::EChangeEntryEvent)
       
   153 			{
       
   154 			if (aChange.iEntryType == CCalEntry::ETodo && aChange.iStartTimeOfEntryUtc == Time::NullTTime() &&  aChange.iEndTimeOfEntryUtc == Time::NullTTime())
       
   155 				{
       
   156 				return ETrue;
       
   157 				}
       
   158 			}
       
   159 		
       
   160 		if ( ! entryInTimeRange && ! originalEntryInTimeRange)
       
   161 			{
       
   162 			return EFalse;
       
   163 			}
       
   164 		}
       
   165 	return ETrue;
       
   166 	}
       
   167 	
       
   168 TBool TAgnChangeFilter::PubSubEnabled() const
       
   169 	{
       
   170 	return iPubSubEnabled;
       
   171 	}
       
   172 
       
   173 void TAgnChangeFilter::SetPubSubChange(TPubSubChange aChange)
       
   174 	{
       
   175 	if(aChange==ENoChange)
       
   176 		{//clear all bits
       
   177 		iPubSubChangeMadeDuringDisable = ENoChange; // = 0
       
   178 		}
       
   179 	else
       
   180 		{
       
   181 		iPubSubChangeMadeDuringDisable = iPubSubChangeMadeDuringDisable | aChange;
       
   182 		}
       
   183 	}
       
   184 	
       
   185 TBool TAgnChangeFilter::TodoChanged() const
       
   186 	{
       
   187 	return iPubSubChangeMadeDuringDisable & ETodoChanged;
       
   188 	}
       
   189 
       
   190 void TAgnChangeFilter::SetEnablePubSubNotification(TBool aEnablePubSubNotification)
       
   191 	{
       
   192 	iPubSubEnabled = aEnablePubSubNotification;
       
   193 	}
       
   194 	
       
   195 CAgnServerSession::CAgnServerSession(CAgnServer& aServer)
       
   196     :iAgnServer(aServer), iSessionReady(ETrue)
       
   197 	{
       
   198 	iAgnServer.SessionAdded();
       
   199 	}
       
   200 
       
   201 CAgnServerSession* CAgnServerSession::NewL(CAgnServer& aServer)
       
   202     {
       
   203     CAgnServerSession* self = new (ELeave) CAgnServerSession(aServer);
       
   204     CleanupStack::PushL(self);
       
   205     self->ConstrucL();
       
   206     CleanupStack::Pop(self);
       
   207     return self;
       
   208     }
       
   209 
       
   210 void CAgnServerSession::ConstrucL()
       
   211     {
       
   212     iAgnSessionFileManager = CAgnSessionFileManager::NewL(*this, *(iAgnServer.FileMgr()));
       
   213     }
       
   214 
       
   215 void CAgnServerSession::ServiceL(const RMessage2 &aMessage)
       
   216 	{
       
   217 	TBool complete = ETrue;
       
   218 	TInt err = KErrNone;
       
   219 	iMessage = aMessage;
       
   220 	
       
   221 #ifdef SYMBIAN_SYSTEM_STATE_MANAGEMENT
       
   222 	if (iAgnServer.SystemStateObserver().IsShutdownInProgress())
       
   223 		{
       
   224 		//Shutdown in progress
       
   225 		err = IsReadOnlyOperation();
       
   226 		complete = ETrue;
       
   227 		}
       
   228 #endif
       
   229 	if (err == KErrNone)
       
   230 		{
       
   231 	    TRAP(err,complete = DispatchMessageL());
       
   232 	    _DBGLOG_IPC(AgmDebug::DebugLogIPCL(aMessage.Function(), TInt(this), err);)
       
   233 
       
   234 	    if ( err != KErrNone )
       
   235 	    	{
       
   236 	    	if (err == KErrNotReady && 
       
   237 	    			aMessage.Function() != ETransferAttachmentFileToServer &&
       
   238 	    			aMessage.Function() != ETransferFileToClientToWrite &&
       
   239 	    			aMessage.Function() != ETransferAttachmentFileToClient&&
       
   240 	    			aMessage.Function() != EMoveFileToServer)
       
   241 	    		{
       
   242 	    		// If a function has failed with Not ready, then a drive must not be ready
       
   243 	    		// If it is not an attachment failure, then it must have happened on the drive containing
       
   244 	    		// the Calendar file. In this case, ensure the session always leaves with KErrNotReady
       
   245 	    		// until the session is closed and re-opened.
       
   246 	    		iSessionReady = EFalse;
       
   247 	    		}
       
   248 	    	delete iBuffer;
       
   249 	    	iBuffer = NULL;
       
   250 	    	}
       
   251 		}
       
   252 		
       
   253 	if (complete && err != KClientHasBeenPanicked)
       
   254 		{
       
   255 		aMessage.Complete(err);
       
   256 		}
       
   257 	}
       
   258 
       
   259 CAgnServerSession::~CAgnServerSession()
       
   260 	{
       
   261 	//This is required for robustness. Clients which are incorrectly
       
   262 	//written can make requests with MCalProgressCallBack callbacks could
       
   263 	//subsequently panic and cause the session to be destructed. 
       
   264 	//The task which the client had initiated will be cancelled so it does not
       
   265 	//attempt to use the session again with further progress information.
       
   266 	
       
   267 	CancelAllTask();
       
   268  
       
   269 	// Cleanup any resources that have been allocated
       
   270 	delete iBuffer;
       
   271 	// Close the calendar file after a delay
       
   272 	CloseAgendas();
       
   273 	iAgnServer.SessionClosed();
       
   274 	delete iAgnSessionFileManager;
       
   275 	delete iInstanceIteratorMgr;
       
   276 	}
       
   277 
       
   278 /** 
       
   279 * Check to see if an operation can be performed due to backup\restore process
       
   280 * @return ETrue, if the operation can not be performed, EFalse otherwise. 
       
   281 */
       
   282 TBool CAgnServerSession::CheckBackupRestore()
       
   283     {
       
   284     if(iBackupRestoreLock  
       
   285     //All opeerations apart from the following ones are not allowed when Backup\Restore is in progress. 
       
   286     && iMessage.Function() != ECloseAgenda
       
   287     && iMessage.Function() != ECancelChangeNotification
       
   288     && iMessage.Function() != EDisableChangeBroadcast
       
   289     && iMessage.Function() != ETransmitBuffer
       
   290     && iMessage.Function() != ERequestChangeNotificationParameters
       
   291     && iMessage.Function() != ERequestChangeNotification
       
   292     && iMessage.Function() != EEnableChangeBroadcast
       
   293     && iMessage.Function() != EGetChangesSinceLastNotification
       
   294     && iMessage.Function() != ERequestProgress)
       
   295         {
       
   296         return ETrue;
       
   297         }
       
   298         
       
   299   // Return false, if iBackupRestoreLock is false or operations are those above, CAgnServFile::IsLocked()
       
   300   // will determine whether or not an operation can be performed.
       
   301     return EFalse;
       
   302     }
       
   303 
       
   304 TBool CAgnServerSession::DispatchMessageL()
       
   305 	{
       
   306     TBool operationRequiresFileLock = EFalse;
       
   307     TBool callIsAsynchronous = ETrue;
       
   308  	if(CheckBackupRestore())
       
   309 	    {
       
   310 	    User::Leave(KErrLocked);
       
   311 	    }
       
   312 
       
   313 	switch (iMessage.Function())
       
   314 		{
       
   315 		case EOpenAgenda:
       
   316 			{
       
   317 			OpenAgendaL();
       
   318 			iSessionReady = ETrue;
       
   319 			}
       
   320 			break;
       
   321 			
       
   322 		case ECloseAgenda:
       
   323 			{
       
   324 			// Close the calendar file after a delay
       
   325 			CloseAgendaL();
       
   326 			iSessionReady = ETrue;
       
   327 			}
       
   328 			break;
       
   329 	
       
   330 		case ERequestChangeNotificationParameters:
       
   331 			{
       
   332 			RequestChangeNotificationParametersL();
       
   333 			}			
       
   334 			break;
       
   335 			
       
   336 		case ERequestChangeNotification:
       
   337 			{
       
   338 			RequestChangeNotification();
       
   339 			callIsAsynchronous = EFalse;
       
   340 			}
       
   341 			break;
       
   342 
       
   343 		case ECancelChangeNotification:
       
   344 			{
       
   345 			CancelChangeNotification();
       
   346 			}
       
   347 			break;
       
   348 
       
   349 		case EDisableChangeBroadcast:
       
   350 			{
       
   351 			DisableChangeBroadcastL();
       
   352 			}
       
   353 			break;
       
   354 
       
   355 		case EEnableChangeBroadcast:
       
   356 			{
       
   357 			EnableChangeBroadcastL();
       
   358 			}
       
   359 			break;
       
   360 
       
   361 		case EAgnHeapSizeCount:
       
   362 			{
       
   363 			TInt allocSize;
       
   364 			User::Heap().AllocSize(allocSize);
       
   365 			TPckg<TInt> HeapSize(allocSize);
       
   366 			iMessage.WriteL(KSlot0, HeapSize);			
       
   367 			}
       
   368 			break;
       
   369 
       
   370 		case EAgnResourceCount:
       
   371 			{
       
   372 			TPckg<TInt> HeapCells(User::Heap().Count());
       
   373 			iMessage.WriteL(KSlot0, HeapCells);			
       
   374 			}
       
   375 			break;
       
   376 			
       
   377 		case EAgnSetHeapFailure:
       
   378 			{
       
   379 			User::__DbgSetAllocFail(RHeap::EUser,(RHeap::TAllocFail)iMessage.Int0(),iMessage.Int1());		
       
   380 			}
       
   381 			break;
       
   382 
       
   383 		case ECreateAgendaFile:
       
   384 			{
       
   385 			CreateAgendaFileL();			
       
   386 			}
       
   387   			break;
       
   388  
       
   389 		case EGetListFileNames:
       
   390 			{
       
   391 			ListAgendaFilesL();
       
   392 			}
       
   393 			break;
       
   394 
       
   395 		case EDeleteAgendaFile:
       
   396 			{
       
   397 	  		DeleteAgendaFileL();
       
   398 			}
       
   399 	  		break;
       
   400 
       
   401 		case ECancelTask:
       
   402 			{
       
   403 			CancelTaskL();
       
   404 			}
       
   405 			break;
       
   406 
       
   407 		case EAgendaFileExists:
       
   408 			{
       
   409 			AgendaFileExistsL();
       
   410 			}
       
   411 			break;
       
   412 
       
   413 		case ETransmitBuffer:
       
   414 			{
       
   415 			TransmitBufferL();
       
   416 			}
       
   417 			break;
       
   418 
       
   419 		case ESetUpdateAlarm:
       
   420 			{
       
   421 			SetUpdateAlarmL();
       
   422 			}
       
   423 			break;
       
   424 
       
   425 		case ESetEnablePubSubNotification:
       
   426 			{
       
   427 			SetEnablePubSubNotificationL();
       
   428 			}
       
   429 			break;
       
   430 
       
   431 		case ERequestProgress:
       
   432 			{
       
   433 			RequestProgressL();
       
   434 			callIsAsynchronous = EFalse; 
       
   435 			}
       
   436 			break;
       
   437 			
       
   438 		case EGetChangesSinceLastNotification:
       
   439 			{
       
   440 			GetChangesSinceLastNotificationL();
       
   441 			}
       
   442 			break;
       
   443 			
       
   444 		case EStartBuildIndex:
       
   445 			{
       
   446 			//Asynchronous call
       
   447 			StartBuildIndex();
       
   448 			callIsAsynchronous = EFalse; 
       
   449 			}
       
   450 			break;
       
   451 		case ETzDbChangedTime:
       
   452 			{
       
   453 			TzRulesLastModifiedDateTimeL();
       
   454 			}
       
   455 			break;
       
   456 		case ERollback:
       
   457 			{
       
   458 			RollbackL();
       
   459 			}
       
   460 			break;
       
   461 		case EGetFileChangesSinceLastNotification:
       
   462 		    {
       
   463 		    GetFileChangesSinceLastNotificationL();
       
   464 		    }
       
   465 		    break;
       
   466 		default:
       
   467 			{
       
   468 			operationRequiresFileLock = ETrue;
       
   469 			}
       
   470 			break;
       
   471 		}
       
   472 		
       
   473 	// Most commands are not permitted while the file is locked
       
   474     
       
   475     if ( operationRequiresFileLock )
       
   476 	    {
       
   477     	if ( ! iSessionReady)
       
   478 			{
       
   479 			User::Leave(KErrNotReady);
       
   480 			}
       
   481 		else
       
   482 			{
       
   483 			switch ( iMessage.Function() )
       
   484 				{
       
   485 				case EFetchEntry:
       
   486 					{
       
   487 					FetchEntryL();
       
   488 					}
       
   489 					break;
       
   490 				case EFetchEntryByUID:
       
   491 					{
       
   492 					FetchEntryByUIDL();
       
   493 					}
       
   494 					break;
       
   495 				case EFetchSimpleEntry:
       
   496 					{
       
   497 					FetchSimpleEntryL();
       
   498 					}
       
   499 					break;
       
   500 				case EFetchSimpleEntries:
       
   501 					{
       
   502 					FetchSimpleEntriesL();
       
   503 					}
       
   504 					break;
       
   505 				case EUpdateEntry:
       
   506 					{
       
   507 					UpdateEntryL();
       
   508 					}
       
   509 					break;
       
   510 				case EAddEntry:
       
   511 					{
       
   512 					AddEntryL();
       
   513 					}
       
   514 					break;
       
   515 				case EDeleteEntry:
       
   516 					{
       
   517 					DeleteEntryL();
       
   518 					}
       
   519 					break;
       
   520 				case EPreviousInstances:
       
   521 					{
       
   522 					PreviousInstancesL();
       
   523 					}
       
   524 					break;
       
   525 				case ENextInstances:
       
   526 					{
       
   527 					NextInstancesL();
       
   528 					}
       
   529 					break;
       
   530 				case ECreateEntryIterator:
       
   531 					{
       
   532 					CreateEntryIteratorL();
       
   533 					}
       
   534 					break;
       
   535 				case EEntryIteratorNext:
       
   536 					{
       
   537 					EntryIteratorNextL();
       
   538 					}
       
   539 					break;
       
   540 				case EEntryIteratorPosition:
       
   541 					{
       
   542 					EntryIteratorPositionL();
       
   543 					}
       
   544 					break;
       
   545 				case ECommit:
       
   546 					{
       
   547 					CommitL();
       
   548 					}
       
   549 					break;
       
   550 				case EGetEntryUidsSinceDate:
       
   551 					{
       
   552 					GetEntryUidsSinceDateL();
       
   553 					}
       
   554 					break;
       
   555 				case ERestoreText:
       
   556 					{
       
   557 					RestoreTextL();
       
   558 					}
       
   559 					break;
       
   560 				case ERestoreAlarmAction:
       
   561 					{
       
   562 					RestoreAlarmActionL();
       
   563 					}
       
   564 					break;
       
   565 				case EGetCategoryListCount:
       
   566 					{
       
   567 					GetCategoryListCountL();
       
   568 					}
       
   569 					break;
       
   570 				case EGetCategoryListItem:
       
   571 					{
       
   572 					GetCategoryListItemL();
       
   573 					}
       
   574 					break;
       
   575 				case EAddCategoryToList:
       
   576 					{
       
   577 					AddCategoryToListL();
       
   578 					}
       
   579 					break;
       
   580 				case ECategoryFilter:
       
   581 					{
       
   582 					FilterCategoryL();
       
   583 					}
       
   584 					break;
       
   585 				case ETidyByDateReadParams:
       
   586 					{
       
   587 					TidyByDateReadParamsL();
       
   588 					}
       
   589 					break;
       
   590 				case ETidyByDateStart:
       
   591 					{
       
   592 					TidyByDateStartL();
       
   593 					callIsAsynchronous = EFalse; 
       
   594 					}
       
   595 					break;
       
   596 				case ECategoryStart:
       
   597 					{
       
   598 					CategoryTaskStartL();
       
   599 					}
       
   600 					break;
       
   601 				case ECategoryStartAsyn:
       
   602 					{
       
   603 					AsynchCategoryTaskStartL();
       
   604 					callIsAsynchronous = EFalse;
       
   605 					}
       
   606 					break;
       
   607 				case EInstanceIteratorCreate:
       
   608 					{
       
   609 					CreateInstanceIteratorL();
       
   610 					}
       
   611 					break;
       
   612 				case EInstanceIteratorDestroy:
       
   613 					{
       
   614 					DestroyInstanceIteratorL();
       
   615 					}
       
   616 					break;
       
   617 				case EInstanceIteratorNext:
       
   618 					{
       
   619 					InstanceIteratorNextL();
       
   620 					}
       
   621 					break;
       
   622 				case EInstanceIteratorPrevious:
       
   623 					{
       
   624 					InstanceIteratorPreviousL();
       
   625 					}
       
   626 					break;
       
   627 				case EInstanceIteratorCount:
       
   628 					{
       
   629 					InstanceIteratorCountL();
       
   630 					}
       
   631 					break;
       
   632 				case EInstanceIteratorLocateIndex:
       
   633 					{
       
   634 					InstanceIteratorLocateIndexL();
       
   635 					}
       
   636 					break;
       
   637 				
       
   638 			// Group Scheduling
       
   639 				case EGetChangesSinceLastNotification:
       
   640 					{
       
   641 					GetChangesSinceLastNotificationL();
       
   642 					}
       
   643 					break;
       
   644 				case EFetchEntryByGuid:
       
   645 					{
       
   646 					FetchEntryByGuidL();
       
   647 					}
       
   648 					break;
       
   649 				case EFetchSimpleEntriesByGuid:
       
   650 					{
       
   651 					FetchSimpleEntriesByGuidL();
       
   652 					}
       
   653 					break;
       
   654 				case EDeleteEntriesByLocalUid:
       
   655 					{
       
   656 					DeleteEntriesByLocalUidL();
       
   657 					}
       
   658 					break;
       
   659 				case EDeleteEntryByGuid:
       
   660 					{
       
   661 					DeleteEntryByGuidL();
       
   662 					}
       
   663 					break;
       
   664 				case EFindInstances:
       
   665 					{
       
   666 					FindInstancesL();
       
   667 					}
       
   668 					break;
       
   669 				case ETransferAttachmentFileToServer:
       
   670 					{
       
   671 					TransferAttachmentFileToServerL();
       
   672 					}
       
   673 					break;
       
   674 				case ETransferAttachmentFileToClient:
       
   675 					{
       
   676 					TransferAttachmentFileToClientL();
       
   677 					callIsAsynchronous = EFalse;
       
   678 					}
       
   679 					break;
       
   680 				case ETransferFileToClientToWrite:
       
   681 					{
       
   682 					TransferFileToClientToWriteL();
       
   683 					callIsAsynchronous = EFalse;
       
   684 					}
       
   685 					break;
       
   686 				case EFetchSortedAttachments:
       
   687 					{
       
   688 					FetchSortedAttachmentsL();
       
   689 					}
       
   690 					break;
       
   691 				case EEntriesWithAttachment:
       
   692 					{
       
   693 					EntriesWithAttachmentL();
       
   694 					}
       
   695 					break;
       
   696 				case EFetchAttachmentById:
       
   697 					{
       
   698 					FetchAttachmentByIdL();
       
   699 					}
       
   700 					break;
       
   701 				case EMoveFileToServer:
       
   702 					{
       
   703 					MoveFileToServerL();
       
   704 					}
       
   705 					break;
       
   706 				case EFetchSimpleEntryByUID:
       
   707 					{
       
   708 					FetchSimpleEntryByUIDL();
       
   709 					}
       
   710 					break;
       
   711                case ESetCalendarInfo:
       
   712                     {
       
   713                     SetCalendarInfoL();
       
   714                     }
       
   715                     break;
       
   716                case EGetCalendarInfo:
       
   717                     {
       
   718                     GetCalendarInfoL();
       
   719                     }
       
   720                     break;
       
   721                case EGetPropertyValue:
       
   722                     {
       
   723                     GetPropertyValueL();
       
   724                     }
       
   725                     break;
       
   726 				default:
       
   727 					PanicClientL(EBadRequest);
       
   728 					return ETrue;
       
   729 				}
       
   730 			}
       
   731 		}
       
   732 	
       
   733 	// If the buffer size is greater than KInitialBufferSize, then the buffer cannot be 
       
   734 	// transmitted now. A large enough buffer must first be created on the client side to 
       
   735 	// hold this.
       
   736 	if ( iBuffer && iBuffer->Size() <= KInitialBufferSize && 
       
   737 		 iBuffer->Size() > 0 )
       
   738 		{
       
   739 		TransmitBufferL();
       
   740 		}
       
   741 
       
   742 	return callIsAsynchronous;	// complete normally
       
   743 	}
       
   744 
       
   745 void CAgnServerSession::SetUpdateAlarmL()
       
   746 	{
       
   747 	TBool updateAlarm = iMessage.Int0();
       
   748 	CAgnServFile* file = GetFileL(KSlot1);
       
   749 	file->Model()->SetUpdateAlarmL(updateAlarm);
       
   750 	}
       
   751 
       
   752 void CAgnServerSession::SetEnablePubSubNotificationL()
       
   753 	{
       
   754 	TBool enablePubsub = iMessage.Int0();
       
   755 	TPckgBuf<TInt64> fileId;
       
   756 	iMessage.ReadL(KSlot1, fileId);
       
   757 	
       
   758 	if(iAgnSessionFileManager)
       
   759 		{
       
   760 		CAgnSessionFile* client = NULL;
       
   761 		TRAPD(err, client = &(iAgnSessionFileManager->GetSessionFileL(fileId())));
       
   762 		if(err == KErrNone && client)
       
   763 		    {
       
   764 		    client->SetEnablePubSubNotificationL(enablePubsub);
       
   765 		    }
       
   766 		else if (err != KErrNotFound)
       
   767 		    {
       
   768 		    User::Leave(err);
       
   769 		    }		    
       
   770 		}
       
   771 	}
       
   772 
       
   773 void CAgnServerSession::PanicClientL(TInt aPanic) const
       
   774 	{
       
   775 	_LIT(KAgendaServerPanic,"AgnServer");
       
   776   	iMessage.Panic(KAgendaServerPanic,aPanic);
       
   777 	User::Leave(KClientHasBeenPanicked);
       
   778 	}
       
   779 
       
   780 //
       
   781 // Utility Functions:
       
   782 
       
   783 HBufC* CAgnServerSession::ReadClientDesLC(TInt aDesNum)
       
   784 	{
       
   785 	const TInt KDesLength = iMessage.GetDesLength(aDesNum);
       
   786 	if (KDesLength == KErrArgument)
       
   787 		{
       
   788         PanicClientL(EIndexError);
       
   789 		}
       
   790 	else if (KDesLength == KErrBadDescriptor)
       
   791 		{
       
   792         PanicClientL(EBadDescriptor);
       
   793 		}
       
   794 	User::LeaveIfError(KDesLength);
       
   795 
       
   796 	HBufC* readBuffer = HBufC::NewLC(KDesLength);
       
   797 	TPtr readPtr(readBuffer->Des());
       
   798 
       
   799 	TRAPD(ret, iMessage.ReadL(aDesNum, readPtr));
       
   800 	if (ret != KErrNone)
       
   801 		{
       
   802 		PanicClientL(EBadDescriptor);
       
   803 		}
       
   804 
       
   805 	return readBuffer;
       
   806 	}
       
   807 
       
   808 
       
   809 HBufC8* CAgnServerSession::ReadClientDes8LC(TInt aDesNum)
       
   810 	{
       
   811 	const TInt KDesLength = iMessage.GetDesLength(aDesNum);
       
   812 	if (KDesLength == KErrArgument)
       
   813 		{
       
   814         PanicClientL(EIndexError);
       
   815 		}
       
   816 	else if (KDesLength == KErrBadDescriptor)
       
   817 		{
       
   818         PanicClientL(EBadDescriptor);
       
   819 		}
       
   820 	User::LeaveIfError(KDesLength);
       
   821 	
       
   822 	HBufC8* readBuffer = HBufC8::NewLC(KDesLength);
       
   823 	TPtr8 readPtr(readBuffer->Des());
       
   824 
       
   825 	TRAPD(ret, iMessage.ReadL(aDesNum, readPtr));
       
   826 	if (ret != KErrNone)
       
   827 		{
       
   828 		PanicClientL(EBadDescriptor);
       
   829 		}
       
   830 
       
   831 	return readBuffer;
       
   832 	}	
       
   833 
       
   834 //
       
   835 //Server Functions:
       
   836 void CAgnServerSession::OpenAgendaL()
       
   837 	{
       
   838 	// Open a new file for this session
       
   839 	// Arguments:   0: Input - buffer contains name of file and session ID
       
   840 	//              1: Output - status
       
   841 	//              2: Output - file ID
       
   842 	//              3: Output - collection ID
       
   843 	//
       
   844 
       
   845 	// Get descriptor for filename to open
       
   846 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot0);
       
   847 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
   848 	CleanupStack::PushL(buffer);
       
   849 	buffer->ExpandL(0, KBufferSize);
       
   850 	TPtr8 des(buffer->Ptr(0));
       
   851 	iMessage.ReadL(KSlot0, des);
       
   852 	RDesReadStream readStream(des);
       
   853 	HBufC* fileName = HBufC::NewLC(readStream, KMaxTInt);
       
   854 	TInt sessionId = readStream.ReadInt32L();	
       
   855 	CalCommon::TCalFileVersionSupport status;
       
   856 
       
   857 	HBufC* nameWithPath = iAgnServer.FileMgr()->ParseFilenameLC(*fileName);
       
   858 	CAgnServFile* file = iAgnServer.FileMgr()->GetFile(*nameWithPath);
       
   859 	TInt err = KErrNone;
       
   860 	if(file)
       
   861 		{
       
   862 		if(IsOwnFileL(sessionId, *file))
       
   863 			{//If this file has been opened by same CCalSession object
       
   864 			User::Leave(KErrAlreadyExists);
       
   865 			}
       
   866 		else if (FileHasBeenOpenedL(*file))
       
   867 			{//If this file has been opened by a different CCalSession object
       
   868 			User::Leave(KErrArgument);
       
   869 			} 
       
   870 		}
       
   871 	CleanupStack::PopAndDestroy(nameWithPath);
       
   872 	CloseAgendaL(sessionId);//Check if this CCalSession object has had opened a different file, if so, close it.      
       
   873 	TRAP(err, file = &iAgnServer.FileMgr()->OpenAgendaL(*fileName, iAgnServer, status));
       
   874 	CleanupStack::PopAndDestroy(fileName);
       
   875 	CleanupStack::PopAndDestroy(buffer);
       
   876 	User::LeaveIfError(err);
       
   877 	CleanupStack::PushL(TCleanupItem(CleanupCloseAgendaImmediately, file));
       
   878 	TPckg<TInt> theStatus(status);
       
   879 	iMessage.WriteL(KSlot1, theStatus);
       
   880 
       
   881 	__ASSERT_ALWAYS(file, User::Leave(KErrCorrupt));
       
   882 	TInt64 fileId = file->Model()->GetFileIdL();
       
   883 	TCalCollectionId shortFileId = file->CollectionId();
       
   884 	TPckg<TInt64> fileIdPackage(fileId);
       
   885 	iMessage.WriteL(KSlot2, fileIdPackage);
       
   886 	TPckg<TUint8> shortFileIdPackage(shortFileId);
       
   887 	iMessage.WriteL(KSlot3, shortFileIdPackage);
       
   888 	file->Model()->CategoryIndex().SetCategoryList(&(file->CategoryList()));
       
   889 	if(iAgnSessionFileManager->AddClientL(fileId, sessionId))
       
   890 		{
       
   891 		file->Model()->CheckTzDbModificationL();
       
   892 		}
       
   893 
       
   894 	// This is the cleanup item to close agenda if anything fails
       
   895 	CleanupStack::Pop(); 
       
   896 	}
       
   897 
       
   898 void CAgnServerSession::BackupReStoreChangedL(TInt64 aOldFileId, const CAgnServFile& aServFile, MCalChangeCallBack2::TChangeType aChangeType)
       
   899 	{
       
   900 	if(iAgnSessionFileManager)
       
   901 		{
       
   902 		TAgnChange change;
       
   903 		change.iOperationType = aChangeType;
       
   904 		
       
   905 		//reset model and file id if restore ends
       
   906 		if(aChangeType == MCalChangeCallBack2::ERestoreEnd)
       
   907 			{
       
   908 			iAgnSessionFileManager->ReSetModel(aOldFileId, aServFile);
       
   909 			change.iFileId = aServFile.Model()->GetFileIdL();
       
   910 			}
       
   911 		else
       
   912 			{
       
   913 			change.iFileId = aOldFileId;        
       
   914 			}
       
   915 		
       
   916 		iAgnSessionFileManager->AddChangeL(change);
       
   917 		}
       
   918 
       
   919 	if(aChangeType == MCalChangeCallBack2::EBackupStart || aChangeType == MCalChangeCallBack2::ERestoreStart)
       
   920 	   {
       
   921 	   LockClient(ETrue);
       
   922 	   }
       
   923 	else
       
   924 	   {
       
   925 	   LockClient(EFalse);
       
   926 	   }
       
   927 	}
       
   928 
       
   929 void CAgnServerSession::LockClient(TBool aLock)
       
   930 	{
       
   931 	iBackupRestoreLock = aLock;
       
   932 	}
       
   933 
       
   934 /** 
       
   935 * Closes the calendar file in the current agenda server session immediately or after a delay.
       
   936 * The delay is triggered using a timer owned by the calendar file. If a session then tries to access the same calendar file, the delay is cancelled and the file is not closed
       
   937 * @param aCloseImmediately EFalse if a delay is required before the closure of the calendar file, ETrue if the calendar file is to be closed immediately
       
   938 */
       
   939 void CAgnServerSession::CloseAgendaL()
       
   940 	{
       
   941 	TInt sessionId = iMessage.Int0();
       
   942 	CloseAgendaL(sessionId);
       
   943 	}
       
   944 
       
   945 void CAgnServerSession::CloseAgendaL(TInt aSessionId)
       
   946 	{
       
   947 	if(iAgnSessionFileManager)
       
   948 		{
       
   949 		TInt index = iAgnSessionFileManager->GetSessionFile(aSessionId);
       
   950 		CAgnServFile* file = NULL;
       
   951 		if(index >= 0)
       
   952 			{
       
   953 			TRAPD(err, file = iAgnServer.FileMgr()->GetFileL(iAgnSessionFileManager->GetSessionFileByIndex(index).FileId()));           
       
   954 			if(file && err == KErrNone)
       
   955 				{
       
   956 				User::LeaveIfError(iAgnServer.FileMgr()->CloseAgenda(*file, EFalse));
       
   957 				}       
       
   958 			iAgnSessionFileManager->DeleteSessionFile(aSessionId);           
       
   959 			}
       
   960 		}
       
   961 	}
       
   962 void CAgnServerSession::FetchEntryL()
       
   963 	{
       
   964 	// Fetch an entry from the agenda file
       
   965 	// Arguments: 0 : Output - Data Buffer
       
   966 	//			  1 : Input  - Entry Id to fetch
       
   967 	//			  2 : Output - Size of buffer
       
   968 	//			  3 : Input  - File Id
       
   969 	TPckgBuf<TAgnEntryId> entryId;
       
   970 	iMessage.ReadL(KSlot1, entryId);
       
   971 	
       
   972 	CAgnServFile* file = GetFileL(KSlot3);
       
   973 	if(file->IsLocked())
       
   974 		{
       
   975 		User::Leave(KErrLocked);
       
   976 		}
       
   977 	CAgnEntry* entry = file->Model()->FetchEntryL(entryId());
       
   978 	
       
   979 	if ( entry )
       
   980 		{
       
   981 		CleanupStack::PushL(entry);
       
   982 	
       
   983 		ExternalizeEntryToClientL(*entry, KSlot2);
       
   984 	
       
   985 		CleanupStack::PopAndDestroy(entry);
       
   986 		}
       
   987 	else
       
   988 		{
       
   989 		TPckg<TInt> size(0);
       
   990 		iMessage.WriteL(KSlot2, size);
       
   991 		}	
       
   992 	}
       
   993 
       
   994 
       
   995 void CAgnServerSession::FetchEntryByUIDL()
       
   996 	{
       
   997 	// Fetch an entry from the agenda file
       
   998 	// Arguments: 0 : Output - Data Buffer
       
   999 	//			  1 : Input  - Unique Id to fetch
       
  1000 	//			  2 : Output - Size of buffer
       
  1001 	//			  3 : Input  - File ID
       
  1002 
       
  1003 	TPckgBuf<TCalLocalUid> uniqueId;
       
  1004 	iMessage.ReadL(KSlot1, uniqueId);
       
  1005 	
       
  1006 	CAgnServFile* file = GetFileL(KSlot3);
       
  1007 	if(file->IsLocked())
       
  1008 		{
       
  1009 		User::Leave(KErrLocked);
       
  1010 		}
       
  1011 	CAgnEntry* entry = file->Model()->FetchEntryL(uniqueId());
       
  1012 	
       
  1013 	if ( entry )
       
  1014 		{
       
  1015 		CleanupStack::PushL(entry);
       
  1016 	
       
  1017 		ExternalizeEntryToClientL(*entry, KSlot2);
       
  1018 	
       
  1019 		CleanupStack::PopAndDestroy(entry);
       
  1020 		}
       
  1021 	else
       
  1022 		{
       
  1023 		TPckg<TInt> size(0);
       
  1024 		iMessage.WriteL(KSlot2, size);
       
  1025 		}	
       
  1026 	}
       
  1027 
       
  1028 
       
  1029 void CAgnServerSession::ExternalizeEntryToClientL(const CAgnEntry& aEntry, TInt aSlot)
       
  1030 	{
       
  1031 	delete iBuffer;
       
  1032 	iBuffer = NULL;
       
  1033 		
       
  1034 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1035 
       
  1036 	// Create a write stream for this buffer
       
  1037 	RBufWriteStream bufStream;
       
  1038 	bufStream.Open(*iBuffer);
       
  1039 	CleanupClosePushL(bufStream);	
       
  1040 
       
  1041 	bufStream.WriteUint32L( aEntry.Type() );
       
  1042 	aEntry.ExternalizeToBufferL(bufStream);
       
  1043 
       
  1044 	bufStream.CommitL();
       
  1045 
       
  1046 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1047 
       
  1048 	// Send it back to the client
       
  1049 	TPckg<TInt> size(iBuffer->Size());
       
  1050 	iMessage.WriteL(aSlot, size);	
       
  1051 	}
       
  1052 
       
  1053 
       
  1054 void CAgnServerSession::TransmitBufferL()
       
  1055 	{
       
  1056 	// Transmit the contents of the buffer stream to the client,
       
  1057 	// then delete it
       
  1058 	// Arguments: 0 : Output - Data Buffer
       
  1059 
       
  1060 	if (!iBuffer)
       
  1061 		{
       
  1062 		PanicClientL(EBadRequest);	
       
  1063 		}
       
  1064 	iMessage.WriteL(KSlot0, iBuffer->Ptr(0));
       
  1065 
       
  1066 	delete iBuffer;
       
  1067 	iBuffer = NULL;
       
  1068 	}
       
  1069 
       
  1070 
       
  1071 void CAgnServerSession::FetchSimpleEntryL()
       
  1072 	{
       
  1073 	// Fetch a lite-entry from the server
       
  1074 	// (A lite entry consists of time information without any text)
       
  1075 	// Arguments: 0 : Output - Data buffer
       
  1076 	//			  1 : Input  - TAgnInstace
       
  1077 	//			  2 : Output - Size of buffer
       
  1078 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot1);
       
  1079 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1080 	CleanupStack::PushL(buffer);
       
  1081 	buffer->ExpandL(0, KBufferSize);
       
  1082 	TPtr8 des(buffer->Ptr(0));
       
  1083 	iMessage.ReadL(KSlot1, des);
       
  1084 	RDesReadStream readStream(des);
       
  1085 	TAgnEntryId entryId;
       
  1086 	readStream >> entryId;
       
  1087 	CleanupStack::PopAndDestroy(buffer);
       
  1088 
       
  1089 	// Make sure this entry hasn't been deleted or updated		TAgnInstanceId entryId = (*entryIds)[ii].iId;
       
  1090 	TCalCollectionId collectionId = iMessage.Int3();
       
  1091 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(collectionId);
       
  1092 	if(file->IsLocked())
       
  1093 		{
       
  1094 		User::Leave(KErrLocked);
       
  1095 		}
       
  1096 
       
  1097 	const CAgnSimpleEntry* KEntry = file->Model()->GetSimpleEntryFromIndexes(entryId);
       
  1098 
       
  1099 	if ( KEntry )
       
  1100 		{
       
  1101 		delete iBuffer;
       
  1102 		iBuffer = NULL;
       
  1103 
       
  1104 		iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1105 
       
  1106 		// Create a write stream for this buffer
       
  1107 		RBufWriteStream bufStream;
       
  1108 		bufStream.Open(*iBuffer);
       
  1109 		CleanupClosePushL(bufStream);	
       
  1110 
       
  1111 		// Write a bool to indicate if entry is available
       
  1112 		bufStream.WriteUint8L(KEntry != NULL);
       
  1113 
       
  1114 		bufStream.WriteUint32L(KEntry->Type());
       
  1115 		KEntry->ExternalizeL(bufStream, ETrue);
       
  1116 
       
  1117 		bufStream.CommitL();
       
  1118 
       
  1119 		CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1120 
       
  1121 		// Send it back to the client
       
  1122 		TPckg<TInt> size(iBuffer->Size());
       
  1123 		iMessage.WriteL(KSlot2, size);
       
  1124 		}
       
  1125 	else
       
  1126 		{
       
  1127 		TPckg<TInt> emptyBuffer(0);
       
  1128 		iMessage.WriteL(KSlot2, emptyBuffer);
       
  1129 		}
       
  1130 	}
       
  1131 
       
  1132 void CAgnServerSession::FetchSimpleEntryByUIDL()
       
  1133 	{
       
  1134 	// Fetch a lite-entry from the server
       
  1135 	// (A lite entry is consists of time information without any text)
       
  1136 	// Arguments: 0 : Output - Data buffer
       
  1137 	//			  1 : Input  - TAgnInstace
       
  1138 	//			  2 : Output - Size of buffer
       
  1139 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot1);
       
  1140 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1141 	CleanupStack::PushL(buffer);
       
  1142 	buffer->ExpandL(0, KBufferSize);
       
  1143 	TPtr8 des(buffer->Ptr(0));
       
  1144 	iMessage.ReadL(KSlot1, des);
       
  1145 	RDesReadStream readStream(des);	
       
  1146 	TUint32 entryId = readStream.ReadUint32L();
       
  1147 	CleanupStack::PopAndDestroy(buffer);
       
  1148 
       
  1149 	TCalCollectionId collectionId = iMessage.Int3();
       
  1150 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(collectionId );
       
  1151 	if(file->IsLocked())
       
  1152 		{
       
  1153 		User::Leave(KErrLocked);
       
  1154 		}
       
  1155 	// Make sure this entry hasn't been deleted or updated
       
  1156 	const CAgnSimpleEntry* KEntry = file->Model()->GetSimpleEntryFromIndexes(entryId);
       
  1157 
       
  1158 	if ( KEntry )
       
  1159 		{
       
  1160 		delete iBuffer;
       
  1161 		iBuffer = NULL;
       
  1162 
       
  1163 		iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1164 
       
  1165 		// Create a write stream for this buffer
       
  1166 		RBufWriteStream bufStream;
       
  1167 		bufStream.Open(*iBuffer);
       
  1168 		CleanupClosePushL(bufStream);	
       
  1169 
       
  1170 		// Write a bool to indicate if entry is available
       
  1171 		bufStream.WriteUint8L(KEntry != NULL);
       
  1172 
       
  1173 		bufStream.WriteUint32L(KEntry->Type());
       
  1174 		KEntry->ExternalizeL(bufStream, ETrue);
       
  1175 		bufStream.CommitL();
       
  1176 
       
  1177 		CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1178 
       
  1179 		// Send it back to the client
       
  1180 		TPckg<TInt> size(iBuffer->Size());
       
  1181 		iMessage.WriteL(KSlot2, size);
       
  1182 		}
       
  1183 	else
       
  1184 		{
       
  1185 		TPckg<TInt> emptyBuffer(0);
       
  1186 		iMessage.WriteL(KSlot2, emptyBuffer);
       
  1187 		}
       
  1188 	}
       
  1189 
       
  1190 void CAgnServerSession::EnsureStringsLoadedL(CAgnEntry& aEntry, TUint8 aShortFileId)
       
  1191 	{
       
  1192 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(aShortFileId);
       
  1193 	if (!aEntry.SummaryIsLoaded())
       
  1194 		{
       
  1195 		HBufC* summary = file->Model()->RestoreTextL(aEntry.SummaryStreamId());
       
  1196 		aEntry.SetSummary(summary);
       
  1197 		}
       
  1198 
       
  1199 	if (!aEntry.DescriptionIsLoaded())
       
  1200 		{
       
  1201 		HBufC* description = file->Model()->RestoreTextL(aEntry.DescriptionStreamId());
       
  1202 		aEntry.SetDescription(description);
       
  1203 		}
       
  1204 	}
       
  1205 		
       
  1206 void CAgnServerSession::FetchSimpleEntriesL()
       
  1207 	{
       
  1208 	// Fetch an array of lite-entries from the server
       
  1209 	// (A lite entry consists of time information without any text)
       
  1210 	// Arguments: 0 : Output - Data buffer
       
  1211 	//			  1 : Input  - TArray<TAgnEntryId> to fetch
       
  1212 	//			  2 : Output - Size of buffer
       
  1213 
       
  1214 	CArrayFixSeg<TAgnInstance>* instanceIds = new (ELeave) CArrayFixSeg<TAgnInstance>(8);
       
  1215 	CleanupStack::PushL(instanceIds);
       
  1216 	
       
  1217 	const TInt KDesLength = iMessage.GetDesLength(KSlot1);
       
  1218 	if(KDesLength<0)
       
  1219 		{
       
  1220 		User::Leave(KErrArgument);
       
  1221 		}
       
  1222 
       
  1223 	CBufFlat* buffer = CBufFlat::NewL(KDesLength);
       
  1224 	CleanupStack::PushL(buffer);
       
  1225 	
       
  1226 	buffer->ExpandL(0, KDesLength);
       
  1227 	TPtr8 des(buffer->Ptr(0));
       
  1228 	iMessage.ReadL(KSlot1, des);
       
  1229 
       
  1230 	RBufReadStream readStream;
       
  1231 	readStream.Open(*buffer);
       
  1232 	CleanupClosePushL(readStream);
       
  1233 	
       
  1234 	const TInt KIdCount1 = readStream.ReadUint32L();
       
  1235 	
       
  1236 	for ( TInt i = 0; i < KIdCount1; ++i )
       
  1237 		{
       
  1238 		TAgnInstance instance;
       
  1239 		instance.InternalizeL(readStream);
       
  1240 		instanceIds->AppendL(instance);
       
  1241 		}
       
  1242 		
       
  1243 	CleanupStack::PopAndDestroy(&readStream);	// readStream.Close();
       
  1244 
       
  1245 	CleanupStack::PopAndDestroy(buffer);		// buffer
       
  1246 	
       
  1247 	delete iBuffer;
       
  1248 	iBuffer = NULL;
       
  1249 
       
  1250 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1251 	
       
  1252 	// Create a write stream for this buffer
       
  1253 	RBufWriteStream bufStream;
       
  1254 	bufStream.Open(*iBuffer);
       
  1255 	CleanupClosePushL(bufStream);	
       
  1256 	
       
  1257 	const TInt KIdCount2 = instanceIds->Count();
       
  1258 	
       
  1259 	bufStream.WriteUint8L(KIdCount2);
       
  1260 	
       
  1261 	for ( TInt ii = 0; ii < KIdCount2 ; ++ii )
       
  1262 		{
       
  1263 #if defined (__CAL_VERBOSE_LOGGING__) || defined (__CAL_ENTRY_LOGGING__)
       
  1264 		CAgnServFile* agnFile = iAgnServer.FileMgr()->GetFile((*instanceIds)[ii].iCollectionId);
       
  1265 		CAgnEntry* fullEntry = agnFile->Model()->FetchEntryL((*instanceIds)[ii]);
       
  1266 		CleanupStack::PushL(fullEntry);
       
  1267 		AgmDebug::DebugLog("FetchSimpleEntriesL - Fetch entry with Id %d", (*instanceIds)[ii].Value());
       
  1268 		EnsureStringsLoadedL(*fullEntry, *entryIds[ii].iCollectionId);
       
  1269 		AgmDebug::DebugLogEntryL(*fullEntry, EDumpEntryAll);
       
  1270 		CleanupStack::PopAndDestroy(fullEntry);
       
  1271 #endif
       
  1272 		TAgnInstanceId entryId = (*instanceIds)[ii].iId;
       
  1273 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL((*instanceIds)[ii].iCollectionId);
       
  1274 		if(file->IsLocked())
       
  1275 			{
       
  1276 			User::Leave(KErrLocked);
       
  1277 			}
       
  1278 		const CAgnSimpleEntry* KEntry = file->Model()->GetSimpleEntryFromIndexes(entryId);
       
  1279 		
       
  1280 		// Write a bool to indicate if entry is available
       
  1281 		bufStream.WriteUint8L(KEntry != NULL);
       
  1282 		
       
  1283 		if ( KEntry )
       
  1284 			{
       
  1285 			bufStream.WriteUint32L(KEntry->Type());
       
  1286 			KEntry->ExternalizeL(bufStream, ETrue);
       
  1287 			bufStream.WriteUint8L((*instanceIds)[ii].iCollectionId);
       
  1288 			}
       
  1289 		}
       
  1290 
       
  1291 	bufStream.CommitL();
       
  1292 	
       
  1293 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1294 	
       
  1295 	CleanupStack::PopAndDestroy(instanceIds);
       
  1296 
       
  1297 	// Send it back to the client
       
  1298 	TPckg<TInt> size(iBuffer->Size());
       
  1299 	iMessage.WriteL(KSlot2, size);
       
  1300 	}
       
  1301 
       
  1302 void CAgnServerSession::UpdateEntryL()
       
  1303 	{
       
  1304 	// Updates an entry on the server
       
  1305 	// Arguments: 0 : Input  - Size of buffer
       
  1306 	//            1 : Input  - Data Buffer (containing entry data)
       
  1307 	//		      2 : Output - Entry Id of updated entry
       
  1308 	//			  3 : File ID	
       
  1309 	
       
  1310 	// Restore length
       
  1311 	const TInt KBufferSize = iMessage.Int0();
       
  1312 	
       
  1313 	// Restore buffer
       
  1314 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1315 	CleanupStack::PushL(buffer);
       
  1316 
       
  1317 	buffer->ExpandL(0, KBufferSize);
       
  1318 	TPtr8 des(buffer->Ptr(0));
       
  1319 	iMessage.ReadL(KSlot1, des);
       
  1320 
       
  1321 	// Internalize the data from the stream
       
  1322 	RBufReadStream readStream;
       
  1323 	readStream.Open(*buffer);
       
  1324 	CleanupClosePushL(readStream);
       
  1325 
       
  1326 	const CCalEntry::TType KEntryType = static_cast<CCalEntry::TType>(readStream.ReadUint32L());
       
  1327 
       
  1328 	TBool deleteChildren = readStream.ReadUint8L();
       
  1329 
       
  1330 	CAgnEntry* entry = CAgnEntry::NewL(KEntryType);
       
  1331 	CleanupStack::PushL(entry);
       
  1332 
       
  1333 	entry->InternalizeFromBufferL(readStream);
       
  1334 
       
  1335 	_DBGLOG_ENTRY(AgmDebug::DebugLog("Updating calendar file with entry");)
       
  1336 	_DBGLOG_ENTRY(AgmDebug::DebugLogEntryL(*entry, EDumpEntryAll);)
       
  1337 
       
  1338 	TCalCollectionId collectionId = iMessage.Int3();
       
  1339 	CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(collectionId);
       
  1340 	client.UpdateEntryL(*entry, deleteChildren);
       
  1341 	_DBGLOG_ENTRY(AgmDebug::DebugLog("Entry: Updated entry on file. Entry ID: %d",entry->EntryId().Value());)
       
  1342 
       
  1343 	// Return entry id
       
  1344 	TPckg<TAgnEntryId> entryPckg(entry->EntryId());
       
  1345 	iMessage.WriteL(KSlot2, entryPckg);
       
  1346 
       
  1347 	CleanupStack::PopAndDestroy(entry);
       
  1348 	CleanupStack::PopAndDestroy(&readStream); // readStream.Close();	
       
  1349 	CleanupStack::PopAndDestroy(buffer);
       
  1350 	}
       
  1351 
       
  1352 void CAgnServerSession::AddChangeL(const TAgnChange& aChange)
       
  1353     {
       
  1354     if(iAgnSessionFileManager)
       
  1355         {
       
  1356         iAgnSessionFileManager->AddChangeL(aChange);
       
  1357         }
       
  1358  	}
       
  1359 
       
  1360 void CAgnServerSession::AddEntryL()
       
  1361 	{
       
  1362 	// Adds an entry to the server
       
  1363 	// Arguments: 0 : Input  - Size of buffer
       
  1364 	//            1 : Input  - Data Buffer (containing entry data)
       
  1365 	//		      2 : Output - Ids of updated entry
       
  1366 	//            3 : Input  - File Id
       
  1367 		
       
  1368 
       
  1369 	// Restore length
       
  1370 	const TInt KBufferSize = iMessage.Int0();
       
  1371 	
       
  1372 	// Restore buffer
       
  1373 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1374 	CleanupStack::PushL(buffer);
       
  1375 
       
  1376 	buffer->ExpandL(0, KBufferSize);
       
  1377 	TPtr8 des(buffer->Ptr(0));
       
  1378 	iMessage.ReadL(KSlot1, des);
       
  1379 
       
  1380 	// Internalize the data from the stream
       
  1381 	RBufReadStream readStream;
       
  1382 	readStream.Open(*buffer);
       
  1383 	CleanupClosePushL(readStream);
       
  1384 
       
  1385 	const CCalEntry::TType KEntryType = (CCalEntry::TType) readStream.ReadUint32L();
       
  1386 	CAgnEntry* entry = CAgnEntry::NewL(KEntryType);
       
  1387 	CleanupStack::PushL(entry);
       
  1388 
       
  1389 	entry->InternalizeFromBufferL(readStream);
       
  1390 
       
  1391 	TAgnEntryParameters params;
       
  1392 	TPckgBuf<TInt64> fileId;
       
  1393 	iMessage.ReadL(KSlot3, fileId);
       
  1394 	CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileId());
       
  1395 	params.iEntryId = client.StoreEntryL(*entry);
       
  1396 	params.iLocalId = entry->LocalUid();
       
  1397 	params.iRecurrenceId = entry->RecurrenceId().LocalL();
       
  1398 	params.iLastModifiedDateUtc = entry->LastModifiedDateUtc();
       
  1399 	params.iRecurrenceRange = entry->RecurrenceRange();
       
  1400 
       
  1401 	if (entry->TimeMode() != MAgnCalendarTimeMode::EFloating &&	entry->RptDef() != NULL )
       
  1402 		{
       
  1403 		CAgnTzRules* tzRules = entry->RptDef()->AgnTzRules();
       
  1404 		if(tzRules != NULL)
       
  1405 			{
       
  1406 			params.iTzStreamId = (tzRules->TzZoneStreamId());
       
  1407 			params.iSystemTzRule = (tzRules->SystemTzRule());
       
  1408 			}
       
  1409 		}
       
  1410 	
       
  1411 	// Set entry Id and unique Id
       
  1412 	TPckg<TAgnEntryParameters> paramsPckg(params);
       
  1413  	iMessage.WriteL(KSlot2, paramsPckg);
       
  1414 
       
  1415 	CleanupStack::PopAndDestroy(entry);			// entry
       
  1416 	CleanupStack::PopAndDestroy(&readStream);	// readStream.Close();
       
  1417 	CleanupStack::PopAndDestroy(buffer);		// buffer
       
  1418 	}
       
  1419 
       
  1420 /**
       
  1421 Called when a new attachment is stored with a file handle.
       
  1422 The file handle is transferred to the server side and the file is moved to the Calendar store.
       
  1423 */
       
  1424 void CAgnServerSession::TransferAttachmentFileToServerL()
       
  1425 	{
       
  1426 	// Arguments: 0 - Output	: Attachment Data - local UID of entry and index of attachment on that entry
       
  1427 	//			  1 - Input		: Attachment UID of new attachment
       
  1428 	//			  2,3 - FS		: Used by file server to transfer file from client to agenda server
       
  1429 	
       
  1430 	RFile file;
       
  1431 	CleanupClosePushL(file);
       
  1432 	
       
  1433 	User::LeaveIfError(file.AdoptFromClient(iMessage, KTransferAttachmentToSrvFsArgIndex, KTransferAttachmentToSrvFileArgIndex));
       
  1434 	
       
  1435 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot0);
       
  1436 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1437 	CleanupStack::PushL(buffer);
       
  1438 	buffer->ExpandL(0, KBufferSize);
       
  1439 
       
  1440 	TPtr8 des(buffer->Ptr(0));
       
  1441 	iMessage.ReadL(KSlot0, des);
       
  1442 	
       
  1443 	RDesReadStream readStream(des);
       
  1444 	TCalLocalUid localUid = readStream.ReadUint32L();
       
  1445 	TInt attachmentIndex = readStream.ReadInt16L();
       
  1446 	TInt64 fileId;
       
  1447 	readStream >> fileId;	
       
  1448 	
       
  1449 	CAgnServFile* agnFile = iAgnServer.FileMgr()->GetFileL(fileId);
       
  1450 	TPckg<TCalAttachmentUid> attachUid = agnFile->Model()->TransferAttachmentFileToServerL(file, localUid, attachmentIndex);
       
  1451 	iMessage.WriteL(1, attachUid);
       
  1452 	CleanupStack::PopAndDestroy();
       
  1453 	CleanupStack::PopAndDestroy(&file); // file.Close()
       
  1454 	}
       
  1455 	
       
  1456 void CAgnServerSession::MoveFileToServerL()
       
  1457 	{
       
  1458 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot0);
       
  1459 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1460 	CleanupStack::PushL(buffer);
       
  1461 	buffer->ExpandL(0, KBufferSize);
       
  1462 
       
  1463 	TPtr8 des(buffer->Ptr(0));
       
  1464 	iMessage.ReadL(KSlot0, des);
       
  1465 	
       
  1466 	RDesReadStream readStream(des);
       
  1467 	TCalLocalUid localUid = readStream.ReadUint32L();
       
  1468 	TInt attachmentIndex = readStream.ReadInt16L();
       
  1469 	TInt64 fileId;
       
  1470 	readStream >> fileId;	
       
  1471 	
       
  1472 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  1473 	TPckg<TCalAttachmentUid> attachUid = file->Model()->MoveFileToServerL(localUid, attachmentIndex);
       
  1474 	iMessage.WriteL(1, attachUid);
       
  1475 	CleanupStack::PopAndDestroy();
       
  1476 	}
       
  1477 /**
       
  1478 Called when a file attachment is fetched from the client.
       
  1479 The file handle is opened on the server side then transferred to the client.
       
  1480 */
       
  1481 void CAgnServerSession::TransferAttachmentFileToClientL()
       
  1482 	{
       
  1483 	// Arguments: 0 - Output	: Attachment UID of file attachment to send to client
       
  1484 	//			  1 - FS		: Used by file server to transfer file from agenda server to client
       
  1485 	//			  2 - File Id   : Long file id of the calendar file
       
  1486 	TCalAttachmentUid attachmentUid = iMessage.Int0();
       
  1487 
       
  1488 	RFile file;
       
  1489 	CleanupClosePushL(file);
       
  1490 	
       
  1491 	TPckgBuf<TInt64> fileId;
       
  1492 	iMessage.ReadL(KSlot2, fileId);
       
  1493 	CAgnServFile* agnServfile = iAgnServer.FileMgr()->GetFileL(fileId());
       
  1494 	agnServfile->Model()->OpenAttachmentFileL(file, attachmentUid);
       
  1495 	
       
  1496 	TPckg<TInt> pckgSubSessionHandle(file.SubSessionHandle()); 
       
  1497 	iMessage.WriteL(KTransferAttachmentToCliFileArgIndex, pckgSubSessionHandle);
       
  1498 	
       
  1499 	User::LeaveIfError(file.TransferToClient(iMessage, KTransferAttachmentToCliFileArgIndex));
       
  1500 	
       
  1501 	CleanupStack::PopAndDestroy(&file); // file.Close()
       
  1502 	}
       
  1503 
       
  1504 /**
       
  1505 Called when a new attachment is stored with binary data.
       
  1506 The new file handle is opened on the server side, then transferred to the client side where the data is written directly onto the file.
       
  1507 This means that the binary data is not passed directly over IPC.
       
  1508 */
       
  1509 void CAgnServerSession::TransferFileToClientToWriteL()
       
  1510 	{
       
  1511 	// Arguments: 0 - Output	: Attachment data of new file attachment to be created
       
  1512 	//			  1 - FS		: Used by file server to transfer new file from agenda server to client
       
  1513 	//			  2 - Input     : File Id
       
  1514 	// 			  3 - Output	: Size of attachment data that will be written to file handle on client side
       
  1515 	TAttachmentData data;
       
  1516 	TPckg<TAttachmentData> pckgData(data);
       
  1517 	iMessage.ReadL(0, pckgData);
       
  1518 	TInt dataSize = iMessage.Int3();
       
  1519 	
       
  1520 	RFile file;
       
  1521 	CleanupClosePushL(file);
       
  1522 	
       
  1523 	TPckgBuf<TInt64> fileId;
       
  1524 	iMessage.ReadL(KSlot2, fileId);
       
  1525 	CAgnServFile* agnServFile = iAgnServer.FileMgr()->GetFileL(fileId());
       
  1526 	HBufC* fileName = agnServFile->Model()->GenerateRandomFilenameLC(data.iDrive);
       
  1527 	agnServFile->Model()->CreateNewFileL(file, *fileName);
       
  1528 	agnServFile->Model()->UpdateAttachmentDetailsL(data.iLocalUid, data.iAttachmentIndex, *fileName, dataSize);
       
  1529 	CleanupStack::PopAndDestroy(fileName);
       
  1530 	
       
  1531 	TPckg<TInt> pckgSubSessionHandle(file.SubSessionHandle()); 
       
  1532 	iMessage.WriteL(KTransferAttachmentToCliFileArgIndex, pckgSubSessionHandle);
       
  1533 	User::LeaveIfError(file.TransferToClient(iMessage, KTransferAttachmentToCliFileArgIndex));
       
  1534 	
       
  1535 	CleanupStack::PopAndDestroy(&file); // file.Close()
       
  1536 	}
       
  1537 
       
  1538 /**
       
  1539 Fetches attachment UIDs of all file attachments in the order specified in CCalAttachmentManager::FetchAttachmentsL.
       
  1540 */
       
  1541 void CAgnServerSession::FetchSortedAttachmentsL()
       
  1542 	{
       
  1543 	// Arguments: 0 - Output	: Data buffer (containing list of TCalLocalUid's of entries)
       
  1544 	//			  1 - Output	: Size of data buffer
       
  1545 	//			  2 - Input		: Sort order
       
  1546 	//			  3 - Input     : File Id
       
  1547 	
       
  1548 	TUint32 sortOrder = iMessage.Int2();
       
  1549 
       
  1550 	RArray<TCalAttachmentUid> attachmentIds;
       
  1551 	CleanupClosePushL(attachmentIds);
       
  1552 	
       
  1553 	TPckgBuf<TInt64> fileId;
       
  1554 	iMessage.ReadL(KSlot3, fileId);
       
  1555 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  1556 	if(file->IsLocked())
       
  1557 		{
       
  1558 		User::Leave(KErrLocked);
       
  1559 		}
       
  1560 
       
  1561 	file->Model()->GetSortedAttachmentsL(attachmentIds, static_cast<CCalAttachmentManager::TSortOrder>(sortOrder));
       
  1562 	
       
  1563 	WriteIntArrayToBufferL(attachmentIds);
       
  1564 
       
  1565 	CleanupStack::PopAndDestroy(&attachmentIds); // attachmentIds->Close()
       
  1566 
       
  1567 	// Send it back to the client
       
  1568 	TPckg<TInt> listsize(iBuffer->Size());
       
  1569 	iMessage.WriteL(KSlot1, listsize);
       
  1570 	}
       
  1571 
       
  1572 void CAgnServerSession::WriteIntArrayToBufferL(const RArray<TUint32>& aArray)
       
  1573 	{
       
  1574 	// Create a write stream for this buffer
       
  1575 	const TInt KCount = aArray.Count();
       
  1576 	
       
  1577 	// Buffer contains enough space for KCount integers and a count
       
  1578 	const TInt KSizeOfBuffer = (KCount + 1) * sizeof(TUint32);
       
  1579 	
       
  1580 	delete iBuffer;
       
  1581 	iBuffer = NULL;
       
  1582 	
       
  1583 	iBuffer = CBufFlat::NewL(KSizeOfBuffer);
       
  1584 	RBufWriteStream bufStream;
       
  1585 	bufStream.Open(*iBuffer);
       
  1586 	CleanupClosePushL(bufStream);	
       
  1587 
       
  1588 	// Externalize the list 
       
  1589 	bufStream.WriteUint32L(KCount);
       
  1590 
       
  1591 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  1592 		{
       
  1593 		bufStream << aArray[ii];
       
  1594 		}
       
  1595 
       
  1596 	bufStream.CommitL();
       
  1597 	
       
  1598 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1599 	}
       
  1600 
       
  1601 /**
       
  1602 Fetches all file attachments with the attachment specified by the UID. 
       
  1603 This is called from CCalAttachmentManager::EntriesReferencingFileAttachmentL.
       
  1604 */
       
  1605 void CAgnServerSession::EntriesWithAttachmentL()
       
  1606 	{
       
  1607 	// Arguments: 0 - Output	: Data buffer (containing list of TCalLocalUid's of entries)
       
  1608 	//			  1 - Output	: Size of data buffer
       
  1609 	//			  2 - Input		: attachment Uid
       
  1610 	//			  3 - Input     : File Id
       
  1611 	TCalAttachmentUid attachUid = iMessage.Int2();
       
  1612 	TPckgBuf<TInt64> fileId;
       
  1613 	iMessage.ReadL(KSlot3, fileId);
       
  1614 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  1615 	if(file->IsLocked())
       
  1616 		{
       
  1617 		User::Leave(KErrLocked);
       
  1618 		}
       
  1619 
       
  1620 	const RArray<TCalLocalUid>* KUniqueIdList = file->Model()->GetEntriesWithAttachment(attachUid);
       
  1621 
       
  1622 	WriteIntArrayToBufferL(*KUniqueIdList);
       
  1623 	
       
  1624 	// Send it back to the client
       
  1625 	TPckg<TInt> listsize(iBuffer->Size());
       
  1626 	iMessage.WriteL(KSlot1, listsize);
       
  1627 	}
       
  1628 
       
  1629 /**
       
  1630 Fetches a file attachment by its UID.
       
  1631 Attachment UIDs are not exposed to the user. This function is used in the CCalAttachmentIterator.
       
  1632 */
       
  1633 void CAgnServerSession::FetchAttachmentByIdL()
       
  1634 	{
       
  1635 	// Get a list of file names held by the server 
       
  1636 	// currently setup extractor
       
  1637 	// Arguments: 0 : Output - Data buffer 
       
  1638 	//			   1 : Output - Size of buffer
       
  1639 	//			   2 : Input - attachment uid
       
  1640 	//			   3 : Input - File Id
       
  1641 
       
  1642 	TCalAttachmentUid attachUid = iMessage.Int2();
       
  1643 	TPckgBuf<TInt64> fileId;
       
  1644 	iMessage.ReadL(KSlot3, fileId);
       
  1645 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  1646 	if(file->IsLocked())
       
  1647 		{
       
  1648 		User::Leave(KErrLocked);
       
  1649 		}
       
  1650 
       
  1651 	CAgnAttachment* attachmentToWrite = file->Model()->FetchAttachmentByIdL(attachUid);
       
  1652 
       
  1653 	if ( attachmentToWrite )
       
  1654 		{
       
  1655 		CleanupStack::PushL(attachmentToWrite);
       
  1656 
       
  1657 		delete iBuffer;
       
  1658 		iBuffer = NULL;
       
  1659 
       
  1660 		iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1661 
       
  1662 		// Create a write stream for this buffer
       
  1663 		RBufWriteStream bufStream;
       
  1664 		bufStream.Open(*iBuffer);
       
  1665 		CleanupClosePushL(bufStream);
       
  1666 	
       
  1667 		attachmentToWrite->ExternalizeL(bufStream);
       
  1668 			
       
  1669 		bufStream.CommitL();
       
  1670 
       
  1671 		CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1672 		CleanupStack::PopAndDestroy(attachmentToWrite);
       
  1673 
       
  1674 		// Send it back to the client
       
  1675 		TPckg<TInt> size(iBuffer->Size());
       
  1676 		iMessage.WriteL(KSlot1, size);
       
  1677 		}
       
  1678 	else
       
  1679 		{
       
  1680 		TPckg<TInt> emptyBuffer(0);
       
  1681 		iMessage.WriteL(KSlot1, emptyBuffer);
       
  1682 		}
       
  1683 	}
       
  1684 
       
  1685 void CAgnServerSession::PreviousInstancesL()
       
  1686 	{
       
  1687 	// Gets the time of the previous instance to today
       
  1688 	// Arguments: 0 : output data buffer
       
  1689 	//			  1 : size of output data buffer
       
  1690 	//			  2 : input data buffer
       
  1691 	//			  3 : size of input data buffer
       
  1692 
       
  1693 	// Restore length
       
  1694 	const TInt KBufferSize = iMessage.Int3();
       
  1695 	
       
  1696 	const TInt KInstanceArrayGranularity = 16;
       
  1697 	CArrayFixSeg<TAgnSortInstance>* instances = new (ELeave) CArrayFixSeg<TAgnSortInstance>(KInstanceArrayGranularity);
       
  1698 	CleanupStack::PushL(instances);
       
  1699 
       
  1700 	// Restore buffer
       
  1701 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1702 	CleanupStack::PushL(buffer);
       
  1703 	buffer->ExpandL(0, KBufferSize);
       
  1704 
       
  1705 	TPtr8 des(buffer->Ptr(0));
       
  1706 	iMessage.ReadL(KSlot2, des);
       
  1707 	
       
  1708 	TFindInstanceParams parameters;
       
  1709 	
       
  1710 	RDesReadStream readStream(des);
       
  1711 	
       
  1712 	parameters.InternalizeL(readStream);
       
  1713 
       
  1714 	TInt filecount = readStream.ReadInt16L();
       
  1715 	for(TInt ii=0;ii<filecount;++ii)
       
  1716 		{
       
  1717 		TInt64 fileId;
       
  1718 		readStream >> fileId;
       
  1719 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  1720 		if(file->IsLocked())
       
  1721 			{
       
  1722 			User::Leave(KErrLocked);
       
  1723 			}
       
  1724 		CAgnEntryModel* model = file->Model();
       
  1725 		model->PreviousPossibleInstancesL(*instances, parameters);
       
  1726 		}
       
  1727 
       
  1728 	CleanupStack::PopAndDestroy(buffer);
       
  1729 
       
  1730 	const CAgnSimpleEntry* searchFromEntry = NULL;
       
  1731 	if(parameters.iInstance.iCollectionId > 0)
       
  1732 		{//If the iInstance.iFileId ==0, instances should be found from the start date of the searching range so there is no searchFromEntry
       
  1733 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(parameters.iInstance.iCollectionId);
       
  1734 		if(file->IsLocked())
       
  1735 			{
       
  1736 			User::Leave(KErrLocked);
       
  1737 			}
       
  1738 		searchFromEntry = file->Model()->GetSimpleEntryFromIndexes(parameters.iInstance.iId);
       
  1739 		}
       
  1740 	
       
  1741 	TAgnSortInstance searchFromInstance(*searchFromEntry);
       
  1742 	
       
  1743 	if (searchFromEntry)
       
  1744 		{
       
  1745 		TAgnDaySortKey sortKey(AgnDateTime::MaxDate(), parameters.iUndatedTodoTimeLocal);
       
  1746 		searchFromInstance.SetL(parameters.iInstance.iId.Date().LocalL(), parameters.iUndatedTodoTimeLocal);
       
  1747 		const_cast<CAgnSimpleEntry&>(searchFromInstance.SimpleEntry()).SetCollectionId(parameters.iInstance.iCollectionId);
       
  1748 		//the search from instance must match the filter settings
       
  1749 		__ASSERT_ALWAYS(searchFromInstance.CheckStartAndEndDateOverlap(parameters), User::Leave(KErrNotFound));
       
  1750 		
       
  1751 		// remove all instances before and including the searched from instance
       
  1752 		TInt thisPosition(0);
       
  1753 		User::LeaveIfError(instances->FindIsq(searchFromInstance, sortKey, thisPosition));
       
  1754 		instances->Delete(thisPosition, instances->Count() - thisPosition);
       
  1755 		}
       
  1756 	else if (!parameters.iInstance.iId.IsNullId())
       
  1757 		{
       
  1758 		// The entry searched has been deleted or the entry id is wrong
       
  1759 		User::Leave(KErrNotFound);
       
  1760 		}
       
  1761 	else
       
  1762 		{
       
  1763 		// we did not search from a specified instance
       
  1764 		// so remove all instances that are after and including the start time
       
  1765 		for (TInt i(instances->Count() - 1) ; i >= 0 && instances->At(i).InstanceDate() >= parameters.iInstance.iId.Date().LocalL() ; --i)
       
  1766 			{
       
  1767 			instances->Delete(i);
       
  1768 			}
       
  1769 		}
       
  1770 	
       
  1771 	// Truncate the list to the length of aSearchParams.iNumInstances by removeing instances from the end
       
  1772 	if (instances->Count() > parameters.iNumInstances)
       
  1773 		{
       
  1774 		instances->Delete(0, instances->Count() - parameters.iNumInstances);
       
  1775 		}
       
  1776 	delete iBuffer;
       
  1777 	iBuffer = NULL;
       
  1778 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1779 
       
  1780 	// Create a write stream for this buffer
       
  1781 	RBufWriteStream bufStream;
       
  1782 	bufStream.Open(*iBuffer);
       
  1783 	CleanupClosePushL(bufStream);
       
  1784 
       
  1785 	const TInt KInstanceCount(instances->Count());
       
  1786 
       
  1787 	bufStream.WriteUint32L(KInstanceCount);
       
  1788 
       
  1789 	for (TInt i(0) ; i < KInstanceCount ; ++i)
       
  1790 		{
       
  1791 		TAgnInstance instance;
       
  1792 		instance.iId = instances->At(i).InstanceIdL();
       
  1793 		instance.iCollectionId = (*instances)[i].SimpleEntry().CollectionId();
       
  1794 		bufStream << instance;
       
  1795 		}
       
  1796 
       
  1797 	bufStream.CommitL();
       
  1798 
       
  1799 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1800 	CleanupStack::PopAndDestroy(instances);
       
  1801 
       
  1802 	// Send it back to the client
       
  1803 	TPckg<TInt> size(iBuffer->Size());
       
  1804 	iMessage.WriteL(KSlot1, size);
       
  1805 	}
       
  1806 
       
  1807 void CAgnServerSession::NextInstancesL()
       
  1808 	{
       
  1809 	// Gets the time of the next instance to today
       
  1810 	// Arguments: 0 : output data buffer
       
  1811 	//			  1 : size of the output data buffer
       
  1812 	//			  2 : input data buffer
       
  1813 
       
  1814 	// Restore length
       
  1815 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot2);
       
  1816 	
       
  1817 	// Restore buffer
       
  1818 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  1819 	CleanupStack::PushL(buffer);
       
  1820 	buffer->ExpandL(0, KBufferSize);
       
  1821 
       
  1822 	TPtr8 des(buffer->Ptr(0));
       
  1823 	iMessage.ReadL(KSlot2, des);
       
  1824 	
       
  1825 	TFindInstanceParams parameters;
       
  1826 	
       
  1827 	RDesReadStream readStream(des);
       
  1828 	
       
  1829 	parameters.InternalizeL(readStream);
       
  1830 	TInt filecount = readStream.ReadInt16L();
       
  1831 	const TInt KInstanceArrayGranularity = 16;
       
  1832 	CArrayFixSeg<TAgnSortInstance>* instances = new (ELeave) CArrayFixSeg<TAgnSortInstance>(KInstanceArrayGranularity);
       
  1833 	CleanupStack::PushL(instances);
       
  1834 
       
  1835 	for(TInt ii=0;ii<filecount;++ii)
       
  1836 		{
       
  1837 		TInt64 fileId;
       
  1838 		readStream >> fileId;
       
  1839 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  1840 		if(file->IsLocked())
       
  1841 			{
       
  1842 			User::Leave(KErrLocked);
       
  1843 			}
       
  1844 		CAgnEntryModel* model = file->Model();
       
  1845 		model->NextPossibleInstancesL(*instances, parameters);
       
  1846 		}
       
  1847 	
       
  1848 	const CAgnSimpleEntry* searchFromEntry = NULL;
       
  1849 	if(parameters.iInstance.iCollectionId > 0)
       
  1850 		{
       
  1851 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(parameters.iInstance.iCollectionId);
       
  1852 		if(file->IsLocked())
       
  1853 			{
       
  1854 			User::Leave(KErrLocked);
       
  1855 			}
       
  1856 		searchFromEntry = file->Model()->GetSimpleEntryFromIndexes(parameters.iInstance.iId);
       
  1857 		}
       
  1858 
       
  1859 	TAgnSortInstance searchFromInstance(*searchFromEntry);
       
  1860 	if (searchFromEntry)
       
  1861 		{
       
  1862 		TAgnDaySortKey sortKey(AgnDateTime::MaxDate(), parameters.iUndatedTodoTimeLocal);
       
  1863 		searchFromInstance.SetL(parameters.iInstance.iId.Date().LocalL(), parameters.iUndatedTodoTimeLocal);
       
  1864 		const_cast<CAgnSimpleEntry&>(searchFromInstance.SimpleEntry()).SetCollectionId(parameters.iInstance.iCollectionId);
       
  1865 		//the search from instance must match the filter settings
       
  1866 		__ASSERT_ALWAYS(searchFromInstance.CheckStartAndEndDateOverlap(parameters), User::Leave(KErrNotFound));
       
  1867 		TInt thisPosition(0);
       
  1868 		User::LeaveIfError(instances->FindIsq(searchFromInstance, sortKey, thisPosition));
       
  1869 		instances->Delete(0, thisPosition + 1);
       
  1870 		}
       
  1871 	else if (!parameters.iInstance.iId.IsNullId())
       
  1872 		{
       
  1873 		// The entry searched has been deleted or the entry id is wrong
       
  1874 		User::Leave(KErrNotFound);
       
  1875 		}
       
  1876 	
       
  1877 	// Truncate the list to the length of aSearchParams.iNumInstances by removeing instances from the end
       
  1878 	if (instances->Count() > parameters.iNumInstances)
       
  1879 		{
       
  1880 		instances->Delete(parameters.iNumInstances, instances->Count() - parameters.iNumInstances);
       
  1881 		}
       
  1882 	delete iBuffer;
       
  1883 	iBuffer = NULL;
       
  1884 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  1885 
       
  1886 	// Create a write stream for this buffer
       
  1887 	RBufWriteStream bufStream;
       
  1888 	bufStream.Open(*iBuffer);
       
  1889 	CleanupClosePushL(bufStream);
       
  1890 
       
  1891 	const TInt KInstanceCount(instances->Count());
       
  1892 
       
  1893 	bufStream.WriteUint32L(KInstanceCount);
       
  1894 
       
  1895 	for (TInt i(0) ; i < KInstanceCount ; ++i)
       
  1896 		{
       
  1897 		TAgnInstance instance;
       
  1898 		instance.iId = instances->At(i).InstanceIdL();
       
  1899 		instance.iCollectionId = (*instances)[i].SimpleEntry().CollectionId();
       
  1900 		bufStream << instance;
       
  1901 		}
       
  1902 
       
  1903 	bufStream.CommitL();
       
  1904 
       
  1905 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  1906 	CleanupStack::PopAndDestroy(instances);
       
  1907 	CleanupStack::PopAndDestroy(buffer);
       
  1908 
       
  1909 	// Send it back to the client
       
  1910 	TPckg<TInt> size(iBuffer->Size());
       
  1911 	iMessage.WriteL(KSlot1, size);
       
  1912 	}
       
  1913 
       
  1914 void CAgnServerSession::CreateEntryIteratorL()
       
  1915 	{
       
  1916 	// Creates a server side entry iterator
       
  1917 	// Used to iterate through all entries in the model e.g. for saving
       
  1918 	// Arguments: 1 : Output - True if an entry is available
       
  1919 	//			  0 : Input  - File Id
       
  1920 
       
  1921 	TPckgBuf<TInt64> fileId;
       
  1922 	iMessage.ReadL(KSlot0, fileId);
       
  1923 
       
  1924 	TBool isEntry = EFalse;
       
  1925 	if(iAgnSessionFileManager)
       
  1926 		{
       
  1927 		CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileId());
       
  1928 		isEntry = client.CreateEntryIterL();
       
  1929 		}
       
  1930 	TPckg<TBool> entryBuffer(isEntry);
       
  1931 	iMessage.WriteL(KSlot1, entryBuffer);
       
  1932 	}
       
  1933 
       
  1934 void CAgnServerSession::EntryIteratorNextL()
       
  1935 	{
       
  1936 	TPckgBuf<TInt64> fileId;
       
  1937 	iMessage.ReadL(KSlot0, fileId);
       
  1938 
       
  1939 	// Iterates to the next entry
       
  1940 	// Arguments: 0 : Output - True if an entry is available
       
  1941 	TBool isEntry = EFalse;
       
  1942 	if(iAgnSessionFileManager)
       
  1943 		{
       
  1944 		CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileId());
       
  1945 		isEntry = client.IsEntryAvailableAtIteratorL();
       
  1946 		}
       
  1947 
       
  1948 	TPckg<TBool> boolBuffer(isEntry);
       
  1949 	iMessage.WriteL(KSlot1, boolBuffer);
       
  1950 	}
       
  1951 
       
  1952 void CAgnServerSession::EntryIteratorPositionL()
       
  1953 	{
       
  1954 	TPckgBuf<TInt64> fileId;
       
  1955 	iMessage.ReadL(KSlot2, fileId);
       
  1956 
       
  1957 	// Returns the entry ID of the current entry
       
  1958 	// Arguments: 0 : Output - Entry ID
       
  1959 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  1960 	if(file->IsLocked())
       
  1961 		{
       
  1962 		User::Leave(KErrLocked);
       
  1963 		}
       
  1964 	CAgnEntry* entry = NULL;
       
  1965 	if(iAgnSessionFileManager)
       
  1966 		{
       
  1967 		CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileId());
       
  1968 		entry = client.FetchEntryAtIteratorL();
       
  1969 		}
       
  1970 	
       
  1971 	if ( entry )
       
  1972 		{
       
  1973 		CleanupStack::PushL(entry);
       
  1974 	
       
  1975 		ExternalizeEntryToClientL(*entry, KSlot1);
       
  1976 	
       
  1977 		CleanupStack::PopAndDestroy(entry);
       
  1978 		}
       
  1979 	else
       
  1980 		{
       
  1981 		TPckg<TInt> size(0);
       
  1982 		iMessage.WriteL(KSlot1, size);
       
  1983 		}	
       
  1984 	}
       
  1985 
       
  1986 void CAgnServerSession::GetEntryUidsSinceDateL()
       
  1987 	{
       
  1988 	// Selects entries with a last changed date greater than specified and that match filter
       
  1989 	// Arguments: 0 - Output	: Data buffer (containing list of TCalLocalUid's of entries)
       
  1990 	//			  1 - Output	: Size of data buffer
       
  1991 	//			  2 - Input		: Time
       
  1992 
       
  1993 	TPckgBuf<TTime> time;
       
  1994 	iMessage.ReadL(KSlot2,time);
       
  1995 
       
  1996  	RArray<TCalLocalUid> uniqueIdList;
       
  1997  	CleanupClosePushL(uniqueIdList);
       
  1998 
       
  1999  	CAgnServFile* file = GetFileL(KSlot3);
       
  2000  	if(file->IsLocked())
       
  2001  		{
       
  2002  		User::Leave(KErrLocked);
       
  2003  		}
       
  2004 	file->Model()->GetEntryUidsSinceDateL(time(), uniqueIdList);
       
  2005 
       
  2006 	WriteIntArrayToBufferL(uniqueIdList);
       
  2007 
       
  2008 	CleanupStack::PopAndDestroy(&uniqueIdList); //uniqueIdList.Close();
       
  2009 
       
  2010 	// Send it back to the client
       
  2011 	TPckg<TInt> listsize(iBuffer->Size());
       
  2012 	iMessage.WriteL(KSlot1, listsize);
       
  2013 	}
       
  2014 	
       
  2015 void CAgnServerSession::RequestChangeNotification()
       
  2016 	{	
       
  2017 	if(iAgnSessionFileManager)
       
  2018 		{
       
  2019 		iAgnSessionFileManager->RequestChangeNotification(iMessage);
       
  2020 		}
       
  2021 	}
       
  2022 
       
  2023 void CAgnSessionFileManager::RequestChangeNotification(const RMessage2 aMessage)
       
  2024     {
       
  2025     TInt sessionId = aMessage.Int0();
       
  2026     TUint8 whichNotification = aMessage.Int1();
       
  2027 
       
  2028     TInt index = GetSessionFile(sessionId);
       
  2029     if (index == KErrNotFound && whichNotification &EFileChange)
       
  2030         {
       
  2031         CAgnSessionFile* sessionFile = CAgnSessionFile::NewL(sessionId, iAgnServerSession);
       
  2032         CleanupStack::PushL(sessionFile);
       
  2033         iSessionFiles.AppendL(sessionFile);
       
  2034         CleanupStack::Pop(sessionFile);
       
  2035         sessionFile->RequestChangeNotification(aMessage);
       
  2036         }
       
  2037     else if(index >= 0)
       
  2038         {
       
  2039         iSessionFiles[index]->RequestChangeNotification(aMessage);
       
  2040         }
       
  2041     }
       
  2042 
       
  2043 void CAgnServerSession::CancelChangeNotification()
       
  2044 	{
       
  2045 	//get fileid
       
  2046 	TInt sessionId = iMessage.Int0();
       
  2047 	TUint8 aNotificationType = iMessage.Int1();
       
  2048 	if(iAgnSessionFileManager)
       
  2049 		{
       
  2050 		TInt index = iAgnSessionFileManager->GetSessionFile(sessionId);	
       
  2051 		if (index >= 0)
       
  2052 			{
       
  2053 			iAgnSessionFileManager->GetSessionFileByIndex(index).CancelChangeNotification(aNotificationType);
       
  2054 			}
       
  2055 		}
       
  2056 	}
       
  2057 
       
  2058 void CAgnServerSession::RequestChangeNotificationParametersL()
       
  2059 	{
       
  2060 	TPckgBuf<TTime> start;
       
  2061 	iMessage.ReadL(KSlot0, start);
       
  2062 
       
  2063 	TPckgBuf<TTime> end;
       
  2064 	iMessage.ReadL(KSlot1, end);
       
  2065 	
       
  2066 	// Restore length
       
  2067 	const TInt KBufferSize = iMessage.GetDesLength(KSlot2);
       
  2068 	
       
  2069 	// Restore buffer
       
  2070 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  2071 	CleanupStack::PushL(buffer);
       
  2072 	buffer->ExpandL(0, KBufferSize);
       
  2073 
       
  2074 	TPtr8 des(buffer->Ptr(0));
       
  2075 	iMessage.ReadL(KSlot2, des);
       
  2076 	RDesReadStream readStream(des);
       
  2077 	TInt16 type = readStream.ReadInt16L();
       
  2078 	TBool includeUndatedTodos = readStream.ReadInt16L(); 
       
  2079 	TInt64 fileid;
       
  2080 	readStream >> fileid;
       
  2081 	CleanupStack::PopAndDestroy(buffer);
       
  2082 	if(iAgnSessionFileManager)
       
  2083 		{
       
  2084 		CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileid);
       
  2085 		client.SetChangeNotificationParametersL(start(), end(), MCalChangeCallBack2::TChangeEntryType(type));
       
  2086 		}
       
  2087 	}
       
  2088 
       
  2089 /**
       
  2090  * Gets the Notes Text writes it to a stream buffer and returns the size.
       
  2091  * Arguments:
       
  2092  *		0.  Output  - Buffer
       
  2093  *		1.  Input  - Stream Id
       
  2094  *		2.	Output - Size of Notes Field
       
  2095  */
       
  2096 void CAgnServerSession::RestoreTextL()
       
  2097 	{
       
  2098 	delete iBuffer;
       
  2099 	iBuffer = NULL;
       
  2100 	
       
  2101 	iBuffer = CBufFlat::NewL(KInitialBufferSize);	
       
  2102 	
       
  2103 	// Create a write stream for this buffer
       
  2104 	RBufWriteStream bufStream;
       
  2105 	bufStream.Open(*iBuffer);
       
  2106 	CleanupClosePushL(bufStream);	
       
  2107 
       
  2108 	TPckgBuf<TStreamId> textId;
       
  2109 	iMessage.ReadL(KSlot1,textId);
       
  2110 	
       
  2111 	CAgnServFile* file = GetFileL(KSlot3);
       
  2112 	if(file->IsLocked())
       
  2113 		{
       
  2114 		User::Leave(KErrLocked);
       
  2115 		}
       
  2116 	HBufC* text = file->Model()->RestoreTextL(textId());
       
  2117 	CleanupStack::PushL(text);
       
  2118 	
       
  2119 	bufStream.WriteUint32L(text->Length());
       
  2120 	bufStream << *text;
       
  2121 	CleanupStack::PopAndDestroy(text);
       
  2122 	
       
  2123 	bufStream.CommitL();
       
  2124 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  2125 
       
  2126 	// Send the size back to the client
       
  2127 	TPckg<TInt> sizeBuf(iBuffer->Size());
       
  2128 	iMessage.WriteL(KSlot2, sizeBuf); 
       
  2129 	}
       
  2130 
       
  2131 /**
       
  2132 Gets the Alarm Action writes it to a stream buffer and returns the size.
       
  2133 Arguments:
       
  2134 	0.  Output - Buffer
       
  2135 	1.  Input  - Stream Id
       
  2136 	2.	Output - Size of alarm action
       
  2137 	3.  Input  - File Id  
       
  2138 */
       
  2139 void CAgnServerSession::RestoreAlarmActionL()
       
  2140 	{
       
  2141 	delete iBuffer;
       
  2142 	iBuffer = NULL;
       
  2143 	
       
  2144 	iBuffer = CBufFlat::NewL(KInitialBufferSize);	
       
  2145 	
       
  2146 	// Create a write stream for this buffer
       
  2147 	RBufWriteStream bufStream;
       
  2148 	bufStream.Open(*iBuffer);
       
  2149 	CleanupClosePushL(bufStream);
       
  2150 	
       
  2151 	TPckgBuf<TStreamId> id;
       
  2152 
       
  2153 	iMessage.ReadL(KSlot1, id);
       
  2154 	TPckgBuf<TInt64> fileId;
       
  2155 	iMessage.ReadL(KSlot3, fileId);
       
  2156 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  2157 	if(file->IsLocked())
       
  2158 		{
       
  2159 		User::Leave(KErrLocked);
       
  2160 		}
       
  2161 	CAgnContent* alarmAction = file->Model()->RestoreAlarmActionL(id());
       
  2162 	CleanupStack::PushL(alarmAction);
       
  2163 	alarmAction->ExternalizeL(bufStream);
       
  2164 	CleanupStack::PopAndDestroy(alarmAction);	
       
  2165 	
       
  2166 	bufStream.CommitL();
       
  2167 
       
  2168 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close(); 
       
  2169 
       
  2170 	// Send the size back to the client
       
  2171 	TPckg<TInt> sizeBuf(iBuffer->Size());
       
  2172 	iMessage.WriteL(KSlot2, sizeBuf);
       
  2173 	}
       
  2174 
       
  2175 void CAgnServerSession::StartBuildIndex()
       
  2176 	{
       
  2177 	// if the calendar file is not opened, leave
       
  2178 	TBool reportProgress = iMessage.Int0();
       
  2179 	TAgnMessageToComplete message(iMessage, reportProgress, *this);
       
  2180 	
       
  2181 	TUint8 fileId = iMessage.Int1();
       
  2182 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  2183 	file->StartBuildIndex(message);
       
  2184 	}
       
  2185 
       
  2186 void CAgnServerSession::TidyByDateStartL()
       
  2187 	{
       
  2188 	TBool reportProgress = iMessage.Int0();
       
  2189 	TAgnMessageToComplete message(iMessage, reportProgress, *this);
       
  2190 	TUint8 fileId = iMessage.Int1();
       
  2191 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  2192 	if(file->IsLocked())
       
  2193 		{
       
  2194 		User::Leave(KErrLocked);
       
  2195 		}
       
  2196 	CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileId);
       
  2197 	client.TidyByDateStartL(message, *file);
       
  2198 	}
       
  2199 
       
  2200 void CAgnServerSession::RequestProgressL()
       
  2201 	{
       
  2202 	TAgnMessageToComplete message(iMessage, ETrue, *this);
       
  2203 	TUint8 fileId = iMessage.Int0();
       
  2204 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  2205 	file->RequestProgressL(message);
       
  2206 	}
       
  2207 
       
  2208 void CAgnServerSession::AsynchCategoryTaskStartL()
       
  2209 	{
       
  2210 	TBool reportProgress = iMessage.Int0();
       
  2211 	TAgnMessageToComplete message(iMessage, reportProgress, *this);
       
  2212 	CCalAsyncTaskManager::TAsyncAction task = (CCalAsyncTaskManager::TAsyncAction)iMessage.Int1();
       
  2213 	TUint8 fileId = iMessage.Int2();
       
  2214 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  2215 	if(file->IsLocked())
       
  2216 		{
       
  2217 		User::Leave(KErrLocked);
       
  2218 		}
       
  2219 	file->CategoryTaskStartL(message, task);
       
  2220 	}
       
  2221 
       
  2222 void CAgnServerSession::GetCategoryListCountL()
       
  2223 // gets the number of categories in the list
       
  2224 // arguments:
       
  2225 //	0 - output, count
       
  2226 //  1 - input, file id
       
  2227 	{
       
  2228 	TPckgBuf<TInt64> fileId;
       
  2229 	iMessage.ReadL(KSlot1, fileId);
       
  2230 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  2231 	if(file->IsLocked())
       
  2232 		{
       
  2233 		User::Leave(KErrLocked);
       
  2234 		}
       
  2235 	TInt count = file->CategoryList().CategoryCount();
       
  2236 	TPckg<TInt> buf(count);
       
  2237 	iMessage.WriteL(KSlot0, buf);
       
  2238 	}
       
  2239 
       
  2240 void CAgnServerSession::GetCategoryListItemL()
       
  2241 // gets the category in the list at index passed in from the client
       
  2242 // arguments:
       
  2243 //	0 - output,	data buffer
       
  2244 //	1 - input, index
       
  2245 //  2 - output, size of buffer
       
  2246 //  3 - input, file id
       
  2247 	{
       
  2248 	TInt index = iMessage.Int1();
       
  2249 	
       
  2250 	TPckgBuf<TInt64> fileId;
       
  2251 	iMessage.ReadL(KSlot3, fileId);
       
  2252 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  2253 	if(file->IsLocked())
       
  2254 		{
       
  2255 		User::Leave(KErrLocked);
       
  2256 		}
       
  2257 	if( index >= file->CategoryList().CategoryCount() )
       
  2258 		{
       
  2259 		User::Leave(KErrNotFound);
       
  2260 		}
       
  2261 	
       
  2262 	delete iBuffer;
       
  2263 	iBuffer = NULL;
       
  2264 
       
  2265 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  2266 	
       
  2267 	// Create a write stream for this buffer
       
  2268 	RBufWriteStream bufStream;
       
  2269 	bufStream.Open(*iBuffer);
       
  2270 	CleanupClosePushL(bufStream);	
       
  2271 
       
  2272 	// Buffer contains one byte for category type and the string for the extended category name
       
  2273 	file->CategoryList().Category(index).ExternalizeL(bufStream);
       
  2274 
       
  2275 	bufStream.CommitL();
       
  2276 
       
  2277 	TPckg<TInt> size(iBuffer->Size());
       
  2278 	iMessage.WriteL(KSlot2, size);
       
  2279 	
       
  2280 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close()
       
  2281 	}
       
  2282 
       
  2283 void CAgnServerSession::AddCategoryToListL()
       
  2284 // adds a new category to the list; 
       
  2285 // arguments:
       
  2286 //	0 - input,	category name
       
  2287 //  1 - input,  file id
       
  2288 	{
       
  2289 
       
  2290 	HBufC* bufptr = ReadClientDesLC(KSlot0);
       
  2291 	TPtr categoryName = bufptr->Des();
       
  2292 	
       
  2293 	TPckgBuf<TInt64> fileId;
       
  2294 	iMessage.ReadL(KSlot1, fileId);
       
  2295 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  2296 	if(file->IsLocked())
       
  2297 		{
       
  2298 		User::Leave(KErrLocked);
       
  2299 		}
       
  2300 	file->CategoryList().AddCategoryL(categoryName);
       
  2301 	
       
  2302 	CleanupStack::PopAndDestroy(bufptr);
       
  2303 	}
       
  2304 
       
  2305 void CAgnServerSession::CategoryTaskStartL()
       
  2306 	{
       
  2307 	// Arguments: 0 - Input	: Data buffer (category and step size)
       
  2308 	//			  1 - Input	: Size of data buffer
       
  2309 	//			  2 - Input : step of the task
       
  2310 	//			  3 - Input	: File Id
       
  2311 	const TInt KBufferSize = iMessage.Int1();
       
  2312 	// Restore buffer
       
  2313 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  2314 	CleanupStack::PushL(buffer);
       
  2315 
       
  2316 	buffer->ExpandL(0, KBufferSize);
       
  2317 
       
  2318 	TPtr8 buf(buffer->Ptr(0));
       
  2319 	iMessage.ReadL(KSlot0,buf);
       
  2320 	// Internalize the data from the stream
       
  2321 	TInt categoryIndex;
       
  2322 	TUint8 shortFileId = iMessage.Int3();
       
  2323 	GetCategoryInfoL(*buffer,categoryIndex, shortFileId);
       
  2324 	CleanupStack::PopAndDestroy(buffer);
       
  2325 	
       
  2326 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(shortFileId);
       
  2327 	if(file->IsLocked())
       
  2328 		{
       
  2329 		User::Leave(KErrLocked);
       
  2330 		}
       
  2331 	TInt task = iMessage.Int2();
       
  2332 	file->Model()->CategoryIndex().PrepareStepTaskL(task,categoryIndex);
       
  2333 	}
       
  2334 
       
  2335 void CAgnServerSession::FilterCategoryL()
       
  2336 	{
       
  2337 	//	Arguments:0 - Input		: Data Buffer (category and step size)
       
  2338 	//			  1 - Input		: Size of data buffer
       
  2339 	CArrayFixSeg<TAgnEntryId>* entryList = new (ELeave) CArrayFixSeg<TAgnEntryId>(KGranFilteredEntries);
       
  2340 	CleanupStack::PushL(entryList);
       
  2341 	
       
  2342 	TPckgBuf<TInt64> fileId;
       
  2343 	iMessage.ReadL(KSlot2, fileId);
       
  2344 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  2345 	if(file->IsLocked())
       
  2346 		{
       
  2347 		User::Leave(KErrLocked);
       
  2348 		}
       
  2349 	file->Model()->CategoryIndex().GetArrayFilterCategoryL(*entryList);
       
  2350 	
       
  2351 	delete iBuffer;
       
  2352 	iBuffer = NULL;
       
  2353 	
       
  2354 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  2355 
       
  2356 	// Create a write stream for this buffer
       
  2357 	RBufWriteStream bufStream;
       
  2358 	bufStream.Open(*iBuffer);
       
  2359 	CleanupClosePushL(bufStream);	
       
  2360 
       
  2361 	const TInt KCount = entryList->Count();
       
  2362 
       
  2363 	bufStream.WriteInt16L(KCount);
       
  2364 	
       
  2365 	for(  TInt ii = 0; ii < KCount; ++ii )
       
  2366 		{
       
  2367 		entryList->At(ii).ExternalizeL(bufStream);
       
  2368 		}
       
  2369 		
       
  2370 	bufStream.CommitL();
       
  2371 
       
  2372 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  2373 
       
  2374 	CleanupStack::PopAndDestroy(entryList);
       
  2375 
       
  2376 	// Send it back to the client
       
  2377 	TPckg<TInt> size(iBuffer->Size());
       
  2378 	iMessage.WriteL(KSlot1, size);
       
  2379 	}
       
  2380 
       
  2381 void CAgnServerSession::CancelTaskL()
       
  2382 	{
       
  2383 	TPckgBuf<TInt64> fileId;
       
  2384 	iMessage.ReadL(KSlot0, fileId);
       
  2385 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  2386 	if(file)
       
  2387 		{
       
  2388 		file->DoTaskCompleteL(KErrCancel, this);
       
  2389 		}
       
  2390 	}
       
  2391 
       
  2392 void CAgnServerSession::CancelAllTask()
       
  2393 	{
       
  2394 	const TInt count = FileIdCount();
       
  2395 	for(TInt ii=0; ii<count; ++ii)
       
  2396 		{
       
  2397 		CAgnServFile* file = NULL;
       
  2398 		TRAPD(err, file = iAgnServer.FileMgr()->GetFileL(FileId(ii)));
       
  2399 		if(err == KErrNone)
       
  2400 			{
       
  2401 			TRAP_IGNORE(file->DoTaskCompleteL(KErrCancel, this));
       
  2402 			}
       
  2403 		}
       
  2404 	}
       
  2405 
       
  2406 void CAgnServerSession::BackupRestoreCancelTask()
       
  2407     {
       
  2408     const TInt count = FileIdCount();
       
  2409     for(TInt ii=0; ii<count; ++ii)
       
  2410         {
       
  2411         CAgnServFile* file = NULL;
       
  2412         TRAPD(err, file = iAgnServer.FileMgr()->GetFileL(FileId(ii)));
       
  2413         if(err == KErrNone)
       
  2414             {
       
  2415             TRAP_IGNORE(file->CancelTaskL(this));
       
  2416             }
       
  2417         }
       
  2418     }
       
  2419 
       
  2420 void CAgnServerSession::GetCategoryInfoL(const CBufFlat& aBufFlat,TInt& aCategoryIndex, TCalCollectionId aCollectionId)
       
  2421 	{
       
  2422 	RBufReadStream readStream;
       
  2423 	readStream.Open(aBufFlat);
       
  2424 	CleanupClosePushL(readStream);
       
  2425 		
       
  2426 	CAgnCategory* category = CAgnCategory::NewL(readStream);
       
  2427 
       
  2428 	CleanupStack::PopAndDestroy(&readStream); // readStream.Close();
       
  2429 
       
  2430 	CleanupStack::PushL(category);
       
  2431 	
       
  2432 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(aCollectionId);
       
  2433 	if(file->IsLocked())
       
  2434 		{
       
  2435 		User::Leave(KErrLocked);
       
  2436 		}
       
  2437 	aCategoryIndex = file->CategoryList().FindCategoryIndex(*category);
       
  2438 	User::LeaveIfError(aCategoryIndex);
       
  2439 
       
  2440 	CleanupStack::PopAndDestroy(category);
       
  2441 	}
       
  2442 
       
  2443 /** Create a store with Agenda file */
       
  2444 void CAgnServerSession::CreateAgendaFileL()
       
  2445 	{
       
  2446 	// Arguments: 0 : Input - size fo buffer
       
  2447 	//			  1 : Input - Data Buffer
       
  2448 	//			  2 : Input - file name
       
  2449 	//			  3 : Input - todo list name
       
  2450 
       
  2451 	//Create a store
       
  2452 	HBufC* filenameBuf = ReadClientDesLC(KSlot0);
       
  2453 	CFileStore* store=iAgnServer.FileMgr()->CreateAgendaFileLC(*filenameBuf);//PUSH: store
       
  2454 	store->SetTypeL(TUidType(KPermanentFileStoreLayoutUid, KUidAppDllDoc, KUidAgnApp));
       
  2455 
       
  2456 	CAgnEntryModel* model = CAgnEntryModel::NewL(NULL);
       
  2457 	CleanupStack::PushL(model); //PUSH: model
       
  2458 	TStreamId headstreamId = model->CreateL(*store); 
       
  2459 
       
  2460 	//Write dummy app id to the store
       
  2461 	//Create the streamdictionary (effectively the root stream)
       
  2462 	CStreamDictionary* streamDic=CStreamDictionary::NewLC();//PUSH: streamDic
       
  2463 	if (streamDic->At(KUidAgnModel)!=headstreamId)
       
  2464 		{
       
  2465 		streamDic->AssignL(KUidAgnModel, headstreamId);
       
  2466 		}
       
  2467 
       
  2468 	// Stream dictionary (root)
       
  2469 	TApaAppIdentifier dummyApp(KUidAgnModel, KNullDesC());
       
  2470 	CApaProcess::WriteRootStreamL(*store,*streamDic, dummyApp);
       
  2471 	store->CommitL();
       
  2472 	CleanupStack::PopAndDestroy(3, store);
       
  2473 	
       
  2474 	//Convert the file name into standard format "c:filename
       
  2475 	HBufC* parsedFilename = iAgnServer.FileMgr()->ParseFilenameLC(*filenameBuf);//full name include the parth	
       
  2476     parsedFilename->Des().Fold();   
       
  2477     TParsePtrC parse(*parsedFilename);
       
  2478     HBufC* shortFileName = HBufC::NewLC(parsedFilename->Length());
       
  2479     shortFileName->Des().Append(parse.Drive());
       
  2480     shortFileName->Des().Append(parse.NameAndExt());   
       
  2481     CAgnFileChangeInfo* changeInfo = NULL;
       
  2482     changeInfo = CAgnFileChangeInfo::NewL(shortFileName, MCalFileChangeObserver::ECalendarFileCreated);
       
  2483     CleanupStack::Pop(shortFileName);
       
  2484     CleanupStack::PushL(changeInfo);
       
  2485     CalendarFileChangedL(*changeInfo);//add the change to the buffer  
       
  2486     CleanupStack::PopAndDestroy(3, filenameBuf);//changeInfo, parsedFilename, filenameBuf
       
  2487 	}
       
  2488 
       
  2489 TBool CAgnServerSession::IsOwnFileL(TInt aSessionId, const CAgnServFile& file)
       
  2490     {
       
  2491     TBool isOwnFile = EFalse;    
       
  2492     //Check whether it is its own file
       
  2493     if(iAgnSessionFileManager)
       
  2494        {
       
  2495        TInt index = iAgnSessionFileManager->GetSessionFile(aSessionId);
       
  2496        if(index >= 0)
       
  2497            {
       
  2498            TCalFileId fileId = iAgnSessionFileManager->GetSessionFileByIndex(index).FileId();
       
  2499            if(fileId == file.Model()->GetFileIdL())
       
  2500                {
       
  2501                isOwnFile = ETrue;
       
  2502                }
       
  2503            }
       
  2504        }
       
  2505     return isOwnFile;
       
  2506     }
       
  2507 
       
  2508 TBool CAgnServerSession::FileCanBeDeletedL(TInt aSessionId, const CAgnServFile& file)
       
  2509     {
       
  2510     TBool fileCanBeDeleted = EFalse;
       
  2511     TBool isOwnFile = IsOwnFileL(aSessionId, file);    
       
  2512     if(file.ReferenceCount() == 0 || (isOwnFile && file.ReferenceCount() == 1))
       
  2513         {
       
  2514         fileCanBeDeleted = ETrue;
       
  2515         }
       
  2516     return fileCanBeDeleted;       
       
  2517     }
       
  2518 
       
  2519 TBool CAgnServerSession::FileHasBeenOpenedL(const CAgnServFile& file)
       
  2520     {
       
  2521     TBool fileHasBeenOpened = EFalse;
       
  2522     if(iAgnSessionFileManager)
       
  2523         {
       
  2524         if(iAgnSessionFileManager->FindL(file.Model()->GetFileIdL()) != KErrNotFound)
       
  2525             {
       
  2526             fileHasBeenOpened = ETrue;
       
  2527             }      
       
  2528         }
       
  2529     return fileHasBeenOpened;
       
  2530     }
       
  2531 
       
  2532 void CAgnServerSession::DeleteAgendaFileL()
       
  2533     {
       
  2534     // Delete a file held by the server
       
  2535     //              1: Input - Agenda file name
       
  2536     
       
  2537     // Get descriptor for filename to delete
       
  2538     HBufC* bufptr = ReadClientDesLC(KSlot0);
       
  2539     TPtr filename = bufptr->Des();
       
  2540     
       
  2541     HBufC* fullFilename = iAgnServer.FileMgr()->ParseFilenameLC(filename);
       
  2542     TInt sessionId = iMessage.Int1();
       
  2543   
       
  2544     CAgnServFile* file = NULL;
       
  2545     file = iAgnServer.FileMgr()->GetFile(*fullFilename);
       
  2546     if(file && !FileCanBeDeletedL(sessionId, *file))
       
  2547         {
       
  2548         User::Leave(KErrInUse);
       
  2549         }
       
  2550     
       
  2551     TBool closeFile(EFalse);
       
  2552     TInt err = KErrNone;
       
  2553     if (!file)
       
  2554         {
       
  2555         // the file is not open so we must open it now
       
  2556         CalCommon::TCalFileVersionSupport status;
       
  2557         TRAP(err, file = &iAgnServer.FileMgr()->OpenAgendaL(filename, iAgnServer, status));       
       
  2558         if (err == KErrNone)
       
  2559             {
       
  2560             // Everything was fine when opening the file
       
  2561             closeFile = ETrue;
       
  2562             CleanupStack::PushL(TCleanupItem(CleanupCloseAgendaImmediately, file));        
       
  2563             }
       
  2564         }
       
  2565     if(!file)
       
  2566         {
       
  2567         iAgnServer.FileMgr()->DeleteAgendaFileL(filename);
       
  2568         }
       
  2569     else
       
  2570         {
       
  2571         TBool calInfoExist = file->IsCalendarInfoExistL();
       
  2572         TBool deleteSessionFile = EFalse;     
       
  2573         if (closeFile)
       
  2574             {
       
  2575             // This will call CloseAgenda(ETrue)
       
  2576             CleanupStack::PopAndDestroy();
       
  2577             }
       
  2578         else if( IsOwnFileL(sessionId, *file) )
       
  2579             {
       
  2580             // The client has requested to delete it's own calendar file
       
  2581             // so try to close it immediately
       
  2582             User::LeaveIfError(iAgnServer.FileMgr()->CloseAgenda(*file, ETrue));
       
  2583             deleteSessionFile = ETrue;
       
  2584             iSessionReady = ETrue;
       
  2585             }
       
  2586         iAgnServer.FileMgr()->DeleteAgendaFileL(filename);
       
  2587         
       
  2588         TParsePtrC parse(*fullFilename);
       
  2589         HBufC* shortFileName = HBufC::NewLC(fullFilename->Length());
       
  2590         shortFileName->Des().Append(parse.Drive());
       
  2591         shortFileName->Des().Append(parse.NameAndExt());
       
  2592 		iAgnServer.AlarmServer().AlarmDeleteByCalendarFile(*shortFileName, EAllAlarms);
       
  2593         CAgnFileChangeInfo* changeInfo = NULL;
       
  2594     
       
  2595         if(calInfoExist)
       
  2596             {
       
  2597             HBufC* shortFileNameCopy = shortFileName->AllocLC();
       
  2598             changeInfo = CAgnFileChangeInfo::NewL(shortFileNameCopy, MCalFileChangeObserver::ECalendarInfoDeleted);
       
  2599             CleanupStack::Pop(shortFileNameCopy);         
       
  2600             CleanupStack::PushL(changeInfo);
       
  2601             CalendarFileChangedL(*changeInfo);//add the change to the buffer
       
  2602             CleanupStack::PopAndDestroy(changeInfo);
       
  2603             }       
       
  2604         changeInfo = CAgnFileChangeInfo::NewL(shortFileName, MCalFileChangeObserver::ECalendarFileDeleted);
       
  2605         CleanupStack::Pop(shortFileName);
       
  2606         CleanupStack::PushL(changeInfo);
       
  2607         CalendarFileChangedL(*changeInfo);
       
  2608         CleanupStack::PopAndDestroy(changeInfo);
       
  2609         if(deleteSessionFile)
       
  2610             {
       
  2611             iAgnSessionFileManager->DeleteSessionFileIfFileNotificationNotRequired(sessionId); 
       
  2612             }
       
  2613         }  
       
  2614     
       
  2615     CleanupStack::PopAndDestroy(fullFilename);
       
  2616     CleanupStack::PopAndDestroy(bufptr);    // buffer
       
  2617     }
       
  2618 
       
  2619 void CAgnServerSession::CalendarFileChangedL(CAgnFileChangeInfo& aFileChangeInfo)
       
  2620     {
       
  2621     RPointerArray<CAgnServerSession> sessions;
       
  2622     CleanupClosePushL(sessions);
       
  2623     iAgnServer.FetchSessionsL(sessions);
       
  2624     const TInt count = sessions.Count();
       
  2625     for ( TInt i = 0; i < count; ++i )
       
  2626         {       
       
  2627         sessions[i]->AddFileChangeL(aFileChangeInfo, this);
       
  2628         }
       
  2629     CleanupStack::PopAndDestroy(&sessions); // sessions.Close()   
       
  2630     }
       
  2631 
       
  2632 void CAgnServerSession::AddFileChangeL(CAgnFileChangeInfo& aFileChangeInfo, CAgnServerSession* aSession)
       
  2633     {
       
  2634     if(iAgnSessionFileManager && this != aSession)
       
  2635         {
       
  2636         iAgnSessionFileManager->AddFileChangeL(aFileChangeInfo);
       
  2637         }
       
  2638     }
       
  2639 
       
  2640 void CAgnSessionFileManager::AddFileChangeL(CAgnFileChangeInfo& aFileChangeInfo)
       
  2641     {
       
  2642     const TInt count = iSessionFiles.Count();
       
  2643     for(TInt ii = 0; ii < count; ++ii)
       
  2644         {
       
  2645         iSessionFiles[ii]->AddFileChangeToBufferL(aFileChangeInfo);
       
  2646         }
       
  2647     }
       
  2648 
       
  2649 void CAgnServerSession::ListAgendaFilesL()
       
  2650 	{
       
  2651 	// Get a list of file names held by the server 
       
  2652 	// currently setup extractor
       
  2653 	// Arguments: 0 : Output - Data buffer 
       
  2654 	//			   1 : Output - Size of buffer
       
  2655 
       
  2656 	//create the buffer
       
  2657 
       
  2658 	delete iBuffer;
       
  2659 	iBuffer = NULL;
       
  2660 
       
  2661 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  2662 	
       
  2663 	// Create a write stream for this buffer
       
  2664 	RBufWriteStream bufStream;
       
  2665 	bufStream.Open(*iBuffer);
       
  2666 	CleanupClosePushL(bufStream);	
       
  2667 
       
  2668 	CDesCArray* fileNames = iAgnServer.FileMgr()->ListAgendaFilesL();
       
  2669 	if( fileNames )
       
  2670 		{
       
  2671 		CleanupStack::PushL(fileNames);
       
  2672 
       
  2673 		const TInt KCount = fileNames->Count();
       
  2674 
       
  2675 		bufStream.WriteUint8L(KCount);
       
  2676 
       
  2677 		for ( TInt ii = 0; ii < KCount; ++ii )
       
  2678 			{
       
  2679 			const TInt KLength = (fileNames->MdcaPoint(ii)).Length();
       
  2680 			bufStream.WriteUint8L(KLength);
       
  2681 			bufStream.WriteL(fileNames->MdcaPoint(ii), KLength);
       
  2682 			}
       
  2683 
       
  2684 		CleanupStack::PopAndDestroy(fileNames);			
       
  2685 		}
       
  2686 	else
       
  2687 		{
       
  2688 		bufStream.WriteUint8L(0);
       
  2689 		}
       
  2690 		
       
  2691 	bufStream.CommitL();
       
  2692 
       
  2693 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  2694 
       
  2695 	// Send it back to the client
       
  2696 	TPckg<TInt> size(iBuffer->Size());
       
  2697 	iMessage.WriteL(KSlot1, size);
       
  2698 	}
       
  2699 
       
  2700 void CAgnServerSession::TidyByDateReadParamsL()
       
  2701 	{
       
  2702 	// Set up a tidy by date operation 
       
  2703 	// Arguments: 0 : Input -  Buffer containing packaged tidy by date operation data
       
  2704 	//			  1 : Input - File Id	 
       
  2705 	TUint8 fileId = iMessage.Int1();
       
  2706 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  2707 	__ASSERT_ALWAYS( file, Panic(EAgmErrTidyByDateNoFileOpen));
       
  2708 	// If the file already has a session associated with it, then it's busy
       
  2709 	// for this delete operation.
       
  2710 	if (file->IsLocked())
       
  2711 	    {
       
  2712 	    return;
       
  2713 	    }
       
  2714 	
       
  2715 	const TInt KDesLength = iMessage.GetDesLength(KSlot0);
       
  2716 	if(KDesLength<0)
       
  2717 		{
       
  2718 		User::Leave(KErrArgument);
       
  2719 		}
       
  2720 	CBufFlat* buffer = CBufFlat::NewL(KDesLength);
       
  2721 	CleanupStack::PushL(buffer);
       
  2722 
       
  2723 	buffer->ExpandL(0, KDesLength);
       
  2724 	TPtr8 des(buffer->Ptr(0));
       
  2725 	iMessage.ReadL(KSlot0, des);
       
  2726 
       
  2727 	RBufReadStream readStream;
       
  2728 	readStream.Open(*buffer);
       
  2729 	CleanupClosePushL(readStream);
       
  2730 
       
  2731 	TAgnFilter filter;
       
  2732 	filter.InternalizeL(readStream);
       
  2733 	TPckgBuf<TTime> undatedTodosDatePckgBuf;
       
  2734 	readStream.ReadL(undatedTodosDatePckgBuf);
       
  2735 	TPckgBuf<TTime> startDatePckgBuf;
       
  2736 	readStream.ReadL(startDatePckgBuf);
       
  2737 	TPckgBuf<TTime> endDatePckgBuf;
       
  2738 	readStream.ReadL(endDatePckgBuf);
       
  2739 	
       
  2740 	CleanupStack::PopAndDestroy(&readStream); // readStream.Close();
       
  2741 
       
  2742 	file->TidyByDateSetup(*this,
       
  2743 							  filter,
       
  2744 							  undatedTodosDatePckgBuf(),
       
  2745 							  startDatePckgBuf(),
       
  2746 							  endDatePckgBuf());
       
  2747 
       
  2748 	CleanupStack::PopAndDestroy(buffer);
       
  2749 	}
       
  2750 
       
  2751 void CAgnServerSession::AgendaFileExistsL()
       
  2752 	{
       
  2753 	// Check if a Calendar file exists 
       
  2754 	// Arguments: 0 : Output -  True if the file exists, otherwise False
       
  2755 	//			  1 : Input  -  Buffer containing calendar file name
       
  2756 	HBufC* bufptr = ReadClientDesLC(KSlot1);
       
  2757 
       
  2758 	TPckg<TBool> isExists(iAgnServer.FileMgr()->AgendaFileExistsL(*bufptr));
       
  2759 	
       
  2760 	CleanupStack::PopAndDestroy(bufptr);	// bufptr
       
  2761 
       
  2762 	iMessage.WriteL(KSlot0, isExists);
       
  2763 	}
       
  2764 
       
  2765 void CAgnServerSession::BulkChangeCompletedL(TInt64 aFileId, TInt aErr)
       
  2766 	{
       
  2767 	CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(aFileId);
       
  2768 	client.BulkChangeCompletedL(*this, aErr);
       
  2769 	}
       
  2770 
       
  2771 void CAgnServerSession::EnableChangeBroadcastL()
       
  2772 	{
       
  2773 	//get fileid
       
  2774 	TPckgBuf<TInt64> fileId;
       
  2775 	iMessage.ReadL(KSlot0, fileId);
       
  2776 	if(iAgnSessionFileManager)
       
  2777 		{
       
  2778 		CAgnSessionFile* client = NULL;
       
  2779 		TRAPD(err, client = &(iAgnSessionFileManager->GetSessionFileL(fileId())));
       
  2780 		if(err == KErrNone && client)
       
  2781 			{
       
  2782 			client->EnableChangeBroadcastL(*this);
       
  2783 			}
       
  2784 		else if (err != KErrNotFound)
       
  2785 			{
       
  2786 			User::Leave(err);
       
  2787 			}           
       
  2788 		}    
       
  2789 	}
       
  2790 
       
  2791 void CAgnServerSession::DisableChangeBroadcastL()
       
  2792 	{
       
  2793 	//get fileid
       
  2794 	TPckgBuf<TInt64> fileId;
       
  2795 	iMessage.ReadL(KSlot0, fileId);
       
  2796 	if(iAgnSessionFileManager)
       
  2797 		{
       
  2798 		CAgnSessionFile* client = NULL;
       
  2799 		TRAPD(err, client = &(iAgnSessionFileManager->GetSessionFileL(fileId())));
       
  2800 		if(err == KErrNone && client)
       
  2801 			{
       
  2802 			client->DisableChangeBroadcast();
       
  2803 			}
       
  2804 		else if (err != KErrNotFound)
       
  2805 			{
       
  2806 			User::Leave(err);
       
  2807 			}           
       
  2808 		}    
       
  2809 	}
       
  2810 
       
  2811 void CAgnServerSession::GetFileChangesSinceLastNotificationL()
       
  2812 	{
       
  2813 	// Get calendar change info
       
  2814 	// Arguments: 0 : Output - Data buffer 
       
  2815 	//            1 : Output - Size of buffer
       
  2816 	//            2 : Input - Session Id
       
  2817 
       
  2818 	TInt sessionId = iMessage.Int2();;
       
  2819 	delete iBuffer;
       
  2820 	iBuffer = NULL;
       
  2821 	TInt buffersize = 0;
       
  2822 	if(iAgnSessionFileManager)
       
  2823 		{
       
  2824 		TInt index = iAgnSessionFileManager->GetSessionFile(sessionId);
       
  2825 		if(index >= 0)
       
  2826 			{
       
  2827 			buffersize = iAgnSessionFileManager->GetSessionFileByIndex(index).GetFileChangesSinceLastNotificationL(iBuffer);       
       
  2828 			}
       
  2829 		}
       
  2830 
       
  2831 	TPckg<TInt> size(buffersize);
       
  2832 	iMessage.WriteL(KSlot1, size);
       
  2833 	}
       
  2834 
       
  2835 void CAgnServerSession::GetChangesSinceLastNotificationL()
       
  2836 	{
       
  2837 	// Get changed entries from the log kept in the model
       
  2838 	// Arguments: 0 : Output - Data buffer 
       
  2839 	//			   1 : Input  - Size of buffer
       
  2840 	
       
  2841 	TCalCollectionId collectionId = iMessage.Int2();;
       
  2842 	delete iBuffer;
       
  2843 	iBuffer = NULL;
       
  2844 	TInt buffersize = 0;
       
  2845 	TInt64 fileId = 0;
       
  2846 	if(iAgnSessionFileManager)
       
  2847 		{
       
  2848 		CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(collectionId);
       
  2849 		buffersize = client.GetChangesSinceLastNotificationL(iBuffer);
       
  2850 		fileId = client.FileId();
       
  2851 		}
       
  2852 	
       
  2853 	TPckg<TInt> size(buffersize);
       
  2854 	iMessage.WriteL(KSlot1, size);
       
  2855 	TPckg<TInt64> fileIdPackage(fileId);
       
  2856 	iMessage.WriteL(KSlot3, fileIdPackage);
       
  2857 	}
       
  2858 
       
  2859 void CAgnServerSession::FindInstancesL()
       
  2860 	{
       
  2861 	// Restore length
       
  2862 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot2);
       
  2863 	
       
  2864 	// Restore buffer
       
  2865 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  2866 	CleanupStack::PushL(buffer);
       
  2867 	buffer->ExpandL(0, KBufferSize);
       
  2868 
       
  2869 	TPtr8 des(buffer->Ptr(0));
       
  2870 	iMessage.ReadL(KSlot2, des);
       
  2871 	
       
  2872 	TFindInstanceParams parameters;
       
  2873 	
       
  2874 	RDesReadStream readStream(des);
       
  2875 	
       
  2876 	parameters.InternalizeL(readStream);
       
  2877 	TInt filecount = readStream.ReadInt16L();
       
  2878 	const TInt KInstanceArrayGranularity = 16;
       
  2879 	CArrayFixSeg<TAgnSortInstance>* instances = new (ELeave) CArrayFixSeg<TAgnSortInstance>(KInstanceArrayGranularity);
       
  2880 	CleanupStack::PushL(instances);
       
  2881 	for(TInt ii=0;ii<filecount;++ii)
       
  2882 		{
       
  2883 		TInt64 fileId;
       
  2884 		readStream >> fileId;
       
  2885 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  2886 		if(file->IsLocked())
       
  2887 			{
       
  2888 			User::Leave(KErrLocked);
       
  2889 			}
       
  2890 		CAgnEntryModel* model = file->Model();
       
  2891 		model->FindInstancesL(*instances, parameters);
       
  2892 		}
       
  2893 	
       
  2894 	TAgnDaySortKey sortKey(AgnDateTime::MaxDate(), parameters.iUndatedTodoTimeLocal);
       
  2895 	instances->Sort(sortKey);
       
  2896 	
       
  2897 	// Now put the relevant info into a buffer
       
  2898 	delete iBuffer;
       
  2899 	iBuffer = NULL;
       
  2900 
       
  2901 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  2902 	
       
  2903 	// Create a write stream for this buffer
       
  2904 	RBufWriteStream bufStream;
       
  2905 	bufStream.Open(*iBuffer);
       
  2906 	CleanupClosePushL(bufStream);	
       
  2907 
       
  2908 	const TInt KCount = instances->Count();
       
  2909 
       
  2910 	bufStream.WriteUint32L(KCount);
       
  2911 	
       
  2912 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  2913 		{
       
  2914 		TAgnInstance instance;
       
  2915 		instance.iId = (*instances)[ii].InstanceIdL();
       
  2916 		instance.iCollectionId = (*instances)[ii].SimpleEntry().CollectionId();
       
  2917 		bufStream << instance;
       
  2918 		}
       
  2919 
       
  2920 	bufStream.CommitL();
       
  2921 	
       
  2922 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  2923 
       
  2924 	CleanupStack::PopAndDestroy(instances);
       
  2925 	CleanupStack::PopAndDestroy(buffer);
       
  2926 
       
  2927 	// Send it back to the client
       
  2928 	TPckg<TInt> size(iBuffer->Size());
       
  2929 	iMessage.WriteL(KSlot1, size);
       
  2930 	}
       
  2931 
       
  2932 // CAgnInstanceInfo //	
       
  2933 	
       
  2934 CAgnInstanceInfo* CAgnInstanceInfo::NewL(const CAgnSimpleEntry& aSimpleEntry)
       
  2935 	{
       
  2936 	CAgnInstanceInfo* self = CAgnInstanceInfo::NewLC(aSimpleEntry);
       
  2937 	CleanupStack::Pop(self);
       
  2938 	return self;
       
  2939 	}
       
  2940 
       
  2941 
       
  2942 CAgnInstanceInfo* CAgnInstanceInfo::NewLC(const CAgnSimpleEntry& aSimpleEntry)
       
  2943 	{
       
  2944 	CAgnInstanceInfo* self = new (ELeave) CAgnInstanceInfo();
       
  2945 	CleanupStack::PushL(self);
       
  2946 	self->ConstructL(aSimpleEntry);
       
  2947 	return self;
       
  2948 	}
       
  2949 
       
  2950 void CAgnInstanceInfo::ConstructL(const CAgnSimpleEntry& aSimpleEntry)
       
  2951 	{
       
  2952 	iType = aSimpleEntry.Type();
       
  2953 	if ( aSimpleEntry.RptDef() )
       
  2954 		{
       
  2955 		iRptDef = CAgnRptDef::NewL(aSimpleEntry);
       
  2956 		iRptDef->CopyL(*aSimpleEntry.RptDef());
       
  2957 		}
       
  2958 	else
       
  2959 		{
       
  2960 		iStartTimeUtc = aSimpleEntry.StartTime().UtcL();
       
  2961 		iEndTimeUtc = aSimpleEntry.EndTime().UtcL();
       
  2962 		}
       
  2963 	}
       
  2964 
       
  2965 CAgnInstanceInfo::CAgnInstanceInfo()
       
  2966 	{
       
  2967 	}
       
  2968 
       
  2969 CCalEntry::TType CAgnInstanceInfo::Type() const
       
  2970 	{
       
  2971 	return iType;
       
  2972 	}
       
  2973 	
       
  2974 CAgnInstanceInfo::~CAgnInstanceInfo()
       
  2975 	{
       
  2976 	delete iRptDef;
       
  2977 	}
       
  2978 
       
  2979 const CAgnRptDef* CAgnInstanceInfo::RptDef() const
       
  2980 	{
       
  2981 	return iRptDef;
       
  2982 	}
       
  2983 
       
  2984 const TTime& CAgnInstanceInfo::StartTimeUtc() const
       
  2985 	{
       
  2986 	return iStartTimeUtc;
       
  2987 	}
       
  2988 
       
  2989 const TTime& CAgnInstanceInfo::EndTimeUtc() const
       
  2990 	{
       
  2991 	return iEndTimeUtc;
       
  2992 	}
       
  2993 	
       
  2994 // TAgnMessageToComplete //
       
  2995 	
       
  2996 TAgnMessageToComplete::TAgnMessageToComplete(RMessage2& aMessage, TBool aReportProgress, CAgnServerSession& aSession)
       
  2997 	:iMessage(aMessage), iReportProgress(aReportProgress), iSession(aSession)		
       
  2998 	{
       
  2999 	}
       
  3000 
       
  3001 RMessage2 TAgnMessageToComplete::Message() const
       
  3002 	{
       
  3003 	return iMessage;
       
  3004 	}
       
  3005 
       
  3006 TBool TAgnMessageToComplete::ReportProgress() const
       
  3007 	{
       
  3008 	return iReportProgress;
       
  3009 	}
       
  3010 
       
  3011 CAgnServerSession& TAgnMessageToComplete::Session() const
       
  3012 	{
       
  3013 	return iSession;
       
  3014 	}
       
  3015        
       
  3016 /*
       
  3017 @capability WriteUserData
       
  3018 @capability ReadUserData
       
  3019 */
       
  3020 void CAgnServerSession::DeleteEntryByUIdL(TCalLocalUid aUniqueId, TCalCollectionId aCollectionId)
       
  3021 	{
       
  3022 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(aCollectionId); 
       
  3023 	if(file->IsLocked())
       
  3024 		{
       
  3025 		User::Leave(KErrLocked);
       
  3026 		}
       
  3027 
       
  3028 	CAgnEntry* entry = file->Model()->FetchEntryL(aUniqueId);
       
  3029 	if (entry)
       
  3030 		{
       
  3031 		CleanupStack::PushL(entry);
       
  3032 		DeleteEntryL(*entry, aCollectionId);
       
  3033 		CleanupStack::PopAndDestroy(entry);
       
  3034 		}
       
  3035 	}
       
  3036 	
       
  3037 void CAgnServerSession::DeleteEntryByIdL(TAgnEntryId aEntryId, TCalCollectionId aCollectionId)
       
  3038 	{
       
  3039 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(aCollectionId);
       
  3040 	__ASSERT_ALWAYS(file, User::Leave(KErrCorrupt));
       
  3041 	if(file->IsLocked())
       
  3042 		{
       
  3043 		User::Leave(KErrLocked);
       
  3044 		}
       
  3045 	CAgnEntry* entry = file->Model()->FetchEntryL(aEntryId);
       
  3046 	if (entry)
       
  3047 		{
       
  3048 		CleanupStack::PushL(entry);
       
  3049 		DeleteEntryL(*entry, aCollectionId);
       
  3050 		CleanupStack::PopAndDestroy(entry);
       
  3051 		}
       
  3052 	}
       
  3053 	
       
  3054 void CAgnServerSession::DeleteEntryL()
       
  3055 	{
       
  3056 	TPckgBuf<TAgnEntryId> entryId;
       
  3057 	iMessage.ReadL(KSlot0,entryId);
       
  3058 	TUint8 fileId = iMessage.Int1();
       
  3059 	DeleteEntryByIdL(entryId(), fileId);
       
  3060 	}
       
  3061 	
       
  3062 void CAgnServerSession::DeleteEntryL(CAgnEntry& aEntry, TCalCollectionId aCollectionId)
       
  3063 	{
       
  3064 	CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(aCollectionId);
       
  3065 	client.DeleteEntryL(aEntry);
       
  3066 	}
       
  3067 
       
  3068 void CAgnServerSession::FetchEntryByGuidL()
       
  3069 	{
       
  3070 	// Get a list of entries from the server with this GUID
       
  3071 	// currently setup extractor
       
  3072 	// Arguments:  0 : Output - Data buffer 
       
  3073 	//			   1 : Output - Size of buffer
       
  3074 	//			   2 : Input - Guid
       
  3075 	//create the buffer
       
  3076 
       
  3077 	HBufC8* bufptr = ReadClientDes8LC(KSlot2);
       
  3078 	TPtr8 guid = bufptr->Des();
       
  3079 
       
  3080 	RPointerArray<CAgnEntry> list;
       
  3081 	CleanupResetAndDestroyPushL(list);
       
  3082 	CAgnServFile* file = GetFileL(KSlot3);
       
  3083 	if(file->IsLocked())
       
  3084 		{
       
  3085 		User::Leave(KErrLocked);
       
  3086 		}
       
  3087 
       
  3088 	file->Model()->FetchEntriesL(guid, list);
       
  3089 
       
  3090 	delete iBuffer;
       
  3091 	iBuffer = NULL;
       
  3092 
       
  3093 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  3094 	
       
  3095 	// Create a write stream for this buffer
       
  3096 	RBufWriteStream bufStream;
       
  3097 	bufStream.Open(*iBuffer);
       
  3098 	CleanupClosePushL(bufStream);	
       
  3099 
       
  3100 	const TInt KCount = list.Count();
       
  3101 
       
  3102 	bufStream.WriteUint32L(KCount);
       
  3103 
       
  3104 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  3105 		{
       
  3106 		CAgnEntry* entry = list[ii];
       
  3107 
       
  3108  		bufStream.WriteUint32L( entry->Type() );
       
  3109  		entry->ExternalizeToBufferL(bufStream);
       
  3110 		}
       
  3111 		
       
  3112 	bufStream.CommitL();
       
  3113 	
       
  3114 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  3115 	CleanupStack::PopAndDestroy(&list); // list.Close()
       
  3116 	CleanupStack::PopAndDestroy(bufptr);
       
  3117 
       
  3118 
       
  3119 	// Send it back to the client
       
  3120 	TPckg<TInt> size(iBuffer->Size());
       
  3121 	iMessage.WriteL(KSlot1, size);
       
  3122 	}
       
  3123 
       
  3124 void CAgnServerSession::FetchSimpleEntriesByGuidL()
       
  3125 	{
       
  3126 	// Get a list of entries from the server with this GUID
       
  3127 	// currently setup extractor
       
  3128 	// Arguments:  0 : Output - Data buffer 
       
  3129 	//			   1 : Output - Size of buffer
       
  3130 	//			   2 : Input - Guid
       
  3131 	//create the buffer
       
  3132 
       
  3133 	RPointerArray<CAgnEntry> list;
       
  3134 	CleanupResetAndDestroyPushL(list);
       
  3135 
       
  3136 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot2);
       
  3137 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  3138 	CleanupStack::PushL(buffer);
       
  3139 	buffer->ExpandL(0, KBufferSize);
       
  3140 
       
  3141 	TPtr8 des(buffer->Ptr(0));
       
  3142 	iMessage.ReadL(KSlot2, des);
       
  3143 
       
  3144 	RDesReadStream readStream(des);
       
  3145 	TInt uidLen = readStream.ReadInt16L();
       
  3146 	HBufC8* uid = HBufC8::NewLC(uidLen);
       
  3147 	TPtr8 guid = uid->Des();
       
  3148 	readStream.ReadL(guid, uidLen);
       
  3149 	TInt filecount = readStream.ReadInt16L();
       
  3150 	TInt preEntryCount = 0;;
       
  3151 	TInt entryCount = 0;
       
  3152 	for(TInt ii=0;ii<filecount;++ii)
       
  3153 		{
       
  3154 		TUint8 fileId = readStream.ReadUint8L();
       
  3155 		CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  3156 		if(file->IsLocked())
       
  3157 			{
       
  3158 			User::Leave(KErrLocked);
       
  3159 			}
       
  3160 		file->Model()->FetchEntriesL(*uid, list);
       
  3161 		entryCount = list.Count();
       
  3162 		for(TInt jj = preEntryCount; jj<entryCount; ++jj)
       
  3163 			{
       
  3164 			list[jj]->SetCollectionId(fileId);
       
  3165 			}
       
  3166 		preEntryCount = entryCount;
       
  3167 		}
       
  3168 	CleanupStack::PopAndDestroy(uid);
       
  3169 	CleanupStack::PopAndDestroy(buffer);
       
  3170 
       
  3171 	delete iBuffer;
       
  3172 	iBuffer = NULL;
       
  3173 
       
  3174 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  3175 	
       
  3176 	// Create a write stream for this buffer
       
  3177 	RBufWriteStream bufStream;
       
  3178 	bufStream.Open(*iBuffer);
       
  3179 	CleanupClosePushL(bufStream);	
       
  3180 
       
  3181 	const TInt KCount = list.Count();
       
  3182 
       
  3183 	bufStream.WriteUint32L(KCount);
       
  3184 
       
  3185 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  3186 		{
       
  3187 		CAgnEntry* entry = list[ii];
       
  3188 		
       
  3189 		bufStream.WriteUint32L(entry->Type());
       
  3190 		// explictly use the simple entriy's ExternalizeL
       
  3191  		entry->CAgnSimpleEntry::ExternalizeL(bufStream, ETrue);
       
  3192  		bufStream.WriteUint8L(entry->CollectionId());
       
  3193 		}
       
  3194 		
       
  3195 	bufStream.CommitL();
       
  3196 	
       
  3197 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  3198 	CleanupStack::PopAndDestroy(&list); // list.Close()
       
  3199 
       
  3200 	// Send it back to the client
       
  3201 	TPckg<TInt> size(iBuffer->Size());
       
  3202 	iMessage.WriteL(KSlot1, size);
       
  3203 	}
       
  3204 
       
  3205 void CAgnServerSession::DeleteEntriesByLocalUidL()
       
  3206 	{
       
  3207 	
       
  3208 	// Delete entries by their local uids
       
  3209 	// Arguments: 0 : Input  - Size of data buffer
       
  3210 	//			  1 : Input  - Data Buffer (containing filter)
       
  3211 	const TInt KBufferSize = iMessage.Int0();
       
  3212 
       
  3213 	// Restore buffer
       
  3214 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  3215 	CleanupStack::PushL(buffer);
       
  3216 
       
  3217 	buffer->ExpandL(0, KBufferSize);
       
  3218 	TPtr8 des(buffer->Ptr(0));
       
  3219 	iMessage.ReadL(KSlot1, des);
       
  3220 
       
  3221 	// Internalize the data from the stream
       
  3222 	RBufReadStream readStream;
       
  3223 	readStream.Open(*buffer);
       
  3224 	CleanupClosePushL(readStream);
       
  3225 	
       
  3226 	const TInt KCount = readStream.ReadUint32L();
       
  3227 	TUint8 fileId = iMessage.Int2();
       
  3228 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  3229 		{
       
  3230 		const TCalLocalUid KUniqueId = readStream.ReadUint32L();
       
  3231 		DeleteEntryByUIdL(KUniqueId, fileId);
       
  3232 		}
       
  3233 
       
  3234 	CleanupStack::PopAndDestroy(&readStream);	// readStream.Close();
       
  3235 
       
  3236 	CleanupStack::PopAndDestroy(buffer);		// buffer
       
  3237 	}
       
  3238 
       
  3239 void CAgnServerSession::DeleteEntryByGuidL()
       
  3240 	{
       
  3241 
       
  3242 	HBufC8* guid = ReadClientDes8LC(KSlot0);
       
  3243 	TBool commitAndNotify = iMessage.Int1();
       
  3244 	TPckgBuf<TInt64> fileId;
       
  3245 	iMessage.ReadL(KSlot2, fileId);
       
  3246 	CAgnSessionFile& client = iAgnSessionFileManager->GetSessionFileL(fileId());
       
  3247 	client.DeleteEntryByGuidL(*guid, commitAndNotify);
       
  3248 	CleanupStack::PopAndDestroy(guid);
       
  3249 	}
       
  3250 	
       
  3251 void CAgnServerSession::CommitL()
       
  3252 	{
       
  3253 	TUint8 fileId = iMessage.Int0();
       
  3254 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  3255 	if(file->IsLocked())
       
  3256 		{
       
  3257 		User::Leave(KErrLocked);
       
  3258 		}
       
  3259 	file->Model()->CommitL();
       
  3260 	}	
       
  3261 
       
  3262 void CAgnServerSession::RollbackL()
       
  3263 	{
       
  3264 	TUint8 fileId = iMessage.Int0();
       
  3265 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId);
       
  3266 
       
  3267 	//We cannot allow Rollback to happen if a file is locked.
       
  3268 	//A change requested by one client if not committed, can be undone when another client requests a RollBack.
       
  3269 	//This cannot be shifted to "RequiresFileLock" section as this operation can be allowed if session is not ready. 
       
  3270 	if(file->IsLocked())
       
  3271 		{
       
  3272 		User::Leave(KErrLocked);
       
  3273 		}
       
  3274 	file->Model()->Rollback();
       
  3275 	}
       
  3276 
       
  3277 CAgnServFile* CAgnServerSession::GetFileL(TInt aSlot)
       
  3278 	{
       
  3279 	TPckgBuf<TInt64> fileId;
       
  3280 	iMessage.ReadL(aSlot, fileId);
       
  3281 	return iAgnServer.FileMgr()->GetFileL(fileId());
       
  3282 	}
       
  3283 
       
  3284 void CAgnServerSession::TzRulesLastModifiedDateTimeL()
       
  3285 	{
       
  3286 	TPckgBuf<TInt64> fileId;
       
  3287 	iMessage.ReadL(KSlot1, fileId);
       
  3288 	CAgnServFile* file = iAgnServer.FileMgr()->GetFileL(fileId());
       
  3289 	TPckgBuf<TTime> time(file->Model()->TzRulesLastModifiedDateL());
       
  3290 	iMessage.WriteL(KSlot0, time);
       
  3291 	}
       
  3292 
       
  3293 TInt CAgnServerSession::FileIdCount()
       
  3294 	{
       
  3295 	TInt count = 0;
       
  3296 	if(iAgnSessionFileManager)
       
  3297 		{
       
  3298 		count = iAgnSessionFileManager->FileIdCount();
       
  3299 		}
       
  3300 	return count;
       
  3301 	}
       
  3302 
       
  3303 TInt64 CAgnServerSession::FileId(TInt aIndex)
       
  3304 	{
       
  3305 	TInt64 fileId = KNullFileId;
       
  3306 	if(iAgnSessionFileManager)
       
  3307 		{
       
  3308 		fileId = iAgnSessionFileManager->FileId(aIndex);
       
  3309 		}
       
  3310 	return fileId;
       
  3311 	}
       
  3312 
       
  3313 void CAgnServerSession::SetCalendarInfoL()
       
  3314 	{
       
  3315 	// Restore length
       
  3316 	const TInt KBufferSize = iMessage.GetDesLength(KSlot1);
       
  3317 
       
  3318 	// Restore buffer
       
  3319 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  3320 	CleanupStack::PushL(buffer);
       
  3321 	buffer->ExpandL(0, KBufferSize);
       
  3322 
       
  3323 	TPtr8 des(buffer->Ptr(0));
       
  3324 	iMessage.ReadL(KSlot1, des);
       
  3325 	RDesReadStream readStream(des);
       
  3326 
       
  3327 	CAgnCalendarInfo* info = CAgnCalendarInfo::NewL();
       
  3328 	CleanupStack::PushL(info);
       
  3329 	info->IpcInternalizeL(readStream);
       
  3330 
       
  3331 	// try to get the file if it is already open
       
  3332 	HBufC* filename = ReadClientDesLC(KSlot0);
       
  3333 	HBufC* parsedFilename = iAgnServer.FileMgr()->ParseFilenameLC(*filename);
       
  3334 	parsedFilename->Des().Fold();
       
  3335 	CAgnServFile* file = iAgnServer.FileMgr()->GetFile(*parsedFilename);
       
  3336 
       
  3337 	TBool closeFile(EFalse);
       
  3338 
       
  3339 	if (!file)
       
  3340 		{
       
  3341 		// the file is not open so we must open it now
       
  3342 		CalCommon::TCalFileVersionSupport status;
       
  3343 		file = &iAgnServer.FileMgr()->OpenAgendaL(*filename, iAgnServer, status);
       
  3344 		closeFile = ETrue;
       
  3345 		CleanupStack::PushL(TCleanupItem(CleanupCloseAgendaImmediately, file));
       
  3346 		}
       
  3347 
       
  3348 	// we have the file open, now set the file name on the info
       
  3349 	// before saving the info in a stream in the file.
       
  3350 	TParsePtrC parse(*parsedFilename);
       
  3351 	HBufC* shortFileName = HBufC::NewLC(parsedFilename->Length());
       
  3352 	shortFileName->Des().Append(parse.Drive());
       
  3353 	shortFileName->Des().Append(parse.NameAndExt());
       
  3354 	info->SetFileNameL(*shortFileName);
       
  3355 	TBool fileInfoExist = file->SetCalendarInfoL(*info);
       
  3356 
       
  3357 	// set the file name to the correct format
       
  3358 	CAgnFileChangeInfo* changeInfo = NULL;
       
  3359 	if(fileInfoExist)
       
  3360 		{
       
  3361 		changeInfo = CAgnFileChangeInfo::NewL(shortFileName, MCalFileChangeObserver::ECalendarInfoUpdated);
       
  3362 		}
       
  3363 	else
       
  3364 		{
       
  3365 		changeInfo = CAgnFileChangeInfo::NewL(shortFileName, MCalFileChangeObserver::ECalendarInfoCreated);
       
  3366 		}
       
  3367 	CleanupStack::Pop(shortFileName);
       
  3368 	CleanupStack::PushL(changeInfo);
       
  3369 	CalendarFileChangedL(*changeInfo);//add the change to the buffer
       
  3370 	CleanupStack::PopAndDestroy(changeInfo);
       
  3371 	if (closeFile)
       
  3372 		{
       
  3373 		// This will call CloseAgenda(ETrue)
       
  3374 		CleanupStack::PopAndDestroy();
       
  3375 		}
       
  3376 
       
  3377 	CleanupStack::PopAndDestroy(parsedFilename);
       
  3378 	CleanupStack::PopAndDestroy(filename);
       
  3379 	CleanupStack::PopAndDestroy(info);
       
  3380 	CleanupStack::PopAndDestroy(buffer);
       
  3381 	}
       
  3382 
       
  3383 	void CAgnServerSession::GetPropertyValueL()
       
  3384 	{
       
  3385 	// try to get the file if it is already open
       
  3386 	HBufC* filename = ReadClientDesLC(KSlot2);
       
  3387 	HBufC* parsedFilename = iAgnServer.FileMgr()->ParseFilenameLC(*filename);
       
  3388 	parsedFilename->Des().Fold();
       
  3389 	CAgnServFile* file = iAgnServer.FileMgr()->GetFile(*parsedFilename);
       
  3390 
       
  3391 	TBool closeFile(EFalse);
       
  3392 
       
  3393 	if (!file)
       
  3394 		{
       
  3395 		// the file is not open so we must open it now
       
  3396 		CalCommon::TCalFileVersionSupport status;
       
  3397 		TRAPD(err, file = &iAgnServer.FileMgr()->OpenAgendaL(*filename, iAgnServer, status));
       
  3398 		
       
  3399 		if (err == KErrNone)
       
  3400 			{
       
  3401 			// Everything was fine when opening the file
       
  3402 			closeFile = ETrue;
       
  3403 			CleanupStack::PushL(TCleanupItem(CleanupCloseAgendaImmediately, file));
       
  3404 			}
       
  3405 		else if (err == KErrNoMemory || err == KErrNotFound)
       
  3406 			{
       
  3407 			// Leave if we ran out of memory or the file does not exist
       
  3408 			// for other leave types we assume that the file is corrupt
       
  3409 			// and we will return some invalid metadata later
       
  3410 			User::Leave(err);
       
  3411 			}
       
  3412 		}
       
  3413 
       
  3414 	HBufC8* value(NULL);
       
  3415 
       
  3416 	if (file)
       
  3417 		{
       
  3418 		TPckgBuf<TStreamId> streamId;
       
  3419 		iMessage.ReadL(KSlot3, streamId);
       
  3420 		value = file->GetPropertyValueLC(streamId());
       
  3421 		}
       
  3422 	else
       
  3423 		{
       
  3424 		// We failed to open the file
       
  3425 		value = KNullDesC8().AllocLC();
       
  3426 		}
       
  3427 
       
  3428 	delete iBuffer;
       
  3429 	iBuffer = NULL;
       
  3430 	iBuffer = CBufFlat::NewL(1000);
       
  3431 	RBufWriteStream bufStream;
       
  3432 	bufStream.Open(*iBuffer);
       
  3433 	CleanupClosePushL(bufStream);   
       
  3434 
       
  3435 	// Externalize the calendar info
       
  3436 	bufStream << *value;
       
  3437 
       
  3438 	bufStream.CommitL();    
       
  3439 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  3440 
       
  3441 	CleanupStack::PopAndDestroy(value);
       
  3442 
       
  3443 	if (closeFile)
       
  3444 		{
       
  3445 		// This will call CloseAgenda(ETrue)
       
  3446 		CleanupStack::PopAndDestroy();
       
  3447 		}
       
  3448 
       
  3449 	CleanupStack::PopAndDestroy(parsedFilename);
       
  3450 	CleanupStack::PopAndDestroy(filename);
       
  3451 	}
       
  3452 
       
  3453 	void CAgnServerSession::GetCalendarInfoL()
       
  3454 	{
       
  3455 	// try to get the file if it is already open
       
  3456 	HBufC* filename = ReadClientDesLC(KSlot2);
       
  3457 	HBufC* parsedFilename = iAgnServer.FileMgr()->ParseFilenameLC(*filename);
       
  3458 	parsedFilename->Des().Fold();
       
  3459 	CAgnServFile* file = iAgnServer.FileMgr()->GetFile(*parsedFilename);
       
  3460 
       
  3461 	TBool closeFile(EFalse);
       
  3462 
       
  3463 	if (!file)
       
  3464 		{
       
  3465 		// the file is not open so we must open it now
       
  3466 		CalCommon::TCalFileVersionSupport status;
       
  3467 		TRAPD(err, file = &iAgnServer.FileMgr()->OpenAgendaL(*filename, iAgnServer, status));
       
  3468 		
       
  3469 		if (err == KErrNone)
       
  3470 			{
       
  3471 			// Everything was fine when opening the file
       
  3472 			closeFile = ETrue;
       
  3473 			CleanupStack::PushL(TCleanupItem(CleanupCloseAgendaImmediately, file));
       
  3474 			}
       
  3475 		else if (err == KErrNoMemory || err == KErrNotFound)
       
  3476 			{
       
  3477 			// Leave if we ran out of memory or the file does not exist
       
  3478 			// for other leave types we assume that the file is corrupt
       
  3479 			// and we will return some invalid metadata later
       
  3480 			User::Leave(err);
       
  3481 			}
       
  3482 		}
       
  3483 
       
  3484 	CAgnCalendarInfo* info(NULL);
       
  3485 
       
  3486 	if (file)
       
  3487 		{
       
  3488 		info = file->GetCalendarInfoLC();
       
  3489 		}
       
  3490 	else
       
  3491 		{
       
  3492 		// We failed to open the file so send back some
       
  3493 		// invalid calendar info
       
  3494 		info = CAgnCalendarInfo::NewL();
       
  3495 		CleanupStack::PushL(info);
       
  3496 		info->SetIsValid(EFalse);
       
  3497 		
       
  3498 		// set the file name to the correct format
       
  3499 		TParsePtrC parse(*parsedFilename);
       
  3500 		TFileName shortFileName(parse.Drive());
       
  3501 		shortFileName.Append(parse.NameAndExt());
       
  3502 		info->SetFileNameL(shortFileName);
       
  3503 		}
       
  3504 
       
  3505 	delete iBuffer;
       
  3506 	iBuffer = NULL;
       
  3507 	iBuffer = CBufFlat::NewL(1000);
       
  3508 	RBufWriteStream bufStream;
       
  3509 	bufStream.Open(*iBuffer);
       
  3510 	CleanupClosePushL(bufStream);   
       
  3511 
       
  3512 	// Externalize the calendar info
       
  3513 	info->IpcExternalizeL(bufStream);
       
  3514 
       
  3515 	bufStream.CommitL();    
       
  3516 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  3517 
       
  3518 	CleanupStack::PopAndDestroy(info);
       
  3519 
       
  3520 	if (closeFile)
       
  3521 		{
       
  3522 		// This will call CloseAgenda(ETrue)
       
  3523 		CleanupStack::PopAndDestroy();
       
  3524 		}
       
  3525 
       
  3526 	CleanupStack::PopAndDestroy(parsedFilename);
       
  3527 	CleanupStack::PopAndDestroy(filename);
       
  3528 	}
       
  3529 
       
  3530 void CAgnServerSession::CloseAgendas()
       
  3531 	{
       
  3532 	const TInt count = FileIdCount();
       
  3533 	for (TInt ii =0; ii<count; ii++)
       
  3534 		{
       
  3535 		CAgnServFile* servFile = NULL;
       
  3536 		TRAPD(err,  servFile = iAgnServer.FileMgr()->GetFileL(FileId(ii)));
       
  3537 		if(servFile && err==KErrNone)
       
  3538 			{
       
  3539 			servFile->CloseAgenda(EFalse);
       
  3540 			}
       
  3541 		}
       
  3542 	}
       
  3543 
       
  3544 //CAgnSessionFileManager
       
  3545 CAgnSessionFileManager::CAgnSessionFileManager(CAgnServerSession& aAgnServerSession, CAgnServFileMgr& aAgnServFileMgr)
       
  3546 	:iAgnServerSession(aAgnServerSession),iAgnServFileMgr(aAgnServFileMgr)
       
  3547 	{
       
  3548 	}
       
  3549 
       
  3550 CAgnSessionFileManager* CAgnSessionFileManager::NewL(CAgnServerSession& aAgnServerSession, CAgnServFileMgr& aAgnServFileMgr)
       
  3551 	{
       
  3552 	return new(ELeave) CAgnSessionFileManager(aAgnServerSession, aAgnServFileMgr);
       
  3553 	}
       
  3554 
       
  3555 CAgnSessionFileManager::~CAgnSessionFileManager()
       
  3556 	{
       
  3557 	iSessionFiles.ResetAndDestroy();
       
  3558 	}
       
  3559 
       
  3560 TBool CAgnSessionFileManager::AddClientL(TInt64 aFileId, TInt aSessionId)
       
  3561 	{//return ETrue if an object of CAgnSessionFile has been added in the array iSessionFiles
       
  3562 	TBool objectAdded = EFalse;
       
  3563 	TInt index = GetSessionFile(aSessionId);
       
  3564 	if(index < 0)
       
  3565 		{
       
  3566 		CAgnServFile* file = iAgnServFileMgr.GetFileL(aFileId);
       
  3567 		CAgnSessionFile* SessionFile = CAgnSessionFile::NewL(aSessionId, aFileId, *(file->Model()), iAgnServerSession);
       
  3568 		CleanupStack::PushL(SessionFile);
       
  3569 		TLinearOrder<CAgnSessionFile> order(CompareFileId);
       
  3570 		User::LeaveIfError(iSessionFiles.InsertInOrder(SessionFile, order));
       
  3571 		CleanupStack::Pop(SessionFile);
       
  3572 		objectAdded = ETrue;
       
  3573 		}
       
  3574 	else if (iSessionFiles[index]->FileId() == 0)
       
  3575 	    {//CAgnSessionFile was added when the client start to observ the file change but file may not opened yet.
       
  3576 	    CAgnServFile* file = iAgnServFileMgr.GetFileL(aFileId);
       
  3577 	    iSessionFiles[index]->ResetModel(*file);//set the model and file Id.
       
  3578 	    }
       
  3579 	return objectAdded;
       
  3580 	}
       
  3581 	
       
  3582 TInt CAgnSessionFileManager::FileIdCount()
       
  3583 	{
       
  3584 	return iSessionFiles.Count();
       
  3585 	}
       
  3586 
       
  3587 TInt64 CAgnSessionFileManager::FileId(TInt aIndex)
       
  3588 	{
       
  3589 	return iSessionFiles[aIndex]->FileId();
       
  3590 	}
       
  3591 
       
  3592 TInt CAgnSessionFileManager::CompareFileId(const CAgnSessionFile& aLeft, const CAgnSessionFile& aRight)
       
  3593 	 {
       
  3594 	 TInt64 key =aLeft.FileId();
       
  3595 	 return CompareFileId(&key, aRight);
       
  3596 	 }
       
  3597 
       
  3598 TInt CAgnSessionFileManager::CompareFileId(const TInt64* aKey, const CAgnSessionFile& aAgnSessionFile)
       
  3599 	 {
       
  3600 	 if (*aKey > aAgnSessionFile.FileId())
       
  3601 	     {
       
  3602 	     return 1;
       
  3603 	     }
       
  3604 	 else if (*aKey < aAgnSessionFile.FileId())
       
  3605 	     {
       
  3606 	     return -1;
       
  3607 	     }
       
  3608 	 
       
  3609 	 return 0;
       
  3610 	 }
       
  3611 
       
  3612 TInt CAgnSessionFileManager::FindL(TInt64 aFileId) const
       
  3613 	{
       
  3614 	return iSessionFiles.FindInOrder(aFileId, CompareFileId);
       
  3615 	}
       
  3616 
       
  3617 void CAgnSessionFileManager::AddChangeL(const TAgnChange& aChange)
       
  3618 	{
       
  3619 	TInt index = FindL(aChange.iFileId);
       
  3620 	if(index >= 0)
       
  3621 		{
       
  3622 		(*iSessionFiles[index]).AddChangeToBufferL(aChange, &iAgnServerSession);
       
  3623 		}
       
  3624 	}
       
  3625 
       
  3626 void CAgnSessionFileManager::DeleteSessionFile(TInt aSessionId)
       
  3627 	{
       
  3628 	TInt index = GetSessionFile(aSessionId);
       
  3629 	if(index >= 0)
       
  3630 		{
       
  3631 		delete iSessionFiles[index];
       
  3632 		iSessionFiles.Remove(index);
       
  3633 		}
       
  3634 	}
       
  3635 
       
  3636 void CAgnSessionFileManager::DeleteSessionFileIfFileNotificationNotRequired(TInt aSessionId)
       
  3637     {//Delete the object ony if it doesn't request for file notification otherwise set its fileid = 0 which indicate the file is closed by this CCalSession object.
       
  3638     TInt index = GetSessionFile(aSessionId);
       
  3639     if(index >= 0)
       
  3640         {
       
  3641         if(!iSessionFiles[index]->FileNotificationIsReqested())
       
  3642             {
       
  3643             delete iSessionFiles[index];
       
  3644             iSessionFiles.Remove(index);
       
  3645             }
       
  3646         else
       
  3647             {
       
  3648             iSessionFiles[index]->SetFileId(KNullFileId);
       
  3649             }
       
  3650         }
       
  3651     }
       
  3652 
       
  3653 CAgnSessionFile& CAgnSessionFileManager::GetSessionFileL(TInt64 aFileId)
       
  3654 	{
       
  3655 	TInt index = FindL(aFileId);
       
  3656 	if(index < 0)
       
  3657 		{
       
  3658 		User::Leave(KErrNotFound);
       
  3659 		}
       
  3660 	return *iSessionFiles[index];
       
  3661 	}
       
  3662 
       
  3663 TInt CAgnSessionFileManager::GetSessionFile(TInt aSessionId)
       
  3664     {
       
  3665     const TInt count = iSessionFiles.Count();
       
  3666     for (TInt ii = 0; ii < count; ++ii)
       
  3667         {
       
  3668         if(iSessionFiles[ii]->SessionId() == aSessionId)
       
  3669             {
       
  3670             return ii;
       
  3671             }
       
  3672         }
       
  3673     
       
  3674     return KErrNotFound;
       
  3675     }
       
  3676 
       
  3677 CAgnSessionFile& CAgnSessionFileManager::GetSessionFileByIndex(TInt aIndex)
       
  3678     {
       
  3679     __ASSERT_ALWAYS(aIndex >= 0, User::Invariant());
       
  3680     return *iSessionFiles[aIndex];
       
  3681     }
       
  3682 
       
  3683 CAgnSessionFile& CAgnSessionFileManager::GetSessionFileL(TCalCollectionId aCollectionId)
       
  3684 	{
       
  3685 	TInt64 fileId = iAgnServFileMgr.GetLongFileIdL(aCollectionId);
       
  3686 	return GetSessionFileL(fileId);
       
  3687 	}
       
  3688 
       
  3689 void CAgnSessionFileManager::ReSetModel(TInt64 aFileId, const CAgnServFile& aServFile)
       
  3690     {
       
  3691     CAgnSessionFile& sessionFile = GetSessionFileL(aFileId);
       
  3692     sessionFile.ResetModel(aServFile);
       
  3693     }
       
  3694 
       
  3695 CAgnSessionFile::CAgnSessionFile(TInt aSessionId, TInt64 aFileId, CAgnEntryModel* aModel, CAgnServerSession& aAgnServerSession)
       
  3696 	:iSessionId(aSessionId),
       
  3697     iFileId(aFileId),
       
  3698 	iModel(aModel),
       
  3699 	iChangeNotificationPending(ENotificationNotRequested),
       
  3700 	iBulkChangeInProgress(EFalse),
       
  3701 	iChangeFilter(aAgnServerSession),
       
  3702 	iBufferedNotificationsCount(0),
       
  3703 	iNotificationBufferFull(EFalse)
       
  3704 	{
       
  3705 	}
       
  3706 
       
  3707 TInt64 CAgnSessionFile::FileId() const 
       
  3708 	{
       
  3709 	return iFileId;
       
  3710 	}
       
  3711 
       
  3712 CAgnSessionFile* CAgnSessionFile::NewL(TInt aSessionId, TInt64 aFileId, CAgnEntryModel& aModel, CAgnServerSession& aAgnServerSession)
       
  3713 	{
       
  3714 	return new(ELeave) CAgnSessionFile(aSessionId, aFileId, &aModel, aAgnServerSession);
       
  3715 	}
       
  3716 
       
  3717 CAgnSessionFile* CAgnSessionFile::NewL(TInt aSessionId, CAgnServerSession& aAgnServerSession)
       
  3718     {
       
  3719     return new(ELeave) CAgnSessionFile(aSessionId, 0, NULL, aAgnServerSession);
       
  3720     }
       
  3721 
       
  3722 CAgnSessionFile::~CAgnSessionFile()
       
  3723 	{
       
  3724 	iBufferedNotificationStream.Close();
       
  3725 	delete iBufferedNotification;
       
  3726 	delete iEntryIter;
       
  3727 	}
       
  3728 
       
  3729 void CAgnSessionFile::TidyByDateStartL(TAgnMessageToComplete& aMessageToComplete, CAgnServFile& aServerFile)
       
  3730 	{
       
  3731 	aServerFile.TidyByDateStartL(aMessageToComplete, iChangeFilter);
       
  3732 	iBulkChangeInProgress = ETrue;
       
  3733 	}
       
  3734 
       
  3735 void CAgnSessionFile::BulkChangeCompletedL(const CAgnServerSession& aSession, TInt aErr)
       
  3736 	{
       
  3737 	if ( iBulkChangeInProgress )
       
  3738 		{
       
  3739 		if ( aErr == KErrNone )
       
  3740 			{
       
  3741 			if ( iChangeFilter.ChangeBroadcastEnabled() )
       
  3742 				{
       
  3743 				iModel->NotifyChangeL(aSession, NULL, MCalChangeCallBack2::EChangeUndefined, NULL);
       
  3744 				iChangeFilter.SetChangeMadeWhileDisabled(EFalse);
       
  3745 				}
       
  3746 			else
       
  3747 				{
       
  3748 				iChangeFilter.SetChangeMadeWhileDisabled(ETrue);	
       
  3749 				}
       
  3750 
       
  3751 			iModel->NotifyPublishAndSubscribeL(iChangeFilter);
       
  3752 			}
       
  3753 
       
  3754 		iBulkChangeInProgress = EFalse;
       
  3755 		}
       
  3756 
       
  3757 	iModel->SetUpdateAlarmL(ETrue);
       
  3758 	}
       
  3759 
       
  3760 void CAgnSessionFile::SetEnablePubSubNotificationL(TBool aEnablePubSub)
       
  3761 	{
       
  3762 	iChangeFilter.SetEnablePubSubNotification(aEnablePubSub);
       
  3763 	iModel->NotifyPublishAndSubscribeL(iChangeFilter);
       
  3764 	}
       
  3765 
       
  3766 void CAgnSessionFile::EnableChangeBroadcastL(const CAgnServerSession& aAgnServerSession)
       
  3767 	{
       
  3768 	TBool changeMadeWhileDisabled = iChangeFilter.ChangeMadeWhileDisabled();
       
  3769 	iChangeFilter.SetEnableChangeBroadcast(ETrue);
       
  3770 	if ( changeMadeWhileDisabled )
       
  3771 		{
       
  3772 		iModel->NotifyChangeL(aAgnServerSession, NULL, MCalChangeCallBack2::EChangeUndefined, NULL);
       
  3773 		iChangeFilter.SetChangeMadeWhileDisabled(EFalse);
       
  3774 		}
       
  3775 	}
       
  3776 
       
  3777 void CAgnSessionFile::DisableChangeBroadcast()
       
  3778 	{
       
  3779 	iChangeFilter.SetEnableChangeBroadcast(EFalse);
       
  3780 	}
       
  3781 
       
  3782 void CAgnSessionFile::UpdateEntryL(CAgnEntry& aEntry, TBool aDeleteChildren)
       
  3783 	{
       
  3784 	if(iModel->AgnServFile().IsLocked())
       
  3785 		{
       
  3786 		User::Leave(KErrLocked);
       
  3787 		}
       
  3788 	
       
  3789 	iModel->UpdateEntryL(aEntry, &iChangeFilter, aDeleteChildren);
       
  3790 	}
       
  3791 
       
  3792 TAgnEntryId CAgnSessionFile::StoreEntryL(CAgnEntry& aEntry)
       
  3793 	{
       
  3794 	if(iModel->AgnServFile().IsLocked())
       
  3795 		{
       
  3796 		User::Leave(KErrLocked);
       
  3797 		}
       
  3798 
       
  3799 	return iModel->StoreL(aEntry, &iChangeFilter);
       
  3800 	}
       
  3801 
       
  3802 void CAgnSessionFile::DeleteEntryL(CAgnEntry& aEntry)
       
  3803 	{
       
  3804 	if(iModel->AgnServFile().IsLocked())
       
  3805 		{
       
  3806 		User::Leave(KErrLocked);
       
  3807 		}
       
  3808 
       
  3809 	iModel->DeleteEntryL(aEntry, ETrue, &iChangeFilter);
       
  3810 	}
       
  3811 
       
  3812 void CAgnSessionFile::DeleteEntryByGuidL(const TDesC8& aGuid, TBool aCommit)
       
  3813 	{
       
  3814 	if(iModel->AgnServFile().IsLocked())
       
  3815 		{
       
  3816 		User::Leave(KErrLocked);
       
  3817 		}
       
  3818 
       
  3819 	CAgnEntry* entry = iModel->FetchEntryL(aGuid);
       
  3820 
       
  3821 	if( entry )
       
  3822 		{
       
  3823 		CleanupStack::PushL(entry);
       
  3824 		iModel->DeleteEntryL(*entry, ETrue, NULL);
       
  3825 		if (aCommit)
       
  3826 			{
       
  3827 			iModel->CommitAndNotifyDeletesL(iChangeFilter);
       
  3828 			}
       
  3829 		CleanupStack::PopAndDestroy(entry);
       
  3830 		}
       
  3831 	else
       
  3832 		{
       
  3833 		User::Leave(KErrNotFound);
       
  3834 		}
       
  3835 	}
       
  3836 
       
  3837 void CAgnSessionFile::RequestChangeNotification(const RMessage2 aMessage)
       
  3838 	{
       
  3839 	iChangeNotificationMessage = aMessage;
       
  3840 	iChangeNotificationPending = ENotificationRequested;
       
  3841     TUint8 whichNotification = aMessage.Int1();   
       
  3842     if(whichNotification&EEntryChangeInSameFile )
       
  3843         {
       
  3844         RequestEntryChangeNotification();
       
  3845         }
       
  3846     
       
  3847     if(whichNotification&EFileChange  )
       
  3848         {
       
  3849         RequestFileChangeNotification();
       
  3850         }
       
  3851 	}
       
  3852 
       
  3853 void CAgnSessionFile::RequestEntryChangeNotification()
       
  3854     {
       
  3855     iChangeIterested = iChangeIterested|EEntryChangeInSameFile;
       
  3856 	if (iChangeNotificationPending == ENotificationRequested && iBufferedNotification && iBufferedNotification->Size() > 0 )
       
  3857 		{
       
  3858 		iChangeNotificationMessage.Complete(EEntryChangeInSameFile);
       
  3859 		iChangeNotificationPending = ENotificationAwaitingRequest;
       
  3860 		}
       
  3861 	}
       
  3862 
       
  3863 void CAgnSessionFile::RequestFileChangeNotification()
       
  3864     {
       
  3865     iChangeIterested = iChangeIterested|EFileChange;
       
  3866     if ( iChangeNotificationPending == ENotificationRequested && iFileBufferedNotification && iFileBufferedNotification->Size() > 0 )
       
  3867         {
       
  3868         iChangeNotificationMessage.Complete(EFileChange);
       
  3869         iChangeNotificationPending = ENotificationAwaitingRequest;
       
  3870         }
       
  3871       }
       
  3872 
       
  3873 void CAgnSessionFile::CancelChangeNotification(TUint8 aNotificationType)
       
  3874 	{
       
  3875 	if (iChangeNotificationPending != ENotificationNotRequested)
       
  3876 	    {
       
  3877         if(aNotificationType&EEntryChangeInSameFile)
       
  3878             {
       
  3879             iChangeIterested =iChangeIterested&~EEntryChangeInSameFile;
       
  3880             }    
       
  3881         if(aNotificationType&EFileChange)
       
  3882             {
       
  3883             iChangeIterested = iChangeIterested&~EFileChange;
       
  3884             }
       
  3885         if(iChangeIterested == 0)
       
  3886             {
       
  3887             iChangeNotificationPending = ENotificationNotRequested;
       
  3888             if ( ! iChangeNotificationMessage.IsNull())
       
  3889                 {
       
  3890                 iChangeNotificationMessage.Complete(KErrCancel);
       
  3891                 }
       
  3892             }
       
  3893 	    }
       
  3894 	}
       
  3895 
       
  3896 void CAgnSessionFile::SetChangeNotificationParametersL(const TTime aStart, const TTime aEnd,MCalChangeCallBack2::TChangeEntryType aChangeType)
       
  3897 	{
       
  3898 	iChangeFilter.SetChangeParameter(aStart, aEnd, aChangeType);
       
  3899 	}
       
  3900 
       
  3901 TInt CAgnSessionFile::GetChangesSinceLastNotificationL( CBufFlat*& aDataBuffer)
       
  3902 	{
       
  3903 	iBufferedNotificationStream.Close();
       
  3904 		
       
  3905 	// Send it back to the client
       
  3906 	TInt bufferSize = 0;
       
  3907 	if (iBufferedNotification)
       
  3908 		{
       
  3909 		bufferSize = iBufferedNotification->Size();
       
  3910 		}
       
  3911 	
       
  3912 	aDataBuffer = iBufferedNotification ;
       
  3913 	iBufferedNotification = NULL;
       
  3914 	iBufferedNotificationsCount = 0;
       
  3915 	iNotificationBufferFull = EFalse;
       
  3916 	
       
  3917 	return bufferSize;
       
  3918 	}
       
  3919 
       
  3920 TInt CAgnSessionFile::GetFileChangesSinceLastNotificationL( CBufFlat*& aDataBuffer)
       
  3921     {
       
  3922     iFileBufferedNotificationStream.Close();
       
  3923         
       
  3924     // Send it back to the client
       
  3925     TInt bufferSize = 0;
       
  3926     if (iFileBufferedNotification)
       
  3927         {
       
  3928         bufferSize = iFileBufferedNotification->Size();
       
  3929         }
       
  3930     
       
  3931     aDataBuffer = iFileBufferedNotification ;
       
  3932     iFileBufferedNotification = NULL;
       
  3933     iFileBufferedNotificationsCount = 0;
       
  3934     return bufferSize;
       
  3935     }
       
  3936 
       
  3937 TBool CAgnSessionFile::ToNotifyL(const TAgnChange& aChange, CAgnServerSession* aAgnServerSession)
       
  3938     {
       
  3939     if(iChangeNotificationPending == ENotificationNotRequested || !(iChangeIterested &EEntryChangeInSameFile))
       
  3940         {
       
  3941         //Notification is not required.
       
  3942         return EFalse;
       
  3943         }
       
  3944     
       
  3945     if(aChange.iOperationType == MCalChangeCallBack2::EChangeTzRules ||
       
  3946             aChange.iOperationType == MCalChangeCallBack2::EBackupStart ||
       
  3947             aChange.iOperationType == MCalChangeCallBack2::ERestoreStart ||
       
  3948             aChange.iOperationType == MCalChangeCallBack2::EBackupEnd ||
       
  3949             aChange.iOperationType == MCalChangeCallBack2::ERestoreEnd) 
       
  3950         {
       
  3951         //Tz rule has been changed or backup-restore state has been changed.
       
  3952         return ETrue;
       
  3953         }
       
  3954     
       
  3955     if(aAgnServerSession == aChange.iSession)
       
  3956         {
       
  3957         //Calendar entry has been changed but the change came from the same session
       
  3958         return EFalse;
       
  3959         }
       
  3960     
       
  3961     // It is Calendar entry change come from another session
       
  3962     return iChangeFilter.IsValidChangeL(aChange);
       
  3963     }
       
  3964 
       
  3965 void CAgnSessionFile::AddChangeToBufferL(const TAgnChange& aChange, CAgnServerSession* aAgnServerSession)
       
  3966 	{
       
  3967 	if(iChangeNotificationPending == ENotificationRequested && aChange.iOperationType == MCalChangeCallBack2::ERestoredFileCanNotBeOpened)
       
  3968 	    {
       
  3969         iChangeNotificationMessage.Complete(KErrCorrupt);
       
  3970         iChangeNotificationPending = ENotificationAwaitingRequest;
       
  3971 	    }
       
  3972 	else if (ToNotifyL(aChange, aAgnServerSession))         
       
  3973 		{
       
  3974 		// store the change in the notification buffer
       
  3975 		if (!iBufferedNotification)
       
  3976 			{
       
  3977 			iBufferedNotification = CBufFlat::NewL(KGranNotificationBuffer);
       
  3978 			iBufferedNotificationsCount = 0;
       
  3979 			iNotificationBufferFull = EFalse;
       
  3980 			iBufferedNotificationStream.Open(*iBufferedNotification);
       
  3981 			}
       
  3982 
       
  3983 		if (iBufferedNotificationsCount < KMaxNumberOfBufferedNotifications)
       
  3984 			{
       
  3985 			if(!iNotificationBufferFull)
       
  3986 				{
       
  3987 				iBufferedNotificationStream.WriteUint32L(aChange.iEntryId);
       
  3988 				iBufferedNotificationStream.WriteInt8L(aChange.iOperationType);
       
  3989 				iBufferedNotificationStream.WriteInt8L(aChange.iEntryType);
       
  3990 				iBufferedNotificationStream.CommitL();
       
  3991 			
       
  3992 				++iBufferedNotificationsCount;
       
  3993 		
       
  3994 				// notify client that a change has occured
       
  3995 				if (iChangeNotificationPending == ENotificationRequested)
       
  3996 					{
       
  3997 					iChangeNotificationMessage.Complete(EEntryChangeInSameFile);
       
  3998 					iChangeNotificationPending = ENotificationAwaitingRequest;
       
  3999 					}
       
  4000 				}
       
  4001 			}
       
  4002 		else
       
  4003 			{
       
  4004 			iNotificationBufferFull = ETrue;
       
  4005 
       
  4006 			// Clear all the notifications in the buffer
       
  4007 			iBufferedNotification->Reset();
       
  4008 			iBufferedNotificationStream.Open(*iBufferedNotification);		
       
  4009 		
       
  4010 			// Add a single 'Undefined Change' notification to the notification buffer
       
  4011 			iBufferedNotificationStream.WriteUint32L(0);
       
  4012 			iBufferedNotificationStream.WriteInt8L(MCalChangeCallBack2::EChangeUndefined);
       
  4013 			iBufferedNotificationStream.WriteInt8L(MCalChangeCallBack2::EChangeEntryAll);
       
  4014 			iBufferedNotificationStream.CommitL();
       
  4015 	
       
  4016 			// Reset the count to 1 - Undefined Change
       
  4017 			iBufferedNotificationsCount = 1;
       
  4018 			}
       
  4019 		}
       
  4020 	}
       
  4021 
       
  4022 void CAgnSessionFile::AddFileChangeToBufferL(CAgnFileChangeInfo& aFileChangeInfo)
       
  4023     {
       
  4024     if(iChangeNotificationPending != ENotificationNotRequested && iChangeIterested &EFileChange)
       
  4025        {
       
  4026         // store the change in the notification buffer
       
  4027         if (!iFileBufferedNotification)
       
  4028             {
       
  4029             iFileBufferedNotification = CBufFlat::NewL(KGranNotificationBuffer);
       
  4030             iFileBufferedNotificationsCount = 0;
       
  4031             iFileBufferedNotificationStream.Open(*iFileBufferedNotification);
       
  4032             iFileBufferedNotificationStream.WriteInt32L(0);
       
  4033             }
       
  4034         MStreamBuf * streamBuf = iFileBufferedNotificationStream.Sink();
       
  4035         TStreamPos posStart(0);
       
  4036  
       
  4037         if (iFileBufferedNotificationsCount < KMaxNumberOfBufferedNotifications)
       
  4038             {
       
  4039             aFileChangeInfo.ExternalizeL(iFileBufferedNotificationStream);
       
  4040             //bring the stream write position to the start
       
  4041             streamBuf->SeekL(MStreamBuf::EWrite, posStart); 
       
  4042             iFileBufferedNotificationStream.WriteInt32L(++iFileBufferedNotificationsCount);
       
  4043             iFileBufferedNotificationStream.CommitL();           
       
  4044             }
       
  4045         else
       
  4046             {
       
  4047              // Clear all the notifications in the buffer
       
  4048             iFileBufferedNotification->Reset();
       
  4049             iFileBufferedNotificationStream.Open(*iBufferedNotification);       
       
  4050         
       
  4051             // Add a single 'Undefined Change' notification to the notification buffer
       
  4052             CAgnFileChangeInfo* fileChang = CAgnFileChangeInfo::NewL(NULL, MCalFileChangeObserver::ECalendarInfoUpdated);
       
  4053             CleanupStack::PushL(fileChang);
       
  4054             aFileChangeInfo.ExternalizeL(iFileBufferedNotificationStream);
       
  4055             //bring the stream write position to the start
       
  4056             streamBuf->SeekL(MStreamBuf::EWrite, posStart); 
       
  4057             iFileBufferedNotificationStream.WriteInt32L(++iFileBufferedNotificationsCount);
       
  4058             iFileBufferedNotificationStream.CommitL();
       
  4059             CleanupStack::PopAndDestroy(fileChang);
       
  4060             // Reset the count to 1 - Undefined Change
       
  4061             iFileBufferedNotificationsCount = 1;
       
  4062             }
       
  4063         // notify client that a change has occured
       
  4064         if (iChangeNotificationPending == ENotificationRequested)
       
  4065             {
       
  4066             iChangeNotificationMessage.Complete(EFileChange);
       
  4067             iChangeNotificationPending = ENotificationAwaitingRequest;
       
  4068             }
       
  4069         //bring the stream write position to the end
       
  4070        streamBuf->SeekL(MStreamBuf::EWrite, posStart + iFileBufferedNotification->Size());
       
  4071        }
       
  4072     }
       
  4073 
       
  4074 TBool CAgnSessionFile::CreateEntryIterL()
       
  4075 	{
       
  4076 	if(iModel->AgnServFile().IsLocked())
       
  4077 		{
       
  4078 		User::Leave(KErrLocked);
       
  4079 		}
       
  4080 
       
  4081 	if(!iEntryIter)
       
  4082 		{
       
  4083 		iEntryIter = iModel->CreateEntryIterL();
       
  4084 		}
       
  4085 	return  iEntryIter->SetToFirstL();
       
  4086 	}
       
  4087 
       
  4088 TBool CAgnSessionFile::IsEntryAvailableAtIteratorL()
       
  4089 	{
       
  4090 	if(iModel->AgnServFile().IsLocked())
       
  4091 		{
       
  4092 		User::Leave(KErrLocked);
       
  4093 		}
       
  4094 
       
  4095 	__ASSERT_ALWAYS(iEntryIter, User::Leave(KErrCorrupt));
       
  4096 	return iEntryIter->NextL();
       
  4097 	}
       
  4098 
       
  4099 CAgnEntry* CAgnSessionFile::FetchEntryAtIteratorL()
       
  4100 	{
       
  4101 	__ASSERT_ALWAYS(iEntryIter, User::Leave(KErrCorrupt));
       
  4102 	return iModel->FetchEntryL(iEntryIter->At());
       
  4103 	}
       
  4104 
       
  4105 void CAgnSessionFile::ResetModel(const CAgnServFile& aServFile)
       
  4106     {
       
  4107     delete iEntryIter;
       
  4108     iEntryIter = NULL;
       
  4109     iModel = aServFile.Model();
       
  4110     iFileId = iModel->GetFileIdL();
       
  4111     }
       
  4112 
       
  4113 TInt CAgnSessionFile::SessionId()
       
  4114     {
       
  4115     return iSessionId;
       
  4116     }
       
  4117 
       
  4118 TBool CAgnSessionFile::FileNotificationIsReqested()
       
  4119     {
       
  4120     return iChangeIterested& EFileChange;
       
  4121     }
       
  4122 
       
  4123 void CAgnSessionFile::SetFileId(TCalFileId aFileId)
       
  4124     {
       
  4125     iFileId = aFileId;
       
  4126     }
       
  4127 
       
  4128 #ifdef SYMBIAN_SYSTEM_STATE_MANAGEMENT
       
  4129 TBool CAgnServerSession::IsReadOnlyOperation()
       
  4130 	{
       
  4131 	//Only operations that have read user data permissions are allowed once a shutdown notification
       
  4132 	//is received. The Rollback operation is still allowed.
       
  4133 	TInt operation = iMessage.Function();
       
  4134 	if (operation == ERollback || operation < KCapabilityWriteUserData)
       
  4135 		{
       
  4136 		return KErrNone;
       
  4137 		}
       
  4138 	else
       
  4139 		{
       
  4140 		return KErrLocked; 
       
  4141 		}
       
  4142 	}
       
  4143 #endif
       
  4144 
       
  4145 
       
  4146 void CAgnServerSession::CreateInstanceIteratorL()
       
  4147 	{
       
  4148 
       
  4149 	//TFindInstanceParams buffer, CCalSortCriteria buffer, iteratorId
       
  4150 	//Do this first, so it can be pushed off the cleanup stack last
       
  4151 	CAgnSortCriteria* sortCriteria = CAgnSortCriteria::NewL();
       
  4152 	CleanupStack::PushL(sortCriteria);
       
  4153 	
       
  4154 	TFindInstanceParams* parameters = new (ELeave) TFindInstanceParams();
       
  4155 	CleanupStack::PushL(parameters);
       
  4156 	
       
  4157 	RArray<TInt64> fileIds;
       
  4158 	CleanupClosePushL(fileIds);
       
  4159 	
       
  4160 	// Restore find instance parameter
       
  4161 	const TInt KBufferSize = iMessage.GetDesLengthL(KSlot0);
       
  4162 	CBufFlat* buffer = CBufFlat::NewL(KBufferSize);
       
  4163 	CleanupStack::PushL(buffer);
       
  4164 	buffer->ExpandL(0, KBufferSize);
       
  4165 
       
  4166 	TPtr8 des(buffer->Ptr(0));
       
  4167 	iMessage.ReadL(KSlot0, des);
       
  4168 
       
  4169 	RDesReadStream readStream(des);
       
  4170 	parameters->InternalizeL(readStream);
       
  4171 	
       
  4172 	// Restore sort criteria
       
  4173 	const TInt KSortCriteriaSize = iMessage.GetDesLengthL(KSlot1);
       
  4174 	CBufFlat* sortCriteriaBuffer = CBufFlat::NewL(KSortCriteriaSize);
       
  4175 	CleanupStack::PushL(sortCriteriaBuffer);
       
  4176 	sortCriteriaBuffer->ExpandL(0, KSortCriteriaSize);
       
  4177 	TPtr8 desSortCriteria(sortCriteriaBuffer->Ptr(0));
       
  4178 	iMessage.ReadL(KSlot1, desSortCriteria);
       
  4179 	RBufReadStream sortCriteriaStream;
       
  4180 	sortCriteriaStream.Open(*sortCriteriaBuffer);
       
  4181 	sortCriteria->InternalizeL(sortCriteriaStream);
       
  4182 
       
  4183 	//Create iterator with specified finding and sorting settings.
       
  4184 	
       
  4185 	if(iInstanceIteratorMgr == NULL)
       
  4186 		{
       
  4187 		//Do this to protect server from fuzzy attacks.
       
  4188 		iInstanceIteratorMgr = CAgsInstanceIteratorMgr::NewL();
       
  4189 		}
       
  4190 	
       
  4191 	TInt filecount = sortCriteriaStream.ReadInt16L();
       
  4192 	for(TInt ii=0;ii<filecount;++ii)
       
  4193 		{
       
  4194 		TInt64 fileId;
       
  4195 		sortCriteriaStream >> fileId;
       
  4196 		fileIds.AppendL(fileId);
       
  4197 		}
       
  4198 
       
  4199 	CleanupStack::PopAndDestroy(sortCriteriaBuffer);
       
  4200 	CleanupStack::PopAndDestroy(buffer);
       
  4201 
       
  4202 	TInt iteratorId = iInstanceIteratorMgr->CreateIteratorL(parameters, sortCriteria, fileIds, *iAgnServer.FileMgr());
       
  4203 	//We are satisfied that the above line has taken ownership, so we can now pop these two
       
  4204 	CleanupStack::PopAndDestroy(&fileIds);//doesn't destroy the content of the array
       
  4205 	CleanupStack::Pop(parameters);
       
  4206 	CleanupStack::Pop(sortCriteria);
       
  4207 	
       
  4208 	// Send the assigned iterator id back to the client
       
  4209 	TPckg<TInt> id(iteratorId);
       
  4210 	iMessage.WriteL(KSlot2, id);
       
  4211 	}
       
  4212 
       
  4213 void CAgnServerSession::DestroyInstanceIteratorL()
       
  4214 	{
       
  4215 	TInt iteratorId = iMessage.Int0();
       
  4216 	iInstanceIteratorMgr->DestroyIteratorL(iteratorId);
       
  4217 	}
       
  4218 	
       
  4219 void CAgnServerSession::InstanceIteratorNextL()
       
  4220 	{
       
  4221 	TInt iteratorId = iMessage.Int2();
       
  4222 	TInt startIndex = iMessage.Int3();
       
  4223 	
       
  4224 	RArray<TAgnInstance> instances;
       
  4225 	CleanupClosePushL(instances);
       
  4226 	iInstanceIteratorMgr->NextInstancesL(iteratorId, instances, startIndex);
       
  4227 
       
  4228 	delete iBuffer;
       
  4229 	iBuffer = NULL;
       
  4230 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  4231 	
       
  4232 	RBufWriteStream bufStream;
       
  4233 	bufStream.Open(*iBuffer);
       
  4234 	CleanupClosePushL(bufStream);	
       
  4235 
       
  4236 	const TInt KCount = instances.Count();
       
  4237 
       
  4238 	bufStream.WriteUint32L(KCount);
       
  4239 	
       
  4240 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  4241 		{
       
  4242 		bufStream << instances[ii];
       
  4243 		}
       
  4244 
       
  4245 	bufStream.CommitL();
       
  4246 	
       
  4247 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  4248 	CleanupStack::PopAndDestroy(&instances);
       
  4249 
       
  4250 	// Send it back to the client
       
  4251 	TPckg<TInt> size(iBuffer->Size());
       
  4252 	iMessage.WriteL(KSlot1, size);
       
  4253 	}
       
  4254 
       
  4255 void CAgnServerSession::InstanceIteratorPreviousL()
       
  4256 	{
       
  4257 	TInt iteratorId = iMessage.Int2();
       
  4258 	TInt lastIndex = iMessage.Int3();
       
  4259 	
       
  4260 	RArray<TAgnInstance> instances;
       
  4261 	CleanupClosePushL(instances);
       
  4262 	iInstanceIteratorMgr->PreviousInstancesL(iteratorId, instances, lastIndex);
       
  4263 
       
  4264 	delete iBuffer;
       
  4265 	iBuffer = NULL;
       
  4266 	iBuffer = CBufFlat::NewL(KInitialBufferSize);
       
  4267 	
       
  4268 	RBufWriteStream bufStream;
       
  4269 	bufStream.Open(*iBuffer);
       
  4270 	CleanupClosePushL(bufStream);	
       
  4271 
       
  4272 	const TInt KCount = instances.Count();
       
  4273 
       
  4274 	bufStream.WriteUint32L(KCount);
       
  4275 	
       
  4276 	for ( TInt ii = 0; ii < KCount; ++ii )
       
  4277 		{
       
  4278 		bufStream << instances[ii];
       
  4279 		}
       
  4280 
       
  4281 	bufStream.CommitL();
       
  4282 	
       
  4283 	CleanupStack::PopAndDestroy(&bufStream); // bufStream.Close();
       
  4284 	CleanupStack::PopAndDestroy(&instances);
       
  4285 
       
  4286 	// Send it back to the client
       
  4287 	TPckg<TInt> size(iBuffer->Size());
       
  4288 	iMessage.WriteL(KSlot1, size);
       
  4289 	}
       
  4290 
       
  4291 void CAgnServerSession::InstanceIteratorCountL()
       
  4292 	{
       
  4293 	TInt iteratorId = iMessage.Int0();
       
  4294 	TInt count = iInstanceIteratorMgr->CountL(iteratorId);
       
  4295 	TPckg<TInt> size(count);
       
  4296 	iMessage.WriteL(KSlot1, size);
       
  4297 	}
       
  4298 
       
  4299 void CAgnServerSession::InstanceIteratorLocateIndexL()
       
  4300 	{
       
  4301 	TInt iteratorId = iMessage.Int0();
       
  4302 	TPckgBuf<TAgnInstance> instanceId;	
       
  4303 	iMessage.ReadL(KSlot1,instanceId);
       
  4304 	TInt index = iInstanceIteratorMgr->LocateIndexL(iteratorId, instanceId());
       
  4305 	TPckg<TInt> size(index);
       
  4306 	iMessage.WriteL(KSlot2, size);
       
  4307 	}
       
  4308 
       
  4309 
       
  4310