Search code examples
c#c++windowsfile-iofilter-driver

File system filter driver for specific file types


I need to detect when either of two file types are accessed in any way across an entire windows file system.

As I understand it the only way to do this without causing serious slow downs for the operating system is to create a file system filter driver?

Essentially all I need to do is take a copy of any doc(x) files and pdf's that are opened. I decided on this approach as it was either that or use file monitors in C# which wouldn't be effective for an entire drive.

My question is two fold, is there an easier way and secondly how would I go about simply taking a copy of each doc(x)/pdf file as it's accessed?

The solution needs to be deployable with the package we're currently producing.

UPDATE

I'm going to benchmark the file system watcher, after discussing it with people here I think it's possible that it may be acceptable, my concern is the fact that I need to monitor the common user directories where downloads will occur( so "C:\Users\SomeUser*" as well as the outlook temporary folder.


Solution

  • You will need to create a file system watcher. Here is a code example that will watch for changes to docx files.

    using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.IO;
    using System.Security.Permissions;
    
    namespace filewatchtest
    {
        class Program
        {
            static void Main(string[] args)
            {
                Run();
            }
    
            [PermissionSet(SecurityAction.Demand, Name="FullTrust")]
            public static void Run()
            {
                string[] args = System.Environment.GetCommandLineArgs();
    
                // if directory not specified then end program
                if (args.Length != 2)
                {
                    Console.WriteLine("Usage: filewatchtest.exe directory");
                    return;
                }
    
                // create a new fileSystemWatcher and set its properties
                FileSystemWatcher watcher = new FileSystemWatcher();
                watcher.Path = args[1];
    
                // set the notify filters
                watcher.NotifyFilter = NotifyFilters.LastAccess | NotifyFilters.LastWrite | NotifyFilters.FileName | NotifyFilters.DirectoryName;
    
                // set the file extension filter
                watcher.Filter = "*.docx";
    
                // add event handlers
                watcher.Changed += new FileSystemEventHandler(OnChanged);
                watcher.Created += new FileSystemEventHandler(OnChanged);
                watcher.Deleted += new FileSystemEventHandler(OnChanged);
                watcher.Renamed += new RenamedEventHandler(OnRenamed);
    
                // bengin watching
                watcher.EnableRaisingEvents = true;
    
                // wait for the user to quit the program
                Console.WriteLine("Plress q to quit the program");
                while (Console.Read()!='q');
    
    
            }
    
            static void OnRenamed(object sender, RenamedEventArgs e)
            {
                Console.WriteLine("File: {0} renamed to {1}", e.OldFullPath, e.FullPath);
            }
    
            static void OnChanged(object sender, FileSystemEventArgs e)
            {            
                Console.WriteLine("File:" + e.FullPath + " " + e.ChangeType);
            }
    
    
    
        }
    }