From b30c3a429f63bfa83079d2af48378cd0dbc0bdb8 Mon Sep 17 00:00:00 2001 From: Romain Vimont Date: Wed, 17 Nov 2021 21:58:36 +0100 Subject: [PATCH] Always retrieve device serial This allows to execute all adb commands with the specific -s parameter, even if it is not provided by the user. In practice, calling adb without -s works if there is exactly one device connected. But some adb commands (for example "adb push" on drag & drop) could be executed after another device is connected, so the actual device serial must be known. --- app/src/scrcpy.c | 19 ++++--------------- app/src/server.c | 24 ++++++++++++++++++++++++ 2 files changed, 28 insertions(+), 15 deletions(-) diff --git a/app/src/scrcpy.c b/app/src/scrcpy.c index 9643b04e..40bf72a8 100644 --- a/app/src/scrcpy.c +++ b/app/src/scrcpy.c @@ -394,8 +394,11 @@ scrcpy(struct scrcpy_options *options) { // It is necessarily initialized here, since the device is connected struct sc_server_info *info = &s->server.info; + const char *serial = s->server.params.serial; + assert(serial); + if (options->display && options->control) { - if (!file_handler_init(&s->file_handler, options->serial, + if (!file_handler_init(&s->file_handler, serial, options->push_target)) { goto end; } @@ -516,21 +519,7 @@ scrcpy(struct scrcpy_options *options) { #ifdef HAVE_AOA_HID bool aoa_hid_ok = false; - char *serialno = NULL; - - const char *serial = options->serial; - if (!serial) { - serialno = adb_get_serialno(); - if (!serialno) { - LOGE("Could not get device serial"); - goto aoa_hid_end; - } - serial = serialno; - LOGI("Device serial: %s", serial); - } - bool ok = sc_aoa_init(&s->aoa, serial); - free(serialno); if (!ok) { goto aoa_hid_end; } diff --git a/app/src/server.c b/app/src/server.c index 82a6af40..56ba6b68 100644 --- a/app/src/server.c +++ b/app/src/server.c @@ -422,12 +422,36 @@ sc_server_on_terminated(void *userdata) { LOGD("Server terminated"); } +static bool +sc_server_fill_serial(struct sc_server *server) { + // Retrieve the actual device immediately if not provided, so that all + // future adb commands are executed for this specific device, even if other + // devices are connected afterwards (without "more than one + // device/emulator" error) + if (!server->params.serial) { + // The serial is owned by sc_server_params, and will be freed on destroy + server->params.serial = adb_get_serialno(); + if (!server->params.serial) { + LOGE("Could not get device serial"); + return false; + } + } + + return true; +} + static int run_server(void *data) { struct sc_server *server = data; + if (!sc_server_fill_serial(server)) { + goto error_connection_failed; + } + const struct sc_server_params *params = &server->params; + LOGD("Device serial: %s", params->serial); + bool ok = push_server(&server->intr, params->serial); if (!ok) { goto error_connection_failed;