mmsengine/mmscodec/inc/mmsencode.h
changeset 0 72b543305e3a
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/mmsengine/mmscodec/inc/mmsencode.h	Thu Dec 17 08:44:11 2009 +0200
@@ -0,0 +1,784 @@
+/*
+* 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:  
+*     Binary encoding of a multimedia message
+*
+*/
+
+
+
+#ifndef CMMSENCODE_H
+#define CMMSENCODE_H
+
+//  INCLUDES
+#include <mentact.h>
+#include <badesca.h>
+#include <cmsvattachment.h>
+
+#include "mmsconst.h" // needed for TMmsRecipients
+#include "mmsservercommon.h" // needed for logging flag definition
+#include "mmscodecdatasupplier.h"
+
+// CONSTANTS
+
+// MACROS
+
+// DATA TYPES
+
+// FUNCTION PROTOTYPES
+
+// FORWARD DECLARATIONS
+class RBufWriteStream;
+class CMmsHeaders;
+class CMsvMimeHeaders;
+class MMmsEntryWrapper;
+class MMmsEntry;
+class CMsgTextUtils;
+
+// CLASS DECLARATION
+
+/**
+* Binary encoding of a multimedia message.
+*
+* @lib mmscodec.lib
+* @since v2.1
+*/
+class CMmsEncode :public CMsgActive, public MMmsCodecDataSupplier
+    {
+public:
+    
+    /**
+     * @param aFs file system handle.
+     */
+    IMPORT_C static CMmsEncode* NewL( RFs& aFs );
+    
+    virtual ~CMmsEncode();
+
+public: // New functions
+    
+    /**
+     * Start the state machine for encoding a message with headers and data.
+     *
+     * @param aEntryWrapper mixin for handling all message entry access
+     * @param aMmsHeaders reference to CMmsHeaders class.
+     * @param aEncodeBuffer buffer to hold the encoded data,
+     * @param aStatus status of calling active object
+     */
+    IMPORT_C void StartL(
+        MMmsEntryWrapper& aEntryWrapper,
+        CMmsHeaders& aMmsHeaders,
+        CBufFlat& aEncodeBuffer,
+        TRequestStatus& aStatus );
+
+    /**
+     * Encode headers only.
+     *
+     * This function is for the miscellaneous control messages.
+     * This is not an active function, one-shot only.
+     * @param aMmsHeaders reference to CMmsHeaders class.
+     * @param aEncodeBuffer buffer to hold the encoded data,
+     */
+    IMPORT_C void EncodeHeadersL(
+        CMmsHeaders& aMmsHeaders,
+        CBufFlat& aEncodeBuffer );
+
+    /**
+     * Start chunked encoding.
+     * This method can be called only when it is known that the component
+     * that handles the encoded data can use the callback to get more 
+     * data chunks.
+     *
+     * @since v3.1
+     * @param aEntryWrapper mixin for handling all message entry access
+     * @param aMmsHeaders reference to CMmsHeaders class.
+     * @param aEncodeBuffer buffer to hold the encoded data,
+     * @param aStatus status of calling active object
+     */
+    IMPORT_C void StartChunkedL(
+        MMmsEntryWrapper& aEntryWrapper,
+        CMmsHeaders& aMmsHeaders,
+        CBufFlat& aEncodeBuffer,
+        TRequestStatus& aStatus );
+
+// from base class MMmsCodecDataSupplier
+
+    /**
+     * from MMmsCodecDataSupplier.
+     * Give poiner to next encoded data chunk.
+     *
+     * @since v3.1
+     * @param aDataPart pointer to the next encoded data part
+     * @param aLastDataChunk 
+     *     ETrue if this is the last data chunk
+     *     EFalse if this is not the last data chunk
+     * @return error code, KErrNone if all is well.
+     *     If returns some other error, transaction must be cancelled.
+     */
+    virtual TInt GetNextDataPart(
+        TPtrC8& aDataPart, TBool& aLastDataChunk );
+    
+    /**
+     * from MMmsCodecDataSupplier.
+     * Empty buffer and prepare next data part (synchronous encoding).
+     * When needed, caller will tell HTTP stack that the next data part is
+     * ready by calling RHTTPTransaction::NotifyNewRequestBodyPartL()
+     *
+     * @since v3.1
+     * @return error code, KErrNone if all is well.
+     *     If returns some other error, transaction must be cancelled.
+     */
+    virtual TInt ReleaseData();
+    
+    /**
+     * from MMmsCodecDataSupplier.
+     * Return the overall data size.
+     *
+     * @since v3.1
+     * @return The overall data size if it is known, otherwise KErrNotFound
+     */
+    virtual TInt OverallDataSize();
+    
+    /**
+     * from MMmsCodecDataSupplier.
+     * Reset the data supplier.
+     * Data supplier must start the data generation from the beginning again.
+     *
+     * @since v3.1
+     * @return KErrNone if reset is successful, other error code if data
+     *     supplier cannot be reset
+     */
+    TInt ResetSupplier();
+
+protected:
+    
+private:
+
+    CMmsEncode();
+
+    /**
+     * @param aFs file system handle.
+     */
+    void ConstructL( RFs& aFs );
+
+    /**
+     * from CMsgActive.
+     *
+     * Active object completion.
+     */
+    void DoRunL();
+
+    /**
+     * from CMsgActive.
+     *    
+     * Sweep the floor after everything has crashed.
+     * @param aStatus completion code
+     */
+    void DoComplete( TInt& aStatus );
+
+    /**
+     * Select next state for state machine.
+     */
+    void SelectNextState();
+
+    /**
+     * Switch states.
+     */
+    void ChangeStateL();
+
+    /**
+     * Initialize members to allow one-shot functions.
+     * (for short tasks no active object invocation is needed)
+     */
+    void Reset();
+
+    /**
+     * Encode headers.
+     */
+    void EncodeHeadersL();
+    
+    /**
+     * Encode headers in chunked mode.
+     */
+    void EncodeHeadersChunkedL();
+
+    /** 
+     * Do one attachment at a time.
+     */
+    void EncodeAttachmentL();
+    
+    /**
+     * Do the actual work, can be called from active loop or passive loop
+     */
+    void DoEncodeAttachmentL(); 
+    
+    /**
+     * Get encoding length for one attachment
+     * @return size of the encoded attachment headers and attachment data
+     */
+    TInt DoGetAttachmentEncodingLengthL();
+    
+    /**
+     * Encode attachment headers into the buffer and open the attachment file
+     * @param aAttachMan reference to attachment manager for accessing
+     *        attachment information and opening the file
+     * @return size of the attachment
+     */
+    TInt EncodeHeadersAndGetFileL( MMsvAttachmentManager& aAttachMan );
+    
+    /**
+     * Get the encoded size of the mime headers and the attachment data
+     * @param aAttachMan reference to attachment manager for accessing
+     *        attachment information and opening the file
+     * @return size of the encoded attachment headers and attachment data
+     */
+    TInt GetHeadersAndFileSizeL( MMsvAttachmentManager& aAttachMan );
+    
+    /**
+     * Calculate the length of headers for the attachment
+     * @param aAttachmentInfo attachmentInformation structure for current attacment
+     * @param aHeaderLength total length of encoded headers
+     * @param aFoundName ETrue the name is among content-type parameters
+     *                   EFalse the name is in the recommended filename parameter
+     * @param aContentTypeSize length of the content type header
+     * @param aContentType assigned number for content type, -1 if not found
+     * @param aContentTypeString content type in string format if aContentType == -1
+     * @return pointer to attachment name in 8bit format if aFoundName == EFalse
+     *     If aFoundName == ETrue, returns NULL, because name in included in content
+     *     type parameters and is not added separately.
+     *     Caller must delete buffer when no longer needed.
+     */
+    HBufC8* CalculateAttachmentHeaderLengthL(
+        CMsvAttachment& aAttachmentInfo,
+        TUint& aHeaderLength,
+        TBool& aFoundName,
+        TUint& aContentTypeSize,
+        TInt8& aContentType,
+        TPtrC8& aContentTypeString );
+    
+    /**
+     * Encode headers for one attachment
+     * @param aSize size of the attachment binary data
+     * @param aHeaderSize size of the headers in encoded format
+     * @param aFoundName ETrue if the name parameter is among the 
+     *        Content type parameters in MIME headers
+     * @param aContentTypeSize size of the content type header
+     * @param aContentType assigned number for the content type
+     * @param aContentTypeString content type in string format if
+     *        no assigned number is available
+     * @param aNameString name of the attachment if aFoundName == EFalse
+     */
+    void EncodeAttachmentHeadersL(
+        TUint aSize,
+        TUint aHeaderSize,
+        TBool aFoundName,
+        TUint aContentTypeSize,
+        TInt8 aContentType,
+        TPtrC8& aContentTypeString,
+        TPtrC8& aNameString );
+
+    /**
+     * Write all attachment data to the buffer
+     * @param aAttachFile open handle for attachment file
+     *     After reading the file pointer will point past data read
+     * @param aSize amount of data to be read
+     */
+    void EncodeAttachmentData( RFile& aAttachFile, TInt aSize );
+
+    /**
+     * Cleanup (close streams etc.).
+     */
+    void FinishL();
+    
+    /**
+     * Encode MMS request headers depending on the PDU type
+     */
+    void EncodeRequestHeadersL();
+
+    // As different transactions have widely different headers,
+    // a separate routine is used for each to avoid lots of extra
+    // work when certain headers are not needed anyway.
+
+    // If new transactions (message types) are added, they need
+    // special handling anyway.
+
+    /**
+     * Send Request.
+     */
+    void EncodeSendRequestHeadersL();
+
+    /**
+     * Notify response.
+     */
+    void EncodeNotifyResponse();
+
+    /**
+     * Delivery acknowledgement.
+     */
+    void EncodeAcknowledgeIndication();
+
+    /**
+     * Mms notification.
+     */
+    void EncodeMmsNotificationL();
+
+    // PDUs reserved for testing purposes
+    
+    /**
+     * Send confirmation
+     */
+    void EncodeSendConfirmationL();
+
+    /**
+     * Retrieve confirmation.
+     */
+    void EncodeRetrieveConfirmationL();
+
+    /**
+     * Delivery report.
+     */
+    void EncodeDeliveryReportL();
+
+    // MMS encapsulation version 1.1 PDUs
+
+    /**
+     * Forward Request.
+     */
+    void EncodeForwardRequestL();
+
+    /**
+     * Forward confirmation.
+     * for testing purposes
+     */
+    void EncodeForwardConfirmationL();
+
+    /**
+     * ReadReply.
+     * @param aPDUType KMmsMessageTypeReadRecInd or
+     *    KMmsMessageTypeReadOrigInd (supported for testing purposes)
+     */
+    void EncodeReadReplyL();
+
+    // MMS encapsulation 1.2 PDUs
+
+    /**
+     * MMBox store request.
+     * @since 2.6
+     */
+    void EncodeMMBoxStoreRequestL();
+
+    /**
+     * MMBox store confirmation.
+     * for testing purposes.
+     * @since 2.6
+     */
+    void EncodeMMBoxStoreConfirmationL();
+
+    /**
+     * MMBox view request.
+     * @since 2.6
+     */
+    void EncodeMMBoxViewRequestL();
+
+    /**
+     * MMBox view confirmation.
+     * for testing purposes.
+     * @since 2.6
+     */
+    void EncodeMMBoxViewConfirmationL();
+
+    /**
+     * MMBox upload request
+     * @since 2.6
+     */
+    void EncodeMMBoxUploadRequestL();
+
+    /**
+     * MMBox upload confirmation
+     * for testing purposes.
+     * @since 2.6
+     */
+    void EncodeMMBoxUploadConfirmationL();
+
+    /**
+     * MMBox delete request or MMSC delete request
+     * @since 2.6
+     */
+    void EncodeDeleteRequestL();
+
+    /**
+     * MMBox delete confirmation or MMSC delete confirmation.
+     * for testing purposes.
+     * @since 2.6
+     */
+    void EncodeDeleteConfirmationL();
+
+    /**
+     * MMBox description
+     * for testing purposes.
+     * @since 2.6
+     */
+    void EncodeMMBoxDescriptionL();
+
+    // end of MMS encapsulation PDUs
+
+    /**
+     * Encode Text String (No Character set).
+     * @param aString byte string
+     */
+    void EncodeTextString( const TDesC8& aString );
+
+    /**
+     * Encode Quoted Text String (No Character set).
+     * This function adds a quote to the beginning of the text string.
+     * needed for content-id
+     * @param aString byte string
+     */
+    void EncodeQuotedTextString( const TDesC8& aString );
+
+    /**
+     * Encode Text String.
+     * Checks if string can be sent as plain ASCII,
+     *     if not, encodes it into utf-8
+     * @param aString unicode string
+     */
+    void EncodeTextStringL( const TDesC& aString );
+
+    /**
+     * Encode date.
+     * @param aDate local datetime in seconds from 1.1.1970
+     */
+    void EncodeDate( const TInt64& aDate );
+    
+    /**
+     * Encode long integer.
+     * @param 8 byte integer to be encoded
+     */
+    void EncodeLongInteger( const TInt64& aLongInteger );
+
+    /**
+     * Encode integer.
+     * Will be encoded as short integer or long integer depending on value.
+     * @param 4 byte integer to be encoded
+     */
+    void EncodeInteger( TUint aInteger );
+
+    /**
+     * Encode Sender.
+     * The result is either a legal sender address or an "insert-address"
+     *     token.
+     * @param aSender pointer to sender name
+     */
+    void EncodeSenderL( const TPtrC& aSender );
+
+    /**
+     * Encode Address.
+     * @param aAddress pointer to address
+     */
+    void EncodeAddressL( const TPtrC& aAddress );
+
+    /**
+     * Encode value length (long or short).
+     * @param aLength value length that may be short or long
+     */
+    void EncodeValueLength( TUint aLength );
+
+    /**
+     * Encode Uintvar.
+     * @param aInteger the integer to be coded - usually a length
+     */
+    void EncodeUintvar( TUint aInteger );
+
+    /**
+     * Check how many bytes are needed to encode a Uintvar.
+     * @param aInteger the integer to be coded - usually a length
+     * @return number of bytes needed in the encoding.
+     */
+    TInt GetUintvarLength( TUint aInteger );
+
+    /**
+     * Encode recipient.
+     * @param aRecipientList array of recipient descriptors
+     * @param aType recipient type (To, Cc, Bcc)
+     */
+    void EncodeRecipientL( const CDesCArray& aRecipientList,
+        TMmsRecipients aType );
+
+    /**
+     * Encode optional encoded string text.
+     * @param aHeader assigned header byte
+     * @param aString text
+     */
+    void EncodeOptionalStringL( TUint8 aHeader, const TPtrC16& aString );
+
+    /**
+     * Encode optional encoded string text.
+     * @param aHeader assigned header byte
+     * @param aString text
+     */
+    void EncodeOptionalString( TUint8 aHeader, const TPtrC8& aString );
+
+    /**
+     * Encode absolute time or a time interval.
+     * @param aInterval interval.
+     * @param aDate absolute date. If date is 0, interval is encoded.
+     */
+    void EncodeIntervalOrDate( TInt aInterval, const TInt64& aDate );
+
+    /**
+     * Encode ReplyCharging size if defined.
+     * @param aReplyChargingSize maximum number in octets for the reply-MM
+     */
+    void EncodeReplyChargingSize( TInt aReplyChargingSize );
+
+    /**
+     * Encode specified header if value is different from zero.
+     * Encoding must be assigned byte value.
+     * @param aHeader assigned header byte
+     * @param aValue assigned value for the header
+     */
+    void EncodeOptionalByte( TUint8 aHeader, TInt aValue );
+
+    /**
+     * Encode specified header (mandatory).
+     * Encoding must be assigned byte value
+     * @param aHeader assigned header byte
+     * @param aValue assigned value for the header
+     */
+    void EncodeMandatoryByte( TUint8 aHeader, TInt aValue );
+
+    /**
+     * Encode optional header that may be date or interval
+     * @param aHeader assigned header byte
+     * @param aInterval interval.
+     * @param aDate absolute date. If date is 0, interval is encoded.
+     * if both date and interval are 0, header is not added
+     */
+    void EncodeOptionalIntervalOrDate( TUint8 aHeader,
+        TInt aInterval,
+        const TInt64& aDate );
+
+    /**
+     * Encode header byte and 8-bit Text String (No Character set).
+     * @param aHeader assigned header byte
+     * @param aString byte string
+     */
+    void EncodeHeaderAndTextString( TUint8 aHeader,
+        const TDesC8& aString );
+
+    /**
+     * Check if string contains only US-ASCII characters.
+     * @param aString the string to be checked
+     * @return ETrue = ASCII, EFalse = needs encoding
+     */
+    TBool IsStringSafe( const TDesC& aString );
+    
+    /**
+     * Check if string contains only US-ASCII characters.
+     * @param aString the string to be checked
+     * @param aNumNonSafe number of characters >= 0x7F
+     * @return ETrue = ASCII, EFalse = needs encoding
+     */
+    TBool IsStringSafe( const TDesC8& aString, TInt& aNumNonSafe );
+
+    /**
+     * Encode Content type header with start parameter.
+     * The content-id of the attachment is searched. If the
+     * attachment has no content-id, an id is generated by a random
+     * number generator (not globally unique).
+     * @param aRootId Internal Id of the attachment that is the root
+     *     part of the message.
+     */
+    void EncodeMultipartRelatedHeaderL( const TMsvAttachmentId aRootId );
+
+    /**
+     * Encode Content type as multipart/mixed (no start specified).
+     */
+    void EncodeMultipartMixedHeaderL();
+
+    /**
+     * Encode keyword array.
+     */
+    void EncodeKeywordArrayL();
+
+    /**
+     * Encode optional integer. If value is 0, it is not added
+     * @param aHeader assigned header byte
+     * @aValue value to be encoded as an integer
+     */
+    void EncodeOptionalInteger( TUint8 aHeader, TUint aValue );
+
+    /**
+     * Encode attribute headers from array.
+     * This is the list of information elements required for each message
+     * @param aAttributeArray list of attributes as assigned numbers
+     */
+    void EncodeAttributes( RArray<TUint>& aAttributeArray );
+
+    /**
+     * Encode X-Mms-MM-State headers from an array.
+     * In MMBox view PDUs this header may appear multiple times
+     * @param aStateArray list of states used for filtering messages
+     * (items have values draft/sent/new/retrieved/forwarded)
+     */
+    void EncodeMMBoxStates( RArray<TInt>& aStateArray );
+
+    /**
+     * Encode content location array.
+     * Encodes content location headers in cases where more than one are
+     *     allowed
+     */
+    void EncodeContentLocationArray();
+
+    /**
+     * Encode the three headers appearing at the beginning of most PDUs.
+     * TID is not always required. If length of TID is 0, the header is
+     *     not added.
+     * @param aMessageType value for X-Mms-Message-Type header
+     * @param aTID transaction ID
+     * @param aVersion MMS encapsulation version number
+     */
+    void EncodeStartingHeaders( TInt aMessageType,
+        const TPtrC8& aTID, TInt aVersion );
+        
+    /**
+     * Encode Application Id and Reply to Application id as content type parameters
+     */    
+    void EncodeApplicationIdParametersL();    
+
+    /**
+     * Dump binary data into file.
+     */
+    void Dump();
+    
+    /**
+     * Append a chunk of binary data into file - for chunked encoding support
+     */
+    void DumpAppend();
+    
+    /**
+     * Encode that application id, reply application id and application info
+     */
+    void EncodeApplicationHeadersL();
+    
+    /**
+     *  Encode cancel request PDU - for testing only
+     */    
+    void EncodeCancelRequest();
+    
+    /**
+     * Encode cancel response PDU
+     */
+    void EncodeCancelResponse();
+    
+    /**
+     * Encode utf8 string into MIME quoted printable format.
+     * @param aSource string in utf8 character set.
+     * @return data in encoded format. Caller must delete buffer
+     */
+    HBufC8* EncodeQuotedPrintableWordL( const TPtrC8& aSource );
+    
+    /**
+     * Encode utf8 string into MIME base64 format.
+     * @param aSource string in utf8 character set
+     * @return data in encoded format. Caller must delete buffer
+     */
+    HBufC8* EncodeBase64WordL( const TPtrC8& aSource );
+
+    /**
+     * Open the message store(Edit mode) and process attachments 
+     * for further encoding
+     * @param None
+     * @return void
+     */
+    void PreProcessAttachmentDataL();
+
+    /**
+     * Check and proceed if given attachment can be encoded using 
+     * target encoding type based on its content type.
+     * @param aAttachmentInfo attachment of the msv entry
+     *        aMimeHeaders corresponding attachment mime headers
+     * @return true/false based on attachment content type
+     */
+    TBool CheckAndUpdateAttachmentL( CMsvAttachment& aAttachmentInfo,
+                                     CMsvMimeHeaders& aMimeHeaders );
+    
+
+    /**
+     * checks if input content type is supported for target encoding 
+     * @param aSrcCharSetMIBEnum MIB enum reprsenting current data format 
+     *        aTargetCharSetMIBEnum target encoding MIB enum
+     *        aAttachmentInfo attachment data to be converted 
+     * @return true/false based on encoding success/failure
+     */
+    TBool ProcessAndConvertAttachmentDataL( TUint aSrcCharSetMIBEnum,
+                                            TUint aTargetCharSetMIBEnum, 
+                                            CMsvAttachment& aAttachmentInfo);
+
+    /**
+     * checks if input content type is supported for target encoding 
+     * @param aContentType to check if the attachment data encoding is supported
+     * @return true/false based on attachment content type
+     */
+    TBool IsConversionSupportedContentType( TInt aContentType );
+
+
+    
+private:    // Data
+    RFs                 iFs; // file system
+    TInt                iError;
+    TInt                iState;
+    MMmsEntryWrapper*   iEntryWrapper;
+    CBufFlat*           iEncodeBuffer;
+    CMmsHeaders*        iMmsHeaders;
+    CMsvMimeHeaders*    iMimeHeaders;
+    TInt                iPosition; // pointer to encode buffer (if needed)
+    TInt                iNumberOfAttachments;
+    TInt                iCurrentAttachment; // AttachmentManager index
+    TFileName           iFileName;
+#ifndef _NO_MMSS_LOGGING_
+// only needed if output logging is enabled
+// parse buffer as member to save stack space
+    TParse              iParse;     
+#endif
+    TMsvId              iCurrentMessageId;
+    
+    TInt                iOverallDataSize;
+    TBool               iLastChunk;
+    TBool               iOnlyOneChunk;
+    TInt                iEncodingStage; // stage for chunked encoding
+    // Handle for the current attachment.
+    // If the file is large it may be read to the buffer in chunks.
+    // The file is kept open between reads. We want sole access.
+    RFile               iAttachFile;
+    // The attachment file is kept open if it is read in several parts.
+    // In destructor the file must be closed in case the transaction
+    // terminates with error
+    TBool               iFileOpen;
+    // Size of the current attachment.
+    // This will allow us to keep track of the amount of data read from the file
+    TInt                iCurrentFileSize;
+    // The stage variable that will keep track of the part of message that
+    // is going to be encoded next in case of chunked encoding
+    TInt                iDataSupplierStage;
+    // The max size of the ecode buffer for chunked encoding.
+    TInt                iBufferSize; 
+    // object to provide chaconv functionalities
+    CMsgTextUtils*      iTextUtils;
+    // target encoding type
+    TUint               iTargetEncodingType;
+    };
+
+#endif      // CMMSENCODE_H
+            
+// End of File