Loading init/epoll.cpp +12 −7 Original line number Diff line number Diff line Loading @@ -69,19 +69,24 @@ Result<void> Epoll::UnregisterHandler(int fd) { return {}; } Result<void> Epoll::Wait(std::optional<std::chrono::milliseconds> timeout) { Result<std::vector<std::function<void()>*>> Epoll::Wait( std::optional<std::chrono::milliseconds> timeout) { int timeout_ms = -1; if (timeout && timeout->count() < INT_MAX) { timeout_ms = timeout->count(); } epoll_event ev; auto nr = TEMP_FAILURE_RETRY(epoll_wait(epoll_fd_, &ev, 1, timeout_ms)); if (nr == -1) { const auto max_events = epoll_handlers_.size(); epoll_event ev[max_events]; auto num_events = TEMP_FAILURE_RETRY(epoll_wait(epoll_fd_, ev, max_events, timeout_ms)); if (num_events == -1) { return ErrnoError() << "epoll_wait failed"; } else if (nr == 1) { std::invoke(*reinterpret_cast<std::function<void()>*>(ev.data.ptr)); } return {}; std::vector<std::function<void()>*> pending_functions; for (int i = 0; i < num_events; ++i) { pending_functions.emplace_back(reinterpret_cast<std::function<void()>*>(ev[i].data.ptr)); } return pending_functions; } } // namespace init Loading init/epoll.h +4 −5 Original line number Diff line number Diff line Loading @@ -14,8 +14,7 @@ * limitations under the License. */ #ifndef _INIT_EPOLL_H #define _INIT_EPOLL_H #pragma once #include <stdint.h> #include <sys/epoll.h> Loading @@ -24,6 +23,7 @@ #include <functional> #include <map> #include <optional> #include <vector> #include <android-base/unique_fd.h> Loading @@ -39,7 +39,8 @@ class Epoll { Result<void> Open(); Result<void> RegisterHandler(int fd, std::function<void()> handler, uint32_t events = EPOLLIN); Result<void> UnregisterHandler(int fd); Result<void> Wait(std::optional<std::chrono::milliseconds> timeout); Result<std::vector<std::function<void()>*>> Wait( std::optional<std::chrono::milliseconds> timeout); private: android::base::unique_fd epoll_fd_; Loading @@ -48,5 +49,3 @@ class Epoll { } // namespace init } // namespace android #endif init/init.cpp +11 −2 Original line number Diff line number Diff line Loading @@ -787,8 +787,17 @@ int SecondStageMain(int argc, char** argv) { if (am.HasMoreCommands()) epoll_timeout = 0ms; } if (auto result = epoll.Wait(epoll_timeout); !result) { LOG(ERROR) << result.error(); auto pending_functions = epoll.Wait(epoll_timeout); if (!pending_functions) { LOG(ERROR) << pending_functions.error(); } else if (!pending_functions->empty()) { // We always reap children before responding to the other pending functions. This is to // prevent a race where other daemons see that a service has exited and ask init to // start it again via ctl.start before init has reaped it. ReapAnyOutstandingChildren(); for (const auto& function : *pending_functions) { (*function)(); } } } Loading init/keychords_test.cpp +5 −1 Original line number Diff line number Diff line Loading @@ -212,7 +212,11 @@ TestFrame::TestFrame(const std::vector<const std::vector<int>>& chords, EventHan } void TestFrame::RelaxForMs(std::chrono::milliseconds wait) { epoll_.Wait(wait); auto pending_functions = epoll_.Wait(wait); ASSERT_TRUE(pending_functions) << pending_functions.error(); for (const auto& function : *pending_functions) { (*function)(); } } void TestFrame::SetChord(int key, bool value) { Loading Loading
init/epoll.cpp +12 −7 Original line number Diff line number Diff line Loading @@ -69,19 +69,24 @@ Result<void> Epoll::UnregisterHandler(int fd) { return {}; } Result<void> Epoll::Wait(std::optional<std::chrono::milliseconds> timeout) { Result<std::vector<std::function<void()>*>> Epoll::Wait( std::optional<std::chrono::milliseconds> timeout) { int timeout_ms = -1; if (timeout && timeout->count() < INT_MAX) { timeout_ms = timeout->count(); } epoll_event ev; auto nr = TEMP_FAILURE_RETRY(epoll_wait(epoll_fd_, &ev, 1, timeout_ms)); if (nr == -1) { const auto max_events = epoll_handlers_.size(); epoll_event ev[max_events]; auto num_events = TEMP_FAILURE_RETRY(epoll_wait(epoll_fd_, ev, max_events, timeout_ms)); if (num_events == -1) { return ErrnoError() << "epoll_wait failed"; } else if (nr == 1) { std::invoke(*reinterpret_cast<std::function<void()>*>(ev.data.ptr)); } return {}; std::vector<std::function<void()>*> pending_functions; for (int i = 0; i < num_events; ++i) { pending_functions.emplace_back(reinterpret_cast<std::function<void()>*>(ev[i].data.ptr)); } return pending_functions; } } // namespace init Loading
init/epoll.h +4 −5 Original line number Diff line number Diff line Loading @@ -14,8 +14,7 @@ * limitations under the License. */ #ifndef _INIT_EPOLL_H #define _INIT_EPOLL_H #pragma once #include <stdint.h> #include <sys/epoll.h> Loading @@ -24,6 +23,7 @@ #include <functional> #include <map> #include <optional> #include <vector> #include <android-base/unique_fd.h> Loading @@ -39,7 +39,8 @@ class Epoll { Result<void> Open(); Result<void> RegisterHandler(int fd, std::function<void()> handler, uint32_t events = EPOLLIN); Result<void> UnregisterHandler(int fd); Result<void> Wait(std::optional<std::chrono::milliseconds> timeout); Result<std::vector<std::function<void()>*>> Wait( std::optional<std::chrono::milliseconds> timeout); private: android::base::unique_fd epoll_fd_; Loading @@ -48,5 +49,3 @@ class Epoll { } // namespace init } // namespace android #endif
init/init.cpp +11 −2 Original line number Diff line number Diff line Loading @@ -787,8 +787,17 @@ int SecondStageMain(int argc, char** argv) { if (am.HasMoreCommands()) epoll_timeout = 0ms; } if (auto result = epoll.Wait(epoll_timeout); !result) { LOG(ERROR) << result.error(); auto pending_functions = epoll.Wait(epoll_timeout); if (!pending_functions) { LOG(ERROR) << pending_functions.error(); } else if (!pending_functions->empty()) { // We always reap children before responding to the other pending functions. This is to // prevent a race where other daemons see that a service has exited and ask init to // start it again via ctl.start before init has reaped it. ReapAnyOutstandingChildren(); for (const auto& function : *pending_functions) { (*function)(); } } } Loading
init/keychords_test.cpp +5 −1 Original line number Diff line number Diff line Loading @@ -212,7 +212,11 @@ TestFrame::TestFrame(const std::vector<const std::vector<int>>& chords, EventHan } void TestFrame::RelaxForMs(std::chrono::milliseconds wait) { epoll_.Wait(wait); auto pending_functions = epoll_.Wait(wait); ASSERT_TRUE(pending_functions) << pending_functions.error(); for (const auto& function : *pending_functions) { (*function)(); } } void TestFrame::SetChord(int key, bool value) { Loading