private void AlternateDataStream_Query_FileBasicInformation(FileType fileType)
        {
            //Prerequisites: Create streams on a newly created file

            //Step 1: Query FILE_BASIC_INFORMATION
            long byteCount;

            byte[] outputBuffer;
            FileBasicInformation fileBasicInfo = new FileBasicInformation();
            uint outputBufferSize = (uint)TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInfo).Length;

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "{0}. QueryFileInformation with FileInfoClass.FILE_BASIC_INFORMATION", ++testStep);
            status = this.fsaAdapter.QueryFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, outputBufferSize, out byteCount, out outputBuffer);
            this.fsaAdapter.AssertIfNotSuccess(status, "QueryFileInformation with FileInfoClass.FILE_BASIC_INFORMATION operation failed.");

            // Step 2: Verify FILE_BASIC_INFORMATION
            fileBasicInfo = TypeMarshal.ToStruct <FileBasicInformation>(outputBuffer);
            bool isIntegrityStreamSet = (fileBasicInfo.FileAttributes & (uint)FileAttribute.INTEGRITY_STREAM) == (uint)FileAttribute.INTEGRITY_STREAM;

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "{0}. Verify outputBuffer.FileAttributes.FILE_ATTRIBUTE_INTEGRITY_STREAM", ++testStep);
            if (this.fsaAdapter.IsIntegritySupported == true)
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, true, isIntegrityStreamSet,
                                               "If integrity is supported, the object store MUST set FILE_ATTRIBUTE_INTEGRITY_STREAM in OutputBuffer.FileAttributes.");
            }
            else
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, false, isIntegrityStreamSet, "Integrity is not supported, FILE_ATTRIBUTE_INTEGRITY_STREAM MUST NOT set.");
            }
        }
        private void FileInfo_Set_FileBasicInformation_Negative(FileType fileType)
        {
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Test case steps:");

            //Step 1: Create File
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "1. Create " + fileType.ToString() + " with FileAccess.FILE_WRITE_ATTRIBUTES");

            CreateFile(fileType);

            //Step 2: Set file basic information with invalid inputBuffer
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "2. SetFileInformation with FileInfoClass.FILE_BASIC_INFORMATION having invalid inputBuffer and verify NTSTATUS");

            byte[]        inputBuffer = new byte[1];
            MessageStatus status      = this.fsaAdapter.SetFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, inputBuffer);

            this.fsaAdapter.AssertAreEqual(this.Manager, MessageStatus.INFO_LENGTH_MISMATCH, status,
                                           "If InputBufferSize is less than sizeof(FILE_BASIC_INFORMATION), the operation MUST be failed with STATUS_INFO_LENGTH_MISMATCH.");

            //Step 3: Set file basic information to invalid values
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "3. SetFileInformation with FileInfoClass.FILE_BASIC_INFORMATION having invalid attribute values and verify NTSTATUS");

            FileBasicInformation fileBasicInformation = new FileBasicInformation();

            fileBasicInformation.FileAttributes = fileType == FileType.DataFile ? (uint)(FileAttribute.DIRECTORY | FileAttribute.NORMAL)
                : (uint)(FileAttribute.TEMPORARY | FileAttribute.NORMAL);

            TestFileAttributes(fileType, fileBasicInformation);
        }
예제 #3
0
        internal SMBFileInfo(string path,
                             IFileSystem fileSystem,
                             FileBasicInformation fileBasicInformation,
                             FileStandardInformation fileStandardInformation,
                             ISMBCredential credential) : this(path, fileSystem)
        {
            if (fileBasicInformation.CreationTime.Time.HasValue)
            {
                _creationTime    = fileBasicInformation.CreationTime.Time.Value;
                _creationTimeUtc = CreationTime.ToUniversalTime();
            }
            if (fileBasicInformation.LastAccessTime.Time.HasValue)
            {
                _lastAccessTime    = fileBasicInformation.LastAccessTime.Time.Value;
                _lastAccessTimeUtc = LastAccessTime.ToUniversalTime();
            }
            if (fileBasicInformation.LastWriteTime.Time.HasValue)
            {
                _lastWriteTime    = fileBasicInformation.LastWriteTime.Time.Value;
                _lastWriteTimeUtc = LastWriteTime.ToUniversalTime();
            }

            _attributes = (System.IO.FileAttributes)fileBasicInformation.FileAttributes;

            var pathUri          = new Uri(path);
            var parentUri        = pathUri.AbsoluteUri.EndsWith('/') ? new Uri(pathUri, "..") : new Uri(pathUri, ".");
            var parentPathString = parentUri.IsUnc ? parentUri.LocalPath : parentUri.AbsoluteUri;

            _directory     = _dirInfoFactory.FromDirectoryName(parentPathString, credential);
            _directoryName = Directory?.Name;
            _exists        = _file.Exists(path);
            _isReadOnly    = fileBasicInformation.FileAttributes.HasFlag(SMBLibrary.FileAttributes.ReadOnly);
            _length        = fileStandardInformation.EndOfFile;
        }
예제 #4
0
        public static NTStatus SetInformation(INTFileStore fileStore, string path, SMBFileAttributes fileAttributes, DateTime?lastWriteTime, SecurityContext securityContext)
        {
            object     handle;
            FileStatus fileStatus;
            NTStatus   status = fileStore.CreateFile(out handle, out fileStatus, path, (AccessMask)FileAccessMask.FILE_WRITE_ATTRIBUTES, (FileAttributes)0, ShareAccess.Read | ShareAccess.Write, CreateDisposition.FILE_OPEN, 0, securityContext);

            if (status != NTStatus.STATUS_SUCCESS)
            {
                return(status);
            }

            FileBasicInformation basicInfo = new FileBasicInformation();

            basicInfo.LastWriteTime = lastWriteTime;

            if ((fileAttributes & SMBFileAttributes.Hidden) > 0)
            {
                basicInfo.FileAttributes |= FileAttributes.Hidden;
            }

            if ((fileAttributes & SMBFileAttributes.ReadOnly) > 0)
            {
                basicInfo.FileAttributes |= FileAttributes.ReadOnly;
            }

            if ((fileAttributes & SMBFileAttributes.Archive) > 0)
            {
                basicInfo.FileAttributes |= FileAttributes.Archive;
            }

            status = fileStore.SetFileInformation(handle, basicInfo);
            fileStore.CloseFile(handle);
            return(status);
        }
예제 #5
0
        internal SMBFileInfo(string path,
                             IFileSystem fileSystem,
                             FileBasicInformation fileBasicInformation,
                             FileStandardInformation fileStandardInformation,
                             ISMBCredential credential) : this(path, fileSystem)
        {
            if (fileBasicInformation.CreationTime.Time.HasValue)
            {
                _creationTime    = fileBasicInformation.CreationTime.Time.Value;
                _creationTimeUtc = CreationTime.ToUniversalTime();
            }
            if (fileBasicInformation.LastAccessTime.Time.HasValue)
            {
                _lastAccessTime    = fileBasicInformation.LastAccessTime.Time.Value;
                _lastAccessTimeUtc = LastAccessTime.ToUniversalTime();
            }
            if (fileBasicInformation.LastWriteTime.Time.HasValue)
            {
                _lastWriteTime    = fileBasicInformation.LastWriteTime.Time.Value;
                _lastWriteTimeUtc = LastWriteTime.ToUniversalTime();
            }

            _attributes = (System.IO.FileAttributes)fileBasicInformation.FileAttributes;

            var parentPath = _fileSystem.Path.GetDirectoryName(path);


            _directory     = _dirInfoFactory.FromDirectoryName(parentPath, credential);
            _directoryName = parentPath;
            _exists        = _file.Exists(path);
            _isReadOnly    = fileBasicInformation.FileAttributes.HasFlag(SMBLibrary.FileAttributes.ReadOnly);
            _length        = fileStandardInformation.EndOfFile;
        }
예제 #6
0
        public static NTStatus SetInformation2(INTFileStore fileStore, object handle, DateTime?creationTime, DateTime?lastAccessTime, DateTime?lastWriteTime)
        {
            FileNetworkOpenInformation fileInfo  = NTFileStoreHelper.GetNetworkOpenInformation(fileStore, handle);
            FileBasicInformation       basicInfo = new FileBasicInformation();

            basicInfo.FileAttributes = fileInfo.FileAttributes;
            basicInfo.CreationTime   = creationTime;
            basicInfo.LastAccessTime = lastAccessTime;
            basicInfo.LastWriteTime  = lastWriteTime;
            return(fileStore.SetFileInformation(handle, basicInfo));
        }
예제 #7
0
 public FileAllInformation()
 {
     BasicInformation     = new FileBasicInformation();
     StandardInformation  = new FileStandardInformation();
     InternalInformation  = new FileInternalInformation();
     EaInformation        = new FileEaInformation();
     AccessInformation    = new FileAccessInformation();
     PositionInformation  = new FilePositionInformation();
     ModeInformation      = new FileModeInformation();
     AlignmentInformation = new FileAlignmentInformation();
     NameInformation      = new FileNameInformation();
 }
예제 #8
0
 public FileAllInformation(byte[] buffer, int offset)
 {
     BasicInformation     = new FileBasicInformation(buffer, offset + 0);
     StandardInformation  = new FileStandardInformation(buffer, offset + 40);
     InternalInformation  = new FileInternalInformation(buffer, offset + 64);
     EaInformation        = new FileEaInformation(buffer, offset + 72);
     AccessInformation    = new FileAccessInformation(buffer, offset + 76);
     PositionInformation  = new FilePositionInformation(buffer, offset + 80);
     ModeInformation      = new FileModeInformation(buffer, offset + 88);
     AlignmentInformation = new FileAlignmentInformation(buffer, offset + 92);
     NameInformation      = new FileNameInformation(buffer, offset + 96);
 }
예제 #9
0
        public static FileInformation ToFileInformation(SetInformation information)
        {
            switch (information)
            {
            case SetFileBasicInfo info:
            {
                SetFileBasicInfo     basicInfo     = info;
                FileBasicInformation fileBasicInfo = new FileBasicInformation
                {
                    CreationTime   = basicInfo.CreationTime,
                    LastAccessTime = basicInfo.LastAccessTime,
                    LastWriteTime  = basicInfo.LastWriteTime,
                    ChangeTime     = basicInfo.LastChangeTime,
                    FileAttributes = (FileAttributes)basicInfo.ExtFileAttributes,
                    Reserved       = basicInfo.Reserved
                };
                return(fileBasicInfo);
            }

            case SetFileDispositionInfo info:
            {
                FileDispositionInformation fileDispositionInfo = new FileDispositionInformation
                {
                    DeletePending = info.DeletePending
                };
                return(fileDispositionInfo);
            }

            case SetFileAllocationInfo info:
            {
                // This information level is used to set the file length in bytes.
                // Note: the input will NOT be a multiple of the cluster size / bytes per sector.
                FileAllocationInformation fileAllocationInfo = new FileAllocationInformation
                {
                    AllocationSize = info.AllocationSize
                };
                return(fileAllocationInfo);
            }

            case SetFileEndOfFileInfo info:
            {
                FileEndOfFileInformation fileEndOfFileInfo = new FileEndOfFileInformation
                {
                    EndOfFile = info.EndOfFile
                };
                return(fileEndOfFileInfo);
            }

            default:
                throw new NotImplementedException();
            }
        }
예제 #10
0
        private void QueryFileBasicInformation(out FileAttributes fileAttributes)
        {
            FileBasicInformation fileBasicInformation = new FileBasicInformation();
            uint outputBufferSize = (uint)TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInformation).Length;

            byte[] outputBuffer;
            this.fsaAdapter.QueryFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, outputBufferSize, out _, out outputBuffer);

            fileBasicInformation          = TypeMarshal.ToStruct <FileBasicInformation>(outputBuffer);
            fileAttributes.changeTime     = DateTime.FromFileTime((((long)fileBasicInformation.ChangeTime.dwHighDateTime) << 32) + fileBasicInformation.ChangeTime.dwLowDateTime);
            fileAttributes.creationTime   = DateTime.FromFileTime((((long)fileBasicInformation.CreationTime.dwHighDateTime) << 32) + fileBasicInformation.CreationTime.dwLowDateTime);
            fileAttributes.lastAccessTime = DateTime.FromFileTime((((long)fileBasicInformation.LastAccessTime.dwHighDateTime) << 32) + fileBasicInformation.LastAccessTime.dwLowDateTime);
            fileAttributes.lastWriteTime  = DateTime.FromFileTime((((long)fileBasicInformation.LastWriteTime.dwHighDateTime) << 32) + fileBasicInformation.LastWriteTime.dwLowDateTime);
            fileAttributes.isArchive      = (fileBasicInformation.FileAttributes & (uint)FileAttribute.ARCHIVE) == (uint)FileAttribute.ARCHIVE;
        }
예제 #11
0
        private void QueryFileBasicInformation(out long changeTime, out long creationTime
                                               , out long lastAccessTime, out long lastWriteTime)
        {
            FileBasicInformation fileBasicInformation = new FileBasicInformation();
            uint outputBufferSize = (uint)TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInformation).Length;

            byte[] outputBuffer;
            this.fsaAdapter.QueryFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, outputBufferSize, out _, out outputBuffer);

            fileBasicInformation = TypeMarshal.ToStruct <FileBasicInformation>(outputBuffer);
            changeTime           = (((long)fileBasicInformation.ChangeTime.dwHighDateTime) << 32) + fileBasicInformation.ChangeTime.dwLowDateTime;
            creationTime         = (((long)fileBasicInformation.CreationTime.dwHighDateTime) << 32) + fileBasicInformation.CreationTime.dwLowDateTime;
            lastAccessTime       = (((long)fileBasicInformation.LastAccessTime.dwHighDateTime) << 32) + fileBasicInformation.LastAccessTime.dwLowDateTime;
            lastWriteTime        = (((long)fileBasicInformation.LastWriteTime.dwHighDateTime) << 32) + fileBasicInformation.LastWriteTime.dwLowDateTime;
        }
예제 #12
0
        private void AlternateDataStream_Query_FileBasicInformation(FileType fileType)
        {
            //Prerequisites: Create streams on a newly created file

            //Query FILE_BASIC_INFORMATION
            long byteCount;

            byte[] outputBuffer;
            FileBasicInformation fileBasicInfo = new FileBasicInformation();
            uint outputBufferSize = (uint)TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInfo).Length;

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "{0}. QueryFileInformation with FileInfoClass.FILE_BASIC_INFORMATION", ++testStep);
            status = this.fsaAdapter.QueryFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, outputBufferSize, out byteCount, out outputBuffer);
            this.fsaAdapter.AssertIfNotSuccess(status, "QueryFileInformation with FileInfoClass.FILE_BASIC_INFORMATION operation failed.");
        }
예제 #13
0
        /// <summary>
        /// Get Node from Path and SMB-FileInfomation
        /// </summary>
        /// <param name="fullPath"></param>
        /// <param name="paramSet"></param>
        /// <param name="basicInfo"></param>
        /// <param name="stdInfo"></param>
        /// <returns></returns>
        public static Node Get(
            string fullPath,
            FixedParamSet paramSet,
            FileBasicInformation basicInfo,
            FileStandardInformation stdInfo = null
            )
        {
            if (paramSet == null)
            {
                throw new ArgumentException("Required paramSet.");
            }
            if (basicInfo == null)
            {
                throw new ArgumentException("Required info.");
            }

            var pathSet = PathSet.Parse(fullPath);

            if (basicInfo.FileAttributes.HasFlag(SMBLibrary.FileAttributes.Directory))
            {
                // Folder
                var result = NodeFactory.InnerGet(
                    NodeType.Folder,
                    pathSet,
                    paramSet
                    );
                result.Created      = basicInfo.CreationTime;
                result.Updated      = basicInfo.LastWriteTime;
                result.LastAccessed = basicInfo.LastAccessTime;

                return(result);
            }
            else
            {
                // File
                var result = NodeFactory.InnerGet(
                    NodeType.File,
                    pathSet,
                    paramSet
                    );
                result.Size         = stdInfo?.EndOfFile;
                result.Created      = basicInfo.CreationTime;
                result.Updated      = basicInfo.LastWriteTime;
                result.LastAccessed = basicInfo.LastAccessTime;

                return(result);
            }
        }
예제 #14
0
        private void FileInfo_Set_FileBasicInformation(FileType fileType)
        {
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Test case steps:");

            //Step 1: Create File
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "1. Create " + fileType.ToString() + " with FileAccess.FILE_WRITE_ATTRIBUTES");

            CreateFile(fileType);

            //Step 2: Set file basic information with invalid inputBuffer
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "2. SetFileInformation with FileInfoClass.FILE_BASIC_INFORMATION having invalid inputBuffer and verify NTSTATUS");

            byte[]        inputBuffer = new byte[1];
            MessageStatus status      = this.fsaAdapter.SetFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, inputBuffer);

            this.fsaAdapter.AssertAreEqual(this.Manager, MessageStatus.INFO_LENGTH_MISMATCH, status,
                                           "If InputBufferSize is less than sizeof(FILE_BASIC_INFORMATION), the operation MUST be failed with STATUS_INFO_LENGTH_MISMATCH.");

            //Step 3: Set file basic information time stamp values less than -2
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "3. SetFileInformation with FileInfoClass.FILE_BASIC_INFORMATION having invalid attribute values and verify NTSTATUS");
            SetChangeTime(-3);
            SetLastAccessTime(-3);
            SetLastWriteTime(-3);
            SetCreationTime(-3);

            FileBasicInformation fileBasicInformation = new FileBasicInformation();

            fileBasicInformation.FileAttributes = fileType == FileType.DataFile ? (uint)(FileAttribute.DIRECTORY | FileAttribute.NORMAL)
                : (uint)(FileAttribute.TEMPORARY | FileAttribute.NORMAL);

            TestFileAttributes(fileType, fileBasicInformation);

            //Step 4: Set FileBasicInformation with 0, -1 then -2 and verify system response
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "4. SetFileInformation with FileInfoClass.FILE_BASIC_INFORMATION having values 0, -1, then -2 and verify system response");
            if (fileType == FileType.DataFile &&
                (this.fsaAdapter.FileSystem == FileSystem.NTFS || this.fsaAdapter.FileSystem == FileSystem.REFS))
            {
                TestMinusTwoTimestamp(TimestampType.ChangeTime);
                TestMinusTwoTimestamp(TimestampType.LastAccessTime);
                TestMinusTwoTimestamp(TimestampType.LastWriteTime);
            }
            else if (fileType != FileType.DirectoryFile)
            {
                this.TestSite.Assume.Inconclusive("Value -2 for FileBasicInformation timestamps is only supported by NTFS and ReFS.");
            }
        }
예제 #15
0
        private void FileInfo_Query_FileBasicInfo_IsIntegritySupported(FileType fileType)
        {
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Test case steps:");
            MessageStatus status;

            //Step 1: Create File
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "1. Create " + fileType.ToString() + " with FileAttribute.INTEGRITY_STREAM");

            status = this.fsaAdapter.CreateFile(
                FileAttribute.NORMAL | FileAttribute.INTEGRITY_STREAM,                                             // Set Integrity field
                fileType == FileType.DataFile? CreateOptions.NON_DIRECTORY_FILE : CreateOptions.DIRECTORY_FILE,
                fileType == FileType.DataFile ? StreamTypeNameToOpen.DATA : StreamTypeNameToOpen.INDEX_ALLOCATION, //Stream Type
                FileAccess.GENERIC_READ | FileAccess.GENERIC_WRITE | FileAccess.FILE_WRITE_DATA | FileAccess.FILE_WRITE_ATTRIBUTES,
                ShareAccess.FILE_SHARE_READ | ShareAccess.FILE_SHARE_WRITE,
                CreateDisposition.OPEN_IF,
                StreamFoundType.StreamIsFound,
                SymbolicLinkType.IsNotSymbolicLink,
                fileType,
                FileNameStatus.PathNameValid);

            //Step 2: Query FILE_BASIC_INFORMATION
            long byteCount;

            byte[] outputBuffer;
            FileBasicInformation fileBasicInfo = new FileBasicInformation();
            uint outputBufferSize = (uint)TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInfo).Length;

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "2. QueryFileInformation with FileInfoClass.FILE_BASIC_INFORMATION");
            status = this.fsaAdapter.QueryFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, outputBufferSize, out byteCount, out outputBuffer);

            //Step 3: Verify test result
            fileBasicInfo = TypeMarshal.ToStruct <FileBasicInformation>(outputBuffer);
            bool isIntegrityStreamSet = (fileBasicInfo.FileAttributes & (uint)FileAttribute.INTEGRITY_STREAM) == (uint)FileAttribute.INTEGRITY_STREAM;

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "3. Verify outputBuffer.FileAttributes.FILE_ATTRIBUTE_INTEGRITY_STREAM");
            if (this.fsaAdapter.IsIntegritySupported == true)
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, true, isIntegrityStreamSet,
                                               "If integrity is supported, the object store MUST set FILE_ATTRIBUTE_INTEGRITY_STREAM in OutputBuffer.FileAttributes.");
            }
            else
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, false, isIntegrityStreamSet, "Integrity is not supported, FILE_ATTRIBUTE_INTEGRITY_STREAM MUST NOT set.");
            }
        }
예제 #16
0
        private void TestFileAttributes(FileType fileType, FileBasicInformation fileBasicInformation)
        {
            byte[]        inputBuffer = TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInformation);
            MessageStatus status      = this.fsaAdapter.SetFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, inputBuffer);
            bool          isDirectory = (fileBasicInformation.FileAttributes & (uint)FileAttribute.DIRECTORY) == (uint)FileAttribute.DIRECTORY;
            bool          isTemporary = (fileBasicInformation.FileAttributes & (uint)FileAttribute.TEMPORARY) == (uint)FileAttribute.TEMPORARY;

            if (isDirectory && fileType == FileType.DataFile)
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, MessageStatus.INVALID_PARAMETER, status,
                                               "If InputBuffer.FileAttributes.FILE_ATTRIBUTE_DIRECTORY is TRUE and Open.Stream.StreamType is DataStream., the operation MUST be failed with STATUS_INVALID_PARAMETER");
            }
            else if (isTemporary && fileType == FileType.DirectoryFile)
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, MessageStatus.INVALID_PARAMETER, status,
                                               "If InputBuffer.FileAttributes.FILE_ATTRIBUTE_TEMPORARY is TRUE and Open.File.FileType is DirectoryFile, the operation MUST be failed with STATUS_INVALID_PARAMETER");
            }
        }
예제 #17
0
        internal SMBDirectoryInfo(string fileName,
                                  FileInformation fileInfo,
                                  IFileSystem fileSystem,
                                  ISMBCredentialProvider credentialProvider,
                                  ISMBCredential credential) : this(fileName, fileSystem, credentialProvider)
        {
            FileBasicInformation fileDirectoryInformation = (FileBasicInformation)fileInfo;

            if (fileDirectoryInformation.CreationTime.Time.HasValue)
            {
                _creationTime    = fileDirectoryInformation.CreationTime.Time.Value;
                _creationTimeUtc = CreationTime.ToUniversalTime();
            }
            if (fileDirectoryInformation.LastAccessTime.Time.HasValue)
            {
                _lastAccessTime    = fileDirectoryInformation.LastAccessTime.Time.Value;
                _lastAccessTimeUtc = LastAccessTime.ToUniversalTime();
            }
            if (fileDirectoryInformation.LastWriteTime.Time.HasValue)
            {
                _lastWriteTime    = fileDirectoryInformation.LastWriteTime.Time.Value;
                _lastWriteTimeUtc = LastWriteTime.ToUniversalTime();
            }

            _parent     = _smbDirectory.GetParent(fileName, credential);
            _fileSystem = fileSystem;
            var pathRoot = _fileSystem.Path.GetPathRoot(fileName);

            if (pathRoot != fileName)
            {
                _root = _directoryInfoFactory.FromDirectoryName(pathRoot, credential);
            }
            else
            {
                _root = this;
            }

            _exists    = _fileSystem.Directory.Exists(FullName);
            _extension = string.Empty;
            _name      = _fullName.GetLastPathSegment().RemoveLeadingAndTrailingSeperators();
        }
 public static NTStatus SetFileInformation(INTFileStore fileStore, object handle, SetInformation information)
 {
     if (information is SetFileBasicInfo)
     {
         SetFileBasicInfo     basicInfo     = (SetFileBasicInfo)information;
         FileBasicInformation fileBasicInfo = new FileBasicInformation();
         fileBasicInfo.CreationTime   = basicInfo.CreationTime;
         fileBasicInfo.LastAccessTime = basicInfo.LastAccessTime;
         fileBasicInfo.LastWriteTime  = basicInfo.LastWriteTime;
         fileBasicInfo.ChangeTime     = basicInfo.LastChangeTime;
         fileBasicInfo.FileAttributes = (FileAttributes)basicInfo.ExtFileAttributes;
         fileBasicInfo.Reserved       = basicInfo.Reserved;
         return(fileStore.SetFileInformation(handle, fileBasicInfo));
     }
     else if (information is SetFileDispositionInfo)
     {
         FileDispositionInformation fileDispositionInfo = new FileDispositionInformation();
         fileDispositionInfo.DeletePending = ((SetFileDispositionInfo)information).DeletePending;
         return(fileStore.SetFileInformation(handle, fileDispositionInfo));
     }
     else if (information is SetFileAllocationInfo)
     {
         // This information level is used to set the file length in bytes.
         // Note: the input will NOT be a multiple of the cluster size / bytes per sector.
         FileAllocationInformation fileAllocationInfo = new FileAllocationInformation();
         fileAllocationInfo.AllocationSize = ((SetFileAllocationInfo)information).AllocationSize;
         return(fileStore.SetFileInformation(handle, fileAllocationInfo));
     }
     else if (information is SetFileEndOfFileInfo)
     {
         FileEndOfFileInformation fileEndOfFileInfo = new FileEndOfFileInformation();
         fileEndOfFileInfo.EndOfFile = ((SetFileEndOfFileInfo)information).EndOfFile;
         return(fileStore.SetFileInformation(handle, fileEndOfFileInfo));
     }
     else
     {
         return(NTStatus.STATUS_NOT_IMPLEMENTED);
     }
 }
예제 #19
0
 public static FileInformation ToFileInformation(SetInformation information)
 {
     if (information is SetFileBasicInfo)
     {
         SetFileBasicInfo     basicInfo     = (SetFileBasicInfo)information;
         FileBasicInformation fileBasicInfo = new FileBasicInformation();
         fileBasicInfo.CreationTime   = basicInfo.CreationTime;
         fileBasicInfo.LastAccessTime = basicInfo.LastAccessTime;
         fileBasicInfo.LastWriteTime  = basicInfo.LastWriteTime;
         fileBasicInfo.ChangeTime     = basicInfo.LastChangeTime;
         fileBasicInfo.FileAttributes = (FileAttributes)basicInfo.ExtFileAttributes;
         fileBasicInfo.Reserved       = basicInfo.Reserved;
         return(fileBasicInfo);
     }
     else if (information is SetFileDispositionInfo)
     {
         FileDispositionInformation fileDispositionInfo = new FileDispositionInformation();
         fileDispositionInfo.DeletePending = ((SetFileDispositionInfo)information).DeletePending;
         return(fileDispositionInfo);
     }
     else if (information is SetFileAllocationInfo)
     {
         // This information level is used to set the file length in bytes.
         // Note: the input will NOT be a multiple of the cluster size / bytes per sector.
         FileAllocationInformation fileAllocationInfo = new FileAllocationInformation();
         fileAllocationInfo.AllocationSize = ((SetFileAllocationInfo)information).AllocationSize;
         return(fileAllocationInfo);
     }
     else if (information is SetFileEndOfFileInfo)
     {
         FileEndOfFileInformation fileEndOfFileInfo = new FileEndOfFileInformation();
         fileEndOfFileInfo.EndOfFile = ((SetFileEndOfFileInfo)information).EndOfFile;
         return(fileEndOfFileInfo);
     }
     else
     {
         throw new NotImplementedException();
     }
 }
예제 #20
0
        private void SetCreationTime(long creationTime)
        {
            FileBasicInformation fileBasicInformation = new FileBasicInformation();

            fileBasicInformation.CreationTime.dwHighDateTime = (uint)(creationTime >> 32);
            fileBasicInformation.CreationTime.dwLowDateTime  = (uint)(creationTime & 0xFFFFFFFF);
            fileBasicInformation.Reserved       = 0;
            fileBasicInformation.FileAttributes = (uint)FileAttribute.NORMAL;
            byte[]        inputBuffer = TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInformation);
            MessageStatus status      = this.fsaAdapter.SetFileInformation(FileInfoClass.FILE_BASIC_INFORMATION, inputBuffer);

            if (creationTime < -2)
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, MessageStatus.INVALID_PARAMETER, status,
                                               "If CreationTime is less than -2, the operation MUST be failed with STATUS_INVALID_PARAMETER");
            }
            else
            {
                this.fsaAdapter.AssertAreEqual(this.Manager, MessageStatus.SUCCESS, status,
                                               "Set file information should succeed");
            }
        }
예제 #21
0
 public static extern NTStatus NtQueryAttributesFile(
     ref OBJECT_ATTRIBUTES ObjectAttributes,
     out FileBasicInformation FileInformation);
예제 #22
0
 protected override void PopulateData(string originalPath, SafeFileHandle fileHandle, FileBasicInformation info)
 {
     base.PopulateData(originalPath, fileHandle, info);
     Length     = (ulong)Storage.GetFileSize(fileHandle);
     _directory = Paths.GetDirectory(Path);
 }
예제 #23
0
        new internal static IFileSystemInformation Create(string originalPath, SafeFileHandle fileHandle, FileBasicInformation info, IFileService fileService)
        {
            if ((info.FileAttributes & FileAttributes.Directory) == 0)
            {
                throw new ArgumentOutOfRangeException(nameof(info));
            }

            var directoryInfo = new DirectoryInformation(fileService);

            directoryInfo.PopulateData(originalPath, fileHandle, info);
            return(directoryInfo);
        }
예제 #24
0
 internal static IFileSystemInformation Create(string originalPath, SafeFileHandle fileHandle, FileBasicInformation info, IFileService fileService)
 {
     if ((info.FileAttributes & FileAttributes.Directory) != 0)
     {
         return(DirectoryInformation.Create(originalPath, fileHandle, info, fileService));
     }
     else
     {
         return(FileInformation.Create(originalPath, fileHandle, info, fileService));
     }
 }
예제 #25
0
        protected virtual void PopulateData(string originalPath, SafeFileHandle fileHandle, FileBasicInformation info)
        {
            _source = Source.FileInfo;

            string finalPath = originalPath;

            try
            {
                string originalRoot = Paths.GetRoot(originalPath);
                finalPath = Storage.GetFinalPathNameByHandle(fileHandle, GetFinalPathNameByHandleFlags.FileNameNormalized);

                // GetFinalPathNameByHandle will use the legacy drive for the volume (e.g. \\?\C:\). We may have started with C:\ or some other
                // volume name format (\\?\Volume({GUID}), etc.) and we want to put the original volume specifier back.
                finalPath = Paths.ReplaceCasing(finalPath, originalPath);
            }
            catch
            {
                if (originalPath.IndexOf(@"pipe", StringComparison.OrdinalIgnoreCase) == -1)
                {
                    // Getting the final path name doesn't work with the pipes device. Not sure if there is a programmatic way
                    // to know if an arbitrary file handle won't work with GetFinalPathName- potentially may be other cases.
                    throw;
                }
            }

            _source        = Source.FindResult;
            Path           = finalPath;
            Attributes     = (System.IO.FileAttributes)info.FileAttributes;
            CreationTime   = info.CreationTime.ToDateTimeUtc();
            LastAccessTime = info.LastAccessTime.ToDateTimeUtc();
            LastWriteTime  = info.LastWriteTime.ToDateTimeUtc();
            Name           = Paths.GetFileOrDirectoryName(finalPath) ?? finalPath;
            Exists         = true;
        }
예제 #26
0
        public void BVT_SMB2Basic_QueryAndSet_FileInfo()
        {
            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Starts a client by sending the following requests: NEGOTIATE; SESSION_SETUP; TREE_CONNECT.");
            client1 = new Smb2FunctionalClient(TestConfig.Timeout, TestConfig, BaseTestSite);
            client1.ConnectToServer(TestConfig.UnderlyingTransport, TestConfig.SutComputerName, TestConfig.SutIPAddress);
            client1.Negotiate(TestConfig.RequestDialects, TestConfig.IsSMB1NegotiateEnabled);
            client1.SessionSetup(
                TestConfig.DefaultSecurityPackage,
                TestConfig.SutComputerName,
                TestConfig.AccountCredential,
                TestConfig.UseServerGssToken);
            uint treeId1;

            client1.TreeConnect(uncSharePath, out treeId1);

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client sends CREATE request with desired access set to GENERIC_READ and GENERIC_WRITE to create a file.");
            Smb2CreateContextResponse[] serverCreateContexts;
            CREATE_Response?            createResponse = null;
            string fileName = Guid.NewGuid().ToString() + ".txt";
            FILEID fileId1;

            client1.Create(
                treeId1,
                fileName,
                CreateOptions_Values.FILE_NON_DIRECTORY_FILE,
                out fileId1,
                out serverCreateContexts,
                accessMask: AccessMask.GENERIC_READ | AccessMask.GENERIC_WRITE,
                checker: (Packet_Header header, CREATE_Response response) =>
            {
                BaseTestSite.Assert.AreEqual(
                    Smb2Status.STATUS_SUCCESS,
                    header.Status,
                    "CREATE should succeed, actually server returns {0}.", Smb2Status.GetStatusCode(header.Status));

                BaseTestSite.Log.Add(LogEntryKind.TestStep,
                                     "FileBasicInformation in CREATE response: \r\nCreationTime: {0}\r\nLastAccessTime:{1}\r\nLastWriteTime: {2}\r\nChangeTime: {3}\r\nFileAttributes: {4}",
                                     Smb2Utility.ConvertToDateTimeUtc(response.CreationTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                     Smb2Utility.ConvertToDateTimeUtc(response.LastAccessTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                     Smb2Utility.ConvertToDateTimeUtc(response.LastWriteTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                     Smb2Utility.ConvertToDateTimeUtc(response.ChangeTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                     response.FileAttributes);
                createResponse = response;
            });

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client sends QUERY_INFO request to query file attributes.");
            byte[] outputBuffer;
            client1.QueryFileAttributes(
                treeId1,
                (byte)FileInformationClasses.FileBasicInformation,
                QUERY_INFO_Request_Flags_Values.SL_RESTART_SCAN,
                fileId1,
                new byte[0] {
            },
                out outputBuffer);

            FileBasicInformation fileBasicInfo = TypeMarshal.ToStruct <FileBasicInformation>(outputBuffer);

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "FileBasicInformation in QUERY_INFO response: \r\nCreationTime: {0}\r\nLastAccessTime:{1}\r\nLastWriteTime: {2}\r\nChangeTime: {3}\r\nFileAttributes: {4}",
                                 Smb2Utility.ConvertToDateTimeUtc(fileBasicInfo.CreationTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                 Smb2Utility.ConvertToDateTimeUtc(fileBasicInfo.LastAccessTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                 Smb2Utility.ConvertToDateTimeUtc(fileBasicInfo.LastWriteTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                 Smb2Utility.ConvertToDateTimeUtc(fileBasicInfo.ChangeTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"),
                                 fileBasicInfo.FileAttributes);

            BaseTestSite.Assert.AreEqual(createResponse.Value.CreationTime, fileBasicInfo.CreationTime, "CreationTime received in QUERY_INFO response should be identical with that got in CREATE response");
            BaseTestSite.Assert.AreEqual(createResponse.Value.LastAccessTime, fileBasicInfo.LastAccessTime, "LastAccessTime received in QUERY_INFO response should be identical with that got in CREATE response");
            BaseTestSite.Assert.AreEqual(createResponse.Value.LastWriteTime, fileBasicInfo.LastWriteTime, "LastWriteTime received in QUERY_INFO response should be identical with that got in CREATE response");
            BaseTestSite.Assert.AreEqual(createResponse.Value.ChangeTime, fileBasicInfo.ChangeTime, "ChangeTime received in QUERY_INFO response should be identical with that got in CREATE response");
            BaseTestSite.Assert.AreEqual(createResponse.Value.FileAttributes, fileBasicInfo.FileAttributes, "FileAttributes received in QUERY_INFO response should be identical with that got in CREATE response");

            FileBasicInformation fileBasicInfoToSet = fileBasicInfo;
            DateTime             dateTimeToSet      = DateTime.UtcNow;

            fileBasicInfoToSet.LastAccessTime = Smb2Utility.ConvertToFileTime(dateTimeToSet);

            byte[] inputBuffer;
            inputBuffer = TypeMarshal.ToBytes <FileBasicInformation>(fileBasicInfoToSet);
            BaseTestSite.Log.Add(
                LogEntryKind.TestStep,
                "Client sends SetFileAttributes request to set LastAccessTime for the file to {0}", dateTimeToSet.ToString("MM/dd/yyy hh:mm:ss.ffffff"));
            client1.SetFileAttributes(
                treeId1,
                (byte)FileInformationClasses.FileBasicInformation,
                fileId1,
                inputBuffer);

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Client sends QUERY request to query file attributes.");
            client1.QueryFileAttributes(
                treeId1,
                (byte)FileInformationClasses.FileBasicInformation,
                QUERY_INFO_Request_Flags_Values.SL_RESTART_SCAN,
                fileId1,
                new byte[0] {
            },
                out outputBuffer);
            fileBasicInfo = TypeMarshal.ToStruct <FileBasicInformation>(outputBuffer);
            BaseTestSite.Log.Add(
                LogEntryKind.TestStep,
                "LastAccessTime in QUERY_INFO response after SET_INFO {0}",
                Smb2Utility.ConvertToDateTimeUtc(fileBasicInfo.LastAccessTime).ToString("MM/dd/yyy hh:mm:ss.ffffff"));

            BaseTestSite.Assert.AreNotEqual(
                createResponse.Value.LastAccessTime,
                fileBasicInfo.LastAccessTime,
                "LastAccessTime (dwHighDateTime:{0}, dwLowDateTime:{1}) after SET_INFO should not be equal to the value (dwHighDateTime:{2}, dwLowDateTime:{3}) before SET_INFO",
                fileBasicInfo.LastAccessTime.dwHighDateTime, fileBasicInfo.LastAccessTime.dwLowDateTime, createResponse.Value.LastAccessTime.dwHighDateTime, createResponse.Value.LastAccessTime.dwLowDateTime);

            BaseTestSite.Assert.AreEqual(
                fileBasicInfoToSet.LastAccessTime,
                fileBasicInfo.LastAccessTime,
                "LastAccessTime (dwHighDateTime:{0}, dwLowDateTime:{1}) queried after SET_INFO should be equal to the desired value (dwHighDateTime:{2}, dwLowDateTime:{3})",
                fileBasicInfo.LastAccessTime.dwHighDateTime, fileBasicInfo.LastAccessTime.dwLowDateTime, fileBasicInfoToSet.LastAccessTime.dwHighDateTime, fileBasicInfoToSet.LastAccessTime.dwLowDateTime);

            BaseTestSite.Log.Add(LogEntryKind.TestStep, "Tear down the client by sending the following requests: CLOSE; TREE_DISCONNECT; LOG_OFF");
            client1.Close(treeId1, fileId1);
            client1.TreeDisconnect(treeId1);
            client1.LogOff();
        }
예제 #27
0
        public NTStatus GetFileInformation(out FileInformation result, object handle, FileInformationClass informationClass)
        {
            FileHandle      fileHandle = (FileHandle)handle;
            string          path       = fileHandle.Path;
            FileSystemEntry entry;

            try
            {
                entry = m_fileSystem.GetEntry(path);
            }
            catch (Exception ex)
            {
                if (ex is IOException || ex is UnauthorizedAccessException)
                {
                    NTStatus status = ToNTStatus(ex);
                    Log(Severity.Verbose, "GetFileInformation on '{0}' failed. {1}", path, status);
                    result = null;
                    return(status);
                }
                else
                {
                    throw;
                }
            }

            switch (informationClass)
            {
            case FileInformationClass.FileBasicInformation:
            {
                FileBasicInformation information = new FileBasicInformation();
                information.CreationTime   = entry.CreationTime;
                information.LastAccessTime = entry.LastAccessTime;
                information.LastWriteTime  = entry.LastWriteTime;
                information.ChangeTime     = entry.LastWriteTime;
                information.FileAttributes = GetFileAttributes(entry);
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FileStandardInformation:
            {
                FileStandardInformation information = new FileStandardInformation();
                information.AllocationSize = (long)GetAllocationSize(entry.Size);
                information.EndOfFile      = (long)entry.Size;
                information.Directory      = entry.IsDirectory;
                information.DeletePending  = fileHandle.DeleteOnClose;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FileInternalInformation:
            {
                FileInternalInformation information = new FileInternalInformation();
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FileEaInformation:
            {
                FileEaInformation information = new FileEaInformation();
                information.EaSize = 0;
                result             = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FileAccessInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileNameInformation:
            {
                FileNameInformation information = new FileNameInformation();
                information.FileName = entry.Name;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FilePositionInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileFullEaInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileModeInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileAlignmentInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileAllInformation:
            {
                FileAllInformation information = new FileAllInformation();
                information.BasicInformation.CreationTime      = entry.CreationTime;
                information.BasicInformation.LastAccessTime    = entry.LastAccessTime;
                information.BasicInformation.LastWriteTime     = entry.LastWriteTime;
                information.BasicInformation.ChangeTime        = entry.LastWriteTime;
                information.BasicInformation.FileAttributes    = GetFileAttributes(entry);
                information.StandardInformation.AllocationSize = (long)GetAllocationSize(entry.Size);
                information.StandardInformation.EndOfFile      = (long)entry.Size;
                information.StandardInformation.Directory      = entry.IsDirectory;
                information.StandardInformation.DeletePending  = fileHandle.DeleteOnClose;
                information.NameInformation.FileName           = entry.Name;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FileAlternateNameInformation:
            {
                // If there is no alternate name Windows will return STATUS_OBJECT_NAME_NOT_FOUND
                result = null;
                return(NTStatus.STATUS_OBJECT_NAME_NOT_FOUND);
            }

            case FileInformationClass.FileStreamInformation:
            {
                // This information class is used to enumerate the data streams of a file or a directory.
                // A buffer of FileStreamInformation data elements is returned by the server.
                FileStreamInformation information = new FileStreamInformation();
                List <KeyValuePair <string, ulong> > dataStreams = m_fileSystem.ListDataStreams(fileHandle.Path);
                foreach (KeyValuePair <string, ulong> dataStream in dataStreams)
                {
                    FileStreamEntry streamEntry = new FileStreamEntry();
                    ulong           streamSize  = dataStream.Value;
                    streamEntry.StreamSize           = (long)streamSize;
                    streamEntry.StreamAllocationSize = (long)GetAllocationSize(streamSize);
                    streamEntry.StreamName           = dataStream.Key;
                    information.Entries.Add(streamEntry);
                }
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FilePipeInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FilePipeLocalInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FilePipeRemoteInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileCompressionInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case FileInformationClass.FileNetworkOpenInformation:
            {
                FileNetworkOpenInformation information = new FileNetworkOpenInformation();
                information.CreationTime   = entry.CreationTime;
                information.LastAccessTime = entry.LastAccessTime;
                information.LastWriteTime  = entry.LastWriteTime;
                information.ChangeTime     = entry.LastWriteTime;
                information.AllocationSize = (long)GetAllocationSize(entry.Size);
                information.EndOfFile      = (long)entry.Size;
                information.FileAttributes = GetFileAttributes(entry);
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case FileInformationClass.FileAttributeTagInformation:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            default:
                result = null;
                return(NTStatus.STATUS_INVALID_INFO_CLASS);
            }
        }
예제 #28
0
 public static QueryInformation FromFileInformation(FileInformation fileInformation)
 {
     if (fileInformation is FileBasicInformation)
     {
         FileBasicInformation fileBasicInfo = (FileBasicInformation)fileInformation;
         QueryFileBasicInfo   result        = new QueryFileBasicInfo();
         result.CreationTime      = fileBasicInfo.CreationTime;
         result.LastAccessTime    = fileBasicInfo.LastAccessTime;
         result.LastWriteTime     = fileBasicInfo.LastWriteTime;
         result.LastChangeTime    = fileBasicInfo.ChangeTime;
         result.ExtFileAttributes = (ExtendedFileAttributes)fileBasicInfo.FileAttributes;
         return(result);
     }
     else if (fileInformation is FileStandardInformation)
     {
         FileStandardInformation fileStandardInfo = (FileStandardInformation)fileInformation;
         QueryFileStandardInfo   result           = new QueryFileStandardInfo();
         result.AllocationSize = fileStandardInfo.AllocationSize;
         result.EndOfFile      = fileStandardInfo.EndOfFile;
         result.DeletePending  = fileStandardInfo.DeletePending;
         result.Directory      = fileStandardInfo.Directory;
         return(result);
     }
     else if (fileInformation is FileEaInformation)
     {
         FileEaInformation fileEAInfo = (FileEaInformation)fileInformation;
         QueryFileEaInfo   result     = new QueryFileEaInfo();
         result.EaSize = fileEAInfo.EaSize;
         return(result);
     }
     else if (fileInformation is FileNameInformation)
     {
         FileNameInformation fileNameInfo = (FileNameInformation)fileInformation;
         QueryFileNameInfo   result       = new QueryFileNameInfo();
         result.FileName = fileNameInfo.FileName;
         return(result);
     }
     else if (fileInformation is FileAllInformation)
     {
         FileAllInformation fileAllInfo = (FileAllInformation)fileInformation;
         QueryFileAllInfo   result      = new QueryFileAllInfo();
         result.CreationTime      = fileAllInfo.BasicInformation.CreationTime;
         result.LastAccessTime    = fileAllInfo.BasicInformation.LastAccessTime;
         result.LastWriteTime     = fileAllInfo.BasicInformation.LastWriteTime;
         result.LastChangeTime    = fileAllInfo.BasicInformation.ChangeTime;
         result.ExtFileAttributes = (ExtendedFileAttributes)fileAllInfo.BasicInformation.FileAttributes;
         result.AllocationSize    = fileAllInfo.StandardInformation.AllocationSize;
         result.EndOfFile         = fileAllInfo.StandardInformation.EndOfFile;
         result.DeletePending     = fileAllInfo.StandardInformation.DeletePending;
         result.Directory         = fileAllInfo.StandardInformation.Directory;
         result.EaSize            = fileAllInfo.EaInformation.EaSize;
         result.FileName          = fileAllInfo.NameInformation.FileName;
         return(result);
     }
     else if (fileInformation is FileAlternateNameInformation)
     {
         FileAlternateNameInformation fileAltNameInfo = (FileAlternateNameInformation)fileInformation;
         QueryFileAltNameInfo         result          = new QueryFileAltNameInfo();
         result.FileName = fileAltNameInfo.FileName;
         return(result);
     }
     else if (fileInformation is FileStreamInformation)
     {
         FileStreamInformation fileStreamInfo = (FileStreamInformation)fileInformation;
         QueryFileStreamInfo   result         = new QueryFileStreamInfo();
         result.Entries.AddRange(fileStreamInfo.Entries);
         return(result);
     }
     else if (fileInformation is FileCompressionInformation)
     {
         FileCompressionInformation fileCompressionInfo = (FileCompressionInformation)fileInformation;
         QueryFileCompressionInfo   result = new QueryFileCompressionInfo();
         result.CompressedFileSize   = fileCompressionInfo.CompressedFileSize;
         result.CompressionFormat    = fileCompressionInfo.CompressionFormat;
         result.CompressionUnitShift = fileCompressionInfo.CompressionUnitShift;
         result.ChunkShift           = fileCompressionInfo.ChunkShift;
         result.ClusterShift         = fileCompressionInfo.ClusterShift;
         result.Reserved             = fileCompressionInfo.Reserved;
         return(result);
     }
     else
     {
         throw new NotImplementedException();
     }
 }
        public static NTStatus GetFileInformation(out QueryInformation result, INTFileStore fileStore, object handle, QueryInformationLevel informationLevel)
        {
            result = null;
            FileInformation fileInfo;

            switch (informationLevel)
            {
            case QueryInformationLevel.SMB_INFO_QUERY_ALL_EAS:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case QueryInformationLevel.SMB_INFO_IS_NAME_VALID:
            {
                result = null;
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_BASIC_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileBasicInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileBasicInformation fileBasicInfo = (FileBasicInformation)fileInfo;

                QueryFileBasicInfo information = new QueryFileBasicInfo();
                information.CreationTime      = fileBasicInfo.CreationTime;
                information.LastAccessTime    = fileBasicInfo.LastAccessTime;
                information.LastWriteTime     = fileBasicInfo.LastWriteTime;
                information.LastChangeTime    = fileBasicInfo.LastWriteTime;
                information.ExtFileAttributes = (ExtendedFileAttributes)fileBasicInfo.FileAttributes;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_STANDARD_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileStandardInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileStandardInformation fileStandardInfo = (FileStandardInformation)fileInfo;

                QueryFileStandardInfo information = new QueryFileStandardInfo();
                information.AllocationSize = fileStandardInfo.AllocationSize;
                information.EndOfFile      = fileStandardInfo.EndOfFile;
                information.DeletePending  = fileStandardInfo.DeletePending;
                information.Directory      = fileStandardInfo.Directory;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_EA_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileEaInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileEaInformation fileEAInfo = (FileEaInformation)fileInfo;

                QueryFileExtendedAttributeInfo information = new QueryFileExtendedAttributeInfo();
                information.EASize = fileEAInfo.EaSize;
                result             = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_NAME_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileNameInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileNameInformation fileNameInfo = (FileNameInformation)fileInfo;

                QueryFileNameInfo information = new QueryFileNameInfo();
                information.FileName = fileNameInfo.FileName;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_ALL_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileAllInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileAllInformation fileAllInfo = (FileAllInformation)fileInfo;

                QueryFileAllInfo information = new QueryFileAllInfo();
                information.CreationDateTime   = fileAllInfo.BasicInformation.CreationTime;
                information.LastAccessDateTime = fileAllInfo.BasicInformation.LastAccessTime;
                information.LastWriteDateTime  = fileAllInfo.BasicInformation.LastWriteTime;
                information.LastChangeTime     = fileAllInfo.BasicInformation.LastWriteTime;
                information.ExtFileAttributes  = (ExtendedFileAttributes)fileAllInfo.BasicInformation.FileAttributes;
                information.AllocationSize     = fileAllInfo.StandardInformation.AllocationSize;
                information.EndOfFile          = fileAllInfo.StandardInformation.EndOfFile;
                information.DeletePending      = fileAllInfo.StandardInformation.DeletePending;
                information.Directory          = fileAllInfo.StandardInformation.Directory;
                information.EASize             = fileAllInfo.EaInformation.EaSize;
                information.FileName           = fileAllInfo.NameInformation.FileName;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_ALT_NAME_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileAlternateNameInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileAlternateNameInformation fileAltNameInfo = (FileAlternateNameInformation)fileInfo;

                QueryFileAltNameInfo information = new QueryFileAltNameInfo();
                information.FileName = fileAltNameInfo.FileName;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_STREAM_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileStreamInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileStreamInformation fileStreamInfo = (FileStreamInformation)fileInfo;

                QueryFileStreamInfo information = new QueryFileStreamInfo();
                information.StreamSize           = fileStreamInfo.StreamSize;
                information.StreamAllocationSize = fileStreamInfo.StreamAllocationSize;
                information.StreamName           = fileStreamInfo.StreamName;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            case QueryInformationLevel.SMB_QUERY_FILE_COMPRESSION_INFO:
            {
                NTStatus status = fileStore.GetFileInformation(out fileInfo, handle, FileInformationClass.FileCompressionInformation);
                if (status != NTStatus.STATUS_SUCCESS)
                {
                    return(status);
                }

                FileCompressionInformation fileCompressionInfo = (FileCompressionInformation)fileInfo;

                QueryFileCompressionInfo information = new QueryFileCompressionInfo();
                information.CompressedFileSize   = fileCompressionInfo.CompressedFileSize;
                information.CompressionFormat    = fileCompressionInfo.CompressionFormat;
                information.CompressionUnitShift = fileCompressionInfo.CompressionUnitShift;
                information.ChunkShift           = fileCompressionInfo.ChunkShift;
                information.ClusterShift         = fileCompressionInfo.ClusterShift;
                information.Reserved             = fileCompressionInfo.Reserved;
                result = information;
                return(NTStatus.STATUS_SUCCESS);
            }

            default:
            {
                result = null;
                return(NTStatus.STATUS_OS2_INVALID_LEVEL);
            }
            }
        }
예제 #30
0
        public NTStatus SetFileInformation(object handle, FileInformation information)
        {
            FileHandle fileHandle = (FileHandle)handle;

            if (information is FileBasicInformation)
            {
                FileBasicInformation basicInformation = (FileBasicInformation)information;
                bool isHidden   = ((basicInformation.FileAttributes & FileAttributes.Hidden) > 0);
                bool isReadonly = (basicInformation.FileAttributes & FileAttributes.ReadOnly) > 0;
                bool isArchived = (basicInformation.FileAttributes & FileAttributes.Archive) > 0;
                try
                {
                    m_fileSystem.SetAttributes(fileHandle.Path, isHidden, isReadonly, isArchived);
                }
                catch (Exception ex)
                {
                    if (ex is IOException || ex is UnauthorizedAccessException)
                    {
                        NTStatus status = ToNTStatus(ex);
                        Log(Severity.Verbose, "SetFileInformation: Failed to set file attributes on '{0}'. {1}.", fileHandle.Path, status);
                        return(status);
                    }
                    else
                    {
                        throw;
                    }
                }

                try
                {
                    m_fileSystem.SetDates(fileHandle.Path, basicInformation.CreationTime, basicInformation.LastWriteTime, basicInformation.LastAccessTime);
                }
                catch (Exception ex)
                {
                    if (ex is IOException || ex is UnauthorizedAccessException)
                    {
                        NTStatus status = ToNTStatus(ex);
                        Log(Severity.Verbose, "SetFileInformation: Failed to set file dates on '{0}'. {1}.", fileHandle.Path, status);
                        return(status);
                    }
                    else
                    {
                        throw;
                    }
                }
                return(NTStatus.STATUS_SUCCESS);
            }
            else if (information is FileRenameInformationType2)
            {
                FileRenameInformationType2 renameInformation = (FileRenameInformationType2)information;
                string newFileName = renameInformation.FileName;
                if (!newFileName.StartsWith(@"\"))
                {
                    newFileName = @"\" + newFileName;
                }

                if (fileHandle.Stream != null)
                {
                    fileHandle.Stream.Close();
                }

                // Note: it's possible that we just want to upcase / downcase a filename letter.
                try
                {
                    if (renameInformation.ReplaceIfExists && (IsFileExists(newFileName)))
                    {
                        m_fileSystem.Delete(newFileName);
                    }
                    m_fileSystem.Move(fileHandle.Path, newFileName);
                    Log(Severity.Information, "SetFileInformation: Renamed '{0}' to '{1}'", fileHandle.Path, newFileName);
                }
                catch (Exception ex)
                {
                    if (ex is IOException || ex is UnauthorizedAccessException)
                    {
                        NTStatus status = ToNTStatus(ex);
                        Log(Severity.Verbose, "SetFileInformation: Cannot rename '{0}' to '{1}'. {2}.", fileHandle.Path, newFileName, status);
                        return(status);
                    }
                    else
                    {
                        throw;
                    }
                }
                fileHandle.Path = newFileName;
                return(NTStatus.STATUS_SUCCESS);
            }
            else if (information is FileDispositionInformation)
            {
                if (((FileDispositionInformation)information).DeletePending)
                {
                    // We're supposed to delete the file on close, but it's too late to report errors at this late stage
                    if (fileHandle.Stream != null)
                    {
                        fileHandle.Stream.Close();
                    }

                    try
                    {
                        m_fileSystem.Delete(fileHandle.Path);
                        Log(Severity.Information, "SetFileInformation: Deleted '{0}'", fileHandle.Path);
                    }
                    catch (Exception ex)
                    {
                        if (ex is IOException || ex is UnauthorizedAccessException)
                        {
                            NTStatus status = ToNTStatus(ex);
                            Log(Severity.Information, "SetFileInformation: Error deleting '{0}'. {1}.", fileHandle.Path, status);
                            return(status);
                        }
                        else
                        {
                            throw;
                        }
                    }
                }
                return(NTStatus.STATUS_SUCCESS);
            }
            else if (information is FileAllocationInformation)
            {
                long allocationSize = ((FileAllocationInformation)information).AllocationSize;
                try
                {
                    fileHandle.Stream.SetLength(allocationSize);
                }
                catch (Exception ex)
                {
                    if (ex is IOException || ex is UnauthorizedAccessException)
                    {
                        NTStatus status = ToNTStatus(ex);
                        Log(Severity.Verbose, "SetFileInformation: Cannot set allocation for '{0}'. {1}.", fileHandle.Path, status);
                        return(status);
                    }
                    else
                    {
                        throw;
                    }
                }
                return(NTStatus.STATUS_SUCCESS);
            }
            else if (information is FileEndOfFileInformation)
            {
                long endOfFile = ((FileEndOfFileInformation)information).EndOfFile;
                try
                {
                    fileHandle.Stream.SetLength(endOfFile);
                }
                catch (Exception ex)
                {
                    if (ex is IOException || ex is UnauthorizedAccessException)
                    {
                        NTStatus status = ToNTStatus(ex);
                        Log(Severity.Verbose, "SetFileInformation: Cannot set end of file for '{0}'. {1}.", fileHandle.Path, status);
                        return(status);
                    }
                    else
                    {
                        throw;
                    }
                }
                return(NTStatus.STATUS_SUCCESS);
            }
            else
            {
                return(NTStatus.STATUS_NOT_IMPLEMENTED);
            }
        }