| Index: components/arc/arc_service_manager.h
|
| diff --git a/components/arc/arc_service_manager.h b/components/arc/arc_service_manager.h
|
| index 81a4ea9e98b2e715e289b112d3cae2660d72cbd6..6ab2911c24e41930a6d42f594dafe403cdc2af8b 100644
|
| --- a/components/arc/arc_service_manager.h
|
| +++ b/components/arc/arc_service_manager.h
|
| @@ -6,6 +6,10 @@
|
| #define COMPONENTS_ARC_ARC_SERVICE_MANAGER_H_
|
|
|
| #include <memory>
|
| +#include <string>
|
| +#include <type_traits>
|
| +#include <unordered_map>
|
| +#include <utility>
|
| #include <vector>
|
|
|
| #include "base/macros.h"
|
| @@ -22,6 +26,40 @@ class ArcBridgeService;
|
| class ArcIntentHelperObserver;
|
| class ArcService;
|
|
|
| +namespace internal {
|
| +
|
| +// If an ArcService is declared with a name, e.g.:
|
| +//
|
| +// class MyArcService : public ArcService {
|
| +// public:
|
| +// static const char kArcServiceName[];
|
| +// ...
|
| +// };
|
| +//
|
| +// it can then be retrieved from ArcServiceManager in a type-safe way using
|
| +// GetService<T>(). This two functions allow AddService() to get the name only
|
| +// if it was provided, or use an empty string otherwise.
|
| +//
|
| +// Although the typename is always specified explicitly by the caller, the
|
| +// parameter is required in order for SFINAE to work correctly. It is not used
|
| +// and can be nullptr, though.
|
| +//
|
| +// In order to avoid collisions, kArcServiceName should be the fully-qualified
|
| +// name of the class.
|
| +template <typename T>
|
| +decltype(T::kArcServiceName, std::string()) GetArcServiceName(T* unused) {
|
| + if (strlen(T::kArcServiceName) == 0)
|
| + LOG(ERROR) << "kArcServiceName[] should be a fully-qualified class name.";
|
| + return T::kArcServiceName;
|
| +}
|
| +
|
| +template <typename T>
|
| +std::string GetArcServiceName(...) {
|
| + return std::string();
|
| +}
|
| +
|
| +} // namespace internal
|
| +
|
| // Manages creation and destruction of services that communicate with the ARC
|
| // instance via the ArcBridgeService.
|
| class ArcServiceManager {
|
| @@ -48,8 +86,22 @@ class ArcServiceManager {
|
| // class was created on.
|
| ArcBridgeService* arc_bridge_service();
|
|
|
| - // Adds a service to the managed services list.
|
| - void AddService(std::unique_ptr<ArcService> service);
|
| + // Adds a service to the managed services list. Returns false if another
|
| + // named service with that name had already been added.
|
| + template <typename T>
|
| + bool AddService(std::unique_ptr<T> service) {
|
| + return AddServiceInternal(internal::GetArcServiceName<T>(nullptr),
|
| + std::move(service));
|
| + }
|
| +
|
| + // Gets the named service from the managed services list. This uses SFINAE, so
|
| + // you can only call this function if the service specified by T provides a
|
| + // static member variable called kArcServiceName[] (otherwise this will not
|
| + // compile).
|
| + template <typename T>
|
| + T* GetService() {
|
| + return static_cast<T*>(GetNamedServiceInternal(T::kArcServiceName));
|
| + }
|
|
|
| // Gets the global instance of the ARC Service Manager. This can only be
|
| // called on the thread that this class was created on.
|
| @@ -81,6 +133,11 @@ class ArcServiceManager {
|
| private:
|
| class IntentHelperObserverImpl; // implemented in arc_service_manager.cc.
|
|
|
| + // Helper methods for AddService and GetService.
|
| + bool AddServiceInternal(const std::string& name,
|
| + std::unique_ptr<ArcService> service);
|
| + ArcService* GetNamedServiceInternal(const std::string& name);
|
| +
|
| base::ThreadChecker thread_checker_;
|
| scoped_refptr<base::TaskRunner> blocking_task_runner_;
|
|
|
| @@ -88,7 +145,7 @@ class ArcServiceManager {
|
| std::unique_ptr<ArcIntentHelperObserver> intent_helper_observer_;
|
|
|
| std::unique_ptr<ArcBridgeService> arc_bridge_service_;
|
| - std::vector<std::unique_ptr<ArcService>> services_;
|
| + std::unordered_multimap<std::string, std::unique_ptr<ArcService>> services_;
|
| scoped_refptr<ActivityIconLoader> icon_loader_;
|
| scoped_refptr<LocalActivityResolver> activity_resolver_;
|
|
|
|
|