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.
5
#ifndef NET_BASE_NET_LOG_H_
6
#define NET_BASE_NET_LOG_H_
10
#include "base/atomicops.h"
11
#include "base/basictypes.h"
12
#include "base/callback_forward.h"
13
#include "base/compiler_specific.h"
14
#include "base/observer_list.h"
15
#include "base/strings/string16.h"
16
#include "base/synchronization/lock.h"
17
#include "base/time/time.h"
18
#include "net/base/net_export.h"
21
class DictionaryValue;
27
// NetLog is the destination for log messages generated by the network stack.
28
// Each log message has a "source" field which identifies the specific entity
29
// that generated the message (for example, which URLRequest or which
32
// To avoid needing to pass in the "source ID" to the logging functions, NetLog
33
// is usually accessed through a BoundNetLog, which will always pass in a
34
// specific source ID.
36
// All methods are thread safe, with the exception that no NetLog or
37
// NetLog::ThreadSafeObserver functions may be called by an observer's
38
// OnAddEntry() method. Doing so will result in a deadlock.
40
// For a broader introduction see the design document:
41
// https://sites.google.com/a/chromium.org/dev/developers/design-documents/network-stack/netlog
42
class NET_EXPORT NetLog {
45
#define EVENT_TYPE(label) TYPE_ ## label,
46
#include "net/base/net_log_event_type_list.h"
51
// The 'phase' of an event trace (whether it marks the beginning or end
59
// The "source" identifies the entity that generated the log message.
61
#define SOURCE_TYPE(label) SOURCE_ ## label,
62
#include "net/base/net_log_source_type_list.h"
67
// Specifies the granularity of events that should be emitted to the log.
69
// Since the LogLevel may be read and set on any thread without locking, it
70
// may be possible for an Observer to receive an event or parameters that
71
// normally wouldn't be logged at the currently active log level.
73
// Log everything possible, even if it is slow and memory expensive.
74
// Includes logging of transferred bytes.
77
// Log all events, but do not include the actual transferred bytes as
78
// parameters for bytes sent/received events.
81
// Only log events which are cheap, and don't consume much memory. This is
82
// the default value for observers.
85
// Don't log any events.
89
// A callback function that return a Value representation of the parameters
90
// associated with an event. If called, it will be called synchonously,
91
// so it need not have owning references. May be called more than once, or
92
// not at all. May return NULL.
93
typedef base::Callback<base::Value*(LogLevel)> ParametersCallback;
95
// Identifies the entity that generated this log. The |id| field should
96
// uniquely identify the source, and is used by log observers to infer
97
// message groupings. Can use NetLog::NextID() to create unique IDs.
98
struct NET_EXPORT Source {
99
static const uint32 kInvalidId;
102
Source(SourceType type, uint32 id);
103
bool IsValid() const;
105
// Adds the source to a DictionaryValue containing event parameters,
106
// using the name "source_dependency".
107
void AddToEventParameters(base::DictionaryValue* event_params) const;
109
// Returns a callback that returns a dictionary with a single entry
110
// named "source_dependecy" that describes |this|.
111
ParametersCallback ToEventParametersCallback() const;
113
// Attempts to extract a Source from a set of event parameters. Returns
114
// true and writes the result to |source| on success. Returns false and
115
// makes |source| an invalid source on failure.
116
// TODO(mmenke): Long term, we want to remove this.
117
static bool FromEventParameters(base::Value* event_params, Source* source);
123
struct NET_EXPORT EntryData {
124
EntryData(EventType type,
127
base::TimeTicks time,
128
const ParametersCallback* parameters_callback);
131
const EventType type;
133
const EventPhase phase;
134
const base::TimeTicks time;
135
const ParametersCallback* const parameters_callback;
138
// An Entry pre-binds EntryData to a LogLevel, so observers will observe the
139
// output of ToValue() and ParametersToValue() at their log level rather than
141
class NET_EXPORT Entry {
143
Entry(const EntryData* data, LogLevel log_level);
146
EventType type() const { return data_->type; }
147
Source source() const { return data_->source; }
148
EventPhase phase() const { return data_->phase; }
150
// Serializes the specified event to a Value. The Value also includes the
151
// current time. Caller takes ownership of returned Value. Takes in a time
152
// to allow back-dating entries.
153
base::Value* ToValue() const;
155
// Returns the parameters as a Value. Returns NULL if there are no
156
// parameters. Caller takes ownership of returned Value.
157
base::Value* ParametersToValue() const;
160
const EntryData* const data_;
162
// Log level when the event occurred.
163
const LogLevel log_level_;
165
// It is not safe to copy this class, since |parameters_callback_| may
166
// include pointers that become stale immediately after the event is added,
167
// even if the code were modified to keep its own copy of the callback.
168
DISALLOW_COPY_AND_ASSIGN(Entry);
171
// An observer, that must ensure its own thread safety, for events
172
// being added to a NetLog.
173
class NET_EXPORT ThreadSafeObserver {
175
// Constructs an observer that wants to see network events, with
176
// the specified minimum event granularity. A ThreadSafeObserver can only
177
// observe a single NetLog at a time.
179
// Observers will be called on the same thread an entry is added on,
180
// and are responsible for ensuring their own thread safety.
182
// Observers must stop watching a NetLog before either the Observer or the
183
// NetLog is destroyed.
184
ThreadSafeObserver();
186
// Returns the minimum log level for events this observer wants to
187
// receive. Must not be called when not watching a NetLog.
188
LogLevel log_level() const;
190
// Returns the NetLog we are currently watching, if any. Returns NULL
192
NetLog* net_log() const;
194
// This method will be called on the thread that the event occurs on. It
195
// is the responsibility of the observer to handle it in a thread safe
198
// It is illegal for an Observer to call any NetLog or
199
// NetLog::Observer functions in response to a call to OnAddEntry.
200
virtual void OnAddEntry(const Entry& entry) = 0;
203
virtual ~ThreadSafeObserver();
208
void OnAddEntryData(const EntryData& entry_data);
210
// Both of these values are only modified by the NetLog.
214
DISALLOW_COPY_AND_ASSIGN(ThreadSafeObserver);
220
// Emits a global event to the log stream, with its own unique source ID.
221
void AddGlobalEntry(EventType type);
222
void AddGlobalEntry(EventType type,
223
const NetLog::ParametersCallback& parameters_callback);
225
// Returns a unique ID which can be used as a source ID. All returned IDs
226
// will be unique and greater than 0.
229
// Returns the logging level for this NetLog. This is used to avoid computing
230
// and saving expensive log entries.
231
LogLevel GetLogLevel() const;
233
// Adds an observer and sets its log level. The observer must not be
234
// watching any NetLog, including this one, when this is called.
236
// Typical observers should specify LOG_BASIC.
238
// Observers that need to see the full granularity of events can specify
239
// LOG_ALL_BUT_BYTES. However, doing so will have performance consequences.
241
// NetLog implementations must call NetLog::OnAddObserver to update the
242
// observer's internal state.
243
void AddThreadSafeObserver(ThreadSafeObserver* observer, LogLevel log_level);
245
// Sets the log level of |observer| to |log_level|. |observer| must be
246
// watching |this|. NetLog implementations must call
247
// NetLog::OnSetObserverLogLevel to update the observer's internal state.
248
void SetObserverLogLevel(ThreadSafeObserver* observer, LogLevel log_level);
250
// Removes an observer. NetLog implementations must call
251
// NetLog::OnAddObserver to update the observer's internal state.
253
// For thread safety reasons, it is recommended that this not be called in
254
// an object's destructor.
255
void RemoveThreadSafeObserver(ThreadSafeObserver* observer);
257
// Converts a time to the string format that the NetLog uses to represent
258
// times. Strings are used since integers may overflow.
259
static std::string TickCountToString(const base::TimeTicks& time);
261
// Returns a C-String symbolic name for |event_type|.
262
static const char* EventTypeToString(EventType event_type);
264
// Returns a dictionary that maps event type symbolic names to their enum
265
// values. Caller takes ownership of the returned Value.
266
static base::Value* GetEventTypesAsValue();
268
// Returns a C-String symbolic name for |source_type|.
269
static const char* SourceTypeToString(SourceType source_type);
271
// Returns a dictionary that maps source type symbolic names to their enum
272
// values. Caller takes ownership of the returned Value.
273
static base::Value* GetSourceTypesAsValue();
275
// Returns a C-String symbolic name for |event_phase|.
276
static const char* EventPhaseToString(EventPhase event_phase);
278
// Returns true if |log_level| indicates the actual bytes transferred should
279
// be logged. This is only the case when |log_level| is LOG_ALL.
280
static bool IsLoggingBytes(LogLevel log_level);
282
// Returns true if |log_level| indicates that all events should be logged,
283
// including frequently occuring ones that may impact performances.
284
// This is the case when |log_level| is LOG_ALL or LOG_ALL_BUT_BYTES.
285
static bool IsLoggingAllEvents(LogLevel log_level);
287
// Creates a ParametersCallback that encapsulates a single integer.
288
// Warning: |name| must remain valid for the life of the callback.
289
// TODO(mmenke): Rename this to be consistent with Int64Callback.
290
static ParametersCallback IntegerCallback(const char* name, int value);
292
// Creates a ParametersCallback that encapsulates a single int64. The
293
// callback will return the value as a StringValue, since IntegerValues
294
// only support 32-bit values.
295
// Warning: |name| must remain valid for the life of the callback.
296
static ParametersCallback Int64Callback(const char* name, int64 value);
298
// Creates a ParametersCallback that encapsulates a single UTF8 string. Takes
299
// |value| as a pointer to avoid copying, and emphasize it must be valid for
300
// the life of the callback. |value| may not be NULL.
301
// Warning: |name| and |value| must remain valid for the life of the callback.
302
static ParametersCallback StringCallback(const char* name,
303
const std::string* value);
305
// Same as above, but takes in a UTF16 string.
306
static ParametersCallback StringCallback(const char* name,
307
const base::string16* value);
310
// Set the lowest allowed log level, regardless of any Observers.
311
void SetBaseLogLevel(LogLevel log_level);
314
friend class BoundNetLog;
316
void AddEntry(EventType type,
317
const Source& source,
319
const NetLog::ParametersCallback* parameters_callback);
321
// Called whenever an observer is added or removed, or has its log level
322
// changed. Must have acquired |lock_| prior to calling.
323
void UpdateLogLevel();
325
// |lock_| protects access to |observers_|.
328
// Last assigned source ID. Incremented to get the next one.
329
base::subtle::Atomic32 last_id_;
331
// The lowest allowed log level, regardless of any Observers.
332
// Normally defaults to LOG_NONE, but can be changed with SetBaseLogLevel
333
LogLevel base_log_level_;
335
// The current log level.
336
base::subtle::Atomic32 effective_log_level_;
338
// |lock_| must be acquired whenever reading or writing to this.
339
ObserverList<ThreadSafeObserver, true> observers_;
341
DISALLOW_COPY_AND_ASSIGN(NetLog);
344
// Helper that binds a Source to a NetLog, and exposes convenience methods to
345
// output log messages without needing to pass in the source.
346
class NET_EXPORT BoundNetLog {
348
BoundNetLog() : net_log_(NULL) {}
350
// Add a log entry to the NetLog for the bound source.
351
void AddEntry(NetLog::EventType type, NetLog::EventPhase phase) const;
352
void AddEntry(NetLog::EventType type,
353
NetLog::EventPhase phase,
354
const NetLog::ParametersCallback& get_parameters) const;
356
// Convenience methods that call AddEntry with a fixed "capture phase"
357
// (begin, end, or none).
358
void BeginEvent(NetLog::EventType type) const;
359
void BeginEvent(NetLog::EventType type,
360
const NetLog::ParametersCallback& get_parameters) const;
362
void EndEvent(NetLog::EventType type) const;
363
void EndEvent(NetLog::EventType type,
364
const NetLog::ParametersCallback& get_parameters) const;
366
void AddEvent(NetLog::EventType type) const;
367
void AddEvent(NetLog::EventType type,
368
const NetLog::ParametersCallback& get_parameters) const;
370
// Just like AddEvent, except |net_error| is a net error code. A parameter
371
// called "net_error" with the indicated value will be recorded for the event.
372
// |net_error| must be negative, and not ERR_IO_PENDING, as it's not a true
374
void AddEventWithNetErrorCode(NetLog::EventType event_type,
375
int net_error) const;
377
// Just like EndEvent, except |net_error| is a net error code. If it's
378
// negative, a parameter called "net_error" with a value of |net_error| is
379
// associated with the event. Otherwise, the end event has no parameters.
380
// |net_error| must not be ERR_IO_PENDING, as it's not a true error.
381
void EndEventWithNetErrorCode(NetLog::EventType event_type,
382
int net_error) const;
384
// Logs a byte transfer event to the NetLog. Determines whether to log the
385
// received bytes or not based on the current logging level.
386
void AddByteTransferEvent(NetLog::EventType event_type,
387
int byte_count, const char* bytes) const;
389
NetLog::LogLevel GetLogLevel() const;
391
// Shortcut for NetLog::IsLoggingBytes(this->GetLogLevel()).
392
bool IsLoggingBytes() const;
394
// Shortcut for NetLog::IsLoggingAllEvents(this->GetLogLevel()).
395
bool IsLoggingAllEvents() const;
397
// Helper to create a BoundNetLog given a NetLog and a SourceType. Takes care
398
// of creating a unique source ID, and handles the case of NULL net_log.
399
static BoundNetLog Make(NetLog* net_log, NetLog::SourceType source_type);
401
const NetLog::Source& source() const { return source_; }
402
NetLog* net_log() const { return net_log_; }
405
BoundNetLog(const NetLog::Source& source, NetLog* net_log)
406
: source_(source), net_log_(net_log) {
409
NetLog::Source source_;
415
#endif // NET_BASE_NET_LOG_H_