Exemplo n.º 1
0
        public void Extend(ulong additionalLengthInBytes)
        {
            ulong currentSize = this.Length;

            if (m_attributeRecord is NonResidentAttributeRecord)
            {
                NonResidentAttributeData attributeData = new NonResidentAttributeData(m_volume, m_fileRecord, (NonResidentAttributeRecord)m_attributeRecord);
                attributeData.Extend(additionalLengthInBytes);
            }
            else
            {
                byte[] data              = ((ResidentAttributeRecord)m_attributeRecord).Data;
                ulong  finalDataLength   = (uint)data.Length + additionalLengthInBytes;
                ulong  finalRecordLength = (uint)m_attributeRecord.RecordLength + additionalLengthInBytes;
                if (finalRecordLength >= (ulong)m_volume.AttributeRecordLengthToMakeNonResident &&
                    m_attributeRecord.AttributeType != AttributeType.AttributeList) // We will create an attribute list with the right attribute form in advance.
                {
                    // Convert the attribute to non-resident
                    long clustersToAllocate = (long)Math.Ceiling((double)finalDataLength / m_volume.BytesPerCluster);
                    if (clustersToAllocate > m_volume.NumberOfFreeClusters)
                    {
                        throw new DiskFullException();
                    }
                    NonResidentAttributeRecord attributeRecord = NonResidentAttributeRecord.Create(m_attributeRecord.AttributeType, m_attributeRecord.Name);
                    NonResidentAttributeData   attributeData   = new NonResidentAttributeData(m_volume, null, attributeRecord);
                    attributeData.Extend(finalDataLength);
                    if (data.Length % m_volume.BytesPerCluster > 0)
                    {
                        int fillDataLength = m_volume.BytesPerCluster - (data.Length % m_volume.BytesPerCluster);
                        if ((uint)data.Length + (uint)fillDataLength < finalDataLength)
                        {
                            // Only the last cluster can be partially used, if this is not the last cluster, zero-fill it
                            data = ByteUtils.Concatenate(data, new byte[fillDataLength]);
                        }
                    }
                    attributeData.WriteClusters(0, data);
                    // Note that we overwrite the old attribute only after writing the non-resident data
                    if (m_fileRecord != null)
                    {
                        m_fileRecord.RemoveAttributeRecord(m_attributeRecord.AttributeType, m_attributeRecord.Name);
                        FileRecordHelper.InsertSorted(m_fileRecord.Attributes, attributeRecord);
                    }
                    m_attributeRecord = attributeRecord;
                }
                else
                {
                    int    currentLength = data.Length;
                    byte[] temp          = new byte[currentLength + (int)additionalLengthInBytes];
                    Array.Copy(data, temp, data.Length);
                    ((ResidentAttributeRecord)m_attributeRecord).Data = temp;
                }

                if (m_fileRecord != null)
                {
                    m_volume.UpdateFileRecord(m_fileRecord);
                }
            }
        }
Exemplo n.º 2
0
 public void WriteClusters(long firstClusterVCN, byte[] data)
 {
     if (m_attributeRecord is NonResidentAttributeRecord)
     {
         NonResidentAttributeData attributeData = new NonResidentAttributeData(m_volume, m_fileRecord, (NonResidentAttributeRecord)m_attributeRecord);
         attributeData.WriteClusters(firstClusterVCN, data);
     }
     else
     {
         long firstSectorIndex = firstClusterVCN * m_volume.SectorsPerCluster;
         WriteSectors(firstClusterVCN, data);
     }
 }