• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
1 // Copyright (c) 2011 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 CHROME_BROWSER_NET_CHROME_NET_LOG_H_
6 #define CHROME_BROWSER_NET_CHROME_NET_LOG_H_
7 #pragma once
8 
9 #include <vector>
10 
11 #include "base/atomicops.h"
12 #include "base/memory/scoped_ptr.h"
13 #include "base/observer_list.h"
14 #include "base/synchronization/lock.h"
15 #include "base/time.h"
16 #include "net/base/net_log.h"
17 
18 class LoadTimingObserver;
19 class NetLogLogger;
20 class PassiveLogCollector;
21 
22 // ChromeNetLog is an implementation of NetLog that dispatches network log
23 // messages to a list of observers.
24 //
25 // All methods are thread safe, with the exception that no ChromeNetLog or
26 // ChromeNetLog::ThreadSafeObserver functions may be called by an observer's
27 // OnAddEntry() method.  Doing so will result in a deadlock.
28 //
29 // By default, ChromeNetLog will attach the observer PassiveLogCollector which
30 // will keep track of recent request information (which used when displaying
31 // the about:net-internals page).
32 //
33 class ChromeNetLog : public net::NetLog {
34  public:
35   // This structure encapsulates all of the parameters of an event,
36   // including an "order" field that identifies when it was captured relative
37   // to other events.
38   struct Entry {
39     Entry(uint32 order,
40           net::NetLog::EventType type,
41           const base::TimeTicks& time,
42           net::NetLog::Source source,
43           net::NetLog::EventPhase phase,
44           net::NetLog::EventParameters* params);
45     ~Entry();
46 
47     uint32 order;
48     net::NetLog::EventType type;
49     base::TimeTicks time;
50     net::NetLog::Source source;
51     net::NetLog::EventPhase phase;
52     scoped_refptr<net::NetLog::EventParameters> params;
53   };
54 
55   typedef std::vector<Entry> EntryList;
56 
57   // Interface for observing the events logged by the network stack.
58   class ThreadSafeObserver {
59    public:
60     // Constructs an observer that wants to see network events, with
61     // the specified minimum event granularity.  A ThreadSafeObserver can only
62     // observe a single ChromeNetLog at a time.
63     //
64     // Typical observers should specify LOG_BASIC.
65     //
66     // Observers that need to see the full granularity of events can
67     // specify LOG_ALL. However doing so will have performance consequences,
68     // and may cause PassiveLogCollector to use more memory than anticipated.
69     //
70     // Observers will be called on the same thread an entry is added on,
71     // and are responsible for ensuring their own thread safety.
72     explicit ThreadSafeObserver(LogLevel log_level);
73 
74     virtual ~ThreadSafeObserver();
75 
76     // This method will be called on the thread that the event occurs on.  It
77     // is the responsibility of the observer to handle it in a thread safe
78     // manner.
79     //
80     // It is illegal for an Observer to call any ChromeNetLog or
81     // ChromeNetLog::ThreadSafeObserver functions in response to a call to
82     // OnAddEntry.
83     virtual void OnAddEntry(EventType type,
84                             const base::TimeTicks& time,
85                             const Source& source,
86                             EventPhase phase,
87                             EventParameters* params) = 0;
88     LogLevel log_level() const;
89 
90    protected:
91     void AssertNetLogLockAcquired() const;
92 
93     // Can only be called when actively observing a ChromeNetLog.
94     void SetLogLevel(LogLevel log_level);
95 
96     // ChromeNetLog currently being observed, if any.  Set by ChromeNetLog's
97     // AddObserver and RemoveObserver methods.
98     ChromeNetLog* net_log_;
99 
100    private:
101     friend class ChromeNetLog;
102     LogLevel log_level_;
103     DISALLOW_COPY_AND_ASSIGN(ThreadSafeObserver);
104   };
105 
106   ChromeNetLog();
107   ~ChromeNetLog();
108 
109   // NetLog implementation:
110   virtual void AddEntry(EventType type,
111                         const base::TimeTicks& time,
112                         const Source& source,
113                         EventPhase phase,
114                         EventParameters* params);
115   virtual uint32 NextID();
116   virtual LogLevel GetLogLevel() const;
117 
118   void AddObserver(ThreadSafeObserver* observer);
119   void RemoveObserver(ThreadSafeObserver* observer);
120 
121   // Adds |observer| and writes all passively captured events to
122   // |passive_entries|. Guarantees that no events in |passive_entries| will be
123   // sent to |observer| and all future events that have yet been sent to the
124   // PassiveLogCollector will be sent to |observer|.
125   void AddObserverAndGetAllPassivelyCapturedEvents(ThreadSafeObserver* observer,
126                                                    EntryList* passive_entries);
127 
128   void GetAllPassivelyCapturedEvents(EntryList* passive_entries);
129 
130   void ClearAllPassivelyCapturedEvents();
131 
load_timing_observer()132   LoadTimingObserver* load_timing_observer() {
133     return load_timing_observer_.get();
134   }
135 
136  private:
137   void AddObserverWhileLockHeld(ThreadSafeObserver* observer);
138 
139   // Called whenever an observer is added or removed, or changes its log level.
140   // Must have acquired |lock_| prior to calling.
141   void UpdateLogLevel_();
142 
143   // |lock_| protects access to |observers_| and, indirectly, to
144   // |passive_collector_|.  Should not be acquired by observers.
145   base::Lock lock_;
146 
147   // Last assigned source ID.  Incremented to get the next one.
148   base::subtle::Atomic32 last_id_;
149 
150   base::subtle::Atomic32 log_level_;
151 
152   // Not thread safe.  Must only be used when |lock_| is acquired.
153   scoped_ptr<PassiveLogCollector> passive_collector_;
154 
155   scoped_ptr<LoadTimingObserver> load_timing_observer_;
156   scoped_ptr<NetLogLogger> net_log_logger_;
157 
158   // |lock_| must be acquired whenever reading or writing to this.
159   ObserverList<ThreadSafeObserver, true> observers_;
160 
161   DISALLOW_COPY_AND_ASSIGN(ChromeNetLog);
162 };
163 
164 #endif  // CHROME_BROWSER_NET_CHROME_NET_LOG_H_
165