Upstream version 10.39.225.0
[platform/framework/web/crosswalk.git] / src / chrome / utility / local_discovery / service_discovery_message_handler.cc
index 7e589c5..9882c09 100644 (file)
@@ -8,7 +8,7 @@
 
 #include "base/lazy_instance.h"
 #include "chrome/common/local_discovery/local_discovery_messages.h"
-#include "chrome/utility/local_discovery/service_discovery_client_impl.h"
+#include "chrome/common/local_discovery/service_discovery_client_impl.h"
 #include "content/public/utility/utility_thread.h"
 #include "net/socket/socket_descriptor.h"
 #include "net/udp/datagram_server_socket.h"
@@ -66,38 +66,36 @@ class PreCreatedMDnsSocketFactory : public net::MDnsSocketFactory {
  public:
   PreCreatedMDnsSocketFactory() {}
   virtual ~PreCreatedMDnsSocketFactory() {
-    Reset();
+    // Not empty if process exits too fast, before starting mDns code. If
+    // happened, destructors may crash accessing destroyed global objects.
+    sockets_.weak_clear();
   }
 
   // net::MDnsSocketFactory implementation:
   virtual void CreateSockets(
       ScopedVector<net::DatagramServerSocket>* sockets) OVERRIDE {
-    for (size_t i = 0; i < sockets_.size(); ++i) {
-      // Takes ownership of sockets_[i].socket;
-      ScopedSocketFactory platform_factory(sockets_[i].socket);
-      scoped_ptr<net::DatagramServerSocket> socket(
-          net::CreateAndBindMDnsSocket(sockets_[i].address_family,
-                                       sockets_[i].interface_index));
-      if (socket)
-        sockets->push_back(socket.release());
-    }
-    sockets_.clear();
+    sockets->swap(sockets_);
+    Reset();
   }
 
-  void AddSocket(const SocketInfo& socket) {
-    sockets_.push_back(socket);
+  void AddSocket(const SocketInfo& socket_info) {
+    // Takes ownership of socket_info.socket;
+    ScopedSocketFactory platform_factory(socket_info.socket);
+    scoped_ptr<net::DatagramServerSocket> socket(
+        net::CreateAndBindMDnsSocket(socket_info.address_family,
+                                     socket_info.interface_index));
+    if (socket) {
+      socket->DetachFromThread();
+      sockets_.push_back(socket.release());
+    }
   }
 
   void Reset() {
-    for (size_t i = 0; i < sockets_.size(); ++i) {
-      if (sockets_[i].socket != net::kInvalidSocket)
-        ClosePlatformSocket(sockets_[i].socket);
-    }
     sockets_.clear();
   }
 
  private:
-  std::vector<SocketInfo> sockets_;
+  ScopedVector<net::DatagramServerSocket> sockets_;
 
   DISALLOW_COPY_AND_ASSIGN(PreCreatedMDnsSocketFactory);
 };
@@ -199,7 +197,7 @@ void ServiceDiscoveryMessageHandler::InitializeMdns() {
 }
 
 bool ServiceDiscoveryMessageHandler::InitializeThread() {
-  if (discovery_task_runner_)
+  if (discovery_task_runner_.get())
     return true;
   if (discovery_thread_)
     return false;
@@ -212,7 +210,7 @@ bool ServiceDiscoveryMessageHandler::InitializeThread() {
         base::Bind(&ServiceDiscoveryMessageHandler::InitializeMdns,
                     base::Unretained(this)));
   }
-  return discovery_task_runner_ != NULL;
+  return discovery_task_runner_.get() != NULL;
 }
 
 bool ServiceDiscoveryMessageHandler::OnMessageReceived(
@@ -224,6 +222,8 @@ bool ServiceDiscoveryMessageHandler::OnMessageReceived(
 #endif  // OS_POSIX
     IPC_MESSAGE_HANDLER(LocalDiscoveryMsg_StartWatcher, OnStartWatcher)
     IPC_MESSAGE_HANDLER(LocalDiscoveryMsg_DiscoverServices, OnDiscoverServices)
+    IPC_MESSAGE_HANDLER(LocalDiscoveryMsg_SetActivelyRefreshServices,
+                        OnSetActivelyRefreshServices)
     IPC_MESSAGE_HANDLER(LocalDiscoveryMsg_DestroyWatcher, OnDestroyWatcher)
     IPC_MESSAGE_HANDLER(LocalDiscoveryMsg_ResolveService, OnResolveService)
     IPC_MESSAGE_HANDLER(LocalDiscoveryMsg_DestroyResolver, OnDestroyResolver)
@@ -272,6 +272,14 @@ void ServiceDiscoveryMessageHandler::OnDiscoverServices(uint64 id,
                       base::Unretained(this), id, force_update));
 }
 
+void ServiceDiscoveryMessageHandler::OnSetActivelyRefreshServices(
+    uint64 id, bool actively_refresh_services) {
+  PostTask(FROM_HERE,
+           base::Bind(
+               &ServiceDiscoveryMessageHandler::SetActivelyRefreshServices,
+               base::Unretained(this), id, actively_refresh_services));
+}
+
 void ServiceDiscoveryMessageHandler::OnDestroyWatcher(uint64 id) {
   PostTask(FROM_HERE,
            base::Bind(&ServiceDiscoveryMessageHandler::DestroyWatcher,
@@ -332,6 +340,16 @@ void ServiceDiscoveryMessageHandler::DiscoverServices(uint64 id,
   service_watchers_[id]->DiscoverNewServices(force_update);
 }
 
+void ServiceDiscoveryMessageHandler::SetActivelyRefreshServices(
+    uint64 id,
+    bool actively_refresh_services) {
+  VLOG(1) << "ActivelyRefreshServices, id=" << id;
+  if (!service_discovery_client_)
+    return;
+  DCHECK(ContainsKey(service_watchers_, id));
+  service_watchers_[id]->SetActivelyRefreshServices(actively_refresh_services);
+}
+
 void ServiceDiscoveryMessageHandler::DestroyWatcher(uint64 id) {
   VLOG(1) << "DestoryWatcher, id=" << id;
   if (!service_discovery_client_)
@@ -387,7 +405,7 @@ void ServiceDiscoveryMessageHandler::DestroyLocalDomainResolver(uint64 id) {
 }
 
 void ServiceDiscoveryMessageHandler::ShutdownLocalDiscovery() {
-  if (!discovery_task_runner_)
+  if (!discovery_task_runner_.get())
     return;
 
   discovery_task_runner_->PostTask(