tor-browser

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

MediaStreamAudioDestinationNode.cpp (5640B)


      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 #include "MediaStreamAudioDestinationNode.h"
      8 
      9 #include "AudioNodeEngine.h"
     10 #include "AudioNodeTrack.h"
     11 #include "AudioStreamTrack.h"
     12 #include "DOMMediaStream.h"
     13 #include "ForwardedInputTrack.h"
     14 #include "mozilla/dom/Document.h"
     15 #include "mozilla/dom/MediaStreamAudioDestinationNodeBinding.h"
     16 #include "nsGlobalWindowInner.h"
     17 
     18 namespace mozilla::dom {
     19 
     20 class AudioDestinationTrackSource final : public MediaStreamTrackSource {
     21 public:
     22  NS_DECL_ISUPPORTS_INHERITED
     23  NS_DECL_CYCLE_COLLECTION_CLASS_INHERITED(AudioDestinationTrackSource,
     24                                           MediaStreamTrackSource)
     25 
     26  AudioDestinationTrackSource(MediaStreamAudioDestinationNode* aNode,
     27                              mozilla::MediaTrack* aInputTrack,
     28                              ProcessedMediaTrack* aTrack,
     29                              nsIPrincipal* aPrincipal)
     30      : MediaStreamTrackSource(
     31            aPrincipal, nsString(),
     32            // We pass 0 here because tracking ids are video only for now.
     33            TrackingId(TrackingId::Source::AudioDestinationNode, 0)),
     34        mTrack(aTrack),
     35        mPort(mTrack->AllocateInputPort(aInputTrack)),
     36        mNode(aNode) {}
     37 
     38  void Destroy() override {
     39    if (!mTrack->IsDestroyed()) {
     40      mTrack->Destroy();
     41      mPort->Destroy();
     42    }
     43    if (mNode) {
     44      mNode->DestroyMediaTrack();
     45      mNode = nullptr;
     46    }
     47  }
     48 
     49  MediaSourceEnum GetMediaSource() const override {
     50    return MediaSourceEnum::AudioCapture;
     51  }
     52 
     53  void GetSettings(MediaTrackSettings& aSettings) override {}
     54 
     55  void Stop() override { Destroy(); }
     56 
     57  void Disable() override {}
     58 
     59  void Enable() override {}
     60 
     61  const RefPtr<ProcessedMediaTrack> mTrack;
     62  const RefPtr<MediaInputPort> mPort;
     63 
     64 private:
     65  ~AudioDestinationTrackSource() = default;
     66 
     67  RefPtr<MediaStreamAudioDestinationNode> mNode;
     68 };
     69 
     70 NS_IMPL_ADDREF_INHERITED(AudioDestinationTrackSource, MediaStreamTrackSource)
     71 NS_IMPL_RELEASE_INHERITED(AudioDestinationTrackSource, MediaStreamTrackSource)
     72 NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(AudioDestinationTrackSource)
     73 NS_INTERFACE_MAP_END_INHERITING(MediaStreamTrackSource)
     74 NS_IMPL_CYCLE_COLLECTION_INHERITED(AudioDestinationTrackSource,
     75                                   MediaStreamTrackSource, mNode)
     76 
     77 NS_IMPL_CYCLE_COLLECTION_INHERITED(MediaStreamAudioDestinationNode, AudioNode,
     78                                   mDOMStream)
     79 
     80 NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(MediaStreamAudioDestinationNode)
     81 NS_INTERFACE_MAP_END_INHERITING(AudioNode)
     82 
     83 NS_IMPL_ADDREF_INHERITED(MediaStreamAudioDestinationNode, AudioNode)
     84 NS_IMPL_RELEASE_INHERITED(MediaStreamAudioDestinationNode, AudioNode)
     85 
     86 MediaStreamAudioDestinationNode::MediaStreamAudioDestinationNode(
     87    AudioContext* aContext)
     88    : AudioNode(aContext, 2, ChannelCountMode::Explicit,
     89                ChannelInterpretation::Speakers),
     90      mDOMStream(MakeAndAddRef<DOMMediaStream>(GetOwnerWindow())) {
     91  // Ensure an audio track with the correct ID is exposed to JS. If we can't get
     92  // a principal here because the document is not available, pass in a null
     93  // principal. This happens in edge cases when the document is being unloaded
     94  // and it does not matter too much to have something working as long as it's
     95  // not dangerous.
     96  nsCOMPtr<nsIPrincipal> principal = nullptr;
     97  if (nsGlobalWindowInner* win = aContext->GetOwnerWindow()) {
     98    Document* doc = win->GetExtantDoc();
     99    principal = doc->NodePrincipal();
    100  }
    101  mTrack = AudioNodeTrack::Create(aContext, new AudioNodeEngine(this),
    102                                  AudioNodeTrack::EXTERNAL_OUTPUT,
    103                                  aContext->Graph());
    104  auto source = MakeRefPtr<AudioDestinationTrackSource>(
    105      this, mTrack,
    106      aContext->Graph()->CreateForwardedInputTrack(MediaSegment::AUDIO),
    107      principal);
    108  auto track =
    109      MakeRefPtr<AudioStreamTrack>(GetOwnerWindow(), source->mTrack, source);
    110  mDOMStream->AddTrackInternal(track);
    111 }
    112 
    113 /* static */
    114 already_AddRefed<MediaStreamAudioDestinationNode>
    115 MediaStreamAudioDestinationNode::Create(AudioContext& aAudioContext,
    116                                        const AudioNodeOptions& aOptions,
    117                                        ErrorResult& aRv) {
    118  // The spec has a pointless check here.  See
    119  // https://github.com/WebAudio/web-audio-api/issues/2149
    120  MOZ_RELEASE_ASSERT(!aAudioContext.IsOffline(), "Bindings messed up?");
    121 
    122  RefPtr<MediaStreamAudioDestinationNode> audioNode =
    123      new MediaStreamAudioDestinationNode(&aAudioContext);
    124 
    125  audioNode->Initialize(aOptions, aRv);
    126  if (NS_WARN_IF(aRv.Failed())) {
    127    return nullptr;
    128  }
    129 
    130  return audioNode.forget();
    131 }
    132 
    133 size_t MediaStreamAudioDestinationNode::SizeOfExcludingThis(
    134    MallocSizeOf aMallocSizeOf) const {
    135  // Future:
    136  // - mDOMStream
    137  size_t amount = AudioNode::SizeOfExcludingThis(aMallocSizeOf);
    138  return amount;
    139 }
    140 
    141 size_t MediaStreamAudioDestinationNode::SizeOfIncludingThis(
    142    MallocSizeOf aMallocSizeOf) const {
    143  return aMallocSizeOf(this) + SizeOfExcludingThis(aMallocSizeOf);
    144 }
    145 
    146 void MediaStreamAudioDestinationNode::DestroyMediaTrack() {
    147  AudioNode::DestroyMediaTrack();
    148 }
    149 
    150 JSObject* MediaStreamAudioDestinationNode::WrapObject(
    151    JSContext* aCx, JS::Handle<JSObject*> aGivenProto) {
    152  return MediaStreamAudioDestinationNode_Binding::Wrap(aCx, this, aGivenProto);
    153 }
    154 
    155 }  // namespace mozilla::dom