1/*
2 *  Copyright (c) 2014 The WebRTC project authors. All Rights Reserved.
3 *
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
6 *  tree. An additional intellectual property rights grant can be found
7 *  in the file PATENTS.  All contributing project authors may
8 *  be found in the AUTHORS file in the root of the source tree.
9 */
10
11#ifndef WEBRTC_MODULES_AUDIO_CODING_NETEQ_TOOLS_NETEQ_QUALITY_TEST_H_
12#define WEBRTC_MODULES_AUDIO_CODING_NETEQ_TOOLS_NETEQ_QUALITY_TEST_H_
13
14#include <fstream>
15#include <gflags/gflags.h>
16#include "testing/gtest/include/gtest/gtest.h"
17#include "webrtc/base/scoped_ptr.h"
18#include "webrtc/modules/audio_coding/neteq/include/neteq.h"
19#include "webrtc/modules/audio_coding/neteq/tools/audio_sink.h"
20#include "webrtc/modules/audio_coding/neteq/tools/input_audio_file.h"
21#include "webrtc/modules/audio_coding/neteq/tools/rtp_generator.h"
22#include "webrtc/typedefs.h"
23
24using google::RegisterFlagValidator;
25
26namespace webrtc {
27namespace test {
28
29class LossModel {
30 public:
31  virtual ~LossModel() {};
32  virtual bool Lost() = 0;
33};
34
35class NoLoss : public LossModel {
36 public:
37  bool Lost() override;
38};
39
40class UniformLoss : public LossModel {
41 public:
42  UniformLoss(double loss_rate);
43  bool Lost() override;
44  void set_loss_rate(double loss_rate) { loss_rate_ = loss_rate; }
45
46 private:
47  double loss_rate_;
48};
49
50class GilbertElliotLoss : public LossModel {
51 public:
52  GilbertElliotLoss(double prob_trans_11, double prob_trans_01);
53  bool Lost() override;
54
55 private:
56  // Prob. of losing current packet, when previous packet is lost.
57  double prob_trans_11_;
58  // Prob. of losing current packet, when previous packet is not lost.
59  double prob_trans_01_;
60  bool lost_last_;
61  rtc::scoped_ptr<UniformLoss> uniform_loss_model_;
62};
63
64class NetEqQualityTest : public ::testing::Test {
65 protected:
66  NetEqQualityTest(int block_duration_ms,
67                   int in_sampling_khz,
68                   int out_sampling_khz,
69                   NetEqDecoder decoder_type);
70  virtual ~NetEqQualityTest();
71
72  void SetUp() override;
73
74  // EncodeBlock(...) does the following:
75  // 1. encodes a block of audio, saved in |in_data| and has a length of
76  // |block_size_samples| (samples per channel),
77  // 2. save the bit stream to |payload| of |max_bytes| bytes in size,
78  // 3. returns the length of the payload (in bytes),
79  virtual int EncodeBlock(int16_t* in_data, size_t block_size_samples,
80                          uint8_t* payload, size_t max_bytes) = 0;
81
82  // PacketLost(...) determines weather a packet sent at an indicated time gets
83  // lost or not.
84  bool PacketLost();
85
86  // DecodeBlock() decodes a block of audio using the payload stored in
87  // |payload_| with the length of |payload_size_bytes_| (bytes). The decoded
88  // audio is to be stored in |out_data_|.
89  int DecodeBlock();
90
91  // Transmit() uses |rtp_generator_| to generate a packet and passes it to
92  // |neteq_|.
93  int Transmit();
94
95  // Runs encoding / transmitting / decoding.
96  void Simulate();
97
98  // Write to log file. Usage Log() << ...
99  std::ofstream& Log();
100
101  NetEqDecoder decoder_type_;
102  const size_t channels_;
103
104 private:
105  int decoded_time_ms_;
106  int decodable_time_ms_;
107  double drift_factor_;
108  int packet_loss_rate_;
109  const int block_duration_ms_;
110  const int in_sampling_khz_;
111  const int out_sampling_khz_;
112
113  // Number of samples per channel in a frame.
114  const size_t in_size_samples_;
115
116  // Expected output number of samples per channel in a frame.
117  const size_t out_size_samples_;
118
119  size_t payload_size_bytes_;
120  size_t max_payload_bytes_;
121
122  rtc::scoped_ptr<InputAudioFile> in_file_;
123  rtc::scoped_ptr<AudioSink> output_;
124  std::ofstream log_file_;
125
126  rtc::scoped_ptr<RtpGenerator> rtp_generator_;
127  rtc::scoped_ptr<NetEq> neteq_;
128  rtc::scoped_ptr<LossModel> loss_model_;
129
130  rtc::scoped_ptr<int16_t[]> in_data_;
131  rtc::scoped_ptr<uint8_t[]> payload_;
132  rtc::scoped_ptr<int16_t[]> out_data_;
133  WebRtcRTPHeader rtp_header_;
134
135  size_t total_payload_size_bytes_;
136};
137
138}  // namespace test
139}  // namespace webrtc
140
141#endif  // WEBRTC_MODULES_AUDIO_CODING_NETEQ_TOOLS_NETEQ_QUALITY_TEST_H_
142