From ab1f4954e0f7365a67a6e9860e0778dbd9429f17 Mon Sep 17 00:00:00 2001 From: Bluzume <39113159+KuromeSan@users.noreply.github.com> Date: Thu, 12 Aug 2021 01:03:30 +1200 Subject: [PATCH] update stuff --- .gitignore | 4 +- .vs/AppInfoParser/v16/.suo | Bin 0 -> 67584 bytes AppInfoCli/CXML.cs | 113 ++++++++++++++++++++++++------------- AppInfoCli/Program.cs | 3 +- AppInfoCli/Tools.cs | 45 ++++++++++++++- 5 files changed, 120 insertions(+), 45 deletions(-) create mode 100644 .vs/AppInfoParser/v16/.suo diff --git a/.gitignore b/.gitignore index eef088d..4f72b31 100644 --- a/.gitignore +++ b/.gitignore @@ -1,2 +1,2 @@ -*bin/* -*obj/* \ No newline at end of file +*bin* +*obj* \ No newline at end of file diff --git a/.vs/AppInfoParser/v16/.suo b/.vs/AppInfoParser/v16/.suo new file mode 100644 index 0000000000000000000000000000000000000000..9f6ecbecf994673de689c3e79a0bfa40a69a50a9 GIT binary patch literal 67584 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 literal 0 HcmV?d00001 diff --git a/AppInfoCli/CXML.cs b/AppInfoCli/CXML.cs index 603e326..18b461e 100644 --- a/AppInfoCli/CXML.cs +++ b/AppInfoCli/CXML.cs @@ -35,6 +35,7 @@ namespace CXML { String Magic = Tools.ReadStringAt(InfoFile, 0x00); + MagicNumber = Magic.Substring(0,4); if (Magic.StartsWith("PSMA")) { @@ -58,7 +59,7 @@ namespace CXML String MainDir = ""; String FileDir = ""; String XMLFilename = ""; - + String MagicNumber = ""; FileStream InfoFile; @@ -98,9 +99,10 @@ namespace CXML public void Init(string path, bool CheckMagic = true) { InfoFile = File.Open(path, FileMode.Open, FileAccess.Read); - if(CheckMagic) + bool MagicValid = _checkMagicNumber(); + if (CheckMagic) { - if (!_checkMagicNumber()) + if (!MagicValid) { throw new Exception("Incorrect magic number."); } @@ -335,7 +337,6 @@ namespace CXML InfoFile.Read(FileTable, 0x00, DataLength); return FileTable; } - public void DecompileCXML(String CXMLFile, bool force = false) { @@ -354,7 +355,7 @@ namespace CXML string XMLPath = Path.Combine(MainDir, XMLFilename); XMLFile = XmlWriter.Create(XMLPath, XMLSettings); XMLFile.WriteStartDocument(); - + XMLFile.WriteComment("Decompiled with CXML Decompiler v6 By SilicaAndPina (Magic: \"" + MagicNumber + "\")"); ReadElements(); XMLFile.WriteEndDocument(); @@ -367,11 +368,29 @@ namespace CXML { if(lpHandler.OldFileName != null) { - Console.WriteLine("Replacing: " + lpHandler.OldFileName + " With " + lpHandler.FileName); - XmlData = XmlData.Replace(lpHandler.OldFileName, lpHandler.FileName); + if(lpHandler.FileName != null) + { + string oldName = Path.Combine(lpHandler.OldFileName); + string extension = Path.GetExtension(oldName); + string folderPath = Path.GetDirectoryName(oldName); + string newPath = Path.ChangeExtension(Path.Combine(folderPath, lpHandler.FileName), extension); + File.Move(oldName, newPath); + + string xmlRelOldPath = oldName.Substring(Tools.GetRootFolder(oldName).Length + 1); + string xmlRelNewPath = newPath.Substring(Tools.GetRootFolder(newPath).Length + 1); + Console.WriteLine("Moved " + xmlRelOldPath + " => " + xmlRelNewPath); + XmlData = XmlData.Replace(xmlRelOldPath, xmlRelNewPath); + + if (ProcessFiles) + ProcessFile(newPath); + } + else + { + Console.WriteLine("Generated Filename used for " + lpHandler.OldFileName); + if (ProcessFiles) + ProcessFile(lpHandler.OldFileName); + } } - if(ProcessFiles) - ProcessFile(Path.Combine(MainDir, lpHandler.FileName)); } File.WriteAllText(XMLPath, XmlData); @@ -457,25 +476,40 @@ namespace CXML } } - public void ChangeFilename(Int64 ElementPtr, String NewName) + public void ChangeFilename(Int64 ElementPtr, String NewName, Boolean FileEntry) { - Console.WriteLine("Correcting for Loopback: 0x" + ElementPtr.ToString("X8") + " (" + NewName + ")"); + Console.WriteLine("Adding Entry for Loopback: 0x" + ElementPtr.ToString("X8") + " (" + NewName + ")"); for(int i = 0; i < FileList.Count; i++) { if(FileList[i].FilePointer == ElementPtr) { - string oldName = FileList[i].FileName; - string extension = Path.GetExtension(oldName); - string folderPath = Path.GetDirectoryName(FileList[i].FileName); - string newPath = Path.ChangeExtension(Path.Combine(folderPath, NewName), extension); - Console.WriteLine("Changed " + Path.Combine(MainDir, oldName) + " => " + Path.Combine(MainDir, newPath)); - File.Move(Path.Combine(MainDir, oldName), Path.Combine(MainDir, newPath)); - FileList[i].FileName = newPath; - FileList[i].OldFileName = oldName; - return; + if (FileEntry) + { + if (FileList[i].OldFileName != null) + break; + FileList[i].OldFileName = NewName; + return; + } + else + { + FileList[i].FileName = NewName; + return; + } } } - Console.WriteLine("Nothing to correct!"); + + LoopbackHandler lpHandler = new LoopbackHandler(); + if (FileEntry) + { + lpHandler.OldFileName = NewName; + } + else + { + lpHandler.FileName = NewName; + } + lpHandler.FilePointer = ElementPtr; + FileList.Add(lpHandler); + return; } public void ReadAttribute(String ElementName = "", Int64 ElementPtr = 0) @@ -495,12 +529,12 @@ namespace CXML break; case AttributeType.TYPE_INT: AttributeValue = bTreeTable.ReadInt32(); - TreeTable.Seek(4, SeekOrigin.Current); + Console.WriteLine("Int - Value: " + AttributeValue.ToString() + " sz:" + bTreeTable.ReadInt32()); break; case AttributeType.TYPE_FLOAT: float FloatValue = bTreeTable.ReadSingle(); AttributeValue = FloatValue.ToString()+"f"; - TreeTable.Seek(4, SeekOrigin.Current); + Console.WriteLine("Float - Value: " + AttributeValue.ToString() + " sz:" + bTreeTable.ReadInt32()); break; case AttributeType.TYPE_STRING: int StringOffset = bTreeTable.ReadInt32(); @@ -525,10 +559,13 @@ namespace CXML case AttributeType.TYPE_HASH_ID: int HashTableOffset = bTreeTable.ReadInt32(); int HashTableSize = bTreeTable.ReadInt32(); - HashIDTable.Seek(HashTableOffset*4, SeekOrigin.Begin); + HashIDTable.Seek(HashTableOffset * 4, SeekOrigin.Begin); + Console.WriteLine("Hash ID Offset:" + HashTableOffset.ToString() + " size: " + HashTableSize); + + int HashId = bHashIDTable.ReadInt32(); + + AttributeValue = "@"+HashId.ToString("X8"); - int HashID = bHashIDTable.ReadInt32(); - AttributeValue = HashID.ToString("X8"); break; case AttributeType.TYPE_INTEGER_ARRAY: int IntArrayOffset = bTreeTable.ReadInt32(); @@ -571,7 +608,6 @@ namespace CXML String Extension = Tools.GetFileExtension(FileData); String FileName = Path.Combine(FileDir, ElementName, FileHash + Extension); - String finalName = Path.Combine(Path.GetFileName(FileDir), ElementName, FileHash + Extension); if (!File.Exists(FileName)) { Console.WriteLine("Writing: " + FileName); @@ -580,18 +616,15 @@ namespace CXML Directory.CreateDirectory(Path.GetDirectoryName(FileName)); File.WriteAllBytes(FileName, FileData); - LoopbackHandler lpHandler = new LoopbackHandler(); - lpHandler.FileName = finalName; - lpHandler.OldFileName = null; - lpHandler.FilePointer = ElementPtr; - FileList.Add(lpHandler); + ChangeFilename(ElementPtr, FileName, true); } else { Console.WriteLine("File allready extracted \n(theres a VERY low chance that it acturally is a different file that has the same hash.)"); } - AttributeValue = finalName; + string xmlRelPath = FileName.Substring(Tools.GetRootFolder(FileName).Length + 1); + AttributeValue = xmlRelPath; break; case AttributeType.TYPE_ID_STRING_LOOPBACK: int StringIdTableOffset = bTreeTable.ReadInt32(); @@ -604,9 +637,9 @@ namespace CXML Console.WriteLine("Loopback: " + LoopbackAttribute +" "+ LoopbackPtr.ToString("X")+" ("+ElementPtr.ToString("X")+")"); AttributeValue = Tools.ReadString(StringIDTable); - ChangeFilename(LoopbackPtr, AttributeValue.ToString()); + ChangeFilename(LoopbackPtr, AttributeValue.ToString(), false); - TreeTable.Seek(4, SeekOrigin.Current); + Console.WriteLine("Loopback String: " + StringIdTableOffset + " sz: " + bTreeTable.ReadInt32()); break; case AttributeType.TYPE_ID_STRING: Console.WriteLine("UNSUPPORTED TYPE @ " + TreeTable.Position); @@ -624,18 +657,18 @@ namespace CXML LoopbackAttribute = Tools.ReadStringAt(StringTable, StringPtr); Console.WriteLine("Loopback: " + LoopbackAttribute + " " + LoopbackPtr.ToString("X") + " (" + ElementPtr.ToString("X") + ")"); - AttributeValue = IDValue.ToString("X8"); - ChangeFilename(LoopbackPtr, AttributeValue.ToString()); + AttributeValue = "$"+IDValue.ToString("X8"); + ChangeFilename(LoopbackPtr, IDValue.ToString("X8"), false); - TreeTable.Seek(4, SeekOrigin.Current); + Console.WriteLine("Loopback Int: " + IntIdTableOffset + " sz: " + bTreeTable.ReadInt32()); break; case AttributeType.TYPE_ID_INT: IntIdTableOffset = bTreeTable.ReadInt32(); IntIDTable.Seek(IntIdTableOffset + 4, SeekOrigin.Begin); IDValue = bIntIDTable.ReadInt32(); - AttributeValue = IDValue.ToString("X8"); - TreeTable.Seek(4, SeekOrigin.Current); + AttributeValue = "#"+IDValue.ToString("X8"); + Console.WriteLine("Int Id: " + IntIdTableOffset + " sz: " + bTreeTable.ReadInt32()); break; default: Console.WriteLine("UNKNOWN TYPE @ " + TreeTable.Position); diff --git a/AppInfoCli/Program.cs b/AppInfoCli/Program.cs index a5798ab..d3a5749 100644 --- a/AppInfoCli/Program.cs +++ b/AppInfoCli/Program.cs @@ -36,7 +36,7 @@ namespace CXMLCli Console.WriteLine("\t-w --wait-exit Wait for keypress before exiting"); Console.WriteLine("\t-d --decompile Decompile CXML."); Console.WriteLine("Example: " + Path.GetFileName(Assembly.GetEntryAssembly().Location) + " app.info -f -s -t -f -d"); - Console.WriteLine("Default functonality is to Decompile,\ntThis is canceled if any other arguments passed."); + Console.WriteLine("Default functonality is to Decompile,\nThis is canceled if any other arguments passed."); return; } @@ -147,6 +147,7 @@ namespace CXMLCli if(cxmlParser.WaitExit) Console.ReadKey(); } + return 0; } } } diff --git a/AppInfoCli/Tools.cs b/AppInfoCli/Tools.cs index 7297f12..727bc02 100644 --- a/AppInfoCli/Tools.cs +++ b/AppInfoCli/Tools.cs @@ -1,6 +1,7 @@ using System; using System.Collections.Generic; using System.Drawing; +using System.Drawing.Imaging; using System.IO; using System.Linq; using System.Security.Cryptography; @@ -38,7 +39,29 @@ namespace General { if (IsImage(Bytes)) { - return ".png"; + using (Bitmap bmp = GetBitmap(Bytes)) + { + if (bmp.RawFormat.Equals(ImageFormat.Jpeg)) + return ".jpeg"; + else if (bmp.RawFormat.Equals(ImageFormat.Bmp)) + return ".bmp"; + else if (bmp.RawFormat.Equals(ImageFormat.Gif)) + return ".gif"; + else if (bmp.RawFormat.Equals(ImageFormat.Png)) + return ".png"; + else if (bmp.RawFormat.Equals(ImageFormat.Tiff)) + return ".tiff"; + else if (bmp.RawFormat.Equals(ImageFormat.Icon)) + return ".ico"; + else if (bmp.RawFormat.Equals(ImageFormat.Exif)) + return ".exif"; + else if (bmp.RawFormat.Equals(ImageFormat.Emf)) + return ".emf"; + else if (bmp.RawFormat.Equals(ImageFormat.Wmf)) + return ".wmf"; + else + return ".raw"; + } } else if (IsZlib(Bytes)) { @@ -60,6 +83,10 @@ namespace General { return ".gim"; } + else if(!HasBinaryContent(Encoding.UTF8.GetString(Bytes))) + { + return ".txt"; + } else { return ".bin"; @@ -178,7 +205,10 @@ namespace General ms.Seek(ogPos, SeekOrigin.Begin); return i; } - + public static bool HasBinaryContent(string content) + { + return content.Any(ch => char.IsControl(ch) && ch != '\r' && ch != '\n'); + } public static int ReadInt(Stream ms) { BinaryReader BinReader = new BinaryReader(ms); @@ -203,6 +233,17 @@ namespace General int i = BitConverter.ToInt32(IntBytes, 0x00); return i; } + public static String GetRootFolder(string path) + { + while (true) + { + string temp = Path.GetDirectoryName(path); + if (String.IsNullOrEmpty(temp)) + break; + path = temp; + } + return path; + } public static String GenerateHash(byte[] Data) {