Merge "adb: add authorizing, connecting states to transport."

This commit is contained in:
Josh Gao 2018-05-09 20:43:31 +00:00 committed by Gerrit Code Review
commit c97cea0d20
6 changed files with 68 additions and 30 deletions

View file

@ -365,8 +365,8 @@ void handle_packet(apacket *p, atransport *t)
switch (p->msg.arg0) {
#if ADB_HOST
case ADB_AUTH_TOKEN:
if (t->GetConnectionState() == kCsOffline) {
t->SetConnectionState(kCsUnauthorized);
if (t->GetConnectionState() != kCsAuthorizing) {
t->SetConnectionState(kCsAuthorizing);
}
send_auth_response(p->payload.data(), p->msg.data_length, t);
break;
@ -1103,14 +1103,11 @@ int handle_host_request(const char* service, TransportType type, const char* ser
if (!strcmp(service, "reconnect-offline")) {
std::string response;
close_usb_devices([&response](const atransport* transport) {
switch (transport->GetConnectionState()) {
case kCsOffline:
case kCsUnauthorized:
response += "reconnecting " + transport->serial_name() + "\n";
return true;
default:
return false;
if (!ConnectionStateIsOnline(transport->GetConnectionState())) {
response += "reconnecting " + transport->serial_name() + "\n";
return true;
}
return false;
});
if (!response.empty()) {
response.resize(response.size() - 1);

View file

@ -95,16 +95,33 @@ enum TransportType {
enum ConnectionState {
kCsAny = -1,
kCsOffline = 0,
kCsConnecting = 0, // Haven't received a response from the device yet.
kCsAuthorizing, // Authorizing with keys from ADB_VENDOR_KEYS.
kCsUnauthorized, // ADB_VENDOR_KEYS exhausted, fell back to user prompt.
kCsNoPerm, // Insufficient permissions to communicate with the device.
kCsOffline,
kCsBootloader,
kCsDevice,
kCsHost,
kCsRecovery,
kCsNoPerm, // Insufficient permissions to communicate with the device.
kCsSideload,
kCsUnauthorized,
};
inline bool ConnectionStateIsOnline(ConnectionState state) {
switch (state) {
case kCsBootloader:
case kCsDevice:
case kCsHost:
case kCsRecovery:
case kCsSideload:
return true;
default:
return false;
}
}
void print_packet(const char* label, apacket* p);
// These use the system (v)fprintf, not the adb prefixed ones defined in sysdeps.h, so they

View file

@ -464,6 +464,7 @@ void send_auth_response(const char* token, size_t token_size, atransport* t) {
std::shared_ptr<RSA> key = t->NextKey();
if (key == nullptr) {
// No more private keys to try, send the public key.
t->SetConnectionState(kCsUnauthorized);
send_auth_publickey(t);
return;
}

View file

@ -750,7 +750,7 @@ static int smart_socket_enqueue(asocket* s, apacket::payload_type data) {
if (!s->transport) {
SendFail(s->peer->fd, "device offline (no transport)");
goto fail;
} else if (s->transport->GetConnectionState() == kCsOffline) {
} else if (!ConnectionStateIsOnline(s->transport->GetConnectionState())) {
/* if there's no remote we fail the connection
** right here and terminate it
*/

View file

@ -708,22 +708,41 @@ atransport* acquire_one_transport(TransportType type, const char* serial, Transp
}
lock.unlock();
// Don't return unauthorized devices; the caller can't do anything with them.
if (result && result->GetConnectionState() == kCsUnauthorized && !accept_any_state) {
*error_out = "device unauthorized.\n";
char* ADB_VENDOR_KEYS = getenv("ADB_VENDOR_KEYS");
*error_out += "This adb server's $ADB_VENDOR_KEYS is ";
*error_out += ADB_VENDOR_KEYS ? ADB_VENDOR_KEYS : "not set";
*error_out += "\n";
*error_out += "Try 'adb kill-server' if that seems wrong.\n";
*error_out += "Otherwise check for a confirmation dialog on your device.";
result = nullptr;
}
if (result && !accept_any_state) {
// The caller requires an active transport.
// Make sure that we're actually connected.
ConnectionState state = result->GetConnectionState();
switch (state) {
case kCsConnecting:
*error_out = "device still connecting";
result = nullptr;
break;
// Don't return offline devices; the caller can't do anything with them.
if (result && result->GetConnectionState() == kCsOffline && !accept_any_state) {
*error_out = "device offline";
result = nullptr;
case kCsAuthorizing:
*error_out = "device still authorizing";
result = nullptr;
break;
case kCsUnauthorized: {
*error_out = "device unauthorized.\n";
char* ADB_VENDOR_KEYS = getenv("ADB_VENDOR_KEYS");
*error_out += "This adb server's $ADB_VENDOR_KEYS is ";
*error_out += ADB_VENDOR_KEYS ? ADB_VENDOR_KEYS : "not set";
*error_out += "\n";
*error_out += "Try 'adb kill-server' if that seems wrong.\n";
*error_out += "Otherwise check for a confirmation dialog on your device.";
result = nullptr;
break;
}
case kCsOffline:
*error_out = "device offline";
result = nullptr;
break;
default:
break;
}
}
if (result) {
@ -802,6 +821,10 @@ std::string atransport::connection_state_name() const {
return "sideload";
case kCsUnauthorized:
return "unauthorized";
case kCsAuthorizing:
return "authorizing";
case kCsConnecting:
return "connecting";
default:
return "unknown";
}
@ -1080,7 +1103,7 @@ void kick_all_tcp_devices() {
void register_usb_transport(usb_handle* usb, const char* serial, const char* devpath,
unsigned writeable) {
atransport* t = new atransport((writeable ? kCsOffline : kCsNoPerm));
atransport* t = new atransport((writeable ? kCsConnecting : kCsNoPerm));
D("transport: %p init'ing for usb_handle %p (sn='%s')", t, usb, serial ? serial : "");
init_usb_transport(t, usb);

View file

@ -198,7 +198,7 @@ class atransport {
// class in one go is a very large change. Given how bad our testing is,
// it's better to do this piece by piece.
atransport(ConnectionState state = kCsOffline)
atransport(ConnectionState state = kCsConnecting)
: id(NextTransportId()),
connection_state_(state),
connection_waitable_(std::make_shared<ConnectionWaitable>()),