crosspad-mcp-server 5.1.0 → 8.1.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (66) hide show
  1. package/README.md +109 -44
  2. package/dist/config.d.ts +2 -2
  3. package/dist/config.js +42 -8
  4. package/dist/config.js.map +1 -1
  5. package/dist/index.js +953 -219
  6. package/dist/index.js.map +1 -1
  7. package/dist/tools/app-manager.d.ts +13 -5
  8. package/dist/tools/app-manager.js +94 -28
  9. package/dist/tools/app-manager.js.map +1 -1
  10. package/dist/tools/architecture.js +13 -4
  11. package/dist/tools/architecture.js.map +1 -1
  12. package/dist/tools/build-check.d.ts +1 -1
  13. package/dist/tools/build-check.js +19 -9
  14. package/dist/tools/build-check.js.map +1 -1
  15. package/dist/tools/build.d.ts +43 -4
  16. package/dist/tools/build.js +147 -15
  17. package/dist/tools/build.js.map +1 -1
  18. package/dist/tools/diff-core.d.ts +5 -1
  19. package/dist/tools/diff-core.js +11 -6
  20. package/dist/tools/diff-core.js.map +1 -1
  21. package/dist/tools/idf-build.d.ts +1 -1
  22. package/dist/tools/idf-build.js +5 -5
  23. package/dist/tools/idf-build.js.map +1 -1
  24. package/dist/tools/idf-flash.d.ts +20 -0
  25. package/dist/tools/idf-flash.js +185 -0
  26. package/dist/tools/idf-flash.js.map +1 -0
  27. package/dist/tools/idf-monitor.d.ts +29 -0
  28. package/dist/tools/idf-monitor.js +222 -0
  29. package/dist/tools/idf-monitor.js.map +1 -0
  30. package/dist/tools/log.d.ts +2 -2
  31. package/dist/tools/log.js +6 -5
  32. package/dist/tools/log.js.map +1 -1
  33. package/dist/tools/midi.d.ts +27 -0
  34. package/dist/tools/midi.js +112 -0
  35. package/dist/tools/midi.js.map +1 -0
  36. package/dist/tools/repo-actions.d.ts +46 -0
  37. package/dist/tools/repo-actions.js +286 -0
  38. package/dist/tools/repo-actions.js.map +1 -0
  39. package/dist/tools/repos.js +14 -10
  40. package/dist/tools/repos.js.map +1 -1
  41. package/dist/tools/screenshot.js +42 -7
  42. package/dist/tools/screenshot.js.map +1 -1
  43. package/dist/tools/settings.js +11 -1
  44. package/dist/tools/settings.js.map +1 -1
  45. package/dist/tools/symbols.d.ts +2 -1
  46. package/dist/tools/symbols.js +121 -53
  47. package/dist/tools/symbols.js.map +1 -1
  48. package/dist/tools/test.d.ts +1 -9
  49. package/dist/tools/test.js +11 -92
  50. package/dist/tools/test.js.map +1 -1
  51. package/dist/utils/device.d.ts +38 -0
  52. package/dist/utils/device.js +287 -0
  53. package/dist/utils/device.js.map +1 -0
  54. package/dist/utils/exec.d.ts +17 -5
  55. package/dist/utils/exec.js +73 -27
  56. package/dist/utils/exec.js.map +1 -1
  57. package/dist/utils/git.d.ts +9 -0
  58. package/dist/utils/git.js +61 -1
  59. package/dist/utils/git.js.map +1 -1
  60. package/dist/utils/remote-client.d.ts +1 -0
  61. package/dist/utils/remote-client.js +56 -15
  62. package/dist/utils/remote-client.js.map +1 -1
  63. package/package.json +4 -1
  64. package/dist/tools/scaffold.d.ts +0 -15
  65. package/dist/tools/scaffold.js +0 -192
  66. package/dist/tools/scaffold.js.map +0 -1
@@ -0,0 +1,287 @@
1
+ /**
2
+ * Cross-platform USB device discovery for CrossPad.
3
+ *
4
+ * Primary method: Python/pyserial (required for IDF builds anyway).
5
+ * Fallback: platform-specific commands (Linux sysfs, macOS system_profiler, Windows PowerShell).
6
+ *
7
+ * Supports multiple simultaneous CrossPad devices — each identified by port path.
8
+ */
9
+ import { execSync } from "child_process";
10
+ import fs from "fs";
11
+ import path from "path";
12
+ import { IS_WINDOWS, IS_MAC } from "../config.js";
13
+ // CrossPad USB identifiers
14
+ const ESPRESSIF_VID = 0x303a;
15
+ const CROSSPAD_PID = 0x3456;
16
+ // ═══════════════════════════════════════════════════════════════════════
17
+ // PRIMARY: Python/pyserial enumeration (cross-platform)
18
+ // ═══════════════════════════════════════════════════════════════════════
19
+ function listPortsViaPython() {
20
+ const script = [
21
+ "import json, serial.tools.list_ports",
22
+ "ports = [{"
23
+ + '"port": p.device, "vid": p.vid, "pid": p.pid, '
24
+ + '"serial": p.serial_number, "desc": p.description, '
25
+ + '"mfr": p.manufacturer'
26
+ + "} for p in serial.tools.list_ports.comports() if p.vid]",
27
+ "print(json.dumps(ports))",
28
+ ].join("; ");
29
+ try {
30
+ const output = execSync(`python3 -c "${script}"`, {
31
+ encoding: "utf-8",
32
+ timeout: 10_000,
33
+ stdio: ["pipe", "pipe", "pipe"],
34
+ });
35
+ const raw = JSON.parse(output.trim());
36
+ return raw.map((r) => ({
37
+ port: r.port,
38
+ vid: r.vid ?? 0,
39
+ pid: r.pid ?? 0,
40
+ serial_number: r.serial,
41
+ description: r.desc,
42
+ manufacturer: r.mfr,
43
+ is_crosspad: r.vid === ESPRESSIF_VID && r.pid === CROSSPAD_PID,
44
+ }));
45
+ }
46
+ catch {
47
+ return null;
48
+ }
49
+ }
50
+ // ═══════════════════════════════════════════════════════════════════════
51
+ // FALLBACK: Platform-specific enumeration
52
+ // ═══════════════════════════════════════════════════════════════════════
53
+ function listPortsLinuxSysfs() {
54
+ const devices = [];
55
+ const ttyBase = "/sys/class/tty";
56
+ let entries;
57
+ try {
58
+ entries = fs.readdirSync(ttyBase);
59
+ }
60
+ catch {
61
+ return [];
62
+ }
63
+ for (const name of entries) {
64
+ if (!name.startsWith("ttyACM") && !name.startsWith("ttyUSB"))
65
+ continue;
66
+ const deviceLink = path.join(ttyBase, name, "device");
67
+ if (!fs.existsSync(deviceLink))
68
+ continue;
69
+ // Walk up to find USB device attributes
70
+ const usbDevicePath = findUsbParent(deviceLink);
71
+ if (!usbDevicePath)
72
+ continue;
73
+ const vid = readHexFile(path.join(usbDevicePath, "idVendor"));
74
+ const pid = readHexFile(path.join(usbDevicePath, "idProduct"));
75
+ if (vid === null || pid === null)
76
+ continue;
77
+ const serial = readTextFile(path.join(usbDevicePath, "serial"));
78
+ const manufacturer = readTextFile(path.join(usbDevicePath, "manufacturer"));
79
+ const product = readTextFile(path.join(usbDevicePath, "product"));
80
+ devices.push({
81
+ port: `/dev/${name}`,
82
+ vid,
83
+ pid,
84
+ serial_number: serial,
85
+ description: product ?? name,
86
+ manufacturer,
87
+ is_crosspad: vid === ESPRESSIF_VID && pid === CROSSPAD_PID,
88
+ });
89
+ }
90
+ return devices;
91
+ }
92
+ function findUsbParent(devicePath) {
93
+ let current;
94
+ try {
95
+ current = fs.realpathSync(devicePath);
96
+ }
97
+ catch {
98
+ return null;
99
+ }
100
+ // Walk up looking for idVendor file (USB device level)
101
+ for (let i = 0; i < 6; i++) {
102
+ if (fs.existsSync(path.join(current, "idVendor"))) {
103
+ return current;
104
+ }
105
+ current = path.dirname(current);
106
+ }
107
+ return null;
108
+ }
109
+ function readHexFile(filePath) {
110
+ try {
111
+ return parseInt(fs.readFileSync(filePath, "utf-8").trim(), 16);
112
+ }
113
+ catch {
114
+ return null;
115
+ }
116
+ }
117
+ function readTextFile(filePath) {
118
+ try {
119
+ return fs.readFileSync(filePath, "utf-8").trim() || null;
120
+ }
121
+ catch {
122
+ return null;
123
+ }
124
+ }
125
+ function listPortsMacOS() {
126
+ // Use system_profiler for USB device info
127
+ try {
128
+ const output = execSync("system_profiler SPUSBDataType -json", {
129
+ encoding: "utf-8",
130
+ timeout: 10_000,
131
+ stdio: ["pipe", "pipe", "pipe"],
132
+ });
133
+ const data = JSON.parse(output);
134
+ const devices = [];
135
+ collectMacDevices(data.SPUSBDataType ?? [], devices);
136
+ return devices;
137
+ }
138
+ catch {
139
+ return [];
140
+ }
141
+ }
142
+ function collectMacDevices(items, out) {
143
+ for (const item of items) {
144
+ if (item.vendor_id) {
145
+ const vid = parseMacId(item.vendor_id);
146
+ const pid = parseMacId(item.product_id);
147
+ if (vid !== null && pid !== null) {
148
+ // macOS serial ports follow /dev/cu.usbmodem* pattern
149
+ const serial = item.serial_num ?? null;
150
+ // Try to find matching /dev/cu.* port
151
+ const port = findMacPort(serial, item._name);
152
+ if (port) {
153
+ out.push({
154
+ port,
155
+ vid,
156
+ pid,
157
+ serial_number: serial,
158
+ description: item._name ?? "USB Device",
159
+ manufacturer: item.manufacturer ?? null,
160
+ is_crosspad: vid === ESPRESSIF_VID && pid === CROSSPAD_PID,
161
+ });
162
+ }
163
+ }
164
+ }
165
+ // Recurse into hubs
166
+ if (item._items) {
167
+ collectMacDevices(item._items, out);
168
+ }
169
+ }
170
+ }
171
+ function parseMacId(val) {
172
+ if (!val)
173
+ return null;
174
+ // Format: "0x303a" or "0x303a (Espressif Systems)"
175
+ const match = val.match(/0x([0-9a-f]+)/i);
176
+ return match ? parseInt(match[1], 16) : null;
177
+ }
178
+ function findMacPort(serial, name) {
179
+ try {
180
+ const ports = fs.readdirSync("/dev").filter((f) => f.startsWith("cu.usbmodem") || f.startsWith("cu.usbserial"));
181
+ if (ports.length === 0)
182
+ return null;
183
+ // If serial number is part of the port name, use that
184
+ if (serial) {
185
+ const match = ports.find((p) => p.includes(serial));
186
+ if (match)
187
+ return `/dev/${match}`;
188
+ }
189
+ // Return first matching port (best effort)
190
+ return `/dev/${ports[0]}`;
191
+ }
192
+ catch {
193
+ return null;
194
+ }
195
+ }
196
+ function listPortsWindows() {
197
+ try {
198
+ const cmd = `powershell -NoProfile -Command "Get-CimInstance Win32_PnPEntity | Where-Object { $_.PNPDeviceID -like '*VID_*PID_*' -and $_.Name -like '*(COM*)*' } | Select-Object Name,PNPDeviceID | ConvertTo-Json -Compress"`;
199
+ const output = execSync(cmd, {
200
+ encoding: "utf-8",
201
+ timeout: 15_000,
202
+ shell: "cmd.exe",
203
+ stdio: ["pipe", "pipe", "pipe"],
204
+ });
205
+ const trimmed = output.trim();
206
+ if (!trimmed)
207
+ return [];
208
+ const raw = JSON.parse(trimmed);
209
+ const items = Array.isArray(raw) ? raw : [raw];
210
+ return items.map((item) => {
211
+ const vidMatch = item.PNPDeviceID.match(/VID_([0-9A-F]+)/i);
212
+ const pidMatch = item.PNPDeviceID.match(/PID_([0-9A-F]+)/i);
213
+ const comMatch = item.Name.match(/\((COM\d+)\)/);
214
+ const vid = vidMatch ? parseInt(vidMatch[1], 16) : 0;
215
+ const pid = pidMatch ? parseInt(pidMatch[1], 16) : 0;
216
+ const port = comMatch ? comMatch[1] : "COM?";
217
+ return {
218
+ port,
219
+ vid,
220
+ pid,
221
+ serial_number: null,
222
+ description: item.Name,
223
+ manufacturer: null,
224
+ is_crosspad: vid === ESPRESSIF_VID && pid === CROSSPAD_PID,
225
+ };
226
+ }).filter((d) => d.vid > 0);
227
+ }
228
+ catch {
229
+ return [];
230
+ }
231
+ }
232
+ // ═══════════════════════════════════════════════════════════════════════
233
+ // PUBLIC API
234
+ // ═══════════════════════════════════════════════════════════════════════
235
+ /**
236
+ * List all connected USB serial devices. Returns CrossPad devices separately.
237
+ * Tries Python/pyserial first, falls back to platform-specific methods.
238
+ */
239
+ export function listDevices() {
240
+ // Try pyserial first (most reliable cross-platform)
241
+ let allPorts = listPortsViaPython();
242
+ // Fallback to platform-specific
243
+ if (allPorts === null) {
244
+ if (IS_WINDOWS) {
245
+ allPorts = listPortsWindows();
246
+ }
247
+ else if (IS_MAC) {
248
+ allPorts = listPortsMacOS();
249
+ }
250
+ else {
251
+ allPorts = listPortsLinuxSysfs();
252
+ }
253
+ }
254
+ const crosspadDevices = allPorts.filter((d) => d.is_crosspad);
255
+ return {
256
+ success: true,
257
+ devices: crosspadDevices,
258
+ all_ports: allPorts,
259
+ };
260
+ }
261
+ /**
262
+ * Find a CrossPad device, optionally by port.
263
+ * If port is specified, validates it's a CrossPad device.
264
+ * If not specified, auto-detects (fails if 0 or >1 found).
265
+ */
266
+ export function findCrosspadPort(port) {
267
+ if (port) {
268
+ return { port };
269
+ }
270
+ const result = listDevices();
271
+ const devices = result.devices;
272
+ if (devices.length === 0) {
273
+ return {
274
+ port: "",
275
+ error: "No CrossPad device found. Connect a device or specify port manually.",
276
+ };
277
+ }
278
+ if (devices.length > 1) {
279
+ const portList = devices.map((d) => ` ${d.port} (${d.description})`).join("\n");
280
+ return {
281
+ port: "",
282
+ error: `Multiple CrossPad devices found. Specify port:\n${portList}`,
283
+ };
284
+ }
285
+ return { port: devices[0].port, device: devices[0] };
286
+ }
287
+ //# sourceMappingURL=device.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"device.js","sourceRoot":"","sources":["../../src/utils/device.ts"],"names":[],"mappings":"AAAA;;;;;;;GAOG;AAEH,OAAO,EAAE,QAAQ,EAAE,MAAM,eAAe,CAAC;AACzC,OAAO,EAAE,MAAM,IAAI,CAAC;AACpB,OAAO,IAAI,MAAM,MAAM,CAAC;AACxB,OAAO,EAAE,UAAU,EAAE,MAAM,EAAE,MAAM,cAAc,CAAC;AAElD,2BAA2B;AAC3B,MAAM,aAAa,GAAG,MAAM,CAAC;AAC7B,MAAM,YAAY,GAAG,MAAM,CAAC;AAmB5B,0EAA0E;AAC1E,wDAAwD;AACxD,0EAA0E;AAE1E,SAAS,kBAAkB;IACzB,MAAM,MAAM,GAAG;QACb,sCAAsC;QACtC,YAAY;cACR,gDAAgD;cAChD,oDAAoD;cACpD,uBAAuB;cACvB,yDAAyD;QAC7D,0BAA0B;KAC3B,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;IAEb,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,QAAQ,CAAC,eAAe,MAAM,GAAG,EAAE;YAChD,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,MAAM;YACf,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC;SAChC,CAAC,CAAC;QAEH,MAAM,GAAG,GAOJ,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,IAAI,EAAE,CAAC,CAAC;QAE/B,OAAO,GAAG,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC;YACrB,IAAI,EAAE,CAAC,CAAC,IAAI;YACZ,GAAG,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC;YACf,GAAG,EAAE,CAAC,CAAC,GAAG,IAAI,CAAC;YACf,aAAa,EAAE,CAAC,CAAC,MAAM;YACvB,WAAW,EAAE,CAAC,CAAC,IAAI;YACnB,YAAY,EAAE,CAAC,CAAC,GAAG;YACnB,WAAW,EAAE,CAAC,CAAC,GAAG,KAAK,aAAa,IAAI,CAAC,CAAC,GAAG,KAAK,YAAY;SAC/D,CAAC,CAAC,CAAC;IACN,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC;AAED,0EAA0E;AAC1E,0CAA0C;AAC1C,0EAA0E;AAE1E,SAAS,mBAAmB;IAC1B,MAAM,OAAO,GAAqB,EAAE,CAAC;IACrC,MAAM,OAAO,GAAG,gBAAgB,CAAC;IAEjC,IAAI,OAAiB,CAAC;IACtB,IAAI,CAAC;QACH,OAAO,GAAG,EAAE,CAAC,WAAW,CAAC,OAAO,CAAC,CAAC;IACpC,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,CAAC;IACZ,CAAC;IAED,KAAK,MAAM,IAAI,IAAI,OAAO,EAAE,CAAC;QAC3B,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,QAAQ,CAAC,IAAI,CAAC,IAAI,CAAC,UAAU,CAAC,QAAQ,CAAC;YAAE,SAAS;QAEvE,MAAM,UAAU,GAAG,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,IAAI,EAAE,QAAQ,CAAC,CAAC;QACtD,IAAI,CAAC,EAAE,CAAC,UAAU,CAAC,UAAU,CAAC;YAAE,SAAS;QAEzC,wCAAwC;QACxC,MAAM,aAAa,GAAG,aAAa,CAAC,UAAU,CAAC,CAAC;QAChD,IAAI,CAAC,aAAa;YAAE,SAAS;QAE7B,MAAM,GAAG,GAAG,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,UAAU,CAAC,CAAC,CAAC;QAC9D,MAAM,GAAG,GAAG,WAAW,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,WAAW,CAAC,CAAC,CAAC;QAC/D,IAAI,GAAG,KAAK,IAAI,IAAI,GAAG,KAAK,IAAI;YAAE,SAAS;QAE3C,MAAM,MAAM,GAAG,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,QAAQ,CAAC,CAAC,CAAC;QAChE,MAAM,YAAY,GAAG,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,cAAc,CAAC,CAAC,CAAC;QAC5E,MAAM,OAAO,GAAG,YAAY,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE,SAAS,CAAC,CAAC,CAAC;QAElE,OAAO,CAAC,IAAI,CAAC;YACX,IAAI,EAAE,QAAQ,IAAI,EAAE;YACpB,GAAG;YACH,GAAG;YACH,aAAa,EAAE,MAAM;YACrB,WAAW,EAAE,OAAO,IAAI,IAAI;YAC5B,YAAY;YACZ,WAAW,EAAE,GAAG,KAAK,aAAa,IAAI,GAAG,KAAK,YAAY;SAC3D,CAAC,CAAC;IACL,CAAC;IAED,OAAO,OAAO,CAAC;AACjB,CAAC;AAED,SAAS,aAAa,CAAC,UAAkB;IACvC,IAAI,OAAe,CAAC;IACpB,IAAI,CAAC;QACH,OAAO,GAAG,EAAE,CAAC,YAAY,CAAC,UAAU,CAAC,CAAC;IACxC,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;IAED,uDAAuD;IACvD,KAAK,IAAI,CAAC,GAAG,CAAC,EAAE,CAAC,GAAG,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC;QAC3B,IAAI,EAAE,CAAC,UAAU,CAAC,IAAI,CAAC,IAAI,CAAC,OAAO,EAAE,UAAU,CAAC,CAAC,EAAE,CAAC;YAClD,OAAO,OAAO,CAAC;QACjB,CAAC;QACD,OAAO,GAAG,IAAI,CAAC,OAAO,CAAC,OAAO,CAAC,CAAC;IAClC,CAAC;IACD,OAAO,IAAI,CAAC;AACd,CAAC;AAED,SAAS,WAAW,CAAC,QAAgB;IACnC,IAAI,CAAC;QACH,OAAO,QAAQ,CAAC,EAAE,CAAC,YAAY,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC,IAAI,EAAE,EAAE,EAAE,CAAC,CAAC;IACjE,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC;AAED,SAAS,YAAY,CAAC,QAAgB;IACpC,IAAI,CAAC;QACH,OAAO,EAAE,CAAC,YAAY,CAAC,QAAQ,EAAE,OAAO,CAAC,CAAC,IAAI,EAAE,IAAI,IAAI,CAAC;IAC3D,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC;AAED,SAAS,cAAc;IACrB,0CAA0C;IAC1C,IAAI,CAAC;QACH,MAAM,MAAM,GAAG,QAAQ,CAAC,qCAAqC,EAAE;YAC7D,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,MAAM;YACf,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC;SAChC,CAAC,CAAC;QAEH,MAAM,IAAI,GAAG,IAAI,CAAC,KAAK,CAAC,MAAM,CAAC,CAAC;QAChC,MAAM,OAAO,GAAqB,EAAE,CAAC;QACrC,iBAAiB,CAAC,IAAI,CAAC,aAAa,IAAI,EAAE,EAAE,OAAO,CAAC,CAAC;QACrD,OAAO,OAAO,CAAC;IACjB,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,CAAC;IACZ,CAAC;AACH,CAAC;AAED,SAAS,iBAAiB,CACxB,KAAY,EACZ,GAAqB;IAErB,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,IAAI,IAAI,CAAC,SAAS,EAAE,CAAC;YACnB,MAAM,GAAG,GAAG,UAAU,CAAC,IAAI,CAAC,SAAS,CAAC,CAAC;YACvC,MAAM,GAAG,GAAG,UAAU,CAAC,IAAI,CAAC,UAAU,CAAC,CAAC;YAExC,IAAI,GAAG,KAAK,IAAI,IAAI,GAAG,KAAK,IAAI,EAAE,CAAC;gBACjC,sDAAsD;gBACtD,MAAM,MAAM,GAAG,IAAI,CAAC,UAAU,IAAI,IAAI,CAAC;gBACvC,sCAAsC;gBACtC,MAAM,IAAI,GAAG,WAAW,CAAC,MAAM,EAAE,IAAI,CAAC,KAAK,CAAC,CAAC;gBAE7C,IAAI,IAAI,EAAE,CAAC;oBACT,GAAG,CAAC,IAAI,CAAC;wBACP,IAAI;wBACJ,GAAG;wBACH,GAAG;wBACH,aAAa,EAAE,MAAM;wBACrB,WAAW,EAAE,IAAI,CAAC,KAAK,IAAI,YAAY;wBACvC,YAAY,EAAE,IAAI,CAAC,YAAY,IAAI,IAAI;wBACvC,WAAW,EAAE,GAAG,KAAK,aAAa,IAAI,GAAG,KAAK,YAAY;qBAC3D,CAAC,CAAC;gBACL,CAAC;YACH,CAAC;QACH,CAAC;QAED,oBAAoB;QACpB,IAAI,IAAI,CAAC,MAAM,EAAE,CAAC;YAChB,iBAAiB,CAAC,IAAI,CAAC,MAAM,EAAE,GAAG,CAAC,CAAC;QACtC,CAAC;IACH,CAAC;AACH,CAAC;AAED,SAAS,UAAU,CAAC,GAAuB;IACzC,IAAI,CAAC,GAAG;QAAE,OAAO,IAAI,CAAC;IACtB,mDAAmD;IACnD,MAAM,KAAK,GAAG,GAAG,CAAC,KAAK,CAAC,gBAAgB,CAAC,CAAC;IAC1C,OAAO,KAAK,CAAC,CAAC,CAAC,QAAQ,CAAC,KAAK,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,IAAI,CAAC;AAC/C,CAAC;AAED,SAAS,WAAW,CAAC,MAAqB,EAAE,IAAmB;IAC7D,IAAI,CAAC;QACH,MAAM,KAAK,GAAG,EAAE,CAAC,WAAW,CAAC,MAAM,CAAC,CAAC,MAAM,CACzC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,UAAU,CAAC,aAAa,CAAC,IAAI,CAAC,CAAC,UAAU,CAAC,cAAc,CAAC,CACnE,CAAC;QAEF,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC;YAAE,OAAO,IAAI,CAAC;QAEpC,sDAAsD;QACtD,IAAI,MAAM,EAAE,CAAC;YACX,MAAM,KAAK,GAAG,KAAK,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC;YACpD,IAAI,KAAK;gBAAE,OAAO,QAAQ,KAAK,EAAE,CAAC;QACpC,CAAC;QAED,2CAA2C;QAC3C,OAAO,QAAQ,KAAK,CAAC,CAAC,CAAC,EAAE,CAAC;IAC5B,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,IAAI,CAAC;IACd,CAAC;AACH,CAAC;AAED,SAAS,gBAAgB;IACvB,IAAI,CAAC;QACH,MAAM,GAAG,GAAG,kNAAkN,CAAC;QAC/N,MAAM,MAAM,GAAG,QAAQ,CAAC,GAAG,EAAE;YAC3B,QAAQ,EAAE,OAAO;YACjB,OAAO,EAAE,MAAM;YACf,KAAK,EAAE,SAAS;YAChB,KAAK,EAAE,CAAC,MAAM,EAAE,MAAM,EAAE,MAAM,CAAC;SAChC,CAAC,CAAC;QAEH,MAAM,OAAO,GAAG,MAAM,CAAC,IAAI,EAAE,CAAC;QAC9B,IAAI,CAAC,OAAO;YAAE,OAAO,EAAE,CAAC;QAExB,MAAM,GAAG,GAAG,IAAI,CAAC,KAAK,CAAC,OAAO,CAAC,CAAC;QAChC,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC;QAE/C,OAAO,KAAK,CAAC,GAAG,CAAC,CAAC,IAA2C,EAAE,EAAE;YAC/D,MAAM,QAAQ,GAAG,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC,kBAAkB,CAAC,CAAC;YAC5D,MAAM,QAAQ,GAAG,IAAI,CAAC,WAAW,CAAC,KAAK,CAAC,kBAAkB,CAAC,CAAC;YAC5D,MAAM,QAAQ,GAAG,IAAI,CAAC,IAAI,CAAC,KAAK,CAAC,cAAc,CAAC,CAAC;YAEjD,MAAM,GAAG,GAAG,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;YACrD,MAAM,GAAG,GAAG,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,QAAQ,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;YACrD,MAAM,IAAI,GAAG,QAAQ,CAAC,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC;YAE7C,OAAO;gBACL,IAAI;gBACJ,GAAG;gBACH,GAAG;gBACH,aAAa,EAAE,IAAI;gBACnB,WAAW,EAAE,IAAI,CAAC,IAAI;gBACtB,YAAY,EAAE,IAAI;gBAClB,WAAW,EAAE,GAAG,KAAK,aAAa,IAAI,GAAG,KAAK,YAAY;aAC3D,CAAC;QACJ,CAAC,CAAC,CAAC,MAAM,CAAC,CAAC,CAAiB,EAAE,EAAE,CAAC,CAAC,CAAC,GAAG,GAAG,CAAC,CAAC,CAAC;IAC9C,CAAC;IAAC,MAAM,CAAC;QACP,OAAO,EAAE,CAAC;IACZ,CAAC;AACH,CAAC;AAED,0EAA0E;AAC1E,aAAa;AACb,0EAA0E;AAE1E;;;GAGG;AACH,MAAM,UAAU,WAAW;IACzB,oDAAoD;IACpD,IAAI,QAAQ,GAAG,kBAAkB,EAAE,CAAC;IAEpC,gCAAgC;IAChC,IAAI,QAAQ,KAAK,IAAI,EAAE,CAAC;QACtB,IAAI,UAAU,EAAE,CAAC;YACf,QAAQ,GAAG,gBAAgB,EAAE,CAAC;QAChC,CAAC;aAAM,IAAI,MAAM,EAAE,CAAC;YAClB,QAAQ,GAAG,cAAc,EAAE,CAAC;QAC9B,CAAC;aAAM,CAAC;YACN,QAAQ,GAAG,mBAAmB,EAAE,CAAC;QACnC,CAAC;IACH,CAAC;IAED,MAAM,eAAe,GAAG,QAAQ,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,WAAW,CAAC,CAAC;IAE9D,OAAO;QACL,OAAO,EAAE,IAAI;QACb,OAAO,EAAE,eAAe;QACxB,SAAS,EAAE,QAAQ;KACpB,CAAC;AACJ,CAAC;AAED;;;;GAIG;AACH,MAAM,UAAU,gBAAgB,CAAC,IAAa;IAK5C,IAAI,IAAI,EAAE,CAAC;QACT,OAAO,EAAE,IAAI,EAAE,CAAC;IAClB,CAAC;IAED,MAAM,MAAM,GAAG,WAAW,EAAE,CAAC;IAC7B,MAAM,OAAO,GAAG,MAAM,CAAC,OAAO,CAAC;IAE/B,IAAI,OAAO,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACzB,OAAO;YACL,IAAI,EAAE,EAAE;YACR,KAAK,EAAE,sEAAsE;SAC9E,CAAC;IACJ,CAAC;IAED,IAAI,OAAO,CAAC,MAAM,GAAG,CAAC,EAAE,CAAC;QACvB,MAAM,QAAQ,GAAG,OAAO,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,EAAE,CAAC,KAAK,CAAC,CAAC,IAAI,KAAK,CAAC,CAAC,WAAW,GAAG,CAAC,CAAC,IAAI,CAAC,IAAI,CAAC,CAAC;QACjF,OAAO;YACL,IAAI,EAAE,EAAE;YACR,KAAK,EAAE,mDAAmD,QAAQ,EAAE;SACrE,CAAC;IACJ,CAAC;IAED,OAAO,EAAE,IAAI,EAAE,OAAO,CAAC,CAAC,CAAC,CAAC,IAAI,EAAE,MAAM,EAAE,OAAO,CAAC,CAAC,CAAC,EAAE,CAAC;AACvD,CAAC"}
@@ -1,5 +1,7 @@
1
1
  /** Callback invoked for each line of stdout/stderr during streaming exec. */
2
2
  export type OnLine = (stream: "stdout" | "stderr", line: string) => void;
3
+ /** @internal exported for testing — drop both env caches. */
4
+ export declare function _resetEnvCaches(): void;
3
5
  /**
4
6
  * Capture MSVC environment by running vcvarsall.bat and parsing `set` output.
5
7
  * Cached for the lifetime of the server process. Windows-only.
@@ -20,14 +22,19 @@ export declare function runWithMsvc(cmd: string, cwd: string, timeoutMs?: number
20
22
  * Run a command in the default shell, capturing output.
21
23
  */
22
24
  export declare function runCommand(cmd: string, cwd: string, timeoutMs?: number): ExecResult;
25
+ /**
26
+ * Run an arbitrary executable with argv array (no shell). Use for inputs that
27
+ * may contain user-controlled strings — eliminates shell-injection risk.
28
+ */
29
+ export declare function runArgvStream(cmd: string, args: string[], cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal, env?: Record<string, string>): Promise<ExecResult>;
23
30
  /**
24
31
  * Run a command with the MSVC environment, streaming output line-by-line.
25
32
  */
26
- export declare function runWithMsvcStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number): Promise<ExecResult>;
33
+ export declare function runWithMsvcStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal): Promise<ExecResult>;
27
34
  /**
28
35
  * Run a command in the default shell, streaming output line-by-line.
29
36
  */
30
- export declare function runCommandStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number): Promise<ExecResult>;
37
+ export declare function runCommandStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal): Promise<ExecResult>;
31
38
  /**
32
39
  * Capture ESP-IDF environment. Cached for the lifetime of the server process.
33
40
  * - Windows: runs export.bat and parses `set` output
@@ -41,7 +48,12 @@ export declare function runWithIdf(cmd: string, cwd: string, timeoutMs?: number)
41
48
  /**
42
49
  * Run a command with the ESP-IDF environment, streaming output line-by-line.
43
50
  */
44
- export declare function runWithIdfStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number): Promise<ExecResult>;
51
+ export declare function runWithIdfStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal): Promise<ExecResult>;
52
+ /**
53
+ * Run with IDF env in argv mode (no shell) — use for commands taking
54
+ * user-controlled args (port path, firmware path).
55
+ */
56
+ export declare function runIdfArgvStream(cmd: string, args: string[], cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal): Promise<ExecResult>;
45
57
  /**
46
58
  * Run a build command with the appropriate environment for the current platform.
47
59
  * Windows: MSVC env + cmd.exe shell. Unix: default shell.
@@ -51,7 +63,7 @@ export declare function runBuild(cmd: string, cwd: string, timeoutMs?: number):
51
63
  * Run a build command with streaming output, platform-aware.
52
64
  * Windows: MSVC env + cmd.exe shell. Unix: default shell.
53
65
  */
54
- export declare function runBuildStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number): Promise<ExecResult>;
66
+ export declare function runBuildStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal): Promise<ExecResult>;
55
67
  /**
56
68
  * Run a command with the ESP-IDF environment, platform-aware.
57
69
  */
@@ -59,7 +71,7 @@ export declare function runIdf(cmd: string, cwd: string, timeoutMs?: number): Ex
59
71
  /**
60
72
  * Run a command with the ESP-IDF environment, streaming, platform-aware.
61
73
  */
62
- export declare function runIdfStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number): Promise<ExecResult>;
74
+ export declare function runIdfStream(cmd: string, cwd: string, onLine: OnLine, timeoutMs?: number, signal?: AbortSignal): Promise<ExecResult>;
63
75
  /**
64
76
  * Spawn a detached process (for crosspad_run).
65
77
  */
@@ -1,9 +1,20 @@
1
1
  import { execSync, spawn } from "child_process";
2
+ import fs from "fs";
2
3
  import { VCVARSALL, IS_WINDOWS, IDF_PATH } from "../config.js";
3
- // ═══════════════════════════════════════════════════════════════════════
4
- // MSVC ENVIRONMENT (Windows-only)
5
- // ═══════════════════════════════════════════════════════════════════════
6
4
  let cachedMsvcEnv = null;
5
+ function statMtime(p) {
6
+ try {
7
+ return fs.statSync(p).mtimeMs;
8
+ }
9
+ catch {
10
+ return 0;
11
+ }
12
+ }
13
+ /** @internal exported for testing — drop both env caches. */
14
+ export function _resetEnvCaches() {
15
+ cachedMsvcEnv = null;
16
+ cachedIdfEnv = null;
17
+ }
7
18
  /**
8
19
  * Capture MSVC environment by running vcvarsall.bat and parsing `set` output.
9
20
  * Cached for the lifetime of the server process. Windows-only.
@@ -12,8 +23,9 @@ export function getMsvcEnv() {
12
23
  if (!IS_WINDOWS) {
13
24
  return { ...process.env };
14
25
  }
15
- if (cachedMsvcEnv)
16
- return cachedMsvcEnv;
26
+ const mtime = statMtime(VCVARSALL);
27
+ if (cachedMsvcEnv && cachedMsvcEnv.mtimeMs === mtime)
28
+ return cachedMsvcEnv.data;
17
29
  const cmd = `"${VCVARSALL}" x64 >nul 2>&1 && set`;
18
30
  const output = execSync(cmd, {
19
31
  shell: "cmd.exe",
@@ -27,7 +39,7 @@ export function getMsvcEnv() {
27
39
  env[line.slice(0, eq)] = line.slice(eq + 1).trimEnd();
28
40
  }
29
41
  }
30
- cachedMsvcEnv = env;
42
+ cachedMsvcEnv = { data: env, mtimeMs: mtime };
31
43
  return env;
32
44
  }
33
45
  // ═══════════════════════════════════════════════════════════════════════
@@ -101,12 +113,12 @@ export function runCommand(cmd, cwd, timeoutMs = 60_000) {
101
113
  // ═══════════════════════════════════════════════════════════════════════
102
114
  /**
103
115
  * Helper: spawn a process and stream stdout/stderr line-by-line via onLine.
104
- * Returns the same ExecResult as the sync variants.
116
+ * Supports argv mode (shell:false + args[]) and AbortSignal-driven cancellation.
105
117
  */
106
- function spawnStreaming(cmd, cwd, env, shell, onLine, timeoutMs) {
118
+ function spawnStreaming(cmd, cwd, env, shell, onLine, timeoutMs, args = [], signal) {
107
119
  return new Promise((resolve) => {
108
120
  const start = Date.now();
109
- const child = spawn(cmd, [], {
121
+ const child = spawn(cmd, args, {
110
122
  cwd,
111
123
  env,
112
124
  shell,
@@ -118,10 +130,23 @@ function spawnStreaming(cmd, cwd, env, shell, onLine, timeoutMs) {
118
130
  let stdoutBuf = "";
119
131
  let stderrBuf = "";
120
132
  let killed = false;
133
+ let cancelled = false;
121
134
  const timer = setTimeout(() => {
122
135
  killed = true;
123
136
  child.kill("SIGTERM");
124
137
  }, timeoutMs);
138
+ const escalateKill = () => {
139
+ child.kill("SIGTERM");
140
+ setTimeout(() => { if (!child.killed)
141
+ child.kill("SIGKILL"); }, 2000);
142
+ };
143
+ const onAbort = () => { cancelled = true; killed = true; escalateKill(); };
144
+ if (signal) {
145
+ if (signal.aborted)
146
+ onAbort();
147
+ else
148
+ signal.addEventListener("abort", onAbort, { once: true });
149
+ }
125
150
  function flushLines(buf, stream) {
126
151
  const parts = buf.split("\n");
127
152
  for (let i = 0; i < parts.length - 1; i++) {
@@ -144,6 +169,8 @@ function spawnStreaming(cmd, cwd, env, shell, onLine, timeoutMs) {
144
169
  });
145
170
  child.on("close", (code) => {
146
171
  clearTimeout(timer);
172
+ if (signal)
173
+ signal.removeEventListener("abort", onAbort);
147
174
  if (stdoutBuf.length > 0)
148
175
  onLine("stdout", stdoutBuf.replace(/\r$/, ""));
149
176
  if (stderrBuf.length > 0)
@@ -151,13 +178,15 @@ function spawnStreaming(cmd, cwd, env, shell, onLine, timeoutMs) {
151
178
  resolve({
152
179
  success: killed ? false : code === 0,
153
180
  stdout: normalizeLineEndings(stdout),
154
- stderr: normalizeLineEndings(stderr),
181
+ stderr: normalizeLineEndings(cancelled ? stderr + "\n[cancelled]" : stderr),
155
182
  exitCode: killed ? -1 : (code ?? 1),
156
183
  durationMs: Date.now() - start,
157
184
  });
158
185
  });
159
186
  child.on("error", (err) => {
160
187
  clearTimeout(timer);
188
+ if (signal)
189
+ signal.removeEventListener("abort", onAbort);
161
190
  resolve({
162
191
  success: false,
163
192
  stdout: normalizeLineEndings(stdout),
@@ -168,18 +197,25 @@ function spawnStreaming(cmd, cwd, env, shell, onLine, timeoutMs) {
168
197
  });
169
198
  });
170
199
  }
200
+ /**
201
+ * Run an arbitrary executable with argv array (no shell). Use for inputs that
202
+ * may contain user-controlled strings — eliminates shell-injection risk.
203
+ */
204
+ export function runArgvStream(cmd, args, cwd, onLine, timeoutMs = 60_000, signal, env) {
205
+ return spawnStreaming(cmd, cwd, env, false, onLine, timeoutMs, args, signal);
206
+ }
171
207
  /**
172
208
  * Run a command with the MSVC environment, streaming output line-by-line.
173
209
  */
174
- export function runWithMsvcStream(cmd, cwd, onLine, timeoutMs = 300_000) {
210
+ export function runWithMsvcStream(cmd, cwd, onLine, timeoutMs = 300_000, signal) {
175
211
  const env = getMsvcEnv();
176
- return spawnStreaming(cmd, cwd, env, "cmd.exe", onLine, timeoutMs);
212
+ return spawnStreaming(cmd, cwd, env, "cmd.exe", onLine, timeoutMs, [], signal);
177
213
  }
178
214
  /**
179
215
  * Run a command in the default shell, streaming output line-by-line.
180
216
  */
181
- export function runCommandStream(cmd, cwd, onLine, timeoutMs = 60_000) {
182
- return spawnStreaming(cmd, cwd, undefined, true, onLine, timeoutMs);
217
+ export function runCommandStream(cmd, cwd, onLine, timeoutMs = 60_000, signal) {
218
+ return spawnStreaming(cmd, cwd, undefined, true, onLine, timeoutMs, [], signal);
183
219
  }
184
220
  // ═══════════════════════════════════════════════════════════════════════
185
221
  // ESP-IDF ENVIRONMENT
@@ -191,10 +227,12 @@ let cachedIdfEnv = null;
191
227
  * - Linux/Mac: sources export.sh and captures env via null-delimited output
192
228
  */
193
229
  export function getIdfEnv() {
194
- if (cachedIdfEnv)
195
- return cachedIdfEnv;
230
+ const exportPath = IS_WINDOWS ? `${IDF_PATH}\\export.bat` : `${IDF_PATH}/export.sh`;
231
+ const mtime = statMtime(exportPath);
232
+ if (cachedIdfEnv && cachedIdfEnv.mtimeMs === mtime)
233
+ return cachedIdfEnv.data;
196
234
  if (IS_WINDOWS) {
197
- const exportBat = `${IDF_PATH}\\export.bat`;
235
+ const exportBat = exportPath;
198
236
  const cmd = `set MSYSTEM=&& set PYTHONIOENCODING=utf-8&& call "${exportBat}" >nul 2>&1 && set`;
199
237
  const output = execSync(cmd, {
200
238
  shell: "cmd.exe",
@@ -208,11 +246,11 @@ export function getIdfEnv() {
208
246
  env[line.slice(0, eq)] = line.slice(eq + 1).trimEnd();
209
247
  }
210
248
  }
211
- cachedIdfEnv = env;
249
+ cachedIdfEnv = { data: env, mtimeMs: mtime };
212
250
  return env;
213
251
  }
214
252
  // Linux/Mac: source export.sh and capture environment
215
- const exportSh = `${IDF_PATH}/export.sh`;
253
+ const exportSh = exportPath;
216
254
  const cmd = `bash -c '. "${exportSh}" >/dev/null 2>&1 && env -0'`;
217
255
  const output = execSync(cmd, {
218
256
  encoding: "utf-8",
@@ -228,7 +266,7 @@ export function getIdfEnv() {
228
266
  env[entry.slice(0, eq)] = entry.slice(eq + 1);
229
267
  }
230
268
  }
231
- cachedIdfEnv = env;
269
+ cachedIdfEnv = { data: env, mtimeMs: mtime };
232
270
  return env;
233
271
  }
234
272
  const IDF_SHELL = IS_WINDOWS ? "cmd.exe" : "/bin/bash";
@@ -268,9 +306,17 @@ export function runWithIdf(cmd, cwd, timeoutMs = 600_000) {
268
306
  /**
269
307
  * Run a command with the ESP-IDF environment, streaming output line-by-line.
270
308
  */
271
- export function runWithIdfStream(cmd, cwd, onLine, timeoutMs = 600_000) {
309
+ export function runWithIdfStream(cmd, cwd, onLine, timeoutMs = 600_000, signal) {
310
+ const env = getIdfEnv();
311
+ return spawnStreaming(cmd, cwd, env, IDF_SHELL, onLine, timeoutMs, [], signal);
312
+ }
313
+ /**
314
+ * Run with IDF env in argv mode (no shell) — use for commands taking
315
+ * user-controlled args (port path, firmware path).
316
+ */
317
+ export function runIdfArgvStream(cmd, args, cwd, onLine, timeoutMs = 600_000, signal) {
272
318
  const env = getIdfEnv();
273
- return spawnStreaming(cmd, cwd, env, IDF_SHELL, onLine, timeoutMs);
319
+ return spawnStreaming(cmd, cwd, env, false, onLine, timeoutMs, args, signal);
274
320
  }
275
321
  // ═══════════════════════════════════════════════════════════════════════
276
322
  // PLATFORM-AGNOSTIC BUILD WRAPPERS
@@ -289,11 +335,11 @@ export function runBuild(cmd, cwd, timeoutMs = 300_000) {
289
335
  * Run a build command with streaming output, platform-aware.
290
336
  * Windows: MSVC env + cmd.exe shell. Unix: default shell.
291
337
  */
292
- export function runBuildStream(cmd, cwd, onLine, timeoutMs = 300_000) {
338
+ export function runBuildStream(cmd, cwd, onLine, timeoutMs = 300_000, signal) {
293
339
  if (IS_WINDOWS) {
294
- return runWithMsvcStream(cmd, cwd, onLine, timeoutMs);
340
+ return runWithMsvcStream(cmd, cwd, onLine, timeoutMs, signal);
295
341
  }
296
- return runCommandStream(cmd, cwd, onLine, timeoutMs);
342
+ return runCommandStream(cmd, cwd, onLine, timeoutMs, signal);
297
343
  }
298
344
  /**
299
345
  * Run a command with the ESP-IDF environment, platform-aware.
@@ -304,8 +350,8 @@ export function runIdf(cmd, cwd, timeoutMs = 600_000) {
304
350
  /**
305
351
  * Run a command with the ESP-IDF environment, streaming, platform-aware.
306
352
  */
307
- export function runIdfStream(cmd, cwd, onLine, timeoutMs = 600_000) {
308
- return runWithIdfStream(cmd, cwd, onLine, timeoutMs);
353
+ export function runIdfStream(cmd, cwd, onLine, timeoutMs = 600_000, signal) {
354
+ return runWithIdfStream(cmd, cwd, onLine, timeoutMs, signal);
309
355
  }
310
356
  /** Strip \r from Windows line endings */
311
357
  function normalizeLineEndings(s) {
@@ -1 +1 @@
1
- {"version":3,"file":"exec.js","sourceRoot":"","sources":["../../src/utils/exec.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"exec.js","sourceRoot":"","sources":["../../src/utils/exec.ts"],"names":[],"mappings":"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"}
@@ -6,5 +6,14 @@ export interface RepoStatus {
6
6
  dirtyFiles: string[];
7
7
  }
8
8
  export declare function getRepoStatus(name: string, repoPath: string): RepoStatus;
9
+ /**
10
+ * Get the pinned commit hash of a submodule.
11
+ *
12
+ * `submodule` may be either a canonical name (e.g. "crosspad-core") or a
13
+ * relative path (e.g. "lib/crosspad-core"). Names are resolved via .gitmodules.
14
+ */
9
15
  export declare function getSubmodulePin(repoPath: string, submodule: string): string | null;
10
16
  export declare function getHead(repoPath: string): string | null;
17
+ export declare function listSubmodules(repoPath: string): Record<string, string>;
18
+ /** Resolve a submodule's path within a parent repo by canonical name. Null if not present. */
19
+ export declare function findSubmodulePath(repoPath: string, submoduleName: string): string | null;