public static BF.Index CreateIndex(BF.BigFile bigfile, IndexType indexType)
        {
            switch (indexType)
            {
            case IndexType.Pandemonium:
                BF.PandemoniumFileIndex pfi = new PandemoniumFileIndex("Index", bigfile, null, 0);
                pfi.EntryLength      = 2;
                pfi.OffsetPosition   = 0;
                pfi.NameHashPosition = 1;
                return(pfi);

                break;

            case IndexType.SR1PS1MainIndex:
                BF.IndexIndex ixiSoulReaverPlayStationMainIndex;
                ixiSoulReaverPlayStationMainIndex                = new BF.IndexIndex("Index", bigfile, null, 0);
                ixiSoulReaverPlayStationMainIndex.EntryLength    = 2;
                ixiSoulReaverPlayStationMainIndex.OffsetPosition = 1;
                //??Position = 0;
                ixiSoulReaverPlayStationMainIndex.SubIndexType = IndexType.SR1PS1SubIndex;
                return(ixiSoulReaverPlayStationMainIndex);

                break;

            case IndexType.SR1PS1SubIndex:
                BF.FileIndex ixfSoulReaverPlayStationSubIndex;
                ixfSoulReaverPlayStationSubIndex                  = new BF.FileIndex("Index", bigfile, null, 0);
                ixfSoulReaverPlayStationSubIndex.EntryLength      = 4;
                ixfSoulReaverPlayStationSubIndex.NameHashPosition = 0;
                ixfSoulReaverPlayStationSubIndex.LengthPosition   = 1;
                ixfSoulReaverPlayStationSubIndex.OffsetPosition   = 2;
                //??Position = 3;
                return(ixfSoulReaverPlayStationSubIndex);

                break;

            case IndexType.SR1PS1PALRetailMainIndex:
                BF.IndexIndex ixiSoulReaverPlayStationPALRetailMainIndex;
                ixiSoulReaverPlayStationPALRetailMainIndex                = new BF.IndexIndex("Index", bigfile, null, 0);
                ixiSoulReaverPlayStationPALRetailMainIndex.EntryLength    = 2;
                ixiSoulReaverPlayStationPALRetailMainIndex.OffsetPosition = 1;
                //??Position = 0;
                ixiSoulReaverPlayStationPALRetailMainIndex.SubIndexType = IndexType.SR1PS1PALRetailSubIndex;
                return(ixiSoulReaverPlayStationPALRetailMainIndex);

                break;

            case IndexType.SR1PS1PALRetailSubIndex:
                BF.SoulReaverPlaystationPALFileIndex ixfSoulReaverPlaystationPALRetailSubIndex;
                ixfSoulReaverPlaystationPALRetailSubIndex                  = new BF.SoulReaverPlaystationPALFileIndex("Index", bigfile, null, 0);
                ixfSoulReaverPlaystationPALRetailSubIndex.EntryLength      = 4;
                ixfSoulReaverPlaystationPALRetailSubIndex.NameHashPosition = 0;
                ixfSoulReaverPlaystationPALRetailSubIndex.LengthPosition   = 1;
                ixfSoulReaverPlaystationPALRetailSubIndex.OffsetPosition   = 2;
                //??Position = 3;
                return(ixfSoulReaverPlaystationPALRetailSubIndex);

                break;

            case IndexType.SR1PS1PALJuly1999MainIndex:
                BF.IndexIndex ixiSoulReaverPlayStationPALPrereleaseJuly1999MainIndex;
                ixiSoulReaverPlayStationPALPrereleaseJuly1999MainIndex                = new BF.IndexIndex("Index", bigfile, null, 0);
                ixiSoulReaverPlayStationPALPrereleaseJuly1999MainIndex.EntryLength    = 2;
                ixiSoulReaverPlayStationPALPrereleaseJuly1999MainIndex.OffsetPosition = 1;
                //??Position = 0;
                ixiSoulReaverPlayStationPALPrereleaseJuly1999MainIndex.SubIndexType = IndexType.SR1PS1PALJuly1999SubIndex;
                return(ixiSoulReaverPlayStationPALPrereleaseJuly1999MainIndex);

                break;

            case IndexType.SR1PS1PALJuly1999SubIndex:
                BF.SoulReaverPlaystationPALFileIndex ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex;
                ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex                  = new BF.SoulReaverPlaystationPAL0x1b71FileIndex("Index", bigfile, null, 0);
                ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex.EntryLength      = 4;
                ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex.NameHashPosition = 0;
                ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex.LengthPosition   = 1;
                ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex.OffsetPosition   = 2;
                //??Position = 3;
                return(ixfSoulReaverPlaystationPALPrereleaseJuly1999SubIndex);

                break;

            case IndexType.Gex1PlayStation:
                BF.FileIndex ixfSI100;
                ixfSI100 = new BF.FileIndex("Index", bigfile, null, 0);
                ixfSI100.FirstEntryOffset = 20;
                ixfSI100.EntryLength      = 4;
                ixfSI100.NameHashPosition = 0;
                ixfSI100.LengthPosition   = 1;
                ixfSI100.OffsetPosition   = 2;
                //??Position = 3;
                return(ixfSI100);

                break;

            case IndexType.Gex1Saturn:
                BF.FileIndex ixfSI110;
                ixfSI110                  = new BF.FileIndex("Index", bigfile, null, 0);
                ixfSI110.Endianness       = BenLincoln.Data.Endianness.Big;
                ixfSI110.FirstEntryOffset = 20;
                ixfSI110.EntryLength      = 4;
                ixfSI110.NameHashPosition = 0;
                ixfSI110.LengthPosition   = 1;
                ixfSI110.OffsetPosition   = 2;
                //??Position = 3;
                return(ixfSI110);

                break;

            case IndexType.BloodOmen:
                BF.FileIndex ixfSI200;
                ixfSI200                  = new BF.FileIndex("Index", bigfile, null, 0);
                ixfSI200.EntryLength      = 3;
                ixfSI200.NameHashPosition = 0;
                ixfSI200.LengthPosition   = 1;
                ixfSI200.OffsetPosition   = 2;
                return(ixfSI200);

                break;

            case IndexType.Gex2:
                BF.SR1Proto1FileIndex ixfSI300;
                ixfSI300                          = new BF.SR1Proto1FileIndex("Index", bigfile, null, 0);
                ixfSI300.EntryLength              = 6;
                ixfSI300.NameHashPosition         = 0;
                ixfSI300.LengthPosition           = 1;
                ixfSI300.OffsetPosition           = 3;
                ixfSI300.CompressedLengthPosition = 2;
                //ixfSI300.
                //??Position = 2;
                //??Position = 4;
                //??Position = 5;
                return(ixfSI300);

                break;

            case IndexType.SR1PC:
                BF.FileIndex ixfSI400;
                ixfSI400                  = new BF.FileIndex("Index", bigfile, null, 0);
                ixfSI400.EntryLength      = 4;
                ixfSI400.NameHashPosition = 0;
                ixfSI400.LengthPosition   = 1;
                ixfSI400.OffsetPosition   = 2;
                //??Position = 3;
                return(ixfSI400);

                break;

            case IndexType.SR2AirForgeDemo:
                BF.SoulReaver2AirForgeDemoFileIndex ixfSoulReaver2AirForgeDemo;
                ixfSoulReaver2AirForgeDemo                          = new BF.SoulReaver2AirForgeDemoFileIndex("Index", bigfile, null, 0);
                ixfSoulReaver2AirForgeDemo.EntryLength              = 4;
                ixfSoulReaver2AirForgeDemo.NameHashPosition         = 0;
                ixfSoulReaver2AirForgeDemo.LengthPosition           = 1;
                ixfSoulReaver2AirForgeDemo.OffsetPosition           = 2;
                ixfSoulReaver2AirForgeDemo.CompressedLengthPosition = 3;
                return(ixfSoulReaver2AirForgeDemo);

                break;

            case IndexType.SR2PS2:
                BF.SoulReaver2PS2FileIndex ixfSoulReaver2PS2FileIndex;
                ixfSoulReaver2PS2FileIndex                          = new BF.SoulReaver2PS2FileIndex("Index", bigfile, null, 0);
                ixfSoulReaver2PS2FileIndex.EntryLength              = 3;
                ixfSoulReaver2PS2FileIndex.LengthPosition           = 0;
                ixfSoulReaver2PS2FileIndex.OffsetPosition           = 1;
                ixfSoulReaver2PS2FileIndex.CompressedLengthPosition = 2;
                return(ixfSoulReaver2PS2FileIndex);

                break;

            case IndexType.SR2PC:
                BF.FileIndexWithSeparateHashes ixfSI550;
                ixfSI550                = new BF.FileIndexWithSeparateHashes("Index", bigfile, null, 0);
                ixfSI550.EntryLength    = 3;
                ixfSI550.LengthPosition = 0;
                ixfSI550.OffsetPosition = 1;
                //??Position = 2;
                return(ixfSI550);

                break;

            case IndexType.TRLPS2Demo:
                BF.FileIndexWithSeparateHashes ixfSI600;
                ixfSI600                = new BF.FileIndexWithSeparateHashes("Index", bigfile, null, 0);
                ixfSI600.EntryLength    = 4;
                ixfSI600.LengthPosition = 0;
                ixfSI600.OffsetPosition = 1;
                //??Position = 2;
                //??Position = 3;
                return(ixfSI600);

                break;

            case IndexType.TRLPS2:
                BF.FileIndexWithSeparateHashes ixfSI650;
                ixfSI650                = new BF.FileIndexWithSeparateHashes("Index", bigfile, null, 0);
                ixfSI650.EntryLength    = 4;
                ixfSI650.LengthPosition = 0;
                ixfSI650.OffsetPosition = 1;
                //??Position = 2;
                //??Position = 3;
                //this index type uses offset values divided by 2048
                ixfSI650.OffsetMultiplier = 2048;
                return(ixfSI650);

                break;

            case IndexType.MadDashRacingBigFile:
                BF.MadDashRacingBigFileIndex ixfBloodOmen2FileIndex;
                ixfBloodOmen2FileIndex = new BF.MadDashRacingBigFileIndex("Index", bigfile, null, 0);
                ixfBloodOmen2FileIndex.FirstEntryOffset = 0;
                ixfBloodOmen2FileIndex.EntryLength      = 10;
                ixfBloodOmen2FileIndex.OffsetPosition   = 0;
                return(ixfBloodOmen2FileIndex);

                break;

            case IndexType.WhiplashBigFile:
                BF.WhiplashBigFileFileIndex ixfWhiplashBigFileFileIndex;
                ixfWhiplashBigFileFileIndex = new BF.WhiplashBigFileFileIndex("Index", bigfile, null, 0);
                ixfWhiplashBigFileFileIndex.FirstEntryOffset = 0;
                ixfWhiplashBigFileFileIndex.EntryLength      = 10;
                ixfWhiplashBigFileFileIndex.OffsetPosition   = 0;
                return(ixfWhiplashBigFileFileIndex);

                break;
            }

            return(null);
        }
        protected void ExportIndexRecursive(BF.Index whichIndex, string targetPath)
        {
            FileStream   oStream;
            StreamWriter oWriter;

            //open the file stream and enter the name of the current index
            oStream = new FileStream(targetPath, FileMode.Append, FileAccess.Write);
            oWriter = new StreamWriter(oStream);

            //if the current index has a separate table of hashes, dump that first
            bool hasSeparateHashes = true;

            try
            {
                BF.FileIndexWithSeparateHashes testCast = (BF.FileIndexWithSeparateHashes)whichIndex;
            }
            catch (InvalidCastException ex)
            {
                hasSeparateHashes = false;
            }

            if (hasSeparateHashes)
            {
                BF.FileIndexWithSeparateHashes hashIndex = (BF.FileIndexWithSeparateHashes)whichIndex;
                oWriter.WriteLine("Filename Hashes");
                oWriter.WriteLine("Entry Number,Hex,Dec");
                int hashNum = 0;
                foreach (string currentHash in hashIndex.Hashes)
                {
                    string info = hashNum.ToString() + ",";
                    //info += string.Format("{0:X8},", currentHash);
                    //info += string.Format("{0:000000000000}", currentHash);
                    info += currentHash;
                    oWriter.WriteLine(info);
                    hashNum++;
                }
            }

            //dump the raw contents of the current index
            oWriter.WriteLine("Index Name, Entry Number, Values in Hex, Values in Dec");
            int entryNum = 0;

            foreach (uint[] currentEntry in whichIndex.Entries)
            {
                string info = whichIndex.Name + "," + entryNum + ",";
                foreach (uint currentValue in currentEntry)
                {
                    info += string.Format("{0:X8},", currentValue);
                }
                info += " ,";
                foreach (uint currentValue in currentEntry)
                {
                    info += string.Format("{0:000000000000},", currentValue);
                }
                oWriter.WriteLine(info);
                entryNum++;
            }

            oWriter.Close();
            oStream.Close();

            //if this index has subindices, process them
            if ((whichIndex.Indices != null) && (whichIndex.Indices.GetUpperBound(0) > 0))
            {
                foreach (BF.Index nextIndex in whichIndex.Indices)
                {
                    ExportIndexRecursive(nextIndex, targetPath);
                }
            }
        }