summaryrefslogtreecommitdiffstats
path: root/minadbd
diff options
context:
space:
mode:
authorandroid-build-team Robot <android-build-team-robot@google.com>2019-04-30 05:15:13 +0200
committerandroid-build-team Robot <android-build-team-robot@google.com>2019-04-30 05:15:13 +0200
commite1299d94095e5fc018472b27cc8d980234f2ffb2 (patch)
treeb0e3acf9305aec92ab4f388b6948caeccb05a8f7 /minadbd
parentSnap for 5480912 from d0052c30cef1202fff6bb0f87d64eddb98cfbc99 to qt-release (diff)
parentParse BCB command to enter rescue mode. (diff)
downloadandroid_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.tar
android_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.tar.gz
android_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.tar.bz2
android_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.tar.lz
android_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.tar.xz
android_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.tar.zst
android_bootable_recovery-e1299d94095e5fc018472b27cc8d980234f2ffb2.zip
Diffstat (limited to 'minadbd')
-rw-r--r--minadbd/Android.bp3
-rw-r--r--minadbd/fuse_adb_provider.cpp4
-rw-r--r--minadbd/fuse_adb_provider.h15
-rw-r--r--minadbd/minadbd.cpp12
-rw-r--r--minadbd/minadbd_services.cpp153
-rw-r--r--minadbd/minadbd_services.h6
-rw-r--r--minadbd/minadbd_services_test.cpp213
-rw-r--r--minadbd/minadbd_types.h14
8 files changed, 383 insertions, 37 deletions
diff --git a/minadbd/Android.bp b/minadbd/Android.bp
index e4f7712e5..007e5057b 100644
--- a/minadbd/Android.bp
+++ b/minadbd/Android.bp
@@ -76,7 +76,6 @@ cc_binary {
"libadbd",
"libbase",
"libcrypto",
- "libfusesideload",
"libminadbd_services",
],
}
@@ -91,12 +90,14 @@ cc_test {
srcs: [
"fuse_adb_provider_test.cpp",
+ "minadbd_services_test.cpp",
],
static_libs: [
"libminadbd_services",
"libfusesideload",
"libadbd",
+ "libcrypto",
],
shared_libs: [
diff --git a/minadbd/fuse_adb_provider.cpp b/minadbd/fuse_adb_provider.cpp
index 9d19a1ec3..47719b07a 100644
--- a/minadbd/fuse_adb_provider.cpp
+++ b/minadbd/fuse_adb_provider.cpp
@@ -37,7 +37,3 @@ bool FuseAdbDataProvider::ReadBlockAlignedData(uint8_t* buffer, uint32_t fetch_s
return true;
}
-
-void FuseAdbDataProvider::Close() {
- WriteFdExactly(fd_, "DONEDONE");
-}
diff --git a/minadbd/fuse_adb_provider.h b/minadbd/fuse_adb_provider.h
index 3fb689bd4..c5561e57d 100644
--- a/minadbd/fuse_adb_provider.h
+++ b/minadbd/fuse_adb_provider.h
@@ -14,25 +14,22 @@
* limitations under the License.
*/
-#ifndef __FUSE_ADB_PROVIDER_H
-#define __FUSE_ADB_PROVIDER_H
+#pragma once
#include <stdint.h>
-#include "android-base/unique_fd.h"
-
#include "fuse_provider.h"
// This class reads data from adb server.
class FuseAdbDataProvider : public FuseDataProvider {
public:
- FuseAdbDataProvider(android::base::unique_fd&& fd, uint64_t file_size, uint32_t block_size)
- : FuseDataProvider(std::move(fd), file_size, block_size) {}
+ FuseAdbDataProvider(int fd, uint64_t file_size, uint32_t block_size)
+ : FuseDataProvider(file_size, block_size), fd_(fd) {}
bool ReadBlockAlignedData(uint8_t* buffer, uint32_t fetch_size,
uint32_t start_block) const override;
- void Close() override;
+ private:
+ // The underlying source to read data from (i.e. the one that talks to the host).
+ int fd_;
};
-
-#endif
diff --git a/minadbd/minadbd.cpp b/minadbd/minadbd.cpp
index 57158ad57..c80d5490a 100644
--- a/minadbd/minadbd.cpp
+++ b/minadbd/minadbd.cpp
@@ -31,10 +31,13 @@
#include "minadbd_services.h"
#include "minadbd_types.h"
+using namespace std::string_literals;
+
int main(int argc, char** argv) {
android::base::InitLogging(argv, &android::base::StderrLogger);
// TODO(xunchang) implement a command parser
- if (argc != 3 || strcmp("--socket_fd", argv[1]) != 0) {
+ if ((argc != 3 && argc != 4) || argv[1] != "--socket_fd"s ||
+ (argc == 4 && argv[3] != "--rescue"s)) {
LOG(ERROR) << "minadbd has invalid arguments, argc: " << argc;
exit(kMinadbdArgumentsParsingError);
}
@@ -50,7 +53,12 @@ int main(int argc, char** argv) {
}
SetMinadbdSocketFd(socket_fd);
- adb_device_banner = "sideload";
+ if (argc == 4) {
+ SetMinadbdRescueMode(true);
+ adb_device_banner = "rescue";
+ } else {
+ adb_device_banner = "sideload";
+ }
signal(SIGPIPE, SIG_IGN);
diff --git a/minadbd/minadbd_services.cpp b/minadbd/minadbd_services.cpp
index 79e6fc4e0..9b1999d90 100644
--- a/minadbd/minadbd_services.cpp
+++ b/minadbd/minadbd_services.cpp
@@ -28,15 +28,19 @@
#include <string>
#include <string_view>
#include <thread>
+#include <unordered_set>
#include <android-base/file.h>
#include <android-base/logging.h>
#include <android-base/memory.h>
+#include <android-base/parseint.h>
+#include <android-base/properties.h>
#include <android-base/stringprintf.h>
#include <android-base/strings.h>
#include "adb.h"
#include "adb_unique_fd.h"
+#include "adb_utils.h"
#include "fdevent.h"
#include "fuse_adb_provider.h"
#include "fuse_sideload.h"
@@ -45,11 +49,22 @@
#include "sysdeps.h"
static int minadbd_socket = -1;
+static bool rescue_mode = false;
+static std::string sideload_mount_point = FUSE_SIDELOAD_HOST_MOUNTPOINT;
+
void SetMinadbdSocketFd(int socket_fd) {
minadbd_socket = socket_fd;
}
-static bool WriteCommandToFd(MinadbdCommands cmd, int fd) {
+void SetMinadbdRescueMode(bool rescue) {
+ rescue_mode = rescue;
+}
+
+void SetSideloadMountPoint(const std::string& path) {
+ sideload_mount_point = path;
+}
+
+static bool WriteCommandToFd(MinadbdCommand cmd, int fd) {
char message[kMinadbdMessageSize];
memcpy(message, kMinadbdCommandPrefix, strlen(kMinadbdStatusPrefix));
android::base::put_unaligned(message + strlen(kMinadbdStatusPrefix), cmd);
@@ -81,47 +96,149 @@ static bool WaitForCommandStatus(int fd, MinadbdCommandStatus* status) {
return true;
}
-static void sideload_host_service(unique_fd sfd, const std::string& args) {
+static MinadbdErrorCode RunAdbFuseSideload(int sfd, const std::string& args,
+ MinadbdCommandStatus* status) {
+ auto pieces = android::base::Split(args, ":");
int64_t file_size;
int block_size;
- if ((sscanf(args.c_str(), "%" SCNd64 ":%d", &file_size, &block_size) != 2) || file_size <= 0 ||
- block_size <= 0) {
+ if (pieces.size() != 2 || !android::base::ParseInt(pieces[0], &file_size) || file_size <= 0 ||
+ !android::base::ParseInt(pieces[1], &block_size) || block_size <= 0) {
LOG(ERROR) << "bad sideload-host arguments: " << args;
- exit(kMinadbdPackageSizeError);
+ return kMinadbdPackageSizeError;
}
LOG(INFO) << "sideload-host file size " << file_size << ", block size " << block_size;
- if (!WriteCommandToFd(MinadbdCommands::kInstall, minadbd_socket)) {
- exit(kMinadbdSocketIOError);
+ if (!WriteCommandToFd(MinadbdCommand::kInstall, minadbd_socket)) {
+ return kMinadbdSocketIOError;
}
- auto adb_data_reader =
- std::make_unique<FuseAdbDataProvider>(std::move(sfd), file_size, block_size);
- if (int result = run_fuse_sideload(std::move(adb_data_reader)); result != 0) {
+ auto adb_data_reader = std::make_unique<FuseAdbDataProvider>(sfd, file_size, block_size);
+ if (int result = run_fuse_sideload(std::move(adb_data_reader), sideload_mount_point.c_str());
+ result != 0) {
LOG(ERROR) << "Failed to start fuse";
- exit(kMinadbdFuseStartError);
+ return kMinadbdFuseStartError;
+ }
+
+ if (!WaitForCommandStatus(minadbd_socket, status)) {
+ return kMinadbdMessageFormatError;
}
+ // Signal host-side adb to stop. For sideload mode, we always send kSideloadServiceExitSuccess
+ // (i.e. "DONEDONE") regardless of the install result. For rescue mode, we send failure message on
+ // install error.
+ if (!rescue_mode || *status == MinadbdCommandStatus::kSuccess) {
+ if (!android::base::WriteFully(sfd, kSideloadServiceExitSuccess,
+ strlen(kSideloadServiceExitSuccess))) {
+ return kMinadbdHostSocketIOError;
+ }
+ } else {
+ if (!android::base::WriteFully(sfd, kSideloadServiceExitFailure,
+ strlen(kSideloadServiceExitFailure))) {
+ return kMinadbdHostSocketIOError;
+ }
+ }
+
+ return kMinadbdSuccess;
+}
+
+// Sideload service always exits after serving an install command.
+static void SideloadHostService(unique_fd sfd, const std::string& args) {
+ MinadbdCommandStatus status;
+ exit(RunAdbFuseSideload(sfd.get(), args, &status));
+}
+
+// Rescue service waits for the next command after an install command.
+static void RescueInstallHostService(unique_fd sfd, const std::string& args) {
+ MinadbdCommandStatus status;
+ if (auto result = RunAdbFuseSideload(sfd.get(), args, &status); result != kMinadbdSuccess) {
+ exit(result);
+ }
+}
+
+static void RescueGetpropHostService(unique_fd sfd, const std::string& prop) {
+ static const std::unordered_set<std::string> kGetpropAllowedProps = {
+ "ro.build.fingerprint",
+ "ro.build.date.utc",
+ };
+ auto allowed = kGetpropAllowedProps.find(prop) != kGetpropAllowedProps.end();
+ if (!allowed) {
+ return;
+ }
+
+ auto result = android::base::GetProperty(prop, "");
+ if (result.empty()) {
+ return;
+ }
+ if (!android::base::WriteFully(sfd, result.data(), result.size())) {
+ exit(kMinadbdHostSocketIOError);
+ }
+}
+
+// Reboots into the given target. We don't reboot directly from minadbd, but going through recovery
+// instead. This allows recovery to finish all the pending works (clear BCB, save logs etc) before
+// the reboot.
+static void RebootHostService(unique_fd /* sfd */, const std::string& target) {
+ MinadbdCommand command;
+ if (target == "bootloader") {
+ command = MinadbdCommand::kRebootBootloader;
+ } else if (target == "rescue") {
+ command = MinadbdCommand::kRebootRescue;
+ } else if (target == "recovery") {
+ command = MinadbdCommand::kRebootRecovery;
+ } else if (target == "fastboot") {
+ command = MinadbdCommand::kRebootFastboot;
+ } else {
+ command = MinadbdCommand::kRebootAndroid;
+ }
+ if (!WriteCommandToFd(command, minadbd_socket)) {
+ exit(kMinadbdSocketIOError);
+ }
MinadbdCommandStatus status;
if (!WaitForCommandStatus(minadbd_socket, &status)) {
exit(kMinadbdMessageFormatError);
}
- LOG(INFO) << "Got command status: " << static_cast<unsigned int>(status);
-
- LOG(INFO) << "sideload_host finished";
- exit(kMinadbdSuccess);
}
unique_fd daemon_service_to_fd(std::string_view name, atransport* /* transport */) {
+ // Common services that are supported both in sideload and rescue modes.
+ if (ConsumePrefix(&name, "reboot:")) {
+ // "reboot:<target>", where target must be one of the following.
+ std::string args(name);
+ if (args.empty() || args == "bootloader" || args == "rescue" || args == "recovery" ||
+ args == "fastboot") {
+ return create_service_thread("reboot",
+ std::bind(RebootHostService, std::placeholders::_1, args));
+ }
+ return unique_fd{};
+ }
+
+ // Rescue-specific services.
+ if (rescue_mode) {
+ if (ConsumePrefix(&name, "rescue-install:")) {
+ // rescue-install:<file-size>:<block-size>
+ std::string args(name);
+ return create_service_thread(
+ "rescue-install", std::bind(RescueInstallHostService, std::placeholders::_1, args));
+ } else if (ConsumePrefix(&name, "rescue-getprop:")) {
+ // rescue-getprop:<prop>
+ std::string args(name);
+ return create_service_thread(
+ "rescue-getprop", std::bind(RescueGetpropHostService, std::placeholders::_1, args));
+ }
+ return unique_fd{};
+ }
+
+ // Sideload-specific services.
if (name.starts_with("sideload:")) {
// This exit status causes recovery to print a special error message saying to use a newer adb
// (that supports sideload-host).
exit(kMinadbdAdbVersionError);
- } else if (name.starts_with("sideload-host:")) {
- std::string arg(name.substr(strlen("sideload-host:")));
+ } else if (ConsumePrefix(&name, "sideload-host:")) {
+ // sideload-host:<file-size>:<block-size>
+ std::string args(name);
return create_service_thread("sideload-host",
- std::bind(sideload_host_service, std::placeholders::_1, arg));
+ std::bind(SideloadHostService, std::placeholders::_1, args));
}
return unique_fd{};
}
diff --git a/minadbd/minadbd_services.h b/minadbd/minadbd_services.h
index 6835bd770..5575c6b8e 100644
--- a/minadbd/minadbd_services.h
+++ b/minadbd/minadbd_services.h
@@ -16,4 +16,10 @@
#pragma once
+#include <string>
+
void SetMinadbdSocketFd(int socket_fd);
+
+void SetMinadbdRescueMode(bool);
+
+void SetSideloadMountPoint(const std::string& path);
diff --git a/minadbd/minadbd_services_test.cpp b/minadbd/minadbd_services_test.cpp
new file mode 100644
index 000000000..593180bb3
--- /dev/null
+++ b/minadbd/minadbd_services_test.cpp
@@ -0,0 +1,213 @@
+/*
+ * Copyright (C) 2019 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.
+ */
+
+#include <errno.h>
+#include <fcntl.h>
+#include <signal.h>
+#include <strings.h>
+#include <sys/mount.h>
+#include <sys/socket.h>
+#include <sys/stat.h>
+#include <sys/wait.h>
+#include <unistd.h>
+
+#include <string>
+#include <vector>
+
+#include <android-base/file.h>
+#include <android-base/unique_fd.h>
+#include <gtest/gtest.h>
+
+#include "adb.h"
+#include "adb_io.h"
+#include "fuse_adb_provider.h"
+#include "fuse_sideload.h"
+#include "minadbd_services.h"
+#include "minadbd_types.h"
+#include "socket.h"
+
+class MinadbdServicesTest : public ::testing::Test {
+ protected:
+ static constexpr int EXIT_TIME_OUT = 10;
+
+ void SetUp() override {
+ ASSERT_TRUE(
+ android::base::Socketpair(AF_UNIX, SOCK_STREAM, 0, &minadbd_socket_, &recovery_socket_));
+ SetMinadbdSocketFd(minadbd_socket_);
+ SetSideloadMountPoint(mount_point_.path);
+
+ package_path_ = std::string(mount_point_.path) + "/" + FUSE_SIDELOAD_HOST_FILENAME;
+ exit_flag_ = std::string(mount_point_.path) + "/" + FUSE_SIDELOAD_HOST_EXIT_FLAG;
+
+ signal(SIGPIPE, SIG_IGN);
+ }
+
+ void TearDown() override {
+ // Umount in case the test fails. Ignore the result.
+ umount(mount_point_.path);
+
+ signal(SIGPIPE, SIG_DFL);
+ }
+
+ void ReadAndCheckCommandMessage(int fd, MinadbdCommand expected_command) {
+ std::vector<uint8_t> received(kMinadbdMessageSize, '\0');
+ ASSERT_TRUE(android::base::ReadFully(fd, received.data(), kMinadbdMessageSize));
+
+ std::vector<uint8_t> expected(kMinadbdMessageSize, '\0');
+ memcpy(expected.data(), kMinadbdCommandPrefix, strlen(kMinadbdCommandPrefix));
+ memcpy(expected.data() + strlen(kMinadbdCommandPrefix), &expected_command,
+ sizeof(expected_command));
+ ASSERT_EQ(expected, received);
+ }
+
+ void WaitForFusePath() {
+ constexpr int TIME_OUT = 10;
+ for (int i = 0; i < TIME_OUT; ++i) {
+ struct stat sb;
+ if (stat(package_path_.c_str(), &sb) == 0) {
+ return;
+ }
+
+ if (errno == ENOENT) {
+ sleep(1);
+ continue;
+ }
+ FAIL() << "Timed out waiting for the fuse-provided package " << strerror(errno);
+ }
+ }
+
+ void StatExitFlagAndExitProcess(int exit_code) {
+ struct stat sb;
+ if (stat(exit_flag_.c_str(), &sb) != 0) {
+ PLOG(ERROR) << "Failed to stat " << exit_flag_;
+ }
+
+ exit(exit_code);
+ }
+
+ void WriteMinadbdCommandStatus(MinadbdCommandStatus status) {
+ std::string status_message(kMinadbdMessageSize, '\0');
+ memcpy(status_message.data(), kMinadbdStatusPrefix, strlen(kMinadbdStatusPrefix));
+ memcpy(status_message.data() + strlen(kMinadbdStatusPrefix), &status, sizeof(status));
+ ASSERT_TRUE(
+ android::base::WriteFully(recovery_socket_, status_message.data(), kMinadbdMessageSize));
+ }
+
+ void ExecuteCommandAndWaitForExit(const std::string& command) {
+ unique_fd fd = daemon_service_to_fd(command, nullptr);
+ ASSERT_NE(-1, fd);
+ sleep(EXIT_TIME_OUT);
+ }
+
+ android::base::unique_fd minadbd_socket_;
+ android::base::unique_fd recovery_socket_;
+
+ TemporaryDir mount_point_;
+ std::string package_path_;
+ std::string exit_flag_;
+};
+
+TEST_F(MinadbdServicesTest, SideloadHostService_wrong_size_argument) {
+ ASSERT_EXIT(ExecuteCommandAndWaitForExit("sideload-host:abc:4096"),
+ ::testing::ExitedWithCode(kMinadbdPackageSizeError), "");
+}
+
+TEST_F(MinadbdServicesTest, SideloadHostService_wrong_block_size) {
+ ASSERT_EXIT(ExecuteCommandAndWaitForExit("sideload-host:10:20"),
+ ::testing::ExitedWithCode(kMinadbdFuseStartError), "");
+}
+
+TEST_F(MinadbdServicesTest, SideloadHostService_broken_minadbd_socket) {
+ SetMinadbdSocketFd(-1);
+ ASSERT_EXIT(ExecuteCommandAndWaitForExit("sideload-host:4096:4096"),
+ ::testing::ExitedWithCode(kMinadbdSocketIOError), "");
+}
+
+TEST_F(MinadbdServicesTest, SideloadHostService_broken_recovery_socket) {
+ recovery_socket_.reset();
+ ASSERT_EXIT(ExecuteCommandAndWaitForExit("sideload-host:4096:4096"),
+ ::testing::ExitedWithCode(kMinadbdSocketIOError), "");
+}
+
+TEST_F(MinadbdServicesTest, SideloadHostService_wrong_command_format) {
+ auto test_body = [&](const std::string& command) {
+ unique_fd fd = daemon_service_to_fd(command, nullptr);
+ ASSERT_NE(-1, fd);
+ WaitForFusePath();
+ ReadAndCheckCommandMessage(recovery_socket_, MinadbdCommand::kInstall);
+
+ struct stat sb;
+ ASSERT_EQ(0, stat(exit_flag_.c_str(), &sb));
+ ASSERT_TRUE(android::base::WriteStringToFd("12345678", recovery_socket_));
+ sleep(EXIT_TIME_OUT);
+ };
+
+ ASSERT_EXIT(test_body("sideload-host:4096:4096"),
+ ::testing::ExitedWithCode(kMinadbdMessageFormatError), "");
+}
+
+TEST_F(MinadbdServicesTest, SideloadHostService_read_data_from_fuse) {
+ auto test_body = [&]() {
+ std::vector<uint8_t> content(4096, 'a');
+ // Start a new process instead of a thread to read from the package mounted by FUSE. Because
+ // the test may not exit and report failures correctly when the thread blocks by a syscall.
+ pid_t pid = fork();
+ if (pid == 0) {
+ WaitForFusePath();
+ android::base::unique_fd fd(TEMP_FAILURE_RETRY(open(package_path_.c_str(), O_RDONLY)));
+ // Do not use assertion here because we want to stat the exit flag and exit the process.
+ // Otherwise the test will wait for the time out instead of failing immediately.
+ if (fd == -1) {
+ PLOG(ERROR) << "Failed to open " << package_path_;
+ StatExitFlagAndExitProcess(1);
+ }
+ std::vector<uint8_t> content_from_fuse(4096);
+ if (!android::base::ReadFully(fd, content_from_fuse.data(), 4096)) {
+ PLOG(ERROR) << "Failed to read from " << package_path_;
+ StatExitFlagAndExitProcess(1);
+ }
+ if (content_from_fuse != content) {
+ LOG(ERROR) << "Content read from fuse doesn't match with the expected value";
+ StatExitFlagAndExitProcess(1);
+ }
+ StatExitFlagAndExitProcess(0);
+ }
+
+ unique_fd fd = daemon_service_to_fd("sideload-host:4096:4096", nullptr);
+ ASSERT_NE(-1, fd);
+ ReadAndCheckCommandMessage(recovery_socket_, MinadbdCommand::kInstall);
+
+ // Mimic the response from adb host.
+ std::string adb_message(8, '\0');
+ ASSERT_TRUE(android::base::ReadFully(fd, adb_message.data(), 8));
+ ASSERT_EQ(android::base::StringPrintf("%08u", 0), adb_message);
+ ASSERT_TRUE(android::base::WriteFully(fd, content.data(), 4096));
+
+ // Check that we read the correct data from fuse.
+ int child_status;
+ waitpid(pid, &child_status, 0);
+ ASSERT_TRUE(WIFEXITED(child_status));
+ ASSERT_EQ(0, WEXITSTATUS(child_status));
+
+ WriteMinadbdCommandStatus(MinadbdCommandStatus::kSuccess);
+
+ // TODO(xunchang) check if adb host-side receives "DONEDONE", there's a race condition between
+ // receiving the message and exit of test body (by detached thread in minadbd service).
+ exit(kMinadbdSuccess);
+ };
+
+ ASSERT_EXIT(test_body(), ::testing::ExitedWithCode(kMinadbdSuccess), "");
+}
diff --git a/minadbd/minadbd_types.h b/minadbd/minadbd_types.h
index 7bd69096a..b370b7952 100644
--- a/minadbd/minadbd_types.h
+++ b/minadbd/minadbd_types.h
@@ -35,6 +35,7 @@ enum MinadbdErrorCode : int {
kMinadbdUnsupportedCommandError = 7,
kMinadbdCommandExecutionError = 8,
kMinadbdErrorUnknown = 9,
+ kMinadbdHostSocketIOError = 10,
};
enum class MinadbdCommandStatus : uint32_t {
@@ -42,12 +43,19 @@ enum class MinadbdCommandStatus : uint32_t {
kFailure = 1,
};
-enum class MinadbdCommands : uint32_t {
+enum class MinadbdCommand : uint32_t {
kInstall = 0,
kUiPrint = 1,
- kError = 2,
+ kRebootAndroid = 2,
+ kRebootBootloader = 3,
+ kRebootFastboot = 4,
+ kRebootRecovery = 5,
+ kRebootRescue = 6,
+
+ // Last but invalid command.
+ kError,
};
-static_assert(kMinadbdMessageSize == sizeof(kMinadbdCommandPrefix) - 1 + sizeof(MinadbdCommands));
+static_assert(kMinadbdMessageSize == sizeof(kMinadbdCommandPrefix) - 1 + sizeof(MinadbdCommand));
static_assert(kMinadbdMessageSize ==
sizeof(kMinadbdStatusPrefix) - 1 + sizeof(MinadbdCommandStatus));