summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorAndrii Kalinich <AKalinich@luxoft.com>2019-09-13 15:45:06 -0400
committerAndriy Byzhynar <abyzhynar@luxoft.com>2019-09-24 14:35:57 +0300
commit8c71bbb3e6cf683e03b84ce5d084d2c254549fff (patch)
tree9b11b3eb5102f9e9c87897e288f588017012dae1
parent6b43b00cdcafb5bc386a9fac603b596b882b4c39 (diff)
downloadsdl_core-fix/fix_sdl_low_voltage_behavior.tar.gz
Fix SDL behavior during LOW_VOLTAGEfix/fix_sdl_low_voltage_behavior
There were found a several problems during SDL testing with ATF scripts: 1. SDL does not ignore messages from mobile/HMI during low voltage and processes them on wake up 2. Sometimes SDL ignores messages on wake up due to timings 3. SDL low voltage process is not stopping properly by exit() function 4. SDL does not send OnAppUnregistered after wake up to HMI To solve mentioned problems, the following changes were done: 1. exit() was replaced with _Exit() which allow to force close the process 2. Suspend transport events processing threads during low voltage, such as unexpected disconnect etc. These events should be processed when SDL wakes up completely. 3. Suspend all client listening threads and shut down sockets for a TCP connections to prevent any possibility to receive message during low voltage. These threads will be resumed on wake up. 4. Set low_voltage flag to false in the end of wakeup() function to prevent any timing issues. 5. Don't add pending requests/notifications into request controller if low voltage event has happened, as it may happen at any moment 6. Don't handle received pending messages from mobile/HMI in RPC handler if low voltage event has happened as it may happen at any moment 7. Updated logic of few test case scenarios. Updated unit tests according to code changes
-rw-r--r--src/appMain/life_cycle_impl.cc17
-rw-r--r--src/components/application_manager/src/application_manager_impl.cc2
-rw-r--r--src/components/application_manager/src/request_controller.cc18
-rw-r--r--src/components/application_manager/src/rpc_handler_impl.cc14
-rw-r--r--src/components/connection_handler/src/connection_handler_impl.cc3
-rw-r--r--src/components/connection_handler/test/connection_handler_impl_test.cc4
-rw-r--r--src/components/include/test/transport_manager/mock_transport_manager.h7
-rw-r--r--src/components/include/test/transport_manager/transport_adapter/mock_transport_adapter.h9
-rw-r--r--src/components/include/transport_manager/common.h11
-rw-r--r--src/components/include/transport_manager/transport_adapter/transport_adapter.h22
-rw-r--r--src/components/include/transport_manager/transport_manager.h27
-rw-r--r--src/components/transport_manager/include/transport_manager/tcp/tcp_client_listener.h4
-rw-r--r--src/components/transport_manager/include/transport_manager/transport_adapter/client_connection_listener.h12
-rw-r--r--src/components/transport_manager/include/transport_manager/transport_adapter/transport_adapter_impl.h15
-rw-r--r--src/components/transport_manager/include/transport_manager/transport_manager_impl.h20
-rw-r--r--src/components/transport_manager/src/tcp/platform_specific/linux/platform_specific_network_interface_listener.cc4
-rw-r--r--src/components/transport_manager/src/tcp/tcp_client_listener.cc54
-rw-r--r--src/components/transport_manager/src/transport_adapter/transport_adapter_impl.cc59
-rw-r--r--src/components/transport_manager/src/transport_manager_impl.cc65
-rw-r--r--src/components/transport_manager/test/include/transport_manager/transport_adapter/mock_client_connection_listener.h6
-rw-r--r--src/components/transport_manager/test/transport_adapter_test.cc9
-rw-r--r--src/components/transport_manager/test/transport_manager_default_test.cc13
-rw-r--r--src/components/transport_manager/test/transport_manager_impl_test.cc44
-rw-r--r--src/components/utils/src/signals_posix.cc2
24 files changed, 323 insertions, 118 deletions
diff --git a/src/appMain/life_cycle_impl.cc b/src/appMain/life_cycle_impl.cc
index c903fb1a8a..146380f953 100644
--- a/src/appMain/life_cycle_impl.cc
+++ b/src/appMain/life_cycle_impl.cc
@@ -175,7 +175,8 @@ bool LifeCycleImpl::StartComponents() {
return false;
}
// start transport manager
- transport_manager_->Visibility(true);
+ transport_manager_->PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOn);
LowVoltageSignalsOffset signals_offset{profile_.low_voltage_signal_offset(),
profile_.wake_up_signal_offset(),
@@ -189,7 +190,10 @@ bool LifeCycleImpl::StartComponents() {
void LifeCycleImpl::LowVoltage() {
LOG4CXX_AUTO_TRACE(logger_);
- transport_manager_->Visibility(false);
+ transport_manager_->PerformActionOnClients(
+ transport_manager::TransportAction::kListeningOff);
+ transport_manager_->StopEventsProcessing();
+ transport_manager_->Deinit();
app_manager_->OnLowVoltage();
}
@@ -200,9 +204,11 @@ void LifeCycleImpl::IgnitionOff() {
void LifeCycleImpl::WakeUp() {
LOG4CXX_AUTO_TRACE(logger_);
- app_manager_->OnWakeUp();
transport_manager_->Reinit();
- transport_manager_->Visibility(true);
+ transport_manager_->PerformActionOnClients(
+ transport_manager::TransportAction::kListeningOn);
+ app_manager_->OnWakeUp();
+ transport_manager_->StartEventsProcessing();
}
#ifdef MESSAGEBROKER_HMIADAPTER
@@ -293,7 +299,8 @@ void LifeCycleImpl::StopComponents() {
LOG4CXX_INFO(logger_, "Destroying Transport Manager.");
DCHECK_OR_RETURN_VOID(transport_manager_);
- transport_manager_->Visibility(false);
+ transport_manager_->PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOff);
transport_manager_->Stop();
delete transport_manager_;
transport_manager_ = NULL;
diff --git a/src/components/application_manager/src/application_manager_impl.cc b/src/components/application_manager/src/application_manager_impl.cc
index 46ccb86e8b..652a939e21 100644
--- a/src/components/application_manager/src/application_manager_impl.cc
+++ b/src/components/application_manager/src/application_manager_impl.cc
@@ -3185,10 +3185,10 @@ bool ApplicationManagerImpl::IsLowVoltage() const {
void ApplicationManagerImpl::OnWakeUp() {
LOG4CXX_AUTO_TRACE(logger_);
- is_low_voltage_ = false;
resume_ctrl_->SaveWakeUpTime();
resume_ctrl_->StartSavePersistentDataTimer();
request_ctrl_.OnWakeUp();
+ is_low_voltage_ = false;
}
std::string ApplicationManagerImpl::GetHashedAppID(
diff --git a/src/components/application_manager/src/request_controller.cc b/src/components/application_manager/src/request_controller.cc
index 93c45ed5dc..883db0b4ac 100644
--- a/src/components/application_manager/src/request_controller.cc
+++ b/src/components/application_manager/src/request_controller.cc
@@ -126,6 +126,12 @@ RequestController::TResult RequestController::CheckPosibilitytoAdd(
return RequestController::TOO_MANY_REQUESTS;
}
+ if (IsLowVoltage()) {
+ LOG4CXX_ERROR(logger_,
+ "Impossible to add request due to Low Voltage is active");
+ return RequestController::INVALID_DATA;
+ }
+
return SUCCESS;
}
@@ -192,6 +198,13 @@ RequestController::TResult RequestController::addHMIRequest(
"Default timeout was set to 0."
"RequestController will not track timeout of this request.");
}
+
+ if (IsLowVoltage()) {
+ LOG4CXX_ERROR(logger_,
+ "Impossible to add request due to Low Voltage is active");
+ return RequestController::INVALID_DATA;
+ }
+
waiting_for_response_.Add(request_info_ptr);
LOG4CXX_DEBUG(logger_,
"Waiting for response count:" << waiting_for_response_.Size());
@@ -202,6 +215,11 @@ RequestController::TResult RequestController::addHMIRequest(
void RequestController::addNotification(const RequestPtr ptr) {
LOG4CXX_AUTO_TRACE(logger_);
+ if (IsLowVoltage()) {
+ LOG4CXX_ERROR(
+ logger_, "Impossible to add notification due to Low Voltage is active");
+ return;
+ }
notification_list_.push_back(ptr);
}
diff --git a/src/components/application_manager/src/rpc_handler_impl.cc b/src/components/application_manager/src/rpc_handler_impl.cc
index d1ca05e9a1..695d94628d 100644
--- a/src/components/application_manager/src/rpc_handler_impl.cc
+++ b/src/components/application_manager/src/rpc_handler_impl.cc
@@ -208,6 +208,10 @@ void RPCHandlerImpl::Handle(const impl::MessageFromMobile message) {
LOG4CXX_INFO(logger_, "Application manager is stopping");
return;
}
+ if (app_manager_.IsLowVoltage()) {
+ LOG4CXX_ERROR(logger_, "Low Voltage is active.");
+ return;
+ }
ProcessMessageFromMobile(message);
}
@@ -219,6 +223,11 @@ void RPCHandlerImpl::Handle(const impl::MessageFromHmi message) {
LOG4CXX_ERROR(logger_, "Null-pointer message received.");
return;
}
+ if (app_manager_.IsLowVoltage()) {
+ LOG4CXX_ERROR(logger_, "Low Voltage is active.");
+ return;
+ }
+
ProcessMessageFromHMI(message);
}
@@ -226,6 +235,11 @@ void RPCHandlerImpl::OnMessageReceived(
const protocol_handler::RawMessagePtr message) {
LOG4CXX_AUTO_TRACE(logger_);
+ if (app_manager_.IsLowVoltage()) {
+ LOG4CXX_ERROR(logger_, "Low Voltage is active.");
+ return;
+ }
+
if (!message) {
LOG4CXX_ERROR(logger_, "Null-pointer message received.");
NOTREACHED();
diff --git a/src/components/connection_handler/src/connection_handler_impl.cc b/src/components/connection_handler/src/connection_handler_impl.cc
index 84609d47b8..d6c15c8e82 100644
--- a/src/components/connection_handler/src/connection_handler_impl.cc
+++ b/src/components/connection_handler/src/connection_handler_impl.cc
@@ -1368,7 +1368,8 @@ void ConnectionHandlerImpl::RemoveCloudAppDevice(const DeviceHandle device_id) {
void ConnectionHandlerImpl::StartTransportManager() {
LOG4CXX_AUTO_TRACE(logger_);
- transport_manager_.Visibility(true);
+ transport_manager_.PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOn);
}
void ConnectionHandlerImpl::CloseRevokedConnection(uint32_t connection_key) {
diff --git a/src/components/connection_handler/test/connection_handler_impl_test.cc b/src/components/connection_handler/test/connection_handler_impl_test.cc
index af7009c2f5..855225c460 100644
--- a/src/components/connection_handler/test/connection_handler_impl_test.cc
+++ b/src/components/connection_handler/test/connection_handler_impl_test.cc
@@ -787,7 +787,9 @@ TEST_F(ConnectionHandlerTest, StartTransportManager) {
AddTestDeviceConnection();
AddTestSession();
- EXPECT_CALL(mock_transport_manager_, Visibility(true));
+ EXPECT_CALL(mock_transport_manager_,
+ PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOn));
connection_handler_->StartTransportManager();
}
diff --git a/src/components/include/test/transport_manager/mock_transport_manager.h b/src/components/include/test/transport_manager/mock_transport_manager.h
index 395beeff7b..884bde50bf 100644
--- a/src/components/include/test/transport_manager/mock_transport_manager.h
+++ b/src/components/include/test/transport_manager/mock_transport_manager.h
@@ -58,6 +58,9 @@ class MockTransportManager : public ::transport_manager::TransportManager,
public:
MOCK_METHOD1(Init, int(resumption::LastState& last_state));
MOCK_METHOD0(Reinit, int());
+ MOCK_METHOD0(Deinit, void());
+ MOCK_METHOD0(StopEventsProcessing, void());
+ MOCK_METHOD0(StartEventsProcessing, void());
MOCK_METHOD0(SearchDevices, int());
MOCK_METHOD1(
AddCloudDevice,
@@ -78,7 +81,9 @@ class MockTransportManager : public ::transport_manager::TransportManager,
MOCK_METHOD1(AddEventListener, int(TransportManagerListener* listener));
MOCK_METHOD0(Stop, int());
MOCK_METHOD1(RemoveDevice, int(const DeviceHandle));
- MOCK_CONST_METHOD1(Visibility, int(const bool&));
+ MOCK_CONST_METHOD1(PerformActionOnClients,
+ int(transport_manager::TransportAction required_action));
+
MOCK_METHOD1(SetTelemetryObserver,
void(transport_manager::TMTelemetryObserver* observer));
};
diff --git a/src/components/include/test/transport_manager/transport_adapter/mock_transport_adapter.h b/src/components/include/test/transport_manager/transport_adapter/mock_transport_adapter.h
index 3ac6331f71..0c0e2dd5ec 100644
--- a/src/components/include/test/transport_manager/transport_adapter/mock_transport_adapter.h
+++ b/src/components/include/test/transport_manager/transport_adapter/mock_transport_adapter.h
@@ -72,12 +72,9 @@ class MockTransportAdapter
const ::transport_manager::DeviceUID& device_handle));
MOCK_METHOD2(RunAppOnDevice, void(const std::string&, const std::string&));
MOCK_CONST_METHOD0(IsClientOriginatedConnectSupported, bool());
- MOCK_METHOD0(
- StartClientListening,
- ::transport_manager::transport_adapter::TransportAdapter::Error());
- MOCK_METHOD0(
- StopClientListening,
- ::transport_manager::transport_adapter::TransportAdapter::Error());
+ MOCK_METHOD1(ChangeClientListening,
+ ::transport_manager::transport_adapter::TransportAdapter::Error(
+ ::transport_manager::TransportAction required_change));
MOCK_METHOD2(RemoveFinalizedConnection,
void(const ::transport_manager::DeviceUID& device_handle,
const ::transport_manager::ApplicationHandle& app_handle));
diff --git a/src/components/include/transport_manager/common.h b/src/components/include/transport_manager/common.h
index 300ce26d0b..08f52ae1d0 100644
--- a/src/components/include/transport_manager/common.h
+++ b/src/components/include/transport_manager/common.h
@@ -43,6 +43,17 @@
namespace transport_manager {
/**
+ * @enum Actions that could
+ * be performed on connected clients.
+ */
+enum class TransportAction {
+ kVisibilityOn,
+ kVisibilityOff,
+ kListeningOn,
+ kListeningOff
+};
+
+/**
* @enum Transport manager states.
*/
enum {
diff --git a/src/components/include/transport_manager/transport_adapter/transport_adapter.h b/src/components/include/transport_manager/transport_adapter/transport_adapter.h
index 1d21ff4ae4..b92e010ece 100644
--- a/src/components/include/transport_manager/transport_adapter/transport_adapter.h
+++ b/src/components/include/transport_manager/transport_adapter/transport_adapter.h
@@ -111,7 +111,15 @@ class TransportAdapter {
/**
* @enum Available types of errors.
*/
- enum Error { OK, FAIL, NOT_SUPPORTED, ALREADY_EXISTS, BAD_STATE, BAD_PARAM };
+ enum Error {
+ UNKNOWN = -1,
+ OK,
+ FAIL,
+ NOT_SUPPORTED,
+ ALREADY_EXISTS,
+ BAD_STATE,
+ BAD_PARAM
+ };
public:
/**
@@ -236,18 +244,10 @@ class TransportAdapter {
virtual bool IsClientOriginatedConnectSupported() const = 0;
/**
- * @brief Start client listener.
- *
- * @return Error information about possible reason of failure.
- */
- virtual Error StartClientListening() = 0;
-
- /**
- * @brief Stop client listener.
- *
+ * @brief Changes client listening state of current adapter
* @return Error information about possible reason of failure.
*/
- virtual Error StopClientListening() = 0;
+ virtual Error ChangeClientListening(TransportAction required_change) = 0;
/**
* @brief Remove marked as FINALISING connection from accounting.
diff --git a/src/components/include/transport_manager/transport_manager.h b/src/components/include/transport_manager/transport_manager.h
index 275608c315..ce92bfd9cb 100644
--- a/src/components/include/transport_manager/transport_manager.h
+++ b/src/components/include/transport_manager/transport_manager.h
@@ -69,6 +69,21 @@ class TransportManager {
virtual int Reinit() = 0;
/**
+ * @brief Deinitializes all transport adapters and device instances
+ */
+ virtual void Deinit() = 0;
+
+ /**
+ * @brief Stops transport events processing handler threads
+ */
+ virtual void StopEventsProcessing() = 0;
+
+ /**
+ * @brief Resumes transport events processing handler threads
+ */
+ virtual void StartEventsProcessing() = 0;
+
+ /**
* @brief Start scanning for new devices.
*
* @return Code error.
@@ -193,13 +208,13 @@ class TransportManager {
virtual int RemoveDevice(const DeviceHandle device_handle) = 0;
/**
- * @brief Turns on or off visibility of SDL to mobile devices
- * when visibility is ON (on_off = true) mobile devices are able to connect
- * otherwise ((on_off = false)) SDL is not visible from outside
- *
- * @return Code error.
+ * @brief Performs specified action on connected clients
+ * @param required_action is the action which should be performed for the
+ * connected clients
+ * @return error code
*/
- virtual int Visibility(const bool& on_off) const = 0;
+ virtual int PerformActionOnClients(
+ const TransportAction required_action) const = 0;
};
} // namespace transport_manager
#endif // SRC_COMPONENTS_INCLUDE_TRANSPORT_MANAGER_TRANSPORT_MANAGER_H_
diff --git a/src/components/transport_manager/include/transport_manager/tcp/tcp_client_listener.h b/src/components/transport_manager/include/transport_manager/tcp/tcp_client_listener.h
index 28784fe3c7..f033d35bf7 100644
--- a/src/components/transport_manager/include/transport_manager/tcp/tcp_client_listener.h
+++ b/src/components/transport_manager/include/transport_manager/tcp/tcp_client_listener.h
@@ -108,6 +108,10 @@ class TcpClientListener : public ClientConnectionListener {
*/
virtual TransportAdapter::Error StopListening();
+ TransportAdapter::Error SuspendListening() OVERRIDE;
+
+ TransportAdapter::Error ResumeListening() OVERRIDE;
+
/**
* @brief Called from NetworkInterfaceListener when IP address of the network
* interface is changed.
diff --git a/src/components/transport_manager/include/transport_manager/transport_adapter/client_connection_listener.h b/src/components/transport_manager/include/transport_manager/transport_adapter/client_connection_listener.h
index f905e11c43..e49a355e53 100644
--- a/src/components/transport_manager/include/transport_manager/transport_adapter/client_connection_listener.h
+++ b/src/components/transport_manager/include/transport_manager/transport_adapter/client_connection_listener.h
@@ -76,6 +76,18 @@ class ClientConnectionListener {
virtual TransportAdapter::Error StopListening() = 0;
/**
+ * @brief Suspends current listening thread
+ * @return Error information about possible reason of failure.
+ */
+ virtual TransportAdapter::Error SuspendListening() = 0;
+
+ /**
+ * @brief Resumes current listening thread
+ * @return Error information about possible reason of failure.
+ */
+ virtual TransportAdapter::Error ResumeListening() = 0;
+
+ /**
* @brief Destructor.
*/
virtual ~ClientConnectionListener() {}
diff --git a/src/components/transport_manager/include/transport_manager/transport_adapter/transport_adapter_impl.h b/src/components/transport_manager/include/transport_manager/transport_adapter/transport_adapter_impl.h
index 84b80e956f..0750b58aae 100644
--- a/src/components/transport_manager/include/transport_manager/transport_adapter/transport_adapter_impl.h
+++ b/src/components/transport_manager/include/transport_manager/transport_adapter/transport_adapter_impl.h
@@ -202,19 +202,8 @@ class TransportAdapterImpl : public TransportAdapter,
const ApplicationHandle& app_handle,
const ::protocol_handler::RawMessagePtr data) OVERRIDE;
- /**
- * @brief Start client listener.
- *
- * @return Error information about possible reason of failure.
- */
- TransportAdapter::Error StartClientListening() OVERRIDE;
-
- /**
- * @brief Stop client listener.
- *
- * @return Error information about possible reason of failure.
- */
- TransportAdapter::Error StopClientListening() OVERRIDE;
+ TransportAdapter::Error ChangeClientListening(
+ TransportAction required_change) OVERRIDE;
/**
* @brief Notify that device scanner is available.
diff --git a/src/components/transport_manager/include/transport_manager/transport_manager_impl.h b/src/components/transport_manager/include/transport_manager/transport_manager_impl.h
index d576db7500..5e97a5567e 100644
--- a/src/components/transport_manager/include/transport_manager/transport_manager_impl.h
+++ b/src/components/transport_manager/include/transport_manager/transport_manager_impl.h
@@ -132,6 +132,12 @@ class TransportManagerImpl
*/
virtual int Reinit() OVERRIDE;
+ virtual void Deinit() OVERRIDE;
+
+ void StopEventsProcessing() OVERRIDE;
+
+ void StartEventsProcessing() OVERRIDE;
+
/**
* @brief Start scanning for new devices.
*
@@ -250,14 +256,8 @@ class TransportManagerImpl
**/
int RemoveDevice(const DeviceHandle device) OVERRIDE;
- /**
- * @brief Turns on or off visibility of SDL to mobile devices
- * when visibility is ON (on_off = true) mobile devices are able to connect
- * otherwise ((on_off = false)) SDL is not visible from outside
- *
- * @return Code error.
- */
- int Visibility(const bool& on_off) const OVERRIDE;
+ int PerformActionOnClients(
+ const TransportAction required_action) const OVERRIDE;
/**
* @brief OnDeviceListUpdated updates device list and sends appropriate
@@ -414,6 +414,10 @@ class TransportManagerImpl
sync_primitives::Lock device_lock_;
DeviceUID device_to_reconnect_;
+ std::atomic_bool events_processing_is_active_;
+ sync_primitives::Lock events_processing_lock_;
+ sync_primitives::ConditionalVariable events_processing_cond_var_;
+
/**
* @brief Adds new incoming connection to connections list
* @param c New connection
diff --git a/src/components/transport_manager/src/tcp/platform_specific/linux/platform_specific_network_interface_listener.cc b/src/components/transport_manager/src/tcp/platform_specific/linux/platform_specific_network_interface_listener.cc
index e0bda61e4d..2e79e84f2e 100644
--- a/src/components/transport_manager/src/tcp/platform_specific/linux/platform_specific_network_interface_listener.cc
+++ b/src/components/transport_manager/src/tcp/platform_specific/linux/platform_specific_network_interface_listener.cc
@@ -105,7 +105,7 @@ PlatformSpecificNetworkInterfaceListener::
bool PlatformSpecificNetworkInterfaceListener::Init() {
LOG4CXX_AUTO_TRACE(logger_);
-
+ LOG4CXX_DEBUG(logger_, "Init socket: " << socket_);
if (socket_ >= 0) {
LOG4CXX_WARN(logger_, "Network interface listener is already initialized");
return false;
@@ -151,7 +151,7 @@ bool PlatformSpecificNetworkInterfaceListener::Init() {
void PlatformSpecificNetworkInterfaceListener::Deinit() {
LOG4CXX_AUTO_TRACE(logger_);
-
+ LOG4CXX_DEBUG(logger_, "Deinit socket: " << socket_);
if (socket_ >= 0) {
close(socket_);
socket_ = -1;
diff --git a/src/components/transport_manager/src/tcp/tcp_client_listener.cc b/src/components/transport_manager/src/tcp/tcp_client_listener.cc
index 66be810a9b..d29ffeb144 100644
--- a/src/components/transport_manager/src/tcp/tcp_client_listener.cc
+++ b/src/components/transport_manager/src/tcp/tcp_client_listener.cc
@@ -374,17 +374,16 @@ TransportAdapter::Error TcpClientListener::StartListening() {
return TransportAdapter::OK;
}
-void TcpClientListener::ListeningThreadDelegate::exitThreadMain() {
- parent_->StopLoop();
-}
+TransportAdapter::Error TcpClientListener::ResumeListening() {
+ LOG4CXX_AUTO_TRACE(logger_);
-void TcpClientListener::ListeningThreadDelegate::threadMain() {
- parent_->Loop();
-}
+ interface_listener_->Init();
+ StartListeningThread();
+ started_ = true;
-TcpClientListener::ListeningThreadDelegate::ListeningThreadDelegate(
- TcpClientListener* parent)
- : parent_(parent) {}
+ LOG4CXX_INFO(logger_, "Tcp client listener was resumed successfully");
+ return TransportAdapter::OK;
+}
TransportAdapter::Error TcpClientListener::StopListening() {
LOG4CXX_AUTO_TRACE(logger_);
@@ -398,10 +397,45 @@ TransportAdapter::Error TcpClientListener::StopListening() {
StopListeningThread();
started_ = false;
- LOG4CXX_INFO(logger_, "Tcp client listener has stopped successfully");
+ LOG4CXX_INFO(logger_, "Tcp client listener was stopped successfully");
+ return TransportAdapter::OK;
+}
+
+TransportAdapter::Error TcpClientListener::SuspendListening() {
+ LOG4CXX_AUTO_TRACE(logger_);
+ if (!started_) {
+ LOG4CXX_DEBUG(logger_, "TcpClientListener is not running now");
+ return TransportAdapter::BAD_STATE;
+ }
+
+ if (shutdown(socket_, SHUT_RDWR) != 0) {
+ LOG4CXX_WARN(logger_, "Socket was unable to be shutdowned");
+ }
+
+ if (close(socket_) != 0) {
+ LOG4CXX_ERROR_WITH_ERRNO(logger_, "Failed to close socket");
+ }
+
+ interface_listener_->Deinit();
+ StopListeningThread();
+ started_ = false;
+
+ LOG4CXX_INFO(logger_, "Tcp client listener was suspended");
return TransportAdapter::OK;
}
+void TcpClientListener::ListeningThreadDelegate::exitThreadMain() {
+ parent_->StopLoop();
+}
+
+void TcpClientListener::ListeningThreadDelegate::threadMain() {
+ parent_->Loop();
+}
+
+TcpClientListener::ListeningThreadDelegate::ListeningThreadDelegate(
+ TcpClientListener* parent)
+ : parent_(parent) {}
+
TransportAdapter::Error TcpClientListener::StartListeningThread() {
LOG4CXX_AUTO_TRACE(logger_);
diff --git a/src/components/transport_manager/src/transport_adapter/transport_adapter_impl.cc b/src/components/transport_manager/src/transport_adapter/transport_adapter_impl.cc
index fc43cfc63e..f0bfabf2e4 100644
--- a/src/components/transport_manager/src/transport_adapter/transport_adapter_impl.cc
+++ b/src/components/transport_manager/src/transport_adapter/transport_adapter_impl.cc
@@ -418,8 +418,9 @@ TransportAdapter::Error TransportAdapterImpl::SendData(
}
}
-TransportAdapter::Error TransportAdapterImpl::StartClientListening() {
- LOG4CXX_TRACE(logger_, "enter");
+TransportAdapter::Error TransportAdapterImpl::ChangeClientListening(
+ TransportAction required_change) {
+ LOG4CXX_AUTO_TRACE(logger_);
if (client_connection_listener_ == 0) {
LOG4CXX_TRACE(logger_, "exit with NOT_SUPPORTED");
return NOT_SUPPORTED;
@@ -428,27 +429,43 @@ TransportAdapter::Error TransportAdapterImpl::StartClientListening() {
LOG4CXX_TRACE(logger_, "exit with BAD_STATE");
return BAD_STATE;
}
- TransportAdapter::Error err = client_connection_listener_->StartListening();
- LOG4CXX_TRACE(logger_, "exit with error: " << err);
- return err;
-}
-TransportAdapter::Error TransportAdapterImpl::StopClientListening() {
- LOG4CXX_TRACE(logger_, "enter");
- if (client_connection_listener_ == 0) {
- LOG4CXX_TRACE(logger_, "exit with NOT_SUPPORTED");
- return NOT_SUPPORTED;
- }
- if (!client_connection_listener_->IsInitialised()) {
- LOG4CXX_TRACE(logger_, "exit with BAD_STATE");
- return BAD_STATE;
- }
- TransportAdapter::Error err = client_connection_listener_->StopListening();
- sync_primitives::AutoLock locker(devices_mutex_);
- for (DeviceMap::iterator it = devices_.begin(); it != devices_.end(); ++it) {
- it->second->Stop();
+ TransportAdapter::Error err = TransportAdapter::Error::UNKNOWN;
+
+ switch (required_change) {
+ case transport_manager::TransportAction::kVisibilityOn:
+ err = client_connection_listener_->StartListening();
+ break;
+
+ case transport_manager::TransportAction::kListeningOn:
+ err = client_connection_listener_->ResumeListening();
+ break;
+
+ case transport_manager::TransportAction::kListeningOff:
+ err = client_connection_listener_->SuspendListening();
+ {
+ sync_primitives::AutoLock locker(devices_mutex_);
+ for (DeviceMap::iterator it = devices_.begin(); it != devices_.end();
+ ++it) {
+ it->second->Stop();
+ }
+ }
+ break;
+
+ case transport_manager::TransportAction::kVisibilityOff:
+ err = client_connection_listener_->StopListening();
+ {
+ sync_primitives::AutoLock locker(devices_mutex_);
+ for (DeviceMap::iterator it = devices_.begin(); it != devices_.end();
+ ++it) {
+ it->second->Stop();
+ }
+ }
+ break;
+ default:
+ NOTREACHED();
}
- LOG4CXX_TRACE(logger_, "exit with error: " << err);
+ LOG4CXX_TRACE(logger_, "Exit with error: " << err);
return err;
}
diff --git a/src/components/transport_manager/src/transport_manager_impl.cc b/src/components/transport_manager/src/transport_manager_impl.cc
index a2bc95bfdd..07dd35bc2f 100644
--- a/src/components/transport_manager/src/transport_manager_impl.cc
+++ b/src/components/transport_manager/src/transport_manager_impl.cc
@@ -67,6 +67,7 @@ struct ConnectionFinder {
return id_ == connection.id;
}
};
+
} // namespace
namespace transport_manager {
@@ -100,7 +101,10 @@ TransportManagerImpl::TransportManagerImpl(
, device_switch_timer_(
"Device reconection timer",
new timer::TimerTaskImpl<TransportManagerImpl>(
- this, &TransportManagerImpl::ReconnectionTimeout)) {
+ this, &TransportManagerImpl::ReconnectionTimeout))
+ , events_processing_is_active_(true)
+ , events_processing_lock_()
+ , events_processing_cond_var_() {
LOG4CXX_TRACE(logger_, "TransportManager has created");
}
@@ -586,21 +590,36 @@ int TransportManagerImpl::Init(resumption::LastState& last_state) {
return E_SUCCESS;
}
-int TransportManagerImpl::Reinit() {
+void TransportManagerImpl::Deinit() {
LOG4CXX_AUTO_TRACE(logger_);
DisconnectAllDevices();
TerminateAllAdapters();
device_to_adapter_map_.clear();
connection_id_counter_ = 0;
+}
+
+int TransportManagerImpl::Reinit() {
int ret = InitAllAdapters();
return ret;
}
-int TransportManagerImpl::Visibility(const bool& on_off) const {
- LOG4CXX_TRACE(logger_, "enter. On_off: " << &on_off);
- TransportAdapter::Error ret;
+void TransportManagerImpl::StopEventsProcessing() {
+ LOG4CXX_AUTO_TRACE(logger_);
+ events_processing_is_active_ = false;
+}
- LOG4CXX_DEBUG(logger_, "Visibility change requested to " << on_off);
+void TransportManagerImpl::StartEventsProcessing() {
+ LOG4CXX_AUTO_TRACE(logger_);
+ events_processing_is_active_ = true;
+ events_processing_cond_var_.Broadcast();
+}
+
+int TransportManagerImpl::PerformActionOnClients(
+ const TransportAction required_action) const {
+ LOG4CXX_TRACE(logger_,
+ "The following action requested: "
+ << static_cast<int>(required_action)
+ << " to be performed on connected clients");
if (!is_initialized_) {
LOG4CXX_ERROR(logger_, "TM is not initialized");
LOG4CXX_TRACE(logger_,
@@ -609,21 +628,19 @@ int TransportManagerImpl::Visibility(const bool& on_off) const {
return E_TM_IS_NOT_INITIALIZED;
}
- for (std::vector<TransportAdapter*>::const_iterator it =
- transport_adapters_.begin();
- it != transport_adapters_.end();
- ++it) {
- if (on_off) {
- ret = (*it)->StartClientListening();
- } else {
- ret = (*it)->StopClientListening();
- }
+ TransportAdapter::Error ret = TransportAdapter::Error::UNKNOWN;
+
+ for (auto adapter_ptr : transport_adapters_) {
+ ret = adapter_ptr->ChangeClientListening(required_action);
+
if (TransportAdapter::Error::NOT_SUPPORTED == ret) {
LOG4CXX_DEBUG(logger_,
- "Visibility change is not supported for adapter "
- << *it << "[" << (*it)->GetDeviceType() << "]");
+ "Requested action on client is not supported for adapter "
+ << adapter_ptr << "[" << adapter_ptr->GetDeviceType()
+ << "]");
}
}
+
LOG4CXX_TRACE(logger_, "exit with E_SUCCESS");
return E_SUCCESS;
}
@@ -987,6 +1004,13 @@ void TransportManagerImpl::OnDeviceListUpdated(TransportAdapter* ta) {
void TransportManagerImpl::Handle(TransportAdapterEvent event) {
LOG4CXX_TRACE(logger_, "enter");
+
+ if (!events_processing_is_active_) {
+ LOG4CXX_DEBUG(logger_, "Waiting for events handling unlock");
+ sync_primitives::AutoLock auto_lock(events_processing_lock_);
+ events_processing_cond_var_.Wait(auto_lock);
+ }
+
switch (event.event_type) {
case EventTypeEnum::ON_SEARCH_DONE: {
RaiseEvent(&TransportManagerListener::OnScanDevicesFinished);
@@ -1297,6 +1321,13 @@ void TransportManagerImpl::SetTelemetryObserver(TMTelemetryObserver* observer) {
void TransportManagerImpl::Handle(::protocol_handler::RawMessagePtr msg) {
LOG4CXX_TRACE(logger_, "enter");
+
+ if (!events_processing_is_active_) {
+ LOG4CXX_DEBUG(logger_, "Waiting for events handling unlock");
+ sync_primitives::AutoLock auto_lock(events_processing_lock_);
+ events_processing_cond_var_.Wait(auto_lock);
+ }
+
sync_primitives::AutoReadLock lock(connections_lock_);
ConnectionInternal* connection = GetConnection(msg->connection_key());
if (connection == NULL) {
diff --git a/src/components/transport_manager/test/include/transport_manager/transport_adapter/mock_client_connection_listener.h b/src/components/transport_manager/test/include/transport_manager/transport_adapter/mock_client_connection_listener.h
index 0f6f1e9f14..6d451294de 100644
--- a/src/components/transport_manager/test/include/transport_manager/transport_adapter/mock_client_connection_listener.h
+++ b/src/components/transport_manager/test/include/transport_manager/transport_adapter/mock_client_connection_listener.h
@@ -51,6 +51,12 @@ class MockClientConnectionListener
StartListening,
::transport_manager::transport_adapter::TransportAdapter::Error());
MOCK_METHOD0(
+ SuspendListening,
+ ::transport_manager::transport_adapter::TransportAdapter::Error());
+ MOCK_METHOD0(
+ ResumeListening,
+ ::transport_manager::transport_adapter::TransportAdapter::Error());
+ MOCK_METHOD0(
StopListening,
::transport_manager::transport_adapter::TransportAdapter::Error());
};
diff --git a/src/components/transport_manager/test/transport_adapter_test.cc b/src/components/transport_manager/test/transport_adapter_test.cc
index aa41c0bc6d..712cc5f750 100644
--- a/src/components/transport_manager/test/transport_adapter_test.cc
+++ b/src/components/transport_manager/test/transport_adapter_test.cc
@@ -1035,7 +1035,8 @@ TEST_F(TransportAdapterTest, StartClientListening_ClientNotInitialized) {
EXPECT_CALL(*clientMock, IsInitialised()).WillOnce(Return(false));
EXPECT_CALL(*clientMock, StartListening()).Times(0);
- TransportAdapter::Error res = transport_adapter.StartClientListening();
+ TransportAdapter::Error res = transport_adapter.ChangeClientListening(
+ transport_manager::TransportAction::kVisibilityOn);
EXPECT_EQ(TransportAdapter::BAD_STATE, res);
EXPECT_CALL(*dev_mock, Terminate());
@@ -1058,7 +1059,8 @@ TEST_F(TransportAdapterTest, StartClientListening) {
EXPECT_CALL(*clientMock, StartListening())
.WillOnce(Return(TransportAdapter::OK));
- TransportAdapter::Error res = transport_adapter.StartClientListening();
+ TransportAdapter::Error res = transport_adapter.ChangeClientListening(
+ transport_manager::TransportAction::kVisibilityOn);
EXPECT_EQ(TransportAdapter::OK, res);
EXPECT_CALL(*dev_mock, Terminate());
@@ -1092,7 +1094,8 @@ TEST_F(TransportAdapterTest, StopClientListening_Success) {
EXPECT_CALL(*clientMock, StopListening())
.WillOnce(Return(TransportAdapter::OK));
- res = transport_adapter.StopClientListening();
+ res = transport_adapter.ChangeClientListening(
+ transport_manager::TransportAction::kVisibilityOff);
EXPECT_EQ(TransportAdapter::OK, res);
EXPECT_CALL(*dev_mock, Terminate());
diff --git a/src/components/transport_manager/test/transport_manager_default_test.cc b/src/components/transport_manager/test/transport_manager_default_test.cc
index e102458b96..40938d0370 100644
--- a/src/components/transport_manager/test/transport_manager_default_test.cc
+++ b/src/components/transport_manager/test/transport_manager_default_test.cc
@@ -97,6 +97,19 @@ TEST(TestTransportManagerDefault, Init_LastStateNotUsed) {
EXPECT_CALL(transport_manager_settings, bluetooth_uuid())
.WillRepeatedly(Return(kBTUUID.data()));
+ std::string dummy_parameter;
+ EXPECT_CALL(transport_manager_settings, aoa_filter_manufacturer())
+ .WillRepeatedly(ReturnRef(dummy_parameter));
+ EXPECT_CALL(transport_manager_settings, aoa_filter_model_name())
+ .WillRepeatedly(ReturnRef(dummy_parameter));
+ EXPECT_CALL(transport_manager_settings, aoa_filter_description())
+ .WillRepeatedly(ReturnRef(dummy_parameter));
+ EXPECT_CALL(transport_manager_settings, aoa_filter_version())
+ .WillRepeatedly(ReturnRef(dummy_parameter));
+ EXPECT_CALL(transport_manager_settings, aoa_filter_uri())
+ .WillRepeatedly(ReturnRef(dummy_parameter));
+ EXPECT_CALL(transport_manager_settings, aoa_filter_serial_number())
+ .WillRepeatedly(ReturnRef(dummy_parameter));
transport_manager.Init(mock_last_state);
transport_manager.Stop();
}
diff --git a/src/components/transport_manager/test/transport_manager_impl_test.cc b/src/components/transport_manager/test/transport_manager_impl_test.cc
index 6411352ac9..ac9b801dbd 100644
--- a/src/components/transport_manager/test/transport_manager_impl_test.cc
+++ b/src/components/transport_manager/test/transport_manager_impl_test.cc
@@ -664,15 +664,23 @@ TEST_F(TransportManagerImplTest, RemoveDevice_DeviceWasAdded) {
}
TEST_F(TransportManagerImplTest, SetVisibilityOn_StartClientListening) {
- EXPECT_CALL(*mock_adapter_, StartClientListening())
+ EXPECT_CALL(
+ *mock_adapter_,
+ ChangeClientListening(transport_manager::TransportAction::kVisibilityOn))
.WillOnce(Return(TransportAdapter::OK));
- EXPECT_EQ(::transport_manager::E_SUCCESS, tm_.Visibility(true));
+ EXPECT_EQ(::transport_manager::E_SUCCESS,
+ tm_.PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOn));
}
TEST_F(TransportManagerImplTest, SetVisibilityOff_StopClientListening) {
- EXPECT_CALL(*mock_adapter_, StopClientListening())
+ EXPECT_CALL(
+ *mock_adapter_,
+ ChangeClientListening(transport_manager::TransportAction::kVisibilityOff))
.WillOnce(Return(TransportAdapter::OK));
- EXPECT_EQ(::transport_manager::E_SUCCESS, tm_.Visibility(false));
+ EXPECT_EQ(::transport_manager::E_SUCCESS,
+ tm_.PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOff));
}
TEST_F(TransportManagerImplTest, StopTransportManager) {
@@ -691,12 +699,14 @@ TEST_F(TransportManagerImplTest, StopTransportManager) {
TEST_F(TransportManagerImplTest, Reinit) {
EXPECT_CALL(*mock_adapter_, Terminate());
EXPECT_CALL(*mock_adapter_, Init()).WillOnce(Return(TransportAdapter::OK));
+ tm_.Deinit();
EXPECT_EQ(E_SUCCESS, tm_.Reinit());
}
TEST_F(TransportManagerImplTest, Reinit_InitAdapterFailed) {
EXPECT_CALL(*mock_adapter_, Terminate());
EXPECT_CALL(*mock_adapter_, Init()).WillOnce(Return(TransportAdapter::FAIL));
+ tm_.Deinit();
EXPECT_EQ(E_ADAPTERS_FAIL, tm_.Reinit());
}
@@ -940,12 +950,16 @@ TEST_F(TransportManagerImplTest, RemoveDevice_TMIsNotInitialized) {
TEST_F(TransportManagerImplTest, Visibility_TMIsNotInitialized) {
// Arrange
- const bool visible = true;
+ const transport_manager::TransportAction action =
+ transport_manager::TransportAction::kVisibilityOn;
// Check before Act
UninitializeTM();
// Act and Assert
- EXPECT_CALL(*mock_adapter_, StartClientListening()).Times(0);
- EXPECT_EQ(E_TM_IS_NOT_INITIALIZED, tm_.Visibility(visible));
+ EXPECT_CALL(
+ *mock_adapter_,
+ ChangeClientListening(transport_manager::TransportAction::kVisibilityOn))
+ .Times(0);
+ EXPECT_EQ(E_TM_IS_NOT_INITIALIZED, tm_.PerformActionOnClients(action));
}
TEST_F(TransportManagerImplTest, HandleMessage_ConnectionNotExist) {
@@ -971,16 +985,24 @@ TEST_F(TransportManagerImplTest, SearchDevices_TMIsNotInitialized) {
}
TEST_F(TransportManagerImplTest, SetVisibilityOn_TransportAdapterNotSupported) {
- EXPECT_CALL(*mock_adapter_, StartClientListening())
+ EXPECT_CALL(
+ *mock_adapter_,
+ ChangeClientListening(transport_manager::TransportAction::kVisibilityOn))
.WillOnce(Return(TransportAdapter::NOT_SUPPORTED));
- EXPECT_EQ(E_SUCCESS, tm_.Visibility(true));
+ EXPECT_EQ(E_SUCCESS,
+ tm_.PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOn));
}
TEST_F(TransportManagerImplTest,
SetVisibilityOff_TransportAdapterNotSupported) {
- EXPECT_CALL(*mock_adapter_, StopClientListening())
+ EXPECT_CALL(
+ *mock_adapter_,
+ ChangeClientListening(transport_manager::TransportAction::kVisibilityOff))
.WillOnce(Return(TransportAdapter::NOT_SUPPORTED));
- EXPECT_EQ(E_SUCCESS, tm_.Visibility(false));
+ EXPECT_EQ(E_SUCCESS,
+ tm_.PerformActionOnClients(
+ transport_manager::TransportAction::kVisibilityOff));
}
TEST_F(TransportManagerImplTest,
diff --git a/src/components/utils/src/signals_posix.cc b/src/components/utils/src/signals_posix.cc
index 8d1134576f..9b23aba804 100644
--- a/src/components/utils/src/signals_posix.cc
+++ b/src/components/utils/src/signals_posix.cc
@@ -83,7 +83,7 @@ pid_t Signals::Fork() {
}
void Signals::ExitProcess(const int status) {
- exit(status);
+ _Exit(status);
}
void Signals::WaitPid(pid_t cpid, int* status, int options) {