alphaleonis / AlphaFS

AlphaFS is a .NET library providing more complete Win32 file system functionality to the .NET platform than the standard System.IO classes.
http://alphafs.alphaleonis.com/
MIT License
562 stars 99 forks source link

Moving Files on the Same NTFS Volume does NOT Inherit Permissions #442

Open mikec25 opened 6 years ago

mikec25 commented 6 years ago

Hi

I had a client complain that suddenly when using my app to move a file, the target folder permissions were not being inherited by the files. We removed the variables like Windows 10 version (very latest) and my app has the latest AlphaFS 2.2.1 and targets .NET 4.7.2.

Before anyone quotes the rules around this, they should read: http://www.think-like-a-computer.com/2011/07/24/moving-files-on-the-same-ntfs-volume-does-inherit-permissions/

Also, you will notice that when using Microsoft Explorer to move a file, the file does inherit the target folder permissions. Ie, validating the blog above.

However, using AlphaFS File.Move(Source, Target) call is moving the file and not inheriting the folder permissions. The only way I could get a workaround was to use a 2 step (and slower for same volume scenarios) copy to target and then delete from source. Then the permissions were inherited in the same way as if they used Windows Explorer. I tried the moveoption CopyAllowed but since this is a local move it probably didn’t apply because it didn’t work.

Thanks Mike

Yomodo commented 6 years ago

Do you get the same result/behavior when using the System.IO.File.Move method?

mikec25 commented 6 years ago

Yes. The test case is very easy to set up. 2 folders on the SAME drive. Folder A has a file, Folder B none but folder B does have an additional User with permissions. Adding a file to B would see that file inherit the folder B rights (ie, you can see the additional user). Now make a file in A and CUT + PASTE to B using Windows Explorer. You will see the additional user when checking the file security. Try the same using AlphaFS and you will not see the additional user inherited using AlphaFS MOVE. The only way i could get it to work like Windows was AlphaFS copy and then delete from A. Thanks.

Yomodo commented 6 years ago

If the System.IO.File.Move() method does exactly what the AlphaFS implementation does (and/or vice versa), than it is not a bug because both methods behave the same, as they should.

mikec25 commented 6 years ago

Sure, I'm not going as far as calling it a "bug" but rather a missing "feature". Right now using Windows Explorer the cut and paste of a file is behaving as expected but both AlphaFS and System.IO are not. It is puzzling that suddenly this has happened and also that Windows Explorer is behaving differently to System.IO. I have just checked again: //Alphaleonis.Win32.Filesystem.File.Move(Source, Target); - FILE NOT INHERITING PERMISSIONS //System.IO.File.Move(Source, Target); - FILE NOT INHERITING PERMISSIONS //Forced to use: File.Copy(Source, Target); File.Delete(Source);

The workaround is not optimal on same drive/volume scenarios. A user would have to wait for a large file to copy and paste when a move is what was expected (ie, instant). Network "moves" would take the same time but not local.

Yomodo commented 6 years ago

Just out of curiosity, could you try System.IO/Alphaleonis.Win32.Filesystem.Directory.Move to see what happens? (Directory.Move can also be used for files.)

mikec25 commented 6 years ago

Neither worked: Alphaleonis.Win32.Filesystem.Directory.Move(FileToMove_InclPath, FileToMove_InclTargetPath); System.IO.Directory.Move(FileToMove_InclPath, FileToMove_InclTargetPath);

Yomodo commented 6 years ago

The behavior of Windows Explorer is explained here but seems only applicable when using the MoveSecurityAttributes registry key.

The Move­Security­Attributes policy applies to Explorer's file copy engine, the thing that kicks in when you call SHFile­Operation or use the IFile­Operation interface.

Perhaps you can use File.GetAccessControl and File.SetAccessControl after the File.Move action, as a workaround? You would at least retain the speedy move action.

mikec25 commented 6 years ago

Thanks, that gives me something to think about. The called to SetAccessControl is issuing an "Access Denied" error so I'll have to look deeper as to why.

Yomodo commented 6 years ago

Access denied... perhaps file has read-only and/or hidden attribute? If the process is run elevated, you might want to use the Backup privilege.

mikec25 commented 6 years ago

I think I have a fundamental problem here: The application I use cannot/should not run elevate and unless it is, SetAccessControl will get denied on the file.