commandline.cpp revision 0e42c2a4ad06be7601377da0b3abc2cc2ad86cbf
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 std::string gProductOutPath; 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}; 472 473// Loops to read from stdin and push the data to the given FD. 474// The argument should be a pointer to a StdinReadArgs object. This function 475// will take ownership of the object and delete it when finished. 476static void* stdin_read_thread_loop(void* x) { 477 std::unique_ptr<StdinReadArgs> args(reinterpret_cast<StdinReadArgs*>(x)); 478 int state = 0; 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[1024]; 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 while (true) { 509 // Use unix_read() rather than adb_read() for stdin. 510 D("stdin_read_thread_loop(): pre unix_read(fdi=%d,...)", args->stdin_fd); 511#if !defined(_WIN32) 512#undef read 513 int r = read(args->stdin_fd, buffer_ptr, buffer_size); 514 if (r == -1 && errno == EINTR) { 515 send_window_size_change(args->stdin_fd, args->protocol); 516 continue; 517 } 518#define read ___xxx_read 519#else 520 int r = unix_read(args->stdin_fd, buffer_ptr, buffer_size); 521#endif 522 D("stdin_read_thread_loop(): post unix_read(fdi=%d,...)", args->stdin_fd); 523 if (r <= 0) { 524 // Only devices using the shell protocol know to close subprocess 525 // stdin. For older devices we want to just leave the connection 526 // open, otherwise an unpredictable amount of return data could 527 // be lost due to the FD closing before all data has been received. 528 if (args->protocol) { 529 args->protocol->Write(ShellProtocol::kIdCloseStdin, 0); 530 } 531 break; 532 } 533 // If we made stdin raw, check input for the "~." escape sequence. In 534 // this situation signals like Ctrl+C are sent remotely rather than 535 // interpreted locally so this provides an emergency out if the remote 536 // process starts ignoring the signal. SSH also does this, see the 537 // "escape characters" section on the ssh man page for more info. 538 if (args->raw_stdin) { 539 for (int n = 0; n < r; n++) { 540 switch (buffer_ptr[n]) { 541 case '\n': 542 state = 1; 543 break; 544 case '\r': 545 state = 1; 546 break; 547 case '~': 548 if (state == 1) { 549 state++; 550 } else { 551 state = 0; 552 } 553 break; 554 case '.': 555 if (state == 2) { 556 fprintf(stderr,"\r\n* disconnect *\r\n"); 557 stdin_raw_restore(); 558 exit(0); 559 } 560 default: 561 state = 0; 562 } 563 } 564 } 565 if (args->protocol) { 566 if (!args->protocol->Write(ShellProtocol::kIdStdin, r)) { 567 break; 568 } 569 } else { 570 if (!WriteFdExactly(args->write_fd, buffer_ptr, r)) { 571 break; 572 } 573 } 574 } 575 576 return nullptr; 577} 578 579// Returns a shell service string with the indicated arguments and command. 580static std::string ShellServiceString(bool use_shell_protocol, 581 const std::string& type_arg, 582 const std::string& command) { 583 std::vector<std::string> args; 584 if (use_shell_protocol) { 585 args.push_back(kShellServiceArgShellProtocol); 586 } 587 if (!type_arg.empty()) { 588 args.push_back(type_arg); 589 } 590 591 // Shell service string can look like: shell[,arg1,arg2,...]:[command]. 592 return android::base::StringPrintf("shell%s%s:%s", 593 args.empty() ? "" : ",", 594 android::base::Join(args, ',').c_str(), 595 command.c_str()); 596} 597 598// Connects to a shell on the device and read/writes data. 599// 600// Note: currently this function doesn't properly clean up resources; the 601// FD connected to the adb server is never closed and the stdin read thread 602// may never exit. 603// 604// On success returns the remote exit code if |use_shell_protocol| is true, 605// 0 otherwise. On failure returns 1. 606static int RemoteShell(bool use_shell_protocol, const std::string& type_arg, 607 const std::string& command) { 608 std::string service_string = ShellServiceString(use_shell_protocol, 609 type_arg, command); 610 611 // Make local stdin raw if the device allocates a PTY, which happens if: 612 // 1. We are explicitly asking for a PTY shell, or 613 // 2. We don't specify shell type and are starting an interactive session. 614 bool raw_stdin = (type_arg == kShellServiceArgPty || 615 (type_arg.empty() && command.empty())); 616 617 std::string error; 618 int fd = adb_connect(service_string, &error); 619 if (fd < 0) { 620 fprintf(stderr,"error: %s\n", error.c_str()); 621 return 1; 622 } 623 624 StdinReadArgs* args = new StdinReadArgs; 625 if (!args) { 626 LOG(ERROR) << "couldn't allocate StdinReadArgs object"; 627 return 1; 628 } 629 args->stdin_fd = STDIN_FILENO; 630 args->write_fd = fd; 631 args->raw_stdin = raw_stdin; 632 if (use_shell_protocol) { 633 args->protocol.reset(new ShellProtocol(args->write_fd)); 634 } 635 636 if (raw_stdin) stdin_raw_init(); 637 638#if !defined(_WIN32) 639 // Ensure our process is notified if the local window size changes. 640 // We use sigaction(2) to ensure that the SA_RESTART flag is not set, 641 // because the whole reason we're sending signals is to unblock the read(2)! 642 // That also means we don't need to do anything in the signal handler: 643 // the side effect of delivering the signal is all we need. 644 struct sigaction sa; 645 memset(&sa, 0, sizeof(sa)); 646 sa.sa_handler = [](int) {}; 647 sa.sa_flags = 0; 648 sigaction(SIGWINCH, &sa, nullptr); 649 650 // Now block SIGWINCH in this thread (the main thread) and all threads spawned 651 // from it. The stdin read thread will unblock this signal to ensure that it's 652 // the thread that receives the signal. 653 sigset_t mask; 654 sigemptyset(&mask); 655 sigaddset(&mask, SIGWINCH); 656 pthread_sigmask(SIG_BLOCK, &mask, nullptr); 657#endif 658 659 // TODO: combine read_and_dump with stdin_read_thread to make life simpler? 660 int exit_code = 1; 661 if (!adb_thread_create(stdin_read_thread_loop, args)) { 662 PLOG(ERROR) << "error starting stdin read thread"; 663 delete args; 664 } else { 665 exit_code = read_and_dump(fd, use_shell_protocol); 666 } 667 668 // TODO: properly exit stdin_read_thread_loop and close |fd|. 669 670 // TODO: we should probably install signal handlers for this. 671 // TODO: can we use atexit? even on Windows? 672 if (raw_stdin) stdin_raw_restore(); 673 674 return exit_code; 675} 676 677static int adb_shell(int argc, const char** argv, 678 TransportType transport_type, const char* serial) { 679 FeatureSet features = GetFeatureSet(transport_type, serial); 680 681 bool use_shell_protocol = CanUseFeature(features, kFeatureShell2); 682 if (!use_shell_protocol) { 683 D("shell protocol not supported, using raw data transfer"); 684 } else { 685 D("using shell protocol"); 686 } 687 688 // Parse shell-specific command-line options. 689 // argv[0] is always "shell". 690 --argc; 691 ++argv; 692 int t_arg_count = 0; 693 while (argc) { 694 if (!strcmp(argv[0], "-T") || !strcmp(argv[0], "-t")) { 695 if (!CanUseFeature(features, kFeatureShell2)) { 696 fprintf(stderr, "error: target doesn't support PTY args -Tt\n"); 697 return 1; 698 } 699 // Like ssh, -t arguments are cumulative so that multiple -t's 700 // are needed to force a PTY. 701 if (argv[0][1] == 't') { 702 ++t_arg_count; 703 } else { 704 t_arg_count = -1; 705 } 706 --argc; 707 ++argv; 708 } else if (!strcmp(argv[0], "-x")) { 709 use_shell_protocol = false; 710 --argc; 711 ++argv; 712 } else { 713 break; 714 } 715 } 716 717 std::string shell_type_arg; 718 if (CanUseFeature(features, kFeatureShell2)) { 719 if (t_arg_count < 0) { 720 shell_type_arg = kShellServiceArgRaw; 721 } else if (t_arg_count == 0) { 722 // If stdin isn't a TTY, default to a raw shell; this lets 723 // things like `adb shell < my_script.sh` work as expected. 724 // Otherwise leave |shell_type_arg| blank which uses PTY for 725 // interactive shells and raw for non-interactive. 726 if (!unix_isatty(STDIN_FILENO)) { 727 shell_type_arg = kShellServiceArgRaw; 728 } 729 } else if (t_arg_count == 1) { 730 // A single -t arg isn't enough to override implicit -T. 731 if (!unix_isatty(STDIN_FILENO)) { 732 fprintf(stderr, 733 "Remote PTY will not be allocated because stdin is not a terminal.\n" 734 "Use multiple -t options to force remote PTY allocation.\n"); 735 shell_type_arg = kShellServiceArgRaw; 736 } else { 737 shell_type_arg = kShellServiceArgPty; 738 } 739 } else { 740 shell_type_arg = kShellServiceArgPty; 741 } 742 } 743 744 std::string command; 745 if (argc) { 746 // We don't escape here, just like ssh(1). http://b/20564385. 747 command = android::base::Join(std::vector<const char*>(argv, argv + argc), ' '); 748 } 749 750 return RemoteShell(use_shell_protocol, shell_type_arg, command); 751} 752 753static int adb_download_buffer(const char *service, const char *fn, const void* data, unsigned sz, 754 bool show_progress) 755{ 756 std::string error; 757 int fd = adb_connect(android::base::StringPrintf("%s:%d", service, sz), &error); 758 if (fd < 0) { 759 fprintf(stderr,"error: %s\n", error.c_str()); 760 return -1; 761 } 762 763 int opt = CHUNK_SIZE; 764 opt = adb_setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (const void *) &opt, sizeof(opt)); 765 766 unsigned total = sz; 767 const uint8_t* ptr = reinterpret_cast<const uint8_t*>(data); 768 769 if (show_progress) { 770 const char* x = strrchr(service, ':'); 771 if (x) service = x + 1; 772 } 773 774 while (sz > 0) { 775 unsigned xfer = (sz > CHUNK_SIZE) ? CHUNK_SIZE : sz; 776 if (!WriteFdExactly(fd, ptr, xfer)) { 777 std::string error; 778 adb_status(fd, &error); 779 fprintf(stderr,"* failed to write data '%s' *\n", error.c_str()); 780 adb_close(fd); 781 return -1; 782 } 783 sz -= xfer; 784 ptr += xfer; 785 if (show_progress) { 786 printf("sending: '%s' %4d%% \r", fn, (int)(100LL - ((100LL * sz) / (total)))); 787 fflush(stdout); 788 } 789 } 790 if (show_progress) { 791 printf("\n"); 792 } 793 794 if (!adb_status(fd, &error)) { 795 fprintf(stderr,"* error response '%s' *\n", error.c_str()); 796 adb_close(fd); 797 return -1; 798 } 799 800 adb_close(fd); 801 return 0; 802} 803 804#define SIDELOAD_HOST_BLOCK_SIZE (CHUNK_SIZE) 805 806/* 807 * The sideload-host protocol serves the data in a file (given on the 808 * command line) to the client, using a simple protocol: 809 * 810 * - The connect message includes the total number of bytes in the 811 * file and a block size chosen by us. 812 * 813 * - The other side sends the desired block number as eight decimal 814 * digits (eg "00000023" for block 23). Blocks are numbered from 815 * zero. 816 * 817 * - We send back the data of the requested block. The last block is 818 * likely to be partial; when the last block is requested we only 819 * send the part of the block that exists, it's not padded up to the 820 * block size. 821 * 822 * - When the other side sends "DONEDONE" instead of a block number, 823 * we hang up. 824 */ 825static int adb_sideload_host(const char* fn) { 826 unsigned sz; 827 size_t xfer = 0; 828 int status; 829 int last_percent = -1; 830 int opt = SIDELOAD_HOST_BLOCK_SIZE; 831 832 printf("loading: '%s'", fn); 833 fflush(stdout); 834 uint8_t* data = reinterpret_cast<uint8_t*>(load_file(fn, &sz)); 835 if (data == 0) { 836 printf("\n"); 837 fprintf(stderr, "* cannot read '%s' *\n", fn); 838 return -1; 839 } 840 841 std::string service = 842 android::base::StringPrintf("sideload-host:%d:%d", sz, SIDELOAD_HOST_BLOCK_SIZE); 843 std::string error; 844 int fd = adb_connect(service, &error); 845 if (fd < 0) { 846 // Try falling back to the older sideload method. Maybe this 847 // is an older device that doesn't support sideload-host. 848 printf("\n"); 849 status = adb_download_buffer("sideload", fn, data, sz, true); 850 goto done; 851 } 852 853 opt = adb_setsockopt(fd, SOL_SOCKET, SO_SNDBUF, (const void *) &opt, sizeof(opt)); 854 855 while (true) { 856 char buf[9]; 857 if (!ReadFdExactly(fd, buf, 8)) { 858 fprintf(stderr, "* failed to read command: %s\n", strerror(errno)); 859 status = -1; 860 goto done; 861 } 862 buf[8] = '\0'; 863 864 if (strcmp("DONEDONE", buf) == 0) { 865 status = 0; 866 break; 867 } 868 869 int block = strtol(buf, NULL, 10); 870 871 size_t offset = block * SIDELOAD_HOST_BLOCK_SIZE; 872 if (offset >= sz) { 873 fprintf(stderr, "* attempt to read block %d past end\n", block); 874 status = -1; 875 goto done; 876 } 877 uint8_t* start = data + offset; 878 size_t offset_end = offset + SIDELOAD_HOST_BLOCK_SIZE; 879 size_t to_write = SIDELOAD_HOST_BLOCK_SIZE; 880 if (offset_end > sz) { 881 to_write = sz - offset; 882 } 883 884 if(!WriteFdExactly(fd, start, to_write)) { 885 adb_status(fd, &error); 886 fprintf(stderr,"* failed to write data '%s' *\n", error.c_str()); 887 status = -1; 888 goto done; 889 } 890 xfer += to_write; 891 892 // For normal OTA packages, we expect to transfer every byte 893 // twice, plus a bit of overhead (one read during 894 // verification, one read of each byte for installation, plus 895 // extra access to things like the zip central directory). 896 // This estimate of the completion becomes 100% when we've 897 // transferred ~2.13 (=100/47) times the package size. 898 int percent = (int)(xfer * 47LL / (sz ? sz : 1)); 899 if (percent != last_percent) { 900 printf("\rserving: '%s' (~%d%%) ", fn, percent); 901 fflush(stdout); 902 last_percent = percent; 903 } 904 } 905 906 printf("\rTotal xfer: %.2fx%*s\n", (double)xfer / (sz ? sz : 1), (int)strlen(fn)+10, ""); 907 908 done: 909 if (fd >= 0) adb_close(fd); 910 free(data); 911 return status; 912} 913 914/** 915 * Run ppp in "notty" mode against a resource listed as the first parameter 916 * eg: 917 * 918 * ppp dev:/dev/omap_csmi_tty0 <ppp options> 919 * 920 */ 921static int ppp(int argc, const char** argv) { 922#if defined(_WIN32) 923 fprintf(stderr, "error: adb %s not implemented on Win32\n", argv[0]); 924 return -1; 925#else 926 if (argc < 2) { 927 fprintf(stderr, "usage: adb %s <adb service name> [ppp opts]\n", 928 argv[0]); 929 930 return 1; 931 } 932 933 const char* adb_service_name = argv[1]; 934 std::string error; 935 int fd = adb_connect(adb_service_name, &error); 936 if (fd < 0) { 937 fprintf(stderr,"Error: Could not open adb service: %s. Error: %s\n", 938 adb_service_name, error.c_str()); 939 return 1; 940 } 941 942 pid_t pid = fork(); 943 944 if (pid < 0) { 945 perror("from fork()"); 946 return 1; 947 } else if (pid == 0) { 948 int err; 949 int i; 950 const char **ppp_args; 951 952 // copy args 953 ppp_args = (const char **) alloca(sizeof(char *) * argc + 1); 954 ppp_args[0] = "pppd"; 955 for (i = 2 ; i < argc ; i++) { 956 //argv[2] and beyond become ppp_args[1] and beyond 957 ppp_args[i - 1] = argv[i]; 958 } 959 ppp_args[i-1] = NULL; 960 961 // child side 962 963 dup2(fd, STDIN_FILENO); 964 dup2(fd, STDOUT_FILENO); 965 adb_close(STDERR_FILENO); 966 adb_close(fd); 967 968 err = execvp("pppd", (char * const *)ppp_args); 969 970 if (err < 0) { 971 perror("execing pppd"); 972 } 973 exit(-1); 974 } else { 975 // parent side 976 977 adb_close(fd); 978 return 0; 979 } 980#endif /* !defined(_WIN32) */ 981} 982 983static bool wait_for_device(const char* service, TransportType t, const char* serial) { 984 // Was the caller vague about what they'd like us to wait for? 985 // If so, check they weren't more specific in their choice of transport type. 986 if (strcmp(service, "wait-for-device") == 0) { 987 if (t == kTransportUsb) { 988 service = "wait-for-usb"; 989 } else if (t == kTransportLocal) { 990 service = "wait-for-local"; 991 } else { 992 service = "wait-for-any"; 993 } 994 } 995 996 std::string cmd = format_host_command(service, t, serial); 997 return adb_command(cmd); 998} 999 1000// Connects to the device "shell" service with |command| and prints the 1001// resulting output. 1002static int send_shell_command(TransportType transport_type, const char* serial, 1003 const std::string& command, 1004 bool disable_shell_protocol) { 1005 // Only use shell protocol if it's supported and the caller doesn't want 1006 // to explicitly disable it. 1007 bool use_shell_protocol = false; 1008 if (!disable_shell_protocol) { 1009 FeatureSet features = GetFeatureSet(transport_type, serial); 1010 use_shell_protocol = CanUseFeature(features, kFeatureShell2); 1011 } 1012 1013 std::string service_string = ShellServiceString(use_shell_protocol, "", 1014 command); 1015 1016 int fd; 1017 while (true) { 1018 std::string error; 1019 fd = adb_connect(service_string, &error); 1020 if (fd >= 0) { 1021 break; 1022 } 1023 fprintf(stderr,"- waiting for device -\n"); 1024 adb_sleep_ms(1000); 1025 wait_for_device("wait-for-device", transport_type, serial); 1026 } 1027 1028 int exit_code = read_and_dump(fd, use_shell_protocol); 1029 1030 if (adb_close(fd) < 0) { 1031 PLOG(ERROR) << "failure closing FD " << fd; 1032 } 1033 1034 return exit_code; 1035} 1036 1037static int logcat(TransportType transport, const char* serial, int argc, const char** argv) { 1038 char* log_tags = getenv("ANDROID_LOG_TAGS"); 1039 std::string quoted = escape_arg(log_tags == nullptr ? "" : log_tags); 1040 1041 std::string cmd = "export ANDROID_LOG_TAGS=\"" + quoted + "\"; exec logcat"; 1042 1043 if (!strcmp(argv[0], "longcat")) { 1044 cmd += " -v long"; 1045 } 1046 1047 --argc; 1048 ++argv; 1049 while (argc-- > 0) { 1050 cmd += " " + escape_arg(*argv++); 1051 } 1052 1053 // No need for shell protocol with logcat, always disable for simplicity. 1054 return send_shell_command(transport, serial, cmd, true); 1055} 1056 1057static int backup(int argc, const char** argv) { 1058 const char* filename = "backup.ab"; 1059 1060 /* find, extract, and use any -f argument */ 1061 for (int i = 1; i < argc; i++) { 1062 if (!strcmp("-f", argv[i])) { 1063 if (i == argc-1) { 1064 fprintf(stderr, "adb: -f passed with no filename\n"); 1065 return usage(); 1066 } 1067 filename = argv[i+1]; 1068 for (int j = i+2; j <= argc; ) { 1069 argv[i++] = argv[j++]; 1070 } 1071 argc -= 2; 1072 argv[argc] = NULL; 1073 } 1074 } 1075 1076 /* bare "adb backup" or "adb backup -f filename" are not valid invocations */ 1077 if (argc < 2) return usage(); 1078 1079 adb_unlink(filename); 1080 int outFd = adb_creat(filename, 0640); 1081 if (outFd < 0) { 1082 fprintf(stderr, "adb: unable to open file %s\n", filename); 1083 return -1; 1084 } 1085 1086 std::string cmd = "backup:"; 1087 --argc; 1088 ++argv; 1089 while (argc-- > 0) { 1090 cmd += " " + escape_arg(*argv++); 1091 } 1092 1093 D("backup. filename=%s cmd=%s", filename, cmd.c_str()); 1094 std::string error; 1095 int fd = adb_connect(cmd, &error); 1096 if (fd < 0) { 1097 fprintf(stderr, "adb: unable to connect for backup: %s\n", error.c_str()); 1098 adb_close(outFd); 1099 return -1; 1100 } 1101 1102 printf("Now unlock your device and confirm the backup operation.\n"); 1103 copy_to_file(fd, outFd); 1104 1105 adb_close(fd); 1106 adb_close(outFd); 1107 return 0; 1108} 1109 1110static int restore(int argc, const char** argv) { 1111 if (argc != 2) return usage(); 1112 1113 const char* filename = argv[1]; 1114 int tarFd = adb_open(filename, O_RDONLY); 1115 if (tarFd < 0) { 1116 fprintf(stderr, "adb: unable to open file %s: %s\n", filename, strerror(errno)); 1117 return -1; 1118 } 1119 1120 std::string error; 1121 int fd = adb_connect("restore:", &error); 1122 if (fd < 0) { 1123 fprintf(stderr, "adb: unable to connect for restore: %s\n", error.c_str()); 1124 adb_close(tarFd); 1125 return -1; 1126 } 1127 1128 printf("Now unlock your device and confirm the restore operation.\n"); 1129 copy_to_file(tarFd, fd); 1130 1131 adb_close(fd); 1132 adb_close(tarFd); 1133 return 0; 1134} 1135 1136/* <hint> may be: 1137 * - A simple product name 1138 * e.g., "sooner" 1139 * - A relative path from the CWD to the ANDROID_PRODUCT_OUT dir 1140 * e.g., "out/target/product/sooner" 1141 * - An absolute path to the PRODUCT_OUT dir 1142 * e.g., "/src/device/out/target/product/sooner" 1143 * 1144 * Given <hint>, try to construct an absolute path to the 1145 * ANDROID_PRODUCT_OUT dir. 1146 */ 1147static std::string find_product_out_path(const std::string& hint) { 1148 if (hint.empty()) { 1149 return ""; 1150 } 1151 1152 // If it's already absolute, don't bother doing any work. 1153 if (adb_is_absolute_host_path(hint.c_str())) { 1154 return hint; 1155 } 1156 1157 // If there are any slashes in it, assume it's a relative path; 1158 // make it absolute. 1159 if (hint.find_first_of(OS_PATH_SEPARATORS) != std::string::npos) { 1160 std::string cwd; 1161 if (!getcwd(&cwd)) { 1162 fprintf(stderr, "adb: getcwd failed: %s\n", strerror(errno)); 1163 return ""; 1164 } 1165 return android::base::StringPrintf("%s%c%s", cwd.c_str(), OS_PATH_SEPARATOR, hint.c_str()); 1166 } 1167 1168 // It's a string without any slashes. Try to do something with it. 1169 // 1170 // Try to find the root of the build tree, and build a PRODUCT_OUT 1171 // path from there. 1172 char* top = getenv("ANDROID_BUILD_TOP"); 1173 if (top == nullptr) { 1174 fprintf(stderr, "adb: ANDROID_BUILD_TOP not set!\n"); 1175 return ""; 1176 } 1177 1178 std::string path = top; 1179 path += OS_PATH_SEPARATOR_STR; 1180 path += "out"; 1181 path += OS_PATH_SEPARATOR_STR; 1182 path += "target"; 1183 path += OS_PATH_SEPARATOR_STR; 1184 path += "product"; 1185 path += OS_PATH_SEPARATOR_STR; 1186 path += hint; 1187 if (!directory_exists(path)) { 1188 fprintf(stderr, "adb: Couldn't find a product dir based on -p %s; " 1189 "\"%s\" doesn't exist\n", hint.c_str(), path.c_str()); 1190 return ""; 1191 } 1192 return path; 1193} 1194 1195static void parse_push_pull_args(const char** arg, int narg, 1196 std::vector<const char*>* srcs, 1197 const char** dst, bool* copy_attrs) { 1198 *copy_attrs = false; 1199 1200 srcs->clear(); 1201 bool ignore_flags = false; 1202 while (narg > 0) { 1203 if (ignore_flags || *arg[0] != '-') { 1204 srcs->push_back(*arg); 1205 } else { 1206 if (!strcmp(*arg, "-p")) { 1207 // Silently ignore for backwards compatibility. 1208 } else if (!strcmp(*arg, "-a")) { 1209 *copy_attrs = true; 1210 } else if (!strcmp(*arg, "--")) { 1211 ignore_flags = true; 1212 } else { 1213 fprintf(stderr, "adb: unrecognized option '%s'\n", *arg); 1214 exit(1); 1215 } 1216 } 1217 ++arg; 1218 --narg; 1219 } 1220 1221 if (srcs->size() > 1) { 1222 *dst = srcs->back(); 1223 srcs->pop_back(); 1224 } 1225} 1226 1227static int adb_connect_command(const std::string& command) { 1228 std::string error; 1229 int fd = adb_connect(command, &error); 1230 if (fd < 0) { 1231 fprintf(stderr, "error: %s\n", error.c_str()); 1232 return 1; 1233 } 1234 read_and_dump(fd); 1235 adb_close(fd); 1236 return 0; 1237} 1238 1239static int adb_query_command(const std::string& command) { 1240 std::string result; 1241 std::string error; 1242 if (!adb_query(command, &result, &error)) { 1243 fprintf(stderr, "error: %s\n", error.c_str()); 1244 return 1; 1245 } 1246 printf("%s\n", result.c_str()); 1247 return 0; 1248} 1249 1250// Disallow stdin, stdout, and stderr. 1251static bool _is_valid_ack_reply_fd(const int ack_reply_fd) { 1252#ifdef _WIN32 1253 const HANDLE ack_reply_handle = cast_int_to_handle(ack_reply_fd); 1254 return (GetStdHandle(STD_INPUT_HANDLE) != ack_reply_handle) && 1255 (GetStdHandle(STD_OUTPUT_HANDLE) != ack_reply_handle) && 1256 (GetStdHandle(STD_ERROR_HANDLE) != ack_reply_handle); 1257#else 1258 return ack_reply_fd > 2; 1259#endif 1260} 1261 1262int adb_commandline(int argc, const char **argv) { 1263 int no_daemon = 0; 1264 int is_daemon = 0; 1265 int is_server = 0; 1266 int r; 1267 TransportType transport_type = kTransportAny; 1268 int ack_reply_fd = -1; 1269 1270 // If defined, this should be an absolute path to 1271 // the directory containing all of the various system images 1272 // for a particular product. If not defined, and the adb 1273 // command requires this information, then the user must 1274 // specify the path using "-p". 1275 char* ANDROID_PRODUCT_OUT = getenv("ANDROID_PRODUCT_OUT"); 1276 if (ANDROID_PRODUCT_OUT != nullptr) { 1277 gProductOutPath = ANDROID_PRODUCT_OUT; 1278 } 1279 // TODO: also try TARGET_PRODUCT/TARGET_DEVICE as a hint 1280 1281 /* Validate and assign the server port */ 1282 const char* server_port_str = getenv("ANDROID_ADB_SERVER_PORT"); 1283 int server_port = DEFAULT_ADB_PORT; 1284 if (server_port_str && strlen(server_port_str) > 0) { 1285 server_port = strtol(server_port_str, nullptr, 0); 1286 if (server_port <= 0 || server_port > 65535) { 1287 fprintf(stderr, 1288 "adb: Env var ANDROID_ADB_SERVER_PORT must be a positive number less than 65536. Got \"%s\"\n", 1289 server_port_str); 1290 return usage(); 1291 } 1292 } 1293 1294 // We need to check for -d and -e before we look at $ANDROID_SERIAL. 1295 const char* serial = nullptr; 1296 1297 while (argc > 0) { 1298 if (!strcmp(argv[0],"server")) { 1299 is_server = 1; 1300 } else if (!strcmp(argv[0],"nodaemon")) { 1301 no_daemon = 1; 1302 } else if (!strcmp(argv[0], "fork-server")) { 1303 /* this is a special flag used only when the ADB client launches the ADB Server */ 1304 is_daemon = 1; 1305 } else if (!strcmp(argv[0], "--reply-fd")) { 1306 if (argc < 2) return usage(); 1307 const char* reply_fd_str = argv[1]; 1308 argc--; 1309 argv++; 1310 ack_reply_fd = strtol(reply_fd_str, nullptr, 10); 1311 if (!_is_valid_ack_reply_fd(ack_reply_fd)) { 1312 fprintf(stderr, "adb: invalid reply fd \"%s\"\n", reply_fd_str); 1313 return usage(); 1314 } 1315 } else if (!strncmp(argv[0], "-p", 2)) { 1316 const char* product = nullptr; 1317 if (argv[0][2] == '\0') { 1318 if (argc < 2) return usage(); 1319 product = argv[1]; 1320 argc--; 1321 argv++; 1322 } else { 1323 product = argv[0] + 2; 1324 } 1325 gProductOutPath = find_product_out_path(product); 1326 if (gProductOutPath.empty()) { 1327 fprintf(stderr, "adb: could not resolve \"-p %s\"\n", product); 1328 return usage(); 1329 } 1330 } else if (argv[0][0]=='-' && argv[0][1]=='s') { 1331 if (isdigit(argv[0][2])) { 1332 serial = argv[0] + 2; 1333 } else { 1334 if (argc < 2 || argv[0][2] != '\0') return usage(); 1335 serial = argv[1]; 1336 argc--; 1337 argv++; 1338 } 1339 } else if (!strcmp(argv[0],"-d")) { 1340 transport_type = kTransportUsb; 1341 } else if (!strcmp(argv[0],"-e")) { 1342 transport_type = kTransportLocal; 1343 } else if (!strcmp(argv[0],"-a")) { 1344 gListenAll = 1; 1345 } else if (!strncmp(argv[0], "-H", 2)) { 1346 const char *hostname = NULL; 1347 if (argv[0][2] == '\0') { 1348 if (argc < 2) return usage(); 1349 hostname = argv[1]; 1350 argc--; 1351 argv++; 1352 } else { 1353 hostname = argv[0] + 2; 1354 } 1355 adb_set_tcp_name(hostname); 1356 1357 } else if (!strncmp(argv[0], "-P", 2)) { 1358 if (argv[0][2] == '\0') { 1359 if (argc < 2) return usage(); 1360 server_port_str = argv[1]; 1361 argc--; 1362 argv++; 1363 } else { 1364 server_port_str = argv[0] + 2; 1365 } 1366 if (strlen(server_port_str) > 0) { 1367 server_port = (int) strtol(server_port_str, NULL, 0); 1368 if (server_port <= 0 || server_port > 65535) { 1369 fprintf(stderr, 1370 "adb: port number must be a positive number less than 65536. Got \"%s\"\n", 1371 server_port_str); 1372 return usage(); 1373 } 1374 } else { 1375 fprintf(stderr, 1376 "adb: port number must be a positive number less than 65536. Got empty string.\n"); 1377 return usage(); 1378 } 1379 } else { 1380 /* out of recognized modifiers and flags */ 1381 break; 1382 } 1383 argc--; 1384 argv++; 1385 } 1386 1387 // If none of -d, -e, or -s were specified, try $ANDROID_SERIAL. 1388 if (transport_type == kTransportAny && serial == nullptr) { 1389 serial = getenv("ANDROID_SERIAL"); 1390 } 1391 1392 adb_set_transport(transport_type, serial); 1393 adb_set_tcp_specifics(server_port); 1394 1395 if (is_server) { 1396 if (no_daemon || is_daemon) { 1397 if (is_daemon && (ack_reply_fd == -1)) { 1398 fprintf(stderr, "reply fd for adb server to client communication not specified.\n"); 1399 return usage(); 1400 } 1401 r = adb_main(is_daemon, server_port, ack_reply_fd); 1402 } else { 1403 r = launch_server(server_port); 1404 } 1405 if (r) { 1406 fprintf(stderr,"* could not start server *\n"); 1407 } 1408 return r; 1409 } 1410 1411 if (argc == 0) { 1412 return usage(); 1413 } 1414 1415 /* handle wait-for-* prefix */ 1416 if (!strncmp(argv[0], "wait-for-", strlen("wait-for-"))) { 1417 const char* service = argv[0]; 1418 1419 if (!wait_for_device(service, transport_type, serial)) { 1420 return 1; 1421 } 1422 1423 // Allow a command to be run after wait-for-device, 1424 // e.g. 'adb wait-for-device shell'. 1425 if (argc == 1) { 1426 return 0; 1427 } 1428 1429 /* Fall through */ 1430 argc--; 1431 argv++; 1432 } 1433 1434 /* adb_connect() commands */ 1435 if (!strcmp(argv[0], "devices")) { 1436 const char *listopt; 1437 if (argc < 2) { 1438 listopt = ""; 1439 } else if (argc == 2 && !strcmp(argv[1], "-l")) { 1440 listopt = argv[1]; 1441 } else { 1442 fprintf(stderr, "Usage: adb devices [-l]\n"); 1443 return 1; 1444 } 1445 1446 std::string query = android::base::StringPrintf("host:%s%s", argv[0], listopt); 1447 printf("List of devices attached\n"); 1448 return adb_query_command(query); 1449 } 1450 else if (!strcmp(argv[0], "connect")) { 1451 if (argc != 2) { 1452 fprintf(stderr, "Usage: adb connect <host>[:<port>]\n"); 1453 return 1; 1454 } 1455 1456 std::string query = android::base::StringPrintf("host:connect:%s", argv[1]); 1457 return adb_query_command(query); 1458 } 1459 else if (!strcmp(argv[0], "disconnect")) { 1460 if (argc > 2) { 1461 fprintf(stderr, "Usage: adb disconnect [<host>[:<port>]]\n"); 1462 return 1; 1463 } 1464 1465 std::string query = android::base::StringPrintf("host:disconnect:%s", 1466 (argc == 2) ? argv[1] : ""); 1467 return adb_query_command(query); 1468 } 1469 else if (!strcmp(argv[0], "emu")) { 1470 return adb_send_emulator_command(argc, argv, serial); 1471 } 1472 else if (!strcmp(argv[0], "shell")) { 1473 return adb_shell(argc, argv, transport_type, serial); 1474 } 1475 else if (!strcmp(argv[0], "exec-in") || !strcmp(argv[0], "exec-out")) { 1476 int exec_in = !strcmp(argv[0], "exec-in"); 1477 1478 std::string cmd = "exec:"; 1479 cmd += argv[1]; 1480 argc -= 2; 1481 argv += 2; 1482 while (argc-- > 0) { 1483 cmd += " " + escape_arg(*argv++); 1484 } 1485 1486 std::string error; 1487 int fd = adb_connect(cmd, &error); 1488 if (fd < 0) { 1489 fprintf(stderr, "error: %s\n", error.c_str()); 1490 return -1; 1491 } 1492 1493 if (exec_in) { 1494 copy_to_file(STDIN_FILENO, fd); 1495 } else { 1496 copy_to_file(fd, STDOUT_FILENO); 1497 } 1498 1499 adb_close(fd); 1500 return 0; 1501 } 1502 else if (!strcmp(argv[0], "kill-server")) { 1503 std::string error; 1504 int fd = _adb_connect("host:kill", &error); 1505 if (fd == -2) { 1506 // Failed to make network connection to server. Don't output the 1507 // network error since that is expected. 1508 fprintf(stderr,"* server not running *\n"); 1509 // Successful exit code because the server is already "killed". 1510 return 0; 1511 } else if (fd == -1) { 1512 // Some other error. 1513 fprintf(stderr, "error: %s\n", error.c_str()); 1514 return 1; 1515 } else { 1516 // Successfully connected, kill command sent, okay status came back. 1517 // Server should exit() in a moment, if not already. 1518 ReadOrderlyShutdown(fd); 1519 adb_close(fd); 1520 return 0; 1521 } 1522 } 1523 else if (!strcmp(argv[0], "sideload")) { 1524 if (argc != 2) return usage(); 1525 if (adb_sideload_host(argv[1])) { 1526 return 1; 1527 } else { 1528 return 0; 1529 } 1530 } 1531 else if (!strcmp(argv[0], "tcpip") && argc > 1) { 1532 return adb_connect_command(android::base::StringPrintf("tcpip:%s", argv[1])); 1533 } 1534 else if (!strcmp(argv[0], "remount") || 1535 !strcmp(argv[0], "reboot") || 1536 !strcmp(argv[0], "reboot-bootloader") || 1537 !strcmp(argv[0], "usb") || 1538 !strcmp(argv[0], "root") || 1539 !strcmp(argv[0], "unroot") || 1540 !strcmp(argv[0], "disable-verity") || 1541 !strcmp(argv[0], "enable-verity")) { 1542 std::string command; 1543 if (!strcmp(argv[0], "reboot-bootloader")) { 1544 command = "reboot:bootloader"; 1545 } else if (argc > 1) { 1546 command = android::base::StringPrintf("%s:%s", argv[0], argv[1]); 1547 } else { 1548 command = android::base::StringPrintf("%s:", argv[0]); 1549 } 1550 return adb_connect_command(command); 1551 } 1552 else if (!strcmp(argv[0], "bugreport")) { 1553 if (argc != 1) return usage(); 1554 // No need for shell protocol with bugreport, always disable for 1555 // simplicity. 1556 return send_shell_command(transport_type, serial, "bugreport", true); 1557 } 1558 else if (!strcmp(argv[0], "forward") || !strcmp(argv[0], "reverse")) { 1559 bool reverse = !strcmp(argv[0], "reverse"); 1560 ++argv; 1561 --argc; 1562 if (argc < 1) return usage(); 1563 1564 // Determine the <host-prefix> for this command. 1565 std::string host_prefix; 1566 if (reverse) { 1567 host_prefix = "reverse"; 1568 } else { 1569 if (serial) { 1570 host_prefix = android::base::StringPrintf("host-serial:%s", serial); 1571 } else if (transport_type == kTransportUsb) { 1572 host_prefix = "host-usb"; 1573 } else if (transport_type == kTransportLocal) { 1574 host_prefix = "host-local"; 1575 } else { 1576 host_prefix = "host"; 1577 } 1578 } 1579 1580 std::string cmd; 1581 if (strcmp(argv[0], "--list") == 0) { 1582 if (argc != 1) return usage(); 1583 return adb_query_command(host_prefix + ":list-forward"); 1584 } else if (strcmp(argv[0], "--remove-all") == 0) { 1585 if (argc != 1) return usage(); 1586 cmd = host_prefix + ":killforward-all"; 1587 } else if (strcmp(argv[0], "--remove") == 0) { 1588 // forward --remove <local> 1589 if (argc != 2) return usage(); 1590 cmd = host_prefix + ":killforward:" + argv[1]; 1591 } else if (strcmp(argv[0], "--no-rebind") == 0) { 1592 // forward --no-rebind <local> <remote> 1593 if (argc != 3) return usage(); 1594 cmd = host_prefix + ":forward:norebind:" + argv[1] + ";" + argv[2]; 1595 } else { 1596 // forward <local> <remote> 1597 if (argc != 2) return usage(); 1598 cmd = host_prefix + ":forward:" + argv[0] + ";" + argv[1]; 1599 } 1600 1601 return adb_command(cmd) ? 0 : 1; 1602 } 1603 /* do_sync_*() commands */ 1604 else if (!strcmp(argv[0], "ls")) { 1605 if (argc != 2) return usage(); 1606 return do_sync_ls(argv[1]) ? 0 : 1; 1607 } 1608 else if (!strcmp(argv[0], "push")) { 1609 bool copy_attrs = false; 1610 std::vector<const char*> srcs; 1611 const char* dst = nullptr; 1612 1613 parse_push_pull_args(&argv[1], argc - 1, &srcs, &dst, ©_attrs); 1614 if (srcs.empty() || !dst) return usage(); 1615 return do_sync_push(srcs, dst) ? 0 : 1; 1616 } 1617 else if (!strcmp(argv[0], "pull")) { 1618 bool copy_attrs = false; 1619 std::vector<const char*> srcs; 1620 const char* dst = "."; 1621 1622 parse_push_pull_args(&argv[1], argc - 1, &srcs, &dst, ©_attrs); 1623 if (srcs.empty()) return usage(); 1624 return do_sync_pull(srcs, dst, copy_attrs) ? 0 : 1; 1625 } 1626 else if (!strcmp(argv[0], "install")) { 1627 if (argc < 2) return usage(); 1628 FeatureSet features = GetFeatureSet(transport_type, serial); 1629 if (CanUseFeature(features, kFeatureCmd)) { 1630 return install_app(transport_type, serial, argc, argv); 1631 } 1632 return install_app_legacy(transport_type, serial, argc, argv); 1633 } 1634 else if (!strcmp(argv[0], "install-multiple")) { 1635 if (argc < 2) return usage(); 1636 return install_multiple_app(transport_type, serial, argc, argv); 1637 } 1638 else if (!strcmp(argv[0], "uninstall")) { 1639 if (argc < 2) return usage(); 1640 FeatureSet features = GetFeatureSet(transport_type, serial); 1641 if (CanUseFeature(features, kFeatureCmd)) { 1642 return uninstall_app(transport_type, serial, argc, argv); 1643 } 1644 return uninstall_app_legacy(transport_type, serial, argc, argv); 1645 } 1646 else if (!strcmp(argv[0], "sync")) { 1647 std::string src; 1648 bool list_only = false; 1649 if (argc < 2) { 1650 // No local path was specified. 1651 src = ""; 1652 } else if (argc >= 2 && strcmp(argv[1], "-l") == 0) { 1653 list_only = true; 1654 if (argc == 3) { 1655 src = argv[2]; 1656 } else { 1657 src = ""; 1658 } 1659 } else if (argc == 2) { 1660 // A local path or "android"/"data" arg was specified. 1661 src = argv[1]; 1662 } else { 1663 return usage(); 1664 } 1665 1666 if (src != "" && 1667 src != "system" && src != "data" && src != "vendor" && src != "oem") { 1668 return usage(); 1669 } 1670 1671 std::string system_src_path = product_file("system"); 1672 std::string data_src_path = product_file("data"); 1673 std::string vendor_src_path = product_file("vendor"); 1674 std::string oem_src_path = product_file("oem"); 1675 1676 bool okay = true; 1677 if (okay && (src.empty() || src == "system")) { 1678 okay = do_sync_sync(system_src_path, "/system", list_only); 1679 } 1680 if (okay && (src.empty() || src == "vendor") && directory_exists(vendor_src_path)) { 1681 okay = do_sync_sync(vendor_src_path, "/vendor", list_only); 1682 } 1683 if (okay && (src.empty() || src == "oem") && directory_exists(oem_src_path)) { 1684 okay = do_sync_sync(oem_src_path, "/oem", list_only); 1685 } 1686 if (okay && (src.empty() || src == "data")) { 1687 okay = do_sync_sync(data_src_path, "/data", list_only); 1688 } 1689 return okay ? 0 : 1; 1690 } 1691 /* passthrough commands */ 1692 else if (!strcmp(argv[0],"get-state") || 1693 !strcmp(argv[0],"get-serialno") || 1694 !strcmp(argv[0],"get-devpath")) 1695 { 1696 return adb_query_command(format_host_command(argv[0], transport_type, serial)); 1697 } 1698 /* other commands */ 1699 else if (!strcmp(argv[0],"logcat") || !strcmp(argv[0],"lolcat") || !strcmp(argv[0],"longcat")) { 1700 return logcat(transport_type, serial, argc, argv); 1701 } 1702 else if (!strcmp(argv[0],"ppp")) { 1703 return ppp(argc, argv); 1704 } 1705 else if (!strcmp(argv[0], "start-server")) { 1706 std::string error; 1707 const int result = adb_connect("host:start-server", &error); 1708 if (result < 0) { 1709 fprintf(stderr, "error: %s\n", error.c_str()); 1710 } 1711 return result; 1712 } 1713 else if (!strcmp(argv[0], "backup")) { 1714 return backup(argc, argv); 1715 } 1716 else if (!strcmp(argv[0], "restore")) { 1717 return restore(argc, argv); 1718 } 1719 else if (!strcmp(argv[0], "keygen")) { 1720 if (argc < 2) return usage(); 1721 // Always print key generation information for keygen command. 1722 adb_trace_enable(AUTH); 1723 return adb_auth_keygen(argv[1]); 1724 } 1725 else if (!strcmp(argv[0], "jdwp")) { 1726 return adb_connect_command("jdwp"); 1727 } 1728 /* "adb /?" is a common idiom under Windows */ 1729 else if (!strcmp(argv[0], "help") || !strcmp(argv[0], "/?")) { 1730 help(); 1731 return 0; 1732 } 1733 else if (!strcmp(argv[0], "version")) { 1734 fprintf(stdout, "%s", adb_version().c_str()); 1735 return 0; 1736 } 1737 else if (!strcmp(argv[0], "features")) { 1738 // Only list the features common to both the adb client and the device. 1739 FeatureSet features = GetFeatureSet(transport_type, serial); 1740 for (const std::string& name : features) { 1741 if (CanUseFeature(features, name)) { 1742 printf("%s\n", name.c_str()); 1743 } 1744 } 1745 return 0; 1746 } 1747 1748 usage(); 1749 return 1; 1750} 1751 1752static int uninstall_app(TransportType transport, const char* serial, int argc, const char** argv) { 1753 // 'adb uninstall' takes the same arguments as 'cmd package uninstall' on device 1754 std::string cmd = "cmd package"; 1755 while (argc-- > 0) { 1756 // deny the '-k' option until the remaining data/cache can be removed with adb/UI 1757 if (strcmp(*argv, "-k") == 0) { 1758 printf( 1759 "The -k option uninstalls the application while retaining the data/cache.\n" 1760 "At the moment, there is no way to remove the remaining data.\n" 1761 "You will have to reinstall the application with the same signature, and fully uninstall it.\n" 1762 "If you truly wish to continue, execute 'adb shell cmd package uninstall -k'.\n"); 1763 return EXIT_FAILURE; 1764 } 1765 cmd += " " + escape_arg(*argv++); 1766 } 1767 1768 return send_shell_command(transport, serial, cmd, false); 1769} 1770 1771static int install_app(TransportType transport, const char* serial, int argc, const char** argv) { 1772 // The last argument must be the APK file 1773 const char* file = argv[argc - 1]; 1774 const char* dot = strrchr(file, '.'); 1775 bool found_apk = false; 1776 struct stat sb; 1777 if (dot && !strcasecmp(dot, ".apk")) { 1778 if (stat(file, &sb) == -1 || !S_ISREG(sb.st_mode)) { 1779 fprintf(stderr, "Invalid APK file: %s\n", file); 1780 return EXIT_FAILURE; 1781 } 1782 found_apk = true; 1783 } 1784 1785 if (!found_apk) { 1786 fprintf(stderr, "Missing APK file\n"); 1787 return EXIT_FAILURE; 1788 } 1789 1790 int localFd = adb_open(file, O_RDONLY); 1791 if (localFd < 0) { 1792 fprintf(stderr, "Failed to open %s: %s\n", file, strerror(errno)); 1793 return 1; 1794 } 1795 1796 std::string error; 1797 std::string cmd = "exec:cmd package"; 1798 1799 // don't copy the APK name, but, copy the rest of the arguments as-is 1800 while (argc-- > 1) { 1801 cmd += " " + escape_arg(std::string(*argv++)); 1802 } 1803 1804 // add size parameter [required for streaming installs] 1805 // do last to override any user specified value 1806 cmd += " " + android::base::StringPrintf("-S %" PRIu64, static_cast<uint64_t>(sb.st_size)); 1807 1808 int remoteFd = adb_connect(cmd, &error); 1809 if (remoteFd < 0) { 1810 fprintf(stderr, "Connect error for write: %s\n", error.c_str()); 1811 adb_close(localFd); 1812 return 1; 1813 } 1814 1815 char buf[BUFSIZ]; 1816 copy_to_file(localFd, remoteFd); 1817 read_status_line(remoteFd, buf, sizeof(buf)); 1818 1819 adb_close(localFd); 1820 adb_close(remoteFd); 1821 1822 if (strncmp("Success", buf, 7)) { 1823 fprintf(stderr, "Failed to write %s\n", file); 1824 fputs(buf, stderr); 1825 return 1; 1826 } 1827 fputs(buf, stderr); 1828 return 0; 1829} 1830 1831static int install_multiple_app(TransportType transport, const char* serial, int argc, 1832 const char** argv) 1833{ 1834 int i; 1835 struct stat sb; 1836 uint64_t total_size = 0; 1837 1838 // Find all APK arguments starting at end. 1839 // All other arguments passed through verbatim. 1840 int first_apk = -1; 1841 for (i = argc - 1; i >= 0; i--) { 1842 const char* file = argv[i]; 1843 const char* dot = strrchr(file, '.'); 1844 if (dot && !strcasecmp(dot, ".apk")) { 1845 if (stat(file, &sb) == -1 || !S_ISREG(sb.st_mode)) { 1846 fprintf(stderr, "Invalid APK file: %s\n", file); 1847 return EXIT_FAILURE; 1848 } 1849 1850 total_size += sb.st_size; 1851 first_apk = i; 1852 } else { 1853 break; 1854 } 1855 } 1856 1857 if (first_apk == -1) { 1858 fprintf(stderr, "Missing APK file\n"); 1859 return 1; 1860 } 1861 1862 std::string cmd = android::base::StringPrintf("exec:pm install-create -S %" PRIu64, total_size); 1863 for (i = 1; i < first_apk; i++) { 1864 cmd += " " + escape_arg(argv[i]); 1865 } 1866 1867 // Create install session 1868 std::string error; 1869 int fd = adb_connect(cmd, &error); 1870 if (fd < 0) { 1871 fprintf(stderr, "Connect error for create: %s\n", error.c_str()); 1872 return EXIT_FAILURE; 1873 } 1874 char buf[BUFSIZ]; 1875 read_status_line(fd, buf, sizeof(buf)); 1876 adb_close(fd); 1877 1878 int session_id = -1; 1879 if (!strncmp("Success", buf, 7)) { 1880 char* start = strrchr(buf, '['); 1881 char* end = strrchr(buf, ']'); 1882 if (start && end) { 1883 *end = '\0'; 1884 session_id = strtol(start + 1, NULL, 10); 1885 } 1886 } 1887 if (session_id < 0) { 1888 fprintf(stderr, "Failed to create session\n"); 1889 fputs(buf, stderr); 1890 return EXIT_FAILURE; 1891 } 1892 1893 // Valid session, now stream the APKs 1894 int success = 1; 1895 for (i = first_apk; i < argc; i++) { 1896 const char* file = argv[i]; 1897 if (stat(file, &sb) == -1) { 1898 fprintf(stderr, "Failed to stat %s\n", file); 1899 success = 0; 1900 goto finalize_session; 1901 } 1902 1903 std::string cmd = android::base::StringPrintf( 1904 "exec:pm install-write -S %" PRIu64 " %d %d_%s -", 1905 static_cast<uint64_t>(sb.st_size), session_id, i, adb_basename(file).c_str()); 1906 1907 int localFd = adb_open(file, O_RDONLY); 1908 if (localFd < 0) { 1909 fprintf(stderr, "Failed to open %s: %s\n", file, strerror(errno)); 1910 success = 0; 1911 goto finalize_session; 1912 } 1913 1914 std::string error; 1915 int remoteFd = adb_connect(cmd, &error); 1916 if (remoteFd < 0) { 1917 fprintf(stderr, "Connect error for write: %s\n", error.c_str()); 1918 adb_close(localFd); 1919 success = 0; 1920 goto finalize_session; 1921 } 1922 1923 copy_to_file(localFd, remoteFd); 1924 read_status_line(remoteFd, buf, sizeof(buf)); 1925 1926 adb_close(localFd); 1927 adb_close(remoteFd); 1928 1929 if (strncmp("Success", buf, 7)) { 1930 fprintf(stderr, "Failed to write %s\n", file); 1931 fputs(buf, stderr); 1932 success = 0; 1933 goto finalize_session; 1934 } 1935 } 1936 1937finalize_session: 1938 // Commit session if we streamed everything okay; otherwise abandon 1939 std::string service = 1940 android::base::StringPrintf("exec:pm install-%s %d", 1941 success ? "commit" : "abandon", session_id); 1942 fd = adb_connect(service, &error); 1943 if (fd < 0) { 1944 fprintf(stderr, "Connect error for finalize: %s\n", error.c_str()); 1945 return EXIT_FAILURE; 1946 } 1947 read_status_line(fd, buf, sizeof(buf)); 1948 adb_close(fd); 1949 1950 if (!strncmp("Success", buf, 7)) { 1951 fputs(buf, stderr); 1952 return 0; 1953 } else { 1954 fprintf(stderr, "Failed to finalize session\n"); 1955 fputs(buf, stderr); 1956 return EXIT_FAILURE; 1957 } 1958} 1959 1960static int pm_command(TransportType transport, const char* serial, int argc, const char** argv) { 1961 std::string cmd = "pm"; 1962 1963 while (argc-- > 0) { 1964 cmd += " " + escape_arg(*argv++); 1965 } 1966 1967 return send_shell_command(transport, serial, cmd, false); 1968} 1969 1970static int uninstall_app_legacy(TransportType transport, const char* serial, int argc, const char** argv) { 1971 /* if the user choose the -k option, we refuse to do it until devices are 1972 out with the option to uninstall the remaining data somehow (adb/ui) */ 1973 int i; 1974 for (i = 1; i < argc; i++) { 1975 if (!strcmp(argv[i], "-k")) { 1976 printf( 1977 "The -k option uninstalls the application while retaining the data/cache.\n" 1978 "At the moment, there is no way to remove the remaining data.\n" 1979 "You will have to reinstall the application with the same signature, and fully uninstall it.\n" 1980 "If you truly wish to continue, execute 'adb shell pm uninstall -k'\n."); 1981 return EXIT_FAILURE; 1982 } 1983 } 1984 1985 /* 'adb uninstall' takes the same arguments as 'pm uninstall' on device */ 1986 return pm_command(transport, serial, argc, argv); 1987} 1988 1989static int delete_file(TransportType transport, const char* serial, const std::string& filename) { 1990 std::string cmd = "rm -f " + escape_arg(filename); 1991 return send_shell_command(transport, serial, cmd, false); 1992} 1993 1994static int install_app_legacy(TransportType transport, const char* serial, int argc, const char** argv) { 1995 static const char *const DATA_DEST = "/data/local/tmp/%s"; 1996 static const char *const SD_DEST = "/sdcard/tmp/%s"; 1997 const char* where = DATA_DEST; 1998 int i; 1999 struct stat sb; 2000 2001 for (i = 1; i < argc; i++) { 2002 if (!strcmp(argv[i], "-s")) { 2003 where = SD_DEST; 2004 } 2005 } 2006 2007 // Find last APK argument. 2008 // All other arguments passed through verbatim. 2009 int last_apk = -1; 2010 for (i = argc - 1; i >= 0; i--) { 2011 const char* file = argv[i]; 2012 const char* dot = strrchr(file, '.'); 2013 if (dot && !strcasecmp(dot, ".apk")) { 2014 if (stat(file, &sb) == -1 || !S_ISREG(sb.st_mode)) { 2015 fprintf(stderr, "Invalid APK file: %s\n", file); 2016 return EXIT_FAILURE; 2017 } 2018 2019 last_apk = i; 2020 break; 2021 } 2022 } 2023 2024 if (last_apk == -1) { 2025 fprintf(stderr, "Missing APK file\n"); 2026 return EXIT_FAILURE; 2027 } 2028 2029 int result = -1; 2030 std::vector<const char*> apk_file = {argv[last_apk]}; 2031 std::string apk_dest = android::base::StringPrintf( 2032 where, adb_basename(argv[last_apk]).c_str()); 2033 if (!do_sync_push(apk_file, apk_dest.c_str())) goto cleanup_apk; 2034 argv[last_apk] = apk_dest.c_str(); /* destination name, not source location */ 2035 result = pm_command(transport, serial, argc, argv); 2036 2037cleanup_apk: 2038 delete_file(transport, serial, apk_dest); 2039 return result; 2040} 2041