Skip to content

Commit b826a0e

Browse files
committed
firmware/ev3: allow buggy replies from EV3 bootloader
Add a hack to not fail if the EV3 bootloader sends an echo of the request instead of the expected response. There is a known compatibility issue with the EV3 bootloader USB and, e.g. Windows with USB 3.0 ports. This apparently causes a race condition where commands that don't take long to process before sending a response will have the request echoed back instead of receiving the actual response. If this happens, we can ignore it and assume the command was successful. It just won't work, e.g. for the version command since that has a payload in the response.
1 parent d19ded5 commit b826a0e

1 file changed

Lines changed: 24 additions & 7 deletions

File tree

src/firmware/sagas.ts

Lines changed: 24 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -1113,16 +1113,33 @@ function* handleFlashEV3(action: ReturnType<typeof firmwareFlashEV3>): Generator
11131113
continue; // ignore empty reports
11141114
}
11151115

1116-
const length = event.data.getInt16(0, true);
1116+
let length = event.data.getInt16(0, true);
11171117
const replyNumber = event.data.getInt16(2, true);
1118-
const messageType = event.data.getUint8(4);
1118+
let messageType = event.data.getUint8(4);
11191119
const replyCommand = event.data.getUint8(5);
1120-
const status = event.data.getUint8(6);
1121-
const payload = event.data.buffer.slice(7, 7 + length + 2);
1120+
let status = event.data.getUint8(6);
1121+
let payload = event.data.buffer.slice(7, 7 + length + 2);
1122+
1123+
if (messageType === 0x01) {
1124+
// HACK: This works around a strange bug that can be triggered
1125+
// e.g. by USB 3.0 on Windows. Sometimes the EV3 bootloader will
1126+
// send the request back instead of the reply. In this case,
1127+
// fake the reply to avoid protocol errors. This seems to work
1128+
// as long as we aren't sending commands that have a reply
1129+
// with a payload (like reading version or checksum)
1130+
1131+
console.warn(
1132+
`Bad EV3 reply: length=${length}, replyNumber=${replyNumber}, messageType=${messageType}, replyCommand=${replyCommand}, status=${status}`,
1133+
);
1134+
length = 5;
1135+
messageType = 0x03;
1136+
status = 0x00;
1137+
payload = new ArrayBuffer(0);
11221138

1123-
console.debug(
1124-
`EV3 reply: length=${length}, replyNumber=${replyNumber}, messageType=${messageType}, replyCommand=${replyCommand}, status=${status}, payload=${payload}`,
1125-
);
1139+
console.info(
1140+
`Fixed EV3 reply: length=${length}, replyNumber=${replyNumber}, messageType=${messageType}, replyCommand=${replyCommand}, status=${status}`,
1141+
);
1142+
}
11261143

11271144
yield* put(
11281145
firmwareDidReceiveEV3Reply(

0 commit comments

Comments
 (0)