--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/profilesservices/MediaFileList/Src/mediafileprotection.cpp Wed Sep 01 12:20:44 2010 +0100
@@ -0,0 +1,625 @@
+/*
+* Copyright (c) 2007 Nokia Corporation and/or its subsidiary(-ies).
+* All rights reserved.
+* This component and the accompanying materials are made available
+* under the terms of "Eclipse Public License v1.0"
+* which accompanies this distribution, and is available
+* at the URL "http://www.eclipse.org/legal/epl-v10.html".
+*
+* Initial Contributors:
+* Nokia Corporation - initial contribution.
+*
+* Contributors:
+*
+* Description: Class used to check the protection of the
+* media files.
+*
+*/
+
+
+
+
+// INCLUDE FILES
+
+#include "mediafileprotection.h"
+#include "mediafilelist.h"
+#include "mediafilelistdebug.h"
+#include <mediafilelist.rsg>
+
+#include <DRMCommon.h>
+#include <drmutility.h>
+#include <drmagents.h>
+#include <bautils.h>
+#include <StringLoader.h>
+
+
+
+/******************************************************************************
+ * class CMFProtectionHandler
+ ******************************************************************************/
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::NewL
+//
+// -----------------------------------------------------------------------------
+CMFProtectionHandler* CMFProtectionHandler::NewL()
+ {
+ CMFProtectionHandler* self = new (ELeave) CMFProtectionHandler();
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ CleanupStack::Pop(self);
+
+ return self;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::CMFProtectionHandler
+//
+// -----------------------------------------------------------------------------
+//
+CMFProtectionHandler::CMFProtectionHandler()
+ {
+ iMaxFileSize = KErrNotFound;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::CMFProtectionHandler
+//
+// -----------------------------------------------------------------------------
+//
+void CMFProtectionHandler::ConstructL()
+ {
+ iDriveUtil = CDriveUtil::NewL();
+ iVariation = CMediaFileDialogVariation::NewL();
+
+ iDRMHelper = CDRMHelper::NewL( *CCoeEnv::Static() );
+
+ iDRMCommon = DRMCommon::NewL();
+ User::LeaveIfError( iDRMCommon->Connect() );
+
+ iExcludedMimeTypes = CMimeTypeList::NewL();
+
+ User::LeaveIfError( iApaLsSession.Connect() );
+ User::LeaveIfError( iFsSession.Connect() );
+ }
+
+
+// ----------------------------------------------------------------------------
+// Destructor
+//
+// ----------------------------------------------------------------------------
+//
+CMFProtectionHandler::~CMFProtectionHandler()
+ {
+ delete iDriveUtil;
+ delete iVariation;
+
+ delete iDRMHelper;
+
+ if ( iDRMCommon )
+ {
+ iDRMCommon->Disconnect(); // ignore possible error
+ delete iDRMCommon;
+ }
+
+ delete iExcludedMimeTypes;
+ iApaLsSession.Close();
+ iFsSession.Close();
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::SetAttr
+//
+// -----------------------------------------------------------------------------
+void CMFProtectionHandler::SetAttrL( TInt aAttr, TInt aValue )
+ {
+ switch ( aAttr )
+ {
+ case CMediaFileList::EAttrFileSize:
+ {
+ iMaxFileSize = aValue;
+ break;
+ }
+ case CMediaFileList::EAttrAutomatedType:
+ {
+ iAutomatedType = (CDRMHelper::TDRMHelperAutomatedType) aValue;
+ break;
+ }
+
+ default:
+ {
+ break;
+ }
+ }
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::SetAttrL
+//
+// -----------------------------------------------------------------------------
+void CMFProtectionHandler::SetAttrL( TInt aAttr, const TDesC& aValue )
+ {
+ if ( aAttr == CMediaFileList::EAttrExcludeMimeType )
+ {
+ if ( aValue.Length() > KMaxFileName || aValue.Length() == 0 )
+ {
+ User::Leave( KErrArgument );
+ }
+
+ iExcludedMimeTypes->AddMimeTypeL( aValue );
+ }
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsVideoValid
+//
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsVideoValid( const TDesC& aFileName,
+ TIntention aIntention )
+ {
+ TInt err = KErrNone;
+ TBool ret = EFalse;
+
+ TRAP( err, ret = IsVideoValidL (aFileName, aIntention ) )
+
+ if ( err != KErrNone )
+ {
+ return EFalse; // in case of error file is not valid
+ }
+
+ return ret;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsVideoValidL
+//
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsVideoValidL( const TDesC& aFileName,
+ TIntention /*aIntention*/ )
+ {
+ TBuf<KMaxDataTypeLength> dataType( DataTypeL( aFileName ).Des() );
+
+ if ( iExcludedMimeTypes->FindMimeTypeL( dataType ) )
+ {
+ return EFalse;
+ }
+
+ CContent* content = CContent::NewLC( aFileName,
+ EContentShareReadWrite );
+ TInt deliveryMethod = 0;
+ content->GetAttribute( EDeliveryMethod, deliveryMethod );
+
+ CleanupStack::PopAndDestroy( content );
+
+ if( deliveryMethod == EOmaDrm2 )
+ {
+ // if video it is OMA DRM 2 protected, it cannot be previewed
+ return EFalse;
+ }
+ return ETrue;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsFileValid
+//
+// Checks protection state of media file. If this function returns EFalse,
+// media file cannot be used for playing/selection.
+//
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsFileValid( const TDesC& aFileName,
+ TIntention aIntention )
+ {
+ TInt err = KErrNone;
+ TBool ret = EFalse;
+
+ TRAP( err, ret = IsFileValidL (aFileName, aIntention ) )
+
+ if ( err != KErrNone )
+ {
+ return EFalse; // in case of error file is not valid
+ }
+
+ return ret;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsFlieDRMExpired
+//
+// Check if the DRM protect file is expired or have no rights.
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsFlieDRMExpired( const TDesC& aFileName )
+ {
+ // Check whether the file can be set as automated content or not
+ TBool canSetAutomated = EFalse;
+ TInt canSetAutomatedErr = iDRMHelper->CanSetAutomated( aFileName, canSetAutomated );
+
+ // Check if rights expried or no rights to use
+ if ( canSetAutomatedErr == DRMCommon::ERightsExpired ||
+ canSetAutomatedErr == DRMCommon::ENoRights )
+ {
+ return ETrue;
+ }
+ return EFalse;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsFileValidL
+//
+// Function is copy from CFLDDRMImplementation.cpp.
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsFileValidL( const TDesC& aFileName,
+ TIntention aIntention )
+ {
+ TInt err = KErrNone;
+ TBuf<KMaxDataTypeLength> dataType( DataTypeL( aFileName ).Des() );
+
+ if ( aFileName.Length() == 0 )
+ {
+ return ETrue; // empty filename is valid??
+ }
+
+ if ( iExcludedMimeTypes->FindMimeTypeL( dataType ) )
+ {
+ ShowErrorNoteL( R_QTN_INFO_FILE_FORMAT_ERROR );
+ return EFalse;
+ }
+
+ if ( aIntention == CMFProtectionHandler::ESelect &&
+ !CheckFileSize( aFileName, dataType ) )
+ {
+ HBufC* hBuf = StringLoader::LoadLC( R_QTN_INFO_FILE_SIZE_ERROR, iMaxFileSize );
+ TMFDialogUtil::ShowInformationNoteL( *hBuf );
+ CleanupStack::PopAndDestroy( hBuf );
+ return EFalse;
+ }
+
+ if ( iDriveUtil->IsRom( aFileName ) )
+ {
+ return ETrue; // files in ROM are always valid
+ }
+
+ // check if file is WMDRM protected
+ TBool prot = EFalse;
+ TRAP( err, prot = IsFileWMDRMProtectedL( aFileName ) );
+ if ( err != KErrNone )
+ {
+ ShowErrorNoteL( R_QTN_INFO_FILE_FORMAT_ERROR );
+ return EFalse;
+ }
+ if ( prot )
+ {
+ if ( aIntention == EPlay )
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PREV_RIGHTS_USE );
+ }
+ else
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PROTECTED );
+ }
+ return EFalse;
+ }
+
+ ContentAccess::TVirtualPathPtr path( aFileName,
+ ContentAccess::KDefaultContentObject );
+ CData* data = CData::NewLC( path, EContentShareReadWrite );
+ TInt isProtected;
+ err = data->GetAttribute( EIsProtected, isProtected );
+ CleanupStack::PopAndDestroy( data );
+
+ if ( err != DRMCommon::EOk )
+ {
+ // DRM Helper class knows at least rights db corrupted error message.
+ // Leaves on system-wide error code.
+ iDRMHelper->HandleErrorL( err, aFileName );
+ return EFalse;
+ }
+
+ // Obtain information whether the file can be set as automated content
+ TBool canSetAutomated = EFalse;
+ TInt canSetAutomatedErr =
+ iDRMHelper->CanSetAutomated( aFileName, canSetAutomated );
+
+ if ( !isProtected && canSetAutomated )
+ {
+ // The file in question is not DRM protected.
+ // Return ETrue if file is also Ok unprotected, otherwise EFalse.
+ TBool ret = IsFileValidUnprotectedL( aFileName, aIntention );
+ return ret;
+ }
+
+ // Operator requirement: Check restrictions if file is mp4 audio
+ if ( iVariation->IsBlockedProtectedType( dataType ) )
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PROTECTED );
+ return EFalse;
+ }
+
+ if ( canSetAutomatedErr == DRMCommon::ERightsExpired ||
+ canSetAutomatedErr == DRMCommon::ENoRights )
+ {
+ // Rights are expired, future rights or missing
+ iDRMHelper->HandleErrorL( canSetAutomatedErr, aFileName );
+ return EFalse;
+ }
+
+ // Operator requirement: Check DRM v2 tones
+ if ( !canSetAutomated )
+ {
+ // This is DRM v2 file OR count based v1 tone
+ if ( aIntention == EPlay )
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PREV_RIGHTS_USE );
+ }
+ else
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PROTECTED );
+ }
+ return EFalse;
+ }
+
+ TInt32 infoBits( 0x00000000 );
+
+ // Find out rights information
+ if ( !GetFileInfoL( aFileName, infoBits ) )
+ {
+ // Corrupted file or "No rights" situation
+ return EFalse;
+ }
+
+ // Operator requirement: Check CFM protection
+ if ( infoBits & ENoRingingTone )
+ {
+ // This is CFM protected file, ringingtone is set to "no"
+ if ( aIntention == EPlay )
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PREV_RIGHTS_USE );
+ }
+ else
+ {
+ ShowErrorNoteL( R_QTN_INFO_DRM_PREV_RIGHTS_SET );
+ }
+ return EFalse;
+ }
+
+ if ( aIntention == ESelect )
+ {
+ // Rights are good to go, and intention is selection
+ // call SetAutomatedPassive to show 'activation query'
+ iDRMHelper->SetAutomatedType( iAutomatedType );
+ err = iDRMHelper->SetAutomatedPassive( aFileName );
+ if ( err != KErrCancel )
+ {
+ // User accepted dialog
+ User::LeaveIfError( err );
+ // New way, does not require DRM capability
+ data = CData::NewLC( path, EContentShareReadWrite );
+ err = data->ExecuteIntent( ContentAccess::EPlay );
+ // Wrongly requires DRM after all. According to Risto Vilkman
+ // from DRM, KErrAccessDenied can be ignored, since if
+ // CanSetAutomated says the tone is OK, it's OK.
+ if ( err != KErrNone && err != KErrAccessDenied )
+ {
+ User::Leave( err );
+ }
+ CleanupStack::PopAndDestroy( data );
+ }
+ else
+ {
+ // User canceled dialog
+ return EFalse;
+ }
+ }
+
+ return ETrue;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::GetFileInfo
+//
+// Function is copy from CFLDDRMImplementation.cpp.
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::GetFileInfoL( const TDesC& aFileName,
+ TInt32& aInfoBits )
+ {
+ DRMCommon::TContentProtection contentProtection; // ignored
+ HBufC8* mimeType = NULL; // ignored
+ TUint dataLength = 0; // ignored
+ HBufC8* contentURI = NULL;
+
+ // Obtain content URI
+ TInt error = iDRMCommon->GetFileInfo(
+ aFileName, contentProtection, mimeType, contentURI, dataLength );
+ delete mimeType;
+
+ if ( error != DRMCommon::EOk )
+ {
+ delete contentURI;
+ // Handle possible corrupt file situation
+ iDRMHelper->HandleErrorL( error, aFileName );
+ return EFalse;
+ }
+
+ // Obtain rights object
+ CDRMRights* rights = NULL;
+ error = iDRMCommon->GetActiveRights( *contentURI, DRMCommon::EPlay, rights );
+ delete contentURI;
+
+ if ( error == DRMCommon::ENoRights )
+ {
+ delete rights;
+ // There is no rights for given file
+ // Should never arrive here, ENoRights is handled
+ // already in IsFileValidL()
+ iDRMHelper->HandleErrorL( error, aFileName );
+ return EFalse;
+ }
+
+ // Obtain infobits ( needed only for CFM case )
+ aInfoBits = rights->GetPermission().iInfoBits;
+ delete rights;
+ return ETrue;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsFileWMDRMProtectedL
+//
+// Function is copy from CFLDDRMImplementation.cpp.
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsFileWMDRMProtectedL( const TDesC& aFileName )
+ {
+ TBool res = EFalse;
+ RFile hFile;
+
+ TInt err = hFile.Open( iFsSession, aFileName,
+ EFileRead | EFileStream | EFileShareReadersOnly );
+ if ( err == KErrInUse )
+ {
+ err = hFile.Open( iFsSession, aFileName,
+ EFileRead | EFileStream | EFileShareAny );
+ }
+ if ( err != KErrNone )
+ {
+ User::Leave( err );
+ }
+ CleanupClosePushL( hFile );
+
+ TPtrC agent( KNullDesC );
+ DRM::CDrmUtility* drmUtil = DRM::CDrmUtility::NewLC();
+ drmUtil->GetAgentL( hFile, agent );
+ if ( agent.Compare( DRM::KDrmWMAgentName ) == 0 )
+ {
+ res = ETrue;
+ }
+ CleanupStack::PopAndDestroy( drmUtil );
+
+ CleanupStack::PopAndDestroy( &hFile );
+ return res;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::DataTypeL
+//
+// Function is copy from CFLDDRMImplementationCommon.cpp.
+// -----------------------------------------------------------------------------
+//
+TDataType CMFProtectionHandler::DataTypeL( const TDesC& aFileName )
+ {
+ TUid dummyUid = { 0 };
+ TDataType dataType( dummyUid );
+ User::LeaveIfError(
+ iApaLsSession.AppForDocument( aFileName, dummyUid, dataType ) );
+
+ return dataType;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::IsFileValidUnprotectedL
+//
+// Function is copy from CFLDDRMImplementationCommon.cpp.
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::IsFileValidUnprotectedL( const TDesC& aFileName,
+ TIntention aIntention )
+ {
+ TDataType dataType = DataTypeL( aFileName );
+ TBuf<KMaxDataTypeLength> mimeType;
+
+ mimeType = dataType.Des();
+
+ if ( iVariation->IsBlockedType( mimeType ) )
+ {
+ if ( aIntention == ESelect )
+ {
+ ShowErrorNoteL( R_QTN_INFO_TEXT_NOT_ALLOWED );
+ }
+ return EFalse;
+ }
+
+ // Operator requirement. Check if DRM is required with tones.
+ if ( aIntention == EPlay )
+ {
+ if ( iVariation->IsBlockedDemoPlayType( mimeType ) )
+ {
+ return EFalse;
+ }
+ }
+ else
+ {
+ if ( iVariation->IsBlockedUnprotectedType( mimeType ) )
+ {
+ ShowErrorNoteL( R_QTN_INFO_NO_DRM );
+ return EFalse;
+ }
+ }
+
+ return ETrue;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::CheckFileSize
+//
+// -----------------------------------------------------------------------------
+//
+TBool CMFProtectionHandler::CheckFileSize( const TDesC& aFile, const TDesC& aMimeType )
+ {
+ _LIT( KVideo, "video" );
+ const TInt KKiloByte = 1024;
+ const TInt KSmallSize = 10;
+
+ if ( iMaxFileSize < KSmallSize )
+ {
+ return ETrue; // too small size limit
+ }
+ if ( aMimeType.Find( KVideo ) != KErrNotFound )
+ {
+ return ETrue; // only audio files are checked
+ }
+
+ TEntry entry;
+ TInt err = iFsSession.Entry( aFile, entry );
+ if ( err == KErrNone && iMaxFileSize != KErrNotFound )
+ {
+ TInt size = iMaxFileSize * KKiloByte; // KBytes -> Bytes
+ if ( entry.iSize > size )
+ {
+ return EFalse;
+ }
+ }
+
+ return ETrue;
+ }
+
+
+// -----------------------------------------------------------------------------
+// CMFProtectionHandler::ShowErrorNoteL
+//
+// -----------------------------------------------------------------------------
+//
+void CMFProtectionHandler::ShowErrorNoteL( TInt aResourceId )
+ {
+ TMFDialogUtil::ShowInformationNoteL( aResourceId );
+ }
+
+
+// End of File