/// <summary> /// Creates undelivered warning for user and places it to relay folder. /// </summary> /// <param name="relayInfo">Relay info</param> /// <param name="error">SMTP returned error text.</param> /// <param name="file">Messsage file.</param> private void MakeUndeliveredWarning(RelayInfo relayInfo,string error,Stream file) { try { // If sender isn't specified, we can't send warning to sender. // Just skip warning sending. if(relayInfo.From.Length == 0){ return; } file.Position = relayInfo.MessageStartPos; // Make new message MimeConstructor mime = new MimeConstructor(); mime.From = "postmaster"; mime.To = new string[]{relayInfo.From}; mime.Subject = "Undelivered mail warning"; mime.Attachments.Add(new Attachment("data.eml",file)); string bodyTxt = Relay.UndelWarningTemplate; bodyTxt = bodyTxt.Replace("<#RECEPTIENT>",relayInfo.To); bodyTxt = bodyTxt.Replace("<#ERROR>",error); bodyTxt = bodyTxt.Replace("<#UNDELIVERED_HOURS>",relayInfo.DeviveringForHours.ToString()); mime.Body = bodyTxt; byte[] data = System.Text.Encoding.Default.GetBytes(mime.ConstructMime()); using(MemoryStream strm = new MemoryStream(data)){ m_pServer.ProcessAndStoreMessage("",new string[]{relayInfo.From},strm); } // byte[] data = System.Text.Encoding.Default.GetBytes(mime.ConstructMime()); // MailStore.StoreMessage("",new MemoryStream(data),relayInfo.From,"",true); } catch(Exception x) { Error.DumpError(x,new System.Diagnostics.StackTrace()); } }
/// <summary> /// Filters message. /// </summary> /// <param name="messageStream">Message stream which to filter.</param> /// <param name="filteredStream">Filtered stream.</param> /// <param name="sender">Senders email address.</param> /// <param name="recipients">Recipients email addresses.</param> /// <param name="api">Access to server API.</param> public FilterResult Filter(MemoryStream messageStream,out MemoryStream filteredStream,string sender,string[] recipients,ServerAPI api) { messageStream.Position = 0; filteredStream = messageStream; // we don't change message content, just return same stream //--- Load data ----------------------- DataSet ds = new DataSet(); DataTable dt = ds.Tables.Add("KewWords"); dt.Columns.Add("Cost",typeof(int)); dt.Columns.Add("KeyWord"); dt = ds.Tables.Add("ContentMd5"); dt.Columns.Add("Description"); dt.Columns.Add("EntryMd5Value"); ds.ReadXml(Path.GetDirectoryName(Assembly.GetExecutingAssembly().Location) + "\\lsSpam_db.xml"); //--- Do mime parts data md5 hash compare ---------------- ArrayList entries = new ArrayList(); MimeParser parser = new MimeParser(messageStream.ToArray()); GetEntries(parser.MimeEntries,entries); System.Security.Cryptography.MD5 md5 = System.Security.Cryptography.MD5.Create(); foreach(MimeEntry ent in entries){ if(ent.Data != null){ string md5Hash = Convert.ToBase64String(md5.ComputeHash(ent.Data)); foreach(DataRow dr in ds.Tables["ContentMd5"].Rows){ // Message contains blocked content(attachment,...) if(dr["EntryMd5Value"].ToString() == md5Hash){ WriteFilterLog(DateTime.Now.ToString() + " From:" + sender + " Subject:\"" + parser.Subject + "\" Contained blocked content\r\n"); return FilterResult.DontStore; } } } } byte[] topLines = new byte[2000]; if(messageStream.Length < 2000){ topLines = new byte[messageStream.Length]; } messageStream.Read(topLines,0,topLines.Length); string lines = System.Text.Encoding.ASCII.GetString(topLines).ToLower(); //--- Try spam keywords ----------- int totalCost = 0; string keyWords = ""; DataView dv = ds.Tables["KewWords"].DefaultView; dv.Sort = "Cost DESC"; foreach(DataRowView drV in dv){ if(lines.IndexOf(drV.Row["KeyWord"].ToString().ToLower()) > -1){ totalCost += Convert.ToInt32(drV.Row["Cost"]); keyWords += drV.Row["KeyWord"].ToString() + " cost:" + drV.Row["Cost"].ToString() + " "; // Check that total cost isn't exceeded if(totalCost > 99){ //--- Send blocked note to sender MimeConstructor m = new MimeConstructor(); m.Body = "Message was blocked by server and considered as SPAM !!!\n\nCaused by keywords: " + keyWords + "\n\nMaximum total cost is 100 !"; m.From = "postmaster"; m.To = new string[]{sender}; m.Attachments.Add(new Attachment("data.eml",messageStream.ToArray())); using(MemoryStream msg = new MemoryStream(System.Text.Encoding.ASCII.GetBytes(m.ConstructMime()))){ api.StoreMessage("","",msg,sender,"",true,DateTime.Now,0); } WriteFilterLog(DateTime.Now.ToString() + " From:" + sender + " Blocked KeyWords: " + keyWords + "\r\n"); return FilterResult.DontStore; } } } //--------------------------------- return FilterResult.Store; }