OLD | NEW |
---|---|
1 /* | 1 /* |
2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved. | 2 * Copyright (c) 2015 The WebRTC project authors. All Rights Reserved. |
3 * | 3 * |
4 * Use of this source code is governed by a BSD-style license | 4 * Use of this source code is governed by a BSD-style license |
5 * that can be found in the LICENSE file in the root of the source | 5 * that can be found in the LICENSE file in the root of the source |
6 * tree. An additional intellectual property rights grant can be found | 6 * tree. An additional intellectual property rights grant can be found |
7 * in the file PATENTS. All contributing project authors may | 7 * in the file PATENTS. All contributing project authors may |
8 * be found in the AUTHORS file in the root of the source tree. | 8 * be found in the AUTHORS file in the root of the source tree. |
9 */ | 9 */ |
10 #include <stdio.h> | 10 #include <stdio.h> |
(...skipping 25 matching lines...) Expand all Loading... | |
36 | 36 |
37 namespace webrtc { | 37 namespace webrtc { |
38 | 38 |
39 static const int kSendStatsPollingIntervalMs = 1000; | 39 static const int kSendStatsPollingIntervalMs = 1000; |
40 static const int kPayloadTypeVP8 = 123; | 40 static const int kPayloadTypeVP8 = 123; |
41 static const int kPayloadTypeVP9 = 124; | 41 static const int kPayloadTypeVP9 = 124; |
42 | 42 |
43 class VideoAnalyzer : public PacketReceiver, | 43 class VideoAnalyzer : public PacketReceiver, |
44 public Transport, | 44 public Transport, |
45 public VideoRenderer, | 45 public VideoRenderer, |
46 public VideoCaptureInput, | |
47 public EncodedFrameObserver, | 46 public EncodedFrameObserver, |
48 public EncodingTimeObserver { | 47 public EncodingTimeObserver { |
49 public: | 48 public: |
50 VideoAnalyzer(test::LayerFilteringTransport* transport, | 49 VideoAnalyzer(test::LayerFilteringTransport* transport, |
51 const std::string& test_label, | 50 const std::string& test_label, |
52 double avg_psnr_threshold, | 51 double avg_psnr_threshold, |
53 double avg_ssim_threshold, | 52 double avg_ssim_threshold, |
54 int duration_frames, | 53 int duration_frames, |
55 FILE* graph_data_output_file, | 54 FILE* graph_data_output_file, |
56 const std::string& graph_title, | 55 const std::string& graph_title, |
57 uint32_t ssrc_to_analyze) | 56 uint32_t ssrc_to_analyze) |
58 : input_(nullptr), | 57 : transport_(transport), |
59 transport_(transport), | |
60 receiver_(nullptr), | 58 receiver_(nullptr), |
61 send_stream_(nullptr), | 59 send_stream_(nullptr), |
62 test_label_(test_label), | 60 test_label_(test_label), |
63 graph_data_output_file_(graph_data_output_file), | 61 graph_data_output_file_(graph_data_output_file), |
64 graph_title_(graph_title), | 62 graph_title_(graph_title), |
65 ssrc_to_analyze_(ssrc_to_analyze), | 63 ssrc_to_analyze_(ssrc_to_analyze), |
66 frames_to_process_(duration_frames), | 64 frames_to_process_(duration_frames), |
67 frames_recorded_(0), | 65 frames_recorded_(0), |
68 frames_processed_(0), | 66 frames_processed_(0), |
69 dropped_frames_(0), | 67 dropped_frames_(0), |
(...skipping 55 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
125 | 123 |
126 return receiver_->DeliverPacket(media_type, packet, length, packet_time); | 124 return receiver_->DeliverPacket(media_type, packet, length, packet_time); |
127 } | 125 } |
128 | 126 |
129 // EncodingTimeObserver. | 127 // EncodingTimeObserver. |
130 void OnReportEncodedTime(int64_t ntp_time_ms, int encode_time_ms) override { | 128 void OnReportEncodedTime(int64_t ntp_time_ms, int encode_time_ms) override { |
131 rtc::CritScope crit(&comparison_lock_); | 129 rtc::CritScope crit(&comparison_lock_); |
132 samples_encode_time_ms_[ntp_time_ms] = encode_time_ms; | 130 samples_encode_time_ms_[ntp_time_ms] = encode_time_ms; |
133 } | 131 } |
134 | 132 |
135 void IncomingCapturedFrame(const VideoFrame& video_frame) override { | |
136 VideoFrame copy = video_frame; | |
137 copy.set_timestamp(copy.ntp_time_ms() * 90); | |
138 | |
139 { | |
140 rtc::CritScope lock(&crit_); | |
141 if (first_send_frame_.IsZeroSize() && rtp_timestamp_delta_ == 0) | |
142 first_send_frame_ = copy; | |
143 | |
144 frames_.push_back(copy); | |
145 } | |
146 | |
147 input_->IncomingCapturedFrame(video_frame); | |
148 } | |
149 | |
150 bool SendRtp(const uint8_t* packet, | 133 bool SendRtp(const uint8_t* packet, |
151 size_t length, | 134 size_t length, |
152 const PacketOptions& options) override { | 135 const PacketOptions& options) override { |
153 RtpUtility::RtpHeaderParser parser(packet, length); | 136 RtpUtility::RtpHeaderParser parser(packet, length); |
154 RTPHeader header; | 137 RTPHeader header; |
155 parser.Parse(header); | 138 parser.Parse(header); |
156 | 139 |
157 int64_t current_time = | 140 int64_t current_time = |
158 Clock::GetRealTimeClock()->CurrentNtpInMilliseconds(); | 141 Clock::GetRealTimeClock()->CurrentNtpInMilliseconds(); |
159 bool result = transport_->SendRtp(packet, length, options); | 142 bool result = transport_->SendRtp(packet, length, options); |
(...skipping 17 matching lines...) Expand all Loading... | |
177 bool SendRtcp(const uint8_t* packet, size_t length) override { | 160 bool SendRtcp(const uint8_t* packet, size_t length) override { |
178 return transport_->SendRtcp(packet, length); | 161 return transport_->SendRtcp(packet, length); |
179 } | 162 } |
180 | 163 |
181 void EncodedFrameCallback(const EncodedFrame& frame) override { | 164 void EncodedFrameCallback(const EncodedFrame& frame) override { |
182 rtc::CritScope lock(&comparison_lock_); | 165 rtc::CritScope lock(&comparison_lock_); |
183 if (frames_recorded_ < frames_to_process_) | 166 if (frames_recorded_ < frames_to_process_) |
184 encoded_frame_size_.AddSample(frame.length_); | 167 encoded_frame_size_.AddSample(frame.length_); |
185 } | 168 } |
186 | 169 |
187 void RenderFrame(const VideoFrame& video_frame, | 170 void RenderFrame(const VideoFrame& video_frame, |
pbos-webrtc
2015/12/19 11:02:34
Put a comment on this function to document that th
| |
188 int time_to_render_ms) override { | 171 int time_to_render_ms) override { |
172 rtc::CritScope lock(&crit_); | |
173 uint32_t last_timestamp = | |
174 frames_.empty() ? 0 : frames_.rbegin()->timestamp(); | |
175 if (video_frame.timestamp() > last_timestamp) { | |
176 // This is must be an input frame, just add a copy to frames_ and return. | |
177 if (first_send_frame_.IsZeroSize() && rtp_timestamp_delta_ == 0) | |
178 first_send_frame_ = video_frame; | |
179 | |
180 frames_.push_back(video_frame); | |
181 return; | |
182 } | |
183 | |
189 int64_t render_time_ms = | 184 int64_t render_time_ms = |
190 Clock::GetRealTimeClock()->CurrentNtpInMilliseconds(); | 185 Clock::GetRealTimeClock()->CurrentNtpInMilliseconds(); |
191 uint32_t send_timestamp = video_frame.timestamp() - rtp_timestamp_delta_; | 186 uint32_t send_timestamp = video_frame.timestamp() - rtp_timestamp_delta_; |
192 | 187 |
193 rtc::CritScope lock(&crit_); | |
194 | |
195 while (frames_.front().timestamp() < send_timestamp) { | 188 while (frames_.front().timestamp() < send_timestamp) { |
196 AddFrameComparison(frames_.front(), last_rendered_frame_, true, | 189 AddFrameComparison(frames_.front(), last_rendered_frame_, true, |
197 render_time_ms); | 190 render_time_ms); |
198 frames_.pop_front(); | 191 frames_.pop_front(); |
199 } | 192 } |
200 | 193 |
201 VideoFrame reference_frame = frames_.front(); | 194 VideoFrame reference_frame = frames_.front(); |
202 frames_.pop_front(); | 195 frames_.pop_front(); |
203 assert(!reference_frame.IsZeroSize()); | 196 assert(!reference_frame.IsZeroSize()); |
204 if (send_timestamp == reference_frame.timestamp() - 1) { | 197 if (send_timestamp == reference_frame.timestamp() - 1) { |
(...skipping 46 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
251 if (iteration > 0) | 244 if (iteration > 0) |
252 printf("- Farewell, sweet Concorde!\n"); | 245 printf("- Farewell, sweet Concorde!\n"); |
253 | 246 |
254 // Signal stats polling thread if that is still waiting and stop it now, | 247 // Signal stats polling thread if that is still waiting and stop it now, |
255 // since it uses the send_stream_ reference that might be reclaimed after | 248 // since it uses the send_stream_ reference that might be reclaimed after |
256 // returning from this method. | 249 // returning from this method. |
257 done_.Set(); | 250 done_.Set(); |
258 stats_polling_thread_.Stop(); | 251 stats_polling_thread_.Stop(); |
259 } | 252 } |
260 | 253 |
261 VideoCaptureInput* input_; | |
262 test::LayerFilteringTransport* const transport_; | 254 test::LayerFilteringTransport* const transport_; |
263 PacketReceiver* receiver_; | 255 PacketReceiver* receiver_; |
264 VideoSendStream* send_stream_; | 256 VideoSendStream* send_stream_; |
265 | 257 |
266 private: | 258 private: |
267 struct FrameComparison { | 259 struct FrameComparison { |
268 FrameComparison() | 260 FrameComparison() |
269 : dropped(false), | 261 : dropped(false), |
270 send_time_ms(0), | 262 send_time_ms(0), |
271 recv_time_ms(0), | 263 recv_time_ms(0), |
(...skipping 691 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
963 params_.analyzer.test_durations_secs * params_.common.fps, | 955 params_.analyzer.test_durations_secs * params_.common.fps, |
964 graph_data_output_file, graph_title, | 956 graph_data_output_file, graph_title, |
965 kSendSsrcs[params_.ss.selected_stream]); | 957 kSendSsrcs[params_.ss.selected_stream]); |
966 | 958 |
967 analyzer.SetReceiver(receiver_call_->Receiver()); | 959 analyzer.SetReceiver(receiver_call_->Receiver()); |
968 send_transport.SetReceiver(&analyzer); | 960 send_transport.SetReceiver(&analyzer); |
969 recv_transport.SetReceiver(sender_call_->Receiver()); | 961 recv_transport.SetReceiver(sender_call_->Receiver()); |
970 | 962 |
971 SetupCommon(&analyzer, &recv_transport); | 963 SetupCommon(&analyzer, &recv_transport); |
972 send_config_.encoding_time_observer = &analyzer; | 964 send_config_.encoding_time_observer = &analyzer; |
965 send_config_.local_renderer = &analyzer; | |
973 receive_configs_[params_.ss.selected_stream].renderer = &analyzer; | 966 receive_configs_[params_.ss.selected_stream].renderer = &analyzer; |
974 for (auto& config : receive_configs_) | 967 for (auto& config : receive_configs_) |
975 config.pre_decode_callback = &analyzer; | 968 config.pre_decode_callback = &analyzer; |
976 | 969 |
977 if (params_.screenshare.enabled) | 970 if (params_.screenshare.enabled) |
978 SetupScreenshare(); | 971 SetupScreenshare(); |
979 | 972 |
980 CreateStreams(); | 973 CreateStreams(); |
981 analyzer.input_ = send_stream_->Input(); | |
982 analyzer.send_stream_ = send_stream_; | 974 analyzer.send_stream_ = send_stream_; |
983 | 975 |
984 CreateCapturer(&analyzer); | 976 CreateCapturer(send_stream_->Input()); |
985 | 977 |
986 send_stream_->Start(); | 978 send_stream_->Start(); |
987 for (size_t i = 0; i < receive_streams_.size(); ++i) | 979 for (size_t i = 0; i < receive_streams_.size(); ++i) |
988 receive_streams_[i]->Start(); | 980 receive_streams_[i]->Start(); |
989 capturer_->Start(); | 981 capturer_->Start(); |
990 | 982 |
991 analyzer.Wait(); | 983 analyzer.Wait(); |
992 | 984 |
993 send_transport.StopSending(); | 985 send_transport.StopSending(); |
994 recv_transport.StopSending(); | 986 recv_transport.StopSending(); |
(...skipping 66 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... | |
1061 send_stream_->Stop(); | 1053 send_stream_->Stop(); |
1062 receive_stream->Stop(); | 1054 receive_stream->Stop(); |
1063 | 1055 |
1064 call->DestroyVideoReceiveStream(receive_stream); | 1056 call->DestroyVideoReceiveStream(receive_stream); |
1065 call->DestroyVideoSendStream(send_stream_); | 1057 call->DestroyVideoSendStream(send_stream_); |
1066 | 1058 |
1067 transport.StopSending(); | 1059 transport.StopSending(); |
1068 } | 1060 } |
1069 | 1061 |
1070 } // namespace webrtc | 1062 } // namespace webrtc |
OLD | NEW |