I do agree with Alex - it is very complex. My approach in the past has always been to refuse to grant oplocks as the default implementation and then add in only what was absolutely necessary. After all, oplocks are an optimization mechanism and getting them wrong leads to potentially ugly problems (because they manifest as cache incoherency issues). For many years this approach has worked fine because only the SMB server really used oplocks and it handled failures (including not being granted an oplock) gracefully.
Unfortunately, applications are now using them. They are proving to be intolerant of refusing to grant an oplock, which leads to application compatibility errors. For example, one of my customers has found that if a filter rejects oplocks on Windows 8, the tiles displayed by Metro are blank in some instances.
This is forcing us into a position of not only supporting oplocks but supporting essentially ALL oplocks - including oplocks on directories (new in Windows 8).
Here is the code in the FAT fsctl handler for the oplock request in Windows 7:
//
// We only permit oplock requests on files.
//
if ( FatDecodeFileObject( IrpSp->FileObject,
&Vcb,
&Fcb,
&Ccb ) != UserFileOpen ) {
FatCompleteRequest( IrpContext, Irp, STATUS_INVALID_PARAMETER );
DebugTrace(-1, Dbg, “FatOplockRequest -> STATUS_INVALID_PARAMETER\n”, 0);
return STATUS_INVALID_PARAMETER;
}
And here is the same routine in the last preview release for Windows 8:
//
// We permit oplock requests on files and directories.
//
if ((TypeOfOpen != UserFileOpen) &&
(TypeOfOpen != UserDirectoryOpen)) {
FatCompleteRequest( IrpContext, Irp, STATUS_INVALID_PARAMETER );
DebugTrace(-1, Dbg, “FatOplockRequest -> STATUS_INVALID_PARAMETER\n”, 0);
return STATUS_INVALID_PARAMETER;
}
This is even beyond the rename issue (note the FAT rename sample is quite complex and is related to how FAT deals with batch oplocks.)
Tony
OSR