Results 1 to 3 of 3

Thread: Recursive scan skipping over accessible files and folders

  1. #1

    Thread Starter
    Fanatic Member Peter Porter's Avatar
    Join Date
    Jul 2013
    Location
    Germany
    Posts
    581

    Question Recursive scan skipping over accessible files and folders

    Please skip to the last reply.

    Below my code works fine when I choose a folder with no restrictions, but when I want to log unrestricted files of the entire C drive I get:

    UnauthorizedAccessException was unhandled by user code

    Access to the path 'C:\$RECYCLE.BIN\S-1-5-18\' is denied.
    How can I get around this, catching this exception so my app doesn't crash on Recycle.Bin, but skips over it as well as other restricted folders, restricted subfolders, and restricted files?

    Code:
    Option Strict On
    
    Imports System.IO
    
    Public Class Form1
    
        Private Dir As String
        Dim FileExt As String
        Dim FilePath As String
        Dim Filename As String
        Dim Items As New List(Of ListViewItem)
        Dim Item As ListViewItem
        Dim i2 As Integer = 0
        Dim message As String
    
    
        Private Sub Form1_Load(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles MyBase.Load
            Me.CenterToScreen()
        End Sub
    
    
        Private Sub Form1_Resize(ByVal sender As Object, ByVal e As System.EventArgs) Handles Me.Resize
            Dim height As Integer = Me.Height
            If WindowState = FormWindowState.Maximized Then
                Me.Width = SystemInformation.VirtualScreen.Width
                Me.Height = height
                ListView1.Width = Me.Width - 40
                ListView1.Height = Me.Height - 130
            Else
            End If
            Me.CenterToScreen()
        End Sub
    
    
        Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
            ListView1.Items.Clear()
            Items.Clear()
            Dim i As Integer = 0
            Dir = New String(CType(FolderBrowserDialog1.SelectedPath, Char()))
            If (FolderBrowserDialog1.ShowDialog() = DialogResult.OK) Then
                Dir = New String(CType(FolderBrowserDialog1.SelectedPath, Char()))
                Label1.Text = Dir
                ListView1.Items.Clear()
            End If
            BackgroundWorker1.RunWorkerAsync()
        End Sub
    
    
        'label2 delegate
        Delegate Sub SetLabelTextInvoker(ByVal label As Label, ByVal Text As String)
    
        Sub SetLabelText(ByVal Label As Label, ByVal Text As String)
            If Label2.InvokeRequired = True Then
                Label2.Invoke(New SetLabelTextInvoker(AddressOf SetLabelText), Label, Text)
            Else
                Label2.Text = Text
            End If
        End Sub
    
    
        Private Sub BackgroundWorker1_DoWork(ByVal sender As System.Object, ByVal e As System.ComponentModel.DoWorkEventArgs) Handles BackgroundWorker1.DoWork
            For i As Integer = 0 To i
                For Each files As String In Directory.EnumerateFiles(Dir, "*.*", SearchOption.AllDirectories)
    
                    FileExt = New String(CType(IO.Path.GetExtension(files.ToLower), Char()))
                    FilePath = New String(CType(IO.Path.GetDirectoryName(files), Char()))
                    Filename = New String(CType(IO.Path.GetFileNameWithoutExtension(files), Char()))
    
                    Dim maxThreads As String = Nothing
                    Dim randomc As String
    
                    If maxThreads Is Nothing Then
                        Dim fExt As String = StrConv(FileExt, VbStrConv.ProperCase)
                        randomc = fExt.Trim(CChar(".")).ToUpper & " "
                        If randomc = " " Then
                            randomc = "Unknown"
                        Else
                        End If
                        maxThreads = randomc
                    End If
    
                    Dim sizeInBytes As System.IO.FileInfo = My.Computer.FileSystem.GetFileInfo(files)
    
                    Dim separators() As String = {"*", ","}
                    Dim filesize As String = CStr(sizeInBytes.Length / 1024)
                    Dim input As String() = filesize.Split(separators, StringSplitOptions.RemoveEmptyEntries)
                    filesize = input(0)
    
                    Item = New ListViewItem
                    Item.Text = Filename & FileExt
                    Item.SubItems.Add(maxThreads)
                    Item.SubItems.Add(filesize & " KB")
                    Item.SubItems.Add(FilePath)
    
                    Items.Add(Item)
    
                    BackgroundWorker1.ReportProgress(i)
    
                    i2 = i
                    i = i + 1
                    If i = 1 Then
                        SetLabelText(Label2, CStr(i) + " file")
                    Else
                        SetLabelText(Label2, CStr(i) + " files")
                    End If
                Next
    
                If i > i2 Then
                    If i = 1 Then
                        message = "done"
                        BackgroundWorker1.ReportProgress(i)
                        i = 0
                    Else
                        message = "done"
                        BackgroundWorker1.ReportProgress(i)
                        i = 0
                    End If
                Else
                End If
            Next
        End Sub
    
    
        Private Sub BackgroundWorker1_ProgressChanged(ByVal sender As Object, ByVal e As System.ComponentModel.ProgressChangedEventArgs) Handles BackgroundWorker1.ProgressChanged
            If message = "done" Then
                ListView1.BeginUpdate()
                ListView1.ListViewItemSorter = Nothing
                ListView1.Items.AddRange(Items.ToArray)
                'ListView1.AutoResizeColumns(ColumnHeaderAutoResizeStyle.ColumnContent)
                ListView1.Sort()
                ListView1.EndUpdate()
                message = ""
            Else
            End If
            Label2.Refresh()
        End Sub
    
    End Class
    Attached Files Attached Files
    Last edited by Peter Porter; May 5th, 2018 at 05:33 AM.

  2. #2
    Super Moderator jmcilhinney's Avatar
    Join Date
    May 2005
    Location
    Sydney, Australia
    Posts
    111,221

    Re: Help logging accessible files, skipping all restricted folders & restricted files

    You cannot use this:
    Code:
    For Each files As String In Directory.EnumerateFiles(Dir, "*.*", SearchOption.AllDirectories)
    You need to build your own recursive file search that gets files and subfolders one level at a time. That way, you can wrap the Directory.GetFiles or Directory.EnumerateFiles call in a Try block and catch any exceptions thrown on that call specifically and still carry on searching more folders.

    By the way, how does this make sense:
    Code:
    For i As Integer = 0 To i
    Why is my data not saved to my database? | MSDN Data Walkthroughs
    VBForums Database Development FAQ
    My CodeBank Submissions: VB | C#
    My Blog: Data Among Multiple Forms (3 parts)
    Beginner Tutorials: VB | C# | SQL

  3. #3

    Thread Starter
    Fanatic Member Peter Porter's Avatar
    Join Date
    Jul 2013
    Location
    Germany
    Posts
    581

    Resolved Re: Help logging accessible files, skipping all restricted folders & restricted files

    jmcilhinney, I've been running on fumes the last few days.

    Quote Originally Posted by jmcilhinney View Post
    By the way, how does this make sense:
    Code:
    For i As Integer = 0 To i
    Don't know what I was thinking when I coded that above.

    Anyway, I've slapped together my own recursive search. I knew I had to get the directory first and catch exceptions while it searched for files, just couldn't concentrate while struggling to keep my eyes open.

    The code below is sloppy, but it works. I'll clean it up after some rest.

    Uses 1 button, 1 label, 2 listboxes and a FolderBrowserDialog.
    Code:
    Imports System.IO
    
    Public Class Form1
    
        Private Dir As String
        Dim FileExt As String
        Dim FilePath As String
        Dim Filename As String
        Dim Items As New List(Of ListViewItem)
        Dim Item As ListViewItem
        Dim i As Integer = 0
        Dim i2 As Integer = 0
        Dim i3 As Integer = 0
        Dim message As String
    
        Private Sub Button1_Click(ByVal sender As System.Object, ByVal e As System.EventArgs) Handles Button1.Click
            i2 = 0
            i3 = 0
            Dir = New String(CType(FolderBrowserDialog1.SelectedPath, Char()))
    
            'FolderBrowserDialog
            If (FolderBrowserDialog1.ShowDialog() = DialogResult.OK) Then
                Dir = New String(CType(FolderBrowserDialog1.SelectedPath, Char()))
                ListBox1.Items.Clear()
                ListBox2.Items.Clear()
            End If
    
            'Add folders to listbox1
            For Each Folder As String In _
       My.Computer.FileSystem.GetDirectories(Dir)
                ListBox1.Items.Add(Folder)
            Next
    
            Try
                For Each files As String In Directory.EnumerateFiles(Dir, "*.*", SearchOption.TopDirectoryOnly)
                    FileExt = New String(CType(IO.Path.GetExtension(files.ToLower), Char()))
                    FilePath = New String(CType(IO.Path.GetDirectoryName(files), Char()))
                    Filename = New String(CType(IO.Path.GetFileNameWithoutExtension(files), Char()))
                    ListBox2.Items.Add(FilePath)
    
                    Dim maxThreads As String = Nothing
                    Dim randomc As String
    
                    If maxThreads Is Nothing Then
                        Dim fExt As String = StrConv(FileExt, VbStrConv.ProperCase)
                        randomc = fExt.Trim(CChar(".")).ToUpper & " "
                        If randomc = " " Then
                            randomc = "Unknown"
                        Else
                        End If
                        maxThreads = randomc
                    End If
    
                    Dim sizeInBytes As System.IO.FileInfo = My.Computer.FileSystem.GetFileInfo(files)
                    Dim separators() As String = {"*", ","}
                    Dim filesize As String = CStr(sizeInBytes.Length / 1024)
                    Dim input As String() = filesize.Split(separators, StringSplitOptions.RemoveEmptyEntries)
                    filesize = input(0)
    
                    Item = New ListViewItem
                    Item.Text = Filename & FileExt
                    Item.SubItems.Add(maxThreads)
                    Item.SubItems.Add(filesize & " KB")
                    Item.SubItems.Add(FilePath)
                    Items.Add(Item)
    
                    i3 = i2
                    i2 = i2 + 1
                    If i2 = 1 Then
                        Label1.Text = CStr(i2) + " file"
                    Else
                        Label1.Text = CStr(i2) + " files"
                    End If
                    Label1.Refresh()
                Next
            Catch ex As Exception
            End Try
    
    
            'go through Listbox1's items
            For i = 0 To ListBox1.Items.Count - 1
    
                Try
    
                    'search each folder in listbox1 for all subfolders and files
                    For Each files As String In Directory.EnumerateFiles(CStr(ListBox1.Items(i)), "*.*", SearchOption.AllDirectories)
                        FileExt = New String(CType(IO.Path.GetExtension(files.ToLower), Char()))
                        FilePath = New String(CType(IO.Path.GetDirectoryName(files), Char()))
                        Filename = New String(CType(IO.Path.GetFileNameWithoutExtension(files), Char()))
                        ListBox2.Items.Add(FilePath)
    
                        Dim maxThreads As String = Nothing
                        Dim randomc As String
    
                        If maxThreads Is Nothing Then
                            Dim fExt As String = StrConv(FileExt, VbStrConv.ProperCase)
                            randomc = fExt.Trim(CChar(".")).ToUpper & " "
                            If randomc = " " Then
                                randomc = "Unknown"
                            Else
                            End If
                            maxThreads = randomc
                        End If
    
                        Dim sizeInBytes As System.IO.FileInfo = My.Computer.FileSystem.GetFileInfo(files)
                        Dim separators() As String = {"*", ","}
                        Dim filesize As String = CStr(sizeInBytes.Length / 1024)
                        Dim input As String() = filesize.Split(separators, StringSplitOptions.RemoveEmptyEntries)
                        filesize = input(0)
    
                        Item = New ListViewItem
                        Item.Text = Filename & FileExt
                        Item.SubItems.Add(maxThreads)
                        Item.SubItems.Add(filesize & " KB")
                        Item.SubItems.Add(FilePath)
                        Items.Add(Item)
    
                        i3 = i2
                        i2 = i2 + 1
                        If i2 = 1 Then
                            Label1.Text = CStr(i2) + " file"
                        Else
                            Label1.Text = CStr(i2) + " files"
                        End If
                        Label1.Refresh()
                    Next
                Catch ex As Exception
                End Try
            Next
    
        End Sub
    
        
    End Class

Tags for this Thread

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width