private void MoveCaches(string cookedPath, string NewCache)
        {
            //DebugOutput.PrintLn( "\nMoving cache...\n");
            //Fix the GUID
            using (FileStream newCache = new FileStream(Path.Combine(cookedPath, NewCache), FileMode.Open, FileAccess.Read))
            {
                SaltPropertyReader.Property GUIDProp = properties["TFCFileGuid"];

                for (int i = 0; i < 16; i++)
                {
                    SaltPropertyReader.PropertyValue tempVal = GUIDProp.Value.Array[i];
                    tempVal.IntValue = newCache.ReadByte();
                    GUIDProp.Value.Array[i] = tempVal;
                }
            }


            //Move across any existing textures
            //using (FileStream oldCache = new FileStream(Path.Combine(cookedPath, arcName + ".tfc"), FileMode.Open, FileAccess.Read))
            using (FileStream oldCache = new FileStream(FullArcPath, FileMode.Open, FileAccess.Read))
            {
                using (FileStream newCache = new FileStream(Path.Combine(cookedPath, NewCache), FileMode.Append, FileAccess.Write))
                {
                    for (int i = 0; i < privateimgList.Count; i++)
                    {
                        ImageInfo img = privateimgList[i];

                        switch (img.storageType)
                        {
                            case storage.arcCpr:
                                byte[] buff = new byte[img.cprSize];
                                oldCache.Seek(img.offset, SeekOrigin.Begin);
                                Buffer.BlockCopy(oldCache.ReadBytes(img.cprSize), 0, buff, 0, img.cprSize);
                                img.offset = (int)newCache.Position;
                                newCache.WriteBytes(buff);
                                break;
                            case storage.arcUnc:
                                buff = new byte[img.uncSize];
                                oldCache.Seek(img.offset, SeekOrigin.Begin);
                                Buffer.BlockCopy(oldCache.ReadBytes(img.cprSize), 0, buff, 0, img.cprSize);
                                img.offset = (int)newCache.Position;
                                newCache.WriteBytes(buff);
                                break;
                            case storage.pccSto:
                                break;
                            case storage.empty:
                                break;
                            default:
                                throw new NotImplementedException("Storage type not supported yet");
                        }
                        privateimgList[i] = img;
                    }
                }
            }
        }
Example #2
0
        public void write(string FileName)
        {
            FileStream FileStream = new FileStream(FileName, FileMode.OpenOrCreate, FileAccess.Write);
            FileStream.WriteStruct(this.header);

            if (this.header.revision >= 3)
            {
                FileStream.WriteStruct(this.headerExtraRevision3);
            }

            FileStream.WriteStructVector(dimensionTable);
            FileStream.WriteStructVector(xAdjustTable);
            FileStream.WriteStructVector(yAdjustTable);
            FileStream.WriteStructVector(advanceTable);
            FileStream.WriteStructVector(packedShadowCharMap);

            if (header.revision == 3)
            {
                FileStream.WriteStructVector(charmapCompressionTable1);
                FileStream.WriteStructVector(charmapCompressionTable2);
            }

            FileStream.WriteStructVector(packedCharMap);
            FileStream.WriteStructVector(packedCharPointerTable);

            FileStream.WriteBytes(charData);
        }
Example #3
0
 private void dumpRawExportToolStripMenuItem_Click(object sender, EventArgs e)
 {
     if (CurrList != 2)
         return;
     int n = listBox1.SelectedIndex;
     if (n < 0)
         return;
     PCCObject.ExportEntry exp = pcc.Exports[n];
     SaveFileDialog d = new SaveFileDialog();
     //d.Filter = "*.u;*.upk;*sfm|*.u;*.upk;*sfm";
     d.Filter = "Binary File|*.bin";
     if (d.ShowDialog() == System.Windows.Forms.DialogResult.OK)
     {
         using (FileStream fs = new FileStream(d.FileName, FileMode.Create, FileAccess.Write))
         {
             fs.WriteBytes(exp.Data);
         }
         MessageBox.Show("Done.");
     }
 }
Example #4
0
 public void DumpPCC(string path)
 {
     listsStream.Seek(0, SeekOrigin.Begin);
     byte[] stream = listsStream.ToArray();
     using (FileStream fs = new FileStream(path, FileMode.Create))
     {
         fs.WriteBytes(stream);
     }
 }
            /// <summary>
            /// Write current job to fileStream.
            /// </summary>
            /// <param name="fs">FileStream to write to.</param>
            public void WriteJobToFile(FileStream fs)
            {
                // KFreon: Write job name
                //fs.WriteBytes(BitConverter.GetBytes(Name.Length));
                fs.WriteValueS32(Name.Length);
                foreach (char c in Name)
                    fs.WriteByte((byte)c);

                // KFreon: Write script
                //fs.WriteBytes(BitConverter.GetBytes(Script.Length));
                fs.WriteValueS32(Script.Length);
                foreach (char c in Script)
                    fs.WriteByte((byte)c);

                // KFreon: Write job data
                //fs.WriteBytes(BitConverter.GetBytes(data.Length));
                fs.WriteValueS32(data.Length);
                fs.WriteBytes(data);
            }
Example #6
0
        public void Write(string FileName)
        {
            var FileStream = new FileStream(FileName, FileMode.OpenOrCreate, FileAccess.Write);
            FileStream.WriteStruct(this.Header);

            if (this.Header.Revision >= 3)
            {
                FileStream.WriteStruct(this.HeaderExtraRevision3);
            }

            FileStream.WriteStructVector(DimensionTable);
            FileStream.WriteStructVector(XAdjustTable);
            FileStream.WriteStructVector(YAdjustTable);
            FileStream.WriteStructVector(AdvanceTable);
            FileStream.WriteStructVector(PackedShadowCharMap);

            if (Header.Revision == 3)
            {
                FileStream.WriteStructVector(CharmapCompressionTable1);
                FileStream.WriteStructVector(CharmapCompressionTable2);
            }

            FileStream.WriteStructVector(PackedCharMap);
            FileStream.WriteStructVector(PackedCharPointerTable);

            FileStream.WriteBytes(CharData);
        }
Example #7
0
        /// <summary>
        ///     save ME3PCCObject to file.
        /// </summary>
        /// <param name="newFileName">set full path + file name.</param>
        /// <param name="saveCompress">set true if you want a zlib compressed pcc file.</param>
        public void saveToFile(string newFileName = null, bool WriteToMemoryStream = false)
        {
            //Refresh header and namelist
            listsStream.Seek(0, SeekOrigin.End);
            NameOffset = (int)listsStream.Position;
            NameCount = Names.Count;
            foreach (string name in Names)
            {
                listsStream.WriteValueS32(-(name.Length + 1));
                listsStream.WriteString(name + "\0", (uint)(name.Length + 1) * 2, Encoding.Unicode);
            }

            listsStream.Seek(0, SeekOrigin.Begin);
            listsStream.WriteBytes(header);

            // KFreon: If want to write to memorystream instead of to file, exit here
            if (WriteToMemoryStream)
                return;

            // Heff: try to remove any read-only attribute if we have permission to:
            File.SetAttributes(newFileName, FileAttributes.Normal);

            while (true)
            {
                int tries = 0;
                try
                {
                    using (FileStream fs = new FileStream(newFileName, FileMode.Create, FileAccess.Write))
                    {
                        byte[] test = listsStream.ToArray();
                        fs.WriteBytes(test);
                        test = null;
                    }
                    break;
                }
                catch (IOException)
                {
                    System.Threading.Thread.Sleep(50);
                    tries++;
                    if (tries > 100)
                    {
                        throw new IOException("The PCC can't be written to disk because of an IOException");
                    }
                }
            }
            listsStream.Dispose();
            Exports.Clear();
            Imports.Clear();
            Names.Clear();
            Exports = null;
            Imports = null;
            Names = null;
            GC.Collect();
        }
        /// <summary>
        /// Step #5
        /// 
        /// Save the unpacked file.
        /// </summary>
        /// <returns></returns>
        private bool Step5()
        {
            FileStream fStream = null;
            byte[] overlayData = null;

            try
            {
                // Determine if the file has any overlay data..
                var lastSection = this.File.Sections.Last();
                var fileSize = lastSection.SizeOfRawData + lastSection.PointerToRawData;

                if (fileSize < this.File.FileData.Length)
                {
                    // Overlay exists, copy it..
                    overlayData = new byte[this.File.FileData.Length - fileSize];
                    Array.Copy(this.File.FileData, fileSize, overlayData, 0, this.File.FileData.Length - fileSize);
                }
            }
            catch
            {
                return false;
            }

            try
            {
                // Open the unpacked file for writing..
                var unpackedPath = this.File.FilePath + ".unpacked.exe";
                fStream = new FileStream(unpackedPath, FileMode.Create, FileAccess.ReadWrite);

                // Write the dos header back to the file..
                fStream.WriteBytes(Helpers.GetStructureBytes(this.File.DosHeader));

                // Write the dos stub back to the file if it exists..
                if (this.File.DosStubSize > 0)
                    fStream.WriteBytes(this.File.DosStubData);

                // Determine if we should remove the .bind section..
                if (!Program.HasArgument("--keepbind"))
                {
                    // Remove the .bind section from the file..
                    this.File.Sections.Remove(this.File.GetSection(".bind"));
                }

                // Rebuild the NT headers of the file..
                var ntHeaders = this.File.NtHeaders;
                var lastSection = this.File.Sections[this.File.Sections.Count - 1];
                if (!Program.HasArgument("--keepbind"))
                    ntHeaders.FileHeader.NumberOfSections--;
                ntHeaders.OptionalHeader.AddressOfEntryPoint = this.StubHeader.OriginalEntryPoint;
                ntHeaders.OptionalHeader.SizeOfImage = lastSection.VirtualAddress + lastSection.VirtualSize;

                // Write the Nt headers to the file..
                fStream.WriteBytes(Helpers.GetStructureBytes(ntHeaders));

                // Write the sections to the file..
                foreach (var s in this.File.Sections)
                {
                    // Obtain the sections data from the original file..
                    var sectionData = new byte[s.SizeOfRawData];
                    Array.Copy(this.File.FileData, this.File.GetFileOffsetFromRva(s.VirtualAddress), sectionData, 0, s.SizeOfRawData);

                    // Write the section header to the file..
                    fStream.WriteBytes(Helpers.GetStructureBytes(s));

                    // Write the section data to the file..
                    var sectionOffset = fStream.Position;
                    fStream.Position = s.PointerToRawData;

                    // Determine if this is the code section..
                    if (s.SizeOfRawData == this.CodeSection.SizeOfRawData && s.PointerToRawData == this.CodeSection.PointerToRawData)
                        fStream.WriteBytes(this.CodeSectionData ?? sectionData);
                    else
                        fStream.WriteBytes(sectionData);

                    // Reset the file offset..
                    fStream.Position = sectionOffset;
                }

                // Skip to the end of the stream..
                fStream.Position = fStream.Length;

                // Write the overlay back to the file if it exists..
                if (overlayData != null)
                    fStream.WriteBytes(overlayData);

                return true;
            }
            catch
            {
                return false;
            }
            finally
            {
                fStream?.Dispose();
            }
        }
Example #9
0
        /// <summary>
        /// This method is an alternate way of saving PCCs
        /// Instead of reconstructing the PCC from the data taken, it instead copies across the existing
        /// data, appends new exports, updates the export list, changes the namelist location and updates the
        /// value in the header
        /// </summary>
        /// <param name="newFileName">The filename to write to</param>
        /// 
        public void appendSave(string newFileName)
        {
            IEnumerable<ME2ExportEntry> replaceExports;
            IEnumerable<ME2ExportEntry> appendExports;

            int lastDataOffset;
            int max;
            if (IsAppend)
            {
                replaceExports = exports.Where(export => export.DataChanged && export.DataOffset < NameOffset && export.DataSize <= export.OriginalDataSize);
                appendExports = exports.Where(export => export.DataOffset > NameOffset || (export.DataChanged && export.DataSize > export.OriginalDataSize));
                max = exports.Where(exp => exp.DataOffset < NameOffset).Max(e => e.DataOffset);
            }
            else
            {
                IEnumerable<ME2ExportEntry> changedExports;
                changedExports = exports.Where(export => export.DataChanged);
                replaceExports = changedExports.Where(export => export.DataSize <= export.OriginalDataSize);
                appendExports = changedExports.Except(replaceExports);
                max = exports.Max(maxExport => maxExport.DataOffset);
            }

            ME2ExportEntry lastExport = exports.Find(export => export.DataOffset == max);
            lastDataOffset = lastExport.DataOffset + lastExport.DataSize;

            byte[] oldPCC = new byte[lastDataOffset];//Check whether compressed
            if (IsCompressed)
            {
                oldPCC = CompressionHelper.Decompress(FileName).Take(lastDataOffset).ToArray();
                IsCompressed = false;
            }
            else
            {
                using (FileStream oldPccStream = new FileStream(this.FileName, FileMode.Open))
                {
                    //Read the original data up to the last export
                    oldPccStream.Read(oldPCC, 0, lastDataOffset);
                }
            }
            //Start writing the new file
            using (FileStream newPCCStream = new FileStream(newFileName, FileMode.Create))
            {
                newPCCStream.Seek(0, SeekOrigin.Begin);
                //Write the original file up til the last original export (note that this leaves in all the original exports)
                newPCCStream.Write(oldPCC, 0, lastDataOffset);

                //write the in-place export updates
                foreach (ME2ExportEntry export in replaceExports)
                {
                    newPCCStream.Seek(export.DataOffset, SeekOrigin.Begin);
                    export.DataSize = export.Data.Length;
                    newPCCStream.WriteBytes(export.Data);
                }

                
                newPCCStream.Seek(lastDataOffset, SeekOrigin.Begin);
                //Set the new nameoffset and namecounts
                NameOffset = (int)newPCCStream.Position;
                NameCount = names.Count;
                //Then write out the namelist
                foreach (string name in names)
                {
                    newPCCStream.WriteValueS32(name.Length + 1);
                    newPCCStream.WriteString(name);
                    newPCCStream.WriteByte(0);
                    newPCCStream.WriteValueS32(-14);
                }

                //Write the import list
                ImportOffset = (int)newPCCStream.Position;
                ImportCount = imports.Count;
                foreach (ImportEntry import in imports)
                {
                    newPCCStream.WriteBytes(import.header);
                }

                //append the new data
                foreach (ME2ExportEntry export in appendExports)
                {
                    export.DataOffset = (int)newPCCStream.Position;
                    export.DataSize = export.Data.Length;
                    newPCCStream.Write(export.Data, 0, export.Data.Length);
                }
                
                //Write the export list
                ExportOffset = (int)newPCCStream.Position;
                ExportCount = exports.Count;
                foreach (ME2ExportEntry export in exports)
                {
                    newPCCStream.WriteBytes(export.header);
                }

                IsAppend = true;

                //write the updated header
                newPCCStream.Seek(0, SeekOrigin.Begin);
                newPCCStream.WriteBytes(header);
            }
            AfterSave();
        }