Exemple #1
0
        public static void Replace(string sourceFileName,
                                   string destinationFileName,
                                   string destinationBackupFileName,
                                   bool ignoreMetadataErrors)
        {
            MonoIOError error;

            if (sourceFileName == null)
            {
                throw new ArgumentNullException("sourceFileName");
            }
            if (destinationFileName == null)
            {
                throw new ArgumentNullException("destinationFileName");
            }
            if (sourceFileName.Trim().Length == 0 || sourceFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("sourceFileName");
            }
            if (destinationFileName.Trim().Length == 0 || destinationFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("destinationFileName");
            }

            string fullSource = Path.GetFullPath(sourceFileName);
            string fullDest   = Path.GetFullPath(destinationFileName);

            if (MonoIO.ExistsDirectory(fullSource, out error))
            {
                throw new IOException(Locale.GetText("{0} is a directory", sourceFileName));
            }
            if (MonoIO.ExistsDirectory(fullDest, out error))
            {
                throw new IOException(Locale.GetText("{0} is a directory", destinationFileName));
            }

            if (!Exists(fullSource))
            {
                throw new FileNotFoundException(Locale.GetText("{0} does not exist", sourceFileName),
                                                sourceFileName);
            }
            if (!Exists(fullDest))
            {
                throw new FileNotFoundException(Locale.GetText("{0} does not exist", destinationFileName),
                                                destinationFileName);
            }
            if (fullSource == fullDest)
            {
                throw new IOException(Locale.GetText("Source and destination arguments are the same file."));
            }

            string fullBackup = null;

            if (destinationBackupFileName != null)
            {
                if (destinationBackupFileName.Trim().Length == 0 ||
                    destinationBackupFileName.IndexOfAny(Path.InvalidPathChars) != -1)
                {
                    throw new ArgumentException("destinationBackupFileName");
                }

                fullBackup = Path.GetFullPath(destinationBackupFileName);
                if (MonoIO.ExistsDirectory(fullBackup, out error))
                {
                    throw new IOException(Locale.GetText("{0} is a directory", destinationBackupFileName));
                }
                if (fullSource == fullBackup)
                {
                    throw new IOException(Locale.GetText("Source and backup arguments are the same file."));
                }
                if (fullDest == fullBackup)
                {
                    throw new IOException(Locale.GetText(
                                              "Destination and backup arguments are the same file."));
                }
            }

            if (!MonoIO.ReplaceFile(fullSource, fullDest, fullBackup,
                                    ignoreMetadataErrors, out error))
            {
                throw MonoIO.GetException(error);
            }
        }
Exemple #2
0
        static internal IEnumerable <FileSystemInfo> EnumerateFileSystemInfos(string full, string searchPattern, SearchOption searchOption)
        {
            string         path_with_pattern = Path.Combine(full, searchPattern);
            IntPtr         handle;
            MonoIOError    error;
            FileAttributes rattr;
            bool           subdirs = searchOption == SearchOption.AllDirectories;

            Path.Validate(full);

            string s = MonoIO.FindFirst(full, path_with_pattern, out rattr, out error, out handle);

            if (s == null)
            {
                yield break;
            }
            if (error != 0)
            {
                throw MonoIO.GetException(Path.GetDirectoryName(path_with_pattern), (MonoIOError)error);
            }

            try {
                if (((rattr & FileAttributes.ReparsePoint) == 0))
                {
                    if ((rattr & FileAttributes.Directory) != 0)
                    {
                        yield return(new DirectoryInfo(s));
                    }
                    else
                    {
                        yield return(new FileInfo(s));
                    }
                }

                while ((s = MonoIO.FindNext(handle, out rattr, out error)) != null)
                {
                    if ((rattr & FileAttributes.ReparsePoint) != 0)
                    {
                        continue;
                    }
                    if ((rattr & FileAttributes.Directory) != 0)
                    {
                        yield return(new DirectoryInfo(s));
                    }
                    else
                    {
                        yield return(new FileInfo(s));
                    }

                    if (((rattr & FileAttributes.Directory) != 0) && subdirs)
                    {
                        foreach (FileSystemInfo child in EnumerateFileSystemInfos(s, searchPattern, searchOption))
                        {
                            yield return(child);
                        }
                    }
                }
            } finally {
                MonoIO.FindClose(handle);
            }
        }
Exemple #3
0
        public static void Move(string sourceFileName, string destFileName)
        {
            if (sourceFileName == null)
            {
                throw new ArgumentNullException("sourceFileName");
            }
            if (destFileName == null)
            {
                throw new ArgumentNullException("destFileName");
            }
            if (sourceFileName.Length == 0)
            {
                throw new ArgumentException("An empty file name is not valid.", "sourceFileName");
            }
            if (sourceFileName.Trim().Length == 0 || sourceFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("The file name is not valid.");
            }
            if (destFileName.Length == 0)
            {
                throw new ArgumentException("An empty file name is not valid.", "destFileName");
            }
            if (destFileName.Trim().Length == 0 || destFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("The file name is not valid.");
            }

            SecurityManager.EnsureElevatedPermissions();              // this is a no-op outside moonlight

            MonoIOError error;

            if (!MonoIO.Exists(sourceFileName, out error))
            {
                throw new FileNotFoundException(Locale.GetText("{0} does not exist", sourceFileName), sourceFileName);
            }

            // Don't check for this error here to allow the runtime
            // to check if sourceFileName and destFileName are equal.
            // Comparing sourceFileName and destFileName is not enough.
            //if (MonoIO.Exists (destFileName, out error))
            //	throw new IOException (Locale.GetText ("{0} already exists", destFileName));

            string DirName;

            DirName = Path.GetDirectoryName(destFileName);
            if (DirName != String.Empty && !Directory.Exists(DirName))
            {
                throw new DirectoryNotFoundException(Locale.GetText("Could not find a part of the path."));
            }

            if (!MonoIO.MoveFile(sourceFileName, destFileName, out error))
            {
                if (error == MonoIOError.ERROR_ALREADY_EXISTS)
                {
                    throw MonoIO.GetException(error);
                }
                else if (error == MonoIOError.ERROR_SHARING_VIOLATION)
                {
                    throw MonoIO.GetException(sourceFileName, error);
                }

                throw MonoIO.GetException(error);
            }
        }
Exemple #4
0
        public static void Copy(string sourceFileName, string destFileName, bool overwrite)
        {
            MonoIOError error;

            if (sourceFileName == null)
            {
                throw new ArgumentNullException("sourceFileName");
            }
            if (destFileName == null)
            {
                throw new ArgumentNullException("destFileName");
            }
            if (sourceFileName.Length == 0)
            {
                throw new ArgumentException("An empty file name is not valid.", "sourceFileName");
            }
            if (sourceFileName.Trim().Length == 0 || sourceFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("The file name is not valid.");
            }
            if (destFileName.Length == 0)
            {
                throw new ArgumentException("An empty file name is not valid.", "destFileName");
            }
            if (destFileName.Trim().Length == 0 || destFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("The file name is not valid.");
            }

            SecurityManager.EnsureElevatedPermissions();              // this is a no-op outside moonlight

            if (!MonoIO.Exists(sourceFileName, out error))
            {
                throw new FileNotFoundException(Locale.GetText("{0} does not exist", sourceFileName), sourceFileName);
            }
            if ((GetAttributes(sourceFileName) & FileAttributes.Directory) == FileAttributes.Directory)
            {
                throw new ArgumentException(Locale.GetText("{0} is a directory", sourceFileName));
            }

            if (MonoIO.Exists(destFileName, out error))
            {
                if ((GetAttributes(destFileName) & FileAttributes.Directory) == FileAttributes.Directory)
                {
                    throw new ArgumentException(Locale.GetText("{0} is a directory", destFileName));
                }
                if (!overwrite)
                {
                    throw new IOException(Locale.GetText("{0} already exists", destFileName));
                }
            }

            string DirName = Path.GetDirectoryName(destFileName);

            if (DirName != String.Empty && !Directory.Exists(DirName))
            {
                throw new DirectoryNotFoundException(Locale.GetText("Destination directory not found: {0}", DirName));
            }

            if (!MonoIO.CopyFile(sourceFileName, destFileName, overwrite, out error))
            {
                string p = Locale.GetText("{0}\" or \"{1}", sourceFileName, destFileName);
                throw MonoIO.GetException(p, error);
            }
        }
Exemple #5
0
        internal static IEnumerable <string> EnumerateKind(string path, string searchPattern, SearchOption searchOption, FileAttributes kind)
        {
            if (searchPattern.Length == 0)
            {
                yield break;
            }

            bool   stop;
            string path_with_pattern = ValidateDirectoryListing(path, searchPattern, out stop);

            if (stop)
            {
                yield return(path_with_pattern);

                yield break;
            }

            IntPtr         handle;
            MonoIOError    error;
            FileAttributes rattr;
            string         s = MonoIO.FindFirst(path, path_with_pattern, out rattr, out error, out handle);

            try {
                while (s != null)
                {
                    // Convert any file specific flag to FileAttributes.Normal which is used as include files flag
                    if (((rattr & FileAttributes.Directory) == 0) && rattr != 0)
                    {
                        rattr |= FileAttributes.Normal;
                    }

                    if ((rattr & kind) != 0)
                    {
                        yield return(s);
                    }

                    s = MonoIO.FindNext(handle, out rattr, out error);
                }

                if (error != 0)
                {
                    throw MonoIO.GetException(Path.GetDirectoryName(Path.Combine(path, searchPattern)), (MonoIOError)error);
                }
            } finally {
                if (handle != IntPtr.Zero)
                {
                    MonoIO.FindClose(handle);
                }
            }

            if (searchOption == SearchOption.AllDirectories)
            {
                s = MonoIO.FindFirst(path, Path.Combine(path, "*"), out rattr, out error, out handle);

                try {
                    while (s != null)
                    {
                        if ((rattr & FileAttributes.Directory) != 0 && (rattr & FileAttributes.ReparsePoint) == 0)
                        {
                            foreach (string child in EnumerateKind(s, searchPattern, searchOption, kind))
                            {
                                yield return(child);
                            }
                        }
                        s = MonoIO.FindNext(handle, out rattr, out error);
                    }

                    if (error != 0)
                    {
                        throw MonoIO.GetException(path, (MonoIOError)error);
                    }
                } finally {
                    if (handle != IntPtr.Zero)
                    {
                        MonoIO.FindClose(handle);
                    }
                }
            }
        }
Exemple #6
0
        public override long Seek(long offset, SeekOrigin origin)
        {
            long pos;

            if (handle == MonoIO.InvalidHandle)
            {
                throw new ObjectDisposedException("Stream has been closed");
            }

            // make absolute

            if (CanSeek == false)
            {
                throw new NotSupportedException("The stream does not support seeking");
            }

            switch (origin)
            {
            case SeekOrigin.End:
                pos = Length + offset;
                break;

            case SeekOrigin.Current:
                pos = Position + offset;
                break;

            case SeekOrigin.Begin:
                pos = offset;
                break;

            default:
                throw new ArgumentException("origin", "Invalid SeekOrigin");
            }

            if (pos < 0)
            {
                /* LAMESPEC: shouldn't this be
                 * ArgumentOutOfRangeException?
                 */
                throw new IOException("Attempted to Seek before the beginning of the stream");
            }

            if (pos < this.append_startpos)
            {
                /* More undocumented crap */
                throw new IOException("Can't seek back over pre-existing data in append mode");
            }

            FlushBuffer();

            MonoIOError error;

            buf_start = MonoIO.Seek(handle, pos,
                                    SeekOrigin.Begin,
                                    out error);

            if (error != MonoIOError.ERROR_SUCCESS)
            {
                // don't leak the path information for isolated storage
                throw MonoIO.GetException(GetSecureFileName(name), error);
            }

            return(buf_start);
        }
Exemple #7
0
        public static void Replace(string sourceFileName,
                                   string destinationFileName,
                                   string destinationBackupFileName,
                                   bool ignoreMetadataErrors)
        {
            MonoIOError error;

            if (sourceFileName == null)
            {
                throw new ArgumentNullException("sourceFileName");
            }
            if (destinationFileName == null)
            {
                throw new ArgumentNullException("destinationFileName");
            }
            if (sourceFileName.Trim().Length == 0 || sourceFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("sourceFileName");
            }
            if (destinationFileName.Trim().Length == 0 || destinationFileName.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("destinationFileName");
            }

            string fullSource = Path.GetFullPath(sourceFileName);
            string fullDest   = Path.GetFullPath(destinationFileName);

            if (MonoIO.ExistsDirectory(fullSource, out error))
            {
                throw new IOException(Locale.GetText("{0} is a directory", sourceFileName));
            }
            if (MonoIO.ExistsDirectory(fullDest, out error))
            {
                throw new IOException(Locale.GetText("{0} is a directory", destinationFileName));
            }

            if (!Exists(fullSource))
            {
                throw new FileNotFoundException(Locale.GetText("{0} does not exist", sourceFileName),
                                                sourceFileName);
            }
            if (!Exists(fullDest))
            {
                throw new FileNotFoundException(Locale.GetText("{0} does not exist", destinationFileName),
                                                destinationFileName);
            }
            if (fullSource == fullDest)
            {
                throw new IOException(Locale.GetText("Source and destination arguments are the same file."));
            }

            string fullBackup = null;

            if (destinationBackupFileName != null)
            {
                if (destinationBackupFileName.Trim().Length == 0 ||
                    destinationBackupFileName.IndexOfAny(Path.InvalidPathChars) != -1)
                {
                    throw new ArgumentException("destinationBackupFileName");
                }

                fullBackup = Path.GetFullPath(destinationBackupFileName);
                if (MonoIO.ExistsDirectory(fullBackup, out error))
                {
                    throw new IOException(Locale.GetText("{0} is a directory", destinationBackupFileName));
                }
                if (fullSource == fullBackup)
                {
                    throw new IOException(Locale.GetText("Source and backup arguments are the same file."));
                }
                if (fullDest == fullBackup)
                {
                    throw new IOException(Locale.GetText(
                                              "Destination and backup arguments are the same file."));
                }
            }

            var attrs = GetAttributes(fullDest);

            // TODO: Should be done in wapi, win32 api handles this already
            if ((attrs & FileAttributes.ReadOnly) != 0)
            {
                throw MonoIO.GetException(MonoIOError.ERROR_ACCESS_DENIED);
            }

            if (!MonoIO.ReplaceFile(fullSource, fullDest, fullBackup,
                                    ignoreMetadataErrors, out error))
            {
                throw MonoIO.GetException(error);
            }
        }
Exemple #8
0
        internal FileStream(string path, FileMode mode, FileAccess access, FileShare share, int bufferSize, bool anonymous, FileOptions options)
        {
            if (path == null)
            {
                throw new ArgumentNullException("path");
            }

            if (path.Length == 0)
            {
                throw new ArgumentException("Path is empty");
            }

            this.anonymous = anonymous;
            // ignore the Inheritable flag
            share &= ~FileShare.Inheritable;

            if (bufferSize <= 0)
            {
                throw new ArgumentOutOfRangeException("bufferSize", "Positive number required.");
            }

            if (mode < FileMode.CreateNew || mode > FileMode.Append)
            {
#if NET_2_1
                if (anonymous)
                {
                    throw new ArgumentException("mode", "Enum value was out of legal range.");
                }
                else
#endif
                throw new ArgumentOutOfRangeException("mode", "Enum value was out of legal range.");
            }

            if (access < FileAccess.Read || access > FileAccess.ReadWrite)
            {
                throw new ArgumentOutOfRangeException("access", "Enum value was out of legal range.");
            }

            if (share < FileShare.None || share > (FileShare.ReadWrite | FileShare.Delete))
            {
                throw new ArgumentOutOfRangeException("share", "Enum value was out of legal range.");
            }

            if (path.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("Name has invalid chars");
            }

            if (Directory.Exists(path))
            {
                // don't leak the path information for isolated storage
                string msg = Locale.GetText("Access to the path '{0}' is denied.");
                throw new UnauthorizedAccessException(String.Format(msg, GetSecureFileName(path, false)));
            }

            /* Append streams can't be read (see FileMode
             * docs)
             */
            if (mode == FileMode.Append &&
                (access & FileAccess.Read) == FileAccess.Read)
            {
                throw new ArgumentException("Append access can be requested only in write-only mode.");
            }

            if ((access & FileAccess.Write) == 0 &&
                (mode != FileMode.Open && mode != FileMode.OpenOrCreate))
            {
                string msg = Locale.GetText("Combining FileMode: {0} with " +
                                            "FileAccess: {1} is invalid.");
                throw new ArgumentException(string.Format(msg, access, mode));
            }

            SecurityManager.EnsureElevatedPermissions();              // this is a no-op outside moonlight

            string dname;
            if (Path.DirectorySeparatorChar != '/' && path.IndexOf('/') >= 0)
            {
                dname = Path.GetDirectoryName(Path.GetFullPath(path));
            }
            else
            {
                dname = Path.GetDirectoryName(path);
            }
            if (dname.Length > 0)
            {
                string fp = Path.GetFullPath(dname);
                if (!Directory.Exists(fp))
                {
                    // don't leak the path information for isolated storage
                    string msg   = Locale.GetText("Could not find a part of the path \"{0}\".");
                    string fname = (anonymous) ? dname : Path.GetFullPath(path);
                    throw new DirectoryNotFoundException(String.Format(msg, fname));
                }
            }

            if (access == FileAccess.Read && mode != FileMode.Create && mode != FileMode.OpenOrCreate &&
                mode != FileMode.CreateNew && !File.Exists(path))
            {
                // don't leak the path information for isolated storage
                string msg   = Locale.GetText("Could not find file \"{0}\".");
                string fname = GetSecureFileName(path);
                throw new FileNotFoundException(String.Format(msg, fname), fname);
            }

            // IsolatedStorage needs to keep the Name property to the default "[Unknown]"
            if (!anonymous)
            {
                this.name = path;
            }

            // TODO: demand permissions

            MonoIOError error;

            this.handle = MonoIO.Open(path, mode, access, share, options, out error);
            if (handle == MonoIO.InvalidHandle)
            {
                // don't leak the path information for isolated storage
                throw MonoIO.GetException(GetSecureFileName(path), error);
            }

            this.access = access;
            this.owner  = true;

            /* Can we open non-files by name? */

            if (MonoIO.GetFileType(handle, out error) == MonoFileType.Disk)
            {
                this.canseek = true;
                this.async   = (options & FileOptions.Asynchronous) != 0;
            }
            else
            {
                this.canseek = false;
                this.async   = false;
            }


            if (access == FileAccess.Read && canseek && (bufferSize == DefaultBufferSize))
            {
                /* Avoid allocating a large buffer for small files */
                long len = Length;
                if (bufferSize > len)
                {
                    bufferSize = (int)(len < 1000 ? 1000 : len);
                }
            }

            InitBuffer(bufferSize, false);

            if (mode == FileMode.Append)
            {
                this.Seek(0, SeekOrigin.End);
                this.append_startpos = this.Position;
            }
            else
            {
                this.append_startpos = 0;
            }
        }
Exemple #9
0
        internal static IEnumerable <string> EnumerateKind(string path, string searchPattern, SearchOption searchOption, FileAttributes kind)
        {
            if (searchPattern.Length == 0)
            {
                yield break;
            }

            bool   stop;
            string path_with_pattern = ValidateDirectoryListing(path, searchPattern, out stop);

            if (stop)
            {
                yield return(path_with_pattern);

                yield break;
            }

            IntPtr         handle;
            MonoIOError    error;
            FileAttributes rattr;
            bool           subdirs = searchOption == SearchOption.AllDirectories;

            string s = MonoIO.FindFirst(path, path_with_pattern, out rattr, out error, out handle);

            if (s == null)
            {
                yield break;
            }
            if (error != 0)
            {
                throw MonoIO.GetException(Path.GetDirectoryName(Path.Combine(path, searchPattern)), (MonoIOError)error);
            }

            try {
                if (((rattr & FileAttributes.ReparsePoint) == 0) && ((rattr & kind) != 0))
                {
                    yield return(s);
                }

                while ((s = MonoIO.FindNext(handle, out rattr, out error)) != null)
                {
                    if ((rattr & FileAttributes.ReparsePoint) != 0)
                    {
                        continue;
                    }
                    if ((rattr & kind) != 0)
                    {
                        yield return(s);
                    }

                    if (((rattr & FileAttributes.Directory) != 0) && subdirs)
                    {
                        foreach (string child in EnumerateKind(s, searchPattern, searchOption, kind))
                        {
                            yield return(child);
                        }
                    }
                }
            } finally {
                MonoIO.FindClose(handle);
            }
        }
Exemple #10
0
        private static string [] GetFileSystemEntries(string path, string searchPattern, FileAttributes mask, FileAttributes attrs)
        {
            if (path == null || searchPattern == null)
            {
                throw new ArgumentNullException();
            }

            if (searchPattern.Length == 0)
            {
                return new string [] {}
            }
            ;

            if (path.Trim().Length == 0)
            {
                throw new ArgumentException("The Path does not have a valid format");
            }

            string wild     = Path.Combine(path, searchPattern);
            string wildpath = Path.GetDirectoryName(wild);

            if (wildpath.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("Path contains invalid characters");
            }

            if (wildpath.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                if (path.IndexOfAny(SearchPattern.InvalidChars) == -1)
                {
                    throw new ArgumentException("Path contains invalid characters", "path");
                }

                throw new ArgumentException("Pattern contains invalid characters", "pattern");
            }

            MonoIOError error;

            if (!MonoIO.ExistsDirectory(wildpath, out error))
            {
                if (error == MonoIOError.ERROR_SUCCESS)
                {
                    MonoIOError file_error;
                    if (MonoIO.ExistsFile(wildpath, out file_error))
                    {
                        return(new string [] { wildpath });
                    }
                }

                if (error != MonoIOError.ERROR_PATH_NOT_FOUND)
                {
                    throw MonoIO.GetException(wildpath, error);
                }

                if (wildpath.IndexOfAny(SearchPattern.WildcardChars) == -1)
                {
                    throw new DirectoryNotFoundException("Directory '" + wildpath + "' not found.");
                }

                if (path.IndexOfAny(SearchPattern.WildcardChars) == -1)
                {
                    throw new ArgumentException("Pattern is invalid", "searchPattern");
                }

                throw new ArgumentException("Path is invalid", "path");
            }

            string path_with_pattern = Path.Combine(wildpath, searchPattern);

            string [] result = MonoIO.GetFileSystemEntries(path, path_with_pattern, (int)attrs, (int)mask, out error);
            if (error != 0)
            {
                throw MonoIO.GetException(wildpath, error);
            }

            return(result);
        }
Exemple #11
0
        public static void Delete(string path)
        {
            if (path == null)
            {
                throw new ArgumentNullException("path");
            }

            if (path.Length == 0)
            {
                throw new ArgumentException("Path is empty");
            }

            if (path.IndexOfAny(Path.InvalidPathChars) != -1)
            {
                throw new ArgumentException("Path contains invalid chars");
            }

            if (path.Trim().Length == 0)
            {
                throw new ArgumentException("Only blank characters in path");
            }

            if (path == ":")
            {
                throw new NotSupportedException("Only ':' In path");
            }

            MonoIOError error;
            bool        success;

            if (MonoIO.ExistsSymlink(path, out error))
            {
                /* RemoveDirectory maps to rmdir()
                 * which fails on symlinks (ENOTDIR)
                 */
                success = MonoIO.DeleteFile(path, out error);
            }
            else
            {
                success = MonoIO.RemoveDirectory(path, out error);
            }

            if (!success)
            {
                /*
                 * FIXME:
                 * In io-layer/io.c rmdir returns error_file_not_found if directory does not exists.
                 * So maybe this could be handled somewhere else?
                 */
                if (error == MonoIOError.ERROR_FILE_NOT_FOUND)
                {
                    if (File.Exists(path))
                    {
                        throw new IOException("Directory does not exist, but a file of the same name exist.");
                    }
                    else
                    {
                        throw new DirectoryNotFoundException("Directory does not exist.");
                    }
                }
                else
                {
                    throw MonoIO.GetException(path, error);
                }
            }
        }
Exemple #12
0
        static internal IEnumerable <FileSystemInfo> EnumerateFileSystemInfos(string basePath, string searchPattern, SearchOption searchOption)
        {
            Path.Validate(basePath);

            SafeFindHandle findHandle = null;

            try {
                string filePath;
                int    nativeAttrs;

                string basePathWithPattern = Path.Combine(basePath, searchPattern);

                int nativeError;
                try {} finally {
                    findHandle = new SafeFindHandle(MonoIO.FindFirstFile(basePathWithPattern, out filePath, out nativeAttrs, out nativeError));
                }

                if (findHandle.IsInvalid)
                {
                    MonoIOError error = (MonoIOError)nativeError;
                    if (error != MonoIOError.ERROR_FILE_NOT_FOUND)
                    {
                        throw MonoIO.GetException(Path.GetDirectoryName(basePathWithPattern), error);
                    }

                    yield break;
                }

                do
                {
                    if (filePath == null)
                    {
                        yield break;
                    }

                    if (filePath == "." || filePath == "..")
                    {
                        continue;
                    }

                    FileAttributes attrs = (FileAttributes)nativeAttrs;

                    string fullPath = Path.Combine(basePath, filePath);

                    if ((attrs & FileAttributes.ReparsePoint) == 0)
                    {
                        if ((attrs & FileAttributes.Directory) != 0)
                        {
                            yield return(new DirectoryInfo(fullPath));
                        }
                        else
                        {
                            yield return(new FileInfo(fullPath));
                        }
                    }

                    if ((attrs & FileAttributes.Directory) != 0 && searchOption == SearchOption.AllDirectories)
                    {
                        foreach (FileSystemInfo child in EnumerateFileSystemInfos(fullPath, searchPattern, searchOption))
                        {
                            yield return(child);
                        }
                    }
                } while (MonoIO.FindNextFile(findHandle.DangerousGetHandle(), out filePath, out nativeAttrs, out int _));
            } finally {
                if (findHandle != null)
                {
                    findHandle.Dispose();
                }
            }
        }