File: audio_node_output.h

package info (click to toggle)
chromium 138.0.7204.183-1
  • links: PTS, VCS
  • area: main
  • in suites: trixie
  • size: 6,071,908 kB
  • sloc: cpp: 34,937,088; ansic: 7,176,967; javascript: 4,110,704; python: 1,419,953; asm: 946,768; xml: 739,971; pascal: 187,324; sh: 89,623; perl: 88,663; objc: 79,944; sql: 50,304; cs: 41,786; fortran: 24,137; makefile: 21,806; php: 13,980; tcl: 13,166; yacc: 8,925; ruby: 7,485; awk: 3,720; lisp: 3,096; lex: 1,327; ada: 727; jsp: 228; sed: 36
file content (182 lines) | stat: -rw-r--r-- 7,780 bytes parent folder | download | duplicates (7)
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
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
/*
 * Copyright (C) 2010, Google Inc. All rights reserved.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions
 * are met:
 * 1.  Redistributions of source code must retain the above copyright
 *    notice, this list of conditions and the following disclaimer.
 * 2.  Redistributions in binary form must reproduce the above copyright
 *    notice, this list of conditions and the following disclaimer in the
 *    documentation and/or other materials provided with the distribution.
 *
 * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND
 * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
 * ARE DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE
 * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
 * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR
 * SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER
 * CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
 * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
 * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH
 * DAMAGE.
 */

#ifndef THIRD_PARTY_BLINK_RENDERER_MODULES_WEBAUDIO_AUDIO_NODE_OUTPUT_H_
#define THIRD_PARTY_BLINK_RENDERER_MODULES_WEBAUDIO_AUDIO_NODE_OUTPUT_H_

#include "base/memory/raw_ref.h"
#include "base/memory/scoped_refptr.h"
#include "third_party/blink/renderer/modules/modules_export.h"
#include "third_party/blink/renderer/modules/webaudio/audio_node.h"
#include "third_party/blink/renderer/modules/webaudio/audio_param.h"
#include "third_party/blink/renderer/platform/audio/audio_bus.h"
#include "third_party/blink/renderer/platform/wtf/hash_set.h"

namespace blink {

class AudioNodeInput;

// AudioNodeOutput represents a single output for an AudioNode.
// It may be connected to one or more AudioNodeInputs.
class MODULES_EXPORT AudioNodeOutput final {
  USING_FAST_MALLOC(AudioNodeOutput);

 public:
  // It's OK to pass 0 for numberOfChannels in which case
  // setNumberOfChannels() must be called later on.
  AudioNodeOutput(AudioHandler*, unsigned number_of_channels);

  void Dispose();

  // Causes our AudioNode to process if it hasn't already for this render
  // quantum.  It returns the bus containing the processed audio for this
  // output, returning inPlaceBus if in-place processing was possible.  Called
  // from context's audio thread.
  AudioBus* Pull(AudioBus* in_place_bus, uint32_t frames_to_process);

  // bus() will contain the rendered audio after pull() is called for each
  // rendering time quantum.
  // Called from context's audio thread.
  AudioBus* Bus() const;

  // renderingFanOutCount() is the number of AudioNodeInputs that we're
  // connected to during rendering.  Unlike fanOutCount() it will not change
  // during the course of a render quantum.
  unsigned RenderingFanOutCount() const;

  // Returns the number of AudioParams that this output is connected to
  // during rendering. Unlike `ParamFanOutCount()` this will not change
  // during a render quantum. MUST be called from the audio thread.
  unsigned RenderingParamFanOutCount() const;

  // Return true if either `RenderingFanOutCount()` or
  // `RenderingParamFanOutCount()` is greater than zero.
  bool IsConnectedDuringRendering() const;

  // Must be called with the context's graph lock.
  void DisconnectAll();

  // Disconnect a specific input or AudioParam.
  void DisconnectAudioParam(AudioParamHandler&);

  void SetNumberOfChannels(unsigned);
  unsigned NumberOfChannels() const { return number_of_channels_; }
  bool IsChannelCountKnown() const { return NumberOfChannels() > 0; }

  bool IsConnected() { return FanOutCount() > 0 || ParamFanOutCount() > 0; }

  // Disable/Enable happens when there are still JavaScript references to a
  // node, but it has otherwise "finished" its work.  For example, when a note
  // has finished playing.  It is kept around, because it may be played again at
  // a later time.  They must be called with the context's graph lock.
  void Disable();
  void Enable();

  // updateRenderingState() is called in the audio thread at the start or end of
  // the render quantum to handle any recent changes to the graph state.
  // It must be called with the context's graph lock.
  void UpdateRenderingState();

 private:
  // Can be called from any thread.
  AudioHandler& Handler() const { return *handler_; }
  DeferredTaskHandler& GetDeferredTaskHandler() const {
    return handler_->GetDeferredTaskHandler();
  }

  // This reference is safe because the AudioHandler owns this AudioNodeOutput
  // object.
  const raw_ref<AudioHandler> handler_;

  // fanOutCount() is the number of AudioNodeInputs that we're connected to.
  // This method should not be called in audio thread rendering code, instead
  // renderingFanOutCount() should be used.
  // It must be called with the context's graph lock.
  unsigned FanOutCount();

  // Similar to `FanOutCount()`, `ParamFanOutCount()` is the number of
  // AudioParams that this output is connected to.  This method MUST be
  // called from the main thread with the context graph lock.
  // For audio thread, use `RenderingParamFanOutCount()` instead.
  unsigned ParamFanOutCount();

  // Must be called with the context's graph lock.
  void DisconnectAllInputs();
  void DisconnectAllParams();

  // updateInternalBus() updates m_internalBus appropriately for the number of
  // channels.  It is called in the constructor or in the audio thread with the
  // context's graph lock.
  void UpdateInternalBus();

  // Announce to any nodes we're connected to that we changed our channel count
  // for its input.
  // It must be called in the audio thread with the context's graph lock.
  void PropagateChannelCount();

  // updateNumberOfChannels() is called in the audio thread at the start or end
  // of the render quantum to pick up channel changes.
  // It must be called with the context's graph lock.
  void UpdateNumberOfChannels();

  // m_numberOfChannels will only be changed in the audio thread.
  // The main thread sets m_desiredNumberOfChannels which will later get picked
  // up in the audio thread in updateNumberOfChannels().
  unsigned number_of_channels_;
  unsigned desired_number_of_channels_;

  // m_internalBus and m_inPlaceBus must only be changed in the audio thread
  // with the context's graph lock (or constructor).
  scoped_refptr<AudioBus> internal_bus_;
  scoped_refptr<AudioBus> in_place_bus_;
  // If m_isInPlace is true, use m_inPlaceBus as the valid AudioBus; If false,
  // use the default m_internalBus.
  bool is_in_place_ = false;

  // This HashSet holds connection references. We must call
  // AudioNode::makeConnection when we add an AudioNodeInput to this, and must
  // call AudioNode::breakConnection() when we remove an AudioNodeInput from
  // this.
  HashSet<AudioNodeInput*> inputs_;
  bool is_enabled_ = true;

  bool did_call_dispose_ = false;

  // For the purposes of rendering, keeps track of the number of inputs and
  // AudioParams we're connected to.  These value should only be changed at the
  // very start or end of the rendering quantum.
  unsigned rendering_fan_out_count_ = 0;
  unsigned rendering_param_fan_out_count_ = 0;

  // This collection of raw pointers is safe because they are retained by
  // AudioParam objects retained by m_connectedParams of the owner AudioNode.
  HashSet<AudioParamHandler*> params_;

  friend class AudioNodeWiring;
};

}  // namespace blink

#endif  // THIRD_PARTY_BLINK_RENDERER_MODULES_WEBAUDIO_AUDIO_NODE_OUTPUT_H_