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

📄 filefolderc.c

📁 linux下的E_MAIL客户端源码
💻 C
📖 第 1 页 / 共 2 页
字号:
/* *  $Id: FileFolderC.C,v 1.7 2000/08/07 11:05:16 evgeny Exp $ *   *  Copyright (c) 1994 HAL Computer Systems International, Ltd. *  *          HAL COMPUTER SYSTEMS INTERNATIONAL, LTD. *                  1315 Dell Avenue *                  Campbell, CA  95008 * * Author: Greg Hilton * Contributors: Tom Lang, Frank Bieser, and others * * This program is free software; you can redistribute it and/or * modify it under the terms of the GNU General Public License * as published by the Free Software Foundation; either version 2 * of the License, or (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the * GNU General Public License for more details. * * http://www.gnu.org/copyleft/gpl.html * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA  02111-1307, USA. */#include <config.h>#include "FileFolderC.h"#include "FileMisc.h"#include "FilePartMsgC.h"#include "IshAppC.h"#include "AppPrefC.h"#include "MainWinC.h"#include "SortMgrC.h"#include "UndelWinC.h"#include "MsgListC.h"#include "LoginWinC.h"#include <hgl/SysErr.h>#include <hgl/System.h>#include <hgl/VBoxC.h>#include <unistd.h>#include <stdlib.h>#include <fcntl.h>#include <utime.h>#include <signal.h>#include <errno.h>#include <sys/stat.h>// FIXME: more fs access types should be here#ifdef HAVE_STATVFS // SOLARIS || SVR4 || OSF1 || MIPS#  include <sys/statvfs.h>#  define FSTATFS(fd, bufp) fstatvfs(fd, bufp)#  define STATFS statvfs#else#  include <sys/vfs.h>#  define FSTATFS(fd, bufp) fstatfs(fd, bufp)#  define STATFS statfs#endif#ifdef HAVE___VAL_IN_F_FSID#  define GET_FS_ID(fsid) (fsid.__val[0])  #else#  define GET_FS_ID(fsid) (fsid)#endifextern int	debuglev;/*------------------------------------------------------------------------ * FileFolderC constructor */FileFolderC::FileFolderC(const char *n, FolderTypeT t, Boolean create): FolderC(n, t, create){   openLevel    = 0;   lockLevel    = 0;   lockFile     = name + ".lock";   fp           = NULL;   changedWhileSleeping = False;//// Get the date of the file//   if ( stat(name, &stats) != 0 ) {//// Create the file if necessary//      if ( errno == ENOENT && create ) {	 if ( debuglev > 0 ) cout <<"Creating folder: " <<name <<endl;	 if ( !MakeFile(name) ) return;	 stat(name, &stats);      }      else {	 StringC	errmsg = "Could not stat ";	 errmsg += name;	 errmsg += "\n" + SystemErrorMessage(errno);	 halApp->PopupMessage(errmsg);	 return;      }   }//// Make sure this is a file//   if ( !S_ISREG(stats.st_mode) && name != "/dev/null" ) {      StringC	errmsg = name;      errmsg += " is not a folder.";      halApp->PopupMessage(errmsg);      return;   }//// See if file is writable//   writable = (access(name, W_OK) == 0);   if ( !writable ) {      StringC	errmsg = "Folder \"";      errmsg += name;      errmsg += "\" is not writable and will be opened read-only";      halApp->PopupMessage(errmsg, XmDIALOG_WARNING);   }//// See if lock file can be created//   if ( !Lock(True) ) {      int	err = errno;      StringC	errmsg = "Folder \"";      errmsg += name;      errmsg += "\" cannot be locked and will be opened read-only.";      errmsg += "\n";      errmsg += SystemErrorMessage(err);      halApp->PopupMessage(errmsg, XmDIALOG_WARNING);   } // End if lock file not created   else {      Lock(False);   }   opened = True;} // End FileFolderC constructor/*------------------------------------------------------------------------ * FileFolderC destructor */FileFolderC::~FileFolderC(){   if ( lockLevel > 0 ) unlink(lockFile);   CloseFile(True/*force*/);   if ( delFiles ) unlink(name);}/*------------------------------------------------------------------------ * Method to create mail lock on folder */BooleanFileFolderC::Lock(Boolean val){   if ( !isInBox ) return True;   static SIG_PF oldhup  = (SIG_PF)SIG_DFL;   static SIG_PF oldint  = (SIG_PF)SIG_DFL;   static SIG_PF oldquit = (SIG_PF)SIG_DFL;   static SIG_PF oldterm = (SIG_PF)SIG_DFL;   static SIG_PF oldtstp = (SIG_PF)SIG_DFL;   if ( !writable ) return True;   if ( val ) {	 lockLevel++;	 if ( lockLevel > 1 && access(lockFile, F_OK) == 0 ) return True;	    // Already locked   } else {	 if ( lockLevel < 1 ) return True;	// Not locked	 lockLevel--;	 if ( lockLevel > 0 ) return True;	// Not ready to unlock   }   if ( val ) {      oldhup  = signal(SIGHUP,  (SIG_PF)SIG_IGN);      oldint  = signal(SIGINT,  (SIG_PF)SIG_IGN);      oldquit = signal(SIGQUIT, (SIG_PF)SIG_IGN);      oldterm = signal(SIGTERM, (SIG_PF)SIG_IGN);      oldtstp = signal(SIGTSTP, (SIG_PF)SIG_IGN);      Boolean	success = CreateLock(lockFile);      if ( !success ) {	 lockLevel--;	 signal(SIGHUP,  oldhup);	 signal(SIGINT,  oldint);	 signal(SIGQUIT, oldquit);	 signal(SIGTERM, oldterm);	 signal(SIGTSTP, oldtstp);      }      return success;   }   else {      unlink(lockFile);      signal(SIGHUP,  oldhup);      signal(SIGINT,  oldint);      signal(SIGQUIT, oldquit);      signal(SIGTERM, oldterm);      signal(SIGTSTP, oldtstp);   }   return True;} // End Lock/*------------------------------------------------------------------------ * Method to create a lock file */BooleanFileFolderC::CreateLock(const char *file){   Boolean	retVal = True;//// Loop while file exists.  Try for 60 seconds before giving up.//   int		count = 60;   struct stat	statbuf;   while ( (stat(file, &statbuf) >= 0) && (count > 0) ) {      sleep(1);      count--;   }//// If we timed out, this is probably an old lock file, so just use it.//   if ( count > 0 ) {      int	fd = open(file, O_WRONLY|O_CREAT|O_TRUNC, 0);      if ( fd < 0 ) {	 retVal = False;      }      else	 close(fd);   }   return retVal;} // End CreateLock/*--------------------------------------------------------------- *  Method to open file */BooleanFileFolderC::OpenFile(){   openLevel++;   if ( fp ) return True;   char	*mode;   if ( writable ) {      if ( access(name, F_OK) != 0 && errno == ENOENT ) mode = "w+";      else						mode = "r+";   }   else      mode = "r";//// Open the file//   if ( debuglev > 1 ) cout <<"Opening folder file " <<name <<endl;   fp = fopen(name, mode);   if ( !fp ) {      StringC   errmsg("Could not open file: ");      errmsg += name;      errmsg += "\n" + SystemErrorMessage(errno);      halApp->PopupMessage(errmsg);      openLevel = 0;      return False;   }   return True;}/*--------------------------------------------------------------- *  Method to close file */voidFileFolderC::CloseFile(Boolean force){   if ( !fp ) return;   if ( force ) openLevel = 0;   else		openLevel--;   if ( openLevel > 0 ) return;   if ( openLevel < 0 ) openLevel = 0;   if ( debuglev > 1 ) cout <<"Closing folder file " <<name <<endl;   fclose(fp);   fp = NULL;//// Get new stats.  This can cause loss of new mail!!//   // An unconditional update of the stats can lose new mail in the   // following scenario:   // 1. stats updated   // 2. new mail arrives   // 3. folder action results in close, stats updated *without*    //		checking for new mail   // 4. mailcheck now will fail to see the new mail   //stat(name, &stats);} // End CloseFile/*------------------------------------------------------------------------ * Method to check for new mail */BooleanFileFolderC::NewMail(){   if ( debuglev > 1 )       cout <<"Checking for new mail in folder " <<name <<endl;   Boolean	newMail = False;//// If the external mods flag is set and we're not sleeping, this is the first//    check since we woke up.  We need to reread the folder.//   if ( changedWhileSleeping && !ishApp->sleeping ) {      if ( debuglev > 1 )	 cout <<"Incorporating changes made while asleep." <<endl;      Rescan();      newMail = HasNewMessages();      if ( newMail && !ishApp->exiting ) UpdateIcon();      changedWhileSleeping = False;      return newMail;   }//// If there is a POP server specified, run popclient to suck over new mail//   if ( isInBox && ishApp->appPrefs->usingPop ) {      StringC	cmd   = ishApp->appPrefs->popclientCmd;      Boolean	doPop = True;      if ( cmd.Contains("%user") || cmd.Contains("%pass") ) {	 StringC	user, pass;	 if ( GetLogin(ishApp->appPrefs->popServer, user, pass) ) {	    cmd.Replace("%user", user);	    cmd.Replace("%pass", pass);	 }	 else {	    doPop = False;	 }      }      if ( doPop ) {	 cmd += ' ';	 cmd += ishApp->appPrefs->popServer;	 StringC	msg("Checking for mail on POP server ");	 msg += ishApp->appPrefs->popServer;	 msg += "...";	 ishApp->Broadcast(msg);	 System(cmd);	 ishApp->Broadcast("");      }   } // End if using pop//// Open, read the last byte and close the file so that the stat() call//    works over NFS.//   int	fd = open(name, O_RDWR);   if ( fd >= 0 ) {      lseek(fd, 1, SEEK_END);      char	buf;      read(fd, &buf, 1);      close(fd);   }//// Get the stats of the mail file//   struct stat	newStats;   if ( stat(name, &newStats) != 0 ) {      int	err = errno;      if ( ishApp->sleeping )	 changedWhileSleeping = True;      else if ( err == ENOENT && stats.st_size > 0 ) {//// If the file is gone but was there before, this is a problem.//	 StringC	errmsg = "Mail folder ";	 errmsg += name;	 errmsg += " has disappeared.\n";	 errmsg += "The last time we checked, it had a size of ";	 errmsg += (int)stats.st_size;	 errmsg += " bytes.";	 halApp->PopupMessage(errmsg, XmDIALOG_WARNING);	 Lock(True);	 Reset();	 MakeFile(name);	 stat(name, &stats);	 Lock(False);      } // End if file was there before      else if ( err != ENOENT ) {	 StringC	errmsg = "Mail folder ";	 errmsg += name;	 errmsg += " could not be checked:\n";	 errmsg += SystemErrorMessage(err);	 halApp->PopupMessage(errmsg, XmDIALOG_ERROR);      }      else if ( debuglev > 1 )	 cout <<"Folder not present" <<endl;      return False;   } // End if folder can't be stat'd   if ( debuglev > 1 )      cout <<"Folder is " <<newStats.st_size <<" bytes at time "      			  <<newStats.st_mtime <<endl;//// Check file times//   if ( newStats.st_mtime == stats.st_mtime &&	newStats.st_size  == stats.st_size ) {      if ( debuglev > 1 ) cout <<"No change." <<endl;      return False;   }//// Something changed.  Let's find out what...//   if ( newStats.st_size < stats.st_size ) { // File shrunk!      if ( ishApp->sleeping )	 changedWhileSleeping = True;      else {	 StringC	errmsg = "Mail folder ";	 errmsg += name;	 errmsg += " has shrunk from ";	 errmsg += (int)stats.st_size;	 errmsg += " bytes to ";	 errmsg += (int)newStats.st_size;	 errmsg += " bytes.";	 halApp->PopupMessage(errmsg, XmDIALOG_WARNING);	 Rescan();	 newMail = HasNewMessages();	 if ( newMail && !ishApp->exiting ) UpdateIcon();	 stats = newStats;      } // End if not sleeping      return newMail;   } // End if mail file shrunk   if ( debuglev > 1 ) cout <<"Folder changed." <<endl;   stats = newStats;   if ( ishApp->sleeping ) {      changedWhileSleeping = True;      return True;   }

⌨️ 快捷键说明

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