OLD | NEW |
| (Empty) |
1 // Copyright 2015 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 REMOTING_HOST_VIDEO_FRAME_PUMP_H_ | |
6 #define REMOTING_HOST_VIDEO_FRAME_PUMP_H_ | |
7 | |
8 #include "base/basictypes.h" | |
9 #include "base/memory/ref_counted.h" | |
10 #include "base/memory/scoped_ptr.h" | |
11 #include "base/memory/scoped_vector.h" | |
12 #include "base/threading/thread_checker.h" | |
13 #include "base/time/time.h" | |
14 #include "base/timer/timer.h" | |
15 #include "remoting/codec/video_encoder.h" | |
16 #include "remoting/host/capture_scheduler.h" | |
17 #include "remoting/proto/video.pb.h" | |
18 #include "third_party/webrtc/modules/desktop_capture/desktop_capturer.h" | |
19 | |
20 namespace base { | |
21 class SingleThreadTaskRunner; | |
22 } // namespace base | |
23 | |
24 namespace remoting { | |
25 | |
26 namespace protocol { | |
27 class VideoFeedbackStub; | |
28 class VideoStub; | |
29 } // namespace protocol | |
30 | |
31 // Class responsible for scheduling frame captures from a screen capturer., | |
32 // delivering them to a VideoEncoder to encode, and | |
33 // finally passing the encoded video packets to the specified VideoStub to send | |
34 // on the network. | |
35 // | |
36 // THREADING | |
37 // | |
38 // This class is supplied TaskRunners to use for capture, encode and network | |
39 // operations. Capture, encode and network transmission tasks are interleaved | |
40 // as illustrated below: | |
41 // | |
42 // | CAPTURE ENCODE NETWORK | |
43 // | ............. | |
44 // | . Capture . | |
45 // | ............. | |
46 // | ............ | |
47 // | . . | |
48 // | ............. . . | |
49 // | . Capture . . Encode . | |
50 // | ............. . . | |
51 // | . . | |
52 // | ............ | |
53 // | ............. ............ .......... | |
54 // | . Capture . . . . Send . | |
55 // | ............. . . .......... | |
56 // | . Encode . | |
57 // | . . | |
58 // | . . | |
59 // | ............ | |
60 // | Time | |
61 // v | |
62 // | |
63 // VideoFramePump would ideally schedule captures so as to saturate the slowest | |
64 // of the capture, encode and network processes. However, it also needs to | |
65 // rate-limit captures to avoid overloading the host system, either by consuming | |
66 // too much CPU, or hogging the host's graphics subsystem. | |
67 class VideoFramePump : public webrtc::DesktopCapturer::Callback { | |
68 public: | |
69 // Enables timestamps for generated frames. Used for testing. | |
70 static void EnableTimestampsForTests(); | |
71 | |
72 // Creates a VideoFramePump running capture, encode and network tasks on the | |
73 // supplied TaskRunners. Video will be pumped to |video_stub|, which must | |
74 // outlive the pump.. | |
75 VideoFramePump( | |
76 scoped_refptr<base::SingleThreadTaskRunner> encode_task_runner, | |
77 scoped_ptr<webrtc::DesktopCapturer> capturer, | |
78 scoped_ptr<VideoEncoder> encoder, | |
79 protocol::VideoStub* video_stub); | |
80 ~VideoFramePump() override; | |
81 | |
82 // Pauses or resumes scheduling of frame captures. Pausing/resuming captures | |
83 // only affects capture scheduling and does not stop/start the capturer. | |
84 void Pause(bool pause); | |
85 | |
86 // Called whenever input event is received. | |
87 void OnInputEventReceived(int64_t event_timestamp); | |
88 | |
89 // Sets whether the video encoder should be requested to encode losslessly, | |
90 // or to use a lossless color space (typically requiring higher bandwidth). | |
91 void SetLosslessEncode(bool want_lossless); | |
92 void SetLosslessColor(bool want_lossless); | |
93 | |
94 protocol::VideoFeedbackStub* video_feedback_stub() { | |
95 return &capture_scheduler_; | |
96 } | |
97 | |
98 private: | |
99 struct FrameTimestamps { | |
100 FrameTimestamps(); | |
101 ~FrameTimestamps(); | |
102 | |
103 // The following two fields are set only for one frame after each incoming | |
104 // input event. |input_event_client_timestamp| is event timestamp | |
105 // received from the client. |input_event_received_time| is local time when | |
106 // the event was received. | |
107 int64_t input_event_client_timestamp = -1; | |
108 base::TimeTicks input_event_received_time; | |
109 | |
110 base::TimeTicks capture_started_time; | |
111 base::TimeTicks capture_ended_time; | |
112 base::TimeTicks encode_started_time; | |
113 base::TimeTicks encode_ended_time; | |
114 base::TimeTicks can_send_time; | |
115 }; | |
116 | |
117 struct PacketWithTimestamps { | |
118 PacketWithTimestamps(scoped_ptr<VideoPacket> packet, | |
119 scoped_ptr<FrameTimestamps> timestamps); | |
120 ~PacketWithTimestamps(); | |
121 | |
122 scoped_ptr<VideoPacket> packet; | |
123 scoped_ptr<FrameTimestamps> timestamps; | |
124 }; | |
125 | |
126 // webrtc::DesktopCapturer::Callback interface. | |
127 webrtc::SharedMemory* CreateSharedMemory(size_t size) override; | |
128 void OnCaptureCompleted(webrtc::DesktopFrame* frame) override; | |
129 | |
130 // Callback for CaptureScheduler. | |
131 void CaptureNextFrame(); | |
132 | |
133 // Task running on the encoder thread to encode the |frame|. | |
134 static scoped_ptr<PacketWithTimestamps> EncodeFrame( | |
135 VideoEncoder* encoder, | |
136 scoped_ptr<webrtc::DesktopFrame> frame, | |
137 scoped_ptr<FrameTimestamps> timestamps); | |
138 | |
139 // Task called when a frame has finished encoding. | |
140 void OnFrameEncoded(scoped_ptr<PacketWithTimestamps> packet); | |
141 | |
142 // Sends |packet| to the client. | |
143 void SendPacket(scoped_ptr<PacketWithTimestamps> packet); | |
144 | |
145 // Helper called from SendPacket() to calculate timing fields in the |packet| | |
146 // before sending it. | |
147 void UpdateFrameTimers(VideoPacket* packet, FrameTimestamps* timestamps); | |
148 | |
149 // Callback passed to |video_stub_|. | |
150 void OnVideoPacketSent(); | |
151 | |
152 // Called by |keep_alive_timer_|. | |
153 void SendKeepAlivePacket(); | |
154 | |
155 // Callback for |video_stub_| called after a keep-alive packet is sent. | |
156 void OnKeepAlivePacketSent(); | |
157 | |
158 // Task runner used to run |encoder_|. | |
159 scoped_refptr<base::SingleThreadTaskRunner> encode_task_runner_; | |
160 | |
161 // Capturer used to capture the screen. | |
162 scoped_ptr<webrtc::DesktopCapturer> capturer_; | |
163 | |
164 // Used to encode captured frames. Always accessed on the encode thread. | |
165 scoped_ptr<VideoEncoder> encoder_; | |
166 | |
167 // Interface through which video frames are passed to the client. | |
168 protocol::VideoStub* video_stub_; | |
169 | |
170 // Timer used to ensure that we send empty keep-alive frames to the client | |
171 // even when the video stream is paused or encoder is busy. | |
172 base::Timer keep_alive_timer_; | |
173 | |
174 // CaptureScheduler calls CaptureNextFrame() whenever a new frame needs to be | |
175 // captured. | |
176 CaptureScheduler capture_scheduler_; | |
177 | |
178 // Timestamps for the frame to be captured next. | |
179 scoped_ptr<FrameTimestamps> next_frame_timestamps_; | |
180 | |
181 // Timestamps for the frame that's being captured. | |
182 scoped_ptr<FrameTimestamps> captured_frame_timestamps_; | |
183 | |
184 bool send_pending_ = false; | |
185 | |
186 ScopedVector<PacketWithTimestamps> pending_packets_; | |
187 | |
188 base::ThreadChecker thread_checker_; | |
189 | |
190 base::WeakPtrFactory<VideoFramePump> weak_factory_; | |
191 | |
192 DISALLOW_COPY_AND_ASSIGN(VideoFramePump); | |
193 }; | |
194 | |
195 } // namespace remoting | |
196 | |
197 #endif // REMOTING_HOST_VIDEO_FRAME_PUMP_H_ | |
OLD | NEW |