@futpib/parser 1.0.1 → 1.0.3

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 (425) hide show
  1. package/.github/copilot-instructions.md +149 -0
  2. package/.github/workflows/copilot-setup-steps.yml +18 -0
  3. package/.github/workflows/main.yml +29 -8
  4. package/.yarn/releases/yarn-4.9.4.cjs +942 -0
  5. package/.yarnrc.yml +1 -1
  6. package/build/allSettledStream.js +32 -14
  7. package/build/allSettledStream.test.js +32 -0
  8. package/build/androidPackage.d.ts +39 -0
  9. package/build/androidPackageParser.d.ts +17 -0
  10. package/build/androidPackageParser.js +185 -0
  11. package/build/androidPackageParser.test.js +22 -0
  12. package/build/androidPackageUnparser.d.ts +4 -0
  13. package/build/androidPackageUnparser.js +94 -0
  14. package/build/androidPackageUnparser.test.js +26 -0
  15. package/build/arbitrarilySlicedAsyncInterable.d.ts +3 -1
  16. package/build/arbitrarilySlicedAsyncInterable.js +3 -3
  17. package/build/arbitrarilySlicedAsyncInterator.js +2 -1
  18. package/build/arbitraryDalvikBytecode.d.ts +4 -0
  19. package/build/arbitraryDalvikBytecode.js +640 -0
  20. package/build/arbitraryDalvikExecutable.d.ts +3 -0
  21. package/build/arbitraryDalvikExecutable.js +282 -0
  22. package/build/arbitraryDosDateTime.js +1 -0
  23. package/build/arbitraryZipStream.js +1 -1
  24. package/build/arrayParser.js +2 -2
  25. package/build/arrayParser.test.js +3 -3
  26. package/build/arrayUnparser.d.ts +1 -1
  27. package/build/backsmali.d.ts +3 -0
  28. package/build/backsmali.js +50 -0
  29. package/build/bsonParser.js +6 -2
  30. package/build/customInvariant.d.ts +2 -1
  31. package/build/customInvariant.js +4 -6
  32. package/build/dalvikBytecodeParser/formatParsers.d.ts +171 -0
  33. package/build/dalvikBytecodeParser/formatParsers.js +304 -0
  34. package/build/dalvikBytecodeParser/formatSizes.d.ts +34 -0
  35. package/build/dalvikBytecodeParser/formatSizes.js +34 -0
  36. package/build/dalvikBytecodeParser/operationFormats.d.ts +225 -0
  37. package/build/dalvikBytecodeParser/operationFormats.js +225 -0
  38. package/build/dalvikBytecodeParser.d.ts +1207 -0
  39. package/build/dalvikBytecodeParser.js +1289 -0
  40. package/build/dalvikBytecodeUnparser/formatUnparsers.d.ts +152 -0
  41. package/build/dalvikBytecodeUnparser/formatUnparsers.js +225 -0
  42. package/build/dalvikBytecodeUnparser.d.ts +3 -0
  43. package/build/dalvikBytecodeUnparser.js +642 -0
  44. package/build/dalvikBytecodeUnparser.test.js +25 -0
  45. package/build/dalvikExecutable.d.ts +215 -0
  46. package/build/dalvikExecutable.js +56 -0
  47. package/build/dalvikExecutableParser/stringSyntaxParser.d.ts +4 -0
  48. package/build/dalvikExecutableParser/stringSyntaxParser.js +76 -0
  49. package/build/dalvikExecutableParser/typeParsers.d.ts +11 -0
  50. package/build/dalvikExecutableParser/typeParsers.js +39 -0
  51. package/build/dalvikExecutableParser/typedNumbers.d.ts +106 -0
  52. package/build/dalvikExecutableParser/typedNumbers.js +18 -0
  53. package/build/dalvikExecutableParser.d.ts +5 -0
  54. package/build/dalvikExecutableParser.js +1757 -0
  55. package/build/dalvikExecutableParser.test.js +72 -0
  56. package/build/dalvikExecutableParserAgainstSmaliParser.test.js +275 -0
  57. package/build/dalvikExecutableUnparser/annotationUnparsers.d.ts +14 -0
  58. package/build/dalvikExecutableUnparser/annotationUnparsers.js +97 -0
  59. package/build/dalvikExecutableUnparser/poolBuilders.d.ts +49 -0
  60. package/build/dalvikExecutableUnparser/poolBuilders.js +140 -0
  61. package/build/dalvikExecutableUnparser/poolScanners.d.ts +4 -0
  62. package/build/dalvikExecutableUnparser/poolScanners.js +220 -0
  63. package/build/dalvikExecutableUnparser/sectionUnparsers.d.ts +25 -0
  64. package/build/dalvikExecutableUnparser/sectionUnparsers.js +581 -0
  65. package/build/dalvikExecutableUnparser/utils.d.ts +10 -0
  66. package/build/dalvikExecutableUnparser/utils.js +108 -0
  67. package/build/dalvikExecutableUnparser.d.ts +4 -0
  68. package/build/dalvikExecutableUnparser.js +406 -0
  69. package/build/dalvikExecutableUnparser.test.js +31 -0
  70. package/build/debugLogInputParser.d.ts +4 -0
  71. package/build/debugLogInputParser.js +16 -0
  72. package/build/debugLogParser.js +14 -3
  73. package/build/disjunctionParser.d.ts +2 -1
  74. package/build/disjunctionParser.js +6 -4
  75. package/build/elementTerminatedArrayParser.d.ts +3 -0
  76. package/build/elementTerminatedArrayParser.js +18 -0
  77. package/build/elementTerminatedArrayParser.test.js +52 -0
  78. package/build/elementTerminatedSequenceArrayParser.d.ts +3 -0
  79. package/build/elementTerminatedSequenceArrayParser.js +32 -0
  80. package/build/elementTerminatedSequenceArrayParser.test.js +34 -0
  81. package/build/elementTerminatedSequenceParser.d.ts +3 -0
  82. package/build/elementTerminatedSequenceParser.js +27 -0
  83. package/build/elementTerminatedSequenceParser.test.js +34 -0
  84. package/build/endOfInputParser.d.ts +1 -1
  85. package/build/exactElementParser.js +10 -5
  86. package/build/exactElementSwitchParser.d.ts +3 -0
  87. package/build/exactElementSwitchParser.js +22 -0
  88. package/build/exactSequenceParser.d.ts +2 -1
  89. package/build/exactSequenceParser.js +12 -2
  90. package/build/fetchCid.d.ts +1 -0
  91. package/build/fetchCid.js +103 -0
  92. package/build/fetchCid.test.js +16 -0
  93. package/build/fixedLengthSequenceParser.d.ts +1 -0
  94. package/build/fixedLengthSequenceParser.js +18 -1
  95. package/build/fixedLengthSequenceParser.test.js +41 -0
  96. package/build/hasExecutable.d.ts +1 -0
  97. package/build/hasExecutable.js +8 -0
  98. package/build/highResolutionTimer.d.ts +16 -0
  99. package/build/highResolutionTimer.js +42 -0
  100. package/build/inputReader.d.ts +11 -0
  101. package/build/inputReader.js +37 -0
  102. package/build/inputReader.test.js +161 -8
  103. package/build/inputReaderState.d.ts +10 -0
  104. package/build/inputReaderState.js +16 -0
  105. package/build/inspect.d.ts +1 -0
  106. package/build/inspect.js +7 -0
  107. package/build/javaKeyStoreParser.test.js +8 -8
  108. package/build/jsonParser.d.ts +2 -0
  109. package/build/jsonParser.js +19 -22
  110. package/build/lazyMessageError.d.ts +48 -0
  111. package/build/lazyMessageError.js +53 -0
  112. package/build/lazyMessageError.test.d.ts +1 -0
  113. package/build/lazyMessageError.test.js +15 -0
  114. package/build/leb128Parser.d.ts +7 -0
  115. package/build/leb128Parser.js +82 -0
  116. package/build/leb128Parser.test.d.ts +1 -0
  117. package/build/leb128Parser.test.js +107 -0
  118. package/build/lookaheadParser.d.ts +2 -0
  119. package/build/lookaheadParser.js +14 -0
  120. package/build/negativeLookaheadParser.js +22 -16
  121. package/build/negativeLookaheadParser.test.d.ts +1 -0
  122. package/build/negativeLookaheadParser.test.js +30 -0
  123. package/build/noStackCaptureOverheadError.d.ts +4 -0
  124. package/build/noStackCaptureOverheadError.js +9 -0
  125. package/build/noStackCaptureOverheadError.test.d.ts +1 -0
  126. package/build/noStackCaptureOverheadError.test.js +15 -0
  127. package/build/nonEmptyArrayParser.d.ts +2 -0
  128. package/build/nonEmptyArrayParser.js +32 -0
  129. package/build/nonEmptyArrayParser.test.d.ts +1 -0
  130. package/build/nonEmptyArrayParser.test.js +17 -0
  131. package/build/optionalParser.js +2 -2
  132. package/build/parser.d.ts +11 -1
  133. package/build/parser.js +82 -32
  134. package/build/parser.test.js +141 -25
  135. package/build/parserAccessorParser.js +9 -1
  136. package/build/parserConsumedSequenceParser.d.ts +1 -1
  137. package/build/parserConsumedSequenceParser.js +21 -16
  138. package/build/parserContext.d.ts +22 -6
  139. package/build/parserContext.js +113 -57
  140. package/build/parserContext.test.js +33 -2
  141. package/build/parserCreatorCompose.d.ts +1 -0
  142. package/build/parserCreatorCompose.js +8 -2
  143. package/build/parserError.d.ts +605 -40
  144. package/build/parserError.js +98 -53
  145. package/build/parserImplementationInvariant.d.ts +1 -1
  146. package/build/parserImplementationInvariant.js +2 -2
  147. package/build/parserInputCompanion.d.ts +15 -0
  148. package/build/parserInputCompanion.js +38 -0
  149. package/build/promiseCompose.d.ts +1 -1
  150. package/build/promiseCompose.js +11 -1
  151. package/build/promiseSettled.d.ts +1 -0
  152. package/build/promiseSettled.js +4 -0
  153. package/build/separatedArrayParser.d.ts +2 -0
  154. package/build/separatedArrayParser.js +39 -0
  155. package/build/separatedArrayParser.test.d.ts +1 -0
  156. package/build/separatedArrayParser.test.js +21 -0
  157. package/build/separatedNonEmptyArrayParser.d.ts +2 -0
  158. package/build/separatedNonEmptyArrayParser.js +40 -0
  159. package/build/separatedNonEmptyArrayParser.test.d.ts +1 -0
  160. package/build/separatedNonEmptyArrayParser.test.js +66 -0
  161. package/build/sequenceBuffer.d.ts +10 -0
  162. package/build/sequenceBuffer.js +54 -2
  163. package/build/sequenceBuffer.test.js +57 -0
  164. package/build/sequenceTerminatedSequenceParser.d.ts +5 -0
  165. package/build/sequenceTerminatedSequenceParser.js +32 -0
  166. package/build/sequenceTerminatedSequenceParser.test.d.ts +1 -0
  167. package/build/sequenceTerminatedSequenceParser.test.js +37 -0
  168. package/build/sequenceUnparser.d.ts +1 -1
  169. package/build/skipParser.d.ts +1 -1
  170. package/build/skipParser.js +4 -2
  171. package/build/skipToParser.d.ts +2 -0
  172. package/build/skipToParser.js +11 -0
  173. package/build/sliceBoundedParser.d.ts +1 -1
  174. package/build/sliceBoundedParser.js +7 -2
  175. package/build/sliceBoundedParser.test.js +30 -1
  176. package/build/smali.d.ts +1 -0
  177. package/build/smali.js +21 -0
  178. package/build/smaliParser.d.ts +68 -0
  179. package/build/smaliParser.js +2081 -0
  180. package/build/smaliParser.test.d.ts +1 -0
  181. package/build/smaliParser.test.js +410 -0
  182. package/build/stringFromAsyncIterable.d.ts +1 -0
  183. package/build/stringFromAsyncIterable.js +7 -0
  184. package/build/terminatedArrayParser.d.ts +3 -1
  185. package/build/terminatedArrayParser.js +79 -2
  186. package/build/terminatedArrayParser.test.d.ts +1 -0
  187. package/build/terminatedArrayParser.test.js +131 -0
  188. package/build/toAsyncIterable.d.ts +1 -0
  189. package/build/toAsyncIterable.js +7 -0
  190. package/build/toAsyncIterator.d.ts +1 -0
  191. package/build/toAsyncIterator.js +33 -0
  192. package/build/tupleParser.d.ts +4 -0
  193. package/build/tupleParser.js +1 -5
  194. package/build/unionParser.d.ts +2 -1
  195. package/build/unionParser.js +29 -14
  196. package/build/unionParser.test.d.ts +1 -0
  197. package/build/unionParser.test.js +60 -0
  198. package/build/unparser.d.ts +3 -3
  199. package/build/unparser.js +6 -4
  200. package/build/unparser.test.js +7 -19
  201. package/build/unparserContext.d.ts +2 -2
  202. package/build/unparserContext.js +2 -3
  203. package/build/unparserError.d.ts +2 -1
  204. package/build/unparserError.js +2 -1
  205. package/build/unparserImplementationInvariant.d.ts +1 -1
  206. package/build/unparserOutputCompanion.d.ts +1 -1
  207. package/build/unparserOutputCompanion.js +1 -1
  208. package/build/zipParser.d.ts +7 -2
  209. package/build/zipParser.js +36 -12
  210. package/build/zipUnparser.d.ts +7 -4
  211. package/build/zipUnparser.js +64 -45
  212. package/build/zipUnparser.test.js +15 -15
  213. package/package.json +33 -24
  214. package/src/allSettledStream.test.ts +40 -0
  215. package/src/allSettledStream.ts +47 -15
  216. package/src/androidPackage.ts +48 -0
  217. package/src/androidPackageParser.test.ts +27 -0
  218. package/src/{apkParser.test.ts.md → androidPackageParser.test.ts.md} +4 -4
  219. package/src/androidPackageParser.test.ts.snap +0 -0
  220. package/src/androidPackageParser.ts +398 -0
  221. package/src/androidPackageUnparser.test.ts +34 -0
  222. package/src/androidPackageUnparser.ts +126 -0
  223. package/src/arbitrarilySlicedAsyncInterable.ts +7 -2
  224. package/src/arbitrarilySlicedAsyncInterator.ts +4 -4
  225. package/src/arbitraryDalvikBytecode.ts +992 -0
  226. package/src/arbitraryDalvikExecutable.ts +434 -0
  227. package/src/arbitraryDosDateTime.ts +1 -0
  228. package/src/arbitraryZipStream.ts +1 -1
  229. package/src/arrayParser.test.ts +3 -3
  230. package/src/arrayParser.ts +2 -2
  231. package/src/arrayUnparser.ts +2 -2
  232. package/src/backsmali.ts +74 -0
  233. package/src/bsonParser.test.ts +12 -14
  234. package/src/bsonParser.ts +13 -2
  235. package/src/customInvariant.ts +8 -12
  236. package/src/dalvikBytecodeParser/formatParsers.ts +780 -0
  237. package/src/dalvikBytecodeParser/formatSizes.ts +35 -0
  238. package/src/dalvikBytecodeParser/operationFormats.ts +226 -0
  239. package/src/dalvikBytecodeParser.ts +2873 -0
  240. package/src/dalvikBytecodeUnparser/formatUnparsers.ts +442 -0
  241. package/src/dalvikBytecodeUnparser.test.ts +44 -0
  242. package/src/dalvikBytecodeUnparser.ts +758 -0
  243. package/src/dalvikExecutable.ts +282 -0
  244. package/src/dalvikExecutableParser/stringSyntaxParser.ts +145 -0
  245. package/src/dalvikExecutableParser/typeParsers.ts +74 -0
  246. package/src/dalvikExecutableParser/typedNumbers.ts +57 -0
  247. package/src/dalvikExecutableParser.test.ts +89 -0
  248. package/src/dalvikExecutableParser.test.ts.md +634 -0
  249. package/src/dalvikExecutableParser.test.ts.snap +0 -0
  250. package/src/dalvikExecutableParser.ts +3245 -0
  251. package/src/dalvikExecutableParserAgainstSmaliParser.test.ts +363 -0
  252. package/src/dalvikExecutableUnparser/annotationUnparsers.ts +135 -0
  253. package/src/dalvikExecutableUnparser/poolBuilders.ts +189 -0
  254. package/src/dalvikExecutableUnparser/poolScanners.ts +297 -0
  255. package/src/dalvikExecutableUnparser/sectionUnparsers.ts +683 -0
  256. package/src/dalvikExecutableUnparser/utils.ts +149 -0
  257. package/src/dalvikExecutableUnparser.test.ts +57 -0
  258. package/src/dalvikExecutableUnparser.ts +581 -0
  259. package/src/debugLogInputParser.ts +28 -0
  260. package/src/debugLogParser.ts +19 -3
  261. package/src/disjunctionParser.ts +12 -7
  262. package/src/elementTerminatedArrayParser.test.ts +99 -0
  263. package/src/elementTerminatedArrayParser.ts +31 -0
  264. package/src/elementTerminatedSequenceArrayParser.test.ts +52 -0
  265. package/src/elementTerminatedSequenceArrayParser.ts +52 -0
  266. package/src/elementTerminatedSequenceParser.test.ts +52 -0
  267. package/src/elementTerminatedSequenceParser.ts +43 -0
  268. package/src/endOfInputParser.ts +1 -1
  269. package/src/exactElementParser.ts +17 -11
  270. package/src/exactElementSwitchParser.ts +41 -0
  271. package/src/exactSequenceParser.ts +23 -2
  272. package/src/fetchCid.test.ts +20 -0
  273. package/src/fetchCid.ts +121 -0
  274. package/src/fixedLengthSequenceParser.test.ts +75 -0
  275. package/src/fixedLengthSequenceParser.ts +28 -1
  276. package/src/hasExecutable.ts +11 -0
  277. package/src/highResolutionTimer.ts +49 -0
  278. package/src/inputReader.test.ts +204 -8
  279. package/src/inputReader.ts +76 -3
  280. package/src/inputReaderState.ts +33 -0
  281. package/src/inspect.ts +9 -0
  282. package/src/javaKeyStoreParser.test.ts +12 -15
  283. package/src/javaKeyStoreParser.ts +2 -6
  284. package/src/jsonParser.test.ts +2 -4
  285. package/src/jsonParser.ts +46 -62
  286. package/src/lazyMessageError.test.ts +21 -0
  287. package/src/lazyMessageError.ts +88 -0
  288. package/src/leb128Parser.test.ts +173 -0
  289. package/src/leb128Parser.ts +125 -0
  290. package/src/lookaheadParser.ts +19 -0
  291. package/src/negativeLookaheadParser.test.ts +49 -0
  292. package/src/negativeLookaheadParser.ts +27 -15
  293. package/src/noStackCaptureOverheadError.test.ts +17 -0
  294. package/src/noStackCaptureOverheadError.ts +12 -0
  295. package/src/nonEmptyArrayParser.test.ts +21 -0
  296. package/src/nonEmptyArrayParser.ts +44 -0
  297. package/src/optionalParser.ts +3 -2
  298. package/src/parser.test.ts +203 -31
  299. package/src/parser.test.ts.md +34 -27
  300. package/src/parser.test.ts.snap +0 -0
  301. package/src/parser.ts +172 -45
  302. package/src/parserAccessorParser.ts +12 -2
  303. package/src/parserConsumedSequenceParser.ts +26 -17
  304. package/src/parserContext.test.ts +37 -2
  305. package/src/parserContext.ts +185 -79
  306. package/src/parserCreatorCompose.ts +20 -2
  307. package/src/parserError.ts +144 -61
  308. package/src/parserImplementationInvariant.ts +3 -3
  309. package/src/parserInputCompanion.ts +55 -0
  310. package/src/promiseCompose.ts +17 -3
  311. package/src/promiseSettled.ts +6 -0
  312. package/src/separatedArrayParser.test.ts +34 -0
  313. package/src/separatedArrayParser.ts +55 -0
  314. package/src/separatedNonEmptyArrayParser.test.ts +117 -0
  315. package/src/separatedNonEmptyArrayParser.ts +61 -0
  316. package/src/sequenceBuffer.test.ts +70 -0
  317. package/src/sequenceBuffer.ts +88 -2
  318. package/src/sequenceTerminatedSequenceParser.test.ts +58 -0
  319. package/src/sequenceTerminatedSequenceParser.ts +62 -0
  320. package/src/sequenceUnparser.ts +2 -2
  321. package/src/skipParser.ts +7 -5
  322. package/src/skipToParser.ts +16 -0
  323. package/src/sliceBoundedParser.test.ts +35 -1
  324. package/src/sliceBoundedParser.ts +19 -1
  325. package/src/smali.ts +29 -0
  326. package/src/smaliParser.test.ts +443 -0
  327. package/src/smaliParser.test.ts.md +3907 -0
  328. package/src/smaliParser.test.ts.snap +0 -0
  329. package/src/smaliParser.ts +3348 -0
  330. package/src/stringFromAsyncIterable.ts +9 -0
  331. package/src/terminatedArrayParser.test.ts +258 -0
  332. package/src/terminatedArrayParser.ts +109 -6
  333. package/src/toAsyncIterable.ts +7 -0
  334. package/src/toAsyncIterator.ts +48 -0
  335. package/src/tupleParser.ts +8 -5
  336. package/src/uint8Array.ts +2 -3
  337. package/src/unionParser.test.ts +78 -0
  338. package/src/unionParser.ts +47 -21
  339. package/src/unparser.test.ts +18 -34
  340. package/src/unparser.ts +13 -9
  341. package/src/unparserContext.ts +9 -13
  342. package/src/unparserError.ts +2 -1
  343. package/src/unparserImplementationInvariant.ts +1 -1
  344. package/src/unparserOutputCompanion.ts +1 -1
  345. package/src/zip.ts +2 -6
  346. package/src/zipParser.ts +71 -20
  347. package/src/zipUnparser.test.ts +19 -19
  348. package/src/zipUnparser.ts +139 -90
  349. package/tsconfig.json +7 -1
  350. package/xo.config.ts +15 -0
  351. package/.yarn/releases/yarn-4.5.3.cjs +0 -934
  352. package/build/apk.d.ts +0 -39
  353. package/build/apkParser.d.ts +0 -16
  354. package/build/apkParser.js +0 -164
  355. package/build/apkParser.test.js +0 -22
  356. package/build/apkUnparser.d.ts +0 -4
  357. package/build/apkUnparser.js +0 -90
  358. package/build/apkUnparser.test.js +0 -26
  359. package/build/arbitraryDosDate.d.ts +0 -2
  360. package/build/arbitraryDosDate.js +0 -8
  361. package/build/arbitraryZipEntry.d.ts +0 -3
  362. package/build/arbitraryZipEntry.js +0 -26
  363. package/build/createDisjunctionParser.d.ts +0 -2
  364. package/build/createDisjunctionParser.js +0 -47
  365. package/build/createExactParser.d.ts +0 -2
  366. package/build/createExactParser.js +0 -12
  367. package/build/createSequentialUnionParser.d.ts +0 -2
  368. package/build/createSequentialUnionParser.js +0 -69
  369. package/build/fixedLengthChunkParser.d.ts +0 -2
  370. package/build/fixedLengthChunkParser.js +0 -12
  371. package/build/fixedLengthParser.d.ts +0 -2
  372. package/build/fixedLengthParser.js +0 -12
  373. package/build/inputChunkBuffer.d.ts +0 -15
  374. package/build/inputChunkBuffer.js +0 -40
  375. package/build/inputChunkBuffer.test.js +0 -34
  376. package/build/inputCompanion.d.ts +0 -18
  377. package/build/inputCompanion.js +0 -28
  378. package/build/invariantDefined.d.ts +0 -1
  379. package/build/invariantDefined.js +0 -5
  380. package/build/invariantIdentity.d.ts +0 -3
  381. package/build/invariantIdentity.js +0 -5
  382. package/build/javaKeystoreParser.d.ts +0 -2
  383. package/build/javaKeystoreParser.js +0 -7
  384. package/build/jsonParser2.d.ts +0 -3
  385. package/build/jsonParser2.js +0 -52
  386. package/build/jsonParser2.test.js +0 -22
  387. package/build/negativeLookahead.d.ts +0 -2
  388. package/build/negativeLookahead.js +0 -18
  389. package/build/parserCompose.d.ts +0 -3
  390. package/build/parserCompose.js +0 -7
  391. package/build/parserImplementationInvariantInvariant.d.ts +0 -3
  392. package/build/parserImplementationInvariantInvariant.js +0 -15
  393. package/build/parserInvariant.d.ts +0 -4
  394. package/build/parserInvariant.js +0 -11
  395. package/build/promiseFish.d.ts +0 -1
  396. package/build/promiseFish.js +0 -3
  397. package/build/sequenceParser.d.ts +0 -3
  398. package/build/sequenceParser.js +0 -10
  399. package/build/terminatedSequenceParser.d.ts +0 -2
  400. package/build/terminatedSequenceParser.js +0 -24
  401. package/build/unparserInputCompanion.d.ts +0 -15
  402. package/build/unparserInputCompanion.js +0 -13
  403. package/build/zipEntry.d.ts +0 -28
  404. package/build/zipFile.d.ts +0 -32
  405. package/build/zipFileEntry.d.ts +0 -6
  406. package/src/apk.ts +0 -48
  407. package/src/apkParser.test.ts +0 -30
  408. package/src/apkParser.test.ts.snap +0 -0
  409. package/src/apkParser.ts +0 -392
  410. package/src/apkUnparser.test.ts +0 -37
  411. package/src/apkUnparser.ts +0 -120
  412. package/src/invariantDefined.ts +0 -6
  413. package/src/invariantIdentity.ts +0 -8
  414. /package/build/{apk.js → androidPackage.js} +0 -0
  415. /package/build/{apkParser.test.d.ts → androidPackageParser.test.d.ts} +0 -0
  416. /package/build/{apkUnparser.test.d.ts → androidPackageUnparser.test.d.ts} +0 -0
  417. /package/build/{arbitraryDosPermissions.d.ts → dalvikBytecodeUnparser.test.d.ts} +0 -0
  418. /package/build/{arbitraryDosPermissions.js → dalvikExecutableParser.test.d.ts} +0 -0
  419. /package/build/{inputChunkBuffer.test.d.ts → dalvikExecutableParserAgainstSmaliParser.test.d.ts} +0 -0
  420. /package/build/{jsonParser2.test.d.ts → dalvikExecutableUnparser.test.d.ts} +0 -0
  421. /package/build/{parserParsingInvariant.d.ts → elementTerminatedArrayParser.test.d.ts} +0 -0
  422. /package/build/{parserParsingInvariant.js → elementTerminatedSequenceArrayParser.test.d.ts} +0 -0
  423. /package/build/{zipEntry.js → elementTerminatedSequenceParser.test.d.ts} +0 -0
  424. /package/build/{zipFile.js → fetchCid.test.d.ts} +0 -0
  425. /package/build/{zipFileEntry.js → fixedLengthSequenceParser.test.d.ts} +0 -0
@@ -0,0 +1,683 @@
1
+ import { type Unparser } from '../unparser.js';
2
+ import { type UnparserContext } from '../unparserContext.js';
3
+
4
+ async function* yieldAndCapture<T>(gen: AsyncIterable<T, T>): AsyncIterable<T, T> {
5
+ let value: T | undefined;
6
+ for await (value of gen) {
7
+ yield value;
8
+ }
9
+ return value!;
10
+ }
11
+ import {
12
+ type DalvikExecutableAccessFlags,
13
+ type DalvikExecutableAnnotation,
14
+ type DalvikExecutableClassAnnotations,
15
+ type DalvikExecutableClassData,
16
+ type DalvikExecutableClassDefinition,
17
+ type DalvikExecutableCode,
18
+ type DalvikExecutableDebugInfo,
19
+ type DalvikExecutableEncodedValue,
20
+ type DalvikExecutableField,
21
+ type DalvikExecutableFieldWithAccess,
22
+ type DalvikExecutableMethod,
23
+ type DalvikExecutableMethodWithAccess,
24
+ type DalvikExecutablePrototype,
25
+ isDalvikExecutableField,
26
+ isDalvikExecutableMethod,
27
+ } from '../dalvikExecutable.js';
28
+ import { type DalvikBytecode } from '../dalvikBytecodeParser.js';
29
+ import { dalvikBytecodeUnparser } from '../dalvikBytecodeUnparser.js';
30
+ import { ubyteUnparser, ushortUnparser, uintUnparser } from '../dalvikBytecodeUnparser/formatUnparsers.js';
31
+ import { type PoolBuilders } from './poolBuilders.js';
32
+ import { WriteLater } from '../unparserContext.js';
33
+ import { alignmentUnparser, encodeModifiedUtf8, mutf8Unparser, sleb128Unparser, uleb128p1Unparser, uleb128Unparser } from './utils.js';
34
+
35
+ export function createSectionUnparsers(poolBuilders: PoolBuilders) {
36
+ const { stringPool, typePool, protoPool, fieldPool, methodPool } = poolBuilders;
37
+
38
+ function getStringIndex(str: string | undefined): number {
39
+ if (str === undefined) {
40
+ throw new Error('String is undefined');
41
+ }
42
+
43
+ const index = stringPool.getIndex(str);
44
+ if (index === undefined) {
45
+ throw new Error(`String not found in pool: ${str}`);
46
+ }
47
+
48
+ return index;
49
+ }
50
+
51
+ function getTypeIndex(typeDescriptor: string | undefined): number {
52
+ if (typeDescriptor === undefined) {
53
+ throw new Error('Type descriptor is undefined');
54
+ }
55
+
56
+ const index = typePool.getIndex(typeDescriptor);
57
+ if (index === undefined) {
58
+ throw new Error(`Type not found in pool: ${typeDescriptor}`);
59
+ }
60
+
61
+ return index;
62
+ }
63
+
64
+ function getProtoIndex(proto: DalvikExecutablePrototype): number {
65
+ const index = protoPool.getIndex(proto);
66
+ if (index === undefined) {
67
+ throw new Error(`Prototype not found in pool: ${JSON.stringify(proto)}`);
68
+ }
69
+
70
+ return index;
71
+ }
72
+
73
+ function getFieldIndex(field: DalvikExecutableField): number {
74
+ const index = fieldPool.getIndex(field);
75
+ if (index === undefined) {
76
+ throw new Error(`Field not found in pool: ${JSON.stringify(field)}`);
77
+ }
78
+
79
+ return index;
80
+ }
81
+
82
+ function getMethodIndex(method: DalvikExecutableMethod): number {
83
+ const index = methodPool.getIndex(method);
84
+ if (index === undefined) {
85
+ throw new Error(`Method not found in pool: ${JSON.stringify(method)}`);
86
+ }
87
+
88
+ return index;
89
+ }
90
+
91
+ const stringDataUnparser: Unparser<string, Uint8Array> = async function * (input, unparserContext) {
92
+ const encoded = encodeModifiedUtf8(input);
93
+
94
+ yield * uleb128Unparser(input.length, unparserContext);
95
+
96
+ yield encoded;
97
+
98
+ yield new Uint8Array([ 0 ]);
99
+ };
100
+
101
+ const typeListUnparser: Unparser<string[], Uint8Array> = async function * (input, unparserContext) {
102
+ yield * uintUnparser(input.length, unparserContext);
103
+
104
+ for (const type of input) {
105
+ const typeIndex = getTypeIndex(type);
106
+ yield * ushortUnparser(typeIndex, unparserContext);
107
+ }
108
+ };
109
+
110
+ const protoDataUnparser: Unparser<DalvikExecutablePrototype, Uint8Array> = async function * (input, unparserContext) {
111
+ const shortyIndex = getStringIndex(input.shorty);
112
+ const returnTypeIndex = getTypeIndex(input.returnType);
113
+
114
+ yield * uintUnparser(shortyIndex, unparserContext);
115
+ yield * uintUnparser(returnTypeIndex, unparserContext);
116
+
117
+ if (input.parameters.length > 0) {
118
+ const parametersOffsetWriteLater = yield * yieldAndCapture(unparserContext.writeLater(4));
119
+ } else {
120
+ yield * uintUnparser(0, unparserContext);
121
+ }
122
+ };
123
+
124
+ const fieldIdUnparser: Unparser<DalvikExecutableField, Uint8Array> = async function * (input, unparserContext) {
125
+ const classIndex = getTypeIndex(input.class);
126
+ const typeIndex = getTypeIndex(input.type);
127
+ const nameIndex = getStringIndex(input.name);
128
+
129
+ yield * ushortUnparser(classIndex, unparserContext);
130
+ yield * ushortUnparser(typeIndex, unparserContext);
131
+ yield * uintUnparser(nameIndex, unparserContext);
132
+ };
133
+
134
+ const methodIdUnparser: Unparser<DalvikExecutableMethod, Uint8Array> = async function * (input, unparserContext) {
135
+ const classIndex = getTypeIndex(input.class);
136
+ const protoIndex = getProtoIndex(input.prototype);
137
+ const nameIndex = getStringIndex(input.name);
138
+
139
+ yield * ushortUnparser(classIndex, unparserContext);
140
+ yield * ushortUnparser(protoIndex, unparserContext);
141
+ yield * uintUnparser(nameIndex, unparserContext);
142
+ };
143
+
144
+ function accessFlagsToNumber(accessFlags: DalvikExecutableAccessFlags): number {
145
+ let flags = 0;
146
+
147
+ if (accessFlags.public) flags |= 0x0001;
148
+ if (accessFlags.private) flags |= 0x0002;
149
+ if (accessFlags.protected) flags |= 0x0004;
150
+ if (accessFlags.static) flags |= 0x0008;
151
+ if (accessFlags.final) flags |= 0x0010;
152
+ if (accessFlags.synchronized) flags |= 0x0020;
153
+ if (accessFlags.volatile) flags |= 0x0040;
154
+ if (accessFlags.bridge) flags |= 0x0040;
155
+ if (accessFlags.transient) flags |= 0x0080;
156
+ if (accessFlags.varargs) flags |= 0x0080;
157
+ if (accessFlags.native) flags |= 0x0100;
158
+ if (accessFlags.interface) flags |= 0x0200;
159
+ if (accessFlags.abstract) flags |= 0x0400;
160
+ if (accessFlags.strict) flags |= 0x0800;
161
+ if (accessFlags.synthetic) flags |= 0x1000;
162
+ if (accessFlags.annotation) flags |= 0x2000;
163
+ if (accessFlags.enum) flags |= 0x4000;
164
+ if (accessFlags.constructor) flags |= 0x10000;
165
+ if (accessFlags.declaredSynchronized) flags |= 0x20000;
166
+
167
+ return flags;
168
+ }
169
+
170
+ const encodedValueUnparser: Unparser<DalvikExecutableEncodedValue, Uint8Array> = async function * (input, unparserContext) {
171
+ const { type, value } = input;
172
+
173
+ // Handle null
174
+ if (type === 'null') {
175
+ yield new Uint8Array([ 0x1E ]);
176
+ return;
177
+ }
178
+
179
+ // Handle boolean
180
+ if (type === 'boolean') {
181
+ // VALUE_BOOLEAN = 0x1F, with value_arg=0 for false, value_arg=1 for true
182
+ yield new Uint8Array([ value ? ((1 << 5) | 0x1F) : ((0 << 5) | 0x1F) ]);
183
+ return;
184
+ }
185
+
186
+ // Handle primitive numeric types
187
+ if (type === 'byte') {
188
+ const bytes = encodeSignedInt(value);
189
+ yield new Uint8Array([ 0x00 | ((bytes.length - 1) << 5) ]);
190
+ yield bytes;
191
+ return;
192
+ }
193
+
194
+ if (type === 'short') {
195
+ const bytes = encodeSignedInt(value);
196
+ yield new Uint8Array([ 0x02 | ((bytes.length - 1) << 5) ]);
197
+ yield bytes;
198
+ return;
199
+ }
200
+
201
+ if (type === 'char') {
202
+ const bytes = encodeUnsignedInt(value);
203
+ yield new Uint8Array([ 0x03 | ((bytes.length - 1) << 5) ]);
204
+ yield bytes;
205
+ return;
206
+ }
207
+
208
+ if (type === 'int') {
209
+ const bytes = encodeSignedInt(value);
210
+ yield new Uint8Array([ 0x04 | ((bytes.length - 1) << 5) ]);
211
+ yield bytes;
212
+ return;
213
+ }
214
+
215
+ if (type === 'long') {
216
+ const bytes = encodeSignedLong(value);
217
+ yield new Uint8Array([ 0x06 | ((bytes.length - 1) << 5) ]);
218
+ yield bytes;
219
+ return;
220
+ }
221
+
222
+ if (type === 'float') {
223
+ const bytes = encodeFloat(value);
224
+ yield new Uint8Array([ 0x10 | ((bytes.length - 1) << 5) ]);
225
+ yield bytes;
226
+ return;
227
+ }
228
+
229
+ if (type === 'double') {
230
+ const bytes = encodeDouble(value);
231
+ yield new Uint8Array([ 0x11 | ((bytes.length - 1) << 5) ]);
232
+ yield bytes;
233
+ return;
234
+ }
235
+
236
+ // Handle method handle
237
+ if (type === 'methodHandle') {
238
+ const bytes = encodeValueArgument(value);
239
+ yield new Uint8Array([ 0x16 | ((bytes.length - 1) << 5) ]);
240
+ yield bytes;
241
+ return;
242
+ }
243
+
244
+ // Handle types that reference the pool
245
+ if (type === 'string') {
246
+ const stringIndex = getStringIndex(value);
247
+ const bytes = encodeValueArgument(stringIndex);
248
+ yield new Uint8Array([ 0x17 | ((bytes.length - 1) << 5) ]);
249
+ yield bytes;
250
+ return;
251
+ }
252
+
253
+ if (type === 'type') {
254
+ const typeIndex = getTypeIndex(value);
255
+ const bytes = encodeValueArgument(typeIndex);
256
+ yield new Uint8Array([ 0x18 | ((bytes.length - 1) << 5) ]);
257
+ yield bytes;
258
+ return;
259
+ }
260
+
261
+ if (type === 'field') {
262
+ const fieldIndex = getFieldIndex(value);
263
+ const bytes = encodeValueArgument(fieldIndex);
264
+ yield new Uint8Array([ 0x19 | ((bytes.length - 1) << 5) ]);
265
+ yield bytes;
266
+ return;
267
+ }
268
+
269
+ if (type === 'method') {
270
+ const methodIndex = getMethodIndex(value);
271
+ const bytes = encodeValueArgument(methodIndex);
272
+ yield new Uint8Array([ 0x1A | ((bytes.length - 1) << 5) ]);
273
+ yield bytes;
274
+ return;
275
+ }
276
+
277
+ if (type === 'enum') {
278
+ const fieldIndex = getFieldIndex(value);
279
+ const bytes = encodeValueArgument(fieldIndex);
280
+ yield new Uint8Array([ 0x1B | ((bytes.length - 1) << 5) ]);
281
+ yield bytes;
282
+ return;
283
+ }
284
+
285
+ if (type === 'methodType') {
286
+ const protoIndex = getProtoIndex(value);
287
+ const bytes = encodeValueArgument(protoIndex);
288
+ yield new Uint8Array([ 0x15 | ((bytes.length - 1) << 5) ]);
289
+ yield bytes;
290
+ return;
291
+ }
292
+
293
+ // Handle arrays
294
+ if (type === 'array') {
295
+ yield new Uint8Array([ 0x1C ]);
296
+ yield * uleb128Unparser(value.length, unparserContext);
297
+
298
+ for (const element of value) {
299
+ yield * encodedValueUnparser(element, unparserContext);
300
+ }
301
+ return;
302
+ }
303
+
304
+ // Handle annotations
305
+ if (type === 'annotation') {
306
+ const typeIndex = getTypeIndex(value.type);
307
+ yield new Uint8Array([ 0x1D ]);
308
+ yield * uleb128Unparser(typeIndex, unparserContext);
309
+ yield * uleb128Unparser(value.elements.length, unparserContext);
310
+
311
+ for (const element of value.elements) {
312
+ const nameIndex = getStringIndex(element.name);
313
+ yield * uleb128Unparser(nameIndex, unparserContext);
314
+ yield * encodedValueUnparser(element.value, unparserContext);
315
+ }
316
+ return;
317
+ }
318
+ };
319
+
320
+ function encodeValueArgument(value: number): Uint8Array {
321
+ if (value === 0) {
322
+ return new Uint8Array([ 0 ]);
323
+ }
324
+
325
+ const bytes: number[] = [];
326
+ let v = value;
327
+
328
+ while (v !== 0) {
329
+ bytes.push(v & 0xFF);
330
+ v >>>= 8;
331
+ }
332
+
333
+ return new Uint8Array(bytes);
334
+ }
335
+
336
+ function encodeSignedInt(value: number): Uint8Array {
337
+ const buffer = Buffer.alloc(4);
338
+ buffer.writeInt32LE(value);
339
+
340
+ let length = 4;
341
+ const signByte = value < 0 ? 0xFF : 0x00;
342
+
343
+ while (length > 1 && buffer[length - 1] === signByte) {
344
+ const prevByte = buffer[length - 2];
345
+ const signBitMatches = value < 0 ? (prevByte & 0x80) !== 0 : (prevByte & 0x80) === 0;
346
+
347
+ if (signBitMatches) {
348
+ length--;
349
+ } else {
350
+ break;
351
+ }
352
+ }
353
+
354
+ return buffer.subarray(0, length);
355
+ }
356
+
357
+ function encodeSignedLong(value: bigint): Uint8Array {
358
+ const buffer = Buffer.alloc(8);
359
+ buffer.writeBigInt64LE(value);
360
+
361
+ let length = 8;
362
+ const signByte = value < 0n ? 0xFF : 0x00;
363
+
364
+ while (length > 1 && buffer[length - 1] === signByte) {
365
+ if (length === 2) {
366
+ break;
367
+ }
368
+
369
+ const prevByte = buffer[length - 2];
370
+ const signBitMatches = value < 0n ? (prevByte & 0x80) !== 0 : (prevByte & 0x80) === 0;
371
+
372
+ if (signBitMatches) {
373
+ length--;
374
+ } else {
375
+ break;
376
+ }
377
+ }
378
+
379
+ return buffer.subarray(0, length);
380
+ }
381
+
382
+ function encodeUnsignedInt(value: number): Uint8Array {
383
+ const buffer = Buffer.alloc(4);
384
+ buffer.writeUInt32LE(value);
385
+
386
+ let length = 4;
387
+
388
+ while (length > 1 && buffer[length - 1] === 0x00) {
389
+ length--;
390
+ }
391
+
392
+ return buffer.subarray(0, length);
393
+ }
394
+
395
+ function encodeFloat(value: number): Uint8Array {
396
+ const buffer = Buffer.alloc(4);
397
+ buffer.writeFloatLE(value);
398
+
399
+ let start = 0;
400
+ let end = 4;
401
+
402
+ // Remove leading zero bytes (low-order), but keep at least one byte
403
+ // Note: In DEX format, encoded values keep high-order bytes
404
+ while (end > start + 1 && buffer[start] === 0x00) {
405
+ start++;
406
+ }
407
+
408
+ return buffer.subarray(start, end);
409
+ }
410
+
411
+ function encodeDouble(value: number): Uint8Array {
412
+ const buffer = Buffer.alloc(8);
413
+ buffer.writeDoubleLE(value);
414
+
415
+ let start = 0;
416
+ let end = 8;
417
+
418
+ // Remove leading zero bytes (low-order), but keep at least one byte
419
+ // Note: In DEX format, encoded values keep high-order bytes
420
+ while (end > start + 1 && buffer[start] === 0x00) {
421
+ start++;
422
+ }
423
+
424
+ return buffer.subarray(start, end);
425
+ }
426
+
427
+ const encodedArrayUnparser: Unparser<DalvikExecutableEncodedValue[], Uint8Array> = async function * (input, unparserContext) {
428
+ yield * uleb128Unparser(input.length, unparserContext);
429
+
430
+ for (const value of input) {
431
+ yield * encodedValueUnparser(value, unparserContext);
432
+ }
433
+ };
434
+
435
+ const debugInfoUnparser: Unparser<DalvikExecutableDebugInfo, Uint8Array> = async function * (input, unparserContext) {
436
+ yield * uleb128Unparser(input.lineStart, unparserContext);
437
+
438
+ yield * uleb128Unparser(input.parameterNames.length, unparserContext);
439
+
440
+ for (const paramName of input.parameterNames) {
441
+ if (paramName === undefined) {
442
+ yield * uleb128p1Unparser(-1, unparserContext);
443
+ } else {
444
+ const nameIndex = getStringIndex(paramName);
445
+ yield * uleb128p1Unparser(nameIndex, unparserContext);
446
+ }
447
+ }
448
+
449
+ for (const bytecode of input.bytecode) {
450
+ if (bytecode.type === 'advancePc') {
451
+ yield * ubyteUnparser(0x01, unparserContext);
452
+ yield * uleb128Unparser(bytecode.addressDiff, unparserContext);
453
+ } else if (bytecode.type === 'advanceLine') {
454
+ yield * ubyteUnparser(0x02, unparserContext);
455
+ yield * sleb128Unparser(bytecode.lineDiff, unparserContext);
456
+ } else if (bytecode.type === 'startLocal') {
457
+ yield * ubyteUnparser(0x03, unparserContext);
458
+ yield * uleb128Unparser(bytecode.registerNum, unparserContext);
459
+
460
+ if (bytecode.name === undefined) {
461
+ yield * uleb128p1Unparser(-1, unparserContext);
462
+ } else {
463
+ const nameIndex = getStringIndex(bytecode.name);
464
+ yield * uleb128p1Unparser(nameIndex, unparserContext);
465
+ }
466
+
467
+ if (bytecode.type_ === undefined) {
468
+ yield * uleb128p1Unparser(-1, unparserContext);
469
+ } else {
470
+ const typeIndex = getTypeIndex(bytecode.type_);
471
+ yield * uleb128p1Unparser(typeIndex, unparserContext);
472
+ }
473
+ } else if (bytecode.type === 'startLocalExtended') {
474
+ yield * ubyteUnparser(0x04, unparserContext);
475
+ yield * uleb128Unparser(bytecode.registerNum, unparserContext);
476
+
477
+ if (bytecode.name === undefined) {
478
+ yield * uleb128p1Unparser(-1, unparserContext);
479
+ } else {
480
+ const nameIndex = getStringIndex(bytecode.name);
481
+ yield * uleb128p1Unparser(nameIndex, unparserContext);
482
+ }
483
+
484
+ if (bytecode.type_ === undefined) {
485
+ yield * uleb128p1Unparser(-1, unparserContext);
486
+ } else {
487
+ const typeIndex = getTypeIndex(bytecode.type_);
488
+ yield * uleb128p1Unparser(typeIndex, unparserContext);
489
+ }
490
+
491
+ if (bytecode.signature === undefined) {
492
+ yield * uleb128p1Unparser(-1, unparserContext);
493
+ } else {
494
+ const sigIndex = getStringIndex(bytecode.signature);
495
+ yield * uleb128p1Unparser(sigIndex, unparserContext);
496
+ }
497
+ } else if (bytecode.type === 'endLocal') {
498
+ yield * ubyteUnparser(0x05, unparserContext);
499
+ yield * uleb128Unparser(bytecode.registerNum, unparserContext);
500
+ } else if (bytecode.type === 'restartLocal') {
501
+ yield * ubyteUnparser(0x06, unparserContext);
502
+ yield * uleb128Unparser(bytecode.registerNum, unparserContext);
503
+ } else if (bytecode.type === 'setPrologueEnd') {
504
+ yield * ubyteUnparser(0x07, unparserContext);
505
+ } else if (bytecode.type === 'setEpilogueBegin') {
506
+ yield * ubyteUnparser(0x08, unparserContext);
507
+ } else if (bytecode.type === 'setFile') {
508
+ yield * ubyteUnparser(0x09, unparserContext);
509
+
510
+ if (bytecode.name === undefined) {
511
+ yield * uleb128p1Unparser(-1, unparserContext);
512
+ } else {
513
+ const nameIndex = getStringIndex(bytecode.name);
514
+ yield * uleb128p1Unparser(nameIndex, unparserContext);
515
+ }
516
+ } else if (bytecode.type === 'special') {
517
+ yield * ubyteUnparser(bytecode.value, unparserContext);
518
+ }
519
+ }
520
+
521
+ yield * ubyteUnparser(0x00, unparserContext);
522
+ };
523
+
524
+ const codeItemUnparser = (callback?: (result: { debugInfoOffsetWriteLater?: WriteLater<Uint8Array, number> }) => void): Unparser<DalvikExecutableCode<DalvikBytecode>, Uint8Array> => {
525
+ return async function * (input, unparserContext) {
526
+ yield * ushortUnparser(input.registersSize, unparserContext);
527
+ yield * ushortUnparser(input.insSize, unparserContext);
528
+ yield * ushortUnparser(input.outsSize, unparserContext);
529
+
530
+ yield * ushortUnparser(input.tries.length, unparserContext);
531
+
532
+ let debugInfoOffsetWriteLater;
533
+ if (input.debugInfo) {
534
+ debugInfoOffsetWriteLater = yield * yieldAndCapture(unparserContext.writeLater(4));
535
+ } else {
536
+ yield * uintUnparser(0, unparserContext);
537
+ }
538
+
539
+ if (callback) {
540
+ callback({ debugInfoOffsetWriteLater });
541
+ }
542
+
543
+ const instructionsSizeInShorts = await calculateInstructionsSize(input.instructions);
544
+ yield * uintUnparser(instructionsSizeInShorts, unparserContext);
545
+
546
+ yield * dalvikBytecodeUnparser(input.instructions, unparserContext);
547
+
548
+ if (input.tries.length > 0 && instructionsSizeInShorts % 2 !== 0) {
549
+ yield * ushortUnparser(0, unparserContext);
550
+ }
551
+
552
+ if (input.tries.length > 0) {
553
+ const handlerOffsetWriteLaters: Array<WriteLater<Uint8Array, number>> = [];
554
+
555
+ for (const tryBlock of input.tries) {
556
+ yield * uintUnparser(tryBlock.startAddress, unparserContext);
557
+ yield * ushortUnparser(tryBlock.instructionCount, unparserContext);
558
+ const handlerOffsetWriteLater = yield * yieldAndCapture(unparserContext.writeLater(2));
559
+ handlerOffsetWriteLaters.push(handlerOffsetWriteLater);
560
+ }
561
+
562
+ const handlersStartOffset = unparserContext.position;
563
+ yield * uleb128Unparser(input.tries.length, unparserContext);
564
+
565
+ for (let i = 0; i < input.tries.length; i++) {
566
+ const tryBlock = input.tries[i];
567
+ const handler = tryBlock.handler;
568
+
569
+ const handlerOffset = unparserContext.position - handlersStartOffset;
570
+ yield * unparserContext.writeEarlier(handlerOffsetWriteLaters[i], ushortUnparser, handlerOffset);
571
+
572
+ if (handler.catchAllAddress !== undefined) {
573
+ yield * sleb128Unparser(-handler.handlers.length, unparserContext);
574
+ } else {
575
+ yield * sleb128Unparser(handler.handlers.length, unparserContext);
576
+ }
577
+
578
+ for (const handlerItem of handler.handlers) {
579
+ const typeIndex = getTypeIndex(handlerItem.type);
580
+ yield * uleb128Unparser(typeIndex, unparserContext);
581
+ yield * uleb128Unparser(handlerItem.address, unparserContext);
582
+ }
583
+
584
+ if (handler.catchAllAddress !== undefined) {
585
+ yield * uleb128Unparser(handler.catchAllAddress, unparserContext);
586
+ }
587
+ }
588
+ }
589
+ };
590
+ };
591
+
592
+ async function calculateInstructionsSize(instructions: DalvikBytecode): Promise<number> {
593
+ let totalSize = 0;
594
+
595
+ const mockContext: UnparserContext<Uint8Array, number> = {
596
+ position: 0,
597
+ writeLater: () => { throw new Error('Not supported'); },
598
+ writeEarlier: () => { throw new Error('Not supported'); },
599
+ };
600
+
601
+ for await (const chunk of dalvikBytecodeUnparser(instructions, mockContext)) {
602
+ if (chunk instanceof Uint8Array) {
603
+ totalSize += chunk.length;
604
+ }
605
+ }
606
+
607
+ return Math.floor(totalSize / 2);
608
+ }
609
+
610
+ const classDataUnparser = (codeOffsetMap: Map<DalvikExecutableCode<DalvikBytecode>, number>): Unparser<DalvikExecutableClassData<DalvikBytecode>, Uint8Array> => {
611
+ return async function * (input, unparserContext) {
612
+ yield * uleb128Unparser(input.staticFields.length, unparserContext);
613
+ yield * uleb128Unparser(input.instanceFields.length, unparserContext);
614
+ yield * uleb128Unparser(input.directMethods.length, unparserContext);
615
+ yield * uleb128Unparser(input.virtualMethods.length, unparserContext);
616
+
617
+ let prevFieldIndex = 0;
618
+ for (const field of input.staticFields) {
619
+ const fieldIndex = getFieldIndex(field.field);
620
+ yield * uleb128Unparser(fieldIndex - prevFieldIndex, unparserContext);
621
+ yield * uleb128Unparser(accessFlagsToNumber(field.accessFlags), unparserContext);
622
+ prevFieldIndex = fieldIndex;
623
+ }
624
+
625
+ prevFieldIndex = 0;
626
+ for (const field of input.instanceFields) {
627
+ const fieldIndex = getFieldIndex(field.field);
628
+ yield * uleb128Unparser(fieldIndex - prevFieldIndex, unparserContext);
629
+ yield * uleb128Unparser(accessFlagsToNumber(field.accessFlags), unparserContext);
630
+ prevFieldIndex = fieldIndex;
631
+ }
632
+
633
+ let prevMethodIndex = 0;
634
+ for (const method of input.directMethods) {
635
+ const methodIndex = getMethodIndex(method.method);
636
+ yield * uleb128Unparser(methodIndex - prevMethodIndex, unparserContext);
637
+ yield * uleb128Unparser(accessFlagsToNumber(method.accessFlags), unparserContext);
638
+
639
+ const codeOffset = method.code ? codeOffsetMap.get(method.code) : 0;
640
+ if (method.code && codeOffset === undefined) {
641
+ throw new Error('Code offset not found in map');
642
+ }
643
+ yield * uleb128Unparser(codeOffset || 0, unparserContext);
644
+
645
+ prevMethodIndex = methodIndex;
646
+ }
647
+
648
+ prevMethodIndex = 0;
649
+ for (const method of input.virtualMethods) {
650
+ const methodIndex = getMethodIndex(method.method);
651
+ yield * uleb128Unparser(methodIndex - prevMethodIndex, unparserContext);
652
+ yield * uleb128Unparser(accessFlagsToNumber(method.accessFlags), unparserContext);
653
+
654
+ const codeOffset = method.code ? codeOffsetMap.get(method.code) : 0;
655
+ if (method.code && codeOffset === undefined) {
656
+ throw new Error('Code offset not found in map');
657
+ }
658
+ yield * uleb128Unparser(codeOffset || 0, unparserContext);
659
+
660
+ prevMethodIndex = methodIndex;
661
+ }
662
+ };
663
+ };
664
+
665
+ return {
666
+ stringDataUnparser,
667
+ typeListUnparser,
668
+ protoDataUnparser,
669
+ fieldIdUnparser,
670
+ methodIdUnparser,
671
+ encodedValueUnparser,
672
+ encodedArrayUnparser,
673
+ debugInfoUnparser,
674
+ codeItemUnparser,
675
+ classDataUnparser,
676
+ accessFlagsToNumber,
677
+ getStringIndex,
678
+ getTypeIndex,
679
+ getProtoIndex,
680
+ getFieldIndex,
681
+ getMethodIndex,
682
+ };
683
+ }