예제 #1
0
 /// <summary>
 /// The constructor for a file contained as a hidden data stream.
 /// </summary>
 public FileNTFS(MFTRecord record, MFTAttribute attr, string path)
 {
     _record    = record;
     _stream    = new NTFSFileStream(_record.PartitionStream, _record, attr);
     FileSystem = record.FileSystem;
     Deleted    = _record.Deleted;
     Name       = PathUtils.MakeFileNameValid(record.FileName + "_" + attr.Name);
     Path       = PathUtils.Combine(path, Name);
 }
예제 #2
0
 public NTFSFileStream(IDataStream partition, MFTRecord record, MFTAttribute attr)
 {
     if (attr != null)
     {
         _nonResident = attr.NonResident;
         if (_nonResident)
         {
             _runs   = attr.Runs;
             _length = attr.DataSize;
         }
         else
         {
             _residentStream = attr.ResidentData;
             _length         = attr.ResidentData.StreamLength;
         }
     }
     _record          = record;
     _partitionStream = partition;
 }
예제 #3
0
        public FolderNTFS(MFTRecord record, string path, bool isRoot = false)
        {
            _record    = record;
            FileSystem = record.FileSystem;
            Deleted    = _record.Deleted;
            _indexRoot = new NTFSFileStream(_record.PartitionStream, _record, AttributeType.IndexRoot);

            MFTAttribute attr = _record.GetAttribute(AttributeType.IndexAllocation);

            if (attr != null)
            {
                _indexAllocation = new NTFSFileStream(_record.PartitionStream, _record, AttributeType.IndexAllocation);
            }
            if (isRoot)               // root
            {
                Root = true;
                Name = FileSystem.Store.DeviceID;
                Path = FileSystem.Store.DeviceID;
                foreach (FileSystemNode node in GetChildren("$Volume"))
                {
                    FileNTFS file = node as FileNTFS;
                    if (file != null && file.VolumeLabel != "")
                    {
                        Name = file.VolumeLabel;
                        break;
                    }
                }
            }
            else
            {
                Name = PathUtils.MakeFileNameValid(record.FileName);
                if (!string.IsNullOrEmpty(path))
                {
                    Path = PathUtils.Combine(path, Name);
                }
                else
                {
                    // We don't know the path
                    Path = PathUtils.Combine(FileSystem.Store.DeviceID, "?", Name);
                }
            }
        }
예제 #4
0
        private void LoadExternalAttributeList(int startOffset, MFTAttribute attrList)
        {
            int offset = 0;

            while (true)
            {
                //Align to 8 byte boundary
                if (offset % 8 != 0)
                {
                    offset = (offset / 8 + 1) * 8;
                }

                // Load the header for this external attribute reference.
                AttributeType type = (AttributeType)BitConverter.ToUInt32(_data, offset + startOffset + 0x0);
                // 0xFFFFFFFF marks end of attributes.
                if (offset == attrList.ValueLength || type == AttributeType.End)
                {
                    break;
                }
                ushort length                = BitConverter.ToUInt16(_data, offset + startOffset + 0x4);
                byte   nameLength            = _data[offset + startOffset + 0x6];
                ushort id                    = BitConverter.ToUInt16(_data, offset + startOffset + 0x18);
                ulong  vcn                   = BitConverter.ToUInt64(_data, offset + startOffset + 0x8);
                ulong  extensionRecordNumber = (BitConverter.ToUInt64(_data, offset + startOffset + 0x10) & 0x00000000FFFFFFFF);

                if (extensionRecordNumber != RecordNum && extensionRecordNumber != MFTRecordNumber)                   // TODO: Are these ever different?
                // Load the MFT extension record, locate the attribute we want, and copy it over.
                {
                    MFTRecord extensionRecord = MFTRecord.Load(extensionRecordNumber, this.FileSystem);
                    if (extensionRecord.Valid)
                    {
                        foreach (MFTAttribute externalAttribute in extensionRecord._attributes)
                        {
                            if (id == externalAttribute.Id)
                            {
                                if (externalAttribute.NonResident && externalAttribute.Type == AttributeType.Data)
                                {
                                    // Find the corresponding data attribute on this record and merge the runlists
                                    bool merged = false;
                                    foreach (MFTAttribute attribute in _attributes)
                                    {
                                        if (attribute.Type == AttributeType.Data && externalAttribute.Name == attribute.Name)
                                        {
                                            MergeRunLists(ref attribute.Runs, externalAttribute.Runs);
                                            merged = true;
                                            break;
                                        }
                                    }
                                    if (!merged)
                                    {
                                        this._attributes.Add(externalAttribute);
                                    }
                                }
                                else
                                {
                                    this._attributes.Add(externalAttribute);
                                }
                            }
                        }
                    }
                }

                offset += 0x1A + (nameLength * 2);
            }
        }
예제 #5
0
        private void LoadAttributes(int startOffset, MFTLoadDepth loadDepth)
        {
            _attributes = new List <MFTAttribute>();
            while (true)
            {
                //Align to 8 byte boundary
                if (startOffset % 8 != 0)
                {
                    startOffset = (startOffset / 8 + 1) * 8;
                }

                // Read the attribute type and length and determine whether we care about this attribute.
                AttributeType type = (AttributeType)BitConverter.ToUInt32(_data, startOffset);
                if (type == AttributeType.End)
                {
                    break;
                }
                int length = BitConverter.ToUInt16(_data, startOffset + 4);
                if (loadDepth == MFTLoadDepth.NameAttributeOnly && type != AttributeType.FileName)
                {
                    // Skip this attribute if we're only loading the filename
                    startOffset += length;
                    continue;
                }

                MFTAttribute attribute = MFTAttribute.Load(_data, startOffset, this);
                if (!attribute.NonResident)
                {
                    switch (attribute.Type)
                    {
                    case AttributeType.StandardInformation:
                        LoadStandardAttribute(startOffset + attribute.ValueOffset);
                        break;

                    case AttributeType.FileName:
                        LoadNameAttribute(startOffset + attribute.ValueOffset);
                        break;

                    case AttributeType.AttributeList:
                        LoadExternalAttributeList(startOffset + attribute.ValueOffset, attribute);
                        break;

                    case AttributeType.VolumeLabel:
                        LoadVolumeLabelAttribute(startOffset + attribute.ValueOffset, (int)attribute.ValueLength);
                        break;
                    }
                }
                if (attribute.Valid)
                {
                    if (attribute.Type == AttributeType.Data)
                    {
                        if (attribute.Name == null)
                        {
                            if (_dataAttribute != null)
                            {
                                Console.Error.WriteLine("Warning: multiple unnamed data streams found on MFT record {0}.", RecordNum);
                            }
                            _dataAttribute = attribute;
                        }
                        else
                        {
                            _namedDataAttributes.Add(attribute);
                        }
                    }
                    _attributes.Add(attribute);
                }

                startOffset += (int)attribute.Length;
            }
        }