diff --git a/init/init.cpp b/init/init.cpp index e5c154893..169808df0 100644 --- a/init/init.cpp +++ b/init/init.cpp @@ -570,23 +570,6 @@ static void InitAborter(const char* abort_message) { RebootSystem(ANDROID_RB_RESTART2, "bootloader"); } -static void InitKernelLogging(char* argv[]) { - // Make stdin/stdout/stderr all point to /dev/null. - int fd = open("/sys/fs/selinux/null", O_RDWR); - if (fd == -1) { - int saved_errno = errno; - android::base::InitLogging(argv, &android::base::KernelLogger, InitAborter); - errno = saved_errno; - PLOG(FATAL) << "Couldn't open /sys/fs/selinux/null"; - } - dup2(fd, 0); - dup2(fd, 1); - dup2(fd, 2); - if (fd > 2) close(fd); - - android::base::InitLogging(argv, &android::base::KernelLogger, InitAborter); -} - static void GlobalSeccomp() { import_kernel_cmdline(false, [](const std::string& key, const std::string& value, bool in_qemu) { @@ -643,7 +626,8 @@ int main(int argc, char** argv) { SetupSelinux(argv); } - InitKernelLogging(argv); + // We need to set up stdin/stdout/stderr again now that we're running in init's context. + InitKernelLogging(argv, InitAborter); LOG(INFO) << "init second stage started!"; // Enable seccomp if global boot option was passed (otherwise it is enabled in zygote). diff --git a/init/init_first_stage.cpp b/init/init_first_stage.cpp index 0c4a11093..fa5e658f3 100644 --- a/init/init_first_stage.cpp +++ b/init/init_first_stage.cpp @@ -99,9 +99,11 @@ int main(int argc, char** argv) { // Now that tmpfs is mounted on /dev and we have /dev/kmsg, we can actually // talk to the outside world... - android::base::InitLogging(argv, &android::base::KernelLogger, [](const char*) { - RebootSystem(ANDROID_RB_RESTART2, "bootloader"); - }); + // We need to set up stdin/stdout/stderr for child processes forked from first + // stage init as part of the mount process. This closes /dev/console if the + // kernel had previously opened it. + auto reboot_bootloader = [](const char*) { RebootSystem(ANDROID_RB_RESTART2, "bootloader"); }; + InitKernelLogging(argv, reboot_bootloader); if (!errors.empty()) { for (const auto& [error_string, error_errno] : errors) { diff --git a/init/util.cpp b/init/util.cpp index 105ac87fc..378114120 100644 --- a/init/util.cpp +++ b/init/util.cpp @@ -436,5 +436,21 @@ bool IsLegalPropertyName(const std::string& name) { return true; } +void InitKernelLogging(char** argv, std::function abort_function) { + // Make stdin/stdout/stderr all point to /dev/null. + int fd = open("/dev/null", O_RDWR); + if (fd == -1) { + int saved_errno = errno; + android::base::InitLogging(argv, &android::base::KernelLogger, std::move(abort_function)); + errno = saved_errno; + PLOG(FATAL) << "Couldn't open /dev/null"; + } + dup2(fd, 0); + dup2(fd, 1); + dup2(fd, 2); + if (fd > 2) close(fd); + android::base::InitLogging(argv, &android::base::KernelLogger, std::move(abort_function)); +} + } // namespace init } // namespace android diff --git a/init/util.h b/init/util.h index 07e4864ac..53f45473a 100644 --- a/init/util.h +++ b/init/util.h @@ -64,6 +64,8 @@ bool is_android_dt_value_expected(const std::string& sub_path, const std::string bool IsLegalPropertyName(const std::string& name); +void InitKernelLogging(char** argv, std::function abort_function); + } // namespace init } // namespace android