⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 imapserverc.c

📁 linux下的E_MAIL客户端源码
💻 C
📖 第 1 页 / 共 5 页
字号:
{   StringC	cmd = "RENAME ";   cmd += oldname;   cmd += " ";   cmd += newname;   Boolean	success = RunCommand(cmd, output);   if ( success && oldname == folder ) folder = newname;   return success;}/*------------------------------------------------------------------------ * Function to send SELECT command and wait for response. */BooleanImapServerC::Select(CharC mailbox, StringListC& output){   // If the folder has been opened, and the server doesn't answer   // duplicate SELECT correctly (UW, for one) close the folder first   if ( bugs & IMAP_BUG_DUPLICATE_SELECT && folder == mailbox ) {      StringListC output;      if ( !Close(output) ) return False;   }      StringC	cmd = "SELECT ";   cmd += mailbox;   Boolean	success = RunCommand(cmd, output);   if ( success ) folder = mailbox;   return success;}/*------------------------------------------------------------------------ * Function to send CLOSE command and wait for response. */BooleanImapServerC::Close(StringListC& output){   return RunCommand("CLOSE", output);}/*------------------------------------------------------------------------ * Function to send EXPUNGE command and wait for response. */BooleanImapServerC::Expunge(StringListC& output){   return RunCommand("EXPUNGE", output);}/*------------------------------------------------------------------------ * Function to send FETCH command and wait for response. */BooleanImapServerC::Fetch(int msgnum, ImapFolderC* fld, CharC key, char **output, char **flags,		   StringC& response){   *output = NULL;   *flags  = NULL;   response.Clear();   StringC	saveFolderName = folder;   StringC	folderName = fld->name;   //// May need to select the named folder first//   if ( folderName != saveFolderName ) {      StringListC output;      if ( !Select(folderName, output) ) return False;   }   //// Build the command we will send//   StringC	tag;   GenTag(tag);   StringC	cmd(tag);   cmd += "FETCH ";   cmd += msgnum;   cmd += " ";   cmd += key;//// Send the command and wait for the response//   if ( !PutLine(cmd) ) return False;   if ( !GetLine(response) ) return False;   StringC	expect("* ");   expect += msgnum;   expect += " FETCH ";   while ( !response.StartsWith(expect, IGNORE_CASE) &&      	   !response.StartsWith(tag) ) {      Unexpected(response);      if ( !GetLine(response) ) return False;      if ( response.StartsWith(tag) ) {	 response.CutBeg(tag.size());	 return False;      }   }//// Parse the response//   if ( response.StartsWith(expect, IGNORE_CASE) )       response.CutBeg(expect.size());   else if ( response.StartsWith(tag) )       response.CutBeg(tag.size());    if ( response.StartsWith('(') ) response.CutBeg(1);   response.Trim();//// These commands send the total size in the first line//   if ( response.StartsWith("INTERNALDATE ",	IGNORE_CASE) ||	response.StartsWith("RFC822.HEADER ",	IGNORE_CASE) ||	response.StartsWith("RFC822.SIZE ",	IGNORE_CASE) ||	response.StartsWith("UID ",		IGNORE_CASE) ||	response.StartsWith("BODY[",		IGNORE_CASE) ||	response.StartsWith("RFC822 ",		IGNORE_CASE) ||	response.StartsWith("RFC822.TEXT ",	IGNORE_CASE) ) {//// See if there is a length present//      int	pos = response.PosOf(' ');      if ( pos >= 0 ) response.CutBeg(pos+1);      response.Trim();      if ( response.StartsWith('{') ) {	 char	*lenp = response;	 char	*cp = ++lenp;	 while ( *cp != '}' ) cp++;	 *cp = 0;          // Temporary	 int	len = atoi(lenp);//// Allocate buffer of specified length//	 *output = new char[len+1];	 **output = 0;//// Read until buffer is filled//	 int	readlen = 0;         char *output_p = *output;	 while ( readlen < len && GetLine(response) &&	         !response.StartsWith(tag) ) {	    int	space = len - readlen;            int response_size = response.size();	    if ( response_size >= space ) {	       strncpy(output_p, response, space);               output_p += space;	       *output_p = '\0';	       response.CutBeg(space);	       readlen = len;	    }	    else {	       strcpy(output_p, response);               output_p += response_size;	       strcpy(output_p, "\n");               output_p += 1;	       readlen += response_size + 2;	// CRLF was stripped	    }	 }//// There can also be FLAGS//	 response.Trim();	 if ( response.StartsWith("FLAGS ", IGNORE_CASE) ) {	    response.CutBeg(6);	    if ( response.EndsWith(')') ) response.CutEnd(1);	    *flags = new char[response.size()+1];	    **flags = 0;	    strcpy(*flags, response);	    response.Clear();	 }      } // End if length is known      //// If the length is not known, the length is whatever's left in the response//   line.//      else if ( !response.StartsWith("NIL") ) {	 if ( response.EndsWith(')') ) response.CutEnd(1);	 *output = new char[response.size()+1];	 **output = 0;	 strcpy(*output, response);	 response.Clear();      }   } // End if the command is recognized//// These commands can contain many sized literals//   else if ( response.StartsWith("BODY ",		IGNORE_CASE) ||	     response.StartsWith("BODYSTRUCTURE ",	IGNORE_CASE) ||	     response.StartsWith("ENVELOPE ",		IGNORE_CASE) ) {      int	pos = response.PosOf(' ');      response.CutBeg(pos+1);      response.Trim();//// Read lines until we get the tag//      StringC	buffer = response;      if ( !GetLine(response) ) return False;      while ( !response.StartsWith(tag) ) {//// Check for FLAGS//	 response.Trim();	 if ( response.StartsWith("FLAGS ", IGNORE_CASE) ) {	    response.CutBeg(6);	    if ( response.EndsWith(')') ) response.CutEnd(1);	    *flags = new char[response.size()+1];	    **flags = 0;	    strcpy(*flags, response);	    response.Clear();	 }	 else	    buffer += response;	 if ( !GetLine(response) ) return False;      } // End for each line up to tag      *output = new char[buffer.size()+1];      **output = 0;      strcpy(*output, buffer);   } // End if BODYSTRUCTURE or ENVELOPE command//// Check for flags only//   else if ( response.StartsWith("FLAGS ", IGNORE_CASE) ) {      response.CutBeg(6);      if ( response.EndsWith(')') ) response.CutEnd(1);      *flags = new char[response.size()+1];      **flags = 0;      strcpy(*flags, response);      response.Clear();   }   else {      Unexpected(response);   }//// Continue reading until we get the tag//   while ( !response.StartsWith(tag) ) {      if ( !GetLine(response) ||           response.StartsWith("NO ", IGNORE_CASE) ) return False;   }   response.CutBeg(tag.size());//// Restore the original folder, if any//   if ( saveFolderName.IsNull() && folderName != saveFolderName ) {      StringListC output;      if ( !Select(saveFolderName, output) ) return False;   }   return True;} // End Fetch/*------------------------------------------------------------------------ * Function to send FETCH command to get a sequence of 1 or more  * message headers. */BooleanImapServerC::FetchHdrs(int msgnum, ImapFolderC *fld, int *bytes,		char **output, char **flags, StringC& response){   int pos;   *output = NULL;   *flags  = NULL;   response.Clear();//// First time through, build the FETCH command we will send.// Save the "tag" prefix in the folder object, so that after the// last message is fetched we can find the trailing tag.//   if ( fld->fetchNeeded ) {      fld->fetchNeeded = False;      GenTag(fld->fetchTag);      StringC	cmd(fld->fetchTag);      cmd += "FETCH ";      cmd += msgnum;      cmd += ":";      cmd += fld->msgCount;      cmd += " (FLAGS RFC822.SIZE";//// For max compatibility with function of other folder types, we want// all the headers. However, the tradeoff is performance. Decision: The// Message-ID and Received headers are least useful, and can take up a // lot of lines, so don't fetch them. Get everything else, though.//      //cmd += " RFC822.HEADER.LINES.NOT (MESSAGE-ID RECEIVED))";      cmd += " RFC822.HEADER)";//// Send the command and wait for the response//      if ( !PutLine(cmd) ) return False;   }   if ( !GetLine(response) ) return False;   StringC	expect("* ");   expect += msgnum;   expect += " FETCH ";   while ( !response.StartsWith(expect, IGNORE_CASE) &&      	   !response.StartsWith(fld->fetchTag) ) {      Unexpected(response);      if ( !GetLine(response) ) return False;      if ( response.StartsWith(fld->fetchTag) ) {	 response.CutBeg(fld->fetchTag.size());	 return False;      }   }// Got a response, set the data pending flag on the server object   dataPending = True;//// Parse the response//   if ( response.StartsWith(expect, IGNORE_CASE) )       response.CutBeg(expect.size());   else if ( response.StartsWith(fld->fetchTag) )       response.CutBeg(fld->fetchTag.size());    if ( response.StartsWith('(') ) response.CutBeg(1);   response.Trim();//// The first thing in the response line should be the flags//    if ( response.StartsWith("FLAGS ", IGNORE_CASE) ) {      response.CutBeg(6);      StringC flgs(response);      pos = flgs.PosOf(')');      if ( pos >=0 ) flgs.CutEnd(flgs.size()-pos-1);      *flags = new char[flgs.size()+1];      **flags = 0;      strcpy(*flags, flgs);      //      // Skip over the flags      //      pos = response.PosOf(')');      if ( pos >= 0 ) response.CutBeg(pos+1);      response.Trim();   } else {      Unexpected(response);      return False;   }//// Next should be the size of the message//   if ( response.StartsWith("RFC822.SIZE", IGNORE_CASE) ) {      pos = response.PosOf(' ');      if ( pos >= 0 ) response.CutBeg(pos+1);      response.Trim();      StringC msgSize(response);      pos = msgSize.PosOf(' ');      if ( pos >= 0 ) msgSize.CutEnd(msgSize.size()-pos-1);      msgSize.Trim();      *bytes = atoi(msgSize);      //      // Skip over the size info      //      pos = response.PosOf(' ');      if ( pos >= 0 ) response.CutBeg(pos+1);      response.Trim();   } else {      Unexpected(response);      return False;   }//// Next should be the header info, with length of headers enclosed// in curly braces. The headers will follow on subsequent lines.//   if ( response.StartsWith("RFC822.HEADER", IGNORE_CASE)) {      pos = response.PosOf(' ');      if ( pos >= 0 ) response.CutBeg(pos+1);      response.Trim();   } else {      Unexpected(response);      return False;   }//// See if there is a length present//   Boolean seenEnd = False;	// flag: closing parenthesis found   if ( response.StartsWith('{') ) {      char	*lenp = response;      char	*cp = ++lenp;      while ( *cp != '}' ) cp++;      *cp = 0;          // Temporary      int	len = atoi(lenp);//// Allocate buffer of specified length//      *output = new char[len+1];      **output = 0;//// Read until buffer is filled//      int	readlen = 0;      while ( readlen < len && GetLine(response) ) {	 //	 // This means that the header length was too big - seems	 // to happen sometimes...	 //         if (response.StartsWith(')') ) {	    // Got all the data, clear the data pending flag	    dataPending = False;	    seenEnd = True;	    break;	 }	 //	 // Shouldn't see these yet...	 //	 if (response.StartsWith('*')  ||	     response.StartsWith(fld->fetchTag) ) {		Unexpected(response);		return False;	 }         int	space = len - readlen;         if ( response.size() >= space ) {            strncat(*output, response, space);            (*output)[len] = 0;            response.CutBeg(space);            readlen = len;         }         else {            strcat(*output, response);            strcat(*output, "\n");            readlen += response.size() + 2;	// CRLF was stripped         }      }  } else {      Unexpected(response);      return False;  }      //// The last response should have ended with a close parenthesis, indicating// end of the FETCH data. If we haven't seen it yet, it should be on the// next line.//  if (!seenEnd) {    response.Trim();    if (!response.EndsWith(')')) {	GetLine(response);	if (!response.EndsWith(')')) {	  Unexpected(response);	  return False;	}    }    // Got it all, clear the data pending flag on the server object    dataPending = False;  }  return True;} // End FetchHdrs/*------------------------------------------------------------------------ * Function to flush trailing output from a FETCH command, after * processing one or more headers. */voidImapServerC::FetchFlush( StringC& tag ){//// If last message in the folder, continue reading until we get the tag//    StringC response;    while ( !response.StartsWith(tag) ) {      if (!GetLine(response)) return;    }    return;} // End FetchFlush/*------------------------------------------------------------------------ * Function to send STORE FLAGS command and wait for response. */Boolean

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -