Skip to content

Commit 5633bfa

Browse files
committedApr 5, 2023
Avoid resetting serial terminal when possible.
Follow up to ca1f325 This aims to avoid EVENT_RESET when its due to the workaround we have in place that disconnects background tabs.
1 parent 1889831 commit 5633bfa

File tree

4 files changed

+68
-37
lines changed

4 files changed

+68
-37
lines changed
 

‎src/device/device.ts

+16-1
Original file line numberDiff line numberDiff line change
@@ -129,8 +129,23 @@ export interface FlashDataSource {
129129
files(): Promise<Record<string, Uint8Array>>;
130130
}
131131

132+
export const enum SerialOption {
133+
/**
134+
* Don't read serial data.
135+
*/
136+
None,
137+
/**
138+
* Emit a reset to clear any listeners, then read serial data.
139+
*/
140+
Reset,
141+
/**
142+
* Read serial data. No reset is emitted.
143+
*/
144+
NoReset,
145+
}
146+
132147
export interface ConnectOptions {
133-
serial?: boolean;
148+
serial: SerialOption;
134149
}
135150

136151
export interface DeviceConnection extends EventEmitter {

‎src/device/webusb.ts

+20-10
Original file line numberDiff line numberDiff line change
@@ -23,6 +23,7 @@ import {
2323
FlashDataSource,
2424
HexGenerationError,
2525
MicrobitWebUSBConnectionOptions,
26+
SerialOption,
2627
WebUSBError,
2728
} from "./device";
2829

@@ -78,7 +79,11 @@ export class MicrobitWebUSBConnection
7879
this.visibilityReconnect = false;
7980
if (!this.flashing) {
8081
this.log("Reconnecting visible tab");
81-
this.connect();
82+
this.connect({
83+
// If any other connection status change occurs then visibilitReconnect is set to false, so
84+
// it's likely the same program at this point.
85+
serial: SerialOption.NoReset,
86+
});
8287
}
8388
}
8489
} else {
@@ -113,7 +118,7 @@ export class MicrobitWebUSBConnection
113118
setTimeout(() => {
114119
if (this.status === ConnectionStatus.CONNECTED) {
115120
this.unloading = false;
116-
this.startSerialInternal();
121+
this.startSerialInternal(SerialOption.NoReset);
117122
}
118123
}, assumePageIsStayingOpenDelay);
119124
},
@@ -165,7 +170,9 @@ export class MicrobitWebUSBConnection
165170
}
166171
}
167172

168-
async connect(options: ConnectOptions = {}): Promise<ConnectionStatus> {
173+
async connect(
174+
options: ConnectOptions = { serial: SerialOption.Reset }
175+
): Promise<ConnectionStatus> {
169176
return this.withEnrichedErrors(async () => {
170177
await this.connectInternal(options);
171178
return this.status;
@@ -217,7 +224,7 @@ export class MicrobitWebUSBConnection
217224
await this.stopSerialInternal();
218225
this.log("Reconnecting before flash");
219226
await this.connectInternal({
220-
serial: false,
227+
serial: SerialOption.None,
221228
});
222229
if (!this.connection) {
223230
throw new Error("Must be connected now");
@@ -249,13 +256,13 @@ export class MicrobitWebUSBConnection
249256
this.log("Reinstating serial after flash");
250257
if (this.connection.daplink) {
251258
await this.connection.daplink.connect();
252-
await this.startSerialInternal();
259+
await this.startSerialInternal(SerialOption.Reset);
253260
}
254261
}
255262
}
256263
}
257264

258-
private async startSerialInternal() {
265+
private async startSerialInternal(option: SerialOption) {
259266
if (!this.connection) {
260267
// As connecting then starting serial are async we could disconnect between them,
261268
// so handle this gracefully.
@@ -264,6 +271,12 @@ export class MicrobitWebUSBConnection
264271
if (this.serialReadInProgress) {
265272
await this.stopSerialInternal();
266273
}
274+
if (option === SerialOption.None || option === SerialOption.Reset) {
275+
this.emit(EVENT_SERIAL_RESET, {});
276+
}
277+
if (option === SerialOption.None) {
278+
return;
279+
}
267280
// This is async but won't return until we stop serial so we error handle with an event.
268281
this.serialReadInProgress = this.connection
269282
.startSerial(this.serialListener)
@@ -278,7 +291,6 @@ export class MicrobitWebUSBConnection
278291
this.connection.stopSerial(this.serialListener);
279292
await this.serialReadInProgress;
280293
this.serialReadInProgress = undefined;
281-
this.emit(EVENT_SERIAL_RESET, {});
282294
}
283295
}
284296

@@ -384,9 +396,7 @@ export class MicrobitWebUSBConnection
384396
this.connection = new DAPWrapper(device, this.logging);
385397
}
386398
await withTimeout(this.connection.reconnectAsync(), 10_000);
387-
if (options.serial === undefined || options.serial) {
388-
this.startSerialInternal();
389-
}
399+
this.startSerialInternal(options.serial);
390400
this.setStatus(ConnectionStatus.CONNECTED);
391401
}
392402

‎src/project/project-actions.tsx

+7-1
Original file line numberDiff line numberDiff line change
@@ -24,6 +24,7 @@ import {
2424
DeviceConnection,
2525
EVENT_END_USB_SELECT,
2626
HexGenerationError,
27+
SerialOption,
2728
WebUSBError,
2829
WebUSBErrorCode,
2930
} from "../device/device";
@@ -131,7 +132,12 @@ export class ProjectActions {
131132
} else {
132133
if (await this.showConnectHelp(forceConnectHelp, finalFocusRef)) {
133134
return this.connectInternal(
134-
{ serial: userAction !== ConnectionAction.FLASH },
135+
{
136+
serial:
137+
userAction === ConnectionAction.FLASH
138+
? SerialOption.None
139+
: SerialOption.Reset,
140+
},
135141
userAction,
136142
finalFocusRef
137143
);

‎src/serial/SerialArea.tsx

+25-25
Original file line numberDiff line numberDiff line change
@@ -53,31 +53,31 @@ const SerialArea = ({
5353
position="relative"
5454
overflow="hidden"
5555
>
56-
{!connected ? null : (
57-
<Box
58-
alignItems="stretch"
59-
backgroundColor={backgroundColorTerm}
60-
height="100%"
61-
>
62-
<SerialBar
63-
height={12}
64-
compact={compact}
65-
onSizeChange={onSizeChange}
66-
showSyncStatus={showSyncStatus}
67-
expandDirection={expandDirection}
68-
hideExpandTextOnTraceback={hideExpandTextOnTraceback}
69-
showHintsAndTips={showHintsAndTips}
70-
/>
71-
<XTerm
72-
visibility={compact ? "hidden" : undefined}
73-
height={`calc(100% - ${SerialArea.compactSize}px)`}
74-
ml={1}
75-
mr={1}
76-
fontSizePt={terminalFontSizePt}
77-
tabOutRef={tabOutRef}
78-
/>
79-
</Box>
80-
)}
56+
<Box
57+
// Need to render this when not connected as we need it to maintain scrollback across disconnect/reconnect in some cases.
58+
display={connected ? undefined : "none"}
59+
alignItems="stretch"
60+
backgroundColor={backgroundColorTerm}
61+
height="100%"
62+
>
63+
<SerialBar
64+
height={12}
65+
compact={compact}
66+
onSizeChange={onSizeChange}
67+
showSyncStatus={showSyncStatus}
68+
expandDirection={expandDirection}
69+
hideExpandTextOnTraceback={hideExpandTextOnTraceback}
70+
showHintsAndTips={showHintsAndTips}
71+
/>
72+
<XTerm
73+
visibility={compact ? "hidden" : undefined}
74+
height={`calc(100% - ${SerialArea.compactSize}px)`}
75+
ml={1}
76+
mr={1}
77+
fontSizePt={terminalFontSizePt}
78+
tabOutRef={tabOutRef}
79+
/>
80+
</Box>
8181
</Flex>
8282
</TerminalContext>
8383
);

0 commit comments

Comments
 (0)
Failed to load comments.