summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJuergen Gehring <juergen.gehring@bmw.de>2017-02-28 03:42:58 -0800
committerJuergen Gehring <juergen.gehring@bmw.de>2017-02-28 03:42:58 -0800
commitfad59c73675aea115d0c292b5743de2591bdf6b3 (patch)
tree76ce9670838f0edeb8d8777c1a9f4cc721d8fd16
parent55559fa14073203f9efc53a6c20d0b92e9bb69e5 (diff)
downloadgenivi-common-api-dbus-runtime-fad59c73675aea115d0c292b5743de2591bdf6b3.tar.gz
CommonAPI-D-Bus 3.1.113.1.11
-rw-r--r--CHANGES20
-rw-r--r--CMakeLists.txt8
-rw-r--r--README.md4
-rw-r--r--include/CommonAPI/DBus/CommonAPIDBus.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusAddress.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusAddressTranslator.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusAttribute.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusClientId.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusConfig.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusConnection.hpp18
-rw-r--r--include/CommonAPI/DBus/DBusDaemonProxy.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusDeployment.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusError.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusErrorEvent.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusEvent.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusFactory.hpp7
-rw-r--r--include/CommonAPI/DBus/DBusFreedesktopAttribute.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusFreedesktopPropertiesStub.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusFreedesktopStubAdapterHelper.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusFreedesktopVariant.hpp4
-rw-r--r--include/CommonAPI/DBus/DBusFunctionalHash.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusHelper.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusInputStream.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusInterfaceHandler.hpp2
-rwxr-xr-xinclude/CommonAPI/DBus/DBusMainLoop.hpp7
-rw-r--r--include/CommonAPI/DBus/DBusMainLoopContext.hpp19
-rw-r--r--include/CommonAPI/DBus/DBusMessage.hpp4
-rw-r--r--include/CommonAPI/DBus/DBusMultiEvent.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusObjectManager.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusObjectManagerStub.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusOutputStream.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusProxy.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusProxyAsyncCallbackHandler.hpp4
-rw-r--r--include/CommonAPI/DBus/DBusProxyAsyncSignalMemberCallbackHandler.hpp8
-rw-r--r--include/CommonAPI/DBus/DBusProxyBase.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusProxyConnection.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusProxyHelper.hpp18
-rw-r--r--include/CommonAPI/DBus/DBusProxyManager.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusSelectiveEvent.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusSerializableArguments.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusServiceRegistry.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusStubAdapter.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusStubAdapterHelper.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusTypeOutputStream.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusTypes.hpp2
-rw-r--r--include/CommonAPI/DBus/DBusUtils.hpp2
-rw-r--r--src/CommonAPI/DBus/DBusAddress.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusAddressTranslator.cpp6
-rw-r--r--src/CommonAPI/DBus/DBusClientId.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusConnection.cpp500
-rw-r--r--src/CommonAPI/DBus/DBusDaemonProxy.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusError.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusFactory.cpp16
-rw-r--r--src/CommonAPI/DBus/DBusFreedesktopPropertiesStub.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusFunctionalHash.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusInputStream.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.cpp2
-rwxr-xr-xsrc/CommonAPI/DBus/DBusMainLoop.cpp51
-rw-r--r--src/CommonAPI/DBus/DBusMainLoopContext.cpp40
-rw-r--r--src/CommonAPI/DBus/DBusMessage.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusObjectManager.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusObjectManagerStub.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusOutputStream.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusProxy.cpp11
-rw-r--r--src/CommonAPI/DBus/DBusProxyBase.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusProxyManager.cpp2
-rw-r--r--src/CommonAPI/DBus/DBusServiceRegistry.cpp132
-rw-r--r--src/CommonAPI/DBus/DBusStubAdapter.cpp2
-rw-r--r--src/test/CMakeLists.txt2
-rw-r--r--src/test/DBusClientIdTest.cpp2
-rw-r--r--src/test/DBusConnectionTest.cpp2
-rw-r--r--src/test/DBusDaemonProxyTest.cpp2
-rw-r--r--src/test/DBusStubAdapterTest.cpp2
-rw-r--r--src/test/DBusVariantOutputStreamTest.cpp2
-rw-r--r--src/test/DBusVariantTest.cpp2
76 files changed, 578 insertions, 413 deletions
diff --git a/CHANGES b/CHANGES
index ecc3954..46ae22e 100644
--- a/CHANGES
+++ b/CHANGES
@@ -1,6 +1,12 @@
Changes
=======
+v3.1.11
+- Fixed availability problem of proxies that connect to legacy managed services by changing the way of resolving object paths and available interfaces
+- Fixed several data races and potential deadlocks reported by the thread sanitizer
+- Ensure proxy is not destroyed while callback function is invoked
+- check for #define _WIN32 instead of (deprecated) WIN32
+
v3.1.10.4
- Prevent crash (double free) on destruction of static objects
- Fixed 'terminate called without an active exception' on verification test exit
@@ -8,15 +14,6 @@ v3.1.10.4
v3.1.10.3
- Fixed crash on dlclose()
-v3.1.10.2
-- Fix of calling unregisterStub() sometimes freezes
-- Fix deadlock by changing 'std::mutex connectionGuard_' to 'std::recursive_mutex' in D-Bus connection
-
-v3.1.10.1
-- Fix deadlock in connection: If data is currently dispatched and disconnecting tooks place it waits until disconnecting is finished. The problem is that the 'connectionGuard_' mutex is locked which is tried to be locked in 'sendDBusMessageWithReplyAsync' as well. This leads to deadlock and is fixed by removing the 'dispatchMutex' and instead of this the 'connectionGuard_' mutex is now used.
-- Fix availability listeners: Use an incrementing index as an identifier for subscriptions instead of iterators to a list that will get modified. Store the receiver proxy with each listener, instead of assuming that all proxies that connect to an interface are the same.
-- Avoid seg fault when creating a connection failed.
-
v3.1.10
- If an 'DBusInstanceAvailabilityStatusChangedEvent' occurs and the manager proxy was deleted, a bad_weak_ptr occurs. This is now avoided by introducing a weak_ptr. If the weak_ptr can be locked, the manager proxy was not deleted yet.
- Moved mutex lock in 'DBusMainLoop::registerWatch' to avoid deadlock.
@@ -29,3 +26,8 @@ v3.1.10
- Fixed THMainloopIndependence and THMainloopIntegration segfault. The problem is that a 'DBusQueueDispatchSource' has a pointer to its related 'DBusQueueWatch' as member variable and in the destructor of the dispatch source the watch is accessed. So a segfault can occur when the watch is deleted before the dispatch source.
- Replaced polling mechanism in 'DBusMainLoop' from sockets to WSAEvents in combination with named pipes.
- Added support for the DBus message type 'Error'. This needed the introduction of a new class ('DBusErrorEvent'), adaptions on proxy side ('DBusProxyHelper') and on stub side ('DBusStubAdapterHelper') and a libdbus patch that avoids the deletion of a message reply when an error occured / when an error reply was sent. This is necessary to deserialize the arguments of the error reply.
+
+
+
+
+
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 9967698..350a1ed 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -1,4 +1,4 @@
-# Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+# Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -10,7 +10,7 @@ PROJECT(libcommonapi-dbus)
# version of CommonAPI-DBus
SET( LIBCOMMONAPI_DBUS_MAJOR_VERSION 3 )
SET( LIBCOMMONAPI_DBUS_MINOR_VERSION 1 )
-SET( LIBCOMMONAPI_DBUS_PATCH_VERSION 10 )
+SET( LIBCOMMONAPI_DBUS_PATCH_VERSION 11 )
message(STATUS "Project name: ${PROJECT_NAME}")
@@ -123,9 +123,9 @@ message(STATUS "CMAKE_FIND_ROOT_PATH: ${CMAKE_FIND_ROOT_PATH}")
FIND_PACKAGE(PkgConfig)
FIND_PACKAGE(Threads REQUIRED)
if ("${USE_INSTALLED_COMMONAPI}" STREQUAL "ON")
- FIND_PACKAGE(CommonAPI 3.1.10 REQUIRED CONFIG NO_CMAKE_PACKAGE_REGISTRY)
+ FIND_PACKAGE(CommonAPI 3.1.11 REQUIRED CONFIG NO_CMAKE_PACKAGE_REGISTRY)
else()
- FIND_PACKAGE(CommonAPI 3.1.10 REQUIRED CONFIG NO_SYSTEM_ENVIRONMENT_PATH NO_CMAKE_SYSTEM_PATH)
+ FIND_PACKAGE(CommonAPI 3.1.11 REQUIRED CONFIG NO_SYSTEM_ENVIRONMENT_PATH NO_CMAKE_SYSTEM_PATH)
endif()
message(STATUS "CommonAPI_CONSIDERED_CONFIGS: ${CommonAPI_CONSIDERED_CONFIGS}")
diff --git a/README.md b/README.md
index d165993..f3b577e 100644
--- a/README.md
+++ b/README.md
@@ -1,8 +1,8 @@
### CommonAPI C++ D-Bus Runtime
##### Copyright
-Copyright (C) 2016, Bayerische Motoren Werke Aktiengesellschaft (BMW AG).
-Copyright (C) 2016, GENIVI Alliance, Inc.
+Copyright (C) 2016-2017, Bayerische Motoren Werke Aktiengesellschaft (BMW AG).
+Copyright (C) 2016-2017, GENIVI Alliance, Inc.
This file is part of GENIVI Project IPC Common API C++.
Contributions are licensed to the GENIVI Alliance under one or more Contribution License Agreements or MPL 2.0.
diff --git a/include/CommonAPI/DBus/CommonAPIDBus.hpp b/include/CommonAPI/DBus/CommonAPIDBus.hpp
index 1be7770..3df526d 100644
--- a/include/CommonAPI/DBus/CommonAPIDBus.hpp
+++ b/include/CommonAPI/DBus/CommonAPIDBus.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2015-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusAddress.hpp b/include/CommonAPI/DBus/DBusAddress.hpp
index 448012c..171a482 100644
--- a/include/CommonAPI/DBus/DBusAddress.hpp
+++ b/include/CommonAPI/DBus/DBusAddress.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2015-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusAddressTranslator.hpp b/include/CommonAPI/DBus/DBusAddressTranslator.hpp
index b3b0dde..dd5cbef 100644
--- a/include/CommonAPI/DBus/DBusAddressTranslator.hpp
+++ b/include/CommonAPI/DBus/DBusAddressTranslator.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusAttribute.hpp b/include/CommonAPI/DBus/DBusAttribute.hpp
index 2fd5bd3..5db6b49 100644
--- a/include/CommonAPI/DBus/DBusAttribute.hpp
+++ b/include/CommonAPI/DBus/DBusAttribute.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusClientId.hpp b/include/CommonAPI/DBus/DBusClientId.hpp
index 982b4dd..f5f5e85 100644
--- a/include/CommonAPI/DBus/DBusClientId.hpp
+++ b/include/CommonAPI/DBus/DBusClientId.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusConfig.hpp b/include/CommonAPI/DBus/DBusConfig.hpp
index cb07461..3043c8e 100644
--- a/include/CommonAPI/DBus/DBusConfig.hpp
+++ b/include/CommonAPI/DBus/DBusConfig.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusConnection.hpp b/include/CommonAPI/DBus/DBusConnection.hpp
index 90a6cb6..e88eab6 100644
--- a/include/CommonAPI/DBus/DBusConnection.hpp
+++ b/include/CommonAPI/DBus/DBusConnection.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -291,7 +291,7 @@ public:
COMMONAPI_EXPORT static void onWakeupMainContext(void* data);
- COMMONAPI_EXPORT void enforceAsynchronousTimeouts() const;
+ COMMONAPI_EXPORT void enforceAsynchronousTimeouts();
COMMONAPI_EXPORT static const DBusObjectPathVTable* getDBusObjectPathVTable();
COMMONAPI_EXPORT void sendPendingSelectiveSubscription(DBusProxy* proxy,
@@ -300,6 +300,16 @@ public:
uint32_t tag,
std::string interfaceMemberSignature);
+ void notifyDBusSignalHandlers(DBusSignalHandlerPath handlerPath,
+ const DBusMessage& dbusMessage,
+ ::DBusHandlerResult& dbusHandlerResult);
+
+ void notifyDBusOMSignalHandlers(const char* dbusSenderName,
+ const DBusMessage& dbusMessage,
+ ::DBusHandlerResult& dbusHandlerResult);
+
+ void deleteAsyncHandlers();
+
::DBusConnection* connection_;
mutable std::recursive_mutex connectionGuard_;
@@ -387,8 +397,10 @@ public:
std::set<std::thread::id> dispatchThreads_;
std::condition_variable_any dispatchCondition_;
-};
+ std::vector<DBusMessageReplyAsyncHandler*> asyncHandlersToDelete_;
+ std::mutex asyncHandlersToDeleteMutex_;
+};
template<class Function, class... Arguments>
void FunctionQueueEntry<Function, Arguments ...>::process(std::shared_ptr<DBusConnection> _connection) {
diff --git a/include/CommonAPI/DBus/DBusDaemonProxy.hpp b/include/CommonAPI/DBus/DBusDaemonProxy.hpp
index 44b882b..22d461f 100644
--- a/include/CommonAPI/DBus/DBusDaemonProxy.hpp
+++ b/include/CommonAPI/DBus/DBusDaemonProxy.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusDeployment.hpp b/include/CommonAPI/DBus/DBusDeployment.hpp
index c6ce15c..b12d67c 100644
--- a/include/CommonAPI/DBus/DBusDeployment.hpp
+++ b/include/CommonAPI/DBus/DBusDeployment.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusError.hpp b/include/CommonAPI/DBus/DBusError.hpp
index bd3a636..25d7864 100644
--- a/include/CommonAPI/DBus/DBusError.hpp
+++ b/include/CommonAPI/DBus/DBusError.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusErrorEvent.hpp b/include/CommonAPI/DBus/DBusErrorEvent.hpp
index 2256d33..966f9e1 100644
--- a/include/CommonAPI/DBus/DBusErrorEvent.hpp
+++ b/include/CommonAPI/DBus/DBusErrorEvent.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusEvent.hpp b/include/CommonAPI/DBus/DBusEvent.hpp
index 945988d..4d53d23 100644
--- a/include/CommonAPI/DBus/DBusEvent.hpp
+++ b/include/CommonAPI/DBus/DBusEvent.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusFactory.hpp b/include/CommonAPI/DBus/DBusFactory.hpp
index 51ec476..157382d 100644
--- a/include/CommonAPI/DBus/DBusFactory.hpp
+++ b/include/CommonAPI/DBus/DBusFactory.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -18,6 +18,9 @@
#include <CommonAPI/DBus/DBusTypes.hpp>
namespace CommonAPI {
+
+class Runtime;
+
namespace DBus {
class DBusAddress;
@@ -95,6 +98,8 @@ public:
// Initialization
COMMONAPI_EXPORT void registerInterface(InterfaceInitFunction _function);
+ static std::weak_ptr<CommonAPI::Runtime> runtime_;
+
private:
COMMONAPI_EXPORT void incrementConnection(std::shared_ptr<DBusProxyConnection>);
COMMONAPI_EXPORT std::shared_ptr<DBusConnection> getConnection(const ConnectionId_t &);
diff --git a/include/CommonAPI/DBus/DBusFreedesktopAttribute.hpp b/include/CommonAPI/DBus/DBusFreedesktopAttribute.hpp
index 8f35928..28b41da 100644
--- a/include/CommonAPI/DBus/DBusFreedesktopAttribute.hpp
+++ b/include/CommonAPI/DBus/DBusFreedesktopAttribute.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2015-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusFreedesktopPropertiesStub.hpp b/include/CommonAPI/DBus/DBusFreedesktopPropertiesStub.hpp
index bc31a89..0a0914d 100644
--- a/include/CommonAPI/DBus/DBusFreedesktopPropertiesStub.hpp
+++ b/include/CommonAPI/DBus/DBusFreedesktopPropertiesStub.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusFreedesktopStubAdapterHelper.hpp b/include/CommonAPI/DBus/DBusFreedesktopStubAdapterHelper.hpp
index d5abcca..42b8f92 100644
--- a/include/CommonAPI/DBus/DBusFreedesktopStubAdapterHelper.hpp
+++ b/include/CommonAPI/DBus/DBusFreedesktopStubAdapterHelper.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2015-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusFreedesktopVariant.hpp b/include/CommonAPI/DBus/DBusFreedesktopVariant.hpp
index 243604e..bd1fb58 100644
--- a/include/CommonAPI/DBus/DBusFreedesktopVariant.hpp
+++ b/include/CommonAPI/DBus/DBusFreedesktopVariant.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -45,7 +45,7 @@ struct ApplyTypeCompareVisitor<Visitor_, Variant_, Deployment_, Type_, Types_...
output.writeType(current, static_cast<CommonAPI::EmptyDeployment*>(nullptr));
}
-#ifdef WIN32
+#ifdef _WIN32
if (_visitor.operator()<Type_>(output.getSignature())) {
#else
if (_visitor.template operator()<Type_>(output.getSignature())) {
diff --git a/include/CommonAPI/DBus/DBusFunctionalHash.hpp b/include/CommonAPI/DBus/DBusFunctionalHash.hpp
index 4903c21..fbc1ea3 100644
--- a/include/CommonAPI/DBus/DBusFunctionalHash.hpp
+++ b/include/CommonAPI/DBus/DBusFunctionalHash.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusHelper.hpp b/include/CommonAPI/DBus/DBusHelper.hpp
index 889cf53..ebde2b8 100644
--- a/include/CommonAPI/DBus/DBusHelper.hpp
+++ b/include/CommonAPI/DBus/DBusHelper.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusInputStream.hpp b/include/CommonAPI/DBus/DBusInputStream.hpp
index 61e4133..fab82dd 100644
--- a/include/CommonAPI/DBus/DBusInputStream.hpp
+++ b/include/CommonAPI/DBus/DBusInputStream.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.hpp b/include/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.hpp
index 9be2e9a..91fa410 100644
--- a/include/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.hpp
+++ b/include/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusInterfaceHandler.hpp b/include/CommonAPI/DBus/DBusInterfaceHandler.hpp
index fa6c0bb..9804aff 100644
--- a/include/CommonAPI/DBus/DBusInterfaceHandler.hpp
+++ b/include/CommonAPI/DBus/DBusInterfaceHandler.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusMainLoop.hpp b/include/CommonAPI/DBus/DBusMainLoop.hpp
index b09a8f1..2ca7202 100755
--- a/include/CommonAPI/DBus/DBusMainLoop.hpp
+++ b/include/CommonAPI/DBus/DBusMainLoop.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -18,6 +18,7 @@
#include <mutex>
#include <set>
#include <vector>
+#include <atomic>
namespace CommonAPI {
namespace DBus {
@@ -173,11 +174,11 @@ class DBusMainLoop {
DBusMainLoopPollFd wakeFd_;
-#ifdef WIN32
+#ifdef _WIN32
DBusMainLoopPollFd sendFd_;
#endif
- bool hasToStop_;
+ std::atomic<bool> hasToStop_;
bool isBroken_;
};
diff --git a/include/CommonAPI/DBus/DBusMainLoopContext.hpp b/include/CommonAPI/DBus/DBusMainLoopContext.hpp
index 708cfa3..adf132f 100644
--- a/include/CommonAPI/DBus/DBusMainLoopContext.hpp
+++ b/include/CommonAPI/DBus/DBusMainLoopContext.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -13,6 +13,7 @@
#include <list>
#include <memory>
#include <queue>
+#include <atomic>
#include <dbus/dbus.h>
@@ -50,8 +51,6 @@ class DBusQueueDispatchSource: public DispatchSource {
private:
DBusQueueWatch* watch_;
-
- std::mutex watchMutex_;
};
class DBusWatch: public Watch {
@@ -67,7 +66,7 @@ class DBusWatch: public Watch {
const pollfd& getAssociatedFileDescriptor();
-#ifdef WIN32
+#ifdef _WIN32
const HANDLE& getAssociatedEvent();
#endif
@@ -79,11 +78,12 @@ class DBusWatch: public Watch {
::DBusWatch* libdbusWatch_;
pollfd pollFileDescriptor_;
std::vector<DispatchSource*> dependentDispatchSources_;
+ std::mutex dependentDispatchSourcesMutex_;
std::weak_ptr<MainLoopContext> mainLoopContext_;
std::weak_ptr<DBusConnection> dbusConnection_;
-#ifdef WIN32
+#ifdef _WIN32
HANDLE wsaEvent_;
#endif
};
@@ -100,7 +100,7 @@ public:
const pollfd& getAssociatedFileDescriptor();
-#ifdef WIN32
+#ifdef _WIN32
const HANDLE& getAssociatedEvent();
#endif
@@ -129,11 +129,12 @@ private:
std::queue<std::shared_ptr<QueueEntry>> queue_;
std::mutex queueMutex_;
+ std::mutex dependentDispatchSourcesMutex_;
std::weak_ptr<DBusConnection> connection_;
const int pipeValue_;
-#ifdef WIN32
+#ifdef _WIN32
HANDLE wsaEvent_;
#endif
@@ -157,7 +158,7 @@ class DBusTimeout: public Timeout {
void setPendingCall(DBusPendingCall* _pendingCall);
-#ifdef WIN32
+#ifdef _WIN32
__declspec(thread) static DBusTimeout *currentTimeout_;
#else
thread_local static DBusTimeout *currentTimeout_;
@@ -166,7 +167,7 @@ class DBusTimeout: public Timeout {
private:
void recalculateDueTime();
- int64_t dueTimeInMs_;
+ std::atomic<int64_t> dueTimeInMs_;
::DBusTimeout* libdbusTimeout_;
std::weak_ptr<MainLoopContext> mainLoopContext_;
std::weak_ptr<DBusConnection> dbusConnection_;
diff --git a/include/CommonAPI/DBus/DBusMessage.hpp b/include/CommonAPI/DBus/DBusMessage.hpp
index ece0b21..98a668d 100644
--- a/include/CommonAPI/DBus/DBusMessage.hpp
+++ b/include/CommonAPI/DBus/DBusMessage.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -14,7 +14,7 @@
#include <dbus/dbus.h>
-#ifdef WIN32
+#ifdef _WIN32
#include <stdint.h>
#endif
diff --git a/include/CommonAPI/DBus/DBusMultiEvent.hpp b/include/CommonAPI/DBus/DBusMultiEvent.hpp
index db0c1e5..cf18a48 100644
--- a/include/CommonAPI/DBus/DBusMultiEvent.hpp
+++ b/include/CommonAPI/DBus/DBusMultiEvent.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusObjectManager.hpp b/include/CommonAPI/DBus/DBusObjectManager.hpp
index 2d36aaf..432e733 100644
--- a/include/CommonAPI/DBus/DBusObjectManager.hpp
+++ b/include/CommonAPI/DBus/DBusObjectManager.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusObjectManagerStub.hpp b/include/CommonAPI/DBus/DBusObjectManagerStub.hpp
index de8495d..d8de02d 100644
--- a/include/CommonAPI/DBus/DBusObjectManagerStub.hpp
+++ b/include/CommonAPI/DBus/DBusObjectManagerStub.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusOutputStream.hpp b/include/CommonAPI/DBus/DBusOutputStream.hpp
index 6814430..3cd9cb6 100644
--- a/include/CommonAPI/DBus/DBusOutputStream.hpp
+++ b/include/CommonAPI/DBus/DBusOutputStream.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusProxy.hpp b/include/CommonAPI/DBus/DBusProxy.hpp
index cc9bd06..feedb12 100644
--- a/include/CommonAPI/DBus/DBusProxy.hpp
+++ b/include/CommonAPI/DBus/DBusProxy.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusProxyAsyncCallbackHandler.hpp b/include/CommonAPI/DBus/DBusProxyAsyncCallbackHandler.hpp
index d21807d..25b2ecd 100644
--- a/include/CommonAPI/DBus/DBusProxyAsyncCallbackHandler.hpp
+++ b/include/CommonAPI/DBus/DBusProxyAsyncCallbackHandler.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -225,7 +225,7 @@ private:
}
}
- //ensure that delegate object (e.g. Proxy) survives
+ //ensure that delegate object (i.e Proxy) is not destroyed while callback function is invoked
if(auto itsDelegateObject = this->delegate_.object_.lock())
this->delegate_.function_(callStatus, std::move(std::get<ArgIndices_>(_argTuple))...);
diff --git a/include/CommonAPI/DBus/DBusProxyAsyncSignalMemberCallbackHandler.hpp b/include/CommonAPI/DBus/DBusProxyAsyncSignalMemberCallbackHandler.hpp
index 788c1ff..a768e45 100644
--- a/include/CommonAPI/DBus/DBusProxyAsyncSignalMemberCallbackHandler.hpp
+++ b/include/CommonAPI/DBus/DBusProxyAsyncSignalMemberCallbackHandler.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2015-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -105,9 +105,9 @@ class DBusProxyAsyncSignalMemberCallbackHandler: public DBusProxyConnection::DBu
inline CallStatus handleDBusMessageReply(const CallStatus dbusMessageCallStatus, const DBusMessage& dbusMessage) const {
CallStatus callStatus = dbusMessageCallStatus;
- //check if object is expired
- if(!delegate_.object_.expired())
- delegate_.function_(callStatus, dbusMessage, dbusSignalHandler_, tag_);
+ //ensure that delegate object (i.e Proxy) is not destroyed while callback function is invoked
+ if(auto itsDelegateObject = this->delegate_.object_.lock())
+ this->delegate_.function_(callStatus, dbusMessage, dbusSignalHandler_, tag_);
return callStatus;
}
diff --git a/include/CommonAPI/DBus/DBusProxyBase.hpp b/include/CommonAPI/DBus/DBusProxyBase.hpp
index e0fbaec..5a24de4 100644
--- a/include/CommonAPI/DBus/DBusProxyBase.hpp
+++ b/include/CommonAPI/DBus/DBusProxyBase.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusProxyConnection.hpp b/include/CommonAPI/DBus/DBusProxyConnection.hpp
index d0db2ba..ec02082 100644
--- a/include/CommonAPI/DBus/DBusProxyConnection.hpp
+++ b/include/CommonAPI/DBus/DBusProxyConnection.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusProxyHelper.hpp b/include/CommonAPI/DBus/DBusProxyHelper.hpp
index 3f9e175..43655f4 100644
--- a/include/CommonAPI/DBus/DBusProxyHelper.hpp
+++ b/include/CommonAPI/DBus/DBusProxyHelper.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -31,7 +31,7 @@ class DBusProxy;
template< class, class... >
struct DBusProxyHelper;
-#ifdef WIN32
+#ifdef _WIN32
// Visual Studio 2013 does not support 'magic statics' yet.
// Change back when switched to Visual Studio 2015 or higher.
static std::mutex callMethod_mutex_;
@@ -51,7 +51,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
const std::string &_signature,
const InArgs_&... _in,
CommonAPI::CallStatus &_status) {
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethod_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethod_mutex_);
@@ -119,7 +119,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
const InArgs_&... _in,
CommonAPI::CallStatus &_status,
OutArgs_&... _out) {
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethodWithReply_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethodWithReply_mutex_);
@@ -160,7 +160,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
const InArgs_&... _in,
CommonAPI::CallStatus &_status,
OutArgs_&... _out) {
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethodWithReply_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethodWithReply_mutex_);
@@ -269,7 +269,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
const InArgs_&... _in,
DelegateFunction_ _function,
std::tuple<OutArgs_...> _out) {
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethodAsync_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethodAsync_mutex_);
@@ -307,7 +307,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
const InArgs_&... _in,
DelegateFunction_ _function,
std::tuple<OutArgs_...> _out) {
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethodAsync_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethodAsync_mutex_);
@@ -384,7 +384,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
CommonAPI::CallStatus &_status,
OutArgs_&... _out,
const std::tuple<ErrorEvents_*...> &_errorEvents){
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethodWithReply_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethodWithReply_mutex_);
@@ -494,7 +494,7 @@ struct DBusProxyHelper<In_<DBusInputStream, DBusOutputStream, InArgs_...>,
DelegateFunction_ _function,
std::tuple<OutArgs_...> _out,
const std::tuple<ErrorEvents_*...> &_errorEvents) {
-#ifndef WIN32
+#ifndef _WIN32
static std::mutex callMethodAsync_mutex_;
#endif
std::lock_guard<std::mutex> lock(callMethodAsync_mutex_);
diff --git a/include/CommonAPI/DBus/DBusProxyManager.hpp b/include/CommonAPI/DBus/DBusProxyManager.hpp
index 1dd8dbe..f8829b4 100644
--- a/include/CommonAPI/DBus/DBusProxyManager.hpp
+++ b/include/CommonAPI/DBus/DBusProxyManager.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusSelectiveEvent.hpp b/include/CommonAPI/DBus/DBusSelectiveEvent.hpp
index 93bb5ea..075b819 100644
--- a/include/CommonAPI/DBus/DBusSelectiveEvent.hpp
+++ b/include/CommonAPI/DBus/DBusSelectiveEvent.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusSerializableArguments.hpp b/include/CommonAPI/DBus/DBusSerializableArguments.hpp
index 6b48eff..771de26 100644
--- a/include/CommonAPI/DBus/DBusSerializableArguments.hpp
+++ b/include/CommonAPI/DBus/DBusSerializableArguments.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusServiceRegistry.hpp b/include/CommonAPI/DBus/DBusServiceRegistry.hpp
index 497e909..3181226 100644
--- a/include/CommonAPI/DBus/DBusServiceRegistry.hpp
+++ b/include/CommonAPI/DBus/DBusServiceRegistry.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusStubAdapter.hpp b/include/CommonAPI/DBus/DBusStubAdapter.hpp
index 710277b..882ec8f 100644
--- a/include/CommonAPI/DBus/DBusStubAdapter.hpp
+++ b/include/CommonAPI/DBus/DBusStubAdapter.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusStubAdapterHelper.hpp b/include/CommonAPI/DBus/DBusStubAdapterHelper.hpp
index 3a9b7e8..50ba9ae 100644
--- a/include/CommonAPI/DBus/DBusStubAdapterHelper.hpp
+++ b/include/CommonAPI/DBus/DBusStubAdapterHelper.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusTypeOutputStream.hpp b/include/CommonAPI/DBus/DBusTypeOutputStream.hpp
index a2e96e5..6cab51f 100644
--- a/include/CommonAPI/DBus/DBusTypeOutputStream.hpp
+++ b/include/CommonAPI/DBus/DBusTypeOutputStream.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusTypes.hpp b/include/CommonAPI/DBus/DBusTypes.hpp
index 86bed2d..ec7e092 100644
--- a/include/CommonAPI/DBus/DBusTypes.hpp
+++ b/include/CommonAPI/DBus/DBusTypes.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2014-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2014-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/include/CommonAPI/DBus/DBusUtils.hpp b/include/CommonAPI/DBus/DBusUtils.hpp
index d12e024..03fd401 100644
--- a/include/CommonAPI/DBus/DBusUtils.hpp
+++ b/include/CommonAPI/DBus/DBusUtils.hpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusAddress.cpp b/src/CommonAPI/DBus/DBusAddress.cpp
index d73cfc0..4819a40 100644
--- a/src/CommonAPI/DBus/DBusAddress.cpp
+++ b/src/CommonAPI/DBus/DBusAddress.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2015-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusAddressTranslator.cpp b/src/CommonAPI/DBus/DBusAddressTranslator.cpp
index 460ab16..49f42d4 100644
--- a/src/CommonAPI/DBus/DBusAddressTranslator.cpp
+++ b/src/CommonAPI/DBus/DBusAddressTranslator.cpp
@@ -1,9 +1,9 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
-#ifdef WIN32
+#ifdef _WIN32
#include <Windows.h>
#else
#include <unistd.h>
@@ -223,7 +223,7 @@ DBusAddressTranslator::readConfiguration() {
#define MAX_PATH_LEN 255
std::string config;
char currentDirectory[MAX_PATH_LEN];
-#ifdef WIN32
+#ifdef _WIN32
if (GetCurrentDirectory(MAX_PATH_LEN, currentDirectory)) {
#else
if (getcwd(currentDirectory, MAX_PATH_LEN)) {
diff --git a/src/CommonAPI/DBus/DBusClientId.cpp b/src/CommonAPI/DBus/DBusClientId.cpp
index 7c9f195..12983b5 100644
--- a/src/CommonAPI/DBus/DBusClientId.cpp
+++ b/src/CommonAPI/DBus/DBusClientId.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusConnection.cpp b/src/CommonAPI/DBus/DBusConnection.cpp
index 3ed06a7..589b5f4 100644
--- a/src/CommonAPI/DBus/DBusConnection.cpp
+++ b/src/CommonAPI/DBus/DBusConnection.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -498,11 +498,10 @@ DBusProxyConnection::ConnectionStatusEvent& DBusConnection::getConnectionStatusE
//Does this need to be a weak pointer?
const std::shared_ptr<DBusObjectManager> DBusConnection::getDBusObjectManager() {
if (!dbusObjectManager_) {
- objectManagerGuard_.lock();
+ std::lock_guard<std::mutex> itsLock(objectManagerGuard_);
if (!dbusObjectManager_) {
dbusObjectManager_ = std::make_shared<DBusObjectManager>(shared_from_this());
}
- objectManagerGuard_.unlock();
}
return dbusObjectManager_;
}
@@ -656,140 +655,163 @@ void DBusConnection::onLibdbusDataCleanup(void *_data) {
}
//Would not be needed if libdbus would actually handle its timeouts for pending calls.
-void DBusConnection::enforceAsynchronousTimeouts() const {
- std::unique_lock<std::recursive_mutex> itsLock(enforcerThreadMutex_);
-
- while (!enforcerThreadCancelled_) {
- enforceTimeoutMutex_.lock();
+void DBusConnection::enforceAsynchronousTimeouts() {
+ {
+ std::unique_lock<std::recursive_mutex> itsLock(enforcerThreadMutex_);
- int timeout = std::numeric_limits<int>::max(); // not really, but nearly "forever"
- if (timeoutMap_.size() > 0) {
- auto minTimeoutElement = std::min_element(timeoutMap_.begin(), timeoutMap_.end(),
- [] (const TimeoutMapElement& lhs, const TimeoutMapElement& rhs) {
- return std::get<0>(lhs.second) < std::get<0>(rhs.second);
- });
+ while (!enforcerThreadCancelled_) {
- auto minTimeout = std::get<0>(minTimeoutElement->second);
+ int timeout = std::numeric_limits<int>::max(); // not really, but nearly "forever"
+ {
+ std::lock_guard<std::mutex> itsLock(enforceTimeoutMutex_);
+ if (timeoutMap_.size() > 0) {
+ auto minTimeoutElement = std::min_element(timeoutMap_.begin(), timeoutMap_.end(),
+ [] (const TimeoutMapElement& lhs, const TimeoutMapElement& rhs) {
+ return std::get<0>(lhs.second) < std::get<0>(rhs.second);
+ });
- std::chrono::steady_clock::time_point now = (std::chrono::steady_clock::time_point) std::chrono::steady_clock::now();
+ auto minTimeout = std::get<0>(minTimeoutElement->second);
- timeout = (int)std::chrono::duration_cast<std::chrono::milliseconds>(minTimeout - now).count();
- }
+ std::chrono::steady_clock::time_point now = (std::chrono::steady_clock::time_point) std::chrono::steady_clock::now();
- enforceTimeoutMutex_.unlock();
+ timeout = (int)std::chrono::duration_cast<std::chrono::milliseconds>(minTimeout - now).count();
+ }
+ }
- if (std::cv_status::timeout ==
- enforceTimeoutCondition_.wait_for(itsLock, std::chrono::milliseconds(timeout))) {
+ if (std::cv_status::timeout ==
+ enforceTimeoutCondition_.wait_for(itsLock, std::chrono::milliseconds(timeout))) {
- //Do not access members if the DBusConnection was destroyed during the unlocked phase.
- enforceTimeoutMutex_.lock();
- auto it = timeoutMap_.begin();
- while (it != timeoutMap_.end()) {
- std::chrono::steady_clock::time_point now = (std::chrono::steady_clock::time_point) std::chrono::steady_clock::now();
+ //Do not access members if the DBusConnection was destroyed during the unlocked phase.
+ std::lock_guard<std::mutex> itsLock(enforceTimeoutMutex_);
+ auto it = timeoutMap_.begin();
+ while (it != timeoutMap_.end()) {
+ std::chrono::steady_clock::time_point now = (std::chrono::steady_clock::time_point) std::chrono::steady_clock::now();
- DBusMessageReplyAsyncHandler* asyncHandler = std::get<1>(it->second);
- DBusPendingCall* libdbusPendingCall = it->first;
+ DBusMessageReplyAsyncHandler* asyncHandler = std::get<1>(it->second);
+ DBusPendingCall* libdbusPendingCall = it->first;
- if (now > std::get<0>(it->second)) {
+ if (now > std::get<0>(it->second)) {
- asyncHandler->lock();
- bool executionStarted = asyncHandler->getExecutionStarted();
- bool executionFinished = asyncHandler->getExecutionFinished();
- if (!executionStarted && !executionFinished) {
- asyncHandler->setTimeoutOccurred();
- if (!dbus_pending_call_get_completed(libdbusPendingCall)) {
- dbus_pending_call_cancel(libdbusPendingCall);
+ asyncHandler->lock();
+ bool executionStarted = asyncHandler->getExecutionStarted();
+ bool executionFinished = asyncHandler->getExecutionFinished();
+ if (!executionStarted && !executionFinished) {
+ asyncHandler->setTimeoutOccurred();
+ if (!dbus_pending_call_get_completed(libdbusPendingCall)) {
+ dbus_pending_call_cancel(libdbusPendingCall);
+ }
}
- }
- asyncHandler->unlock();
+ asyncHandler->unlock();
- if (executionStarted && !executionFinished) {
- // execution of asyncHandler is still running
- // ==> add 100 ms for next timeout check
- std::get<0>(it->second) = (std::chrono::steady_clock::time_point) std::chrono::steady_clock::now() + std::chrono::milliseconds(100);
- } else {
- if (!executionFinished) {
- // execution of asyncHandler was not finished (and not started)
- // => add asyncHandler to mainloopTimeouts list
- DBusMessage& dbusMessageCall = std::get<2>(it->second);
-
- auto lockedContext = mainLoopContext_.lock();
- if (!lockedContext) {
- COMMONAPI_ERROR(std::string(__FUNCTION__), "lockedContext == nullptr");
- } else {
- {
- std::lock_guard<std::mutex> itsLock(mainloopTimeoutsMutex_);
- mainloopTimeouts_.push_back(std::make_tuple(asyncHandler,
- dbusMessageCall.createMethodError(DBUS_ERROR_TIMEOUT),
- CallStatus::REMOTE_ERROR,
- nullptr));
+ if (executionStarted && !executionFinished) {
+ // execution of asyncHandler is still running
+ // ==> add 100 ms for next timeout check
+ std::get<0>(it->second) = (std::chrono::steady_clock::time_point) std::chrono::steady_clock::now() + std::chrono::milliseconds(100);
+ } else {
+ if (!executionFinished) {
+ // execution of asyncHandler was not finished (and not started)
+ // => add asyncHandler to mainloopTimeouts list
+ DBusMessage& dbusMessageCall = std::get<2>(it->second);
+
+ auto lockedContext = mainLoopContext_.lock();
+ if (!lockedContext) {
+ COMMONAPI_ERROR(std::string(__FUNCTION__), "lockedContext == nullptr");
+ } else {
+ {
+ std::lock_guard<std::mutex> itsLock(mainloopTimeoutsMutex_);
+ mainloopTimeouts_.push_back(std::make_tuple(asyncHandler,
+ dbusMessageCall.createMethodError(DBUS_ERROR_TIMEOUT),
+ CallStatus::REMOTE_ERROR,
+ nullptr));
+ }
+ lockedContext->wakeup();
}
- lockedContext->wakeup();
+ it = timeoutMap_.erase(it);
+
+ //This unref MIGHT cause the destruction of the last callback object that references the DBusConnection.
+ //So after this unref has been called, it has to be ensured that continuation of the loop is an option.
+ dbus_pending_call_unref(libdbusPendingCall);
+ } else {
+ // execution of asyncHandler was finished
+ it = timeoutMap_.erase(it);
+ // The deletion of the async handler (which leads to destruction of the DBusProxy and DBusConnection)
+ // needs to be done asynchronously by the main loop
+ // because of a potential deadlock.
+ std::lock_guard<std::mutex> asyncHandlersLock(asyncHandlersToDeleteMutex_);
+ asyncHandlersToDelete_.push_back(asyncHandler);
+ proxyPushFunctionToMainLoop(std::bind(&DBusConnection::deleteAsyncHandlers, this));
}
+ }
+ } else {
+ asyncHandler->lock();
+ bool executionFinished = asyncHandler->getExecutionFinished();
+ asyncHandler->unlock();
+ if (executionFinished) {
+ // execution of asyncHandler was finished but timeout is not expired
it = timeoutMap_.erase(it);
-
- //This unref MIGHT cause the destruction of the last callback object that references the DBusConnection.
- //So after this unref has been called, it has to be ensured that continuation of the loop is an option.
- dbus_pending_call_unref(libdbusPendingCall);
+ // The deletion of the async handler (which leads to destruction of the DBusProxy and DBusConnection)
+ // needs to be done asynchronously by the main loop
+ // because of a potential deadlock.
+ std::lock_guard<std::mutex> asyncHandlersLock(asyncHandlersToDeleteMutex_);
+ asyncHandlersToDelete_.push_back(asyncHandler);
+ proxyPushFunctionToMainLoop(std::bind(&DBusConnection::deleteAsyncHandlers, this));
} else {
- // execution of asyncHandler was finished
- it = timeoutMap_.erase(it);
- delete asyncHandler;
+ ++it;
}
}
- } else {
+ }
+ } else {
+
+ std::lock_guard<std::mutex> itsLock(enforceTimeoutMutex_);
+
+ auto it = timeoutMap_.begin();
+ while (it != timeoutMap_.end()) {
+ DBusMessageReplyAsyncHandler* asyncHandler = std::get<1>(it->second);
asyncHandler->lock();
bool executionFinished = asyncHandler->getExecutionFinished();
asyncHandler->unlock();
if (executionFinished) {
// execution of asyncHandler was finished but timeout is not expired
it = timeoutMap_.erase(it);
- delete asyncHandler;
+ // The deletion of the async handler (which leads to destruction of the DBusProxy and DBusConnection)
+ // needs to be done asynchronously by the main loop
+ // because of a potential deadlock.
+ std::lock_guard<std::mutex> asyncHandlersLock(asyncHandlersToDeleteMutex_);
+ asyncHandlersToDelete_.push_back(asyncHandler);
+ proxyPushFunctionToMainLoop(std::bind(&DBusConnection::deleteAsyncHandlers, this));
} else {
++it;
}
}
}
- enforceTimeoutMutex_.unlock();
- } else {
- std::lock_guard<std::mutex> itsLock(enforceTimeoutMutex_);
-
- auto it = timeoutMap_.begin();
- while (it != timeoutMap_.end()) {
- DBusMessageReplyAsyncHandler* asyncHandler = std::get<1>(it->second);
- asyncHandler->lock();
- bool executionFinished = asyncHandler->getExecutionFinished();
- asyncHandler->unlock();
- if (executionFinished) {
- // execution of asyncHandler was finished but timeout is not expired
- it = timeoutMap_.erase(it);
- delete asyncHandler;
- } else {
- ++it;
- }
- }
- }
-
- {
- std::lock_guard<std::mutex> itsLock(timeoutInfiniteAsyncHandlersMutex_);
- // check for asyncHandler with infinite timeout whose execution is finished
- auto it = timeoutInfiniteAsyncHandlers_.begin();
- while (it != timeoutInfiniteAsyncHandlers_.end()) {
- DBusMessageReplyAsyncHandler* asyncHandler = (*it);
- asyncHandler->lock();
- bool executionFinished = asyncHandler->getExecutionFinished();
- asyncHandler->unlock();
- if ( executionFinished ) {
- it = timeoutInfiniteAsyncHandlers_.erase(it);
- delete asyncHandler;
- } else {
- it++;
+ {
+ std::lock_guard<std::mutex> itsLock(timeoutInfiniteAsyncHandlersMutex_);
+ // check for asyncHandler with infinite timeout whose execution is finished
+ auto it = timeoutInfiniteAsyncHandlers_.begin();
+ while (it != timeoutInfiniteAsyncHandlers_.end()) {
+ DBusMessageReplyAsyncHandler* asyncHandler = (*it);
+ asyncHandler->lock();
+ bool executionFinished = asyncHandler->getExecutionFinished();
+ asyncHandler->unlock();
+ if ( executionFinished ) {
+ it = timeoutInfiniteAsyncHandlers_.erase(it);
+ // The deletion of the async handler (which leads to destruction of the DBusProxy and DBusConnection)
+ // needs to be done asynchronously by the main loop
+ // because of a potential deadlock.
+ std::lock_guard<std::mutex> asyncHandlersLock(asyncHandlersToDeleteMutex_);
+ asyncHandlersToDelete_.push_back(asyncHandler);
+ proxyPushFunctionToMainLoop(std::bind(&DBusConnection::deleteAsyncHandlers, this));
+ } else {
+ it++;
+ }
}
}
}
-
}
+
+ // delete left async handlers that could not be deleted by the main loop
+ deleteAsyncHandlers();
}
bool DBusConnection::sendDBusMessageWithReplyAsync(
@@ -797,35 +819,37 @@ bool DBusConnection::sendDBusMessageWithReplyAsync(
std::unique_ptr<DBusMessageReplyAsyncHandler> dbusMessageReplyAsyncHandler,
const CommonAPI::CallInfo *_info) const {
- std::lock_guard<std::recursive_mutex> dbusConnectionLock(connectionGuard_);
-
- if (!dbusMessage) {
- COMMONAPI_ERROR(std::string(__FUNCTION__), "message == NULL");
- return false;
- }
- if (!isConnected()) {
- COMMONAPI_ERROR(std::string(__FUNCTION__), "not connected");
- return false;
- }
-
DBusPendingCall* libdbusPendingCall;
dbus_bool_t libdbusSuccess;
+ DBusMessageReplyAsyncHandler* replyAsyncHandler = nullptr;
+ {
+ std::lock_guard<std::recursive_mutex> dbusConnectionLock(connectionGuard_);
- DBusMessageReplyAsyncHandler* replyAsyncHandler = dbusMessageReplyAsyncHandler.release();
+ if (!dbusMessage) {
+ COMMONAPI_ERROR(std::string(__FUNCTION__), "message == NULL");
+ return false;
+ }
+ if (!isConnected()) {
+ COMMONAPI_ERROR(std::string(__FUNCTION__), "not connected");
+ return false;
+ }
- PendingCallNotificationData* userData = new PendingCallNotificationData(this, replyAsyncHandler);
- DBusTimeout::currentTimeout_ = NULL;
+ replyAsyncHandler = dbusMessageReplyAsyncHandler.release();
- libdbusSuccess = dbus_connection_send_with_reply_set_notify(connection_,
- dbusMessage.message_,
- &libdbusPendingCall,
- onLibdbusPendingCallNotifyThunk,
- userData,
- onLibdbusDataCleanup,
- _info->timeout_);
+ PendingCallNotificationData* userData = new PendingCallNotificationData(this, replyAsyncHandler);
+ DBusTimeout::currentTimeout_ = NULL;
- if (_info->sender_ != 0) {
- COMMONAPI_DEBUG("Message sent: SenderID: ", _info->sender_, " - Serial number: ", dbusMessage.getSerial());
+ libdbusSuccess = dbus_connection_send_with_reply_set_notify(connection_,
+ dbusMessage.message_,
+ &libdbusPendingCall,
+ onLibdbusPendingCallNotifyThunk,
+ userData,
+ onLibdbusDataCleanup,
+ _info->timeout_);
+
+ if (_info->sender_ != 0) {
+ COMMONAPI_DEBUG("Message sent: SenderID: ", _info->sender_, " - Serial number: ", dbusMessage.getSerial());
+ }
}
if (!libdbusSuccess || !libdbusPendingCall) {
@@ -864,25 +888,28 @@ bool DBusConnection::sendDBusMessageWithReplyAsync(
if(DBusTimeout::currentTimeout_)
DBusTimeout::currentTimeout_->setPendingCall(libdbusPendingCall);
- enforceTimeoutMutex_.lock();
- auto ret = timeoutMap_.insert( { libdbusPendingCall, toInsert } );
- if (ret.second == false) {
- // key has been reused
- // update the map value with the new info
- DBusMessageReplyAsyncHandler* asyncHandler;
- auto it = timeoutMap_.find(ret.first->first);
- if(it != timeoutMap_.end()) {
- asyncHandler = std::get<1>(it->second);
- delete asyncHandler;
+ DBusMessageReplyAsyncHandler* asyncHandler = nullptr;
+ {
+ std::lock_guard<std::mutex> enforcerLock(enforceTimeoutMutex_);
+ auto ret = timeoutMap_.insert( { libdbusPendingCall, toInsert } );
+ if (ret.second == false) {
+ // key has been reused
+ // update the map value with the new info
+ auto it = timeoutMap_.find(ret.first->first);
+ if(it != timeoutMap_.end()) {
+ asyncHandler = std::get<1>(it->second);
+ }
+ timeoutMap_.erase(ret.first);
+ timeoutMap_.insert( { libdbusPendingCall, toInsert } );
}
- timeoutMap_.erase(ret.first);
- timeoutMap_.insert( { libdbusPendingCall, toInsert } );
}
- enforceTimeoutMutex_.unlock();
- enforcerThreadMutex_.lock();
+ if(asyncHandler) {
+ delete asyncHandler;
+ }
+
+ std::lock_guard<std::recursive_mutex> enforcerLock(enforcerThreadMutex_);
enforceTimeoutCondition_.notify_one();
- enforcerThreadMutex_.unlock();
} else {
// add asyncHandler with infinite timeout to corresponding list
std::lock_guard<std::mutex> itsLock(timeoutInfiniteAsyncHandlersMutex_);
@@ -928,12 +955,11 @@ void DBusConnection::dispatchDBusMessageReply(const DBusMessage& _reply,
bool DBusConnection::singleDispatch() {
std::list<MainloopTimeout_t> mainloopTimeouts;
{
- mainloopTimeoutsMutex_.lock();
+ std::lock_guard<std::mutex> itsLock(mainloopTimeoutsMutex_);
for (auto t : mainloopTimeouts_) {
mainloopTimeouts.push_back(t);
}
mainloopTimeouts_.clear();
- mainloopTimeoutsMutex_.unlock();
}
for (auto t : mainloopTimeouts) {
@@ -1116,11 +1142,14 @@ DBusProxyConnection::DBusSignalHandlerToken DBusConnection::addSignalMemberHandl
interfaceName,
interfaceMemberName,
interfaceMemberSignature);
- std::lock_guard < std::mutex > dbusSignalLock(signalGuard_);
+
+ std::unique_lock<std::mutex> dbusSignalLock(signalGuard_);
auto signalEntry = dbusSignalHandlerTable_.find(dbusSignalHandlerPath);
const bool isFirstSignalMemberHandler = (signalEntry == dbusSignalHandlerTable_.end());
+
auto itsHandler = dbusSignalHandler.lock();
+
if (itsHandler && isFirstSignalMemberHandler) {
addLibdbusSignalMatchRule(objectPath, interfaceName, interfaceMemberName, justAddFilter);
@@ -1132,9 +1161,31 @@ DBusProxyConnection::DBusSignalHandlerToken DBusConnection::addSignalMemberHandl
std::make_pair(std::make_shared<std::recursive_mutex>(), std::move(handlerList))
} );
} else if (itsHandler && !isFirstSignalMemberHandler) {
- signalEntry->second.first->lock();
- signalEntry->second.second[itsHandler.get()] = dbusSignalHandler;
- signalEntry->second.first->unlock();
+
+ //get mutex for signal entry
+ auto signalEntryMutex = signalEntry->second.first;
+
+ // mutex of signal entry must be locked first to avoid potential deadlock
+ dbusSignalLock.unlock();
+ signalEntryMutex->lock();
+
+ dbusSignalLock.lock();
+ signalEntry = dbusSignalHandlerTable_.find(dbusSignalHandlerPath);
+ if(signalEntry != dbusSignalHandlerTable_.end()) {
+ signalEntry->second.second[itsHandler.get()] = dbusSignalHandler;
+ } else {
+ //is first signal member handler again
+ addLibdbusSignalMatchRule(objectPath, interfaceName, interfaceMemberName, justAddFilter);
+
+ std::map<DBusSignalHandler*, std::weak_ptr<DBusSignalHandler>> handlerList;
+ handlerList[itsHandler.get()] = dbusSignalHandler;
+
+ dbusSignalHandlerTable_.insert( {
+ dbusSignalHandlerPath,
+ std::make_pair(std::make_shared<std::recursive_mutex>(), std::move(handlerList))
+ } );
+ }
+ signalEntryMutex->unlock();
}
return dbusSignalHandlerPath;
@@ -1143,18 +1194,27 @@ DBusProxyConnection::DBusSignalHandlerToken DBusConnection::addSignalMemberHandl
bool DBusConnection::removeSignalMemberHandler(const DBusSignalHandlerToken &dbusSignalHandlerToken,
const DBusSignalHandler* dbusSignalHandler) {
bool lastHandlerRemoved = false;
- std::lock_guard < std::mutex > dbusSignalLock(signalGuard_);
+ std::unique_lock<std::mutex> itsLock(signalGuard_);
auto signalEntry = dbusSignalHandlerTable_.find(dbusSignalHandlerToken);
if (signalEntry != dbusSignalHandlerTable_.end()) {
- signalEntry->second.first->lock();
- auto selectedHandler = signalEntry->second.second.find(const_cast<DBusSignalHandler*>(dbusSignalHandler));
- if (selectedHandler != signalEntry->second.second.end()) {
- signalEntry->second.second.erase(selectedHandler);
- lastHandlerRemoved = (signalEntry->second.second.empty());
+ auto signalEntryMutex = signalEntry->second.first;
+
+ // mutex of signal entry must be locked first to avoid potential deadlock
+ itsLock.unlock();
+ signalEntryMutex->lock();
+
+ itsLock.lock();
+ signalEntry = dbusSignalHandlerTable_.find(dbusSignalHandlerToken);
+ if(signalEntry != dbusSignalHandlerTable_.end()) {
+ auto selectedHandler = signalEntry->second.second.find(const_cast<DBusSignalHandler*>(dbusSignalHandler));
+ if (selectedHandler != signalEntry->second.second.end()) {
+ signalEntry->second.second.erase(selectedHandler);
+ lastHandlerRemoved = (signalEntry->second.second.empty());
+ }
}
- signalEntry->second.first->unlock();
+ signalEntryMutex->unlock();
}
if (lastHandlerRemoved) {
@@ -1571,42 +1631,72 @@ void DBusConnection::initLibdbusSignalFilterAfterConnect() {
return isDBusMessageHandled ? DBUS_HANDLER_RESULT_HANDLED : DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
}
-template<typename DBusSignalHandlersTable>
-void notifyDBusSignalHandlers(DBusSignalHandlersTable& dbusSignalHandlerstable,
- typename DBusSignalHandlersTable::iterator& signalEntry,
- const CommonAPI::DBus::DBusMessage& dbusMessage,
- ::DBusHandlerResult& dbusHandlerResult) {
- if (signalEntry == dbusSignalHandlerstable.end() || signalEntry->second.second.empty()) {
- dbusHandlerResult = DBUS_HANDLER_RESULT_HANDLED;
- return;
+void DBusConnection::notifyDBusSignalHandlers(DBusSignalHandlerPath handlerPath,
+ const DBusMessage& dbusMessage,
+ ::DBusHandlerResult& dbusHandlerResult) {
+
+ // mutex of signal entry must be locked first to avoid potential deadlock
+ DBusSignalHandlerTable::iterator signalEntry;
+ bool entryFound = false;
+ std::shared_ptr<std::recursive_mutex> signalEntryMutex;
+ {
+ std::lock_guard<std::mutex> itsLock(signalGuard_);
+ signalEntry = dbusSignalHandlerTable_.find(handlerPath);
+
+ if(signalEntry != dbusSignalHandlerTable_.end()) {
+ signalEntryMutex = signalEntry->second.first;
+ entryFound = true;
+ }
}
- auto handlerEntry = signalEntry->second.second.begin();
- while (handlerEntry != signalEntry->second.second.end()) {
- std::weak_ptr<DBusProxyConnection::DBusSignalHandler> dbusSignalHandler = handlerEntry->second;
- if(auto itsHandler = dbusSignalHandler.lock())
- itsHandler->onSignalDBusMessage(dbusMessage);
- handlerEntry++;
+ if(entryFound) {
+ signalEntryMutex->lock();
+ std::lock_guard<std::mutex> itsLock(signalGuard_);
+ signalEntry = dbusSignalHandlerTable_.find(handlerPath);
+ }
+
+ // ensure, the registry survives
+ std::shared_ptr<DBusServiceRegistry> itsRegistry_ = DBusServiceRegistry::get(shared_from_this());
+
+ if(entryFound &&
+ signalEntry != dbusSignalHandlerTable_.end() &&
+ !signalEntry->second.second.empty()) {
+
+ // copy signal handlers
+ auto dbusSignalhandlers = signalEntry->second.second;
+ signalEntryMutex->unlock();
+
+ auto handlerEntry = dbusSignalhandlers.begin();
+ while (handlerEntry != dbusSignalhandlers.end()) {
+ std::weak_ptr<DBusProxyConnection::DBusSignalHandler> dbusSignalHandler = handlerEntry->second;
+ if(auto itsHandler = dbusSignalHandler.lock())
+ itsHandler->onSignalDBusMessage(dbusMessage);
+ handlerEntry++;
+ }
}
dbusHandlerResult = DBUS_HANDLER_RESULT_HANDLED;
}
-template<typename DBusSignalHandlersTable>
-void notifyDBusOMSignalHandlers(DBusSignalHandlersTable& dbusSignalHandlerstable,
- std::pair<typename DBusSignalHandlersTable::iterator,
- typename DBusSignalHandlersTable::iterator>& equalRange,
- const CommonAPI::DBus::DBusMessage &dbusMessage,
- ::DBusHandlerResult &dbusHandlerResult) {
- (void)dbusSignalHandlerstable;
+void DBusConnection::notifyDBusOMSignalHandlers(const char* dbusSenderName,
+ const DBusMessage& dbusMessage,
+ ::DBusHandlerResult& dbusHandlerResult) {
+ std::vector<std::weak_ptr<DBusProxyConnection::DBusSignalHandler>> dbusOMSignalHandlers;
+ {
+ std::lock_guard<std::mutex> itsLock(dbusObjectManagerSignalGuard_);
+ auto equalRange = dbusObjectManagerSignalHandlerTable_.equal_range(dbusSenderName);
- if (equalRange.first != equalRange.second) {
- dbusHandlerResult = DBUS_HANDLER_RESULT_HANDLED;
+ if (equalRange.first != equalRange.second) {
+ dbusHandlerResult = DBUS_HANDLER_RESULT_HANDLED;
+ }
+ while (equalRange.first != equalRange.second) {
+ dbusOMSignalHandlers.push_back(equalRange.first->second.second);
+ equalRange.first++;
+ }
}
- while (equalRange.first != equalRange.second) {
- std::weak_ptr<DBusProxyConnection::DBusSignalHandler> dbusSignalHandler = equalRange.first->second.second;
- if(auto itsHandler = dbusSignalHandler.lock())
+
+ for(auto it = dbusOMSignalHandlers.begin(); it != dbusOMSignalHandlers.end(); ++it) {
+ if(auto itsHandler = it->lock())
itsHandler->onSignalDBusMessage(dbusMessage);
- equalRange.first++;
}
}
@@ -1636,40 +1726,23 @@ void notifyDBusOMSignalHandlers(DBusSignalHandlersTable& dbusSignalHandlerstable
DBusMessage dbusMessage(libdbusMessage);
::DBusHandlerResult dbusHandlerResult = DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
- signalGuard_.lock();
- auto signalEntry = dbusSignalHandlerTable_.find(DBusSignalHandlerPath(
- objectPath,
- interfaceName,
- interfaceMemberName,
- interfaceMemberSignature));
-
- if(signalEntry != dbusSignalHandlerTable_.end())
- signalEntry->second.first->lock();
- signalGuard_.unlock();
+ DBusSignalHandlerPath handlerPath = DBusSignalHandlerPath(
+ objectPath,
+ interfaceName,
+ interfaceMemberName,
+ interfaceMemberSignature);
- // ensure, the registry survives
- std::shared_ptr<DBusServiceRegistry> itsRegistry_ = DBusServiceRegistry::get(shared_from_this());
-
- notifyDBusSignalHandlers(dbusSignalHandlerTable_,
- signalEntry, dbusMessage, dbusHandlerResult);
-
- if(signalEntry != dbusSignalHandlerTable_.end())
- signalEntry->second.first->unlock();
+ notifyDBusSignalHandlers(handlerPath, dbusMessage, dbusHandlerResult);
if (dbusMessage.hasInterfaceName("org.freedesktop.DBus.ObjectManager")) {
+
const char* dbusSenderName = dbusMessage.getSender();
if (NULL == dbusSenderName) {
COMMONAPI_ERROR(std::string(__FUNCTION__), " dbusSenderName == NULL");
return DBUS_HANDLER_RESULT_NOT_YET_HANDLED;
}
- dbusObjectManagerSignalGuard_.lock();
- auto dbusObjectManagerSignalHandlerIteratorPair = dbusObjectManagerSignalHandlerTable_.equal_range(dbusSenderName);
- notifyDBusOMSignalHandlers(dbusObjectManagerSignalHandlerTable_,
- dbusObjectManagerSignalHandlerIteratorPair,
- dbusMessage,
- dbusHandlerResult);
- dbusObjectManagerSignalGuard_.unlock();
+ notifyDBusOMSignalHandlers(dbusSenderName, dbusMessage, dbusHandlerResult);
}
return dbusHandlerResult;
@@ -1756,5 +1829,20 @@ void DBusConnection::setPendingCallTimedOut(DBusPendingCall* _pendingCall, ::DBu
}
}
+void DBusConnection::deleteAsyncHandlers() {
+ std::vector<DBusMessageReplyAsyncHandler*> asyncHandlers;
+ {
+ std::lock_guard<std::mutex> asyncHandlersLock(asyncHandlersToDeleteMutex_);
+ asyncHandlers = asyncHandlersToDelete_;
+ asyncHandlersToDelete_.clear();
+ }
+
+ auto it = asyncHandlers.begin();
+ while(it != asyncHandlers.end()) {
+ delete *it;
+ it = asyncHandlers.erase(it);
+ }
+}
+
} // namespace DBus
} // namespace CommonAPI
diff --git a/src/CommonAPI/DBus/DBusDaemonProxy.cpp b/src/CommonAPI/DBus/DBusDaemonProxy.cpp
index 3b5b29f..7c2ce50 100644
--- a/src/CommonAPI/DBus/DBusDaemonProxy.cpp
+++ b/src/CommonAPI/DBus/DBusDaemonProxy.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusError.cpp b/src/CommonAPI/DBus/DBusError.cpp
index 884f23b..4b51318 100644
--- a/src/CommonAPI/DBus/DBusError.cpp
+++ b/src/CommonAPI/DBus/DBusError.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusFactory.cpp b/src/CommonAPI/DBus/DBusFactory.cpp
index 31a44c4..99f7e8e 100644
--- a/src/CommonAPI/DBus/DBusFactory.cpp
+++ b/src/CommonAPI/DBus/DBusFactory.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -17,19 +17,19 @@
namespace CommonAPI {
namespace DBus {
-static std::weak_ptr<CommonAPI::Runtime> runtime__;
-
INITIALIZER(FactoryInit) {
- runtime__ = Runtime::get();
- Runtime::get()->registerFactory("dbus", Factory::get());
+ Factory::runtime_ = Runtime::get();
+ Factory::runtime_.lock()->registerFactory("dbus", Factory::get());
}
DEINITIALIZER(FactoryDeinit) {
- if (auto rt = runtime__.lock()) {
+ if (auto rt = Factory::runtime_.lock()) {
rt->unregisterFactory("dbus");
}
}
+std::weak_ptr<CommonAPI::Runtime> Factory::runtime_;
+
std::shared_ptr<CommonAPI::DBus::Factory>
Factory::get() {
static std::shared_ptr<Factory> theFactory = std::make_shared<Factory>();
@@ -44,7 +44,7 @@ Factory::~Factory() {
void
Factory::init() {
-#ifndef WIN32
+#ifndef _WIN32
std::lock_guard<std::mutex> itsLock(initializerMutex_);
#endif
if (!isInitialized_) {
@@ -56,7 +56,7 @@ Factory::init() {
void
Factory::registerInterface(InterfaceInitFunction _function) {
-#ifndef WIN32
+#ifndef _WIN32
std::lock_guard<std::mutex> itsLock(initializerMutex_);
#endif
if (isInitialized_) {
diff --git a/src/CommonAPI/DBus/DBusFreedesktopPropertiesStub.cpp b/src/CommonAPI/DBus/DBusFreedesktopPropertiesStub.cpp
index f41b77e..d9c950f 100644
--- a/src/CommonAPI/DBus/DBusFreedesktopPropertiesStub.cpp
+++ b/src/CommonAPI/DBus/DBusFreedesktopPropertiesStub.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusFunctionalHash.cpp b/src/CommonAPI/DBus/DBusFunctionalHash.cpp
index 5e11bfc..c02150a 100644
--- a/src/CommonAPI/DBus/DBusFunctionalHash.cpp
+++ b/src/CommonAPI/DBus/DBusFunctionalHash.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusInputStream.cpp b/src/CommonAPI/DBus/DBusInputStream.cpp
index 0c838a0..c13353e 100644
--- a/src/CommonAPI/DBus/DBusInputStream.cpp
+++ b/src/CommonAPI/DBus/DBusInputStream.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.cpp b/src/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.cpp
index a8d538d..8b88753 100644
--- a/src/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.cpp
+++ b/src/CommonAPI/DBus/DBusInstanceAvailabilityStatusChangedEvent.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusMainLoop.cpp b/src/CommonAPI/DBus/DBusMainLoop.cpp
index 5bf27a2..6b3d5e6 100755
--- a/src/CommonAPI/DBus/DBusMainLoop.cpp
+++ b/src/CommonAPI/DBus/DBusMainLoop.cpp
@@ -1,9 +1,9 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
-#ifdef WIN32
+#ifdef _WIN32
#include <WinSock2.h>
#include <ws2tcpip.h>
#include <atomic>
@@ -28,7 +28,7 @@ DBusMainLoop::DBusMainLoop(std::shared_ptr<MainLoopContext> context)
currentMinimalTimeoutInterval_(TIMEOUT_INFINITE),
hasToStop_(false),
isBroken_(false) {
-#ifdef WIN32
+#ifdef _WIN32
WSADATA wsaData;
int iResult;
@@ -188,7 +188,7 @@ DBusMainLoop::~DBusMainLoop() {
context_->unsubscribeForTimeouts(timeoutSourceListenerSubscription_);
context_->unsubscribeForWakeupEvents(wakeupListenerSubscription_);
-#ifdef WIN32
+#ifdef _WIN32
// shutdown the connection since no more data will be sent
int iResult = shutdown(wakeFd_.fd, SD_SEND);
if (iResult == SOCKET_ERROR) {
@@ -403,20 +403,44 @@ bool DBusMainLoop::prepare(const int64_t& timeout) {
}
void DBusMainLoop::poll() {
- int managedFileDescriptorOffset = 0;
+
+ // copy file descriptors
+ std::vector<DBusMainLoopPollFd> fileDescriptors;
{
std::lock_guard<std::mutex> itsLock(fileDescriptorsMutex_);
- for (auto fileDescriptor = managedFileDescriptors_.begin() + managedFileDescriptorOffset; fileDescriptor != managedFileDescriptors_.end(); ++fileDescriptor) {
+ for (auto fileDescriptor = managedFileDescriptors_.begin();
+ fileDescriptor != managedFileDescriptors_.end();
+ ++fileDescriptor) {
(*fileDescriptor).revents = 0;
+ fileDescriptors.push_back(*fileDescriptor);
}
}
-#ifdef WIN32
- int numReadyFileDescriptors = WSAPoll(&managedFileDescriptors_[0], managedFileDescriptors_.size(), int(currentMinimalTimeoutInterval_));
+#ifdef _WIN32
+ int numReadyFileDescriptors = WSAPoll(&fileDescriptors[0], fileDescriptors.size(), int(currentMinimalTimeoutInterval_));
#else
- int numReadyFileDescriptors = ::poll(&(managedFileDescriptors_[0]),
- managedFileDescriptors_.size(), int(currentMinimalTimeoutInterval_));
+ int numReadyFileDescriptors = ::poll(&(fileDescriptors[0]),
+ fileDescriptors.size(), int(currentMinimalTimeoutInterval_));
#endif
+
+ // update file descriptors
+ {
+ std::lock_guard<std::mutex> itsLock(fileDescriptorsMutex_);
+ for (auto itFds = fileDescriptors.begin();
+ itFds != fileDescriptors.end();
+ itFds++) {
+ for(auto itManagedFds = managedFileDescriptors_.begin();
+ itManagedFds != managedFileDescriptors_.end();
+ ++itManagedFds) {
+ if((*itFds).fd == (*itManagedFds).fd &&
+ (*itFds).events == (*itManagedFds).events) {
+ (*itManagedFds).revents = (*itFds).revents;
+ continue;
+ }
+ }
+ }
+ }
+
if (!numReadyFileDescriptors) {
int64_t currentContextTime = getCurrentTimeInMs();
@@ -449,6 +473,7 @@ void DBusMainLoop::poll() {
}
// If the wakeup descriptor woke us up, we must acknowledge
+ std::lock_guard<std::mutex> itsLock(fileDescriptorsMutex_);
if (managedFileDescriptors_[0].revents) {
wakeupAck();
}
@@ -564,7 +589,7 @@ void DBusMainLoop::dispatch() {
}
void DBusMainLoop::wakeup() {
-#ifdef WIN32
+#ifdef _WIN32
// Send an initial buffer
char *sendbuf = "1";
@@ -585,7 +610,7 @@ void DBusMainLoop::wakeup() {
}
void DBusMainLoop::wakeupAck() {
-#ifdef WIN32
+#ifdef _WIN32
// Receive until the peer closes the connection
int iResult;
char recvbuf[DEFAULT_BUFLEN];
@@ -704,7 +729,7 @@ void DBusMainLoop::registerWatch(Watch* watch,
std::lock_guard<std::mutex> itsLock(watchesMutex_);
std::mutex* mtx = new std::mutex;
-#ifdef WIN32
+#ifdef _WIN32
std::atomic_signal_fence(std::memory_order_acq_rel);
#else
asm volatile ("":::"memory");
diff --git a/src/CommonAPI/DBus/DBusMainLoopContext.cpp b/src/CommonAPI/DBus/DBusMainLoopContext.cpp
index 3124027..c44c16d 100644
--- a/src/CommonAPI/DBus/DBusMainLoopContext.cpp
+++ b/src/CommonAPI/DBus/DBusMainLoopContext.cpp
@@ -1,9 +1,9 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
-#ifdef WIN32
+#ifdef _WIN32
#include <WinSock2.h>
#include <ws2tcpip.h>
#else
@@ -48,25 +48,20 @@ DBusQueueDispatchSource::DBusQueueDispatchSource(DBusQueueWatch* watch) :
}
DBusQueueDispatchSource::~DBusQueueDispatchSource() {
- std::unique_lock<std::mutex> itsLock(watchMutex_);
watch_->removeDependentDispatchSource(this);
}
bool DBusQueueDispatchSource::prepare(int64_t& timeout) {
- std::unique_lock<std::mutex> itsLock(watchMutex_);
timeout = -1;
return !watch_->emptyQueue();
}
bool DBusQueueDispatchSource::check() {
- std::unique_lock<std::mutex> itsLock(watchMutex_);
return !watch_->emptyQueue();
}
bool DBusQueueDispatchSource::dispatch() {
- std::unique_lock<std::mutex> itsLock(watchMutex_);
- if (!watch_->emptyQueue()) {
- auto queueEntry = watch_->frontQueue();
+ if (auto queueEntry = watch_->frontQueue()) {
watch_->popQueue();
watch_->processQueueEntry(queueEntry);
}
@@ -101,7 +96,7 @@ void DBusWatch::startWatching() {
pollFlags |= POLLOUT;
}
-#ifdef WIN32
+#ifdef _WIN32
pollFileDescriptor_.fd = dbus_watch_get_socket(libdbusWatch_);
wsaEvent_ = WSACreateEvent();
WSAEventSelect(pollFileDescriptor_.fd, wsaEvent_, FD_READ);
@@ -131,14 +126,14 @@ const pollfd& DBusWatch::getAssociatedFileDescriptor() {
return pollFileDescriptor_;
}
-#ifdef WIN32
+#ifdef _WIN32
const HANDLE& DBusWatch::getAssociatedEvent() {
return wsaEvent_;
}
#endif
void DBusWatch::dispatch(unsigned int eventFlags) {
-#ifdef WIN32
+#ifdef _WIN32
unsigned int dbusWatchFlags = 0;
if (eventFlags & (POLLRDBAND | POLLRDNORM)) {
@@ -173,15 +168,17 @@ void DBusWatch::dispatch(unsigned int eventFlags) {
}
const std::vector<DispatchSource*>& DBusWatch::getDependentDispatchSources() {
+ std::lock_guard<std::mutex> itsLock(dependentDispatchSourcesMutex_);
return dependentDispatchSources_;
}
void DBusWatch::addDependentDispatchSource(DispatchSource* dispatchSource) {
+ std::lock_guard<std::mutex> itsLock(dependentDispatchSourcesMutex_);
dependentDispatchSources_.push_back(dispatchSource);
}
DBusQueueWatch::DBusQueueWatch(std::shared_ptr<DBusConnection> _connection) : pipeValue_(4) {
-#ifdef WIN32
+#ifdef _WIN32
WSADATA wsaData;
int iResult;
@@ -316,7 +313,7 @@ DBusQueueWatch::DBusQueueWatch(std::shared_ptr<DBusConnection> _connection) : pi
}
DBusQueueWatch::~DBusQueueWatch() {
-#ifdef WIN32
+#ifdef _WIN32
// shutdown the connection since no more data will be sent
int iResult = shutdown(pipeFileDescriptors_[0], SD_SEND);
if (iResult == SOCKET_ERROR) {
@@ -348,21 +345,24 @@ const pollfd& DBusQueueWatch::getAssociatedFileDescriptor() {
return pollFileDescriptor_;
}
-#ifdef WIN32
+#ifdef _WIN32
const HANDLE& DBusQueueWatch::getAssociatedEvent() {
return wsaEvent_;
}
#endif
const std::vector<DispatchSource*>& DBusQueueWatch::getDependentDispatchSources() {
+ std::lock_guard<std::mutex> itsLock(dependentDispatchSourcesMutex_);
return dependentDispatchSources_;
}
void DBusQueueWatch::addDependentDispatchSource(CommonAPI::DispatchSource* _dispatchSource) {
+ std::lock_guard<std::mutex> itsLock(dependentDispatchSourcesMutex_);
dependentDispatchSources_.push_back(_dispatchSource);
}
void DBusQueueWatch::removeDependentDispatchSource(CommonAPI::DispatchSource* _dispatchSource) {
+ std::lock_guard<std::mutex> itsLock(dependentDispatchSourcesMutex_);
std::vector<CommonAPI::DispatchSource*>::iterator it;
for (it = dependentDispatchSources_.begin(); it != dependentDispatchSources_.end(); it++) {
@@ -377,7 +377,7 @@ void DBusQueueWatch::pushQueue(std::shared_ptr<QueueEntry> _queueEntry) {
std::unique_lock<std::mutex> itsLock(queueMutex_);
queue_.push(_queueEntry);
-#ifdef WIN32
+#ifdef _WIN32
// Send an initial buffer
char *sendbuf = "1";
@@ -399,7 +399,7 @@ void DBusQueueWatch::pushQueue(std::shared_ptr<QueueEntry> _queueEntry) {
void DBusQueueWatch::popQueue() {
std::unique_lock<std::mutex> itsLock(queueMutex_);
-#ifdef WIN32
+#ifdef _WIN32
// Receive until the peer closes the connection
int iResult;
char recvbuf[1];
@@ -428,7 +428,11 @@ void DBusQueueWatch::popQueue() {
std::shared_ptr<QueueEntry> DBusQueueWatch::frontQueue() {
std::unique_lock<std::mutex> itsLock(queueMutex_);
- return queue_.front();
+ if(queue_.empty()) {
+ return NULL;
+ } else {
+ return queue_.front();
+ }
}
bool DBusQueueWatch::emptyQueue() {
@@ -444,7 +448,7 @@ void DBusQueueWatch::processQueueEntry(std::shared_ptr<QueueEntry> _queueEntry)
}
}
-#ifdef WIN32
+#ifdef _WIN32
__declspec(thread) DBusTimeout* DBusTimeout::currentTimeout_ = NULL;
#else
thread_local DBusTimeout* DBusTimeout::currentTimeout_ = NULL;
diff --git a/src/CommonAPI/DBus/DBusMessage.cpp b/src/CommonAPI/DBus/DBusMessage.cpp
index 927624c..9321315 100644
--- a/src/CommonAPI/DBus/DBusMessage.cpp
+++ b/src/CommonAPI/DBus/DBusMessage.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusObjectManager.cpp b/src/CommonAPI/DBus/DBusObjectManager.cpp
index c9484fd..85fdbf4 100644
--- a/src/CommonAPI/DBus/DBusObjectManager.cpp
+++ b/src/CommonAPI/DBus/DBusObjectManager.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusObjectManagerStub.cpp b/src/CommonAPI/DBus/DBusObjectManagerStub.cpp
index 20bbf1d..226c825 100644
--- a/src/CommonAPI/DBus/DBusObjectManagerStub.cpp
+++ b/src/CommonAPI/DBus/DBusObjectManagerStub.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusOutputStream.cpp b/src/CommonAPI/DBus/DBusOutputStream.cpp
index 564aa61..ae42e36 100644
--- a/src/CommonAPI/DBus/DBusOutputStream.cpp
+++ b/src/CommonAPI/DBus/DBusOutputStream.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusProxy.cpp b/src/CommonAPI/DBus/DBusProxy.cpp
index 2d19670..ef6388b 100644
--- a/src/CommonAPI/DBus/DBusProxy.cpp
+++ b/src/CommonAPI/DBus/DBusProxy.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -93,7 +93,6 @@ void DBusProxy::availabilityTimeoutThreadHandler() const {
if (now > std::get<0>(*it)) {
//timeout
- availabilityMutex_.lock();
std::chrono::steady_clock::time_point timepoint_;
if(isAvailable())
callbacks.push_back(std::make_tuple(callback, std::move(std::get<2>(*it)),
@@ -104,10 +103,8 @@ void DBusProxy::availabilityTimeoutThreadHandler() const {
AvailabilityStatus::NOT_AVAILABLE,
timepoint_));
it = timeouts_.erase(it);
- availabilityMutex_.unlock();
} else {
//timeout not expired
- availabilityMutex_.lock();
if(isAvailable()) {
callbacks.push_back(std::make_tuple(callback, std::move(std::get<2>(*it)),
AvailabilityStatus::AVAILABLE,
@@ -116,7 +113,6 @@ void DBusProxy::availabilityTimeoutThreadHandler() const {
} else {
++it;
}
- availabilityMutex_.unlock();
}
}
@@ -134,7 +130,6 @@ void DBusProxy::availabilityTimeoutThreadHandler() const {
while (it != timeouts_.end()) {
isAvailableAsyncCallback callback = std::get<1>(*it);
- availabilityMutex_.lock();
if(isAvailable()) {
callbacks.push_back(std::make_tuple(callback, std::move(std::get<2>(*it)),
AvailabilityStatus::AVAILABLE,
@@ -143,7 +138,6 @@ void DBusProxy::availabilityTimeoutThreadHandler() const {
} else {
++it;
}
- availabilityMutex_.unlock();
}
timeoutsMutex_.unlock();
@@ -214,6 +208,7 @@ DBusProxy::~DBusProxy() {
}
bool DBusProxy::isAvailable() const {
+ std::lock_guard<std::mutex>itsLock(availabilityMutex_);
return (availabilityStatus_ == AvailabilityStatus::AVAILABLE);
}
@@ -221,7 +216,7 @@ bool DBusProxy::isAvailableBlocking() const {
std::unique_lock<std::mutex> lock(availabilityMutex_);
if(!getDBusConnection()->hasDispatchThread()) {
- return isAvailable();
+ return (availabilityStatus_ == AvailabilityStatus::AVAILABLE);
}
while (availabilityStatus_ != AvailabilityStatus::AVAILABLE) {
diff --git a/src/CommonAPI/DBus/DBusProxyBase.cpp b/src/CommonAPI/DBus/DBusProxyBase.cpp
index 3052f9e..d24e58b 100644
--- a/src/CommonAPI/DBus/DBusProxyBase.cpp
+++ b/src/CommonAPI/DBus/DBusProxyBase.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusProxyManager.cpp b/src/CommonAPI/DBus/DBusProxyManager.cpp
index cedd58b..a522bf4 100644
--- a/src/CommonAPI/DBus/DBusProxyManager.cpp
+++ b/src/CommonAPI/DBus/DBusProxyManager.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/CommonAPI/DBus/DBusServiceRegistry.cpp b/src/CommonAPI/DBus/DBusServiceRegistry.cpp
index 7ad5987..4ef9fbc 100644
--- a/src/CommonAPI/DBus/DBusServiceRegistry.cpp
+++ b/src/CommonAPI/DBus/DBusServiceRegistry.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
@@ -22,7 +22,7 @@ static CommonAPI::CallInfo serviceRegistryInfo(10000);
std::shared_ptr<DBusServiceRegistry>
DBusServiceRegistry::get(std::shared_ptr<DBusProxyConnection> _connection) {
- std::lock_guard<std::mutex> itsGuard(registriesMutex_);
+ std::unique_lock<std::mutex> itsGuard(registriesMutex_);
auto registries = getRegistryMap();
auto registryIterator = registries->find(_connection);
if (registryIterator != registries->end())
@@ -31,8 +31,9 @@ DBusServiceRegistry::get(std::shared_ptr<DBusProxyConnection> _connection) {
std::shared_ptr<DBusServiceRegistry> registry
= std::make_shared<DBusServiceRegistry>(_connection);
if (registry) {
- registry->init();
registries->insert( { _connection, registry } );
+ itsGuard.unlock();
+ registry->init();
}
return registry;
}
@@ -108,13 +109,13 @@ DBusServiceRegistry::subscribeAvailabilityListener(
DBusAddress dbusAddress;
translator_->translate(_address, dbusAddress);
+ dbusServicesMutex_.lock();
if (notificationThread_ == std::this_thread::get_id()) {
COMMONAPI_ERROR(
"You must not build proxies in callbacks of ProxyStatusEvent.",
" Please refer to the documentation for suggestions how to avoid this.");
}
- dbusServicesMutex_.lock();
auto& dbusServiceListenersRecord = dbusServiceListenersMap[dbusAddress.getService()];
if (dbusServiceListenersRecord.uniqueBusNameState == DBusRecordState::AVAILABLE) {
COMMONAPI_ERROR(std::string(__FUNCTION__), " uniqueBusName ", dbusServiceListenersRecord.uniqueBusName, " already AVAILABLE");
@@ -610,15 +611,6 @@ DBusServiceRegistry::getDBusObjectPathCacheReference(
DBusUniqueNameRecord& dbusUniqueNameRecord) {
const bool isFirstDBusObjectPathCache = dbusUniqueNameRecord.dbusObjectPathsCache.empty();
- auto dbusObjectPathCacheIterator = dbusUniqueNameRecord.dbusObjectPathsCache.find(dbusObjectPath);
- if(dbusObjectPathCacheIterator == dbusUniqueNameRecord.dbusObjectPathsCache.end()) {
- DBusObjectPathCache objectPathCache;
- objectPathCache.serviceName = dbusServiceName;
- std::unordered_map<std::string, DBusObjectPathCache>::value_type value (dbusObjectPath, std::move(objectPathCache));
- dbusUniqueNameRecord.dbusObjectPathsCache.insert(std::move(value));
- dbusObjectPathCacheIterator = dbusUniqueNameRecord.dbusObjectPathsCache.find(dbusObjectPath);
- }
-
if (isFirstDBusObjectPathCache) {
auto dbusProxyConnection = dbusDaemonProxy_->getDBusConnection();
const bool isSubscriptionSuccessful = dbusProxyConnection->addObjectManagerSignalMemberHandler(
@@ -629,6 +621,15 @@ DBusServiceRegistry::getDBusObjectPathCacheReference(
}
}
+ auto dbusObjectPathCacheIterator = dbusUniqueNameRecord.dbusObjectPathsCache.find(dbusObjectPath);
+ if(dbusObjectPathCacheIterator == dbusUniqueNameRecord.dbusObjectPathsCache.end()) {
+ DBusObjectPathCache objectPathCache;
+ objectPathCache.serviceName = dbusServiceName;
+ std::unordered_map<std::string, DBusObjectPathCache>::value_type value (dbusObjectPath, std::move(objectPathCache));
+ dbusUniqueNameRecord.dbusObjectPathsCache.insert(std::move(value));
+ dbusObjectPathCacheIterator = dbusUniqueNameRecord.dbusObjectPathsCache.find(dbusObjectPath);
+ }
+
if (dbusObjectPathCacheIterator->second.state == DBusRecordState::UNKNOWN
&& resolveObjectPathWithObjectManager(dbusServiceUniqueName, dbusObjectPath)) {
dbusObjectPathCacheIterator->second.state = DBusRecordState::RESOLVING;
@@ -677,7 +678,6 @@ void DBusServiceRegistry::releaseDBusObjectPathCacheReference(const std::string&
const bool isLastDBusObjectPathCache = dbusUniqueNameRecord.dbusObjectPathsCache.empty();
if (isLastDBusObjectPathCache) {
- dbusServicesMutex_.unlock();
auto dbusProxyConnection = dbusDaemonProxy_->getDBusConnection();
const bool isSubscriptionCancelled = dbusProxyConnection->removeObjectManagerSignalMemberHandler(
dbusServiceListenersRecord.uniqueBusName,
@@ -685,7 +685,6 @@ void DBusServiceRegistry::releaseDBusObjectPathCacheReference(const std::string&
if (!isSubscriptionCancelled) {
COMMONAPI_ERROR(std::string(__FUNCTION__), ": still subscribed too ", dbusServiceListenersRecord.uniqueBusName);
}
- dbusServicesMutex_.lock();
}
}
}
@@ -778,9 +777,9 @@ void DBusServiceRegistry::onGetManagedObjectsCallbackResolve(const CallStatus& c
const std::string& dbusServiceUniqueName,
const std::string& dbusObjectPath) {
+ dbusServicesMutex_.lock();
if(callStatus == CallStatus::SUCCESS) {
//has object manager
- bool objectPathFound = false;
for(auto objectPathDict : availableServiceInstances)
{
std::string objectPath = objectPathDict.first;
@@ -788,38 +787,36 @@ void DBusServiceRegistry::onGetManagedObjectsCallbackResolve(const CallStatus& c
continue;
// object path that should be resolved is found --> resolve
- objectPathFound = true;
CommonAPI::DBus::DBusObjectManagerStub::DBusInterfacesAndPropertiesDict interfacesAndPropertiesDict = objectPathDict.second;
for(auto interfaceDict : interfacesAndPropertiesDict)
{
std::string interfaceName = interfaceDict.first;
- dbusServicesMutex_.lock();
processManagedObject(dbusObjectPath, dbusServiceUniqueName, interfaceName);
- dbusServicesMutex_.unlock();
}
}
- if(!objectPathFound) {
+ // resolve further interfaces with the help of the manager
+ bool managerFound = false;
+ std::string objectPathManager = dbusObjectPath.substr(0, dbusObjectPath.find_last_of("\\/"));
+ for(auto objectPathDict : availableServiceInstances)
+ {
+
// check if the main part of the object path is in the list.
// if it is, the object path could be managed.
// else, it maybe existed a while back but is now gone, in which case just ignore.
+ std::string objectPath = objectPathDict.first;
+ if (dbusObjectPath.substr(0, objectPath.size()) != objectPath)
+ continue;
- std::string objectPathManager = dbusObjectPath.substr(0, dbusObjectPath.find_last_of("\\/"));
- for(auto objectPathDict : availableServiceInstances)
- {
-
- std::string objectPath = objectPathDict.first;
-
- if (dbusObjectPath.substr(0, objectPath.size()) != objectPath)
- continue;
-
- // also check that the next character in dbusObject path is a slash or a backslash,
- // so that we can make sure that we have compared against a full path element
+ // also check that the next character in dbusObject path is a slash or a backslash,
+ // so that we can make sure that we have compared against a full path element
+ if(dbusObjectPath != objectPath) {
auto delimiter = dbusObjectPath.at(objectPath.size());
if (delimiter != '\\' && delimiter != '/')
continue;
- // object path is managed. Try to resolve object path with the help of the manager
+ managerFound = true;
+
auto getManagedObjectsCallback = std::bind(
&DBusServiceRegistry::onGetManagedObjectsCallbackResolve,
shared_from_this(),
@@ -828,13 +825,41 @@ void DBusServiceRegistry::onGetManagedObjectsCallbackResolve(const CallStatus& c
dbusServiceUniqueName,
dbusObjectPath);
getManagedObjectsAsync(dbusServiceUniqueName, objectPathManager, getManagedObjectsCallback);
+ }
+ }
+
+ if(!managerFound) {
+ //mark object path as resolved
+ auto dbusServiceUniqueNameIterator = dbusUniqueNamesMap_.find(dbusServiceUniqueName);
+ const bool isDBusServiceUniqueNameFound = (dbusServiceUniqueNameIterator != dbusUniqueNamesMap_.end());
+
+ if (!isDBusServiceUniqueNameFound) {
+ dbusServicesMutex_.unlock();
+ return;
+ }
+
+ DBusUniqueNameRecord& dbusUniqueNameRecord = dbusServiceUniqueNameIterator->second;
+ auto dbusObjectPathIterator = dbusUniqueNameRecord.dbusObjectPathsCache.find(dbusObjectPath);
+ const bool isDBusObjectPathFound = (dbusObjectPathIterator != dbusUniqueNameRecord.dbusObjectPathsCache.end());
+
+ if (!isDBusObjectPathFound) {
+ dbusServicesMutex_.unlock();
+ return;
}
+ DBusObjectPathCache& dbusObjectPathRecord = dbusObjectPathIterator->second;
+
+ dbusObjectPathRecord.state = DBusRecordState::RESOLVED;
+ if(dbusObjectPathRecord.futureOnResolve.valid())
+ dbusObjectPathRecord.promiseOnResolve.set_value(dbusObjectPathRecord.state);
+
+ dbusUniqueNameRecord.objectPathsState = DBusRecordState::RESOLVED;
}
} else {
COMMONAPI_ERROR("There is no Object Manager that manages " + dbusObjectPath + ". Resolving failed!");
}
+ dbusServicesMutex_.unlock();
}
void DBusServiceRegistry::processManagedObject(const std::string& dbusObjectPath,
@@ -862,12 +887,6 @@ void DBusServiceRegistry::processManagedObject(const std::string& dbusObjectPath
dbusObjectPathRecord.dbusInterfaceNamesCache.insert(interfaceName);
}
- dbusObjectPathRecord.state = DBusRecordState::RESOLVED;
- if(dbusObjectPathRecord.futureOnResolve.valid())
- dbusObjectPathRecord.promiseOnResolve.set_value(dbusObjectPathRecord.state);
-
- dbusUniqueNameRecord.objectPathsState = DBusRecordState::RESOLVED;
-
notifyDBusServiceListeners(
dbusUniqueNameRecord,
dbusObjectPath,
@@ -981,7 +1000,19 @@ void DBusServiceRegistry::onDBusServiceNotAvailable(DBusServiceListenersRecord&
for (auto dbusObjectPathListenersIterator = dbusServiceListenersRecord.dbusObjectPathListenersMap.begin();
dbusObjectPathListenersIterator != dbusServiceListenersRecord.dbusObjectPathListenersMap.end(); ) {
auto& dbusInterfaceNameListenersMap = dbusObjectPathListenersIterator->second;
- notifyDBusObjectPathResolved(dbusInterfaceNameListenersMap, dbusInterfaceNamesCache);
+
+ for (auto dbusInterfaceNameListenersIterator = dbusInterfaceNameListenersMap.begin();
+ dbusInterfaceNameListenersIterator != dbusInterfaceNameListenersMap.end();) {
+ auto& dbusInterfaceNameListenersRecord = dbusInterfaceNameListenersIterator->second;
+
+ notifyDBusInterfaceNameListeners(dbusInterfaceNameListenersRecord, false);
+
+ if (dbusInterfaceNameListenersRecord.listenerList.empty()) {
+ dbusInterfaceNameListenersIterator = dbusInterfaceNameListenersMap.erase(dbusInterfaceNameListenersIterator);
+ } else {
+ dbusInterfaceNameListenersIterator++;
+ }
+ }
if (dbusInterfaceNameListenersMap.empty()) {
dbusObjectPathListenersIterator = dbusServiceListenersRecord.dbusObjectPathListenersMap.erase(
@@ -1036,19 +1067,21 @@ void DBusServiceRegistry::notifyDBusServiceListeners(const DBusUniqueNameRecord&
void DBusServiceRegistry::notifyDBusObjectPathResolved(DBusInterfaceNameListenersMap& dbusInterfaceNameListenersMap,
const std::unordered_set<std::string>& dbusInterfaceNames) {
- for (auto dbusObjectPathListenersIterator = dbusInterfaceNameListenersMap.begin();
- dbusObjectPathListenersIterator != dbusInterfaceNameListenersMap.end();) {
- const auto& listenersDBusInterfaceName = dbusObjectPathListenersIterator->first;
- auto& dbusInterfaceNameListenersRecord = dbusObjectPathListenersIterator->second;
+ for (auto dbusInterfaceNameListenersIterator = dbusInterfaceNameListenersMap.begin();
+ dbusInterfaceNameListenersIterator != dbusInterfaceNameListenersMap.end();) {
+ const auto& listenersDBusInterfaceName = dbusInterfaceNameListenersIterator->first;
+ auto& dbusInterfaceNameListenersRecord = dbusInterfaceNameListenersIterator->second;
const auto& dbusInterfaceNameIterator = dbusInterfaceNames.find(listenersDBusInterfaceName);
- const bool isDBusInterfaceNameAvailable = (dbusInterfaceNameIterator != dbusInterfaceNames.end());
- notifyDBusInterfaceNameListeners(dbusInterfaceNameListenersRecord, isDBusInterfaceNameAvailable);
+
+ if(dbusInterfaceNameIterator != dbusInterfaceNames.end()) {
+ notifyDBusInterfaceNameListeners(dbusInterfaceNameListenersRecord, true);
+ }
if (dbusInterfaceNameListenersRecord.listenerList.empty()) {
- dbusObjectPathListenersIterator = dbusInterfaceNameListenersMap.erase(dbusObjectPathListenersIterator);
+ dbusInterfaceNameListenersIterator = dbusInterfaceNameListenersMap.erase(dbusInterfaceNameListenersIterator);
} else {
- dbusObjectPathListenersIterator++;
+ dbusInterfaceNameListenersIterator++;
}
}
}
@@ -1100,8 +1133,9 @@ void DBusServiceRegistry::notifyDBusInterfaceNameListeners(DBusInterfaceNameList
dbusInterfaceNameListenersRecord.listenersToRemove.remove(dbusServiceListenerIterator->first);
dbusServiceListenerIterator = dbusInterfaceNameListenersRecord.listenerList.erase(dbusServiceListenerIterator);
} else {
- if(auto itsProxy = dbusServiceListenerIterator->second->proxy.lock())
+ if(auto itsProxy = dbusServiceListenerIterator->second->proxy.lock()) {
(dbusServiceListenerIterator->second->listener)(itsProxy, availabilityStatus);
+ }
++dbusServiceListenerIterator;
}
}
@@ -1119,14 +1153,12 @@ void DBusServiceRegistry::removeUniqueName(const DBusUniqueNamesMapIterator& dbu
if (dbusUniqueNamesIterator->second.ownedBusNames.size() == 0) {
std::string dbusUniqueName = dbusUniqueNamesIterator->first;
dbusUniqueNamesMap_.erase(dbusUniqueNamesIterator);
- dbusServicesMutex_.unlock();
const bool isSubscriptionCancelled = dbusDaemonProxy_->getDBusConnection()->removeObjectManagerSignalMemberHandler(
dbusUniqueName,
this);
if (!isSubscriptionCancelled) {
COMMONAPI_ERROR(std::string(__FUNCTION__), ": still subscribed too ", dbusUniqueName);
}
- dbusServicesMutex_.lock();
} else {
//delete object path cache entry of service
auto& dbusObjectPathsCache = dbusUniqueNamesIterator->second.dbusObjectPathsCache;
diff --git a/src/CommonAPI/DBus/DBusStubAdapter.cpp b/src/CommonAPI/DBus/DBusStubAdapter.cpp
index 0f86cc1..44ed866 100644
--- a/src/CommonAPI/DBus/DBusStubAdapter.cpp
+++ b/src/CommonAPI/DBus/DBusStubAdapter.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/CMakeLists.txt b/src/test/CMakeLists.txt
index be5aa1e..5ae19c9 100644
--- a/src/test/CMakeLists.txt
+++ b/src/test/CMakeLists.txt
@@ -1,4 +1,4 @@
-# Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+# Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/DBusClientIdTest.cpp b/src/test/DBusClientIdTest.cpp
index 1a75943..d94a4aa 100644
--- a/src/test/DBusClientIdTest.cpp
+++ b/src/test/DBusClientIdTest.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/DBusConnectionTest.cpp b/src/test/DBusConnectionTest.cpp
index 1e999f3..5f66707 100644
--- a/src/test/DBusConnectionTest.cpp
+++ b/src/test/DBusConnectionTest.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/DBusDaemonProxyTest.cpp b/src/test/DBusDaemonProxyTest.cpp
index b2a4364..4bb9d80 100644
--- a/src/test/DBusDaemonProxyTest.cpp
+++ b/src/test/DBusDaemonProxyTest.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/DBusStubAdapterTest.cpp b/src/test/DBusStubAdapterTest.cpp
index 5c1d742..387aec9 100644
--- a/src/test/DBusStubAdapterTest.cpp
+++ b/src/test/DBusStubAdapterTest.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/DBusVariantOutputStreamTest.cpp b/src/test/DBusVariantOutputStreamTest.cpp
index b23e12f..b68f3ac 100644
--- a/src/test/DBusVariantOutputStreamTest.cpp
+++ b/src/test/DBusVariantOutputStreamTest.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.
diff --git a/src/test/DBusVariantTest.cpp b/src/test/DBusVariantTest.cpp
index b2b4b8b..88800cb 100644
--- a/src/test/DBusVariantTest.cpp
+++ b/src/test/DBusVariantTest.cpp
@@ -1,4 +1,4 @@
-// Copyright (C) 2013-2015 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
+// Copyright (C) 2013-2017 Bayerische Motoren Werke Aktiengesellschaft (BMW AG)
// This Source Code Form is subject to the terms of the Mozilla Public
// License, v. 2.0. If a copy of the MPL was not distributed with this
// file, You can obtain one at http://mozilla.org/MPL/2.0/.