Add experimental decompression support.

This commit is contained in:
KimLS 2024-10-17 22:53:33 -07:00
parent d3cd037fa7
commit 999ccdcb19
3 changed files with 89 additions and 13 deletions

View File

@ -13,6 +13,7 @@ using Org.BouncyCastle.Crypto.Engines;
using Org.BouncyCastle.Crypto.Modes;
using Org.BouncyCastle.Crypto;
using Org.BouncyCastle.Crypto.Parameters;
using Ionic.Zlib;
namespace StreamParser
{
@ -72,7 +73,7 @@ namespace StreamParser
{
if(o.Dump)
{
DumpConnectionToTextFile(c.Value, o.Output, o.Decrypt);
DumpConnectionToTextFile(c.Value, o.Output, o.Decrypt, o.DecompressOpcodes);
}
if(o.Csv)
@ -153,7 +154,7 @@ namespace StreamParser
});
}
private void DumpConnectionToTextFile(ParsedConnection c, string output, bool decrypt)
private void DumpConnectionToTextFile(ParsedConnection c, string output, bool decrypt, IEnumerable<int> decompressOpcodes)
{
try
{
@ -213,12 +214,58 @@ namespace StreamParser
break;
default:
{
bool reported_decompressed = false;
int opcode = BitConverter.ToUInt16(data.Slice(0, 2));
File.AppendAllText(path,
string.Format("{0} [Opcode: 0x{1}, Size: {2}] ({3})\n", dir, opcode.ToString("X4"), data.Length - 2, p.Time.ToString("s")));
foreach (var decompressOpcode in decompressOpcodes)
{
if (opcode == decompressOpcode && data.Length > 12)
{
if (data[10] == 0x78 && data[11] == 0xDA)
{
var totalLen = BitConverter.ToInt32(data.Slice(6, 4));
if (totalLen > 0)
{
var decompressed = Inflate(data.Slice(10));
if(decompressed != null)
{
var decompressed_gp = new GamePacket(decompressed);
File.AppendAllText(path,
string.Format("{0} [Opcode: 0x{1}, Size (decompressed): {2}] ({3})\n", dir, opcode.ToString("X4"), totalLen, p.Time.ToString("s")));
var gp = new GamePacket(data.Slice(2));
File.AppendAllText(path, string.Format("{0}\n", gp.ToString()));
File.AppendAllText(path, string.Format("{0}\n", decompressed_gp.ToString()));
reported_decompressed = true;
break;
}
}
}
else if (data[6] == 0x78 && data[7] == 0xDA)
{
var totalLen = BitConverter.ToInt32(data.Slice(2, 4));
if (totalLen > 0)
{
var decompressed = Inflate(data.Slice(6));
if (decompressed != null)
{
File.AppendAllText(path,
string.Format("{0} [Opcode: 0x{1}, Size (decompressed): {2}] ({3})\n", dir, opcode.ToString("X4"), totalLen, p.Time.ToString("s")));
var decompressed_gp = new GamePacket(decompressed);
File.AppendAllText(path, string.Format("{0}\n", decompressed_gp.ToString()));
reported_decompressed = true;
break;
}
}
}
}
}
if (!reported_decompressed)
{
File.AppendAllText(path,
string.Format("{0} [Opcode: 0x{1}, Size: {2}] ({3})\n", dir, opcode.ToString("X4"), data.Length - 2, p.Time.ToString("s")));
var gp = new GamePacket(data.Slice(2));
File.AppendAllText(path, string.Format("{0}\n", gp.ToString()));
}
}
break;
}
@ -230,6 +277,36 @@ namespace StreamParser
}
}
private byte[] Inflate(ReadOnlySpan<byte> data)
{
try
{
using (var out_stream = new MemoryStream())
using (var in_stream = new MemoryStream(data.ToArray()))
{
const int bufferLen = 4096;
var buffer = new byte[bufferLen];
using (var zs = new ZlibStream(in_stream, CompressionMode.Decompress))
{
int r = 0;
do
{
r = zs.Read(buffer, 0, bufferLen);
out_stream.Write(buffer, 0, r);
} while (r == bufferLen);
}
var ret = out_stream.ToArray();
return ret;
}
}
catch (Exception ex)
{
_logger.LogError(ex, "Error inflating data");
return null;
}
}
private class CsvRow
{
public int Index { get; set; }

View File

@ -1,8 +1,4 @@
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using System.Collections.Generic;
using CommandLine;
namespace StreamParser
@ -23,5 +19,8 @@ namespace StreamParser
[Option("decrypt", Default = false, HelpText = "Decrypt the \"Encrypted\" packets.")]
public bool Decrypt { get; set; }
[Option("decompress", Default = false, HelpText = "Which opcodes to attempt to decompress")]
public IEnumerable<int> DecompressOpcodes { get; set; }
}
}

View File

@ -2,8 +2,8 @@
"profiles": {
"stream_parser": {
"commandName": "Project",
"commandLineArgs": "--input input/cap_login_to_zone_10_16_2024.pcap --output output_test/ --text --decrypt",
"commandLineArgs": "--input input/cap_login_to_zone_10_16_2024.pcap --output output_test/ --text --decrypt --decompress 16742 168 30346",
"workingDirectory": "E:\\Projects\\stream_parser\\stream_parser\\bin\\Debug\\net6.0\\"
}
}
}
}