email/pop3andsmtpmtm/servermtmutils/inc/IMCVRECV.H
changeset 0 72b543305e3a
equal deleted inserted replaced
-1:000000000000 0:72b543305e3a
       
     1 // Copyright (c) 1998-2009 Nokia Corporation and/or its subsidiary(-ies).
       
     2 // All rights reserved.
       
     3 // This component and the accompanying materials are made available
       
     4 // under the terms of "Eclipse Public License v1.0"
       
     5 // which accompanies this distribution, and is available
       
     6 // at the URL "http://www.eclipse.org/legal/epl-v10.html".
       
     7 //
       
     8 // Initial Contributors:
       
     9 // Nokia Corporation - initial contribution.
       
    10 //
       
    11 // Contributors:
       
    12 //
       
    13 // Description:
       
    14 // IMCVRECV.H
       
    15 //
       
    16 
       
    17 #if !defined (__IMCVRECV_H__)
       
    18 #define __IMCVRECV_H__
       
    19 
       
    20 #include <s32mem.h>
       
    21 #include <badesca.h> // required for CBufSeg
       
    22 #include <msvstd.h>
       
    23 #include <msventry.h>
       
    24 #include <msvstore.h>
       
    25 #include <msvuids.h>
       
    26 #include <msvids.h>
       
    27 #include <miutatch.h>
       
    28 #include <miutlog.h>
       
    29 #include <imcvcodc.h>
       
    30 #include <imcvtext.h>
       
    31 #include <imutdll.h>
       
    32 #include <cimcaf.h>
       
    33 #ifdef SYMBIAN_ENABLE_SPLIT_HEADERS 
       
    34 #include "cimconvertheader.h"
       
    35 #endif
       
    36 
       
    37 class CMsvPlainBodyTextEntry;
       
    38 class CImHeader;
       
    39 class CRichText;
       
    40 class CMimeParser;
       
    41 class CImRecvConvert;
       
    42 class RFs;
       
    43 class TImConvert;
       
    44 class TImAttachmentFile;
       
    45 class CImcvUtils;
       
    46 class CMsvBodyText;
       
    47 
       
    48 const TInt KHeaderBufferLength = 100;
       
    49 
       
    50 // Max filename length
       
    51 const TInt MaxMimeParameterValueLength = 256;
       
    52 // Likely maximum size of an encoded parameter value decoding to a length of 
       
    53 // MaxMimeParameterValueLength. In quoted printable usually 3 encoded characters
       
    54 // per decoded character. 60 characters is given to allow for delimiters and
       
    55 // charset information.
       
    56 const TInt KMimeEncodedParameterSize = MaxMimeParameterValueLength * 3 + 60;
       
    57 
       
    58 const TInt KConversionRemainderLength=20;
       
    59 
       
    60 //boundary stuff
       
    61 const TInt KBoundaryNotFound	=0;
       
    62 const TInt KBoundaryFound		=1;
       
    63 const TInt KBoundaryError		=2;
       
    64 
       
    65 
       
    66 // Stores the details about a message nneded in the Message entry.
       
    67 struct TParentDetails
       
    68 /**
       
    69 @internalComponent
       
    70 @released
       
    71 */
       
    72 	{
       
    73 	TInt				iSize;
       
    74 	TBool				iAttachment;
       
    75 	TBool				iMHTML;
       
    76 	TImEmailFolderType  iFolder;	// Only interested in the Related type
       
    77 	TBool				iICal;
       
    78 	TBool				iVCal;
       
    79 	};
       
    80 
       
    81 //----------------------------------------------------------------------------------------
       
    82 class CRfc822Token : public CBase
       
    83 //----------------------------------------------------------------------------------------
       
    84 /**
       
    85 @internalComponent
       
    86 @released
       
    87 */
       
    88 	{
       
    89 public:
       
    90 	enum THeaderPart { EUnknown, ENotFinished, EFrom, EReplyTo, ETo, ECc, EBcc, ESubject, EDate, EReceived, EMessageId, EPriority, EImportance, EReturnReceiptTo, EEndOfHeader };
       
    91 	THeaderPart iHeaderPart;
       
    92 	TBool iLastToken;
       
    93 	TBool iFirstLine;
       
    94 	TBool i822FieldsExist;
       
    95 
       
    96 	IMPORT_C static CRfc822Token* NewLC();
       
    97 	IMPORT_C void Reset();
       
    98 	inline HBufC8* OutputLine();
       
    99 	IMPORT_C void ParseNextLineL( const TDesC8& aSourceLine );
       
   100 	IMPORT_C ~CRfc822Token();
       
   101 	inline TBool LastToken();
       
   102 
       
   103 	inline void SetImRecvConvert( CImRecvConvert* );
       
   104 private:
       
   105 	TBool MatchAndRemoveL( const TDesC8& );
       
   106 	TBool PriorityAndReceiptsMatchAndRemoveL(THeaderPart aPriority);
       
   107 
       
   108 	CRfc822Token();
       
   109 	void ConstructL();
       
   110 
       
   111 private:
       
   112 	TBuf8<KMaxIMailHeaderReadLineLength+1> iInputLine;
       
   113 	TBuf8<KMaxIMailHeaderReadLineLength+1> iBufferedInput;
       
   114 	HBufC8* iOutputLine;
       
   115 	CImRecvConvert* iImRecvConvert;
       
   116 	};
       
   117 
       
   118 //----------------------------------------------------------------------------------------
       
   119 class CImRecvConvert : public CBase
       
   120 //----------------------------------------------------------------------------------------	
       
   121 /**
       
   122 @internalAll
       
   123 @released
       
   124 */
       
   125 	{
       
   126 friend class CMimeParser;
       
   127 public:
       
   128 	IMPORT_C static CImRecvConvert* NewLC( RFs& anFs, CMsvServerEntry* aServerEntry, 
       
   129 												TUid aMsgType, TMsvId aEmailServiceId);
       
   130 	IMPORT_C static CImRecvConvert* NewL( RFs& anFs, CMsvServerEntry* aServerEntry,
       
   131 												TUid aMsgType, TMsvId aEmailServiceId);
       
   132 	IMPORT_C ~CImRecvConvert();
       
   133 
       
   134 	IMPORT_C void Cancel();
       
   135 
       
   136 	IMPORT_C void ResetL();
       
   137 	IMPORT_C void ResetForHeadersL();
       
   138 
       
   139 	inline void SetAttachmentPathL(const TDesC& aFullPath);	// attachment path, if not set then IMCV will reject attachments
       
   140 	inline void SetMsvId(TMsvId aId);
       
   141 
       
   142 	IMPORT_C TInt ParseNextField(const TDesC8& aSourceLine);
       
   143 	IMPORT_C void MessageCompleteL();
       
   144 	IMPORT_C void MessageCompleteL(TMsvEmailEntry aEmailEntry);
       
   145 	IMPORT_C void MessageCompleteL(TBool aPartialDownload);
       
   146 	IMPORT_C TInt DeletedAttachmentSize();
       
   147 	IMPORT_C void WritePartialFooterL(TInt aAmountLeft);
       
   148 	IMPORT_C void SetCaf(CImCaf& aCAF);
       
   149 	IMPORT_C TMsvEmailEntry MessageEntryDetailsL();
       
   150 
       
   151 	enum TValidEntryType {EUnknownEntry, EMessageEntry, EFolderEntry, EAttachmentEntry, ETextEntry, EHtmlEntry, ERtfEntry};
       
   152 	enum TImEntryStreamSaveSettings
       
   153 		{
       
   154 		KStoreBodyText					= 0x00000001,
       
   155 		KStore822Header					= KStoreBodyText << 1,		//0x00000002
       
   156 		KStoreMIMEHeader				= KStore822Header << 1,	//0x00000004
       
   157 		};
       
   158 
       
   159 	inline const TTime Date() const;	// return RFC822 date
       
   160 	inline const TMsvPriority Priority() const;
       
   161 	inline void SaveAllAttachments(TBool aSave);
       
   162 	inline const TInt ReceiveError() const;
       
   163 	inline CMsvServerEntry& ServerEntry();
       
   164 	inline const CImHeader& Header() const;
       
   165 	inline const TBool ValidCompleteHeader() const;
       
   166 	inline const TMsvId EntryId() const;	
       
   167 	inline TBool NotFinishedRfc822Header();
       
   168 	inline CImConvertCharconv& CharacterConverter();
       
   169 	void ImCafRegisterL(const TDesC8& aMimeLine);
       
   170 	void ImAddToCafMetaDataL(const TDesC8& aMimeLine);
       
   171 	void ImAddToCafMetaDataL(const TDesC8& aField, const TDesC8& aData);
       
   172 	TBool ImCafProcessing() const;
       
   173 	TBool ImCafRegistered() const;
       
   174 private:
       
   175 	CImRecvConvert(RFs& anFs, CMsvServerEntry* aServerEntry, 
       
   176 							TUid aMsgType, TMsvId aEmailServiceId);
       
   177 	void ConstructL(RFs& anFs);
       
   178 
       
   179 	void ParseNextLineL(const TDesC8& aSourceLine);
       
   180 	void ParseBodyLineL(const TDesC8& aSourceLine);
       
   181 	void ParseMimeLineL(const TDesC8& aSourceLine);
       
   182 	void EndOfHeaderProcessingL();
       
   183 	void EndOfHeaderMIMEProcessingL();
       
   184 	TBool CreateNonMIMEFolderEntryL(TMsvId aCurrentId);
       
   185 	void DecodeAndStoreLineL(const TDesC8& aSourceLine);
       
   186 
       
   187 	void ParseRecipientListL(CDesCArray& aRecipientList);
       
   188 	void PrepareDecoder();
       
   189 
       
   190 	void WriteToBodyL(const TDesC8& aText, TBool aBlankLine=EFalse);
       
   191 	void WriteToBodyL(const TDesC16& aText);
       
   192 
       
   193 	void AddFileExtension();
       
   194 	void ExtractFilename(TLex& aLex, TDes& rFileName);
       
   195 	void ReplaceInvalidCharacters(TDes& rFileName);
       
   196 	void SetAttachmentName(TDes& aFileName);
       
   197 	
       
   198 	TBool CheckUUEStartL(const TDesC8& aSourceLine);
       
   199 
       
   200 	// returns numeric value of text up to next delimiter
       
   201 	TInt Value(const TUint8*&);
       
   202 	void Whitespace(const TUint8*&);
       
   203 	TBool LineIsAllWhitespace();	
       
   204 
       
   205 	TBool CreateAttachmentL();
       
   206 	void WriteToAttachmentL(const TDesC8& text);
       
   207 	void CloseAttachmentFileL();
       
   208 
       
   209 	// Message Entry specific functions
       
   210 	void ResetForNewEntryL(TValidEntryType entryType);
       
   211 	void ResetForNonMimeEntryL();
       
   212 	void MoveUpFromFolderEntryL();
       
   213 	void MoveToParentEntryL();
       
   214 	void UpdateMultipartDataL();
       
   215 
       
   216 	TBool StoreEntryDataL();
       
   217 
       
   218 	void StoreEntryStreamsL();
       
   219 	void StoreEntryStreamsL(TInt aSettings);
       
   220 	void Store822HeaderL(CMsvStore& aStore, TBool& aCommit);
       
   221 	void StoreMIMEHeaderL(CMsvStore& aStore, TBool& aCommit);
       
   222 	void StoreBodyTextL(CMsvStore& aStore, TBool& aCommit);
       
   223 
       
   224 	void CreateEntryL();
       
   225 	void Logging(const TDesC8& aString1, const TDesC8& aString2);
       
   226 	void StoreMessageEntryDetailsL();
       
   227 	void WritePartialFooter8L(TInt aAmountLeft);
       
   228 	
       
   229 private:
       
   230 	enum { KNoPart = 0, KParentPart, KMultiPart };
       
   231 	TInt iEmailPart;
       
   232 	TMsvId iCurrentMultipartFolderEntryId;
       
   233 
       
   234 	TBool iMessageEntryCalled;
       
   235 	TBool iReceivingHeadersOnly;
       
   236 	TInt iReceiveError; // indicates if any anomalies were observed whilst the message was received
       
   237 	TInt iLeaveError; // keeps any errors that have caused a leave (ie Out of memory, Corrupt file, Server error)
       
   238 
       
   239 	TMsvId iRootEntryId;
       
   240 	TMsvId iTopMessagePart;
       
   241 
       
   242 	TInt8 iBCPadding[1348]; // Padding to maintain BC - TImAttachmentFile used to be here before it's size was expanded to buffer more data.
       
   243 	CMsvServerEntry* iServerEntry;
       
   244 	TUid iNewMsgType;
       
   245 
       
   246 	CRfc822Token* iRfc822Token;
       
   247 
       
   248 	TValidEntryType iDefaultEntryType;
       
   249 	TValidEntryType iEntryType;
       
   250 
       
   251 	TMsvEmailEntry* iEmailEntry;
       
   252 	CImHeader* iOutputHeader;
       
   253 	
       
   254 	CParaFormatLayer* iParaLayer;
       
   255 	CCharFormatLayer* iCharLayer;
       
   256 	CRichText* iOutputBody;
       
   257 	
       
   258 	CImConvertCharconv* iCharConv;
       
   259 	CCnvCharacterSetConverter* iConverter;
       
   260 	TBool iPreparedToConvert;
       
   261 	
       
   262 	TBool iMIMEPart_822Header;	
       
   263 	TInt iEmptyHeaderSize;
       
   264 	TImBodyConvAlgorithm iAlgorithm;
       
   265 
       
   266 	TBool iCommitLine;	
       
   267 	TBool iFinalLine;	
       
   268 	TBool iPrepared;
       
   269 	TBool iFinishedHeader;
       
   270 	TBool iNotFinishedRfc822Header;
       
   271 	TBool iNewNonMIMEBodyPart;
       
   272 	TBool iFirstBoundaryReached;
       
   273 
       
   274 	CCnvCharacterSetConverter* iCharacterConverter;
       
   275 	CImConvertHeader* iHeaderConverter;
       
   276 
       
   277 	TImRfc822DateField iRfc822Date;
       
   278 
       
   279 	RFs* iFsSession;  
       
   280 
       
   281 	TBool iSkipData;
       
   282 	TBool iEncounteredLineEndingInCarriageReturn;
       
   283 
       
   284 	TBool iCurrentPartIsRichText;	//indicates if current body part is RichText, set on every Close Attachment()
       
   285 	TImCodecQP iQPCodec;
       
   286 	TImCodecB64 iB64Codec;
       
   287 	TImCodecUU iUUCodec;
       
   288 	TPtrC8 iThisLine;
       
   289 	
       
   290 	HBufC* iRemovedAttachmentTag;		// resource text which is put into the body in place of a removed MIME attachment
       
   291 	HBufC* iRetainedAttachmentTag;		// Not used at all - resource text which is put into the body next to a retained MIME attachment
       
   292 	HBufC* iDefaultAttachmentName;		// used when no name found	
       
   293 	HBufC* iAttachmentFullPath;			// full path to current message file
       
   294 
       
   295 	TBool iSavingAttachments;			// Turn on/off saving of attachments
       
   296 
       
   297 	TBuf8<KMaxBoundaryTextLength> iSeekBoundary;
       
   298 	
       
   299 	TInt iGlobalIndent;
       
   300 	TInt iPreviousLineLength;
       
   301 	TInt iPreviousTrailingWhitespace;
       
   302 	TChar iLastChar;
       
   303 	TInt iLongestLine;
       
   304 	TBool iNewEntry;
       
   305 
       
   306 	TImAttachmentFileState iAttachmentFileState;
       
   307 	TUint32 iEntryDataSize;
       
   308 
       
   309 	TBool	iLogFileExists;
       
   310 	RFile	iLogFile;
       
   311 	TLex8	iLineLex;
       
   312 	TTime   iTimeDate;
       
   313 	TBool	iParsedTime;
       
   314 
       
   315 	//priorities   //vk
       
   316 	TInt iPriority;		//{1..5}
       
   317 	TInt iXPriority;   // {1..5} 1,2-high, 3-normal, 4,5-low
       
   318 	TBuf8<KMaxPriorityTextLength> iPrecedence;  //   {bulk-low, list-normal,first class,special delivery-0}
       
   319 	TBuf8<KMaxPriorityTextLength> iImportance;  // {high, low, normal}
       
   320 	TMsvPriority iImPriority;
       
   321 
       
   322 	TMsvId	iEmailServiceId;
       
   323 	TBool	iPopulateMessage;
       
   324 	CImcvUtils* iImcvUtils;
       
   325 
       
   326 	TBuf8<KConversionRemainderLength> iLeftOver;
       
   327 
       
   328 	TMsvId	iSavedEntryId;
       
   329 	CArrayFixFlat<TParentDetails>* iParent;
       
   330 	// Logging
       
   331 	CImLog*					iImcvLog;
       
   332 
       
   333 	TMsvId					iBodyId;
       
   334 	
       
   335 public:
       
   336 	TFileName 				iAttachmentName;
       
   337 	CMimeParser* 			iMimeParser;
       
   338 private:
       
   339 	TBool					iRelatedAttachments;
       
   340 	CBufBase* 				iBodyBuf;
       
   341 	CMsvBodyText 			*iBodyText;
       
   342 	TInt 					iStore8BitData;
       
   343 	TImAttachmentFile 		iAttachmentFile;
       
   344 	TBool 					iParsedMimeBoundaryLast;
       
   345 	TInt 					iSizeOfAttachmentsRemoved;
       
   346 	HBufC* 					iPartialEmailFooter;
       
   347 	HBufC8* 				iPartialEmailFooter8;
       
   348 	HBufC8* 				iPartialRetrievalBody; // for storing the partial email body
       
   349 	TInt 					iTopPartialDownloadCounter; // added to support correct attachment downloading after partial download
       
   350 	TBool 					iPartialEmail;
       
   351 	RFile*					iFile;
       
   352 	// Additions for CAF;
       
   353 	CImCaf*					iCaf;
       
   354 	// Indicates whether the first line of the plaintext body part is received.
       
   355 	TBool   				iFirstLinePlainText;
       
   356 	// Indicates whether to store the mail bodytext in chunks or entire.
       
   357 	TBool    				iStorePlainBodyText;
       
   358 	// A wrapper over CMsvPlainBodyText to store body text in chunks.
       
   359 	CMsvPlainBodyTextEntry *iPlainBodyTextEntry;
       
   360 	};
       
   361 
       
   362 
       
   363 //----------------------------------------------------------------------------------------
       
   364 class CMimeParser : public CBase
       
   365 //----------------------------------------------------------------------------------------
       
   366 /**
       
   367 @internalComponent
       
   368 @released
       
   369 */
       
   370 	{
       
   371 public:
       
   372 	IMPORT_C static CMimeParser* NewLC(CImRecvConvert& aImRecvConvert);
       
   373 	IMPORT_C static CMimeParser* NewL(CImRecvConvert& aImRecvConvert);
       
   374 	IMPORT_C ~CMimeParser();
       
   375 	
       
   376 	void Reset();
       
   377 	void ResetForNewEntry();
       
   378 	void ParseLineL(const TDesC8& aSourceLine);
       
   379 
       
   380 	void SetBoundaryL(const TDesC8& aBoundaryText);
       
   381 	TBool IsBoundary(const TDesC8& aSourceLine);
       
   382 	void RemoveBoundary();
       
   383 	
       
   384 	inline void StoreMimeHeaderL(CMsvStore& entryStore);
       
   385 	inline void StoreMimeHeaderWithoutCommitL(CMsvStore& entryStore);
       
   386 	inline void RestoreMimeHeaderL(CMsvStore& entryStore);
       
   387 
       
   388 	inline TImEncodingType ContentEncoding();
       
   389 	inline TMimeContentType ContentType();
       
   390 	TPtrC8 ContentSubType() const;
       
   391 	TUint CurrentCharsetL() const;
       
   392 
       
   393 	inline const TBool MessageIsMime() const;
       
   394 	inline const TBool IsTerminatingBoundary() const;
       
   395 	inline const TBool BoundaryExists() const;
       
   396 	inline const TBool BoundaryFound() const;
       
   397 	inline const TInt MimeHeaderSize() const;
       
   398 	inline const TInt ReceiveError() const;
       
   399 	inline const TDesC& ContentDescription() const;
       
   400 	inline const TPtrC ContentLocation() const;
       
   401 	inline const TPtrC8 ContentId() const;
       
   402 	inline const TPtrC8 ContentDisposition() const;
       
   403 	inline TBool IsMessageDigest();
       
   404 
       
   405 	TBool VCard() const;
       
   406 	TBool VCalendar() const;
       
   407 	TBool ICalendar() const;
       
   408 	TImEmailFolderType MessageFolderType() const;
       
   409 	void SetMessageFolderType(TImEmailFolderType aFolderType);
       
   410 	TBool StartPart() const;
       
   411 	void RestoreMimeParserL(CMsvStore& entryStore);
       
   412 	void ExtractParameterInfoL(const TDesC8& aTag, TDes16& rBuffer, HBufC8*& paramValue8);	
       
   413 	void ExtractParameterInfoL(const TDesC8& aTag, HBufC8*& rBuffer);	
       
   414 	TBool MimeFieldsExist() const;
       
   415 	void ResetMimeFieldsExist();
       
   416 	void DoMultipartTypeForNonMIMEL();
       
   417 
       
   418 #if defined (_DEBUG)
       
   419 	inline TLex8& Lex() {return iLex;};
       
   420 #endif
       
   421 	
       
   422 	TPtrC8 ContentTypeDescription() const;
       
   423 
       
   424 private:
       
   425 	CMimeParser(CImRecvConvert& aImRecvConvert);
       
   426 	void ConstructL();
       
   427 
       
   428 	// String scanning functions
       
   429 	TBool IsSpecialChar(const TUint8 aChar);
       
   430 	TBool MatchAndRemoveToken(const TDesC8& aToken);
       
   431 	TInt FindAttribute(const TDesC8& aTag, const TDesC8& aParameterList);
       
   432 
       
   433 	// MIME token recognition functions
       
   434 	void DoMimeVersion();
       
   435 	void DoContentTypeL();
       
   436 	void DoContentLocationL();
       
   437 	void DoContentBaseL();
       
   438 	void DoContentIdL();
       
   439 	void DoEncodingL();
       
   440 	void DoDescriptionL();
       
   441 	void DoDispositionL();
       
   442 
       
   443 	// MIME Content-Type type recognition functions
       
   444 	void DoTextTypeL();
       
   445 	void DoMultipartTypeL();
       
   446 	void DoMessageTypeL();
       
   447 	void DoAttachmentTypeL();
       
   448 
       
   449 	// Will be moved to MIUT, but for now ..
       
   450 	const TPtrC8 GetContentTypeValue(const TDesC8& aContentTypeParameter) const;
       
   451 	      
       
   452 	TBool ParseRfc2047ParameterInfoL( const TDesC8& aParam, TDes& rBuffer);
       
   453 	TBool ParseRfc2231ParameterInfoL( const TDesC8& aTag, TDes& rBuffer, TInt aOffset );
       
   454 	TBool DecodeRfc2231ParameterInfoL( TDes8& aInput, TDes& rBufOut, 
       
   455 											TPtrC8 aCharset/*, TPtrC8 aLanguage*/);
       
   456 	TPtrC8 ExtractParameterString(TLexMark8& rMark);
       
   457 
       
   458 private:
       
   459 	CImRecvConvert& iImRecvConvert;
       
   460 	CImMimeHeader* iMimeHeader;
       
   461 
       
   462 	TInt iEmptyMimeHeaderSize;
       
   463 	
       
   464 	TBool isMime;
       
   465 	TBool iCorrectMimeVersion;
       
   466 	TImEncodingType iContentEncoding;
       
   467 	TMimeContentType iContentType;
       
   468 	TFileName iContentDescription;
       
   469 	TBool iVCard;
       
   470 	TBool iVCalendar;
       
   471 	TBool iICalendar;
       
   472 	TBool iStartPart;
       
   473 	TImEmailFolderType iMessageFolderType;
       
   474 	TUint iCharset;
       
   475 	TUint iDefaultCharset;
       
   476 	HBufC8* iStartId;
       
   477 
       
   478 	// Boundary stuff
       
   479 	CDesC8ArrayFlat* iBoundaryText;
       
   480 	TInt iBoundaryIndex;
       
   481 	TInt iBoundaryLength;
       
   482 	TBool iTerminatingBoundary;
       
   483 	TBool iBoundaryFound;
       
   484 	TInt iReceiveError; // Indicates if any anomalies were observed whilst the message was received
       
   485 						// Can be accessed via the inline ReceiveError()
       
   486 	TPtrC8 iTestLine;
       
   487 
       
   488 	HBufC8* iMimeHeaderLine;
       
   489 	TLexMark8 iMark;
       
   490 	TLex8 iLex;
       
   491 	TLex8 iTestLex;	
       
   492 	TBool isMessageDigest;
       
   493 	TBool iMimeFieldsExist;
       
   494 
       
   495 	};
       
   496 
       
   497 #include <imcvrecv.inl>
       
   498 
       
   499 #endif