From a8d8a83e125a6dad6ea5999b0b3c4ac4b2d10cf2 Mon Sep 17 00:00:00 2001 From: "michal.szwaj" Date: Thu, 5 Apr 2018 23:33:38 +0200 Subject: [PATCH] Standarize behavior of pinger cancel --- .../openauto/autoapp/Projection/IPinger.hpp | 2 +- .../openauto/autoapp/Projection/Pinger.hpp | 1 + src/autoapp/App.cpp | 4 +- src/autoapp/Projection/AndroidAutoEntity.cpp | 19 ++++---- src/autoapp/Projection/Pinger.cpp | 47 ++++++++++++------- 5 files changed, 46 insertions(+), 27 deletions(-) diff --git a/include/f1x/openauto/autoapp/Projection/IPinger.hpp b/include/f1x/openauto/autoapp/Projection/IPinger.hpp index 63def2b..379462f 100644 --- a/include/f1x/openauto/autoapp/Projection/IPinger.hpp +++ b/include/f1x/openauto/autoapp/Projection/IPinger.hpp @@ -33,7 +33,7 @@ class IPinger { public: typedef std::shared_ptr Pointer; - typedef aasdk::io::Promise Promise; + typedef aasdk::io::Promise Promise; virtual ~IPinger() = default; virtual void ping(Promise::Pointer promise) = 0; diff --git a/include/f1x/openauto/autoapp/Projection/Pinger.hpp b/include/f1x/openauto/autoapp/Projection/Pinger.hpp index 5c111eb..bc7884f 100644 --- a/include/f1x/openauto/autoapp/Projection/Pinger.hpp +++ b/include/f1x/openauto/autoapp/Projection/Pinger.hpp @@ -46,6 +46,7 @@ private: boost::asio::io_service::strand strand_; boost::asio::deadline_timer timer_; time_t duration_; + bool cancelled_; Promise::Pointer promise_; int64_t pingsCount_; int64_t pongsCount_; diff --git a/src/autoapp/App.cpp b/src/autoapp/App.cpp index 100293e..311891f 100644 --- a/src/autoapp/App.cpp +++ b/src/autoapp/App.cpp @@ -174,8 +174,8 @@ void App::onUSBHubError(const aasdk::error::Error& error) { OPENAUTO_LOG(error) << "[App] usb hub error: " << error.what(); - if(error.getCode() != aasdk::error::ErrorCode::OPERATION_ABORTED && - error.getCode() != aasdk::error::ErrorCode::OPERATION_IN_PROGRESS) + if(error != aasdk::error::ErrorCode::OPERATION_ABORTED && + error != aasdk::error::ErrorCode::OPERATION_IN_PROGRESS) { this->waitForDevice(); } diff --git a/src/autoapp/Projection/AndroidAutoEntity.cpp b/src/autoapp/Projection/AndroidAutoEntity.cpp index 7e9c0d1..b36bb29 100644 --- a/src/autoapp/Projection/AndroidAutoEntity.cpp +++ b/src/autoapp/Projection/AndroidAutoEntity.cpp @@ -60,17 +60,18 @@ void AndroidAutoEntity::start(IAndroidAutoEntityEventHandler& eventHandler) { strand_.dispatch([this, self = this->shared_from_this(), eventHandler = &eventHandler]() { OPENAUTO_LOG(info) << "[AndroidAutoEntity] start."; - eventHandler_ = eventHandler; cryptor_->init(); serviceList_ = serviceFactory_.create(messenger_); std::for_each(serviceList_.begin(), serviceList_.end(), std::bind(&IService::start, std::placeholders::_1)); + this->ping(); - controlServiceChannel_->receive(this->shared_from_this()); auto versionRequestPromise = aasdk::channel::SendPromise::defer(strand_); versionRequestPromise->then([]() {}, std::bind(&AndroidAutoEntity::onChannelError, this->shared_from_this(), std::placeholders::_1)); controlServiceChannel_->sendVersionRequest(std::move(versionRequestPromise)); + eventHandler_ = eventHandler; + controlServiceChannel_->receive(this->shared_from_this()); }); } @@ -79,12 +80,12 @@ void AndroidAutoEntity::stop() strand_.dispatch([this, self = this->shared_from_this()]() { OPENAUTO_LOG(info) << "[AndroidAutoEntity] stop."; + eventHandler_ = nullptr; pinger_->cancel(); std::for_each(serviceList_.begin(), serviceList_.end(), std::bind(&IService::stop, std::placeholders::_1)); messenger_->stop(); cryptor_->deinit(); transport_->stop(); - eventHandler_ = nullptr; }); } @@ -145,7 +146,6 @@ void AndroidAutoEntity::onHandshake(const aasdk::common::DataConstBuffer& payloa auto authCompletePromise = aasdk::channel::SendPromise::defer(strand_); authCompletePromise->then([]() {}, std::bind(&AndroidAutoEntity::onChannelError, this->shared_from_this(), std::placeholders::_1)); controlServiceChannel_->sendAuthComplete(authCompleteIndication, std::move(authCompletePromise)); - this->ping(); } controlServiceChannel_->receive(this->shared_from_this()); @@ -212,7 +212,6 @@ void AndroidAutoEntity::onShutdownRequest(const aasdk::proto::messages::Shutdown std::bind(&AndroidAutoEntity::onChannelError, this->shared_from_this(), std::placeholders::_1)); controlServiceChannel_->sendShutdownResponse(response, std::move(promise)); - controlServiceChannel_->receive(this->shared_from_this()); } void AndroidAutoEntity::onShutdownResponse(const aasdk::proto::messages::ShutdownResponse&) @@ -265,9 +264,13 @@ void AndroidAutoEntity::ping() controlServiceChannel_->sendPingRequest(request, std::move(promise)); this->ping(); }, - [this, self = this->shared_from_this()]() { - OPENAUTO_LOG(error) << "[AndroidAutoEntity] ping timer exceeded."; - this->triggerQuit(); + [this, self = this->shared_from_this()](auto error) { + if(error != aasdk::error::ErrorCode::OPERATION_ABORTED && + error != aasdk::error::ErrorCode::OPERATION_IN_PROGRESS) + { + OPENAUTO_LOG(error) << "[AndroidAutoEntity] ping timer exceeded."; + this->triggerQuit(); + } }); pinger_->ping(std::move(promise)); diff --git a/src/autoapp/Projection/Pinger.cpp b/src/autoapp/Projection/Pinger.cpp index 7dd5284..8be0cde 100644 --- a/src/autoapp/Projection/Pinger.cpp +++ b/src/autoapp/Projection/Pinger.cpp @@ -31,6 +31,7 @@ Pinger::Pinger(boost::asio::io_service& ioService, time_t duration) : strand_(ioService) , timer_(ioService) , duration_(duration) + , cancelled_(false) , pingsCount_(0) , pongsCount_(0) { @@ -40,11 +41,20 @@ Pinger::Pinger(boost::asio::io_service& ioService, time_t duration) void Pinger::ping(Promise::Pointer promise) { strand_.dispatch([this, self = this->shared_from_this(), promise = std::move(promise)]() mutable { - ++pingsCount_; + cancelled_ = false; - promise_ = std::move(promise); - timer_.expires_from_now(boost::posix_time::milliseconds(duration_)); - timer_.async_wait(strand_.wrap(std::bind(&Pinger::onTimerExceeded, this->shared_from_this(), std::placeholders::_1))); + if(promise_ != nullptr) + { + promise_->reject(aasdk::error::Error(aasdk::error::ErrorCode::OPERATION_IN_PROGRESS)); + } + else + { + ++pingsCount_; + + promise_ = std::move(promise); + timer_.expires_from_now(boost::posix_time::milliseconds(duration_)); + timer_.async_wait(strand_.wrap(std::bind(&Pinger::onTimerExceeded, this->shared_from_this(), std::placeholders::_1))); + } }); } @@ -57,25 +67,30 @@ void Pinger::pong() void Pinger::onTimerExceeded(const boost::system::error_code& error) { - if(!error && promise_ != nullptr) + if(promise_ == nullptr) { - if(std::abs(pingsCount_ - pongsCount_) > 1) - { - promise_->reject(); - } - else - { - promise_->resolve(); - } - - promise_.reset(); + return; } + else if(error == boost::asio::error::operation_aborted || cancelled_) + { + promise_->reject(aasdk::error::Error(aasdk::error::ErrorCode::OPERATION_ABORTED)); + } + else if(pingsCount_ - pongsCount_ > 1) + { + promise_->reject(aasdk::error::Error()); + } + else + { + promise_->resolve(); + } + + promise_.reset(); } void Pinger::cancel() { strand_.dispatch([this, self = this->shared_from_this()]() { - promise_.reset(); + cancelled_ = true; timer_.cancel(); }); }