diff -r 000000000000 -r 95b198f216e5 omadrm/drmengine/dcfrepository/server/src/DcfRepSrv.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/omadrm/drmengine/dcfrepository/server/src/DcfRepSrv.cpp Thu Dec 17 08:52:27 2009 +0200 @@ -0,0 +1,1254 @@ +/* +* Copyright (c) 2002-2009 Nokia Corporation and/or its subsidiary(-ies). +* All rights reserved. +* This component and the accompanying materials are made available +* under the terms of "Eclipse Public License v1.0" +* which accompanies this distribution, and is available +* at the URL "http://www.eclipse.org/legal/epl-v10.html". +* +* Initial Contributors: +* Nokia Corporation - initial contribution. +* +* Contributors: +* +* Description: server implementation +* +*/ + + +// INCLUDE FILES +#include "DcfRepSrv.h" +#include "DcfRepSrvSes.h" +#include "DcfRepCommon.h" +#include "Pair.h" +#include "FileScan.h" +#include +#include +#include +#include +#include +#include // oma2agent +#include "Oma2Dcf.h" +#include "Oma1Dcf.h" +#include "drmlog.h" +#include + +#ifdef RD_MULTIPLE_DRIVE +#include +#endif + +// EXTERNAL DATA STRUCTURES +// EXTERNAL FUNCTION PROTOTYPES +// CONSTANTS +_LIT(KSqlUpdate1 , "select filename,position,cid,group,ttid from dcf where filename = '"); +_LIT(KSqlUpdate2 , "' and position = "); +_LIT(KSqlInsert , "select filename,position,cid,group,ttid from dcf"); +_LIT(KSqlDeleteAll , "delete from dcf"); +_LIT(KGroupIdReplacement, "cid:group@localhost"); +// MACROS +// LOCAL CONSTANTS AND MACROS + +#ifdef RD_MULTIPLE_DRIVE +_LIT( KDbFileLoc, "%c:\\system\\data\\DcfRepDb" ); +#endif + +// MODULE DATA STRUCTURES +// LOCAL FUNCTION PROTOTYPES +LOCAL_C TInt CreateDataBase(RFs& aFs); + +#ifndef RD_MULTIPLE_DRIVE +LOCAL_C TParse DataFile(); +#else // RD_MULTIPLE_DRIVE +LOCAL_C TParse DataFile( RFs& aFs ); +#endif + +LOCAL_C void CreateTablesL(RDbDatabase& aDatabase); +LOCAL_C TInt CreateDataBasePath(RFs& aFs); +// FORWARD DECLARATIONS + +//#define _DRM_TESTING +//#define _MEM_HEAP_USAGE + +// ============================ LOCAL FUNCTIONS =============================== +#ifdef _DRM_TESTING +LOCAL_C void WriteLogL( const TDesC8& text , RFs &aFs ); +LOCAL_C void WriteFileL( const TDesC8& text , RFs &aFs , const TDesC& aName ); +LOCAL_C void CreateLogL(); +LOCAL_C void WriteL( const TDesC8& aText ); +LOCAL_C void WriteL( const TDesC8& aText , TInt aErr ); +LOCAL_C void WriteCurrentTimeL(); + +#ifdef _MEM_HEAP_USAGE +LOCAL_C void WriteHeapAllocL(); +#endif //_MEM_HEAP_USAGE + +#endif //_DRM_TESTING + +// ----------------------------------------------------------------------------- +// Testing stuff +// ----------------------------------------------------------------------------- +// +#ifdef _DRM_TESTING +LOCAL_C void WriteLogL( const TDesC8& text , RFs &aFs ) + { + _LIT( KLogFile , "c:\\CDcfRepSrv.txt" ); + WriteFileL( text , aFs , KLogFile ); + } + +LOCAL_C void WriteFileL( const TDesC8& text , RFs &aFs , const TDesC& aName ) + { + RFile file; + TInt size; + User::LeaveIfError( file.Open( aFs, aName , EFileWrite ) ); + CleanupClosePushL( file ); + User::LeaveIfError( file.Size( size ) ); + User::LeaveIfError( file.Write( size, text ) ); + CleanupStack::PopAndDestroy(&file); //file + } + +LOCAL_C void CreateLogL() + { + RFs fs; + User::LeaveIfError(fs.Connect()); + CleanupClosePushL(fs); + RFile file; + User::LeaveIfError( file.Replace( fs , _L("c:\\CDcfRepSrv.txt") , EFileWrite ) ); + file.Close(); + CleanupStack::PopAndDestroy(&fs); //fs + } + +LOCAL_C void WriteL( const TDesC8& aText ) + { + RFs fs; + User::LeaveIfError( fs.Connect() ); + CleanupClosePushL(fs); + HBufC8* text = HBufC8::NewLC(1000); + TPtr8 textptr(text->Des() ); + textptr.Append( aText ); + textptr.Append( _L8("\r\n") ); + WriteLogL(textptr , fs); + CleanupStack::PopAndDestroy(text); + CleanupStack::PopAndDestroy(&fs); //fs + WriteCurrentTimeL(); +#ifdef _MEM_HEAP_USAGE + WriteHeapAllocL(); +#endif //_MEM_HEAP_USAGE + } + +LOCAL_C void WriteL( const TDesC8& aText , TInt aErr ) + { + _LIT8(KErr,": %d"); + HBufC8* text = HBufC8::NewLC(1000+20); + TBuf8<20> num; + TPtr8 textptr(text->Des()); + textptr.Append(aText); + num.Format(KErr(),aErr); + textptr.Append(num); + WriteL(textptr); + CleanupStack::PopAndDestroy(text); + } + +LOCAL_C void WriteCurrentTimeL() + { + RFs fs; + User::LeaveIfError( fs.Connect() ); + CleanupClosePushL(fs); + HBufC8* text = HBufC8::NewLC(100); + TPtr8 textptr(text->Des() ); + // Date and Time display + TTime time; + time.HomeTime(); + TBuf<256> dateString; + _LIT(KDate,"%*E%*D%X%*N%*Y %1 %2 '%3"); + time.FormatL(dateString,KDate); + textptr.Append(_L( "\r\n\t\tData:\t" ) ); + textptr.Append( dateString ); + _LIT(KTime,"%-B%:0%J%:1%T%:2%S%:3%+B"); + time.FormatL(dateString,KTime); + textptr.Append(_L( "\r\n\t\tTime:\t" ) ); + textptr.Append( dateString ); + textptr.Append(_L( "\r\n" ) ); + textptr.Append(_L( "\r\n" ) ); + WriteLogL(textptr , fs); + CleanupStack::PopAndDestroy(text); + CleanupStack::PopAndDestroy(&fs); //fs + } + +#ifdef _MEM_HEAP_USAGE +LOCAL_C void WriteHeapAllocL() + { + _LIT8(KHeapUsage,"\r\n***** Heap cells allocated: %d *****\r\n"); + TBuf8<256> string; + TInt size = 0; + RFs fs; + User::LeaveIfError( fs.Connect() ); + CleanupClosePushL(fs); + User::Heap().AllocSize(size); + string.Format(KHeapUsage(),size); + WriteLogL(string , fs); + CleanupStack::PopAndDestroy(&fs); //fs + } +#endif //_MEM_HEAP_USAGE + + +#endif //_DRM_TESTING + +// ----------------------------------------------------------------------------- +// DataFile +// Return TParse which contain database file name +// ----------------------------------------------------------------------------- +// +#ifdef RD_MULTIPLE_DRIVE +LOCAL_C TParse DataFile( RFs& aFs ) +#else +LOCAL_C TParse DataFile() +#endif + { +#ifdef _DRM_TESTING + TRAP_IGNORE( WriteL(_L8("DataFile")) ); +#endif + + TParse p; + +#ifndef RD_MULTIPLE_DRIVE + + p.Set(KDbFileLocation,NULL,NULL); + +#else //RD_MULTIPLE_DRIVE + + TInt driveNumber( -1 ); + TChar driveLetter; + DriveInfo::GetDefaultDrive( DriveInfo::EDefaultSystem, driveNumber ); + + aFs.DriveToChar( driveNumber, driveLetter ); + + TFileName dbFile; + dbFile.Format( KDbFileLoc, (TUint)driveLetter ); + + p.Set(dbFile,NULL,NULL); + +#endif + + return p; + } + + +// ----------------------------------------------------------------------------- +// CreateTablesL +// Create table through database session +// ----------------------------------------------------------------------------- +// +LOCAL_C void CreateTablesL(RDbDatabase& aDatabase) + { +#ifdef _DRM_TESTING + WriteL(_L8("CreateTablesL")); +#endif + + CDbColSet* columns = CDbColSet::NewLC(); + + //filename columns + TDbCol filename(KColFilename,EDbColLongText16); + filename.iAttributes = TDbCol::ENotNull; + columns->AddL(filename); + + //position columns + TDbCol position(KColPosition,EDbColUint16); + position.iAttributes = TDbCol::ENotNull; + columns->AddL(position); + + //content id columns + TDbCol cid(KColCid,EDbColLongText16); + cid.iAttributes = TDbCol::ENotNull; + columns->AddL(cid); + + //content group id columns + TDbCol group(KColGroupId,EDbColLongText16); + columns->AddL(group); + + //transaction id columns + TDbCol ttid(KColTtid,EDbColText16,KTtidLen); + columns->AddL(ttid); + + aDatabase.CreateTable( KTable,*columns); + CleanupStack::PopAndDestroy(columns); //columns + + } + +// ----------------------------------------------------------------------------- +// CreateDataBasePath +// Create database with client side database access +// ----------------------------------------------------------------------------- +// +LOCAL_C TInt CreateDataBasePath(RFs& aFs) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("CreateDataBasePath"))); +#endif + + TInt err = 0; + +#ifndef RD_MULTIPLE_DRIVE + + err = aFs.MkDirAll( DataFile(). DriveAndPath() ); + +#else //RD_MULTIPLE_DRIVE + + err = aFs.MkDirAll( DataFile( aFs ). DriveAndPath() ); + +#endif + + return err; + } + +// ----------------------------------------------------------------------------- +// CreateDataBase +// Create database with client side database access +// ----------------------------------------------------------------------------- +// +LOCAL_C TInt CreateDataBase(RFs& aFs) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("CreateDataBase"))); +#endif + + RDbNamedDatabase database; + TInt err = 0; + TFileName file; + +#ifndef RD_MULTIPLE_DRIVE + + file = DataFile().FullName(); + + +#else // RD_MULTIPLE_DRIVE + + file = DataFile( aFs ).FullName(); + +#endif + + if (!err) + { +#ifdef _DRM_TESTING + TRAP(r,WriteL(_L8("CreateDataBase->DataFile"),err)); +#endif + err = CreateDataBasePath(aFs); + + err = database.Create(aFs,file); + if (!err) + { +#ifdef _DRM_TESTING + TRAP(r,WriteL(_L8("CreateDataBase->database.Create"),err)); +#endif + TRAP( err , CreateTablesL(database) ); +#ifdef _DRM_TESTING + TRAP(r,WriteL(_L8("CreateDataBase->CreateTablesL"),err)); +#endif + } + database.Close(); + } + return err; + } + +// ----------------------------------------------------------------------------- +// From8To16 +// transfer buf from 8 bit to 16 bit +// ----------------------------------------------------------------------------- +// +LOCAL_C TInt From8To16( const TDesC8& a8 , HBufC16*& a16 ) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("From8To16"))); +#endif + + TInt err = KErrNone; + a16 = HBufC::NewMax( a8.Length() ); + if ( a16 ) + { + TPtr ptr( a16->Des() ); + ptr.SetLength( a8.Length() ); + for (TInt i = 0 ; iStartWatching(); + iArmed = ETrue; + } + + +// ----------------------------------------------------------------------------- +// CDcfRepSrv::NewLC +// Two-phased constructor. +// ----------------------------------------------------------------------------- +// +CDcfRepSrv* CDcfRepSrv::NewLC() + { + CDcfRepSrv* self = new( ELeave ) CDcfRepSrv; + CleanupStack::PushL( self ); + self->ConstructL(); + return self; + } + + +// Destructor +CDcfRepSrv::~CDcfRepSrv() + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("~CDcfRepSrv"))); +#endif + + delete iScan; + CleanScanInternal(); + CleanDatabase(); + iFs.Close(); + for (TInt i = 0 ; i < iMessageList.Count() ; i++ ) + { + if ( iMessageList[i]!=NULL && !(iMessageList[i]->IsNull()) ) + { + iMessageList[i]->Complete(KErrCancel); + } + + } + iMessageList.ResetAndDestroy(); + iMessageList.Close(); + } + +// ----------------------------------------------------------------------------- +// CDcfRepSrv::NewSessionL +// Called when a client requires a new instance. +// ----------------------------------------------------------------------------- +CSession2* CDcfRepSrv::NewSessionL(const TVersion &aVersion, + const RMessage2& /*aMessage*/ ) const + { +#ifdef _DRM_TESTING + WriteL(_L8("NewSessionL")); +#endif + // check we're the right version + if (!User::QueryVersionSupported(TVersion(KDcfRepMajorVersionNumber, + KDcfRepMinorVersionNumber, + KDcfRepBuildVersionNumber), + aVersion)) + { + User::Leave(KErrNotSupported); + } + + // make new session + return CDcfRepSrvSes::NewL(); + } + + +// ----------------------------------------------------------------------------- +// Startup(). +// This function starts the actual DCF Repository server after initializing +// the cleanup stack and active scheduler. +// Returns: TInt: Symbian OS error code. +// ----------------------------------------------------------------------------- +// + +TInt CDcfRepSrv::Startup( void ) + { + TInt err = 0; + TBool clientIsWaiting = EFalse; + RSemaphore semaphore; + + CTrapCleanup* cleanupStack = CTrapCleanup::New(); + + if (cleanupStack == NULL) + { + PanicServer(ECreateTrapCleanup); + } + + // check if the client wants to be signaled that we are ready + if ( semaphore.OpenGlobal(KDcfRepSemaphoreName) == KErrNone ) + { + clientIsWaiting = ETrue; + } + + TRAP(err, StartupL()); + + // release client side waiting + if (clientIsWaiting) + { + semaphore.Signal(); + semaphore.Close(); + } + + if (err != KErrNone) + { + PanicServer(ESrvCreateServer); + } + + delete cleanupStack; + cleanupStack = NULL; + return KErrNone; + } + + +// ----------------------------------------------------------------------------- +// StartupL(). +// This function starts the actual DCF Repository after initializing scheduler +// ----------------------------------------------------------------------------- +// + +void CDcfRepSrv::StartupL() + { + // Construct active scheduler + CActiveScheduler* activeScheduler = new (ELeave) CActiveScheduler; + CleanupStack::PushL(activeScheduler) ; + + // Install active scheduler + // We don't need to check whether an active scheduler is already installed + // as this is a new thread, so there won't be one + CActiveScheduler::Install(activeScheduler); + + // Construct our server + CDcfRepSrv::NewLC(); + + // Start handling requests + CActiveScheduler::Start(); + + CleanupStack::PopAndDestroy(2); // activeScheduler and anonymous CDcfRepSrv + } + +void CDcfRepSrv::PanicServer(TDcfRepSrvPanic aPanic) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("PanicServer"))); + r = 0; +#endif + + User::Panic(KDcfRepSrv, aPanic); + } + + +// ----------------------------------------------------------------------------- +// AddFileL() +// The function will add a file info into database +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::AddFileL( const TDesC& aFile ) + { +#ifdef _DRM_TESTING + WriteL(_L8("AddFileL")); +#endif + + TInt err = 0; + TInt state = iState; + TBool flag = EFalse; + + // to process the file as doing scanning fully for file system + iState = EStateFullScan; + err = ProcessFile(aFile , flag); + // change the state back + iState = state; + User::LeaveIfError(err); + if ( flag == ENoDcf ) + { + User::Leave(KErrNotSupported); + } + else if (flag == EOma2Dcf) + { + AddDomainRoL(aFile); + } + } + +// ----------------------------------------------------------------------------- +// AddDomainRoL() +// The function will add a file info into database +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::AddDomainRoL( const TDesC& aFile ) + { +#ifdef _DRM_TESTING + WriteL(_L8("AddDomainRoL")); +#endif + + __UHEAP_MARK; + RFile file; + TPtr8 ptr(NULL,0,0); + CContent* content =NULL; + User::LeaveIfError(file.Open(iFs, aFile, EFileShareReadersOrWriters | EFileWrite ) ); + CleanupClosePushL(file); + content = CContent::NewL(file); + CleanupStack::PushL(content); + User::LeaveIfError(content->AgentSpecificCommand(EEmbedDomainRo, + KNullDesC8, ptr )); + CleanupStack::PopAndDestroy(2); // content, file + __UHEAP_MARKEND; + } + + +// ----------------------------------------------------------------------------- +// OpenDatabaseL() +// The function will open database +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::OpenDatabaseL() + { +#ifdef _DRM_TESTING + WriteL(_L8("OpenDatabaseL")); +#endif + + + TInt err = CreateDataBase(iFs); + if ( err==KErrAlreadyExists ) + { + err = KErrNone; + } + + User::LeaveIfError(iDbs.Connect()); + +#ifndef RD_MULTIPLE_DRIVE + + User::LeaveIfError(iDb.Open(iDbs,DataFile().FullName())); + +#else // RD_MULTIPLE_DRIVE + + User::LeaveIfError(iDb.Open(iDbs,DataFile(iFs).FullName())); + +#endif + } + + +// ----------------------------------------------------------------------------- +// CleanTableL() +// The function will empty the talbe +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::CleanTableL() + { +#ifdef _DRM_TESTING + WriteL(_L8("CleanTableL")); +#endif + + User::LeaveIfError(iDb.Execute(KSqlDeleteAll())); + } + +// ----------------------------------------------------------------------------- +// ProcessFile() +// This function check if the file is DRM protected and add it into database. +// ----------------------------------------------------------------------------- +// +TInt CDcfRepSrv::ProcessFile(const TDesC& aFile , TInt& aType) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("ProcessFile"))); +#endif + + TInt err = 0; + aType = ENoDcf; + + TRAP(err , CheckFileL(aFile , aType)); + if (aType) + { + TRAP(err , StoreFileL(aFile,aType)); + } + return err; + } + +// ----------------------------------------------------------------------------- +// CheckFileL() +// check if it is target file +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::CheckFileL(const TDesC& aFile , TInt& aType) + { +#ifdef _DRM_TESTING + WriteL(_L8("CheckFileL")); +#endif + + RFile f; + TInt pos = 0; + TBuf8<256> buf; + + switch(iState) + { + case EStateFullScan: + case EStateScan: + { + User::LeaveIfError(f.Open(iFs,aFile,EFileRead|EFileShareReadersOrWriters)); + CleanupClosePushL(f); + User::LeaveIfError(f.Seek(ESeekStart,pos)); + User::LeaveIfError(f.Read(0,buf)); + CleanupStack::PopAndDestroy(&f); + if (COma1Dcf::IsValidDcf(buf)) + { + aType = EOma1Dcf; + } +#ifdef __DRM_OMA2 + else if (COma2Dcf::IsValidDcf(buf)) + { + aType = EOma2Dcf; + } +#endif + else + { + aType = ENoDcf; + } + + } + break; + case EStateSetTtid: + { + TParse p; + User::LeaveIfError(p.Set(aFile,NULL,NULL)); + if ( !p.Ext().Compare( KOma2DcfExtension ) || + !p.Ext().Compare( KOma2DcfExtensionAudio ) || + !p.Ext().Compare( KOma2DcfExtensionVideo ) ) + { + User::LeaveIfError(f.Open(iFs,aFile,EFileRead|EFileShareReadersOrWriters)); + CleanupClosePushL(f); + User::LeaveIfError(f.Seek(ESeekStart,pos)); + User::LeaveIfError(f.Read(0,buf)); + CleanupStack::PopAndDestroy(&f); + if (COma1Dcf::IsValidDcf(buf)) + { + aType = EOma1Dcf; + } +#ifdef __DRM_OMA2 + else if (COma2Dcf::IsValidDcf(buf)) + { + aType = EOma2Dcf; + } +#endif + else + { + aType = ENoDcf; + } + } + } + break; + default: + ; + } + } + +// ----------------------------------------------------------------------------- +// StoreFile() +// save file info into database +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::StoreFileL(const TDesC& aFile , TInt aType) + { +#ifdef _DRM_TESTING + WriteL(_L8("StoreFileL")); +#endif + + RFile f; + User::LeaveIfError(f.Open(iFs,aFile,EFileRead|EFileShareReadersOrWriters)); + CleanupClosePushL(f); + TInt i = 0; + TInt setTtid = -1; + HBufC16* cid = NULL; + HBufC16* ttid = NULL; + HBufC16* group = NULL; + + if (aType == EOma1Dcf) + { + COma1Dcf* d = COma1Dcf::NewL(f); + CleanupStack::PushL(d); + User::LeaveIfError( From8To16( *(d->iContentID) , cid ) ); + CleanupStack::PopAndDestroy(d); + CleanupStack::PushL(cid); + ttid = HBufC::NewMaxLC(16); + *ttid = KNullDesC16; + UpdateDatabaseL(aFile , KStartPosition , *cid , KNullDesC() , *ttid); + if (iCidList) + { + for (i = 0; iCount(); i++) + { + HBufC* temp = NULL; + User::LeaveIfError( From8To16(*((*iCidList)[i]) , temp ) ); + CleanupStack::PushL(temp); + if (!temp->Compare(*cid)) + { + delete (*iCidList)[i]; + iCidList->Remove(i); + CleanupStack::PopAndDestroy(temp); + break; + } + CleanupStack::PopAndDestroy(temp); //temp + } + if (iCidList->Count()<=0) + { + CompleteScanning(KErrNone); + } + } + CleanupStack::PopAndDestroy(2); //cid,ttid + } + else if (aType == EOma2Dcf) + { + COma2Dcf* d = COma2Dcf::NewL(f); + CleanupStack::PushL(d); + + // Set group ID and content ID for this entry + if (d->iGroupId) + { + User::LeaveIfError( From8To16( *(d->iGroupId) , group ) ); + + // replace the content ID for this entry with a placeholder to prevent + // that the file is listed wrongly under the group ID + cid = KGroupIdReplacement().AllocL(); + } + else + { + User::LeaveIfError( From8To16( *(d->iContentID) , cid ) ); + group = HBufC::NewMaxL(16); + *group = KNullDesC16; + } + CleanupStack::PushL(cid); + CleanupStack::PushL(group); + + if (iState == EStateSetTtid) + { + for (i = 0; iPairList && iCount() && !ttid; i++) + { + HBufC* temp = NULL; + User::LeaveIfError( From8To16(*((*iPairList)[i]->iCid) , temp ) ); + CleanupStack::PushL(temp); + if (!temp->Compare(*cid)) + { + User::LeaveIfError( From8To16(*((*iPairList)[i]->iTtid) , ttid ) ); + + // EFileWrite is needed for this case + // So we cannot do it here. we must close the file + setTtid = i; + } + CleanupStack::PopAndDestroy(temp); //temp + } + } + if (!ttid) + { + if (d->iTransactionTracking) + { + User::LeaveIfError( From8To16( *(d->iTransactionTracking) , ttid ) ); + } + else + { + ttid = HBufC::NewMaxL(16); + *ttid = KNullDesC16; + } + } + CleanupStack::PushL(ttid); + + UpdateDatabaseL(aFile , KStartPosition , *cid , *group , *ttid); + if (iCidList) + { + for (i = 0; iCount(); i++) + { + HBufC* temp = NULL; + User::LeaveIfError( From8To16(*((*iCidList)[i]) , temp ) ); + CleanupStack::PushL(temp); + if (!temp->Compare(*cid)) + { + delete (*iCidList)[i]; + iCidList->Remove(i); + CleanupStack::PopAndDestroy(temp); + break; + } + CleanupStack::PopAndDestroy(temp); //temp + } + if (iCidList->Count()<=0) + { + CompleteScanning(KErrNone); + } + } + CleanupStack::PopAndDestroy(4); // group,ttid,cid,d + } + + CleanupStack::PopAndDestroy(&f); // f + + if (setTtid>=0) + { + ResetTtidL( aFile , *((*iPairList)[setTtid]->iTtid)); + } + } + +// ----------------------------------------------------------------------------- +// ResetTtidL() +// save new ttid into file +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::ResetTtidL( + const TDesC& aFile, + const TDesC8& aTtid + ) + { +#ifdef _DRM_TESTING + WriteL(_L8("ResetTtidL")); +#endif + + RFile f; + User::LeaveIfError(f.Open(iFs,aFile, EFileWrite|EFileShareReadersOrWriters )); + CleanupClosePushL(f); + COma2Dcf* d = COma2Dcf::NewL(f); + CleanupStack::PushL(d); + ResetTtidL(d,aTtid); + CleanupStack::PopAndDestroy(2); // f,d + } + +// ----------------------------------------------------------------------------- +// ResetTtidL() +// save new ttid into file +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::ResetTtidL( + COma2Dcf* aDcf, + const TDesC8& aTtid + ) + { +#ifdef _DRM_TESTING + WriteL(_L8("ResetTtidL")); +#endif + + aDcf->SetTransactionIdL(aTtid); + } + +// ----------------------------------------------------------------------------- +// UpdateDatabaseL() +// save info into database +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::UpdateDatabaseL( + const TDesC& aFile, + TInt aPos, + const TDesC& aCid , + const TDesC& aGroupId , + const TDesC& aTtid) + { +#ifdef _DRM_TESTING + WriteL(_L8("UpdateDatabaseL")); +#endif + + HBufC* sql = NULL; + TPtr ptr(NULL,0,0); + TBuf<4> num; + sql = HBufC::NewMaxLC(aFile.Length()+200); + ptr.Set(sql->Des()); + ptr.SetLength(0); + ptr.Append(KSqlUpdate1); + ptr.Append(aFile); + ptr.Append(KSqlUpdate2); + num.Num(aPos); + ptr.Append(num); + + iView.Close(); + + User::LeaveIfError( + iView.Prepare( + iDb,TDbQuery(ptr), + TDbWindow::EUnlimited, + RDbView::EUpdatable + ) + ); + User::LeaveIfError(iView.EvaluateAll()); + if (iView.FirstL()) + { + iView.UpdateL(); + iView.SetColL(KOrdCid,aCid); + iView.SetColL(KOrdGroupId,aGroupId); + iView.SetColL(KOrdTtid,aTtid); + iView.PutL(); + } + else + { + iView.Reset(); + iView.Close(); + iView.Prepare( + iDb,TDbQuery(KSqlInsert), + TDbWindow::EUnlimited, + RDbView::EInsertOnly + ); + iView.InsertL(); + iView.SetColL(KOrdFilename,aFile); + iView.SetColL(KOrdPosition,aPos); + iView.SetColL(KOrdCid,aCid); + iView.SetColL(KOrdGroupId,aGroupId); + iView.SetColL(KOrdTtid,aTtid); + iView.PutL(); + } + iView.Reset(); + iView.Close(); + CleanupStack::PopAndDestroy(sql); //sql + } + +// ----------------------------------------------------------------------------- +// State() +// This function returns the state of the Server +// ----------------------------------------------------------------------------- +// +TInt CDcfRepSrv::State() const + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("State"))); +#endif + + return iState; + } + +// ----------------------------------------------------------------------------- +// SetState() +// This function set the state of the Server +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::SetState(TServerState aMode) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("SetState"))); +#endif + + iState = aMode; + } + + +// ----------------------------------------------------------------------------- +// CompleteScanning(). +// This function complete request from client +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::CompleteScanning(TInt aRet) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("CompleteScanning"))); +#endif + + for (TInt i = 0 ; iIsNull()) ) + { + iMessageList[i]->Complete(aRet); + } + } + iMessageList.ResetAndDestroy(); + + CleanScanInternal(); + iState = EStateIdle; + } + +// ----------------------------------------------------------------------------- +// SetMessage(). +// This function save the incomplete message to server +// ----------------------------------------------------------------------------- +// +RMessage2* CDcfRepSrv::SetMessageL(const RMessage2& aMessage) + { +#ifdef _DRM_TESTING + WriteL(_L8("SetMessageL")); +#endif + RMessage2* m = NULL; + m = new (ELeave) RMessage2(aMessage); + iMessageList.AppendL(m); + return m; + } + + +// ----------------------------------------------------------------------------- +// RemoveMessage(). +// This function to remove the imcomplete message from server if it is still there +// when session is deleted +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::RemoveMessageL( const RMessage2* aMessage ) + { + for (TInt i = 0 ; i*& aList) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("SetCidList"))); +#endif + + if (iCidList) + { + iCidList->ResetAndDestroy(); + iCidList->Close(); + delete iCidList; + } + iCidList = aList; + } + +// ----------------------------------------------------------------------------- +// SetPairList(). +// This function set list of pairs for content ID and transation ID +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::SetPairList(RPointerArray*& aList) + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("SetPairList"))); +#endif + + if (iPairList) + { + iPairList->ResetAndDestroy(); + iPairList->Close(); + delete iPairList; + } + iPairList = aList; + } + + +// ----------------------------------------------------------------------------- +// Scan() +// This function scan the file system +// ----------------------------------------------------------------------------- +// +TInt CDcfRepSrv::Scan() + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("Scan"))); +#endif + + TInt err = 0; + if (iState == EStateFullScan) + { + TRAP(err,CleanTableL()); + } + err = iScan->SearchContent(this); + if (err) + { + CleanScanInternal(); + iState = EStateIdle; + } + return err; + } + +void CDcfRepSrv::CleanScanInternal() + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("CleanScanInternal"))); +#endif + + if (iCidList) + { + iCidList->ResetAndDestroy(); + iCidList->Close(); + delete iCidList; + iCidList = NULL; + } + if (iPairList) + { + iPairList->ResetAndDestroy(); + iPairList->Close(); + delete iPairList; + iPairList = NULL; + } + } + +void CDcfRepSrv::CleanDatabase() + { +#ifdef _DRM_TESTING + TRAPD(r,WriteL(_L8("CleanDatabase"))); +#endif + + iView.Close(); + iDb.Close(); + iDbs.Close(); + } + +// ----------------------------------------------------------------------------- +// CDcfRepSrv::WatchedObjectChangedL +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::WatchedObjectChangedL( const TDesC& aObject ) + { + DRMLOG( _L( "CDcfRepSrv::WatchedObjectChangedL ->" ) ); + DRMLOG( aObject ); + + if ( aObject.Left( KProcIdentifier().Length() ) == KProcIdentifier && iArmed ) + { +#ifdef _DEBUG + DRMLOG( _L( "Peer process killed (DEBUG mode, not rebooting)" ) ); +#else + DRMLOG( _L( "Peer process killed, rebooting" ) ); + RStarterSession starter; + User::LeaveIfError( starter.Connect() ); + starter.Shutdown(); + starter.Close(); +#endif + } + + DRMLOG( _L( "CDRMRightsServer::WatchedObjectChangedL <-" ) ); + } + +// ----------------------------------------------------------------------------- +// CDcfRepSrv::StopWatchingL +// ----------------------------------------------------------------------------- +// +void CDcfRepSrv::StopWatchingL() + { + DRMLOG( _L( "CDcfRepSrv::StopWatchingL ->" ) ); + iArmed = EFalse; + DRMLOG( _L( "CDRMRightsServer::StopWatchingL <-" ) ); + } + +// ========================== OTHER EXPORTED FUNCTIONS ========================= + +// ----------------------------------------------------------------------------- +// E32 Entry for Executable +// ----------------------------------------------------------------------------- + +TInt E32Main() + { + return CDcfRepSrv::Startup(); + } + +// End of File