@jshookmcp/jshook 0.3.0 → 0.3.1
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.
- package/README.md +25 -50
- package/README.zh.md +25 -48
- package/dist/AntiCheatDetector-CGVGNfy5.mjs +1 -0
- package/dist/CacheAdapters-CdAxBmVW.mjs +1 -0
- package/dist/CodeInjector-BlgyqTOk.mjs +1 -0
- package/dist/ConsoleMonitor-Dkqc0HNi.mjs +490 -0
- package/dist/DOMInspector-BYY_EJ0C.mjs +95 -0
- package/dist/DarwinAPI-DC4HGGLl.mjs +1 -0
- package/dist/DetailedDataManager-BniBJlVv.mjs +1 -0
- package/dist/EventBus-DgciURGg.mjs +1 -0
- package/dist/EvidenceGraphBridge-BIfgB7HP.mjs +1 -0
- package/dist/ExtensionManager-erMpqcLk.mjs +1 -0
- package/dist/FingerprintManager-N7BZqjxP.mjs +1 -0
- package/dist/HardwareBreakpoint-OcJqNFVc.mjs +1 -0
- package/dist/HeapAnalyzer-CqAxZzeS.mjs +1 -0
- package/dist/{HookGeneratorBuilders.core.generators.storage-CTbB4Lcx.mjs → HookGeneratorBuilders.core.generators.storage-Bf1fbrNK.mjs} +66 -101
- package/dist/InstrumentationSession-DxXs0sCp.mjs +1 -0
- package/dist/MCPServer.search.handlers.domain-DVbWL1bT.mjs +1 -0
- package/dist/MemoryController-BaqstM5w.mjs +2 -0
- package/dist/MemoryScanSession-CaxAjZJf.mjs +1 -0
- package/dist/MemoryScanner-BLYnMJy6.mjs +1 -0
- package/dist/NativeMemoryManager.impl-CI554XbY.mjs +1 -0
- package/dist/NativeMemoryManager.utils-DM4NC3FE.mjs +1 -0
- package/dist/PEAnalyzer-DJyaJTQJ.mjs +1 -0
- package/dist/PageController-D9jVkH0i.mjs +1 -0
- package/dist/PointerChainEngine-5nF9eNlu.mjs +1 -0
- package/dist/PrerequisiteError-Bl3dK8XA.mjs +1 -0
- package/dist/ProcessRegistry-Hf12LlR9.mjs +1 -0
- package/dist/ResponseBuilder-B2lu4KEl.mjs +1 -0
- package/dist/ReverseEvidenceGraph-B931HeoW.mjs +2 -0
- package/dist/ScriptManager-fgqiALgj.mjs +7 -0
- package/dist/Speedhack-l6s8L2Qw.mjs +1 -0
- package/dist/StealthVerifier-Dhbj4B4P.mjs +1 -0
- package/dist/StructureAnalyzer-A-WamfYE.mjs +2 -0
- package/dist/ToolCatalog-D_IKl1Hu.mjs +1 -0
- package/dist/ToolError-DWU_z7gp.mjs +1 -0
- package/dist/ToolProbe-xsfALmN3.mjs +1 -0
- package/dist/ToolRegistry-B0Zs-phN.mjs +1 -0
- package/dist/ToolRouter.policy-CFHoN_Lw.mjs +4 -0
- package/dist/TraceRecorder-Dd8jLXpi.mjs +272 -0
- package/dist/VersionDetector-DMoUWyNm.mjs +9 -0
- package/dist/Win32API-Bhi5xFBe.mjs +1 -0
- package/dist/Win32Debug-CQteFL4F.mjs +1 -0
- package/dist/WorkflowEngine-CxEp2WXH.mjs +1 -0
- package/dist/analysis-BuR-NgX8.mjs +5 -0
- package/dist/{antidebug-BRKeyt27.mjs → antidebug-BOTZH6-0.mjs} +8 -259
- package/dist/artifactRetention-NBdncOEW.mjs +1 -0
- package/dist/artifacts-B5xQuEa_.mjs +1 -0
- package/dist/authorization-schema-B40obG1A.mjs +1 -0
- package/dist/betterSqlite3-CGaxz4AX.mjs +1 -0
- package/dist/binary-instrument-Cf9qqLlM.mjs +7 -0
- package/dist/bind-helpers-BlAOQrFQ.mjs +1 -0
- package/dist/boringssl-inspector-BST5vtKx.mjs +2 -0
- package/dist/browser-C4Le3xqA.mjs +11 -0
- package/dist/capabilities-DbYCv-HF.mjs +1 -0
- package/dist/chunk-C_pMuVsO.mjs +1 -0
- package/dist/collector-CKO8RPK8.mjs +1 -0
- package/dist/concurrency-CcK46d0h.mjs +1 -0
- package/dist/constants-Cp6hBrrx.mjs +1 -0
- package/dist/coordination-BbijHEHH.mjs +1 -0
- package/dist/debugger-CRJq_krh.mjs +1 -0
- package/dist/definitions-BGobEDQa.mjs +1 -0
- package/dist/definitions-BGwNSkVm.mjs +1 -0
- package/dist/definitions-BbxOUiP-.mjs +1 -0
- package/dist/definitions-CCP9gphV.mjs +1 -0
- package/dist/definitions-CIO9O-Sw.mjs +1 -0
- package/dist/definitions-CYFbewnd.mjs +1 -0
- package/dist/definitions-CdWEuIkI.mjs +1 -0
- package/dist/definitions-CoQFbggH.mjs +1 -0
- package/dist/definitions-CuJRsJ6N.mjs +1 -0
- package/dist/definitions-DI9YXsJk.mjs +1 -0
- package/dist/definitions-DJklW2sS.mjs +1 -0
- package/dist/definitions-DZ8uKusP.mjs +1 -0
- package/dist/definitions-Dds_zrWx.mjs +1 -0
- package/dist/definitions-Dgrg7f3D.mjs +1 -0
- package/dist/definitions-DtE0XLrT.mjs +1 -0
- package/dist/definitions-LaYTuwQd.mjs +26 -0
- package/dist/definitions-NoVp_9Pm.mjs +1 -0
- package/dist/definitions-OvGsfxdt.mjs +1 -0
- package/dist/definitions-jXPaVy4P.mjs +1 -0
- package/dist/encoding-DGcr6Aj_.mjs +2 -0
- package/dist/ensure-browser-core-Buls24LQ.mjs +1 -0
- package/dist/evidence-graph-bridge-B0yhGPcs.mjs +1 -0
- package/dist/factory-Cx_1LorX.mjs +1 -0
- package/dist/flat-target-session-CO5g78k3.mjs +1 -0
- package/dist/formatAddress-C7j2fDlM.mjs +1 -0
- package/dist/graphql-HLf3MS8H.mjs +62 -0
- package/dist/handlers-BLMa4X7l.mjs +54 -0
- package/dist/handlers-BP12ZsWc.mjs +4 -0
- package/dist/handlers-BZoPla6E.mjs +1 -0
- package/dist/handlers-BggKiVx9.mjs +2 -0
- package/dist/handlers-D3iev8g1.mjs +1 -0
- package/dist/handlers-D49r1-1P.mjs +1 -0
- package/dist/handlers-DCE45Ww8.mjs +2 -0
- package/dist/handlers-DW5AbYs5.mjs +5 -0
- package/dist/handlers-De5u62Ga2.mjs +1 -0
- package/dist/handlers-DmQzIc44.mjs +31 -0
- package/dist/handlers-DnJRGp7t.mjs +302 -0
- package/dist/handlers-Dv_runVv.mjs +2 -0
- package/dist/handlers-S9Ws0IGy.mjs +2 -0
- package/dist/{handlers-Dz9PYsCa.mjs → handlers-pVNpaw4A.mjs} +118 -904
- package/dist/handlers.impl-CD2_kOcC.mjs +1 -0
- package/dist/hooks-DDKppogd.mjs +600 -0
- package/dist/index.mjs +12 -5235
- package/dist/logger-sBC6IdRT.mjs +1 -0
- package/dist/maintenance-CutEO84j.mjs +1 -0
- package/dist/manifest-BFGxlDRh.mjs +123 -0
- package/dist/manifest-BPuE6oH2.mjs +1 -0
- package/dist/manifest-BXry5N09.mjs +1 -0
- package/dist/manifest-BeP_zJGb2.mjs +1 -0
- package/dist/manifest-C0g67k6U.mjs +1 -0
- package/dist/manifest-C1nZkTkO.mjs +1 -0
- package/dist/manifest-C7qV1z7F.mjs +1 -0
- package/dist/manifest-CDeUZGUZ.mjs +1 -0
- package/dist/manifest-CDiCtaQT.mjs +1 -0
- package/dist/manifest-CFn0359q2.mjs +1 -0
- package/dist/manifest-CGq4NpqH2.mjs +1 -0
- package/dist/manifest-CJMGt7Qy.mjs +1 -0
- package/dist/manifest-CRIJq4Hs.mjs +1 -0
- package/dist/manifest-C_hEIjSx.mjs +1 -0
- package/dist/manifest-CeQmtQOY.mjs +1 -0
- package/dist/manifest-Cq0j7GZt.mjs +1 -0
- package/dist/manifest-CtPmHAdn.mjs +1 -0
- package/dist/manifest-Cx2IVMUY.mjs +1 -0
- package/dist/manifest-D16xPXro.mjs +1 -0
- package/dist/manifest-D44TaRJU.mjs +1 -0
- package/dist/manifest-D610kxZr.mjs +2 -0
- package/dist/manifest-DC-SMF6b.mjs +1 -0
- package/dist/manifest-DD3rtxvV.mjs +1 -0
- package/dist/manifest-DKUorv5M.mjs +1 -0
- package/dist/manifest-DMJlcsTR.mjs +1 -0
- package/dist/manifest-DWUUWBz0.mjs +1 -0
- package/dist/manifest-De-6Wf2R.mjs +1 -0
- package/dist/manifest-Dgh0uDW-.mjs +1 -0
- package/dist/manifest-Dm0o3i2U.mjs +1 -0
- package/dist/manifest-DsVh7Y4U.mjs +1 -0
- package/dist/manifest-DtEFSRaq.mjs +1 -0
- package/dist/manifest-H-EpAyZQ.mjs +1 -0
- package/dist/manifest-ais9Afrw.mjs +1 -0
- package/dist/manifest-tmb54wmA.mjs +1 -0
- package/dist/manifest-yu2xiQqe.mjs +1 -0
- package/dist/manifest-zrbrpKCC.mjs +1 -0
- package/dist/matchesWildcardPattern-BGqLSmEs.mjs +1 -0
- package/dist/modules-p-PUNv9r.mjs +332 -0
- package/dist/mojo-ipc-VGlv3Qyp.mjs +9 -0
- package/dist/network-BjZ1Y-GB.mjs +7 -0
- package/dist/outputPaths-BonGThuc.mjs +2 -0
- package/dist/parse-args-Cuk7-xUt.mjs +1 -0
- package/dist/platform-C446Lf97.mjs +93 -0
- package/dist/playwright-cdp-fallback-BwVR-_T3.mjs +1 -0
- package/dist/process-C9f2A5zk.mjs +962 -0
- package/dist/proxy-CvRepxgV.mjs +1 -0
- package/dist/registry-DUHIPE-v.mjs +1 -0
- package/dist/response-C7rKQst4.mjs +1 -0
- package/dist/search-defaults-D2bY-rzH.mjs +1 -0
- package/dist/server/plugin-api.mjs +1 -293
- package/dist/shared-state-board-Cyg-xh_k.mjs +1 -0
- package/dist/sourcemap-D6Q1UuAp.mjs +1 -0
- package/dist/ssrf-policy-T96MR3r6.mjs +1 -0
- package/dist/streaming-CTX58tbb.mjs +1 -0
- package/dist/tool-builder-CI9914Tf.mjs +1 -0
- package/dist/transform-Cv9P2vVD.mjs +103 -0
- package/dist/types-CuyefmGT.mjs +1 -0
- package/dist/types-DtThH00r.mjs +1 -0
- package/dist/wasm-DaJa8J0V.mjs +174 -0
- package/dist/webcrack-CsLLJIs9.mjs +46 -0
- package/dist/workflow-CYIXtrWD.mjs +101 -0
- package/package.json +50 -78
- package/dist/AntiCheatDetector-CqGDXmfc.mjs +0 -350
- package/dist/CacheAdapters-jJFy20G-.mjs +0 -80
- package/dist/CodeInjector-BdjRfNx7.mjs +0 -150
- package/dist/ConsoleMonitor-DykL3IAw.mjs +0 -2269
- package/dist/DarwinAPI-ETyy0xyo.mjs +0 -363
- package/dist/DetailedDataManager-HT49OrvF.mjs +0 -217
- package/dist/EventBus-DFKvADm3.mjs +0 -141
- package/dist/EvidenceGraphBridge-318Oi0Lf.mjs +0 -153
- package/dist/ExtensionManager-BDMsY2Dz.mjs +0 -721
- package/dist/FingerprintManager-BN4UQWnX.mjs +0 -96
- package/dist/HardwareBreakpoint-Cc2AFq1Y.mjs +0 -239
- package/dist/HeapAnalyzer-DruMgsgj.mjs +0 -284
- package/dist/InstrumentationSession-DLH0vd-z.mjs +0 -244
- package/dist/MemoryController-CMtviNW_.mjs +0 -167
- package/dist/MemoryScanSession-ITgb_NMi.mjs +0 -278
- package/dist/MemoryScanner-CiL7Z3ey.mjs +0 -428
- package/dist/NativeMemoryManager.impl-D9Lkovvn.mjs +0 -485
- package/dist/NativeMemoryManager.utils-BBlAixF5.mjs +0 -165
- package/dist/PEAnalyzer-DMQ44gen.mjs +0 -385
- package/dist/PageController-BPJNqqBN.mjs +0 -431
- package/dist/PointerChainEngine-K7wN8Z-w.mjs +0 -325
- package/dist/PrerequisiteError-TuyZIs6n.mjs +0 -20
- package/dist/ProcessRegistry-zGg12QbE.mjs +0 -74
- package/dist/ResponseBuilder-CJXWmWNw.mjs +0 -143
- package/dist/ReverseEvidenceGraph-C02-gXOh.mjs +0 -269
- package/dist/ScriptManager-ZuWD-0Jg.mjs +0 -3003
- package/dist/Speedhack-D-z0umeT.mjs +0 -156
- package/dist/StealthVerifier-BWmPgQsv.mjs +0 -135
- package/dist/StructureAnalyzer-Cav5AVSL.mjs +0 -429
- package/dist/ToolCatalog-5OJdMiF0.mjs +0 -582
- package/dist/ToolError-jh9whhMd.mjs +0 -15
- package/dist/ToolProbe-DbCFGyrg.mjs +0 -45
- package/dist/ToolRegistry-B9krbTtI.mjs +0 -180
- package/dist/ToolRouter.policy-BGDAGyeH.mjs +0 -344
- package/dist/TraceRecorder-B41Z5XBj.mjs +0 -1286
- package/dist/VersionDetector-K3V4vGsw.mjs +0 -104
- package/dist/Win32API-C2kjj0ze.mjs +0 -346
- package/dist/Win32Debug-CKrGOTpo.mjs +0 -274
- package/dist/WorkflowEngine-DJ6M4opp.mjs +0 -569
- package/dist/analysis-BHeJW2Nb.mjs +0 -1234
- package/dist/artifactRetention-CPXkUJXp.mjs +0 -598
- package/dist/artifacts-DkfosXH3.mjs +0 -59
- package/dist/authorization-schema-DRqyJMSk.mjs +0 -31
- package/dist/betterSqlite3-DLSBZodi.mjs +0 -74
- package/dist/binary-instrument--V3MAhJ4.mjs +0 -971
- package/dist/bind-helpers-ClV34xdn.mjs +0 -42
- package/dist/boringssl-inspector-Bo_LOLaS.mjs +0 -180
- package/dist/browser-Dx3_S2cG.mjs +0 -4369
- package/dist/capabilities-CcHlvWgK.mjs +0 -33
- package/dist/chunk-CjcI7cDX.mjs +0 -15
- package/dist/concurrency-Drev_Vz9.mjs +0 -41
- package/dist/constants-CDZLOoVv.mjs +0 -534
- package/dist/coordination-DgItD9DL.mjs +0 -259
- package/dist/debugger-RS3RSAqs.mjs +0 -1288
- package/dist/definitions-BEoYofW5.mjs +0 -47
- package/dist/definitions-BRaefg3u.mjs +0 -365
- package/dist/definitions-BbkvZkiv.mjs +0 -96
- package/dist/definitions-BtWSHJ3o.mjs +0 -17
- package/dist/definitions-C1gCHO0i.mjs +0 -43
- package/dist/definitions-CDOg_b-l.mjs +0 -138
- package/dist/definitions-CVPD9hzZ.mjs +0 -54
- package/dist/definitions-Cea8Lgl7.mjs +0 -94
- package/dist/definitions-DAgIyjxM.mjs +0 -10
- package/dist/definitions-DJA27nsL.mjs +0 -66
- package/dist/definitions-DKPFU3LW.mjs +0 -25
- package/dist/definitions-DPRpZQ96.mjs +0 -47
- package/dist/definitions-DUE5gmdn.mjs +0 -18
- package/dist/definitions-DYVjOtxa.mjs +0 -26
- package/dist/definitions-DcYLVLCo.mjs +0 -37
- package/dist/definitions-Pp5LI2H4.mjs +0 -27
- package/dist/definitions-j9KdHVNR.mjs +0 -14
- package/dist/definitions-uzkjBwa7.mjs +0 -258
- package/dist/definitions-va-AnLuQ.mjs +0 -28
- package/dist/encoding-DJeqHmpd.mjs +0 -1079
- package/dist/evidence-graph-bridge-DcYizFk2.mjs +0 -136
- package/dist/factory-C90tBff6.mjs +0 -575
- package/dist/flat-target-session-Dgax2Cy3.mjs +0 -29
- package/dist/formatAddress-nnMvEohD.mjs +0 -17
- package/dist/graphql-CoHrhweh.mjs +0 -1197
- package/dist/handlers-4jmR0nMs.mjs +0 -898
- package/dist/handlers-BAHPxcch.mjs +0 -789
- package/dist/handlers-BOs9b907.mjs +0 -2600
- package/dist/handlers-BWXEy6ef.mjs +0 -917
- package/dist/handlers-Bndn6QvE.mjs +0 -111
- package/dist/handlers-BqC4bD4s.mjs +0 -681
- package/dist/handlers-BtYq60bM2.mjs +0 -276
- package/dist/handlers-BzgcB4iv.mjs +0 -799
- package/dist/handlers-CRyRWj2b.mjs +0 -859
- package/dist/handlers-CVv2H1uq.mjs +0 -592
- package/dist/handlers-Dl5a7JS4.mjs +0 -572
- package/dist/handlers-Dx2d7jt7.mjs +0 -2537
- package/dist/handlers-HujRKC3b.mjs +0 -661
- package/dist/handlers.impl-XWXkQfyi.mjs +0 -807
- package/dist/hooks-B1B8NRHL.mjs +0 -898
- package/dist/logger-Dh_xb7_2.mjs +0 -93
- package/dist/maintenance-PRMkLVRW.mjs +0 -835
- package/dist/manifest-67Bok-Si.mjs +0 -58
- package/dist/manifest-6lNTMZAB2.mjs +0 -87
- package/dist/manifest-B2duEHiH.mjs +0 -90
- package/dist/manifest-B6EY9Vm8.mjs +0 -57
- package/dist/manifest-B6nKSbyY.mjs +0 -95
- package/dist/manifest-BL8AQNPF.mjs +0 -106
- package/dist/manifest-BSZvJJmV.mjs +0 -47
- package/dist/manifest-BU7qzUyX.mjs +0 -418
- package/dist/manifest-Bl62e8WK.mjs +0 -49
- package/dist/manifest-Bo5cXjdt.mjs +0 -82
- package/dist/manifest-BpS4gtUK.mjs +0 -1347
- package/dist/manifest-Bv65_e2W.mjs +0 -101
- package/dist/manifest-BytNIF4Z.mjs +0 -117
- package/dist/manifest-C-xtsjS3.mjs +0 -81
- package/dist/manifest-CDYl7OhA.mjs +0 -66
- package/dist/manifest-CRZ3xmkD.mjs +0 -61
- package/dist/manifest-CoW6u4Tp.mjs +0 -132
- package/dist/manifest-Cq5zN_8A.mjs +0 -50
- package/dist/manifest-D7YZM_2e.mjs +0 -194
- package/dist/manifest-DE_VrAeQ.mjs +0 -314
- package/dist/manifest-DGsXSCpT.mjs +0 -39
- package/dist/manifest-DJ2vfEuW.mjs +0 -156
- package/dist/manifest-DPXDYhEu.mjs +0 -80
- package/dist/manifest-Dd4fQb0a.mjs +0 -322
- package/dist/manifest-Deq6opGg.mjs +0 -223
- package/dist/manifest-DfJTafJK.mjs +0 -37
- package/dist/manifest-DgOdgN_j.mjs +0 -50
- package/dist/manifest-DlbMW4v4.mjs +0 -47
- package/dist/manifest-DmVfbH0w.mjs +0 -374
- package/dist/manifest-Dog6Ddjr.mjs +0 -109
- package/dist/manifest-DvgU5FWb.mjs +0 -58
- package/dist/manifest-HsfDBs7j.mjs +0 -50
- package/dist/manifest-I8oQHvCG.mjs +0 -186
- package/dist/manifest-NvH_a-av.mjs +0 -786
- package/dist/manifest-cEJU1v0Z.mjs +0 -129
- package/dist/manifest-wOl5XLB12.mjs +0 -112
- package/dist/modules-tZozf0LQ.mjs +0 -10635
- package/dist/mojo-ipc-DXNEXEqb.mjs +0 -640
- package/dist/network-CPVvwvFg.mjs +0 -3852
- package/dist/outputPaths-um7lCRY3.mjs +0 -1141
- package/dist/parse-args-B4cY5Vx5.mjs +0 -39
- package/dist/platform-CYeFoTWp.mjs +0 -2161
- package/dist/process-BTbgcVc6.mjs +0 -1306
- package/dist/proxy-r8YN6nP1.mjs +0 -192
- package/dist/registry-Bl8ZQW61.mjs +0 -34
- package/dist/response-CWhh2aLo.mjs +0 -34
- package/dist/shared-state-board-BoZnSoj-.mjs +0 -586
- package/dist/sourcemap-BIDHUVXy.mjs +0 -934
- package/dist/ssrf-policy-Dsqd-DTX.mjs +0 -166
- package/dist/streaming-Dal6utPp.mjs +0 -725
- package/dist/tool-builder-BHJp32mV.mjs +0 -186
- package/dist/transform-DRVgGG90.mjs +0 -1011
- package/dist/types-Bx92KJfT.mjs +0 -4
- package/dist/types-DDBWs9UP.mjs +0 -37
- package/dist/wasm-BYx5UOeG.mjs +0 -1044
- package/dist/webcrack-Be0_FccV.mjs +0 -747
- package/dist/workflow-BpuKEtvn.mjs +0 -725
|
@@ -0,0 +1,962 @@
|
|
|
1
|
+
import{t as e}from"./logger-sBC6IdRT.mjs";import{At as t,Br as n,Bt as r,Dt as i,Et as a,F as o,Ft as s,H as c,Ht as l,I as u,It as d,Lt as f,Mt as p,Nt as m,Ot as h,Pt as g,Tt as _,Vr as v,Vt as ee,Wt as y,Y as b,in as x,jt as S,kt as C,rn as te,zt as ne}from"./constants-Cp6hBrrx.mjs";import{t as w}from"./ProcessRegistry-Hf12LlR9.mjs";import{n as re,r as T,t as E}from"./types-DtThH00r.mjs";import{v as ie}from"./Win32API-Bhi5xFBe.mjs";import{i as D,r as ae}from"./factory-Cx_1LorX.mjs";import{r as O,t as oe}from"./NativeMemoryManager.utils-DM4NC3FE.mjs";import{t as k}from"./NativeMemoryManager.impl-CI554XbY.mjs";import{o as se,r as ce}from"./parse-args-Cuk7-xUt.mjs";import{t as le}from"./playwright-cdp-fallback-BwVR-_T3.mjs";import"./definitions-OvGsfxdt.mjs";import{existsSync as ue,promises as de,readFileSync as fe}from"fs";import{platform as pe,tmpdir as A}from"node:os";import{closeSync as me,openSync as he,promises as j,readFileSync as ge,readSync as _e}from"node:fs";import{join as M}from"node:path";import{fileURLToPath as ve}from"node:url";import{exec as N,execFile as ye,spawn as P}from"child_process";import{promisify as F}from"util";let I=null;function be(){try{let e=Function(`try { return import.meta.url ?? null; } catch { return null; }`)();return e?ve(new URL(`.`,e)):null}catch{return null}}function xe(){if(I)return I;let e=be();return e?(I=e,I):process.cwd()}var L=class{scriptCache=new Map;scriptsDir;constructor(){let e=xe();ue(M(e,`native`,`scripts`))?this.scriptsDir=M(e,`native`,`scripts`):ue(M(e,`scripts`))?this.scriptsDir=M(e,`scripts`):ue(M(process.cwd(),`dist`,`native`,`scripts`))?this.scriptsDir=M(process.cwd(),`dist`,`native`,`scripts`):this.scriptsDir=M(process.cwd(),`src`,`native`,`scripts`)}async loadScript(e){if(this.scriptCache.has(e))return this.scriptCache.get(e);let t=pe(),n=t===`win32`?`windows`:t===`darwin`?`macos`:`linux`,r=M(this.scriptsDir,n,e),i=await de.readFile(r,`utf-8`);return this.scriptCache.set(e,i),i}getScriptPath(e){let t=pe(),n=t===`win32`?`windows`:t===`darwin`?`macos`:`linux`;return M(this.scriptsDir,n,e)}clearCache(){this.scriptCache.clear()}},Se=class{scriptLoader;browserSignatures=new Map([[`chrome`,{windowClasses:[`Chrome_WidgetWin_0`,`Chrome_WidgetWin_1`,`Chrome_WidgetWin_*`],processNames:[`chrome.exe`,`chrome`],mainWindowTitle:/.*- Google Chrome$/,debugPorts:[9222,9229,9333]}],[`edge`,{windowClasses:[`Edge_WidgetWin_0`,`Edge_WidgetWin_1`,`Edge_WidgetWin_*`],processNames:[`msedge.exe`,`msedge`],mainWindowTitle:/.*- Microsoft Edge$/,debugPorts:[9222,9229]}],[`firefox`,{windowClasses:[`MozillaWindowClass`],processNames:[`firefox.exe`,`firefox`],mainWindowTitle:/.*- Mozilla Firefox$/,debugPorts:[9222]}]]);constructor(){this.scriptLoader=new L}sanitizePsInput(e){return e.replace(/[`$"'{}();|<>@#%!\\\n\r]/g,``)}escapePowerShellSingleQuoted(e){return this.sanitizePsInput(e).replace(/'/g,`''`)}async discoverBrowsers(){let e=[];for(let[t,n]of this.browserSignatures){let r=await this.findBySignature(t,n);e.push(...r)}return e}async findBySignature(e,t){let n=[],r=new Set;for(let i of t.processNames){let t=await this.findByProcessName(i);for(let i of t)r.has(i.pid)||(r.add(i.pid),n.push({type:e,pid:i.pid,hwnd:i.hwnd,title:i.title}))}for(let i of t.windowClasses){let t=await this.findByWindowClass(i);for(let i of t)r.has(i.pid)||(r.add(i.pid),n.push({type:e,pid:i.pid,hwnd:i.hwnd,title:i.title}))}for(let e of n){let n=await this.detectDebugPort(e.pid,t.debugPorts);n&&(e.debugPort=n)}return n}async findByWindowClass(e){let t=this.scriptLoader.getScriptPath(`enum-windows-by-class.ps1`);try{let n=this.escapePowerShellSingleQuoted(e),{execFile:r}=await import(`child_process`),{promisify:i}=await import(`util`),{stdout:a}=await i(r)(`powershell.exe`,[`-NoProfile`,`-ExecutionPolicy`,`Bypass`,`-File`,t,`-ClassPattern`,n],{maxBuffer:1024*1024*10});return this.parseWindowsResult(a,e)}catch(t){return console.error(`Failed to find windows by class '${e}':`,t),[]}}async findByProcessName(e){try{let t=`$Pattern='${this.escapePowerShellSingleQuoted(e)}'; Get-Process -Name "*$Pattern*" -ErrorAction SilentlyContinueSelect-Object Id, ProcessName, Path, MainWindowTitle, MainWindowHandle, CPU, WorkingSet64ConvertTo-Json -Compress`,{execFile:n}=await import(`child_process`),{promisify:r}=await import(`util`),{stdout:i}=await r(n)(`powershell.exe`,[`-NoProfile`,`-Command`,t],{maxBuffer:1024*1024*10});return this.parseProcessResult(i,e)}catch(t){return console.error(`Failed to find process by name '${e}':`,t),[]}}parseWindowsResult(e,t){let n=[];if(!e.trim()||e.trim()===`null`)return n;try{let t=JSON.parse(e.trim()),r=Array.isArray(t)?t:[t];for(let e of r){let t=`unknown`,r=e.Title||``;for(let[e,n]of this.browserSignatures)if(n.mainWindowTitle?.test(r)){t=e;break}if(t===`unknown`)for(let[n,r]of this.browserSignatures){for(let i of r.windowClasses){let r=i.replace(/\*/g,`.*`);if(new RegExp(r).test(e.ClassName||``)){t=n;break}}if(t!==`unknown`)break}n.push({type:t,pid:e.ProcessId,hwnd:e.Handle,title:e.Title})}}catch(e){console.error(`Failed to parse windows result:`,e)}return n}parseProcessResult(e,t){let n=[];if(!e.trim()||e.trim()===`null`)return n;try{let t=JSON.parse(e.trim()),r=Array.isArray(t)?t:[t];for(let e of r){let t=`unknown`,r=(e.ProcessName||``).toLowerCase();r.includes(`chrome`)?t=`chrome`:r.includes(`msedge`)||r.includes(`edge`)?t=`edge`:r.includes(`firefox`)&&(t=`firefox`),n.push({type:t,pid:e.Id,hwnd:e.MainWindowHandle?.toString(),title:e.MainWindowTitle})}}catch(e){console.error(`Failed to parse process result:`,e)}return n}async detectDebugPort(e,t){let n=await this.checkDebugPortFromCommandLine(e);if(n)return n;for(let n of t)if(await this.checkPort(e,n))return n;return null}async checkDebugPortFromCommandLine(e){let{execFile:t}=await import(`child_process`),{promisify:n}=await import(`util`),r=n(t);try{if(!Number.isFinite(e)||e<=0)return null;let{stdout:t}=await r(`powershell.exe`,[`-NoProfile`,`-Command`,`Get-CimInstance Win32_Process -Filter "ProcessId = ${Math.trunc(e)}"Select-Object CommandLine, ParentProcessId | ConvertTo-Json -Compress`],{maxBuffer:1024*1024});if(!t.trim()||t.trim()===`null`)return null;let n=(JSON.parse(t.trim()).CommandLine||``).match(/--remote-debugging-port=(\d+)/);return n?.[1]?parseInt(n[1],10):null}catch{return null}}async checkPort(e,t){let{execFile:n}=await import(`child_process`),{promisify:r}=await import(`util`),i=r(n);try{if(!Number.isFinite(e)||e<=0||!Number.isFinite(t)||t<=0)return!1;let{stdout:n}=await i(`powershell.exe`,[`-NoProfile`,`-Command`,`Get-NetTCPConnection -OwningProcess ${Math.trunc(e)} -State Listen -ErrorAction SilentlyContinueSelect-Object LocalPort | ConvertTo-Json -Compress`],{maxBuffer:1024*1024});if(!n.trim()||n.trim()===`null`)return!1;let r=JSON.parse(n.trim()),a=Array.isArray(r)?r:[r];for(let e of a)if(e.LocalPort===t)return!0;return!1}catch{return!1}}};function Ce(e,t){return t?typeof t==`string`?e.includes(t):t.test(e):!1}async function we(e,t){let n={rendererProcesses:[],utilityProcesses:[]};try{let r;if(e.processNamePattern instanceof RegExp){let n=await t.findProcesses(``),i=e.processNamePattern;r=n.filter(e=>i.test(e.name))}else{let n=e.processNamePattern||`chromium`;r=await t.findProcesses(n)}for(let e of r){let r=await t.getProcessCommandLine(e.pid);if(r?.commandLine){let t=r.commandLine.toLowerCase();t.includes(`--type=renderer`)?n.rendererProcesses.push({...e,...r}):t.includes(`--type=gpu-process`)?n.gpuProcess={...e,...r}:t.includes(`--type=utility`)?n.utilityProcesses.push({...e,...r}):t.includes(`--type=`)||(n.mainProcess={...e,...r})}else n.mainProcess||=e}let i=[n.mainProcess?.pid,...n.rendererProcesses.map(e=>e.pid)].filter(Boolean),a=t=>Ce(t.title,e.windowTitlePattern)||Ce(t.className,e.windowClassPattern);for(let e of i){let r=(await t.getProcessWindows(e)).find(a);if(r){n.targetWindow=r;break}}return t.logInfo(`Chromium processes found:`,{main:n.mainProcess?.pid,renderers:n.rendererProcesses.length,hasTargetWindow:!!n.targetWindow}),n}catch(e){return t.logError(`Failed to find Chromium processes:`,e),n}}const Te={processNamePattern:/^(chromium|chrome|msedge)$/i,windowClassPattern:`Chrome_WidgetWin`},R=F(N);function Ee(e){return String(e||``).replace(/[`$"'{}();|<>@#%!\\\n\r]/g,``)}function z(e){let t=Math.trunc(Number(e));if(!Number.isFinite(t)||t<=0)throw Error(`Invalid PID: ${e}`);return t}var De=class{powershellPath=`powershell.exe`;scriptLoader;browserDiscovery;processCache=new Map;constructor(){this.scriptLoader=new L,this.browserDiscovery=new Se,e.info(`ProcessManager initialized for Windows platform`)}async findProcesses(t){try{let n=Ee(String(t||``).trim()),r=n.toLowerCase()||`*`,i=Date.now(),a=this.processCache.get(r);if(a&&a.expiresAt>i)return a.snapshot;let o;o=n?`Get-Process -Name "*${n.replace(/"/g,`""`)}*" -ErrorAction SilentlyContinue Select-Object Id, ProcessName, Path, MainWindowTitle, MainWindowHandle, CPU, WorkingSet64 ConvertTo-Json -Compress`:`Get-Process -ErrorAction SilentlyContinue | Select-Object Id, ProcessName, Path, MainWindowTitle, MainWindowHandle, CPU, WorkingSet64 | ConvertTo-Json -Compress`;let{stdout:s}=await R(`${this.powershellPath} -NoProfile -Command "${o}"`,{maxBuffer:x}),c=s.trim(),l=[];if(c&&c!==`null`){let e=JSON.parse(c),t=Array.isArray(e)?e:[e];for(let e of t)l.push({pid:e.Id,name:e.ProcessName,executablePath:e.Path})}let u=new Map;for(let e of l)u.set(e.pid,e);let d=this.computeProcessDiff(a?.byPid??new Map,u);this.processCache.set(r,{expiresAt:i+3e3,snapshot:l,byPid:u,lastDelta:d});let f=n.length>0?`'${n}'`:`all`;return e.info(`Found ${l.length} processes matching ${f}`),l}catch(n){return e.error(`Failed to find processes with pattern '${t}':`,n),[]}}computeProcessDiff(e,t){let n=[],r=[],i=[];for(let[r,a]of t){let t=e.get(r);if(!t){n.push(a);continue}(t.pid!==a.pid||t.name!==a.name||t.executablePath!==a.executablePath)&&i.push({before:t,after:a})}for(let[n,i]of e)t.has(n)||r.push(i);return{added:n,removed:r,changed:i}}async getProcessByPid(t){try{t=z(t);let e=`Get-Process -Id ${t} -ErrorAction SilentlyContinueSelect-Object Id, ProcessName, Path, MainWindowTitle, MainWindowHandle, CPU, WorkingSet64, StartTimeConvertTo-Json -Compress`,{stdout:n}=await R(`${this.powershellPath} -NoProfile -Command "${e}"`,{maxBuffer:1024*1024});if(!n.trim()||n.trim()===`null`)return null;let r=JSON.parse(n.trim());return{pid:r.Id,name:r.ProcessName,executablePath:r.Path,windowTitle:r.MainWindowTitle,windowHandle:r.MainWindowHandle?.toString(),cpuUsage:r.CPU,memoryUsage:r.WorkingSet64}}catch(n){return e.error(`Failed to get process by PID ${t}:`,n),null}}async getProcessWindows(t){try{t=z(t);let e=await this.scriptLoader.getScriptPath(`enum-windows.ps1`),{stdout:n}=await R(`${this.powershellPath} -NoProfile -ExecutionPolicy Bypass -File "${e}" -TargetPid ${t}`,{maxBuffer:1024*1024});if(!n.trim()||n.trim()===`null`)return[];let r=JSON.parse(n.trim()),i=[],a=Array.isArray(r)?r:[r];for(let e of a)i.push({handle:e.Handle,title:e.Title,className:e.ClassName,processId:e.ProcessId,threadId:0});return i}catch(n){return e.error(`Failed to get windows for PID ${t}:`,n),[]}}async findChromiumProcesses(t=Te){return we(t,{findProcesses:e=>this.findProcesses(e),getProcessCommandLine:e=>this.getProcessCommandLine(e),getProcessWindows:e=>this.getProcessWindows(e),logInfo:(t,n)=>e.info(t,n),logError:(t,n)=>e.error(t,n)})}async findChromiumAppProcesses(){return this.findChromiumProcesses()}async getProcessCommandLine(t){try{t=z(t);let e=`Get-CimInstance Win32_Process -Filter 'ProcessId = ${t}' | Select-Object CommandLine, ParentProcessIdConvertTo-Json -Compress`,{stdout:n}=await R(`${this.powershellPath} -NoProfile -Command "${e}"`,{maxBuffer:1024*1024});if(!n.trim()||n.trim()===`null`)return{};let r=JSON.parse(n.trim());return{commandLine:r.CommandLine,parentPid:r.ParentProcessId}}catch(n){return e.error(`Failed to get command line for PID ${t}:`,n),{}}}async checkDebugPort(t,n){try{t=z(t);let e=n?.commandLine??(await this.getProcessCommandLine(t)).commandLine;if(e){let t=e.match(/--remote-debugging-port=(\d+)/);if(t?.[1])return parseInt(t[1],10)}let r=`Get-NetTCPConnection -OwningProcess ${t} -State Listen -ErrorAction SilentlyContinueSelect-Object LocalPort | ConvertTo-Json -Compress`,{stdout:i}=await R(`${this.powershellPath} -NoProfile -Command "${r}"`,{maxBuffer:1024*1024});if(i.trim()&&i.trim()!==`null`){let e=JSON.parse(i.trim()),t=Array.isArray(e)?e:[e];for(let e of t)if(o.includes(e.LocalPort))return e.LocalPort}return null}catch(n){return e.error(`Failed to check debug port for PID ${t}:`,n),null}}async findPidByListeningPort(e){try{let t=`Get-NetTCPConnection -LocalPort ${e} -State Listen -ErrorAction SilentlyContinueSelect-Object -First 1 OwningProcess | ConvertTo-Json -Compress`,{stdout:n}=await R(`${this.powershellPath} -NoProfile -Command "${t}"`,{maxBuffer:1024*1024});if(!n.trim()||n.trim()===`null`)return null;let r=JSON.parse(n.trim()),i=Array.isArray(r)?r[0]:r,a=i?.OwningProcess??i?.owningProcess??i,o=Number(a);return Number.isFinite(o)&&o>0?o:null}catch{return null}}async launchWithDebug(t,r=u,i=[]){try{let a=P(t,[`--remote-debugging-port=${r}`,...i],{detached:!0,stdio:`ignore`});a.unref(),w.register(a);let o=a.pid||0,s=t.split(/[\\/]/).pop()||`unknown`,c=o>0?o:null;for(let i=0;i<n;i++){let n=await this.findPidByListeningPort(r);if(n&&n>0&&(c=n),c&&c>0){let i=await this.getProcessByPid(c);if(i)return e.info(`Launched process with debug port ${r}:`,{pid:a.pid,resolvedPid:c,executable:t}),i;if(n&&n===c)return e.info(`Launched process with debug port ${r}:`,{pid:a.pid,resolvedPid:c,executable:t}),{pid:c,name:s,executablePath:t}}await new Promise(e=>setTimeout(e,v))}return e.info(`Launched process with debug port ${r}:`,{pid:a.pid,resolvedPid:c,executable:t}),c&&c>0?{pid:c,name:s,executablePath:t}:null}catch(t){return e.error(`Failed to launch process with debug:`,t),null}}async injectDll(t,n){try{if(!Number.isFinite(t)||t<=0)return e.error(`Invalid PID for injectDll: ${t}`),!1;let r=this.scriptLoader.getScriptPath(`inject-dll.ps1`),i=Math.trunc(t),a=String(n).replace(/'/g,`''`);return await R(`${this.powershellPath} -NoProfile -ExecutionPolicy Bypass -File "${r}" -TargetPid ${i} -DllPath '${a}'`,{maxBuffer:1024*1024}),e.warn(`DLL injection is disabled for safety in this implementation`),!1}catch(t){return e.error(`DLL injection failed:`,t),!1}}async killProcess(t){try{if(!Number.isFinite(t)||t<=0)return e.error(`Invalid PID for killProcess: ${t}`),!1;let n=Math.trunc(t),r=`Stop-Process -Id ${n} -Force -ErrorAction SilentlyContinue; Write-Output "Process ${n} killed"`;return await R(`${this.powershellPath} -NoProfile -Command "${r}"`,{maxBuffer:1024*1024}),e.info(`Process ${n} killed successfully`),!0}catch(n){return e.error(`Failed to kill process ${t}:`,n),!1}}async discoverBrowsers(){try{let t=await this.browserDiscovery.discoverBrowsers();return e.info(`Discovered ${t.length} browser instances`),t}catch(t){return e.error(`Failed to discover browsers:`,t),[]}}async findBrowserByWindowClass(t){try{let n=await this.browserDiscovery.findByWindowClass(t);return e.info(`Found ${n.length} browsers matching window class '${t}'`),n}catch(n){return e.error(`Failed to find browser by window class '${t}':`,n),[]}}async findBrowserByProcessName(t){try{let n=await this.browserDiscovery.findByProcessName(t);return e.info(`Found ${n.length} browsers matching process name '${t}'`),n}catch(n){return e.error(`Failed to find browser by process name '${t}':`,n),[]}}async detectBrowserDebugPort(t,n){try{let r=n||o,i=await this.browserDiscovery.detectDebugPort(t,r);return i?e.info(`Detected debug port ${i} for process ${t}`):e.warn(`No debug port detected for process ${t}`),i}catch(n){return e.error(`Failed to detect debug port for PID ${t}:`,n),null}}};const B=F(N);function Oe(e){return String(e||``).replace(/[^\w\s.@/\-:,+]/g,``)}function V(e){let t=Math.trunc(Number(e));if(!Number.isFinite(t)||t<=0)throw Error(`Invalid PID: ${e}`);return t}var ke=class{isWayland=!1;constructor(){this.detectDisplayServer(),e.info(`LinuxProcessManager initialized`,{displayServer:this.isWayland?`Wayland`:`X11`})}async detectDisplayServer(){try{let{stdout:e}=await B(`echo $XDG_SESSION_TYPE`);this.isWayland=e.trim()===`wayland`}catch{this.isWayland=!1}}async findProcesses(t){try{let{stdout:n}=await B(`ps aux | grep -i "${Oe(t)}" | grep -v grep || true`,{maxBuffer:x}),r=[],i=n.trim().split(`
|
|
2
|
+
`).filter(e=>e.trim());for(let e of i){let t=e.trim().split(/\s+/);if(t.length>=11){let e=parseInt(t[1]||`0`,10);if(isNaN(e))continue;let n=parseFloat(t[2]||`0`),i=parseFloat(t[3]||`0`),a=t.slice(10).join(` `);r.push({pid:e,name:t[10]||a.split(` `)[0]||`unknown`,commandLine:a,cpuUsage:n,memoryUsage:i*1024*1024})}}return e.info(`Found ${r.length} processes matching '${t}'`),r}catch(n){return e.error(`Failed to find processes with pattern '${t}':`,n),[]}}async getProcessByPid(t){try{t=V(t);let{stdout:e}=await B(`cat /proc/${t}/status 2>/dev/null || echo ""`),{stdout:n}=await B(`cat /proc/${t}/cmdline 2>/dev/null | tr '\0' ' ' || echo ""`),{stdout:r}=await B(`cat /proc/${t}/stat 2>/dev/null || echo ""`);if(!e.trim())return null;let i={};for(let t of e.split(`
|
|
3
|
+
`)){let[e,n]=t.split(`:`);e&&n&&(i[e.trim()]=n.trim())}let a=r.trim().split(` `),o=a.length>13?parseInt(a[13]||`0`,10):0,s=a.length>14?parseInt(a[14]||`0`,10):0;return{pid:t,name:i.Name||`unknown`,executablePath:await this.getProcessPath(t),commandLine:n.trim()||void 0,parentPid:i.PPid?parseInt(i.PPid,10):void 0,memoryUsage:i.VmRSS?parseInt(i.VmRSS.replace(/\D/g,``),10)*1024:void 0,cpuUsage:o+s}}catch(n){return e.error(`Failed to get process by PID ${t}:`,n),null}}async getProcessPath(e){try{e=V(e);let{stdout:t}=await B(`readlink -f /proc/${e}/exe 2>/dev/null || echo ""`);return t.trim()||void 0}catch{return}}async getProcessWindows(t){let n=[];try{if(t=V(t),this.isWayland){e.debug(`Attempting Wayland window enumeration via compositor-specific APIs`);try{let{stdout:e}=await B(`hyprctl clients -j 2>/dev/null`);if(e.trim()){let r=JSON.parse(e);for(let e of r)e.pid===t&&n.push({handle:e.address||e.window||`0`,title:e.title||``,className:e.class||``,processId:t,threadId:0});if(n.length>0)return n}}catch{}try{let{stdout:n}=await B(`gdbus call --session --dest org.gnome.Shell --object-path /org/gnome/Shell --method org.gnome.Shell.Eval "global.get_window_actors().filter(w => w.meta_window.get_pid() === ${t}).map(w => w.meta_window.get_title() + '|' + w.meta_window.get_wm_class())" 2>/dev/null`);(n.includes(String(t))||n.includes(`,`))&&e.debug(`GNOME Wayland window query returned data, but reliable parsing is not yet implemented`)}catch{}}let{stdout:r}=await B(`which xdotool 2>/dev/null || echo ""`);if(!r.trim())return this.isWayland&&n.length===0?e.warn(`Wayland native enumeration failed and xdotool is missing. Install xdotool for XWayland fallback.`):this.isWayland||e.warn(`xdotool not found. Install it for window management: sudo apt-get install xdotool`),n;let{stdout:i}=await B(`xdotool search --all --pid ${t} 2>/dev/null || true`),a=i.trim().split(`
|
|
4
|
+
`).filter(e=>e.trim());for(let e of a)try{let{stdout:r}=await B(`xdotool getwindowname ${e} 2>/dev/null || echo ""`),{stdout:i}=await B(`xdotool getwindowclassname ${e} 2>/dev/null || echo ""`);n.push({handle:e,title:r.trim(),className:i.trim(),processId:t,threadId:0})}catch{}return n}catch(r){return e.error(`Failed to get windows for PID ${t}:`,r),n}}async findChromeProcesses(){let t={rendererProcesses:[],utilityProcesses:[]};try{let n=await this.findProcesses(`chrome`),r=await Promise.all(n.map(e=>this.getProcessByPid(e.pid)));for(let e=0;e<n.length;e++){let i=n[e],a=r[e];if(a?.commandLine){let e=a.commandLine.toLowerCase();e.includes(`--type=renderer`)?t.rendererProcesses.push({...i,...a}):e.includes(`--type=gpu-process`)?t.gpuProcess={...i,...a}:e.includes(`--type=utility`)?t.utilityProcesses.push({...i,...a}):e.includes(`--type=`)||(t.mainProcess={...i,...a})}else t.mainProcess||=i}let i=[t.mainProcess?.pid,...t.rendererProcesses.map(e=>e.pid)].filter(Boolean);for(let e of i){let n=(await this.getProcessWindows(e)).find(e=>e.title.includes(`Chrome`)||e.className.includes(`Chrome`)||e.title.includes(`Chromium`));if(n){t.targetWindow=n;break}}return e.info(`Chrome processes found:`,{main:t.mainProcess?.pid,renderers:t.rendererProcesses.length,hasTargetWindow:!!t.targetWindow}),t}catch(n){return e.error(`Failed to find Chrome processes:`,n),t}}async getProcessCommandLine(t){try{t=V(t);let{stdout:e}=await B(`cat /proc/${t}/cmdline 2>/dev/null | tr '\0' ' ' || echo ""`),{stdout:n}=await B(`cat /proc/${t}/status 2>/dev/null | grep PPid || echo ""`),r=n.match(/PPid:\s*(\d+)/);return{commandLine:e.trim()||void 0,parentPid:r?.[1]?parseInt(r[1],10):void 0}}catch(n){return e.error(`Failed to get command line for PID ${t}:`,n),{}}}async checkDebugPort(t,n){try{t=V(t);let e=n?.commandLine??(await this.getProcessCommandLine(t)).commandLine;if(e){let t=e.match(/--remote-debugging-port=(\d+)/);if(t?.[1])return parseInt(t[1],10)}let{stdout:r}=await B(`ss -tlnp 2>/dev/null | grep "pid=${t}" || netstat -tlnp 2>/dev/null | grep "${t}" || true`,{maxBuffer:1024*1024});for(let e of o)if(r.includes(`:${e}`))return e;return null}catch(n){return e.error(`Failed to check debug port for PID ${t}:`,n),null}}async launchWithDebug(t,n=u,r=[]){try{let i=P(t,[`--remote-debugging-port=${n}`,...r],{detached:!0,stdio:`ignore`});if(i.unref(),w.register(i),await new Promise(e=>setTimeout(e,te)),!i.pid)return e.error(`Failed to spawn process: PID is undefined for ${t}`),null;let a=await this.getProcessByPid(i.pid);return e.info(`Launched process with debug port ${n}:`,{pid:i.pid,executable:t}),a}catch(t){return e.error(`Failed to launch process with debug:`,t),null}}async killProcess(t){try{return t=V(t),await B(`kill -9 ${t} 2>/dev/null || kill -15 ${t}`),e.info(`Process ${t} killed successfully`),!0}catch(n){return e.error(`Failed to kill process ${t}:`,n),!1}}isRunningOnWayland(){return this.isWayland}};const H=F(N),Ae=F(ye);function je(e){return String(e||``).replace(/[^\w\s.@/\-:,+]/g,``)}function U(e){let t=Math.trunc(Number(e));if(!Number.isFinite(t)||t<=0)throw Error(`Invalid PID: ${e}`);return t}function Me(e,t){let n=e;for(let[e,r]of Object.entries(t)){let t=RegExp(`\\{\\{${e}\\}\\}`,`g`);n=n.replace(t,String(r))}return n}var Ne=class{constructor(){e.info(`MacProcessManager initialized`)}async findProcesses(t){try{let{stdout:n}=await H(`ps aux | grep -i "${je(t)}" | grep -v grep || true`,{maxBuffer:x}),r=[],i=n.trim().split(`
|
|
5
|
+
`).filter(e=>e.trim());for(let e of i){let t=e.trim().split(/\s+/);if(t.length>=11){let e=parseInt(t[1]||`0`,10);if(isNaN(e))continue;let n=parseFloat(t[2]||`0`),i=parseFloat(t[3]||`0`),a=t.slice(10).join(` `);r.push({pid:e,name:t[10]||a.split(` `)[0]||`unknown`,commandLine:a,cpuUsage:n,memoryUsage:i*1024*1024})}}return e.info(`Found ${r.length} processes matching '${t}'`),r}catch(n){return e.error(`Failed to find processes with pattern '${t}':`,n),[]}}async getProcessByPid(t){try{t=U(t);let{stdout:e}=await H(`ps -p ${t} -o pid,ppid,pcpu,pmem,comm,args 2>/dev/null || echo ""`),n=e.trim().split(`
|
|
6
|
+
`).filter(e=>e.trim());if(n.length<2)return null;let r=(n[1]||``).trim().split(/\s+/);return r.length>=6?{pid:parseInt(r[0]||`0`,10),parentPid:parseInt(r[1]||`0`,10),name:r[4]||`unknown`,executablePath:await this.getProcessPath(t),commandLine:r.slice(5).join(` `),cpuUsage:parseFloat(r[2]||`0`),memoryUsage:parseFloat(r[3]||`0`)*1024*1024}:null}catch(n){return e.error(`Failed to get process by PID ${t}:`,n),null}}async getProcessPath(e){try{e=U(e);let{stdout:t}=await H(`ps -p ${e} -o comm= 2>/dev/null || echo ""`);return t.trim()||void 0}catch{return}}async getProcessWindows(t){try{t=U(t);let e=await this.getProcessByPid(t);if(!e)return[];let{stdout:n}=await H(`osascript -e '${`
|
|
7
|
+
tell application "System Events"
|
|
8
|
+
set processList to {}
|
|
9
|
+
try
|
|
10
|
+
set targetProcess to first process whose unix id is ${t}
|
|
11
|
+
set procName to name of targetProcess
|
|
12
|
+
set windowList to {}
|
|
13
|
+
|
|
14
|
+
tell targetProcess
|
|
15
|
+
repeat with win in windows
|
|
16
|
+
set winInfo to {|
|
|
17
|
+
title:name of win,
|
|
18
|
+
className:procName,
|
|
19
|
+
processId:${t},
|
|
20
|
+
handle:"applescript-window"
|
|
21
|
+
|}
|
|
22
|
+
set end of windowList to winInfo
|
|
23
|
+
end repeat
|
|
24
|
+
end tell
|
|
25
|
+
|
|
26
|
+
return windowList
|
|
27
|
+
on error
|
|
28
|
+
return {}
|
|
29
|
+
end try
|
|
30
|
+
end tell
|
|
31
|
+
`.replace(/'/g,`'"'"'`)}' 2>/dev/null || echo "[]"`,{timeout:b}),r=[];if(n.trim()&&n.trim()!==`[]`){let i=n.match(/title:([^,}]+)/g);if(i)for(let n of i){let i=n.replace(`title:`,``).trim();r.push({handle:`mac-window-${t}`,title:i,className:e.name,processId:t,threadId:0})}}return r}catch(n){return e.error(`Failed to get windows for PID ${t}:`,n),[]}}async getProcessWindowsCG(t){try{t=U(t);let{stdout:e}=await Ae(`python3`,[`-c`,Me(await new L().loadScript(`process_list.py`),{PID:t})],{timeout:y*2,windowsHide:!0}),n=[];try{let t=JSON.parse(e.trim());for(let e of t)n.push({handle:e.handle,title:e.title,className:e.className,processId:e.processId,threadId:0,bounds:e.bounds?{x:e.bounds.X||0,y:e.bounds.Y||0,width:e.bounds.Width||0,height:e.bounds.Height||0}:void 0})}catch{}return n}catch(n){return e.error(`Failed to get windows via CoreGraphics for PID ${t}:`,n),[]}}async findChromeProcesses(){let t={rendererProcesses:[],utilityProcesses:[]};try{let n=await this.findProcesses(`chrome`),r=await Promise.all(n.map(e=>this.getProcessByPid(e.pid)));for(let e=0;e<n.length;e++){let i=n[e],a=r[e];if(a?.commandLine){let e=a.commandLine.toLowerCase();e.includes(`--type=renderer`)?t.rendererProcesses.push({...i,...a}):e.includes(`--type=gpu-process`)?t.gpuProcess={...i,...a}:e.includes(`--type=utility`)?t.utilityProcesses.push({...i,...a}):e.includes(`--type=`)||(t.mainProcess={...i,...a})}else t.mainProcess||=i}if(t.mainProcess){let e=await this.getProcessWindowsCG(t.mainProcess.pid);e.length>0&&(t.targetWindow=e[0])}return e.info(`Chrome processes found:`,{main:t.mainProcess?.pid,renderers:t.rendererProcesses.length,hasTargetWindow:!!t.targetWindow}),t}catch(n){return e.error(`Failed to find Chrome processes:`,n),t}}async getProcessCommandLine(t){try{t=U(t);let{stdout:e}=await H(`ps -p ${t} -o ppid=,args= 2>/dev/null || echo ""`),n=e.trim().split(/\s+/);return n.length>=2?{parentPid:parseInt(n[0]||`0`,10),commandLine:n.slice(1).join(` `)||void 0}:{}}catch(n){return e.error(`Failed to get command line for PID ${t}:`,n),{}}}async checkDebugPort(t,n){try{t=U(t);let e=n?.commandLine??(await this.getProcessCommandLine(t)).commandLine;if(e){let t=e.match(/--remote-debugging-port=(\d+)/);if(t?.[1])return parseInt(t[1],10)}let{stdout:r}=await H(`lsof -Pan -p ${t} -i 2>/dev/null | grep LISTEN || true`,{maxBuffer:1024*1024});for(let e of o)if(r.includes(`:${e}`))return e;return null}catch(n){return e.error(`Failed to check debug port for PID ${t}:`,n),null}}async launchWithDebug(t,n=u,r=[]){try{let i=P(t,[`--remote-debugging-port=${n}`,...r],{detached:!0,stdio:`ignore`});if(i.unref(),w.register(i),await new Promise(e=>setTimeout(e,te)),!i.pid)return e.error(`Failed to spawn process: PID is undefined for ${t}`),null;let a=await this.getProcessByPid(i.pid);return e.info(`Launched process with debug port ${n}:`,{pid:i.pid,executable:t}),a}catch(t){return e.error(`Failed to launch process with debug:`,t),null}}async killProcess(t){try{return t=U(t),await H(`kill -9 ${t} 2>/dev/null || kill -15 ${t}`),e.info(`Process ${t} killed successfully`),!0}catch(n){return e.error(`Failed to kill process ${t}:`,n),!1}}};const Pe=/^(?:0x)?[0-9a-fA-F]{1,16}$/;async function Fe(t,n,r){try{let{stdout:e}=await T(`
|
|
32
|
+
Add-Type @"
|
|
33
|
+
using System;
|
|
34
|
+
using System.Runtime.InteropServices;
|
|
35
|
+
using System.ComponentModel;
|
|
36
|
+
|
|
37
|
+
public class MemoryReader {
|
|
38
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
39
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
40
|
+
|
|
41
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
42
|
+
public static extern bool ReadProcessMemory(IntPtr hProcess, IntPtr addr, byte[] buffer, int size, out int read);
|
|
43
|
+
|
|
44
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
45
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
46
|
+
|
|
47
|
+
const int PROCESS_VM_READ = 0x0010;
|
|
48
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
49
|
+
|
|
50
|
+
public static string ReadMemory(int pid, long address, int size) {
|
|
51
|
+
IntPtr hProcess = OpenProcess(PROCESS_VM_READ | PROCESS_QUERY_INFORMATION, false, pid);
|
|
52
|
+
if (hProcess == IntPtr.Zero) {
|
|
53
|
+
int error = Marshal.GetLastWin32Error();
|
|
54
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
55
|
+
}
|
|
56
|
+
|
|
57
|
+
try {
|
|
58
|
+
byte[] buffer = new byte[size];
|
|
59
|
+
int bytesRead;
|
|
60
|
+
bool success = ReadProcessMemory(hProcess, (IntPtr)address, buffer, size, out bytesRead);
|
|
61
|
+
|
|
62
|
+
if (!success) {
|
|
63
|
+
int error = Marshal.GetLastWin32Error();
|
|
64
|
+
throw new Win32Exception(error, "Failed to read memory");
|
|
65
|
+
}
|
|
66
|
+
|
|
67
|
+
return BitConverter.ToString(buffer, 0, bytesRead).Replace("-", " ");
|
|
68
|
+
} finally {
|
|
69
|
+
CloseHandle(hProcess);
|
|
70
|
+
}
|
|
71
|
+
}
|
|
72
|
+
}
|
|
73
|
+
"@
|
|
74
|
+
|
|
75
|
+
try {
|
|
76
|
+
$result = [MemoryReader]::ReadMemory(${t}, ${n}, ${r})
|
|
77
|
+
@{ success = $true; data = $result } | ConvertTo-Json -Compress
|
|
78
|
+
} catch {
|
|
79
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
80
|
+
}
|
|
81
|
+
`,{maxBuffer:1024*1024*10}),i=e.trim();if(!i)throw Error(`PowerShell returned empty output`);let a=JSON.parse(i);return{success:a.success,data:a.data,error:a.error}}catch(t){return e.error(`Windows memory read failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed. Run as Administrator.`}}}let W=null,Ie=!1;async function Le(){if(Ie)return W;try{let{createPlatformProvider:e}=await import(`./factory-Cx_1LorX.mjs`).then(e=>e.n),t=e();(await t.checkAvailability()).available&&(W=t)}catch{}return Ie=!0,W}function Re(e,t){return e.subarray(0,t).toString(`hex`).toUpperCase().replace(/../g,`$& `)}async function ze(t,n,r){try{let i=await Le();if(i){let a=i.openProcess(t,!1);try{let t=i.readMemory(a,BigInt(n),r);return e.debug(`Native Linux memory read succeeded`),{success:!0,data:Re(t.data,t.bytesRead).trim()}}finally{i.closeProcess(a)}}}catch(t){e.debug(`Native Linux read failed, falling back to dd:`,t)}try{let{stdout:e}=await E(`dd if=/proc/${t}/mem bs=1 skip=${n} count=${r} 2>/dev/null | xxd -p | tr -d '\\n' || echo ""`,{maxBuffer:1024*1024*10,timeout:d});return e.trim()?{success:!0,data:(e.trim().match(/.{1,2}/g)?.join(` `)||e.trim()).toUpperCase()}:{success:!1,error:`Failed to read memory. Requires ptrace access or root. Check kernel.yama.ptrace_scope if access denied.`}}catch(t){return e.error(`Linux memory read failed:`,t),{success:!1,error:`Memory read failed. Requires ptrace access or root (check kernel.yama.ptrace_scope).`}}}async function Be(t,n,r,i){if(n===0)return{success:!1,error:`Invalid address: null pointer (0x0)`};if(r<=0||r>C)return{success:!1,error:`Invalid size: must be 1–${C} bytes`};let a=`0x${n.toString(16)}`;try{let{createPlatformProvider:i}=await import(`./factory-Cx_1LorX.mjs`).then(e=>e.n),a=i();if((await a.checkAvailability()).available){let i=a.openProcess(t,!1);try{let t=a.readMemory(i,BigInt(n),r),o=Array.from(t.data.subarray(0,t.bytesRead)).map(e=>e.toString(16).padStart(2,`0`).toUpperCase()).join(` `);return e.debug(`Native Mach memory read succeeded (zero-pause)`),{success:!0,data:o}}finally{a.closeProcess(i)}}}catch(t){e.debug(`Native Mach read failed, falling back to lldb:`,t)}let o=await i(t,a);if(!o.success)return{success:!1,error:`Cannot verify memory region: ${o.error}`};if(!o.isReadable)return{success:!1,error:`Address ${a} is not readable (protection: ${o.protection??`unknown`})`};let s=`/tmp/mread_${t}_${Date.now()}.bin`;try{let{stdout:e}=await E(`lldb --batch -p ${t} -o "memory read --outfile ${s} --binary ${a} -c ${r}" -o "process detach"`,{timeout:ee,maxBuffer:1024*1024*10});if(!e.includes(`bytes written`))return{success:!1,error:`lldb memory read failed: ${(e.split(`
|
|
82
|
+
`).find(e=>e.includes(`error:`))??e).trim()}`};let n=await j.readFile(s);return{success:!0,data:Array.from(n).map(e=>e.toString(16).padStart(2,`0`).toUpperCase()).join(` `)}}catch(e){return{success:!1,error:e instanceof Error?e.message:String(e)}}finally{await j.unlink(s).catch(()=>{})}}async function Ve(t,n,r,i,a){try{if(!Pe.test(r))return{success:!1,error:`Invalid address format. Use hex like "0x12345678"`};let o=parseInt(r,16);if(isNaN(o))return{success:!1,error:`Invalid address format. Use hex like "0x12345678"`};if(i<=0||i>C)return{success:!1,error:`Read size must be 1–${C} bytes (${(C/1024/1024).toFixed(0)} MB)`};if(t===`win32`&&ie())try{let t=await k.readMemory(n,r,i);if(t.success)return e.debug(`Native memory read succeeded`),t;e.warn(`Native memory read failed, falling back to PowerShell:`,t.error)}catch(t){e.warn(`Native memory read error, falling back to PowerShell:`,t)}switch(t){case`win32`:return Fe(n,o,i);case`linux`:return ze(n,o,i);case`darwin`:return Be(n,o,i,a);default:return{success:!1,error:`Memory operations not supported on platform: ${t}`}}}catch(t){return e.error(`Memory read failed:`,t),{success:!1,error:t instanceof Error?t.message:String(t)}}}async function He(t,n,r){try{let{stdout:e}=await T(`
|
|
83
|
+
Add-Type @"
|
|
84
|
+
using System;
|
|
85
|
+
using System.Runtime.InteropServices;
|
|
86
|
+
using System.ComponentModel;
|
|
87
|
+
|
|
88
|
+
public class MemoryWriter {
|
|
89
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
90
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
91
|
+
|
|
92
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
93
|
+
public static extern bool WriteProcessMemory(IntPtr hProcess, IntPtr addr, byte[] buffer, int size, out int written);
|
|
94
|
+
|
|
95
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
96
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
97
|
+
|
|
98
|
+
const int PROCESS_VM_WRITE = 0x0020;
|
|
99
|
+
const int PROCESS_VM_OPERATION = 0x0008;
|
|
100
|
+
|
|
101
|
+
public static int WriteMemory(int pid, long address, string hexData) {
|
|
102
|
+
IntPtr hProcess = OpenProcess(PROCESS_VM_WRITE | PROCESS_VM_OPERATION, false, pid);
|
|
103
|
+
if (hProcess == IntPtr.Zero) {
|
|
104
|
+
int error = Marshal.GetLastWin32Error();
|
|
105
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
106
|
+
}
|
|
107
|
+
|
|
108
|
+
try {
|
|
109
|
+
byte[] buffer = new byte[hexData.Length / 2];
|
|
110
|
+
for (int i = 0; i < hexData.Length; i += 2) {
|
|
111
|
+
buffer[i / 2] = Convert.ToByte(hexData.Substring(i, 2), 16);
|
|
112
|
+
}
|
|
113
|
+
|
|
114
|
+
int bytesWritten;
|
|
115
|
+
bool success = WriteProcessMemory(hProcess, (IntPtr)address, buffer, buffer.Length, out bytesWritten);
|
|
116
|
+
|
|
117
|
+
if (!success) {
|
|
118
|
+
int error = Marshal.GetLastWin32Error();
|
|
119
|
+
throw new Win32Exception(error, "Failed to write memory");
|
|
120
|
+
}
|
|
121
|
+
|
|
122
|
+
return bytesWritten;
|
|
123
|
+
} finally {
|
|
124
|
+
CloseHandle(hProcess);
|
|
125
|
+
}
|
|
126
|
+
}
|
|
127
|
+
}
|
|
128
|
+
"@
|
|
129
|
+
|
|
130
|
+
try {
|
|
131
|
+
$bytesWritten = [MemoryWriter]::WriteMemory(${t}, ${n}, "${r.toString(`hex`).toUpperCase()}")
|
|
132
|
+
@{ success = $true; bytesWritten = $bytesWritten } | ConvertTo-Json -Compress
|
|
133
|
+
} catch {
|
|
134
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
135
|
+
}
|
|
136
|
+
`,{maxBuffer:1024*1024}),i=e.trim();if(!i)throw Error(`PowerShell returned empty output`);let a=JSON.parse(i);return{success:a.success,bytesWritten:a.bytesWritten,error:a.error}}catch(t){return e.error(`Windows memory write failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed. Run as Administrator.`}}}let G=null,Ue=!1;async function We(){if(Ue)return G;try{let{createPlatformProvider:e}=await import(`./factory-Cx_1LorX.mjs`).then(e=>e.n),t=e();(await t.checkAvailability()).available&&(G=t)}catch{}return Ue=!0,G}async function Ge(t,n,r){try{let i=await We();if(i){let a=i.openProcess(t,!0);try{let t=i.writeMemory(a,BigInt(n),r);return e.debug(`Native Linux memory write succeeded`),{success:!0,bytesWritten:t.bytesWritten}}finally{i.closeProcess(a)}}}catch(t){e.debug(`Native Linux write failed, falling back to dd:`,t)}try{let{stderr:e}=await E(`printf "${r.toString(`hex`)}" | xxd -r -p | dd of=/proc/${t}/mem bs=1 seek=${n} conv=notrunc`,{maxBuffer:1024*1024,timeout:l});return e&&/error|denied|cannot/i.test(e)?{success:!1,error:`Memory write failed. Requires ptrace access or root. Check kernel.yama.ptrace_scope if access denied.`}:{success:!0,bytesWritten:r.length}}catch(t){return e.error(`Linux memory write failed:`,t),{success:!1,error:`Memory write failed. Requires ptrace access or root (check kernel.yama.ptrace_scope).`}}}async function Ke(n,r,i,a){if(r===0)return{success:!1,error:`Invalid address: null pointer (0x0)`};if(i.length===0||i.length>t)return{success:!1,error:`Invalid write size: must be 1–${t} bytes`};let o=`0x${r.toString(16)}`;try{let{createPlatformProvider:t}=await import(`./factory-Cx_1LorX.mjs`).then(e=>e.n),a=t();if((await a.checkAvailability()).available){let t=a.openProcess(n,!0);try{let n=a.writeMemory(t,BigInt(r),i);return e.debug(`Native Mach memory write succeeded (zero-pause)`),{success:!0,bytesWritten:n.bytesWritten}}finally{a.closeProcess(t)}}}catch(t){e.debug(`Native Mach write failed, falling back to lldb:`,t)}let s=await a(n,o);if(!s.success)return{success:!1,error:`Cannot verify memory region: ${s.error}`};if(!s.isWritable)return{success:!1,error:`Address ${o} is not writable (protection: ${s.protection??`unknown`})`};try{let{stdout:e}=await E(`lldb --batch -p ${n} -o "memory write ${o} ${Array.from(i).map(e=>`0x${e.toString(16).padStart(2,`0`)}`).join(` `)}" -o "process detach"`,{timeout:l,maxBuffer:1024*1024});return e.includes(`error:`)?{success:!1,error:`lldb memory write failed: ${(e.split(`
|
|
137
|
+
`).find(e=>e.includes(`error:`))??e).trim()}`}:{success:!0,bytesWritten:i.length}}catch(e){return{success:!1,error:e instanceof Error?e.message:String(e)}}}const qe=/^(?:0x)?[0-9a-fA-F]{1,16}$/;async function Je(n,r,i,a,o=`hex`,s){try{if(!qe.test(i))return{success:!1,error:`Invalid address format. Use hex like "0x12345678"`};let c=parseInt(i,16);if(isNaN(c))return{success:!1,error:`Invalid address format`};let l;try{if(o===`base64`)l=Buffer.from(a,`base64`);else{let e=a.replace(/\s/g,``);l=Buffer.from(e,`hex`)}}catch{return{success:!1,error:`Invalid ${o} data`}}if(l.length===0||l.length>t)return{success:!1,error:`Write size must be 1–${t} bytes (${(t/1024).toFixed(0)} KB)`};if(n===`win32`&&ie())try{let t=await k.writeMemory(r,i,a,o);if(t.success)return e.debug(`Native memory write succeeded`),t;e.warn(`Native memory write failed, falling back to PowerShell:`,t.error)}catch(t){e.warn(`Native memory write error, falling back to PowerShell:`,t)}switch(n){case`win32`:return He(r,c,l);case`linux`:return Ge(r,c,l);case`darwin`:return Ke(r,c,l,s);default:return{success:!1,error:`Memory operations not supported on platform: ${n}`}}}catch(t){return e.error(`Memory write failed:`,t),{success:!1,error:t instanceof Error?t.message:String(t)}}}const Ye=1e3;async function Xe(e,t,n){if(t.length>Ye)return{success:!1,results:[],error:`Too many patches (${t.length}), max ${Ye}`};let r=[];for(let i of t){let t=await n(e,i.address,i.data,i.encoding||`hex`);r.push({address:i.address,success:t.success,error:t.error})}let i=r.every(e=>e.success);return{success:i,results:r,error:i?void 0:`Failed to write ${r.filter(e=>!e.success).length} of ${r.length} patches`}}function Ze(e,t){let n=[],r=[];switch(t){case`hex`:{let t=e.trim().split(/\s+/);for(let e of t)if(e===`??`||e===`**`||e===`?`)n.push(0),r.push(0);else{let t=parseInt(e,16);isNaN(t)||(n.push(t),r.push(1))}break}case`int32`:{let t=parseInt(e);if(!isNaN(t)){let e=Buffer.allocUnsafe(4);e.writeInt32LE(t,0),n=Array.from(e),r=[1,1,1,1]}break}case`int64`:{let t=BigInt.asIntN(64,BigInt(e)),i=Buffer.allocUnsafe(8);i.writeBigInt64LE(t,0),n=Array.from(i),r=[1,1,1,1,1,1,1,1];break}case`float`:{let t=parseFloat(e);if(!isNaN(t)){let e=Buffer.allocUnsafe(4);e.writeFloatLE(t,0),n=Array.from(e),r=[1,1,1,1]}break}case`double`:{let t=parseFloat(e);if(!isNaN(t)){let e=Buffer.allocUnsafe(8);e.writeDoubleLE(t,0),n=Array.from(e),r=[1,1,1,1,1,1,1,1]}break}case`string`:{let t=Buffer.from(e,`utf8`);n=Array.from(t),r=n.map(()=>1);break}}if(n.length===0)throw Error(`Invalid pattern`);return{patternBytes:n,mask:r}}function Qe(e,t){let n=[],r=[];switch(t){case`hex`:{let t=e.trim().split(/\s+/);for(let e of t)if(e===`??`||e===`?`||e===`**`)n.push(0),r.push(0);else{let t=parseInt(e,16);if(isNaN(t))throw Error(`Invalid hex byte: ${e}`);n.push(t),r.push(1)}if(!n.length)throw Error(`Pattern is empty`);break}case`int32`:{let t=parseInt(e);if(isNaN(t))throw Error(`Invalid int32 value`);let i=Buffer.allocUnsafe(4);i.writeInt32LE(t,0);let a=Array.from(i);n.push(...a),r.push(...a.map(()=>1));break}case`int64`:{let t=Buffer.allocUnsafe(8);t.writeBigInt64LE(BigInt.asIntN(64,BigInt(e)),0);let i=Array.from(t);n.push(...i),r.push(...i.map(()=>1));break}case`float`:{let t=parseFloat(e);if(isNaN(t))throw Error(`Invalid float value`);let i=Buffer.allocUnsafe(4);i.writeFloatLE(t,0);let a=Array.from(i);n.push(...a),r.push(...a.map(()=>1));break}case`double`:{let t=parseFloat(e);if(isNaN(t))throw Error(`Invalid double value`);let i=Buffer.allocUnsafe(8);i.writeDoubleLE(t,0);let a=Array.from(i);n.push(...a),r.push(...a.map(()=>1));break}case`string`:{let t=Array.from(Buffer.from(e,`utf8`));n.push(...t),r.push(...t.map(()=>1));break}default:throw Error(`Unsupported pattern type: ${t}`)}return{bytes:n,mask:r}}function $e(e,t,n){let{patternBytes:r,mask:i}=Ze(t,n);return`
|
|
138
|
+
Add-Type @"
|
|
139
|
+
using System;
|
|
140
|
+
using System.Runtime.InteropServices;
|
|
141
|
+
using System.Collections.Generic;
|
|
142
|
+
using System.ComponentModel;
|
|
143
|
+
|
|
144
|
+
public class MemoryScanner {
|
|
145
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
146
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
147
|
+
|
|
148
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
149
|
+
public static extern bool ReadProcessMemory(IntPtr hProcess, IntPtr addr, byte[] buffer, int size, out int read);
|
|
150
|
+
|
|
151
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
152
|
+
public static extern int VirtualQueryEx(IntPtr hProcess, IntPtr addr, out MEMORY_BASIC_INFORMATION info, int size);
|
|
153
|
+
|
|
154
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
155
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
156
|
+
|
|
157
|
+
const int PROCESS_VM_READ = 0x0010;
|
|
158
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
159
|
+
|
|
160
|
+
[StructLayout(LayoutKind.Sequential)]
|
|
161
|
+
public struct MEMORY_BASIC_INFORMATION {
|
|
162
|
+
public IntPtr BaseAddress;
|
|
163
|
+
public IntPtr AllocationBase;
|
|
164
|
+
public uint AllocationProtect;
|
|
165
|
+
public IntPtr RegionSize;
|
|
166
|
+
public uint State;
|
|
167
|
+
public uint Protect;
|
|
168
|
+
public uint Type;
|
|
169
|
+
}
|
|
170
|
+
|
|
171
|
+
const uint MEM_COMMIT = 0x1000;
|
|
172
|
+
const uint PAGE_READONLY = 0x02;
|
|
173
|
+
const uint PAGE_READWRITE = 0x04;
|
|
174
|
+
const uint PAGE_WRITECOPY = 0x08;
|
|
175
|
+
const uint PAGE_EXECUTE_READ = 0x20;
|
|
176
|
+
const uint PAGE_EXECUTE_READWRITE = 0x40;
|
|
177
|
+
|
|
178
|
+
public static List<string> ScanMemory(int pid, byte[] pattern, byte[] mask, int maxResults = 10000) {
|
|
179
|
+
var results = new List<string>();
|
|
180
|
+
IntPtr hProcess = OpenProcess(PROCESS_VM_READ | PROCESS_QUERY_INFORMATION, false, pid);
|
|
181
|
+
if (hProcess == IntPtr.Zero) {
|
|
182
|
+
int error = Marshal.GetLastWin32Error();
|
|
183
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
184
|
+
}
|
|
185
|
+
|
|
186
|
+
try {
|
|
187
|
+
IntPtr addr = IntPtr.Zero;
|
|
188
|
+
MEMORY_BASIC_INFORMATION info;
|
|
189
|
+
int infoSize = Marshal.SizeOf(typeof(MEMORY_BASIC_INFORMATION));
|
|
190
|
+
int scannedRegions = 0;
|
|
191
|
+
|
|
192
|
+
while (VirtualQueryEx(hProcess, addr, out info, infoSize) == infoSize) {
|
|
193
|
+
scannedRegions++;
|
|
194
|
+
bool isReadable = (info.State == MEM_COMMIT) &&
|
|
195
|
+
((info.Protect & PAGE_READONLY) != 0 ||
|
|
196
|
+
(info.Protect & PAGE_READWRITE) != 0 ||
|
|
197
|
+
(info.Protect & PAGE_WRITECOPY) != 0 ||
|
|
198
|
+
(info.Protect & PAGE_EXECUTE_READ) != 0 ||
|
|
199
|
+
(info.Protect & PAGE_EXECUTE_READWRITE) != 0);
|
|
200
|
+
|
|
201
|
+
if (isReadable && info.RegionSize.ToInt64() > 0 && info.RegionSize.ToInt64() < 1073741824) {
|
|
202
|
+
long regionSize = info.RegionSize.ToInt64();
|
|
203
|
+
if (regionSize > 16777216) regionSize = 16777216; // bound scan window per region (16MB)
|
|
204
|
+
byte[] buffer = new byte[(int)regionSize];
|
|
205
|
+
int bytesRead;
|
|
206
|
+
|
|
207
|
+
if (ReadProcessMemory(hProcess, info.BaseAddress, buffer, buffer.Length, out bytesRead)) {
|
|
208
|
+
for (int i = 0; i <= bytesRead - pattern.Length; i++) {
|
|
209
|
+
if (PatternMatch(buffer, i, pattern, mask)) {
|
|
210
|
+
long foundAddr = info.BaseAddress.ToInt64() + i;
|
|
211
|
+
results.Add("0x" + foundAddr.ToString("X"));
|
|
212
|
+
if (results.Count >= maxResults) break;
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
}
|
|
216
|
+
}
|
|
217
|
+
|
|
218
|
+
if (results.Count >= maxResults) break;
|
|
219
|
+
if (scannedRegions >= 50000) break;
|
|
220
|
+
long baseAddr = info.BaseAddress.ToInt64();
|
|
221
|
+
long regionSizeRaw = info.RegionSize.ToInt64();
|
|
222
|
+
if (regionSizeRaw <= 0) break;
|
|
223
|
+
long nextAddr = baseAddr + regionSizeRaw;
|
|
224
|
+
if (nextAddr <= baseAddr) break;
|
|
225
|
+
addr = new IntPtr(nextAddr);
|
|
226
|
+
if (addr.ToInt64() >= 0x7FFFFFFF0000) break;
|
|
227
|
+
}
|
|
228
|
+
|
|
229
|
+
return results;
|
|
230
|
+
} finally {
|
|
231
|
+
CloseHandle(hProcess);
|
|
232
|
+
}
|
|
233
|
+
}
|
|
234
|
+
|
|
235
|
+
private static bool PatternMatch(byte[] buffer, int offset, byte[] pattern, byte[] mask) {
|
|
236
|
+
for (int i = 0; i < pattern.Length; i++) {
|
|
237
|
+
if (mask[i] == 1 && buffer[offset + i] != pattern[i]) {
|
|
238
|
+
return false;
|
|
239
|
+
}
|
|
240
|
+
}
|
|
241
|
+
return true;
|
|
242
|
+
}
|
|
243
|
+
}
|
|
244
|
+
"@
|
|
245
|
+
|
|
246
|
+
try {
|
|
247
|
+
$patternBytes = @(${r.join(`,`)})
|
|
248
|
+
$maskBytes = @(${i.join(`,`)})
|
|
249
|
+
$results = [MemoryScanner]::ScanMemory(${e}, $patternBytes, $maskBytes, 1000)
|
|
250
|
+
@{
|
|
251
|
+
success = $true;
|
|
252
|
+
addresses = $results;
|
|
253
|
+
stats = @{
|
|
254
|
+
patternLength = $patternBytes.Length;
|
|
255
|
+
resultsFound = $results.Count
|
|
256
|
+
}
|
|
257
|
+
} | ConvertTo-Json -Compress
|
|
258
|
+
} catch {
|
|
259
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
260
|
+
}
|
|
261
|
+
`.trim()}async function et(t,n,r){try{if(O())try{let i=await k.scanMemory(t,n,r);if(i.success)return i;e.warn(`Native Windows memory scan failed, falling back to PowerShell`,{pid:t,patternType:r,error:i.error,nativeAvailable:O()})}catch(n){e.warn(`Native Windows memory scan threw, falling back to PowerShell`,{pid:t,patternType:r,error:n instanceof Error?n.message:String(n),nativeAvailable:O()})}let{stdout:i,stderr:a}=await T($e(t,n,r),{maxBuffer:f,timeout:ne});if(a&&a.includes(`Error`))return{success:!1,addresses:[],error:a};let o=i.trim();if(!o)throw Error(`PowerShell returned empty output`);let s=JSON.parse(o);return{success:s.success,addresses:s.addresses||[],error:s.error,stats:s.stats}}catch(t){return e.error(`Windows memory scan failed:`,t),{success:!1,addresses:[],error:t instanceof Error?t.message:`PowerShell execution failed. Run as Administrator.`}}}function tt(e,t,n){let r=n;switch(r?.code){case`ENOENT`:case`ESRCH`:return`Process ${e} no longer exists or /proc/${e}/${t} is unavailable.`;case`EACCES`:case`EPERM`:return`Cannot access /proc/${e}/${t}. Requires root privileges or ptrace access.`;default:return r instanceof Error?r.message:String(n)}}async function nt(t,n,r){let i,a;try{let e=Ze(n,r);i=e.patternBytes,a=e.mask}catch(e){return{success:!1,addresses:[],error:e instanceof Error?e.message:`Invalid pattern`}}try{let n;try{n=ge(`/proc/${t}/maps`,`utf-8`)}catch(e){return{success:!1,addresses:[],error:tt(t,`maps`,e)}}let r=D(n),o=Array.isArray(r)?r.filter(e=>e.permissions.read):[],s;try{s=he(`/proc/${t}/mem`,`r`)}catch(e){return{success:!1,addresses:[],error:tt(t,`mem`,e)}}let c=new Set,l=16*1024*1024,u=1e4,d=Math.max(i.length-1,0);try{for(let n of o){if(c.size>=u)break;if(n.end<=n.start)continue;let r=0n,o=Buffer.alloc(0),f=n.end-n.start;for(;r<f&&c.size<u;){let p=f-r,m=Number(p>BigInt(l)?BigInt(l):p),h=Buffer.allocUnsafe(m),g;try{g=_e(s,h,0,m,n.start+r)}catch(i){let a=i;if(a?.code===`EIO`||a?.code===`EFAULT`||a?.code===`EACCES`||a?.code===`EPERM`){e.debug(`Skipping unreadable Linux memory region chunk`,{pid:t,start:`0x${n.start.toString(16)}`,offset:r.toString(),code:a.code});break}throw i}if(g<=0)break;let _=g===m?h:h.subarray(0,g),v=o.length>0?Buffer.concat([o,_]):_,ee=n.start+r-BigInt(o.length),y=BigInt(g),b=r+y>=f||g<m,x=b?0:Math.min(d,v.length),S=v.length-x,C=oe(v,i,a);for(let e of C){if(!b&&e>=S)continue;let t=ee+BigInt(e);if(!(t<n.start||t>=n.end)&&(c.add(`0x${t.toString(16)}`),c.size>=u))break}if(o=x>0?v.subarray(v.length-x):Buffer.alloc(0),r+=y,g<m){e.debug(`Linux memory scan stopped after short read`,{pid:t,start:`0x${n.start.toString(16)}`,requested:m,bytesRead:g});break}}}}finally{me(s)}let f=Array.from(c);return{success:!0,addresses:f,stats:{patternLength:i.length,resultsFound:f.length}}}catch(e){return{success:!1,addresses:[],error:e instanceof Error?e.message:String(e)}}}async function rt(t,n,r){let i,a;try{let e=Qe(n,r);i=e.bytes,a=e.mask}catch(e){return{success:!1,addresses:[],error:e instanceof Error?e.message:`Invalid pattern`}}try{let e=await it(t,i,a);if(e)return e}catch(t){e.debug(`Native Mach scan failed, falling back to lldb:`,t)}return at(t,i,a)}async function it(t,n,r){let{createPlatformProvider:i}=await import(`./factory-Cx_1LorX.mjs`).then(e=>e.n),a=i();if(!(await a.checkAvailability()).available)return null;let o=a.openProcess(t,!1),s=[],c=1e3;try{let e=0n;for(let t=0;t<5e4&&s.length<c;t++){let t=a.queryRegion(o,e);if(!t)break;if(t.isReadable&&t.size>0&&t.size<=33554432)try{let e=oe(a.readMemory(o,t.baseAddress,t.size).data,n,r);for(let n of e)if(s.push(`0x${(t.baseAddress+BigInt(n)).toString(16)}`),s.length>=c)break}catch{}if(e=t.baseAddress+BigInt(t.size),e<=t.baseAddress)break}}finally{a.closeProcess(o)}return e.debug(`Native Mach scan completed (zero-pause): ${s.length} results`),{success:!0,addresses:s,stats:{patternLength:n.length,resultsFound:s.length}}}async function at(e,t,n){let r=t.map(e=>`0x${e.toString(16)}`).join(`,`),i=n.join(`,`),a=`${e}_${Date.now()}`,o=`/tmp/lldb_scan_${a}.py`,s=`/tmp/lldb_scan_${a}.txt`,c=`
|
|
262
|
+
import lldb, json, sys
|
|
263
|
+
|
|
264
|
+
def __lldb_init_module(debugger, internal_dict):
|
|
265
|
+
proc = debugger.GetSelectedTarget().GetProcess()
|
|
266
|
+
pat = bytes([${r}])
|
|
267
|
+
mask = [${i}]
|
|
268
|
+
results = []
|
|
269
|
+
rl = proc.GetMemoryRegions()
|
|
270
|
+
for i in range(rl.GetSize()):
|
|
271
|
+
info = lldb.SBMemoryRegionInfo()
|
|
272
|
+
rl.GetMemoryRegionAtIndex(i, info)
|
|
273
|
+
if not info.IsReadable():
|
|
274
|
+
continue
|
|
275
|
+
s = info.GetRegionBase()
|
|
276
|
+
sz = info.GetRegionEnd() - s
|
|
277
|
+
if sz > 32 * 1024 * 1024:
|
|
278
|
+
continue
|
|
279
|
+
err = lldb.SBError()
|
|
280
|
+
data = proc.ReadMemory(s, sz, err)
|
|
281
|
+
if not err.Success():
|
|
282
|
+
continue
|
|
283
|
+
n = len(pat)
|
|
284
|
+
for j in range(len(data) - n + 1):
|
|
285
|
+
match = True
|
|
286
|
+
for k in range(n):
|
|
287
|
+
if mask[k] == 1 and data[j+k] != pat[k]:
|
|
288
|
+
match = False
|
|
289
|
+
break
|
|
290
|
+
if match:
|
|
291
|
+
results.append(hex(s + j))
|
|
292
|
+
if len(results) >= 1000:
|
|
293
|
+
break
|
|
294
|
+
if len(results) >= 1000:
|
|
295
|
+
break
|
|
296
|
+
sys.stdout.write('SCAN_RESULT:' + json.dumps({
|
|
297
|
+
'success': True,
|
|
298
|
+
'addresses': results,
|
|
299
|
+
'stats': {'patternLength': len(pat), 'resultsFound': len(results)}
|
|
300
|
+
}) + '\\n')
|
|
301
|
+
sys.stdout.flush()
|
|
302
|
+
`;await j.writeFile(o,c,`utf8`),await j.writeFile(s,`command script import ${o}\nprocess detach\n`,`utf8`);try{let{stdout:t}=await E(`lldb --batch -p ${e} --source ${s}`,{timeout:ne,maxBuffer:1024*1024*5}),n=t.split(`
|
|
303
|
+
`).find(e=>e.startsWith(`SCAN_RESULT:`));if(!n)return{success:!1,addresses:[],error:`lldb scan returned no result. ${t.split(`
|
|
304
|
+
`).find(e=>e.includes(`error:`))??``}`.trim()};try{return JSON.parse(n.slice(12))}catch{let e=t.split(`
|
|
305
|
+
`).find(e=>e.includes(`error:`))??``;if(e)return{success:!1,addresses:[],error:e.trim()};throw Error(`Unexpected end of JSON input`)}}catch(e){return{success:!1,addresses:[],error:e instanceof Error?e.message:String(e)}}finally{await j.unlink(o).catch(()=>{}),await j.unlink(s).catch(()=>{})}}async function ot(t,n,r,i=`hex`,a=!1){let o=!1;try{switch(a&&(o=await lt(t,n),o?e.info(`Suspended process ${n} for consistent memory scan`):e.warn(`Could not suspend process ${n} — scanning unsuspended`)),t){case`win32`:return await et(n,r,i);case`linux`:return await nt(n,r,i);case`darwin`:return await rt(n,r,i);default:return{success:!1,addresses:[],error:`Memory scan not supported on ${t}`}}}catch(t){return e.error(`Memory scan failed:`,t),{success:!1,addresses:[],error:t instanceof Error?t.message:String(t)}}finally{o&&(await ut(t,n),e.info(`Resumed process ${n} after memory scan`))}}async function st(e,t,n,r=`hex`,i,a){let o=[];for(let e of n){let t=parseInt(e,16);isNaN(t)||o.push(t)}if(o.length===0)return{success:!1,addresses:[],error:`No valid addresses provided`};let s=await a(e,t,r);if(!s.success||s.addresses.length===0)return{success:!0,addresses:[],stats:{resultsFound:0,patternLength:t.length}};let c=[];for(let e of s.addresses){let t=parseInt(e,16);o.some(e=>Math.abs(e-t)<256)&&(c.includes(e)||c.push(e))}return{success:!0,addresses:c,stats:{resultsFound:c.length,patternLength:t.length}}}async function ct(e,t){let{machTaskSelf:n,taskForPid:r,machPortDeallocate:i,KERN:a}=await import(`./DarwinAPI-DC4HGGLl.mjs`).then(e=>e.t),o=n(),{kr:s,task:c}=r(o,e);if(s!==a.SUCCESS)return!1;try{return t(c)}finally{i(o,c)}}async function lt(t,n){try{switch(t){case`darwin`:{let{taskSuspend:e,KERN:t}=await import(`./DarwinAPI-DC4HGGLl.mjs`).then(e=>e.t);return ct(n,n=>e(n)===t.SUCCESS)}case`linux`:{let{execAsync:e}=await import(`./types-DtThH00r.mjs`).then(e=>e.i);return await e(`kill -STOP ${n}`,{timeout:m}),!0}case`win32`:{let{execAsync:e}=await import(`./types-DtThH00r.mjs`).then(e=>e.i);return await e(`powershell -NoProfile -Command "(Add-Type -MemberDefinition '[DllImport("ntdll.dll")] public static extern int NtSuspendProcess(IntPtr h);' -Name W -Namespace N -PassThru)::NtSuspendProcess((Get-Process -Id ${n}).Handle)"`,{timeout:p}),!0}default:return!1}}catch(t){return e.warn(`Failed to suspend process ${n}:`,t),!1}}async function ut(t,n){try{switch(t){case`darwin`:{let{taskResume:e}=await import(`./DarwinAPI-DC4HGGLl.mjs`).then(e=>e.t);await ct(n,t=>{e(t)});break}case`linux`:{let{execAsync:e}=await import(`./types-DtThH00r.mjs`).then(e=>e.i);await e(`kill -CONT ${n}`,{timeout:m});break}case`win32`:{let{execAsync:e}=await import(`./types-DtThH00r.mjs`).then(e=>e.i);await e(`powershell -NoProfile -Command "(Add-Type -MemberDefinition '[DllImport("ntdll.dll")] public static extern int NtResumeProcess(IntPtr h);' -Name W -Namespace N -PassThru)::NtResumeProcess((Get-Process -Id ${n}).Handle)"`,{timeout:p});break}}}catch(t){e.error(`CRITICAL: Failed to resume process ${n} — may need manual SIGCONT:`,t)}}function dt(e,t,n,r){return`
|
|
306
|
+
Add-Type @"
|
|
307
|
+
using System;
|
|
308
|
+
using System.Runtime.InteropServices;
|
|
309
|
+
using System.IO;
|
|
310
|
+
using System.ComponentModel;
|
|
311
|
+
|
|
312
|
+
public class MemoryDumper {
|
|
313
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
314
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
315
|
+
|
|
316
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
317
|
+
public static extern bool ReadProcessMemory(IntPtr hProcess, IntPtr addr, byte[] buffer, int size, out int read);
|
|
318
|
+
|
|
319
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
320
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
321
|
+
|
|
322
|
+
const int PROCESS_VM_READ = 0x0010;
|
|
323
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
324
|
+
|
|
325
|
+
public static string DumpMemory(int pid, long address, int size, string outputPath) {
|
|
326
|
+
IntPtr hProcess = OpenProcess(PROCESS_VM_READ | PROCESS_QUERY_INFORMATION, false, pid);
|
|
327
|
+
if (hProcess == IntPtr.Zero) {
|
|
328
|
+
int error = Marshal.GetLastWin32Error();
|
|
329
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
330
|
+
}
|
|
331
|
+
|
|
332
|
+
try {
|
|
333
|
+
byte[] buffer = new byte[size];
|
|
334
|
+
int bytesRead;
|
|
335
|
+
|
|
336
|
+
if (!ReadProcessMemory(hProcess, (IntPtr)address, buffer, size, out bytesRead)) {
|
|
337
|
+
int error = Marshal.GetLastWin32Error();
|
|
338
|
+
throw new Win32Exception(error, "Failed to read memory");
|
|
339
|
+
}
|
|
340
|
+
|
|
341
|
+
File.WriteAllBytes(outputPath, buffer);
|
|
342
|
+
return "Dumped " + bytesRead + " bytes to " + outputPath;
|
|
343
|
+
} finally {
|
|
344
|
+
CloseHandle(hProcess);
|
|
345
|
+
}
|
|
346
|
+
}
|
|
347
|
+
}
|
|
348
|
+
"@
|
|
349
|
+
|
|
350
|
+
try {
|
|
351
|
+
$result = [MemoryDumper]::DumpMemory(${e}, ${t}, ${n}, "${r.replace(/\\/g,`\\\\`).replace(/"/g,'`"').replace(/\$/g,"`$")}")
|
|
352
|
+
@{ success = $true; message = $result } | ConvertTo-Json -Compress
|
|
353
|
+
} catch {
|
|
354
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
355
|
+
}
|
|
356
|
+
`.trim()}async function ft(t,n,r,a,o){if(t!==`win32`&&t!==`darwin`)return{success:!1,error:`Memory dump currently only implemented for Windows and macOS`};if(t===`darwin`){let e=parseInt(r,16);if(isNaN(e))return{success:!1,error:`Invalid address format`};if(!Number.isInteger(n)||n<=0)return{success:!1,error:`Invalid pid`};if(!Number.isInteger(a)||a<=0)return{success:!1,error:`Invalid size`};let t=`0x${e.toString(16)}`;try{let{stdout:e}=await re(`lldb`,[`--batch`,`-p`,String(n),`-o`,`memory read --outfile ${o} --binary ${t} -c ${a}`,`-o`,`process detach`],{timeout:i,maxBuffer:1024*1024});return e.includes(`bytes written`)?{success:!0}:{success:!1,error:`lldb dump failed: ${(e.split(`
|
|
357
|
+
`).find(e=>e.includes(`error:`))??e).trim()}`}}catch(e){return{success:!1,error:e instanceof Error?e.message:String(e)}}}try{let e=parseInt(r,16);if(isNaN(e))return{success:!1,error:`Invalid address format`};if(!Number.isInteger(n)||n<=0)return{success:!1,error:`Invalid pid`};if(!Number.isInteger(a)||a<=0)return{success:!1,error:`Invalid size`};let{stdout:t}=await T(dt(n,e,a,o),{maxBuffer:1024*1024,timeout:i}),s=t.trim();if(!s)throw Error(`PowerShell returned empty output`);let c=JSON.parse(s);return{success:c.success,error:c.error}}catch(t){return e.error(`Memory dump failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed`}}}function pt(e){return`
|
|
358
|
+
Add-Type @"
|
|
359
|
+
using System;
|
|
360
|
+
using System.Runtime.InteropServices;
|
|
361
|
+
using System.Collections.Generic;
|
|
362
|
+
using System.ComponentModel;
|
|
363
|
+
|
|
364
|
+
public class RegionEnumerator {
|
|
365
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
366
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
367
|
+
|
|
368
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
369
|
+
public static extern int VirtualQueryEx(IntPtr hProcess, IntPtr addr, out MEMORY_BASIC_INFORMATION info, int size);
|
|
370
|
+
|
|
371
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
372
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
373
|
+
|
|
374
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
375
|
+
|
|
376
|
+
[StructLayout(LayoutKind.Sequential)]
|
|
377
|
+
public struct MEMORY_BASIC_INFORMATION {
|
|
378
|
+
public IntPtr BaseAddress;
|
|
379
|
+
public IntPtr AllocationBase;
|
|
380
|
+
public uint AllocationProtect;
|
|
381
|
+
public IntPtr RegionSize;
|
|
382
|
+
public uint State;
|
|
383
|
+
public uint Protect;
|
|
384
|
+
public uint Type;
|
|
385
|
+
}
|
|
386
|
+
|
|
387
|
+
const uint MEM_COMMIT = 0x1000;
|
|
388
|
+
const uint MEM_FREE = 0x10000;
|
|
389
|
+
const uint MEM_RESERVE = 0x2000;
|
|
390
|
+
const uint PAGE_READONLY = 0x02;
|
|
391
|
+
const uint PAGE_READWRITE = 0x04;
|
|
392
|
+
const uint PAGE_WRITECOPY = 0x08;
|
|
393
|
+
const uint PAGE_EXECUTE = 0x10;
|
|
394
|
+
const uint PAGE_EXECUTE_READ = 0x20;
|
|
395
|
+
const uint PAGE_EXECUTE_READWRITE = 0x40;
|
|
396
|
+
|
|
397
|
+
public static List<object> EnumerateRegions(int pid) {
|
|
398
|
+
var regions = new List<object>();
|
|
399
|
+
IntPtr hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, false, pid);
|
|
400
|
+
if (hProcess == IntPtr.Zero) {
|
|
401
|
+
int error = Marshal.GetLastWin32Error();
|
|
402
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
403
|
+
}
|
|
404
|
+
|
|
405
|
+
try {
|
|
406
|
+
IntPtr addr = IntPtr.Zero;
|
|
407
|
+
MEMORY_BASIC_INFORMATION info;
|
|
408
|
+
int infoSize = Marshal.SizeOf(typeof(MEMORY_BASIC_INFORMATION));
|
|
409
|
+
int scannedRegions = 0;
|
|
410
|
+
|
|
411
|
+
while (VirtualQueryEx(hProcess, addr, out info, infoSize) == infoSize) {
|
|
412
|
+
scannedRegions++;
|
|
413
|
+
string state = info.State == MEM_COMMIT ?
|
|
414
|
+
"COMMIT" :
|
|
415
|
+
(info.State == MEM_RESERVE ? "RESERVE" : (info.State == MEM_FREE ? "FREE" : "UNKNOWN"));
|
|
416
|
+
string protect = GetProtectionString(info.Protect);
|
|
417
|
+
bool isReadable = (info.State == MEM_COMMIT) && ((info.Protect & (PAGE_READONLY | PAGE_READWRITE | PAGE_EXECUTE_READ | PAGE_EXECUTE_READWRITE)) != 0);
|
|
418
|
+
|
|
419
|
+
regions.Add(new {
|
|
420
|
+
baseAddress = "0x" + info.BaseAddress.ToInt64().ToString("X"),
|
|
421
|
+
size = info.RegionSize.ToInt64(),
|
|
422
|
+
state = state,
|
|
423
|
+
protection = protect,
|
|
424
|
+
isReadable = isReadable,
|
|
425
|
+
type = info.Type == 0x1000000 ? "IMAGE" : (info.Type == 0x40000 ? "MAPPED" : "PRIVATE")
|
|
426
|
+
});
|
|
427
|
+
|
|
428
|
+
if (regions.Count >= 10000 || scannedRegions >= 50000) break;
|
|
429
|
+
long baseAddr = info.BaseAddress.ToInt64();
|
|
430
|
+
long regionSize = info.RegionSize.ToInt64();
|
|
431
|
+
if (regionSize <= 0) break;
|
|
432
|
+
long nextAddr = baseAddr + regionSize;
|
|
433
|
+
if (nextAddr <= baseAddr) break;
|
|
434
|
+
addr = new IntPtr(nextAddr);
|
|
435
|
+
if (addr.ToInt64() >= 0x7FFFFFFF0000) break;
|
|
436
|
+
}
|
|
437
|
+
|
|
438
|
+
return regions;
|
|
439
|
+
} finally {
|
|
440
|
+
CloseHandle(hProcess);
|
|
441
|
+
}
|
|
442
|
+
}
|
|
443
|
+
|
|
444
|
+
private static string GetProtectionString(uint protect) {
|
|
445
|
+
if (protect == 0) return "NOACCESS";
|
|
446
|
+
string s = "";
|
|
447
|
+
if ((protect & 0x100) != 0) s += "NOACCESS ";
|
|
448
|
+
if ((protect & PAGE_READONLY) != 0) s += "R ";
|
|
449
|
+
if ((protect & PAGE_READWRITE) != 0) s += "RW ";
|
|
450
|
+
if ((protect & PAGE_WRITECOPY) != 0) s += "W ";
|
|
451
|
+
if ((protect & PAGE_EXECUTE) != 0) s += "X ";
|
|
452
|
+
if ((protect & PAGE_EXECUTE_READ) != 0) s += "RX ";
|
|
453
|
+
if ((protect & PAGE_EXECUTE_READWRITE) != 0) s += "RWX ";
|
|
454
|
+
if ((protect & 0x100) != 0) s += "GUARD ";
|
|
455
|
+
return s.Trim();
|
|
456
|
+
}
|
|
457
|
+
}
|
|
458
|
+
"@
|
|
459
|
+
|
|
460
|
+
try {
|
|
461
|
+
$regions = [RegionEnumerator]::EnumerateRegions(${e})
|
|
462
|
+
@{ success = $true; regions = $regions; count = $regions.Count } | ConvertTo-Json -Compress -Depth 10
|
|
463
|
+
} catch {
|
|
464
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
465
|
+
}
|
|
466
|
+
`.trim()}async function mt(t,n){if(t===`linux`)try{return{success:!0,regions:D(fe(`/proc/${n}/maps`,`utf-8`)).filter(e=>e.permissions.read).map(e=>({baseAddress:`0x${e.start.toString(16)}`,size:Number(e.end-e.start),state:`COMMIT`,protection:ae(e.permissions),isReadable:!0,type:e.pathname||`anonymous`}))}}catch(t){return e.error(`Linux region enumeration failed:`,t),{success:!1,error:t instanceof Error?t.message:String(t)}}if(t!==`win32`&&t!==`darwin`)return{success:!1,error:`Region enumeration currently only implemented for Windows, Linux, and macOS`};if(t===`darwin`)try{let{stdout:e}=await E(`vmmap -v ${n}`,{timeout:r,maxBuffer:1024*1024*5}),t=[],i=/^(\S[^\t]*?)\s{2,}([0-9a-f]+)-([0-9a-f]+)\s+\[.*?\]\s+([a-z-]+)\/([a-z-]+)/;for(let n of e.split(`
|
|
467
|
+
`)){let e=n.match(i);if(!e)continue;let r=e[1],a=e[2],o=e[3],s=e[4],c=e[5],l=parseInt(a,16),u=parseInt(o,16);t.push({baseAddress:`0x${a}`,size:u-l,type:r.trim(),protect:s,maxProtect:c,isReadable:s.includes(`r`),isWritable:s.includes(`w`),isExecutable:s.includes(`x`)})}return{success:!0,regions:t}}catch(t){return e.error(`macOS region enumeration failed:`,t),{success:!1,error:t instanceof Error?t.message:String(t)}}if(O())try{let t=await k.enumerateRegions(n);if(t.success)return t;e.warn(`Native Windows region enumeration failed, falling back to PowerShell`,{pid:n,error:t.error,nativeAvailable:O()})}catch(t){e.warn(`Native Windows region enumeration threw, falling back to PowerShell`,{pid:n,error:t instanceof Error?t.message:String(t),nativeAvailable:O()})}try{let{stdout:e}=await T(pt(n),{maxBuffer:1024*1024*10,timeout:S}),t=e.trim();if(!t)throw Error(`PowerShell returned empty output`);let r=JSON.parse(t);return{success:r.success,regions:r.regions,error:r.error}}catch(t){return e.error(`Region enumeration failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed`}}}function ht(e,t){return`
|
|
468
|
+
Add-Type @"
|
|
469
|
+
using System;
|
|
470
|
+
using System.Runtime.InteropServices;
|
|
471
|
+
using System.ComponentModel;
|
|
472
|
+
|
|
473
|
+
public class ProtectionChecker {
|
|
474
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
475
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
476
|
+
|
|
477
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
478
|
+
public static extern int VirtualQueryEx(IntPtr hProcess, IntPtr addr, out MEMORY_BASIC_INFORMATION info, int size);
|
|
479
|
+
|
|
480
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
481
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
482
|
+
|
|
483
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
484
|
+
|
|
485
|
+
[StructLayout(LayoutKind.Sequential)]
|
|
486
|
+
public struct MEMORY_BASIC_INFORMATION {
|
|
487
|
+
public IntPtr BaseAddress;
|
|
488
|
+
public IntPtr AllocationBase;
|
|
489
|
+
public uint AllocationProtect;
|
|
490
|
+
public IntPtr RegionSize;
|
|
491
|
+
public uint State;
|
|
492
|
+
public uint Protect;
|
|
493
|
+
public uint Type;
|
|
494
|
+
}
|
|
495
|
+
|
|
496
|
+
const uint MEM_COMMIT = 0x1000;
|
|
497
|
+
const uint PAGE_NOACCESS = 0x01;
|
|
498
|
+
const uint PAGE_READONLY = 0x02;
|
|
499
|
+
const uint PAGE_READWRITE = 0x04;
|
|
500
|
+
const uint PAGE_WRITECOPY = 0x08;
|
|
501
|
+
const uint PAGE_EXECUTE = 0x10;
|
|
502
|
+
const uint PAGE_EXECUTE_READ = 0x20;
|
|
503
|
+
const uint PAGE_EXECUTE_READWRITE = 0x40;
|
|
504
|
+
const uint PAGE_EXECUTE_WRITECOPY = 0x80;
|
|
505
|
+
const uint PAGE_GUARD = 0x100;
|
|
506
|
+
|
|
507
|
+
public static object CheckProtection(int pid, long address) {
|
|
508
|
+
IntPtr hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, false, pid);
|
|
509
|
+
if (hProcess == IntPtr.Zero) {
|
|
510
|
+
int error = Marshal.GetLastWin32Error();
|
|
511
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
512
|
+
}
|
|
513
|
+
|
|
514
|
+
try {
|
|
515
|
+
MEMORY_BASIC_INFORMATION info;
|
|
516
|
+
int infoSize = Marshal.SizeOf(typeof(MEMORY_BASIC_INFORMATION));
|
|
517
|
+
int result = VirtualQueryEx(hProcess, (IntPtr)address, out info, infoSize);
|
|
518
|
+
|
|
519
|
+
if (result != infoSize) {
|
|
520
|
+
return new { success = false, error = "Failed to query memory region" };
|
|
521
|
+
}
|
|
522
|
+
|
|
523
|
+
if (info.State != MEM_COMMIT) {
|
|
524
|
+
return new {
|
|
525
|
+
success = true,
|
|
526
|
+
protection = "NOT_COMMITTED",
|
|
527
|
+
isWritable = false,
|
|
528
|
+
isReadable = false,
|
|
529
|
+
isExecutable = false,
|
|
530
|
+
regionStart = "0x" + info.BaseAddress.ToInt64().ToString("X"),
|
|
531
|
+
regionSize = info.RegionSize.ToInt64()
|
|
532
|
+
};
|
|
533
|
+
}
|
|
534
|
+
|
|
535
|
+
uint protect = info.Protect;
|
|
536
|
+
string protectionStr = "";
|
|
537
|
+
bool isWritable = false;
|
|
538
|
+
bool isReadable = false;
|
|
539
|
+
bool isExecutable = false;
|
|
540
|
+
|
|
541
|
+
if ((protect & PAGE_NOACCESS) != 0) protectionStr += "NOACCESS ";
|
|
542
|
+
if ((protect & PAGE_READONLY) != 0) { protectionStr += "R "; isReadable = true; }
|
|
543
|
+
if ((protect & PAGE_READWRITE) != 0) { protectionStr += "RW "; isReadable = true; isWritable = true; }
|
|
544
|
+
if ((protect & PAGE_WRITECOPY) != 0) { protectionStr += "WC "; isReadable = true; isWritable = true; }
|
|
545
|
+
if ((protect & PAGE_EXECUTE) != 0) { protectionStr += "X "; isExecutable = true; }
|
|
546
|
+
if ((protect & PAGE_EXECUTE_READ) != 0) { protectionStr += "RX "; isReadable = true; isExecutable = true; }
|
|
547
|
+
if ((protect & PAGE_EXECUTE_READWRITE) != 0) {
|
|
548
|
+
protectionStr += "RWX ";
|
|
549
|
+
isReadable = true;
|
|
550
|
+
isWritable = true;
|
|
551
|
+
isExecutable = true;
|
|
552
|
+
;
|
|
553
|
+
}
|
|
554
|
+
if ((protect & PAGE_EXECUTE_WRITECOPY) != 0) {
|
|
555
|
+
protectionStr += "RWCX ";
|
|
556
|
+
isReadable = true;
|
|
557
|
+
isWritable = true;
|
|
558
|
+
isExecutable = true;
|
|
559
|
+
;
|
|
560
|
+
}
|
|
561
|
+
if ((protect & PAGE_GUARD) != 0) protectionStr += "GUARD ";
|
|
562
|
+
|
|
563
|
+
return new {
|
|
564
|
+
success = true,
|
|
565
|
+
protection = protectionStr.Trim(),
|
|
566
|
+
isWritable = isWritable,
|
|
567
|
+
isReadable = isReadable,
|
|
568
|
+
isExecutable = isExecutable,
|
|
569
|
+
regionStart = "0x" + info.BaseAddress.ToInt64().ToString("X"),
|
|
570
|
+
regionSize = info.RegionSize.ToInt64()
|
|
571
|
+
};
|
|
572
|
+
} finally {
|
|
573
|
+
CloseHandle(hProcess);
|
|
574
|
+
}
|
|
575
|
+
}
|
|
576
|
+
}
|
|
577
|
+
"@
|
|
578
|
+
|
|
579
|
+
try {
|
|
580
|
+
$result = [ProtectionChecker]::CheckProtection(${e}, ${t})
|
|
581
|
+
$result | ConvertTo-Json -Compress
|
|
582
|
+
} catch {
|
|
583
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
584
|
+
}
|
|
585
|
+
`.trim()}async function K(t,n,r){let i=BigInt(r.startsWith(`0x`)?r:`0x${r}`);if(t===`linux`)try{let e=D(await de.readFile(`/proc/${n}/maps`,`utf-8`)).find(e=>i>=e.start&&i<e.end);return e?{success:!0,protection:ae(e.permissions),isReadable:e.permissions.read,isWritable:e.permissions.write,isExecutable:e.permissions.exec,regionStart:`0x${e.start.toString(16)}`,regionSize:Number(e.end-e.start)}:{success:!1,error:`Address ${r} not found in any memory region`}}catch(e){return{success:!1,error:e instanceof Error?e.message:String(e)}}if(t===`darwin`){try{let{createPlatformProvider:e}=await import(`./factory-Cx_1LorX.mjs`).then(e=>e.n),t=e();if((await t.checkAvailability()).available){let e=t.openProcess(n,!1);try{let n=t.queryRegion(e,i);return n?{success:!0,protection:[n.isReadable?`r`:`-`,n.isWritable?`w`:`-`,n.isExecutable?`x`:`-`].join(``),isReadable:n.isReadable,isWritable:n.isWritable,isExecutable:n.isExecutable,regionStart:`0x${n.baseAddress.toString(16)}`,regionSize:n.size}:{success:!1,error:`Address ${r} not found in any memory region`}}finally{t.closeProcess(e)}}}catch{}try{let e=parseInt(r,16);if(isNaN(e))return{success:!1,error:`Invalid address format`};let{stdout:t}=await E(`vmmap -v ${n}`,{timeout:s,maxBuffer:1024*1024*5}),i=/^(\S[^\t]*?)\s{2,}([0-9a-f]+)-([0-9a-f]+)\s+\[.*?\]\s+([a-z-]+)\/([a-z-]+)/;for(let n of t.split(`
|
|
586
|
+
`)){let t=n.match(i);if(!t)continue;let r=parseInt(t[2],16),a=parseInt(t[3],16);if(e>=r&&e<a){let e=t[4];return{success:!0,protection:e,isReadable:e.includes(`r`),isWritable:e.includes(`w`),isExecutable:e.includes(`x`),regionStart:`0x${t[2]}`,regionSize:a-r}}}return{success:!1,error:`Address ${r} not found in any memory region`}}catch(e){return{success:!1,error:e instanceof Error?e.message:String(e)}}}if(O())try{let t=await k.checkMemoryProtection(n,r);if(t.success)return t;e.warn(`Native Windows memory protection check failed, falling back to PowerShell`,{pid:n,address:r,error:t.error,nativeAvailable:O()})}catch(t){e.warn(`Native Windows memory protection check threw, falling back to PowerShell`,{pid:n,address:r,error:t instanceof Error?t.message:String(t),nativeAvailable:O()})}try{let e=parseInt(r,16);if(isNaN(e))return{success:!1,error:`Invalid address format`};let{stdout:t}=await T(ht(n,e),{maxBuffer:1024*1024,timeout:g}),i=t.trim();if(!i)throw Error(`PowerShell returned empty output`);let a=JSON.parse(i);return{success:a.success,protection:a.protection,isWritable:a.isWritable,isReadable:a.isReadable,isExecutable:a.isExecutable,regionStart:a.regionStart,regionSize:a.regionSize,error:a.error}}catch(t){return e.error(`Memory protection check failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed`}}}async function gt(t,n){if(t!==`win32`)return{success:!1,error:`Module enumeration currently only implemented for Windows`};try{let{stdout:e}=await T(`
|
|
587
|
+
Add-Type @"
|
|
588
|
+
using System;
|
|
589
|
+
using System.Runtime.InteropServices;
|
|
590
|
+
using System.Collections.Generic;
|
|
591
|
+
using System.ComponentModel;
|
|
592
|
+
|
|
593
|
+
public class ModuleEnumerator {
|
|
594
|
+
[DllImport("psapi.dll", SetLastError = true)]
|
|
595
|
+
public static extern bool EnumProcessModules(IntPtr hProcess, [Out] IntPtr[] lphModule, int cb, out int lpcbNeeded);
|
|
596
|
+
|
|
597
|
+
[DllImport("psapi.dll", SetLastError = true)]
|
|
598
|
+
public static extern int GetModuleBaseName(IntPtr hProcess, IntPtr hModule, [Out] System.Text.StringBuilder lpBaseName, int nSize);
|
|
599
|
+
|
|
600
|
+
[DllImport("psapi.dll", SetLastError = true)]
|
|
601
|
+
public static extern bool GetModuleInformation(IntPtr hProcess, IntPtr hModule, out MODULEINFO lpmodinfo, int cb);
|
|
602
|
+
|
|
603
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
604
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
605
|
+
|
|
606
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
607
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
608
|
+
|
|
609
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
610
|
+
const int PROCESS_VM_READ = 0x0010;
|
|
611
|
+
|
|
612
|
+
[StructLayout(LayoutKind.Sequential)]
|
|
613
|
+
public struct MODULEINFO {
|
|
614
|
+
public IntPtr lpBaseOfDll;
|
|
615
|
+
public int SizeOfImage;
|
|
616
|
+
public IntPtr EntryPoint;
|
|
617
|
+
}
|
|
618
|
+
|
|
619
|
+
public static object Enumerate(int pid) {
|
|
620
|
+
IntPtr hProcess = OpenProcess(PROCESS_QUERY_INFORMATION | PROCESS_VM_READ, false, pid);
|
|
621
|
+
if (hProcess == IntPtr.Zero) {
|
|
622
|
+
int error = Marshal.GetLastWin32Error();
|
|
623
|
+
throw new Win32Exception(error, "Failed to open process");
|
|
624
|
+
}
|
|
625
|
+
|
|
626
|
+
try {
|
|
627
|
+
IntPtr[] modules = new IntPtr[1024];
|
|
628
|
+
int cbNeeded;
|
|
629
|
+
|
|
630
|
+
if (!EnumProcessModules(hProcess, modules, modules.Length * IntPtr.Size, out cbNeeded)) {
|
|
631
|
+
int error = Marshal.GetLastWin32Error();
|
|
632
|
+
throw new Win32Exception(error, "EnumProcessModules failed");
|
|
633
|
+
}
|
|
634
|
+
|
|
635
|
+
int numModules = cbNeeded / IntPtr.Size;
|
|
636
|
+
var result = new List<object>();
|
|
637
|
+
|
|
638
|
+
for (int i = 0; i < numModules; i++) {
|
|
639
|
+
System.Text.StringBuilder baseName = new System.Text.StringBuilder(256);
|
|
640
|
+
if (GetModuleBaseName(hProcess, modules[i], baseName, baseName.Capacity) > 0) {
|
|
641
|
+
MODULEINFO modInfo;
|
|
642
|
+
if (GetModuleInformation(hProcess, modules[i], out modInfo, Marshal.SizeOf(typeof(MODULEINFO)))) {
|
|
643
|
+
result.Add(new {
|
|
644
|
+
name = baseName.ToString(),
|
|
645
|
+
baseAddress = "0x" + modInfo.lpBaseOfDll.ToInt64().ToString("X"),
|
|
646
|
+
size = modInfo.SizeOfImage
|
|
647
|
+
});
|
|
648
|
+
}
|
|
649
|
+
}
|
|
650
|
+
}
|
|
651
|
+
|
|
652
|
+
return new { success = true, modules = result };
|
|
653
|
+
} finally {
|
|
654
|
+
CloseHandle(hProcess);
|
|
655
|
+
}
|
|
656
|
+
}
|
|
657
|
+
}
|
|
658
|
+
"@
|
|
659
|
+
|
|
660
|
+
try {
|
|
661
|
+
$result = [ModuleEnumerator]::Enumerate(${n})
|
|
662
|
+
$result | ConvertTo-Json -Compress -Depth 10
|
|
663
|
+
} catch {
|
|
664
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
665
|
+
}
|
|
666
|
+
`,{maxBuffer:1024*1024*10,timeout:S}),t=e.trim();if(!t)throw Error(`PowerShell returned empty output`);return JSON.parse(t)}catch(t){return e.error(`Module enumeration failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed`}}}function _t(e){if(/[`$"';|<>&()\\\n\r]/.test(e))throw Error(`Path contains unsafe characters: ${e}`)}function vt(e,t){return`
|
|
667
|
+
Add-Type @"
|
|
668
|
+
using System;
|
|
669
|
+
using System.Runtime.InteropServices;
|
|
670
|
+
using System.ComponentModel;
|
|
671
|
+
using System.IO;
|
|
672
|
+
|
|
673
|
+
public class DllInjector {
|
|
674
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
675
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
676
|
+
|
|
677
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
678
|
+
public static extern IntPtr VirtualAllocEx(IntPtr hProcess, IntPtr addr, int size, int allocType, int protect);
|
|
679
|
+
|
|
680
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
681
|
+
public static extern bool WriteProcessMemory(IntPtr hProcess, IntPtr addr, byte[] buffer, int size, out int written);
|
|
682
|
+
|
|
683
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
684
|
+
public static extern IntPtr CreateRemoteThread(IntPtr hProcess, IntPtr attr, int stackSize, IntPtr startAddr, IntPtr param, int flags, out int threadId);
|
|
685
|
+
|
|
686
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
687
|
+
public static extern IntPtr GetModuleHandle(string name);
|
|
688
|
+
|
|
689
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
690
|
+
public static extern IntPtr GetProcAddress(IntPtr hModule, string name);
|
|
691
|
+
|
|
692
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
693
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
694
|
+
|
|
695
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
696
|
+
public static extern bool VirtualFreeEx(IntPtr hProcess, IntPtr addr, int size, int freeType);
|
|
697
|
+
|
|
698
|
+
const int PROCESS_CREATE_THREAD = 0x0002;
|
|
699
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
700
|
+
const int PROCESS_VM_OPERATION = 0x0008;
|
|
701
|
+
const int PROCESS_VM_WRITE = 0x0020;
|
|
702
|
+
const int MEM_COMMIT = 0x1000;
|
|
703
|
+
const int MEM_RESERVE = 0x2000;
|
|
704
|
+
const int PAGE_READWRITE = 0x04;
|
|
705
|
+
const int MEM_RELEASE = 0x8000;
|
|
706
|
+
|
|
707
|
+
public static object Inject(int pid, string dllPath) {
|
|
708
|
+
if (!File.Exists(dllPath)) {
|
|
709
|
+
return new { success = false, error = "DLL not found: " + dllPath };
|
|
710
|
+
}
|
|
711
|
+
|
|
712
|
+
IntPtr hProcess = OpenProcess(PROCESS_CREATE_THREAD | PROCESS_QUERY_INFORMATION | PROCESS_VM_OPERATION | PROCESS_VM_WRITE, false, pid);
|
|
713
|
+
if (hProcess == IntPtr.Zero) {
|
|
714
|
+
int error = Marshal.GetLastWin32Error();
|
|
715
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
716
|
+
}
|
|
717
|
+
|
|
718
|
+
try {
|
|
719
|
+
byte[] dllBytes = System.Text.Encoding.ASCII.GetBytes(dllPath + "\\0");
|
|
720
|
+
IntPtr remoteMem = VirtualAllocEx(hProcess, IntPtr.Zero, dllBytes.Length, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE);
|
|
721
|
+
if (remoteMem == IntPtr.Zero) {
|
|
722
|
+
int error = Marshal.GetLastWin32Error();
|
|
723
|
+
throw new Win32Exception(error, "Failed to allocate memory in target");
|
|
724
|
+
}
|
|
725
|
+
|
|
726
|
+
try {
|
|
727
|
+
int written;
|
|
728
|
+
if (!WriteProcessMemory(hProcess, remoteMem, dllBytes, dllBytes.Length, out written)) {
|
|
729
|
+
int error = Marshal.GetLastWin32Error();
|
|
730
|
+
throw new Win32Exception(error, "Failed to write DLL path to target");
|
|
731
|
+
}
|
|
732
|
+
|
|
733
|
+
IntPtr hKernel32 = GetModuleHandle("kernel32.dll");
|
|
734
|
+
IntPtr loadLibraryAddr = GetProcAddress(hKernel32, "LoadLibraryA");
|
|
735
|
+
if (loadLibraryAddr == IntPtr.Zero) {
|
|
736
|
+
throw new Exception("Failed to get LoadLibraryA address");
|
|
737
|
+
}
|
|
738
|
+
|
|
739
|
+
int threadId;
|
|
740
|
+
IntPtr hThread = CreateRemoteThread(hProcess, IntPtr.Zero, 0, loadLibraryAddr, remoteMem, 0, out threadId);
|
|
741
|
+
if (hThread == IntPtr.Zero) {
|
|
742
|
+
int error = Marshal.GetLastWin32Error();
|
|
743
|
+
throw new Win32Exception(error, "Failed to create remote thread");
|
|
744
|
+
}
|
|
745
|
+
|
|
746
|
+
CloseHandle(hThread);
|
|
747
|
+
return new { success = true, remoteThreadId = threadId };
|
|
748
|
+
} finally {
|
|
749
|
+
VirtualFreeEx(hProcess, remoteMem, 0, MEM_RELEASE);
|
|
750
|
+
}
|
|
751
|
+
} finally {
|
|
752
|
+
CloseHandle(hProcess);
|
|
753
|
+
}
|
|
754
|
+
}
|
|
755
|
+
}
|
|
756
|
+
"@
|
|
757
|
+
|
|
758
|
+
try {
|
|
759
|
+
$result = [DllInjector]::Inject(${e}, "${t.replace(/\\/g,`\\\\`).replace(/"/g,'`"').replace(/`/g,"``").replace(/\$/g,"`$")}")
|
|
760
|
+
$result | ConvertTo-Json -Compress
|
|
761
|
+
} catch {
|
|
762
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
763
|
+
}
|
|
764
|
+
`.trim()}async function yt(t,n,r){if(t===`linux`)try{_t(r);let{stderr:e}=await E(`gdb -p ${n} -batch -ex "call (void*)dlopen(\\"${r}\\", 1)" -ex "quit"`,{timeout:h});if(e.includes(`Operation not permitted`)||e.includes(`ptrace:`))throw Error(`GDB injection failed (ptrace blocked): ${e}`);return{success:!0}}catch(t){return e.error(`Linux DLL injection failed:`,t),{success:!1,error:t instanceof Error?t.message:String(t)}}else if(t===`darwin`)try{_t(r);let{stdout:e,stderr:t}=await E(`lldb --batch -p ${n} -o "expr (void*)dlopen(\\"${r}\\", 1)"`,{timeout:h});if(t.includes(`error:`)||e.includes(`error:`))throw Error(`LLDB injection failed: ${t||e}`);return{success:!0}}catch(t){return e.error(`macOS DLL injection failed:`,t),{success:!1,error:t instanceof Error?t.message:String(t)}}else if(t!==`win32`)return{success:!1,error:`DLL injection not supported on this platform`};try{let{stdout:e}=await T(vt(n,r),{maxBuffer:1024*1024,timeout:h}),t=e.trim();if(!t)throw Error(`PowerShell returned empty output`);let i=JSON.parse(t);return{success:i.success,remoteThreadId:i.remoteThreadId,error:i.error}}catch(t){return e.error(`DLL injection failed:`,t),{success:!1,error:t instanceof Error?t.message:`PowerShell execution failed`}}}function bt(e,t){return`
|
|
765
|
+
Add-Type @"
|
|
766
|
+
using System;
|
|
767
|
+
using System.Runtime.InteropServices;
|
|
768
|
+
using System.ComponentModel;
|
|
769
|
+
|
|
770
|
+
public class ShellcodeInjector {
|
|
771
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
772
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
773
|
+
|
|
774
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
775
|
+
public static extern IntPtr VirtualAllocEx(IntPtr hProcess, IntPtr addr, int size, int allocType, int protect);
|
|
776
|
+
|
|
777
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
778
|
+
public static extern bool WriteProcessMemory(IntPtr hProcess, IntPtr addr, byte[] buffer, int size, out int written);
|
|
779
|
+
|
|
780
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
781
|
+
public static extern IntPtr CreateRemoteThread(IntPtr hProcess, IntPtr attr, int stackSize, IntPtr startAddr, IntPtr param, int flags, out int threadId);
|
|
782
|
+
|
|
783
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
784
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
785
|
+
|
|
786
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
787
|
+
public static extern bool VirtualProtectEx(IntPtr hProcess, IntPtr addr, int size, int newProtect, out int oldProtect);
|
|
788
|
+
|
|
789
|
+
const int PROCESS_CREATE_THREAD = 0x0002;
|
|
790
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
791
|
+
const int PROCESS_VM_OPERATION = 0x0008;
|
|
792
|
+
const int PROCESS_VM_WRITE = 0x0020;
|
|
793
|
+
const int MEM_COMMIT = 0x1000;
|
|
794
|
+
const int MEM_RESERVE = 0x2000;
|
|
795
|
+
const int PAGE_READWRITE = 0x04;
|
|
796
|
+
const int PAGE_EXECUTE_READWRITE = 0x40;
|
|
797
|
+
|
|
798
|
+
public static object Inject(int pid, byte[] shellcode) {
|
|
799
|
+
IntPtr hProcess = OpenProcess(PROCESS_CREATE_THREAD | PROCESS_QUERY_INFORMATION | PROCESS_VM_OPERATION | PROCESS_VM_WRITE, false, pid);
|
|
800
|
+
if (hProcess == IntPtr.Zero) {
|
|
801
|
+
int error = Marshal.GetLastWin32Error();
|
|
802
|
+
throw new Win32Exception(error, "Failed to open process. Run as Administrator.");
|
|
803
|
+
}
|
|
804
|
+
|
|
805
|
+
try {
|
|
806
|
+
IntPtr remoteMem = VirtualAllocEx(hProcess, IntPtr.Zero, shellcode.Length, MEM_COMMIT | MEM_RESERVE, PAGE_READWRITE);
|
|
807
|
+
if (remoteMem == IntPtr.Zero) {
|
|
808
|
+
int error = Marshal.GetLastWin32Error();
|
|
809
|
+
throw new Win32Exception(error, "Failed to allocate memory in target");
|
|
810
|
+
}
|
|
811
|
+
|
|
812
|
+
try {
|
|
813
|
+
int written;
|
|
814
|
+
if (!WriteProcessMemory(hProcess, remoteMem, shellcode, shellcode.Length, out written)) {
|
|
815
|
+
int error = Marshal.GetLastWin32Error();
|
|
816
|
+
throw new Win32Exception(error, "Failed to write shellcode to target");
|
|
817
|
+
}
|
|
818
|
+
|
|
819
|
+
int oldProtect;
|
|
820
|
+
if (!VirtualProtectEx(hProcess, remoteMem, shellcode.Length, PAGE_EXECUTE_READWRITE, out oldProtect)) {
|
|
821
|
+
int error = Marshal.GetLastWin32Error();
|
|
822
|
+
throw new Win32Exception(error, "Failed to change memory protection to executable");
|
|
823
|
+
}
|
|
824
|
+
|
|
825
|
+
int threadId;
|
|
826
|
+
IntPtr hThread = CreateRemoteThread(hProcess, IntPtr.Zero, 0, remoteMem, IntPtr.Zero, 0, out threadId);
|
|
827
|
+
if (hThread == IntPtr.Zero) {
|
|
828
|
+
int error = Marshal.GetLastWin32Error();
|
|
829
|
+
throw new Win32Exception(error, "Failed to create remote thread");
|
|
830
|
+
}
|
|
831
|
+
|
|
832
|
+
CloseHandle(hThread);
|
|
833
|
+
return new { success = true, remoteThreadId = threadId };
|
|
834
|
+
} finally {
|
|
835
|
+
// Note: Memory is not freed to allow shellcode to execute
|
|
836
|
+
}
|
|
837
|
+
} finally {
|
|
838
|
+
CloseHandle(hProcess);
|
|
839
|
+
}
|
|
840
|
+
}
|
|
841
|
+
}
|
|
842
|
+
"@
|
|
843
|
+
|
|
844
|
+
try {
|
|
845
|
+
$shellcode = @(${Array.from(t).join(`,`)})
|
|
846
|
+
$result = [ShellcodeInjector]::Inject(${e}, $shellcode)
|
|
847
|
+
$result | ConvertTo-Json -Compress
|
|
848
|
+
} catch {
|
|
849
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
850
|
+
}
|
|
851
|
+
`.trim()}async function xt(t,n,r,i=`hex`){try{let e;if(i===`base64`)e=Buffer.from(r,`base64`);else{let t=r.replace(/\s/g,``);e=Buffer.from(t,`hex`)}if(t===`linux`){let t=Array.from(e).map(e=>`\\x${e.toString(16).padStart(2,`0`)}`).join(``),r=`
|
|
852
|
+
import gdb
|
|
853
|
+
import sys
|
|
854
|
+
|
|
855
|
+
def inject():
|
|
856
|
+
try:
|
|
857
|
+
# mmap: PROT_READ|PROT_WRITE|PROT_EXEC (7), MAP_PRIVATE|MAP_ANONYMOUS (34)
|
|
858
|
+
mmap_res = gdb.parse_and_eval("(void*)mmap(0, ${e.length}, 7, 34, -1, 0)")
|
|
859
|
+
addr = int(mmap_res)
|
|
860
|
+
if addr == -1 or addr == 0:
|
|
861
|
+
print("ERROR_INJECT: mmap failed")
|
|
862
|
+
return
|
|
863
|
+
|
|
864
|
+
inf = gdb.selected_inferior()
|
|
865
|
+
inf.write_memory(addr, b"${t}")
|
|
866
|
+
|
|
867
|
+
# Call it directly (creates a crash potentially) or via pthread_create
|
|
868
|
+
# Let's use pthread_create
|
|
869
|
+
thread_t = gdb.parse_and_eval("(void*)malloc(8)")
|
|
870
|
+
res = gdb.parse_and_eval(f"(int)pthread_create({int(thread_t)}, 0, {addr}, 0)")
|
|
871
|
+
|
|
872
|
+
print(f"SUCCESS_INJECT: {int(res)}")
|
|
873
|
+
except Exception as e:
|
|
874
|
+
print(f"ERROR_INJECT: {str(e)}")
|
|
875
|
+
|
|
876
|
+
inject()
|
|
877
|
+
`,i=M(A(),`gdb_inject_${n}_${Date.now()}.py`);await j.writeFile(i,r,`utf8`);try{let{stdout:e,stderr:t}=await E(`gdb -p ${n} -batch -x ${i}`,{timeout:h});if(e.includes(`ERROR_INJECT:`)||t.includes(`ERROR_INJECT:`))throw Error(`GDB injection failed: ${e||t}`);return{success:!0}}finally{await j.unlink(i).catch(()=>{})}}else if(t===`darwin`){let t=Array.from(e).map(e=>e.toString()).join(`,`),r=`
|
|
878
|
+
import lldb
|
|
879
|
+
import sys
|
|
880
|
+
|
|
881
|
+
def __lldb_init_module(debugger, internal_dict):
|
|
882
|
+
try:
|
|
883
|
+
target = debugger.GetSelectedTarget()
|
|
884
|
+
process = target.GetProcess()
|
|
885
|
+
|
|
886
|
+
# mmap: PROT_READ|PROT_WRITE|PROT_EXEC (7), MAP_PRIVATE|MAP_ANON (4098 on macOS)
|
|
887
|
+
res = lldb.SBCommandReturnObject()
|
|
888
|
+
debugger.GetCommandInterpreter().HandleCommand("expr (void*)mmap(0, ${e.length}, 7, 4098, -1, 0)", res)
|
|
889
|
+
|
|
890
|
+
if not res.Succeeded():
|
|
891
|
+
print("ERROR_INJECT: " + res.GetError())
|
|
892
|
+
return
|
|
893
|
+
|
|
894
|
+
addr_str = res.GetOutput().split()[-1]
|
|
895
|
+
addr = int(addr_str, 16)
|
|
896
|
+
|
|
897
|
+
err = lldb.SBError()
|
|
898
|
+
bytes_data = bytes([${t}])
|
|
899
|
+
process.WriteMemory(addr, bytes_data, err)
|
|
900
|
+
|
|
901
|
+
if not err.Success():
|
|
902
|
+
print("ERROR_INJECT: write failed")
|
|
903
|
+
return
|
|
904
|
+
|
|
905
|
+
# create thread
|
|
906
|
+
res2 = lldb.SBCommandReturnObject()
|
|
907
|
+
debugger.GetCommandInterpreter().HandleCommand(f"expr (int)pthread_create((void*)malloc(8), 0, (void*){addr}, 0)", res2)
|
|
908
|
+
|
|
909
|
+
print("SUCCESS_INJECT")
|
|
910
|
+
except Exception as e:
|
|
911
|
+
print("ERROR_INJECT: " + str(e))
|
|
912
|
+
`,i=M(A(),`lldb_inject_${n}_${Date.now()}.py`),a=M(A(),`lldb_inject_cmd_${n}_${Date.now()}.txt`);await j.writeFile(i,r,`utf8`),await j.writeFile(a,`command script import ${i}\\nprocess detach\\n`,`utf8`);try{let{stdout:e}=await E(`lldb --batch -p ${n} --source ${a}`,{timeout:h});if(e.includes(`ERROR_INJECT:`))throw Error(`LLDB injection failed: ${e}`);return{success:!0}}finally{await j.unlink(i).catch(()=>{}),await j.unlink(a).catch(()=>{})}}else if(t!==`win32`)return{success:!1,error:`Shellcode injection not supported on this platform`};let{stdout:a}=await T(bt(n,e),{maxBuffer:1024*1024,timeout:h}),o=a.trim();if(!o)throw Error(`PowerShell returned empty output`);let s=JSON.parse(o);return{success:s.success,remoteThreadId:s.remoteThreadId,error:s.error}}catch(t){return e.error(`Shellcode injection failed:`,t),{success:!1,error:t instanceof Error?t.message:`Execution failed`}}}var St=class{activeMonitors=new Map;start(e,t,n=4,r=1e3,i,a){let o=`monitor_${Date.now()}_${Math.random().toString(36).substr(2,9)}`,s=setInterval(async()=>{let r=this.activeMonitors.get(o);if(r&&!r.inFlight){r.inFlight=!0;try{let o=await i(e,t,n);o.success&&o.data&&r.lastValue!==o.data&&(a&&r.lastValue!==``&&a(r.lastValue,o.data),r.lastValue=o.data)}finally{r.inFlight=!1}}},r);return typeof s.unref==`function`&&s.unref(),this.activeMonitors.set(o,{pid:e,address:t,interval:r,lastValue:``,timer:s,inFlight:!1}),o}stop(e){let t=this.activeMonitors.get(e);return t?(clearInterval(t.timer),this.activeMonitors.delete(e),!0):!1}};const Ct=a;let q=null;function wt(e,t){if(typeof e!=`object`||!e)return``;let n=e[t];return typeof n==`string`?n:``}function Tt(e){let t=e instanceof Error?e.message:String(e),n=`${t}\n${wt(e,`stderr`)}`.toLowerCase();return n.includes(`enoent`)||n.includes(`command not found`)||n.includes(`is not recognized as an internal or external command`)||n.includes(`cannot find`)&&n.includes(`powershell`)?`PowerShell is unavailable. Windows memory operations require powershell.exe to verify Administrator privileges.`:`PowerShell command execution failed while checking Administrator privileges: ${t}`}async function Et(){try{let{stdout:e}=await T(`([Security.Principal.WindowsPrincipal][Security.Principal.WindowsIdentity]::GetCurrent()).IsInRole([Security.Principal.WindowsBuiltInRole]::Administrator)`,{timeout:p}),t=e.trim().toLowerCase();return t===`true`?{available:!0}:t===`false`?{available:!1,reason:`Windows memory operations require Administrator privileges. Please run your terminal/IDE as Administrator and retry.`}:{available:!1,reason:`PowerShell command execution failed while checking Administrator privileges: unexpected output "${e.trim()} '(empty)'}".`}}catch(e){return{available:!1,reason:Tt(e)}}}async function Dt(){let e=Date.now();if(q&&q.expiresAt>e)return q.result;let t=await Et();return q={expiresAt:e+Ct,result:t},t}async function Ot(e){switch(e){case`win32`:return Dt();case`linux`:try{let{stdout:e}=await E(`id -u`,{timeout:m});if(e.trim()===`0`)return{available:!0};try{return await E(`capsh --print 2>/dev/null | grep -q "cap_sys_ptrace"`,{timeout:m}),{available:!0}}catch{return{available:!1,reason:`Linux memory operations require root privileges or CAP_SYS_PTRACE capability. Run with sudo.`}}}catch{return{available:!1,reason:`Requires root privileges for /proc/pid/mem access. Run with sudo.`}}case`darwin`:try{return await E(`which lldb`,{timeout:m}),{available:!0,reason:process.getuid?.()===0?void 0:`Running without root — memory access works for own processes only. Use sudo for other processes.`}}catch{return{available:!1,reason:`lldb not found. Install Xcode Command Line Tools: xcode-select --install`}}default:return{available:!1,reason:`Platform ${e} not supported for memory operations.`}}}async function kt(e,t){if(e!==`win32`)return{success:!1,error:`Debug port check currently only implemented for Windows`};try{let{stdout:e}=await T(`
|
|
913
|
+
Add-Type @"
|
|
914
|
+
using System;
|
|
915
|
+
using System.Runtime.InteropServices;
|
|
916
|
+
using System.ComponentModel;
|
|
917
|
+
|
|
918
|
+
public class DebugChecker {
|
|
919
|
+
[DllImport("ntdll.dll")]
|
|
920
|
+
public static extern int NtQueryInformationProcess(IntPtr processHandle, int processInformationClass, out IntPtr processInformation, int processInformationLength, out int returnLength);
|
|
921
|
+
|
|
922
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
923
|
+
public static extern IntPtr OpenProcess(int access, bool inherit, int pid);
|
|
924
|
+
|
|
925
|
+
[DllImport("kernel32.dll", SetLastError = true)]
|
|
926
|
+
public static extern bool CloseHandle(IntPtr handle);
|
|
927
|
+
|
|
928
|
+
const int PROCESS_QUERY_INFORMATION = 0x0400;
|
|
929
|
+
const int ProcessDebugPort = 7;
|
|
930
|
+
|
|
931
|
+
public static object Check(int pid) {
|
|
932
|
+
IntPtr hProcess = OpenProcess(PROCESS_QUERY_INFORMATION, false, pid);
|
|
933
|
+
if (hProcess == IntPtr.Zero) {
|
|
934
|
+
int error = Marshal.GetLastWin32Error();
|
|
935
|
+
throw new Win32Exception(error, "Failed to open process");
|
|
936
|
+
}
|
|
937
|
+
|
|
938
|
+
try {
|
|
939
|
+
IntPtr debugPort;
|
|
940
|
+
int returnLength;
|
|
941
|
+
int status = NtQueryInformationProcess(hProcess, ProcessDebugPort, out debugPort, IntPtr.Size, out returnLength);
|
|
942
|
+
|
|
943
|
+
if (status != 0) {
|
|
944
|
+
return new { success = false, error = "NtQueryInformationProcess failed with status: 0x" + status.ToString("X") };
|
|
945
|
+
}
|
|
946
|
+
|
|
947
|
+
return new { success = true, isDebugged = debugPort != IntPtr.Zero };
|
|
948
|
+
} finally {
|
|
949
|
+
CloseHandle(hProcess);
|
|
950
|
+
}
|
|
951
|
+
}
|
|
952
|
+
}
|
|
953
|
+
"@
|
|
954
|
+
|
|
955
|
+
try {
|
|
956
|
+
$result = [DebugChecker]::Check(${t})
|
|
957
|
+
$result | ConvertTo-Json -Compress
|
|
958
|
+
} catch {
|
|
959
|
+
@{ success = $false; error = $_.Exception.Message } | ConvertTo-Json -Compress
|
|
960
|
+
}
|
|
961
|
+
`,{maxBuffer:1024*1024,timeout:p*2}),n=e.trim();if(!n)throw Error(`PowerShell returned empty output`);try{return JSON.parse(n)}catch{throw Error(`PowerShell returned empty output`)}}catch(e){return{success:!1,error:e instanceof Error?e.message:`PowerShell execution failed`}}}function At(){switch(process.platform){case`win32`:return`win32`;case`linux`:return`linux`;case`darwin`:return`darwin`;default:return`unknown`}}var jt=class{platform;monitorManager=new St;constructor(){this.platform=At(),e.info(`MemoryManager initialized for platform: ${this.platform}`)}async readMemory(e,t,n){return Ve(this.platform,e,t,n,(e,t)=>K(this.platform,e,t))}async writeMemory(e,t,n,r=`hex`){return Je(this.platform,e,t,n,r,(e,t)=>K(this.platform,e,t))}async batchMemoryWrite(e,t){return Xe(e,t,(e,t,n,r)=>this.writeMemory(e,t,n,r))}async scanMemory(e,t,n=`hex`,r=!1){return ot(this.platform,e,t,n,r)}async scanMemoryFiltered(e,t,n,r=`hex`){return st(e,t,n,r,(e,t,n)=>this.readMemory(e,t,n),(e,t,n)=>this.scanMemory(e,t,n))}async dumpMemoryRegion(e,t,n,r){return ft(this.platform,e,t,n,r)}async enumerateRegions(e){return mt(this.platform,e)}async checkMemoryProtection(e,t){return K(this.platform,e,t)}async enumerateModules(e){return gt(this.platform,e)}async injectDll(e,t){return yt(this.platform,e,t)}async injectShellcode(e,t,n=`hex`){return xt(this.platform,e,t,n)}async checkDebugPort(e){return kt(this.platform,e)}startMemoryMonitor(e,t,n=4,r=1e3,i){return this.monitorManager.start(e,t,n,r,(e,t,n)=>this.readMemory(e,t,n),i)}stopMemoryMonitor(e){return this.monitorManager.stop(e)}async checkAvailability(){return Ot(this.platform)}};function Mt(){let t=process.platform;switch(t){case`win32`:return`win32`;case`linux`:return`linux`;case`darwin`:return`darwin`;default:return e.warn(`Unsupported platform: ${t}`),`unknown`}}function Nt(){let t=Mt();switch(e.info(`Creating ProcessManager for platform: ${t}`),t){case`win32`:return new De;case`linux`:return new ke;case`darwin`:return new Ne;default:throw Error(`Unsupported platform: ${t}. ProcessManager requires Windows, Linux, or macOS.`)}}var Pt=class{manager;platform;constructor(){this.platform=Mt(),this.manager=Nt()}getPlatform(){return this.platform}async findProcesses(e){return this.manager.findProcesses(e)}async getProcessByPid(e){return this.manager.getProcessByPid(e)}async getProcessWindows(e){return this.manager.getProcessWindows(e)}async checkDebugPort(e,t){return this.manager.checkDebugPort(e,t)}async launchWithDebug(e,t,n){return this.manager.launchWithDebug(e,t,n)}async killProcess(e){return this.manager.killProcess(e)}async getProcessCommandLine(e){return this.manager.getProcessCommandLine(e)}async findBrowserProcesses(e){return this.platform===`win32`?e?.processNamePattern||e?.windowClassPattern?this.manager.findChromiumProcesses({processNamePattern:e.processNamePattern,windowClassPattern:e.windowClassPattern}):this.manager.findChromiumAppProcesses():this.platform===`linux`||this.platform===`darwin`?this.manager.findChromeProcesses():null}},Ft=class{buffer;head=0;count=0;capacity;constructor(e=_){this.capacity=Number.isInteger(e)&&e>0?e:_,this.buffer=Array.from({length:this.capacity})}record(e){let t={...e,timestamp:new Date().toISOString(),user:process.env.USERNAME||process.env.USER||`unknown`};if(this.count<this.capacity){let e=(this.head+this.count)%this.capacity;this.buffer[e]=t,this.count+=1;return}this.buffer[this.head]=t,this.head=(this.head+1)%this.capacity}exportJson(){let e=[];for(let t=0;t<this.count;t+=1){let n=(this.head+t)%this.capacity,r=this.buffer[n];r&&e.push(r)}return JSON.stringify(e,null,2)}clear(){this.buffer=[],this.head=0,this.count=0}size(){return this.count}};const It=new Set([`hex`,`int32`,`int64`,`float`,`double`,`string`]);function J(e){let t=Number(e);if(!Number.isInteger(t)||t<=0)throw Error(`Invalid PID: ${JSON.stringify(e)}`);return t}function Y(e,t){if(typeof e!=`string`||e.length===0)throw Error(`${t} must be a non-empty string`);return e}function Lt(e,t){let n=Number(e);if(!Number.isFinite(n)||n<=0)throw Error(`${t} must be a positive number`);return n}function Rt(e){return typeof e==`string`&&It.has(e)?e:`hex`}function zt(e){let t=Number(e);return Number.isInteger(t)&&t>0?t:void 0}function Bt(e){return typeof e==`string`&&e.length>0?e:void 0}function Vt(e){let t=Number(e);return Number.isFinite(t)&&t>0?t:void 0}function Ht(e,t){if(t===`hex`){let t=e.replace(/\s+/g,``);return Math.ceil(t.length/2)}return Buffer.from(e,`base64`).length}var Ut=class{processManager;memoryManager;platform;auditTrail;constructor(e){this.processManager=e.processManager,this.memoryManager=e.memoryManager,this.platform=e.platform,this.auditTrail=e.auditTrail}async buildMemoryDiagnostics(e){let t=new Set,n=await this.memoryManager.checkAvailability();n.available||t.add(`Run as administrator`);let r=await this.resolveProcessInfo(e.pid);e.pid!==void 0&&e.pid!==null&&!r&&t.add(`Check if process is still running`);let i=await this.queryProtection(e);(i.queryFailed||i.info?.success===!1)&&t.add(`Verify address is within valid memory region`),e.size!==void 0&&e.size!==null&&i.info?.regionSize!==void 0&&i.info.regionSize!==null&&e.size>i.info.regionSize&&t.add(`Reduce the requested size to fit the target memory region`),e.operation===`memory_read`&&i.info?.success&&i.info.isReadable===!1&&t.add(`Ensure target memory region is readable`),e.operation===`memory_write`&&i.info?.success&&i.info.isWritable===!1&&t.add(`Ensure target memory region is writable`);let a=await this.enumerateModulesSafe(e.pid);e.pid!==void 0&&e.pid!==null&&e.address&&t.add(`Re-resolve the address after the process restarts because ASLR can shift module addresses`);let o=e.error?.toLowerCase()??``;(o.includes(`access denied`)||o.includes(`permission`)||o.includes(`privilege`)||o.includes(`administrator`))&&t.add(`Run as administrator`);let s=a.enumerated?a.count&&a.count>0?`Enumerated ${a.count} module(s). Treat absolute addresses as session-specific because ASLR can shift module bases between launches.`:`Module enumeration succeeded but returned no modules. Absolute addresses may still change across process launches because of ASLR.`:`Module enumeration was unavailable. Assume ASLR may shift absolute addresses between launches and re-resolve addresses after restarts.`;return{permission:{available:n.available,reason:n.reason,platform:this.platform},process:{exists:e.pid!==void 0&&e.pid!==null?!!r:null,pid:e.pid??null,name:r?.name??null},address:{queried:e.pid!==void 0&&e.pid!==null&&!!e.address,valid:e.pid!==void 0&&e.pid!==null&&e.address?i.info?.success??null:null,protection:i.info?.protection??null,regionStart:i.info?.regionStart??null,regionSize:i.info?.regionSize??null},aslr:{heuristic:!0,note:s},recommendedActions:Array.from(t)}}async safeBuildMemoryDiagnostics(t){try{return await this.buildMemoryDiagnostics(t)}catch(t){e.warn(`Memory diagnostics generation failed:`,t);return}}recordMemoryAudit(t){try{this.auditTrail.record(t)}catch(t){e.warn(`Memory audit trail recording failed:`,t)}}get platformValue(){return this.platform}exportMemoryAuditEntries(){return JSON.parse(this.auditTrail.exportJson())}clearMemoryAuditEntries(){this.auditTrail.clear()}getMemoryAuditCount(){return this.auditTrail.size()}async handleProcessList(t){try{let e=await this.processManager.findProcesses(``);return{content:[{type:`text`,text:JSON.stringify({success:!0,count:e.length,processes:e.map(e=>({pid:e.pid,name:e.name,path:e.executablePath,windowTitle:e.windowTitle,windowHandle:e.windowHandle,memoryMB:e.memoryUsage?Math.round(e.memoryUsage/1024/1024):void 0}))},null,2)}]}}catch(t){return e.error(`Process list failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleProcessFind(t){try{let e=Y(t.pattern,`pattern`),n=await this.processManager.findProcesses(e);return{content:[{type:`text`,text:JSON.stringify({success:!0,pattern:e,count:n.length,processes:n.map(e=>({pid:e.pid,name:e.name,path:e.executablePath,windowTitle:e.windowTitle,windowHandle:e.windowHandle,memoryMB:e.memoryUsage?Math.round(e.memoryUsage/1024/1024):void 0}))},null,2)}]}}catch(t){return e.error(`Process find failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleProcessGet(t){try{let e=J(t.pid),n=await this.processManager.getProcessByPid(e);if(!n)return{content:[{type:`text`,text:JSON.stringify({success:!1,message:`Process with PID ${e} not found`},null,2)}]};let r=await this.processManager.getProcessCommandLine(e),i=await this.processManager.checkDebugPort(e,{commandLine:r.commandLine});return{content:[{type:`text`,text:JSON.stringify({success:!0,process:{...n,commandLine:r.commandLine,parentPid:r.parentPid,debugPort:i}},null,2)}]}}catch(t){return e.error(`Process get failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleProcessWindows(t){try{let e=J(t.pid),n=await this.processManager.getProcessWindows(e);return{content:[{type:`text`,text:JSON.stringify({success:!0,pid:e,windowCount:n.length,windows:n.map(e=>({handle:e.handle,title:e.title,className:e.className,processId:e.processId}))},null,2)}]}}catch(t){return e.error(`Process windows failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleProcessCheckDebugPort(t){try{let e=J(t.pid),n=await this.processManager.checkDebugPort(e);return{content:[{type:`text`,text:JSON.stringify({success:!0,pid:e,debugPort:n,canAttach:n!==null,attachUrl:n?`http://localhost:${n}`:null},null,2)}]}}catch(t){return e.error(`Check debug port failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleProcessLaunchDebug(t){try{let e=Y(t.executablePath,`executablePath`),n=ce(t,`debugPort`,9222),r=se(t,`args`),i=await this.processManager.launchWithDebug(e,n,r);return i?{content:[{type:`text`,text:JSON.stringify({success:!0,process:{pid:i.pid,name:i.name,path:i.executablePath},debugPort:n,attachUrl:`http://localhost:${n}`},null,2)}]}:{content:[{type:`text`,text:JSON.stringify({success:!1,message:`Failed to launch process`},null,2)}]}}catch(t){return e.error(`Launch debug failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleProcessKill(t){try{let e=J(t.pid),n=await this.processManager.killProcess(e);return{content:[{type:`text`,text:JSON.stringify({success:n,pid:e,message:n?`Process ${e} killed successfully`:`Failed to kill process ${e}`},null,2)}]}}catch(t){return e.error(`Process kill failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async resolveProcessInfo(e){if(e==null)return null;try{let t=await this.processManager.getProcessByPid(e);return t?{pid:t.pid,name:t.name,executablePath:t.executablePath,windowTitle:t.windowTitle,windowHandle:t.windowHandle,memoryUsage:t.memoryUsage}:null}catch{return null}}async queryProtection(e){if(e.pid===void 0||e.pid===null||!e.address)return{info:null,queryFailed:!1};let t=!1,n=null;try{n=await this.memoryManager.checkMemoryProtection(e.pid,e.address)}catch{t=!0}return{info:n,queryFailed:t}}async enumerateModulesSafe(e){if(e==null)return{enumerated:!1,count:null};try{let t=await this.memoryManager.enumerateModules(e);return{enumerated:t.success,count:t.modules?.length??null}}catch{return{enumerated:!1,count:null}}}},Wt=class{memoryManager;platform;host;constructor(e,t){this.memoryManager=e.memoryManager,this.platform=e.platform,this.host=t}async handleMemoryRead(t){let n=Date.now();try{let e=J(t.pid),r=Y(t.address,`address`),i=Lt(t.size,`size`),a=await this.memoryManager.checkAvailability();if(!a.available)return this.auditedUnavailableResponse({operation:`memory_read`,pid:e,address:r,size:i,startedAt:n,reason:a.reason,extra:{requestedAddress:r,requestedSize:i}});let o=await this.memoryManager.readMemory(e,r,i);return this.auditedResultResponse({operation:`memory_read`,pid:e,address:r,size:i,startedAt:n,result:o,payload:{success:o.success,data:o.data,error:o.error,pid:e,address:r,size:i,platform:this.platform}})}catch(r){return e.error(`Memory read failed:`,r),this.auditedExceptionResponse({operation:`memory_read`,pid:zt(t.pid)??null,address:Bt(t.address)??null,size:Vt(t.size)??null,startedAt:n,error:r})}}async handleMemoryWrite(t){let n=Date.now();try{let e=J(t.pid),r=Y(t.address,`address`),i=Y(t.data,`data`),a=this.normalizeEncoding(t.encoding,`encoding`)??`hex`,o=Ht(i,a),s=await this.memoryManager.checkAvailability();if(!s.available)return this.auditedUnavailableResponse({operation:`memory_write`,pid:e,address:r,size:o,startedAt:n,reason:s.reason,extra:{requestedAddress:r,dataLength:i.length,encoding:a}});let c=await this.memoryManager.writeMemory(e,r,i,a);return this.auditedResultResponse({operation:`memory_write`,pid:e,address:r,size:o,startedAt:n,result:c,payload:{success:c.success,bytesWritten:c.bytesWritten,error:c.error,pid:e,address:r,dataLength:i.length,encoding:a,platform:this.platform}})}catch(r){e.error(`Memory write failed:`,r);let i=Bt(t.data),a=this.normalizeEncoding(t.encoding,`encoding`)??`hex`;return this.auditedExceptionResponse({operation:`memory_write`,pid:zt(t.pid)??null,address:Bt(t.address)??null,size:i?Ht(i,a):null,startedAt:n,error:r})}}async handleMemoryScan(t){let n=Date.now();try{let e=J(t.pid),r=Y(t.pattern,`pattern`),i=Rt(t.patternType),a=t.suspendTarget===!0,o=await this.memoryManager.checkAvailability();if(!o.available)return this.auditedUnavailableResponse({operation:`memory_scan`,pid:e,address:null,size:null,startedAt:n,reason:o.reason,extra:{requestedPattern:r,patternType:i}});let s=await this.memoryManager.scanMemory(e,r,i,a);return this.auditedResultResponse({operation:`memory_scan`,pid:e,address:null,size:null,startedAt:n,result:s,payload:{success:s.success,addresses:s.addresses,error:s.error,pid:e,pattern:r,patternType:i,platform:this.platform}})}catch(r){return e.error(`Memory scan failed:`,r),this.auditedExceptionResponse({operation:`memory_scan`,pid:zt(t.pid)??null,address:null,size:null,startedAt:n,error:r})}}async handleMemoryAuditExport(t){try{let e=this.host.exportMemoryAuditEntries(),n=t.clear===!0,r=this.host.getMemoryAuditCount();return n&&this.host.clearMemoryAuditEntries(),this.jsonResponse({success:!0,count:r,cleared:n,entries:e})}catch(t){return e.error(`Memory audit export failed:`,t),this.errorResponse(t)}}async handleMemoryCheckProtection(t){try{let e=J(t.pid),n=Y(t.address,`address`),r=await this.memoryManager.checkMemoryProtection(e,n);return this.jsonResponse(r)}catch(t){return e.error(`Memory check protection failed:`,t),this.errorResponse(t)}}async handleMemoryScanFiltered(t){try{let e=J(t.pid),n=Y(t.pattern,`pattern`),r=this.requireStringArray(t.addresses,`addresses`),i=Rt(t.patternType),a=await this.memoryManager.checkAvailability();if(!a.available)return this.unavailableResponse(e,a.reason);let o=await this.memoryManager.scanMemoryFiltered(e,n,r,i);return this.jsonResponse(o)}catch(t){return e.error(`Memory scan filtered failed:`,t),this.errorResponse(t)}}async handleMemoryBatchWrite(t){try{let e=J(t.pid),n=this.requirePatches(t.patches),r=await this.memoryManager.checkAvailability();if(!r.available)return this.unavailableResponse(e,r.reason);let i=await this.memoryManager.batchMemoryWrite(e,n);return this.jsonResponse(i)}catch(t){return e.error(`Memory batch write failed:`,t),this.errorResponse(t)}}async handleMemoryDumpRegion(t){try{let e=J(t.pid),n=Y(t.address,`address`),r=Lt(t.size,`size`),i=Y(t.outputPath,`outputPath`);this.ensureRelativeOutputPath(i);let a=await this.memoryManager.dumpMemoryRegion(e,n,r,i);return this.jsonResponse(a)}catch(t){return e.error(`Memory dump region failed:`,t),this.errorResponse(t)}}async handleMemoryListRegions(t){try{let e=J(t.pid),n=await this.memoryManager.enumerateRegions(e);return this.jsonResponse(n)}catch(t){return e.error(`Memory list regions failed:`,t),this.errorResponse(t)}}jsonResponse(e){return{content:[{type:`text`,text:JSON.stringify(e,null,2)}]}}errorResponse(e){return this.jsonResponse({success:!1,error:this.errorMessage(e)})}errorMessage(e){return e instanceof Error?e.message:String(e)}async auditedUnavailableResponse(e){let t=e.reason??`Memory operations not available`,n=await this.host.safeBuildMemoryDiagnostics({pid:e.pid,address:e.address??void 0,size:e.size??void 0,operation:e.operation,error:t});return this.host.recordMemoryAudit({operation:e.operation,pid:e.pid,address:e.address,size:e.size,result:`failure`,error:t,durationMs:Date.now()-e.startedAt}),this.jsonResponse({success:!1,message:`Memory operations not available`,reason:e.reason,platform:this.platform,pid:e.pid,...e.extra,diagnostics:n})}async auditedResultResponse(e){let t=e.result.success?void 0:await this.host.safeBuildMemoryDiagnostics({pid:e.pid,address:e.address??void 0,size:e.size??void 0,operation:e.operation,error:e.result.error});return this.host.recordMemoryAudit({operation:e.operation,pid:e.pid,address:e.address,size:e.size,result:e.result.success?`success`:`failure`,error:e.result.error,durationMs:Date.now()-e.startedAt}),e.result.success||(e.payload.diagnostics=t),this.jsonResponse(e.payload)}async auditedExceptionResponse(e){let t=this.errorMessage(e.error),n=await this.host.safeBuildMemoryDiagnostics({pid:e.pid??void 0,address:e.address??void 0,size:e.size??void 0,operation:e.operation,error:t});return this.host.recordMemoryAudit({operation:e.operation,pid:e.pid,address:e.address,size:e.size,result:`failure`,error:t,durationMs:Date.now()-e.startedAt}),this.jsonResponse({success:!1,error:t,diagnostics:n})}unavailableResponse(e,t){return this.jsonResponse({success:!1,message:`Memory operations not available`,reason:t,platform:this.platform,pid:e})}requireStringArray(e,t){if(!Array.isArray(e))throw Error(`${t} must be an array of strings`);return e.map((e,n)=>Y(e,`${t}[${n}]`))}requirePatches(e){if(!Array.isArray(e))throw Error(`patches must be an array`);return e.map((e,t)=>{if(typeof e!=`object`||!e)throw Error(`patches[${t}] must be an object`);let n=e,r=this.normalizeEncoding(n.encoding,`patches[${t}].encoding`);return{address:Y(n.address,`patches[${t}].address`),data:Y(n.data,`patches[${t}].data`),...r?{encoding:r}:{}}})}normalizeEncoding(e,t){if(e!==void 0){if(e===`hex`||e===`base64`)return e;throw Error(`${t} must be "hex" or "base64"`)}}ensureRelativeOutputPath(e){if(/^[/\\]/.test(e)||/\.\./.test(e)||/^[A-Za-z]:/.test(e))throw Error(`outputPath must be a relative path without parent directory traversal or drive letters`)}};const Gt=`Injection tools are disabled by configuration. Set ENABLE_INJECTION_TOOLS=true before starting the server to enable DLL and shellcode injection.`;function Kt(){return{success:!1,error:Gt,howToEnable:`Set ENABLE_INJECTION_TOOLS=true before starting the server.`,securityNotice:`Injection tools can destabilize target processes; review impact before use.`}}function X(e){let t=Number(e);return Number.isInteger(t)&&t>0?t:null}function Z(e){if(e instanceof Error)return e.message;if(typeof e==`object`&&e)try{return JSON.stringify(e,null,2)}catch{return String(e)}return String(e)}function Q(e){return typeof e==`string`&&e.length>0?e:null}function $(e,t){if(t===`hex`){let t=e.replace(/\s+/g,``);return Math.ceil(t.length/2)}return Buffer.from(e,`base64`).length}const qt=Number(process.env.JSHOOK_ELECTRON_ATTACH_CONNECT_TIMEOUT_MS)||5e3;async function Jt(e){let{default:t}=await import(`rebrowser-puppeteer-core`);try{return await new Promise((n,r)=>{let i=!1,a=setTimeout(()=>{i=!0,r(Error(`Timed out after ${qt}ms while connecting to Electron browser endpoint ${e}.`))},qt);t.connect({browserWSEndpoint:e,defaultViewport:null}).then(async e=>{if(i){try{await e.disconnect()}catch{}return}i=!0,clearTimeout(a),n(e)}).catch(e=>{i||(i=!0,clearTimeout(a),r(e))})})}catch(t){try{return await le(e,qt)}catch(n){throw Error(`Failed to connect to Electron browser endpoint ${e} via both rebrowser-puppeteer and Playwright compatibility fallback. Primary error: ${Z(t)}. Fallback error: ${Z(n)}.`,{cause:n})}}}var Yt=class{memoryManager;processMgmt;constructor(e,t){this.memoryManager=e.memoryManager,this.processMgmt=t}async handleInjectDll(t){let n=Date.now();if(!c)return this.processMgmt.recordMemoryAudit({operation:`inject_dll`,pid:X(t.pid),address:Q(t.dllPath),size:null,result:`failure`,error:Gt,durationMs:Date.now()-n}),{content:[{type:`text`,text:JSON.stringify(Kt(),null,2)}]};try{let e=J(t.pid),r=Y(t.dllPath,`dllPath`),i=await this.memoryManager.injectDll(e,r);return this.processMgmt.recordMemoryAudit({operation:`inject_dll`,pid:e,address:r,size:null,result:i.success?`success`:`failure`,error:i.error,durationMs:Date.now()-n}),{content:[{type:`text`,text:JSON.stringify(i,null,2)}]}}catch(r){e.error(`DLL injection failed:`,r);let i=r instanceof Error?r.message:String(r);return this.processMgmt.recordMemoryAudit({operation:`inject_dll`,pid:X(t.pid),address:Q(t.dllPath),size:null,result:`failure`,error:i,durationMs:Date.now()-n}),{content:[{type:`text`,text:JSON.stringify({success:!1,error:i},null,2)}]}}}async handleInjectShellcode(t){let n=Date.now();if(!c){let e=Q(t.shellcode),r=t.encoding||`hex`;return this.processMgmt.recordMemoryAudit({operation:`inject_shellcode`,pid:X(t.pid),address:null,size:e?$(e,r):null,result:`failure`,error:Gt,durationMs:Date.now()-n}),{content:[{type:`text`,text:JSON.stringify(Kt(),null,2)}]}}try{let e=J(t.pid),r=Y(t.shellcode,`shellcode`),i=t.encoding||`hex`,a=$(r,i),o=await this.memoryManager.injectShellcode(e,r,i);return this.processMgmt.recordMemoryAudit({operation:`inject_shellcode`,pid:e,address:null,size:a,result:o.success?`success`:`failure`,error:o.error,durationMs:Date.now()-n}),{content:[{type:`text`,text:JSON.stringify(o,null,2)}]}}catch(r){e.error(`Shellcode injection failed:`,r);let i=r instanceof Error?r.message:String(r),a=Q(t.shellcode),o=t.encoding||`hex`;return this.processMgmt.recordMemoryAudit({operation:`inject_shellcode`,pid:X(t.pid),address:null,size:a?$(a,o):null,result:`failure`,error:i,durationMs:Date.now()-n}),{content:[{type:`text`,text:JSON.stringify({success:!1,error:i},null,2)}]}}}async handleCheckDebugPort(t){try{let e=J(t.pid),n=await this.memoryManager.checkDebugPort(e);return{content:[{type:`text`,text:JSON.stringify({success:n.success,pid:e,isDebugged:n.isDebugged??null,error:n.error},null,2)}]}}catch(t){return e.error(`check_debug_port failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleEnumerateModules(t){try{let e=J(t.pid),n=await this.memoryManager.enumerateModules(e);return{content:[{type:`text`,text:JSON.stringify({success:n.success,pid:e,moduleCount:n.modules?.length??0,modules:n.modules??[],error:n.error},null,2)}]}}catch(t){return e.error(`enumerate_modules failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:t instanceof Error?t.message:String(t)},null,2)}]}}}async handleElectronAttach(t){let n=t.port??9229,r=Number(n);if(!Number.isInteger(r)||r<1||r>65535)return{content:[{type:`text`,text:JSON.stringify({success:!1,error:`Invalid port: ${JSON.stringify(n)}. Must be integer 1-65535.`})}]};let i=t.wsEndpoint??``,a=t.evaluate??``,o=t.pageUrl??``;try{let t=`http://127.0.0.1:${r}`,n=await this.fetchCdpTargets(t);if(!Array.isArray(n))throw Error(`CDP target list is not an array`);let s=o?n.filter(e=>e.url.includes(o)):n;if(!a)return{content:[{type:`text`,text:JSON.stringify({total:n.length,filtered:s.length,pages:s.map(e=>({id:e.id,title:e.title,url:e.url,type:e.type,wsUrl:e.webSocketDebuggerUrl}))},null,2)}]};let c=s[0];if(!c?.webSocketDebuggerUrl)return{content:[{type:`text`,text:`No matching page found (pageUrl filter: "${o}"). Available targets:\n`+n.map(e=>` [${e.type}] ${e.title} — ${e.url}`).join(`
|
|
962
|
+
`)}]};let l=await this.resolveBrowserWsEndpoint(t,i,c);if(!l)throw Error(`Could not determine browser WebSocket endpoint`);let u=await Jt(l),d,f;try{let e=await u.pages(),t=e.find(e=>e.url().includes(c.url))??e[0];if(!t)throw Error(`Could not get page from connected browser`);let n=await t.evaluate(e=>{try{return{ok:!0,result:Function(`return (`+e+`)`)()}}catch(e){let t=typeof e==`object`&&e?e:{};return{ok:!1,error:{name:t.name||`Error`,message:String(t.message||e),stack:t.stack?String(t.stack):void 0}}}},a);n?.ok?d=n.result:f=`Evaluation failed: ${n?.error?.name||`Error`}: ${n?.error?.message||`Unknown error`}`}finally{await u.disconnect()}return f?{content:[{type:`text`,text:JSON.stringify({success:!1,error:f,target:{title:c.title,url:c.url}},null,2)}]}:(e.info(`electron_attach: evaluated in ${c.title}`),{content:[{type:`text`,text:JSON.stringify({success:!0,target:{title:c.title,url:c.url},result:d},null,2)}]})}catch(t){return e.error(`electron_attach failed:`,t),{content:[{type:`text`,text:JSON.stringify({success:!1,error:Z(t)},null,2)}]}}}async fetchCdpTargets(e){let t=`${e}/json/list`;try{let e=await fetch(t);if(!e.ok)throw Error(`CDP list endpoint returned HTTP ${e.status}`);return await e.json()}catch(t){try{let n=await fetch(`${e}/json`);if(!n.ok)throw Error(`CDP fallback endpoint returned HTTP ${n.status}`,{cause:t});return await n.json()}catch(n){let r=Z(n||t);throw Error(`Cannot connect to Electron CDP at ${e}. Ensure the target app is running with a remote debugging port (for example: process_launch_debug with debugPort=${e.split(`:`).pop()}), then retry electron_attach. Original error: ${r}`,{cause:n})}}}async resolveBrowserWsEndpoint(e,t,n){if(t)return t;try{let t=await fetch(`${e}/json/version`);if(t.ok){let e=await t.json();if(e.webSocketDebuggerUrl)return e.webSocketDebuggerUrl}}catch{}if(n.webSocketDebuggerUrl)return n.webSocketDebuggerUrl.replace(/\/devtools\/page\/[^/]+$/,``).replace(`/devtools/page`,`/devtools/browser`)}};function Xt(){let e=new Pt,t=new jt,n=e.getPlatform();return{processManager:e,memoryManager:t,auditTrail:new Ft,platform:n}}var Zt=class{processMgmt;memoryOps;deps;buildMemoryDiagnostics;safeBuildMemoryDiagnostics;recordMemoryAudit;constructor(){this.deps=Xt(),e.info(`ProcessToolHandlers initialized for platform: ${this.deps.platform}`),this.processMgmt=new Ut(this.deps),this.memoryOps=new Wt(this.deps,this.processMgmt),this.buildMemoryDiagnostics=this.processMgmt.buildMemoryDiagnostics.bind(this.processMgmt),this.safeBuildMemoryDiagnostics=this.processMgmt.safeBuildMemoryDiagnostics.bind(this.processMgmt),this.recordMemoryAudit=this.processMgmt.recordMemoryAudit.bind(this.processMgmt)}async handleProcessWindows(e){return this.processMgmt.handleProcessWindows(e)}async handleProcessCheckDebugPort(e){return this.processMgmt.handleProcessCheckDebugPort(e)}async handleProcessLaunchDebug(e){return this.processMgmt.handleProcessLaunchDebug(e)}async handleMemoryRead(e){return this.memoryOps.handleMemoryRead(e)}async handleMemoryWrite(e){return this.memoryOps.handleMemoryWrite(e)}async handleMemoryScan(e){return this.memoryOps.handleMemoryScan(e)}async handleMemoryAuditExport(e){return this.memoryOps.handleMemoryAuditExport(e)}async handleMemoryCheckProtection(e){return this.memoryOps.handleMemoryCheckProtection(e)}async handleMemoryScanFiltered(e){return this.memoryOps.handleMemoryScanFiltered(e)}async handleMemoryBatchWrite(e){return this.memoryOps.handleMemoryBatchWrite(e)}async handleMemoryDumpRegion(e){return this.memoryOps.handleMemoryDumpRegion(e)}async handleMemoryListRegions(e){return this.memoryOps.handleMemoryListRegions(e)}},Qt=class extends Zt{injection;constructor(){super(),this.injection=new Yt(this.deps,this.processMgmt)}async handleInjectDll(e){return this.injection.handleInjectDll(e)}async handleInjectShellcode(e){return this.injection.handleInjectShellcode(e)}async handleCheckDebugPort(e){return this.injection.handleCheckDebugPort(e)}async handleEnumerateModules(e){return this.injection.handleEnumerateModules(e)}async handleElectronAttach(e){return this.injection.handleElectronAttach(e)}};export{Qt as ProcessToolHandlers};
|