diff --git a/.gitignore b/.gitignore index 3c4efe2..2c8a90d 100644 --- a/.gitignore +++ b/.gitignore @@ -13,12 +13,12 @@ # Build results [Dd]ebug/ [Dd]ebugPublic/ -[Rr]elease/ -[Rr]eleases/ +#[Rr]elease/ +#[Rr]eleases/ x64/ x86/ bld/ -[Bb]in/ +#[Bb]in/ [Oo]bj/ [Ll]og/ diff --git a/EventFinder/EventFinder.csproj b/EventFinder/EventFinder.csproj index c33b43a..10037a7 100644 --- a/EventFinder/EventFinder.csproj +++ b/EventFinder/EventFinder.csproj @@ -14,6 +14,9 @@ 512 true true + false + + publish\ true Disk @@ -26,11 +29,8 @@ true 0 1.0.0.%2a - false false true - - AnyCPU @@ -71,7 +71,9 @@ - + + Form + Form1.cs diff --git a/EventFinder/Form1.Designer.cs b/EventFinder/Form1.Designer.cs index 06db3a1..0eb844a 100644 --- a/EventFinder/Form1.Designer.cs +++ b/EventFinder/Form1.Designer.cs @@ -125,7 +125,7 @@ private void InitializeComponent() this.Controls.Add(this.EventRangeBox); this.Controls.Add(this.Status); this.Name = "FindEvents"; - this.Text = "FindEvents"; + this.Text = "EventFinder 2.0"; this.EventRangeBox.ResumeLayout(false); this.EventRangeBox.PerformLayout(); this.Status.ResumeLayout(false); diff --git a/EventFinder/Form1.cs b/EventFinder/Form1.cs index b20f3b3..8ed6f0a 100644 --- a/EventFinder/Form1.cs +++ b/EventFinder/Form1.cs @@ -6,7 +6,7 @@ using System.Linq; using System.Text; using System.Threading.Tasks; -using System.Diagnostics.Eventing.Reader; // I think this will be needed? +using System.Diagnostics.Eventing.Reader; using System.Diagnostics; using System.Xml; using System.Xml.Linq; @@ -14,37 +14,7 @@ using System.Windows.Forms; using System.IO; using CsvHelper; - -public class Record -{ - public string Message { get; set; } - public string SystemTime { get; set; } - public string Id { get; set; } - public string Version { get; set; } - public string Qualifiers { get; set; } - public string Level { get; set; } - public string Task { get; set; } - public string Opcode { get; set; } - public string Keywords { get; set; } - public string RecordId { get; set; } - public string ProviderName { get; set; } - public string ProviderID { get; set; } - public string LogName { get; set; } - public string ProcessId { get; set; } - public string ThreadId { get; set; } - public string MachineName { get; set; } - public string UserID { get; set; } - public string TimeCreated { get; set; } - public string ActivityId { get; set; } - public string RelatedActivityId { get; set; } - public string Hashcode { get; set; } - public string MatchedQueryIds { get; set; } - public string LevelDisplayName { get; set; } - public string OpcodeDisplayName { get; set; } - public string TaskDisplayName { get; set; } - -} - +using System.Security.Principal; namespace EventFinder { @@ -54,128 +24,162 @@ public FindEvents() { InitializeComponent(); - - - EventLogSession session = new EventLogSession(); - var providers = session.GetProviderNames().ToList(); - Regex rgx = new Regex(@"^Security$"); - bool AdminFlag = false; - - foreach (string provider in providers) + // Check if the User is running as Administrator. Display appropriate text. + bool isElevated; + using (WindowsIdentity identity = WindowsIdentity.GetCurrent()) { - if (rgx.IsMatch(provider)) - { - AdminFlag = true; - } + WindowsPrincipal principal = new WindowsPrincipal(identity); + isElevated = principal.IsInRole(WindowsBuiltInRole.Administrator); } - if (AdminFlag) + if (isElevated) { - StatusOutput.Text = "Security log found!\nYou are likely administrator"; + StatusOutput.Text = "Running as Administrator.\nRestricted logs will be enumerated."; StatusOutput.ForeColor = System.Drawing.Color.Green; } else { - StatusOutput.Text = "Unable to read Security log.\nAre you administrator?"; + StatusOutput.Text = "Not running as Administrator!\nYou will not be able to read Security, etc."; StatusOutput.ForeColor = System.Drawing.Color.Red; } } + // Get a start time for our filter private void StartButton_Click(object sender, EventArgs e) { string CurrentTime = DateTime.Now.ToString("MM/dd/yyyy HH:mm:ss"); StartInput.Text = CurrentTime; } + // Get an end time for our filter private void EndButton_Click(object sender, EventArgs e) { string CurrentTime = DateTime.Now.ToString("MM/dd/yyyy HH:mm:ss"); EndInput.Text = CurrentTime; } + // Our Find Events button, this is where the magic happens private void FindEventsButton_Click(object sender, EventArgs e) { FindEventsButton.Enabled = false; + if (StartInput.Text == "" || EndInput.Text == "") // Check to make sure times are populated + { + StatusOutput.Text = "Missing Start or End Time!"; + StatusOutput.ForeColor = System.Drawing.Color.Red; + } else if (!DateTime.TryParse(StartInput.Text, out DateTime temp)) // And that the start time is valid + { + StatusOutput.Text = "Invalid Start Time"; + StatusOutput.ForeColor = System.Drawing.Color.Red; + } else if (!DateTime.TryParse(EndInput.Text, out DateTime temp2)) // And that the end time is valid + { + StatusOutput.Text = "Invalid End Time"; + StatusOutput.ForeColor = System.Drawing.Color.Red; + } else // If everything is valid, run! + { - - - // Variables we will need - DateTime StartTime = DateTime.ParseExact(StartInput.Text, "MM/dd/yyyy HH:mm:ss", null); - DateTime EndTime = DateTime.ParseExact(EndInput.Text, "MM/dd/yyyy HH:mm:ss", null); - string RunTime = DateTime.Now.ToString("yyyyMMdd_HHmmss"); - string DesktopPath = Environment.GetFolderPath(Environment.SpecialFolder.Desktop); - EventLogSession Session = new EventLogSession(); - var Providers = Session.GetProviderNames().ToList(); - - var query = string.Format(@"*[System[TimeCreated[@SystemTime >= '{0}']]] and *[System[TimeCreated[@SystemTime <= '{1}']]]", StartTime.ToString("o"), EndTime.ToString("o")); - - List records = new List { }; + // Variables we will need + DateTime StartTime = DateTime.ParseExact(StartInput.Text, "MM/dd/yyyy HH:mm:ss", null); // Needed for filter query + DateTime EndTime = DateTime.ParseExact(EndInput.Text, "MM/dd/yyyy HH:mm:ss", null); // Needed for filter query + string DesktopPath = Environment.GetFolderPath(Environment.SpecialFolder.Desktop); // Needed for file name + string RunTime = DateTime.Now.ToString("yyyyMMdd_HHmmss"); // Needed for file name + EventLogSession Session = new EventLogSession(); + var Logs = Session.GetLogNames().ToList(); + var query = string.Format(@"*[System[TimeCreated[@SystemTime >= '{0}']]] and *[System[TimeCreated[@SystemTime <= '{1}']]]", StartTime.ToUniversalTime().ToString("o"), EndTime.ToUniversalTime().ToString("o")); + List records = new List { }; // Start a list for all those sweet sweet logs we're going to get - foreach (var Provider in Providers) - { - try + foreach (var Log in Logs) { - EventLogQuery eventlogQuery = new EventLogQuery(Provider, PathType.LogName, query); - EventLogReader eventlogReader = new EventLogReader(eventlogQuery); - - for (EventRecord eventRecord = eventlogReader.ReadEvent(); null != eventRecord; eventRecord = eventlogReader.ReadEvent()) + try { - // Get the SystemTime from the event record XML - var xml = XDocument.Parse(eventRecord.ToXml()); - XNamespace ns = xml.Root.GetDefaultNamespace(); - - // Collect ALL THE THINGS! - string Message = eventRecord.FormatDescription(); - string SystemTime = xml.Root.Element(ns + "System").Element(ns + "TimeCreated").Attribute("SystemTime").Value; - string Id = eventRecord.Id.ToString(); - string Version = eventRecord.Version.ToString(); - string Qualifiers = eventRecord.Qualifiers.ToString(); - string Level = eventRecord.Level.ToString(); - string Task = eventRecord.Task.ToString(); - string Opcode = eventRecord.Opcode.ToString(); - string Keywords = eventRecord.Keywords.ToString(); - string RecordId = eventRecord.RecordId.ToString(); - string ProviderName = eventRecord.ProviderName; - string ProviderID = eventRecord.ProviderId.ToString(); - string LogName = eventRecord.LogName; - string ProcessId = eventRecord.ProcessId.ToString(); - string ThreadId = eventRecord.ThreadId.ToString(); - string MachineName = eventRecord.MachineName; - string UserID = eventRecord.UserId?.ToString(); - string TimeCreated = eventRecord.TimeCreated.ToString(); - string ActivityId = eventRecord.ActivityId.ToString(); - string RelatedActivityId = eventRecord.RelatedActivityId.ToString(); - string Hashcode = eventRecord.GetHashCode().ToString(); - string LevelDisplayName = eventRecord.LevelDisplayName; - string OpcodeDisplayName = eventRecord.OpcodeDisplayName; - string TaskDisplayName = eventRecord.TaskDisplayName; - - // Add them to the record. The things equal the things. - records.Add(new Record() { Message = Message, SystemTime = SystemTime, Id = Id, Version = Version, Qualifiers = Qualifiers, Level = Level, Task = Task, Opcode = Opcode, Keywords = Keywords, RecordId = RecordId, ProviderName = ProviderName, ProviderID = ProviderID, LogName = LogName, ProcessId = ProcessId, ThreadId = ThreadId, MachineName = MachineName, UserID = UserID, TimeCreated = TimeCreated, ActivityId = ActivityId, RelatedActivityId = RelatedActivityId, Hashcode = Hashcode, LevelDisplayName = LevelDisplayName, OpcodeDisplayName = OpcodeDisplayName, TaskDisplayName = TaskDisplayName }); + EventLogQuery eventlogQuery = new EventLogQuery(Log, PathType.LogName, query); + EventLogReader eventlogReader = new EventLogReader(eventlogQuery); + + for (EventRecord eventRecord = eventlogReader.ReadEvent(); null != eventRecord; eventRecord = eventlogReader.ReadEvent()) + { + // Get the SystemTime from the event record XML + var xml = XDocument.Parse(eventRecord.ToXml()); + XNamespace ns = xml.Root.GetDefaultNamespace(); + + // Collect ALL THE THINGS! + string Message = eventRecord.FormatDescription(); + string SystemTime = xml.Root.Element(ns + "System").Element(ns + "TimeCreated").Attribute("SystemTime").Value; + string Id = eventRecord.Id.ToString(); + string Version = eventRecord.Version.ToString(); + string Qualifiers = eventRecord.Qualifiers.ToString(); + string Level = eventRecord.Level.ToString(); + string Task = eventRecord.Task.ToString(); + string Opcode = eventRecord.Opcode.ToString(); + string Keywords = eventRecord.Keywords.ToString(); + string RecordId = eventRecord.RecordId.ToString(); + string ProviderName = eventRecord.ProviderName; + string ProviderID = eventRecord.ProviderId.ToString(); + string LogName = eventRecord.LogName; + string ProcessId = eventRecord.ProcessId.ToString(); + string ThreadId = eventRecord.ThreadId.ToString(); + string MachineName = eventRecord.MachineName; + string UserID = eventRecord.UserId?.ToString(); + string TimeCreated = eventRecord.TimeCreated.ToString(); + string ActivityId = eventRecord.ActivityId.ToString(); + string RelatedActivityId = eventRecord.RelatedActivityId.ToString(); + string Hashcode = eventRecord.GetHashCode().ToString(); + string LevelDisplayName = eventRecord.LevelDisplayName; + string OpcodeDisplayName = eventRecord.OpcodeDisplayName; + string TaskDisplayName = eventRecord.TaskDisplayName; + + // Add them to the record. The things equal the things. + records.Add(new Record() { Message = Message, SystemTime = SystemTime, Id = Id, Version = Version, Qualifiers = Qualifiers, Level = Level, Task = Task, Opcode = Opcode, Keywords = Keywords, RecordId = RecordId, ProviderName = ProviderName, ProviderID = ProviderID, LogName = LogName, ProcessId = ProcessId, ThreadId = ThreadId, MachineName = MachineName, UserID = UserID, TimeCreated = TimeCreated, ActivityId = ActivityId, RelatedActivityId = RelatedActivityId, Hashcode = Hashcode, LevelDisplayName = LevelDisplayName, OpcodeDisplayName = OpcodeDisplayName, TaskDisplayName = TaskDisplayName }); + } + } + catch (UnauthorizedAccessException) + { + // If you are running as admin, you will get unauthorized for some logs. Hey, I warned you! Nothing to do here. } - } catch (EventLogNotFoundException) - { - // No events found - Nothing to be done - } catch (EventLogException) - { - // Error Reading Provider - Nothing to be done - } - - - } - records.OrderBy(x => x.SystemTime); + } - using (var writer = new StreamWriter(DesktopPath + "\\Logs_Runtime_" + RunTime + ".csv", append: true)) - using (var csv = new CsvWriter(writer)) - { - csv.Configuration.ShouldQuote = (field, context) => true; - csv.WriteRecords(records); + records.OrderBy(x => x.SystemTime); // Sort our records in chronological order + // and write them to a CSV + using (var writer = new StreamWriter(DesktopPath + "\\Logs_Runtime_" + RunTime + ".csv", append: true)) + using (var csv = new CsvWriter(writer)) + { + csv.Configuration.ShouldQuote = (field, context) => true; + csv.WriteRecords(records); + } + StatusOutput.Text = "Run Complete"; + StatusOutput.ForeColor = System.Drawing.Color.Blue; } - FindEventsButton.Enabled = true; } } } + +public class Record // All the things that will be used in our CSV later. +{ + public string Message { get; set; } + public string SystemTime { get; set; } + public string Id { get; set; } + public string Version { get; set; } + public string Qualifiers { get; set; } + public string Level { get; set; } + public string Task { get; set; } + public string Opcode { get; set; } + public string Keywords { get; set; } + public string RecordId { get; set; } + public string ProviderName { get; set; } + public string ProviderID { get; set; } + public string LogName { get; set; } + public string ProcessId { get; set; } + public string ThreadId { get; set; } + public string MachineName { get; set; } + public string UserID { get; set; } + public string TimeCreated { get; set; } + public string ActivityId { get; set; } + public string RelatedActivityId { get; set; } + public string Hashcode { get; set; } + public string MatchedQueryIds { get; set; } + public string LevelDisplayName { get; set; } + public string OpcodeDisplayName { get; set; } + public string TaskDisplayName { get; set; } +} \ No newline at end of file diff --git a/EventFinder/bin/Release/EventFinder.exe b/EventFinder/bin/Release/EventFinder.exe new file mode 100644 index 0000000..e253d2f Binary files /dev/null and b/EventFinder/bin/Release/EventFinder.exe differ diff --git a/EventFinder/bin/Release/EventFinder.exe.config b/EventFinder/bin/Release/EventFinder.exe.config new file mode 100644 index 0000000..8cd6e46 --- /dev/null +++ b/EventFinder/bin/Release/EventFinder.exe.config @@ -0,0 +1,14 @@ + + + + + + + + + + + + + + \ No newline at end of file diff --git a/README.md b/README.md new file mode 100644 index 0000000..68f4821 --- /dev/null +++ b/README.md @@ -0,0 +1,2 @@ +# EventFinder2 +Finds event logs between two time points. Useful for helpdesk/support/malware analysis.