/usr/include/thunderbird/AudioMixer.h is in thunderbird-dev 1:52.8.0-1~deb8u1.
This file is owned by root:root, with mode 0o644.
The actual contents of the file can be viewed below.
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 | /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this file,
* You can obtain one at http://mozilla.org/MPL/2.0/. */
#ifndef MOZILLA_AUDIOMIXER_H_
#define MOZILLA_AUDIOMIXER_H_
#include "AudioSampleFormat.h"
#include "nsTArray.h"
#include "mozilla/PodOperations.h"
#include "mozilla/LinkedList.h"
#include "AudioStream.h"
namespace mozilla {
struct MixerCallbackReceiver {
virtual void MixerCallback(AudioDataValue* aMixedBuffer,
AudioSampleFormat aFormat,
uint32_t aChannels,
uint32_t aFrames,
uint32_t aSampleRate) = 0;
};
/**
* This class mixes multiple streams of audio together to output a single audio
* stream.
*
* AudioMixer::Mix is to be called repeatedly with buffers that have the same
* length, sample rate, sample format and channel count. This class works with
* interleaved and plannar buffers, but the buffer mixed must be of the same
* type during a mixing cycle.
*
* When all the tracks have been mixed, calling FinishMixing will call back with
* a buffer containing the mixed audio data.
*
* This class is not thread safe.
*/
class AudioMixer
{
public:
AudioMixer()
: mFrames(0),
mChannels(0),
mSampleRate(0)
{ }
~AudioMixer()
{
MixerCallback* cb;
while ((cb = mCallbacks.popFirst())) {
delete cb;
}
}
void StartMixing()
{
mSampleRate = mChannels = mFrames = 0;
}
/* Get the data from the mixer. This is supposed to be called when all the
* tracks have been mixed in. The caller should not hold onto the data. */
void FinishMixing() {
MOZ_ASSERT(mChannels && mFrames && mSampleRate, "Mix not called for this cycle?");
for (MixerCallback* cb = mCallbacks.getFirst();
cb != nullptr; cb = cb->getNext()) {
cb->mReceiver->MixerCallback(mMixedAudio.Elements(),
AudioSampleTypeToFormat<AudioDataValue>::Format,
mChannels,
mFrames,
mSampleRate);
}
PodZero(mMixedAudio.Elements(), mMixedAudio.Length());
mSampleRate = mChannels = mFrames = 0;
}
/* Add a buffer to the mix. */
void Mix(AudioDataValue* aSamples,
uint32_t aChannels,
uint32_t aFrames,
uint32_t aSampleRate) {
if (!mFrames && !mChannels) {
mFrames = aFrames;
mChannels = aChannels;
mSampleRate = aSampleRate;
EnsureCapacityAndSilence();
}
MOZ_ASSERT(aFrames == mFrames);
MOZ_ASSERT(aChannels == mChannels);
MOZ_ASSERT(aSampleRate == mSampleRate);
for (uint32_t i = 0; i < aFrames * aChannels; i++) {
mMixedAudio[i] += aSamples[i];
}
}
void AddCallback(MixerCallbackReceiver* aReceiver) {
mCallbacks.insertBack(new MixerCallback(aReceiver));
}
bool FindCallback(MixerCallbackReceiver* aReceiver) {
for (MixerCallback* cb = mCallbacks.getFirst();
cb != nullptr; cb = cb->getNext()) {
if (cb->mReceiver == aReceiver) {
return true;
}
}
return false;
}
bool RemoveCallback(MixerCallbackReceiver* aReceiver) {
for (MixerCallback* cb = mCallbacks.getFirst();
cb != nullptr; cb = cb->getNext()) {
if (cb->mReceiver == aReceiver) {
cb->remove();
delete cb;
return true;
}
}
return false;
}
private:
void EnsureCapacityAndSilence() {
if (mFrames * mChannels > mMixedAudio.Length()) {
mMixedAudio.SetLength(mFrames* mChannels);
}
PodZero(mMixedAudio.Elements(), mMixedAudio.Length());
}
class MixerCallback : public LinkedListElement<MixerCallback>
{
public:
explicit MixerCallback(MixerCallbackReceiver* aReceiver)
: mReceiver(aReceiver)
{ }
MixerCallbackReceiver* mReceiver;
};
/* Function that is called when the mixing is done. */
LinkedList<MixerCallback> mCallbacks;
/* Number of frames for this mixing block. */
uint32_t mFrames;
/* Number of channels for this mixing block. */
uint32_t mChannels;
/* Sample rate the of the mixed data. */
uint32_t mSampleRate;
/* Buffer containing the mixed audio data. */
nsTArray<AudioDataValue> mMixedAudio;
};
} // namespace mozilla
#endif // MOZILLA_AUDIOMIXER_H_
|