summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorYifan Hong <elsk@google.com>2017-02-22 18:28:23 +0000
committerGerrit Code Review <noreply-gerritcodereview@google.com>2017-02-22 18:28:24 +0000
commit057e74631b8b1c658ec9b67684bf486e1ec3e7e5 (patch)
tree73b4a3411b300e0d176d3440673c811efb61cd75
parent52a60e08fb3c636b073a9b6a27672bbd3061e5b8 (diff)
parenta57dffb151145529e71b22a8d7f985bc1de105f4 (diff)
downloadnative-057e74631b8b1c658ec9b67684bf486e1ec3e7e5.tar.gz
Merge "lshal: Fix timeout causes unexpected exits."
-rw-r--r--cmds/lshal/Lshal.cpp8
-rw-r--r--cmds/lshal/Timeout.h32
2 files changed, 32 insertions, 8 deletions
diff --git a/cmds/lshal/Lshal.cpp b/cmds/lshal/Lshal.cpp
index ce058c8a47..6fd9b21368 100644
--- a/cmds/lshal/Lshal.cpp
+++ b/cmds/lshal/Lshal.cpp
@@ -469,9 +469,17 @@ int Lshal::main(int argc, char **argv) {
return status;
}
+void signalHandler(int sig) {
+ if (sig == SIGINT) {
+ int retVal;
+ pthread_exit(&retVal);
+ }
+}
+
} // namespace lshal
} // namespace android
int main(int argc, char **argv) {
+ signal(SIGINT, ::android::lshal::signalHandler);
return ::android::lshal::Lshal{}.main(argc, argv);
}
diff --git a/cmds/lshal/Timeout.h b/cmds/lshal/Timeout.h
index 001c3d6790..ca477bf615 100644
--- a/cmds/lshal/Timeout.h
+++ b/cmds/lshal/Timeout.h
@@ -29,7 +29,8 @@ static constexpr std::chrono::milliseconds IPC_CALL_WAIT{500};
class BackgroundTaskState {
public:
- BackgroundTaskState(){}
+ BackgroundTaskState(std::function<void(void)> &&func)
+ : mFunc(std::forward<decltype(func)>(func)) {}
void notify() {
std::unique_lock<std::mutex> lock(mMutex);
mFinished = true;
@@ -42,22 +43,37 @@ public:
mCondVar.wait_until(lock, end, [this](){ return this->mFinished; });
return mFinished;
}
+ void operator()() {
+ mFunc();
+ }
private:
std::mutex mMutex;
std::condition_variable mCondVar;
bool mFinished = false;
+ std::function<void(void)> mFunc;
};
+void *callAndNotify(void *data) {
+ BackgroundTaskState &state = *static_cast<BackgroundTaskState *>(data);
+ state();
+ state.notify();
+ return NULL;
+}
+
template<class R, class P>
-bool timeout(std::chrono::duration<R, P> delay, const std::function<void(void)> &func) {
+bool timeout(std::chrono::duration<R, P> delay, std::function<void(void)> &&func) {
auto now = std::chrono::system_clock::now();
- BackgroundTaskState state{};
- std::thread t([&state, &func] {
- func();
- state.notify();
- });
- t.detach();
+ BackgroundTaskState state{std::forward<decltype(func)>(func)};
+ pthread_t thread;
+ if (pthread_create(&thread, NULL, callAndNotify, &state)) {
+ std::cerr << "FATAL: could not create background thread." << std::endl;
+ return false;
+ }
bool success = state.wait(now + delay);
+ if (!success) {
+ pthread_kill(thread, SIGINT);
+ }
+ pthread_join(thread, NULL);
return success;
}