--- /dev/null Thu Jan 01 00:00:00 1970 +0000
+++ b/email/pop3andsmtpmtm/clientmtms/src/cimencodedheader.cpp Thu Dec 17 08:44:11 2009 +0200
@@ -0,0 +1,712 @@
+// Copyright (c) 2003-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:
+// cimencodeheader.cpp
+//
+
+#include "cimencodedheader.h"
+#include "MIUT_ERR.H"
+#ifdef SYMBIAN_ENABLE_SPLIT_HEADERS
+#include "miut_errconsts.h"
+#include "timrfc822datefield.h"
+#endif
+
+#if (defined SYMBIAN_MESSAGESTORE_HEADER_BODY_USING_SQLDB)
+#include <msvstd.h>
+#endif
+
+#if (defined SYMBIAN_MESSAGESTORE_HEADER_BODY_USING_SQLDB)
+_LIT16(KComma, ",");
+_LIT16(KDelimiter, ";");
+#endif
+
+const TInt KArrayGranularity = 16;
+
+// Identifies which version of CImEncodedHeader has been stored in stream
+const TUint16 KImEncodedHeaderVersion = 1;
+
+extern TPtrC8 LimitStringSize(const TPtrC8& aString, TInt aMaxSize);
+extern TPtrC16 LimitStringSize(const TPtrC16& aString, TInt aMaxSize);
+extern void ExternalizeL(const CDesC8Array& anArray,RWriteStream& aStream);
+extern void InternalizeL(CDesC8Array& anArray,RReadStream& aStream);
+extern void ExternalizeL(const CDesC16Array& anArray,RWriteStream& aStream);
+extern void InternalizeL(CDesC16Array& anArray,RReadStream& aStream);
+
+//------------------------------------------------------------------------------
+// Class CImEncodedHeader Functions
+//------------------------------------------------------------------------------
+
+CImEncodedHeader::CImEncodedHeader() : iDecodeCharset(0)
+ {
+ }
+
+//------------------------------------------------------------------------------
+
+CImEncodedHeader* CImEncodedHeader::NewLC()
+/** Allocates and creates a new CImHeader object, leaving the object on the cleanup
+stack.
+
+@return New CImEncodedHeader object */
+ {
+ CImEncodedHeader* self = new(ELeave) CImEncodedHeader;
+ CleanupStack::PushL(self);
+ self->ConstructL();
+ return self;
+ }
+
+//------------------------------------------------------------------------------
+
+CImEncodedHeader* CImEncodedHeader::NewL()
+/** Allocates and creates a new CImHeader object, leaving the object on the cleanup
+stack.
+
+@return New CImEncodedHeader object */
+ {
+ CImEncodedHeader* self = CImEncodedHeader::NewLC();
+ CleanupStack::Pop(self);
+ return self;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::ConstructL()
+ {
+ iTo = new (ELeave)CDesCArrayFlat(KArrayGranularity);
+ iCc = new (ELeave)CDesCArrayFlat(KArrayGranularity);
+ iBcc = new (ELeave)CDesCArrayFlat(KArrayGranularity);
+ }
+
+//------------------------------------------------------------------------------
+
+CImEncodedHeader::~CImEncodedHeader()
+ {
+ Reset();
+ delete iTo;
+ delete iCc;
+ delete iBcc;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::Reset()
+ {
+ iVersion = KImEncodedHeaderVersion;
+ delete iFrom; iFrom = NULL;
+ delete iSubject; iSubject = NULL;
+ delete iReplyTo; iReplyTo = NULL;
+
+ if (iTo)
+ iTo->Reset();
+ if (iCc)
+ iCc->Reset();
+ if (iBcc)
+ iBcc->Reset();
+
+ iDecodeCharset = 0;
+ }
+
+//------------------------------------------------------------------------------
+
+const TPtrC8 CImEncodedHeader::Subject() const
+/** Gets the "Subject" header field.
+
+@return Field value */
+ {
+ return iSubject ? TPtrC8(*iSubject) : TPtrC8();
+ }
+
+//------------------------------------------------------------------------------
+
+const TPtrC8 CImEncodedHeader::From() const
+/** Gets the "From" header field.
+
+This consists of an address and (possibly) an alias.
+
+@return Field value */
+ {
+ return iFrom ? TPtrC8(*iFrom) : TPtrC8();
+ }
+
+//------------------------------------------------------------------------------
+
+const TPtrC8 CImEncodedHeader::ReplyTo() const
+/** Gets the "ReplyTo" header field.
+
+@return Field value */
+ {
+ return iReplyTo ? TPtrC8(*iReplyTo) : TPtrC8();
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::SetSubjectL( const TDesC8& aSubject )
+/** Sets the "Subject" header field.
+
+@param aSubject Field value */
+ {
+ HBufC8* newSubject = aSubject.AllocL();
+ delete iSubject;
+ iSubject = newSubject;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::SetFromL( const TDesC8& aFrom )
+/** Sets the "From" header field.
+
+@param aFrom Field value */
+ {
+ HBufC8* newFrom = aFrom.AllocL();
+ delete iFrom;
+ iFrom = newFrom;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::SetReplyToL( const TDesC8& aReplyTo )
+/** Sets the "ReplyTo" header field.
+
+@param aReplyTo Field value */
+ {
+ HBufC8* newReplyTo = aReplyTo.AllocL();
+ delete iReplyTo;
+ iReplyTo = newReplyTo;
+ }
+
+//------------------------------------------------------------------------------
+
+CDesCArray& CImEncodedHeader::ToRecipients ()
+ {
+ return *iTo;
+ }
+
+//------------------------------------------------------------------------------
+
+CDesCArray& CImEncodedHeader::CcRecipients ()
+/** Gets a list of "Cc" recipients.
+
+@return Recipient list */
+ {
+ return *iCc;
+ }
+
+//------------------------------------------------------------------------------
+
+CDesCArray& CImEncodedHeader::BccRecipients()
+/** Gets a list of "Bcc" recipients.
+
+@return Recipient list */
+ {
+ return *iBcc;
+ }
+
+//------------------------------------------------------------------------------
+
+const CDesCArray& CImEncodedHeader::ToRecipients () const
+/** Gets a const list of "To" recipients.
+
+@return Recipient list */
+ {
+ return *iTo;
+ }
+
+//------------------------------------------------------------------------------
+
+const CDesCArray& CImEncodedHeader::CcRecipients () const
+/** Gets a const list of "Cc" recipients.
+
+@return Recipient list */
+ {
+ return *iCc;
+ }
+
+//------------------------------------------------------------------------------
+
+const CDesCArray& CImEncodedHeader::BccRecipients() const
+/** Gets a const list of "Bcc" recipients.
+
+@return Recipient list */
+ {
+ return *iBcc;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::ExternalizeL( RMsvWriteStream& aWriteStream ) const
+/** Externalises the settings to a specified stream.
+
+@param aWriteStream Stream to write to */
+ {
+ aWriteStream.WriteUint16L(Version()); // This MUST be the 1st item written into the stream
+
+ aWriteStream << LimitStringSize(From(), KMaxImHeaderStringLength);
+ aWriteStream << LimitStringSize(ReplyTo(), KMaxImHeaderStringLength);
+ aWriteStream << LimitStringSize(Subject(), KMaxImHeaderStringLength);
+
+ aWriteStream << ToRecipients();
+ aWriteStream << CcRecipients();
+ aWriteStream << BccRecipients();
+
+ aWriteStream.WriteUint32L(iDecodeCharset);
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::InternalizeL( RMsvReadStream& aReadStream )
+/** Internalises the settings from a specified stream.
+
+@param aReadStream Stream to read from */
+ {
+ Reset();
+
+ iVersion = aReadStream.ReadUint16L();
+ iFrom = HBufC8::NewL(aReadStream, KMaxImHeaderStringLength);
+ iReplyTo = HBufC8::NewL(aReadStream, KMaxImHeaderStringLength);
+ iSubject = HBufC8::NewL(aReadStream, KMaxImHeaderStringLength);
+
+ aReadStream >> ToRecipients();
+ aReadStream >> CcRecipients();
+ aReadStream >> BccRecipients();
+
+ iDecodeCharset = aReadStream.ReadUint32L();
+ }
+
+void CImEncodedHeader::StoreL(CMsvStore& aMessageStore) const
+ /** Stores settings to a specified message store.
+
+ @param aMessageStore Message store to write to */
+ {
+ //------------------------------------------------------------------------------
+ RMsvWriteStream out;
+ out.AssignLC(aMessageStore, KUidMsgFileIMailEncodedHeader);
+ ExternalizeL(out);
+ out.CommitL();
+ CleanupStack::PopAndDestroy(&out);
+ }
+
+
+void CImEncodedHeader::RestoreL(CMsvStore& aMessageStore)
+ /** Restores settings from a specified message store.
+
+ @param aMessageStore Message store to read from */
+ {
+ RMsvReadStream in;
+ in.OpenLC( aMessageStore, KUidMsgFileIMailEncodedHeader );
+ InternalizeL(in);
+ in.Close();
+ CleanupStack::PopAndDestroy(&in);
+ }
+//------------------------------------------------------------------------------
+
+TUint16 CImEncodedHeader::Version() const
+ {
+ return iVersion;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::SetVersion( TUint16 aVersion )
+ {
+ iVersion = aVersion;
+ }
+
+//------------------------------------------------------------------------------
+
+TUint CImEncodedHeader::DecodeCharset() const
+ {
+ return iDecodeCharset;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::SetDecodeCharset(TUint aCharset)
+ {
+ iDecodeCharset = aCharset;
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::CopyFromHeaderL(
+ const CImHeader& aFromHeader, TBool aDeleteExistingData)
+ {
+ // From field
+ const TPtrC& fromDes = aFromHeader.From();
+ if (fromDes.Length() && (!iFrom || aDeleteExistingData))
+ {
+ HBufC8* buffer = HBufC8::NewL(fromDes.Length());
+ buffer->Des().Copy(fromDes);
+ delete iFrom;
+ iFrom = buffer;
+ }
+
+ // Subject field
+ const TPtrC& subjectDes = aFromHeader.Subject();
+ if (subjectDes.Length() && (!iSubject || aDeleteExistingData))
+ {
+ HBufC8* buffer = HBufC8::NewL(subjectDes.Length());
+ buffer->Des().Copy(subjectDes);
+ delete iSubject;
+ iSubject = buffer;
+ }
+
+ // ReplyTo field
+ const TPtrC& replyToDes = aFromHeader.ReplyTo();
+ if (replyToDes.Length() && (!iReplyTo || aDeleteExistingData))
+ {
+ HBufC8* buffer = HBufC8::NewL(replyToDes.Length());
+ buffer->Des().Copy(replyToDes);
+ delete iReplyTo;
+ iReplyTo = buffer;
+ }
+ // Copy iTo, iCc, iBcc
+ const CDesCArray& srcToArray = aFromHeader.ToRecipients();
+ if (srcToArray.Count() && ((iTo->Count() == 0) || aDeleteExistingData))
+ ::CopyArrayL(srcToArray, *iTo);
+
+ const CDesCArray& srcCcArray = aFromHeader.CcRecipients();
+ if (srcCcArray.Count() && ((iCc->Count() == 0) || aDeleteExistingData))
+ ::CopyArrayL(srcCcArray, *iCc);
+
+ const CDesCArray& srcBccArray = aFromHeader.BccRecipients();
+ if (srcBccArray.Count() && ((iBcc->Count() == 0) || aDeleteExistingData))
+ ::CopyArrayL(srcBccArray, *iBcc);
+ }
+
+//------------------------------------------------------------------------------
+
+void CImEncodedHeader::CopyToHeaderL(CImHeader& aToHeader) const
+ {
+ //
+ aToHeader.SetFromL(From());
+ aToHeader.SetSubjectL(Subject());
+ aToHeader.SetReplyToL(ReplyTo());
+
+ // Copy iTo, iCc, iBcc
+ ::CopyArrayL(*iTo, aToHeader.ToRecipients());
+ ::CopyArrayL(*iCc, aToHeader.CcRecipients());
+ ::CopyArrayL(*iBcc, aToHeader.BccRecipients());
+ }
+
+//------------------------------------------------------------------------------
+
+TInt CImEncodedHeader::DataSize() const
+/** Gets the combined length of all the field values stored.
+
+@return Combined length */
+ {
+ TInt headerSize = 2; // CRLF at end of header
+ const CImEncodedHeader* self = this;
+
+ headerSize += self->From().Length();
+ headerSize += self->ReplyTo().Length();
+ headerSize += self->Subject().Length();
+ headerSize += sizeof(TUint); // size of Charset
+
+ TInt count;
+ CDesCArray& toArray = *self->iTo;
+ for (count = 0; count < toArray.Count(); count++)
+ {
+ headerSize += toArray[count].Length();
+ }
+
+ CDesCArray& ccArray = *self->iCc;
+ for (count = 0; count < ccArray.Count(); count++)
+ {
+ headerSize += ccArray[count].Length();
+ }
+
+ CDesCArray& bccArray = *self->iBcc;
+ for (count = 0; count < bccArray.Count(); count++)
+ {
+ headerSize += bccArray[count].Length();
+ }
+
+ return headerSize;
+ }
+
+
+#if (defined SYMBIAN_MESSAGESTORE_HEADER_BODY_USING_SQLDB)
+/**Stores encoded header to a specified message store.
+ * @param aMessageStore Message store to write to
+ * @return None.
+ */
+void CImEncodedHeader::StoreEncodedDBL(CMsvStore& aMessageStore) const
+ {
+ CHeaderFields* emailHeaderFields = new (ELeave)CHeaderFields();
+ CleanupStack::PushL(emailHeaderFields);
+ emailHeaderFields->iUid = KUidMsgFileIMailEncodedHeader;
+
+ //----------------------Encoded Info 19th Field ------------------------------ // 19
+ CFieldPair* emaildetailField = new (ELeave)CFieldPair();
+ CleanupStack::PushL(emaildetailField);
+
+ //Make a string from encoded header info.
+ RBuf8 encodedheader;
+ CleanupClosePushL(encodedheader);
+ encodedheader.CreateL(EncodedBufSize()); //
+
+ encodedheader.AppendNum(Version());
+ encodedheader.Append(KDelimiter);
+
+ encodedheader.Append(LimitStringSize(From(), KMaxImHeaderStringLength));
+ encodedheader.Append(KDelimiter);
+ encodedheader.Append(LimitStringSize(ReplyTo(), KMaxImHeaderStringLength));
+ encodedheader.Append(KDelimiter);
+ encodedheader.Append(LimitStringSize(Subject(), KMaxImHeaderStringLength));
+ encodedheader.Append(KDelimiter);
+
+ //ToRecipients
+ for(TInt i=0 ; i<iTo->MdcaCount() ; i++)
+ {
+ encodedheader.Append(iTo->MdcaPoint(i));
+ if(i< iTo->MdcaCount()-1)
+ encodedheader.Append(KComma);
+ }
+ encodedheader.Append(KDelimiter);
+
+ //CcRecipients
+ for(TInt i=0 ; i<iCc->MdcaCount() ; i++)
+ {
+ encodedheader.Append(iCc->MdcaPoint(i));
+ if(i< iCc->MdcaCount()-1)
+ encodedheader.Append(KComma);
+ }
+ encodedheader.Append(KDelimiter);
+
+ //BCcRecipients
+ for(TInt i=0 ; i<iBcc->MdcaCount() ; i++)
+ {
+ encodedheader.Append(iBcc->MdcaPoint(i));
+ if(i< iBcc->MdcaCount()-1)
+ encodedheader.Append(KComma);
+ }
+ encodedheader.Append(KDelimiter);
+
+ encodedheader.AppendNum(iDecodeCharset);
+ encodedheader.Append(KDelimiter);
+
+ //8 bit to 16 bit
+ HBufC* newFrom = HBufC::NewL(encodedheader.Length());
+ newFrom->Des().Copy(encodedheader);
+ emaildetailField->iFieldTextValue = newFrom;
+ emailHeaderFields->iFieldPairList.AppendL(emaildetailField);
+ CleanupStack::Pop(); //RBuf8
+ CleanupStack::Pop(emaildetailField);
+
+ //---------------------------Encoded info end-------------------------------
+
+ TMsvWriteStore storeWriter(aMessageStore);
+ storeWriter.AssignL(emailHeaderFields);
+ encodedheader.Close();
+ CleanupStack::Pop(emailHeaderFields);
+ }
+
+/**
+ * Restores encoded header to a specified message store.
+ * @param aMessageStore Message store to read from.
+ * @return NOne.
+ */
+
+void CImEncodedHeader::ReStoreEncodedDBL(CMsvStore& aMessageStore)
+ {
+ Reset();
+
+ CHeaderFields* aEncodedHeader = NULL;
+ TMsvReadStore storeReader(aMessageStore, KUidMsgFileIMailEncodedHeader);
+ storeReader.ReadL(aEncodedHeader);
+
+ TInt i = 0; // EncodedHeader field is on 19th coloum of header table.
+ HBufC* encodedheaderinfo = aEncodedHeader->iFieldPairList[i++]->iFieldTextValue ;
+
+ TPtr16 encodedheaderPtr = (encodedheaderinfo->Des());
+
+ //Parsing the encodedheader string
+ TInt firstSemiColonPos = encodedheaderPtr.Locate(';');
+ TInt lastSemiColonPos = encodedheaderPtr.LocateReverse(';');
+
+ RPointerArray<HBufC16> encodedheaderinfoData;
+ CleanupClosePushL(encodedheaderinfoData);
+ TInt ii = 0 ;
+
+ do
+ {
+ TPtrC16 str1 = encodedheaderPtr.Left(firstSemiColonPos); // First data
+ HBufC16* tt = str1.AllocL();
+ firstSemiColonPos++;
+ encodedheaderinfoData.AppendL(tt);
+
+ if(firstSemiColonPos != lastSemiColonPos)
+ {
+ encodedheaderPtr = (encodedheaderPtr.Mid(firstSemiColonPos,encodedheaderPtr.Length()-(firstSemiColonPos) ));
+ firstSemiColonPos = encodedheaderPtr.Locate(';');
+ lastSemiColonPos = encodedheaderPtr.LocateReverse(';');
+ if(firstSemiColonPos == lastSemiColonPos)
+ {
+ TPtrC16 str1 = encodedheaderPtr.Left(firstSemiColonPos); // Last data
+ HBufC16* tt = str1.AllocL();
+ encodedheaderinfoData.AppendL(tt);
+ }
+ }
+
+ ii++;
+ }while(firstSemiColonPos != lastSemiColonPos);
+
+ iVersion= ConvertToTInt(*encodedheaderinfoData[0]);
+
+ HBufC8* form = HBufC8::NewL((encodedheaderinfoData[1])->Length());
+ form->Des().Copy(encodedheaderinfoData[1]->Des());
+ iFrom = form;
+
+ HBufC8* replyTo = HBufC8::NewL((encodedheaderinfoData[2])->Length());
+ replyTo->Des().Copy(encodedheaderinfoData[2]->Des());
+ iReplyTo = replyTo ;
+
+ HBufC8* subject = HBufC8::NewL((encodedheaderinfoData[3])->Length());
+ subject->Des().Copy(encodedheaderinfoData[3]->Des());
+ iSubject = subject ;
+
+ //iTo
+ HBufC16* tmpBuf = encodedheaderinfoData[4]->Des().AllocL();
+ if ((encodedheaderinfoData[4]->Des().Locate(',')) > -1 )
+ {
+ CreateEncodedArrayListL(tmpBuf->Des(),0); //To
+ }
+ else
+ {
+ if(encodedheaderinfoData[4]->Length()>0)
+ iTo->AppendL(tmpBuf->Des());
+ }
+ delete tmpBuf;
+ //iCc
+ tmpBuf = encodedheaderinfoData[5]->Des().AllocL();
+ if ((encodedheaderinfoData[5]->Des().Locate(',')) > -1 )
+ {
+ CreateEncodedArrayListL(tmpBuf->Des(),1); //CC
+ }
+ else
+ {
+ if(encodedheaderinfoData[5]->Length()>0)
+ iCc->AppendL(tmpBuf->Des());
+ }
+ delete tmpBuf;
+ //iBcc
+ tmpBuf = encodedheaderinfoData[6]->Des().AllocL();
+ if ((encodedheaderinfoData[6]->Des().Locate(',')) > -1 )
+ {
+ CreateEncodedArrayListL(tmpBuf->Des(),2); //Bcc
+ }
+ else
+ {
+ if(encodedheaderinfoData[6]->Length()>0)
+ iBcc->AppendL(tmpBuf->Des());
+ }
+
+ delete tmpBuf;
+ iDecodeCharset= ConvertToTInt(*encodedheaderinfoData[7]);
+ encodedheaderinfoData.ResetAndDestroy();
+ encodedheaderinfoData.Close();
+ CleanupStack::Pop(); //RpointerArray
+
+
+ }
+
+
+/**
+ * Create Encoded Array List.
+ * @param aEncodedStr : A string.
+ * @param aI :A Integer value.
+ * @return None.
+ */
+void CImEncodedHeader::CreateEncodedArrayListL(TPtrC16 aEncodedStr ,TInt aI)
+ {
+ TInt startPos = aEncodedStr.Locate(',') ;
+ while(startPos >= -1 )
+ {
+ TPtrC16 str2 = aEncodedStr.Left(startPos);
+ //ainto.AppendL(str2);
+ if(aI == 0)
+ {
+ //iTo
+ iTo->AppendL(str2);
+ }
+ if(aI == 1)
+ {
+ //iCc
+ iCc->AppendL(str2);
+ }
+ if( aI == 2)
+ {
+ //iBcc
+ iBcc->AppendL(str2);
+ }
+ startPos++;
+ aEncodedStr.Set(aEncodedStr.Mid(startPos, aEncodedStr.Length()- startPos));
+
+ startPos = aEncodedStr.Locate(',');
+ if(startPos == -1)
+ {
+ TInt ll = aEncodedStr.Length();
+ TPtrC16 str3;
+ str3.Set(aEncodedStr.Mid(0,aEncodedStr.Length()));
+ if(aI == 0)
+ {
+ //iTo
+ iTo->AppendL(str3);
+ }
+ if(aI == 1)
+ {
+ //iCc
+ iCc->AppendL(str3);
+ }
+ if( aI == 2)
+ {
+ //iBcc
+ iBcc->AppendL(str3);
+ }
+ break;
+ }
+ }
+ }
+
+
+TInt CImEncodedHeader::EncodedBufSize() const
+/** Gets the combined length of all the field values stored.
+
+@return Combined length */
+ {
+ TInt headerSize = 4; // Version
+ const CImEncodedHeader* self = this;
+
+ headerSize += Align4(self->From().Size());
+ headerSize += Align4(self->ReplyTo().Size());
+ headerSize += Align4(self->Subject().Size());
+ headerSize += sizeof(TUint); // size of Charset
+
+ TInt count;
+ for (count=0; count<iTo->MdcaCount(); count++)
+ {
+ headerSize += Align4(iTo->MdcaPoint(count).Size()) + 1; //1 for Comma
+ }
+ for (count=0; count<iCc->MdcaCount(); count++)
+ {
+ headerSize += Align4(iCc->MdcaPoint(count).Size()) + 1; //1 for Comma
+ }
+ for (count=0; count<iBcc->MdcaCount(); count++)
+ {
+ headerSize += Align4(iBcc->MdcaPoint(count).Size()) + 1;//1 for Comma
+ }
+
+ return headerSize + 8; //8 delimiters ";".
+ }
+
+#endif