예제 #1
0
        private FileObject.FileMemoryStream OpenStreamInternal(AbsolutePath path, FileAccess accessMode, FileMode mode, FileShare share)
        {
            if (mode == FileMode.CreateNew && accessMode == FileAccess.Read)
            {
                throw new ArgumentException("FileMode.CreateNew and FileAccess.Read is an invalid combination.");
            }

            lock (_drives)
            {
                FileObject fileObj = FindFileObjectAndParent(path, out var parent);

                if (parent == null)
                {
                    return(null);
                }

                switch (mode)
                {
                case FileMode.Create:
                    if (fileObj != null)
                    {
                        fileObj.DeleteLink(path, false);
                        parent.Children.Remove(path.FileName);
                    }

                    fileObj = new FileObject(path, this, new byte[] {});
                    parent.Children[path.FileName] = fileObj;
                    break;

                case FileMode.Open:
                    if (fileObj == null)
                    {
                        return(null);
                    }

                    break;

                case FileMode.OpenOrCreate:
                    if (fileObj == null)
                    {
                        fileObj = new FileObject(path, this, new byte[] {});
                        parent.Children[path.FileName] = fileObj;
                    }

                    break;

                case FileMode.CreateNew:
                    if (fileObj != null)
                    {
                        unchecked
                        {
                            throw new IOException("File already exists", new IOException("File exists", (int)Hresult.FileExists));
                        }
                    }

                    fileObj = new FileObject(path, this, new byte[] {});
                    parent.Children[path.FileName] = fileObj;
                    break;

                default:
                    throw new NotImplementedException($"Mode '{mode}' is not supported.");
                }

                var file = fileObj.Open(path, accessMode, share);
                if (accessMode.HasFlag(FileAccess.Write))
                {
                    _currentStatistics.FileOpensForWrite++;
                }
                else
                {
                    _currentStatistics.FileOpensForRead++;
                }

                return(file);
            }
        }
예제 #2
0
        /// <inheritdoc />
        /// <remarks>Ref count limit is not implemented for the In Memory file system.</remarks>
        public CreateHardLinkResult CreateHardLink(AbsolutePath sourceFileName, AbsolutePath destinationFileName, bool replaceExisting)
        {
            lock (_drives)
            {
                if (!_useHardLinks)
                {
                    return(CreateHardLinkResult.FailedNotSupported);
                }

                FileObject fileObj = FindFileObject(sourceFileName);

                if (fileObj == null)
                {
                    return(CreateHardLinkResult.FailedSourceDoesNotExist);
                }

                if (destinationFileName.Length >= FileSystemConstants.MaxPath)
                {
                    // Please note, we use FileSystemConstants.MaxPath that returns
                    // ShortMaxPath or LongMaxPath depending on whether the system supports long paths or not.
                    return(CreateHardLinkResult.FailedPathTooLong);
                }

                FileObject destination = FindFileObjectAndParent(destinationFileName, out var parentDestination);

                if (parentDestination == null)
                {
                    throw new IOException(
                              string.Format(CultureInfo.InvariantCulture, "Parent of destination {0} does not exist", destinationFileName.Path));
                }

                // ReSharper disable PossibleNullReferenceException
                char sourceDrive      = sourceFileName.DriveLetter;
                char destinationDrive = destinationFileName.DriveLetter;

                // ReSharper restore PossibleNullReferenceException
                if (sourceDrive != destinationDrive)
                {
                    return(CreateHardLinkResult.FailedSourceAndDestinationOnDifferentVolumes);
                }

                if (!fileObj.CanAddLink())
                {
                    return(CreateHardLinkResult.FailedMaxHardLinkLimitReached);
                }

                if (destination != null)
                {
                    if (!replaceExisting)
                    {
                        return(CreateHardLinkResult.FailedDestinationExists);
                    }

                    try
                    {
                        destination.DeleteLink(destinationFileName, false, true);
                    }
                    catch (UnauthorizedAccessException)
                    {
                        return(CreateHardLinkResult.FailedAccessDenied);
                    }
                }

                fileObj.AddLink(destinationFileName);
                parentDestination.Children[destinationFileName.FileName] = fileObj;
            }

            return(CreateHardLinkResult.Success);
        }