esp32tool 1.6.3 → 1.6.4
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 +2 -0
- package/apple-touch-icon.png +0 -0
- package/css/style.css +23 -0
- package/dist/cli.js +13 -2
- package/dist/esp_loader.js +12 -0
- package/dist/web/index.js +1 -1
- package/icons/icon-128.png +0 -0
- package/icons/icon-144.png +0 -0
- package/icons/icon-152.png +0 -0
- package/icons/icon-192.png +0 -0
- package/icons/icon-384.png +0 -0
- package/icons/icon-512.png +0 -0
- package/icons/icon-72.png +0 -0
- package/icons/icon-96.png +0 -0
- package/index.html +1 -0
- package/js/modules/esptool.js +1 -1
- package/js/script.js +3 -0
- package/js/util/console-color.js +29 -2
- package/package.cli.json +2 -2
- package/package.json +15 -11
- package/screenshots/desktop.png +0 -0
- package/screenshots/mobile.png +0 -0
- package/src/cli.ts +13 -2
- package/src/esp_loader.ts +24 -0
- package/sw.js +1 -1
package/js/script.js
CHANGED
|
@@ -199,6 +199,7 @@ const butReadFlash = document.getElementById("butReadFlash");
|
|
|
199
199
|
const readOffset = document.getElementById("readOffset");
|
|
200
200
|
const readSize = document.getElementById("readSize");
|
|
201
201
|
const readProgress = document.getElementById("readProgress");
|
|
202
|
+
const eraseProgress = document.getElementById("eraseProgress");
|
|
202
203
|
const butReadPartitions = document.getElementById("butReadPartitions");
|
|
203
204
|
const butDetectFS = document.getElementById("butDetectFS");
|
|
204
205
|
const butOpenFSManager = document.getElementById("butOpenFSManager");
|
|
@@ -1601,6 +1602,7 @@ async function clickErase() {
|
|
|
1601
1602
|
baudRateSelect.disabled = true;
|
|
1602
1603
|
butErase.disabled = true;
|
|
1603
1604
|
butProgram.disabled = true;
|
|
1605
|
+
eraseProgress.classList.remove("hidden");
|
|
1604
1606
|
try {
|
|
1605
1607
|
logMsg("Erasing flash memory. Please wait...");
|
|
1606
1608
|
let stamp = Date.now();
|
|
@@ -1609,6 +1611,7 @@ async function clickErase() {
|
|
|
1609
1611
|
} catch (e) {
|
|
1610
1612
|
errorMsg(e);
|
|
1611
1613
|
} finally {
|
|
1614
|
+
eraseProgress.classList.add("hidden");
|
|
1612
1615
|
butErase.disabled = false;
|
|
1613
1616
|
baudRateSelect.disabled = false;
|
|
1614
1617
|
butProgram.disabled = getValidFiles().length == 0;
|
package/js/util/console-color.js
CHANGED
|
@@ -10,6 +10,8 @@ export class ColoredConsole {
|
|
|
10
10
|
backgroundColor: null,
|
|
11
11
|
carriageReturn: false,
|
|
12
12
|
secret: false,
|
|
13
|
+
blink: false,
|
|
14
|
+
rapidBlink: false,
|
|
13
15
|
};
|
|
14
16
|
}
|
|
15
17
|
|
|
@@ -49,6 +51,8 @@ export class ColoredConsole {
|
|
|
49
51
|
if (this.state.underline) span.classList.add("log-underline");
|
|
50
52
|
if (this.state.strikethrough) span.classList.add("log-strikethrough");
|
|
51
53
|
if (this.state.secret) span.classList.add("log-secret");
|
|
54
|
+
if (this.state.blink) span.classList.add("log-blink");
|
|
55
|
+
if (this.state.rapidBlink) span.classList.add("log-rapid-blink");
|
|
52
56
|
if (this.state.foregroundColor !== null)
|
|
53
57
|
span.classList.add(`log-fg-${this.state.foregroundColor}`);
|
|
54
58
|
if (this.state.backgroundColor !== null)
|
|
@@ -85,6 +89,8 @@ export class ColoredConsole {
|
|
|
85
89
|
this.state.foregroundColor = null;
|
|
86
90
|
this.state.backgroundColor = null;
|
|
87
91
|
this.state.secret = false;
|
|
92
|
+
this.state.blink = false;
|
|
93
|
+
this.state.rapidBlink = false;
|
|
88
94
|
break;
|
|
89
95
|
case 1:
|
|
90
96
|
this.state.bold = true;
|
|
@@ -96,10 +102,13 @@ export class ColoredConsole {
|
|
|
96
102
|
this.state.underline = true;
|
|
97
103
|
break;
|
|
98
104
|
case 5:
|
|
99
|
-
this.state.
|
|
105
|
+
this.state.blink = true;
|
|
100
106
|
break;
|
|
101
107
|
case 6:
|
|
102
|
-
this.state.
|
|
108
|
+
this.state.rapidBlink = true;
|
|
109
|
+
break;
|
|
110
|
+
case 8:
|
|
111
|
+
this.state.secret = true;
|
|
103
112
|
break;
|
|
104
113
|
case 9:
|
|
105
114
|
this.state.strikethrough = true;
|
|
@@ -113,6 +122,13 @@ export class ColoredConsole {
|
|
|
113
122
|
case 24:
|
|
114
123
|
this.state.underline = false;
|
|
115
124
|
break;
|
|
125
|
+
case 25:
|
|
126
|
+
this.state.blink = false;
|
|
127
|
+
this.state.rapidBlink = false;
|
|
128
|
+
break;
|
|
129
|
+
case 28:
|
|
130
|
+
this.state.secret = false;
|
|
131
|
+
break;
|
|
116
132
|
case 29:
|
|
117
133
|
this.state.strikethrough = false;
|
|
118
134
|
break;
|
|
@@ -232,6 +248,17 @@ export const coloredConsoleStyles = `
|
|
|
232
248
|
width: 1px;
|
|
233
249
|
font-size: 1px;
|
|
234
250
|
}
|
|
251
|
+
.log-blink {
|
|
252
|
+
animation: blink 1s step-start infinite;
|
|
253
|
+
}
|
|
254
|
+
.log-rapid-blink {
|
|
255
|
+
animation: blink 0.3s step-start infinite;
|
|
256
|
+
}
|
|
257
|
+
@keyframes blink {
|
|
258
|
+
50% {
|
|
259
|
+
opacity: 0;
|
|
260
|
+
}
|
|
261
|
+
}
|
|
235
262
|
.log-fg-black {
|
|
236
263
|
color: rgb(128, 128, 128);
|
|
237
264
|
}
|
package/package.cli.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "esp32tool",
|
|
3
|
-
"version": "1.3
|
|
3
|
+
"version": "1.6.3",
|
|
4
4
|
"private": true,
|
|
5
5
|
"type": "module",
|
|
6
6
|
"description": "ESP32Tool - Standalone command-line tool (build-time config only)",
|
|
@@ -20,7 +20,7 @@
|
|
|
20
20
|
"dependencies": {
|
|
21
21
|
"pako": "^2.1.0",
|
|
22
22
|
"tslib": "^2.8.1",
|
|
23
|
-
"usb": "^2.
|
|
23
|
+
"usb": "^2.17.0"
|
|
24
24
|
},
|
|
25
25
|
"devDependencies": {
|
|
26
26
|
"electron": "^39.2.5"
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "esp32tool",
|
|
3
|
-
"version": "1.6.
|
|
3
|
+
"version": "1.6.4",
|
|
4
4
|
"type": "module",
|
|
5
5
|
"description": "Flash & Read ESP devices using WebSerial, Electron, and also Android mobile via WebUSB",
|
|
6
6
|
"main": "electron/main.cjs",
|
|
@@ -17,7 +17,7 @@
|
|
|
17
17
|
"author": "Johann Obermeier",
|
|
18
18
|
"license": "MIT",
|
|
19
19
|
"engines": {
|
|
20
|
-
"node": ">=
|
|
20
|
+
"node": ">=25.4.0"
|
|
21
21
|
},
|
|
22
22
|
"scripts": {
|
|
23
23
|
"prebuild": "node -e \"const fs=require('fs'); fs.rmSync('dist',{recursive:true,force:true}); fs.rmSync('js/modules',{recursive:true,force:true}); fs.mkdirSync('js/modules',{recursive:true});\"",
|
|
@@ -48,28 +48,28 @@
|
|
|
48
48
|
"@electron-forge/maker-squirrel": "^7.11.1",
|
|
49
49
|
"@electron-forge/maker-zip": "^7.11.1",
|
|
50
50
|
"@electron-forge/plugin-auto-unpack-natives": "^7.11.1",
|
|
51
|
-
"@electron/fuses": "^2.
|
|
51
|
+
"@electron/fuses": "^2.1.1",
|
|
52
52
|
"@eslint/js": "^9.39.3",
|
|
53
53
|
"@rollup/plugin-json": "^6.1.0",
|
|
54
54
|
"@rollup/plugin-node-resolve": "^16.0.0",
|
|
55
|
-
"@rollup/plugin-terser": "^0.
|
|
55
|
+
"@rollup/plugin-terser": "^1.0.0",
|
|
56
56
|
"@rollup/plugin-typescript": "^12.3.0",
|
|
57
|
-
"@types/node": "^25.
|
|
57
|
+
"@types/node": "^25.4.0",
|
|
58
58
|
"@types/pako": "^2.0.4",
|
|
59
59
|
"@types/serialport": "^10.2.0",
|
|
60
60
|
"@types/w3c-web-serial": "^1.0.7",
|
|
61
61
|
"archiver": "^7.0.1",
|
|
62
|
-
"electron": "^
|
|
62
|
+
"electron": "^41.1.0",
|
|
63
63
|
"electron-squirrel-startup": "^1.0.1",
|
|
64
64
|
"eslint": "^10.0.2",
|
|
65
65
|
"eslint-config-prettier": "^10.1.8",
|
|
66
66
|
"eslint-plugin-prettier": "^5.5.5",
|
|
67
67
|
"npm-run-all": "^4.1.5",
|
|
68
68
|
"prettier": "^3.8.1",
|
|
69
|
-
"rollup": "^4.
|
|
70
|
-
"serve": "^14.2.
|
|
71
|
-
"typescript": "^5.
|
|
72
|
-
"typescript-eslint": "^8.
|
|
69
|
+
"rollup": "^4.60.1",
|
|
70
|
+
"serve": "^14.2.6",
|
|
71
|
+
"typescript": "^5.9.3",
|
|
72
|
+
"typescript-eslint": "^8.57.2"
|
|
73
73
|
},
|
|
74
74
|
"dependencies": {
|
|
75
75
|
"pako": "^2.1.0",
|
|
@@ -83,6 +83,10 @@
|
|
|
83
83
|
"serve": {
|
|
84
84
|
"ajv": "^8.18.0"
|
|
85
85
|
},
|
|
86
|
-
"@electron/asar": "^4.0.1"
|
|
86
|
+
"@electron/asar": "^4.0.1",
|
|
87
|
+
"serialize-javascript": "^7.0.3",
|
|
88
|
+
"@tootallnate/once": "^3.0.1",
|
|
89
|
+
"http-proxy-agent": "^7.0.2",
|
|
90
|
+
"make-fetch-happen": "^13.0.1"
|
|
87
91
|
}
|
|
88
92
|
}
|
package/screenshots/desktop.png
CHANGED
|
Binary file
|
package/screenshots/mobile.png
CHANGED
|
Binary file
|
package/src/cli.ts
CHANGED
|
@@ -399,8 +399,19 @@ async function cmdEraseFlash(esploader: ESPLoader) {
|
|
|
399
399
|
// Use stub for erasing
|
|
400
400
|
const stub = await esploader.runStub();
|
|
401
401
|
|
|
402
|
-
//
|
|
403
|
-
|
|
402
|
+
// Show animated progress while erasing
|
|
403
|
+
const frames = ["|", "/", "-", "\\"];
|
|
404
|
+
let frameIdx = 0;
|
|
405
|
+
const spinner = setInterval(() => {
|
|
406
|
+
process.stdout.write(`\rErasing... ${frames[frameIdx++ % frames.length]}`);
|
|
407
|
+
}, 200);
|
|
408
|
+
|
|
409
|
+
try {
|
|
410
|
+
await stub.eraseFlash();
|
|
411
|
+
} finally {
|
|
412
|
+
clearInterval(spinner);
|
|
413
|
+
process.stdout.write("\r \r");
|
|
414
|
+
}
|
|
404
415
|
|
|
405
416
|
cliLogger.log("Erase complete!");
|
|
406
417
|
}
|
package/src/esp_loader.ts
CHANGED
|
@@ -4335,6 +4335,8 @@ export class ESPLoader extends EventTarget {
|
|
|
4335
4335
|
// Flush serial buffers before flash read operation
|
|
4336
4336
|
await this.flushSerialBuffers();
|
|
4337
4337
|
|
|
4338
|
+
const readStartTime = Date.now();
|
|
4339
|
+
|
|
4338
4340
|
this.logger.log(
|
|
4339
4341
|
`Reading ${size} bytes from flash at address 0x${addr.toString(16)}...`,
|
|
4340
4342
|
);
|
|
@@ -4442,6 +4444,8 @@ export class ESPLoader extends EventTarget {
|
|
|
4442
4444
|
maxInFlight,
|
|
4443
4445
|
);
|
|
4444
4446
|
|
|
4447
|
+
const chunkStartTime = Date.now();
|
|
4448
|
+
|
|
4445
4449
|
const [res] = await this.checkCommand(ESP_READ_FLASH, pkt);
|
|
4446
4450
|
|
|
4447
4451
|
if (res != 0) {
|
|
@@ -4520,6 +4524,16 @@ export class ESPLoader extends EventTarget {
|
|
|
4520
4524
|
|
|
4521
4525
|
chunkSuccess = true;
|
|
4522
4526
|
|
|
4527
|
+
const chunkDuration = Date.now() - chunkStartTime;
|
|
4528
|
+
const speedKBs = (
|
|
4529
|
+
resp.length /
|
|
4530
|
+
1024 /
|
|
4531
|
+
(chunkDuration / 1000)
|
|
4532
|
+
).toFixed(1);
|
|
4533
|
+
this.logger.debug(
|
|
4534
|
+
`Chunk read took ${chunkDuration} ms (${resp.length} bytes, ${speedKBs} KB/s)`,
|
|
4535
|
+
);
|
|
4536
|
+
|
|
4523
4537
|
// ADAPTIVE SPEED ADJUSTMENT: Only for CDC devices
|
|
4524
4538
|
// Non-CDC devices (CH340, CP2102) stay at fixed blockSize=31, maxInFlight=31
|
|
4525
4539
|
if (this.isWebUSB() && this._isCDCDevice && retryCount === 0) {
|
|
@@ -4666,6 +4680,16 @@ export class ESPLoader extends EventTarget {
|
|
|
4666
4680
|
);
|
|
4667
4681
|
}
|
|
4668
4682
|
|
|
4683
|
+
const totalDuration = Date.now() - readStartTime;
|
|
4684
|
+
const totalSpeedKBs = (
|
|
4685
|
+
allData.length /
|
|
4686
|
+
1024 /
|
|
4687
|
+
(totalDuration / 1000)
|
|
4688
|
+
).toFixed(1);
|
|
4689
|
+
this.logger.log(
|
|
4690
|
+
`Read complete: ${allData.length} bytes in ${(totalDuration / 1000).toFixed(1)} s (${totalSpeedKBs} KB/s)`,
|
|
4691
|
+
);
|
|
4692
|
+
|
|
4669
4693
|
return allData;
|
|
4670
4694
|
}
|
|
4671
4695
|
}
|
package/sw.js
CHANGED