diff -r 000000000000 -r 95b198f216e5 omadrm/drmengine/utils/src/MultipartHandler.cpp --- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/omadrm/drmengine/utils/src/MultipartHandler.cpp Thu Dec 17 08:52:27 2009 +0200 @@ -0,0 +1,335 @@ +/* +* Copyright (c) 2005 - 2008 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: utility class for handling multipart/related HTTP responses +* in ROAP +* +*/ + + + +// INCLUDE FILES +#include +#include +#include "Base64.h" +#include "MultipartHandler.h" + +#ifdef _DEBUG + +#include +#define MULTIPART_DEBUGLIT( a ) RDebug::Print( _L ( a ) ); + +#else // DEBUG + +#define MULTIPART_DEBUGLIT( a ) + +#endif // DEBUG + +// CONSTANTS + +_LIT8( KBoundaryPrefix, "--" ); +_LIT8( KCrLf, "\r\n" ); +_LIT8( KCrLfCrLf, "\r\n\r\n" ); + + +// ============================ MEMBER FUNCTIONS =============================== + +// --------------------------------------------------------------------------- +// TMultipartHandler::TMultipartHandler +// --------------------------------------------------------------------------- +// +TMultipartHandler::TMultipartHandler(): + iState( EPreamble ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::TMultipartHandler -->" ) + iBuffer.SetLength( 0 ); + MULTIPART_DEBUGLIT( "--> TMultipartHandler::TMultipartHandler" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::WriteL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::WriteL( + const TDesC8& aData ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::WriteL -->" ) + switch ( iState ) + { + case EPreamble: + MULTIPART_DEBUGLIT( "EPreamble" ) + HandlePreambleL( aData ); + break; + case EBodyPartHeaders: + MULTIPART_DEBUGLIT( "EBodyPartHeaders" ) + HandleBodyPartHeadersL( aData ); + break; + case EBodyPart: + MULTIPART_DEBUGLIT( "EBodyPart" ) + HandleBodyPartL( aData ); + break; + case EEpilog: + MULTIPART_DEBUGLIT( "EEpilog" ) + break; + } + MULTIPART_DEBUGLIT( "--> TMultipartHandler::WriteL" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::FindDashBoundary +// --------------------------------------------------------------------------- +// +TBool TMultipartHandler::FindDashBoundary( + const TDesC8& aBuffer, + TInt& aStart, + TInt& aEnd ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::FindDashBoundary -->" ) + TBool r( EFalse ); + const TInt KBoundaryPrefixLength( KBoundaryPrefix().Length() ); + const TInt KCrLfLength( KCrLf().Length() ); + aStart = aBuffer.Find( KBoundaryPrefix ); + if ( aStart >= 0 ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::FindDashBoundary aStart nonnegative" ) + aEnd = aBuffer.Mid( aStart ).Find( KCrLf ); + aEnd += aStart; + if ( aEnd > aStart + KBoundaryPrefixLength ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::FindDashBoundary aEnd > aStart + (boundary prefix length)" ) + const TInt delimiterLength( aEnd - aStart + KCrLfLength ); + __ASSERT_ALWAYS( KMaxBoundaryLength >= delimiterLength, User::Invariant() ); + iDelimiter.Copy( KCrLf ); + iDelimiter.Append( KBoundaryPrefix ); + iDelimiter.Append( aBuffer.Mid( + aStart + KBoundaryPrefixLength, + aEnd - aStart - KBoundaryPrefixLength ) ); + r = ETrue; + MULTIPART_DEBUGLIT( "TMultipartHandler::FindDashBoundary found dash boundary" ) + } + } + MULTIPART_DEBUGLIT( "--> TMultipartHandler::FindDashBoundary" ) + return r; + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::FindHeaderEnd +// --------------------------------------------------------------------------- +// +TBool TMultipartHandler::FindHeaderEnd( + const TDesC8& aBuffer, + TInt& aStart, + TInt& aEnd ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::FindHeaderEnd -->" ) + TBool r( EFalse ); + + aStart = aBuffer.Find( KCrLfCrLf ); + if ( aStart >= 0 ) + { + aEnd = aStart + KCrLfCrLf().Length(); + r = ETrue; + } + MULTIPART_DEBUGLIT( "--> TMultipartHandler::FindHeaderEnd" ) + return r; + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::FindDelimiter +// --------------------------------------------------------------------------- +// +TBool TMultipartHandler::FindDelimiter( + const TDesC8& aBuffer, + TInt& aStart, + TInt& aEnd ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::FindDelimiter -->" ) + TBool r( EFalse ); + + aStart = aBuffer.Find( iDelimiter ); + if ( aStart >= 0 ) + { + aEnd = aStart + iDelimiter.Length(); + r = ETrue; + } + MULTIPART_DEBUGLIT( "--> TMultipartHandler::FindDelimiter" ) + return r; + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::HandlePreambleL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::HandlePreambleL( + const TDesC8& aData ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::HandlePreambleL -->" ) + TInt bStart( 0 ); + TInt bEnd( 0 ); + HBufC8* buffer( NULL ); + + buffer = HBufC8::NewLC( iBuffer.Length() + aData.Length() ); + buffer->Des().Copy( iBuffer ); + buffer->Des().Append( aData ); + if ( !FindDashBoundary( *buffer, bStart, bEnd ) ) + { + iBuffer.Copy( buffer->Right( Min( + KMaxBoundaryLength, buffer->Length() ) ) ); + } + else + { + iBuffer.SetLength( 0 ); + iState = EBodyPartHeaders; + StartBodyPartHeadersL(); + HandleBodyPartHeadersL( buffer->Mid( bEnd + KCrLf().Length() ) ); + } + CleanupStack::PopAndDestroy( buffer ); + MULTIPART_DEBUGLIT( "--> TMultipartHandler::HandlePreambleL" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::HandleBodyPartHeadersL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::HandleBodyPartHeadersL( + const TDesC8& aData ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::HandleBodyPartHeadersL -->" ) + TInt bStart( 0 ); + TInt bEnd( 0 ); + HBufC8* buffer( HBufC8::NewLC( iBuffer.Length() + aData.Length() ) ); + buffer->Des().Copy( iBuffer ); + buffer->Des().Append( aData ); + iBuffer.Copy( buffer->Right( Min( + KMaxBoundaryLength, buffer->Length() ) ) ); + if ( !FindHeaderEnd( *buffer, bStart, bEnd ) ) + { + const TInt lengthNoBoundary( buffer->Length() - KMaxBoundaryLength ); + if ( lengthNoBoundary > 0 ) + { + HandleBodyHeaderDataL( buffer->Left( lengthNoBoundary ) ); + } + } + else + { + HandleBodyHeaderDataL( buffer->Left( bStart ) ); + iBuffer.SetLength( 0 ); + iState = EBodyPart; + StartBodyPartL(); + HandleBodyPartL( buffer->Mid( bEnd ) ); + } + CleanupStack::PopAndDestroy( buffer ); + MULTIPART_DEBUGLIT( "--> TMultipartHandler::HandleBodyPartHeadersL" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::HandleBodyPartL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::HandleBodyPartL( + const TDesC8& aData ) + { + MULTIPART_DEBUGLIT( "TMultipartHandler::HandleBodyPartL -->" ) + TInt bStart( 0 ); + TInt bEnd( 0 ); + + HBufC8* buffer( HBufC8::NewLC( iBuffer.Length() + aData.Length() ) ); + buffer->Des().Copy( iBuffer ); + buffer->Des().Append( aData ); + + iBuffer.Copy( buffer->Right( Min( + KMaxBoundaryLength, buffer->Length() ) ) ); + + if ( !FindDelimiter( *buffer, bStart, bEnd ) ) + { + const TInt lengthNoBoundary( buffer->Length() - KMaxBoundaryLength ); + if ( lengthNoBoundary > 0 ) + { + HandleBodyDataL( buffer->Left( lengthNoBoundary ) ); + } + } + else + { + HandleBodyDataL( buffer->Left( bStart ) ); + iBuffer.SetLength( 0 ); + if ( ( *buffer )[ bEnd ] == '-' && ( *buffer )[ bEnd + 1 ] == '-' ) + { + EndBodyPartL(); + iState = EEpilog; + } + else + { + iState = EBodyPartHeaders; + StartBodyPartHeadersL(); + HandleBodyPartHeadersL( buffer->Mid( bEnd + KCrLf().Length() ) ); + } + } + CleanupStack::PopAndDestroy( buffer ); + MULTIPART_DEBUGLIT( "--> TMultipartHandler::HandleBodyPartL" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::StartBodyPartHeadersL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::StartBodyPartHeadersL() + { + MULTIPART_DEBUGLIT( "--> TMultipartHandler::StartBodyPartHeadersL -->" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::EndBodyPartHeadersL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::EndBodyPartHeadersL() + { + MULTIPART_DEBUGLIT( "--> TMultipartHandler::EndBodyPartHeadersL -->" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::HandleBodyHeaderDataL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::HandleBodyHeaderDataL( + const TDesC8& /*aData*/ ) + { + MULTIPART_DEBUGLIT( "--> TMultipartHandler::HandleBodyHeaderDataL -->" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::StartBodyPartL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::StartBodyPartL() + { + MULTIPART_DEBUGLIT( "--> TMultipartHandler::StartBodyPartL -->" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::EndBodyPartL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::EndBodyPartL() + { + MULTIPART_DEBUGLIT( "--> TMultipartHandler::EndBodyPartL -->" ) + } + +// --------------------------------------------------------------------------- +// TMultipartHandler::HandleBodyDataL +// --------------------------------------------------------------------------- +// +void TMultipartHandler::HandleBodyDataL( + const TDesC8& /*aData*/ ) + { + MULTIPART_DEBUGLIT( "--> TMultipartHandler::HandleBodyDataL -->" ) + }