update libchdr
[pcsx_rearmed.git] / deps / libchdr / deps / lzma-22.01 / src / Bra86.c
CommitLineData
9e052883 1/* Bra86.c -- Converter for x86 code (BCJ)\r
22021-02-09 : Igor Pavlov : Public domain */\r
3\r
4#include "Precomp.h"\r
5\r
6#include "Bra.h"\r
7\r
8#define Test86MSByte(b) ((((b) + 1) & 0xFE) == 0)\r
9\r
10SizeT x86_Convert(Byte *data, SizeT size, UInt32 ip, UInt32 *state, int encoding)\r
11{\r
12 SizeT pos = 0;\r
13 UInt32 mask = *state & 7;\r
14 if (size < 5)\r
15 return 0;\r
16 size -= 4;\r
17 ip += 5;\r
18\r
19 for (;;)\r
20 {\r
21 Byte *p = data + pos;\r
22 const Byte *limit = data + size;\r
23 for (; p < limit; p++)\r
24 if ((*p & 0xFE) == 0xE8)\r
25 break;\r
26\r
27 {\r
28 SizeT d = (SizeT)(p - data) - pos;\r
29 pos = (SizeT)(p - data);\r
30 if (p >= limit)\r
31 {\r
32 *state = (d > 2 ? 0 : mask >> (unsigned)d);\r
33 return pos;\r
34 }\r
35 if (d > 2)\r
36 mask = 0;\r
37 else\r
38 {\r
39 mask >>= (unsigned)d;\r
40 if (mask != 0 && (mask > 4 || mask == 3 || Test86MSByte(p[(size_t)(mask >> 1) + 1])))\r
41 {\r
42 mask = (mask >> 1) | 4;\r
43 pos++;\r
44 continue;\r
45 }\r
46 }\r
47 }\r
48\r
49 if (Test86MSByte(p[4]))\r
50 {\r
51 UInt32 v = ((UInt32)p[4] << 24) | ((UInt32)p[3] << 16) | ((UInt32)p[2] << 8) | ((UInt32)p[1]);\r
52 UInt32 cur = ip + (UInt32)pos;\r
53 pos += 5;\r
54 if (encoding)\r
55 v += cur;\r
56 else\r
57 v -= cur;\r
58 if (mask != 0)\r
59 {\r
60 unsigned sh = (mask & 6) << 2;\r
61 if (Test86MSByte((Byte)(v >> sh)))\r
62 {\r
63 v ^= (((UInt32)0x100 << sh) - 1);\r
64 if (encoding)\r
65 v += cur;\r
66 else\r
67 v -= cur;\r
68 }\r
69 mask = 0;\r
70 }\r
71 p[1] = (Byte)v;\r
72 p[2] = (Byte)(v >> 8);\r
73 p[3] = (Byte)(v >> 16);\r
74 p[4] = (Byte)(0 - ((v >> 24) & 1));\r
75 }\r
76 else\r
77 {\r
78 mask = (mask >> 1) | 4;\r
79 pos++;\r
80 }\r
81 }\r
82}\r