Exemple #1
0
 public bool UpdateVariables(IList <FileFragment> list, ref int index, ref List <int> changed)
 {
     if (index == 2) //Even though setting this is slightly dangerous due to a lack of validation, it's more important this value always exists for everything else to run smoothly
     {
         loadedImageCount = BinaryFileInterpreter.ReadFileAs <ushort>(list[index].Path);
     }
     return(false);
 }
Exemple #2
0
 private static void UpdateLogicalScreenDescriptorValidity(IList <FileFragment> list, int index, params SectionTypes[] sections)
 {
     list[index].Validity = (0 <= BinaryFileInterpreter.ReadFileAs <short>(list[index].Path)) ? Validity.Valid : Validity.HardInvalid;
     //Need to re-validate anything that relies on the full image's width/height
     for (int i = 6; i < list.Count; i++) //items 0-5 are guarenteed to not be widths, heigths, xoffsets, or yoffsets
     {
         if (sections.Any(x => x == (list[i] as GIFFileFragment).SectionType))
         {
             list[i].Validity = Validity.Unchecked;
         }
     }
 }
Exemple #3
0
        private void UpdateImage(IList <FileFragment> list, int index)
        {
            /*
             * This equation is the simplifcation of these two equations:
             * int imageNumber = index - ((loadedImageCount*8) + 3);
             * int imageLengthIndex = 1 + ((1 + imageNumber)*8);
             */
            int imageLengthIndex = (((index - (loadedImageCount * 8)) - 2) * 8) + 1;

            //Starting off out of scope, only to be changed if something goes horribly wrong
            Validity imageValidity = Validity.OutOfScope;

            //Length
            uint currentImageLength = BinaryFileInterpreter.ReadFileAs <uint>(list[imageLengthIndex].Path);
            long actualImageLength  = new FileInfo(list[index].Path).Length;

            if (actualImageLength <= uint.MaxValue) //If the length is longer than a uint can hold, the image is invalid
            {
                if (FixLength && currentImageLength != actualImageLength)
                {
                    File.WriteAllBytes(list[imageLengthIndex].Path, BitConverter.GetBytes(currentImageLength = (uint)actualImageLength));
                }
                list[imageLengthIndex].Validity = (currentImageLength == actualImageLength) ? Validity.Valid : Validity.HardInvalid;
            }
            else
            {
                imageValidity = Validity.HardInvalid;
            }

            //Offset
            uint currentImageOffset = BinaryFileInterpreter.ReadFileAs <uint>(list[imageLengthIndex + 1].Path);
            long actualImageOffset  = 0;

            for (int i = 0; i < index; i++)
            {
                actualImageOffset += new FileInfo(list[i].Path).Length;
            }
            if (actualImageOffset <= uint.MaxValue) //Same thing with the offset
            {
                if (FixOffset && currentImageOffset != actualImageOffset)
                {
                    File.WriteAllBytes(list[imageLengthIndex + 1].Path, BitConverter.GetBytes(currentImageOffset = (uint)actualImageOffset));
                }
                list[imageLengthIndex + 1].Validity = (currentImageOffset == actualImageOffset) ? Validity.Valid : Validity.HardInvalid;
            }
            else
            {
                imageValidity = Validity.HardInvalid;
            }

            //Actual File
            list[index].Validity = imageValidity; //TODO maybe this can be known...?
        }
Exemple #4
0
 private static FileTypes GetFileType(IList <FileFragment> list)
 {
     if (new FileInfo(list[1].Path).Length == 2)
     {
         ushort fileTypeValue = BinaryFileInterpreter.ReadFileAs <ushort>(list[1].Path);
         if (fileTypeValue == 1 || fileTypeValue == 2)
         {
             list[1].Validity = Validity.Valid;
             return((FileTypes)fileTypeValue);
         }
     }
     list[1].Validity = Validity.HardInvalid;
     return(FileTypes.Unknown);
 }
Exemple #5
0
        private static void UpdateOffsetOrLengthValidity(IList <FileFragment> list, int offsetIndex, int lengthIndex, int maxIndex, bool isOffset)
        {
            short    max    = BinaryFileInterpreter.ReadFileAs <short>(list[maxIndex].Path);
            short    offset = BinaryFileInterpreter.ReadFileAs <short>(list[offsetIndex].Path);
            short    length = BinaryFileInterpreter.ReadFileAs <short>(list[lengthIndex].Path);
            Validity v      = (0 <= length && 0 <= offset && offset + length <= max) ? Validity.Valid : Validity.HardInvalid;

            if (v == Validity.Valid)
            {
                list[offsetIndex].Validity = list[lengthIndex].Validity = v;
            }
            else
            {
                list[isOffset ? offset : length].Validity = v;
            }
        }
Exemple #6
0
        private List <SectionTypes> LabelDataSections(IList <FileFragment> list, int index, bool addTrailer)
        {
            List <SectionTypes> s = new List <SectionTypes>();
            byte length;

            while ((length = BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path)) != 0)
            {
                s.AddRange(new SectionTypes[]
                {
                    SectionTypes.Length,
                    SectionTypes.Data
                });
                index += 2;
            }
            if (addTrailer)
            {
                s.Add(SectionTypes.Trailer);
            }
            return(s);
        }
Exemple #7
0
        public bool UpdateVariables(IList <FileFragment> list, ref int index, ref List <int> changed)
        {
            //Starting saftey thingy
            if (index == 0)
            {
                (list[index] as GIFFileFragment).SectionType = SectionTypes.Header;
                return(false);
            }

            List <SectionTypes> SectionTypeQueue = new List <SectionTypes>();
            bool exists = new PackedGlobalColorTableInfo(BinaryFileInterpreter.ReadFileAs <byte>(list[3].Path)).Exists;

            if (index <= (exists ? 6 : 5))
            {
                SectionTypeQueue.AddRange(new SectionTypes[]
                {
                    SectionTypes.Header,
                    SectionTypes.Width,
                    SectionTypes.Height,
                    SectionTypes.GlobalColorTablePacked,
                    SectionTypes.ColorIndex,
                    SectionTypes.PixelAspectRatio
                });
                if (exists)
                {
                    SectionTypeQueue.Add(SectionTypes.ColorTable);
                }
                index = 0;
            }
            else
            {
                index = FindSectionOfType(list, index, SectionTypes.Sentinal, SectionTypes.Trailer);
                switch ((list[index] as GIFFileFragment).SectionType)
                {
                case (SectionTypes.Trailer):
                    index++;
                    goto case (SectionTypes.Sentinal);

                case (SectionTypes.Sentinal):
                    switch (BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path))
                    {
                    case ((byte)','):
                        SectionTypeQueue.AddRange(new SectionTypes[]
                        {
                            SectionTypes.Sentinal,
                            SectionTypes.XOffset,
                            SectionTypes.YOffset,
                            SectionTypes.Width,
                            SectionTypes.Height,
                            SectionTypes.LocalColorTablePacked
                        });
                        bool lctexists = new PackedLocalColorTableInfo(BinaryFileInterpreter.ReadFileAs <byte>(list[index + 5].Path)).Exists;
                        if (lctexists)
                        {
                            SectionTypeQueue.Add(SectionTypes.ColorTable);
                        }
                        SectionTypeQueue.Add(SectionTypes.Unknown);         //Unencoded length?
                        //Need to +8 if the local color table exists
                        SectionTypeQueue.AddRange(LabelDataSections(list, index + (lctexists ? 8 : 7), true));
                        break;

                    case ((byte)'!'):
                        SectionTypeQueue.AddRange(new SectionTypes[]
                        {
                            SectionTypes.Sentinal,
                            SectionTypes.ExtensionType
                        });
                        switch (BinaryFileInterpreter.ReadFileAs <byte>(list[index + 1].Path))
                        {
                        //Plain Text
                        case (0x01):
                            SectionTypeQueue.AddRange(new SectionTypes[]
                            {
                                SectionTypes.Length,
                                SectionTypes.XOffset,
                                SectionTypes.YOffset,
                                SectionTypes.Width,
                                SectionTypes.Height,
                                SectionTypes.Width,
                                SectionTypes.Height,
                                SectionTypes.ColorIndex,
                                SectionTypes.ColorIndex
                            });
                            SectionTypeQueue.AddRange(LabelDataSections(list, index + 11, false));
                            break;

                        //Graphics Control
                        case (0xF9):
                            SectionTypeQueue.AddRange(new SectionTypes[]
                            {
                                SectionTypes.Length,
                                SectionTypes.GraphicsControlPacked,
                                SectionTypes.DelayTime,
                                SectionTypes.ColorIndex
                            });
                            break;

                        //Comment
                        case (0xFE):
                            SectionTypeQueue.AddRange(LabelDataSections(list, index + 2, false));
                            break;

                        //Application
                        case (0xFF):
                            SectionTypeQueue.AddRange(new SectionTypes[]
                            {
                                SectionTypes.Length,
                                SectionTypes.ApplicationIdentifier,
                                SectionTypes.ApplicationAuthCode
                            });
                            SectionTypeQueue.AddRange(LabelDataSections(list, index + 5, false));
                            break;

                        //Unknown
                        default:
                            SectionTypeQueue.Add(SectionTypes.Unknown);
                            break;
                        }
                        SectionTypeQueue.Add(SectionTypes.Trailer);
                        break;

                    case ((byte)';'):
                        SectionTypeQueue.Add(SectionTypes.EndOfFile);
                        EndOfFileIndex = index;         //TODO check this again
                        break;

                    default:
                        SectionTypeQueue.Add(SectionTypes.Unknown);
                        break;
                    }
                    break;
                }
            }

            bool didWork = false;

            for (int i = 0; i < SectionTypeQueue.Count; i++) //TODO is this confusing having i++ all the way up here?
            {
                if ((list[index] as GIFFileFragment).SectionType != SectionTypeQueue[i])
                {
                    (list[index] as GIFFileFragment).SectionType = SectionTypeQueue[i];
                    changed.Add(index);
                    didWork = true;
                }
                index++;
            }
            return(didWork);
        }
Exemple #8
0
        //This code sucks more than BLink 😂👌
        public void UpdateValidity(IList <FileFragment> list, int index)
        {
            //Anything after the first EndOfFile marker is ignored, but could still be valid if it was removed
            if (index > EndOfFileIndex.Value)
            {
                list[index].Validity = Validity.SoftInvalid;
                return;
            }

            byte  CurrentLength;
            ulong ActualLength;

            switch ((list[index] as GIFFileFragment).SectionType)
            {
            case (SectionTypes.Header):
                list[index].Validity = headerTypes.Contains(File.ReadAllText(list[index].Path))
                        ? Validity.Valid : Validity.HardInvalid;
                break;

            case (SectionTypes.Sentinal):
                list[index].Validity = new FileInfo(list[index].Path).Length == 1 && SentinalTypes.Contains(BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path))
                        ? Validity.Valid : Validity.HardInvalid;
                break;

                #region Image Sizes/Offsets
            case (SectionTypes.XOffset):
                UpdateOffsetOrLengthValidity(list, index, index + 2, 1, true);
                break;

            case (SectionTypes.Width):
                if (index == 1)
                {
                    UpdateLogicalScreenDescriptorValidity(list, index, SectionTypes.Width, SectionTypes.XOffset);
                }
                else
                {
                    UpdateOffsetOrLengthValidity(list, index - 2, index, 1, false);
                }
                break;

            case (SectionTypes.YOffset):
                UpdateOffsetOrLengthValidity(list, index, index + 2, 2, true);
                break;

            case (SectionTypes.Height):
                if (index == 2)
                {
                    UpdateLogicalScreenDescriptorValidity(list, index, SectionTypes.Height, SectionTypes.YOffset);
                }
                else
                {
                    UpdateOffsetOrLengthValidity(list, index - 2, index, 2, false);
                }
                break;
                #endregion

                #region Packed Bytes
            case (SectionTypes.GlobalColorTablePacked):
                list[index].Description = new PackedGlobalColorTableInfo(BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path)).ToString();
                list[index].Validity    = Validity.Valid;
                break;

            case (SectionTypes.LocalColorTablePacked):
                list[index].Description = new PackedLocalColorTableInfo(BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path)).ToString();
                list[index].Validity    = Validity.Valid;
                break;

            case (SectionTypes.GraphicsControlPacked):
                list[index].Description = new PackedGraphicsControlInfo(BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path)).ToString();
                list[index].Validity    = Validity.Valid;
                break;
                #endregion

            case (SectionTypes.Length):
                byte[] filecontents = File.ReadAllBytes(list[index].Path);
                if (filecontents.Length != 1)
                {
                    list[index].Validity = Validity.HardInvalid;
                    break;
                }
                CurrentLength = filecontents[0];
                ActualLength  = 0;
                for (int i = index + 1; !LengthEnders.Contains((list[i] as GIFFileFragment).SectionType); i++)
                {
                    ActualLength += (ulong)new FileInfo(list[i].Path).Length;
                }

                list[index].Validity = CurrentLength == ActualLength ? Validity.Valid : Validity.HardInvalid;
                break;

            case (SectionTypes.Data):
                ActualLength = 0;
                int lengthIndex;
                for (lengthIndex = index; (list[lengthIndex] as GIFFileFragment).SectionType != SectionTypes.Length; lengthIndex--)
                {
                    ActualLength += (ulong)new FileInfo(list[lengthIndex].Path).Length;
                }
                CurrentLength = BinaryFileInterpreter.ReadFileAs <byte>(list[lengthIndex].Path);
                if (FixLength && (CurrentLength != ActualLength) && ActualLength <= byte.MaxValue)
                {
                    File.WriteAllBytes(list[lengthIndex].Path, new byte[] { (byte)ActualLength });
                    list[lengthIndex].Validity = Validity.Valid;
                }
                list[index].Validity = CurrentLength == ActualLength ? Validity.Valid : Validity.HardInvalid;
                break;

            case (SectionTypes.ColorIndex):
                //TODO need to check a packed byte to validate...?
                break;

            case (SectionTypes.DelayTime):
                list[index].Validity = (0 <= BinaryFileInterpreter.ReadFileAs <short>(list[index].Path)) ? Validity.Valid : Validity.HardInvalid;
                break;

            //These could be anything, and anything could be valid, so...
            case (SectionTypes.ApplicationIdentifier):
            case (SectionTypes.ApplicationAuthCode):
                list[index].Validity = Validity.Valid;
                break;

            case (SectionTypes.ExtensionType):
                //TODO need to make that list of types...
                break;

            case (SectionTypes.Trailer):
                if (new FileInfo(list[index].Path).Length == 1)
                {
                    list[index].Validity = (BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path) == 0x00) ? Validity.Valid : Validity.SoftInvalid;
                }
                else     //This would cause giant collateral bad
                {
                    list[index].Validity = Validity.HardInvalid;
                }
                break;

            //TODO this might break in some cases?
            case (SectionTypes.EndOfFile):
                //If anything about this EOF marker would make it not reconisable
                if (new FileInfo(list[index].Path).Length == 1 && BinaryFileInterpreter.ReadFileAs <byte>(list[index].Path) == (byte)';')
                {
                    list[index].Validity = Validity.Valid;
                }
                //assume the user removed it
                else
                {
                    list[index].Validity = Validity.Unknown;
                    //and find the next available EOF marker
                    for (int i = index + 1; i < list.Count; i++)
                    {
                        if ((list[i] as GIFFileFragment).SectionType == SectionTypes.EndOfFile)
                        {
                            //Stop once we find it
                            EndOfFileIndex = i;
                            return;
                        }
                    }
                }
                break;

            case (SectionTypes.PixelAspectRatio):
            case (SectionTypes.ColorTable):
            case (SectionTypes.Unknown):
                //TODO
                list[index].Validity = Validity.Unknown;
                break;
            }
            return;
        }
Exemple #9
0
        public void UpdateValidity(IList <FileFragment> list, int index)
        {
            //Switch based on box type
            switch ((list[index] as ISOFileFragment).BoxType)
            {
            //TODO length is super complicated with these, so I'll have to spend a good chunk of time to fix them
            case (BoxTypes.Length):     //length (uint)
                string lengthPath   = list[index].Path;
                long   lengthLength = new FileInfo(lengthPath).Length;
                if (lengthLength != 4)
                {
                    list[index].Validity = (lengthLength < 4) ? Validity.HardInvalid : Validity.Unknown;
                }
                else
                {
                    //TODO why did I have to rename these?!?!?!?!?!?!?!?!?!?!?!
                    uint lengthData1 = BinaryFileInterpreter.ReadFileAs <uint>(lengthPath, true);

                    if ((list[index + 2] as ISOFileFragment).BoxType == BoxTypes.ExtendedLength)
                    {
                        list[index].Validity    = (lengthData1 == 1) ? Validity.Valid : Validity.HardInvalid;
                        list[index].Description = $"Box {(list[index] as ISOFileFragment).BoxNumber} Length = <unknown>";
                    }
                    else
                    {
                        ulong        correctLength1 = 4; //Starts at the length of "Length"
                        int          i1             = 0;
                        FileFragment ff1;
                        do
                        {
                            i1++;
                            ff1             = list[index + i1];
                            correctLength1 += (ulong)new FileInfo(ff1.Path).Length;
                        } while ((ff1 as ISOFileFragment).BoxType != BoxTypes.Data);

                        //Assuming it did work, we can go as usual
                        list[index].Validity = (lengthData1 == correctLength1)
                                ? Validity.Valid : Validity.HardInvalid;
                    }
                    list[index].Description = $"Box {(list[index] as ISOFileFragment).BoxNumber} Length = {lengthData1}";
                }
                break;

            case (BoxTypes.Type):     //type
                string typeData = File.ReadAllText(list[index].Path);
                list[index].Validity =
                    IsValidBoxType(typeData)
                        ? Validity.Valid
                        : Validity.HardInvalid;
                list[index].Description = $"Box {(list[index] as ISOFileFragment).BoxNumber} Type = {typeData}";
                break;

            case (BoxTypes.ExtendedLength):     //Extended Length (ulong)
                //TODO implement extended length validation
                break;

            case (BoxTypes.ExtendedType):     //Extended Type (GUID)
                Guid extTypeData = new Guid(File.ReadAllBytes(list[index].Path));
                list[index].Validity =
                    IsValidExtendedBoxType(extTypeData)
                        ? Validity.Valid
                        : Validity.HardInvalid;
                list[index].Description = $"Box {(list[index] as ISOFileFragment).BoxNumber} GUID = {extTypeData.ToString()}";
                break;

            case (BoxTypes.Data):     //data
                //HACK this entire code is probably messy but hopefully actually works
                string dataPath = list[index].Path;
                ulong  correctLength, dataLength;
                correctLength = dataLength = (ulong)new FileInfo(dataPath).Length;

                int          i = 0;
                FileFragment ff, lengthToEdit = null;
                do
                {
                    i++;
                    ff             = list[index - i];
                    correctLength += (ulong)new FileInfo(ff.Path).Length;

                    //Save the first length or extended length box we find
                    if (lengthToEdit == null && ((ff as ISOFileFragment).BoxType == BoxTypes.Length || (ff as ISOFileFragment).BoxType == BoxTypes.ExtendedLength))
                    {
                        lengthToEdit = ff;
                    }
                } while ((ff as ISOFileFragment).BoxType != BoxTypes.Length);

                bool isExtended = ((lengthToEdit as ISOFileFragment).BoxType == BoxTypes.ExtendedLength);     //Storing this since it's used twice

                /*
                 * ulong lengthData = isExtended
                 *  ? BitConverter.ToUInt64(File.ReadAllBytes(lengthToEdit.Path).Reverse().ToArray(), 0)
                 *  : BitConverter.ToUInt32(File.ReadAllBytes(lengthToEdit.Path).Reverse().ToArray(), 0);
                 */
                ulong lengthData = BinaryFileInterpreter.ReadFileAs(lengthToEdit.Path, isExtended ? typeof(ulong) : typeof(uint), true);

                if (FixLength && lengthData != correctLength)
                {
                    //TODO this is so dumb that this conditional operator doesn't work :angery:
                    //BitConverter.GetBytes(isExtended ? correctLength : (uint)correctLength).Reverse().ToArray();
                    byte[] bytesToWrite = isExtended ? BitConverter.GetBytes(correctLength) : BitConverter.GetBytes((uint)correctLength);
                    File.WriteAllBytes(lengthToEdit.Path, bytesToWrite.Reverse().ToArray());
                    lengthData               = correctLength;
                    lengthToEdit.Validity    = Validity.Valid;
                    lengthToEdit.Description = $"Box {(lengthToEdit as ISOFileFragment).BoxNumber} Length = {correctLength}";
                }
                list[index].Validity = (lengthData == correctLength)
                        ? Validity.Valid
                        : Validity.HardInvalid;
                list[index].Description = $"Box {(list[index] as ISOFileFragment).BoxNumber} Data length = {dataLength}";

                break;
            }
            return;
        }
Exemple #10
0
        public bool UpdateVariables(IList <FileFragment> list, ref int index, ref List <int> changed)
        {
            //Default start
            if (index == 0)
            {
                (list[index] as ISOFileFragment).BoxType   = BoxTypes.Length;
                (list[index] as ISOFileFragment).BoxNumber = 1;
                return(false);
            }
            else
            {
                //Shared between both cases
                BoxTypes current   = BoxTypes.Unknown;
                BoxTypes prev      = (list[index - 1] as ISOFileFragment).BoxType;
                int      boxNumber = (list[index - 1] as ISOFileFragment).BoxNumber;

                //HACK abandon all (some) hope ye who enter here
                //HACK it might be faster to just not have this first case, since it's only used once (if a file is created while enabled)
                //If in the middle of list
                if (index + 1 < list.Count)
                {
                    BoxTypes next = (list[index + 1] as ISOFileFragment).BoxType;
                    //TODO maybe move to C# 7 and use "when"?
                    switch (prev)
                    {
                    case (BoxTypes.Length):
                        current = (next == BoxTypes.Type || next == BoxTypes.Length)
                                  //If you're trying to insert a box in between a Length and a Type, I don't know what to tell ya...
                                  //And if you managed to get two lengths right next to eachother...
                                ? BoxTypes.Unknown
                                : BoxTypes.Type;
                        break;

                    case (BoxTypes.Type):
                        switch (next)
                        {
                        case (BoxTypes.ExtendedType):
                            current = BoxTypes.ExtendedLength;
                            break;

                        case (BoxTypes.Data):
                            switch (new FileInfo(list[index].Path).Length)
                            {
                            case (8):
                                current = BoxTypes.ExtendedLength;
                                break;

                            case (16):
                                current = BoxTypes.ExtendedType;
                                break;

                            default:
                                current = BoxTypes.Unknown;
                                break;
                            }
                            break;

                        //Only way length is gonna show up is if this box is missing data
                        case (BoxTypes.Length):
                            current = BoxTypes.Data;
                            break;

                        default:
                            current = BoxTypes.Unknown;
                            break;
                        }
                        break;

                    case (BoxTypes.ExtendedLength):
                        switch (next)
                        {
                        case (BoxTypes.Data):
                            current = BoxTypes.ExtendedType;
                            break;

                        case (BoxTypes.Length):
                            current = BoxTypes.Data;
                            break;

                        default:
                            current = BoxTypes.Unknown;
                            break;
                        }
                        break;

                    case (BoxTypes.ExtendedType):
                        current = (next == BoxTypes.Length)
                                ? BoxTypes.Data
                                : BoxTypes.Unknown;
                        break;

                    case (BoxTypes.Data):
                        current = (next == BoxTypes.Type)
                                ? BoxTypes.Length
                                : BoxTypes.Unknown;
                        boxNumber++;     //TODO might cause issues if the BoxType was found to be unknown?
                        break;
                    }
                }
                //If at end of list
                else
                {
                    switch (prev)
                    {
                    case (BoxTypes.Length):
                        current = BoxTypes.Type;
                        break;

                    case (BoxTypes.Type):
                        string typeData = File.ReadAllText(list[index - 1].Path);
                        switch (new FileInfo(list[index].Path).Length)
                        {
                        case (8):
                            //HACK just look at this. It basically has to validate the entire box before checking aaaaaaaaaaaaa
                            if (index >= 2 && (list[index - 2] as ISOFileFragment).BoxType == BoxTypes.Length &&      //TODO isn't this (vvv) big endian???????
                                new FileInfo(list[index - 2].Path).Length == 4 && BinaryFileInterpreter.ReadFileAs <uint>(list[index - 2].Path) == 0)
                            {
                                current = BoxTypes.ExtendedLength;
                            }
                            else
                            {
                                goto default;
                            }
                            break;

                        case (16):
                            if (typeData != "uuid")         //HACK this might not be good enough?
                            {
                                goto default;
                            }
                            current = BoxTypes.ExtendedType;
                            break;

                        default:
                            current = BoxTypes.Data;
                            break;
                        }
                        break;

                    case (BoxTypes.ExtendedLength):
                        current = (new FileInfo(list[index].Path).Length == 16)
                                ? BoxTypes.ExtendedType
                                : BoxTypes.Data;
                        break;

                    case (BoxTypes.ExtendedType):
                        current = BoxTypes.Data;
                        break;

                    case (BoxTypes.Data):
                        current = BoxTypes.Length;
                        boxNumber++;
                        break;
                    }
                }

                (list[index] as ISOFileFragment).BoxType   = current;
                (list[index] as ISOFileFragment).BoxNumber = boxNumber;
                return(false);
            }
        }
        public void UpdateValidity(IList <FileFragment> list, int index)
        {
            if (index < 0) //error
            {
                return;
            }
            else if (index == 0) //header
            {
                HeaderDictionary.TryGetValue(File.ReadAllBytes(list[index].Path), out HeaderType);
                list[index].Validity    = (HeaderType != NetworkGraphicTypes.Other) ? Validity.Valid : Validity.HardInvalid;
                list[index].Description = $"File type = {HeaderType} Network Graphics";
                return;
            }
            else //everything else
            {
                int chunkNumber = ((index - 1) / 4) + 1;
                switch (((index - 1) % 4) + 1) //Switch based on chunk type
                {
                case (1):                      //length
                    string lengthPath   = list[index].Path;
                    long   lengthLength = new FileInfo(lengthPath).Length;
                    if (lengthLength != 4)
                    {
                        list[index].Validity    = (lengthLength < 4) ? Validity.HardInvalid : Validity.Unknown;
                        list[index].Description = $"Chunk {chunkNumber} Length = <unkown>";
                    }
                    else if (lengthLength == 4)
                    {
                        int lengthData = BinaryFileInterpreter.ReadFileAs <int>(lengthPath, true);
                        list[index].Validity =
                            (lengthData == new FileInfo(list[index + 2].Path).Length)
                                ? Validity.Valid : Validity.HardInvalid;
                        list[index].Description = $"Chunk {chunkNumber} Length = {lengthData}";
                    }
                    break;

                case (2):     //type
                    byte[] typeData = File.ReadAllBytes(list[index].Path);
                    list[index].Validity =
                        IsValidChunkType(typeData)
                            ? Validity.Valid
                            : Validity.HardInvalid;
                    list[index].Description = $"Chunk {chunkNumber} Type = {Encoding.ASCII.GetString(typeData)}";     //HACK
                    goto case (4);

                case (3):     //data
                    string dataPath   = list[index].Path;
                    long   dataLength = new FileInfo(dataPath).Length;
                    if (dataLength > int.MaxValue)
                    {
                        list[index].Validity = Validity.HardInvalid;
                    }
                    else
                    {
                        int lengthData = BinaryFileInterpreter.ReadFileAs <int>(list[index - 2].Path, true);
                        if (FixLength && dataLength != lengthData)
                        {
                            File.WriteAllBytes(list[index - 2].Path, ((int)dataLength).GetBytes(true));
                            list[index - 2].Description = $"Chunk {chunkNumber} Length = {dataLength}";
                            list[index - 2].Validity    = Validity.Valid;
                        }
                        list[index].Validity = (FixLength || dataLength == lengthData) ? Validity.Valid : Validity.HardInvalid;
                    }
                    list[index].Description = $"Chunk {chunkNumber} Data length = {dataLength}";
                    goto case (4);

                case (4):                                            //crc
                    //int chunkStart = (((index - 1) / 4) * 4) + 1;
                    int    chunkStart = ((chunkNumber - 1) * 4) + 1; //Using this since this case is goto'd a few times
                    byte[] correctCRC = CalculateCRCOf(
                        File.ReadAllBytes(list[chunkStart + 1].Path)
                        .Concat(File.ReadAllBytes(list[chunkStart + 2].Path))
                        .ToArray());
                    byte[] currentCRC = File.ReadAllBytes(list[chunkStart + 3].Path);
                    if (!correctCRC.SequenceEqual(currentCRC))
                    {
                        if (FixCRC)
                        {
                            File.WriteAllBytes(list[chunkStart + 3].Path, correctCRC);
                        }
                        list[chunkStart + 3].Validity = (FixCRC)
                                ? Validity.Valid
                                : Validity.HardInvalid;
                    }
                    else
                    {
                        list[chunkStart + 3].Validity = Validity.Valid;
                    }
                    list[chunkStart + 3].Description = $"Chunk {chunkNumber} CRC (Big Endian) = {currentCRC.ConvertTo<uint>(true)}";
                    break;
                }
                return;
            }
        }
Exemple #12
0
        public void UpdateValidity(IList <FileFragment> list, int index)
        {
            //Error
            if (index < 0)
            {
                return;
            }
            //Header
            else if (index <= 2)
            {
                switch (index)
                {
                case (0):
                    list[index].Validity = (new FileInfo(list[index].Path).Length == 2 &&
                                            BitConverter.ToUInt16(File.ReadAllBytes(list[index].Path), 0) == 0)
                            ? Validity.Valid
                            : Validity.HardInvalid;
                    break;

                case (1):
                    GetFileType(list);
                    break;

                case (2):
                    list[index].Validity = (new FileInfo(list[index].Path).Length == 2) ? Validity.Valid : Validity.HardInvalid;
                    break;
                }
            }
            //Image directory entry
            else if (index <= 2 + (loadedImageCount * 8))
            {
                switch (((index - 3) % 8))
                {
                //Width
                case (0):
                //Height
                case (1):
                //Color Palette
                case (2):
                    list[index].Validity = Validity.Valid;     //TODO how do you even validate one byte? :-|
                    break;

                //Reserved
                case (3):
                    byte[] reservedData = File.ReadAllBytes(list[index].Path);
                    list[index].Validity = (reservedData.Length == 1 && reservedData[0] == 0) ? Validity.Valid : Validity.SoftInvalid;
                    break;

                //Variable 1
                case (4):
                    switch (GetFileType(list))
                    {
                    //Color Planes
                    case (FileTypes.Icon):
                        if (new FileInfo(list[index].Path).Length == 2)
                        {
                            ushort fileTypeValue = BinaryFileInterpreter.ReadFileAs <ushort>(list[index].Path);
                            if (fileTypeValue == 0 || fileTypeValue == 1)
                            {
                                list[index].Validity = Validity.Valid;
                                break;
                            }
                        }
                        list[index].Validity = Validity.HardInvalid;
                        break;

                    //Hotspot X Offset
                    case (FileTypes.Cursor):
                        list[index].Validity = Validity.Valid;
                        break;

                    case (FileTypes.Unknown):
                        list[index].Validity = Validity.Unknown;
                        break;
                    }
                    break;

                //Variable 2
                case (5):
                    switch (GetFileType(list))
                    {
                    //Bits Per Pixel
                    case (FileTypes.Icon):
                    //Hotspot Y Offset
                    case (FileTypes.Cursor):
                        list[index].Validity = Validity.Valid;
                        break;

                    case (FileTypes.Unknown):
                        list[index].Validity = Validity.Unknown;
                        break;
                    }
                    break;

                //Image Data Length
                case (6):
                    if (new FileInfo(list[index].Path).Length == 4)
                    {
                        uint offset   = BinaryFileInterpreter.ReadFileAs <uint>(list[index + 1].Path);
                        uint length   = BinaryFileInterpreter.ReadFileAs <uint>(list[index].Path);
                        long fileSize = 0;
                        for (int i = 0; i < list.Count; i++)
                        {
                            fileSize += new FileInfo(list[i].Path).Length;
                        }
                        list[index].Validity = ((offset + length) < fileSize) ? Validity.Valid : Validity.HardInvalid;
                    }
                    else
                    {
                        list[index].Validity = Validity.HardInvalid;
                    }
                    break;

                //Image Data Offset
                case (7):
                    list[index].Validity = (new FileInfo(list[index].Path).Length == 4 &&
                                            BinaryFileInterpreter.ReadFileAs <uint>(list[index].Path) > (3 + (loadedImageCount * 8)))
                            ? Validity.Valid
                            : Validity.HardInvalid;
                    break;
                }
            }
            //Image
            else
            {
                //Iterating over all later images because length/offset changes will ripple
                for (int i = index; i < list.Count; i++)
                {
                    UpdateImage(list, i);
                }
            }
            return;
        }