semantifold 0.3.0 → 0.5.0

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 (303) hide show
  1. package/README.md +61 -15
  2. package/build/index.d.ts +52 -2
  3. package/build/index.d.ts.map +1 -1
  4. package/build/index.js +60 -8
  5. package/build/src/artifact-path.d.ts +23 -1
  6. package/build/src/artifact-path.d.ts.map +1 -1
  7. package/build/src/artifact-path.js +45 -3
  8. package/build/src/artifacts.d.ts.map +1 -1
  9. package/build/src/artifacts.js +66 -1
  10. package/build/src/backends/android.d.ts +49 -0
  11. package/build/src/backends/android.d.ts.map +1 -0
  12. package/build/src/backends/android.js +1274 -0
  13. package/build/src/backends/c-validation.d.ts.map +1 -1
  14. package/build/src/backends/c-validation.js +7 -3
  15. package/build/src/backends/cpp-validation.d.ts.map +1 -1
  16. package/build/src/backends/cpp-validation.js +7 -3
  17. package/build/src/backends/csharp.js +7 -1
  18. package/build/src/backends/dart-runtime.d.ts +2 -0
  19. package/build/src/backends/dart-runtime.d.ts.map +1 -0
  20. package/build/src/backends/dart-runtime.js +41 -0
  21. package/build/src/backends/dart.d.ts +20 -0
  22. package/build/src/backends/dart.d.ts.map +1 -0
  23. package/build/src/backends/dart.js +321 -0
  24. package/build/src/backends/effects.d.ts +60 -0
  25. package/build/src/backends/effects.d.ts.map +1 -0
  26. package/build/src/backends/effects.js +746 -0
  27. package/build/src/backends/go.js +18 -4
  28. package/build/src/backends/identifiers.d.ts +36 -4
  29. package/build/src/backends/identifiers.d.ts.map +1 -1
  30. package/build/src/backends/identifiers.js +160 -10
  31. package/build/src/backends/index.d.ts.map +1 -1
  32. package/build/src/backends/index.js +27 -4
  33. package/build/src/backends/ios.d.ts +68 -0
  34. package/build/src/backends/ios.d.ts.map +1 -0
  35. package/build/src/backends/ios.js +1503 -0
  36. package/build/src/backends/java.d.ts.map +1 -1
  37. package/build/src/backends/java.js +429 -36
  38. package/build/src/backends/javascript.d.ts +6 -0
  39. package/build/src/backends/javascript.d.ts.map +1 -1
  40. package/build/src/backends/javascript.js +380 -24
  41. package/build/src/backends/kotlin-runtime.d.ts +3 -0
  42. package/build/src/backends/kotlin-runtime.d.ts.map +1 -0
  43. package/build/src/backends/kotlin-runtime.js +29 -0
  44. package/build/src/backends/kotlin.d.ts +33 -0
  45. package/build/src/backends/kotlin.d.ts.map +1 -0
  46. package/build/src/backends/kotlin.js +138 -0
  47. package/build/src/backends/native-validation.d.ts +2 -2
  48. package/build/src/backends/native-validation.d.ts.map +1 -1
  49. package/build/src/backends/native-validation.js +2 -2
  50. package/build/src/backends/ordered-expressions.d.ts.map +1 -1
  51. package/build/src/backends/ordered-expressions.js +39 -7
  52. package/build/src/backends/php-stdlib-support.d.ts +19 -0
  53. package/build/src/backends/php-stdlib-support.d.ts.map +1 -0
  54. package/build/src/backends/php-stdlib-support.js +227 -0
  55. package/build/src/backends/php.d.ts.map +1 -1
  56. package/build/src/backends/php.js +448 -33
  57. package/build/src/backends/program.d.ts +83 -0
  58. package/build/src/backends/program.d.ts.map +1 -0
  59. package/build/src/backends/program.js +1309 -0
  60. package/build/src/backends/python.js +7 -1
  61. package/build/src/backends/ruby.d.ts.map +1 -1
  62. package/build/src/backends/ruby.js +310 -24
  63. package/build/src/backends/rust-runtime.d.ts +7 -0
  64. package/build/src/backends/rust-runtime.d.ts.map +1 -0
  65. package/build/src/backends/rust-runtime.js +32 -0
  66. package/build/src/backends/rust-validation.d.ts +9 -0
  67. package/build/src/backends/rust-validation.d.ts.map +1 -0
  68. package/build/src/backends/rust-validation.js +78 -0
  69. package/build/src/backends/rust.d.ts +24 -0
  70. package/build/src/backends/rust.d.ts.map +1 -0
  71. package/build/src/backends/rust.js +344 -0
  72. package/build/src/backends/scalars.d.ts +14 -6
  73. package/build/src/backends/scalars.d.ts.map +1 -1
  74. package/build/src/backends/scalars.js +167 -17
  75. package/build/src/backends/shared.d.ts +23 -4
  76. package/build/src/backends/shared.d.ts.map +1 -1
  77. package/build/src/backends/shared.js +2174 -62
  78. package/build/src/backends/stdlib-support.d.ts +14 -0
  79. package/build/src/backends/stdlib-support.d.ts.map +1 -0
  80. package/build/src/backends/stdlib-support.js +237 -0
  81. package/build/src/backends/swift-runtime.d.ts +3 -0
  82. package/build/src/backends/swift-runtime.d.ts.map +1 -0
  83. package/build/src/backends/swift-runtime.js +14 -0
  84. package/build/src/backends/swift.d.ts +8 -0
  85. package/build/src/backends/swift.d.ts.map +1 -0
  86. package/build/src/backends/swift.js +127 -0
  87. package/build/src/backends/typescript.d.ts.map +1 -1
  88. package/build/src/backends/typescript.js +344 -24
  89. package/build/src/backends/wasm.d.ts +43 -0
  90. package/build/src/backends/wasm.d.ts.map +1 -0
  91. package/build/src/backends/wasm.js +2164 -0
  92. package/build/src/backends/writer.d.ts +255 -4
  93. package/build/src/backends/writer.d.ts.map +1 -1
  94. package/build/src/backends/writer.js +491 -3
  95. package/build/src/diagnostic.d.ts +4 -3
  96. package/build/src/diagnostic.d.ts.map +1 -1
  97. package/build/src/diagnostic.js +5 -3
  98. package/build/src/frontends/c.d.ts.map +1 -1
  99. package/build/src/frontends/c.js +5 -3
  100. package/build/src/frontends/cpp.d.ts.map +1 -1
  101. package/build/src/frontends/cpp.js +5 -3
  102. package/build/src/frontends/csharp.d.ts.map +1 -1
  103. package/build/src/frontends/csharp.js +7 -3
  104. package/build/src/frontends/dart.d.ts +10 -0
  105. package/build/src/frontends/dart.d.ts.map +1 -0
  106. package/build/src/frontends/dart.js +913 -0
  107. package/build/src/frontends/index.d.ts +3 -1
  108. package/build/src/frontends/index.d.ts.map +1 -1
  109. package/build/src/frontends/index.js +15 -5
  110. package/build/src/frontends/java.d.ts +110 -1
  111. package/build/src/frontends/java.d.ts.map +1 -1
  112. package/build/src/frontends/java.js +1725 -70
  113. package/build/src/frontends/javascript-typescript.d.ts +69 -1
  114. package/build/src/frontends/javascript-typescript.d.ts.map +1 -1
  115. package/build/src/frontends/javascript-typescript.js +1825 -93
  116. package/build/src/frontends/kotlin.d.ts +10 -0
  117. package/build/src/frontends/kotlin.d.ts.map +1 -0
  118. package/build/src/frontends/kotlin.js +685 -0
  119. package/build/src/frontends/php.d.ts +118 -1
  120. package/build/src/frontends/php.d.ts.map +1 -1
  121. package/build/src/frontends/php.js +1583 -76
  122. package/build/src/frontends/program.d.ts +74 -0
  123. package/build/src/frontends/program.d.ts.map +1 -0
  124. package/build/src/frontends/program.js +989 -0
  125. package/build/src/frontends/ruby.d.ts +68 -1
  126. package/build/src/frontends/ruby.d.ts.map +1 -1
  127. package/build/src/frontends/ruby.js +1446 -101
  128. package/build/src/frontends/rust-parser.d.ts +11 -0
  129. package/build/src/frontends/rust-parser.d.ts.map +1 -0
  130. package/build/src/frontends/rust-parser.js +15 -0
  131. package/build/src/frontends/rust.d.ts +14 -0
  132. package/build/src/frontends/rust.d.ts.map +1 -0
  133. package/build/src/frontends/rust.js +715 -0
  134. package/build/src/frontends/scalars.d.ts +10 -0
  135. package/build/src/frontends/scalars.d.ts.map +1 -1
  136. package/build/src/frontends/scalars.js +28 -2
  137. package/build/src/frontends/swift.d.ts +10 -0
  138. package/build/src/frontends/swift.d.ts.map +1 -0
  139. package/build/src/frontends/swift.js +860 -0
  140. package/build/src/frontends/types.d.ts +186 -0
  141. package/build/src/frontends/types.d.ts.map +1 -0
  142. package/build/src/frontends/types.js +634 -0
  143. package/build/src/language-registry.d.ts +46 -4
  144. package/build/src/language-registry.d.ts.map +1 -1
  145. package/build/src/language-registry.js +177 -13
  146. package/build/src/mapping.d.ts +2 -2
  147. package/build/src/mapping.d.ts.map +1 -1
  148. package/build/src/mapping.js +31 -10
  149. package/build/src/semantic/capabilities.d.ts +66 -0
  150. package/build/src/semantic/capabilities.d.ts.map +1 -0
  151. package/build/src/semantic/capabilities.js +649 -0
  152. package/build/src/semantic/effects.d.ts +26 -0
  153. package/build/src/semantic/effects.d.ts.map +1 -0
  154. package/build/src/semantic/effects.js +764 -0
  155. package/build/src/semantic/generics.d.ts +23 -0
  156. package/build/src/semantic/generics.d.ts.map +1 -0
  157. package/build/src/semantic/generics.js +61 -0
  158. package/build/src/semantic/lifetime.d.ts +37 -0
  159. package/build/src/semantic/lifetime.d.ts.map +1 -0
  160. package/build/src/semantic/lifetime.js +527 -0
  161. package/build/src/semantic/provenance.d.ts +9 -2
  162. package/build/src/semantic/provenance.d.ts.map +1 -1
  163. package/build/src/semantic/provenance.js +462 -20
  164. package/build/src/semantic/scalars.d.ts +11 -0
  165. package/build/src/semantic/scalars.d.ts.map +1 -1
  166. package/build/src/semantic/scalars.js +16 -1
  167. package/build/src/semantic/stdlib.d.ts +254 -0
  168. package/build/src/semantic/stdlib.d.ts.map +1 -0
  169. package/build/src/semantic/stdlib.js +880 -0
  170. package/build/src/semantic/types.d.ts +3108 -178
  171. package/build/src/semantic/types.d.ts.map +1 -1
  172. package/build/src/semantic/types.js +730 -15
  173. package/build/src/semantic/validate.d.ts +85 -5
  174. package/build/src/semantic/validate.d.ts.map +1 -1
  175. package/build/src/semantic/validate.js +2576 -98
  176. package/build/src/stdlib-facades.d.ts +304 -0
  177. package/build/src/stdlib-facades.d.ts.map +1 -0
  178. package/build/src/stdlib-facades.js +1167 -0
  179. package/build/src/stdlib-negotiation.d.ts +69 -0
  180. package/build/src/stdlib-negotiation.d.ts.map +1 -0
  181. package/build/src/stdlib-negotiation.js +403 -0
  182. package/build/src/stdlib-providers.d.ts +72 -0
  183. package/build/src/stdlib-providers.d.ts.map +1 -0
  184. package/build/src/stdlib-providers.js +339 -0
  185. package/build/src/toolchains.d.ts +55 -1
  186. package/build/src/toolchains.d.ts.map +1 -1
  187. package/build/src/toolchains.js +15 -4
  188. package/docs/android.md +79 -0
  189. package/docs/architecture.md +47 -13
  190. package/docs/dart.md +60 -0
  191. package/docs/goals.md +3 -3
  192. package/docs/ios.md +121 -0
  193. package/docs/kotlin.md +42 -0
  194. package/docs/language-support.md +238 -26
  195. package/docs/multi-file-modules.md +52 -0
  196. package/docs/parser-qualification.md +121 -8
  197. package/docs/plans/2026-09-05-standard-library-portability.md +10 -10
  198. package/docs/rust.md +88 -0
  199. package/docs/source-maps.md +17 -7
  200. package/docs/specification.md +5 -0
  201. package/docs/standard-library-portability.md +39 -8
  202. package/docs/swift.md +44 -0
  203. package/docs/testing.md +381 -4
  204. package/docs/webassembly.md +52 -0
  205. package/index.js +66 -8
  206. package/node_modules/semantifold-tree-sitter-legacy-internal/README.md +2 -2
  207. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/LICENSE +21 -0
  208. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/README.md +45 -0
  209. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/binding.gyp +30 -0
  210. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/bindings/node/binding.cc +20 -0
  211. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/bindings/node/binding_test.js +9 -0
  212. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/bindings/node/index.d.ts +28 -0
  213. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/bindings/node/index.js +11 -0
  214. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/grammar.js +1630 -0
  215. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/package.json +64 -0
  216. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/prebuilds/darwin-arm64/tree-sitter-rust.node +0 -0
  217. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/prebuilds/darwin-x64/tree-sitter-rust.node +0 -0
  218. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/prebuilds/linux-arm64/tree-sitter-rust.node +0 -0
  219. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/prebuilds/linux-x64/tree-sitter-rust.node +0 -0
  220. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/prebuilds/win32-arm64/tree-sitter-rust.node +0 -0
  221. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/prebuilds/win32-x64/tree-sitter-rust.node +0 -0
  222. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/queries/highlights.scm +159 -0
  223. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/queries/injections.scm +9 -0
  224. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/queries/tags.scm +60 -0
  225. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/grammar.json +9405 -0
  226. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/node-types.json +5399 -0
  227. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/parser.c +192569 -0
  228. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/scanner.c +393 -0
  229. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/tree_sitter/alloc.h +54 -0
  230. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/tree_sitter/array.h +290 -0
  231. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/src/tree_sitter/parser.h +266 -0
  232. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/tree-sitter-rust.wasm +0 -0
  233. package/node_modules/semantifold-tree-sitter-legacy-internal/node_modules/tree-sitter-rust/tree-sitter.json +53 -0
  234. package/node_modules/semantifold-tree-sitter-legacy-internal/package.json +3 -2
  235. package/node_modules/semantifold-tree-sitter-legacy-internal/src/c.js +5 -4
  236. package/package.json +5 -2
  237. package/src/artifact-path.js +47 -2
  238. package/src/artifacts.js +67 -0
  239. package/src/backends/android.js +1370 -0
  240. package/src/backends/c-validation.js +6 -1
  241. package/src/backends/cpp-validation.js +6 -1
  242. package/src/backends/csharp.js +3 -0
  243. package/src/backends/dart-runtime.js +41 -0
  244. package/src/backends/dart.js +326 -0
  245. package/src/backends/effects.js +705 -0
  246. package/src/backends/go.js +14 -2
  247. package/src/backends/identifiers.js +166 -9
  248. package/src/backends/index.js +27 -2
  249. package/src/backends/ios.js +1612 -0
  250. package/src/backends/java.js +454 -36
  251. package/src/backends/javascript.js +389 -23
  252. package/src/backends/kotlin-runtime.js +29 -0
  253. package/src/backends/kotlin.js +144 -0
  254. package/src/backends/native-validation.js +1 -1
  255. package/src/backends/ordered-expressions.js +40 -6
  256. package/src/backends/php-stdlib-support.js +239 -0
  257. package/src/backends/php.js +469 -32
  258. package/src/backends/program.js +1408 -0
  259. package/src/backends/python.js +3 -0
  260. package/src/backends/ruby.js +326 -23
  261. package/src/backends/rust-runtime.js +34 -0
  262. package/src/backends/rust-validation.js +75 -0
  263. package/src/backends/rust.js +335 -0
  264. package/src/backends/scalars.js +141 -16
  265. package/src/backends/shared.js +2314 -115
  266. package/src/backends/stdlib-support.js +234 -0
  267. package/src/backends/swift-runtime.js +14 -0
  268. package/src/backends/swift.js +132 -0
  269. package/src/backends/typescript.js +349 -23
  270. package/src/backends/wasm.js +2208 -0
  271. package/src/backends/writer.js +545 -2
  272. package/src/diagnostic.js +4 -2
  273. package/src/frontends/c.js +4 -2
  274. package/src/frontends/cpp.js +4 -2
  275. package/src/frontends/csharp.js +4 -2
  276. package/src/frontends/dart.js +963 -0
  277. package/src/frontends/index.js +14 -4
  278. package/src/frontends/java.js +1977 -69
  279. package/src/frontends/javascript-typescript.js +2046 -102
  280. package/src/frontends/kotlin.js +713 -0
  281. package/src/frontends/php.js +1725 -79
  282. package/src/frontends/program.js +1062 -0
  283. package/src/frontends/ruby.js +1624 -98
  284. package/src/frontends/rust-parser.js +18 -0
  285. package/src/frontends/rust.js +714 -0
  286. package/src/frontends/scalars.js +31 -1
  287. package/src/frontends/swift.js +893 -0
  288. package/src/frontends/types.js +750 -0
  289. package/src/language-registry.js +182 -12
  290. package/src/mapping.js +33 -9
  291. package/src/semantic/capabilities.js +671 -0
  292. package/src/semantic/effects.js +737 -0
  293. package/src/semantic/generics.js +58 -0
  294. package/src/semantic/lifetime.js +517 -0
  295. package/src/semantic/provenance.js +412 -19
  296. package/src/semantic/scalars.js +17 -0
  297. package/src/semantic/stdlib.js +921 -0
  298. package/src/semantic/types.js +810 -14
  299. package/src/semantic/validate.js +2934 -209
  300. package/src/stdlib-facades.js +1211 -0
  301. package/src/stdlib-negotiation.js +446 -0
  302. package/src/stdlib-providers.js +377 -0
  303. package/src/toolchains.js +16 -3
@@ -0,0 +1,685 @@
1
+ // @ts-check
2
+ import Parser from "tree-sitter";
3
+ import KotlinLanguage from "tree-sitter-kotlin";
4
+ import { isKotlinIdentifier } from "../backends/identifiers.js";
5
+ import { kotlinRuntime } from "../backends/kotlin-runtime.js";
6
+ import { missingType, SemantifoldDiagnostic, unsupportedSyntax } from "../diagnostic.js";
7
+ import { locationFromOffsets, moduleLocation, utf8ByteOffsetToUtf16Offset } from "../semantic/location.js";
8
+ import { withAdaptedOperation } from "../semantic/operators.js";
9
+ import { withParserRanges } from "../semantic/provenance.js";
10
+ import { hasOnlyUnicodeScalars } from "../semantic/scalars.js";
11
+ import { validateParsedModule } from "../semantic/validate.js";
12
+ import { sourceScalarType } from "./scalars.js";
13
+ const parser = new Parser();
14
+ parser.setLanguage(/** @type {import("tree-sitter").Language} */ ( /** @type {unknown} */(KotlinLanguage)));
15
+ const binaryOperations = new Map([
16
+ ["+", "Add"], ["-", "Subtract"], ["*", "Multiply"], ["==", "Equal"], ["!=", "NotEqual"],
17
+ ["<", "LessThan"], ["<=", "LessThanOrEqual"], [">", "GreaterThan"], [">=", "GreaterThanOrEqual"],
18
+ ["&&", "And"], ["||", "Or"]
19
+ ]);
20
+ const binaryNodeOperators = new Map([
21
+ ["additive_expression", new Set(["+", "-"])],
22
+ ["multiplicative_expression", new Set(["*"])],
23
+ ["equality_expression", new Set(["==", "!="])],
24
+ ["comparison_expression", new Set(["<", "<=", ">", ">="])],
25
+ ["conjunction_expression", new Set(["&&"])],
26
+ ["disjunction_expression", new Set(["||"])]
27
+ ]);
28
+ /** @type {Map<string, import("../semantic/operators.js").AdaptedOperation>} */
29
+ const helperOperations = new Map([
30
+ ["semantifold_integer_add", "Add"], ["semantifold_integer_subtract", "Subtract"],
31
+ ["semantifold_integer_multiply", "Multiply"], ["semantifold_integer_negate", "Negate"]
32
+ ]);
33
+ const commentTypes = new Set(["line_comment", "multiline_comment"]);
34
+ /**
35
+ * Verifies a Tree-sitter binding index through the shared byte converter.
36
+ * @param {string} source - Complete source.
37
+ * @param {number} index - Binding-reported UTF-16 index.
38
+ * @returns {number} Verified UTF-16 offset.
39
+ */
40
+ function bindingIndexToUtf16Offset(source, index) {
41
+ if (!Number.isInteger(index) || index < 0 || index > source.length ||
42
+ index > 0 && index < source.length && /[\uD800-\uDBFF]/u.test(source[index - 1]) && /[\uDC00-\uDFFF]/u.test(source[index])) {
43
+ throw new RangeError("Invalid Tree-sitter source index: " + index);
44
+ }
45
+ return utf8ByteOffsetToUtf16Offset(source, new TextEncoder().encode(source.slice(0, index)).length);
46
+ }
47
+ /**
48
+ * Finds an unpaired UTF-16 surrogate.
49
+ * @param {string} source - Complete source.
50
+ * @returns {number} Invalid offset or -1.
51
+ */
52
+ function firstLoneSurrogateOffset(source) {
53
+ for (let index = 0; index < source.length; index += 1) {
54
+ const unit = source.charCodeAt(index);
55
+ if (unit >= 0xD800 && unit <= 0xDBFF) {
56
+ const next = source.charCodeAt(index + 1);
57
+ if (next >= 0xDC00 && next <= 0xDFFF)
58
+ index += 1;
59
+ else
60
+ return index;
61
+ }
62
+ else if (unit >= 0xDC00 && unit <= 0xDFFF)
63
+ return index;
64
+ }
65
+ return -1;
66
+ }
67
+ /** Consumes exact qualified Kotlin CST shapes without retaining parser handles. */
68
+ class KotlinReader {
69
+ /**
70
+ * Creates a reader over one parser-owned Kotlin source.
71
+ * @param {string} filename - Original filename.
72
+ * @param {string} source - Complete source.
73
+ */
74
+ constructor(filename, source) {
75
+ this.filename = filename;
76
+ this.source = source;
77
+ this.runtime = false;
78
+ }
79
+ /**
80
+ * Converts one parser range to Semantifold UTF-16 coordinates.
81
+ * @param {import("tree-sitter").SyntaxNode} node - Parser node.
82
+ * @returns {import("../semantic/types.js").SourceLocation} Exact location.
83
+ */
84
+ location(node) {
85
+ return locationFromOffsets(this.filename, this.source, bindingIndexToUtf16Offset(this.source, node.startIndex), bindingIndexToUtf16Offset(this.source, node.endIndex));
86
+ }
87
+ /**
88
+ * Rejects one located source-profile violation.
89
+ * @param {import("tree-sitter").SyntaxNode} node - Violating node.
90
+ * @param {string} [detail] - Profile detail.
91
+ * @returns {never} Always throws.
92
+ */
93
+ fail(node, detail = node.type) {
94
+ unsupportedSyntax("kotlin", detail, this.location(node));
95
+ }
96
+ /**
97
+ * Traverses every named, anonymous, extra, directive, and recovery node.
98
+ * @param {import("tree-sitter").SyntaxNode} root - Complete parser root.
99
+ * @returns {void}
100
+ */
101
+ validateTree(root) {
102
+ const pending = [{ depth: 0, node: root, visited: false }];
103
+ while (pending.length) {
104
+ const current = pending.pop();
105
+ if (!current)
106
+ throw new Error("Kotlin traversal lost a pending parser node.");
107
+ const { depth, node, visited } = current;
108
+ if (depth > 512)
109
+ this.fail(node, "CST exceeds the 512-level traversal limit");
110
+ if (!visited) {
111
+ pending.push({ depth, node, visited: true });
112
+ for (let index = node.childCount - 1; index >= 0; index -= 1) {
113
+ const child = node.child(index);
114
+ if (!child)
115
+ throw new Error(`Tree-sitter omitted child ${index} of ${node.type}.`);
116
+ pending.push({ depth: depth + 1, node: child, visited: false });
117
+ }
118
+ continue;
119
+ }
120
+ if (node.hasError || node.isError || node.isMissing) {
121
+ throw new SemantifoldDiagnostic({
122
+ code: "PARSE_ERROR",
123
+ language: "kotlin",
124
+ location: this.location(node),
125
+ message: `Tree-sitter exposed recovery at '${node.type}'.`
126
+ });
127
+ }
128
+ if (["annotation", "file_annotation", "shebang_line"].includes(node.type))
129
+ this.fail(node, node.type);
130
+ if (commentTypes.has(node.type) && /(?:language|api|jvm)[-_ ]version/iu.test(node.text)) {
131
+ this.fail(node, "directive-bearing comment");
132
+ }
133
+ }
134
+ }
135
+ /**
136
+ * Omits only inert comments already accounted for by exhaustive traversal.
137
+ * @param {import("tree-sitter").SyntaxNode} node - Parent node.
138
+ * @returns {import("tree-sitter").SyntaxNode[]} Structural children.
139
+ */
140
+ parts(node) {
141
+ return node.children.filter((child) => !commentTypes.has(child.type));
142
+ }
143
+ /**
144
+ * Requires all ordered children, including anonymous punctuation.
145
+ * @param {import("tree-sitter").SyntaxNode} node - Shape owner.
146
+ * @param {(import("tree-sitter").SyntaxNode | string)[]} expected - Exact child sequence.
147
+ * @returns {void}
148
+ */
149
+ shape(node, expected) {
150
+ const actual = this.parts(node);
151
+ if (actual.length != expected.length)
152
+ this.fail(actual[Math.min(actual.length, expected.length)] ?? node, `${node.type} child shape`);
153
+ for (let index = 0; index < expected.length; index += 1) {
154
+ const wanted = expected[index];
155
+ const child = actual[index];
156
+ const matches = typeof wanted == "string" ? child.text == wanted : child.id == wanted.id;
157
+ if (!matches)
158
+ this.fail(child, `${node.type} child shape`);
159
+ }
160
+ }
161
+ /**
162
+ * Requires one exact parser field edge.
163
+ * @param {import("tree-sitter").SyntaxNode} node - Field owner.
164
+ * @param {string} name - Field name.
165
+ * @returns {import("tree-sitter").SyntaxNode} Sole field node.
166
+ */
167
+ field(node, name) {
168
+ const matches = [];
169
+ for (let index = 0; index < node.childCount; index += 1) {
170
+ const child = node.child(index);
171
+ if (!child)
172
+ throw new Error(`Tree-sitter omitted child ${index} of ${node.type}.`);
173
+ if (node.fieldNameForChild(index) == name)
174
+ matches.push(child);
175
+ }
176
+ if (matches.length != 1)
177
+ this.fail(node, `expected one '${name}' field`);
178
+ return matches[0];
179
+ }
180
+ /**
181
+ * Validates one Kotlin identifier in the portable source profile.
182
+ * @param {import("tree-sitter").SyntaxNode} node - Identifier token.
183
+ * @param {boolean} [allowMain] - Whether the fixed main scaffold is expected.
184
+ * @param {boolean} [allowPrint] - Whether the fixed print scaffold is expected.
185
+ * @returns {string} Accepted spelling.
186
+ */
187
+ identifier(node, allowMain = false, allowPrint = false) {
188
+ const name = node.text;
189
+ if (node.type != "simple_identifier" || !(allowMain && name == "main") && !(allowPrint && name == "println") &&
190
+ (!isKotlinIdentifier(name) || name.normalize("NFC") != name))
191
+ this.fail(node, "reserved or unsupported identifier");
192
+ return name;
193
+ }
194
+ /**
195
+ * Converts exactly Long, Boolean, or String.
196
+ * @param {import("tree-sitter").SyntaxNode} node - Type node.
197
+ * @returns {import("../semantic/types.js").TypeReference} Semantic scalar.
198
+ */
199
+ type(node) {
200
+ const parts = this.parts(node);
201
+ if (node.type != "user_type" || parts.length != 1 || parts[0].type != "type_identifier")
202
+ this.fail(node, "scalar type shape");
203
+ this.shape(node, [parts[0]]);
204
+ const type = sourceScalarType("kotlin", parts[0].text, this.location(parts[0]));
205
+ if (!type)
206
+ this.fail(parts[0], `unsupported scalar type '${parts[0].text}'`);
207
+ return type;
208
+ }
209
+ /**
210
+ * Decodes an ordinary noninterpolated Kotlin string.
211
+ * @param {import("tree-sitter").SyntaxNode} node - String literal node.
212
+ * @returns {string} Decoded Unicode scalar string.
213
+ */
214
+ string(node) {
215
+ const parts = this.parts(node);
216
+ if (node.type != "string_literal" || parts.some((part) => part.type != "string_content") ||
217
+ !node.text.startsWith('"') || !node.text.endsWith('"'))
218
+ this.fail(node, "ordinary noninterpolated string literal required");
219
+ this.shape(node, parts);
220
+ let value = "";
221
+ const simpleEscapes = new Map([
222
+ ["t", "\t"], ["b", "\b"], ["n", "\n"], ["r", "\r"], ["'", "'"], ['"', '"'], ["\\", "\\"], ["$", "$"]
223
+ ]);
224
+ for (let index = 1; index < node.text.length - 1; index += 1) {
225
+ const character = node.text[index];
226
+ if (character != "\\") {
227
+ if (character == "\n" || character == "\r" || character == '"')
228
+ this.fail(node, "invalid string content");
229
+ value += character;
230
+ continue;
231
+ }
232
+ const escaped = node.text[++index];
233
+ if (simpleEscapes.has(escaped))
234
+ value += simpleEscapes.get(escaped);
235
+ else if (escaped == "u") {
236
+ const hexadecimal = node.text.slice(index + 1, index + 5);
237
+ if (!/^[0-9A-Fa-f]{4}$/u.test(hexadecimal))
238
+ this.fail(node, "unsupported string escape");
239
+ value += String.fromCharCode(Number.parseInt(hexadecimal, 16));
240
+ index += 4;
241
+ }
242
+ else
243
+ this.fail(node, "unsupported string escape");
244
+ }
245
+ if (!hasOnlyUnicodeScalars(value))
246
+ this.fail(node, "invalid Unicode string literal");
247
+ return value;
248
+ }
249
+ /**
250
+ * Extracts exact unnamed call arguments.
251
+ * @param {import("tree-sitter").SyntaxNode} suffix - Call suffix node.
252
+ * @returns {import("tree-sitter").SyntaxNode[]} Argument expression nodes.
253
+ */
254
+ arguments(suffix) {
255
+ const suffixParts = this.parts(suffix);
256
+ if (suffix.type != "call_suffix" || suffixParts.length != 1 || suffixParts[0].type != "value_arguments") {
257
+ return this.fail(suffix, "call suffix shape");
258
+ }
259
+ this.shape(suffix, [suffixParts[0]]);
260
+ const list = suffixParts[0];
261
+ const parts = this.parts(list);
262
+ if (parts.length < 2 || parts[0].text != "(" || parts.at(-1)?.text != ")")
263
+ this.fail(list, "call argument list shape");
264
+ const arguments_ = parts.slice(1, -1).filter((_part, index) => index % 2 == 0);
265
+ this.shape(list, ["(", ...arguments_.flatMap((argument, index) => index ? [",", argument] : [argument]), ")"]);
266
+ return arguments_.map((argument) => {
267
+ const argumentParts = this.parts(argument);
268
+ if (argument.type != "value_argument" || argumentParts.length != 1)
269
+ this.fail(argument, "unnamed argument required");
270
+ this.shape(argument, [argumentParts[0]]);
271
+ return argumentParts[0];
272
+ });
273
+ }
274
+ /**
275
+ * Converts a direct semantic or generated-helper call.
276
+ * @param {import("tree-sitter").SyntaxNode} node - Call expression node.
277
+ * @returns {import("../semantic/types.js").Expression} Semantic expression.
278
+ */
279
+ call(node) {
280
+ const parts = this.parts(node);
281
+ if (node.type != "call_expression" || parts.length != 2 || parts[0].type != "simple_identifier")
282
+ this.fail(node, "direct call shape");
283
+ this.shape(node, [parts[0], parts[1]]);
284
+ const argumentNodes = this.arguments(parts[1]);
285
+ const name = parts[0].text;
286
+ const helper = this.runtime ? helperOperations.get(name) : undefined;
287
+ const location = this.location(node);
288
+ if (helper) {
289
+ const count = helper == "Negate" ? 1 : 2;
290
+ if (argumentNodes.length != count)
291
+ this.fail(node, "Kotlin checked-integer helper shape");
292
+ if (helper == "Negate") {
293
+ return /** @type {import("../semantic/types.js").Expression} */ ( /** @type {unknown} */(withAdaptedOperation(withParserRanges({
294
+ kind: /** @type {const} */ ("UnaryExpression"), location, operand: this.expression(argumentNodes[0])
295
+ }, { operator: this.location(parts[0]) }), helper)));
296
+ }
297
+ return /** @type {import("../semantic/types.js").Expression} */ (withAdaptedOperation(withParserRanges({
298
+ kind: /** @type {const} */ ("BinaryExpression"), left: this.expression(argumentNodes[0]), location, right: this.expression(argumentNodes[1])
299
+ }, { operator: this.location(parts[0]) }), helper));
300
+ }
301
+ const semanticName = this.identifier(parts[0]);
302
+ if (argumentNodes.length != 2)
303
+ this.fail(parts[1], "semantic call argument count");
304
+ return withParserRanges({
305
+ arguments: argumentNodes.map((argument) => this.expression(argument)), callee: semanticName,
306
+ kind: /** @type {const} */ ("CallExpression"), location
307
+ }, { callee: this.location(parts[0]) });
308
+ }
309
+ /**
310
+ * Converts one supported scalar expression.
311
+ * @param {import("tree-sitter").SyntaxNode} node - Expression node.
312
+ * @returns {import("../semantic/types.js").Expression} Semantic expression.
313
+ */
314
+ expression(node) {
315
+ const location = this.location(node);
316
+ if (node.type == "simple_identifier") {
317
+ return withParserRanges({ kind: /** @type {const} */ ("IdentifierExpression"), location, name: this.identifier(node) }, { name: location });
318
+ }
319
+ if (node.type == "integer_literal" || node.type == "long_literal") {
320
+ const literal = node.type == "long_literal" ? this.parts(node)[0] : node;
321
+ if (node.type == "long_literal")
322
+ this.shape(node, [literal, "L"]);
323
+ if (!literal || literal.type != "integer_literal" || !/^(?:0|[1-9][0-9]*)$/u.test(literal.text) ||
324
+ node.type == "long_literal" && !/L$/u.test(node.text))
325
+ this.fail(node, "noncanonical integer literal");
326
+ const value = Number(BigInt(literal.text));
327
+ if (!Number.isSafeInteger(value))
328
+ this.fail(node, "non-safe integer literal");
329
+ return withParserRanges({ kind: /** @type {const} */ ("IntegerLiteral"), location, value }, { literal: location });
330
+ }
331
+ if (node.type == "boolean_literal") {
332
+ const parts = this.parts(node);
333
+ if (parts.length != 1 || !["true", "false"].includes(parts[0].text))
334
+ this.fail(node, "Boolean literal shape");
335
+ this.shape(node, [parts[0].text]);
336
+ return withParserRanges({ kind: /** @type {const} */ ("BooleanLiteral"), location, value: parts[0].text == "true" }, { literal: location });
337
+ }
338
+ if (node.type == "string_literal") {
339
+ return withParserRanges({ kind: /** @type {const} */ ("StringLiteral"), location, value: this.string(node) }, { literal: location });
340
+ }
341
+ if (node.type == "parenthesized_expression") {
342
+ const parts = this.parts(node);
343
+ if (parts.length != 3)
344
+ this.fail(node, "parenthesized expression shape");
345
+ this.shape(node, ["(", parts[1], ")"]);
346
+ return this.expression(parts[1]);
347
+ }
348
+ if (node.type == "prefix_expression") {
349
+ const parts = this.parts(node);
350
+ if (parts.length != 2 || !["-", "!"].includes(parts[0].text))
351
+ this.fail(node, "unary operator");
352
+ this.shape(node, [parts[0].text, parts[1]]);
353
+ return /** @type {import("../semantic/types.js").Expression} */ ( /** @type {unknown} */(withAdaptedOperation(withParserRanges({
354
+ kind: /** @type {const} */ ("UnaryExpression"), location, operand: this.expression(parts[1])
355
+ }, { operator: this.location(parts[0]) }), parts[0].text == "-" ? "Negate" : "Not")));
356
+ }
357
+ if (binaryNodeOperators.has(node.type))
358
+ return this.binary(node);
359
+ if (node.type == "call_expression")
360
+ return this.call(node);
361
+ return this.fail(node);
362
+ }
363
+ /**
364
+ * Converts one binary expression.
365
+ * @param {import("tree-sitter").SyntaxNode} node - Binary expression node.
366
+ * @returns {import("../semantic/types.js").Expression} Semantic expression.
367
+ */
368
+ binary(node) {
369
+ const parts = this.parts(node);
370
+ const accepted = binaryNodeOperators.get(node.type);
371
+ if (parts.length != 3)
372
+ this.fail(node, `${node.type} child shape`);
373
+ this.shape(node, [parts[0], parts[1], parts[2]]);
374
+ const operation = binaryOperations.get(parts[1].text);
375
+ if (!accepted?.has(parts[1].text) || !operation)
376
+ this.fail(parts[1], "unsupported binary operator");
377
+ return /** @type {import("../semantic/types.js").Expression} */ (withAdaptedOperation(withParserRanges({
378
+ kind: /** @type {const} */ ("BinaryExpression"), left: this.expression(parts[0]), location: this.location(node), right: this.expression(parts[2])
379
+ }, { operator: this.location(parts[1]) }), /** @type {import("../semantic/operators.js").AdaptedOperation} */ (operation)));
380
+ }
381
+ /**
382
+ * Converts one explicitly typed local declaration.
383
+ * @param {import("tree-sitter").SyntaxNode} node - Property declaration node.
384
+ * @returns {import("../semantic/types.js").LocalDeclaration} Semantic declaration.
385
+ */
386
+ local(node) {
387
+ const parts = this.parts(node);
388
+ const location = this.location(node);
389
+ if (node.type != "property_declaration" || parts.length != 4 || parts[0].type != "binding_pattern_kind" ||
390
+ parts[1].type != "variable_declaration" || parts[2].text != "=")
391
+ this.fail(node, "local declaration shape");
392
+ const bindingParts = this.parts(parts[0]);
393
+ const variableParts = this.parts(parts[1]);
394
+ if (bindingParts.length != 1 || !["val", "var"].includes(bindingParts[0].text))
395
+ this.fail(parts[0], "local binding kind");
396
+ if (variableParts.length == 1)
397
+ return missingType("kotlin", "Local", location);
398
+ if (variableParts.length != 3 || variableParts[0].type != "simple_identifier" || variableParts[1].text != ":") {
399
+ this.fail(parts[1], "local declaration shape");
400
+ }
401
+ this.shape(parts[0], [bindingParts[0].text]);
402
+ this.shape(parts[1], [variableParts[0], ":", variableParts[2]]);
403
+ this.shape(node, [parts[0], parts[1], "=", parts[3]]);
404
+ const name = this.identifier(variableParts[0]);
405
+ return withParserRanges({
406
+ initializer: this.expression(parts[3]), kind: /** @type {const} */ ("LocalDeclaration"), location,
407
+ mutable: bindingParts[0].text == "var", name, type: this.type(variableParts[2])
408
+ }, { name: this.location(variableParts[0]), operator: this.location(parts[2]) });
409
+ }
410
+ /**
411
+ * Converts one plain local assignment.
412
+ * @param {import("tree-sitter").SyntaxNode} node - Assignment node.
413
+ * @returns {import("../semantic/types.js").AssignmentStatement} Semantic assignment.
414
+ */
415
+ assignment(node) {
416
+ const parts = this.parts(node);
417
+ if (node.type != "assignment" || parts.length != 3 || parts[0].type != "directly_assignable_expression" || parts[1].text != "=") {
418
+ this.fail(node, "assignment shape");
419
+ }
420
+ const targetParts = this.parts(parts[0]);
421
+ if (targetParts.length != 1 || targetParts[0].type != "simple_identifier")
422
+ this.fail(parts[0], "assignment target shape");
423
+ this.shape(parts[0], [targetParts[0]]);
424
+ this.shape(node, [parts[0], "=", parts[2]]);
425
+ const name = this.identifier(targetParts[0]);
426
+ const targetLocation = this.location(targetParts[0]);
427
+ return withParserRanges({
428
+ expression: this.expression(parts[2]), kind: /** @type {const} */ ("AssignmentStatement"), location: this.location(node),
429
+ target: withParserRanges({ kind: /** @type {const} */ ("IdentifierExpression"), location: targetLocation, name }, { name: targetLocation })
430
+ }, { operator: this.location(parts[1]) });
431
+ }
432
+ /**
433
+ * Converts the exact println entry scaffold.
434
+ * @param {import("tree-sitter").SyntaxNode} node - Call node.
435
+ * @returns {import("../semantic/types.js").PrintStatement} Semantic print.
436
+ */
437
+ print(node) {
438
+ const parts = this.parts(node);
439
+ if (node.type != "call_expression" || parts.length != 2 || parts[0].type != "simple_identifier" ||
440
+ this.identifier(parts[0], false, true) != "println")
441
+ this.fail(node, "exact println call required");
442
+ const arguments_ = this.arguments(parts[1]);
443
+ if (arguments_.length != 1)
444
+ this.fail(parts[1], "println argument count");
445
+ return { expression: this.expression(arguments_[0]), kind: /** @type {const} */ ("PrintStatement"), location: this.location(node) };
446
+ }
447
+ /**
448
+ * Converts one supported statement.
449
+ * @param {import("tree-sitter").SyntaxNode} node - Statement node.
450
+ * @returns {import("../semantic/types.js").Statement} Semantic statement.
451
+ */
452
+ statement(node) {
453
+ if (node.type == "property_declaration")
454
+ return this.local(node);
455
+ if (node.type == "assignment")
456
+ return this.assignment(node);
457
+ if (node.type == "if_expression")
458
+ return this.conditional(node);
459
+ if (node.type == "call_expression")
460
+ return this.print(node);
461
+ if (node.type == "jump_expression") {
462
+ const parts = this.parts(node);
463
+ if (parts.length != 2 || parts[0].text != "return")
464
+ this.fail(node, "return expression shape");
465
+ this.shape(node, ["return", parts[1]]);
466
+ return { expression: this.expression(parts[1]), kind: /** @type {const} */ ("ReturnStatement"), location: this.location(node) };
467
+ }
468
+ return this.fail(node);
469
+ }
470
+ /**
471
+ * Converts an optional parser statement list.
472
+ * @param {import("tree-sitter").SyntaxNode | undefined} node - Statement-list node.
473
+ * @returns {import("../semantic/types.js").Statement[]} Semantic statements.
474
+ */
475
+ statements(node) {
476
+ if (!node)
477
+ return [];
478
+ if (node.type != "statements")
479
+ this.fail(node, "statement list shape");
480
+ return this.parts(node).map((statement) => this.statement(statement));
481
+ }
482
+ /**
483
+ * Converts one braced conditional body.
484
+ * @param {import("tree-sitter").SyntaxNode} node - Control body node.
485
+ * @returns {import("../semantic/types.js").Block} Semantic block.
486
+ */
487
+ controlBody(node) {
488
+ const parts = this.parts(node);
489
+ const statements = parts[1]?.type == "statements" ? parts[1] : undefined;
490
+ if (node.type != "control_structure_body")
491
+ this.fail(node, "conditional block shape");
492
+ this.shape(node, ["{", ...(statements ? [statements] : []), "}"]);
493
+ return { kind: /** @type {const} */ ("Block"), location: this.location(node), statements: this.statements(statements) };
494
+ }
495
+ /**
496
+ * Converts one strict Boolean conditional.
497
+ * @param {import("tree-sitter").SyntaxNode} node - If expression node.
498
+ * @returns {import("../semantic/types.js").IfStatement} Semantic conditional.
499
+ */
500
+ conditional(node) {
501
+ const parts = this.parts(node);
502
+ const condition = this.field(node, "condition");
503
+ const consequence = this.field(node, "consequence");
504
+ const base = ["if", "(", condition, ")", consequence];
505
+ if (node.type != "if_expression" || consequence.type != "control_structure_body")
506
+ this.fail(node, "if expression shape");
507
+ const statement = /** @type {import("../semantic/types.js").IfStatement} */ ({
508
+ condition: this.expression(condition), consequent: this.controlBody(consequence), kind: /** @type {const} */ ("IfStatement"),
509
+ location: this.location(node)
510
+ });
511
+ if (parts.length == base.length) {
512
+ this.shape(node, base);
513
+ return statement;
514
+ }
515
+ const alternative = this.field(node, "alternative");
516
+ this.shape(node, [...base, "else", alternative]);
517
+ if (alternative.type != "control_structure_body")
518
+ this.fail(alternative, "if alternate shape");
519
+ const alternativeParts = this.parts(alternative);
520
+ if (alternativeParts.length == 1 && alternativeParts[0].type == "if_expression") {
521
+ this.shape(alternative, [alternativeParts[0]]);
522
+ return { ...statement, alternate: { kind: /** @type {const} */ ("Block"), location: this.location(alternative),
523
+ statements: [this.conditional(alternativeParts[0])] } };
524
+ }
525
+ return { ...statement, alternate: this.controlBody(alternative) };
526
+ }
527
+ /**
528
+ * Converts one exact braced block.
529
+ * @param {import("tree-sitter").SyntaxNode} node - Block node.
530
+ * @param {"function_body" | "control_structure_body"} type - Required parser node type.
531
+ * @returns {import("../semantic/types.js").Block} Semantic block.
532
+ */
533
+ block(node, type = "function_body") {
534
+ const parts = this.parts(node);
535
+ const statements = parts[1]?.type == "statements" ? parts[1] : undefined;
536
+ if (node.type != type)
537
+ this.fail(node, `${type} shape`);
538
+ this.shape(node, ["{", ...(statements ? [statements] : []), "}"]);
539
+ return { kind: /** @type {const} */ ("Block"), location: this.location(node), statements: this.statements(statements) };
540
+ }
541
+ /**
542
+ * Converts one explicitly typed parameter.
543
+ * @param {import("tree-sitter").SyntaxNode} node - Parameter node.
544
+ * @returns {import("../semantic/types.js").Parameter} Semantic parameter.
545
+ */
546
+ parameter(node) {
547
+ const parts = this.parts(node);
548
+ if (node.type != "parameter" || parts.length != 3 || parts[0].type != "simple_identifier" || parts[1].text != ":") {
549
+ this.fail(node, "parameter shape");
550
+ }
551
+ this.shape(node, [parts[0], ":", parts[2]]);
552
+ const name = this.identifier(parts[0]);
553
+ return withParserRanges({ kind: /** @type {const} */ ("Parameter"), location: this.location(node), name, type: this.type(parts[2]) }, {
554
+ name: this.location(parts[0])
555
+ });
556
+ }
557
+ /**
558
+ * Converts one supported top-level function.
559
+ * @param {import("tree-sitter").SyntaxNode} node - Function declaration node.
560
+ * @returns {import("../semantic/types.js").FunctionDeclaration} Semantic function.
561
+ */
562
+ function(node) {
563
+ const parts = this.parts(node);
564
+ if (node.type != "function_declaration" || parts.length < 4 || parts[0].text != "fun" || parts[1].type != "simple_identifier" ||
565
+ parts[2].type != "function_value_parameters" || parts.at(-1)?.type != "function_body")
566
+ this.fail(node, "function declaration shape");
567
+ if (!parts.some((part) => part.text == ":"))
568
+ return missingType("kotlin", "Function return", this.location(node));
569
+ if (parts.length != 6 || parts[3].text != ":")
570
+ this.fail(node, "function declaration shape");
571
+ this.shape(node, ["fun", parts[1], parts[2], ":", parts[4], parts[5]]);
572
+ const parameterParts = this.parts(parts[2]);
573
+ const parameters = parameterParts.filter((part) => part.type == "parameter");
574
+ if (parameters.length != 2)
575
+ this.fail(parts[2], "function parameter count other than two");
576
+ this.shape(parts[2], ["(", parameters[0], ",", parameters[1], ")"]);
577
+ const name = this.identifier(parts[1]);
578
+ return withParserRanges({
579
+ body: this.block(parts[5]), kind: /** @type {const} */ ("FunctionDeclaration"), location: this.location(node), name,
580
+ parameters: parameters.map((parameter) => this.parameter(parameter)), returnType: this.type(parts[4])
581
+ }, { name: this.location(parts[1]) });
582
+ }
583
+ /**
584
+ * Converts the exact final main function.
585
+ * @param {import("tree-sitter").SyntaxNode} node - Main declaration node.
586
+ * @returns {import("../semantic/types.js").EntryPoint} Semantic entry point.
587
+ */
588
+ main(node) {
589
+ const parts = this.parts(node);
590
+ if (node.type != "function_declaration" || parts.length != 4 || parts[0].text != "fun" ||
591
+ this.identifier(parts[1], true) != "main" || parts[2].type != "function_value_parameters" || parts[3].type != "function_body") {
592
+ this.fail(node, "exact main declaration required");
593
+ }
594
+ this.shape(parts[2], ["(", ")"]);
595
+ this.shape(node, ["fun", parts[1], parts[2], parts[3]]);
596
+ return { body: this.block(parts[3]), kind: /** @type {const} */ ("EntryPoint"), location: this.location(node) };
597
+ }
598
+ /**
599
+ * Compares source support with the canonical generated helper CST.
600
+ * @param {import("tree-sitter").SyntaxNode} actual - Source node.
601
+ * @param {import("tree-sitter").SyntaxNode} expected - Canonical support node.
602
+ * @returns {void}
603
+ */
604
+ compareTree(actual, expected) {
605
+ if (actual.type != expected.type || actual.isNamed != expected.isNamed || actual.isExtra != expected.isExtra ||
606
+ actual.childCount != expected.childCount)
607
+ this.fail(actual, "modified Kotlin support node");
608
+ if (!actual.childCount && actual.text != expected.text)
609
+ this.fail(actual, "modified Kotlin support token");
610
+ for (let index = 0; index < actual.childCount; index += 1) {
611
+ const left = actual.child(index);
612
+ const right = expected.child(index);
613
+ if (!left || !right || actual.fieldNameForChild(index) != expected.fieldNameForChild(index)) {
614
+ this.fail(left ?? actual, "modified Kotlin support field");
615
+ }
616
+ this.compareTree(left, right);
617
+ }
618
+ }
619
+ /**
620
+ * Converts and validates one complete Kotlin source file.
621
+ * @param {import("tree-sitter").SyntaxNode} root - Source file root.
622
+ * @returns {import("../semantic/types.js").SemanticModule} Semantic module.
623
+ */
624
+ module(root) {
625
+ this.validateTree(root);
626
+ if (root.type != "source_file")
627
+ this.fail(root, "source file root");
628
+ const parts = this.parts(root);
629
+ const supportTree = parser.parse(kotlinRuntime);
630
+ const support = this.parts(supportTree.rootNode);
631
+ let supportIndex = 0;
632
+ while (supportIndex < parts.length && supportIndex < support.length && parts[supportIndex].type == support[supportIndex].type) {
633
+ this.compareTree(parts[supportIndex], support[supportIndex]);
634
+ supportIndex += 1;
635
+ }
636
+ if (supportIndex > 0 && supportIndex != support.length)
637
+ this.fail(parts[supportIndex - 1], "complete Kotlin support required");
638
+ this.runtime = supportIndex == support.length;
639
+ const semanticParts = parts.slice(supportIndex);
640
+ const mainIndex = semanticParts.findIndex((node) => node.type == "function_declaration" && this.parts(node)[1]?.text == "main");
641
+ if (mainIndex < 0)
642
+ this.fail(root, "source file without main");
643
+ if (mainIndex == 0)
644
+ this.fail(semanticParts[0], "top-level semantic function required");
645
+ if (mainIndex != semanticParts.length - 1)
646
+ this.fail(semanticParts[mainIndex + 1], "declaration after main");
647
+ const declarations = semanticParts.slice(0, mainIndex);
648
+ for (const declaration of declarations) {
649
+ if (declaration.type != "function_declaration")
650
+ this.fail(declaration);
651
+ }
652
+ const module = {
653
+ entryPoint: this.main(semanticParts[mainIndex]), functions: declarations.map((declaration) => this.function(declaration)),
654
+ kind: /** @type {const} */ ("Module"), location: this.location(root)
655
+ };
656
+ validateParsedModule(module, "kotlin");
657
+ return module;
658
+ }
659
+ }
660
+ /**
661
+ * Parses the strict Task 023 Kotlin/JVM profile through the qualified grammar.
662
+ * @param {{filename: string, source: string}} input - Exact source request.
663
+ * @returns {import("../semantic/types.js").SemanticModule} Semantic module.
664
+ */
665
+ export function parseKotlin({ filename, source }) {
666
+ if (!hasOnlyUnicodeScalars(source)) {
667
+ const offset = firstLoneSurrogateOffset(source);
668
+ throw new SemantifoldDiagnostic({
669
+ code: "PARSE_ERROR", language: "kotlin", location: locationFromOffsets(filename, source, offset, offset + 1),
670
+ message: "Kotlin source contains an invalid lone UTF-16 surrogate."
671
+ });
672
+ }
673
+ let tree;
674
+ try {
675
+ tree = parser.parse(source);
676
+ }
677
+ catch (error) {
678
+ throw new SemantifoldDiagnostic({
679
+ cause: error instanceof Error ? error : undefined, code: "PARSE_ERROR", language: "kotlin",
680
+ location: moduleLocation(filename, source), message: "The qualified Kotlin parser could not produce a complete CST."
681
+ });
682
+ }
683
+ return new KotlinReader(filename, source).module(tree.rootNode);
684
+ }
685
+ //# sourceMappingURL=data:application/json;base64,eyJ2ZXJzaW9uIjozLCJmaWxlIjoia290bGluLmpzIiwic291cmNlUm9vdCI6IiIsInNvdXJjZXMiOlsiLi4vLi4vLi4vc3JjL2Zyb250ZW5kcy9rb3RsaW4uanMiXSwibmFtZXMiOltdLCJtYXBwaW5ncyI6IkFBQUEsWUFBWTtBQUVaLE9BQU8sTUFBTSxNQUFNLGFBQWEsQ0FBQTtBQUNoQyxPQUFPLGNBQWMsTUFBTSxvQkFBb0IsQ0FBQTtBQUMvQyxPQUFPLEVBQUMsa0JBQWtCLEVBQUMsTUFBTSw0QkFBNEIsQ0FBQTtBQUM3RCxPQUFPLEVBQUMsYUFBYSxFQUFDLE1BQU0sK0JBQStCLENBQUE7QUFDM0QsT0FBTyxFQUFDLFdBQVcsRUFBRSxxQkFBcUIsRUFBRSxpQkFBaUIsRUFBQyxNQUFNLGtCQUFrQixDQUFBO0FBQ3RGLE9BQU8sRUFBQyxtQkFBbUIsRUFBRSxjQUFjLEVBQUUsMkJBQTJCLEVBQUMsTUFBTSx5QkFBeUIsQ0FBQTtBQUN4RyxPQUFPLEVBQUMsb0JBQW9CLEVBQUMsTUFBTSwwQkFBMEIsQ0FBQTtBQUM3RCxPQUFPLEVBQUMsZ0JBQWdCLEVBQUMsTUFBTSwyQkFBMkIsQ0FBQTtBQUMxRCxPQUFPLEVBQUMscUJBQXFCLEVBQUMsTUFBTSx3QkFBd0IsQ0FBQTtBQUM1RCxPQUFPLEVBQUMsb0JBQW9CLEVBQUMsTUFBTSx5QkFBeUIsQ0FBQTtBQUM1RCxPQUFPLEVBQUMsZ0JBQWdCLEVBQUMsTUFBTSxjQUFjLENBQUE7QUFFN0MsTUFBTSxNQUFNLEdBQUcsSUFBSSxNQUFNLEVBQUUsQ0FBQTtBQUUzQixNQUFNLENBQUMsV0FBVyxDQUFDLDZDQUE2QyxDQUFDLEVBQUMsc0JBQXVCLENBQUMsY0FBYyxDQUFDLENBQUMsQ0FBQyxDQUFBO0FBRTNHLE1BQU0sZ0JBQWdCLEdBQUcsSUFBSSxHQUFHLENBQUM7SUFDL0IsQ0FBQyxHQUFHLEVBQUUsS0FBSyxDQUFDLEVBQUUsQ0FBQyxHQUFHLEVBQUUsVUFBVSxDQUFDLEVBQUUsQ0FBQyxHQUFHLEVBQUUsVUFBVSxDQUFDLEVBQUUsQ0FBQyxJQUFJ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LElBQUksSUFBSSxlQUFlO1lBQUUsSUFBSSxDQUFDLElBQUksQ0FBQyxJQUFJLEVBQUUsNEJBQTRCLENBQUMsQ0FBQTtRQUN0SSxJQUFJLENBQUMsS0FBSyxDQUFDLElBQUksQ0FBQyxDQUFDLElBQUksRUFBRSxFQUFFLENBQUMsSUFBSSxDQUFDLElBQUksSUFBSSxHQUFHLENBQUM7WUFBRSxPQUFPLFdBQVcsQ0FBQyxRQUFRLEVBQUUsaUJBQWlCLEVBQUUsSUFBSSxDQUFDLFFBQVEsQ0FBQyxJQUFJLENBQUMsQ0FBQyxDQUFBO1FBQ2pILElBQUksS0FBSyxDQUFDLE1BQU0sSUFBSSxDQUFDLElBQUksS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLElBQUksSUFBSSxHQUFHO1lBQUUsSUFBSSxDQUFDLElBQUksQ0FBQyxJQUFJLEVBQUUsNEJBQTRCLENBQUMsQ0FBQTtRQUM1RixJQUFJLENBQUMsS0FBSyxDQUFDLElBQUksRUFBRSxDQUFDLEtBQUssRUFBRSxLQUFLLENBQUMsQ0FBQyxDQUFDLEVBQUUsS0FBSyxDQUFDLENBQUMsQ0FBQyxFQUFFLEdBQUcsRUFBRSxLQUFLLENBQUMsQ0FBQyxDQUFDLEVBQUUsS0FBSyxDQUFDLENBQUMsQ0FBQyxDQUFDLENBQUMsQ0FBQTtRQUN0RSxNQUFNLGNBQWMsR0FBRyxJQUFJLENBQUMsS0FBSyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsQ0FBQyxDQUFBO1FBQzNDLE1BQU0sVUFBVSxHQUFHLGNBQWMsQ0FBQyxNQUFNLENBQUMsQ0FBQyxJQUFJLEVBQUUsRUFBRSxDQUFDLElBQUksQ0FBQyxJQUFJLElBQUksV0FBVyxDQUFDLENBQUE7UUFFNUUsSUFBSSxVQUFVLENBQUMsTUFBTSxJQUFJLENBQUM7WUFBRSxJQUFJLENBQUMsSUFBSSxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsRUFBRSx5Q0FBeUMsQ0FBQyxDQUFBO1FBQzFGLElBQUksQ0FBQyxLQUFLLENBQUMsS0FBSyxDQUFDLENBQUMsQ0FBQyxFQUFFLENBQUMsR0FBRyxFQUFFLFVBQVUsQ0FBQyxDQUFD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QUFBO0lBQ0osQ0FBQztJQUNELElBQUksSUFBSSxDQUFBO0lBRVIsSUFBSSxDQUFDO1FBQ0gsSUFBSSxHQUFHLE1BQU0sQ0FBQyxLQUFLLENBQUMsTUFBTSxDQUFDLENBQUE7SUFDN0IsQ0FBQztJQUFDLE9BQU8sS0FBSyxFQUFFLENBQUM7UUFDZixNQUFNLElBQUkscUJBQXFCLENBQUM7WUFDOUIsS0FBSyxFQUFFLEtBQUssWUFBWSxLQUFLLENBQUMsQ0FBQyxDQUFDLEtBQUssQ0FBQyxDQUFDLENBQUMsU0FBUyxFQUFFLElBQUksRUFBRSxhQUFhLEVBQUUsUUFBUSxFQUFFLFFBQVE7WUFDMUYsUUFBUSxFQUFFLGNBQWMsQ0FBQyxRQUFRLEVBQUUsTUFBTSxDQUFDLEVBQUUsT0FBTyxFQUFFLCtEQUErRDtTQUNySCxDQUFDLENBQUE7SUFDSixDQUFDO0lBQ0QsT0FBTyxJQUFJLFlBQVksQ0FBQyxRQUFRLEVBQUUsTUFBTSxDQUFDLENBQUMsTUFBTSxDQUFDLElBQUksQ0FBQyxRQUFRLENBQUMsQ0FBQTtBQUNqRSxDQUFDIiwic291cmNlc0NvbnRlbnQiOlsiLy8gQHRzLWNoZWNrXG5cbmltcG9ydCBQYXJzZXIgZnJvbSBcInRyZWUtc2l0dGVyXCJcbmltcG9ydCBLb3RsaW5MYW5ndWFnZSBmcm9tIFwidHJlZS1zaXR0ZXIta290bGluXCJcbmltcG9ydCB7aXNLb3RsaW5JZGVudGlmaWVyfSBmcm9tIFwiLi4vYmFja2VuZHMvaWRlbnRpZmllcnMuanNcIlxuaW1wb3J0IHtrb3RsaW5SdW50aW1lfSBmcm9tIFwiLi4vYmFja2VuZHMva290bGluLXJ1bnRpbWUuanNcIlxuaW1wb3J0IHttaXNzaW5nVHlwZSwgU2VtYW50aWZvbGREaWFnbm9zdGljLCB1bnN1cHBvcnRlZFN5bnRheH0gZnJvbSBcIi4uL2RpYWdub3N0aWMuanNcIlxuaW1wb3J0IHtsb2NhdGlvbkZyb21PZmZzZXRzLCBtb2R1bGVMb2NhdGlvbiwgdXRmOEJ5dGVPZmZzZXRUb1V0ZjE2T2Zmc2V0fSBmcm9tIFwiLi4vc2VtYW50aWMvbG9jYXRpb24uanNcIlxuaW1wb3J0IHt3aXRoQWRhcHRlZE9wZXJhdGlvbn0gZnJvbSBcIi4uL3NlbWFudGljL29wZXJhdG9ycy5qc1wiXG5pbXBvcnQge3dpdGhQYXJzZXJSYW5nZXN9IGZyb20gXCIuLi9zZW1hbnRpYy9wcm92ZW5hbmNlLmpzXCJcbmltcG9ydCB7aGFzT25seVVuaWNvZGVTY2FsYXJzfSBmcm9tIFwiLi4vc2VtYW50aWMvc2NhbGFycy5qc1wiXG5pbXBvcnQge3ZhbGlkYXRlUGFyc2VkTW9kdWxlfSBmcm9tIFwiLi4vc2VtYW50aWMvdmFsaWRhdGUuanNcIlxuaW1wb3J0IHtzb3VyY2VTY2FsYXJUeXBlfSBmcm9tIFwiLi9zY2FsYXJzLmpzXCJcblxuY29uc3QgcGFyc2VyID0gbmV3IFBhcnNlcigpXG5cbnBhcnNlci5zZXRMYW5ndWFnZSgvKiogQHR5cGUge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLkxhbmd1YWdlfSAqLyAoLyoqIEB0eXBlIHt1bmtub3dufSAqLyAoS290bGluTGFuZ3VhZ2UpKSlcblxuY29uc3QgYmluYXJ5T3BlcmF0aW9ucyA9IG5ldyBNYXAoW1xuICBbXCIrXCIsIFwiQWRkXCJdLCBbXCItXCIsIFwiU3VidHJhY3RcIl0sIFtcIipcIiwgXCJNdWx0aXBseVwiXSwgW1wiPT1cIiwgXCJFcXVhbFwiXSwgW1wiIT1cIiwgXCJOb3RFcXVhbFwiXSxcbiAgW1wiPFwiLCBcIkxlc3NUaGFuXCJdLCBbXCI8PVwiLCBcIkxlc3NUaGFuT3JFcXVhbFwiXSwgW1wiPlwiLCBcIkdyZWF0ZXJUaGFuXCJdLCBbXCI+PVwiLCBcIkdyZWF0ZXJUaGFuT3JFcXVhbFwiXSxcbiAgW1wiJiZcIiwgXCJBbmRcIl0sIFtcInx8XCIsIFwiT3JcIl1cbl0pXG5jb25zdCBiaW5hcnlOb2RlT3BlcmF0b3JzID0gbmV3IE1hcChbXG4gIFtcImFkZGl0aXZlX2V4cHJlc3Npb25cIiwgbmV3IFNldChbXCIrXCIsIFwiLVwiXSldLFxuICBbXCJtdWx0aXBsaWNhdGl2ZV9leHByZXNzaW9uXCIsIG5ldyBTZXQoW1wiKlwiXSldLFxuICBbXCJlcXVhbGl0eV9leHByZXNzaW9uXCIsIG5ldyBTZXQoW1wiPT1cIiwgXCIhPVwiXSldLFxuICBbXCJjb21wYXJpc29uX2V4cHJlc3Npb25cIiwgbmV3IFNldChbXCI8XCIsIFwiPD1cIiwgXCI+XCIsIFwiPj1cIl0pXSxcbiAgW1wiY29uanVuY3Rpb25fZXhwcmVzc2lvblwiLCBuZXcgU2V0KFtcIiYmXCJdKV0sXG4gIFtcImRpc2p1bmN0aW9uX2V4cHJlc3Npb25cIiwgbmV3IFNldChbXCJ8fFwiXSldXG5dKVxuLyoqIEB0eXBlIHtNYXA8c3RyaW5nLCBpbXBvcnQoXCIuLi9zZW1hbnRpYy9vcGVyYXRvcnMuanNcIikuQWRhcHRlZE9wZXJhdGlvbj59ICovXG5jb25zdCBoZWxwZXJPcGVyYXRpb25zID0gbmV3IE1hcChbXG4gIFtcInNlbWFudGlmb2xkX2ludGVnZXJfYWRkXCIsIFwiQWRkXCJdLCBbXCJzZW1hbnRpZm9sZF9pbnRlZ2VyX3N1YnRyYWN0XCIsIFwiU3VidHJhY3RcIl0sXG4gIFtcInNlbWFudGlmb2xkX2ludGVnZXJfbXVsdGlwbHlcIiwgXCJNdWx0aXBseVwiXSwgW1wic2VtYW50aWZvbGRfaW50ZWdlcl9uZWdhdGVcIiwgXCJOZWdhdGVcIl1cbl0pXG5jb25zdCBjb21tZW50VHlwZXMgPSBuZXcgU2V0KFtcImxpbmVfY29tbWVudFwiLCBcIm11bHRpbGluZV9jb21tZW50XCJdKVxuXG4vKipcbiAqIFZlcmlmaWVzIGEgVHJlZS1zaXR0ZXIgYmluZGluZyBpbmRleCB0aHJvdWdoIHRoZSBzaGFyZWQgYnl0ZSBjb252ZXJ0ZXIuXG4gKiBAcGFyYW0ge3N0cmluZ30gc291cmNlIC0gQ29tcGxldGUgc291cmNlLlxuICogQHBhcmFtIHtudW1iZXJ9IGluZGV4IC0gQmluZGluZy1yZXBvcnRlZCBVVEYtMTYgaW5kZXguXG4gKiBAcmV0dXJucyB7bnVtYmVyfSBWZXJpZmllZCBVVEYtMTYgb2Zmc2V0LlxuICovXG5mdW5jdGlvbiBiaW5kaW5nSW5kZXhUb1V0ZjE2T2Zmc2V0KHNvdXJjZSwgaW5kZXgpIHtcbiAgaWYgKCFOdW1iZXIuaXNJbnRlZ2VyKGluZGV4KSB8fCBpbmRleCA8IDAgfHwgaW5kZXggPiBzb3VyY2UubGVuZ3RoIHx8XG4gICAgaW5kZXggPiAwICYmIGluZGV4IDwgc291cmNlLmxlbmd0aCAmJiAvW1xcdUQ4MDAtXFx1REJGRl0vdS50ZXN0KHNvdXJjZVtpbmRleCAtIDFdKSAmJiAvW1xcdURDMDAtXFx1REZGRl0vdS50ZXN0KHNvdXJjZVtpbmRleF0pKSB7XG4gICAgdGhyb3cgbmV3IFJhbmdlRXJyb3IoXCJJbnZhbGlkIFRyZWUtc2l0dGVyIHNvdXJjZSBpbmRleDogXCIgKyBpbmRleClcbiAgfVxuICByZXR1cm4gdXRmOEJ5dGVPZmZzZXRUb1V0ZjE2T2Zmc2V0KHNvdXJjZSwgbmV3IFRleHRFbmNvZGVyKCkuZW5jb2RlKHNvdXJjZS5zbGljZSgwLCBpbmRleCkpLmxlbmd0aClcbn1cblxuLyoqXG4gKiBGaW5kcyBhbiB1bnBhaXJlZCBVVEYtMTYgc3Vycm9nYXRlLlxuICogQHBhcmFtIHtzdHJpbmd9IHNvdXJjZSAtIENvbXBsZXRlIHNvdXJjZS5cbiAqIEByZXR1cm5zIHtudW1iZXJ9IEludmFsaWQgb2Zmc2V0IG9yIC0xLlxuICovXG5mdW5jdGlvbiBmaXJzdExvbmVTdXJyb2dhdGVPZmZzZXQoc291cmNlKSB7XG4gIGZvciAobGV0IGluZGV4ID0gMDsgaW5kZXggPCBzb3VyY2UubGVuZ3RoOyBpbmRleCArPSAxKSB7XG4gICAgY29uc3QgdW5pdCA9IHNvdXJjZS5jaGFyQ29kZUF0KGluZGV4KVxuXG4gICAgaWYgKHVuaXQgPj0gMHhEODAwICYmIHVuaXQgPD0gMHhEQkZGKSB7XG4gICAgICBjb25zdCBuZXh0ID0gc291cmNlLmNoYXJDb2RlQXQoaW5kZXggKyAxKVxuXG4gICAgICBpZiAobmV4dCA+PSAweERDMDAgJiYgbmV4dCA8PSAweERGRkYpIGluZGV4ICs9IDFcbiAgICAgIGVsc2UgcmV0dXJuIGluZGV4XG4gICAgfSBlbHNlIGlmICh1bml0ID49IDB4REMwMCAmJiB1bml0IDw9IDB4REZGRikgcmV0dXJuIGluZGV4XG4gIH1cbiAgcmV0dXJuIC0xXG59XG5cbi8qKiBDb25zdW1lcyBleGFjdCBxdWFsaWZpZWQgS290bGluIENTVCBzaGFwZXMgd2l0aG91dCByZXRhaW5pbmcgcGFyc2VyIGhhbmRsZXMuICovXG5jbGFzcyBLb3RsaW5SZWFkZXIge1xuICAvKipcbiAgICogQ3JlYXRlcyBhIHJlYWRlciBvdmVyIG9uZSBwYXJzZXItb3duZWQgS290bGluIHNvdXJjZS5cbiAgICogQHBhcmFtIHtzdHJpbmd9IGZpbGVuYW1lIC0gT3JpZ2luYWwgZmlsZW5hbWUuXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBzb3VyY2UgLSBDb21wbGV0ZSBzb3VyY2UuXG4gICAqL1xuICBjb25zdHJ1Y3RvcihmaWxlbmFtZSwgc291cmNlKSB7XG4gICAgdGhpcy5maWxlbmFtZSA9IGZpbGVuYW1lXG4gICAgdGhpcy5zb3VyY2UgPSBzb3VyY2VcbiAgICB0aGlzLnJ1bnRpbWUgPSBmYWxzZVxuICB9XG5cbiAgLyoqXG4gICAqIENvbnZlcnRzIG9uZSBwYXJzZXIgcmFuZ2UgdG8gU2VtYW50aWZvbGQgVVRGLTE2IGNvb3JkaW5hdGVzLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBQYXJzZXIgbm9kZS5cbiAgICogQHJldHVybnMge2ltcG9ydChcIi4uL3NlbWFudGljL3R5cGVzLmpzXCIpLlNvdXJjZUxvY2F0aW9ufSBFeGFjdCBsb2NhdGlvbi5cbiAgICovXG4gIGxvY2F0aW9uKG5vZGUpIHtcbiAgICByZXR1cm4gbG9jYXRpb25Gcm9tT2Zmc2V0cyh0aGlzLmZpbGVuYW1lLCB0aGlzLnNvdXJjZSwgYmluZGluZ0luZGV4VG9VdGYxNk9mZnNldCh0aGlzLnNvdXJjZSwgbm9kZS5zdGFydEluZGV4KSxcbiAgICAgIGJpbmRpbmdJbmRleFRvVXRmMTZPZmZzZXQodGhpcy5zb3VyY2UsIG5vZGUuZW5kSW5kZXgpKVxuICB9XG5cbiAgLyoqXG4gICAqIFJlamVjdHMgb25lIGxvY2F0ZWQgc291cmNlLXByb2ZpbGUgdmlvbGF0aW9uLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBWaW9sYXRpbmcgbm9kZS5cbiAgICogQHBhcmFtIHtzdHJpbmd9IFtkZXRhaWxdIC0gUHJvZmlsZSBkZXRhaWwuXG4gICAqIEByZXR1cm5zIHtuZXZlcn0gQWx3YXlzIHRocm93cy5cbiAgICovXG4gIGZhaWwobm9kZSwgZGV0YWlsID0gbm9kZS50eXBlKSB7XG4gICAgdW5zdXBwb3J0ZWRTeW50YXgoXCJrb3RsaW5cIiwgZGV0YWlsLCB0aGlzLmxvY2F0aW9uKG5vZGUpKVxuICB9XG5cbiAgLyoqXG4gICAqIFRyYXZlcnNlcyBldmVyeSBuYW1lZCwgYW5vbnltb3VzLCBleHRyYSwgZGlyZWN0aXZlLCBhbmQgcmVjb3Zlcnkgbm9kZS5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSByb290IC0gQ29tcGxldGUgcGFyc2VyIHJvb3QuXG4gICAqIEByZXR1cm5zIHt2b2lkfVxuICAgKi9cbiAgdmFsaWRhdGVUcmVlKHJvb3QpIHtcbiAgICBjb25zdCBwZW5kaW5nID0gW3tkZXB0aDogMCwgbm9kZTogcm9vdCwgdmlzaXRlZDogZmFsc2V9XVxuXG4gICAgd2hpbGUgKHBlbmRpbmcubGVuZ3RoKSB7XG4gICAgICBjb25zdCBjdXJyZW50ID0gcGVuZGluZy5wb3AoKVxuXG4gICAgICBpZiAoIWN1cnJlbnQpIHRocm93IG5ldyBFcnJvcihcIktvdGxpbiB0cmF2ZXJzYWwgbG9zdCBhIHBlbmRpbmcgcGFyc2VyIG5vZGUuXCIpXG4gICAgICBjb25zdCB7ZGVwdGgsIG5vZGUsIHZpc2l0ZWR9ID0gY3VycmVudFxuXG4gICAgICBpZiAoZGVwdGggPiA1MTIpIHRoaXMuZmFpbChub2RlLCBcIkNTVCBleGNlZWRzIHRoZSA1MTItbGV2ZWwgdHJhdmVyc2FsIGxpbWl0XCIpXG4gICAgICBpZiAoIXZpc2l0ZWQpIHtcbiAgICAgICAgcGVuZGluZy5wdXNoKHtkZXB0aCwgbm9kZSwgdmlzaXRlZDogdHJ1ZX0pXG4gICAgICAgIGZvciAobGV0IGluZGV4ID0gbm9kZS5jaGlsZENvdW50IC0gMTsgaW5kZXggPj0gMDsgaW5kZXggLT0gMSkge1xuICAgICAgICAgIGNvbnN0IGNoaWxkID0gbm9kZS5jaGlsZChpbmRleClcblxuICAgICAgICAgIGlmICghY2hpbGQpIHRocm93IG5ldyBFcnJvcihgVHJlZS1zaXR0ZXIgb21pdHRlZCBjaGlsZCAke2luZGV4fSBvZiAke25vZGUudHlwZX0uYClcbiAgICAgICAgICBwZW5kaW5nLnB1c2goe2RlcHRoOiBkZXB0aCArIDEsIG5vZGU6IGNoaWxkLCB2aXNpdGVkOiBmYWxzZX0pXG4gICAgICAgIH1cbiAgICAgICAgY29udGludWVcbiAgICAgIH1cbiAgICAgIGlmIChub2RlLmhhc0Vycm9yIHx8IG5vZGUuaXNFcnJvciB8fCBub2RlLmlzTWlzc2luZykge1xuICAgICAgICB0aHJvdyBuZXcgU2VtYW50aWZvbGREaWFnbm9zdGljKHtcbiAgICAgICAgICBjb2RlOiBcIlBBUlNFX0VSUk9SXCIsXG4gICAgICAgICAgbGFuZ3VhZ2U6IFwia290bGluXCIsXG4gICAgICAgICAgbG9jYXRpb246IHRoaXMubG9jYXRpb24obm9kZSksXG4gICAgICAgICAgbWVzc2FnZTogYFRyZWUtc2l0dGVyIGV4cG9zZWQgcmVjb3ZlcnkgYXQgJyR7bm9kZS50eXBlfScuYFxuICAgICAgICB9KVxuICAgICAgfVxuICAgICAgaWYgKFtcImFubm90YXRpb25cIiwgXCJmaWxlX2Fubm90YXRpb25cIiwgXCJzaGViYW5nX2xpbmVcIl0uaW5jbHVkZXMobm9kZS50eXBlKSkgdGhpcy5mYWlsKG5vZGUsIG5vZGUudHlwZSlcbiAgICAgIGlmIChjb21tZW50VHlwZXMuaGFzKG5vZGUudHlwZSkgJiYgLyg/Omxhbmd1YWdlfGFwaXxqdm0pWy1fIF12ZXJzaW9uL2l1LnRlc3Qobm9kZS50ZXh0KSkge1xuICAgICAgICB0aGlzLmZhaWwobm9kZSwgXCJkaXJlY3RpdmUtYmVhcmluZyBjb21tZW50XCIpXG4gICAgICB9XG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIE9taXRzIG9ubHkgaW5lcnQgY29tbWVudHMgYWxyZWFkeSBhY2NvdW50ZWQgZm9yIGJ5IGV4aGF1c3RpdmUgdHJhdmVyc2FsLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBQYXJlbnQgbm9kZS5cbiAgICogQHJldHVybnMge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGVbXX0gU3RydWN0dXJhbCBjaGlsZHJlbi5cbiAgICovXG4gIHBhcnRzKG5vZGUpIHtcbiAgICByZXR1cm4gbm9kZS5jaGlsZHJlbi5maWx0ZXIoKGNoaWxkKSA9PiAhY29tbWVudFR5cGVzLmhhcyhjaGlsZC50eXBlKSlcbiAgfVxuXG4gIC8qKlxuICAgKiBSZXF1aXJlcyBhbGwgb3JkZXJlZCBjaGlsZHJlbiwgaW5jbHVkaW5nIGFub255bW91cyBwdW5jdHVhdGlvbi5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gU2hhcGUgb3duZXIuXG4gICAqIEBwYXJhbSB7KGltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGUgfCBzdHJpbmcpW119IGV4cGVjdGVkIC0gRXhhY3QgY2hpbGQgc2VxdWVuY2UuXG4gICAqIEByZXR1cm5zIHt2b2lkfVxuICAgKi9cbiAgc2hhcGUobm9kZSwgZXhwZWN0ZWQpIHtcbiAgICBjb25zdCBhY3R1YWwgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICBpZiAoYWN0dWFsLmxlbmd0aCAhPSBleHBlY3RlZC5sZW5ndGgpIHRoaXMuZmFpbChhY3R1YWxbTWF0aC5taW4oYWN0dWFsLmxlbmd0aCwgZXhwZWN0ZWQubGVuZ3RoKV0gPz8gbm9kZSwgYCR7bm9kZS50eXBlfSBjaGlsZCBzaGFwZWApXG4gICAgZm9yIChsZXQgaW5kZXggPSAwOyBpbmRleCA8IGV4cGVjdGVkLmxlbmd0aDsgaW5kZXggKz0gMSkge1xuICAgICAgY29uc3Qgd2FudGVkID0gZXhwZWN0ZWRbaW5kZXhdXG4gICAgICBjb25zdCBjaGlsZCA9IGFjdHVhbFtpbmRleF1cbiAgICAgIGNvbnN0IG1hdGNoZXMgPSB0eXBlb2Ygd2FudGVkID09IFwic3RyaW5nXCIgPyBjaGlsZC50ZXh0ID09IHdhbnRlZCA6IGNoaWxkLmlkID09IHdhbnRlZC5pZFxuXG4gICAgICBpZiAoIW1hdGNoZXMpIHRoaXMuZmFpbChjaGlsZCwgYCR7bm9kZS50eXBlfSBjaGlsZCBzaGFwZWApXG4gICAgfVxuICB9XG5cbiAgLyoqXG4gICAqIFJlcXVpcmVzIG9uZSBleGFjdCBwYXJzZXIgZmllbGQgZWRnZS5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gRmllbGQgb3duZXIuXG4gICAqIEBwYXJhbSB7c3RyaW5nfSBuYW1lIC0gRmllbGQgbmFtZS5cbiAgICogQHJldHVybnMge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IFNvbGUgZmllbGQgbm9kZS5cbiAgICovXG4gIGZpZWxkKG5vZGUsIG5hbWUpIHtcbiAgICBjb25zdCBtYXRjaGVzID0gW11cblxuICAgIGZvciAobGV0IGluZGV4ID0gMDsgaW5kZXggPCBub2RlLmNoaWxkQ291bnQ7IGluZGV4ICs9IDEpIHtcbiAgICAgIGNvbnN0IGNoaWxkID0gbm9kZS5jaGlsZChpbmRleClcblxuICAgICAgaWYgKCFjaGlsZCkgdGhyb3cgbmV3IEVycm9yKGBUcmVlLXNpdHRlciBvbWl0dGVkIGNoaWxkICR7aW5kZXh9IG9mICR7bm9kZS50eXBlfS5gKVxuICAgICAgaWYgKG5vZGUuZmllbGROYW1lRm9yQ2hpbGQoaW5kZXgpID09IG5hbWUpIG1hdGNoZXMucHVzaChjaGlsZClcbiAgICB9XG4gICAgaWYgKG1hdGNoZXMubGVuZ3RoICE9IDEpIHRoaXMuZmFpbChub2RlLCBgZXhwZWN0ZWQgb25lICcke25hbWV9JyBmaWVsZGApXG4gICAgcmV0dXJuIG1hdGNoZXNbMF1cbiAgfVxuXG4gIC8qKlxuICAgKiBWYWxpZGF0ZXMgb25lIEtvdGxpbiBpZGVudGlmaWVyIGluIHRoZSBwb3J0YWJsZSBzb3VyY2UgcHJvZmlsZS5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gSWRlbnRpZmllciB0b2tlbi5cbiAgICogQHBhcmFtIHtib29sZWFufSBbYWxsb3dNYWluXSAtIFdoZXRoZXIgdGhlIGZpeGVkIG1haW4gc2NhZmZvbGQgaXMgZXhwZWN0ZWQuXG4gICAqIEBwYXJhbSB7Ym9vbGVhbn0gW2FsbG93UHJpbnRdIC0gV2hldGhlciB0aGUgZml4ZWQgcHJpbnQgc2NhZmZvbGQgaXMgZXhwZWN0ZWQuXG4gICAqIEByZXR1cm5zIHtzdHJpbmd9IEFjY2VwdGVkIHNwZWxsaW5nLlxuICAgKi9cbiAgaWRlbnRpZmllcihub2RlLCBhbGxvd01haW4gPSBmYWxzZSwgYWxsb3dQcmludCA9IGZhbHNlKSB7XG4gICAgY29uc3QgbmFtZSA9IG5vZGUudGV4dFxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcInNpbXBsZV9pZGVudGlmaWVyXCIgfHwgIShhbGxvd01haW4gJiYgbmFtZSA9PSBcIm1haW5cIikgJiYgIShhbGxvd1ByaW50ICYmIG5hbWUgPT0gXCJwcmludGxuXCIpICYmXG4gICAgICAoIWlzS290bGluSWRlbnRpZmllcihuYW1lKSB8fCBuYW1lLm5vcm1hbGl6ZShcIk5GQ1wiKSAhPSBuYW1lKSkgdGhpcy5mYWlsKG5vZGUsIFwicmVzZXJ2ZWQgb3IgdW5zdXBwb3J0ZWQgaWRlbnRpZmllclwiKVxuICAgIHJldHVybiBuYW1lXG4gIH1cblxuICAvKipcbiAgICogQ29udmVydHMgZXhhY3RseSBMb25nLCBCb29sZWFuLCBvciBTdHJpbmcuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZX0gbm9kZSAtIFR5cGUgbm9kZS5cbiAgICogQHJldHVybnMge2ltcG9ydChcIi4uL3NlbWFudGljL3R5cGVzLmpzXCIpLlR5cGVSZWZlcmVuY2V9IFNlbWFudGljIHNjYWxhci5cbiAgICovXG4gIHR5cGUobm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcInVzZXJfdHlwZVwiIHx8IHBhcnRzLmxlbmd0aCAhPSAxIHx8IHBhcnRzWzBdLnR5cGUgIT0gXCJ0eXBlX2lkZW50aWZpZXJcIikgdGhpcy5mYWlsKG5vZGUsIFwic2NhbGFyIHR5cGUgc2hhcGVcIilcbiAgICB0aGlzLnNoYXBlKG5vZGUsIFtwYXJ0c1swXV0pXG4gICAgY29uc3QgdHlwZSA9IHNvdXJjZVNjYWxhclR5cGUoXCJrb3RsaW5cIiwgcGFydHNbMF0udGV4dCwgdGhpcy5sb2NhdGlvbihwYXJ0c1swXSkpXG5cbiAgICBpZiAoIXR5cGUpIHRoaXMuZmFpbChwYXJ0c1swXSwgYHVuc3VwcG9ydGVkIHNjYWxhciB0eXBlICcke3BhcnRzWzBdLnRleHR9J2ApXG4gICAgcmV0dXJuIHR5cGVcbiAgfVxuXG4gIC8qKlxuICAgKiBEZWNvZGVzIGFuIG9yZGluYXJ5IG5vbmludGVycG9sYXRlZCBLb3RsaW4gc3RyaW5nLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBTdHJpbmcgbGl0ZXJhbCBub2RlLlxuICAgKiBAcmV0dXJucyB7c3RyaW5nfSBEZWNvZGVkIFVuaWNvZGUgc2NhbGFyIHN0cmluZy5cbiAgICovXG4gIHN0cmluZyhub2RlKSB7XG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICBpZiAobm9kZS50eXBlICE9IFwic3RyaW5nX2xpdGVyYWxcIiB8fCBwYXJ0cy5zb21lKChwYXJ0KSA9PiBwYXJ0LnR5cGUgIT0gXCJzdHJpbmdfY29udGVudFwiKSB8fFxuICAgICAgIW5vZGUudGV4dC5zdGFydHNXaXRoKCdcIicpIHx8ICFub2RlLnRleHQuZW5kc1dpdGgoJ1wiJykpIHRoaXMuZmFpbChub2RlLCBcIm9yZGluYXJ5IG5vbmludGVycG9sYXRlZCBzdHJpbmcgbGl0ZXJhbCByZXF1aXJlZFwiKVxuICAgIHRoaXMuc2hhcGUobm9kZSwgcGFydHMpXG4gICAgbGV0IHZhbHVlID0gXCJcIlxuICAgIGNvbnN0IHNpbXBsZUVzY2FwZXMgPSBuZXcgTWFwKFtcbiAgICAgIFtcInRcIiwgXCJcXHRcIl0sIFtcImJcIiwgXCJcXGJcIl0sIFtcIm5cIiwgXCJcXG5cIl0sIFtcInJcIiwgXCJcXHJcIl0sIFtcIidcIiwgXCInXCJdLCBbJ1wiJywgJ1wiJ10sIFtcIlxcXFxcIiwgXCJcXFxcXCJdLCBbXCIkXCIsIFwiJFwiXVxuICAgIF0pXG5cbiAgICBmb3IgKGxldCBpbmRleCA9IDE7IGluZGV4IDwgbm9kZS50ZXh0Lmxlbmd0aCAtIDE7IGluZGV4ICs9IDEpIHtcbiAgICAgIGNvbnN0IGNoYXJhY3RlciA9IG5vZGUudGV4dFtpbmRleF1cblxuICAgICAgaWYgKGNoYXJhY3RlciAhPSBcIlxcXFxcIikge1xuICAgICAgICBpZiAoY2hhcmFjdGVyID09IFwiXFxuXCIgfHwgY2hhcmFjdGVyID09IFwiXFxyXCIgfHwgY2hhcmFjdGVyID09ICdcIicpIHRoaXMuZmFpbChub2RlLCBcImludmFsaWQgc3RyaW5nIGNvbnRlbnRcIilcbiAgICAgICAgdmFsdWUgKz0gY2hhcmFjdGVyXG4gICAgICAgIGNvbnRpbnVlXG4gICAgICB9XG4gICAgICBjb25zdCBlc2NhcGVkID0gbm9kZS50ZXh0WysraW5kZXhdXG5cbiAgICAgIGlmIChzaW1wbGVFc2NhcGVzLmhhcyhlc2NhcGVkKSkgdmFsdWUgKz0gc2ltcGxlRXNjYXBlcy5nZXQoZXNjYXBlZClcbiAgICAgIGVsc2UgaWYgKGVzY2FwZWQgPT0gXCJ1XCIpIHtcbiAgICAgICAgY29uc3QgaGV4YWRlY2ltYWwgPSBub2RlLnRleHQuc2xpY2UoaW5kZXggKyAxLCBpbmRleCArIDUpXG5cbiAgICAgICAgaWYgKCEvXlswLTlBLUZhLWZdezR9JC91LnRlc3QoaGV4YWRlY2ltYWwpKSB0aGlzLmZhaWwobm9kZSwgXCJ1bnN1cHBvcnRlZCBzdHJpbmcgZXNjYXBlXCIpXG4gICAgICAgIHZhbHVlICs9IFN0cmluZy5mcm9tQ2hhckNvZGUoTnVtYmVyLnBhcnNlSW50KGhleGFkZWNpbWFsLCAxNikpXG4gICAgICAgIGluZGV4ICs9IDRcbiAgICAgIH0gZWxzZSB0aGlzLmZhaWwobm9kZSwgXCJ1bnN1cHBvcnRlZCBzdHJpbmcgZXNjYXBlXCIpXG4gICAgfVxuICAgIGlmICghaGFzT25seVVuaWNvZGVTY2FsYXJzKHZhbHVlKSkgdGhpcy5mYWlsKG5vZGUsIFwiaW52YWxpZCBVbmljb2RlIHN0cmluZyBsaXRlcmFsXCIpXG4gICAgcmV0dXJuIHZhbHVlXG4gIH1cblxuICAvKipcbiAgICogRXh0cmFjdHMgZXhhY3QgdW5uYW1lZCBjYWxsIGFyZ3VtZW50cy5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBzdWZmaXggLSBDYWxsIHN1ZmZpeCBub2RlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZVtdfSBBcmd1bWVudCBleHByZXNzaW9uIG5vZGVzLlxuICAgKi9cbiAgYXJndW1lbnRzKHN1ZmZpeCkge1xuICAgIGNvbnN0IHN1ZmZpeFBhcnRzID0gdGhpcy5wYXJ0cyhzdWZmaXgpXG5cbiAgICBpZiAoc3VmZml4LnR5cGUgIT0gXCJjYWxsX3N1ZmZpeFwiIHx8IHN1ZmZpeFBhcnRzLmxlbmd0aCAhPSAxIHx8IHN1ZmZpeFBhcnRzWzBdLnR5cGUgIT0gXCJ2YWx1ZV9hcmd1bWVudHNcIikge1xuICAgICAgcmV0dXJuIHRoaXMuZmFpbChzdWZmaXgsIFwiY2FsbCBzdWZmaXggc2hhcGVcIilcbiAgICB9XG4gICAgdGhpcy5zaGFwZShzdWZmaXgsIFtzdWZmaXhQYXJ0c1swXV0pXG4gICAgY29uc3QgbGlzdCA9IHN1ZmZpeFBhcnRzWzBdXG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKGxpc3QpXG5cbiAgICBpZiAocGFydHMubGVuZ3RoIDwgMiB8fCBwYXJ0c1swXS50ZXh0ICE9IFwiKFwiIHx8IHBhcnRzLmF0KC0xKT8udGV4dCAhPSBcIilcIikgdGhpcy5mYWlsKGxpc3QsIFwiY2FsbCBhcmd1bWVudCBsaXN0IHNoYXBlXCIpXG4gICAgY29uc3QgYXJndW1lbnRzXyA9IHBhcnRzLnNsaWNlKDEsIC0xKS5maWx0ZXIoKF9wYXJ0LCBpbmRleCkgPT4gaW5kZXggJSAyID09IDApXG5cbiAgICB0aGlzLnNoYXBlKGxpc3QsIFtcIihcIiwgLi4uYXJndW1lbnRzXy5mbGF0TWFwKChhcmd1bWVudCwgaW5kZXgpID0+IGluZGV4ID8gW1wiLFwiLCBhcmd1bWVudF0gOiBbYXJndW1lbnRdKSwgXCIpXCJdKVxuICAgIHJldHVybiBhcmd1bWVudHNfLm1hcCgoYXJndW1lbnQpID0+IHtcbiAgICAgIGNvbnN0IGFyZ3VtZW50UGFydHMgPSB0aGlzLnBhcnRzKGFyZ3VtZW50KVxuXG4gICAgICBpZiAoYXJndW1lbnQudHlwZSAhPSBcInZhbHVlX2FyZ3VtZW50XCIgfHwgYXJndW1lbnRQYXJ0cy5sZW5ndGggIT0gMSkgdGhpcy5mYWlsKGFyZ3VtZW50LCBcInVubmFtZWQgYXJndW1lbnQgcmVxdWlyZWRcIilcbiAgICAgIHRoaXMuc2hhcGUoYXJndW1lbnQsIFthcmd1bWVudFBhcnRzWzBdXSlcbiAgICAgIHJldHVybiBhcmd1bWVudFBhcnRzWzBdXG4gICAgfSlcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBhIGRpcmVjdCBzZW1hbnRpYyBvciBnZW5lcmF0ZWQtaGVscGVyIGNhbGwuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZX0gbm9kZSAtIENhbGwgZXhwcmVzc2lvbiBub2RlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuRXhwcmVzc2lvbn0gU2VtYW50aWMgZXhwcmVzc2lvbi5cbiAgICovXG4gIGNhbGwobm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcImNhbGxfZXhwcmVzc2lvblwiIHx8IHBhcnRzLmxlbmd0aCAhPSAyIHx8IHBhcnRzWzBdLnR5cGUgIT0gXCJzaW1wbGVfaWRlbnRpZmllclwiKSB0aGlzLmZhaWwobm9kZSwgXCJkaXJlY3QgY2FsbCBzaGFwZVwiKVxuICAgIHRoaXMuc2hhcGUobm9kZSwgW3BhcnRzWzBdLCBwYXJ0c1sxXV0pXG4gICAgY29uc3QgYXJndW1lbnROb2RlcyA9IHRoaXMuYXJndW1lbnRzKHBhcnRzWzFdKVxuICAgIGNvbnN0IG5hbWUgPSBwYXJ0c1swXS50ZXh0XG4gICAgY29uc3QgaGVscGVyID0gdGhpcy5ydW50aW1lID8gaGVscGVyT3BlcmF0aW9ucy5nZXQobmFtZSkgOiB1bmRlZmluZWRcbiAgICBjb25zdCBsb2NhdGlvbiA9IHRoaXMubG9jYXRpb24obm9kZSlcblxuICAgIGlmIChoZWxwZXIpIHtcbiAgICAgIGNvbnN0IGNvdW50ID0gaGVscGVyID09IFwiTmVnYXRlXCIgPyAxIDogMlxuXG4gICAgICBpZiAoYXJndW1lbnROb2Rlcy5sZW5ndGggIT0gY291bnQpIHRoaXMuZmFpbChub2RlLCBcIktvdGxpbiBjaGVja2VkLWludGVnZXIgaGVscGVyIHNoYXBlXCIpXG4gICAgICBpZiAoaGVscGVyID09IFwiTmVnYXRlXCIpIHtcbiAgICAgICAgcmV0dXJuIC8qKiBAdHlwZSB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuRXhwcmVzc2lvbn0gKi8gKC8qKiBAdHlwZSB7dW5rbm93bn0gKi8gKHdpdGhBZGFwdGVkT3BlcmF0aW9uKHdpdGhQYXJzZXJSYW5nZXMoe1xuICAgICAgICAgIGtpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIlVuYXJ5RXhwcmVzc2lvblwiKSwgbG9jYXRpb24sIG9wZXJhbmQ6IHRoaXMuZXhwcmVzc2lvbihhcmd1bWVudE5vZGVzWzBdKVxuICAgICAgICB9LCB7b3BlcmF0b3I6IHRoaXMubG9jYXRpb24ocGFydHNbMF0pfSksIGhlbHBlcikpKVxuICAgICAgfVxuICAgICAgcmV0dXJuIC8qKiBAdHlwZSB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuRXhwcmVzc2lvbn0gKi8gKHdpdGhBZGFwdGVkT3BlcmF0aW9uKHdpdGhQYXJzZXJSYW5nZXMoe1xuICAgICAgICBraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJCaW5hcnlFeHByZXNzaW9uXCIpLCBsZWZ0OiB0aGlzLmV4cHJlc3Npb24oYXJndW1lbnROb2Rlc1swXSksIGxvY2F0aW9uLCByaWdodDogdGhpcy5leHByZXNzaW9uKGFyZ3VtZW50Tm9kZXNbMV0pXG4gICAgICB9LCB7b3BlcmF0b3I6IHRoaXMubG9jYXRpb24ocGFydHNbMF0pfSksIGhlbHBlcikpXG4gICAgfVxuICAgIGNvbnN0IHNlbWFudGljTmFtZSA9IHRoaXMuaWRlbnRpZmllcihwYXJ0c1swXSlcblxuICAgIGlmIChhcmd1bWVudE5vZGVzLmxlbmd0aCAhPSAyKSB0aGlzLmZhaWwocGFydHNbMV0sIFwic2VtYW50aWMgY2FsbCBhcmd1bWVudCBjb3VudFwiKVxuICAgIHJldHVybiB3aXRoUGFyc2VyUmFuZ2VzKHtcbiAgICAgIGFyZ3VtZW50czogYXJndW1lbnROb2Rlcy5tYXAoKGFyZ3VtZW50KSA9PiB0aGlzLmV4cHJlc3Npb24oYXJndW1lbnQpKSwgY2FsbGVlOiBzZW1hbnRpY05hbWUsXG4gICAgICBraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJDYWxsRXhwcmVzc2lvblwiKSwgbG9jYXRpb25cbiAgICB9LCB7Y2FsbGVlOiB0aGlzLmxvY2F0aW9uKHBhcnRzWzBdKX0pXG4gIH1cblxuICAvKipcbiAgICogQ29udmVydHMgb25lIHN1cHBvcnRlZCBzY2FsYXIgZXhwcmVzc2lvbi5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gRXhwcmVzc2lvbiBub2RlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuRXhwcmVzc2lvbn0gU2VtYW50aWMgZXhwcmVzc2lvbi5cbiAgICovXG4gIGV4cHJlc3Npb24obm9kZSkge1xuICAgIGNvbnN0IGxvY2F0aW9uID0gdGhpcy5sb2NhdGlvbihub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSA9PSBcInNpbXBsZV9pZGVudGlmaWVyXCIpIHtcbiAgICAgIHJldHVybiB3aXRoUGFyc2VyUmFuZ2VzKHtraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJJZGVudGlmaWVyRXhwcmVzc2lvblwiKSwgbG9jYXRpb24sIG5hbWU6IHRoaXMuaWRlbnRpZmllcihub2RlKX0sIHtuYW1lOiBsb2NhdGlvbn0pXG4gICAgfVxuICAgIGlmIChub2RlLnR5cGUgPT0gXCJpbnRlZ2VyX2xpdGVyYWxcIiB8fCBub2RlLnR5cGUgPT0gXCJsb25nX2xpdGVyYWxcIikge1xuICAgICAgY29uc3QgbGl0ZXJhbCA9IG5vZGUudHlwZSA9PSBcImxvbmdfbGl0ZXJhbFwiID8gdGhpcy5wYXJ0cyhub2RlKVswXSA6IG5vZGVcblxuICAgICAgaWYgKG5vZGUudHlwZSA9PSBcImxvbmdfbGl0ZXJhbFwiKSB0aGlzLnNoYXBlKG5vZGUsIFtsaXRlcmFsLCBcIkxcIl0pXG4gICAgICBpZiAoIWxpdGVyYWwgfHwgbGl0ZXJhbC50eXBlICE9IFwiaW50ZWdlcl9saXRlcmFsXCIgfHwgIS9eKD86MHxbMS05XVswLTldKikkL3UudGVzdChsaXRlcmFsLnRleHQpIHx8XG4gICAgICAgIG5vZGUudHlwZSA9PSBcImxvbmdfbGl0ZXJhbFwiICYmICEvTCQvdS50ZXN0KG5vZGUudGV4dCkpIHRoaXMuZmFpbChub2RlLCBcIm5vbmNhbm9uaWNhbCBpbnRlZ2VyIGxpdGVyYWxcIilcbiAgICAgIGNvbnN0IHZhbHVlID0gTnVtYmVyKEJpZ0ludChsaXRlcmFsLnRleHQpKVxuXG4gICAgICBpZiAoIU51bWJlci5pc1NhZmVJbnRlZ2VyKHZhbHVlKSkgdGhpcy5mYWlsKG5vZGUsIFwibm9uLXNhZmUgaW50ZWdlciBsaXRlcmFsXCIpXG4gICAgICByZXR1cm4gd2l0aFBhcnNlclJhbmdlcyh7a2luZDogLyoqIEB0eXBlIHtjb25zdH0gKi8gKFwiSW50ZWdlckxpdGVyYWxcIiksIGxvY2F0aW9uLCB2YWx1ZX0sIHtsaXRlcmFsOiBsb2NhdGlvbn0pXG4gICAgfVxuICAgIGlmIChub2RlLnR5cGUgPT0gXCJib29sZWFuX2xpdGVyYWxcIikge1xuICAgICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICAgIGlmIChwYXJ0cy5sZW5ndGggIT0gMSB8fCAhW1widHJ1ZVwiLCBcImZhbHNlXCJdLmluY2x1ZGVzKHBhcnRzWzBdLnRleHQpKSB0aGlzLmZhaWwobm9kZSwgXCJCb29sZWFuIGxpdGVyYWwgc2hhcGVcIilcbiAgICAgIHRoaXMuc2hhcGUobm9kZSwgW3BhcnRzWzBdLnRleHRdKVxuICAgICAgcmV0dXJuIHdpdGhQYXJzZXJSYW5nZXMoe2tpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIkJvb2xlYW5MaXRlcmFsXCIpLCBsb2NhdGlvbiwgdmFsdWU6IHBhcnRzWzBdLnRleHQgPT0gXCJ0cnVlXCJ9LCB7bGl0ZXJhbDogbG9jYXRpb259KVxuICAgIH1cbiAgICBpZiAobm9kZS50eXBlID09IFwic3RyaW5nX2xpdGVyYWxcIikge1xuICAgICAgcmV0dXJuIHdpdGhQYXJzZXJSYW5nZXMoe2tpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIlN0cmluZ0xpdGVyYWxcIiksIGxvY2F0aW9uLCB2YWx1ZTogdGhpcy5zdHJpbmcobm9kZSl9LCB7bGl0ZXJhbDogbG9jYXRpb259KVxuICAgIH1cbiAgICBpZiAobm9kZS50eXBlID09IFwicGFyZW50aGVzaXplZF9leHByZXNzaW9uXCIpIHtcbiAgICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuXG4gICAgICBpZiAocGFydHMubGVuZ3RoICE9IDMpIHRoaXMuZmFpbChub2RlLCBcInBhcmVudGhlc2l6ZWQgZXhwcmVzc2lvbiBzaGFwZVwiKVxuICAgICAgdGhpcy5zaGFwZShub2RlLCBbXCIoXCIsIHBhcnRzWzFdLCBcIilcIl0pXG4gICAgICByZXR1cm4gdGhpcy5leHByZXNzaW9uKHBhcnRzWzFdKVxuICAgIH1cbiAgICBpZiAobm9kZS50eXBlID09IFwicHJlZml4X2V4cHJlc3Npb25cIikge1xuICAgICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICAgIGlmIChwYXJ0cy5sZW5ndGggIT0gMiB8fCAhW1wiLVwiLCBcIiFcIl0uaW5jbHVkZXMocGFydHNbMF0udGV4dCkpIHRoaXMuZmFpbChub2RlLCBcInVuYXJ5IG9wZXJhdG9yXCIpXG4gICAgICB0aGlzLnNoYXBlKG5vZGUsIFtwYXJ0c1swXS50ZXh0LCBwYXJ0c1sxXV0pXG4gICAgICByZXR1cm4gLyoqIEB0eXBlIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5FeHByZXNzaW9ufSAqLyAoLyoqIEB0eXBlIHt1bmtub3dufSAqLyAod2l0aEFkYXB0ZWRPcGVyYXRpb24od2l0aFBhcnNlclJhbmdlcyh7XG4gICAgICAgIGtpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIlVuYXJ5RXhwcmVzc2lvblwiKSwgbG9jYXRpb24sIG9wZXJhbmQ6IHRoaXMuZXhwcmVzc2lvbihwYXJ0c1sxXSlcbiAgICAgIH0sIHtvcGVyYXRvcjogdGhpcy5sb2NhdGlvbihwYXJ0c1swXSl9KSwgcGFydHNbMF0udGV4dCA9PSBcIi1cIiA/IFwiTmVnYXRlXCIgOiBcIk5vdFwiKSkpXG4gICAgfVxuICAgIGlmIChiaW5hcnlOb2RlT3BlcmF0b3JzLmhhcyhub2RlLnR5cGUpKSByZXR1cm4gdGhpcy5iaW5hcnkobm9kZSlcbiAgICBpZiAobm9kZS50eXBlID09IFwiY2FsbF9leHByZXNzaW9uXCIpIHJldHVybiB0aGlzLmNhbGwobm9kZSlcbiAgICByZXR1cm4gdGhpcy5mYWlsKG5vZGUpXG4gIH1cblxuICAvKipcbiAgICogQ29udmVydHMgb25lIGJpbmFyeSBleHByZXNzaW9uLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBCaW5hcnkgZXhwcmVzc2lvbiBub2RlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuRXhwcmVzc2lvbn0gU2VtYW50aWMgZXhwcmVzc2lvbi5cbiAgICovXG4gIGJpbmFyeShub2RlKSB7XG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG4gICAgY29uc3QgYWNjZXB0ZWQgPSBiaW5hcnlOb2RlT3BlcmF0b3JzLmdldChub2RlLnR5cGUpXG5cbiAgICBpZiAocGFydHMubGVuZ3RoICE9IDMpIHRoaXMuZmFpbChub2RlLCBgJHtub2RlLnR5cGV9IGNoaWxkIHNoYXBlYClcbiAgICB0aGlzLnNoYXBlKG5vZGUsIFtwYXJ0c1swXSwgcGFydHNbMV0sIHBhcnRzWzJdXSlcbiAgICBjb25zdCBvcGVyYXRpb24gPSBiaW5hcnlPcGVyYXRpb25zLmdldChwYXJ0c1sxXS50ZXh0KVxuXG4gICAgaWYgKCFhY2NlcHRlZD8uaGFzKHBhcnRzWzFdLnRleHQpIHx8ICFvcGVyYXRpb24pIHRoaXMuZmFpbChwYXJ0c1sxXSwgXCJ1bnN1cHBvcnRlZCBiaW5hcnkgb3BlcmF0b3JcIilcbiAgICByZXR1cm4gLyoqIEB0eXBlIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5FeHByZXNzaW9ufSAqLyAod2l0aEFkYXB0ZWRPcGVyYXRpb24od2l0aFBhcnNlclJhbmdlcyh7XG4gICAgICBraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJCaW5hcnlFeHByZXNzaW9uXCIpLCBsZWZ0OiB0aGlzLmV4cHJlc3Npb24ocGFydHNbMF0pLCBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihub2RlKSwgcmlnaHQ6IHRoaXMuZXhwcmVzc2lvbihwYXJ0c1syXSlcbiAgICB9LCB7b3BlcmF0b3I6IHRoaXMubG9jYXRpb24ocGFydHNbMV0pfSksIC8qKiBAdHlwZSB7aW1wb3J0KFwiLi4vc2VtYW50aWMvb3BlcmF0b3JzLmpzXCIpLkFkYXB0ZWRPcGVyYXRpb259ICovIChvcGVyYXRpb24pKSlcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBvbmUgZXhwbGljaXRseSB0eXBlZCBsb2NhbCBkZWNsYXJhdGlvbi5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gUHJvcGVydHkgZGVjbGFyYXRpb24gbm9kZS5cbiAgICogQHJldHVybnMge2ltcG9ydChcIi4uL3NlbWFudGljL3R5cGVzLmpzXCIpLkxvY2FsRGVjbGFyYXRpb259IFNlbWFudGljIGRlY2xhcmF0aW9uLlxuICAgKi9cbiAgbG9jYWwobm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuICAgIGNvbnN0IGxvY2F0aW9uID0gdGhpcy5sb2NhdGlvbihub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcInByb3BlcnR5X2RlY2xhcmF0aW9uXCIgfHwgcGFydHMubGVuZ3RoICE9IDQgfHwgcGFydHNbMF0udHlwZSAhPSBcImJpbmRpbmdfcGF0dGVybl9raW5kXCIgfHxcbiAgICAgIHBhcnRzWzFdLnR5cGUgIT0gXCJ2YXJpYWJsZV9kZWNsYXJhdGlvblwiIHx8IHBhcnRzWzJdLnRleHQgIT0gXCI9XCIpIHRoaXMuZmFpbChub2RlLCBcImxvY2FsIGRlY2xhcmF0aW9uIHNoYXBlXCIpXG4gICAgY29uc3QgYmluZGluZ1BhcnRzID0gdGhpcy5wYXJ0cyhwYXJ0c1swXSlcbiAgICBjb25zdCB2YXJpYWJsZVBhcnRzID0gdGhpcy5wYXJ0cyhwYXJ0c1sxXSlcblxuICAgIGlmIChiaW5kaW5nUGFydHMubGVuZ3RoICE9IDEgfHwgIVtcInZhbFwiLCBcInZhclwiXS5pbmNsdWRlcyhiaW5kaW5nUGFydHNbMF0udGV4dCkpIHRoaXMuZmFpbChwYXJ0c1swXSwgXCJsb2NhbCBiaW5kaW5nIGtpbmRcIilcbiAgICBpZiAodmFyaWFibGVQYXJ0cy5sZW5ndGggPT0gMSkgcmV0dXJuIG1pc3NpbmdUeXBlKFwia290bGluXCIsIFwiTG9jYWxcIiwgbG9jYXRpb24pXG4gICAgaWYgKHZhcmlhYmxlUGFydHMubGVuZ3RoICE9IDMgfHwgdmFyaWFibGVQYXJ0c1swXS50eXBlICE9IFwic2ltcGxlX2lkZW50aWZpZXJcIiB8fCB2YXJpYWJsZVBhcnRzWzFdLnRleHQgIT0gXCI6XCIpIHtcbiAgICAgIHRoaXMuZmFpbChwYXJ0c1sxXSwgXCJsb2NhbCBkZWNsYXJhdGlvbiBzaGFwZVwiKVxuICAgIH1cbiAgICB0aGlzLnNoYXBlKHBhcnRzWzBdLCBbYmluZGluZ1BhcnRzWzBdLnRleHRdKVxuICAgIHRoaXMuc2hhcGUocGFydHNbMV0sIFt2YXJpYWJsZVBhcnRzWzBdLCBcIjpcIiwgdmFyaWFibGVQYXJ0c1syXV0pXG4gICAgdGhpcy5zaGFwZShub2RlLCBbcGFydHNbMF0sIHBhcnRzWzFdLCBcIj1cIiwgcGFydHNbM11dKVxuICAgIGNvbnN0IG5hbWUgPSB0aGlzLmlkZW50aWZpZXIodmFyaWFibGVQYXJ0c1swXSlcblxuICAgIHJldHVybiB3aXRoUGFyc2VyUmFuZ2VzKHtcbiAgICAgIGluaXRpYWxpemVyOiB0aGlzLmV4cHJlc3Npb24ocGFydHNbM10pLCBraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJMb2NhbERlY2xhcmF0aW9uXCIpLCBsb2NhdGlvbixcbiAgICAgIG11dGFibGU6IGJpbmRpbmdQYXJ0c1swXS50ZXh0ID09IFwidmFyXCIsIG5hbWUsIHR5cGU6IHRoaXMudHlwZSh2YXJpYWJsZVBhcnRzWzJdKVxuICAgIH0sIHtuYW1lOiB0aGlzLmxvY2F0aW9uKHZhcmlhYmxlUGFydHNbMF0pLCBvcGVyYXRvcjogdGhpcy5sb2NhdGlvbihwYXJ0c1syXSl9KVxuICB9XG5cbiAgLyoqXG4gICAqIENvbnZlcnRzIG9uZSBwbGFpbiBsb2NhbCBhc3NpZ25tZW50LlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBBc3NpZ25tZW50IG5vZGUuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5Bc3NpZ25tZW50U3RhdGVtZW50fSBTZW1hbnRpYyBhc3NpZ25tZW50LlxuICAgKi9cbiAgYXNzaWdubWVudChub2RlKSB7XG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICBpZiAobm9kZS50eXBlICE9IFwiYXNzaWdubWVudFwiIHx8IHBhcnRzLmxlbmd0aCAhPSAzIHx8IHBhcnRzWzBdLnR5cGUgIT0gXCJkaXJlY3RseV9hc3NpZ25hYmxlX2V4cHJlc3Npb25cIiB8fCBwYXJ0c1sxXS50ZXh0ICE9IFwiPVwiKSB7XG4gICAgICB0aGlzLmZhaWwobm9kZSwgXCJhc3NpZ25tZW50IHNoYXBlXCIpXG4gICAgfVxuICAgIGNvbnN0IHRhcmdldFBhcnRzID0gdGhpcy5wYXJ0cyhwYXJ0c1swXSlcblxuICAgIGlmICh0YXJnZXRQYXJ0cy5sZW5ndGggIT0gMSB8fCB0YXJnZXRQYXJ0c1swXS50eXBlICE9IFwic2ltcGxlX2lkZW50aWZpZXJcIikgdGhpcy5mYWlsKHBhcnRzWzBdLCBcImFzc2lnbm1lbnQgdGFyZ2V0IHNoYXBlXCIpXG4gICAgdGhpcy5zaGFwZShwYXJ0c1swXSwgW3RhcmdldFBhcnRzWzBdXSlcbiAgICB0aGlzLnNoYXBlKG5vZGUsIFtwYXJ0c1swXSwgXCI9XCIsIHBhcnRzWzJdXSlcbiAgICBjb25zdCBuYW1lID0gdGhpcy5pZGVudGlmaWVyKHRhcmdldFBhcnRzWzBdKVxuICAgIGNvbnN0IHRhcmdldExvY2F0aW9uID0gdGhpcy5sb2NhdGlvbih0YXJnZXRQYXJ0c1swXSlcblxuICAgIHJldHVybiB3aXRoUGFyc2VyUmFuZ2VzKHtcbiAgICAgIGV4cHJlc3Npb246IHRoaXMuZXhwcmVzc2lvbihwYXJ0c1syXSksIGtpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIkFzc2lnbm1lbnRTdGF0ZW1lbnRcIiksIGxvY2F0aW9uOiB0aGlzLmxvY2F0aW9uKG5vZGUpLFxuICAgICAgdGFyZ2V0OiB3aXRoUGFyc2VyUmFuZ2VzKHtraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJJZGVudGlmaWVyRXhwcmVzc2lvblwiKSwgbG9jYXRpb246IHRhcmdldExvY2F0aW9uLCBuYW1lfSwge25hbWU6IHRhcmdldExvY2F0aW9ufSlcbiAgICB9LCB7b3BlcmF0b3I6IHRoaXMubG9jYXRpb24ocGFydHNbMV0pfSlcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyB0aGUgZXhhY3QgcHJpbnRsbiBlbnRyeSBzY2FmZm9sZC5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gQ2FsbCBub2RlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuUHJpbnRTdGF0ZW1lbnR9IFNlbWFudGljIHByaW50LlxuICAgKi9cbiAgcHJpbnQobm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcImNhbGxfZXhwcmVzc2lvblwiIHx8IHBhcnRzLmxlbmd0aCAhPSAyIHx8IHBhcnRzWzBdLnR5cGUgIT0gXCJzaW1wbGVfaWRlbnRpZmllclwiIHx8XG4gICAgICB0aGlzLmlkZW50aWZpZXIocGFydHNbMF0sIGZhbHNlLCB0cnVlKSAhPSBcInByaW50bG5cIikgdGhpcy5mYWlsKG5vZGUsIFwiZXhhY3QgcHJpbnRsbiBjYWxsIHJlcXVpcmVkXCIpXG4gICAgY29uc3QgYXJndW1lbnRzXyA9IHRoaXMuYXJndW1lbnRzKHBhcnRzWzFdKVxuXG4gICAgaWYgKGFyZ3VtZW50c18ubGVuZ3RoICE9IDEpIHRoaXMuZmFpbChwYXJ0c1sxXSwgXCJwcmludGxuIGFyZ3VtZW50IGNvdW50XCIpXG4gICAgcmV0dXJuIHtleHByZXNzaW9uOiB0aGlzLmV4cHJlc3Npb24oYXJndW1lbnRzX1swXSksIGtpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIlByaW50U3RhdGVtZW50XCIpLCBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihub2RlKX1cbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBvbmUgc3VwcG9ydGVkIHN0YXRlbWVudC5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gU3RhdGVtZW50IG5vZGUuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5TdGF0ZW1lbnR9IFNlbWFudGljIHN0YXRlbWVudC5cbiAgICovXG4gIHN0YXRlbWVudChub2RlKSB7XG4gICAgaWYgKG5vZGUudHlwZSA9PSBcInByb3BlcnR5X2RlY2xhcmF0aW9uXCIpIHJldHVybiB0aGlzLmxvY2FsKG5vZGUpXG4gICAgaWYgKG5vZGUudHlwZSA9PSBcImFzc2lnbm1lbnRcIikgcmV0dXJuIHRoaXMuYXNzaWdubWVudChub2RlKVxuICAgIGlmIChub2RlLnR5cGUgPT0gXCJpZl9leHByZXNzaW9uXCIpIHJldHVybiB0aGlzLmNvbmRpdGlvbmFsKG5vZGUpXG4gICAgaWYgKG5vZGUudHlwZSA9PSBcImNhbGxfZXhwcmVzc2lvblwiKSByZXR1cm4gdGhpcy5wcmludChub2RlKVxuICAgIGlmIChub2RlLnR5cGUgPT0gXCJqdW1wX2V4cHJlc3Npb25cIikge1xuICAgICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICAgIGlmIChwYXJ0cy5sZW5ndGggIT0gMiB8fCBwYXJ0c1swXS50ZXh0ICE9IFwicmV0dXJuXCIpIHRoaXMuZmFpbChub2RlLCBcInJldHVybiBleHByZXNzaW9uIHNoYXBlXCIpXG4gICAgICB0aGlzLnNoYXBlKG5vZGUsIFtcInJldHVyblwiLCBwYXJ0c1sxXV0pXG4gICAgICByZXR1cm4ge2V4cHJlc3Npb246IHRoaXMuZXhwcmVzc2lvbihwYXJ0c1sxXSksIGtpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIlJldHVyblN0YXRlbWVudFwiKSwgbG9jYXRpb246IHRoaXMubG9jYXRpb24obm9kZSl9XG4gICAgfVxuICAgIHJldHVybiB0aGlzLmZhaWwobm9kZSlcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBhbiBvcHRpb25hbCBwYXJzZXIgc3RhdGVtZW50IGxpc3QuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZSB8IHVuZGVmaW5lZH0gbm9kZSAtIFN0YXRlbWVudC1saXN0IG5vZGUuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5TdGF0ZW1lbnRbXX0gU2VtYW50aWMgc3RhdGVtZW50cy5cbiAgICovXG4gIHN0YXRlbWVudHMobm9kZSkge1xuICAgIGlmICghbm9kZSkgcmV0dXJuIFtdXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcInN0YXRlbWVudHNcIikgdGhpcy5mYWlsKG5vZGUsIFwic3RhdGVtZW50IGxpc3Qgc2hhcGVcIilcbiAgICByZXR1cm4gdGhpcy5wYXJ0cyhub2RlKS5tYXAoKHN0YXRlbWVudCkgPT4gdGhpcy5zdGF0ZW1lbnQoc3RhdGVtZW50KSlcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBvbmUgYnJhY2VkIGNvbmRpdGlvbmFsIGJvZHkuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZX0gbm9kZSAtIENvbnRyb2wgYm9keSBub2RlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuQmxvY2t9IFNlbWFudGljIGJsb2NrLlxuICAgKi9cbiAgY29udHJvbEJvZHkobm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuICAgIGNvbnN0IHN0YXRlbWVudHMgPSBwYXJ0c1sxXT8udHlwZSA9PSBcInN0YXRlbWVudHNcIiA/IHBhcnRzWzFdIDogdW5kZWZpbmVkXG5cbiAgICBpZiAobm9kZS50eXBlICE9IFwiY29udHJvbF9zdHJ1Y3R1cmVfYm9keVwiKSB0aGlzLmZhaWwobm9kZSwgXCJjb25kaXRpb25hbCBibG9jayBzaGFwZVwiKVxuICAgIHRoaXMuc2hhcGUobm9kZSwgW1wie1wiLCAuLi4oc3RhdGVtZW50cyA/IFtzdGF0ZW1lbnRzXSA6IFtdKSwgXCJ9XCJdKVxuICAgIHJldHVybiB7a2luZDogLyoqIEB0eXBlIHtjb25zdH0gKi8gKFwiQmxvY2tcIiksIGxvY2F0aW9uOiB0aGlzLmxvY2F0aW9uKG5vZGUpLCBzdGF0ZW1lbnRzOiB0aGlzLnN0YXRlbWVudHMoc3RhdGVtZW50cyl9XG4gIH1cblxuICAvKipcbiAgICogQ29udmVydHMgb25lIHN0cmljdCBCb29sZWFuIGNvbmRpdGlvbmFsLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBJZiBleHByZXNzaW9uIG5vZGUuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5JZlN0YXRlbWVudH0gU2VtYW50aWMgY29uZGl0aW9uYWwuXG4gICAqL1xuICBjb25kaXRpb25hbChub2RlKSB7XG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG4gICAgY29uc3QgY29uZGl0aW9uID0gdGhpcy5maWVsZChub2RlLCBcImNvbmRpdGlvblwiKVxuICAgIGNvbnN0IGNvbnNlcXVlbmNlID0gdGhpcy5maWVsZChub2RlLCBcImNvbnNlcXVlbmNlXCIpXG4gICAgY29uc3QgYmFzZSA9IFtcImlmXCIsIFwiKFwiLCBjb25kaXRpb24sIFwiKVwiLCBjb25zZXF1ZW5jZV1cblxuICAgIGlmIChub2RlLnR5cGUgIT0gXCJpZl9leHByZXNzaW9uXCIgfHwgY29uc2VxdWVuY2UudHlwZSAhPSBcImNvbnRyb2xfc3RydWN0dXJlX2JvZHlcIikgdGhpcy5mYWlsKG5vZGUsIFwiaWYgZXhwcmVzc2lvbiBzaGFwZVwiKVxuICAgIGNvbnN0IHN0YXRlbWVudCA9IC8qKiBAdHlwZSB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuSWZTdGF0ZW1lbnR9ICovICh7XG4gICAgICBjb25kaXRpb246IHRoaXMuZXhwcmVzc2lvbihjb25kaXRpb24pLCBjb25zZXF1ZW50OiB0aGlzLmNvbnRyb2xCb2R5KGNvbnNlcXVlbmNlKSwga2luZDogLyoqIEB0eXBlIHtjb25zdH0gKi8gKFwiSWZTdGF0ZW1lbnRcIiksXG4gICAgICBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihub2RlKVxuICAgIH0pXG5cbiAgICBpZiAocGFydHMubGVuZ3RoID09IGJhc2UubGVuZ3RoKSB7XG4gICAgICB0aGlzLnNoYXBlKG5vZGUsIGJhc2UpXG4gICAgICByZXR1cm4gc3RhdGVtZW50XG4gICAgfVxuICAgIGNvbnN0IGFsdGVybmF0aXZlID0gdGhpcy5maWVsZChub2RlLCBcImFsdGVybmF0aXZlXCIpXG5cbiAgICB0aGlzLnNoYXBlKG5vZGUsIFsuLi5iYXNlLCBcImVsc2VcIiwgYWx0ZXJuYXRpdmVdKVxuICAgIGlmIChhbHRlcm5hdGl2ZS50eXBlICE9IFwiY29udHJvbF9zdHJ1Y3R1cmVfYm9keVwiKSB0aGlzLmZhaWwoYWx0ZXJuYXRpdmUsIFwiaWYgYWx0ZXJuYXRlIHNoYXBlXCIpXG4gICAgY29uc3QgYWx0ZXJuYXRpdmVQYXJ0cyA9IHRoaXMucGFydHMoYWx0ZXJuYXRpdmUpXG5cbiAgICBpZiAoYWx0ZXJuYXRpdmVQYXJ0cy5sZW5ndGggPT0gMSAmJiBhbHRlcm5hdGl2ZVBhcnRzWzBdLnR5cGUgPT0gXCJpZl9leHByZXNzaW9uXCIpIHtcbiAgICAgIHRoaXMuc2hhcGUoYWx0ZXJuYXRpdmUsIFthbHRlcm5hdGl2ZVBhcnRzWzBdXSlcbiAgICAgIHJldHVybiB7Li4uc3RhdGVtZW50LCBhbHRlcm5hdGU6IHtraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJCbG9ja1wiKSwgbG9jYXRpb246IHRoaXMubG9jYXRpb24oYWx0ZXJuYXRpdmUpLFxuICAgICAgICBzdGF0ZW1lbnRzOiBbdGhpcy5jb25kaXRpb25hbChhbHRlcm5hdGl2ZVBhcnRzWzBdKV19fVxuICAgIH1cbiAgICByZXR1cm4gey4uLnN0YXRlbWVudCwgYWx0ZXJuYXRlOiB0aGlzLmNvbnRyb2xCb2R5KGFsdGVybmF0aXZlKX1cbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBvbmUgZXhhY3QgYnJhY2VkIGJsb2NrLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBCbG9jayBub2RlLlxuICAgKiBAcGFyYW0ge1wiZnVuY3Rpb25fYm9keVwiIHwgXCJjb250cm9sX3N0cnVjdHVyZV9ib2R5XCJ9IHR5cGUgLSBSZXF1aXJlZCBwYXJzZXIgbm9kZSB0eXBlLlxuICAgKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuQmxvY2t9IFNlbWFudGljIGJsb2NrLlxuICAgKi9cbiAgYmxvY2sobm9kZSwgdHlwZSA9IFwiZnVuY3Rpb25fYm9keVwiKSB7XG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG4gICAgY29uc3Qgc3RhdGVtZW50cyA9IHBhcnRzWzFdPy50eXBlID09IFwic3RhdGVtZW50c1wiID8gcGFydHNbMV0gOiB1bmRlZmluZWRcblxuICAgIGlmIChub2RlLnR5cGUgIT0gdHlwZSkgdGhpcy5mYWlsKG5vZGUsIGAke3R5cGV9IHNoYXBlYClcbiAgICB0aGlzLnNoYXBlKG5vZGUsIFtcIntcIiwgLi4uKHN0YXRlbWVudHMgPyBbc3RhdGVtZW50c10gOiBbXSksIFwifVwiXSlcbiAgICByZXR1cm4ge2tpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIkJsb2NrXCIpLCBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihub2RlKSwgc3RhdGVtZW50czogdGhpcy5zdGF0ZW1lbnRzKHN0YXRlbWVudHMpfVxuICB9XG5cbiAgLyoqXG4gICAqIENvbnZlcnRzIG9uZSBleHBsaWNpdGx5IHR5cGVkIHBhcmFtZXRlci5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gUGFyYW1ldGVyIG5vZGUuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5QYXJhbWV0ZXJ9IFNlbWFudGljIHBhcmFtZXRlci5cbiAgICovXG4gIHBhcmFtZXRlcihub2RlKSB7XG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKG5vZGUpXG5cbiAgICBpZiAobm9kZS50eXBlICE9IFwicGFyYW1ldGVyXCIgfHwgcGFydHMubGVuZ3RoICE9IDMgfHwgcGFydHNbMF0udHlwZSAhPSBcInNpbXBsZV9pZGVudGlmaWVyXCIgfHwgcGFydHNbMV0udGV4dCAhPSBcIjpcIikge1xuICAgICAgdGhpcy5mYWlsKG5vZGUsIFwicGFyYW1ldGVyIHNoYXBlXCIpXG4gICAgfVxuICAgIHRoaXMuc2hhcGUobm9kZSwgW3BhcnRzWzBdLCBcIjpcIiwgcGFydHNbMl1dKVxuICAgIGNvbnN0IG5hbWUgPSB0aGlzLmlkZW50aWZpZXIocGFydHNbMF0pXG5cbiAgICByZXR1cm4gd2l0aFBhcnNlclJhbmdlcyh7a2luZDogLyoqIEB0eXBlIHtjb25zdH0gKi8gKFwiUGFyYW1ldGVyXCIpLCBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihub2RlKSwgbmFtZSwgdHlwZTogdGhpcy50eXBlKHBhcnRzWzJdKX0sIHtcbiAgICAgIG5hbWU6IHRoaXMubG9jYXRpb24ocGFydHNbMF0pXG4gICAgfSlcbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBvbmUgc3VwcG9ydGVkIHRvcC1sZXZlbCBmdW5jdGlvbi5cbiAgICogQHBhcmFtIHtpbXBvcnQoXCJ0cmVlLXNpdHRlclwiKS5TeW50YXhOb2RlfSBub2RlIC0gRnVuY3Rpb24gZGVjbGFyYXRpb24gbm9kZS5cbiAgICogQHJldHVybnMge2ltcG9ydChcIi4uL3NlbWFudGljL3R5cGVzLmpzXCIpLkZ1bmN0aW9uRGVjbGFyYXRpb259IFNlbWFudGljIGZ1bmN0aW9uLlxuICAgKi9cbiAgZnVuY3Rpb24obm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcImZ1bmN0aW9uX2RlY2xhcmF0aW9uXCIgfHwgcGFydHMubGVuZ3RoIDwgNCB8fCBwYXJ0c1swXS50ZXh0ICE9IFwiZnVuXCIgfHwgcGFydHNbMV0udHlwZSAhPSBcInNpbXBsZV9pZGVudGlmaWVyXCIgfHxcbiAgICAgIHBhcnRzWzJdLnR5cGUgIT0gXCJmdW5jdGlvbl92YWx1ZV9wYXJhbWV0ZXJzXCIgfHwgcGFydHMuYXQoLTEpPy50eXBlICE9IFwiZnVuY3Rpb25fYm9keVwiKSB0aGlzLmZhaWwobm9kZSwgXCJmdW5jdGlvbiBkZWNsYXJhdGlvbiBzaGFwZVwiKVxuICAgIGlmICghcGFydHMuc29tZSgocGFydCkgPT4gcGFydC50ZXh0ID09IFwiOlwiKSkgcmV0dXJuIG1pc3NpbmdUeXBlKFwia290bGluXCIsIFwiRnVuY3Rpb24gcmV0dXJuXCIsIHRoaXMubG9jYXRpb24obm9kZSkpXG4gICAgaWYgKHBhcnRzLmxlbmd0aCAhPSA2IHx8IHBhcnRzWzNdLnRleHQgIT0gXCI6XCIpIHRoaXMuZmFpbChub2RlLCBcImZ1bmN0aW9uIGRlY2xhcmF0aW9uIHNoYXBlXCIpXG4gICAgdGhpcy5zaGFwZShub2RlLCBbXCJmdW5cIiwgcGFydHNbMV0sIHBhcnRzWzJdLCBcIjpcIiwgcGFydHNbNF0sIHBhcnRzWzVdXSlcbiAgICBjb25zdCBwYXJhbWV0ZXJQYXJ0cyA9IHRoaXMucGFydHMocGFydHNbMl0pXG4gICAgY29uc3QgcGFyYW1ldGVycyA9IHBhcmFtZXRlclBhcnRzLmZpbHRlcigocGFydCkgPT4gcGFydC50eXBlID09IFwicGFyYW1ldGVyXCIpXG5cbiAgICBpZiAocGFyYW1ldGVycy5sZW5ndGggIT0gMikgdGhpcy5mYWlsKHBhcnRzWzJdLCBcImZ1bmN0aW9uIHBhcmFtZXRlciBjb3VudCBvdGhlciB0aGFuIHR3b1wiKVxuICAgIHRoaXMuc2hhcGUocGFydHNbMl0sIFtcIihcIiwgcGFyYW1ldGVyc1swXSwgXCIsXCIsIHBhcmFtZXRlcnNbMV0sIFwiKVwiXSlcbiAgICBjb25zdCBuYW1lID0gdGhpcy5pZGVudGlmaWVyKHBhcnRzWzFdKVxuXG4gICAgcmV0dXJuIHdpdGhQYXJzZXJSYW5nZXMoe1xuICAgICAgYm9keTogdGhpcy5ibG9jayhwYXJ0c1s1XSksIGtpbmQ6IC8qKiBAdHlwZSB7Y29uc3R9ICovIChcIkZ1bmN0aW9uRGVjbGFyYXRpb25cIiksIGxvY2F0aW9uOiB0aGlzLmxvY2F0aW9uKG5vZGUpLCBuYW1lLFxuICAgICAgcGFyYW1ldGVyczogcGFyYW1ldGVycy5tYXAoKHBhcmFtZXRlcikgPT4gdGhpcy5wYXJhbWV0ZXIocGFyYW1ldGVyKSksIHJldHVyblR5cGU6IHRoaXMudHlwZShwYXJ0c1s0XSlcbiAgICB9LCB7bmFtZTogdGhpcy5sb2NhdGlvbihwYXJ0c1sxXSl9KVxuICB9XG5cbiAgLyoqXG4gICAqIENvbnZlcnRzIHRoZSBleGFjdCBmaW5hbCBtYWluIGZ1bmN0aW9uLlxuICAgKiBAcGFyYW0ge2ltcG9ydChcInRyZWUtc2l0dGVyXCIpLlN5bnRheE5vZGV9IG5vZGUgLSBNYWluIGRlY2xhcmF0aW9uIG5vZGUuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5FbnRyeVBvaW50fSBTZW1hbnRpYyBlbnRyeSBwb2ludC5cbiAgICovXG4gIG1haW4obm9kZSkge1xuICAgIGNvbnN0IHBhcnRzID0gdGhpcy5wYXJ0cyhub2RlKVxuXG4gICAgaWYgKG5vZGUudHlwZSAhPSBcImZ1bmN0aW9uX2RlY2xhcmF0aW9uXCIgfHwgcGFydHMubGVuZ3RoICE9IDQgfHwgcGFydHNbMF0udGV4dCAhPSBcImZ1blwiIHx8XG4gICAgICB0aGlzLmlkZW50aWZpZXIocGFydHNbMV0sIHRydWUpICE9IFwibWFpblwiIHx8IHBhcnRzWzJdLnR5cGUgIT0gXCJmdW5jdGlvbl92YWx1ZV9wYXJhbWV0ZXJzXCIgfHwgcGFydHNbM10udHlwZSAhPSBcImZ1bmN0aW9uX2JvZHlcIikge1xuICAgICAgdGhpcy5mYWlsKG5vZGUsIFwiZXhhY3QgbWFpbiBkZWNsYXJhdGlvbiByZXF1aXJlZFwiKVxuICAgIH1cbiAgICB0aGlzLnNoYXBlKHBhcnRzWzJdLCBbXCIoXCIsIFwiKVwiXSlcbiAgICB0aGlzLnNoYXBlKG5vZGUsIFtcImZ1blwiLCBwYXJ0c1sxXSwgcGFydHNbMl0sIHBhcnRzWzNdXSlcbiAgICByZXR1cm4ge2JvZHk6IHRoaXMuYmxvY2socGFydHNbM10pLCBraW5kOiAvKiogQHR5cGUge2NvbnN0fSAqLyAoXCJFbnRyeVBvaW50XCIpLCBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihub2RlKX1cbiAgfVxuXG4gIC8qKlxuICAgKiBDb21wYXJlcyBzb3VyY2Ugc3VwcG9ydCB3aXRoIHRoZSBjYW5vbmljYWwgZ2VuZXJhdGVkIGhlbHBlciBDU1QuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZX0gYWN0dWFsIC0gU291cmNlIG5vZGUuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZX0gZXhwZWN0ZWQgLSBDYW5vbmljYWwgc3VwcG9ydCBub2RlLlxuICAgKiBAcmV0dXJucyB7dm9pZH1cbiAgICovXG4gIGNvbXBhcmVUcmVlKGFjdHVhbCwgZXhwZWN0ZWQpIHtcbiAgICBpZiAoYWN0dWFsLnR5cGUgIT0gZXhwZWN0ZWQudHlwZSB8fCBhY3R1YWwuaXNOYW1lZCAhPSBleHBlY3RlZC5pc05hbWVkIHx8IGFjdHVhbC5pc0V4dHJhICE9IGV4cGVjdGVkLmlzRXh0cmEgfHxcbiAgICAgIGFjdHVhbC5jaGlsZENvdW50ICE9IGV4cGVjdGVkLmNoaWxkQ291bnQpIHRoaXMuZmFpbChhY3R1YWwsIFwibW9kaWZpZWQgS290bGluIHN1cHBvcnQgbm9kZVwiKVxuICAgIGlmICghYWN0dWFsLmNoaWxkQ291bnQgJiYgYWN0dWFsLnRleHQgIT0gZXhwZWN0ZWQudGV4dCkgdGhpcy5mYWlsKGFjdHVhbCwgXCJtb2RpZmllZCBLb3RsaW4gc3VwcG9ydCB0b2tlblwiKVxuICAgIGZvciAobGV0IGluZGV4ID0gMDsgaW5kZXggPCBhY3R1YWwuY2hpbGRDb3VudDsgaW5kZXggKz0gMSkge1xuICAgICAgY29uc3QgbGVmdCA9IGFjdHVhbC5jaGlsZChpbmRleClcbiAgICAgIGNvbnN0IHJpZ2h0ID0gZXhwZWN0ZWQuY2hpbGQoaW5kZXgpXG5cbiAgICAgIGlmICghbGVmdCB8fCAhcmlnaHQgfHwgYWN0dWFsLmZpZWxkTmFtZUZvckNoaWxkKGluZGV4KSAhPSBleHBlY3RlZC5maWVsZE5hbWVGb3JDaGlsZChpbmRleCkpIHtcbiAgICAgICAgdGhpcy5mYWlsKGxlZnQgPz8gYWN0dWFsLCBcIm1vZGlmaWVkIEtvdGxpbiBzdXBwb3J0IGZpZWxkXCIpXG4gICAgICB9XG4gICAgICB0aGlzLmNvbXBhcmVUcmVlKGxlZnQsIHJpZ2h0KVxuICAgIH1cbiAgfVxuXG4gIC8qKlxuICAgKiBDb252ZXJ0cyBhbmQgdmFsaWRhdGVzIG9uZSBjb21wbGV0ZSBLb3RsaW4gc291cmNlIGZpbGUuXG4gICAqIEBwYXJhbSB7aW1wb3J0KFwidHJlZS1zaXR0ZXJcIikuU3ludGF4Tm9kZX0gcm9vdCAtIFNvdXJjZSBmaWxlIHJvb3QuXG4gICAqIEByZXR1cm5zIHtpbXBvcnQoXCIuLi9zZW1hbnRpYy90eXBlcy5qc1wiKS5TZW1hbnRpY01vZHVsZX0gU2VtYW50aWMgbW9kdWxlLlxuICAgKi9cbiAgbW9kdWxlKHJvb3QpIHtcbiAgICB0aGlzLnZhbGlkYXRlVHJlZShyb290KVxuICAgIGlmIChyb290LnR5cGUgIT0gXCJzb3VyY2VfZmlsZVwiKSB0aGlzLmZhaWwocm9vdCwgXCJzb3VyY2UgZmlsZSByb290XCIpXG4gICAgY29uc3QgcGFydHMgPSB0aGlzLnBhcnRzKHJvb3QpXG4gICAgY29uc3Qgc3VwcG9ydFRyZWUgPSBwYXJzZXIucGFyc2Uoa290bGluUnVudGltZSlcbiAgICBjb25zdCBzdXBwb3J0ID0gdGhpcy5wYXJ0cyhzdXBwb3J0VHJlZS5yb290Tm9kZSlcbiAgICBsZXQgc3VwcG9ydEluZGV4ID0gMFxuXG4gICAgd2hpbGUgKHN1cHBvcnRJbmRleCA8IHBhcnRzLmxlbmd0aCAmJiBzdXBwb3J0SW5kZXggPCBzdXBwb3J0Lmxlbmd0aCAmJiBwYXJ0c1tzdXBwb3J0SW5kZXhdLnR5cGUgPT0gc3VwcG9ydFtzdXBwb3J0SW5kZXhdLnR5cGUpIHtcbiAgICAgIHRoaXMuY29tcGFyZVRyZWUocGFydHNbc3VwcG9ydEluZGV4XSwgc3VwcG9ydFtzdXBwb3J0SW5kZXhdKVxuICAgICAgc3VwcG9ydEluZGV4ICs9IDFcbiAgICB9XG4gICAgaWYgKHN1cHBvcnRJbmRleCA+IDAgJiYgc3VwcG9ydEluZGV4ICE9IHN1cHBvcnQubGVuZ3RoKSB0aGlzLmZhaWwocGFydHNbc3VwcG9ydEluZGV4IC0gMV0sIFwiY29tcGxldGUgS290bGluIHN1cHBvcnQgcmVxdWlyZWRcIilcbiAgICB0aGlzLnJ1bnRpbWUgPSBzdXBwb3J0SW5kZXggPT0gc3VwcG9ydC5sZW5ndGhcbiAgICBjb25zdCBzZW1hbnRpY1BhcnRzID0gcGFydHMuc2xpY2Uoc3VwcG9ydEluZGV4KVxuICAgIGNvbnN0IG1haW5JbmRleCA9IHNlbWFudGljUGFydHMuZmluZEluZGV4KChub2RlKSA9PiBub2RlLnR5cGUgPT0gXCJmdW5jdGlvbl9kZWNsYXJhdGlvblwiICYmIHRoaXMucGFydHMobm9kZSlbMV0/LnRleHQgPT0gXCJtYWluXCIpXG5cbiAgICBpZiAobWFpbkluZGV4IDwgMCkgdGhpcy5mYWlsKHJvb3QsIFwic291cmNlIGZpbGUgd2l0aG91dCBtYWluXCIpXG4gICAgaWYgKG1haW5JbmRleCA9PSAwKSB0aGlzLmZhaWwoc2VtYW50aWNQYXJ0c1swXSwgXCJ0b3AtbGV2ZWwgc2VtYW50aWMgZnVuY3Rpb24gcmVxdWlyZWRcIilcbiAgICBpZiAobWFpbkluZGV4ICE9IHNlbWFudGljUGFydHMubGVuZ3RoIC0gMSkgdGhpcy5mYWlsKHNlbWFudGljUGFydHNbbWFpbkluZGV4ICsgMV0sIFwiZGVjbGFyYXRpb24gYWZ0ZXIgbWFpblwiKVxuICAgIGNvbnN0IGRlY2xhcmF0aW9ucyA9IHNlbWFudGljUGFydHMuc2xpY2UoMCwgbWFpbkluZGV4KVxuXG4gICAgZm9yIChjb25zdCBkZWNsYXJhdGlvbiBvZiBkZWNsYXJhdGlvbnMpIHtcbiAgICAgIGlmIChkZWNsYXJhdGlvbi50eXBlICE9IFwiZnVuY3Rpb25fZGVjbGFyYXRpb25cIikgdGhpcy5mYWlsKGRlY2xhcmF0aW9uKVxuICAgIH1cbiAgICBjb25zdCBtb2R1bGUgPSB7XG4gICAgICBlbnRyeVBvaW50OiB0aGlzLm1haW4oc2VtYW50aWNQYXJ0c1ttYWluSW5kZXhdKSwgZnVuY3Rpb25zOiBkZWNsYXJhdGlvbnMubWFwKChkZWNsYXJhdGlvbikgPT4gdGhpcy5mdW5jdGlvbihkZWNsYXJhdGlvbikpLFxuICAgICAga2luZDogLyoqIEB0eXBlIHtjb25zdH0gKi8gKFwiTW9kdWxlXCIpLCBsb2NhdGlvbjogdGhpcy5sb2NhdGlvbihyb290KVxuICAgIH1cblxuICAgIHZhbGlkYXRlUGFyc2VkTW9kdWxlKG1vZHVsZSwgXCJrb3RsaW5cIilcbiAgICByZXR1cm4gbW9kdWxlXG4gIH1cbn1cblxuLyoqXG4gKiBQYXJzZXMgdGhlIHN0cmljdCBUYXNrIDAyMyBLb3RsaW4vSlZNIHByb2ZpbGUgdGhyb3VnaCB0aGUgcXVhbGlmaWVkIGdyYW1tYXIuXG4gKiBAcGFyYW0ge3tmaWxlbmFtZTogc3RyaW5nLCBzb3VyY2U6IHN0cmluZ319IGlucHV0IC0gRXhhY3Qgc291cmNlIHJlcXVlc3QuXG4gKiBAcmV0dXJucyB7aW1wb3J0KFwiLi4vc2VtYW50aWMvdHlwZXMuanNcIikuU2VtYW50aWNNb2R1bGV9IFNlbWFudGljIG1vZHVsZS5cbiAqL1xuZXhwb3J0IGZ1bmN0aW9uIHBhcnNlS290bGluKHtmaWxlbmFtZSwgc291cmNlfSkge1xuICBpZiAoIWhhc09ubHlVbmljb2RlU2NhbGFycyhzb3VyY2UpKSB7XG4gICAgY29uc3Qgb2Zmc2V0ID0gZmlyc3RMb25lU3Vycm9nYXRlT2Zmc2V0KHNvdXJjZSlcblxuICAgIHRocm93IG5ldyBTZW1hbnRpZm9sZERpYWdub3N0aWMoe1xuICAgICAgY29kZTogXCJQQVJTRV9FUlJPUlwiLCBsYW5ndWFnZTogXCJrb3RsaW5cIiwgbG9jYXRpb246IGxvY2F0aW9uRnJvbU9mZnNldHMoZmlsZW5hbWUsIHNvdXJjZSwgb2Zmc2V0LCBvZmZzZXQgKyAxKSxcbiAgICAgIG1lc3NhZ2U6IFwiS290bGluIHNvdXJjZSBjb250YWlucyBhbiBpbnZhbGlkIGxvbmUgVVRGLTE2IHN1cnJvZ2F0ZS5cIlxuICAgIH0pXG4gIH1cbiAgbGV0IHRyZWVcblxuICB0cnkge1xuICAgIHRyZWUgPSBwYXJzZXIucGFyc2Uoc291cmNlKVxuICB9IGNhdGNoIChlcnJvcikge1xuICAgIHRocm93IG5ldyBTZW1hbnRpZm9sZERpYWdub3N0aWMoe1xuICAgICAgY2F1c2U6IGVycm9yIGluc3RhbmNlb2YgRXJyb3IgPyBlcnJvciA6IHVuZGVmaW5lZCwgY29kZTogXCJQQVJTRV9FUlJPUlwiLCBsYW5ndWFnZTogXCJrb3RsaW5cIixcbiAgICAgIGxvY2F0aW9uOiBtb2R1bGVMb2NhdGlvbihmaWxlbmFtZSwgc291cmNlKSwgbWVzc2FnZTogXCJUaGUgcXVhbGlmaWVkIEtvdGxpbiBwYXJzZXIgY291bGQgbm90IHByb2R1Y2UgYSBjb21wbGV0ZSBDU1QuXCJcbiAgICB9KVxuICB9XG4gIHJldHVybiBuZXcgS290bGluUmVhZGVyKGZpbGVuYW1lLCBzb3VyY2UpLm1vZHVsZSh0cmVlLnJvb3ROb2RlKVxufVxuIl19