diff --git a/legacy/emulator/emulator.h b/legacy/emulator/emulator.h index caa9ec140..bda59207c 100644 --- a/legacy/emulator/emulator.h +++ b/legacy/emulator/emulator.h @@ -30,7 +30,8 @@ void emulatorPoll(void); void emulatorRandom(void *buffer, size_t size); void emulatorSocketInit(void); -size_t emulatorSocketRead(int *iface, void *buffer, size_t size); +size_t emulatorSocketRead(int *iface, void *buffer, size_t size, + int timeout_ms); size_t emulatorSocketWrite(int iface, const void *buffer, size_t size); #endif diff --git a/legacy/emulator/udp.c b/legacy/emulator/udp.c index 2c60be6a2..e74ef0ee8 100644 --- a/legacy/emulator/udp.c +++ b/legacy/emulator/udp.c @@ -19,6 +19,7 @@ #include #include +#include #include #include #include @@ -35,6 +36,8 @@ struct usb_socket { static struct usb_socket usb_main; static struct usb_socket usb_debug; +static struct pollfd usb_fds[2]; + static int socket_setup(int port) { int fd = socket(AF_INET, SOCK_DGRAM, IPPROTO_UDP); if (fd < 0) { @@ -96,23 +99,26 @@ static size_t socket_read(struct usb_socket *sock, void *buffer, size_t size) { void emulatorSocketInit(void) { usb_main.fd = socket_setup(TREZOR_UDP_PORT); usb_main.fromlen = 0; + usb_fds[0].fd = usb_main.fd; + usb_fds[0].events = POLLIN; + usb_debug.fd = socket_setup(TREZOR_UDP_PORT + 1); usb_debug.fromlen = 0; + usb_fds[1].fd = usb_debug.fd; + usb_fds[1].events = POLLIN; } -size_t emulatorSocketRead(int *iface, void *buffer, size_t size) { - size_t n = socket_read(&usb_main, buffer, size); - if (n > 0) { - *iface = 0; - return n; - } - - n = socket_read(&usb_debug, buffer, size); - if (n > 0) { - *iface = 1; - return n; +size_t emulatorSocketRead(int *iface, void *buffer, size_t size, + int timeout_ms) { + if (poll(usb_fds, 2, timeout_ms) > 0) { + if (usb_fds[0].revents & POLLIN) { + *iface = 0; + return socket_read(&usb_main, buffer, size); + } else if (usb_fds[1].revents & POLLIN) { + *iface = 1; + return socket_read(&usb_debug, buffer, size); + } } - return 0; } diff --git a/legacy/firmware/.changelog.d/1743.changed b/legacy/firmware/.changelog.d/1743.changed new file mode 100644 index 000000000..fbda3b491 --- /dev/null +++ b/legacy/firmware/.changelog.d/1743.changed @@ -0,0 +1 @@ +Emulator properly waits for IO without busy loop diff --git a/legacy/firmware/trezor.c b/legacy/firmware/trezor.c index 278a36f9d..02ecfbd17 100644 --- a/legacy/firmware/trezor.c +++ b/legacy/firmware/trezor.c @@ -157,7 +157,11 @@ int main(void) { layoutHome(); usbInit(); for (;;) { +#if EMULATOR + usbSleep(10); +#else usbPoll(); +#endif check_lock_screen(); } diff --git a/legacy/firmware/udp.c b/legacy/firmware/udp.c index 7d0a71d2e..4a8918f37 100644 --- a/legacy/firmware/udp.c +++ b/legacy/firmware/udp.c @@ -35,43 +35,38 @@ void usbInit(void) { emulatorSocketInit(); } #define _ISDBG ('n') #endif -void usbPoll(void) { +void usbSleep(uint32_t millis) { emulatorPoll(); static uint8_t buffer[USB_PACKET_SIZE]; int iface = 0; - if (emulatorSocketRead(&iface, buffer, sizeof(buffer)) > 0) { + if (emulatorSocketRead(&iface, buffer, sizeof(buffer), millis) > 0) { if (!tiny) { - msg_read_common(_ISDBG, buffer, sizeof(buffer)); + do { + msg_read_common(_ISDBG, buffer, sizeof(buffer)); + } while (emulatorSocketRead(&iface, buffer, sizeof(buffer), 0) > 0); } else { msg_read_tiny(buffer, sizeof(buffer)); } } - const uint8_t *data = msg_out_data(); - if (data != NULL) { + const uint8_t *data; + while ((data = msg_out_data()) != NULL) { emulatorSocketWrite(0, data, USB_PACKET_SIZE); } #if DEBUG_LINK - data = msg_debug_out_data(); - if (data != NULL) { + while ((data = msg_debug_out_data()) != NULL) { emulatorSocketWrite(1, data, USB_PACKET_SIZE); } #endif } +void usbPoll(void) { usbSleep(0); } + char usbTiny(char set) { char old = tiny; tiny = set; return old; } - -void usbSleep(uint32_t millis) { - uint32_t start = timer_ms(); - - while ((timer_ms() - start) < millis) { - usbPoll(); - } -}