/// <summary> /// Parse out the xml string from the passed chunk data byte array /// </summary> /// <param name="chunkDataByteArray"></param> /// <returns>xml string</returns> private static string ParseChunkData(byte[] chunkDataByteArray) { var bf = new BinaryFile(chunkDataByteArray, BinaryFile.ByteOrder.BigEndian); int val1 = bf.ReadInt32(); int val2 = bf.ReadInt32(); int val3 = bf.ReadInt32(); string val4 = bf.ReadString(4); string val5 = bf.ReadString(4); //int chunkSize = byteArray.Length - 32; int chunkSize = bf.ReadInt32(); //int val6 = bf.ReadInt32(); string val7 = bf.ReadString(4); var xmlChunkBytes = new byte[chunkSize]; xmlChunkBytes = bf.ReadBytes(0, chunkSize, BinaryFile.ByteOrder.LittleEndian); string xmlString = BinaryFile.ByteArrayToString(xmlChunkBytes); int val8 = bf.ReadInt32(BinaryFile.ByteOrder.LittleEndian); return(xmlString); }
public static void Read24Bit(BinaryFile waveFile, float[][] sound, int sampleCount, int channels) { for (int i = 0; i < sampleCount; i++) { for (int ic = 0; ic < channels; ic++) { byte[] buffer = waveFile.ReadBytes(0, 3); float f = (((sbyte)buffer[2] << 16) | (buffer[1] << 8) | buffer[0]) / 8388608.0f; sound[ic][i] = f; } } }
public byte[] Read(int offset, int count) { lock (_lockObj) { // remember that offset is the starting point in the buffer (bytes), not offset in string. // so use seek instead _binaryFile.Seek(offset, SeekOrigin.Begin); count = (int)Math.Min(count, EndPosition - _binaryFile.Position); if (count <= 0) { return(new byte[0]); } return(_binaryFile.ReadBytes(0, count, BinaryFile.ByteOrder.LittleEndian)); } }
static readonly byte[] NKS_NICNT_TOC = new byte[] { 0x2F, 0x5C, 0x20, 0x4E, 0x49, 0x20, 0x46, 0x43, 0x20, 0x54, 0x4F, 0x43, 0x20, 0x20, 0x2F, 0x5C }; // /\ NI FC TOC /\ public static void Unpack(string inputFilePath, string outputDirectoryPath, bool doList, bool doVerbose) { using (BinaryFile bf = new BinaryFile(inputFilePath, BinaryFile.ByteOrder.LittleEndian, false)) { var header = bf.ReadBytes(16); if (header.SequenceEqual(NKS_NICNT_MTD)) // 2F 5C 20 4E 49 20 46 43 20 4D 54 44 20 20 2F 5C /\ NI FC MTD /\ { bf.Seek(66, SeekOrigin.Begin); string version = bf.ReadString(66, Encoding.Unicode).TrimEnd('\0'); Log.Information("Version: " + version); string outputFileName = Path.GetFileNameWithoutExtension(inputFilePath); if (!doList) { IOUtils.CreateDirectoryIfNotExist(Path.Combine(outputDirectoryPath, outputFileName)); } // Save version in ContentVersion.txt if (!doList) { IOUtils.WriteTextToFile(Path.Combine(outputDirectoryPath, outputFileName, "ContentVersion.txt"), version); } int unknown1 = bf.ReadInt32(); if (doVerbose) { Log.Debug("Unknown1: " + unknown1); } bf.Seek(144, SeekOrigin.Begin); int startOffset = bf.ReadInt32(); Log.Information("Start Offset: " + startOffset); int unknown3 = bf.ReadInt32(); if (doVerbose) { Log.Debug("Unknown3: " + unknown3); } bf.Seek(256, SeekOrigin.Begin); string productHintsXml = bf.ReadStringNull(); Log.Information(string.Format("Read ProductHints Xml with length {0} characters.", productHintsXml.Length)); if (doVerbose) { Log.Debug("ProductHints Xml:\n" + productHintsXml); } // Save productHints as xml if (!doList) { IOUtils.WriteTextToFile(Path.Combine(outputDirectoryPath, outputFileName, outputFileName + ".xml"), productHintsXml); } // get the product hints as an object var productHints = ProductHintsFactory.ReadFromString(productHintsXml); if (productHints != null && productHints.Product.Icon != null && productHints.Product.Icon.ImageBytes != null) { ProductHintsFactory.UpdateImageFromImageBytes(productHints); var image = productHints.Product.Icon.Image; var imageFormat = productHints.Product.Icon.ImageFormat; if (image != null && imageFormat != null) { Log.Information(string.Format("Found Icon in ProductHints Xml in {0} format. (Dimensions: {1} x {2}, Width: {1} pixels, Height: {2} pixels, Bit depth: {3} bpp)", imageFormat.Name, image.Width, image.Height, image.PixelType.BitsPerPixel)); // save icon to file if (!doList) { var iconFileName = outputFileName + " Icon." + imageFormat.Name.ToLower(); var iconFilePath = Path.Combine(outputDirectoryPath, outputFileName, iconFileName); if (doVerbose) { Log.Debug("Saving Icon to: " + iconFilePath); } // save using ImageSharp // var imageEncoder = image.GetConfiguration().ImageFormatsManager.FindEncoder(imageFormat); // image.Save(iconFilePath, imageEncoder); // save using image bytes BinaryFile.ByteArrayToFile(iconFilePath, productHints.Product.Icon.ImageBytes); } } } bf.Seek(startOffset + 256, SeekOrigin.Begin); var header2 = bf.ReadBytes(16); if (header2.SequenceEqual(NKS_NICNT_MTD)) // 2F 5C 20 4E 49 20 46 43 20 4D 54 44 20 20 2F 5C /\ NI FC MTD /\ { bf.ReadBytes(116); long unknown4 = bf.ReadInt64(); if (doVerbose) { Log.Debug("Unknown4: " + unknown4); } bf.ReadBytes(4); long unknown5 = bf.ReadInt64(); if (doVerbose) { Log.Debug("Unknown5: " + unknown5); } bf.ReadBytes(104); long unknown6 = bf.ReadInt64(); if (doVerbose) { Log.Debug("Unknown6: " + unknown6); } var delimiter1 = bf.ReadBytes(8); if (doVerbose) { Log.Debug("Delimiter1: " + StringUtils.ByteArrayToHexString(delimiter1)); // F0 F0 F0 F0 F0 F0 F0 F0 } if (!delimiter1.SequenceEqual(new byte[] { 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0, 0xF0 })) { Log.Error("Delimiter1 not as expected 'F0 F0 F0 F0 F0 F0 F0 F0' but got " + StringUtils.ToHexAndAsciiString(delimiter1)); } long totalResourceCount = bf.ReadInt64(); Log.Information("Total Resource Count: " + totalResourceCount); long totalResourceLength = bf.ReadInt64(); Log.Information("Total Resource Byte Length: " + totalResourceLength); var resourceList = new List <NICNTResource>(); var header3 = bf.ReadBytes(16); if (header3.SequenceEqual(NKS_NICNT_TOC)) // 2F 5C 20 4E 49 20 46 43 20 54 4F 43 20 20 2F 5C /\ NI FC TOC /\ { bf.ReadBytes(600); long lastEndIndex = 0; for (int i = 0; i < totalResourceCount; i++) { var resource = new NICNTResource(); Log.Information("-------- Index: " + bf.Position + " --------"); long resCounter = bf.ReadInt64(); Log.Information("Resource Counter: " + resCounter); resource.Count = resCounter; bf.ReadBytes(16); string resName = bf.ReadString(600, Encoding.Unicode).TrimEnd('\0'); Log.Information("Resource Name: " + resName); resource.Name = resName; long resUnknown = bf.ReadInt64(); if (doVerbose) { Log.Debug("Resource Unknown: " + resUnknown); } long resEndIndex = bf.ReadInt64(); Log.Information("Resource End Index: " + resEndIndex); resource.EndIndex = resEndIndex; // store calculated length if (lastEndIndex > 0) { resource.Length = resEndIndex - lastEndIndex; } else { // for the very first entry the end index is the same as the byte length resource.Length = resEndIndex; } Log.Information("Calculated Resource Byte Length: " + resource.Length); lastEndIndex = resEndIndex; resourceList.Add(resource); } Log.Information("-------- Index: " + bf.Position + " --------"); var delimiter2 = bf.ReadBytes(8); if (doVerbose) { Log.Debug("Delimiter2: " + StringUtils.ByteArrayToHexString(delimiter2)); // F1 F1 F1 F1 F1 F1 F1 F1 } if (!delimiter2.SequenceEqual(new byte[] { 0xF1, 0xF1, 0xF1, 0xF1, 0xF1, 0xF1, 0xF1, 0xF1 })) { Log.Error("Delimiter2 not as expected 'F1 F1 F1 F1 F1 F1 F1 F1' but got " + StringUtils.ToHexAndAsciiString(delimiter2)); } long unknown13 = bf.ReadInt64(); if (doVerbose) { Log.Debug("Unknown13: " + unknown13); } long unknown14 = bf.ReadInt64(); if (doVerbose) { Log.Debug("Unknown14: " + unknown14); } var header4 = bf.ReadBytes(16); if (header4.SequenceEqual(NKS_NICNT_TOC)) // 2F 5C 20 4E 49 20 46 43 20 54 4F 43 20 20 2F 5C /\ NI FC TOC /\ { bf.ReadBytes(592); if (!doList) { IOUtils.CreateDirectoryIfNotExist(Path.Combine(outputDirectoryPath, outputFileName, "Resources")); } foreach (var res in resourceList) { // convert the unix filename to a windows supported filename string escapedFileName = FromUnixFileNames(res.Name); // and add the counter in front string escapedFileNameWithNumber = string.Format("{0:D3}{1}", res.Count, escapedFileName); Log.Information(String.Format("Resource '{0}' @ position {1} [{2} bytes]", escapedFileNameWithNumber, bf.Position, res.Length)); res.Data = bf.ReadBytes((int)res.Length); // if not only listing, save files if (!doList) { string outputFilePath = Path.Combine(outputDirectoryPath, outputFileName, "Resources", escapedFileNameWithNumber); BinaryFile outBinaryFile = new BinaryFile(outputFilePath, BinaryFile.ByteOrder.LittleEndian, true); outBinaryFile.Write(res.Data); outBinaryFile.Close(); } } } else { Log.Error(inputFilePath + ": Header4 not as expected '/\\ NI FC TOC /\\' but got " + StringUtils.ToHexAndAsciiString(header4)); } } else { Log.Error(inputFilePath + ": Header3 not as expected '/\\ NI FC TOC /\\' but got " + StringUtils.ToHexAndAsciiString(header3)); } } else { Log.Error(inputFilePath + ": Header2 not as expected '/\\ NI FC MTD /\\' but got " + StringUtils.ToHexAndAsciiString(header2)); } } else { Log.Error(inputFilePath + ": Header not as expected '/\\ NI FC MTD /\\' but got " + StringUtils.ToHexAndAsciiString(header)); } } }
private static void extract_nimd_entry(BinaryFile bFile, Entry entry, string base_output_dir, string output_dir, Dictionary <string, MassiveMapElement> map) { string path = Path.Combine(output_dir, entry.Name); if (entry.IsList) { foreach (var sub_entry in entry.Entries) { extract_nimd_entry(bFile, sub_entry, base_output_dir, path, map); } } else { // get binary content bFile.Seek(entry.DataOffset); byte[] byteArray = bFile.ReadBytes(entry.DataSize); #region Output Original Filenames // use path after the base dir as map key string mapKey = IOUtils.GetRightPartOfPath(path, base_output_dir + Path.DirectorySeparatorChar); // add all the original files into an Original directory path = Path.Combine(base_output_dir, "Original", mapKey); // create directory string pathDirectory = Path.GetDirectoryName(path); if (!Directory.Exists(pathDirectory)) { Directory.CreateDirectory(pathDirectory); } // write original file System.Console.Out.WriteLine("Creating file {0}.", path); BinaryFile.Write(path, byteArray); #endregion #region Output Correct Filenames // determine correct filename if (map.ContainsKey(mapKey)) { var mapElement = map[mapKey]; if (!mapElement.GroupName.Equals("") && !mapElement.CorrectFileName.Equals("")) { // group directory string groupDirectory = Path.Combine(base_output_dir, "Correct Waveforms", StringUtils.MakeValidFileName(mapElement.GroupName)); if (!Directory.Exists(groupDirectory)) { Directory.CreateDirectory(groupDirectory); } // output the corrected filenames string newFileName = string.Format("{0}_{1}.wav", mapElement.GroupIndex, mapElement.CorrectFileName); string newFilePath = Path.Combine(groupDirectory, newFileName); System.Console.Out.WriteLine("Creating file {0}.", newFilePath); BinaryFile.Write(newFilePath, byteArray); } } #endregion } }
public bool Read(string filePath) { if (File.Exists(filePath)) { string fileName = Path.GetFileNameWithoutExtension(filePath); PresetName = fileName; BinaryFile bFile = new BinaryFile(filePath, BinaryFile.ByteOrder.BigEndian); string firstChunkID = bFile.ReadString(4); // chunk ID = "FORM" int ckSize = bFile.ReadInt32(); string formType = bFile.ReadString(4); // read first data chunk string chunkID = bFile.ReadString(4); // if chunkID == "COMT" then CommentsChunk if (chunkID.Equals("COMT")) { long curposTmpComt = bFile.GetPosition(); bFile.Seek(curposTmpComt - 4); // CommentsChunk string chunkIDComt = bFile.ReadString(4); // chunk ID = "COMT" int chunkSizeComt = bFile.ReadInt32(); int numComments = bFile.ReadUInt16(); long curposTmpComt2 = bFile.GetPosition(); for (int i = 0; i < numComments; i++) { int commentTimestamp = (int)bFile.ReadUInt32(); string marker = bFile.ReadString(4); int count = (int)bFile.ReadByte(); comments.Add(bFile.ReadString(count)); } bFile.Seek(curposTmpComt2 + chunkSizeComt - 2); } string chunkID2 = bFile.ReadString(4); // if chunkID2 == "COMM" then CommonChunk if (chunkID2.Equals("COMM")) { long curposTmpComm = bFile.GetPosition(); bFile.Seek(curposTmpComm - 4); // CommonChunk string chunkIDComm = bFile.ReadString(4); // chunk ID = "COMM" int chunkSizeComm = bFile.ReadInt32(); channels = bFile.ReadInt16(); numSampleFrames = (int)bFile.ReadUInt32(); bitsPerSample = bFile.ReadInt16(); // read IEEE 80-bit extended double precision byte[] sampleRateBytes = bFile.ReadBytes(0, 10, BinaryFile.ByteOrder.LittleEndian); double sampleRateDouble = IEEE.ConvertFromIeeeExtended(sampleRateBytes); sampleRate = (int)sampleRateDouble; } string chunkID3 = bFile.ReadString(4); // if chunkID3 == "SSND" then SoundDataChunk if (chunkID3.Equals("SSND")) { long curposTmpSsnd = bFile.GetPosition(); bFile.Seek(curposTmpSsnd - 4); // SoundDataChunk string chunkIDSsnd = bFile.ReadString(4); // chunk ID = "SSND" int chunkSizeSsnd = bFile.ReadInt32(); int offset = (int)bFile.ReadUInt32(); int blocksize = (int)bFile.ReadUInt32(); byte[] data = bFile.ReadBytes(offset, chunkSizeSsnd - 8, BinaryFile.ByteOrder.LittleEndian); // swap waveform data WaveformData = SwapAiffEndian(data); } bFile.Close(); return(true); } else { return(false); } }
public static void Unpack(string file, string outputDirectoryPath, bool doList, bool doVerbose) { using (BinaryFile bf = new BinaryFile(file, BinaryFile.ByteOrder.LittleEndian, false)) { UInt32 fileSize = bf.ReadUInt32(); Log.Debug("fileSize: " + fileSize); bf.Seek(350, SeekOrigin.Begin); int snpidCount = bf.ReadInt32(); string snpid = bf.ReadString(snpidCount * 2, Encoding.Unicode); // snpid cannot have more than 4 characters (?!) if (snpidCount > 4) { snpidCount = 0; snpid = ""; bf.Seek(355, SeekOrigin.Begin); } else { bf.ReadBytes(25); } Log.Debug("snpid: " + snpid); int versionCount = bf.ReadInt32(); string version = bf.ReadString(versionCount * 2, Encoding.Unicode); Log.Debug("version: " + version); bf.ReadBytes(122); int presetNameCount = bf.ReadInt32(); string presetName = bf.ReadString(presetNameCount * 2, Encoding.Unicode); int presetNameRest = bf.ReadInt32(); Log.Debug("presetName: " + presetName); int companyNameCount = bf.ReadInt32(); string companyName = bf.ReadString(companyNameCount * 2, Encoding.Unicode); int companyNameRest = bf.ReadInt32(); Log.Debug("companyName: " + companyName); bf.ReadBytes(40); int libraryNameCount = bf.ReadInt32(); string libraryName = bf.ReadString(libraryNameCount * 2, Encoding.Unicode); int libraryNameRest = bf.ReadInt32(); Log.Debug("libraryName: " + libraryName); int typeCount = bf.ReadInt32(); if (typeCount != 0) { string type = bf.ReadString(typeCount * 2, Encoding.Unicode); int typeRest = bf.ReadInt32(); Log.Debug("type: " + type); } int number = bf.ReadInt32(); for (int i = 0; i < number * 2; i++) { int sCount = bf.ReadInt32(); string s = bf.ReadString(sCount * 2, Encoding.Unicode); Log.Debug(s); } bf.ReadBytes(249); UInt32 chunkSize = bf.ReadUInt32(); Log.Debug("chunkSize: " + chunkSize); string outputFileName = Path.GetFileNameWithoutExtension(file); string outputFilePath = Path.Combine(outputDirectoryPath, "NKI_CONTENT", outputFileName + ".bin"); IOUtils.CreateDirectoryIfNotExist(Path.Combine(outputDirectoryPath, "NKI_CONTENT")); var nks = new Nks(); nks.BinaryFile = bf; nks.SetKeys = new Dictionary <String, NksSetKey>(); NksEncryptedFileHeader header = new NksEncryptedFileHeader(); header.SetId = snpid.ToUpper(); header.KeyIndex = 0x100; header.Size = chunkSize; BinaryFile outBinaryFile = new BinaryFile(outputFilePath, BinaryFile.ByteOrder.LittleEndian, true); if (snpid == "") { if (!doList) { NKS.ExtractFileEntryToBf(nks, header, outBinaryFile); } } else { if (!doList) { NKS.ExtractEncryptedFileEntryToBf(nks, header, outBinaryFile); } } outBinaryFile.Close(); } }