Return TypeFunction nameArguments
hzEcodehzEmail::Import(const hzChain&,bool,)

Declared in file: hzMailer.h
Defined in file : hzMailer.cpp

Function Logic:

0:START 1:hzEmail::Clear hzChain::Clear zi 2:!zi.eof(); 3:*zi==(char)13 4:zi==\r\n\r\n 5:zi 6:zi==\r\n 7:zi 8:_find_hdr_end 9:*zi 10:(char)98 11:(char)66 12:zi.Equiv(Bcc: ) 13:zi _reademaddr 14:!_reademaddr(strval,emtmp,zi) 15:rc 16:hzList::Add 17:(char)99 18:(char)67 19:zi.Equiv(Cc: ) 20:zi _reademaddr 21:!_reademaddr(strval,emtmp,zi) 22:rc 23:hzList::Add 24:zi.Equiv(Content-Type: ) 25:zi hzChain::Iter::Equiv 26:zi.Equiv(text/plain;) 27:zi m_ContType hzChain::Iter::Equiv 28:zi.Equiv(text/html;) 29:zi m_ContType hzChain::Iter::Equiv 30:zi.Equiv(multipart/alternative;) 31:zi m_ContType hzChain::Iter::Equiv 32:zi.Equiv(multipart/mixed;) 33:zi m_ContType hzChain::Iter::Equiv 34:zi.Equiv(multipart/related;) 35:zi m_ContType 36:rc 37:m_ContType==HZ_CONTENT_TYPE_MULTI_MIXED||m_ContType==HZ_CONTENT_TYPE_MULTI_ALTERNATIVE||m_ContType==HZ_CONTENT_TYPE_MULTI_RELATED 38:mark 39:rc 40:*zi; 41:*zi==(char)98 42:zi==boundary= 43:zi _readStrval 44:!mark 45:rc 46:zi==Content-Transfer-Encoding: 47:zi 48:zi==7bit 49:m_Encoding 50:zi==8bit 51:m_Encoding 52:zi==binary 53:m_Encoding 54:zi==base64 55:m_Encoding 56:zi==quoted-printable 57:m_Encoding 58:rc 59:(char)100 60:(char)68 61:zi.Equiv(Date: ) 62:zi IsFormalDate nLen 63:!nLen 64:(char)70 65:zi==From: 66:zi _reademaddr 67:!_reademaddr(m_RealFrom,m_AddrFrom,zi) 68:rc items 69:(char)77 70:zi==Message-ID: 71:zi _readangle 72:(char)114 73:(char)82 74:zi.Equiv(Return-Path:) 75:zi _reademaddr 76:!_reademaddr(strval,m_AddrReturn,zi) 77:rc 78:zi.Equiv(Reply-To:) 79:zi _reademaddr 80:!_reademaddr(m_RealReply,m_AddrReply,zi) 81:rc 82:(char)115 83:(char)83 84:zi.Equiv(Subject: ) 85:zi _readStrval m_Subject CharsetStringDecode 86:(char)116 87:(char)84 88:zi.Equiv(To: ) 89:zi _reademaddr 90:!_reademaddr(m_RealTo,emtmp,zi) 91:rc 92:!m_AddrTo 93:m_AddrTo 94:hzList::Add 95:(char)120 96:(char)88 97:zi.Equiv(X-Epistula-ServerID: ) 98:zi _readangle 99:zi.Equiv(X-Epistula-Ingress: ) 100:zi _reademaddr 101:!_reademaddr(strval,m_AddrRelay,zi) 102:rc 103:zi 104:rc!=E_OK 105: No text 106:Return rc 107:!m_Date 108:rc 109:!m_AddrFrom 110:rc 111:!m_AddrTo 112:rc 113:!m_Id 114:m_Id 115:!m_Id 116:rc 117:rc!=E_OK 118:Return rc 119:bHead 120:Return rc 121:!mark 122:hzChain::Clear 123:!zi.eof(); 124:*zi==(char)13 125:zi==\r\n.\r\n 126:hzChain::AddByte 127:m_ContType==HZ_CONTENT_TYPE_TEXT_HTML 128:_part_decode 129:_part_decode 130:Return rc 131:markStart markEnd 132:zi!=markStart 133:hzChain::Iter::Skipwhite nP 134:rc==E_OK&&zi==markStart; 135:zi==markEnd 136:hzEmail::_part_process rc 137:Return rc

Function body:

hzEcode hzEmail::Import (const hzChain& emRaw, bool bHead)
{
   _hzfunc("hzEmail::Import") ;
   hzChain     Part ;
   chIter      zi ;
   chIter      xi ;
   chIter      endHdr ;
   chIter      bodyStart ;
   hzEmpart    epart ;
   hzEmaddr    emtmp ;
   hzString    filepath ;
   hzString    mark ;
   hzString    markStart ;
   hzString    markEnd ;
   hzString    strval ;
   hzString    episId ;
   uint32_t    nP ;
   uint32_t    nLen ;
   hzEcode     rc = E_OK ;
   Clear() ;
   m_Err.Clear() ;
   zi = emRaw ;
   for (; !zi.eof() ;)
   {
       if (*zi == CHAR_CR)
       {
           if (zi == "\r\n\r\n")
               { zi += 4; break ; }
           if (zi == "\r\n")
               zi += 2;
       }
       _find_hdr_end(endHdr, zi) ;
       switch  (*zi)
       {
       case CHAR_LC_B:
       case CHAR_UC_B: if (zi.Equiv("Bcc: "))
                       {
                           zi += 5;
                           if (!_reademaddr(strval, emtmp, zi))
                               rc = E_SYNTAX ;
                           m_BCC.Add(emtmp) ;
                           threadLog("Bcc: Added %s\n", *emtmp) ;
                       }
                       break ;
       case CHAR_LC_C:
       case CHAR_UC_C: if (zi.Equiv("Cc: "))
                       {
                           zi += 4;
                           if (!_reademaddr(strval, emtmp, zi))
                               rc = E_SYNTAX ;
                           m_CC.Add(emtmp) ;
                           threadLog("Cc: Added %s\n", *emtmp) ;
                           break ;
                       }
                       if (zi.Equiv("Content-Type: "))
                       {
                           zi += 14;
                           if      (zi.Equiv("text/plain;"))               { zi += 11;m_ContType = HZ_CONTENT_TYPE_TEXT_PLAIN ; }
                           else if (zi.Equiv("text/html;"))                { zi += 10;m_ContType = HZ_CONTENT_TYPE_TEXT_HTML ; }
                           else if (zi.Equiv("multipart/alternative;"))    { zi += 22;m_ContType = HZ_CONTENT_TYPE_MULTI_ALTERNATIVE ; }
                           else if (zi.Equiv("multipart/mixed;"))          { zi += 16;m_ContType = HZ_CONTENT_TYPE_MULTI_MIXED ; }
                           else if (zi.Equiv("multipart/related;"))        { zi += 18;m_ContType = HZ_CONTENT_TYPE_MULTI_RELATED ; }
                           else
                           {
                               rc = E_SYNTAX ;
                               threadLog("Unknown Content-Type\n") ;
                           }
                           if (m_ContType == HZ_CONTENT_TYPE_MULTI_MIXED || m_ContType == HZ_CONTENT_TYPE_MULTI_ALTERNATIVE || m_ContType == HZ_CONTENT_TYPE_MULTI_RELATED)
                           {
                               if (mark)
                               {
                                   rc = E_FORMAT ;
                                   threadLog("MULTIPART MIX/ALT/REL: Boundary already specified\n") ;
                               }
                               else
                               {
                                   for (; *zi ; zi++)
                                   {
                                       if (*zi == CHAR_LC_B)
                                       {
                                           if (zi == "boundary=")
                                           {
                                               zi += 9;
                                               _readStrval(mark, zi) ;
                                               break ;
                                           }
                                       }
                                   }
                                   if (!mark)
                                       { rc = E_SYNTAX ; threadLog("MULTIPART MIX/ALT/REL: Expected a boundary to be specified\n") ; }
                               }
                           }
                           break ;
                       }
                       if (zi == "Content-Transfer-Encoding: ")
                       {
                           zi += 27;
                           if      (zi == "7bit")              m_Encoding = HZ_CONTENT_ENCODE_7BIT ;
                           else if (zi == "8bit")              m_Encoding = HZ_CONTENT_ENCODE_8BIT ;
                           else if (zi == "binary")            m_Encoding = HZ_CONTENT_ENCODE_8BIT ;
                           else if (zi == "base64")            m_Encoding = HZ_CONTENT_ENCODE_BASE64 ;
                           else if (zi == "quoted-printable")  m_Encoding = HZ_CONTENT_ENCODE_QUOTE_PRINT ;
                           else
                               { rc = E_SYNTAX ; threadLog("Unknown Content-Transfer-Encoding value\n") ; }
                       }
                       break ;
       case CHAR_LC_D:
       case CHAR_UC_D: if (zi.Equiv("Date: "))
                       {
                           zi += 6;
                           nLen = IsFormalDate(m_Date, zi) ;
                           if (!nLen)
                               threadLog("Date arg must amount to legal date\n") ;
                       }
                       break ;
       case CHAR_UC_F: if (zi == "From: ")
                       {
                           zi += 6;
                           if (!_reademaddr(m_RealFrom, m_AddrFrom, zi))
                               { rc = E_SYNTAX ; m_Err << "From: arg must amount to an email address\n" ; }
                       }
                       break ;
       case CHAR_UC_M: if (zi == "Message-ID: ")
                       {
                           zi += 12;
                           _readangle(m_Id, zi) ;
                       }
                       break ;
       case CHAR_LC_R:
       case CHAR_UC_R: if (zi.Equiv("Return-Path:"))
                       {
                           zi += 12;
                           if (!_reademaddr(strval, m_AddrReturn, zi))
                               { rc = E_SYNTAX ; threadLog("Return-Path must amount to an email address\n") ; }
                           break ;
                       }
                       if (zi.Equiv("Reply-To:"))
                       {
                           zi += 9;
                           if (!_reademaddr(m_RealReply, m_AddrReply, zi))
                               { rc = E_SYNTAX ; threadLog("Reply-To: arg must amount to an email address\n") ; }
                       }
                       break ;
       case CHAR_LC_S:
       case CHAR_UC_S: if (zi.Equiv("Subject: "))
                       {
                           zi += 9;
                           _readStrval(strval, zi) ;
                           m_Subject = strval ;
                           CharsetStringDecode(m_Subject, strval) ;
                       }
                       break ;
       case CHAR_LC_T:
       case CHAR_UC_T: if (zi.Equiv("To: "))
                       {
                           zi += 4;
                           if (!_reademaddr(m_RealTo, emtmp, zi))
                               { rc = E_SYNTAX ; threadLog("To: arg must amount to an email address\n") ; }
                           if (!m_AddrTo)
                               m_AddrTo = emtmp ;
                           m_Recipients.Add(emtmp) ;
                       }
                       break ;
       case CHAR_LC_X:
       case CHAR_UC_X: if (zi.Equiv("X-Epistula-ServerID: "))
                       {
                           zi += 21;
                           _readangle(episId, zi) ;
                           break ;
                       }
                       if (zi.Equiv("X-Epistula-Ingress: "))
                       {
                           zi += 20;
                           if (!_reademaddr(strval, m_AddrRelay, zi))
                               { rc = E_SYNTAX ; threadLog("X-Epistula-Ingress: arg must amount to an email address\n") ; }
                       }
                       break ;
       }
       zi = endHdr ;
   }
   if (rc != E_OK)
   {
       threadLog("IMPORT FAILED\n") ;
       threadLog(m_Err) ;
       threadLog("--end--\n") ;
       return rc ;
   }
   if (!m_Date)
       { rc = E_BADVALUE ; threadLog("WARNING: No date header\n") ; }
   if (!m_AddrFrom)
       { rc = E_BADVALUE ; threadLog("No From address\n") ; }
   if (!m_AddrTo)
       { rc = E_BADVALUE ; threadLog("No recipients\n") ; }
   if (!m_Id)
       m_Id = episId ;
   if (!m_Id)
       { rc = E_BADVALUE ; threadLog("No mail id\n") ; }
   if (rc != E_OK)
   {
       threadLog("IMPORT FAILED\n") ;
       return rc ;
   }
   if (bHead)
       return rc ;
   /*
   **  ** Process the body. This may or may not come in blocks marked out by the boundary.
   **      */
   if (!mark)
   {
       Part.Clear() ;
       for (; !zi.eof() ; zi++)
       {
           if (*zi == CHAR_CR)
           {
               if (zi == "\r\n.\r\n")
                   break ;
           }
           Part.AddByte(*zi) ;
       }
       if (m_ContType == HZ_CONTENT_TYPE_TEXT_HTML)
           _part_decode(m_Html, Part, m_Encoding) ;
       else
           _part_decode(m_Text, Part, m_Encoding) ;
       threadLog("Processed a non-part message\n") ;
       return rc ;
   }
   markStart = "--" + mark ;
   markEnd = markStart + "--" ;
   threadLog("Operating with BOUNDARY=%s\n", *mark) ;
   if (zi != markStart)
   {
       threadLog("Unexpected data\n") ;
       zi.Skipwhite() ;
   }
   for (nP = 0; rc == E_OK && zi == markStart ; nP++)
   {
       if (zi == markEnd)
           break ;
       threadLog("Processing part %u\n", nP) ;
       rc = _part_process(zi, mark, 1);
   }
   return rc ;
}