@futpib/parser 1.0.3 → 1.0.6

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (262) hide show
  1. package/.claude/settings.local.json +24 -0
  2. package/.github/workflows/main.yml +1 -0
  3. package/build/androidPackageParser.js +30 -32
  4. package/build/arbitraryDalvikBytecode.d.ts +3 -3
  5. package/build/arbitraryDalvikBytecode.js +33 -27
  6. package/build/arbitraryDalvikExecutable.js +55 -17
  7. package/build/arbitraryJava.d.ts +31 -0
  8. package/build/arbitraryJava.js +532 -0
  9. package/build/arbitraryJavaScript.d.ts +3 -0
  10. package/build/arbitraryJavaScript.js +263 -0
  11. package/build/arbitraryJavascript.d.ts +3 -0
  12. package/build/arbitraryJavascript.js +263 -0
  13. package/build/arbitraryZig.d.ts +3 -0
  14. package/build/arbitraryZig.js +240 -0
  15. package/build/arbitraryZipStream.d.ts +1 -1
  16. package/build/arrayParser.js +72 -13
  17. package/build/backsmali.d.ts +4 -3
  18. package/build/backsmali.js +26 -6
  19. package/build/bash.d.ts +89 -0
  20. package/build/bash.js +1 -0
  21. package/build/bashParser.d.ts +6 -0
  22. package/build/bashParser.js +335 -0
  23. package/build/bashParser.test.d.ts +1 -0
  24. package/build/bashParser.test.js +343 -0
  25. package/build/bashParserEdgeCases.test.d.ts +1 -0
  26. package/build/bashParserEdgeCases.test.js +117 -0
  27. package/build/dalvikBytecodeParser/addressConversion.d.ts +110 -0
  28. package/build/dalvikBytecodeParser/addressConversion.js +334 -0
  29. package/build/dalvikBytecodeParser/formatParsers.d.ts +7 -6
  30. package/build/dalvikBytecodeParser/formatParsers.js +13 -14
  31. package/build/dalvikBytecodeParser.d.ts +60 -31
  32. package/build/dalvikBytecodeParser.js +92 -35
  33. package/build/dalvikBytecodeParser.test-d.d.ts +1 -0
  34. package/build/dalvikBytecodeParser.test-d.js +268 -0
  35. package/build/dalvikBytecodeUnparser/formatUnparsers.d.ts +9 -8
  36. package/build/dalvikBytecodeUnparser/formatUnparsers.js +13 -12
  37. package/build/dalvikBytecodeUnparser.d.ts +2 -2
  38. package/build/dalvikBytecodeUnparser.js +23 -23
  39. package/build/dalvikBytecodeUnparser.test.js +7 -7
  40. package/build/dalvikExecutable.d.ts +3 -3
  41. package/build/dalvikExecutable.test-d.d.ts +1 -0
  42. package/build/dalvikExecutable.test-d.js +59 -0
  43. package/build/dalvikExecutableParser/typedNumbers.d.ts +18 -0
  44. package/build/dalvikExecutableParser/typedNumbers.js +3 -0
  45. package/build/dalvikExecutableParser.d.ts +2 -1
  46. package/build/dalvikExecutableParser.js +96 -77
  47. package/build/dalvikExecutableParser.test.js +24 -3
  48. package/build/dalvikExecutableParserAgainstSmaliParser.test.js +3 -0
  49. package/build/dalvikExecutableUnparser/poolScanners.d.ts +2 -2
  50. package/build/dalvikExecutableUnparser/sectionUnparsers.d.ts +3 -3
  51. package/build/dalvikExecutableUnparser/sectionUnparsers.js +26 -11
  52. package/build/dalvikExecutableUnparser.d.ts +2 -2
  53. package/build/dalvikExecutableUnparser.test.js +2 -1
  54. package/build/disjunctionParser.d.ts +5 -3
  55. package/build/disjunctionParser.js +79 -17
  56. package/build/disjunctionParser.test-d.d.ts +1 -0
  57. package/build/disjunctionParser.test-d.js +72 -0
  58. package/build/elementSwitchParser.d.ts +4 -0
  59. package/build/{exactElementSwitchParser.js → elementSwitchParser.js} +3 -4
  60. package/build/elementSwitchParser.test-d.d.ts +1 -0
  61. package/build/elementSwitchParser.test-d.js +44 -0
  62. package/build/exactSequenceParser.d.ts +4 -2
  63. package/build/exactSequenceParser.test-d.d.ts +1 -0
  64. package/build/exactSequenceParser.test-d.js +36 -0
  65. package/build/fetchCid.js +2 -66
  66. package/build/index.d.ts +25 -2
  67. package/build/index.js +23 -1
  68. package/build/index.test.js +16 -1
  69. package/build/inputReader.d.ts +10 -0
  70. package/build/inputReader.js +36 -0
  71. package/build/java.d.ts +502 -0
  72. package/build/java.js +2 -0
  73. package/build/javaKeyStoreParser.js +14 -17
  74. package/build/javaParser.d.ts +51 -0
  75. package/build/javaParser.js +1538 -0
  76. package/build/javaParser.test.d.ts +1 -0
  77. package/build/javaParser.test.js +1287 -0
  78. package/build/javaScript.d.ts +35 -0
  79. package/build/javaScript.js +1 -0
  80. package/build/javaScriptParser.d.ts +9 -0
  81. package/build/javaScriptParser.js +34 -0
  82. package/build/javaScriptUnparser.d.ts +3 -0
  83. package/build/javaScriptUnparser.js +4 -0
  84. package/build/javaScriptUnparser.test.d.ts +1 -0
  85. package/build/javaScriptUnparser.test.js +24 -0
  86. package/build/javaUnparser.d.ts +2 -0
  87. package/build/javaUnparser.js +519 -0
  88. package/build/javaUnparser.test.d.ts +1 -0
  89. package/build/javaUnparser.test.js +24 -0
  90. package/build/javascript.d.ts +35 -0
  91. package/build/javascript.js +1 -0
  92. package/build/javascriptParser.d.ts +9 -0
  93. package/build/javascriptParser.js +34 -0
  94. package/build/javascriptUnparser.d.ts +3 -0
  95. package/build/javascriptUnparser.js +4 -0
  96. package/build/javascriptUnparser.test.d.ts +1 -0
  97. package/build/javascriptUnparser.test.js +24 -0
  98. package/build/jsonParser.js +2 -12
  99. package/build/lazyMessageError.d.ts +3 -0
  100. package/build/lookaheadParser.js +60 -3
  101. package/build/negativeLookaheadParser.js +70 -11
  102. package/build/nonEmptyArrayParser.js +72 -13
  103. package/build/objectParser.d.ts +12 -0
  104. package/build/objectParser.js +31 -0
  105. package/build/objectParser.test-d.d.ts +1 -0
  106. package/build/objectParser.test-d.js +112 -0
  107. package/build/objectParser.test.d.ts +1 -0
  108. package/build/objectParser.test.js +55 -0
  109. package/build/optionalParser.js +69 -10
  110. package/build/parser.d.ts +4 -0
  111. package/build/parser.js +3 -1
  112. package/build/parser.test.js +114 -1
  113. package/build/parserConsumedSequenceParser.js +66 -7
  114. package/build/parserContext.d.ts +6 -0
  115. package/build/parserContext.js +20 -11
  116. package/build/parserError.d.ts +119 -27
  117. package/build/parserError.js +16 -8
  118. package/build/regexpParser.d.ts +2 -0
  119. package/build/regexpParser.js +101 -0
  120. package/build/regexpParser.test.d.ts +1 -0
  121. package/build/regexpParser.test.js +114 -0
  122. package/build/regularExpression.d.ts +63 -0
  123. package/build/regularExpression.js +1 -0
  124. package/build/regularExpressionParser.d.ts +3 -0
  125. package/build/regularExpressionParser.js +600 -0
  126. package/build/regularExpressionParser.test.d.ts +1 -0
  127. package/build/regularExpressionParser.test.js +89 -0
  128. package/build/separatedArrayParser.js +73 -14
  129. package/build/separatedNonEmptyArrayParser.js +73 -14
  130. package/build/sliceBoundedParser.js +62 -5
  131. package/build/smaliParser.d.ts +7 -7
  132. package/build/smaliParser.js +185 -268
  133. package/build/smaliParser.test.js +58 -0
  134. package/build/stringEscapes.d.ts +5 -0
  135. package/build/stringEscapes.js +244 -0
  136. package/build/symbolicExpression.d.ts +29 -0
  137. package/build/symbolicExpression.js +1 -0
  138. package/build/symbolicExpressionParser.d.ts +4 -0
  139. package/build/symbolicExpressionParser.js +123 -0
  140. package/build/symbolicExpressionParser.test.d.ts +1 -0
  141. package/build/symbolicExpressionParser.test.js +289 -0
  142. package/build/terminatedArrayParser.js +113 -38
  143. package/build/terminatedArrayParser.test.js +4 -2
  144. package/build/tupleParser.d.ts +7 -15
  145. package/build/tupleParser.js +1 -0
  146. package/build/unionParser.d.ts +5 -3
  147. package/build/unionParser.js +7 -2
  148. package/build/unionParser.test-d.d.ts +1 -0
  149. package/build/unionParser.test-d.js +72 -0
  150. package/build/unionParser.test.js +10 -11
  151. package/build/zig.d.ts +280 -0
  152. package/build/zig.js +2 -0
  153. package/build/zigParser.d.ts +3 -0
  154. package/build/zigParser.js +1119 -0
  155. package/build/zigParser.test.d.ts +1 -0
  156. package/build/zigParser.test.js +1590 -0
  157. package/build/zigUnparser.d.ts +2 -0
  158. package/build/zigUnparser.js +460 -0
  159. package/build/zigUnparser.test.d.ts +1 -0
  160. package/build/zigUnparser.test.js +24 -0
  161. package/build/zipParser.js +19 -32
  162. package/build/zipUnparser.js +19 -7
  163. package/build/zipUnparser.test.js +1 -1
  164. package/node_modules-@types/s-expression/index.d.ts +5 -0
  165. package/package.json +25 -6
  166. package/src/androidPackageParser.ts +33 -60
  167. package/src/arbitraryDalvikBytecode.ts +39 -31
  168. package/src/arbitraryDalvikExecutable.ts +65 -20
  169. package/src/arbitraryJava.ts +804 -0
  170. package/src/arbitraryJavaScript.ts +410 -0
  171. package/src/arbitraryZig.ts +380 -0
  172. package/src/arrayParser.ts +1 -3
  173. package/src/backsmali.ts +35 -4
  174. package/src/bash.ts +127 -0
  175. package/src/bashParser.test.ts +590 -0
  176. package/src/bashParser.ts +498 -0
  177. package/src/dalvikBytecodeParser/addressConversion.ts +496 -0
  178. package/src/dalvikBytecodeParser/formatParsers.ts +19 -29
  179. package/src/dalvikBytecodeParser.test-d.ts +310 -0
  180. package/src/dalvikBytecodeParser.ts +194 -69
  181. package/src/dalvikBytecodeUnparser/formatUnparsers.ts +27 -26
  182. package/src/dalvikBytecodeUnparser.test.ts +7 -7
  183. package/src/dalvikBytecodeUnparser.ts +31 -30
  184. package/src/dalvikExecutable.test-d.ts +132 -0
  185. package/src/dalvikExecutable.ts +3 -3
  186. package/src/dalvikExecutableParser/typedNumbers.ts +11 -0
  187. package/src/dalvikExecutableParser.test.ts +37 -3
  188. package/src/dalvikExecutableParser.test.ts.md +163 -2
  189. package/src/dalvikExecutableParser.test.ts.snap +0 -0
  190. package/src/dalvikExecutableParser.ts +121 -139
  191. package/src/dalvikExecutableParserAgainstSmaliParser.test.ts +4 -0
  192. package/src/dalvikExecutableUnparser/poolScanners.ts +6 -6
  193. package/src/dalvikExecutableUnparser/sectionUnparsers.ts +38 -14
  194. package/src/dalvikExecutableUnparser.test.ts +3 -2
  195. package/src/dalvikExecutableUnparser.ts +4 -4
  196. package/src/disjunctionParser.test-d.ts +105 -0
  197. package/src/disjunctionParser.ts +18 -15
  198. package/src/elementSwitchParser.test-d.ts +74 -0
  199. package/src/elementSwitchParser.ts +51 -0
  200. package/src/exactSequenceParser.test-d.ts +43 -0
  201. package/src/exactSequenceParser.ts +13 -8
  202. package/src/fetchCid.ts +2 -76
  203. package/src/index.test.ts +22 -1
  204. package/src/index.ts +119 -2
  205. package/src/inputReader.ts +53 -0
  206. package/src/java.ts +708 -0
  207. package/src/javaKeyStoreParser.ts +18 -32
  208. package/src/javaParser.test.ts +1592 -0
  209. package/src/javaParser.ts +2640 -0
  210. package/src/javaScript.ts +36 -0
  211. package/src/javaScriptParser.ts +57 -0
  212. package/src/javaScriptUnparser.test.ts +37 -0
  213. package/src/javaScriptUnparser.ts +7 -0
  214. package/src/javaUnparser.test.ts +37 -0
  215. package/src/javaUnparser.ts +640 -0
  216. package/src/jsonParser.ts +6 -27
  217. package/src/lookaheadParser.ts +2 -6
  218. package/src/negativeLookaheadParser.ts +1 -3
  219. package/src/nonEmptyArrayParser.ts +1 -3
  220. package/src/objectParser.test-d.ts +152 -0
  221. package/src/objectParser.test.ts +71 -0
  222. package/src/objectParser.ts +69 -0
  223. package/src/optionalParser.ts +1 -3
  224. package/src/parser.test.ts +151 -4
  225. package/src/parser.ts +11 -1
  226. package/src/parserConsumedSequenceParser.ts +2 -4
  227. package/src/parserContext.ts +26 -11
  228. package/src/parserError.ts +17 -3
  229. package/src/regexpParser.test.ts +264 -0
  230. package/src/regexpParser.ts +126 -0
  231. package/src/regularExpression.ts +24 -0
  232. package/src/regularExpressionParser.test.ts +102 -0
  233. package/src/regularExpressionParser.ts +920 -0
  234. package/src/separatedArrayParser.ts +1 -3
  235. package/src/separatedNonEmptyArrayParser.ts +1 -3
  236. package/src/sliceBoundedParser.test.ts +2 -2
  237. package/src/sliceBoundedParser.ts +15 -19
  238. package/src/smaliParser.test.ts +64 -0
  239. package/src/smaliParser.test.ts.md +12 -12
  240. package/src/smaliParser.test.ts.snap +0 -0
  241. package/src/smaliParser.ts +246 -534
  242. package/src/stringEscapes.ts +253 -0
  243. package/src/symbolicExpression.ts +17 -0
  244. package/src/symbolicExpressionParser.test.ts +466 -0
  245. package/src/symbolicExpressionParser.ts +190 -0
  246. package/src/terminatedArrayParser.test.ts +9 -6
  247. package/src/terminatedArrayParser.ts +25 -29
  248. package/src/tupleParser.ts +21 -18
  249. package/src/unionParser.test-d.ts +105 -0
  250. package/src/unionParser.test.ts +18 -17
  251. package/src/unionParser.ts +28 -16
  252. package/src/zig.ts +411 -0
  253. package/src/zigParser.test.ts +1693 -0
  254. package/src/zigParser.ts +1745 -0
  255. package/src/zigUnparser.test.ts +37 -0
  256. package/src/zigUnparser.ts +615 -0
  257. package/src/zipParser.ts +20 -56
  258. package/src/zipUnparser.test.ts +1 -1
  259. package/src/zipUnparser.ts +22 -7
  260. package/tsconfig.json +2 -2
  261. package/build/exactElementSwitchParser.d.ts +0 -3
  262. package/src/exactElementSwitchParser.ts +0 -41
@@ -0,0 +1,117 @@
1
+ import test from 'ava';
2
+ import { runParser } from './parser.js';
3
+ import { stringParserInputCompanion } from './parserInputCompanion.js';
4
+ import { bashScriptParser } from './bashParser.js';
5
+ // Braced variable expansion: ${VAR}
6
+ test('braced variable expansion', async (t) => {
7
+ const result = await runParser(bashScriptParser, 'echo ${HOME}', stringParserInputCompanion);
8
+ const cmd = result.entries[0].pipeline.commands[0];
9
+ if (cmd.type === 'simple') {
10
+ t.is(cmd.args[0].parts[0].type, 'variableBraced');
11
+ }
12
+ });
13
+ // Braced variable with default: ${VAR:-default}
14
+ test('braced variable with default value', async (t) => {
15
+ const result = await runParser(bashScriptParser, 'echo ${VAR:-default}', stringParserInputCompanion);
16
+ const cmd = result.entries[0].pipeline.commands[0];
17
+ if (cmd.type === 'simple') {
18
+ t.is(cmd.args[0].parts[0].type, 'variableBraced');
19
+ }
20
+ });
21
+ // Arithmetic expansion: $((1+2))
22
+ test('arithmetic expansion', async (t) => {
23
+ const result = await runParser(bashScriptParser, 'echo $((1+2))', stringParserInputCompanion);
24
+ const cmd = result.entries[0].pipeline.commands[0];
25
+ if (cmd.type === 'simple') {
26
+ t.is(cmd.args[0].parts[0].type, 'arithmeticExpansion');
27
+ }
28
+ });
29
+ // Bare $ at end of unquoted word
30
+ test('bare dollar at end of unquoted word', async (t) => {
31
+ const result = await runParser(bashScriptParser, 'echo foo$', stringParserInputCompanion);
32
+ const cmd = result.entries[0].pipeline.commands[0];
33
+ if (cmd.type === 'simple') {
34
+ t.deepEqual(cmd.args[0], {
35
+ parts: [
36
+ { type: 'literal', value: 'foo' },
37
+ { type: 'literal', value: '$' },
38
+ ],
39
+ });
40
+ }
41
+ });
42
+ // Bare $ as its own unquoted word
43
+ test('bare dollar as standalone unquoted word', async (t) => {
44
+ const result = await runParser(bashScriptParser, 'echo $', stringParserInputCompanion);
45
+ const cmd = result.entries[0].pipeline.commands[0];
46
+ if (cmd.type === 'simple') {
47
+ t.deepEqual(cmd.args[0], {
48
+ parts: [
49
+ { type: 'literal', value: '$' },
50
+ ],
51
+ });
52
+ }
53
+ });
54
+ // Comment after command
55
+ test('comment after command', async (t) => {
56
+ const result = await runParser(bashScriptParser, 'echo hello # this is a comment', stringParserInputCompanion);
57
+ const cmd = result.entries[0].pipeline.commands[0];
58
+ if (cmd.type === 'simple') {
59
+ t.is(cmd.args.length, 1);
60
+ t.deepEqual(cmd.args[0], {
61
+ parts: [{ type: 'literal', value: 'hello' }],
62
+ });
63
+ }
64
+ });
65
+ // ANSI-C quoting: $'...'
66
+ test('ansi-c quoting', async (t) => {
67
+ const result = await runParser(bashScriptParser, "echo $'hello\\nworld'", stringParserInputCompanion);
68
+ const cmd = result.entries[0].pipeline.commands[0];
69
+ if (cmd.type === 'simple') {
70
+ t.is(cmd.args.length, 1);
71
+ }
72
+ });
73
+ // Braced variable in double quotes: "${VAR}"
74
+ test('braced variable in double quotes', async (t) => {
75
+ const result = await runParser(bashScriptParser, 'echo "${HOME}"', stringParserInputCompanion);
76
+ const cmd = result.entries[0].pipeline.commands[0];
77
+ if (cmd.type === 'simple') {
78
+ const dq = cmd.args[0].parts[0];
79
+ if (dq.type === 'doubleQuoted') {
80
+ t.is(dq.parts[0].type, 'variableBraced');
81
+ }
82
+ }
83
+ });
84
+ // Arithmetic expansion in double quotes
85
+ test('arithmetic expansion in double quotes', async (t) => {
86
+ const result = await runParser(bashScriptParser, 'echo "$((1+2))"', stringParserInputCompanion);
87
+ const cmd = result.entries[0].pipeline.commands[0];
88
+ if (cmd.type === 'simple') {
89
+ const dq = cmd.args[0].parts[0];
90
+ if (dq.type === 'doubleQuoted') {
91
+ t.is(dq.parts[0].type, 'arithmeticExpansion');
92
+ }
93
+ }
94
+ });
95
+ // Process substitution: <(cmd)
96
+ test('process substitution input', async (t) => {
97
+ const result = await runParser(bashScriptParser, 'diff <(sort file1) <(sort file2)', stringParserInputCompanion);
98
+ t.truthy(result);
99
+ });
100
+ // Line continuation (backslash-newline)
101
+ test('line continuation', async (t) => {
102
+ const result = await runParser(bashScriptParser, 'echo hello \\\nworld', stringParserInputCompanion);
103
+ const cmd = result.entries[0].pipeline.commands[0];
104
+ if (cmd.type === 'simple') {
105
+ t.is(cmd.args.length, 2);
106
+ }
107
+ });
108
+ // Hash in middle of unquoted word is literal, not a comment
109
+ test('hash in middle of unquoted word', async (t) => {
110
+ const result = await runParser(bashScriptParser, 'echo foo#bar', stringParserInputCompanion);
111
+ const cmd = result.entries[0].pipeline.commands[0];
112
+ if (cmd.type === 'simple') {
113
+ t.deepEqual(cmd.args[0], {
114
+ parts: [{ type: 'literal', value: 'foo#bar' }],
115
+ });
116
+ }
117
+ });
@@ -0,0 +1,110 @@
1
+ import { type RawDalvikBytecodeOperation, type IndexResolvedOperation } from '../dalvikBytecodeParser.js';
2
+ import { type CodeUnit, type InstructionIndex } from '../dalvikExecutableParser/typedNumbers.js';
3
+ /**
4
+ * Map from code unit offset to instruction index.
5
+ * Keys are raw code unit offsets, values are instruction indices.
6
+ */
7
+ export type CodeUnitToIndexMap = Map<CodeUnit, InstructionIndex>;
8
+ /**
9
+ * Map from instruction index to code unit offset.
10
+ * Keys are instruction indices, values are raw code unit offsets.
11
+ */
12
+ export type IndexToCodeUnitMap = Map<InstructionIndex, CodeUnit>;
13
+ /**
14
+ * Calculate the size of an operation in code units (16-bit words).
15
+ * Works with any tier of operation (Tier 1, 2, 3, or SmaliCodeOperation).
16
+ */
17
+ export declare function getOperationSizeInCodeUnits(operation: {
18
+ operation: string;
19
+ data?: Uint8Array | number[];
20
+ }): number;
21
+ /**
22
+ * Build mapping from code unit offset to instruction index.
23
+ * Also maps the end position (total code units) to instructions.length.
24
+ */
25
+ export declare function buildCodeUnitToIndexMap(instructions: RawDalvikBytecodeOperation[]): CodeUnitToIndexMap;
26
+ /**
27
+ * Build mapping from instruction index to code unit offset.
28
+ * Also maps instructions.length to the total code units.
29
+ */
30
+ export declare function buildIndexToCodeUnitMap(instructions: RawDalvikBytecodeOperation[]): IndexToCodeUnitMap;
31
+ /**
32
+ * Convert a code unit offset to an instruction index.
33
+ */
34
+ export declare function codeUnitToInstructionIndex(codeUnitOffset: CodeUnit, codeUnitToIndexMap: CodeUnitToIndexMap): InstructionIndex;
35
+ /**
36
+ * Convert an instruction index to a code unit offset.
37
+ */
38
+ export declare function instructionIndexToCodeUnit(instructionIndex: InstructionIndex, indexToCodeUnitMap: IndexToCodeUnitMap): CodeUnit;
39
+ /**
40
+ * Convert a relative branch offset (in code units) to a relative instruction offset.
41
+ * The offset is relative to the source instruction.
42
+ */
43
+ export declare function convertBranchOffsetToInstructionOffset(branchOffsetInCodeUnits: CodeUnit, sourceInstructionIndex: InstructionIndex, indexToCodeUnitMap: IndexToCodeUnitMap, codeUnitToIndexMap: CodeUnitToIndexMap): InstructionIndex;
44
+ /**
45
+ * Convert a relative instruction offset back to a code unit offset.
46
+ * The offset is relative to the source instruction.
47
+ */
48
+ export declare function convertInstructionOffsetToBranchOffset(instructionOffset: InstructionIndex, sourceInstructionIndex: InstructionIndex, indexToCodeUnitMap: IndexToCodeUnitMap): CodeUnit;
49
+ /**
50
+ * Find the switch instruction that references a payload at the given index.
51
+ * Returns the index of the switch instruction.
52
+ */
53
+ export declare function findSwitchInstructionForPayload(instructions: RawDalvikBytecodeOperation[], payloadIndex: InstructionIndex, indexToCodeUnitMap: IndexToCodeUnitMap): InstructionIndex;
54
+ export type ConvertedBranchOffsetOperation<T> = T extends {
55
+ branchOffsetCodeUnit: CodeUnit;
56
+ } ? Omit<T, 'branchOffsetCodeUnit'> & {
57
+ branchOffsetIndex: InstructionIndex;
58
+ } : T extends {
59
+ branchOffsetsCodeUnit: CodeUnit[];
60
+ } ? Omit<T, 'branchOffsetsCodeUnit'> & {
61
+ branchOffsetsIndex: InstructionIndex[];
62
+ } : T;
63
+ export type ConvertedRawDalvikBytecodeOperation = ConvertedBranchOffsetOperation<RawDalvikBytecodeOperation>;
64
+ export type ResolvedBranchOffsetOperation<T> = T extends {
65
+ branchOffsetIndex: InstructionIndex;
66
+ } ? Omit<T, 'branchOffsetIndex'> & {
67
+ targetInstructionIndex: number;
68
+ } : T extends {
69
+ branchOffsetsIndex: InstructionIndex[];
70
+ } ? Omit<T, 'branchOffsetsIndex'> & {
71
+ targetInstructionIndices: number[];
72
+ } : T;
73
+ export type DalvikBytecodeOperation = IndexResolvedOperation<ResolvedBranchOffsetOperation<ConvertedRawDalvikBytecodeOperation>>;
74
+ export type DalvikBytecode = DalvikBytecodeOperation[];
75
+ /**
76
+ * Convert all branch offsets in instructions from code units to instruction offsets.
77
+ * Tier 1 (CodeUnit) -> Tier 2 (InstructionIndex)
78
+ */
79
+ export declare function convertBranchOffsetsToInstructionOffsets(instructions: RawDalvikBytecodeOperation[]): ConvertedRawDalvikBytecodeOperation[];
80
+ /**
81
+ * Unwrap instruction indices to plain numbers and convert relative to absolute.
82
+ * Tier 2 (InstructionIndex, relative) -> Tier 3 (plain number, absolute)
83
+ */
84
+ export declare function unwrapBranchOffsets(instructions: ConvertedRawDalvikBytecodeOperation[]): DalvikBytecodeOperation[];
85
+ /**
86
+ * Wrap plain numbers to instruction indices and convert absolute to relative.
87
+ * Tier 3 (plain number, absolute) -> Tier 2 (InstructionIndex, relative)
88
+ */
89
+ export declare function wrapBranchOffsets(instructions: DalvikBytecodeOperation[]): ConvertedRawDalvikBytecodeOperation[];
90
+ /**
91
+ * Build mapping from instruction index to code unit offset.
92
+ * Works with any tier of operations.
93
+ */
94
+ export declare function buildIndexToCodeUnitMapGeneric(instructions: Array<{
95
+ operation: string;
96
+ data?: Uint8Array | number[];
97
+ }>): IndexToCodeUnitMap;
98
+ /**
99
+ * Build mapping from instruction index to code unit offset for Tier 2 operations.
100
+ */
101
+ export declare function buildIndexToCodeUnitMapFromConverted(instructions: ConvertedRawDalvikBytecodeOperation[]): IndexToCodeUnitMap;
102
+ /**
103
+ * Build mapping from instruction index to code unit offset for Tier 3 operations.
104
+ */
105
+ export declare function buildIndexToCodeUnitMapFromResolved(instructions: DalvikBytecodeOperation[]): IndexToCodeUnitMap;
106
+ /**
107
+ * Convert all branch offsets in instructions from instruction offsets back to code units.
108
+ * Tier 2 (InstructionIndex) -> Tier 1 (CodeUnit)
109
+ */
110
+ export declare function convertInstructionOffsetsToBranchOffsets(instructions: ConvertedRawDalvikBytecodeOperation[]): RawDalvikBytecodeOperation[];
@@ -0,0 +1,334 @@
1
+ import { isoCodeUnit, isoInstructionIndex, } from '../dalvikExecutableParser/typedNumbers.js';
2
+ import { operationFormats } from './operationFormats.js';
3
+ import { formatSizes } from './formatSizes.js';
4
+ /**
5
+ * Get the branch offsets array length from an operation, regardless of tier.
6
+ * Works with all field name variants: branchOffsetsCodeUnit, branchOffsetsIndex, targetInstructionIndices, branchOffsetIndices.
7
+ */
8
+ function getBranchOffsetsLength(operation) {
9
+ const op = operation;
10
+ return op.branchOffsetsCodeUnit?.length
11
+ ?? op.branchOffsetsIndex?.length
12
+ ?? op.targetInstructionIndices?.length
13
+ ?? op.branchOffsetIndices?.length;
14
+ }
15
+ /**
16
+ * Calculate the size of an operation in code units (16-bit words).
17
+ * Works with any tier of operation (Tier 1, 2, 3, or SmaliCodeOperation).
18
+ */
19
+ export function getOperationSizeInCodeUnits(operation) {
20
+ if (operation.operation === 'packed-switch-payload') {
21
+ const length = getBranchOffsetsLength(operation);
22
+ if (length === undefined) {
23
+ throw new Error('packed-switch-payload missing branch offsets array');
24
+ }
25
+ // Header (4 code units) + targets (2 code units each)
26
+ return (length * 2) + 4;
27
+ }
28
+ if (operation.operation === 'sparse-switch-payload') {
29
+ const length = getBranchOffsetsLength(operation);
30
+ if (length === undefined) {
31
+ throw new Error('sparse-switch-payload missing branch offsets array');
32
+ }
33
+ // Header (2 code units) + keys (2 code units each) + targets (2 code units each)
34
+ return (length * 4) + 2;
35
+ }
36
+ if (operation.operation === 'fill-array-data-payload') {
37
+ // data.length is already the total number of bytes (size * elementWidth)
38
+ const dataSize = operation.data.length;
39
+ const paddingSize = dataSize % 2;
40
+ const totalBytes = 8 + dataSize + paddingSize; // header (8 bytes) + data + padding
41
+ return totalBytes / 2; // Convert to code units
42
+ }
43
+ const format = operationFormats[operation.operation];
44
+ if (!format) {
45
+ throw new Error(`Unknown operation format: ${operation.operation}`);
46
+ }
47
+ return formatSizes[format];
48
+ }
49
+ /**
50
+ * Build mapping from code unit offset to instruction index.
51
+ * Also maps the end position (total code units) to instructions.length.
52
+ */
53
+ export function buildCodeUnitToIndexMap(instructions) {
54
+ const map = new Map();
55
+ let codeUnitOffset = 0;
56
+ for (let index = 0; index < instructions.length; index++) {
57
+ map.set(isoCodeUnit.wrap(codeUnitOffset), isoInstructionIndex.wrap(index));
58
+ codeUnitOffset += getOperationSizeInCodeUnits(instructions[index]);
59
+ }
60
+ // Map the end position
61
+ map.set(isoCodeUnit.wrap(codeUnitOffset), isoInstructionIndex.wrap(instructions.length));
62
+ return map;
63
+ }
64
+ /**
65
+ * Build mapping from instruction index to code unit offset.
66
+ * Also maps instructions.length to the total code units.
67
+ */
68
+ export function buildIndexToCodeUnitMap(instructions) {
69
+ const map = new Map();
70
+ let codeUnitOffset = 0;
71
+ for (let index = 0; index < instructions.length; index++) {
72
+ map.set(isoInstructionIndex.wrap(index), isoCodeUnit.wrap(codeUnitOffset));
73
+ codeUnitOffset += getOperationSizeInCodeUnits(instructions[index]);
74
+ }
75
+ // Map the end position
76
+ map.set(isoInstructionIndex.wrap(instructions.length), isoCodeUnit.wrap(codeUnitOffset));
77
+ return map;
78
+ }
79
+ /**
80
+ * Convert a code unit offset to an instruction index.
81
+ */
82
+ export function codeUnitToInstructionIndex(codeUnitOffset, codeUnitToIndexMap) {
83
+ const index = codeUnitToIndexMap.get(codeUnitOffset);
84
+ if (index === undefined) {
85
+ throw new Error(`Invalid code unit offset: ${isoCodeUnit.unwrap(codeUnitOffset)}. Valid offsets: ${[...codeUnitToIndexMap.keys()].map(k => isoCodeUnit.unwrap(k)).join(', ')}`);
86
+ }
87
+ return index;
88
+ }
89
+ /**
90
+ * Convert an instruction index to a code unit offset.
91
+ */
92
+ export function instructionIndexToCodeUnit(instructionIndex, indexToCodeUnitMap) {
93
+ const offset = indexToCodeUnitMap.get(instructionIndex);
94
+ if (offset === undefined) {
95
+ throw new Error(`Invalid instruction index: ${isoInstructionIndex.unwrap(instructionIndex)}. Valid indices: ${[...indexToCodeUnitMap.keys()].map(k => isoInstructionIndex.unwrap(k)).join(', ')}`);
96
+ }
97
+ return offset;
98
+ }
99
+ /**
100
+ * Convert a relative branch offset (in code units) to a relative instruction offset.
101
+ * The offset is relative to the source instruction.
102
+ */
103
+ export function convertBranchOffsetToInstructionOffset(branchOffsetInCodeUnits, sourceInstructionIndex, indexToCodeUnitMap, codeUnitToIndexMap) {
104
+ const sourceCodeUnit = indexToCodeUnitMap.get(sourceInstructionIndex);
105
+ if (sourceCodeUnit === undefined) {
106
+ throw new Error(`Invalid source instruction index: ${isoInstructionIndex.unwrap(sourceInstructionIndex)}`);
107
+ }
108
+ const targetCodeUnit = isoCodeUnit.wrap(isoCodeUnit.unwrap(sourceCodeUnit) + isoCodeUnit.unwrap(branchOffsetInCodeUnits));
109
+ const targetIndex = codeUnitToIndexMap.get(targetCodeUnit);
110
+ if (targetIndex === undefined) {
111
+ throw new Error(`Invalid branch target code unit: ${isoCodeUnit.unwrap(targetCodeUnit)} (from source ${isoCodeUnit.unwrap(sourceCodeUnit)} + offset ${isoCodeUnit.unwrap(branchOffsetInCodeUnits)})`);
112
+ }
113
+ return isoInstructionIndex.wrap(isoInstructionIndex.unwrap(targetIndex) - isoInstructionIndex.unwrap(sourceInstructionIndex));
114
+ }
115
+ /**
116
+ * Convert a relative instruction offset back to a code unit offset.
117
+ * The offset is relative to the source instruction.
118
+ */
119
+ export function convertInstructionOffsetToBranchOffset(instructionOffset, sourceInstructionIndex, indexToCodeUnitMap) {
120
+ const sourceCodeUnit = indexToCodeUnitMap.get(sourceInstructionIndex);
121
+ if (sourceCodeUnit === undefined) {
122
+ throw new Error(`Invalid source instruction index: ${isoInstructionIndex.unwrap(sourceInstructionIndex)}`);
123
+ }
124
+ const targetInstructionIndex = isoInstructionIndex.wrap(isoInstructionIndex.unwrap(sourceInstructionIndex) + isoInstructionIndex.unwrap(instructionOffset));
125
+ const targetCodeUnit = indexToCodeUnitMap.get(targetInstructionIndex);
126
+ if (targetCodeUnit === undefined) {
127
+ throw new Error(`Invalid target instruction index: ${isoInstructionIndex.unwrap(targetInstructionIndex)}`);
128
+ }
129
+ return isoCodeUnit.wrap(isoCodeUnit.unwrap(targetCodeUnit) - isoCodeUnit.unwrap(sourceCodeUnit));
130
+ }
131
+ /**
132
+ * Find the switch instruction that references a payload at the given index.
133
+ * Returns the index of the switch instruction.
134
+ */
135
+ export function findSwitchInstructionForPayload(instructions, payloadIndex, indexToCodeUnitMap) {
136
+ const payloadCodeUnit = indexToCodeUnitMap.get(payloadIndex);
137
+ if (payloadCodeUnit === undefined) {
138
+ throw new Error(`Invalid payload index: ${isoInstructionIndex.unwrap(payloadIndex)}`);
139
+ }
140
+ for (let i = 0; i < instructions.length; i++) {
141
+ const inst = instructions[i];
142
+ if ((inst.operation === 'packed-switch' || inst.operation === 'sparse-switch')
143
+ && 'branchOffsetCodeUnit' in inst) {
144
+ const sourceCodeUnit = indexToCodeUnitMap.get(isoInstructionIndex.wrap(i));
145
+ if (sourceCodeUnit !== undefined && isoCodeUnit.unwrap(sourceCodeUnit) + isoCodeUnit.unwrap(inst.branchOffsetCodeUnit) === isoCodeUnit.unwrap(payloadCodeUnit)) {
146
+ return isoInstructionIndex.wrap(i);
147
+ }
148
+ }
149
+ }
150
+ throw new Error(`No switch instruction found for payload at index ${isoInstructionIndex.unwrap(payloadIndex)}`);
151
+ }
152
+ /**
153
+ * Convert all branch offsets in instructions from code units to instruction offsets.
154
+ * Tier 1 (CodeUnit) -> Tier 2 (InstructionIndex)
155
+ */
156
+ export function convertBranchOffsetsToInstructionOffsets(instructions) {
157
+ const codeUnitToIndexMap = buildCodeUnitToIndexMap(instructions);
158
+ const indexToCodeUnitMap = buildIndexToCodeUnitMap(instructions);
159
+ return instructions.map((instruction, index) => {
160
+ // Handle single branchOffsetCodeUnit (goto, if-*, packed-switch, sparse-switch, fill-array-data)
161
+ if ('branchOffsetCodeUnit' in instruction) {
162
+ const { branchOffsetCodeUnit, ...rest } = instruction;
163
+ return {
164
+ ...rest,
165
+ branchOffsetIndex: convertBranchOffsetToInstructionOffset(branchOffsetCodeUnit, isoInstructionIndex.wrap(index), indexToCodeUnitMap, codeUnitToIndexMap),
166
+ };
167
+ }
168
+ // Handle branchOffsetsCodeUnit array (packed-switch-payload, sparse-switch-payload)
169
+ if ('branchOffsetsCodeUnit' in instruction) {
170
+ const { branchOffsetsCodeUnit, ...rest } = instruction;
171
+ // For payload instructions, find the referring switch instruction
172
+ const sourceIndex = findSwitchInstructionForPayload(instructions, isoInstructionIndex.wrap(index), indexToCodeUnitMap);
173
+ return {
174
+ ...rest,
175
+ branchOffsetsIndex: branchOffsetsCodeUnit.map(offset => convertBranchOffsetToInstructionOffset(offset, sourceIndex, indexToCodeUnitMap, codeUnitToIndexMap)),
176
+ };
177
+ }
178
+ return instruction;
179
+ });
180
+ }
181
+ /**
182
+ * Unwrap instruction indices to plain numbers and convert relative to absolute.
183
+ * Tier 2 (InstructionIndex, relative) -> Tier 3 (plain number, absolute)
184
+ */
185
+ export function unwrapBranchOffsets(instructions) {
186
+ // First pass: find switch instruction indices for payloads
187
+ const payloadToSwitchIndex = new Map();
188
+ for (let i = 0; i < instructions.length; i++) {
189
+ const inst = instructions[i];
190
+ if ((inst.operation === 'packed-switch' || inst.operation === 'sparse-switch')
191
+ && 'branchOffsetIndex' in inst) {
192
+ const payloadIndex = i + isoInstructionIndex.unwrap(inst.branchOffsetIndex);
193
+ payloadToSwitchIndex.set(payloadIndex, i);
194
+ }
195
+ }
196
+ return instructions.map((instruction, index) => {
197
+ if ('branchOffsetIndex' in instruction) {
198
+ const { branchOffsetIndex, ...rest } = instruction;
199
+ // Convert relative offset to absolute index
200
+ const targetInstructionIndex = index + isoInstructionIndex.unwrap(branchOffsetIndex);
201
+ return {
202
+ ...rest,
203
+ targetInstructionIndex,
204
+ };
205
+ }
206
+ if ('branchOffsetsIndex' in instruction) {
207
+ const { branchOffsetsIndex, ...rest } = instruction;
208
+ // For payloads, the offsets are relative to the switch instruction, not the payload
209
+ const switchIndex = payloadToSwitchIndex.get(index);
210
+ if (switchIndex === undefined) {
211
+ throw new Error(`No switch instruction found for payload at index ${index}`);
212
+ }
213
+ // Convert relative offsets to absolute indices
214
+ const targetInstructionIndices = branchOffsetsIndex.map(offset => switchIndex + isoInstructionIndex.unwrap(offset));
215
+ return {
216
+ ...rest,
217
+ targetInstructionIndices,
218
+ };
219
+ }
220
+ return instruction;
221
+ });
222
+ }
223
+ /**
224
+ * Wrap plain numbers to instruction indices and convert absolute to relative.
225
+ * Tier 3 (plain number, absolute) -> Tier 2 (InstructionIndex, relative)
226
+ */
227
+ export function wrapBranchOffsets(instructions) {
228
+ // First pass: find switch instruction indices for payloads
229
+ const payloadToSwitchIndex = new Map();
230
+ for (let i = 0; i < instructions.length; i++) {
231
+ const inst = instructions[i];
232
+ if ((inst.operation === 'packed-switch' || inst.operation === 'sparse-switch')
233
+ && 'targetInstructionIndex' in inst) {
234
+ const payloadIndex = inst.targetInstructionIndex;
235
+ payloadToSwitchIndex.set(payloadIndex, i);
236
+ }
237
+ }
238
+ return instructions.map((instruction, index) => {
239
+ if ('targetInstructionIndex' in instruction) {
240
+ const { targetInstructionIndex, ...rest } = instruction;
241
+ // Convert absolute index to relative offset
242
+ const branchOffsetIndex = isoInstructionIndex.wrap(targetInstructionIndex - index);
243
+ return {
244
+ ...rest,
245
+ branchOffsetIndex,
246
+ };
247
+ }
248
+ if ('targetInstructionIndices' in instruction) {
249
+ const { targetInstructionIndices, ...rest } = instruction;
250
+ // For payloads, the offsets are relative to the switch instruction, not the payload
251
+ const switchIndex = payloadToSwitchIndex.get(index);
252
+ if (switchIndex === undefined) {
253
+ throw new Error(`No switch instruction found for payload at index ${index}`);
254
+ }
255
+ // Convert absolute indices to relative offsets from switch instruction
256
+ const branchOffsetsIndex = targetInstructionIndices.map(target => isoInstructionIndex.wrap(target - switchIndex));
257
+ return {
258
+ ...rest,
259
+ branchOffsetsIndex,
260
+ };
261
+ }
262
+ return instruction;
263
+ });
264
+ }
265
+ /**
266
+ * Build mapping from instruction index to code unit offset.
267
+ * Works with any tier of operations.
268
+ */
269
+ export function buildIndexToCodeUnitMapGeneric(instructions) {
270
+ const map = new Map();
271
+ let codeUnitOffset = 0;
272
+ for (let index = 0; index < instructions.length; index++) {
273
+ map.set(isoInstructionIndex.wrap(index), isoCodeUnit.wrap(codeUnitOffset));
274
+ codeUnitOffset += getOperationSizeInCodeUnits(instructions[index]);
275
+ }
276
+ // Map the end position
277
+ map.set(isoInstructionIndex.wrap(instructions.length), isoCodeUnit.wrap(codeUnitOffset));
278
+ return map;
279
+ }
280
+ /**
281
+ * Build mapping from instruction index to code unit offset for Tier 2 operations.
282
+ */
283
+ export function buildIndexToCodeUnitMapFromConverted(instructions) {
284
+ return buildIndexToCodeUnitMapGeneric(instructions);
285
+ }
286
+ /**
287
+ * Build mapping from instruction index to code unit offset for Tier 3 operations.
288
+ */
289
+ export function buildIndexToCodeUnitMapFromResolved(instructions) {
290
+ return buildIndexToCodeUnitMapGeneric(instructions);
291
+ }
292
+ /**
293
+ * Find the switch instruction that references a payload at the given index,
294
+ * when branch offsets are in instruction indices (Tier 2).
295
+ */
296
+ function findSwitchInstructionForPayloadByInstructionIndex(instructions, payloadIndex) {
297
+ for (let i = 0; i < instructions.length; i++) {
298
+ const inst = instructions[i];
299
+ if ((inst.operation === 'packed-switch' || inst.operation === 'sparse-switch')
300
+ && 'branchOffsetIndex' in inst
301
+ && i + isoInstructionIndex.unwrap(inst.branchOffsetIndex) === isoInstructionIndex.unwrap(payloadIndex)) {
302
+ return isoInstructionIndex.wrap(i);
303
+ }
304
+ }
305
+ throw new Error(`No switch instruction found for payload at index ${isoInstructionIndex.unwrap(payloadIndex)}`);
306
+ }
307
+ /**
308
+ * Convert all branch offsets in instructions from instruction offsets back to code units.
309
+ * Tier 2 (InstructionIndex) -> Tier 1 (CodeUnit)
310
+ */
311
+ export function convertInstructionOffsetsToBranchOffsets(instructions) {
312
+ const indexToCodeUnitMap = buildIndexToCodeUnitMapFromConverted(instructions);
313
+ return instructions.map((instruction, index) => {
314
+ // Handle single branchOffsetIndex
315
+ if ('branchOffsetIndex' in instruction) {
316
+ const { branchOffsetIndex, ...rest } = instruction;
317
+ return {
318
+ ...rest,
319
+ branchOffsetCodeUnit: convertInstructionOffsetToBranchOffset(branchOffsetIndex, isoInstructionIndex.wrap(index), indexToCodeUnitMap),
320
+ };
321
+ }
322
+ // Handle branchOffsetsIndex array
323
+ if ('branchOffsetsIndex' in instruction) {
324
+ const { branchOffsetsIndex, ...rest } = instruction;
325
+ // For payload instructions, find the referring switch instruction
326
+ const sourceIndex = findSwitchInstructionForPayloadByInstructionIndex(instructions, isoInstructionIndex.wrap(index));
327
+ return {
328
+ ...rest,
329
+ branchOffsetsCodeUnit: branchOffsetsIndex.map(offset => convertInstructionOffsetToBranchOffset(offset, sourceIndex, indexToCodeUnitMap)),
330
+ };
331
+ }
332
+ return instruction;
333
+ });
334
+ }
@@ -1,8 +1,9 @@
1
1
  import { type Iso } from 'monocle-ts';
2
+ import { type CodeUnit } from '../dalvikExecutableParser/typedNumbers.js';
2
3
  import { type Parser } from '../parser.js';
3
4
  export declare const nibblesParser: Parser<[number, number], Uint8Array>;
4
5
  type DalvikBytecodeFormat10t = {
5
- branchOffset: number;
6
+ branchOffsetCodeUnit: CodeUnit;
6
7
  };
7
8
  export declare const dalvikBytecodeFormat10tParser: Parser<DalvikBytecodeFormat10t, Uint8Array>;
8
9
  type DalvikBytecodeFormat10x = void;
@@ -21,7 +22,7 @@ type DalvikBytecodeFormat12x = {
21
22
  };
22
23
  export declare const dalvikBytecodeFormat12xParser: Parser<DalvikBytecodeFormat12x, Uint8Array>;
23
24
  type DalvikBytecodeFormat20t = {
24
- branchOffset: number;
25
+ branchOffsetCodeUnit: CodeUnit;
25
26
  };
26
27
  export declare const dalvikBytecodeFormat20tParser: Parser<DalvikBytecodeFormat20t, Uint8Array>;
27
28
  type DalvikBytecodeFormat21c<Index> = {
@@ -37,7 +38,7 @@ type DalvikBytecodeFormat21h = {
37
38
  };
38
39
  export declare const dalvikBytecodeFormat21hParser: Parser<DalvikBytecodeFormat21h, Uint8Array>;
39
40
  type DalvikBytecodeFormat21t = {
40
- branchOffset: number;
41
+ branchOffsetCodeUnit: CodeUnit;
41
42
  registers: number[];
42
43
  };
43
44
  export declare const createDalvikBytecodeFormat21tParser: () => Parser<DalvikBytecodeFormat21t, Uint8Array>;
@@ -64,7 +65,7 @@ type DalvikBytecodeFormat22s = {
64
65
  };
65
66
  export declare const createDalvikBytecodeFormat22sParser: () => Parser<DalvikBytecodeFormat22s, Uint8Array>;
66
67
  type DalvikBytecodeFormat22t = {
67
- branchOffset: number;
68
+ branchOffsetCodeUnit: CodeUnit;
68
69
  registers: number[];
69
70
  };
70
71
  export declare const createDalvikBytecodeFormat22tParser: () => Parser<DalvikBytecodeFormat22t, Uint8Array>;
@@ -77,7 +78,7 @@ type DalvikBytecodeFormat23x = {
77
78
  };
78
79
  export declare const dalvikBytecodeFormat23xParser: Parser<DalvikBytecodeFormat23x, Uint8Array>;
79
80
  type DalvikBytecodeFormat30t = {
80
- branchOffset: number;
81
+ branchOffsetCodeUnit: CodeUnit;
81
82
  };
82
83
  export declare const dalvikBytecodeFormat30tParser: Parser<DalvikBytecodeFormat30t, Uint8Array>;
83
84
  type DalvikBytecodeFormat31i = {
@@ -93,7 +94,7 @@ export declare const createDalvikBytecodeFormat31cParser: <Index>({ isoIndex, }:
93
94
  isoIndex: Iso<Index, number>;
94
95
  }) => Parser<DalvikBytecodeFormat31c<Index>, Uint8Array>;
95
96
  type DalvikBytecodeFormat31t = {
96
- branchOffset: number;
97
+ branchOffsetCodeUnit: CodeUnit;
97
98
  registers: number[];
98
99
  };
99
100
  export declare const dalvikBytecodeFormat31tParser: Parser<DalvikBytecodeFormat31t, Uint8Array>;