Skip to content
This repository has been archived by the owner on Apr 6, 2024. It is now read-only.

Commit

Permalink
Main
Browse files Browse the repository at this point in the history
  • Loading branch information
Ekey committed Jan 31, 2023
1 parent 35ba23a commit 91cda40
Show file tree
Hide file tree
Showing 12 changed files with 721 additions and 0 deletions.
5 changes: 5 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,5 @@
# TI.Unpacker :see_no_evil:
Tool for extract DAT archives from game [Treasure Island (2005)](https://www.softclub.ru/games/pc/20013-ostrov-sokrovishh)

# Note
> Just old stuff :)
25 changes: 25 additions & 0 deletions TI.Unpacker/TI.Unpacker.sln
Original file line number Diff line number Diff line change
@@ -0,0 +1,25 @@

Microsoft Visual Studio Solution File, Format Version 12.00
# Visual Studio Version 16
VisualStudioVersion = 16.0.32106.194
MinimumVisualStudioVersion = 10.0.40219.1
Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "TI.Unpacker", "TI.Unpacker\TI.Unpacker.csproj", "{70CD71BC-CD8B-48A8-9976-7713E5029AD2}"
EndProject
Global
GlobalSection(SolutionConfigurationPlatforms) = preSolution
Debug|Any CPU = Debug|Any CPU
Release|Any CPU = Release|Any CPU
EndGlobalSection
GlobalSection(ProjectConfigurationPlatforms) = postSolution
{70CD71BC-CD8B-48A8-9976-7713E5029AD2}.Debug|Any CPU.ActiveCfg = Debug|Any CPU
{70CD71BC-CD8B-48A8-9976-7713E5029AD2}.Debug|Any CPU.Build.0 = Debug|Any CPU
{70CD71BC-CD8B-48A8-9976-7713E5029AD2}.Release|Any CPU.ActiveCfg = Release|Any CPU
{70CD71BC-CD8B-48A8-9976-7713E5029AD2}.Release|Any CPU.Build.0 = Release|Any CPU
EndGlobalSection
GlobalSection(SolutionProperties) = preSolution
HideSolutionNode = FALSE
EndGlobalSection
GlobalSection(ExtensibilityGlobals) = postSolution
SolutionGuid = {3B5E4944-2CA6-4ABB-93E5-05DCA2C45E97}
EndGlobalSection
EndGlobal
6 changes: 6 additions & 0 deletions TI.Unpacker/TI.Unpacker/App.config
Original file line number Diff line number Diff line change
@@ -0,0 +1,6 @@
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<startup>
<supportedRuntime version="v4.0" sku=".NETFramework,Version=v4.7.2" />
</startup>
</configuration>
69 changes: 69 additions & 0 deletions TI.Unpacker/TI.Unpacker/FileSystem/Encryption/DatCipher.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,69 @@
using System;

namespace TI.Unpacker
{
class DatCipher
{
class RC4_Ctx
{
public static Byte[] m_State = new Byte[256];
public static Byte x, y = 0;
}

private static Byte[] m_Key = new Byte[] {
0x00, 0x31, 0xBC, 0xBA, 0x31, 0x21, 0xAB, 0xCB, 0x00, 0x43, 0x6B, 0xBA, 0x31, 0x1F, 0x9B, 0xCC,
0x13, 0x34, 0xCB, 0x7A, 0x00, 0x8F, 0xBB, 0xCC, 0x28, 0x37, 0xB6, 0xB5, 0x34, 0x23, 0xA2, 0xC1
};

public static void iInitKey()
{
Int32 k = 0;

for (Int32 i = 0; i < 256; ++i)
{
RC4_Ctx.m_State[i] = (Byte)(-1 - i);
}

for (Int32 i = 0; i < 2; i++)
{
for (Int32 j = 0; j < 256; j++)
{
k = (m_Key[j % m_Key.Length] + RC4_Ctx.m_State[j] + k) % 256;
RC4_Ctx.x = RC4_Ctx.m_State[j];
RC4_Ctx.m_State[j] = RC4_Ctx.m_State[k];
RC4_Ctx.m_State[k] = RC4_Ctx.x;
}
}

RC4_Ctx.x = 0;
RC4_Ctx.y = 0;
}

public static Byte[] iDecrypt(Byte[] lpBuffer)
{
Int32 x = RC4_Ctx.x;
Int32 y = RC4_Ctx.y;

for (Int32 i = 0; i < lpBuffer.Length; i++)
{
Int32 _x = 0;
Int32 _y = 0;

x = x + 1;
_x = RC4_Ctx.m_State[x % 256];
y = y + _x;
_y = RC4_Ctx.m_State[y % 256];

RC4_Ctx.m_State[x % 256] = (Byte)_y;
RC4_Ctx.m_State[y % 256] = (Byte)_x;

lpBuffer[i] ^= RC4_Ctx.m_State[(_y + _x) % 256];
}

RC4_Ctx.x = (Byte)x;
RC4_Ctx.y = (Byte)y;

return lpBuffer;
}
}
}
285 changes: 285 additions & 0 deletions TI.Unpacker/TI.Unpacker/FileSystem/Other/Helpers.cs
Original file line number Diff line number Diff line change
@@ -0,0 +1,285 @@
using System;
using System.IO;
using System.Collections.Generic;
using System.Text;

namespace TI.Unpacker
{
public static class Helpers
{
public static byte[] ReadBytes(this Stream stream, int count)
{
var result = new byte[count];
int offset = 0;
while (offset < count)
{
int bytesRead = stream.Read(result, offset, count - offset);
if (bytesRead <= 0)
throw new IOException();
offset += bytesRead;
}
return result;
}

public static byte[] ReadBytes(this Stream stream)
{
return ReadBytes(stream, (int)stream.Length);
}

public static Int16 ReadInt16(this Stream stream, bool bBigEndian = false)
{
if(bBigEndian == true)
{
var lpTemp = stream.ReadBytes(2);
Array.Reverse(lpTemp);
return BitConverter.ToInt16(lpTemp, 0);
}
else
{
return BitConverter.ToInt16(stream.ReadBytes(2), 0);
}
}

public static Int32 ReadInt32(this Stream stream, bool bBigEndian = false)
{
if (bBigEndian == true)
{
var lpTemp = stream.ReadBytes(4);
Array.Reverse(lpTemp);
return BitConverter.ToInt32(lpTemp, 0);
}
else
{
return BitConverter.ToInt32(stream.ReadBytes(4), 0);
}
}

public static Int64 ReadInt64(this Stream stream, bool bBigEndian = false)
{
if (bBigEndian == true)
{
var lpTemp = stream.ReadBytes(8);
Array.Reverse(lpTemp);
return BitConverter.ToInt64(lpTemp, 0);
}
else
{
return BitConverter.ToInt64(stream.ReadBytes(8), 0);
}
}

public static UInt16 ReadUInt16(this Stream stream, bool bBigEndian = false)
{
if (bBigEndian == true)
{
var lpTemp = stream.ReadBytes(2);
Array.Reverse(lpTemp);
return BitConverter.ToUInt16(lpTemp, 0);
}
else
{
return BitConverter.ToUInt16(stream.ReadBytes(2), 0);
}
}

public static UInt32 ReadUInt32(this Stream stream, bool bBigEndian = false)
{
if (bBigEndian == true)
{
var lpTemp = stream.ReadBytes(4);
Array.Reverse(lpTemp);
return BitConverter.ToUInt32(lpTemp, 0);
}
else
{
return BitConverter.ToUInt32(stream.ReadBytes(4), 0);
}
}

public static UInt64 ReadUInt64(this Stream stream, bool bBigEndian = false)
{
if (bBigEndian == true)
{
var lpTemp = stream.ReadBytes(8);
Array.Reverse(lpTemp);
return BitConverter.ToUInt64(lpTemp, 0);
}
else
{
return BitConverter.ToUInt64(stream.ReadBytes(8), 0);
}
}

public static Single ReadSingle(this Stream stream, bool bBigEndian = false)
{
if (bBigEndian == true)
{
var lpTemp = stream.ReadBytes(4);
Array.Reverse(lpTemp);
return BitConverter.ToSingle(lpTemp, 0);
}
else
{
return BitConverter.ToSingle(stream.ReadBytes(4), 0);
}
}

public static string ReadStringUnicodeLength(this Stream stream, Int32 length)
{
var result = stream.ReadBytes(length * 2);
return Encoding.Unicode.GetString(result);
}

public static string ReadStringLength(this Stream stream)
{
var length = stream.ReadInt32();
var result = stream.ReadBytes(length);
return Encoding.ASCII.GetString(result);
}

public static string ReadString(this Stream stream, int length, Encoding encoding = null, bool trim = true)
{
encoding = encoding ?? Encoding.ASCII;
var result = encoding.GetString(stream.ReadBytes(length));
return trim ? result.Trim() : result;
}

public static string ReadString(this Stream stream, Encoding encoding = null, bool trim = true)
{
encoding = encoding ?? Encoding.ASCII;

int count = 0;
int b;
var data = new List<byte>();
while ((b = stream.ReadByte()) > 10)
{
data.Add((byte)b);
count++;
}

var result = encoding.GetString(data.ToArray(), 0, count);
return trim ? result.Trim() : result;
}

public static string ReadStringByOffset(this Stream stream, uint offset, Encoding encoding = null, bool trim = true)
{
stream.Position = offset;
return ReadString(stream, encoding, trim);
}

public static string[] ReadStringList(this Stream stream, Encoding encoding = null, bool trim = true)
{
var result = new List<string>();
while (stream.Position < stream.Length)
result.Add(ReadString(stream, encoding, trim));
return result.ToArray();
}

public static void CopyTo(this Stream source, Stream target)
{
const int bufferSize = 32768;

if (source == null)
throw new ArgumentNullException("source");
if (target == null)
throw new ArgumentNullException("target");

var buffer = new byte[bufferSize];
int read;
int count = 0;
while ((read = source.Read(buffer, 0, buffer.Length)) > 0)
{
target.Write(buffer, 0, read);
count += read;
}
}
}

public static class ByteArrayExtensions
{
public static byte[] ReadBytes(this byte[] data, int count, int startIndex = 0)
{
var buffer = new byte[4];
Array.Copy(data, buffer, count);
return buffer;
}

public static Int16 ReadInt16(this byte[] data, int startIndex = 0)
{
return BitConverter.ToInt16(data, startIndex);
}

public static Int32 ReadInt32(this byte[] data, int startIndex = 0)
{
return BitConverter.ToInt32(data, startIndex);
}

public static UInt16 ReadUInt16(this byte[] data, int startIndex = 0)
{
return BitConverter.ToUInt16(data, startIndex);
}

public static UInt32 ReadUInt32(this byte[] data, int startIndex = 0)
{
return BitConverter.ToUInt32(data, startIndex);
}

public static UInt64 ReadUInt64(this byte[] data, int startIndex = 0)
{
return BitConverter.ToUInt64(data, startIndex);
}

public static Single ReadSingle(this byte[] data, int startIndex = 0)
{
return BitConverter.ToSingle(data, startIndex);
}

public static Single ReadSingleBE(this byte[] data, int startIndex = 0)
{
var buffer = data.ReadBytes(4);
Array.Reverse(buffer);
return BitConverter.ToSingle(data, startIndex);
}

private static string ReadStringInternal(this byte[] data, ref int startIndex, Encoding encoding, bool trim)
{
encoding = encoding ?? Encoding.ASCII;

int i;
for (i = startIndex; i < data.Length && data[i] != 0; i++) ;

var result = encoding.GetString(data, startIndex, i - startIndex);
startIndex = i + 1;
return trim ? result.Trim() : result;
}

public static string ReadString(this byte[] data, int startIndex = 0, Encoding encoding = null, bool trim = true)
{
return ReadStringInternal(data, ref startIndex, encoding, trim);
}

public static string[] ReadStringList(this byte[] data, int startIndex = 0, Encoding encoding = null, bool trim = true)
{
var result = new List<string>();
while (startIndex < data.Length)
result.Add(ReadStringInternal(data, ref startIndex, encoding, trim));
return result.ToArray();
}

public static Boolean IsText(this byte[] data)
{
foreach (byte b in data)
{
char c = (char)b;
if (
b != 0
&& !char.IsLetterOrDigit(c)
&& !char.IsWhiteSpace(c)
&& !char.IsPunctuation(c)
&& !char.IsSeparator(c))
return false;
}
return true;
}
}
}
Loading

0 comments on commit 91cda40

Please sign in to comment.