1 // Copyright (c) 2012 The Chromium Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style license that can be 3 // found in the LICENSE file. 4 5 #include "remoting/host/host_event_logger.h" 6 7 #include <windows.h> 8 #include <string> 9 #include <vector> 10 11 #include "base/memory/scoped_ptr.h" 12 #include "base/memory/weak_ptr.h" 13 #include "base/strings/string16.h" 14 #include "base/strings/utf_string_conversions.h" 15 #include "net/base/ip_endpoint.h" 16 #include "remoting/host/host_status_monitor.h" 17 #include "remoting/host/host_status_observer.h" 18 #include "remoting/protocol/transport.h" 19 20 #include "remoting_host_messages.h" 21 22 namespace remoting { 23 24 namespace { 25 26 class HostEventLoggerWin : public HostEventLogger, public HostStatusObserver { 27 public: 28 HostEventLoggerWin(base::WeakPtr<HostStatusMonitor> monitor, 29 const std::string& application_name); 30 31 virtual ~HostEventLoggerWin(); 32 33 // HostStatusObserver implementation. These methods will be called from the 34 // network thread. 35 virtual void OnClientAuthenticated(const std::string& jid) OVERRIDE; 36 virtual void OnClientDisconnected(const std::string& jid) OVERRIDE; 37 virtual void OnAccessDenied(const std::string& jid) OVERRIDE; 38 virtual void OnClientRouteChange( 39 const std::string& jid, 40 const std::string& channel_name, 41 const protocol::TransportRoute& route) OVERRIDE; 42 virtual void OnStart(const std::string& xmpp_login) OVERRIDE; 43 virtual void OnShutdown() OVERRIDE; 44 45 private: 46 void LogString(WORD type, DWORD event_id, const std::string& string); 47 void Log(WORD type, DWORD event_id, const std::vector<std::string>& strings); 48 49 base::WeakPtr<HostStatusMonitor> monitor_; 50 51 // The handle of the application event log. 52 HANDLE event_log_; 53 54 DISALLOW_COPY_AND_ASSIGN(HostEventLoggerWin); 55 }; 56 57 } //namespace 58 59 HostEventLoggerWin::HostEventLoggerWin(base::WeakPtr<HostStatusMonitor> monitor, 60 const std::string& application_name) 61 : monitor_(monitor), 62 event_log_(NULL) { 63 event_log_ = RegisterEventSourceW(NULL, 64 UTF8ToUTF16(application_name).c_str()); 65 if (event_log_ != NULL) { 66 monitor_->AddStatusObserver(this); 67 } else { 68 LOG_GETLASTERROR(ERROR) << "Failed to register the event source: " 69 << application_name; 70 } 71 } 72 73 HostEventLoggerWin::~HostEventLoggerWin() { 74 if (event_log_ != NULL) { 75 if (monitor_) 76 monitor_->RemoveStatusObserver(this); 77 DeregisterEventSource(event_log_); 78 } 79 } 80 81 void HostEventLoggerWin::OnClientAuthenticated(const std::string& jid) { 82 LogString(EVENTLOG_INFORMATION_TYPE, MSG_HOST_CLIENT_CONNECTED, jid); 83 } 84 85 void HostEventLoggerWin::OnClientDisconnected(const std::string& jid) { 86 LogString(EVENTLOG_INFORMATION_TYPE, MSG_HOST_CLIENT_DISCONNECTED, jid); 87 } 88 89 void HostEventLoggerWin::OnAccessDenied(const std::string& jid) { 90 LogString(EVENTLOG_ERROR_TYPE, MSG_HOST_CLIENT_ACCESS_DENIED, jid); 91 } 92 93 void HostEventLoggerWin::OnClientRouteChange( 94 const std::string& jid, 95 const std::string& channel_name, 96 const protocol::TransportRoute& route) { 97 std::vector<std::string> strings(5); 98 strings[0] = jid; 99 strings[1] = route.remote_address.ToString(); 100 strings[2] = route.local_address.ToString(); 101 strings[3] = channel_name; 102 strings[4] = protocol::TransportRoute::GetTypeString(route.type); 103 Log(EVENTLOG_INFORMATION_TYPE, MSG_HOST_CLIENT_ROUTING_CHANGED, strings); 104 } 105 106 void HostEventLoggerWin::OnShutdown() { 107 // TODO(rmsousa): Fix host shutdown to actually call this, and add a log line. 108 } 109 110 void HostEventLoggerWin::OnStart(const std::string& xmpp_login) { 111 LogString(EVENTLOG_INFORMATION_TYPE, MSG_HOST_STARTED, xmpp_login); 112 } 113 114 void HostEventLoggerWin::Log(WORD type, 115 DWORD event_id, 116 const std::vector<std::string>& strings) { 117 if (event_log_ == NULL) 118 return; 119 120 // ReportEventW() takes an array of raw string pointers. They should stay 121 // valid for the duration of the call. 122 std::vector<const WCHAR*> raw_strings(strings.size()); 123 std::vector<string16> utf16_strings(strings.size()); 124 for (size_t i = 0; i < strings.size(); ++i) { 125 utf16_strings[i] = UTF8ToUTF16(strings[i]); 126 raw_strings[i] = utf16_strings[i].c_str(); 127 } 128 129 if (!ReportEventW(event_log_, 130 type, 131 HOST_CATEGORY, 132 event_id, 133 NULL, 134 static_cast<WORD>(raw_strings.size()), 135 0, 136 &raw_strings[0], 137 NULL)) { 138 LOG_GETLASTERROR(ERROR) << "Failed to write an event to the event log"; 139 } 140 } 141 142 void HostEventLoggerWin::LogString(WORD type, 143 DWORD event_id, 144 const std::string& string) { 145 std::vector<std::string> strings; 146 strings.push_back(string); 147 Log(type, event_id, strings); 148 } 149 150 // static 151 scoped_ptr<HostEventLogger> HostEventLogger::Create( 152 base::WeakPtr<HostStatusMonitor> monitor, 153 const std::string& application_name) { 154 return scoped_ptr<HostEventLogger>( 155 new HostEventLoggerWin(monitor, application_name)); 156 } 157 158 } // namespace remoting 159