mirror of
https://github.com/kwsch/PKHeX.git
synced 2026-04-24 15:24:19 -05:00
Loosen SV 2.0.0/3.0.0 size checks to ranges
Too many permutations of optional blocks to want to think about. Since we already rely on hash validity, a range check should be more than sufficient to eager-check and prevent size clashes.
This commit is contained in:
parent
3f305c9135
commit
a74d882077
|
|
@ -56,15 +56,15 @@ public static void CryptStaticXorpadBytes(Span<byte> data)
|
|||
// Due to the xorpad being extended 0x7F->0x80, if len%7F==0, we miss the last vectored xor.
|
||||
// Subtract 1 from the data size in the event that the length is an even multiple, to get one less iteration.
|
||||
var xp = StaticXorpad;
|
||||
var xp64 = MemoryMarshal.Cast<byte, Vector<ulong>>(xp);
|
||||
var size = xp.Length - 1;
|
||||
var xpVec = MemoryMarshal.Cast<byte, Vector<byte>>(xp);
|
||||
var size = xp.Length - 1; // 0x7F, not 0x80
|
||||
int iterations = (data.Length - 1) / size;
|
||||
do
|
||||
{
|
||||
var slice = MemoryMarshal.Cast<byte, Vector<ulong>>(data[..xp.Length]);
|
||||
var slice = MemoryMarshal.Cast<byte, Vector<byte>>(data[..xp.Length]);
|
||||
for (int i = slice.Length - 1; i >= 0; i--)
|
||||
slice[i] ^= xp64[i];
|
||||
data = data[size..];
|
||||
slice[i] ^= xpVec[i];
|
||||
data = data[size..]; // Advance by 0x7F, not 0x80
|
||||
} while (--iterations != 0);
|
||||
// Xor the remainder.
|
||||
for (int i = data.Length - 1; i >= 0; i--)
|
||||
|
|
|
|||
|
|
@ -28,43 +28,25 @@ public static class SaveUtil
|
|||
public const int SIZE_G9_2 = 0x31A2D0; // 1.0.0 -> 1.1.0
|
||||
|
||||
// 1.2.0: add 0x2C9F; clean upgrade (1.1.0->1.2.0 is same as *1.2.0)
|
||||
public const int SIZE_G9_3A0 = 0x31CF7C; // 1.0.0 -> 1.0.1 -> 1.1.0 -> 1.2.0 AM
|
||||
public const int SIZE_G9_3A1 = 0x31CA6F; // 1.0.1 -> 1.1.0 -> 1.2.0 AM
|
||||
public const int SIZE_G9_3B0 = SIZE_G9_3A0 - 0xD; // BM
|
||||
public const int SIZE_G9_3B1 = SIZE_G9_3A1 - 0xD; // BM
|
||||
public const int SIZE_G9_3G0 = SIZE_G9_3A0 + 0x5; // GO
|
||||
public const int SIZE_G9_3G1 = SIZE_G9_3A1 + 0x5; // GO
|
||||
public const int SIZE_G9_3P0 = SIZE_G9_3B0 + 0x5; // GO (before Multiplayer)
|
||||
public const int SIZE_G9_3P1 = SIZE_G9_3B1 + 0x5; // GO (before Multiplayer)
|
||||
public const int SIZE_G9_3A1 = 0x31CA6F; // 1.0.1 -> 1.1.0 -> 1.2.0 AM
|
||||
public const int SIZE_G9_3G1 = SIZE_G9_3A1 + 0x5; // GO
|
||||
|
||||
public const int SIZE_G9_3B0 = SIZE_G9_3A0 - 0xD; // BM
|
||||
public const int SIZE_G9_3P0 = SIZE_G9_3B0 + 0x5; // GO (before Multiplayer)
|
||||
public const int SIZE_G9_3A0 = 0x31CF7C; // 1.0.0 -> 1.0.1 -> 1.1.0 -> 1.2.0 AM
|
||||
public const int SIZE_G9_3G0 = SIZE_G9_3A0 + 0x5; // GO
|
||||
|
||||
// 2.0.1 (2.0.0 skipped): Teal Mask
|
||||
public const int SIZE_G9_DLC1_B = 0x4329A0;
|
||||
public const int SIZE_G9_DLC1_T = 0x4329A5; // +5
|
||||
public const int SIZE_G9_DLC1_0 = 0x4329A9; // +4
|
||||
public const int SIZE_G9_DLC1_E = 0x4329AD; // +1
|
||||
public const int SIZE_G9_DLC1_1 = 0x4329AE; // +1
|
||||
public const int SIZE_G9_DLC1_D = 0x4329B2; // +4
|
||||
public const int SIZE_G9_DLC1_F = 0x4329B3; // +1
|
||||
public const int SIZE_G9_DLC1_A = 0x4329B6; // +3
|
||||
public const int SIZE_G9_DLC1_Q = 0x4329B7; // +1
|
||||
public const int SIZE_G9_DLC1_2 = 0x4329BB; // +5
|
||||
public const int SIZE_G9_DLC1_U = 0x4329BC; // +1
|
||||
public const int SIZE_G9_DLC1_W = 0x4329BF; // +4
|
||||
public const int SIZE_G9_DLC1_3 = 0x4329C0; // +5
|
||||
public const int SIZE_G9_DLC1_9 = 0x4329C4;
|
||||
public const int SIZE_G9_DLC1_V = 0x4329C9;
|
||||
public const int SIZE_G9_DLC1_4 = 0x432EB6;
|
||||
public const int SIZE_G9_DLC1_C = 0x432EBB; // +5
|
||||
public const int SIZE_G9_DLC1_5 = 0x432EBF; // +4
|
||||
public const int SIZE_G9_DLC1_H = 0x432EC0; // +1
|
||||
public const int SIZE_G9_DLC1_6 = 0x432EC3; // +4
|
||||
public const int SIZE_G9_DLC1_G = 0x432EC4; // +1
|
||||
public const int SIZE_G9_DLC1_7 = 0x432EC8; // +5
|
||||
public const int SIZE_G9_DLC1_I = 0x432EC9; // +1
|
||||
public const int SIZE_G9_DLC1_R = 0x432ECC; // +1
|
||||
public const int SIZE_G9_DLC1_8 = 0x432ECD; // +5
|
||||
public const int SIZE_G9_DLC1_Y = 0x432ED1; // +1
|
||||
public const int SIZE_G9_DLC1_Z = 0x432ED6; // +5
|
||||
// 3.0.0: The Indigo Disk
|
||||
// Both save file sizes have a ton of optional blocks, so just accept a range (min/max) and rely on the hash validity.
|
||||
private const int SIZE_G9_DLC1_MIN1 = 0x4329A0;
|
||||
private const int SIZE_G9_DLC1_MAX1 = 0x4329C9;
|
||||
private const int SIZE_G9_DLC1_MIN2 = 0x432EB6;
|
||||
private const int SIZE_G9_DLC1_MAX2 = 0x432ED6;
|
||||
private const int SIZE_G9_202 = 0xC8E; // Add 2 blocks (1 obj 0xC80, 1 bool) = 4{key}1{obj}4{len} + 4{key}1{boolT/boolF}
|
||||
private const int SIZE_G9_300 = 0x83AD;
|
||||
|
||||
public const int SIZE_G8LA = 0x136DDE;
|
||||
public const int SIZE_G8LA_1 = 0x13AD06;
|
||||
|
|
@ -74,11 +56,11 @@ public static class SaveUtil
|
|||
public const int SIZE_G8BDSP_2 = 0xEED8C;
|
||||
public const int SIZE_G8BDSP_3 = 0xEF0A4;
|
||||
|
||||
public const int SIZE_G8SWSH = 0x1716B3; // 1.0
|
||||
public const int SIZE_G8SWSH_1 = 0x17195E; // 1.0 -> 1.1
|
||||
public const int SIZE_G8SWSH_2 = 0x180B19; // 1.0 -> 1.1 -> 1.2
|
||||
public const int SIZE_G8SWSH = 0x1716B3; // 1.0
|
||||
public const int SIZE_G8SWSH_1 = 0x17195E; // 1.0 -> 1.1
|
||||
public const int SIZE_G8SWSH_2 = 0x180B19; // 1.0 -> 1.1 -> 1.2
|
||||
public const int SIZE_G8SWSH_2B = 0x180AD0; // 1.0 -> 1.2
|
||||
public const int SIZE_G8SWSH_3 = 0x1876B1; // 1.0 -> 1.1 -> 1.2 -> 1.3
|
||||
public const int SIZE_G8SWSH_3 = 0x1876B1; // 1.0 -> 1.1 -> 1.2 -> 1.3
|
||||
public const int SIZE_G8SWSH_3A = 0x187693; // 1.0 -> 1.1 -> 1.3
|
||||
public const int SIZE_G8SWSH_3B = 0x187668; // 1.0 -> 1.2 -> 1.3
|
||||
public const int SIZE_G8SWSH_3C = 0x18764A; // 1.0 -> 1.3
|
||||
|
|
@ -138,8 +120,6 @@ public static class SaveUtil
|
|||
];
|
||||
#endif
|
||||
|
||||
private const int SIZE_G9_202 = 0xC8E; // Add 2 blocks (1 obj 0xC80, 1 bool) = 4{key}1{obj}4{len} + 4{key}1{boolT/boolF}
|
||||
private const int SIZE_G9_300 = 0x83AD;
|
||||
private static bool IsSizeGen9SV(int length) => length is
|
||||
SIZE_G9_0 or SIZE_G9_0a or
|
||||
SIZE_G9_1 or SIZE_G9_1a or SIZE_G9_1A or SIZE_G9_1Aa or SIZE_G9_1Ba or SIZE_G9_1Ab or
|
||||
|
|
@ -147,33 +127,14 @@ SIZE_G9_2 or
|
|||
SIZE_G9_3 or
|
||||
SIZE_G9_3A0 or SIZE_G9_3A1 or SIZE_G9_3B0 or SIZE_G9_3B1 or
|
||||
SIZE_G9_3G0 or SIZE_G9_3G1 or SIZE_G9_3P0 or SIZE_G9_3P1 or
|
||||
SIZE_G9_DLC1_0 or (SIZE_G9_DLC1_0 + SIZE_G9_202) or (SIZE_G9_DLC1_0 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_1 or (SIZE_G9_DLC1_1 + SIZE_G9_202) or (SIZE_G9_DLC1_1 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_2 or (SIZE_G9_DLC1_2 + SIZE_G9_202) or (SIZE_G9_DLC1_2 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_3 or (SIZE_G9_DLC1_3 + SIZE_G9_202) or (SIZE_G9_DLC1_3 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_4 or (SIZE_G9_DLC1_4 + SIZE_G9_202) or (SIZE_G9_DLC1_4 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_5 or (SIZE_G9_DLC1_5 + SIZE_G9_202) or (SIZE_G9_DLC1_5 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_6 or (SIZE_G9_DLC1_6 + SIZE_G9_202) or (SIZE_G9_DLC1_6 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_7 or (SIZE_G9_DLC1_7 + SIZE_G9_202) or (SIZE_G9_DLC1_7 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_8 or (SIZE_G9_DLC1_8 + SIZE_G9_202) or (SIZE_G9_DLC1_8 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_9 or (SIZE_G9_DLC1_9 + SIZE_G9_202) or (SIZE_G9_DLC1_9 + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_A or (SIZE_G9_DLC1_A + SIZE_G9_202) or (SIZE_G9_DLC1_A + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_B or (SIZE_G9_DLC1_B + SIZE_G9_202) or (SIZE_G9_DLC1_B + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_C or (SIZE_G9_DLC1_C + SIZE_G9_202) or (SIZE_G9_DLC1_C + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_D or (SIZE_G9_DLC1_D + SIZE_G9_202) or (SIZE_G9_DLC1_D + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_E or (SIZE_G9_DLC1_E + SIZE_G9_202) or (SIZE_G9_DLC1_E + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_F or (SIZE_G9_DLC1_F + SIZE_G9_202) or (SIZE_G9_DLC1_F + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_G or (SIZE_G9_DLC1_G + SIZE_G9_202) or (SIZE_G9_DLC1_G + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_H or (SIZE_G9_DLC1_H + SIZE_G9_202) or (SIZE_G9_DLC1_H + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_I or (SIZE_G9_DLC1_I + SIZE_G9_202) or (SIZE_G9_DLC1_I + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_Q or (SIZE_G9_DLC1_Q + SIZE_G9_202) or (SIZE_G9_DLC1_Q + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_W or (SIZE_G9_DLC1_W + SIZE_G9_202) or (SIZE_G9_DLC1_W + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_R or (SIZE_G9_DLC1_R + SIZE_G9_202) or (SIZE_G9_DLC1_R + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_T or (SIZE_G9_DLC1_T + SIZE_G9_202) or (SIZE_G9_DLC1_T + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_Y or (SIZE_G9_DLC1_Y + SIZE_G9_202) or (SIZE_G9_DLC1_Y + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_U or (SIZE_G9_DLC1_U + SIZE_G9_202) or (SIZE_G9_DLC1_U + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_V or (SIZE_G9_DLC1_V + SIZE_G9_202) or (SIZE_G9_DLC1_V + SIZE_G9_300) or
|
||||
SIZE_G9_DLC1_Z or (SIZE_G9_DLC1_Z + SIZE_G9_202) or (SIZE_G9_DLC1_Z + SIZE_G9_300);
|
||||
// tons of optional blocks, just rely on range(+) and hash validity
|
||||
(>= SIZE_G9_DLC1_MIN1 and <= SIZE_G9_DLC1_MAX1 + 100) or
|
||||
(>= SIZE_G9_DLC1_MIN2 and <= SIZE_G9_DLC1_MAX2 + 100) or
|
||||
(>= SIZE_G9_DLC1_MIN1 + SIZE_G9_202 and <= SIZE_G9_DLC1_MAX1 + SIZE_G9_202 + 100) or
|
||||
(>= SIZE_G9_DLC1_MIN2 + SIZE_G9_202 and <= SIZE_G9_DLC1_MAX2 + SIZE_G9_202 + 100) or
|
||||
(>= SIZE_G9_DLC1_MIN1 + SIZE_G9_300 and <= SIZE_G9_DLC1_MAX1 + SIZE_G9_300 + 100) or
|
||||
(>= SIZE_G9_DLC1_MIN2 + SIZE_G9_300 and <= SIZE_G9_DLC1_MAX2 + SIZE_G9_300 + 100)
|
||||
;
|
||||
|
||||
private static bool IsSizeGen8SWSH(int length) => length is SIZE_G8SWSH
|
||||
or SIZE_G8SWSH_1
|
||||
|
|
|
|||
Loading…
Reference in New Issue
Block a user