Since File/Process Monitor falls short in terms of filtering and unnecessary duplication when logging, I want to recreate what that program does and log all Windows file operations live in realtime.
I want to record various attributes such as the time, process name, source path, destination path, operation, result, and detail, just like Process Monitor does.
How can I get C# to extract this information from the OS?
EDIT: As zett42 pointed out, the FileSystemWatcher
won't quite work as for example, file events created from processes themselves won't be intercepted. For instance, none of these transactions show up, even though I added the events: Changed
, Created
, Renamed
, and Deleted
to the FileSystemWatcher
and set the EnableRaisingEvents
flag to true.
EDIT 2: Using SimonMourier's suggestion of the Microsoft.Diagnostics.Tracing.TraceEvent nuget package, I managed to knock up the code below.
This section is put into a background worker:
Console.CancelKeyPress += (sender, e) => session.Stop();
session.EnableKernelProvider(KernelTraceEventParser.Keywords.All);
session.Source.Kernel.FileIOWrite += Kernel_FileIOWrite;
session.Source.Process();
And then the FileIOWrite event created runs the following when called (automatically):
private void Kernel_FileIOWrite(Microsoft.Diagnostics.Tracing.Parsers.Kernel.FileIOReadWriteTraceData obj)
{
string filename = obj.FileName;
string processpath = "";
if (obj.ProcessID == 0) processpath = "System Idle Process";
else if (obj.ProcessID == 4) processpath = "System";
else
{
try { processpath = "ID: " + obj.ProcessID + ": "+ Process.GetProcessById(obj.ProcessID).MainModule.FileName; }
catch { processpath = "error ID: "+ obj.ProcessID; }
}
richTextBox1.AppendText(filename + " ............."+ processpath +"\n");
}
Unfortunately, FileIOReadWriteTraceData.FileName
is not picking up things Procmon picks up such as (for example), very common Chrome stuff such as writing to C:\Users\Dan\AppData\Local\Google\Chrome\User Data\Default\Cookies-journal
or C:\Users\Dan\AppData\Local\Google\Chrome\User Data\Default\Current Session
Did you try to use WMI? The ManagementEventWatcher could provide all information you need, even though it's not that handy as the FileSytemWatcher. I'm not sure it will work and unfortunately cannot try it myself at the moment, but this is the point where I would start.
Take a look at the anwer of RRUZ in this thread, which does exactly what you want. You will just need to find out if WMI provides all required information.