adb.c revision d0eacb8aee77f01edadf525019f8dd1e43671ce7
102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project/* 202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * Copyright (C) 2007 The Android Open Source Project 302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * 402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * Licensed under the Apache License, Version 2.0 (the "License"); 502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * you may not use this file except in compliance with the License. 602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * You may obtain a copy of the License at 702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * 802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * http://www.apache.org/licenses/LICENSE-2.0 902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * 1002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * Unless required by applicable law or agreed to in writing, software 1102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * distributed under the License is distributed on an "AS IS" BASIS, 1202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 1302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * See the License for the specific language governing permissions and 1402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * limitations under the License. 1502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project */ 1602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 1702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#define TRACE_TAG TRACE_ADB 1802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 1902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <stdio.h> 2002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <stdlib.h> 2102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <ctype.h> 2202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <stdarg.h> 2302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <errno.h> 2402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <string.h> 2502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <time.h> 2602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <sys/time.h> 2702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 2802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include "sysdeps.h" 2902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include "adb.h" 3002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 3102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#if !ADB_HOST 3202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <private/android_filesystem_config.h> 3302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <linux/capability.h> 3402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include <linux/prctl.h> 3502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#else 3602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#include "usb_vendors.h" 3702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#endif 3802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 3902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 4002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectint HOST = 0; 4102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 4202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic const char *adb_device_banner = "device"; 4302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 4402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid fatal(const char *fmt, ...) 4502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 4602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project va_list ap; 4702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project va_start(ap, fmt); 4802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fprintf(stderr, "error: "); 4902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project vfprintf(stderr, fmt, ap); 5002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fprintf(stderr, "\n"); 5102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project va_end(ap); 5202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project exit(-1); 5302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 5402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 5502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid fatal_errno(const char *fmt, ...) 5602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 5702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project va_list ap; 5802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project va_start(ap, fmt); 5902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fprintf(stderr, "error: %s: ", strerror(errno)); 6002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project vfprintf(stderr, fmt, ap); 6102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fprintf(stderr, "\n"); 6202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project va_end(ap); 6302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project exit(-1); 6402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 6502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 6602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectint adb_trace_mask; 6702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 6802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project/* read a comma/space/colum/semi-column separated list of tags 6902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * from the ADB_TRACE environment variable and build the trace 7002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * mask from it. note that '1' and 'all' are special cases to 7102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project * enable all tracing 7202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project */ 7302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid adb_trace_init(void) 7402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 7502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project const char* p = getenv("ADB_TRACE"); 7602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project const char* q; 7702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 7802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project static const struct { 7902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project const char* tag; 8002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int flag; 8102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } tags[] = { 8202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "1", 0 }, 8302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "all", 0 }, 8402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "adb", TRACE_ADB }, 8502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "sockets", TRACE_SOCKETS }, 8602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "packets", TRACE_PACKETS }, 8702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "rwx", TRACE_RWX }, 8802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "usb", TRACE_USB }, 8902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "sync", TRACE_SYNC }, 9002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "sysdeps", TRACE_SYSDEPS }, 9102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "transport", TRACE_TRANSPORT }, 9202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { "jdwp", TRACE_JDWP }, 9302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { NULL, 0 } 9402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project }; 9502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 9602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (p == NULL) 9702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 9802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 9902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project /* use a comma/column/semi-colum/space separated list */ 10002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project while (*p) { 10102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int len, tagn; 10202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 10302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project q = strpbrk(p, " ,:;"); 10402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (q == NULL) { 10502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project q = p + strlen(p); 10602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 10702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project len = q - p; 10802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 10902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project for (tagn = 0; tags[tagn].tag != NULL; tagn++) 11002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { 11102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int taglen = strlen(tags[tagn].tag); 11202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 11302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (len == taglen && !memcmp(tags[tagn].tag, p, len) ) 11402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project { 11502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int flag = tags[tagn].flag; 11602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (flag == 0) { 11702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project adb_trace_mask = ~0; 11802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 11902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 12002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project adb_trace_mask |= (1 << flag); 12102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project break; 12202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 12302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 12402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p = q; 12502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (*p) 12602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p++; 12702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 12802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 12902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 13002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 13102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectapacket *get_apacket(void) 13202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 13302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project apacket *p = malloc(sizeof(apacket)); 13402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(p == 0) fatal("failed to allocate an apacket"); 13502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project memset(p, 0, sizeof(apacket) - MAX_PAYLOAD); 13602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return p; 13702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 13802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 13902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid put_apacket(apacket *p) 14002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 14102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free(p); 14202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 14302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 14402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid handle_online(void) 14502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 14602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("adb: online\n"); 14702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 14802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 14902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid handle_offline(atransport *t) 15002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 15102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("adb: offline\n"); 15202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project //Close the associated usb 15302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project run_transport_disconnects(t); 15402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 15502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 15602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#if TRACE_PACKETS 15702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#define DUMPMAX 32 15802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid print_packet(const char *label, apacket *p) 15902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 16002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project char *tag; 16102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project char *x; 16202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project unsigned count; 16302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 16402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project switch(p->msg.command){ 16502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_SYNC: tag = "SYNC"; break; 16602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_CNXN: tag = "CNXN" ; break; 16702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_OPEN: tag = "OPEN"; break; 16802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_OKAY: tag = "OKAY"; break; 16902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_CLSE: tag = "CLSE"; break; 17002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_WRTE: tag = "WRTE"; break; 17102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project default: tag = "????"; break; 17202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 17302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 17402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fprintf(stderr, "%s: %s %08x %08x %04x \"", 17502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project label, tag, p->msg.arg0, p->msg.arg1, p->msg.data_length); 17602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project count = p->msg.data_length; 17702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project x = (char*) p->data; 17802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(count > DUMPMAX) { 17902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project count = DUMPMAX; 18002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project tag = "\n"; 18102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else { 18202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project tag = "\"\n"; 18302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 18402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project while(count-- > 0){ 18502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((*x >= ' ') && (*x < 127)) { 18602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fputc(*x, stderr); 18702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else { 18802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fputc('.', stderr); 18902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 19002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project x++; 19102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 19202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fprintf(stderr, tag); 19302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 19402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#endif 19502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 19602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void send_ready(unsigned local, unsigned remote, atransport *t) 19702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 19802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("Calling send_ready \n"); 19902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project apacket *p = get_apacket(); 20002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->msg.command = A_OKAY; 20102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->msg.arg0 = local; 20202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->msg.arg1 = remote; 20302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_packet(p, t); 20402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 20502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 20602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void send_close(unsigned local, unsigned remote, atransport *t) 20702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 20802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("Calling send_close \n"); 20902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project apacket *p = get_apacket(); 21002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->msg.command = A_CLSE; 21102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->msg.arg0 = local; 21202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->msg.arg1 = remote; 21302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_packet(p, t); 21402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 21502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 21602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void send_connect(atransport *t) 21702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 21802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("Calling send_connect \n"); 21902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project apacket *cp = get_apacket(); 22002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project cp->msg.command = A_CNXN; 22102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project cp->msg.arg0 = A_VERSION; 22202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project cp->msg.arg1 = MAX_PAYLOAD; 22302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project snprintf((char*) cp->data, sizeof cp->data, "%s::", 22402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project HOST ? "host" : adb_device_banner); 22502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project cp->msg.data_length = strlen((char*) cp->data) + 1; 22602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_packet(cp, t); 22702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#if ADB_HOST 22802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project /* XXX why sleep here? */ 22902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project // allow the device some time to respond to the connect message 23002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project adb_sleep_ms(1000); 23102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#endif 23202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 23302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 23402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic char *connection_state_name(atransport *t) 23502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 23602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (t == NULL) { 23702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return "unknown"; 23802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 23902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 24002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project switch(t->connection_state) { 24102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case CS_BOOTLOADER: 24202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return "bootloader"; 24302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case CS_DEVICE: 24402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return "device"; 24502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case CS_OFFLINE: 24602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return "offline"; 24702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project default: 24802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return "unknown"; 24902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 25002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 25102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 25202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid parse_banner(char *banner, atransport *t) 25302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 25402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project char *type, *product, *end; 25502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 25602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("parse_banner: %s\n", banner); 25702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project type = banner; 25802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project product = strchr(type, ':'); 25902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(product) { 26002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project *product++ = 0; 26102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else { 26202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project product = ""; 26302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 26402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 26502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project /* remove trailing ':' */ 26602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project end = strchr(product, ':'); 26702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(end) *end = 0; 26802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 26902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project /* save product name in device structure */ 27002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (t->product == NULL) { 27102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->product = strdup(product); 27202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else if (strcmp(product, t->product) != 0) { 27302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free(t->product); 27402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->product = strdup(product); 27502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 27602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 27702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(!strcmp(type, "bootloader")){ 27802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("setting connection_state to CS_BOOTLOADER\n"); 27902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->connection_state = CS_BOOTLOADER; 28002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project update_transports(); 28102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 28202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 28302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 28402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(!strcmp(type, "device")) { 28502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("setting connection_state to CS_DEVICE\n"); 28602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->connection_state = CS_DEVICE; 28702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project update_transports(); 28802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 28902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 29002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 29102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(!strcmp(type, "recovery")) { 29202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("setting connection_state to CS_RECOVERY\n"); 29302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->connection_state = CS_RECOVERY; 29402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project update_transports(); 29502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 29602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 29702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 29802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->connection_state = CS_HOST; 29902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 30002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 30102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectvoid handle_packet(apacket *p, atransport *t) 30202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 30302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project asocket *s; 30402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 30502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("handle_packet() %d\n", p->msg.command); 30602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 30702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project print_packet("recv", p); 30802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 30902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project switch(p->msg.command){ 31002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_SYNC: 31102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(p->msg.arg0){ 31202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_packet(p, t); 31302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(HOST) send_connect(t); 31402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else { 31502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->connection_state = CS_OFFLINE; 31602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project handle_offline(t); 31702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_packet(p, t); 31802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 31902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 32002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 32102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_CNXN: /* CONNECT(version, maxdata, "system-id-string") */ 32202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project /* XXX verify version, etc */ 32302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(t->connection_state != CS_OFFLINE) { 32402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project t->connection_state = CS_OFFLINE; 32502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project handle_offline(t); 32602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 32702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project parse_banner((char*) p->data, t); 32802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project handle_online(); 32902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(!HOST) send_connect(t); 33002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project break; 33102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 33202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_OPEN: /* OPEN(local-id, 0, "destination") */ 33302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(t->connection_state != CS_OFFLINE) { 33402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project char *name = (char*) p->data; 33502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project name[p->msg.data_length > 0 ? p->msg.data_length - 1 : 0] = 0; 33602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s = create_local_service_socket(name); 33702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(s == 0) { 33802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_close(0, p->msg.arg0, t); 33902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else { 34002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->peer = create_remote_socket(p->msg.arg0, t); 34102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->peer->peer = s; 34202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_ready(s->id, s->peer->id, t); 34302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->ready(s); 34402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 34502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 34602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project break; 34702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 34802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_OKAY: /* READY(local-id, remote-id, "") */ 34902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(t->connection_state != CS_OFFLINE) { 35002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((s = find_local_socket(p->msg.arg1))) { 35102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(s->peer == 0) { 35202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->peer = create_remote_socket(p->msg.arg0, t); 35302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->peer->peer = s; 35402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 35502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->ready(s); 35602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 35702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 35802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project break; 35902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 36002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_CLSE: /* CLOSE(local-id, remote-id, "") */ 36102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(t->connection_state != CS_OFFLINE) { 36202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((s = find_local_socket(p->msg.arg1))) { 36302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->close(s); 36402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 36502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 36602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project break; 36702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 36802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project case A_WRTE: 36902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(t->connection_state != CS_OFFLINE) { 37002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((s = find_local_socket(p->msg.arg1))) { 37102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project unsigned rid = p->msg.arg0; 37202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project p->len = p->msg.data_length; 37302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 37402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(s->enqueue(s, p) == 0) { 37502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project D("Enqueue the socket\n"); 37602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project send_ready(s->id, rid, t); 37702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 37802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 37902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 38002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 38102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project break; 38202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 38302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project default: 38402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project printf("handle_packet: what is %08x?!\n", p->msg.command); 38502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 38602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 38702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project put_apacket(p); 38802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 38902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 39002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectalistener listener_list = { 39102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project .next = &listener_list, 39202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project .prev = &listener_list, 39302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project}; 39402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 39502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void ss_listener_event_func(int _fd, unsigned ev, void *_l) 39602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 39702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project asocket *s; 39802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 39902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(ev & FDE_READ) { 40002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project struct sockaddr addr; 40102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project socklen_t alen; 40202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int fd; 40302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 40402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project alen = sizeof(addr); 40502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fd = adb_socket_accept(_fd, &addr, &alen); 40602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(fd < 0) return; 40702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 40802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project adb_socket_setbufsize(fd, CHUNK_SIZE); 40902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 41002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s = create_local_socket(fd); 41102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(s) { 41202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project connect_to_smartsocket(s); 41302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 41402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 41502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 41602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project adb_close(fd); 41702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 41802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 41902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 42002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void listener_event_func(int _fd, unsigned ev, void *_l) 42102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 42202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project alistener *l = _l; 42302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project asocket *s; 42402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 42502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(ev & FDE_READ) { 42602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project struct sockaddr addr; 42702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project socklen_t alen; 42802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int fd; 42902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 43002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project alen = sizeof(addr); 43102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fd = adb_socket_accept(_fd, &addr, &alen); 43202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(fd < 0) return; 43302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 43402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s = create_local_socket(fd); 43502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(s) { 43602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project s->transport = l->transport; 43702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project connect_to_remote(s, l->connect_to); 43802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return; 43902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 44002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 44102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project adb_close(fd); 44202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 44302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 44402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 44502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void free_listener(alistener* l) 44602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 44702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (l->next) { 44802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->next->prev = l->prev; 44902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->prev->next = l->next; 45002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->next = l->prev = l; 45102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 45202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 45302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project // closes the corresponding fd 45402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project fdevent_remove(&l->fde); 45502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 45602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (l->local_name) 45702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free((char*)l->local_name); 45802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 45902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (l->connect_to) 46002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free((char*)l->connect_to); 46102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 46202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (l->transport) { 46302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project remove_transport_disconnect(l->transport, &l->disconnect); 46402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 46502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free(l); 46602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 46702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 46802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic void listener_disconnect(void* _l, atransport* t) 46902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 47002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project alistener* l = _l; 47102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 47202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free_listener(l); 47302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 47402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 47502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectint local_name_to_fd(const char *name) 47602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 47702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int port; 47802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 47902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(!strncmp("tcp:", name, 4)){ 48002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project int ret; 48102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project port = atoi(name + 4); 48202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project ret = socket_loopback_server(port, SOCK_STREAM); 48302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return ret; 48402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 48502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#ifndef HAVE_WIN32_IPC /* no Unix-domain sockets on Win32 */ 48602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project // It's non-sensical to support the "reserved" space on the adb host side 48702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(!strncmp(name, "local:", 6)) { 48802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return socket_local_server(name + 6, 48902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project ANDROID_SOCKET_NAMESPACE_ABSTRACT, SOCK_STREAM); 49002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else if(!strncmp(name, "localabstract:", 14)) { 49102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return socket_local_server(name + 14, 49202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project ANDROID_SOCKET_NAMESPACE_ABSTRACT, SOCK_STREAM); 49302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } else if(!strncmp(name, "localfilesystem:", 16)) { 49402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return socket_local_server(name + 16, 49502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project ANDROID_SOCKET_NAMESPACE_FILESYSTEM, SOCK_STREAM); 49602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 49702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 49802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project#endif 49902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project printf("unknown local portname '%s'\n", name); 50002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return -1; 50102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 50202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 50302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic int remove_listener(const char *local_name, const char *connect_to, atransport* transport) 50402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 50502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project alistener *l; 50602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 50702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project for (l = listener_list.next; l != &listener_list; l = l->next) { 50802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (!strcmp(local_name, l->local_name) && 50902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project !strcmp(connect_to, l->connect_to) && 51002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->transport && l->transport == transport) { 51102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 51202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project listener_disconnect(l, transport); 51302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return 0; 51402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 51502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 51602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 51702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return -1; 51802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project} 51902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 52002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Projectstatic int install_listener(const char *local_name, const char *connect_to, atransport* transport) 52102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project{ 52202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project alistener *l; 52302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 52402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project //printf("install_listener('%s','%s')\n", local_name, connect_to); 52502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 52602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project for(l = listener_list.next; l != &listener_list; l = l->next){ 52702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(strcmp(local_name, l->local_name) == 0) { 52802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project char *cto; 52902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 53002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project /* can't repurpose a smartsocket */ 53102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(l->connect_to[0] == '*') { 53202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return -1; 53302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 53402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 53502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project cto = strdup(connect_to); 53602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(cto == 0) { 53702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return -1; 53802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 53902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 54002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project //printf("rebinding '%s' to '%s'\n", local_name, connect_to); 54102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free((void*) l->connect_to); 54202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->connect_to = cto; 54302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if (l->transport != transport) { 54402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project remove_transport_disconnect(l->transport, &l->disconnect); 54502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->transport = transport; 54602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project add_transport_disconnect(l->transport, &l->disconnect); 54702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 54802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project return 0; 54902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 55002fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project } 55102fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 55202fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((l = calloc(1, sizeof(alistener))) == 0) goto nomem; 55302fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((l->local_name = strdup(local_name)) == 0) goto nomem; 55402fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if((l->connect_to = strdup(connect_to)) == 0) goto nomem; 55502fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 55602fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project 55702fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project l->fd = local_name_to_fd(local_name); 55802fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project if(l->fd < 0) { 55902fb0aca1189a2c1fd20806c588e9ee80d9755f8The Android Open Source Project free((void*) l->local_name); 560 free((void*) l->connect_to); 561 free(l); 562 printf("cannot bind '%s'\n", local_name); 563 return -2; 564 } 565 566 close_on_exec(l->fd); 567 if(!strcmp(l->connect_to, "*smartsocket*")) { 568 fdevent_install(&l->fde, l->fd, ss_listener_event_func, l); 569 } else { 570 fdevent_install(&l->fde, l->fd, listener_event_func, l); 571 } 572 fdevent_set(&l->fde, FDE_READ); 573 574 l->next = &listener_list; 575 l->prev = listener_list.prev; 576 l->next->prev = l; 577 l->prev->next = l; 578 l->transport = transport; 579 580 if (transport) { 581 l->disconnect.opaque = l; 582 l->disconnect.func = listener_disconnect; 583 add_transport_disconnect(transport, &l->disconnect); 584 } 585 return 0; 586 587nomem: 588 fatal("cannot allocate listener"); 589 return 0; 590} 591 592#ifdef HAVE_FORKEXEC 593static void sigchld_handler(int n) 594{ 595 int status; 596 while(waitpid(-1, &status, WNOHANG) > 0) ; 597} 598#endif 599 600#ifdef HAVE_WIN32_PROC 601static BOOL WINAPI ctrlc_handler(DWORD type) 602{ 603 exit(STATUS_CONTROL_C_EXIT); 604 return TRUE; 605} 606#endif 607 608static void adb_cleanup(void) 609{ 610 usb_cleanup(); 611} 612 613void start_logging(void) 614{ 615#ifdef HAVE_WIN32_PROC 616 char temp[ MAX_PATH ]; 617 FILE* fnul; 618 FILE* flog; 619 620 GetTempPath( sizeof(temp) - 8, temp ); 621 strcat( temp, "adb.log" ); 622 623 /* Win32 specific redirections */ 624 fnul = fopen( "NUL", "rt" ); 625 if (fnul != NULL) 626 stdin[0] = fnul[0]; 627 628 flog = fopen( temp, "at" ); 629 if (flog == NULL) 630 flog = fnul; 631 632 setvbuf( flog, NULL, _IONBF, 0 ); 633 634 stdout[0] = flog[0]; 635 stderr[0] = flog[0]; 636 fprintf(stderr,"--- adb starting (pid %d) ---\n", getpid()); 637#else 638 int fd; 639 640 fd = unix_open("/dev/null", O_RDONLY); 641 dup2(fd, 0); 642 643 fd = unix_open("/tmp/adb.log", O_WRONLY | O_CREAT | O_APPEND, 0640); 644 if(fd < 0) { 645 fd = unix_open("/dev/null", O_WRONLY); 646 } 647 dup2(fd, 1); 648 dup2(fd, 2); 649 fprintf(stderr,"--- adb starting (pid %d) ---\n", getpid()); 650#endif 651} 652 653#if !ADB_HOST 654void start_device_log(void) 655{ 656 int fd; 657 char path[PATH_MAX]; 658 struct tm now; 659 time_t t; 660 char value[PROPERTY_VALUE_MAX]; 661 662 // read the trace mask from persistent property persist.adb.trace_mask 663 // give up if the property is not set or cannot be parsed 664 property_get("persist.adb.trace_mask", value, ""); 665 if (sscanf(value, "%x", &adb_trace_mask) != 1) 666 return; 667 668 adb_mkdir("/data/adb", 0775); 669 tzset(); 670 time(&t); 671 localtime_r(&t, &now); 672 strftime(path, sizeof(path), 673 "/data/adb/adb-%Y-%m-%d-%H-%M-%S.txt", 674 &now); 675 fd = unix_open(path, O_WRONLY | O_CREAT | O_TRUNC, 0640); 676 if (fd < 0) 677 return; 678 679 // redirect stdout and stderr to the log file 680 dup2(fd, 1); 681 dup2(fd, 2); 682 fprintf(stderr,"--- adb starting (pid %d) ---\n", getpid()); 683 684 fd = unix_open("/dev/null", O_RDONLY); 685 dup2(fd, 0); 686} 687#endif 688 689#if ADB_HOST 690int launch_server(int server_port) 691{ 692#ifdef HAVE_WIN32_PROC 693 /* we need to start the server in the background */ 694 /* we create a PIPE that will be used to wait for the server's "OK" */ 695 /* message since the pipe handles must be inheritable, we use a */ 696 /* security attribute */ 697 HANDLE pipe_read, pipe_write; 698 SECURITY_ATTRIBUTES sa; 699 STARTUPINFO startup; 700 PROCESS_INFORMATION pinfo; 701 char program_path[ MAX_PATH ]; 702 int ret; 703 704 sa.nLength = sizeof(sa); 705 sa.lpSecurityDescriptor = NULL; 706 sa.bInheritHandle = TRUE; 707 708 /* create pipe, and ensure its read handle isn't inheritable */ 709 ret = CreatePipe( &pipe_read, &pipe_write, &sa, 0 ); 710 if (!ret) { 711 fprintf(stderr, "CreatePipe() failure, error %ld\n", GetLastError() ); 712 return -1; 713 } 714 715 SetHandleInformation( pipe_read, HANDLE_FLAG_INHERIT, 0 ); 716 717 ZeroMemory( &startup, sizeof(startup) ); 718 startup.cb = sizeof(startup); 719 startup.hStdInput = GetStdHandle( STD_INPUT_HANDLE ); 720 startup.hStdOutput = pipe_write; 721 startup.hStdError = GetStdHandle( STD_ERROR_HANDLE ); 722 startup.dwFlags = STARTF_USESTDHANDLES; 723 724 ZeroMemory( &pinfo, sizeof(pinfo) ); 725 726 /* get path of current program */ 727 GetModuleFileName( NULL, program_path, sizeof(program_path) ); 728 729 ret = CreateProcess( 730 program_path, /* program path */ 731 "adb fork-server server", 732 /* the fork-server argument will set the 733 debug = 2 in the child */ 734 NULL, /* process handle is not inheritable */ 735 NULL, /* thread handle is not inheritable */ 736 TRUE, /* yes, inherit some handles */ 737 DETACHED_PROCESS, /* the new process doesn't have a console */ 738 NULL, /* use parent's environment block */ 739 NULL, /* use parent's starting directory */ 740 &startup, /* startup info, i.e. std handles */ 741 &pinfo ); 742 743 CloseHandle( pipe_write ); 744 745 if (!ret) { 746 fprintf(stderr, "CreateProcess failure, error %ld\n", GetLastError() ); 747 CloseHandle( pipe_read ); 748 return -1; 749 } 750 751 CloseHandle( pinfo.hProcess ); 752 CloseHandle( pinfo.hThread ); 753 754 /* wait for the "OK\n" message */ 755 { 756 char temp[3]; 757 DWORD count; 758 759 ret = ReadFile( pipe_read, temp, 3, &count, NULL ); 760 CloseHandle( pipe_read ); 761 if ( !ret ) { 762 fprintf(stderr, "could not read ok from ADB Server, error = %ld\n", GetLastError() ); 763 return -1; 764 } 765 if (count != 3 || temp[0] != 'O' || temp[1] != 'K' || temp[2] != '\n') { 766 fprintf(stderr, "ADB server didn't ACK\n" ); 767 return -1; 768 } 769 } 770#elif defined(HAVE_FORKEXEC) 771 char path[PATH_MAX]; 772 int fd[2]; 773 774 // set up a pipe so the child can tell us when it is ready. 775 // fd[0] will be parent's end, and fd[1] will get mapped to stderr in the child. 776 if (pipe(fd)) { 777 fprintf(stderr, "pipe failed in launch_server, errno: %d\n", errno); 778 return -1; 779 } 780 get_my_path(path, PATH_MAX); 781 pid_t pid = fork(); 782 if(pid < 0) return -1; 783 784 if (pid == 0) { 785 // child side of the fork 786 787 // redirect stderr to the pipe 788 // we use stderr instead of stdout due to stdout's buffering behavior. 789 adb_close(fd[0]); 790 dup2(fd[1], STDERR_FILENO); 791 adb_close(fd[1]); 792 793 // child process 794 int result = execl(path, "adb", "fork-server", "server", NULL); 795 // this should not return 796 fprintf(stderr, "OOPS! execl returned %d, errno: %d\n", result, errno); 797 } else { 798 // parent side of the fork 799 800 char temp[3]; 801 802 temp[0] = 'A'; temp[1] = 'B'; temp[2] = 'C'; 803 // wait for the "OK\n" message 804 adb_close(fd[1]); 805 int ret = adb_read(fd[0], temp, 3); 806 adb_close(fd[0]); 807 if (ret < 0) { 808 fprintf(stderr, "could not read ok from ADB Server, errno = %d\n", errno); 809 return -1; 810 } 811 if (ret != 3 || temp[0] != 'O' || temp[1] != 'K' || temp[2] != '\n') { 812 fprintf(stderr, "ADB server didn't ACK\n" ); 813 return -1; 814 } 815 816 setsid(); 817 } 818#else 819#error "cannot implement background server start on this platform" 820#endif 821 return 0; 822} 823#endif 824 825/* Constructs a local name of form tcp:port. 826 * target_str points to the target string, it's content will be overwritten. 827 * target_size is the capacity of the target string. 828 * server_port is the port number to use for the local name. 829 */ 830void build_local_name(char* target_str, size_t target_size, int server_port) 831{ 832 snprintf(target_str, target_size, "tcp:%d", server_port); 833} 834 835int adb_main(int is_daemon, int server_port) 836{ 837#if !ADB_HOST 838 int secure = 0; 839 int port; 840 char value[PROPERTY_VALUE_MAX]; 841#endif 842 843 atexit(adb_cleanup); 844#ifdef HAVE_WIN32_PROC 845 SetConsoleCtrlHandler( ctrlc_handler, TRUE ); 846#elif defined(HAVE_FORKEXEC) 847 signal(SIGCHLD, sigchld_handler); 848 signal(SIGPIPE, SIG_IGN); 849#endif 850 851 init_transport_registration(); 852 853 854#if ADB_HOST 855 HOST = 1; 856 usb_vendors_init(); 857 usb_init(); 858 local_init(DEFAULT_ADB_LOCAL_TRANSPORT_PORT); 859 860 char local_name[30]; 861 build_local_name(local_name, sizeof(local_name), server_port); 862 if(install_listener(local_name, "*smartsocket*", NULL)) { 863 exit(1); 864 } 865#else 866 /* run adbd in secure mode if ro.secure is set and 867 ** we are not in the emulator 868 */ 869 property_get("ro.kernel.qemu", value, ""); 870 if (strcmp(value, "1") != 0) { 871 property_get("ro.secure", value, ""); 872 if (strcmp(value, "1") == 0) { 873 // don't run as root if ro.secure is set... 874 secure = 1; 875 876 // ... except we allow running as root in userdebug builds if the 877 // service.adb.root property has been set by the "adb root" command 878 property_get("ro.debuggable", value, ""); 879 if (strcmp(value, "1") == 0) { 880 property_get("service.adb.root", value, ""); 881 if (strcmp(value, "1") == 0) { 882 secure = 0; 883 } 884 } 885 } 886 } 887 888 /* don't listen on a port (default 5037) if running in secure mode */ 889 /* don't run as root if we are running in secure mode */ 890 if (secure) { 891 struct __user_cap_header_struct header; 892 struct __user_cap_data_struct cap; 893 894 prctl(PR_SET_KEEPCAPS, 1, 0, 0, 0); 895 896 /* add extra groups: 897 ** AID_ADB to access the USB driver 898 ** AID_LOG to read system logs (adb logcat) 899 ** AID_INPUT to diagnose input issues (getevent) 900 ** AID_INET to diagnose network issues (netcfg, ping) 901 ** AID_GRAPHICS to access the frame buffer 902 ** AID_NET_BT and AID_NET_BT_ADMIN to diagnose bluetooth (hcidump) 903 ** AID_SDCARD_RW to allow writing to the SD card 904 ** AID_MOUNT to allow unmounting the SD card before rebooting 905 */ 906 gid_t groups[] = { AID_ADB, AID_LOG, AID_INPUT, AID_INET, AID_GRAPHICS, 907 AID_NET_BT, AID_NET_BT_ADMIN, AID_SDCARD_RW, AID_MOUNT }; 908 setgroups(sizeof(groups)/sizeof(groups[0]), groups); 909 910 /* then switch user and group to "shell" */ 911 setgid(AID_SHELL); 912 setuid(AID_SHELL); 913 914 /* set CAP_SYS_BOOT capability, so "adb reboot" will succeed */ 915 header.version = _LINUX_CAPABILITY_VERSION; 916 header.pid = 0; 917 cap.effective = cap.permitted = (1 << CAP_SYS_BOOT); 918 cap.inheritable = 0; 919 capset(&header, &cap); 920 921 D("Local port disabled\n"); 922 } else { 923 char local_name[30]; 924 build_local_name(local_name, sizeof(local_name), server_port); 925 if(install_listener(local_name, "*smartsocket*", NULL)) { 926 exit(1); 927 } 928 } 929 930 /* for the device, start the usb transport if the 931 ** android usb device exists and the "service.adb.tcp.port" and 932 ** "persist.adb.tcp.port" properties are not set. 933 ** Otherwise start the network transport. 934 */ 935 property_get("service.adb.tcp.port", value, ""); 936 if (!value[0]) 937 property_get("persist.adb.tcp.port", value, ""); 938 if (sscanf(value, "%d", &port) == 1 && port > 0) { 939 // listen on TCP port specified by service.adb.tcp.port property 940 local_init(port); 941 } else if (access("/dev/android_adb", F_OK) == 0) { 942 // listen on USB 943 usb_init(); 944 } else { 945 // listen on default port 946 local_init(DEFAULT_ADB_LOCAL_TRANSPORT_PORT); 947 } 948 init_jdwp(); 949#endif 950 951 if (is_daemon) 952 { 953 // inform our parent that we are up and running. 954#ifdef HAVE_WIN32_PROC 955 DWORD count; 956 WriteFile( GetStdHandle( STD_OUTPUT_HANDLE ), "OK\n", 3, &count, NULL ); 957#elif defined(HAVE_FORKEXEC) 958 fprintf(stderr, "OK\n"); 959#endif 960 start_logging(); 961 } 962 963 fdevent_loop(); 964 965 usb_cleanup(); 966 967 return 0; 968} 969 970int handle_host_request(char *service, transport_type ttype, char* serial, int reply_fd, asocket *s) 971{ 972 atransport *transport = NULL; 973 char buf[4096]; 974 975 if(!strcmp(service, "kill")) { 976 fprintf(stderr,"adb server killed by remote request\n"); 977 fflush(stdout); 978 adb_write(reply_fd, "OKAY", 4); 979 usb_cleanup(); 980 exit(0); 981 } 982 983#if ADB_HOST 984 // "transport:" is used for switching transport with a specified serial number 985 // "transport-usb:" is used for switching transport to the only USB transport 986 // "transport-local:" is used for switching transport to the only local transport 987 // "transport-any:" is used for switching transport to the only transport 988 if (!strncmp(service, "transport", strlen("transport"))) { 989 char* error_string = "unknown failure"; 990 transport_type type = kTransportAny; 991 992 if (!strncmp(service, "transport-usb", strlen("transport-usb"))) { 993 type = kTransportUsb; 994 } else if (!strncmp(service, "transport-local", strlen("transport-local"))) { 995 type = kTransportLocal; 996 } else if (!strncmp(service, "transport-any", strlen("transport-any"))) { 997 type = kTransportAny; 998 } else if (!strncmp(service, "transport:", strlen("transport:"))) { 999 service += strlen("transport:"); 1000 serial = strdup(service); 1001 } 1002 1003 transport = acquire_one_transport(CS_ANY, type, serial, &error_string); 1004 1005 if (transport) { 1006 s->transport = transport; 1007 adb_write(reply_fd, "OKAY", 4); 1008 } else { 1009 sendfailmsg(reply_fd, error_string); 1010 } 1011 return 1; 1012 } 1013 1014 // return a list of all connected devices 1015 if (!strcmp(service, "devices")) { 1016 char buffer[4096]; 1017 memset(buf, 0, sizeof(buf)); 1018 memset(buffer, 0, sizeof(buffer)); 1019 D("Getting device list \n"); 1020 list_transports(buffer, sizeof(buffer)); 1021 snprintf(buf, sizeof(buf), "OKAY%04x%s",(unsigned)strlen(buffer),buffer); 1022 D("Wrote device list \n"); 1023 writex(reply_fd, buf, strlen(buf)); 1024 return 0; 1025 } 1026 1027 // add a new TCP transport 1028 if (!strncmp(service, "connect:", 8)) { 1029 char buffer[4096]; 1030 int port, fd; 1031 char* host = service + 8; 1032 char* portstr = strchr(host, ':'); 1033 1034 if (!portstr) { 1035 snprintf(buffer, sizeof(buffer), "unable to parse %s as <host>:<port>", host); 1036 goto done; 1037 } 1038 if (find_transport(host)) { 1039 snprintf(buffer, sizeof(buffer), "Already connected to %s", host); 1040 goto done; 1041 } 1042 1043 // zero terminate host by overwriting the ':' 1044 *portstr++ = 0; 1045 if (sscanf(portstr, "%d", &port) == 0) { 1046 snprintf(buffer, sizeof(buffer), "bad port number %s", portstr); 1047 goto done; 1048 } 1049 1050 fd = socket_network_client(host, port, SOCK_STREAM); 1051 if (fd < 0) { 1052 snprintf(buffer, sizeof(buffer), "unable to connect to %s:%d", host, port); 1053 goto done; 1054 } 1055 1056 D("client: connected on remote on fd %d\n", fd); 1057 close_on_exec(fd); 1058 disable_tcp_nagle(fd); 1059 snprintf(buf, sizeof buf, "%s:%d", host, port); 1060 register_socket_transport(fd, buf, port, 0); 1061 snprintf(buffer, sizeof(buffer), "connected to %s:%d", host, port); 1062 1063done: 1064 snprintf(buf, sizeof(buf), "OKAY%04x%s",(unsigned)strlen(buffer), buffer); 1065 writex(reply_fd, buf, strlen(buf)); 1066 return 0; 1067 } 1068 1069 // remove TCP transport 1070 if (!strncmp(service, "disconnect:", 11)) { 1071 char buffer[4096]; 1072 memset(buffer, 0, sizeof(buffer)); 1073 char* serial = service + 11; 1074 atransport *t = find_transport(serial); 1075 1076 if (t) { 1077 unregister_transport(t); 1078 } else { 1079 snprintf(buffer, sizeof(buffer), "No such device %s", serial); 1080 } 1081 1082 snprintf(buf, sizeof(buf), "OKAY%04x%s",(unsigned)strlen(buffer), buffer); 1083 writex(reply_fd, buf, strlen(buf)); 1084 return 0; 1085 } 1086 1087 // returns our value for ADB_SERVER_VERSION 1088 if (!strcmp(service, "version")) { 1089 char version[12]; 1090 snprintf(version, sizeof version, "%04x", ADB_SERVER_VERSION); 1091 snprintf(buf, sizeof buf, "OKAY%04x%s", (unsigned)strlen(version), version); 1092 writex(reply_fd, buf, strlen(buf)); 1093 return 0; 1094 } 1095 1096 if(!strncmp(service,"get-serialno",strlen("get-serialno"))) { 1097 char *out = "unknown"; 1098 transport = acquire_one_transport(CS_ANY, ttype, serial, NULL); 1099 if (transport && transport->serial) { 1100 out = transport->serial; 1101 } 1102 snprintf(buf, sizeof buf, "OKAY%04x%s",(unsigned)strlen(out),out); 1103 writex(reply_fd, buf, strlen(buf)); 1104 return 0; 1105 } 1106 // indicates a new emulator instance has started 1107 if (!strncmp(service,"emulator:",9)) { 1108 int port = atoi(service+9); 1109 local_connect(port); 1110 /* we don't even need to send a reply */ 1111 return 0; 1112 } 1113#endif // ADB_HOST 1114 1115 if(!strncmp(service,"forward:",8) || !strncmp(service,"killforward:",12)) { 1116 char *local, *remote, *err; 1117 int r; 1118 atransport *transport; 1119 1120 int createForward = strncmp(service,"kill",4); 1121 1122 local = service + (createForward ? 8 : 12); 1123 remote = strchr(local,';'); 1124 if(remote == 0) { 1125 sendfailmsg(reply_fd, "malformed forward spec"); 1126 return 0; 1127 } 1128 1129 *remote++ = 0; 1130 if((local[0] == 0) || (remote[0] == 0) || (remote[0] == '*')){ 1131 sendfailmsg(reply_fd, "malformed forward spec"); 1132 return 0; 1133 } 1134 1135 transport = acquire_one_transport(CS_ANY, ttype, serial, &err); 1136 if (!transport) { 1137 sendfailmsg(reply_fd, err); 1138 return 0; 1139 } 1140 1141 if (createForward) { 1142 r = install_listener(local, remote, transport); 1143 } else { 1144 r = remove_listener(local, remote, transport); 1145 } 1146 if(r == 0) { 1147 /* 1st OKAY is connect, 2nd OKAY is status */ 1148 writex(reply_fd, "OKAYOKAY", 8); 1149 return 0; 1150 } 1151 1152 if (createForward) { 1153 sendfailmsg(reply_fd, (r == -1) ? "cannot rebind smartsocket" : "cannot bind socket"); 1154 } else { 1155 sendfailmsg(reply_fd, "cannot remove listener"); 1156 } 1157 return 0; 1158 } 1159 1160 if(!strncmp(service,"get-state",strlen("get-state"))) { 1161 transport = acquire_one_transport(CS_ANY, ttype, serial, NULL); 1162 char *state = connection_state_name(transport); 1163 snprintf(buf, sizeof buf, "OKAY%04x%s",(unsigned)strlen(state),state); 1164 writex(reply_fd, buf, strlen(buf)); 1165 return 0; 1166 } 1167 return -1; 1168} 1169 1170#if !ADB_HOST 1171int recovery_mode = 0; 1172#endif 1173 1174int main(int argc, char **argv) 1175{ 1176 adb_trace_init(); 1177#if ADB_HOST 1178 adb_sysdeps_init(); 1179 return adb_commandline(argc - 1, argv + 1); 1180#else 1181 if((argc > 1) && (!strcmp(argv[1],"recovery"))) { 1182 adb_device_banner = "recovery"; 1183 recovery_mode = 1; 1184 } 1185 1186 start_device_log(); 1187 return adb_main(0, DEFAULT_ADB_PORT); 1188#endif 1189} 1190