Mount Manager

I have developed a very simple non-pnp WDM disk driver. It basically creates a disk device object and calls IoCreateSymbolicLink to associate the disk with a drive letter. On top of that, I developed a very rudimentary file system driver, with just enough functionality to be able to recognize the preformatted disk and successfully mount on top of the disk. My next step is to get the disk registered with the mount manager. This is where the problem lies. I am not sure if it is my understanding of how the mount manager works, or something else, but I can’t successfully get the disk registered with the mount manager and keep it registered across reboots. I have read every article on MSDN and osr relating to the mount manager and drive letter assignements, and here is what I understand and have tried thus far:

  1. Because my driver does not support PNP, I tried using the IOCTL_MOUNTMGR_ARRIVAL_NOTIFICATION I/O control to notify the mount manager of the arrival of my drive. It turns out, this works and successfully registers my drive with the mount manager. I see two entries get added underneath the HKLM\SYSTEM\MountedDevices registry key. Assuming my drive is assigned the drive letter K:, I see the two keys:

??\Volume{GUID}
\DosDevices\K:

and they both have the value of the unique id I use to respond to the mount manager during arrival notification. The problem is, when the machine is rebooted, the keys remain in the registry, but the mount manager doesn’t have any knowledge of my drive when queried for it. At this point, I can call the arrival notification IOCTL again, but I get a different drive letter than was used before, and I would like to get the same one. Also, this IOCTL states that the mount manager will query my disk for a suggested link name, but may not necessarily take it. I would like the drive letter always determined by me, assuming the one I pick is not in use.

  1. I have tried sending an IOCTL_MOUNTMGR_CREATE_POINT request to the mount manager, with the result being only the \DosDevices\K: entry gets created in the registry and the ??\Volume{GUID} entry is not created. Thus, a call to GetVolumeNameForVolumeMountPoint() fails since there is no volume name key in the registry. Thus, I don’t think this is the call I want to make, unless there is a way to get the volume guid entry into the registry.

I guess I just want to know if there is a way to register a non-pnp disk driver with the mount manager with the drive letter of my choosing and have it be persistent across reboots. Or, is the only way to do it to make a pnp capable disk driver? Would it make it easier to use kmdf? I would like to keep my disk driver intact if possible, but if the only way to correctly register it with the mount manager is to rewrite it, then I could go that route.

My other question is, on reboot, why doesn’t the mount manager pick up the fact that my drive is already in its database in the registry? Is there a call I can make to have it rescan its database? Is my disk starting too late (system start) and not able to respond to requests the mount manager might be making to me at boot time?

Thanks for any help

There are very few mountmgr clients out there and those that I’m aware of support PNP so you might run into problems. You may be able to get away with a simple PNP model.

When you send IOCTL_MOUNTMGR_VOLUME_ARRIVAL_NOTIFICATION mountmgr should be sending IOCTL_MOUNTDEV queries to your device. Are you responding to those with the same device name, unique ID and suggested link name before and after reboot?

I think you need to notify MOUNTMGR (by means of an
IOCTL_MOUNTMGR_VOLUME_ARRIVAL_NOTIFICATION) every time you want to register
your volume with mountmgr. After a reboot, when your device gets mounted
again, you need to tell MountMgr again about your device and use the same
UNIQUE_ID (but of course, the device name might be different). It is at that
time (when you notify MOUNTMGR) that it will look in its database and figure
out if you had a drive letter and what it was and create the new link for
it.

Your device (or the volume manager you use) needs to handle some IOCTLs that
the mount managers sends, like IOCTL_VOLUME_GET_GPT_ATTRIBUTES,
IOCTL_MOUNTDEV_QUERY_DEVICE_NAME, IOCTL_MOUNTDEV_QUERY_UNIQUE_ID,
IOCTL_MOUNTDEV_QUERY_SUGGESTED_LINK_NAME and so on… I think an important
one you must make sure is supported is IOCTL_MOUNTDEV_QUERY_STABLE_GUID…

Good luck,
Alex.

I just tried this again on my XP machine, and got the following results:

I sent the IOCTL_MOUNTMGR_VOLUME_ARRIVAL_NOTIFICATION and received the following IOCTLs:

  1. IOCTL_MOUNTDEV_QUERY_DEVICE_NAME - Responded back before and after the reboot with the same value of \Device\TestDisk.

  2. IOCTL_MOUNTDEV_QUERY_UNIQUE_ID - Responded back before and after the reboot with the same value of ??\Volume{GUID}\ where GUID is a guid that I assigned to my test disk.

  3. IOCTL_MOUNTDEV_QUERY_STABLE_GUID - It says this is not required, so I don’t supply a guid for this request.

  4. IOCTL_MOUNTDEV_QUERY_SUGGESTED_LINK_NAME - Responded back before and after the reboot with the same value of \DosDevices\K:.

When I tested this before the reboot, I check the registry and observed that the following keys were added:

??\Volume{GUID} (where GUID is assigned by the mount manager)
\DosDevices\E: (Which isn’t the drive letter i suggested be used and K is available)
\DosDevices\is (I have no idea what this is)

All three keys above have the same value which is ??\Volume{GUID}\ where GUID is the guid I assigned to my test disk.

Now, my question is, can I not assign the drive letter of my choice through the mount manager, or do I have to let the mount manager decide what drive letter to use? Also, what is the \DosDevices\is key that got created?

Overall, I am still kind of confused about how the IOCTL requests that can be sent to the mount manager relate to how a drive letter/symbolic link is assigned to a device.

Thanks

Alex,

I just sent a reply to Scott about the test I just did and didn’t get the results I expected. I don’t currently support the IOCTL_MOUNTDEV_QUERY_STABLE_GUID request because it is not required. If I do need to support this for my driver, do I return back the guid from my unique id I am responding with, or some other guid, or a new guid i need to create? Thanks for your help.

First, for IOCTL_MOUNTDEV_QUERY_UNIQUE_ID the buffer you pass in is treated
as an opaque blob so there is no need to format it to "??\Volume{GUID}",
you can simply pass in the GUID for example.

IOCTL_MOUNTDEV_QUERY_STABLE_GUID -> I don’t implement it but i have very
different requirements so I’m not sure if it is needed for MOUNTMGR to
remember the drive letter or not (though it does remember it for me even
without it IIRC)…

IOCTL_MOUNTDEV_QUERY_SUGGESTED_LINK_NAME -> mountmgr might chose to ignore
this and I’m guessing it does because it either finds an entry in the
database for your disk (by ID - by this I mean it remembers that your disk
should get drive letter E:) or it finds an entry for the value you suggested
(K:) that doesn’t match your ID (for whatever reason)…

I have no idea what the \DosDevices\is device is…

Thanks,
Alex.

Well, I’m not sure… I used the same ID (which was a GUID) for both the
IOCTL_MOUNTDEV_QUERY_STABLE_GUID and the IOCTL_MOUNTDEV_QUERY_UNIQUE_ID. I’m
pretty sure that MOUNTMGR doesn’t compare one with the other (the UNIQUE_ID
with the STABLE_GUID), mainly because the UNIQUE_ID is treated as an opaque
blob and the STABLE_GUID is, well, a GUID. SO I guess you could use
different GUIDs if you wanted to, but I haven’t really tries it.

Thanks,
Alex.

I tried doing this again, and this time I changed the Unique id from ??\Volume{GUID}\ to just GUID and I am responding to the IOCTL_MOUNTDEV_QUERY_STABLE_GUID request with the same GUID. Now, however, I am still getting the \DosDevices\E: and \DosDevices\is entries in the database, even though there is no K: drive in use and no entries for it in the database. But, I am no longer getting the ??\Volume{GUID} entry in the database, which is a bad thing.

I am hoping someone can shed some light on what is going on here, or just explain why the mount manager does some of the things it does.

>with the drive letter of my choosing and have it be persistent across reboots. Or, is the only way to do

it to make a pnp capable disk driver? Would it make it easier to use kmdf?

Yes, I would go this way, given that you’re at the start of your project and have no large legacy code base.

Note that you will also need the INF file and a signature - without any signature, the users will see the large red warning box while installing your product.

If you target 2003+ - then StorPort virtual miniport is an ideal solution, StorPort (unlike KMDF) is a framework specially taylored for storage controllers.


Maxim S. Shatskih
Windows DDK MVP
xxxxx@storagecraft.com
http://www.storagecraft.com

Brian,
If a mountmgr client responds to the stable GUID query mountmgr won’t generate a volume GUID and it won’t persist it in the registry because it assumes the client will be able to provide the GUID on request.

The client must use a suggested link name format like \DosDevices\K: and mountmgr must not have previously assigned that device a drive letter or the suggestion will be ignored.

Note the unique ID and volume GUID are distinct concepts. The Unique ID should be unique and remain constant on any machine the device is attached to. The GUID serves as unique name for the device that is stable on a particular machine. The mountmgr assigned GUID for the same device will be different on different machines. The GUID name is needed because drive letters are not stable. A device’s lease on the drive letter is only honored when the device is present.

I hope this helps.
Scott

Thanks for your responses. Since I am not getting anywhere with my current method, I am going to at least convert my disk over to kmdf, or possibly the StorPort virtual miniport, if that is feasible.