mirror of
https://github.com/crskycode/GARbro.git
synced 2024-11-30 17:05:37 +08:00
(LPK): moved Decrypt methods to EncryptionScheme class.
This commit is contained in:
parent
9c27c8b4f8
commit
1b3b54f4f9
@ -61,6 +61,47 @@ namespace GameRes.Formats.Lucifen
|
|||||||
public byte ContentXor;
|
public byte ContentXor;
|
||||||
public uint RotatePattern;
|
public uint RotatePattern;
|
||||||
public bool ImportGameInit;
|
public bool ImportGameInit;
|
||||||
|
|
||||||
|
internal void DecryptContent (byte[] data)
|
||||||
|
{
|
||||||
|
for (int i = 0; i < data.Length; ++i)
|
||||||
|
{
|
||||||
|
int v = data[i] ^ ContentXor;
|
||||||
|
data[i] = Binary.RotByteR ((byte)v, 4);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
internal unsafe void DecryptEntry (byte[] data, int length, uint key)
|
||||||
|
{
|
||||||
|
uint pattern = RotatePattern;
|
||||||
|
fixed (byte* buf_raw = data)
|
||||||
|
{
|
||||||
|
uint* encoded = (uint*)buf_raw;
|
||||||
|
length /= 4;
|
||||||
|
for (int i = 0; i < length; ++i)
|
||||||
|
{
|
||||||
|
encoded[i] ^= key;
|
||||||
|
pattern = Binary.RotR (pattern, 4);
|
||||||
|
key = Binary.RotL (key, (int)pattern);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
internal unsafe void DecryptIndex (byte[] data, int length, uint key)
|
||||||
|
{
|
||||||
|
uint pattern = RotatePattern;
|
||||||
|
fixed (byte* buf_raw = data)
|
||||||
|
{
|
||||||
|
uint* encoded = (uint*)buf_raw;
|
||||||
|
length /= 4;
|
||||||
|
for (int i = 0; i < length; ++i)
|
||||||
|
{
|
||||||
|
encoded[i] ^= key;
|
||||||
|
pattern = Binary.RotL (pattern, 4);
|
||||||
|
key = Binary.RotR (key, (int)pattern);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
[Serializable]
|
[Serializable]
|
||||||
@ -150,37 +191,31 @@ namespace GameRes.Formats.Lucifen
|
|||||||
{
|
{
|
||||||
if (0 == entry.Size)
|
if (0 == entry.Size)
|
||||||
return Stream.Null;
|
return Stream.Null;
|
||||||
var larc = arc as LuciArchive;
|
|
||||||
var lent = entry as LuciEntry;
|
var lent = entry as LuciEntry;
|
||||||
Stream input = arc.File.CreateStream (entry.Offset, entry.Size);
|
Stream input = arc.File.CreateStream (entry.Offset, entry.Size);
|
||||||
if (null == larc || null == lent)
|
if (null == lent)
|
||||||
return input;
|
return input;
|
||||||
byte[] data;
|
if (lent.IsPacked)
|
||||||
|
{
|
||||||
|
input = new LzssStream (input);
|
||||||
|
}
|
||||||
|
var larc = arc as LuciArchive;
|
||||||
|
if (null == larc)
|
||||||
|
return input;
|
||||||
|
var data = new byte[lent.UnpackedSize];
|
||||||
using (input)
|
using (input)
|
||||||
{
|
{
|
||||||
if (lent.IsPacked)
|
input.Read (data, 0, data.Length);
|
||||||
{
|
|
||||||
using (var reader = new LzssReader (input, (int)lent.Size, (int)lent.UnpackedSize))
|
|
||||||
{
|
|
||||||
reader.Unpack();
|
|
||||||
data = reader.Data;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
data = new byte[lent.Size];
|
|
||||||
input.Read (data, 0, data.Length);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if (larc.Info.WholeCrypt)
|
if (larc.Info.WholeCrypt)
|
||||||
{
|
{
|
||||||
DecryptContent (data, larc.Scheme.ContentXor);
|
larc.Scheme.DecryptContent (data);
|
||||||
}
|
}
|
||||||
if (larc.Info.IsEncrypted)
|
if (larc.Info.IsEncrypted)
|
||||||
{
|
{
|
||||||
int count = Math.Min (data.Length, 0x100);
|
int count = Math.Min (data.Length, 0x100);
|
||||||
if (count != 0)
|
if (count != 0)
|
||||||
DecryptEntry (data, count, larc.Info.Key, larc.Scheme.RotatePattern);
|
larc.Scheme.DecryptEntry (data, count, larc.Info.Key);
|
||||||
}
|
}
|
||||||
input = new BinMemoryStream (data, entry.Name);
|
input = new BinMemoryStream (data, entry.Name);
|
||||||
if (null != larc.Info.Prefix)
|
if (null != larc.Info.Prefix)
|
||||||
@ -189,45 +224,6 @@ namespace GameRes.Formats.Lucifen
|
|||||||
return input;
|
return input;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void DecryptContent (byte[] data, byte key)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < data.Length; ++i)
|
|
||||||
{
|
|
||||||
int v = data[i] ^ key;
|
|
||||||
data[i] = Binary.RotByteR ((byte)v, 4);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsafe void DecryptEntry (byte[] data, int length, uint key, uint pattern)
|
|
||||||
{
|
|
||||||
fixed (byte* buf_raw = data)
|
|
||||||
{
|
|
||||||
uint* encoded = (uint*)buf_raw;
|
|
||||||
length /= 4;
|
|
||||||
for (int i = 0; i < length; ++i)
|
|
||||||
{
|
|
||||||
encoded[i] ^= key;
|
|
||||||
pattern = Binary.RotR (pattern, 4);
|
|
||||||
key = Binary.RotL (key, (int)pattern);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
static unsafe void DecryptIndex (byte[] data, int length, uint key, uint pattern)
|
|
||||||
{
|
|
||||||
fixed (byte* buf_raw = data)
|
|
||||||
{
|
|
||||||
uint* encoded = (uint*)buf_raw;
|
|
||||||
length /= 4;
|
|
||||||
for (int i = 0; i < length; ++i)
|
|
||||||
{
|
|
||||||
encoded[i] ^= key;
|
|
||||||
pattern = Binary.RotL (pattern, 4);
|
|
||||||
key = Binary.RotR (key, (int)pattern);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
ArcFile Open (byte[] basename, ArcView file, EncryptionScheme scheme, Key key)
|
ArcFile Open (byte[] basename, ArcView file, EncryptionScheme scheme, Key key)
|
||||||
{
|
{
|
||||||
uint key1 = scheme.BaseKey.Key1;
|
uint key1 = scheme.BaseKey.Key1;
|
||||||
@ -254,7 +250,7 @@ namespace GameRes.Formats.Lucifen
|
|||||||
var index = new byte[index_size];
|
var index = new byte[index_size];
|
||||||
if (index_size != file.View.Read (8, index, 0, (uint)index_size))
|
if (index_size != file.View.Read (8, index, 0, (uint)index_size))
|
||||||
return null;
|
return null;
|
||||||
DecryptIndex (index, index_size, key2, scheme.RotatePattern);
|
scheme.DecryptIndex (index, index_size, key2);
|
||||||
var lpk_info = new LpkInfo
|
var lpk_info = new LpkInfo
|
||||||
{
|
{
|
||||||
AlignedOffset = 0 != (flags & 1),
|
AlignedOffset = 0 != (flags & 1),
|
||||||
@ -414,7 +410,7 @@ namespace GameRes.Formats.Lucifen
|
|||||||
{
|
{
|
||||||
m_index = index;
|
m_index = index;
|
||||||
int count = LittleEndian.ToInt32 (m_index, 0);
|
int count = LittleEndian.ToInt32 (m_index, 0);
|
||||||
if (count <= 0 || count > 0xfffff)
|
if (!ArchiveFormat.IsSaneCount (count))
|
||||||
return null;
|
return null;
|
||||||
int index_offset = 4;
|
int index_offset = 4;
|
||||||
int prefix_length = m_index[index_offset++];
|
int prefix_length = m_index[index_offset++];
|
||||||
|
Loading…
Reference in New Issue
Block a user