• Home
  • Line#
  • Scopes#
  • Navigate#
  • Raw
  • Download
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 #include "modules/audio_coding/codecs/g711/audio_encoder_pcm.h"
12 
13 #include <cstdint>
14 
15 #include "modules/audio_coding/codecs/g711/g711_interface.h"
16 #include "rtc_base/checks.h"
17 
18 namespace webrtc {
19 
IsOk() const20 bool AudioEncoderPcm::Config::IsOk() const {
21   return (frame_size_ms % 10 == 0) && (num_channels >= 1);
22 }
23 
AudioEncoderPcm(const Config & config,int sample_rate_hz)24 AudioEncoderPcm::AudioEncoderPcm(const Config& config, int sample_rate_hz)
25     : sample_rate_hz_(sample_rate_hz),
26       num_channels_(config.num_channels),
27       payload_type_(config.payload_type),
28       num_10ms_frames_per_packet_(
29           static_cast<size_t>(config.frame_size_ms / 10)),
30       full_frame_samples_(config.num_channels * config.frame_size_ms *
31                           sample_rate_hz / 1000),
32       first_timestamp_in_buffer_(0) {
33   RTC_CHECK_GT(sample_rate_hz, 0) << "Sample rate must be larger than 0 Hz";
34   RTC_CHECK_EQ(config.frame_size_ms % 10, 0)
35       << "Frame size must be an integer multiple of 10 ms.";
36   speech_buffer_.reserve(full_frame_samples_);
37 }
38 
39 AudioEncoderPcm::~AudioEncoderPcm() = default;
40 
SampleRateHz() const41 int AudioEncoderPcm::SampleRateHz() const {
42   return sample_rate_hz_;
43 }
44 
NumChannels() const45 size_t AudioEncoderPcm::NumChannels() const {
46   return num_channels_;
47 }
48 
Num10MsFramesInNextPacket() const49 size_t AudioEncoderPcm::Num10MsFramesInNextPacket() const {
50   return num_10ms_frames_per_packet_;
51 }
52 
Max10MsFramesInAPacket() const53 size_t AudioEncoderPcm::Max10MsFramesInAPacket() const {
54   return num_10ms_frames_per_packet_;
55 }
56 
GetTargetBitrate() const57 int AudioEncoderPcm::GetTargetBitrate() const {
58   return static_cast<int>(8 * BytesPerSample() * SampleRateHz() *
59                           NumChannels());
60 }
61 
EncodeImpl(uint32_t rtp_timestamp,rtc::ArrayView<const int16_t> audio,rtc::Buffer * encoded)62 AudioEncoder::EncodedInfo AudioEncoderPcm::EncodeImpl(
63     uint32_t rtp_timestamp,
64     rtc::ArrayView<const int16_t> audio,
65     rtc::Buffer* encoded) {
66   if (speech_buffer_.empty()) {
67     first_timestamp_in_buffer_ = rtp_timestamp;
68   }
69   speech_buffer_.insert(speech_buffer_.end(), audio.begin(), audio.end());
70   if (speech_buffer_.size() < full_frame_samples_) {
71     return EncodedInfo();
72   }
73   RTC_CHECK_EQ(speech_buffer_.size(), full_frame_samples_);
74   EncodedInfo info;
75   info.encoded_timestamp = first_timestamp_in_buffer_;
76   info.payload_type = payload_type_;
77   info.encoded_bytes = encoded->AppendData(
78       full_frame_samples_ * BytesPerSample(),
79       [&](rtc::ArrayView<uint8_t> encoded) {
80         return EncodeCall(&speech_buffer_[0], full_frame_samples_,
81                           encoded.data());
82       });
83   speech_buffer_.clear();
84   info.encoder_type = GetCodecType();
85   return info;
86 }
87 
Reset()88 void AudioEncoderPcm::Reset() {
89   speech_buffer_.clear();
90 }
91 
92 absl::optional<std::pair<TimeDelta, TimeDelta>>
GetFrameLengthRange() const93 AudioEncoderPcm::GetFrameLengthRange() const {
94   return {{TimeDelta::Millis(num_10ms_frames_per_packet_ * 10),
95            TimeDelta::Millis(num_10ms_frames_per_packet_ * 10)}};
96 }
97 
EncodeCall(const int16_t * audio,size_t input_len,uint8_t * encoded)98 size_t AudioEncoderPcmA::EncodeCall(const int16_t* audio,
99                                     size_t input_len,
100                                     uint8_t* encoded) {
101   return WebRtcG711_EncodeA(audio, input_len, encoded);
102 }
103 
BytesPerSample() const104 size_t AudioEncoderPcmA::BytesPerSample() const {
105   return 1;
106 }
107 
GetCodecType() const108 AudioEncoder::CodecType AudioEncoderPcmA::GetCodecType() const {
109   return AudioEncoder::CodecType::kPcmA;
110 }
111 
EncodeCall(const int16_t * audio,size_t input_len,uint8_t * encoded)112 size_t AudioEncoderPcmU::EncodeCall(const int16_t* audio,
113                                     size_t input_len,
114                                     uint8_t* encoded) {
115   return WebRtcG711_EncodeU(audio, input_len, encoded);
116 }
117 
BytesPerSample() const118 size_t AudioEncoderPcmU::BytesPerSample() const {
119   return 1;
120 }
121 
GetCodecType() const122 AudioEncoder::CodecType AudioEncoderPcmU::GetCodecType() const {
123   return AudioEncoder::CodecType::kPcmU;
124 }
125 
126 }  // namespace webrtc
127