I need to write a filter that attaches to a volume and redirects all file creation and modification to a different volume. It has to handle the following:
When a new file is created it is actually created on a different volume, but to the user and all applications it looks like it exists on the original volume.
When a file is modified a new copy is made on the second volume, leaving the original untouched. While the filter is active the new copy is used, but when it is unloaded it will be like the file never changed.
I’ve looked through the NTFSD forums and people with similar requirements to mine were advised to try a storage filter driver, as it is simpler than file system minifilters.
I’ve written a basic USB driver in WDF before. I’ve looked at the Diskperf sample and the KMDF Toaster filter sample and I’m thinking of using those as my base. I would like to use WDF if possible, but I’m not sure how to register for the IRP_MJ_CREATE callback.
Please advise me on the feasibility of this option and correct me if I’m completely misunderstanding something.
Volume filters see blocks read or written to a volume, there is no
concept of “creating a file” at this level. The only create that a
volume filter sees is when something opens the volume, thereafter
it’s all read or write block I/O.
Files are a construct of the file system and the meta-data it
stores. None of this information is available to a volume filter.
Certainly you can use a volume filter to mirror block writes to
another location. But if you want to mirror at the file level, all
or selected files, then you’ll need a file system filter.
I suggest you have a think about your requirements. Often management
specify things without understanding what is a file and what are
blocks. From your description it looks like you probably want a f/s
filter, but I could be wrong.
I need to write a filter that attaches to a volume and redirects all
file creation and modification to a different volume. It has to
handle the following:
When a new file is created it is actually created on a different
volume, but to the user and all applications it looks like it exists
on the original volume.
When a file is modified a new copy is made on the second volume,
leaving the original untouched. While the filter is active the new
copy is used, but when it is unloaded it will be like the file never changed.
I’ve looked through the NTFSD forums and people with similar
requirements to mine were advised to try a storage filter driver, as
it is simpler than file system minifilters.
I’ve written a basic USB driver in WDF before. I’ve looked at the
Diskperf sample and the KMDF Toaster filter sample and I’m thinking
of using those as my base. I would like to use WDF if possible, but
I’m not sure how to register for the IRP_MJ_CREATE callback.
Please advise me on the feasibility of this option and correct me if
I’m completely misunderstanding something.
Thanks for the explanation Mark. A few things make more sense now.
Maybe I didn’t word my requirements properly. Basically, the idea is to revert changes to files, that happen while the filter is attached, when the filter is detached. So, I think that mirroring at the block level should do the trick.
I could intercept the WRITE requests and write new data blocks that I receive to the next available space in my new volume and keep a mapping of where it was supposed to be written in the old volume. Then I keep track of which blocks were modified and in the READ requests I map the offsets back.
I’m assuming that files are made up of blocks. Please correct me if this is wrong.
I’m not sure how to redirect to a different volume though. Do I need to have an instance of the filter attached to the other volume like for minifilters?
Would this approach work? And most importantly, would it be easier to write than a minifilter?
A small point, when you install a filter in a stack, PnP ensures the
filter is loaded for every instance of the stack. So you’ll need
some persistent config saying which volume you want to pro-actively monitor.
As for where to store the writes, your simplest method would probably
be to just have a file on another volume and write data to that. You
just keep a mapping table of logical blocks to offsets in the
file. The “gotchas” whether you re-direct to file or volume are
essentially the same e.g. coping with startup race conditions for one.
Btw - there are a number of products out there that do this kind of
thing. Perhaps one of them meets your requirements ? The cost of
buying or licensing such a product will most likely be a whole lot
cheaper than the time to to write one yourself.
Thanks for the explanation Mark. A few things make more sense now.
Maybe I didn’t word my requirements properly. Basically, the idea is
to revert changes to files, that happen while the filter is
attached, when the filter is detached. So, I think that mirroring at
the block level should do the trick.
I could intercept the WRITE requests and write new data blocks that
I receive to the next available space in my new volume and keep a
mapping of where it was supposed to be written in the old volume.
Then I keep track of which blocks were modified and in the READ
requests I map the offsets back.
I’m assuming that files are made up of blocks. Please correct me if
this is wrong.
I’m not sure how to redirect to a different volume though. Do I need
to have an instance of the filter attached to the other volume like
for minifilters?
Would this approach work? And most importantly, would it be easier
to write than a minifilter?
Thanks for the suggestions.
I found info on Enhanced Write Filter and File Based Write Filter, but these seem to only be available on embedded OS’s. There is supposedly a way to install the driver on XP Pro, but it’s a hack.
If anyone knows of other products that would do this please let me know.
Thanks.