commandline.cpp revision 56e6813e2701ee4a775e5e098801cbf16dc9a3d1
1/*
2 * Copyright (C) 2007 The Android Open Source Project
3 *
4 * Licensed under the Apache License, Version 2.0 (the "License");
5 * you may not use this file except in compliance with the License.
6 * You may obtain a copy of the License at
7 *
8 *      http://www.apache.org/licenses/LICENSE-2.0
9 *
10 * Unless required by applicable law or agreed to in writing, software
11 * distributed under the License is distributed on an "AS IS" BASIS,
12 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13 * See the License for the specific language governing permissions and
14 * limitations under the License.
15 */
16
17#define TRACE_TAG ADB
18
19#include "sysdeps.h"
20
21#include <assert.h>
22#include <ctype.h>
23#include <errno.h>
24#include <inttypes.h>
25#include <limits.h>
26#include <stdarg.h>
27#include <stdint.h>
28#include <stdio.h>
29#include <stdlib.h>
30#include <string.h>
31#include <sys/stat.h>
32#include <sys/types.h>
33
34#include <memory>
35#include <string>
36#include <vector>
37
38#include <base/logging.h>
39#include <base/stringprintf.h>
40#include <base/strings.h>
41
42#if !defined(_WIN32)
43#include <signal.h>
44#include <sys/ioctl.h>
45#include <termios.h>
46#include <unistd.h>
47#endif
48
49#include "adb.h"
50#include "adb_auth.h"
51#include "adb_client.h"
52#include "adb_io.h"
53#include "adb_utils.h"
54#include "file_sync_service.h"
55#include "services.h"
56#include "shell_service.h"
57#include "transport.h"
58
59static int install_app(TransportType t, const char* serial, int argc, const char** argv);
60static int install_multiple_app(TransportType t, const char* serial, int argc, const char** argv);
61static int uninstall_app(TransportType t, const char* serial, int argc, const char** argv);
62static int install_app_legacy(TransportType t, const char* serial, int argc, const char** argv);
63static int uninstall_app_legacy(TransportType t, const char* serial, int argc, const char** argv);
64
65static auto& gProductOutPath = *new std::string();
66extern int gListenAll;
67
68static std::string product_file(const char *extra) {
69    if (gProductOutPath.empty()) {
70        fprintf(stderr, "adb: Product directory not specified; "
71                "use -p or define ANDROID_PRODUCT_OUT\n");
72        exit(1);
73    }
74
75    return android::base::StringPrintf("%s%s%s",
76                                       gProductOutPath.c_str(), OS_PATH_SEPARATOR_STR, extra);
77}
78
79static void help() {
80    fprintf(stderr, "%s\n", adb_version().c_str());
81    fprintf(stderr,
82        " -a                            - directs adb to listen on all interfaces for a connection\n"
83        " -d                            - directs command to the only connected USB device\n"
84        "                                 returns an error if more than one USB device is present.\n"
85        " -e                            - directs command to the only running emulator.\n"
86        "                                 returns an error if more than one emulator is running.\n"
87        " -s <specific device>          - directs command to the device or emulator with the given\n"
88        "                                 serial number or qualifier. Overrides ANDROID_SERIAL\n"
89        "                                 environment variable.\n"
90        " -p <product name or path>     - simple product name like 'sooner', or\n"
91        "                                 a relative/absolute path to a product\n"
92        "                                 out directory like 'out/target/product/sooner'.\n"
93        "                                 If -p is not specified, the ANDROID_PRODUCT_OUT\n"
94        "                                 environment variable is used, which must\n"
95        "                                 be an absolute path.\n"
96        " -H                            - Name of adb server host (default: localhost)\n"
97        " -P                            - Port of adb server (default: 5037)\n"
98        " devices [-l]                  - list all connected devices\n"
99        "                                 ('-l' will also list device qualifiers)\n"
100        " connect <host>[:<port>]       - connect to a device via TCP/IP\n"
101        "                                 Port 5555 is used by default if no port number is specified.\n"
102        " disconnect [<host>[:<port>]]  - disconnect from a TCP/IP device.\n"
103        "                                 Port 5555 is used by default if no port number is specified.\n"
104        "                                 Using this command with no additional arguments\n"
105        "                                 will disconnect from all connected TCP/IP devices.\n"
106        "\n"
107        "device commands:\n"
108        "  adb push <local>... <remote>\n"
109        "                               - copy files/dirs to device\n"
110        "  adb pull [-a] <remote>... <local>\n"
111        "                               - copy files/dirs from device\n"
112        "                                 (-a preserves file timestamp and mode)\n"
113        "  adb sync [ <directory> ]     - copy host->device only if changed\n"
114        "                                 (-l means list but don't copy)\n"
115        "  adb shell [-e escape] [-Tt] [-x] [command]\n"
116        "                               - run remote shell command (interactive shell if no command given)\n"
117        "                                 (-e: choose escape character, or \"none\"; default '~')\n"
118        "                                 (-T: disable PTY allocation)\n"
119        "                                 (-t: force PTY allocation)\n"
120        "                                 (-x: disable remote exit codes and stdout/stderr separation)\n"
121        "  adb emu <command>            - run emulator console command\n"
122        "  adb logcat [ <filter-spec> ] - View device log\n"
123        "  adb forward --list           - list all forward socket connections.\n"
124        "                                 the format is a list of lines with the following format:\n"
125        "                                    <serial> \" \" <local> \" \" <remote> \"\\n\"\n"
126        "  adb forward <local> <remote> - forward socket connections\n"
127        "                                 forward specs are one of: \n"
128        "                                   tcp:<port>\n"
129        "                                   localabstract:<unix domain socket name>\n"
130        "                                   localreserved:<unix domain socket name>\n"
131        "                                   localfilesystem:<unix domain socket name>\n"
132        "                                   dev:<character device name>\n"
133        "                                   jdwp:<process pid> (remote only)\n"
134        "  adb forward --no-rebind <local> <remote>\n"
135        "                               - same as 'adb forward <local> <remote>' but fails\n"
136        "                                 if <local> is already forwarded\n"
137        "  adb forward --remove <local> - remove a specific forward socket connection\n"
138        "  adb forward --remove-all     - remove all forward socket connections\n"
139        "  adb reverse --list           - list all reverse socket connections from device\n"
140        "  adb reverse <remote> <local> - reverse socket connections\n"
141        "                                 reverse specs are one of:\n"
142        "                                   tcp:<port>\n"
143        "                                   localabstract:<unix domain socket name>\n"
144        "                                   localreserved:<unix domain socket name>\n"
145        "                                   localfilesystem:<unix domain socket name>\n"
146        "  adb reverse --no-rebind <remote> <local>\n"
147        "                               - same as 'adb reverse <remote> <local>' but fails\n"
148        "                                 if <remote> is already reversed.\n"
149        "  adb reverse --remove <remote>\n"
150        "                               - remove a specific reversed socket connection\n"
151        "  adb reverse --remove-all     - remove all reversed socket connections from device\n"
152        "  adb jdwp                     - list PIDs of processes hosting a JDWP transport\n"
153        "  adb install [-lrtsdg] <file>\n"
154        "                               - push this package file to the device and install it\n"
155        "                                 (-l: forward lock application)\n"
156        "                                 (-r: replace existing application)\n"
157        "                                 (-t: allow test packages)\n"
158        "                                 (-s: install application on sdcard)\n"
159        "                                 (-d: allow version code downgrade)\n"
160        "                                 (-g: grant all runtime permissions)\n"
161        "  adb install-multiple [-lrtsdpg] <file...>\n"
162        "                               - push this package file to the device and install it\n"
163        "                                 (-l: forward lock application)\n"
164        "                                 (-r: replace existing application)\n"
165        "                                 (-t: allow test packages)\n"
166        "                                 (-s: install application on sdcard)\n"
167        "                                 (-d: allow version code downgrade)\n"
168        "                                 (-p: partial application install)\n"
169        "                                 (-g: grant all runtime permissions)\n"
170        "  adb uninstall [-k] <package> - remove this app package from the device\n"
171        "                                 ('-k' means keep the data and cache directories)\n"
172        "  adb bugreport                - return all information from the device\n"
173        "                                 that should be included in a bug report.\n"
174        "\n"
175        "  adb backup [-f <file>] [-apk|-noapk] [-obb|-noobb] [-shared|-noshared] [-all] [-system|-nosystem] [<packages...>]\n"
176        "                               - write an archive of the device's data to <file>.\n"
177        "                                 If no -f option is supplied then the data is written\n"
178        "                                 to \"backup.ab\" in the current directory.\n"
179        "                                 (-apk|-noapk enable/disable backup of the .apks themselves\n"
180        "                                    in the archive; the default is noapk.)\n"
181        "                                 (-obb|-noobb enable/disable backup of any installed apk expansion\n"
182        "                                    (aka .obb) files associated with each application; the default\n"
183        "                                    is noobb.)\n"
184        "                                 (-shared|-noshared enable/disable backup of the device's\n"
185        "                                    shared storage / SD card contents; the default is noshared.)\n"
186        "                                 (-all means to back up all installed applications)\n"
187        "                                 (-system|-nosystem toggles whether -all automatically includes\n"
188        "                                    system applications; the default is to include system apps)\n"
189        "                                 (<packages...> is the list of applications to be backed up.  If\n"
190        "                                    the -all or -shared flags are passed, then the package\n"
191        "                                    list is optional.  Applications explicitly given on the\n"
192        "                                    command line will be included even if -nosystem would\n"
193        "                                    ordinarily cause them to be omitted.)\n"
194        "\n"
195        "  adb restore <file>           - restore device contents from the <file> backup archive\n"
196        "\n"
197        "  adb disable-verity           - disable dm-verity checking on USERDEBUG builds\n"
198        "  adb enable-verity            - re-enable dm-verity checking on USERDEBUG builds\n"
199        "  adb keygen <file>            - generate adb public/private key. The private key is stored in <file>,\n"
200        "                                 and the public key is stored in <file>.pub. Any existing files\n"
201        "                                 are overwritten.\n"
202        "  adb help                     - show this help message\n"
203        "  adb version                  - show version num\n"
204        "\n"
205        "scripting:\n"
206        "  adb wait-for-device          - block until device is online\n"
207        "  adb start-server             - ensure that there is a server running\n"
208        "  adb kill-server              - kill the server if it is running\n"
209        "  adb get-state                - prints: offline | bootloader | device\n"
210        "  adb get-serialno             - prints: <serial-number>\n"
211        "  adb get-devpath              - prints: <device-path>\n"
212        "  adb remount                  - remounts the /system, /vendor (if present) and /oem (if present) partitions on the device read-write\n"
213        "  adb reboot [bootloader|recovery]\n"
214        "                               - reboots the device, optionally into the bootloader or recovery program.\n"
215        "  adb reboot sideload          - reboots the device into the sideload mode in recovery program (adb root required).\n"
216        "  adb reboot sideload-auto-reboot\n"
217        "                               - reboots into the sideload mode, then reboots automatically after the sideload regardless of the result.\n"
218        "  adb sideload <file>          - sideloads the given package\n"
219        "  adb root                     - restarts the adbd daemon with root permissions\n"
220        "  adb unroot                   - restarts the adbd daemon without root permissions\n"
221        "  adb usb                      - restarts the adbd daemon listening on USB\n"
222        "  adb tcpip <port>             - restarts the adbd daemon listening on TCP on the specified port\n"
223        "\n"
224        "networking:\n"
225        "  adb ppp <tty> [parameters]   - Run PPP over USB.\n"
226        " Note: you should not automatically start a PPP connection.\n"
227        " <tty> refers to the tty for PPP stream. Eg. dev:/dev/omap_csmi_tty1\n"
228        " [parameters] - Eg. defaultroute debug dump local notty usepeerdns\n"
229        "\n"
230        "adb sync notes: adb sync [ <directory> ]\n"
231        "  <localdir> can be interpreted in several ways:\n"
232        "\n"
233        "  - If <directory> is not specified, /system, /vendor (if present), /oem (if present) and /data partitions will be updated.\n"
234        "\n"
235        "  - If it is \"system\", \"vendor\", \"oem\" or \"data\", only the corresponding partition\n"
236        "    is updated.\n"
237        "\n"
238        "environment variables:\n"
239        "  ADB_TRACE                    - Print debug information. A comma separated list of the following values\n"
240        "                                 1 or all, adb, sockets, packets, rwx, usb, sync, sysdeps, transport, jdwp\n"
241        "  ANDROID_SERIAL               - The serial number to connect to. -s takes priority over this if given.\n"
242        "  ANDROID_LOG_TAGS             - When used with the logcat option, only these debug tags are printed.\n"
243        );
244}
245
246static int usage() {
247    help();
248    return 1;
249}
250
251#if defined(_WIN32)
252
253// Implemented in sysdeps_win32.cpp.
254void stdin_raw_init();
255void stdin_raw_restore();
256
257#else
258static termios g_saved_terminal_state;
259
260static void stdin_raw_init() {
261    if (tcgetattr(STDIN_FILENO, &g_saved_terminal_state)) return;
262
263    termios tio;
264    if (tcgetattr(STDIN_FILENO, &tio)) return;
265
266    cfmakeraw(&tio);
267
268    // No timeout but request at least one character per read.
269    tio.c_cc[VTIME] = 0;
270    tio.c_cc[VMIN] = 1;
271
272    tcsetattr(STDIN_FILENO, TCSAFLUSH, &tio);
273}
274
275static void stdin_raw_restore() {
276    tcsetattr(STDIN_FILENO, TCSAFLUSH, &g_saved_terminal_state);
277}
278#endif
279
280// Reads from |fd| and prints received data. If |use_shell_protocol| is true
281// this expects that incoming data will use the shell protocol, in which case
282// stdout/stderr are routed independently and the remote exit code will be
283// returned.
284static int read_and_dump(int fd, bool use_shell_protocol=false) {
285    int exit_code = 0;
286    std::unique_ptr<ShellProtocol> protocol;
287    int length = 0;
288    FILE* outfile = stdout;
289
290    char raw_buffer[BUFSIZ];
291    char* buffer_ptr = raw_buffer;
292    if (use_shell_protocol) {
293        protocol.reset(new ShellProtocol(fd));
294        if (!protocol) {
295            LOG(ERROR) << "failed to allocate memory for ShellProtocol object";
296            return 1;
297        }
298        buffer_ptr = protocol->data();
299    }
300
301    while (fd >= 0) {
302        if (use_shell_protocol) {
303            if (!protocol->Read()) {
304                break;
305            }
306            switch (protocol->id()) {
307                case ShellProtocol::kIdStdout:
308                    outfile = stdout;
309                    break;
310                case ShellProtocol::kIdStderr:
311                    outfile = stderr;
312                    break;
313                case ShellProtocol::kIdExit:
314                    exit_code = protocol->data()[0];
315                    continue;
316                default:
317                    continue;
318            }
319            length = protocol->data_length();
320        } else {
321            D("read_and_dump(): pre adb_read(fd=%d)", fd);
322            length = adb_read(fd, raw_buffer, sizeof(raw_buffer));
323            D("read_and_dump(): post adb_read(fd=%d): length=%d", fd, length);
324            if (length <= 0) {
325                break;
326            }
327        }
328
329        fwrite(buffer_ptr, 1, length, outfile);
330        fflush(outfile);
331    }
332
333    return exit_code;
334}
335
336static void read_status_line(int fd, char* buf, size_t count)
337{
338    count--;
339    while (count > 0) {
340        int len = adb_read(fd, buf, count);
341        if (len <= 0) {
342            break;
343        }
344
345        buf += len;
346        count -= len;
347    }
348    *buf = '\0';
349}
350
351static void copy_to_file(int inFd, int outFd) {
352    const size_t BUFSIZE = 32 * 1024;
353    char* buf = (char*) malloc(BUFSIZE);
354    if (buf == nullptr) fatal("couldn't allocate buffer for copy_to_file");
355    int len;
356    long total = 0;
357#ifdef _WIN32
358    int old_stdin_mode = -1;
359    int old_stdout_mode = -1;
360#endif
361
362    D("copy_to_file(%d -> %d)", inFd, outFd);
363
364    if (inFd == STDIN_FILENO) {
365        stdin_raw_init();
366#ifdef _WIN32
367        old_stdin_mode = _setmode(STDIN_FILENO, _O_BINARY);
368        if (old_stdin_mode == -1) {
369            fatal_errno("could not set stdin to binary");
370        }
371#endif
372    }
373
374#ifdef _WIN32
375    if (outFd == STDOUT_FILENO) {
376        old_stdout_mode = _setmode(STDOUT_FILENO, _O_BINARY);
377        if (old_stdout_mode == -1) {
378            fatal_errno("could not set stdout to binary");
379        }
380    }
381#endif
382
383    while (true) {
384        if (inFd == STDIN_FILENO) {
385            len = unix_read(inFd, buf, BUFSIZE);
386        } else {
387            len = adb_read(inFd, buf, BUFSIZE);
388        }
389        if (len == 0) {
390            D("copy_to_file() : read 0 bytes; exiting");
391            break;
392        }
393        if (len < 0) {
394            D("copy_to_file(): read failed: %s", strerror(errno));
395            break;
396        }
397        if (outFd == STDOUT_FILENO) {
398            fwrite(buf, 1, len, stdout);
399            fflush(stdout);
400        } else {
401            adb_write(outFd, buf, len);
402        }
403        total += len;
404    }
405
406    if (inFd == STDIN_FILENO) {
407        stdin_raw_restore();
408#ifdef _WIN32
409        if (_setmode(STDIN_FILENO, old_stdin_mode) == -1) {
410            fatal_errno("could not restore stdin mode");
411        }
412#endif
413    }
414
415#ifdef _WIN32
416    if (outFd == STDOUT_FILENO) {
417        if (_setmode(STDOUT_FILENO, old_stdout_mode) == -1) {
418            fatal_errno("could not restore stdout mode");
419        }
420    }
421#endif
422
423    D("copy_to_file() finished after %lu bytes", total);
424    free(buf);
425}
426
427static std::string format_host_command(const char* command,
428                                       TransportType type, const char* serial) {
429    if (serial) {
430        return android::base::StringPrintf("host-serial:%s:%s", serial, command);
431    }
432
433    const char* prefix = "host";
434    if (type == kTransportUsb) {
435        prefix = "host-usb";
436    } else if (type == kTransportLocal) {
437        prefix = "host-local";
438    }
439    return android::base::StringPrintf("%s:%s", prefix, command);
440}
441
442// Returns the FeatureSet for the indicated transport.
443static FeatureSet GetFeatureSet(TransportType transport_type, const char* serial) {
444    std::string result, error;
445    if (adb_query(format_host_command("features", transport_type, serial), &result, &error)) {
446        return StringToFeatureSet(result);
447    }
448    return FeatureSet();
449}
450
451static void send_window_size_change(int fd, std::unique_ptr<ShellProtocol>& shell) {
452#if !defined(_WIN32)
453    // Old devices can't handle window size changes.
454    if (shell == nullptr) return;
455
456    winsize ws;
457    if (ioctl(fd, TIOCGWINSZ, &ws) == -1) return;
458
459    // Send the new window size as human-readable ASCII for debugging convenience.
460    size_t l = snprintf(shell->data(), shell->data_capacity(), "%dx%d,%dx%d",
461                        ws.ws_row, ws.ws_col, ws.ws_xpixel, ws.ws_ypixel);
462    shell->Write(ShellProtocol::kIdWindowSizeChange, l + 1);
463#endif
464}
465
466// Used to pass multiple values to the stdin read thread.
467struct StdinReadArgs {
468    int stdin_fd, write_fd;
469    bool raw_stdin;
470    std::unique_ptr<ShellProtocol> protocol;
471    char escape_char;
472};
473
474// Loops to read from stdin and push the data to the given FD.
475// The argument should be a pointer to a StdinReadArgs object. This function
476// will take ownership of the object and delete it when finished.
477static void* stdin_read_thread_loop(void* x) {
478    std::unique_ptr<StdinReadArgs> args(reinterpret_cast<StdinReadArgs*>(x));
479
480#if !defined(_WIN32)
481    // Mask SIGTTIN in case we're in a backgrounded process.
482    sigset_t sigset;
483    sigemptyset(&sigset);
484    sigaddset(&sigset, SIGTTIN);
485    pthread_sigmask(SIG_BLOCK, &sigset, nullptr);
486#endif
487
488#if !defined(_WIN32)
489    // Unblock SIGWINCH for this thread, so our read(2) below will be
490    // interrupted if the window size changes.
491    sigset_t mask;
492    sigemptyset(&mask);
493    sigaddset(&mask, SIGWINCH);
494    pthread_sigmask(SIG_UNBLOCK, &mask, nullptr);
495#endif
496
497    // Set up the initial window size.
498    send_window_size_change(args->stdin_fd, args->protocol);
499
500    char raw_buffer[BUFSIZ];
501    char* buffer_ptr = raw_buffer;
502    size_t buffer_size = sizeof(raw_buffer);
503    if (args->protocol != nullptr) {
504        buffer_ptr = args->protocol->data();
505        buffer_size = args->protocol->data_capacity();
506    }
507
508    // If we need to parse escape sequences, make life easy.
509    if (args->raw_stdin && args->escape_char != '\0') {
510        buffer_size = 1;
511    }
512
513    enum EscapeState { kMidFlow, kStartOfLine, kInEscape };
514    EscapeState state = kStartOfLine;
515
516    while (true) {
517        // Use unix_read() rather than adb_read() for stdin.
518        D("stdin_read_thread_loop(): pre unix_read(fdi=%d,...)", args->stdin_fd);
519#if !defined(_WIN32)
520#undef read
521        int r = read(args->stdin_fd, buffer_ptr, buffer_size);
522        if (r == -1 && errno == EINTR) {
523            send_window_size_change(args->stdin_fd, args->protocol);
524            continue;
525        }
526#define read ___xxx_read
527#else
528        int r = unix_read(args->stdin_fd, buffer_ptr, buffer_size);
529#endif
530        D("stdin_read_thread_loop(): post unix_read(fdi=%d,...)", args->stdin_fd);
531        if (r <= 0) {
532            // Only devices using the shell protocol know to close subprocess
533            // stdin. For older devices we want to just leave the connection
534            // open, otherwise an unpredictable amount of return data could
535            // be lost due to the FD closing before all data has been received.
536            if (args->protocol) {
537                args->protocol->Write(ShellProtocol::kIdCloseStdin, 0);
538            }
539            break;
540        }
541        // If we made stdin raw, check input for escape sequences. In
542        // this situation signals like Ctrl+C are sent remotely rather than
543        // interpreted locally so this provides an emergency out if the remote
544        // process starts ignoring the signal. SSH also does this, see the
545        // "escape characters" section on the ssh man page for more info.
546        if (args->raw_stdin && args->escape_char != '\0') {
547            char ch = buffer_ptr[0];
548            if (ch == args->escape_char) {
549                if (state == kStartOfLine) {
550                    state = kInEscape;
551                    // Swallow the escape character.
552                    continue;
553                } else {
554                    state = kMidFlow;
555                }
556            } else {
557                if (state == kInEscape) {
558                    if (ch == '.') {
559                        fprintf(stderr,"\r\n[ disconnected ]\r\n");
560                        stdin_raw_restore();
561                        exit(0);
562                    } else {
563                        // We swallowed an escape character that wasn't part of
564                        // a valid escape sequence; time to cough it up.
565                        buffer_ptr[0] = args->escape_char;
566                        buffer_ptr[1] = ch;
567                        ++r;
568                    }
569                }
570                state = (ch == '\n' || ch == '\r') ? kStartOfLine : kMidFlow;
571            }
572        }
573        if (args->protocol) {
574            if (!args->protocol->Write(ShellProtocol::kIdStdin, r)) {
575                break;
576            }
577        } else {
578            if (!WriteFdExactly(args->write_fd, buffer_ptr, r)) {
579                break;
580            }
581        }
582    }
583
584    return nullptr;
585}
586
587// Returns a shell service string with the indicated arguments and command.
588static std::string ShellServiceString(bool use_shell_protocol,
589                                      const std::string& type_arg,
590                                      const std::string& command) {
591    std::vector<std::string> args;
592    if (use_shell_protocol) {
593        args.push_back(kShellServiceArgShellProtocol);
594    }
595    if (!type_arg.empty()) {
596        args.push_back(type_arg);
597    }
598
599    // Shell service string can look like: shell[,arg1,arg2,...]:[command].
600    return android::base::StringPrintf("shell%s%s:%s",
601                                       args.empty() ? "" : ",",
602                                       android::base::Join(args, ',').c_str(),
603                                       command.c_str());
604}
605
606// Connects to a shell on the device and read/writes data.
607//
608// Note: currently this function doesn't properly clean up resources; the
609// FD connected to the adb server is never closed and the stdin read thread
610// may never exit.
611//
612// On success returns the remote exit code if |use_shell_protocol| is true,
613// 0 otherwise. On failure returns 1.
614static int RemoteShell(bool use_shell_protocol, const std::string& type_arg,
615                       char escape_char,
616                       const std::string& command) {
617    std::string service_string = ShellServiceString(use_shell_protocol,
618                                                    type_arg, command);
619
620    // Make local stdin raw if the device allocates a PTY, which happens if:
621    //   1. We are explicitly asking for a PTY shell, or
622    //   2. We don't specify shell type and are starting an interactive session.
623    bool raw_stdin = (type_arg == kShellServiceArgPty ||
624                      (type_arg.empty() && command.empty()));
625
626    std::string error;
627    int fd = adb_connect(service_string, &error);
628    if (fd < 0) {
629        fprintf(stderr,"error: %s\n", error.c_str());
630        return 1;
631    }
632
633    StdinReadArgs* args = new StdinReadArgs;
634    if (!args) {
635        LOG(ERROR) << "couldn't allocate StdinReadArgs object";
636        return 1;
637    }
638    args->stdin_fd = STDIN_FILENO;
639    args->write_fd = fd;
640    args->raw_stdin = raw_stdin;
641    args->escape_char = escape_char;
642    if (use_shell_protocol) {
643        args->protocol.reset(new ShellProtocol(args->write_fd));
644    }
645
646    if (raw_stdin) stdin_raw_init();
647
648#if !defined(_WIN32)
649    // Ensure our process is notified if the local window size changes.
650    // We use sigaction(2) to ensure that the SA_RESTART flag is not set,
651    // because the whole reason we're sending signals is to unblock the read(2)!
652    // That also means we don't need to do anything in the signal handler:
653    // the side effect of delivering the signal is all we need.
654    struct sigaction sa;
655    memset(&sa, 0, sizeof(sa));
656    sa.sa_handler = [](int) {};
657    sa.sa_flags = 0;
658    sigaction(SIGWINCH, &sa, nullptr);
659
660    // Now block SIGWINCH in this thread (the main thread) and all threads spawned
661    // from it. The stdin read thread will unblock this signal to ensure that it's
662    // the thread that receives the signal.
663    sigset_t mask;
664    sigemptyset(&mask);
665    sigaddset(&mask, SIGWINCH);
666    pthread_sigmask(SIG_BLOCK, &mask, nullptr);
667#endif
668
669    // TODO: combine read_and_dump with stdin_read_thread to make life simpler?
670    int exit_code = 1;
671    if (!adb_thread_create(stdin_read_thread_loop, args)) {
672        PLOG(ERROR) << "error starting stdin read thread";
673        delete args;
674    } else {
675        exit_code = read_and_dump(fd, use_shell_protocol);
676    }
677
678    // TODO: properly exit stdin_read_thread_loop and close |fd|.
679
680    // TODO: we should probably install signal handlers for this.
681    // TODO: can we use atexit? even on Windows?
682    if (raw_stdin) stdin_raw_restore();
683
684    return exit_code;
685}
686
687static int adb_shell(int argc, const char** argv,
688                     TransportType transport_type, const char* serial) {
689    FeatureSet features = GetFeatureSet(transport_type, serial);
690
691    bool use_shell_protocol = CanUseFeature(features, kFeatureShell2);
692    if (!use_shell_protocol) {
693        D("shell protocol not supported, using raw data transfer");
694    } else {
695        D("using shell protocol");
696    }
697
698    // Parse shell-specific command-line options.
699    // argv[0] is always "shell".
700    --argc;
701    ++argv;
702    int t_arg_count = 0;
703    char escape_char = '~';
704    while (argc) {
705        if (!strcmp(argv[0], "-e")) {
706            if (argc < 2 || !(strlen(argv[1]) == 1 || strcmp(argv[1], "none") == 0)) {
707                fprintf(stderr, "error: -e requires a single-character argument or 'none'\n");
708                return 1;
709            }
710            escape_char = (strcmp(argv[1], "none") == 0) ? 0 : argv[1][0];
711            argc -= 2;
712            argv += 2;
713        } else if (!strcmp(argv[0], "-T") || !strcmp(argv[0], "-t")) {
714            if (!CanUseFeature(features, kFeatureShell2)) {
715                fprintf(stderr, "error: target doesn't support PTY args -Tt\n");
716                return 1;
717            }
718            // Like ssh, -t arguments are cumulative so that multiple -t's
719            // are needed to force a PTY.
720            if (argv[0][1] == 't') {
721                ++t_arg_count;
722            } else {
723                t_arg_count = -1;
724            }
725            --argc;
726            ++argv;
727        } else if (!strcmp(argv[0], "-x")) {
728            use_shell_protocol = false;
729            --argc;
730            ++argv;
731        } else {
732            break;
733        }
734    }
735
736    std::string shell_type_arg;
737    if (CanUseFeature(features, kFeatureShell2)) {
738        if (t_arg_count < 0) {
739            shell_type_arg = kShellServiceArgRaw;
740        } else if (t_arg_count == 0) {
741            // If stdin isn't a TTY, default to a raw shell; this lets
742            // things like `adb shell < my_script.sh` work as expected.
743            // Otherwise leave |shell_type_arg| blank which uses PTY for
744            // interactive shells and raw for non-interactive.
745            if (!unix_isatty(STDIN_FILENO)) {
746                shell_type_arg = kShellServiceArgRaw;
747            }
748        } else if (t_arg_count == 1) {
749            // A single -t arg isn't enough to override implicit -T.
750            if (!unix_isatty(STDIN_FILENO)) {
751                fprintf(stderr,
752                        "Remote PTY will not be allocated because stdin is not a terminal.\n"
753                        "Use multiple -t options to force remote PTY allocation.\n");
754                shell_type_arg = kShellServiceArgRaw;
755            } else {
756                shell_type_arg = kShellServiceArgPty;
757            }
758        } else {
759            shell_type_arg = kShellServiceArgPty;
760        }
761    }
762
763    std::string command;
764    if (argc) {
765        // We don't escape here, just like ssh(1). http://b/20564385.
766        command = android::base::Join(std::vector<const char*>(argv, argv + argc), ' ');
767    }
768
769    return RemoteShell(use_shell_protocol, shell_type_arg, escape_char, command);
770}
771
772static int adb_download_buffer(const char *service, const char *fn, const void* data, unsigned sz,
773                               bool show_progress)
774{
775    std::string error;
776    int fd = adb_connect(android::base::StringPrintf("%s:%d", service, sz), &error);
777    if (fd < 0) {
778        fprintf(stderr,"error: %s\n", error.c_str());
779        return -1;
780    }
781
782    int opt = CHUNK_SIZE;
783    opt = adb_setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (const void *) &opt, sizeof(opt));
784
785    unsigned total = sz;
786    const uint8_t* ptr = reinterpret_cast<const uint8_t*>(data);
787
788    if (show_progress) {
789        const char* x = strrchr(service, ':');
790        if (x) service = x + 1;
791    }
792
793    while (sz > 0) {
794        unsigned xfer = (sz > CHUNK_SIZE) ? CHUNK_SIZE : sz;
795        if (!WriteFdExactly(fd, ptr, xfer)) {
796            std::string error;
797            adb_status(fd, &error);
798            fprintf(stderr,"* failed to write data '%s' *\n", error.c_str());
799            adb_close(fd);
800            return -1;
801        }
802        sz -= xfer;
803        ptr += xfer;
804        if (show_progress) {
805            printf("sending: '%s' %4d%%    \r", fn, (int)(100LL - ((100LL * sz) / (total))));
806            fflush(stdout);
807        }
808    }
809    if (show_progress) {
810        printf("\n");
811    }
812
813    if (!adb_status(fd, &error)) {
814        fprintf(stderr,"* error response '%s' *\n", error.c_str());
815        adb_close(fd);
816        return -1;
817    }
818
819    adb_close(fd);
820    return 0;
821}
822
823#define SIDELOAD_HOST_BLOCK_SIZE (CHUNK_SIZE)
824
825/*
826 * The sideload-host protocol serves the data in a file (given on the
827 * command line) to the client, using a simple protocol:
828 *
829 * - The connect message includes the total number of bytes in the
830 *   file and a block size chosen by us.
831 *
832 * - The other side sends the desired block number as eight decimal
833 *   digits (eg "00000023" for block 23).  Blocks are numbered from
834 *   zero.
835 *
836 * - We send back the data of the requested block.  The last block is
837 *   likely to be partial; when the last block is requested we only
838 *   send the part of the block that exists, it's not padded up to the
839 *   block size.
840 *
841 * - When the other side sends "DONEDONE" instead of a block number,
842 *   we hang up.
843 */
844static int adb_sideload_host(const char* fn) {
845    unsigned sz;
846    size_t xfer = 0;
847    int status;
848    int last_percent = -1;
849    int opt = SIDELOAD_HOST_BLOCK_SIZE;
850
851    printf("loading: '%s'", fn);
852    fflush(stdout);
853    uint8_t* data = reinterpret_cast<uint8_t*>(load_file(fn, &sz));
854    if (data == 0) {
855        printf("\n");
856        fprintf(stderr, "* cannot read '%s' *\n", fn);
857        return -1;
858    }
859
860    std::string service =
861            android::base::StringPrintf("sideload-host:%d:%d", sz, SIDELOAD_HOST_BLOCK_SIZE);
862    std::string error;
863    int fd = adb_connect(service, &error);
864    if (fd < 0) {
865        // Try falling back to the older sideload method.  Maybe this
866        // is an older device that doesn't support sideload-host.
867        printf("\n");
868        status = adb_download_buffer("sideload", fn, data, sz, true);
869        goto done;
870    }
871
872    opt = adb_setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (const void *) &opt, sizeof(opt));
873
874    while (true) {
875        char buf[9];
876        if (!ReadFdExactly(fd, buf, 8)) {
877            fprintf(stderr, "* failed to read command: %s\n", strerror(errno));
878            status = -1;
879            goto done;
880        }
881        buf[8] = '\0';
882
883        if (strcmp("DONEDONE", buf) == 0) {
884            status = 0;
885            break;
886        }
887
888        int block = strtol(buf, NULL, 10);
889
890        size_t offset = block * SIDELOAD_HOST_BLOCK_SIZE;
891        if (offset >= sz) {
892            fprintf(stderr, "* attempt to read block %d past end\n", block);
893            status = -1;
894            goto done;
895        }
896        uint8_t* start = data + offset;
897        size_t offset_end = offset + SIDELOAD_HOST_BLOCK_SIZE;
898        size_t to_write = SIDELOAD_HOST_BLOCK_SIZE;
899        if (offset_end > sz) {
900            to_write = sz - offset;
901        }
902
903        if(!WriteFdExactly(fd, start, to_write)) {
904            adb_status(fd, &error);
905            fprintf(stderr,"* failed to write data '%s' *\n", error.c_str());
906            status = -1;
907            goto done;
908        }
909        xfer += to_write;
910
911        // For normal OTA packages, we expect to transfer every byte
912        // twice, plus a bit of overhead (one read during
913        // verification, one read of each byte for installation, plus
914        // extra access to things like the zip central directory).
915        // This estimate of the completion becomes 100% when we've
916        // transferred ~2.13 (=100/47) times the package size.
917        int percent = (int)(xfer * 47LL / (sz ? sz : 1));
918        if (percent != last_percent) {
919            printf("\rserving: '%s'  (~%d%%)    ", fn, percent);
920            fflush(stdout);
921            last_percent = percent;
922        }
923    }
924
925    printf("\rTotal xfer: %.2fx%*s\n", (double)xfer / (sz ? sz : 1), (int)strlen(fn)+10, "");
926
927  done:
928    if (fd >= 0) adb_close(fd);
929    free(data);
930    return status;
931}
932
933/**
934 * Run ppp in "notty" mode against a resource listed as the first parameter
935 * eg:
936 *
937 * ppp dev:/dev/omap_csmi_tty0 <ppp options>
938 *
939 */
940static int ppp(int argc, const char** argv) {
941#if defined(_WIN32)
942    fprintf(stderr, "error: adb %s not implemented on Win32\n", argv[0]);
943    return -1;
944#else
945    if (argc < 2) {
946        fprintf(stderr, "usage: adb %s <adb service name> [ppp opts]\n",
947                argv[0]);
948
949        return 1;
950    }
951
952    const char* adb_service_name = argv[1];
953    std::string error;
954    int fd = adb_connect(adb_service_name, &error);
955    if (fd < 0) {
956        fprintf(stderr,"Error: Could not open adb service: %s. Error: %s\n",
957                adb_service_name, error.c_str());
958        return 1;
959    }
960
961    pid_t pid = fork();
962
963    if (pid < 0) {
964        perror("from fork()");
965        return 1;
966    } else if (pid == 0) {
967        int err;
968        int i;
969        const char **ppp_args;
970
971        // copy args
972        ppp_args = (const char **) alloca(sizeof(char *) * argc + 1);
973        ppp_args[0] = "pppd";
974        for (i = 2 ; i < argc ; i++) {
975            //argv[2] and beyond become ppp_args[1] and beyond
976            ppp_args[i - 1] = argv[i];
977        }
978        ppp_args[i-1] = NULL;
979
980        // child side
981
982        dup2(fd, STDIN_FILENO);
983        dup2(fd, STDOUT_FILENO);
984        adb_close(STDERR_FILENO);
985        adb_close(fd);
986
987        err = execvp("pppd", (char * const *)ppp_args);
988
989        if (err < 0) {
990            perror("execing pppd");
991        }
992        exit(-1);
993    } else {
994        // parent side
995
996        adb_close(fd);
997        return 0;
998    }
999#endif /* !defined(_WIN32) */
1000}
1001
1002static bool wait_for_device(const char* service, TransportType t, const char* serial) {
1003    // Was the caller vague about what they'd like us to wait for?
1004    // If so, check they weren't more specific in their choice of transport type.
1005    if (strcmp(service, "wait-for-device") == 0) {
1006        if (t == kTransportUsb) {
1007            service = "wait-for-usb";
1008        } else if (t == kTransportLocal) {
1009            service = "wait-for-local";
1010        } else {
1011            service = "wait-for-any";
1012        }
1013    }
1014
1015    std::string cmd = format_host_command(service, t, serial);
1016    return adb_command(cmd);
1017}
1018
1019// Connects to the device "shell" service with |command| and prints the
1020// resulting output.
1021static int send_shell_command(TransportType transport_type, const char* serial,
1022                              const std::string& command,
1023                              bool disable_shell_protocol) {
1024    // Only use shell protocol if it's supported and the caller doesn't want
1025    // to explicitly disable it.
1026    bool use_shell_protocol = false;
1027    if (!disable_shell_protocol) {
1028        FeatureSet features = GetFeatureSet(transport_type, serial);
1029        use_shell_protocol = CanUseFeature(features, kFeatureShell2);
1030    }
1031
1032    std::string service_string = ShellServiceString(use_shell_protocol, "",
1033                                                    command);
1034
1035    int fd;
1036    while (true) {
1037        std::string error;
1038        fd = adb_connect(service_string, &error);
1039        if (fd >= 0) {
1040            break;
1041        }
1042        fprintf(stderr,"- waiting for device -\n");
1043        adb_sleep_ms(1000);
1044        wait_for_device("wait-for-device", transport_type, serial);
1045    }
1046
1047    int exit_code = read_and_dump(fd, use_shell_protocol);
1048
1049    if (adb_close(fd) < 0) {
1050        PLOG(ERROR) << "failure closing FD " << fd;
1051    }
1052
1053    return exit_code;
1054}
1055
1056static int logcat(TransportType transport, const char* serial, int argc, const char** argv) {
1057    char* log_tags = getenv("ANDROID_LOG_TAGS");
1058    std::string quoted = escape_arg(log_tags == nullptr ? "" : log_tags);
1059
1060    std::string cmd = "export ANDROID_LOG_TAGS=\"" + quoted + "\"; exec logcat";
1061
1062    if (!strcmp(argv[0], "longcat")) {
1063        cmd += " -v long";
1064    }
1065
1066    --argc;
1067    ++argv;
1068    while (argc-- > 0) {
1069        cmd += " " + escape_arg(*argv++);
1070    }
1071
1072    // No need for shell protocol with logcat, always disable for simplicity.
1073    return send_shell_command(transport, serial, cmd, true);
1074}
1075
1076static int backup(int argc, const char** argv) {
1077    const char* filename = "backup.ab";
1078
1079    /* find, extract, and use any -f argument */
1080    for (int i = 1; i < argc; i++) {
1081        if (!strcmp("-f", argv[i])) {
1082            if (i == argc-1) {
1083                fprintf(stderr, "adb: backup -f passed with no filename.\n");
1084                return EXIT_FAILURE;
1085            }
1086            filename = argv[i+1];
1087            for (int j = i+2; j <= argc; ) {
1088                argv[i++] = argv[j++];
1089            }
1090            argc -= 2;
1091            argv[argc] = NULL;
1092        }
1093    }
1094
1095    // Bare "adb backup" or "adb backup -f filename" are not valid invocations ---
1096    // a list of packages is required.
1097    if (argc < 2) {
1098        fprintf(stderr, "adb: backup either needs a list of packages or -all/-shared.\n");
1099        return EXIT_FAILURE;
1100    }
1101
1102    adb_unlink(filename);
1103    int outFd = adb_creat(filename, 0640);
1104    if (outFd < 0) {
1105        fprintf(stderr, "adb: backup unable to create file '%s': %s\n", filename, strerror(errno));
1106        return EXIT_FAILURE;
1107    }
1108
1109    std::string cmd = "backup:";
1110    --argc;
1111    ++argv;
1112    while (argc-- > 0) {
1113        cmd += " " + escape_arg(*argv++);
1114    }
1115
1116    D("backup. filename=%s cmd=%s", filename, cmd.c_str());
1117    std::string error;
1118    int fd = adb_connect(cmd, &error);
1119    if (fd < 0) {
1120        fprintf(stderr, "adb: unable to connect for backup: %s\n", error.c_str());
1121        adb_close(outFd);
1122        return EXIT_FAILURE;
1123    }
1124
1125    printf("Now unlock your device and confirm the backup operation...\n");
1126    fflush(stdout);
1127
1128    copy_to_file(fd, outFd);
1129
1130    adb_close(fd);
1131    adb_close(outFd);
1132    return EXIT_SUCCESS;
1133}
1134
1135static int restore(int argc, const char** argv) {
1136    if (argc != 2) return usage();
1137
1138    const char* filename = argv[1];
1139    int tarFd = adb_open(filename, O_RDONLY);
1140    if (tarFd < 0) {
1141        fprintf(stderr, "adb: unable to open file %s: %s\n", filename, strerror(errno));
1142        return -1;
1143    }
1144
1145    std::string error;
1146    int fd = adb_connect("restore:", &error);
1147    if (fd < 0) {
1148        fprintf(stderr, "adb: unable to connect for restore: %s\n", error.c_str());
1149        adb_close(tarFd);
1150        return -1;
1151    }
1152
1153    printf("Now unlock your device and confirm the restore operation.\n");
1154    copy_to_file(tarFd, fd);
1155
1156    adb_close(fd);
1157    adb_close(tarFd);
1158    return 0;
1159}
1160
1161/* <hint> may be:
1162 * - A simple product name
1163 *   e.g., "sooner"
1164 * - A relative path from the CWD to the ANDROID_PRODUCT_OUT dir
1165 *   e.g., "out/target/product/sooner"
1166 * - An absolute path to the PRODUCT_OUT dir
1167 *   e.g., "/src/device/out/target/product/sooner"
1168 *
1169 * Given <hint>, try to construct an absolute path to the
1170 * ANDROID_PRODUCT_OUT dir.
1171 */
1172static std::string find_product_out_path(const std::string& hint) {
1173    if (hint.empty()) {
1174        return "";
1175    }
1176
1177    // If it's already absolute, don't bother doing any work.
1178    if (adb_is_absolute_host_path(hint.c_str())) {
1179        return hint;
1180    }
1181
1182    // If there are any slashes in it, assume it's a relative path;
1183    // make it absolute.
1184    if (hint.find_first_of(OS_PATH_SEPARATORS) != std::string::npos) {
1185        std::string cwd;
1186        if (!getcwd(&cwd)) {
1187            fprintf(stderr, "adb: getcwd failed: %s\n", strerror(errno));
1188            return "";
1189        }
1190        return android::base::StringPrintf("%s%c%s", cwd.c_str(), OS_PATH_SEPARATOR, hint.c_str());
1191    }
1192
1193    // It's a string without any slashes.  Try to do something with it.
1194    //
1195    // Try to find the root of the build tree, and build a PRODUCT_OUT
1196    // path from there.
1197    char* top = getenv("ANDROID_BUILD_TOP");
1198    if (top == nullptr) {
1199        fprintf(stderr, "adb: ANDROID_BUILD_TOP not set!\n");
1200        return "";
1201    }
1202
1203    std::string path = top;
1204    path += OS_PATH_SEPARATOR_STR;
1205    path += "out";
1206    path += OS_PATH_SEPARATOR_STR;
1207    path += "target";
1208    path += OS_PATH_SEPARATOR_STR;
1209    path += "product";
1210    path += OS_PATH_SEPARATOR_STR;
1211    path += hint;
1212    if (!directory_exists(path)) {
1213        fprintf(stderr, "adb: Couldn't find a product dir based on -p %s; "
1214                        "\"%s\" doesn't exist\n", hint.c_str(), path.c_str());
1215        return "";
1216    }
1217    return path;
1218}
1219
1220static void parse_push_pull_args(const char** arg, int narg,
1221                                 std::vector<const char*>* srcs,
1222                                 const char** dst, bool* copy_attrs) {
1223    *copy_attrs = false;
1224
1225    srcs->clear();
1226    bool ignore_flags = false;
1227    while (narg > 0) {
1228        if (ignore_flags || *arg[0] != '-') {
1229            srcs->push_back(*arg);
1230        } else {
1231            if (!strcmp(*arg, "-p")) {
1232                // Silently ignore for backwards compatibility.
1233            } else if (!strcmp(*arg, "-a")) {
1234                *copy_attrs = true;
1235            } else if (!strcmp(*arg, "--")) {
1236                ignore_flags = true;
1237            } else {
1238                fprintf(stderr, "adb: unrecognized option '%s'\n", *arg);
1239                exit(1);
1240            }
1241        }
1242        ++arg;
1243        --narg;
1244    }
1245
1246    if (srcs->size() > 1) {
1247        *dst = srcs->back();
1248        srcs->pop_back();
1249    }
1250}
1251
1252static int adb_connect_command(const std::string& command) {
1253    std::string error;
1254    int fd = adb_connect(command, &error);
1255    if (fd < 0) {
1256        fprintf(stderr, "error: %s\n", error.c_str());
1257        return 1;
1258    }
1259    read_and_dump(fd);
1260    adb_close(fd);
1261    return 0;
1262}
1263
1264static int adb_query_command(const std::string& command) {
1265    std::string result;
1266    std::string error;
1267    if (!adb_query(command, &result, &error)) {
1268        fprintf(stderr, "error: %s\n", error.c_str());
1269        return 1;
1270    }
1271    printf("%s\n", result.c_str());
1272    return 0;
1273}
1274
1275// Disallow stdin, stdout, and stderr.
1276static bool _is_valid_ack_reply_fd(const int ack_reply_fd) {
1277#ifdef _WIN32
1278    const HANDLE ack_reply_handle = cast_int_to_handle(ack_reply_fd);
1279    return (GetStdHandle(STD_INPUT_HANDLE) != ack_reply_handle) &&
1280           (GetStdHandle(STD_OUTPUT_HANDLE) != ack_reply_handle) &&
1281           (GetStdHandle(STD_ERROR_HANDLE) != ack_reply_handle);
1282#else
1283    return ack_reply_fd > 2;
1284#endif
1285}
1286
1287int adb_commandline(int argc, const char **argv) {
1288    int no_daemon = 0;
1289    int is_daemon = 0;
1290    int is_server = 0;
1291    int r;
1292    TransportType transport_type = kTransportAny;
1293    int ack_reply_fd = -1;
1294
1295    // If defined, this should be an absolute path to
1296    // the directory containing all of the various system images
1297    // for a particular product.  If not defined, and the adb
1298    // command requires this information, then the user must
1299    // specify the path using "-p".
1300    char* ANDROID_PRODUCT_OUT = getenv("ANDROID_PRODUCT_OUT");
1301    if (ANDROID_PRODUCT_OUT != nullptr) {
1302        gProductOutPath = ANDROID_PRODUCT_OUT;
1303    }
1304    // TODO: also try TARGET_PRODUCT/TARGET_DEVICE as a hint
1305
1306    /* Validate and assign the server port */
1307    const char* server_port_str = getenv("ANDROID_ADB_SERVER_PORT");
1308    int server_port = DEFAULT_ADB_PORT;
1309    if (server_port_str && strlen(server_port_str) > 0) {
1310        server_port = strtol(server_port_str, nullptr, 0);
1311        if (server_port <= 0 || server_port > 65535) {
1312            fprintf(stderr,
1313                    "adb: Env var ANDROID_ADB_SERVER_PORT must be a positive number less than 65536. Got \"%s\"\n",
1314                    server_port_str);
1315            return usage();
1316        }
1317    }
1318
1319    // We need to check for -d and -e before we look at $ANDROID_SERIAL.
1320    const char* serial = nullptr;
1321
1322    while (argc > 0) {
1323        if (!strcmp(argv[0],"server")) {
1324            is_server = 1;
1325        } else if (!strcmp(argv[0],"nodaemon")) {
1326            no_daemon = 1;
1327        } else if (!strcmp(argv[0], "fork-server")) {
1328            /* this is a special flag used only when the ADB client launches the ADB Server */
1329            is_daemon = 1;
1330        } else if (!strcmp(argv[0], "--reply-fd")) {
1331            if (argc < 2) return usage();
1332            const char* reply_fd_str = argv[1];
1333            argc--;
1334            argv++;
1335            ack_reply_fd = strtol(reply_fd_str, nullptr, 10);
1336            if (!_is_valid_ack_reply_fd(ack_reply_fd)) {
1337                fprintf(stderr, "adb: invalid reply fd \"%s\"\n", reply_fd_str);
1338                return usage();
1339            }
1340        } else if (!strncmp(argv[0], "-p", 2)) {
1341            const char* product = nullptr;
1342            if (argv[0][2] == '\0') {
1343                if (argc < 2) return usage();
1344                product = argv[1];
1345                argc--;
1346                argv++;
1347            } else {
1348                product = argv[0] + 2;
1349            }
1350            gProductOutPath = find_product_out_path(product);
1351            if (gProductOutPath.empty()) {
1352                fprintf(stderr, "adb: could not resolve \"-p %s\"\n", product);
1353                return usage();
1354            }
1355        } else if (argv[0][0]=='-' && argv[0][1]=='s') {
1356            if (isdigit(argv[0][2])) {
1357                serial = argv[0] + 2;
1358            } else {
1359                if (argc < 2 || argv[0][2] != '\0') return usage();
1360                serial = argv[1];
1361                argc--;
1362                argv++;
1363            }
1364        } else if (!strcmp(argv[0],"-d")) {
1365            transport_type = kTransportUsb;
1366        } else if (!strcmp(argv[0],"-e")) {
1367            transport_type = kTransportLocal;
1368        } else if (!strcmp(argv[0],"-a")) {
1369            gListenAll = 1;
1370        } else if (!strncmp(argv[0], "-H", 2)) {
1371            const char *hostname = NULL;
1372            if (argv[0][2] == '\0') {
1373                if (argc < 2) return usage();
1374                hostname = argv[1];
1375                argc--;
1376                argv++;
1377            } else {
1378                hostname = argv[0] + 2;
1379            }
1380            adb_set_tcp_name(hostname);
1381
1382        } else if (!strncmp(argv[0], "-P", 2)) {
1383            if (argv[0][2] == '\0') {
1384                if (argc < 2) return usage();
1385                server_port_str = argv[1];
1386                argc--;
1387                argv++;
1388            } else {
1389                server_port_str = argv[0] + 2;
1390            }
1391            if (strlen(server_port_str) > 0) {
1392                server_port = (int) strtol(server_port_str, NULL, 0);
1393                if (server_port <= 0 || server_port > 65535) {
1394                    fprintf(stderr,
1395                            "adb: port number must be a positive number less than 65536. Got \"%s\"\n",
1396                            server_port_str);
1397                    return usage();
1398                }
1399            } else {
1400                fprintf(stderr,
1401                "adb: port number must be a positive number less than 65536. Got empty string.\n");
1402                return usage();
1403            }
1404        } else {
1405                /* out of recognized modifiers and flags */
1406            break;
1407        }
1408        argc--;
1409        argv++;
1410    }
1411
1412    // If none of -d, -e, or -s were specified, try $ANDROID_SERIAL.
1413    if (transport_type == kTransportAny && serial == nullptr) {
1414        serial = getenv("ANDROID_SERIAL");
1415    }
1416
1417    adb_set_transport(transport_type, serial);
1418    adb_set_tcp_specifics(server_port);
1419
1420    if (is_server) {
1421        if (no_daemon || is_daemon) {
1422            if (is_daemon && (ack_reply_fd == -1)) {
1423                fprintf(stderr, "reply fd for adb server to client communication not specified.\n");
1424                return usage();
1425            }
1426            r = adb_main(is_daemon, server_port, ack_reply_fd);
1427        } else {
1428            r = launch_server(server_port);
1429        }
1430        if (r) {
1431            fprintf(stderr,"* could not start server *\n");
1432        }
1433        return r;
1434    }
1435
1436    if (argc == 0) {
1437        return usage();
1438    }
1439
1440    /* handle wait-for-* prefix */
1441    if (!strncmp(argv[0], "wait-for-", strlen("wait-for-"))) {
1442        const char* service = argv[0];
1443
1444        if (!wait_for_device(service, transport_type, serial)) {
1445            return 1;
1446        }
1447
1448        // Allow a command to be run after wait-for-device,
1449        // e.g. 'adb wait-for-device shell'.
1450        if (argc == 1) {
1451            return 0;
1452        }
1453
1454        /* Fall through */
1455        argc--;
1456        argv++;
1457    }
1458
1459    /* adb_connect() commands */
1460    if (!strcmp(argv[0], "devices")) {
1461        const char *listopt;
1462        if (argc < 2) {
1463            listopt = "";
1464        } else if (argc == 2 && !strcmp(argv[1], "-l")) {
1465            listopt = argv[1];
1466        } else {
1467            fprintf(stderr, "Usage: adb devices [-l]\n");
1468            return 1;
1469        }
1470
1471        std::string query = android::base::StringPrintf("host:%s%s", argv[0], listopt);
1472        printf("List of devices attached\n");
1473        return adb_query_command(query);
1474    }
1475    else if (!strcmp(argv[0], "connect")) {
1476        if (argc != 2) {
1477            fprintf(stderr, "Usage: adb connect <host>[:<port>]\n");
1478            return 1;
1479        }
1480
1481        std::string query = android::base::StringPrintf("host:connect:%s", argv[1]);
1482        return adb_query_command(query);
1483    }
1484    else if (!strcmp(argv[0], "disconnect")) {
1485        if (argc > 2) {
1486            fprintf(stderr, "Usage: adb disconnect [<host>[:<port>]]\n");
1487            return 1;
1488        }
1489
1490        std::string query = android::base::StringPrintf("host:disconnect:%s",
1491                                                        (argc == 2) ? argv[1] : "");
1492        return adb_query_command(query);
1493    }
1494    else if (!strcmp(argv[0], "emu")) {
1495        return adb_send_emulator_command(argc, argv, serial);
1496    }
1497    else if (!strcmp(argv[0], "shell")) {
1498        return adb_shell(argc, argv, transport_type, serial);
1499    }
1500    else if (!strcmp(argv[0], "exec-in") || !strcmp(argv[0], "exec-out")) {
1501        int exec_in = !strcmp(argv[0], "exec-in");
1502
1503        std::string cmd = "exec:";
1504        cmd += argv[1];
1505        argc -= 2;
1506        argv += 2;
1507        while (argc-- > 0) {
1508            cmd += " " + escape_arg(*argv++);
1509        }
1510
1511        std::string error;
1512        int fd = adb_connect(cmd, &error);
1513        if (fd < 0) {
1514            fprintf(stderr, "error: %s\n", error.c_str());
1515            return -1;
1516        }
1517
1518        if (exec_in) {
1519            copy_to_file(STDIN_FILENO, fd);
1520        } else {
1521            copy_to_file(fd, STDOUT_FILENO);
1522        }
1523
1524        adb_close(fd);
1525        return 0;
1526    }
1527    else if (!strcmp(argv[0], "kill-server")) {
1528        std::string error;
1529        int fd = _adb_connect("host:kill", &error);
1530        if (fd == -2) {
1531            // Failed to make network connection to server. Don't output the
1532            // network error since that is expected.
1533            fprintf(stderr,"* server not running *\n");
1534            // Successful exit code because the server is already "killed".
1535            return 0;
1536        } else if (fd == -1) {
1537            // Some other error.
1538            fprintf(stderr, "error: %s\n", error.c_str());
1539            return 1;
1540        } else {
1541            // Successfully connected, kill command sent, okay status came back.
1542            // Server should exit() in a moment, if not already.
1543            ReadOrderlyShutdown(fd);
1544            adb_close(fd);
1545            return 0;
1546        }
1547    }
1548    else if (!strcmp(argv[0], "sideload")) {
1549        if (argc != 2) return usage();
1550        if (adb_sideload_host(argv[1])) {
1551            return 1;
1552        } else {
1553            return 0;
1554        }
1555    }
1556    else if (!strcmp(argv[0], "tcpip") && argc > 1) {
1557        return adb_connect_command(android::base::StringPrintf("tcpip:%s", argv[1]));
1558    }
1559    else if (!strcmp(argv[0], "remount") ||
1560             !strcmp(argv[0], "reboot") ||
1561             !strcmp(argv[0], "reboot-bootloader") ||
1562             !strcmp(argv[0], "usb") ||
1563             !strcmp(argv[0], "root") ||
1564             !strcmp(argv[0], "unroot") ||
1565             !strcmp(argv[0], "disable-verity") ||
1566             !strcmp(argv[0], "enable-verity")) {
1567        std::string command;
1568        if (!strcmp(argv[0], "reboot-bootloader")) {
1569            command = "reboot:bootloader";
1570        } else if (argc > 1) {
1571            command = android::base::StringPrintf("%s:%s", argv[0], argv[1]);
1572        } else {
1573            command = android::base::StringPrintf("%s:", argv[0]);
1574        }
1575        return adb_connect_command(command);
1576    }
1577    else if (!strcmp(argv[0], "bugreport")) {
1578        if (argc != 1) return usage();
1579        // No need for shell protocol with bugreport, always disable for
1580        // simplicity.
1581        return send_shell_command(transport_type, serial, "bugreport", true);
1582    }
1583    else if (!strcmp(argv[0], "forward") || !strcmp(argv[0], "reverse")) {
1584        bool reverse = !strcmp(argv[0], "reverse");
1585        ++argv;
1586        --argc;
1587        if (argc < 1) return usage();
1588
1589        // Determine the <host-prefix> for this command.
1590        std::string host_prefix;
1591        if (reverse) {
1592            host_prefix = "reverse";
1593        } else {
1594            if (serial) {
1595                host_prefix = android::base::StringPrintf("host-serial:%s", serial);
1596            } else if (transport_type == kTransportUsb) {
1597                host_prefix = "host-usb";
1598            } else if (transport_type == kTransportLocal) {
1599                host_prefix = "host-local";
1600            } else {
1601                host_prefix = "host";
1602            }
1603        }
1604
1605        std::string cmd;
1606        if (strcmp(argv[0], "--list") == 0) {
1607            if (argc != 1) return usage();
1608            return adb_query_command(host_prefix + ":list-forward");
1609        } else if (strcmp(argv[0], "--remove-all") == 0) {
1610            if (argc != 1) return usage();
1611            cmd = host_prefix + ":killforward-all";
1612        } else if (strcmp(argv[0], "--remove") == 0) {
1613            // forward --remove <local>
1614            if (argc != 2) return usage();
1615            cmd = host_prefix + ":killforward:" + argv[1];
1616        } else if (strcmp(argv[0], "--no-rebind") == 0) {
1617            // forward --no-rebind <local> <remote>
1618            if (argc != 3) return usage();
1619            cmd = host_prefix + ":forward:norebind:" + argv[1] + ";" + argv[2];
1620        } else {
1621            // forward <local> <remote>
1622            if (argc != 2) return usage();
1623            cmd = host_prefix + ":forward:" + argv[0] + ";" + argv[1];
1624        }
1625
1626        return adb_command(cmd) ? 0 : 1;
1627    }
1628    /* do_sync_*() commands */
1629    else if (!strcmp(argv[0], "ls")) {
1630        if (argc != 2) return usage();
1631        return do_sync_ls(argv[1]) ? 0 : 1;
1632    }
1633    else if (!strcmp(argv[0], "push")) {
1634        bool copy_attrs = false;
1635        std::vector<const char*> srcs;
1636        const char* dst = nullptr;
1637
1638        parse_push_pull_args(&argv[1], argc - 1, &srcs, &dst, &copy_attrs);
1639        if (srcs.empty() || !dst) return usage();
1640        return do_sync_push(srcs, dst) ? 0 : 1;
1641    }
1642    else if (!strcmp(argv[0], "pull")) {
1643        bool copy_attrs = false;
1644        std::vector<const char*> srcs;
1645        const char* dst = ".";
1646
1647        parse_push_pull_args(&argv[1], argc - 1, &srcs, &dst, &copy_attrs);
1648        if (srcs.empty()) return usage();
1649        return do_sync_pull(srcs, dst, copy_attrs) ? 0 : 1;
1650    }
1651    else if (!strcmp(argv[0], "install")) {
1652        if (argc < 2) return usage();
1653        FeatureSet features = GetFeatureSet(transport_type, serial);
1654        if (CanUseFeature(features, kFeatureCmd)) {
1655            return install_app(transport_type, serial, argc, argv);
1656        }
1657        return install_app_legacy(transport_type, serial, argc, argv);
1658    }
1659    else if (!strcmp(argv[0], "install-multiple")) {
1660        if (argc < 2) return usage();
1661        return install_multiple_app(transport_type, serial, argc, argv);
1662    }
1663    else if (!strcmp(argv[0], "uninstall")) {
1664        if (argc < 2) return usage();
1665        FeatureSet features = GetFeatureSet(transport_type, serial);
1666        if (CanUseFeature(features, kFeatureCmd)) {
1667            return uninstall_app(transport_type, serial, argc, argv);
1668        }
1669        return uninstall_app_legacy(transport_type, serial, argc, argv);
1670    }
1671    else if (!strcmp(argv[0], "sync")) {
1672        std::string src;
1673        bool list_only = false;
1674        if (argc < 2) {
1675            // No local path was specified.
1676            src = "";
1677        } else if (argc >= 2 && strcmp(argv[1], "-l") == 0) {
1678            list_only = true;
1679            if (argc == 3) {
1680                src = argv[2];
1681            } else {
1682                src = "";
1683            }
1684        } else if (argc == 2) {
1685            // A local path or "android"/"data" arg was specified.
1686            src = argv[1];
1687        } else {
1688            return usage();
1689        }
1690
1691        if (src != "" &&
1692            src != "system" && src != "data" && src != "vendor" && src != "oem") {
1693            return usage();
1694        }
1695
1696        std::string system_src_path = product_file("system");
1697        std::string data_src_path = product_file("data");
1698        std::string vendor_src_path = product_file("vendor");
1699        std::string oem_src_path = product_file("oem");
1700
1701        bool okay = true;
1702        if (okay && (src.empty() || src == "system")) {
1703            okay = do_sync_sync(system_src_path, "/system", list_only);
1704        }
1705        if (okay && (src.empty() || src == "vendor") && directory_exists(vendor_src_path)) {
1706            okay = do_sync_sync(vendor_src_path, "/vendor", list_only);
1707        }
1708        if (okay && (src.empty() || src == "oem") && directory_exists(oem_src_path)) {
1709            okay = do_sync_sync(oem_src_path, "/oem", list_only);
1710        }
1711        if (okay && (src.empty() || src == "data")) {
1712            okay = do_sync_sync(data_src_path, "/data", list_only);
1713        }
1714        return okay ? 0 : 1;
1715    }
1716    /* passthrough commands */
1717    else if (!strcmp(argv[0],"get-state") ||
1718        !strcmp(argv[0],"get-serialno") ||
1719        !strcmp(argv[0],"get-devpath"))
1720    {
1721        return adb_query_command(format_host_command(argv[0], transport_type, serial));
1722    }
1723    /* other commands */
1724    else if (!strcmp(argv[0],"logcat") || !strcmp(argv[0],"lolcat") || !strcmp(argv[0],"longcat")) {
1725        return logcat(transport_type, serial, argc, argv);
1726    }
1727    else if (!strcmp(argv[0],"ppp")) {
1728        return ppp(argc, argv);
1729    }
1730    else if (!strcmp(argv[0], "start-server")) {
1731        std::string error;
1732        const int result = adb_connect("host:start-server", &error);
1733        if (result < 0) {
1734            fprintf(stderr, "error: %s\n", error.c_str());
1735        }
1736        return result;
1737    }
1738    else if (!strcmp(argv[0], "backup")) {
1739        return backup(argc, argv);
1740    }
1741    else if (!strcmp(argv[0], "restore")) {
1742        return restore(argc, argv);
1743    }
1744    else if (!strcmp(argv[0], "keygen")) {
1745        if (argc < 2) return usage();
1746        // Always print key generation information for keygen command.
1747        adb_trace_enable(AUTH);
1748        return adb_auth_keygen(argv[1]);
1749    }
1750    else if (!strcmp(argv[0], "jdwp")) {
1751        return adb_connect_command("jdwp");
1752    }
1753    /* "adb /?" is a common idiom under Windows */
1754    else if (!strcmp(argv[0], "help") || !strcmp(argv[0], "/?")) {
1755        help();
1756        return 0;
1757    }
1758    else if (!strcmp(argv[0], "version")) {
1759        fprintf(stdout, "%s", adb_version().c_str());
1760        return 0;
1761    }
1762    else if (!strcmp(argv[0], "features")) {
1763        // Only list the features common to both the adb client and the device.
1764        FeatureSet features = GetFeatureSet(transport_type, serial);
1765        for (const std::string& name : features) {
1766            if (CanUseFeature(features, name)) {
1767                printf("%s\n", name.c_str());
1768            }
1769        }
1770        return 0;
1771    }
1772
1773    usage();
1774    return 1;
1775}
1776
1777static int uninstall_app(TransportType transport, const char* serial, int argc, const char** argv) {
1778    // 'adb uninstall' takes the same arguments as 'cmd package uninstall' on device
1779    std::string cmd = "cmd package";
1780    while (argc-- > 0) {
1781        // deny the '-k' option until the remaining data/cache can be removed with adb/UI
1782        if (strcmp(*argv, "-k") == 0) {
1783            printf(
1784                "The -k option uninstalls the application while retaining the data/cache.\n"
1785                "At the moment, there is no way to remove the remaining data.\n"
1786                "You will have to reinstall the application with the same signature, and fully uninstall it.\n"
1787                "If you truly wish to continue, execute 'adb shell cmd package uninstall -k'.\n");
1788            return EXIT_FAILURE;
1789        }
1790        cmd += " " + escape_arg(*argv++);
1791    }
1792
1793    return send_shell_command(transport, serial, cmd, false);
1794}
1795
1796static int install_app(TransportType transport, const char* serial, int argc, const char** argv) {
1797    // The last argument must be the APK file
1798    const char* file = argv[argc - 1];
1799    const char* dot = strrchr(file, '.');
1800    bool found_apk = false;
1801    struct stat sb;
1802    if (dot && !strcasecmp(dot, ".apk")) {
1803        if (stat(file, &sb) == -1 || !S_ISREG(sb.st_mode)) {
1804            fprintf(stderr, "Invalid APK file: %s\n", file);
1805            return EXIT_FAILURE;
1806        }
1807        found_apk = true;
1808    }
1809
1810    if (!found_apk) {
1811        fprintf(stderr, "Missing APK file\n");
1812        return EXIT_FAILURE;
1813    }
1814
1815    int localFd = adb_open(file, O_RDONLY);
1816    if (localFd < 0) {
1817        fprintf(stderr, "Failed to open %s: %s\n", file, strerror(errno));
1818        return 1;
1819    }
1820
1821    std::string error;
1822    std::string cmd = "exec:cmd package";
1823
1824    // don't copy the APK name, but, copy the rest of the arguments as-is
1825    while (argc-- > 1) {
1826        cmd += " " + escape_arg(std::string(*argv++));
1827    }
1828
1829    // add size parameter [required for streaming installs]
1830    // do last to override any user specified value
1831    cmd += " " + android::base::StringPrintf("-S %" PRIu64, static_cast<uint64_t>(sb.st_size));
1832
1833    int remoteFd = adb_connect(cmd, &error);
1834    if (remoteFd < 0) {
1835        fprintf(stderr, "Connect error for write: %s\n", error.c_str());
1836        adb_close(localFd);
1837        return 1;
1838    }
1839
1840    char buf[BUFSIZ];
1841    copy_to_file(localFd, remoteFd);
1842    read_status_line(remoteFd, buf, sizeof(buf));
1843
1844    adb_close(localFd);
1845    adb_close(remoteFd);
1846
1847    if (strncmp("Success", buf, 7)) {
1848        fprintf(stderr, "Failed to write %s\n", file);
1849        fputs(buf, stderr);
1850        return 1;
1851    }
1852    fputs(buf, stderr);
1853    return 0;
1854}
1855
1856static int install_multiple_app(TransportType transport, const char* serial, int argc,
1857                                const char** argv)
1858{
1859    int i;
1860    struct stat sb;
1861    uint64_t total_size = 0;
1862
1863    // Find all APK arguments starting at end.
1864    // All other arguments passed through verbatim.
1865    int first_apk = -1;
1866    for (i = argc - 1; i >= 0; i--) {
1867        const char* file = argv[i];
1868        const char* dot = strrchr(file, '.');
1869        if (dot && !strcasecmp(dot, ".apk")) {
1870            if (stat(file, &sb) == -1 || !S_ISREG(sb.st_mode)) {
1871                fprintf(stderr, "Invalid APK file: %s\n", file);
1872                return EXIT_FAILURE;
1873            }
1874
1875            total_size += sb.st_size;
1876            first_apk = i;
1877        } else {
1878            break;
1879        }
1880    }
1881
1882    if (first_apk == -1) {
1883        fprintf(stderr, "Missing APK file\n");
1884        return 1;
1885    }
1886
1887    std::string cmd = android::base::StringPrintf("exec:pm install-create -S %" PRIu64, total_size);
1888    for (i = 1; i < first_apk; i++) {
1889        cmd += " " + escape_arg(argv[i]);
1890    }
1891
1892    // Create install session
1893    std::string error;
1894    int fd = adb_connect(cmd, &error);
1895    if (fd < 0) {
1896        fprintf(stderr, "Connect error for create: %s\n", error.c_str());
1897        return EXIT_FAILURE;
1898    }
1899    char buf[BUFSIZ];
1900    read_status_line(fd, buf, sizeof(buf));
1901    adb_close(fd);
1902
1903    int session_id = -1;
1904    if (!strncmp("Success", buf, 7)) {
1905        char* start = strrchr(buf, '[');
1906        char* end = strrchr(buf, ']');
1907        if (start && end) {
1908            *end = '\0';
1909            session_id = strtol(start + 1, NULL, 10);
1910        }
1911    }
1912    if (session_id < 0) {
1913        fprintf(stderr, "Failed to create session\n");
1914        fputs(buf, stderr);
1915        return EXIT_FAILURE;
1916    }
1917
1918    // Valid session, now stream the APKs
1919    int success = 1;
1920    for (i = first_apk; i < argc; i++) {
1921        const char* file = argv[i];
1922        if (stat(file, &sb) == -1) {
1923            fprintf(stderr, "Failed to stat %s\n", file);
1924            success = 0;
1925            goto finalize_session;
1926        }
1927
1928        std::string cmd = android::base::StringPrintf(
1929                "exec:pm install-write -S %" PRIu64 " %d %d_%s -",
1930                static_cast<uint64_t>(sb.st_size), session_id, i, adb_basename(file).c_str());
1931
1932        int localFd = adb_open(file, O_RDONLY);
1933        if (localFd < 0) {
1934            fprintf(stderr, "Failed to open %s: %s\n", file, strerror(errno));
1935            success = 0;
1936            goto finalize_session;
1937        }
1938
1939        std::string error;
1940        int remoteFd = adb_connect(cmd, &error);
1941        if (remoteFd < 0) {
1942            fprintf(stderr, "Connect error for write: %s\n", error.c_str());
1943            adb_close(localFd);
1944            success = 0;
1945            goto finalize_session;
1946        }
1947
1948        copy_to_file(localFd, remoteFd);
1949        read_status_line(remoteFd, buf, sizeof(buf));
1950
1951        adb_close(localFd);
1952        adb_close(remoteFd);
1953
1954        if (strncmp("Success", buf, 7)) {
1955            fprintf(stderr, "Failed to write %s\n", file);
1956            fputs(buf, stderr);
1957            success = 0;
1958            goto finalize_session;
1959        }
1960    }
1961
1962finalize_session:
1963    // Commit session if we streamed everything okay; otherwise abandon
1964    std::string service =
1965            android::base::StringPrintf("exec:pm install-%s %d",
1966                                        success ? "commit" : "abandon", session_id);
1967    fd = adb_connect(service, &error);
1968    if (fd < 0) {
1969        fprintf(stderr, "Connect error for finalize: %s\n", error.c_str());
1970        return EXIT_FAILURE;
1971    }
1972    read_status_line(fd, buf, sizeof(buf));
1973    adb_close(fd);
1974
1975    if (!strncmp("Success", buf, 7)) {
1976        fputs(buf, stderr);
1977        return 0;
1978    } else {
1979        fprintf(stderr, "Failed to finalize session\n");
1980        fputs(buf, stderr);
1981        return EXIT_FAILURE;
1982    }
1983}
1984
1985static int pm_command(TransportType transport, const char* serial, int argc, const char** argv) {
1986    std::string cmd = "pm";
1987
1988    while (argc-- > 0) {
1989        cmd += " " + escape_arg(*argv++);
1990    }
1991
1992    return send_shell_command(transport, serial, cmd, false);
1993}
1994
1995static int uninstall_app_legacy(TransportType transport, const char* serial, int argc, const char** argv) {
1996    /* if the user choose the -k option, we refuse to do it until devices are
1997       out with the option to uninstall the remaining data somehow (adb/ui) */
1998    int i;
1999    for (i = 1; i < argc; i++) {
2000        if (!strcmp(argv[i], "-k")) {
2001            printf(
2002                "The -k option uninstalls the application while retaining the data/cache.\n"
2003                "At the moment, there is no way to remove the remaining data.\n"
2004                "You will have to reinstall the application with the same signature, and fully uninstall it.\n"
2005                "If you truly wish to continue, execute 'adb shell pm uninstall -k'\n.");
2006            return EXIT_FAILURE;
2007        }
2008    }
2009
2010    /* 'adb uninstall' takes the same arguments as 'pm uninstall' on device */
2011    return pm_command(transport, serial, argc, argv);
2012}
2013
2014static int delete_file(TransportType transport, const char* serial, const std::string& filename) {
2015    std::string cmd = "rm -f " + escape_arg(filename);
2016    return send_shell_command(transport, serial, cmd, false);
2017}
2018
2019static int install_app_legacy(TransportType transport, const char* serial, int argc, const char** argv) {
2020    static const char *const DATA_DEST = "/data/local/tmp/%s";
2021    static const char *const SD_DEST = "/sdcard/tmp/%s";
2022    const char* where = DATA_DEST;
2023    int i;
2024    struct stat sb;
2025
2026    for (i = 1; i < argc; i++) {
2027        if (!strcmp(argv[i], "-s")) {
2028            where = SD_DEST;
2029        }
2030    }
2031
2032    // Find last APK argument.
2033    // All other arguments passed through verbatim.
2034    int last_apk = -1;
2035    for (i = argc - 1; i >= 0; i--) {
2036        const char* file = argv[i];
2037        const char* dot = strrchr(file, '.');
2038        if (dot && !strcasecmp(dot, ".apk")) {
2039            if (stat(file, &sb) == -1 || !S_ISREG(sb.st_mode)) {
2040                fprintf(stderr, "Invalid APK file: %s\n", file);
2041                return EXIT_FAILURE;
2042            }
2043
2044            last_apk = i;
2045            break;
2046        }
2047    }
2048
2049    if (last_apk == -1) {
2050        fprintf(stderr, "Missing APK file\n");
2051        return EXIT_FAILURE;
2052    }
2053
2054    int result = -1;
2055    std::vector<const char*> apk_file = {argv[last_apk]};
2056    std::string apk_dest = android::base::StringPrintf(
2057        where, adb_basename(argv[last_apk]).c_str());
2058    if (!do_sync_push(apk_file, apk_dest.c_str())) goto cleanup_apk;
2059    argv[last_apk] = apk_dest.c_str(); /* destination name, not source location */
2060    result = pm_command(transport, serial, argc, argv);
2061
2062cleanup_apk:
2063    delete_file(transport, serial, apk_dest);
2064    return result;
2065}
2066