tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

DelayBuffer.h (3882B)


      1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
      2 /* vim:set ts=2 sw=2 sts=2 et cindent: */
      3 /* This Source Code Form is subject to the terms of the Mozilla Public
      4 * License, v. 2.0. If a copy of the MPL was not distributed with this
      5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      6 
      7 #ifndef DelayBuffer_h_
      8 #define DelayBuffer_h_
      9 
     10 #include "AudioBlock.h"
     11 #include "AudioSegment.h"
     12 #include "mozilla/dom/AudioNodeBinding.h"  // for ChannelInterpretation
     13 #include "nsTArray.h"
     14 
     15 namespace mozilla {
     16 
     17 class DelayBuffer final {
     18  typedef dom::ChannelInterpretation ChannelInterpretation;
     19 
     20 public:
     21  explicit DelayBuffer(float aMaxDelayTicks)
     22      // Round the maximum delay up to the next tick.
     23      : mMaxDelayTicks(std::ceil(aMaxDelayTicks)),
     24        mCurrentChunk(0)
     25  // mLastReadChunk is initialized in EnsureBuffer
     26 #ifdef DEBUG
     27        ,
     28        mHaveWrittenBlock(false)
     29 #endif
     30  {
     31    // The 180 second limit in AudioContext::CreateDelay() and the
     32    // 1 << MEDIA_TIME_FRAC_BITS limit on sample rate provide a limit on the
     33    // maximum delay.
     34    MOZ_ASSERT(aMaxDelayTicks <=
     35               float(std::numeric_limits<decltype(mMaxDelayTicks)>::max()));
     36  }
     37 
     38  // Write a WEBAUDIO_BLOCK_SIZE block for aChannelCount channels.
     39  void Write(const AudioBlock& aInputChunk);
     40 
     41  // Read a block with an array of delays, in ticks, for each sample frame.
     42  // Each delay should be >= 0 and <= MaxDelayTicks().
     43  void Read(const float aPerFrameDelays[WEBAUDIO_BLOCK_SIZE],
     44            AudioBlock* aOutputChunk,
     45            ChannelInterpretation aChannelInterpretation);
     46  // Read a block with a constant delay. The delay should be >= 0 and
     47  // <= MaxDelayTicks().
     48  void Read(float aDelayTicks, AudioBlock* aOutputChunk,
     49            ChannelInterpretation aChannelInterpretation);
     50 
     51  // Read into one of the channels of aOutputChunk, given an array of
     52  // delays in ticks.  This is useful when delays are different on different
     53  // channels.  aOutputChunk must have already been allocated with at least as
     54  // many channels as were in any of the blocks passed to Write().
     55  void ReadChannel(const float aPerFrameDelays[WEBAUDIO_BLOCK_SIZE],
     56                   AudioBlock* aOutputChunk, uint32_t aChannel,
     57                   ChannelInterpretation aChannelInterpretation);
     58 
     59  // Advance the buffer pointer
     60  void NextBlock() {
     61    mCurrentChunk = (mCurrentChunk + 1) % mChunks.Length();
     62 #ifdef DEBUG
     63    MOZ_ASSERT(mHaveWrittenBlock);
     64    mHaveWrittenBlock = false;
     65 #endif
     66  }
     67 
     68  void Reset() { mChunks.Clear(); };
     69 
     70  int MaxDelayTicks() const { return mMaxDelayTicks; }
     71 
     72  size_t SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const;
     73 
     74 private:
     75  void ReadChannels(const float aPerFrameDelays[WEBAUDIO_BLOCK_SIZE],
     76                    AudioBlock* aOutputChunk, uint32_t aFirstChannel,
     77                    uint32_t aNumChannelsToRead,
     78                    ChannelInterpretation aChannelInterpretation);
     79  bool EnsureBuffer();
     80  int PositionForDelay(int aDelay);
     81  int ChunkForPosition(int aPosition);
     82  int OffsetForPosition(int aPosition);
     83  int ChunkForDelay(int aDelay);
     84  void UpdateUpmixChannels(int aNewReadChunk, uint32_t channelCount,
     85                           ChannelInterpretation aChannelInterpretation);
     86 
     87  // Circular buffer for capturing delayed samples.
     88  FallibleTArray<AudioChunk> mChunks;
     89  // Cached upmixed channel arrays, to avoid repeated allocations.
     90  CopyableAutoTArray<const float*, GUESS_AUDIO_CHANNELS> mUpmixChannels;
     91  // Maximum delay, in ticks
     92  int mMaxDelayTicks;
     93  // The current position in the circular buffer.  The next write will be to
     94  // this chunk, and the next read may begin before this chunk.
     95  int mCurrentChunk;
     96  // The chunk owning the pointers in mUpmixChannels
     97  int mLastReadChunk;
     98 #ifdef DEBUG
     99  bool mHaveWrittenBlock;
    100 #endif
    101 };
    102 
    103 }  // namespace mozilla
    104 
    105 #endif  // DelayBuffer_h_