1ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen// Copyright (c) 2011 The Chromium Authors. All rights reserved. 2c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Use of this source code is governed by a BSD-style license that can be 3c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// found in the LICENSE file. 4c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 5c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#ifndef CHROME_BROWSER_AUTOMATION_AUTOMATION_RESOURCE_TRACKER_H__ 6c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#define CHROME_BROWSER_AUTOMATION_AUTOMATION_RESOURCE_TRACKER_H__ 73345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick#pragma once 8c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 9c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include <map> 10c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 11c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "base/basictypes.h" 12ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/notification_observer.h" 13ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/notification_registrar.h" 14ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/notification_source.h" 15ddb351dbec246cf1fab5ec20d2d5520909041de1Kristian Monsen#include "content/common/notification_type.h" 16c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#include "ipc/ipc_message.h" 17c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 18c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// Template trick so that AutomationResourceTracker can be used with non-pointer 19c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// types. 20c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochtemplate <class T> 21c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct AutomationResourceTraits { 22c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch typedef T ValueType; 23c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}; 24c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 25c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochtemplate <class T> 26c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochstruct AutomationResourceTraits<T*> { 27c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch typedef T ValueType; 28c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}; 29c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 30c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// This class exists for the sole purpose of allowing some of the implementation 31c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// of AutomationResourceTracker to live in a .cc file. 32c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochclass AutomationResourceTrackerImpl { 33c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch public: 343345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick explicit AutomationResourceTrackerImpl(IPC::Message::Sender* sender); 353345a6884c488ff3a535c2c9acdd33d74b37e311Iain Merrick virtual ~AutomationResourceTrackerImpl(); 36c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 3721d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen protected: 38c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // These need to be implemented in AutomationResourceTracker, 39c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // since it needs to call the subclass's type-specific notification 40c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // registration functions. 41513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch virtual void AddObserverTypeProxy(const void* resource) = 0; 42513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch virtual void RemoveObserverTypeProxy(const void* resource) = 0; 43c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 44513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch int AddImpl(const void* resource); 45513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch void RemoveImpl(const void* resource); 46c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch int GenerateHandle(); 47513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch bool ContainsResourceImpl(const void* resource); 48c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool ContainsHandleImpl(int handle); 49513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch const void* GetResourceImpl(int handle); 50513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch int GetHandleImpl(const void* resource); 51513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch void HandleCloseNotification(const void* resource); 52c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 5321d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen private: 54513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch typedef std::map<const void*, int> ResourceToHandleMap; 55513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch typedef std::map<int, const void*> HandleToResourceMap; 5621d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen 57c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch ResourceToHandleMap resource_to_handle_; 58c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HandleToResourceMap handle_to_resource_; 59c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 60c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch IPC::Message::Sender* sender_; 6121d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen 6221d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen DISALLOW_COPY_AND_ASSIGN(AutomationResourceTrackerImpl); 63c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}; 64c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 65c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// This template defines a superclass for an object that wants to track 66c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// a particular kind of application resource (like windows or tabs) for 67c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// automation purposes. The only things that a subclass should need to 68c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// define are AddObserver and RemoveObserver for the given resource's 69c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch// close notifications. 70c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdochtemplate <class T> 7121d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsenclass AutomationResourceTracker : public AutomationResourceTrackerImpl, 7221d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen public NotificationObserver { 73c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch public: 74c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch explicit AutomationResourceTracker(IPC::Message::Sender* automation) 75c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch : AutomationResourceTrackerImpl(automation) {} 76c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 77c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // The implementations for these should call the NotificationService 78c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // to add and remove this object as an observer for the appropriate 79c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // resource closing notification. 80c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch virtual void AddObserver(T resource) = 0; 81c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch virtual void RemoveObserver(T resource) = 0; 82c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 83c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Adds the given resource to this tracker, and returns a handle that 84c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // can be used to refer to that resource. If the resource is already 85c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // being tracked, the handle may be the same as one returned previously. 86c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch int Add(T resource) { 87c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return AddImpl(resource); 88c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 89c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 90c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Removes the given resource from this tracker. If the resource is not 91c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // currently present in the tracker, this is a no-op. 92c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch void Remove(T resource) { 93c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch RemoveImpl(resource); 94c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 95c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 96c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Returns true if this tracker currently tracks the resource pointed to 97c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // by the parameter. 98c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool ContainsResource(T resource) { 99c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return ContainsResourceImpl(resource); 100c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 101c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 102c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Returns true if this tracker currently tracks the given handle. 103c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch bool ContainsHandle(int handle) { 104c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return ContainsHandleImpl(handle); 105c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 106c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 107c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Returns the resource pointer associated with a given handle, or NULL 108c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // if that handle is not present in the mapping. 109513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch // The casts here allow this to compile with both T = Foo and T = const Foo. 110c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch T GetResource(int handle) { 111513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch return static_cast<T>(const_cast<void*>(GetResourceImpl(handle))); 112c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 113c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 114c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Returns the handle associated with a given resource pointer, or 0 if 115c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // the resource is not currently in the mapping. 116c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch int GetHandle(T resource) { 117c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch return GetHandleImpl(resource); 118c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 119c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 120c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // NotificationObserver implementation--the only thing that this tracker 121c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // does in response to notifications is to tell the AutomationProxy 122c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // that the associated handle is now invalid. 123c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch virtual void Observe(NotificationType type, 124c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const NotificationSource& source, 125c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch const NotificationDetails& details) { 126c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch T resource = 127c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch Source<typename AutomationResourceTraits<T>::ValueType>(source).ptr(); 128c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 129c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch CloseResource(resource); 130c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 131c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 132c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch protected: 133c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // Removes |resource| from the tracker, and handles sending the close 134c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // notification back to the client. This typically should not be called 135c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // directly, unless there is no appropriate notification available 136c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // for the resource type. 137c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch void CloseResource(T resource) { 138c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch HandleCloseNotification(resource); 139c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 140c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 141c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch // These proxy calls from the base Impl class to the template's subclss. 142513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch // The casts here allow this to compile with both T = Foo and T = const Foo. 143513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch virtual void AddObserverTypeProxy(const void* resource) { 144513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch AddObserver(static_cast<T>(const_cast<void*>(resource))); 145c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 146513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch virtual void RemoveObserverTypeProxy(const void* resource) { 147513209b27ff55e2841eac0e4120199c23acce758Ben Murdoch RemoveObserver(static_cast<T>(const_cast<void*>(resource))); 148c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch } 149c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 15021d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen NotificationRegistrar registrar_; 15121d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen 15221d179b334e59e9a3bfcaed4c4430bef1bc5759dKristian Monsen private: 153c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch DISALLOW_COPY_AND_ASSIGN(AutomationResourceTracker); 154c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch}; 155c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch 156c407dc5cd9bdc5668497f21b26b09d988ab439deBen Murdoch#endif // CHROME_BROWSER_AUTOMATION_AUTOMATION_RESOURCE_TRACKER_H__ 157