I'm trying to use this code to get all directories on a drive. It works good until it gets an access violation. A lot of people have said to use try-catch to get around the exceptions, but the way I'm trying to do it I only get the directories up til the exception. I must be missing something obvious, but don't see how it can jump over the errors. I tried this as EnumerateDirectories and GetDirectories, but couldn't see an obvious difference.
I tried pasting this as code in Firefox but couldn't. Worked fine in Chrome.

        private void button1_Click(object sender, EventArgs e)
        {
            try
            {
                string dirPath = @"C:\Data\";
                // LINQ query. 
                var dirs = from dir in Directory.EnumerateDirectories(dirPath, "*", SearchOption.AllDirectories) select dir;
                    // Show results. 
                foreach (var dir in dirs)
                {
                    MessageBox.Show(dir);
                }                  
                Console.WriteLine("{0} directories found.", dirs.Count<string>().ToString());
                    // Optionally create a List collection.
                List<string> workDirs = new List<string>(dirs);
            }
            catch (UnauthorizedAccessException UAEx)
            {
                MessageBox.Show(UAEx.Message);
            }
            catch (PathTooLongException PathEx)
            {
                MessageBox.Show(PathEx.Message);
            }
        }

Recommended Answers

All 2 Replies

If EnumerateDirectories ends after trying to access a directory it cannot then you're going to need to create your own search function.

EnumerateDirectories will give you all the directory names for the folder it is currently searching. With the AllDirectories flag it will search all sub directories as well. Your exception will be raised when it tries to enter a sub-directory it doesn't have permission to do so, in this case, you're going to have to re-implement this behaviour yourself.

Retrieve a list of the directories at the current level, then one by one enter the sub-directories. When you hit one you can't enter, just skip it and move to the next.

Thanks Ketsuekiame,
It took a lot of errors and it isn't pretty, but I now have a recursive that works for me. Using WindowsForms, it just needs a comboBox1, a textBox (tbDirectories), and a label (dirCountLbl). It can also get all directoies on all drives at once.

using System;
using System.Collections.Generic;
using System.ComponentModel;
using System.Data;
using System.Drawing;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Windows.Forms;
using System.IO;

namespace GetDirectories
{
    public partial class Form1 : Form
    {
        public Form1()
        {
            InitializeComponent();
            getDrives();
        }

        private void getDrives()
        {
            {
                List<string> logicalDrives = new List<string>();
                string[] tempDrives = Directory.GetLogicalDrives();
                for (int drv = 0; drv < (tempDrives.Length); drv++)
                {
                    logicalDrives.Add(tempDrives[drv]);
                }
                logicalDrives.Add("All");
                for (int i = 0; i < logicalDrives.Count; i++)
                {
                    comboBox1.Items.Add(logicalDrives[i]);
                }
            }
        }
        private void checkFiles(string pattern, string path,List<string> directories)
        {
            try
            {
                string[] directoryList = (Directory.GetDirectories(path, "*"));
                foreach (string dir in directoryList)
                {
                    directories.Add(dir);
                    try
                    {
                        checkFiles(pattern, dir,directories);
                    }
                    catch
                    {
                    }
                }
            }
            catch
            {
                //
            }
        }  
        private void comboBox1_SelectedIndexChanged(object sender, EventArgs e)
        {
            List<string> directories = new List<string>();
            string pattern = "*";
            string path = comboBox1.SelectedItem.ToString();
            if (path != "All")
            {
                checkFiles(pattern, path, directories);
            }
            else
            {
                string[] allDrives = Directory.GetLogicalDrives();
                for (int i = 0; i < allDrives.Length; i++)
                {
                    checkFiles(pattern, (allDrives[i]), directories);
                }
            }
            dirCountLbl.Text = (directories.Count).ToString();
            tbDirectories.Lines = directories.ToArray();
            MessageBox.Show("Finished");
        }
    }
}
Be a part of the DaniWeb community

We're a friendly, industry-focused community of developers, IT pros, digital marketers, and technology enthusiasts meeting, networking, learning, and sharing knowledge.