1

I have built an application and a service that can stream files between each other, but it seems that my code, which supposed to read directories on flash drives and CDs, only works on flash drives.

    foreach (RadTreeNode l_node in m_fileExplorer.SelectedNodes) {

        string l_sSelectedPath = l_node.Name;
        FileAttributes l_fileAttr = File.GetAttributes(l_sSelectedPath);

        if (l_fileAttr == FileAttributes.Directory) {
            foreach (string l_sFilename in Directory.GetFiles(l_sSelectedPath, "*.*", SearchOption.AllDirectories)) {
                m_qUpload.Enqueue(
                    new UploadDescriptor {
                        BatchDescription = m_tbDescription.Text,
                        BatchTimestamp = l_now,
                        BatchId = l_sBatchId,
                        Username = m_frmLogin.Username,
                        TargetUsername = l_sTargetUsername,
                        Filename = l_sFilename
                    }
                );

                AddProgressRow(l_sFilename);
                l_nFilesInBatch++;
                ms_sem.Release();
            }
        }
    }

When I try to do the same to CDs, I get this error:

System.UnauthorizedAccessException: Access to the path 'D:\' is denied.
   at System.IO.__Error.WinIOError(Int32 errorCode, String maybeFullPath)
   at System.IO.FileStream.Init(String path, FileMode mode, FileAccess access, Int32 rights, Boolean useRights, FileShare share, Int32 bufferSize, FileOptions options, SECURITY_ATTRIBUTES secAttrs, String msgPath, Boolean bFromProxy, Boolean useLongPath, Boolean checkHost)
   at System.IO.FileStream..ctor(String path, FileMode mode, FileAccess access, FileShare share)
   at System.IO.File.Open(String path, FileMode mode, FileAccess access)
   at ActivePath.FileUploader.Frontend.UploadForm.UploadEx(Object sender, DoWorkEventArgs e) in c:\code\Customers\FIBI\PWFileUploader\PWFileUploaderApplication\UploadForm.cs:line 697

It seems I cannot do both using the same code, but I have no idea on how to do it.

NULL
  • 313
  • 1
  • 12
Alon M
  • 1,583
  • 7
  • 30
  • 44
  • Any one can help me? please. – Alon M Jan 19 '14 at 07:53
  • You are trying to open a file named `D:\\`. That will *always* fail with an access denied error. It is a directory, not a file. How your code got into that pickle is impossible to guess. Use the debugger. – Hans Passant Jan 24 '14 at 21:02

3 Answers3

4

From the looks of the stack trace, something is calling File.Open. I'll assume UploadEx is something you wrote and that you're in control of.

Check to make sure that the FileMode and FileAccess values are correct.


This should be okay, as FileMode.Open says a file should only be opened if it exists, and FileAccess.Read will prevent writing to the file:

File.Open(somePath, FileMode.Open, FileAccess.Read);

These probably won't be, because if the file doesn't exist, your program will attempt to create it, which won't go well on a cd-rom. Or if you have code that inadvertently modifies the file, that won't work either.

File.Open(somePath, FileMode.OpenOrCreate);

File.Open(somePath, FileMode.Open, FileAccess.ReadWrite);

From the look of your code, you don't seem to be doing anything more than reading all the files in the directory, but I can't see all your code so I'm just throwing it out there as a possible answer.


Alright, here's a solution that should work for you, based on that post I linked in the comments. I haven't actually built this, so there may be one or two syntax errors. Leave me a comment if it doesn't work.

You're current foreach loop:

    foreach (RadTreeNode l_node in m_fileExplorer.SelectedNodes)
    {
        string l_sSelectedPath = l_node.Name;

        FileAttributes l_fileAttr = File.GetAttributes(l_sSelectedPath);

        if (l_fileAttr == FileAttributes.Directory)
            DoWhatever(l_sSelectedPath);
    }

A new method to scan each directory recursively, ignoring the one that throws an exception:

private void DoWhatever(string path)
{
    try
    {
        Directory.GetFiles(path)
                 .ToList()
                 .ForEach(l_sFilename =>
                 {
                     m_qUpload.Enqueue(
                         new UploadDescriptor {
                             BatchDescription = m_tbDescription.Text,
                             BatchTimestamp = l_now,
                             BatchId = l_sBatchId,
                             Username = m_frmLogin.Username,
                             TargetUsername = l_sTargetUsername,
                             Filename = l_sFilename
                         }
                     );

                     AddProgressRow(l_sFilename);
                     l_nFilesInBatch++;
                     ms_sem.Release();
                 });

        Directory.GetDirectories(path)
                 .ToList()
                 .ForEach(s => DoWhatever(s));
    }
    catch (UnauthorizedAccessException ex)
    {
        // We're not authorized to access this directory. Who knows why. Ignore it.
    }
}
Grant Winney
  • 65,241
  • 13
  • 115
  • 165
0

Refer this post How to present credentials in order to open file? to Open file with credentials. And try to grant access to Network Service if you are doing through web.

Refer this MSDN post for the exception http://forums.asp.net/t/1013434.aspx?System+UnauthorizedAccessException+Access+to+the+path+D+thumbs+5B62060C102F6363635A+jpg+is+denied+

Hope this helps!

Community
  • 1
  • 1
Mohamed Alikhan
  • 1,315
  • 11
  • 14
0

I tried fiddling around with your problem. Are you sure you're passing FileAccess.Read flag to File.Open method? I did get error when tried to open file without this flag. But when you use proper flag, it's just fine. TBH best would be if you would show code from UploadEx method as that's where it seems to be a problem.

Error occuring when not using FileAccess.Read

And now with proper flag

File opening correctly

Good luck, hope it'll work for you :-)

mz

mariozski
  • 1,134
  • 1
  • 7
  • 20