rea-agents 2.4.0 → 3.0.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 (231) hide show
  1. package/README.md +91 -19
  2. package/bridge/ghidra/ReaGhidraBridge.java +524 -4
  3. package/bridge/hopper_bridge.py +313 -28
  4. package/dist/application/AnalysisClientCleanup.js +14 -0
  5. package/dist/application/AnalysisContextQueries.js +130 -0
  6. package/dist/application/AnalysisSnapshotCache.js +4 -2
  7. package/dist/application/ApplicationWorkflowEvidenceResolver.js +31 -13
  8. package/dist/application/ArtifactInventory/scanCanonical.js +1 -1
  9. package/dist/application/BinarySession.js +20 -8
  10. package/dist/application/BinarySessionComposition.js +21 -0
  11. package/dist/application/BinarySessionRecords.js +79 -9
  12. package/dist/application/BinarySessionStatus.js +31 -1
  13. package/dist/application/BrowserEvidence.js +14 -0
  14. package/dist/application/BrowserScenarioCapturePort.js +1 -0
  15. package/dist/application/BrowserScenarioCaptureService.js +53 -0
  16. package/dist/application/BrowserScenarioEvidence.js +40 -0
  17. package/dist/application/CallPathTracing.js +160 -0
  18. package/dist/application/CapabilityInventory.js +84 -14
  19. package/dist/application/ClientRegistrationStatus.js +4 -1
  20. package/dist/application/CompositeProvider.js +10 -1
  21. package/dist/application/DirectAnalysis.js +13 -4
  22. package/dist/application/EnhancedLiteralTracing.js +118 -0
  23. package/dist/application/EnhancedTools.js +71 -127
  24. package/dist/application/EvidenceLedger.js +45 -16
  25. package/dist/application/JavaScriptApplicationWorkflowEvidence.js +13 -0
  26. package/dist/application/JavaScriptApplicationWorkflowService.js +27 -1
  27. package/dist/application/JavaScriptArtifactAnalysis.js +13 -4
  28. package/dist/application/JavaScriptRuntimeObservationEvidence.js +34 -0
  29. package/dist/application/JavaScriptRuntimeObservationPort.js +1 -0
  30. package/dist/application/JavaScriptRuntimeObservationService.js +46 -0
  31. package/dist/application/JavaScriptSemanticGraphAsyncProjection.js +147 -0
  32. package/dist/application/JavaScriptSemanticGraphBuilder.js +34 -6
  33. package/dist/application/JavaScriptSemanticGraphChildProcessProjection.js +156 -0
  34. package/dist/application/JavaScriptSemanticGraphConstruction.js +2 -2
  35. package/dist/application/JavaScriptSemanticGraphDataProjection.js +203 -0
  36. package/dist/application/JavaScriptSemanticGraphFingerprintProjection.js +25 -0
  37. package/dist/application/JavaScriptSemanticGraphFlowProjection.js +129 -8
  38. package/dist/application/JavaScriptSemanticGraphObjectProjection.js +81 -0
  39. package/dist/application/JavaScriptSemanticGraphProjection.js +14 -7
  40. package/dist/application/JavaScriptSemanticGraphResourceProjection.js +59 -0
  41. package/dist/application/JavaScriptSemanticGraphValueProjection.js +77 -0
  42. package/dist/application/LazyAnalysisProvider.js +77 -0
  43. package/dist/application/LoopbackReplay.js +1 -1
  44. package/dist/application/NativeApiInspection.js +80 -0
  45. package/dist/application/ProcessReactiveEffects.js +6 -0
  46. package/dist/application/ProcessReactiveHarness.js +16 -1
  47. package/dist/application/ProjectPermissionStore.js +1 -0
  48. package/dist/application/ReconstructionObligationAuthority.js +72 -0
  49. package/dist/application/ReconstructionObligationCandidates.js +265 -0
  50. package/dist/application/ReconstructionObligationLedgerDiagnostics.js +47 -0
  51. package/dist/application/ReconstructionObligationLedgerEvaluation.js +263 -0
  52. package/dist/application/ReconstructionObligationLedgerProjection.js +86 -0
  53. package/dist/application/ReconstructionObligationLedgerService.js +72 -0
  54. package/dist/application/ReconstructionObligationOriginalCases.js +33 -0
  55. package/dist/application/ReconstructionObligationPolicies.js +132 -0
  56. package/dist/application/ReconstructionReadinessService.js +48 -0
  57. package/dist/application/SessionProviderRouter.js +6 -6
  58. package/dist/application/SetupClientConfiguration.js +4 -2
  59. package/dist/application/runtime.js +26 -9
  60. package/dist/artifacts/ArtifactProvider.js +87 -22
  61. package/dist/browser/BrowserScenarioSecrets.js +53 -0
  62. package/dist/browser/BrowserScenarioSessionPort.js +1 -0
  63. package/dist/browser/CdpBrowserProvider.js +2 -2
  64. package/dist/browser/CdpCaptureDocuments.js +57 -0
  65. package/dist/browser/CdpCaptureStorage.js +71 -29
  66. package/dist/browser/CdpCaptureStorageFingerprints.js +328 -0
  67. package/dist/browser/CdpEndpoint.js +8 -6
  68. package/dist/browser/CdpPageCapture.js +2 -0
  69. package/dist/browser/JavaScriptRuntimeScope.js +38 -0
  70. package/dist/browser/PlaywrightBrowserScenarioProvider.js +259 -0
  71. package/dist/browser/PlaywrightExecutionBoundary.js +42 -0
  72. package/dist/browser/PlaywrightScenarioActions.js +62 -0
  73. package/dist/browser/PlaywrightScenarioArtifacts.js +238 -0
  74. package/dist/browser/PlaywrightScenarioBrowser.js +144 -0
  75. package/dist/browser/PlaywrightScenarioEvents.js +301 -0
  76. package/dist/browser/PlaywrightScenarioSession.js +300 -0
  77. package/dist/browser/V8InspectorCaptureProjection.js +110 -0
  78. package/dist/browser/V8InspectorEndpoint.js +72 -0
  79. package/dist/browser/V8InspectorProvider.js +267 -0
  80. package/dist/catalogIdentity.js +11 -3
  81. package/dist/cli/artifactCommands.js +44 -3
  82. package/dist/cli/coreAnalysisCommands.js +78 -0
  83. package/dist/cli.js +4 -0
  84. package/dist/cliApplicationCommands.js +30 -2
  85. package/dist/cliBrowserAdvancedCommands.js +17 -5
  86. package/dist/cliBrowserCommands.js +1 -0
  87. package/dist/cliBrowserScenarioCommands.js +43 -0
  88. package/dist/cliCommandNames.js +9 -0
  89. package/dist/cliJavaScriptRuntimeCommands.js +164 -0
  90. package/dist/cliObservationOptions.js +4 -0
  91. package/dist/cliPolicyCommands.js +1 -0
  92. package/dist/config/environment.js +12 -0
  93. package/dist/config/parseConfig.js +88 -17
  94. package/dist/contracts/analysisSearchContract.js +14 -0
  95. package/dist/contracts/applicationToolContracts.js +86 -2
  96. package/dist/contracts/applicationWorkflowInputContracts.js +18 -0
  97. package/dist/contracts/artifactToolContracts.js +29 -2
  98. package/dist/contracts/browserProviderToolContracts.js +7 -0
  99. package/dist/contracts/browserScenarioToolContracts.js +81 -0
  100. package/dist/contracts/browserToolContracts.js +88 -98
  101. package/dist/contracts/enhancedInputs.js +35 -6
  102. package/dist/contracts/functionInstructionContract.js +8 -0
  103. package/dist/contracts/functionWorkflowToolContracts.js +30 -0
  104. package/dist/contracts/hopperMemoryContracts.js +22 -0
  105. package/dist/contracts/javascriptApplicationWorkflowExamples.js +42 -0
  106. package/dist/contracts/javascriptRuntimeObservationToolContracts.js +58 -0
  107. package/dist/contracts/promptContracts.js +14 -15
  108. package/dist/contracts/reconstructionReadinessExample.js +436 -0
  109. package/dist/contracts/toolContractExamples.js +8 -0
  110. package/dist/contracts/toolContractTypes.js +1 -0
  111. package/dist/contracts/toolContracts.js +34 -25
  112. package/dist/contracts/toolEffects.js +25 -0
  113. package/dist/contracts/toolOutputSchemaGroups.js +120 -30
  114. package/dist/contracts/toolOutputSchemaPrimitives.js +37 -0
  115. package/dist/domain/analysisErrorPresentation.js +8 -2
  116. package/dist/domain/analysisErrorProjection.js +9 -0
  117. package/dist/domain/artifactInspection.js +347 -0
  118. package/dist/domain/browserCaptureComparison.js +82 -0
  119. package/dist/domain/browserObservation.js +8 -1
  120. package/dist/domain/browserObservationErrors.js +1 -0
  121. package/dist/domain/browserObservationSchemas.js +26 -0
  122. package/dist/domain/browserScenario.js +165 -0
  123. package/dist/domain/browserScenarioCapture.js +57 -0
  124. package/dist/domain/browserScenarioCaptureValues.js +204 -0
  125. package/dist/domain/browserScenarioDiff.js +324 -0
  126. package/dist/domain/browserScenarioDiffValues.js +157 -0
  127. package/dist/domain/browserScenarioNormalization.js +45 -0
  128. package/dist/domain/browserScenarioValues.js +372 -0
  129. package/dist/domain/bytecodeProvider.js +179 -0
  130. package/dist/domain/conformancePackage.js +169 -0
  131. package/dist/domain/conformanceReplay.js +104 -0
  132. package/dist/domain/conformanceTrustGate.js +193 -0
  133. package/dist/domain/customProtocolCapture.js +137 -0
  134. package/dist/domain/eventProcessTree.js +214 -0
  135. package/dist/domain/evidenceBundle.js +47 -0
  136. package/dist/domain/hopperStartupFailure.js +1 -1
  137. package/dist/domain/hopperValues.js +14 -1
  138. package/dist/domain/inputIssueProjection.js +7 -1
  139. package/dist/domain/javascriptRuntimeObservation.js +170 -0
  140. package/dist/domain/javascriptRuntimeReconciliationParsing.js +120 -2
  141. package/dist/domain/javascriptRuntimeReconciliationResult.js +3 -3
  142. package/dist/domain/javascriptRuntimeReconciliationRuntime.js +2 -2
  143. package/dist/domain/javascriptRuntimeReconciliationSchemas.js +1 -1
  144. package/dist/domain/javascriptSemanticAnalysis.js +13 -16
  145. package/dist/domain/javascriptSemanticAsyncEffects.js +253 -0
  146. package/dist/domain/javascriptSemanticChildProcesses.js +237 -0
  147. package/dist/domain/javascriptSemanticDataEffectHelpers.js +125 -0
  148. package/dist/domain/javascriptSemanticDataEffects.js +284 -0
  149. package/dist/domain/javascriptSemanticDerivedAnalysis.js +41 -0
  150. package/dist/domain/javascriptSemanticFingerprints.js +174 -0
  151. package/dist/domain/javascriptSemanticIr.js +21 -1
  152. package/dist/domain/javascriptSemanticObjects.js +115 -0
  153. package/dist/domain/javascriptSemanticPromises.js +290 -0
  154. package/dist/domain/javascriptSemanticResources.js +136 -0
  155. package/dist/domain/javascriptSourceParser.js +15 -0
  156. package/dist/domain/javascriptStaticAnalysis.js +12 -15
  157. package/dist/domain/javascriptStaticAnalysisBundler.js +38 -0
  158. package/dist/domain/javascriptStaticAnalysisCalls.js +23 -1
  159. package/dist/domain/javascriptStaticAnalysisHelpers.js +8 -0
  160. package/dist/domain/mobileApplicationInvestigation.js +159 -0
  161. package/dist/domain/nativeApiBoundary.js +130 -0
  162. package/dist/domain/objcSwiftMetadata.js +150 -0
  163. package/dist/domain/packageAnalysis.js +123 -0
  164. package/dist/domain/peInspection.js +196 -0
  165. package/dist/domain/processCapture.js +8 -2
  166. package/dist/domain/processReactiveScenario.js +1 -0
  167. package/dist/domain/processReactiveTransition.js +9 -4
  168. package/dist/domain/protocolCapture.js +243 -0
  169. package/dist/domain/providerCleanupError.js +11 -0
  170. package/dist/domain/reconstructionObligationLedgerSchemas.js +278 -0
  171. package/dist/domain/reconstructionReadiness.js +121 -0
  172. package/dist/domain/reconstructionReadinessFindingHelpers.js +17 -0
  173. package/dist/domain/reconstructionReadinessIntegrityFindings.js +118 -0
  174. package/dist/domain/reconstructionReadinessJourneyFindings.js +193 -0
  175. package/dist/domain/reconstructionReadinessSchemas.js +240 -0
  176. package/dist/domain/sourceToBundleComparison.js +335 -0
  177. package/dist/domain/sourceToBundleComparisonSchemas.js +133 -0
  178. package/dist/domain/sourceToBundleSignals.js +202 -0
  179. package/dist/domain/webCaptureDiff.js +141 -27
  180. package/dist/domain/webScreenshot.js +1 -1
  181. package/dist/dotnet/ManagedStaticProvider.js +34 -5
  182. package/dist/generatedMcpToolCatalog.js +37 -0
  183. package/dist/generatedPackageMetadata.js +4 -4
  184. package/dist/ghidra/GhidraDefaults.js +1 -1
  185. package/dist/ghidra/GhidraFunctionValues.js +40 -2
  186. package/dist/ghidra/GhidraProviderCapabilities.js +47 -38
  187. package/dist/hopper/HopperCleanup.js +158 -0
  188. package/dist/hopper/HopperClient.js +93 -99
  189. package/dist/hopper/HopperProvider.js +61 -30
  190. package/dist/hopper/HopperRequestQueue.js +215 -0
  191. package/dist/hopper/HopperResponseStream.js +46 -0
  192. package/dist/hopper/protocol.js +63 -20
  193. package/dist/main/transport.js +24 -27
  194. package/dist/main.js +14 -6
  195. package/dist/mcpDoctor.js +27 -4
  196. package/dist/mcpStartupPolicy.js +14 -0
  197. package/dist/process/ProcessCommandIdentity.js +19 -0
  198. package/dist/process/ProcessOwnership.js +11 -8
  199. package/dist/server/DynamicToolAvailability.js +70 -0
  200. package/dist/server/LazyToolCatalog.js +134 -0
  201. package/dist/server/createServer.js +92 -154
  202. package/dist/server/hydrateServerTools.js +191 -0
  203. package/dist/server/lifecycleProgress.js +10 -0
  204. package/dist/server/permissionFailure.js +12 -0
  205. package/dist/server/registerApplicationTools/compareSourceToBundle.js +35 -0
  206. package/dist/server/registerApplicationTools/helpers.js +11 -7
  207. package/dist/server/registerApplicationTools/obligationLedger.js +27 -0
  208. package/dist/server/registerApplicationTools/readiness.js +55 -0
  209. package/dist/server/registerApplicationTools.js +6 -0
  210. package/dist/server/registerArtifactTools.js +9 -1
  211. package/dist/server/registerBrowserScenarioTool.js +25 -0
  212. package/dist/server/registerBrowserTools.js +2 -2
  213. package/dist/server/registerCloseLifecycleTool.js +57 -0
  214. package/dist/server/registerEnhancedTools.js +28 -7
  215. package/dist/server/registerEvidenceResources.js +54 -101
  216. package/dist/server/registerEvidenceTools.js +9 -2
  217. package/dist/server/registerInvestigationTools.js +1 -2
  218. package/dist/server/registerJavaScriptApplicationGraphResource.js +0 -4
  219. package/dist/server/registerJavaScriptRuntimeObservationTools.js +37 -0
  220. package/dist/server/registerReconstructionObligationLedgerResource.js +32 -0
  221. package/dist/server/registerReconstructionReadinessResource.js +32 -0
  222. package/dist/server/registerSessionRecordTools.js +82 -12
  223. package/dist/server/registerSessionStatusTool.js +11 -8
  224. package/dist/server/registerSessionTools.js +32 -58
  225. package/dist/server/sessionAvailabilityPolicy.js +10 -8
  226. package/dist/server/toolRegistrationOptions.js +21 -6
  227. package/dist/server/toolResult.js +12 -0
  228. package/package.json +28 -11
  229. package/scripts/package-runner-bootstrap.mjs +72 -0
  230. package/scripts/rea.mjs +11 -1
  231. package/skills/reverse-engineer-anything/SKILL.md +10 -3
@@ -1,25 +1,37 @@
1
1
  import { randomBytes } from "node:crypto";
2
2
  import { CLIENT_CAPABILITIES_META_KEY, createRequestStateCodec, McpServer, PROTOCOL_VERSION_META_KEY, } from "@modelcontextprotocol/server";
3
3
  import { PRODUCT_IDENTITY } from "../identity.js";
4
- import { registerEnhancedTools } from "./registerEnhancedTools.js";
5
- import { registerOfficialTools } from "./registerOfficialTools.js";
6
- import { registerSessionTools } from "./registerSessionTools.js";
7
- import { registerNativeTools } from "./registerNativeTools.js";
8
- import { registerArtifactTools } from "./registerArtifactTools.js";
9
- import { registerManagedTools } from "./registerManagedTools.js";
10
- import { registerManagedWorkflowTools } from "./registerManagedWorkflowTools.js";
11
4
  import { silentLogger } from "../logger.js";
12
5
  import { registerGuidedPrompts } from "./registerPrompts.js";
13
6
  import { registerEvidenceResources } from "./registerEvidenceResources.js";
14
- import { createServerIdentity } from "../serverIdentity.js";
15
- import { registerBrowserTools } from "./registerBrowserTools.js";
16
- import { registerElectronTools } from "./registerElectronTools.js";
17
- import { registerApplicationTools } from "./registerApplicationTools.js";
18
- const TARGET_FREE_INSTRUCTIONS = "REA analyzes shipped artifacts. Route: ASAR/JavaScript -> analyze_javascript_application (configured root required); archive/package -> inventory_artifact; managed PE/CLI -> inspect_managed_artifact; browser/Electron runtime -> list_browser_targets/list_electron_targets; native binary/database -> open_binary, then binary_overview. Check binary_session for policy. Start with summaries and cite Evidence IDs. Never repeat identical analysis or read full Evidence without a specific need.";
7
+ import { sessionAvailabilityPolicy } from "./sessionAvailabilityPolicy.js";
8
+ import { DENY_EVIDENCE_FILE_POLICY, DENY_PROCESS_POLICY, } from "./sessionToolPolicies.js";
9
+ import { installDynamicToolAvailability } from "./DynamicToolAvailability.js";
10
+ const TARGET_FREE_INSTRUCTIONS = "ASAR/JavaScript -> analyze_javascript_application; archive/package -> open_binary(path), then inspect_artifact/inventory_artifact (active target); managed PE/CLI -> inspect_managed_artifact; passive browser/Electron -> list_browser_targets/list_electron_targets; approved browser interaction -> capture_browser_scenario; Node/Electron Inspector -> list_javascript_runtime_targets; native binary/database -> open_binary, then binary_overview. Start with binary_session; call only tools in tools/list. Hidden routes: binary_session detail=capabilities. Use summaries, cite Evidence IDs. Never repeat identical analysis or read full Evidence.";
19
11
  const ACTIVE_TARGET_INSTRUCTIONS = "REA analyzes the active reverse-engineering target. Start native analysis with binary_overview, then narrow with analyze_function, literal search, callers, callees, and xrefs. Prefer summary views, never repeat an identical call, and read full Evidence only when the task requires it.";
20
- import { LinuxJavaScriptReplayRunner } from "../replay/LinuxJavaScriptReplayRunner.js";
21
- import { SystemJavaScriptReplayHost } from "../replay/SystemJavaScriptReplayHost.js";
22
12
  import { PROCESS_CAPTURE_ELICITATION_POLICY, } from "./ProcessCaptureElicitation.js";
13
+ import { LazyToolCatalog } from "./LazyToolCatalog.js";
14
+ const installSessionToolAvailability = (server, session, options) => {
15
+ if (session === undefined)
16
+ return undefined;
17
+ const policy = sessionAvailabilityPolicy(options.availabilityPolicy, {
18
+ processPolicy: options.processPolicy ?? DENY_PROCESS_POLICY,
19
+ evidenceFilePolicy: options.evidenceFilePolicy ?? DENY_EVIDENCE_FILE_POLICY,
20
+ investigationInputRoots: options.investigationInputRoots ?? [],
21
+ optionalFeatures: {
22
+ browserObservationEnabled: options.browserObservation !== undefined,
23
+ browserScenarioEnabled: options.browserScenarioCapture !== undefined,
24
+ electronObservationEnabled: options.electronObservation !== undefined,
25
+ v8InspectorObservationEnabled: options.javascriptRuntimeObservation !== undefined,
26
+ javascriptReplayEnabled: options.javascriptReplayPolicy?.enabled ?? false,
27
+ managedRuntimeEnabled: options.managedRuntimePolicy?.enabled ?? false,
28
+ },
29
+ });
30
+ return {
31
+ policy,
32
+ controller: installDynamicToolAvailability(server, session, policy),
33
+ };
34
+ };
23
35
  /**
24
36
  * Construct one MCP server without acquiring subprocess resources.
25
37
  * Supplying a session adds target lifecycle tools; omitting it retains the
@@ -39,7 +51,7 @@ export const createServer = (analysis, session, options = {}) => {
39
51
  }, {
40
52
  capabilities: {
41
53
  tools: { listChanged: true },
42
- resources: { listChanged: true },
54
+ resources: { listChanged: true, subscribe: true },
43
55
  },
44
56
  inputRequired: {
45
57
  maxRounds: 3,
@@ -50,50 +62,81 @@ export const createServer = (analysis, session, options = {}) => {
50
62
  ? ACTIVE_TARGET_INSTRUCTIONS
51
63
  : TARGET_FREE_INSTRUCTIONS,
52
64
  });
65
+ const dynamicTools = installSessionToolAvailability(server, session, options);
53
66
  server.server.onclose = () => {
54
67
  permissionAuthority?.clearSessionGrants();
55
68
  };
69
+ if (dynamicTools !== undefined)
70
+ server.server.oninitialized = () => server.sendToolListChanged();
56
71
  session?.onAvailabilityChanged?.(() => server.sendToolListChanged());
57
72
  registerServerIdentityResource(server, startedAt);
58
73
  const toolLogger = logger.child({ layer: "server" });
59
74
  const { activeTarget, recordEvidence, recordEvidenceWithUnknown } = createSessionRecorders(server, session);
60
- const toolContext = {
61
- server,
62
- analysis,
63
- session,
64
- options,
65
- logger: toolLogger,
66
- permissionAuthority,
67
- activeTarget,
68
- recordEvidence,
69
- recordEvidenceWithUnknown,
75
+ const processCaptureElicitation = {
76
+ stateCodec: processCaptureStateCodec,
77
+ supported: (context) => {
78
+ const envelope = context.mcpReq.envelope;
79
+ const version = envelope?.[PROTOCOL_VERSION_META_KEY];
80
+ const capabilities = envelope?.[CLIENT_CAPABILITIES_META_KEY];
81
+ return (typeof version === "string" &&
82
+ PROCESS_CAPTURE_ELICITATION_POLICY.protocolVersions.some((supported) => supported === version) &&
83
+ isRecord(capabilities) &&
84
+ isRecord(capabilities.elicitation) &&
85
+ capabilities.elicitation.form !== undefined);
86
+ },
87
+ now: Date.now,
88
+ consumedNonces: new Map(),
70
89
  };
71
- registerBinaryAnalysisTools(toolContext);
72
- registerObservationTools(toolContext);
90
+ let optionalProviders;
91
+ const loadOptionalProviders = () => {
92
+ optionalProviders ??= options
93
+ .loadOptionalProviders?.()
94
+ .catch((cause) => {
95
+ optionalProviders = undefined;
96
+ throw cause;
97
+ });
98
+ return optionalProviders;
99
+ };
100
+ const lazyTools = new LazyToolCatalog(server, async (kind) => {
101
+ const needsObservationProviders = kind === "browser-provider" ||
102
+ kind === "electron-provider" ||
103
+ kind === "runtime-provider";
104
+ const [{ hydrateServerToolFamily }, loadedOptionalProviders] = await Promise.all([
105
+ import("./hydrateServerTools.js"),
106
+ needsObservationProviders ? loadOptionalProviders() : undefined,
107
+ ]);
108
+ const hydratedOptions = loadedOptionalProviders === undefined
109
+ ? options
110
+ : { ...options, ...loadedOptionalProviders };
111
+ await hydrateServerToolFamily({
112
+ kind,
113
+ server,
114
+ analysis,
115
+ session,
116
+ options: hydratedOptions,
117
+ context: {
118
+ logger: toolLogger,
119
+ permissionAuthority,
120
+ activeTarget,
121
+ recordEvidence,
122
+ recordEvidenceWithUnknown,
123
+ availabilityPolicy: dynamicTools?.policy,
124
+ startedAt,
125
+ processCaptureElicitation,
126
+ },
127
+ });
128
+ }, session !== undefined);
129
+ lazyTools.register();
73
130
  registerGuidedPrompts(server, analysis, session);
74
131
  if (session !== undefined) {
75
132
  registerEvidenceResources(server, session);
76
- registerSessionTools(server, session, toolLogger, {
77
- ...options,
78
- ...(permissionAuthority === undefined ? {} : { permissionAuthority }),
79
- startedAt,
80
- processCaptureElicitation: {
81
- stateCodec: processCaptureStateCodec,
82
- supported: (context) => {
83
- const envelope = context.mcpReq.envelope;
84
- const version = envelope?.[PROTOCOL_VERSION_META_KEY];
85
- const capabilities = envelope?.[CLIENT_CAPABILITIES_META_KEY];
86
- return (typeof version === "string" &&
87
- PROCESS_CAPTURE_ELICITATION_POLICY.protocolVersions.some((supported) => supported === version) &&
88
- isRecord(capabilities) &&
89
- isRecord(capabilities.elicitation) &&
90
- capabilities.elicitation.form !== undefined);
91
- },
92
- now: Date.now,
93
- consumedNonces: new Map(),
94
- },
95
- });
96
133
  }
134
+ dynamicTools?.controller.synchronize();
135
+ const close = server.close.bind(server);
136
+ server.close = async () => {
137
+ await lazyTools.close();
138
+ await close();
139
+ };
97
140
  return server;
98
141
  };
99
142
  const createSessionRecorders = (server, session) => ({
@@ -102,16 +145,12 @@ const createSessionRecorders = (server, session) => ({
102
145
  ? undefined
103
146
  : (evidence) => {
104
147
  const recorded = session.recordEvidence(evidence);
105
- if (recorded.ok && recorded.value === "added")
106
- server.sendResourceListChanged();
107
148
  return recorded;
108
149
  },
109
150
  recordEvidenceWithUnknown: session === undefined
110
151
  ? undefined
111
152
  : (evidence, input) => {
112
153
  const recorded = session.recordEvidenceWithUnknown(evidence, input);
113
- if (recorded.ok)
114
- server.sendResourceListChanged();
115
154
  return recorded;
116
155
  },
117
156
  });
@@ -120,7 +159,8 @@ const registerServerIdentityResource = (server, startedAt) => {
120
159
  title: "REA server identity",
121
160
  description: "Live package, SDK, protocol, and catalog identity.",
122
161
  mimeType: "application/json",
123
- }, (uri) => {
162
+ }, async (uri) => {
163
+ const { createServerIdentity } = await import("../serverIdentity.js");
124
164
  const client = server.server.getClientVersion();
125
165
  const protocolVersion = server.server.getNegotiatedProtocolVersion();
126
166
  return {
@@ -138,106 +178,4 @@ const registerServerIdentityResource = (server, startedAt) => {
138
178
  };
139
179
  });
140
180
  };
141
- const registerBinaryAnalysisTools = ({ server, analysis, session, options, logger, permissionAuthority, activeTarget, recordEvidence, recordEvidenceWithUnknown, }) => {
142
- const recordUnknown = session === undefined
143
- ? undefined
144
- : (input) => session.recordUnknown(input);
145
- registerOfficialTools(server, analysis, {
146
- logger,
147
- activeTarget,
148
- recordEvidence,
149
- recordUnknown,
150
- });
151
- registerEnhancedTools(server, analysis, {
152
- logger,
153
- activeTarget,
154
- analysisProfile: session === undefined ? undefined : () => session.analysisProfile(),
155
- recordEvidence,
156
- recordUnknown,
157
- });
158
- registerNativeTools(server, analysis, {
159
- logger,
160
- activeTarget,
161
- recordEvidence,
162
- });
163
- registerArtifactTools(server, analysis, {
164
- logger,
165
- activeTarget,
166
- recordEvidence,
167
- ...(permissionAuthority === undefined ? {} : { permissionAuthority }),
168
- });
169
- registerManagedTools(server, analysis, {
170
- logger,
171
- activeTarget,
172
- recordEvidence,
173
- session,
174
- });
175
- if (session !== undefined)
176
- registerManagedWorkflowTools(server, {
177
- logger,
178
- recordEvidence,
179
- recordEvidenceWithUnknown,
180
- session,
181
- runtime: {
182
- policy: options.managedRuntimePolicy ?? {
183
- enabled: false,
184
- roots: [],
185
- executablePath: "/usr/bin/dotnet",
186
- },
187
- authority: permissionAuthority,
188
- },
189
- });
190
- };
191
- const registerObservationTools = ({ server, session, options, logger, permissionAuthority, recordEvidence, recordEvidenceWithUnknown, }) => {
192
- registerBrowserTools(server, {
193
- logger,
194
- browser: options.browserObservation,
195
- permissionAuthority,
196
- recordEvidence,
197
- });
198
- registerElectronTools(server, {
199
- logger,
200
- electron: options.electronObservation,
201
- permissionAuthority,
202
- recordEvidence,
203
- });
204
- registerApplicationTools(server, {
205
- logger,
206
- recordEvidence,
207
- recordEvidenceWithUnknown,
208
- evidenceLookup: session === undefined
209
- ? undefined
210
- : (evidenceId) => session.evidenceById(evidenceId),
211
- evidenceFilePolicy: options.evidenceFilePolicy ?? {
212
- roots: [],
213
- maxBytes: 1,
214
- maxDepth: 1,
215
- maxStringLength: 1,
216
- maxNodes: 1,
217
- },
218
- permissionAuthority,
219
- retainCoverageWorkspace: session === undefined
220
- ? undefined
221
- : (workspace) => {
222
- const retained = session.retainReconstructionCoverageWorkspace(workspace);
223
- if (retained === "added")
224
- server.sendResourceListChanged();
225
- return retained;
226
- },
227
- replay: {
228
- policy: options.javascriptReplayPolicy ?? {
229
- enabled: false,
230
- roots: [],
231
- nodePath: process.execPath,
232
- bubblewrapPath: "/usr/bin/bwrap",
233
- systemdRunPath: "/usr/bin/systemd-run",
234
- systemctlPath: "/usr/bin/systemctl",
235
- shellPath: "/usr/bin/bash",
236
- },
237
- host: options.javascriptReplayHost ?? new SystemJavaScriptReplayHost(),
238
- runner: options.javascriptReplayRunner ?? new LinuxJavaScriptReplayRunner(),
239
- authority: permissionAuthority,
240
- },
241
- });
242
- };
243
181
  const isRecord = (value) => typeof value === "object" && value !== null && !Array.isArray(value);
@@ -0,0 +1,191 @@
1
+ /**
2
+ * Install production callbacks on generated lazy tool registrations.
3
+ */
4
+ export const hydrateServerToolFamily = async ({ kind, server, analysis, session, options, context, }) => {
5
+ const toolContext = {
6
+ server,
7
+ analysis,
8
+ session,
9
+ options,
10
+ logger: context.logger,
11
+ permissionAuthority: context.permissionAuthority,
12
+ activeTarget: context.activeTarget,
13
+ recordEvidence: context.recordEvidence,
14
+ recordEvidenceWithUnknown: context.recordEvidenceWithUnknown,
15
+ };
16
+ switch (kind) {
17
+ case "official-proxy": {
18
+ const { registerOfficialTools } = await import("./registerOfficialTools.js");
19
+ registerOfficialTools(server, analysis, analysisOptions(toolContext));
20
+ return;
21
+ }
22
+ case "enhanced": {
23
+ const { registerEnhancedTools } = await import("./registerEnhancedTools.js");
24
+ registerEnhancedTools(server, analysis, enhancedOptions(toolContext));
25
+ return;
26
+ }
27
+ case "native-provider": {
28
+ const { registerNativeTools } = await import("./registerNativeTools.js");
29
+ registerNativeTools(server, analysis, evidenceOptions(toolContext));
30
+ return;
31
+ }
32
+ case "artifact-provider": {
33
+ const { registerArtifactTools } = await import("./registerArtifactTools.js");
34
+ registerArtifactTools(server, analysis, {
35
+ ...evidenceOptions(toolContext),
36
+ ...(context.permissionAuthority === undefined
37
+ ? {}
38
+ : { permissionAuthority: context.permissionAuthority }),
39
+ });
40
+ return;
41
+ }
42
+ case "managed-provider": {
43
+ const { registerManagedTools } = await import("./registerManagedTools.js");
44
+ registerManagedTools(server, analysis, {
45
+ ...evidenceOptions(toolContext),
46
+ session,
47
+ });
48
+ return;
49
+ }
50
+ case "application":
51
+ await registerApplicationFamily(toolContext);
52
+ return;
53
+ case "browser-provider":
54
+ case "electron-provider":
55
+ case "runtime-provider": {
56
+ await hydrateObservationFamily(kind, toolContext);
57
+ return;
58
+ }
59
+ case "session": {
60
+ if (session === undefined)
61
+ throw new TypeError("Session tools require a binary session");
62
+ const { registerSessionTools } = await import("./registerSessionTools.js");
63
+ registerSessionTools(server, session, context.logger, {
64
+ ...options,
65
+ ...(context.availabilityPolicy === undefined
66
+ ? {}
67
+ : { availabilityPolicy: context.availabilityPolicy }),
68
+ ...(context.permissionAuthority === undefined
69
+ ? {}
70
+ : { permissionAuthority: context.permissionAuthority }),
71
+ startedAt: context.startedAt,
72
+ processCaptureElicitation: context.processCaptureElicitation,
73
+ });
74
+ }
75
+ }
76
+ };
77
+ const hydrateObservationFamily = async (kind, context) => {
78
+ const common = {
79
+ logger: context.logger,
80
+ permissionAuthority: context.permissionAuthority,
81
+ recordEvidence: context.recordEvidence,
82
+ };
83
+ if (kind === "browser-provider") {
84
+ const [{ registerBrowserTools }, { registerBrowserScenarioTool }] = await Promise.all([
85
+ import("./registerBrowserTools.js"),
86
+ import("./registerBrowserScenarioTool.js"),
87
+ ]);
88
+ registerBrowserTools(context.server, {
89
+ ...common,
90
+ browser: context.options.browserObservation,
91
+ });
92
+ registerBrowserScenarioTool(context.server, {
93
+ ...common,
94
+ provider: context.options.browserScenarioCapture,
95
+ });
96
+ return;
97
+ }
98
+ if (kind === "electron-provider") {
99
+ const { registerElectronTools } = await import("./registerElectronTools.js");
100
+ registerElectronTools(context.server, {
101
+ ...common,
102
+ electron: context.options.electronObservation,
103
+ });
104
+ return;
105
+ }
106
+ const { registerJavaScriptRuntimeObservationTools } = await import("./registerJavaScriptRuntimeObservationTools.js");
107
+ registerJavaScriptRuntimeObservationTools(context.server, {
108
+ ...common,
109
+ runtime: context.options.javascriptRuntimeObservation,
110
+ });
111
+ };
112
+ const analysisOptions = ({ logger, activeTarget, recordEvidence, session, }) => {
113
+ const recordUnknown = session === undefined
114
+ ? undefined
115
+ : (input) => session.recordUnknown(input);
116
+ return {
117
+ logger,
118
+ activeTarget,
119
+ recordEvidence,
120
+ recordUnknown,
121
+ };
122
+ };
123
+ const enhancedOptions = (context) => ({
124
+ ...analysisOptions(context),
125
+ analysisProfile: context.session === undefined
126
+ ? undefined
127
+ : () => context.session?.analysisProfile(),
128
+ });
129
+ const evidenceOptions = ({ logger, activeTarget, recordEvidence, }) => ({
130
+ logger,
131
+ activeTarget,
132
+ recordEvidence,
133
+ });
134
+ const registerApplicationFamily = async ({ server, session, options, logger, permissionAuthority, recordEvidence, recordEvidenceWithUnknown, }) => {
135
+ const [{ registerApplicationTools }, { registerManagedWorkflowTools }, { LinuxJavaScriptReplayRunner }, { SystemJavaScriptReplayHost },] = await Promise.all([
136
+ import("./registerApplicationTools.js"),
137
+ import("./registerManagedWorkflowTools.js"),
138
+ import("../replay/LinuxJavaScriptReplayRunner.js"),
139
+ import("../replay/SystemJavaScriptReplayHost.js"),
140
+ ]);
141
+ if (session !== undefined)
142
+ registerManagedWorkflowTools(server, {
143
+ logger,
144
+ recordEvidence,
145
+ recordEvidenceWithUnknown,
146
+ session,
147
+ runtime: {
148
+ policy: options.managedRuntimePolicy ?? {
149
+ enabled: false,
150
+ roots: [],
151
+ executablePath: "/usr/bin/dotnet",
152
+ },
153
+ authority: permissionAuthority,
154
+ },
155
+ });
156
+ registerApplicationTools(server, {
157
+ logger,
158
+ recordEvidence,
159
+ recordEvidenceWithUnknown,
160
+ evidenceLookup: session === undefined
161
+ ? undefined
162
+ : (evidenceId) => session.evidenceById(evidenceId),
163
+ evidenceFilePolicy: options.evidenceFilePolicy ?? {
164
+ roots: [],
165
+ maxBytes: 1,
166
+ maxDepth: 1,
167
+ maxStringLength: 1,
168
+ maxNodes: 1,
169
+ },
170
+ permissionAuthority,
171
+ retainCoverageWorkspace: session === undefined
172
+ ? undefined
173
+ : (workspace) => {
174
+ return session.retainReconstructionCoverageWorkspace(workspace);
175
+ },
176
+ replay: {
177
+ policy: options.javascriptReplayPolicy ?? {
178
+ enabled: false,
179
+ roots: [],
180
+ nodePath: process.execPath,
181
+ bubblewrapPath: "/usr/bin/bwrap",
182
+ systemdRunPath: "/usr/bin/systemd-run",
183
+ systemctlPath: "/usr/bin/systemctl",
184
+ shellPath: "/usr/bin/bash",
185
+ },
186
+ host: options.javascriptReplayHost ?? new SystemJavaScriptReplayHost(),
187
+ runner: options.javascriptReplayRunner ?? new LinuxJavaScriptReplayRunner(),
188
+ authority: permissionAuthority,
189
+ },
190
+ });
191
+ };
@@ -0,0 +1,10 @@
1
+ /** Report one lifecycle operation start through the shared monotonic boundary. */
2
+ export const reportLifecycleStart = (progress, phase, message = "started") => progress.report({ phase, completed: 0, total: 1, message });
3
+ /** Report one lifecycle operation's terminal disposition. */
4
+ export const reportLifecycleEnd = (progress, phase, succeeded) => progress.report({
5
+ phase,
6
+ completed: 1,
7
+ total: 1,
8
+ message: succeeded ? "completed" : "failed",
9
+ terminal: true,
10
+ });
@@ -0,0 +1,12 @@
1
+ import { AnalysisProtocolError, PermissionRequiredError, } from "../domain/errors.js";
2
+ import { err } from "../domain/result.js";
3
+ /** Preserve a typed permission denial or contain an unexpected authority error. */
4
+ export const permissionFailure = (failure) => {
5
+ if (failure.ok)
6
+ return err(new AnalysisProtocolError("Expected a denied permission"));
7
+ return err(failure.error instanceof PermissionRequiredError
8
+ ? failure.error
9
+ : new AnalysisProtocolError(failure.error.message, {
10
+ cause: failure.error,
11
+ }));
12
+ };
@@ -0,0 +1,35 @@
1
+ import { compareSourceToBundleEvidenceValidated } from "../../application/JavaScriptApplicationWorkflowService.js";
2
+ import { resolveCompareSourceToBundleRequestValidated } from "../../application/ApplicationWorkflowEvidenceResolver.js";
3
+ import { applicationToolContract } from "../../contracts/applicationToolContracts.js";
4
+ import { compareSourceToBundleRequestSchema } from "../../contracts/applicationWorkflowInputContracts.js";
5
+ import { sourceToBundleComparisonResultSchema } from "../../domain/sourceToBundleComparisonSchemas.js";
6
+ import { logToolExecution } from "../toolLogging.js";
7
+ import { safeParseToolInput } from "../toolInputValidation.js";
8
+ import { toolRegistrationOptions } from "../toolRegistrationOptions.js";
9
+ import { toCallToolResult } from "../toolResult.js";
10
+ import { recordResult, recordSources } from "./helpers.js";
11
+ const contract = applicationToolContract("compare_source_to_bundle");
12
+ /** Register conservative historical-source to bundle comparison. */
13
+ export const registerCompareSourceToBundleTool = (server, options) => {
14
+ server.registerTool(contract.name, toolRegistrationOptions(contract), async (input) => {
15
+ const parsedInput = safeParseToolInput(compareSourceToBundleRequestSchema, input, contract.name);
16
+ if (!parsedInput.ok)
17
+ return toCallToolResult(parsedInput, contract);
18
+ const resolved = resolveCompareSourceToBundleRequestValidated(parsedInput.value, options.evidenceLookup);
19
+ if (!resolved.ok)
20
+ return toCallToolResult(resolved, contract);
21
+ const result = await logToolExecution(options.logger, contract.name, () => Promise.resolve(compareSourceToBundleEvidenceValidated(resolved.value)));
22
+ if (!result.ok)
23
+ return toCallToolResult(result, contract);
24
+ const recorded = recordSources(options.recordEvidence, [
25
+ resolved.value.application,
26
+ ]);
27
+ if (!recorded.ok)
28
+ return toCallToolResult(recorded, contract);
29
+ const comparison = sourceToBundleComparisonResultSchema.parse(result.value.normalized_result);
30
+ return recordResult(options, contract, result.value, resolved.value.unknown_registry_approved === true &&
31
+ comparison.summary.unknown > 0
32
+ ? "source-to-bundle-comparison"
33
+ : undefined);
34
+ });
35
+ };
@@ -23,7 +23,9 @@ const unknownRegistration = (evidence, kind) => ({
23
23
  approved: true,
24
24
  question: kind === "application-version-comparison"
25
25
  ? "Which application entities remain unmatched or ambiguous across these versions?"
26
- : "Which selected JavaScript export return shapes remain dynamic, incomplete, or ambiguously paired?",
26
+ : kind === "source-to-bundle-comparison"
27
+ ? "Which historical source files remain unmatched or ambiguously mapped to the shipped bundle?"
28
+ : "Which selected JavaScript export return shapes remain dynamic, incomplete, or ambiguously paired?",
27
29
  severity: "medium",
28
30
  domain: kind,
29
31
  supporting_evidence_ids: [evidence.evidence_id],
@@ -43,12 +45,14 @@ const unknownRegistration = (evidence, kind) => ({
43
45
  rationale: "Add approved passive runtime Evidence without promoting it to static fact.",
44
46
  },
45
47
  ]
46
- : [
47
- {
48
- operation: "run_controlled_replay",
49
- rationale: "Validate exact approved module behavior separately when runtime semantics are required.",
50
- },
51
- ]),
48
+ : kind === "source-to-bundle-comparison"
49
+ ? []
50
+ : [
51
+ {
52
+ operation: "run_controlled_replay",
53
+ rationale: "Validate exact approved module behavior separately when runtime semantics are required.",
54
+ },
55
+ ]),
52
56
  ],
53
57
  relationships: [],
54
58
  });
@@ -0,0 +1,27 @@
1
+ import { buildReconstructionObligationLedgerEvidenceValidated, resolveReconstructionObligationLedgerRequest, } from "../../application/ReconstructionObligationLedgerService.js";
2
+ import { applicationToolContract } from "../../contracts/applicationToolContracts.js";
3
+ import { reconstructionObligationLedgerInputSchema } from "../../domain/reconstructionObligationLedgerSchemas.js";
4
+ import { logToolExecution } from "../toolLogging.js";
5
+ import { safeParseToolInput } from "../toolInputValidation.js";
6
+ import { toolRegistrationOptions } from "../toolRegistrationOptions.js";
7
+ import { toCallToolResult } from "../toolResult.js";
8
+ import { recordResult, recordSources } from "./helpers.js";
9
+ const contract = applicationToolContract("build_reconstruction_obligation_ledger");
10
+ /** Register conservative reconstruction-obligation generation and closure. */
11
+ export const registerReconstructionObligationLedgerTool = (server, options) => {
12
+ server.registerTool(contract.name, toolRegistrationOptions(contract), async (input) => {
13
+ const parsed = safeParseToolInput(reconstructionObligationLedgerInputSchema, input, contract.name);
14
+ if (!parsed.ok)
15
+ return toCallToolResult(parsed, contract);
16
+ const resolved = resolveReconstructionObligationLedgerRequest(parsed.value);
17
+ if (!resolved.ok)
18
+ return toCallToolResult(resolved, contract);
19
+ const result = await logToolExecution(options.logger, contract.name, () => Promise.resolve(buildReconstructionObligationLedgerEvidenceValidated(resolved.value)));
20
+ if (!result.ok)
21
+ return toCallToolResult(result, contract);
22
+ const recorded = recordSources(options.recordEvidence, resolved.value.evidence_bundle.records);
23
+ if (!recorded.ok)
24
+ return toCallToolResult(recorded, contract);
25
+ return recordResult(options, contract, result.value);
26
+ });
27
+ };