Getting UnauthorizedAccessException while counting the size of the directory

白昼怎懂夜的黑 提交于 2021-01-28 05:13:01

问题


I have a simple method that counts the size of the directory and all files within it. Here is the code:

using System;
using System.IO;

namespace MyProject.Libs
{
    public sealed class DirectorySize
    {
        public static long GetDirectorySize(DirectoryInfo dir)
        {
            long total = 0;

            FileInfo[] fileInfos = dir.GetFiles();
            foreach (FileInfo fileInfo in fileInfos)
            {
                total += fileInfo.Length;
            }

            DirectoryInfo[] dirInfos = dir.GetDirectories();
            foreach (DirectoryInfo dirInfo in dirInfos)
            {
                total += DirectorySize.GetDirectorySize(dirInfo);
            }

            return total;
        }
    }
}

When I use it on drive c:\ I get "UnauthorizedAccessException" with a message "Access to the path 'C:\Documents and Settings' is denied." That is:

DirectoryInfo di = new DirectoryInfo(Path.GetPathRoot(Environment.SystemDirectory));
long ds = DirectorySize.GetDirectorySize(di);

Tried to run Visual Studio as Administrator. All the same. Why?


回答1:


Your code fails on C:\Documents and Settings which is now a junction point that points to C:\Users. You could check that with the FileAttributes.ReparsePoint of the directory.

Here's the modified code with additional exception handling(for other dirs which you are not authorized):

public sealed class DirectorySize
{
    public static long GetDirectorySize(DirectoryInfo dir)
    {
        long total = 0;
        FileAttributes attributes = File.GetAttributes(dir.FullName);
        if (!((attributes & FileAttributes.ReparsePoint) == FileAttributes.ReparsePoint))
        {
            try{
                FileInfo[] fileInfos = dir.GetFiles();
                foreach (FileInfo fileInfo in fileInfos)
                {
                    total += fileInfo.Length;
                }

                DirectoryInfo[] dirInfos = dir.GetDirectories();
                foreach (DirectoryInfo dirInfo in dirInfos)
                {
                    total += DirectorySize.GetDirectorySize(dirInfo);
                }
            } catch (UnauthorizedAccessException)
            { 
                // log this?
            }
        }

        return total;
    }
}

Junction Points (Windows)

In Windows Vista and Windows Server 2008, the default locations for user data and system data have changed. For example, user data that was previously stored in the %SystemDrive%\Documents and Settings directory is now stored in the %SystemDrive%\Users directory. For backward compatibility, the old locations have junction points that point to the new locations. For example, C:\Documents and Settings is now a junction point that points to C:\Users. Backup applications must be capable of backing up and restoring junction points. These junction points can be identified as follows: They have the FILE_ATTRIBUTE_REPARSE_POINT, FILE_ATTRIBUTE_HIDDEN, and FILE_ATTRIBUTE_SYSTEM file attributes set. They also have their access control lists (ACLs) set to deny read access to everyone. Applications that call out a specific path can traverse these junction points if they have the required permissions. However, attempts to enumerate the contents of the junction points will result in failures.




回答2:


There are files and folders you don't have permissions to access, even as administrator. The best you can do is add some exception handling and hope the information you return is reasonably complete.




回答3:


There are some folders where even the administrator has no permission to visit them. This most of the time happens with translated systems. For example the "program files" folder would be called "programme" in german. You have no access to "programme" within the code but to "program files"



来源:https://stackoverflow.com/questions/14076336/getting-unauthorizedaccessexception-while-counting-the-size-of-the-directory

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!