Yes, FileShare.Delete tends to cause this problem. Used by any program that runs in the background and scans files, file indexers and antivirus scanners are common examples.
FileShare.Delete allows another process to delete the file, even if the background process still has the file open and is reading it. This other process will not pay attention to the fact that the file has not actually disappeared, because it knows that the file is really deleted.
The problem starts when this other process depends on the actual removal of the file and does something else. Usually triggered by the creation of a new file with the same name. In particular, it is a very unreasonable way to save the file, as this will lead to complete data loss without backup, when the failure fails, but this error is very common.
This will not succeed because the directory entry for the file is still present, it will not disappear until the last process in which the file is open closes the handle. Any other process that tries to open the file again will be deleted with error 5, "access denied." Including this process, which deleted the file and tries to recreate it.
The workaround is to always use transactional saves by renaming the file before trying to overwrite it. Available in .NET with File.Replace (), in native winapi with ReplaceFile (). Also easy to do manually, workflow:
- delete backup file, stop if failed
- rename the old file to the backup file name, stop if failed
- write a new file using the original file name, rename the backup if failed
- delete backup file, ignore failure
Step 2 ensures that there will never be data loss, the original file will remain untouched if something goes wrong. Step 4 ensures that FileShare.Delete will work as planned, this backup file will disappear eventually when other processes close their descriptors.
source share