1d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate/*
2d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * Copyright (C) 2011 The Android Open Source Project
3d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate *
4d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * Licensed under the Apache License, Version 2.0 (the "License");
5d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * you may not use this file except in compliance with the License.
6d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * You may obtain a copy of the License at
7d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate *
8d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate *      http://www.apache.org/licenses/LICENSE-2.0
9d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate *
10d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * Unless required by applicable law or agreed to in writing, software
11d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * distributed under the License is distributed on an "AS IS" BASIS,
12d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * See the License for the specific language governing permissions and
14d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate * limitations under the License.
15d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate */
16d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
17d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate#include <unistd.h>
18d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate#include <stdio.h>
19d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
20d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate#include "sysdeps.h"
21d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
22d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate#define TRACE_TAG  TRACE_ADB
23d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate#include "adb.h"
24d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
2510f129ca8eb266f46393e981484e60521f9011dfChristopher Tatetypedef struct {
2610f129ca8eb266f46393e981484e60521f9011dfChristopher Tate    pid_t pid;
2710f129ca8eb266f46393e981484e60521f9011dfChristopher Tate    int fd;
2810f129ca8eb266f46393e981484e60521f9011dfChristopher Tate} backup_harvest_params;
2910f129ca8eb266f46393e981484e60521f9011dfChristopher Tate
305b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate// socketpair but do *not* mark as close_on_exec
315b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tatestatic int backup_socketpair(int sv[2]) {
325b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    int rc = unix_socketpair( AF_UNIX, SOCK_STREAM, 0, sv );
335b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    if (rc < 0)
345b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        return -1;
355b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
365b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    return 0;
375b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate}
385b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
3910f129ca8eb266f46393e981484e60521f9011dfChristopher Tate// harvest the child process then close the read end of the socketpair
4010f129ca8eb266f46393e981484e60521f9011dfChristopher Tatestatic void* backup_child_waiter(void* args) {
415b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    int status;
4210f129ca8eb266f46393e981484e60521f9011dfChristopher Tate    backup_harvest_params* params = (backup_harvest_params*) args;
435b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
4410f129ca8eb266f46393e981484e60521f9011dfChristopher Tate    waitpid(params->pid, &status, 0);
4510f129ca8eb266f46393e981484e60521f9011dfChristopher Tate    adb_close(params->fd);
4610f129ca8eb266f46393e981484e60521f9011dfChristopher Tate    free(params);
475b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    return NULL;
485b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate}
495b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
50d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate/* returns the data socket passing the backup data here for forwarding */
51702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tateint backup_service(BackupOperation op, char* args) {
52d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    pid_t pid;
53d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    int s[2];
54702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    char* operation;
55702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    int socketnum;
56d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
57702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    // Command string and choice of stdin/stdout for the pipe depend on our invocation
58702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    if (op == BACKUP) {
59702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        operation = "backup";
60702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        socketnum = STDOUT_FILENO;
61702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    } else {
62702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        operation = "restore";
63702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        socketnum = STDIN_FILENO;
64702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    }
65702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate
66702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate    D("backup_service(%s, %s)\n", operation, args);
67d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
68d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    // set up the pipe from the subprocess to here
69d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    // parent will read s[0]; child will write s[1]
705b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    if (backup_socketpair(s)) {
71702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        D("can't create backup/restore socketpair\n");
72702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        fprintf(stderr, "unable to create backup/restore socketpair\n");
73d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        return -1;
74d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    }
75d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
765b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    D("Backup/restore socket pair: (send=%d, receive=%d)\n", s[1], s[0]);
775b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate    close_on_exec(s[0]);    // only the side we hold on to
785b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
79d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    // spin off the child process to run the backup command
80d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    pid = fork();
81d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    if (pid < 0) {
82d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        // failure
83702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        D("can't fork for %s\n", operation);
84702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        fprintf(stderr, "unable to fork for %s\n", operation);
85d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        adb_close(s[0]);
86d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        adb_close(s[1]);
87d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        return -1;
88d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    }
89d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
90d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    // Great, we're off and running.
91d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    if (pid == 0) {
925b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        // child -- actually run the backup here
93d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        char* p;
94d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        int argc;
955b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        char portnum[16];
96702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        char** bu_args;
97d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
985b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        // fixed args:  [0] is 'bu', [1] is the port number, [2] is the 'operation' string
995b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        argc = 3;
100d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        for (p = (char*)args; p && *p; ) {
101d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate            argc++;
102d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate            while (*p && *p != ':') p++;
103d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate            if (*p == ':') p++;
104d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        }
105d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
106702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        bu_args = (char**) alloca(argc*sizeof(char*) + 1);
1075b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
1085b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        // run through again to build the argv array
1095b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        argc = 0;
1105b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        bu_args[argc++] = "bu";
1115b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        snprintf(portnum, sizeof(portnum), "%d", s[1]);
1125b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        bu_args[argc++] = portnum;
1135b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        bu_args[argc++] = operation;
114702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        for (p = (char*)args; p && *p; ) {
115702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate            bu_args[argc++] = p;
116d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate            while (*p && *p != ':') p++;
117d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate            if (*p == ':') {
118d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate                *p = 0;
119d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate                p++;
120d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate            }
121d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        }
122702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        bu_args[argc] = NULL;
123d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
124d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        // Close the half of the socket that we don't care about, route 'bu's console
125d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        // to the output socket, and off we go
126d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        adb_close(s[0]);
127d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
128d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        // off we go
129702967afb1bebc97c0b8a23c075d4932820ef7a3Christopher Tate        execvp("/system/bin/bu", (char * const *)bu_args);
130d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        // oops error - close up shop and go home
131d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        fprintf(stderr, "Unable to exec 'bu', bailing\n");
132d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        exit(-1);
133d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    } else {
1345b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        adb_thread_t t;
13510f129ca8eb266f46393e981484e60521f9011dfChristopher Tate        backup_harvest_params* params;
1365b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
137d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        // parent, i.e. adbd -- close the sending half of the socket
1385b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        D("fork() returned pid %d\n", pid);
139d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate        adb_close(s[1]);
1405b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate
1415b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        // spin a thread to harvest the child process
14210f129ca8eb266f46393e981484e60521f9011dfChristopher Tate        params = (backup_harvest_params*) malloc(sizeof(backup_harvest_params));
14310f129ca8eb266f46393e981484e60521f9011dfChristopher Tate        params->pid = pid;
14410f129ca8eb266f46393e981484e60521f9011dfChristopher Tate        params->fd = s[0];
14510f129ca8eb266f46393e981484e60521f9011dfChristopher Tate        if (adb_thread_create(&t, backup_child_waiter, params)) {
1465b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate            adb_close(s[0]);
14710f129ca8eb266f46393e981484e60521f9011dfChristopher Tate            free(params);
1485b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate            D("Unable to create child harvester\n");
1495b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate            return -1;
1505b811fa5dd00288954f15209a56aea03d5e4a004Christopher Tate        }
151d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    }
152d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate
153d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    // we'll be reading from s[0] as the data is sent by the child process
154d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate    return s[0];
155d2f5415c603f7d9961f7a0b05579a0768e071410Christopher Tate}
156