private Stream Decrypt(out ArchiveListingHeaderV2 header)
        {
            Stream result = _accessor.ExtractListing();
            try
            {
                header = result.ReadStruct<ArchiveListingHeaderV2>();
                if (header.IsValid(result.Length))
                    return result;

                using (TempFileProvider tmpProvider = new TempFileProvider("filelist", ".win32.bin"))
                {
                    using (Stream output = tmpProvider.Create())
                    {
                        output.WriteStruct(header);
                        result.CopyTo(output);
                        result.SafeDispose();
                    }

                    Process decrypter = new Process
                    {
                        StartInfo = new ProcessStartInfo()
                        {
                            FileName = @"Resources\Executable\ffxiiicrypt.exe",
                            Arguments = "-d \"" + tmpProvider.FilePath + "\" 2",
                            CreateNoWindow = true,
                            UseShellExecute = false,
                            RedirectStandardOutput = true,
                            RedirectStandardError = true
                        }
                    };
                    decrypter.Start();
                    Task<string> erroMessage = decrypter.StandardError.ReadToEndAsync();
                    Task<string> outputMessage = decrypter.StandardOutput.ReadToEndAsync();
                    decrypter.WaitForExit();
                    if (decrypter.ExitCode != 0)
                    {
                        StringBuilder sb = new StringBuilder("Decryption error! Code: ");
                        sb.AppendLine(decrypter.ExitCode.ToString());
                        sb.AppendLine("Error: ");
                        sb.AppendLine(erroMessage.Result);
                        sb.AppendLine("Output: ");
                        sb.AppendLine(outputMessage.Result);

                        throw new InvalidDataException(sb.ToString());
                    }

                    result = tmpProvider.OpenRead();
                    header = result.ReadStruct<ArchiveListingHeaderV2>();
                    if (!header.IsValid(result.Length))
                        throw new InvalidDataException();
                }

                return result;
            }
            catch
            {
                result.SafeDispose();
                throw;
            }
        }
Example #2
0
        public void Write()
        {
            using (MemoryStream headerBuff = new MemoryStream(32768))
                using (MemoryStream textBuff = new MemoryStream(32768))
                {
                    ArchiveListingBlockInfo[]   blocksInfo;
                    ArchiveListingEntryInfoV2[] entriesInfoV2;
                    ArchiveListingTextWriterV2  textWriter = new ArchiveListingTextWriterV2(textBuff);
                    textWriter.Write(_listing, out blocksInfo, out entriesInfoV2);

                    for (int i = 0; i < entriesInfoV2.Length; i++)
                    {
                        ArchiveListingEntryInfoV2 info = entriesInfoV2[i];
                        ArchiveEntry entry             = _listing[i];
                        info.UnknownNumber = entry.UnknownNumber;
                        info.UnknownValue  = entry.UnknownValue;
                        info.UnknownData   = entry.UnknownData;
                    }

                    byte[] buff       = new byte[8192];
                    int    blocksSize = (int)textBuff.Position;
                    textBuff.Position = 0;

                    ArchiveListingHeaderV2 header = (ArchiveListingHeaderV2)_listing.Header;
                    header.EntriesCount   = entriesInfoV2.Length;
                    header.RawBlockOffset = entriesInfoV2.Length * 8 + 12;
                    header.RawInfoOffset  = header.RawBlockOffset + blocksInfo.Length * 12;

                    headerBuff.WriteContent(header);
                    foreach (ArchiveListingEntryInfoV2 entry in entriesInfoV2)
                    {
                        headerBuff.WriteContent(entry);
                    }
                    foreach (ArchiveListingBlockInfo block in blocksInfo)
                    {
                        headerBuff.WriteStruct(block);
                    }

                    int hederSize = (int)headerBuff.Length;
                    headerBuff.Position = 0;

                    if (header.IsEncrypted)
                    {
                        RecreateEncryptedListing(headerBuff, hederSize, textBuff, blocksSize, buff);
                    }
                    else
                    {
                        using (Stream output = _accessor.RecreateListing(hederSize + blocksSize))
                        {
                            headerBuff.CopyToStream(output, hederSize, buff);
                            textBuff.CopyToStream(output, blocksSize, buff);
                        }
                    }
                }
        }
Example #3
0
        private Stream Decrypt(out ArchiveListingHeaderV2 header)
        {
            Stream result = _accessor.ExtractListing();

            try
            {
                header = result.ReadContent <ArchiveListingHeaderV2>();
                if (header.IsValid(result.Length))
                {
                    header.IsEncrypted = false;
                    return(result);
                }

                /*using (*/
                TempFileProvider tmpProvider = new TempFileProvider(_accessor.ListingEntry.Name /*"filelist"*/, ".win32.bin");/*)*/
                {
                    using (Stream output = tmpProvider.Create())
                    {
                        output.WriteContent(header);
                        result.CopyTo(output);
                        result.SafeDispose();
                    }

                    Process decrypter = new Process
                    {
                        StartInfo = new ProcessStartInfo()
                        {
                            FileName               = @"Resources\Executable\ffxiiicrypt.exe",
                            Arguments              = "-d \"" + tmpProvider.FilePath + "\" 2",
                            CreateNoWindow         = true,
                            UseShellExecute        = false,
                            RedirectStandardOutput = true,
                            RedirectStandardError  = true
                        }
                    };
                    decrypter.Start();
                    Task <string> erroMessage   = decrypter.StandardError.ReadToEndAsync();
                    Task <string> outputMessage = decrypter.StandardOutput.ReadToEndAsync();
                    decrypter.WaitForExit();
                    if (decrypter.ExitCode != 0)
                    {
                        StringBuilder sb = new StringBuilder("Decryption error! Code: ");
                        sb.AppendLine(decrypter.ExitCode.ToString());
                        sb.AppendLine("Error: ");
                        sb.AppendLine(erroMessage.Result);
                        sb.AppendLine("Output: ");
                        sb.AppendLine(outputMessage.Result);

                        throw new InvalidDataException(sb.ToString());
                    }

                    result             = tmpProvider.OpenRead();
                    header             = result.ReadContent <ArchiveListingHeaderV2>();
                    header.IsEncrypted = true;
                    if (!header.IsValid(result.Length))
                    {
                        throw new InvalidDataException();
                    }
                }

                return(result);
            }
            catch
            {
                result.SafeDispose();
                throw;
            }
        }