开发者

How to check if a Windows file is readable/writable?

First off: I know that this isn't reliable for actually checking if I can write. I'm writing a file transfer client, and want feature parity between the "remote" and "local" file browser panes. I fully understand I will have to handle any permission related exceptions for any operation performed regardless; it's not a programming check it's just to display to the user.

I've seen several examples for these posted, but everything I've tried either wasn't understandable or didn't work. I've tried the following two methods, but both just returned "yes" for things I definitely can't write to (the contents of C:\Windows or C:\Program Files, for example):

System.Security.Permissions.FileIOPermission fp = new System.Security.Permissions.FileIOPermission(System.Security.Permissions.FileIOPermissionAccess.Write, Path);
return System.Security.SecurityManager.IsGranted(fp);

and

System.Security.Permissions.FileIOPermission fp = new System.Security.Permissions.FileIOPermission(System.Security.Permissions.FileIOPermissionAccess.Write, element.Path);
try
{
    fp.Assert();
    return true;
}
catch(Exception x)
{
    return fals开发者_JAVA技巧e;
}

(Again, I'm aware that both catching Exception is horrible and using try/catch for logic is slightly less horrible, I'm just trying to get this to work).

The first one tells me that IsGranted is deprecated and I should be using AppDomain.PermissionSet or Application.PermissionSet, but I can't find any explanation of how to use these that makes sense. I've also seen that I should be manually enumerating all the ACLs to figure it out myself, but again there's no real examples of this. There's quite a few examples for setting permissions, but few for checking them.

Any help would be greatly appreciated.


Well, here's what I eventually wound up with:

    private readonly static WindowsIdentity _identity = WindowsIdentity.GetCurrent();
    protected static bool GetPermission(FileSystemRights right, string path)
    {
        FileSecurity fs;
        try
        {
            fs = System.IO.File.GetAccessControl(path);
        }
        catch(InvalidOperationException)
        {
            // called on a disk that's not present, ...
            return false;
        }
        catch(UnauthorizedAccessException)
        {
            return false;
        }
        foreach(FileSystemAccessRule fsar in fs.GetAccessRules(true, true, typeof(SecurityIdentifier)))
        {
            if(fsar.IdentityReference == _identity.User && fsar.FileSystemRights.HasFlag(right) && fsar.AccessControlType == AccessControlType.Allow)
            {
                return true;
            }
            else if(_identity.Groups.Contains(fsar.IdentityReference) && fsar.FileSystemRights.HasFlag(right) && fsar.AccessControlType == AccessControlType.Allow)
            {
                return true;
            }
        }
        return false;
    }

Of course, it's not ideal, because it ignores Deny rights. But I have no idea in which order to apply the various ACEs (I think?) in order to find out the "correct" ability. Still, Deny rules are relatively rare, so it works most of the time for me.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜