net_log.h revision 5821806d5e7f356e8fa4b058a389a808ea183019
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#ifndef NET_BASE_NET_LOG_H_
6#define NET_BASE_NET_LOG_H_
7
8#include <string>
9
10#include "base/basictypes.h"
11#include "base/callback_forward.h"
12#include "base/compiler_specific.h"
13#include "base/string16.h"
14#include "base/time.h"
15#include "net/base/net_export.h"
16
17namespace base {
18class DictionaryValue;
19class Value;
20}
21
22namespace net {
23
24// NetLog is the destination for log messages generated by the network stack.
25// Each log message has a "source" field which identifies the specific entity
26// that generated the message (for example, which URLRequest or which
27// SocketStream).
28//
29// To avoid needing to pass in the "source ID" to the logging functions, NetLog
30// is usually accessed through a BoundNetLog, which will always pass in a
31// specific source ID.
32//
33// All NetLog methods must be thread-safe.
34//
35// For a broader introduction see the design document:
36// https://sites.google.com/a/chromium.org/dev/developers/design-documents/network-stack/netlog
37class NET_EXPORT NetLog {
38 public:
39  enum EventType {
40#define EVENT_TYPE(label) TYPE_ ## label,
41#include "net/base/net_log_event_type_list.h"
42#undef EVENT_TYPE
43    EVENT_COUNT
44  };
45
46  // The 'phase' of an event trace (whether it marks the beginning or end
47  // of an event.).
48  enum EventPhase {
49    PHASE_NONE,
50    PHASE_BEGIN,
51    PHASE_END,
52  };
53
54  // The "source" identifies the entity that generated the log message.
55  enum SourceType {
56#define SOURCE_TYPE(label) SOURCE_ ## label,
57#include "net/base/net_log_source_type_list.h"
58#undef SOURCE_TYPE
59    SOURCE_COUNT
60  };
61
62  // Specifies the granularity of events that should be emitted to the log.
63  enum LogLevel {
64    // Log everything possible, even if it is slow and memory expensive.
65    // Includes logging of transferred bytes.
66    LOG_ALL,
67
68    // Log all events, but do not include the actual transferred bytes as
69    // parameters for bytes sent/received events.
70    LOG_ALL_BUT_BYTES,
71
72    // Only log events which are cheap, and don't consume much memory.
73    LOG_BASIC,
74  };
75
76  // A callback function that return a Value representation of the parameters
77  // associated with an event.  If called, it will be called synchonously,
78  // so it need not have owning references.  May be called more than once, or
79  // not at all.  May return NULL.
80  typedef base::Callback<base::Value*(LogLevel)> ParametersCallback;
81
82  // Identifies the entity that generated this log. The |id| field should
83  // uniquely identify the source, and is used by log observers to infer
84  // message groupings. Can use NetLog::NextID() to create unique IDs.
85  struct NET_EXPORT Source {
86    static const uint32 kInvalidId = 0;
87
88    Source() : type(SOURCE_NONE), id(kInvalidId) {}
89    Source(SourceType type, uint32 id) : type(type), id(id) {}
90    bool is_valid() const { return id != kInvalidId; }
91
92    // Adds the source to a DictionaryValue containing event parameters,
93    // using the name "source_dependency".
94    void AddToEventParameters(base::DictionaryValue* event_params) const;
95
96    // Returns a callback that returns a dictionary with a single entry
97    // named "source_dependecy" that describes |this|.
98    ParametersCallback ToEventParametersCallback() const;
99
100    // Attempts to extract a Source from a set of event parameters.  Returns
101    // true and writes the result to |source| on success.  Returns false and
102    // makes |source| an invalid source on failure.
103    // TODO(mmenke):  Long term, we want to remove this.
104    static bool FromEventParameters(base::Value* event_params, Source* source);
105
106    SourceType type;
107    uint32 id;
108  };
109
110  class NET_EXPORT Entry {
111   public:
112    Entry(EventType type,
113          Source source,
114          EventPhase phase,
115          base::TimeTicks time,
116          const ParametersCallback* parameters_callback,
117          LogLevel log_level);
118    ~Entry();
119
120    EventType type() const { return type_; }
121    Source source() const { return source_; }
122    EventPhase phase() const { return phase_; }
123
124    // Serializes the specified event to a Value.  The Value also includes the
125    // current time.  Caller takes ownership of returned Value.  Takes in a time
126    // to allow back-dating entries.
127    base::Value* ToValue() const;
128
129    // Returns the parameters as a Value.  Returns NULL if there are no
130    // parameters.  Caller takes ownership of returned Value.
131    base::Value* ParametersToValue() const;
132
133   private:
134    const EventType type_;
135    const Source source_;
136    const EventPhase phase_;
137    const base::TimeTicks time_;
138    const ParametersCallback* parameters_callback_;
139
140    // Log level when the event occurred.
141    const LogLevel log_level_;
142
143    // It is not safe to copy this class, since |parameters_callback_| may
144    // include pointers that become stale immediately after the event is added,
145    // even if the code were modified to keep its own copy of the callback.
146    DISALLOW_COPY_AND_ASSIGN(Entry);
147  };
148
149  // An observer, that must ensure its own thread safety, for events
150  // being added to a NetLog.
151  class NET_EXPORT ThreadSafeObserver {
152   public:
153    // Constructs an observer that wants to see network events, with
154    // the specified minimum event granularity.  A ThreadSafeObserver can only
155    // observe a single NetLog at a time.
156    //
157    // Observers will be called on the same thread an entry is added on,
158    // and are responsible for ensuring their own thread safety.
159    //
160    // Observers must stop watching a NetLog before either the Observer or the
161    // NetLog is destroyed.
162    ThreadSafeObserver();
163
164    // Returns the minimum log level for events this observer wants to
165    // receive.  Must not be called when not watching a NetLog.
166    LogLevel log_level() const;
167
168    // Returns the NetLog we are currently watching, if any.  Returns NULL
169    // otherwise.
170    NetLog* net_log() const;
171
172    // This method will be called on the thread that the event occurs on.  It
173    // is the responsibility of the observer to handle it in a thread safe
174    // manner.
175    //
176    // It is illegal for an Observer to call any NetLog or
177    // NetLog::Observer functions in response to a call to OnAddEntry.
178    virtual void OnAddEntry(const Entry& entry) = 0;
179
180   protected:
181    virtual ~ThreadSafeObserver();
182
183   private:
184    friend class NetLog;
185
186    // Both of these values are only modified by the NetLog.
187    LogLevel log_level_;
188    NetLog* net_log_;
189
190    DISALLOW_COPY_AND_ASSIGN(ThreadSafeObserver);
191  };
192
193  NetLog() {}
194  virtual ~NetLog() {}
195
196  // Emits a global event to the log stream, with its own unique source ID.
197  void AddGlobalEntry(EventType type);
198  void AddGlobalEntry(EventType type,
199                      const NetLog::ParametersCallback& parameters_callback);
200
201  // Returns a unique ID which can be used as a source ID.  All returned IDs
202  // will be unique and greater than 0.
203  virtual uint32 NextID() = 0;
204
205  // Returns the logging level for this NetLog. This is used to avoid computing
206  // and saving expensive log entries.
207  virtual LogLevel GetLogLevel() const = 0;
208
209  // Adds an observer and sets its log level.  The observer must not be
210  // watching any NetLog, including this one, when this is called.
211  //
212  // Typical observers should specify LOG_BASIC.
213  //
214  // Observers that need to see the full granularity of events can specify
215  // LOG_ALL_BUT_BYTES. However, doing so will have performance consequences.
216  //
217  // NetLog implementations must call NetLog::OnAddObserver to update the
218  // observer's internal state.
219  virtual void AddThreadSafeObserver(ThreadSafeObserver* observer,
220                                     LogLevel log_level) = 0;
221
222  // Sets the log level of |observer| to |log_level|.  |observer| must be
223  // watching |this|.  NetLog implementations must call
224  // NetLog::OnSetObserverLogLevel to update the observer's internal state.
225  virtual void SetObserverLogLevel(ThreadSafeObserver* observer,
226                                   LogLevel log_level) = 0;
227
228  // Removes an observer.  NetLog implementations must call
229  // NetLog::OnAddObserver to update the observer's internal state.
230  //
231  // For thread safety reasons, it is recommended that this not be called in
232  // an object's destructor.
233  virtual void RemoveThreadSafeObserver(ThreadSafeObserver* observer) = 0;
234
235  // Converts a time to the string format that the NetLog uses to represent
236  // times.  Strings are used since integers may overflow.
237  static std::string TickCountToString(const base::TimeTicks& time);
238
239  // Returns a C-String symbolic name for |event_type|.
240  static const char* EventTypeToString(EventType event_type);
241
242  // Returns a dictionary that maps event type symbolic names to their enum
243  // values.  Caller takes ownership of the returned Value.
244  static base::Value* GetEventTypesAsValue();
245
246  // Returns a C-String symbolic name for |source_type|.
247  static const char* SourceTypeToString(SourceType source_type);
248
249  // Returns a dictionary that maps source type symbolic names to their enum
250  // values.  Caller takes ownership of the returned Value.
251  static base::Value* GetSourceTypesAsValue();
252
253  // Returns a C-String symbolic name for |event_phase|.
254  static const char* EventPhaseToString(EventPhase event_phase);
255
256  // Returns true if |log_level| indicates the actual bytes transferred should
257  // be logged.  This is only the case when |log_level| is LOG_ALL.
258  static bool IsLoggingBytes(LogLevel log_level);
259
260  // Returns true if |log_level| indicates that all events should be logged,
261  // including frequently occuring ones that may impact performances.
262  // This is the case when |log_level| is LOG_ALL or LOG_ALL_BUT_BYTES.
263  static bool IsLoggingAllEvents(LogLevel log_level);
264
265  // Creates a ParametersCallback that encapsulates a single integer.
266  // Warning: |name| must remain valid for the life of the callback.
267  // TODO(mmenke):  Rename this to be consistent with Int64Callback.
268  static ParametersCallback IntegerCallback(const char* name, int value);
269
270  // Creates a ParametersCallback that encapsulates a single int64.  The
271  // callback will return the value as a StringValue, since IntegerValues
272  // only support 32-bit values.
273  // Warning: |name| must remain valid for the life of the callback.
274  static ParametersCallback Int64Callback(const char* name, int64 value);
275
276  // Creates a ParametersCallback that encapsulates a single UTF8 string.  Takes
277  // |value| as a pointer to avoid copying, and emphasize it must be valid for
278  // the life of the callback.  |value| may not be NULL.
279  // Warning: |name| and |value| must remain valid for the life of the callback.
280  static ParametersCallback StringCallback(const char* name,
281                                           const std::string* value);
282
283  // Same as above, but takes in a UTF16 string.
284  static ParametersCallback StringCallback(const char* name,
285                                           const string16* value);
286
287 protected:
288  // Child classes should respond to the new entry here.  This includes
289  // creating the Entry object and alerting their observers.
290  virtual void OnAddEntry(const Entry& entry) = 0;
291
292  // Subclasses must call these in the corresponding functions to set an
293  // observer's |net_log_| and |log_level_| values.
294  void OnAddObserver(ThreadSafeObserver* observer, LogLevel log_level);
295  void OnSetObserverLogLevel(ThreadSafeObserver* observer,
296                             LogLevel log_level);
297  void OnRemoveObserver(ThreadSafeObserver* observer);
298
299 private:
300  friend class BoundNetLog;
301
302  void AddEntry(EventType type,
303                const Source& source,
304                EventPhase phase,
305                const NetLog::ParametersCallback* parameters_callback);
306
307  DISALLOW_COPY_AND_ASSIGN(NetLog);
308};
309
310// Helper that binds a Source to a NetLog, and exposes convenience methods to
311// output log messages without needing to pass in the source.
312class NET_EXPORT BoundNetLog {
313 public:
314  BoundNetLog() : net_log_(NULL) {}
315
316  // Add a log entry to the NetLog for the bound source.
317  void AddEntry(NetLog::EventType type, NetLog::EventPhase phase) const;
318  void AddEntry(NetLog::EventType type,
319                NetLog::EventPhase phase,
320                const NetLog::ParametersCallback& get_parameters) const;
321
322  // Convenience methods that call AddEntry with a fixed "capture phase"
323  // (begin, end, or none).
324  void BeginEvent(NetLog::EventType type) const;
325  void BeginEvent(NetLog::EventType type,
326                  const NetLog::ParametersCallback& get_parameters) const;
327
328  void EndEvent(NetLog::EventType type) const;
329  void EndEvent(NetLog::EventType type,
330                const NetLog::ParametersCallback& get_parameters) const;
331
332  void AddEvent(NetLog::EventType type) const;
333  void AddEvent(NetLog::EventType type,
334                const NetLog::ParametersCallback& get_parameters) const;
335
336  // Just like AddEvent, except |net_error| is a net error code.  A parameter
337  // called "net_error" with the indicated value will be recorded for the event.
338  // |net_error| must be negative, and not ERR_IO_PENDING, as it's not a true
339  // error.
340  void AddEventWithNetErrorCode(NetLog::EventType event_type,
341                                int net_error) const;
342
343  // Just like EndEvent, except |net_error| is a net error code.  If it's
344  // negative, a parameter called "net_error" with a value of |net_error| is
345  // associated with the event.  Otherwise, the end event has no parameters.
346  // |net_error| must not be ERR_IO_PENDING, as it's not a true error.
347  void EndEventWithNetErrorCode(NetLog::EventType event_type,
348                                int net_error) const;
349
350  // Logs a byte transfer event to the NetLog.  Determines whether to log the
351  // received bytes or not based on the current logging level.
352  void AddByteTransferEvent(NetLog::EventType event_type,
353                            int byte_count, const char* bytes) const;
354
355  NetLog::LogLevel GetLogLevel() const;
356
357  // Shortcut for NetLog::IsLoggingBytes(this->GetLogLevel()).
358  bool IsLoggingBytes() const;
359
360  // Shortcut for NetLog::IsLoggingAllEvents(this->GetLogLevel()).
361  bool IsLoggingAllEvents() const;
362
363  // Helper to create a BoundNetLog given a NetLog and a SourceType. Takes care
364  // of creating a unique source ID, and handles the case of NULL net_log.
365  static BoundNetLog Make(NetLog* net_log, NetLog::SourceType source_type);
366
367  const NetLog::Source& source() const { return source_; }
368  NetLog* net_log() const { return net_log_; }
369
370 private:
371  BoundNetLog(const NetLog::Source& source, NetLog* net_log)
372      : source_(source), net_log_(net_log) {
373  }
374
375  NetLog::Source source_;
376  NetLog* net_log_;
377};
378
379}  // namespace net
380
381#endif  // NET_BASE_NET_LOG_H_
382