[quoted text, click to view] > Nice. You now have me thinking of extending this in two ways.
> Reading other logs (security and IIS http), and adding address
> to a "block pest" IPsec filter.
I did the IPSec stuff last week due to a new string of attacks...
using System;
using System.Collections;
using System.Collections.Specialized;
using System.ComponentModel;
using System.Data;
using System.Diagnostics;
using System.Reflection;
using System.Threading;
using System.Xml;
using System.DirectoryServices;
using System.IO;
using System.Text;
using IISLog;
namespace IISBlock
{
class Class1
{
[STAThread]
static void Main(string[] args)
{
Console.WriteLine("Starting");
FTPBlock ftpb=new FTPBlock("MyWebServer","MyAdmin","MyPassword");
ftpb.GetBlock(DateTime.Now,10);
ftpb.Block();
IPSecBlock ipsb=new IPSecBlock("MyIPSecRule");
ipsb.GetBlock(DateTime.Now,10);
ipsb.Block();
Console.WriteLine("Finished");
}
}
public class IPSecBlock
{
private string FilterList;
public ArrayList Blocked=new ArrayList();
public ArrayList Removed=new ArrayList();
public ArrayList Errors=new ArrayList();
public IPSecBlock(string FilterList)
{
this.FilterList=FilterList;
}
public void Block()
{
if(Blocked.Count==0)
return;
for(int i=0;i<Blocked.Count;i++)
AddFilter(FilterList,(string)Blocked[i]);
}
private void AddFilter(string FilterList,string ip)
{
ProcessStartInfo pi = new ProcessStartInfo("netsh");
pi.Arguments = "ipsec static add filter filterlist="+FilterList+"
\"description="+ip+" on
"+DateTime.Now.ToShortDateString()+"\" srcaddr="+ip+" dstaddr=Me
protocol=any mirrored=yes";
pi.WindowStyle = ProcessWindowStyle.Hidden;
Console.WriteLine("netsh "+pi.Arguments);
System.Diagnostics.Process.Start(pi);
}
public void GetBlock(DateTime dt,int AttemptsBeforeKill)
{
SortedList ht=new SortedList();
EventLog el=new EventLog("Security");
for(int i=0;i<el.Entries.Count;i++)
{
EventLogEntry en=el.Entries[i];
if(en.EventID==529 && en.TimeGenerated>=dt.AddMinutes(-15))
{
int g=en.Message.IndexOf("Source Network Address:");
if(g!=-1)
{
string ip=en.Message.Substring(g);
ip=ip.Replace("Source Network Address:","");
g=ip.IndexOf("\n");
if(g!=-1)
ip=ip.Substring(0,g);
g=ip.IndexOf("\r");
if(g!=-1)
ip=ip.Substring(0,g);
ip=ip.Trim();
if(ip.Length>0 && ip.IndexOf("10.")!=0) // filter out my internal
addresses
{
if(ht.ContainsKey(ip))
ht[ip]=((int)ht[ip])+1;
else
ht.Add(ip,(int)1);
}
}
}
}
for(int i=0;i<ht.Count;i++)
{
string ip=(string)ht.GetKey(i);
if((int)ht[ip]>AttemptsBeforeKill)
Blocked.Add(ip);
}
}
}
public class FTPBlock
{
private string ServerName;
private string ServerUserName;
private string ServerPassword;
public ArrayList Blocked=new ArrayList();
public ArrayList Removed=new ArrayList();
public ArrayList Errors=new ArrayList();
public FTPBlock(string ServerName,string ServerUserName,string
ServerPassword)
{
this.ServerName=ServerName;
this.ServerUserName=ServerUserName;
this.ServerPassword=ServerPassword;
}
public void GetBlock(DateTime dt,int AttemptsBeforeKill)
{
SortedList ht=new SortedList();
string
FileName="ex"+(dt.Year-2000).ToString("00")+dt.Month.ToString("00")+dt.Day.ToString("00")+".log";
DirectoryEntry root = new
DirectoryEntry("IIS://"+ServerName+"/MSFTPSVC",ServerUserName,ServerPassword);
foreach (DirectoryEntry IIS in root.Children)
{
if (IIS.SchemaClassName == "IIsFtpServer")
{
string LogFilePath = System.IO.Path.Combine(
IIS.Properties["LogFileDirectory"].Value.ToString(),
"MSFTPSVC"+IIS.Name);
string LogFileName=LogFilePath+"\\"+FileName;
if(File.Exists(LogFileName))
{
try
{
IISLog.LogScriptingClass l=new IISLog.LogScriptingClass();
l.OpenLogFile(LogFileName,IOMode.ForReading,"MSFTPSVC",1,"0");
while(!l.AtEndOfLog())
{
l.ReadLogRecord();
if(l.ProtocolStatus!=null)
{
if(l.ProtocolStatus.ToString()=="530")
{
string ip=l.ClientIP.ToString();
if(ht.ContainsKey(ip))
ht[ip]=((int)ht[ip])+1;
else
ht.Add(ip,(int)1);
}
}
}
l.CloseLogFiles(IOMode.AllOpenFiles);
}
catch(Exception ex)
{
Errors.Add(ex.Message.ToString());
}
/*
try
{
FileStream fs=new
FileStream(LogFileName,FileMode.Open,FileAccess.Read,FileShare.ReadWrite);
StreamReader sr=new
StreamReader(fs);
string s;
while((s=sr.ReadLine())!=null)
{
if(s.IndexOf("PASS - 530")!=-1)
{
string[] fields=s.Split(' ');
if(fields.Length>1)
{
string ip=fields[1].Trim();
if(ht.ContainsKey(ip))
ht[ip]=((int)ht[ip])+1;
else
ht.Add(ip,(int)1);
}
}
}
sr.Close();
fs.Close();
}
catch(Exception ex)
{
Errors.Add("Can't
open "+LogFileName"+ex.Message.ToString());
}
*/
}
IIS.Close();
//IIS.Dispose();
}
}
root.Close();
//root.Dispose();
for(int i=0;i<ht.Count;i++)
{
string ip=(string)ht.GetKey(i);
if((int)ht[ip]>AttemptsBeforeKill)
Blocked.Add(ip);
}
}
public void Block()
{
bool bDidOne=false;
if(Blocked.Count==0)
return;
DirectoryEntry root = new
DirectoryEntry("IIS://"+ServerName+"/MSFTPSVC",ServerUserName,ServerPassword);
foreach (DirectoryEntry site in root.Children)
{
if (site.SchemaClassName == "IIsFtpServer")
{
DirectoryEntry IIS = new
DirectoryEntry("IIS://"+ServerName+"/MSFTPSVC/"+site.Name+"/root",ServerUserName,ServerPassword);
Type typ = IIS.Properties["IPSecurity"][0].GetType();
object IPSecurity = IIS.Properties["IPSecurity"][0];
Array origIPDenyList = (Array) typ.InvokeMember("IPDeny",
BindingFlags.DeclaredOnly |
BindingFlags.Public | BindingFlags.NonPublic |
BindingFlags.Instance | BindingFlags.GetProperty,
null, IPSecurity, null);
Array.Sort(origIPDenyList);
ArrayList ToAdd=new ArrayList();
for(int i=0;i<Blocked.Count;i++)
{
string block=Blocked[i]+", 255.255.255.255";
bool bAlreadyDone=false;
foreach(string s in origIPDenyList)
{
if(s==block)
bAlreadyDone=true;
}
if(bAlreadyDone==false)
ToAdd.Add(block);
}
if(ToAdd.Count>0)
{