Merge "Add 0X as a valid hex prefix for parseint"
diff --git a/adb/Android.mk b/adb/Android.mk
index 0114ca3..e17240b 100644
--- a/adb/Android.mk
+++ b/adb/Android.mk
@@ -45,7 +45,6 @@
# get enough of adb in here that we no longer need minadb. https://b/17626262
LIBADB_SRC_FILES := \
adb.cpp \
- adb_auth.cpp \
adb_io.cpp \
adb_listeners.cpp \
adb_trace.cpp \
@@ -103,7 +102,7 @@
LOCAL_CFLAGS := $(LIBADB_CFLAGS) -DADB_HOST=0
LOCAL_SRC_FILES := \
$(LIBADB_SRC_FILES) \
- adb_auth_client.cpp \
+ adbd_auth.cpp \
jdwp_service.cpp \
usb_linux_client.cpp \
@@ -324,7 +323,6 @@
LOCAL_FORCE_STATIC_EXECUTABLE := true
LOCAL_MODULE_PATH := $(TARGET_ROOT_OUT_SBIN)
LOCAL_UNSTRIPPED_PATH := $(TARGET_ROOT_OUT_SBIN_UNSTRIPPED)
-LOCAL_C_INCLUDES += system/extras/ext4_utils
LOCAL_SANITIZE := $(adb_target_sanitize)
LOCAL_STRIP_MODULE := keep_symbols
diff --git a/adb/adb.cpp b/adb/adb.cpp
index 9ae3f1c..29d6e65 100644
--- a/adb/adb.cpp
+++ b/adb/adb.cpp
@@ -94,6 +94,18 @@
abort();
}
+uint32_t calculate_apacket_checksum(const apacket* p) {
+ const unsigned char* x = reinterpret_cast<const unsigned char*>(p->data);
+ uint32_t sum = 0;
+ size_t count = p->msg.data_length;
+
+ while (count-- > 0) {
+ sum += *x++;
+ }
+
+ return sum;
+}
+
apacket* get_apacket(void)
{
apacket* p = reinterpret_cast<apacket*>(malloc(sizeof(apacket)));
@@ -351,19 +363,31 @@
break;
case A_AUTH:
- if (p->msg.arg0 == ADB_AUTH_TOKEN) {
- t->connection_state = kCsUnauthorized;
- send_auth_response(p->data, p->msg.data_length, t);
- } else if (p->msg.arg0 == ADB_AUTH_SIGNATURE) {
- if (adb_auth_verify(t->token, sizeof(t->token), p->data, p->msg.data_length)) {
- adb_auth_verified(t);
- t->failed_auth_attempts = 0;
- } else {
- if (t->failed_auth_attempts++ > 256) adb_sleep_ms(1000);
- send_auth_request(t);
- }
- } else if (p->msg.arg0 == ADB_AUTH_RSAPUBLICKEY) {
- adb_auth_confirm_key(p->data, p->msg.data_length, t);
+ switch (p->msg.arg0) {
+#if ADB_HOST
+ case ADB_AUTH_TOKEN:
+ t->connection_state = kCsUnauthorized;
+ send_auth_response(p->data, p->msg.data_length, t);
+ break;
+#else
+ case ADB_AUTH_SIGNATURE:
+ if (adbd_auth_verify(t->token, sizeof(t->token), p->data, p->msg.data_length)) {
+ adbd_auth_verified(t);
+ t->failed_auth_attempts = 0;
+ } else {
+ if (t->failed_auth_attempts++ > 256) adb_sleep_ms(1000);
+ send_auth_request(t);
+ }
+ break;
+
+ case ADB_AUTH_RSAPUBLICKEY:
+ adbd_auth_confirm_key(p->data, p->msg.data_length, t);
+ break;
+#endif
+ default:
+ t->connection_state = kCsOffline;
+ handle_offline(t);
+ break;
}
break;
diff --git a/adb/adb.h b/adb/adb.h
index 0b9fe5b..8064c17 100644
--- a/adb/adb.h
+++ b/adb/adb.h
@@ -18,6 +18,7 @@
#define __ADB_H
#include <limits.h>
+#include <stdint.h>
#include <sys/types.h>
#include <string>
@@ -56,25 +57,27 @@
struct usb_handle;
struct amessage {
- unsigned command; /* command identifier constant */
- unsigned arg0; /* first argument */
- unsigned arg1; /* second argument */
- unsigned data_length; /* length of payload (0 is allowed) */
- unsigned data_check; /* checksum of data payload */
- unsigned magic; /* command ^ 0xffffffff */
+ uint32_t command; /* command identifier constant */
+ uint32_t arg0; /* first argument */
+ uint32_t arg1; /* second argument */
+ uint32_t data_length; /* length of payload (0 is allowed) */
+ uint32_t data_check; /* checksum of data payload */
+ uint32_t magic; /* command ^ 0xffffffff */
};
struct apacket
{
apacket *next;
- unsigned len;
- unsigned char *ptr;
+ size_t len;
+ char* ptr;
amessage msg;
- unsigned char data[MAX_PAYLOAD];
+ char data[MAX_PAYLOAD];
};
+uint32_t calculate_apacket_checksum(const apacket* packet);
+
/* the adisconnect structure is used to record a callback that
** will be called whenever a transport is disconnected (e.g. by the user)
** this should be used to cleanup objects that depend on the
diff --git a/adb/adb_auth.cpp b/adb/adb_auth.cpp
deleted file mode 100644
index 0b07158..0000000
--- a/adb/adb_auth.cpp
+++ /dev/null
@@ -1,101 +0,0 @@
-/*
- * Copyright (C) 2015 The Android Open Source Project
- *
- * Licensed under the Apache License, Version 2.0 (the "License");
- * you may not use this file except in compliance with the License.
- * You may obtain a copy of the License at
- *
- * http://www.apache.org/licenses/LICENSE-2.0
- *
- * Unless required by applicable law or agreed to in writing, software
- * distributed under the License is distributed on an "AS IS" BASIS,
- * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
- * See the License for the specific language governing permissions and
- * limitations under the License.
- */
-
-#define TRACE_TAG ADB
-
-#include "adb.h"
-#include "adb_auth.h"
-#include "transport.h"
-
-#include <errno.h>
-#include <stdio.h>
-#include <string.h>
-#include <sys/types.h>
-#include <unistd.h>
-
-bool auth_required = true;
-
-void send_auth_request(atransport *t)
-{
- LOG(INFO) << "Calling send_auth_request...";
-
- if (!adb_auth_generate_token(t->token, sizeof(t->token))) {
- PLOG(ERROR) << "Error generating token";
- return;
- }
-
- apacket* p = get_apacket();
- memcpy(p->data, t->token, sizeof(t->token));
- p->msg.command = A_AUTH;
- p->msg.arg0 = ADB_AUTH_TOKEN;
- p->msg.data_length = sizeof(t->token);
- send_packet(p, t);
-}
-
-static void send_auth_publickey(atransport* t) {
- LOG(INFO) << "Calling send_auth_publickey";
-
- std::string key = adb_auth_get_userkey();
- if (key.empty()) {
- D("Failed to get user public key");
- return;
- }
-
- if (key.size() >= MAX_PAYLOAD_V1) {
- D("User public key too large (%zu B)", key.size());
- return;
- }
-
- apacket* p = get_apacket();
- memcpy(p->data, key.c_str(), key.size() + 1);
-
- p->msg.command = A_AUTH;
- p->msg.arg0 = ADB_AUTH_RSAPUBLICKEY;
-
- // adbd expects a null-terminated string.
- p->msg.data_length = key.size() + 1;
- send_packet(p, t);
-}
-
-void send_auth_response(uint8_t* 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.
- send_auth_publickey(t);
- return;
- }
-
- LOG(INFO) << "Calling send_auth_response";
- apacket* p = get_apacket();
-
- int ret = adb_auth_sign(key.get(), token, token_size, p->data);
- if (!ret) {
- D("Error signing the token");
- put_apacket(p);
- return;
- }
-
- p->msg.command = A_AUTH;
- p->msg.arg0 = ADB_AUTH_SIGNATURE;
- p->msg.data_length = ret;
- send_packet(p, t);
-}
-
-void adb_auth_verified(atransport *t)
-{
- handle_online(t);
- send_connect(t);
-}
diff --git a/adb/adb_auth.h b/adb/adb_auth.h
index 59b80d8..a6f224f 100644
--- a/adb/adb_auth.h
+++ b/adb/adb_auth.h
@@ -24,14 +24,6 @@
#include <openssl/rsa.h>
-extern bool auth_required;
-
-int adb_auth_keygen(const char* filename);
-void adb_auth_verified(atransport *t);
-
-void send_auth_request(atransport *t);
-void send_auth_response(uint8_t *token, size_t token_size, atransport *t);
-
/* AUTH packets first argument */
/* Request */
#define ADB_AUTH_TOKEN 1
@@ -42,25 +34,25 @@
#if ADB_HOST
void adb_auth_init();
-int adb_auth_sign(RSA* key, const unsigned char* token, size_t token_size, unsigned char* sig);
+
+int adb_auth_keygen(const char* filename);
std::string adb_auth_get_userkey();
std::deque<std::shared_ptr<RSA>> adb_auth_get_private_keys();
-static inline bool adb_auth_generate_token(void*, size_t) { abort(); }
-static inline bool adb_auth_verify(void*, size_t, void*, int) { abort(); }
-static inline void adb_auth_confirm_key(unsigned char*, size_t, atransport*) { abort(); }
+void send_auth_response(const char* token, size_t token_size, atransport* t);
#else // !ADB_HOST
-static inline int adb_auth_sign(void*, const unsigned char*, size_t, unsigned char*) { abort(); }
-static inline std::string adb_auth_get_userkey() { abort(); }
-static inline std::deque<std::shared_ptr<RSA>> adb_auth_get_private_keys() { abort(); }
+extern bool auth_required;
void adbd_auth_init(void);
+void adbd_auth_verified(atransport *t);
+
void adbd_cloexec_auth_socket();
-bool adb_auth_generate_token(void* token, size_t token_size);
-bool adb_auth_verify(uint8_t* token, size_t token_size, uint8_t* sig, int sig_len);
-void adb_auth_confirm_key(unsigned char *data, size_t len, atransport *t);
+bool adbd_auth_verify(const char* token, size_t token_size, const char* sig, int sig_len);
+void adbd_auth_confirm_key(const char* data, size_t len, atransport* t);
+
+void send_auth_request(atransport *t);
#endif // ADB_HOST
diff --git a/adb/adb_auth_host.cpp b/adb/adb_auth_host.cpp
index 072c7f5..ff2d76d 100644
--- a/adb/adb_auth_host.cpp
+++ b/adb/adb_auth_host.cpp
@@ -45,6 +45,7 @@
#include "adb_auth.h"
#include "adb_utils.h"
#include "sysdeps.h"
+#include "transport.h"
static std::mutex& g_keys_mutex = *new std::mutex;
static std::map<std::string, std::shared_ptr<RSA>>& g_keys =
@@ -297,14 +298,15 @@
return result;
}
-int adb_auth_sign(RSA* key, const unsigned char* token, size_t token_size, unsigned char* sig) {
+static int adb_auth_sign(RSA* key, const char* token, size_t token_size, char* sig) {
if (token_size != TOKEN_SIZE) {
D("Unexpected token size %zd", token_size);
return 0;
}
unsigned int len;
- if (!RSA_sign(NID_sha1, token, token_size, sig, &len, key)) {
+ if (!RSA_sign(NID_sha1, reinterpret_cast<const uint8_t*>(token), token_size,
+ reinterpret_cast<uint8_t*>(sig), &len, key)) {
return 0;
}
@@ -421,3 +423,52 @@
read_keys(path.c_str());
}
}
+
+static void send_auth_publickey(atransport* t) {
+ LOG(INFO) << "Calling send_auth_publickey";
+
+ std::string key = adb_auth_get_userkey();
+ if (key.empty()) {
+ D("Failed to get user public key");
+ return;
+ }
+
+ if (key.size() >= MAX_PAYLOAD_V1) {
+ D("User public key too large (%zu B)", key.size());
+ return;
+ }
+
+ apacket* p = get_apacket();
+ memcpy(p->data, key.c_str(), key.size() + 1);
+
+ p->msg.command = A_AUTH;
+ p->msg.arg0 = ADB_AUTH_RSAPUBLICKEY;
+
+ // adbd expects a null-terminated string.
+ p->msg.data_length = key.size() + 1;
+ send_packet(p, t);
+}
+
+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.
+ send_auth_publickey(t);
+ return;
+ }
+
+ LOG(INFO) << "Calling send_auth_response";
+ apacket* p = get_apacket();
+
+ int ret = adb_auth_sign(key.get(), token, token_size, p->data);
+ if (!ret) {
+ D("Error signing the token");
+ put_apacket(p);
+ return;
+ }
+
+ p->msg.command = A_AUTH;
+ p->msg.arg0 = ADB_AUTH_SIGNATURE;
+ p->msg.data_length = ret;
+ send_packet(p, t);
+}
diff --git a/adb/adb_auth_client.cpp b/adb/adbd_auth.cpp
similarity index 79%
rename from adb/adb_auth_client.cpp
rename to adb/adbd_auth.cpp
index 84ad6ef..b5f87be 100644
--- a/adb/adb_auth_client.cpp
+++ b/adb/adbd_auth.cpp
@@ -44,7 +44,9 @@
static atransport* usb_transport;
static bool needs_retry = false;
-bool adb_auth_verify(uint8_t* token, size_t token_size, uint8_t* sig, int sig_len) {
+bool auth_required = true;
+
+bool adbd_auth_verify(const char* token, size_t token_size, const char* sig, int sig_len) {
static constexpr const char* key_paths[] = { "/adb_keys", "/data/misc/adb/adb_keys", nullptr };
for (const auto& path : key_paths) {
@@ -76,7 +78,9 @@
continue;
}
- bool verified = (RSA_verify(NID_sha1, token, token_size, sig, sig_len, key) == 1);
+ bool verified =
+ (RSA_verify(NID_sha1, reinterpret_cast<const uint8_t*>(token), token_size,
+ reinterpret_cast<const uint8_t*>(sig), sig_len, key) == 1);
RSA_free(key);
if (verified) return true;
}
@@ -85,7 +89,7 @@
return false;
}
-bool adb_auth_generate_token(void* token, size_t token_size) {
+static bool adbd_auth_generate_token(void* token, size_t token_size) {
FILE* fp = fopen("/dev/urandom", "re");
if (!fp) return false;
bool okay = (fread(token, token_size, 1, fp) == 1);
@@ -105,7 +109,7 @@
framework_fd = -1;
}
-static void adb_auth_event(int fd, unsigned events, void*) {
+static void adbd_auth_event(int fd, unsigned events, void*) {
if (events & FDE_READ) {
char response[2];
int ret = unix_read(fd, response, sizeof(response));
@@ -113,13 +117,13 @@
framework_disconnected();
} else if (ret == 2 && response[0] == 'O' && response[1] == 'K') {
if (usb_transport) {
- adb_auth_verified(usb_transport);
+ adbd_auth_verified(usb_transport);
}
}
}
}
-void adb_auth_confirm_key(unsigned char* key, size_t len, atransport* t) {
+void adbd_auth_confirm_key(const char* key, size_t len, atransport* t) {
if (!usb_transport) {
usb_transport = t;
t->AddDisconnect(&usb_disconnect);
@@ -150,7 +154,7 @@
}
}
-static void adb_auth_listener(int fd, unsigned events, void* data) {
+static void adbd_auth_listener(int fd, unsigned events, void* data) {
int s = adb_socket_accept(fd, nullptr, nullptr);
if (s < 0) {
PLOG(ERROR) << "Failed to accept";
@@ -163,7 +167,7 @@
}
framework_fd = s;
- fdevent_install(&framework_fde, framework_fd, adb_auth_event, nullptr);
+ fdevent_install(&framework_fde, framework_fd, adbd_auth_event, nullptr);
fdevent_add(&framework_fde, FDE_READ);
if (needs_retry) {
@@ -193,6 +197,28 @@
return;
}
- fdevent_install(&listener_fde, fd, adb_auth_listener, NULL);
+ fdevent_install(&listener_fde, fd, adbd_auth_listener, NULL);
fdevent_add(&listener_fde, FDE_READ);
}
+
+void send_auth_request(atransport* t) {
+ LOG(INFO) << "Calling send_auth_request...";
+
+ if (!adbd_auth_generate_token(t->token, sizeof(t->token))) {
+ PLOG(ERROR) << "Error generating token";
+ return;
+ }
+
+ apacket* p = get_apacket();
+ memcpy(p->data, t->token, sizeof(t->token));
+ p->msg.command = A_AUTH;
+ p->msg.arg0 = ADB_AUTH_TOKEN;
+ p->msg.data_length = sizeof(t->token);
+ send_packet(p, t);
+}
+
+void adbd_auth_verified(atransport *t)
+{
+ handle_online(t);
+ send_connect(t);
+}
diff --git a/adb/sockets.cpp b/adb/sockets.cpp
index b809c4f..fff6049 100644
--- a/adb/sockets.cpp
+++ b/adb/sockets.cpp
@@ -122,7 +122,7 @@
}
static int local_socket_enqueue(asocket* s, apacket* p) {
- D("LS(%d): enqueue %d", s->id, p->len);
+ D("LS(%d): enqueue %zu", s->id, p->len);
p->ptr = p->data;
@@ -195,7 +195,7 @@
/* dispose of any unwritten data */
for (p = s->pkt_first; p; p = n) {
- D("LS(%d): discarding %d bytes", s->id, p->len);
+ D("LS(%d): discarding %zu bytes", s->id, p->len);
n = p->next;
put_apacket(p);
}
@@ -305,7 +305,7 @@
if (ev & FDE_READ) {
apacket* p = get_apacket();
- unsigned char* x = p->data;
+ char* x = p->data;
const size_t max_payload = s->get_max_payload();
size_t avail = max_payload;
int r = 0;
@@ -553,7 +553,7 @@
s->close(s);
}
-static unsigned unhex(unsigned char* s, int len) {
+static unsigned unhex(char* s, int len) {
unsigned n = 0, c;
while (len-- > 0) {
@@ -665,7 +665,7 @@
TransportType type = kTransportAny;
#endif
- D("SS(%d): enqueue %d", s->id, p->len);
+ D("SS(%d): enqueue %zu", s->id, p->len);
if (s->pkt_first == 0) {
s->pkt_first = p;
@@ -698,7 +698,7 @@
D("SS(%d): len is %d", s->id, len);
/* can't do anything until we have the full header */
if ((len + 4) > p->len) {
- D("SS(%d): waiting for %d more bytes", s->id, len + 4 - p->len);
+ D("SS(%d): waiting for %zu more bytes", s->id, len + 4 - p->len);
return 0;
}
diff --git a/adb/transport.cpp b/adb/transport.cpp
index 87712fc..7b4bb1c 100644
--- a/adb/transport.cpp
+++ b/adb/transport.cpp
@@ -150,32 +150,17 @@
}
}
-void send_packet(apacket *p, atransport *t)
-{
- unsigned char *x;
- unsigned sum;
- unsigned count;
-
+void send_packet(apacket* p, atransport* t) {
p->msg.magic = p->msg.command ^ 0xffffffff;
-
- count = p->msg.data_length;
- x = (unsigned char *) p->data;
- sum = 0;
- while(count-- > 0){
- sum += *x++;
- }
- p->msg.data_check = sum;
+ p->msg.data_check = calculate_apacket_checksum(p);
print_packet("send", p);
if (t == NULL) {
- D("Transport is null");
- // Zap errno because print_packet() and other stuff have errno effect.
- errno = 0;
- fatal_errno("Transport is null");
+ fatal("Transport is null");
}
- if(write_packet(t->transport_socket, t->serial, &p)){
+ if (write_packet(t->transport_socket, t->serial, &p)) {
fatal_errno("cannot enqueue packet on transport socket");
}
}
@@ -1052,25 +1037,14 @@
return 0;
}
-int check_data(apacket *p)
-{
- unsigned count, sum;
- unsigned char *x;
-
- count = p->msg.data_length;
- x = p->data;
- sum = 0;
- while(count-- > 0) {
- sum += *x++;
- }
-
- if(sum != p->msg.data_check) {
+int check_data(apacket* p) {
+ if (calculate_apacket_checksum(p) != p->msg.data_check) {
return -1;
- } else {
- return 0;
}
+ return 0;
}
+#if ADB_HOST
std::shared_ptr<RSA> atransport::NextKey() {
if (keys_.empty()) keys_ = adb_auth_get_private_keys();
@@ -1078,3 +1052,4 @@
keys_.pop_front();
return result;
}
+#endif
diff --git a/adb/transport.h b/adb/transport.h
index 959681f..621516c 100644
--- a/adb/transport.h
+++ b/adb/transport.h
@@ -108,9 +108,11 @@
return type == kTransportLocal && local_port_for_emulator_ == -1;
}
+#if ADB_HOST
std::shared_ptr<RSA> NextKey();
+#endif
- unsigned char token[TOKEN_SIZE] = {};
+ char token[TOKEN_SIZE] = {};
size_t failed_auth_attempts = 0;
const std::string connection_state_name() const;
@@ -161,7 +163,9 @@
// A list of adisconnect callbacks called when the transport is kicked.
std::list<adisconnect*> disconnects_;
+#if ADB_HOST
std::deque<std::shared_ptr<RSA>> keys_;
+#endif
DISALLOW_COPY_AND_ASSIGN(atransport);
};
diff --git a/base/logging.cpp b/base/logging.cpp
index ece10ec..dab86fe 100644
--- a/base/logging.cpp
+++ b/base/logging.cpp
@@ -415,6 +415,8 @@
msg[nl] = '\0';
LogLine(data_->GetFile(), data_->GetLineNumber(), data_->GetId(),
data_->GetSeverity(), &msg[i]);
+ // Undo the zero-termination so we can give the complete message to the aborter.
+ msg[nl] = '\n';
i = nl + 1;
}
}
diff --git a/base/logging_test.cpp b/base/logging_test.cpp
index 9fc7736..1ee181a 100644
--- a/base/logging_test.cpp
+++ b/base/logging_test.cpp
@@ -606,3 +606,27 @@
ASSERT_DEATH({SuppressAbortUI(); LOG(FATAL) << "foobar";}, "foobar");
}
+
+struct CountLineAborter {
+ static void CountLineAborterFunction(const char* msg) {
+ while (*msg != 0) {
+ if (*msg == '\n') {
+ newline_count++;
+ }
+ msg++;
+ }
+ }
+ static size_t newline_count;
+};
+size_t CountLineAborter::newline_count = 0;
+
+TEST(logging, LOG_FATAL_ABORTER_MESSAGE) {
+ CountLineAborter::newline_count = 0;
+ android::base::SetAborter(CountLineAborter::CountLineAborterFunction);
+
+ android::base::ScopedLogSeverity sls(android::base::ERROR);
+ CapturedStderr cap;
+ LOG(FATAL) << "foo\nbar";
+
+ EXPECT_EQ(CountLineAborter::newline_count, 1U + 1U); // +1 for final '\n'.
+}
diff --git a/include/backtrace/BacktraceMap.h b/include/backtrace/BacktraceMap.h
index b80045f..df48dfe 100644
--- a/include/backtrace/BacktraceMap.h
+++ b/include/backtrace/BacktraceMap.h
@@ -19,7 +19,7 @@
#include <stdint.h>
#include <sys/types.h>
-#ifdef USE_MINGW
+#ifdef _WIN32
// MINGW does not define these constants.
#define PROT_NONE 0
#define PROT_READ 0x1
diff --git a/include/cutils/native_handle.h b/include/cutils/native_handle.h
index 31695cb..813dadc 100644
--- a/include/cutils/native_handle.h
+++ b/include/cutils/native_handle.h
@@ -57,6 +57,15 @@
native_handle_t* native_handle_create(int numFds, int numInts);
/*
+ * native_handle_clone
+ *
+ * creates a native_handle_t and initializes it from another native_handle_t.
+ * Must be destroyed with native_handle_delete().
+ *
+ */
+native_handle_t* native_handle_clone(const native_handle_t* handle);
+
+/*
* native_handle_delete
*
* frees a native_handle_t allocated with native_handle_create().
diff --git a/libcutils/Android.bp b/libcutils/Android.bp
index 8624d13..955c0ec 100644
--- a/libcutils/Android.bp
+++ b/libcutils/Android.bp
@@ -87,12 +87,6 @@
"uevent.c",
],
- // TODO: remove liblog as whole static library, once we don't have prebuilt that requires
- // liblog symbols present in libcutils.
- whole_static_libs: [
- "liblog",
- ],
-
static_libs: ["libdebuggerd_client"],
export_static_lib_headers: ["libdebuggerd_client"],
diff --git a/libcutils/native_handle.c b/libcutils/native_handle.c
index 7f3479d..cae146d 100644
--- a/libcutils/native_handle.c
+++ b/libcutils/native_handle.c
@@ -44,6 +44,27 @@
return h;
}
+native_handle_t* native_handle_clone(const native_handle_t* handle)
+{
+ native_handle_t* clone = native_handle_create(handle->numFds, handle->numInts);
+ int i;
+
+ for (i = 0; i < handle->numFds; i++) {
+ clone->data[i] = dup(handle->data[i]);
+ if (clone->data[i] < 0) {
+ clone->numFds = i;
+ native_handle_close(clone);
+ native_handle_delete(clone);
+ return NULL;
+ }
+ }
+
+ memcpy(&clone->data[handle->numFds], &handle->data[handle->numFds],
+ sizeof(int) * handle->numInts);
+
+ return clone;
+}
+
int native_handle_delete(native_handle_t* h)
{
if (h) {
diff --git a/libsparse/output_file.c b/libsparse/output_file.c
index d284736..2115998 100644
--- a/libsparse/output_file.c
+++ b/libsparse/output_file.c
@@ -34,7 +34,7 @@
#include "sparse_crc32.h"
#include "sparse_format.h"
-#ifndef USE_MINGW
+#ifndef _WIN32
#include <sys/mman.h>
#define O_BINARY 0
#else
@@ -63,7 +63,7 @@
int (*open)(struct output_file *, int fd);
int (*skip)(struct output_file *, int64_t);
int (*pad)(struct output_file *, int64_t);
- int (*write)(struct output_file *, void *, int);
+ int (*write)(struct output_file *, void *, size_t);
void (*close)(struct output_file *);
};
@@ -149,18 +149,23 @@
return 0;
}
-static int file_write(struct output_file *out, void *data, int len)
+static int file_write(struct output_file *out, void *data, size_t len)
{
- int ret;
+ ssize_t ret;
struct output_file_normal *outn = to_output_file_normal(out);
- ret = write(outn->fd, data, len);
- if (ret < 0) {
- error_errno("write");
- return -1;
- } else if (ret < len) {
- error("incomplete write");
- return -1;
+ while (len > 0) {
+ ret = write(outn->fd, data, len);
+ if (ret < 0) {
+ if (errno == EINTR) {
+ continue;
+ }
+ error_errno("write");
+ return -1;
+ }
+
+ data = (char *)data + ret;
+ len -= ret;
}
return 0;
@@ -232,18 +237,20 @@
return 0;
}
-static int gz_file_write(struct output_file *out, void *data, int len)
+static int gz_file_write(struct output_file *out, void *data, size_t len)
{
int ret;
struct output_file_gz *outgz = to_output_file_gz(out);
- ret = gzwrite(outgz->gz_fd, data, len);
- if (ret < 0) {
- error_errno("gzwrite");
- return -1;
- } else if (ret < len) {
- error("incomplete gzwrite");
- return -1;
+ while (len > 0) {
+ ret = gzwrite(outgz->gz_fd, data,
+ min(len, (unsigned int)INT_MAX));
+ if (ret == 0) {
+ error("gzwrite %s", gzerror(outgz->gz_fd, NULL));
+ return -1;
+ }
+ len -= ret;
+ data = (char *)data + ret;
}
return 0;
@@ -293,7 +300,7 @@
return -1;
}
-static int callback_file_write(struct output_file *out, void *data, int len)
+static int callback_file_write(struct output_file *out, void *data, size_t len)
{
struct output_file_callback *outc = to_output_file_callback(out);
@@ -698,14 +705,16 @@
int ret;
int64_t aligned_offset;
int aligned_diff;
- int buffer_size;
+ uint64_t buffer_size;
char *ptr;
aligned_offset = offset & ~(4096 - 1);
aligned_diff = offset - aligned_offset;
- buffer_size = len + aligned_diff;
+ buffer_size = (uint64_t)len + (uint64_t)aligned_diff;
-#ifndef USE_MINGW
+#ifndef _WIN32
+ if (buffer_size > SIZE_MAX)
+ return -E2BIG;
char *data = mmap64(NULL, buffer_size, PROT_READ, MAP_SHARED, fd,
aligned_offset);
if (data == MAP_FAILED) {
@@ -733,7 +742,7 @@
ret = out->sparse_ops->write_data_chunk(out, len, ptr);
-#ifndef USE_MINGW
+#ifndef _WIN32
munmap(data, buffer_size);
#else
free(data);
diff --git a/libsparse/sparse_read.c b/libsparse/sparse_read.c
index dbb4dab..a188202 100644
--- a/libsparse/sparse_read.c
+++ b/libsparse/sparse_read.c
@@ -79,7 +79,7 @@
s = " at ";
}
if (verbose) {
-#ifndef USE_MINGW
+#ifndef _WIN32
if (err == -EOVERFLOW) {
sparse_print_verbose("EOF while reading file%s%s\n", s, at);
} else
diff --git a/libutils/Printer.cpp b/libutils/Printer.cpp
index 1dc8632..98cd2c6 100644
--- a/libutils/Printer.cpp
+++ b/libutils/Printer.cpp
@@ -44,7 +44,7 @@
char* formattedString;
-#ifndef USE_MINGW
+#ifndef _WIN32
if (vasprintf(&formattedString, format, arglist) < 0) { // returns -1 on error
ALOGE("%s: Failed to format string", __FUNCTION__);
return;
@@ -115,7 +115,7 @@
return;
}
-#ifndef USE_MINGW
+#ifndef _WIN32
dprintf(mFd, mFormatString, mPrefix, string);
#endif
}
diff --git a/logd/LogStatistics.cpp b/logd/LogStatistics.cpp
index c6ebd52..f69bc50 100644
--- a/logd/LogStatistics.cpp
+++ b/logd/LogStatistics.cpp
@@ -21,6 +21,8 @@
#include <sys/types.h>
#include <unistd.h>
+#include <list>
+
#include <log/logger.h>
#include "LogStatistics.h"
@@ -467,55 +469,86 @@
short spaces = 1;
log_id_for_each(id) {
- if (!(logMask & (1 << id))) {
- continue;
- }
+ if (!(logMask & (1 << id))) continue;
oldLength = output.length();
- if (spaces < 0) {
- spaces = 0;
- }
+ if (spaces < 0) spaces = 0;
output += android::base::StringPrintf("%*s%s", spaces, "",
android_log_id_to_name(id));
spaces += spaces_total + oldLength - output.length();
}
+ if (spaces < 0) spaces = 0;
+ output += android::base::StringPrintf("%*sTotal", spaces, "");
- spaces = 4;
- output += "\nTotal";
+ static const char TotalStr[] = "\nTotal";
+ spaces = 10 - strlen(TotalStr);
+ output += TotalStr;
+ size_t totalSize = 0;
+ size_t totalEls = 0;
log_id_for_each(id) {
- if (!(logMask & (1 << id))) {
- continue;
- }
+ if (!(logMask & (1 << id))) continue;
oldLength = output.length();
- if (spaces < 0) {
- spaces = 0;
- }
- output += android::base::StringPrintf("%*s%zu/%zu", spaces, "",
- sizesTotal(id),
- elementsTotal(id));
+ if (spaces < 0) spaces = 0;
+ size_t szs = sizesTotal(id);
+ totalSize += szs;
+ size_t els = elementsTotal(id);
+ totalEls += els;
+ output += android::base::StringPrintf("%*s%zu/%zu", spaces, "", szs, els);
spaces += spaces_total + oldLength - output.length();
}
+ if (spaces < 0) spaces = 0;
+ output += android::base::StringPrintf("%*s%zu/%zu", spaces, "", totalSize, totalEls);
- spaces = 6;
- output += "\nNow";
+ static const char NowStr[] = "\nNow";
+ spaces = 10 - strlen(NowStr);
+ output += NowStr;
+ totalSize = 0;
+ totalEls = 0;
log_id_for_each(id) {
- if (!(logMask & (1 << id))) {
- continue;
- }
+ if (!(logMask & (1 << id))) continue;
size_t els = elements(id);
if (els) {
oldLength = output.length();
- if (spaces < 0) {
- spaces = 0;
- }
- output += android::base::StringPrintf("%*s%zu/%zu", spaces, "",
- sizes(id), els);
+ if (spaces < 0) spaces = 0;
+ size_t szs = sizes(id);
+ totalSize += szs;
+ totalEls += els;
+ output += android::base::StringPrintf("%*s%zu/%zu", spaces, "", szs, els);
spaces -= output.length() - oldLength;
}
spaces += spaces_total;
}
+ if (spaces < 0) spaces = 0;
+ output += android::base::StringPrintf("%*s%zu/%zu", spaces, "", totalSize, totalEls);
+
+ static const char OverheadStr[] = "\nOverhead";
+ spaces = 10 - strlen(OverheadStr);
+ output += OverheadStr;
+
+ totalSize = 0;
+ log_id_for_each(id) {
+ if (!(logMask & (1 << id))) continue;
+
+ size_t els = elements(id);
+ if (els) {
+ oldLength = output.length();
+ if (spaces < 0) spaces = 0;
+ // estimate the std::list overhead.
+ static const size_t overhead =
+ ((sizeof(LogBufferElement) + sizeof(uint64_t) - 1) &
+ -sizeof(uint64_t)) +
+ sizeof(std::list<LogBufferElement*>);
+ size_t szs = sizes(id) + els * overhead;
+ totalSize += szs;
+ output += android::base::StringPrintf("%*s%zu", spaces, "", szs);
+ spaces -= output.length() - oldLength;
+ }
+ spaces += spaces_total;
+ }
+ if (spaces < 0) spaces = 0;
+ output += android::base::StringPrintf("%*s%zu", spaces, "", totalSize);
// Report on Chattiest
@@ -523,9 +556,7 @@
// Chattiest by application (UID)
log_id_for_each(id) {
- if (!(logMask & (1 << id))) {
- continue;
- }
+ if (!(logMask & (1 << id))) continue;
name = (uid == AID_ROOT)
? "Chattiest UIDs in %s log buffer:"
@@ -539,27 +570,21 @@
: "Logging for this PID:";
output += pidTable.format(*this, uid, pid, name);
name = "Chattiest TIDs";
- if (pid) {
- name += android::base::StringPrintf(" for PID %d", pid);
- }
+ if (pid) name += android::base::StringPrintf(" for PID %d", pid);
name += ":";
output += tidTable.format(*this, uid, pid, name);
}
if (enable && (logMask & (1 << LOG_ID_EVENTS))) {
name = "Chattiest events log buffer TAGs";
- if (pid) {
- name += android::base::StringPrintf(" for PID %d", pid);
- }
+ if (pid) name += android::base::StringPrintf(" for PID %d", pid);
name += ":";
output += tagTable.format(*this, uid, pid, name, LOG_ID_EVENTS);
}
if (enable && (logMask & (1 << LOG_ID_SECURITY))) {
name = "Chattiest security log buffer TAGs";
- if (pid) {
- name += android::base::StringPrintf(" for PID %d", pid);
- }
+ if (pid) name += android::base::StringPrintf(" for PID %d", pid);
name += ":";
output += securityTagTable.format(*this, uid, pid, name, LOG_ID_SECURITY);
}