Merge "llkd: bootstat: propagate detailed livelock canonical boot reason"
diff --git a/adb/adb.cpp b/adb/adb.cpp
index 4fbfafb..38c11b9 100644
--- a/adb/adb.cpp
+++ b/adb/adb.cpp
@@ -1221,7 +1221,7 @@
     std::string error;
     atransport* t = acquire_one_transport(type, serial, transport_id, nullptr, &error);
     if (!t) {
-        return SendFail(reply_fd, error);
+        return -1;
     }
 
     int ret = handle_forward_request(service, t, reply_fd);
diff --git a/adb/test_adb.py b/adb/test_adb.py
index 3bb433d..363002f 100644
--- a/adb/test_adb.py
+++ b/adb/test_adb.py
@@ -21,9 +21,11 @@
 """
 from __future__ import print_function
 
+import binascii
 import contextlib
 import os
 import random
+import select
 import socket
 import struct
 import subprocess
@@ -33,6 +35,52 @@
 import adb
 
 
+@contextlib.contextmanager
+def fake_adb_server(protocol=socket.AF_INET, port=0):
+    """Creates a fake ADB server that just replies with a CNXN packet."""
+
+    serversock = socket.socket(protocol, socket.SOCK_STREAM)
+    if protocol == socket.AF_INET:
+        serversock.bind(('127.0.0.1', port))
+    else:
+        serversock.bind(('::1', port))
+    serversock.listen(1)
+
+    # A pipe that is used to signal the thread that it should terminate.
+    readpipe, writepipe = os.pipe()
+
+    def _handle():
+        rlist = [readpipe, serversock]
+        while True:
+            ready, _, _ = select.select(rlist, [], [])
+            for r in ready:
+                if r == readpipe:
+                    # Closure pipe
+                    os.close(r)
+                    serversock.shutdown(socket.SHUT_RDWR)
+                    serversock.close()
+                    return
+                elif r == serversock:
+                    # Server socket
+                    conn, _ = r.accept()
+                    rlist.append(conn)
+                else:
+                    # Client socket
+                    data = r.recv(1024)
+                    if not data:
+                        rlist.remove(r)
+
+    port = serversock.getsockname()[1]
+    server_thread = threading.Thread(target=_handle)
+    server_thread.start()
+
+    try:
+        yield port
+    finally:
+        os.close(writepipe)
+        server_thread.join()
+
+
 class NonApiTest(unittest.TestCase):
     """Tests for ADB that aren't a part of the AndroidDevice API."""
 
@@ -211,45 +259,32 @@
 
         Bug: http://b/30313466
         """
-        ipv4 = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
-        ipv4.bind(('127.0.0.1', 0))
-        ipv4.listen(1)
+        for protocol in (socket.AF_INET, socket.AF_INET6):
+            try:
+                with fake_adb_server(protocol=protocol) as port:
+                    output = subprocess.check_output(
+                        ['adb', 'connect', 'localhost:{}'.format(port)])
 
-        ipv6 = socket.socket(socket.AF_INET6, socket.SOCK_STREAM)
-        try:
-            ipv6.bind(('::1', ipv4.getsockname()[1] + 1))
-            ipv6.listen(1)
-        except socket.error:
-            print("IPv6 not available, skipping")
-            return
+                    self.assertEqual(
+                        output.strip(), 'connected to localhost:{}'.format(port))
+            except socket.error:
+                print("IPv6 not available, skipping")
+                continue
 
-        for s in (ipv4, ipv6):
-            port = s.getsockname()[1]
+    def test_already_connected(self):
+        with fake_adb_server() as port:
             output = subprocess.check_output(
                 ['adb', 'connect', 'localhost:{}'.format(port)])
 
             self.assertEqual(
                 output.strip(), 'connected to localhost:{}'.format(port))
-            s.close()
 
-    def test_already_connected(self):
-        s = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
-        s.bind(('127.0.0.1', 0))
-        s.listen(2)
+            # b/31250450: this always returns 0 but probably shouldn't.
+            output = subprocess.check_output(
+                ['adb', 'connect', 'localhost:{}'.format(port)])
 
-        port = s.getsockname()[1]
-        output = subprocess.check_output(
-            ['adb', 'connect', 'localhost:{}'.format(port)])
-
-        self.assertEqual(
-            output.strip(), 'connected to localhost:{}'.format(port))
-
-        # b/31250450: this always returns 0 but probably shouldn't.
-        output = subprocess.check_output(
-            ['adb', 'connect', 'localhost:{}'.format(port)])
-
-        self.assertEqual(
-            output.strip(), 'already connected to localhost:{}'.format(port))
+            self.assertEqual(
+                output.strip(), 'already connected to localhost:{}'.format(port))
 
 def main():
     random.seed(0)
diff --git a/adb/transport.cpp b/adb/transport.cpp
index 92c52e2..f5f6d26 100644
--- a/adb/transport.cpp
+++ b/adb/transport.cpp
@@ -974,7 +974,7 @@
             VLOG(TRANSPORT) << "socket transport " << transport->serial
                             << " is already in pending_list and fails to register";
             delete t;
-            return -1;
+            return -EALREADY;
         }
     }
 
@@ -983,7 +983,7 @@
             VLOG(TRANSPORT) << "socket transport " << transport->serial
                             << " is already in transport_list and fails to register";
             delete t;
-            return -1;
+            return -EALREADY;
         }
     }
 
diff --git a/adb/transport_local.cpp b/adb/transport_local.cpp
index c09fcb7..8032421 100644
--- a/adb/transport_local.cpp
+++ b/adb/transport_local.cpp
@@ -101,7 +101,11 @@
     int ret = register_socket_transport(fd, serial.c_str(), port, 0);
     if (ret < 0) {
         adb_close(fd);
-        *response = android::base::StringPrintf("already connected to %s", serial.c_str());
+        if (ret == -EALREADY) {
+            *response = android::base::StringPrintf("already connected to %s", serial.c_str());
+        } else {
+            *response = android::base::StringPrintf("failed to connect to %s", serial.c_str());
+        }
     } else {
         *response = android::base::StringPrintf("connected to %s", serial.c_str());
     }
diff --git a/base/include/android-base/parseint.h b/base/include/android-base/parseint.h
index 2c8570e..1b7cc5f 100644
--- a/base/include/android-base/parseint.h
+++ b/base/include/android-base/parseint.h
@@ -19,6 +19,7 @@
 
 #include <errno.h>
 #include <stdlib.h>
+#include <string.h>
 
 #include <limits>
 #include <string>
@@ -31,14 +32,20 @@
 // otherwise valid values will be rejected. Returns boolean success; 'out'
 // is untouched if parsing fails.
 template <typename T>
-bool ParseUint(const char* s, T* out,
-               T max = std::numeric_limits<T>::max()) {
+bool ParseUint(const char* s, T* out, T max = std::numeric_limits<T>::max(),
+               bool allow_suffixes = false) {
   int base = (s[0] == '0' && (s[1] == 'x' || s[1] == 'X')) ? 16 : 10;
   errno = 0;
   char* end;
   unsigned long long int result = strtoull(s, &end, base);
-  if (errno != 0 || s == end || *end != '\0') {
-    return false;
+  if (errno != 0 || end == s) return false;
+  if (*end != '\0') {
+    const char* suffixes = "bkmgtpe";
+    const char* suffix;
+    if (!allow_suffixes || (suffix = strchr(suffixes, tolower(*end))) == nullptr) return false;
+#if __clang__  // TODO: win32 still builds with GCC :-(
+    if (__builtin_mul_overflow(result, 1ULL << (10 * (suffix - suffixes)), &result)) return false;
+#endif
   }
   if (max < result) {
     return false;
@@ -49,9 +56,20 @@
 
 // TODO: string_view
 template <typename T>
-bool ParseUint(const std::string& s, T* out,
-               T max = std::numeric_limits<T>::max()) {
-  return ParseUint(s.c_str(), out, max);
+bool ParseUint(const std::string& s, T* out, T max = std::numeric_limits<T>::max(),
+               bool allow_suffixes = false) {
+  return ParseUint(s.c_str(), out, max, allow_suffixes);
+}
+
+template <typename T>
+bool ParseByteCount(const char* s, T* out, T max = std::numeric_limits<T>::max()) {
+  return ParseUint(s, out, max, true);
+}
+
+// TODO: string_view
+template <typename T>
+bool ParseByteCount(const std::string& s, T* out, T max = std::numeric_limits<T>::max()) {
+  return ParseByteCount(s.c_str(), out, max);
 }
 
 // Parses the signed decimal integer in the string 's' and sets 'out' to
diff --git a/base/parseint_test.cpp b/base/parseint_test.cpp
index 483b1d3..fb1c339 100644
--- a/base/parseint_test.cpp
+++ b/base/parseint_test.cpp
@@ -96,3 +96,44 @@
   ASSERT_FALSE(android::base::ParseInt("456x", &u));
   ASSERT_EQ(123u, u);
 }
+
+TEST(parseint, ParseByteCount) {
+  uint64_t i = 0;
+  ASSERT_TRUE(android::base::ParseByteCount("123b", &i));
+  ASSERT_EQ(123ULL, i);
+
+  ASSERT_TRUE(android::base::ParseByteCount("8k", &i));
+  ASSERT_EQ(8ULL * 1024, i);
+
+  ASSERT_TRUE(android::base::ParseByteCount("8M", &i));
+  ASSERT_EQ(8ULL * 1024 * 1024, i);
+
+  ASSERT_TRUE(android::base::ParseByteCount("6g", &i));
+  ASSERT_EQ(6ULL * 1024 * 1024 * 1024, i);
+
+  ASSERT_TRUE(android::base::ParseByteCount("1T", &i));
+  ASSERT_EQ(1ULL * 1024 * 1024 * 1024 * 1024, i);
+
+  ASSERT_TRUE(android::base::ParseByteCount("2p", &i));
+  ASSERT_EQ(2ULL * 1024 * 1024 * 1024 * 1024 * 1024, i);
+
+  ASSERT_TRUE(android::base::ParseByteCount("4e", &i));
+  ASSERT_EQ(4ULL * 1024 * 1024 * 1024 * 1024 * 1024 * 1024, i);
+}
+
+TEST(parseint, ParseByteCount_invalid_suffix) {
+  unsigned u;
+  ASSERT_FALSE(android::base::ParseByteCount("1x", &u));
+}
+
+TEST(parseint, ParseByteCount_overflow) {
+  uint64_t u64;
+  ASSERT_FALSE(android::base::ParseByteCount("4294967295E", &u64));
+
+  uint16_t u16;
+  ASSERT_TRUE(android::base::ParseByteCount("63k", &u16));
+  ASSERT_EQ(63U * 1024, u16);
+  ASSERT_TRUE(android::base::ParseByteCount("65535b", &u16));
+  ASSERT_EQ(65535U, u16);
+  ASSERT_FALSE(android::base::ParseByteCount("65k", &u16));
+}
diff --git a/fastboot/fastboot.cpp b/fastboot/fastboot.cpp
index 41a3d6b..780ff50 100644
--- a/fastboot/fastboot.cpp
+++ b/fastboot/fastboot.cpp
@@ -82,7 +82,7 @@
 // libsparse will support INT_MAX, but this results in large allocations, so
 // let's keep it at 1GB to avoid memory pressure on the host.
 static constexpr int64_t RESPARSE_LIMIT = 1 * 1024 * 1024 * 1024;
-static int64_t sparse_limit = -1;
+static uint64_t sparse_limit = 0;
 static int64_t target_sparse_limit = -1;
 
 static unsigned g_base_addr = 0x10000000;
@@ -375,7 +375,7 @@
             " -w                         Wipe userdata.\n"
             " -s SERIAL                  Specify a USB device.\n"
             " -s tcp|udp:HOST[:PORT]     Specify a network device.\n"
-            " -S SIZE[K|M|G]             Use sparse files above this limit (0 to disable).\n"
+            " -S SIZE[K|M|G]             Break into sparse files no larger than SIZE.\n"
             " --slot SLOT                Use SLOT; 'all' for both slots, 'other' for\n"
             "                            non-current slot (default: current active slot).\n"
             " --set-active[=SLOT]        Sets the active slot before rebooting.\n"
@@ -730,13 +730,10 @@
 }
 
 static int64_t get_sparse_limit(Transport* transport, int64_t size) {
-    int64_t limit;
-
-    if (sparse_limit == 0) {
-        return 0;
-    } else if (sparse_limit > 0) {
-        limit = sparse_limit;
-    } else {
+    int64_t limit = sparse_limit;
+    if (limit == 0) {
+        // Unlimited, so see what the target device's limit is.
+        // TODO: shouldn't we apply this limit even if you've used -S?
         if (target_sparse_limit == -1) {
             target_sparse_limit = get_target_sparse_limit(transport);
         }
@@ -1197,47 +1194,6 @@
     fb_queue_command(command, "");
 }
 
-static int64_t parse_num(const char *arg)
-{
-    char *endptr;
-    unsigned long long num;
-
-    num = strtoull(arg, &endptr, 0);
-    if (endptr == arg) {
-        return -1;
-    }
-
-    if (*endptr == 'k' || *endptr == 'K') {
-        if (num >= (-1ULL) / 1024) {
-            return -1;
-        }
-        num *= 1024LL;
-        endptr++;
-    } else if (*endptr == 'm' || *endptr == 'M') {
-        if (num >= (-1ULL) / (1024 * 1024)) {
-            return -1;
-        }
-        num *= 1024LL * 1024LL;
-        endptr++;
-    } else if (*endptr == 'g' || *endptr == 'G') {
-        if (num >= (-1ULL) / (1024 * 1024 * 1024)) {
-            return -1;
-        }
-        num *= 1024LL * 1024LL * 1024LL;
-        endptr++;
-    }
-
-    if (*endptr != '\0') {
-        return -1;
-    }
-
-    if (num > INT64_MAX) {
-        return -1;
-    }
-
-    return num;
-}
-
 static std::string fb_fix_numeric_var(std::string var) {
     // Some bootloaders (angler, for example), send spurious leading whitespace.
     var = android::base::Trim(var);
@@ -1471,8 +1427,9 @@
                     serial = optarg;
                     break;
                 case 'S':
-                    sparse_limit = parse_num(optarg);
-                    if (sparse_limit < 0) die("invalid sparse limit");
+                    if (!android::base::ParseByteCount(optarg, &sparse_limit)) {
+                        die("invalid sparse limit %s", optarg);
+                    }
                     break;
                 case 'v':
                     set_verbose();
diff --git a/init/bootchart.cpp b/init/bootchart.cpp
index 379b4fa..c2cf573 100644
--- a/init/bootchart.cpp
+++ b/init/bootchart.cpp
@@ -32,12 +32,14 @@
 #include <mutex>
 #include <thread>
 
+#include <android-base/chrono_utils.h>
 #include <android-base/file.h>
 #include <android-base/logging.h>
 #include <android-base/properties.h>
 #include <android-base/stringprintf.h>
 
 using android::base::StringPrintf;
+using android::base::boot_clock;
 using namespace std::chrono_literals;
 
 namespace android {
@@ -50,9 +52,9 @@
 static bool g_bootcharting_finished;
 
 static long long get_uptime_jiffies() {
-  std::string uptime;
-  if (!android::base::ReadFileToString("/proc/uptime", &uptime)) return 0;
-  return 100LL * strtod(uptime.c_str(), NULL);
+    constexpr int64_t kNanosecondsPerJiffy = 10000000;
+    boot_clock::time_point uptime = boot_clock::now();
+    return uptime.time_since_epoch().count() / kNanosecondsPerJiffy;
 }
 
 static std::unique_ptr<FILE, decltype(&fclose)> fopen_unique(const char* filename,
diff --git a/init/builtins.cpp b/init/builtins.cpp
index acbeca2..8bd92cc 100644
--- a/init/builtins.cpp
+++ b/init/builtins.cpp
@@ -519,6 +519,7 @@
         if (e4crypt_install_keyring()) {
             return Error() << "e4crypt_install_keyring() failed";
         }
+        property_set("ro.crypto.state", "encrypted");
         property_set("ro.crypto.type", "file");
 
         // Although encrypted, vold has already set the device up, so we do not need to
diff --git a/logcat/event.logtags b/logcat/event.logtags
index 0983676..7c40a77 100644
--- a/logcat/event.logtags
+++ b/logcat/event.logtags
@@ -119,6 +119,9 @@
 70200 aggregation (aggregation time|2|3)
 70201 aggregation_test (field1|1|2),(field2|1|2),(field3|1|2),(field4|1|2),(field5|1|2)
 
+# gms refuses to register this log tag, b/30156345
+70220 gms_unknown
+
 # libc failure logging
 80100 bionic_event_memcpy_buffer_overflow (uid|1)
 80105 bionic_event_strcat_buffer_overflow (uid|1)
diff --git a/rootdir/init.rc b/rootdir/init.rc
index 319b4c7..d3504ad 100644
--- a/rootdir/init.rc
+++ b/rootdir/init.rc
@@ -506,6 +506,7 @@
     mkdir /data/ss 0700 system system
 
     mkdir /data/system 0775 system system
+    mkdir /data/system/dropbox 0700 system system
     mkdir /data/system/heapdump 0700 system system
     mkdir /data/system/users 0775 system system