Quellcodebibliothek Statistik Leitseite products/Sources/formale Sprachen/C/Firefox/dom/media/webrtc/jsapi/   (Firefox Browser Version 153.0.1©)  Datei vom 27.6.2026 mit Größe 16 kB image not shown  

Quelle  MediaTransportHandlerIPC.cpp

  Sprache: C
 

/* 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/. */


#include "MediaTransportHandlerIPC.h"

#include "common/browser_logging/CSFLog.h"
#include "mozilla/RefPtr.h"
#include "mozilla/dom/MediaTransportChild.h"
#include "mozilla/ipc/BackgroundChild.h"
#include "mozilla/ipc/Endpoint.h"
#include "mozilla/ipc/PBackgroundChild.h"
#include "mozilla/net/SocketProcessBridgeChild.h"
#include "nsThreadUtils.h"

namespace mozilla {

static const char* mthipcLogTag = "MediaTransportHandler";
#ifdef LOGTAG
#  undef LOGTAG
#endif
#define LOGTAG mthipcLogTag

MediaTransportHandlerIPC::MediaTransportHandlerIPC() = default;

MediaTransportHandlerIPC::~MediaTransportHandlerIPC() = default;

void MediaTransportHandlerIPC::Initialize() {
  using EndpointPromise =
      MozPromise<mozilla::ipc::Endpoint<mozilla::dom::PMediaTransportChild>,
                 nsCString, true>;

  // TODO(bug 1926450): Historically we've used STS for this, but there are
  // probably better options.
  nsresult res;
  mThread = do_GetService(NS_SOCKETTRANSPORTSERVICE_CONTRACTID, &res);
  MOZ_ASSERT(mThread);

  mInitPromise =
      net::SocketProcessBridgeChild::GetSocketProcessBridge()
          ->Then(
              GetCurrentSerialEventTarget(), __func__,
              [](const RefPtr<net::SocketProcessBridgeChild>& aBridge) {
                mozilla::ipc::Endpoint<mozilla::dom::PMediaTransportParent>
                    parentEndpoint;
                mozilla::ipc::Endpoint<mozilla::dom::PMediaTransportChild>
                    childEndpoint;
                mozilla::dom::PMediaTransport::CreateEndpoints(&parentEndpoint,
                                                               &childEndpoint);

                if (!aBridge || !aBridge->SendInitMediaTransport(
                                    std::move(parentEndpoint))) {
                  NS_WARNING(
                      "MediaTransportHandlerIPC async init failed! Webrtc "
                      "networking "
                      "will not work!");
                  return EndpointPromise::CreateAndReject(
                      nsCString("SendInitMediaTransport failed!"), __func__);
                }

                return EndpointPromise::CreateAndResolve(
                    std::move(childEndpoint), __func__);
              },
              [](const nsCString& aError) {
                return EndpointPromise::CreateAndReject(aError, __func__);
              })
          ->Then(
              mThread, __func__,
              [this, self = RefPtr<MediaTransportHandlerIPC>(this)](
                  mozilla::ipc::Endpoint<mozilla::dom::PMediaTransportChild>&&
                      aEndpoint) {
                RefPtr child = MakeRefPtr<MediaTransportChild>(this);
                aEndpoint.Bind(child);
                mChild = child;

                CSFLogDebug(LOGTAG, "%s Init done", __func__);
                return InitPromise::CreateAndResolve(true, __func__);
              },
              [=](const nsCString& aError) {
                CSFLogError(
                    LOGTAG,
                    "MediaTransportHandlerIPC async init failed! Webrtc "
                    "networking will not work! Error was %s",
                    aError.get());
                NS_WARNING(
                    "MediaTransportHandlerIPC async init failed! Webrtc "
                    "networking "
                    "will not work!");
                return InitPromise::CreateAndReject(aError, __func__);
              });
}

RefPtr<MediaTransportHandler::IceLogPromise>
MediaTransportHandlerIPC::GetIceLog(const nsCString& aPattern) {
  return mInitPromise->Then(
      mThread, __func__,
      [=, this,
       self = RefPtr<MediaTransportHandlerIPC>(this)](bool /* dummy */) {
        if (!mChild) {
          return IceLogPromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
        }
        // Compiler has trouble deducing the return type here for some reason,
        // so we use a temp variable as a hint.
        // SendGetIceLog _almost_ returns an IceLogPromise; the reject value
        // differs (ipc::ResponseRejectReason vs nsresult) so we need to
        // convert.
        RefPtr<IceLogPromise> promise = mChild->SendGetIceLog(aPattern)->Then(
            mThread, __func__,
            [](WebrtcGlobalLog&& aLogLines) {
              return IceLogPromise::CreateAndResolve(std::move(aLogLines),
                                                     __func__);
            },
            [](ipc::ResponseRejectReason aReason) {
              return IceLogPromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
            });
        return promise;
      },
      [](const nsCString& aError) {
        return IceLogPromise::CreateAndReject(NS_ERROR_FAILURE, __func__);
      });
}

void MediaTransportHandlerIPC::ClearIceLog() {
  mInitPromise->Then(
      mThread, __func__,
      [this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendClearIceLog();
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::EnterPrivateMode() {
  mInitPromise->Then(
      mThread, __func__,
      [this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendEnterPrivateMode();
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::ExitPrivateMode() {
  mInitPromise->Then(
      mThread, __func__,
      [this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendExitPrivateMode();
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::CreateIceCtx(const std::string& aName) {
  CSFLogDebug(LOGTAG, "MediaTransportHandlerIPC::CreateIceCtx start");

  mInitPromise->Then(
      mThread, __func__,
      [=, this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          CSFLogDebug(LOGTAG, "%s starting", __func__);
          if (NS_WARN_IF(!mChild->SendCreateIceCtx(aName))) {
            CSFLogError(LOGTAG, "%s failed!", __func__);
          }
        }
      },
      [](const nsCString& aError) {});
}

nsresult MediaTransportHandlerIPC::SetIceConfig(
    const nsTArray<dom::RTCIceServer>& aIceServers,
    dom::RTCIceTransportPolicy aIcePolicy) {
  // PeerConnectionImpl validates before calling this.
  // The socket process will re-validate when it receives the RTCIceServer
  // array, so no pre-validation is needed here.
  mInitPromise->Then(
      mThread, __func__,
      [=, this, iceServers = aIceServers.Clone(),
       self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          if (NS_WARN_IF(!mChild->SendSetIceConfig(std::move(iceServers),
                                                   aIcePolicy))) {
            CSFLogError(LOGTAG, "%s failed!", __func__);
          }
        }
      },
      [](const nsCString& aError) {});

  return NS_OK;
}

void MediaTransportHandlerIPC::Destroy() {
  if (mChild) {
    mChild->Shutdown();
    mThread->Dispatch(NS_NewRunnableFunction(
        __func__, [child = std::move(mChild)]() { child->Close(); }));
  }
  delete this;
}

// We will probably be able to move the proxy lookup stuff into
// this class once we move mtransport to its own process.
void MediaTransportHandlerIPC::SetProxyConfig(
    NrSocketProxyConfig&& aProxyConfig) {
  mInitPromise->Then(
      mThread, __func__,
      [aProxyConfig = std::move(aProxyConfig), this,
       self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) mutable {
        if (mChild) {
          mChild->SendSetProxyConfig(aProxyConfig.GetConfig());
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::EnsureProvisionalTransport(
    const std::string& aTransportId, const std::string& aLocalUfrag,
    const std::string& aLocalPwd, int aComponentCount) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendEnsureProvisionalTransport(aTransportId, aLocalUfrag,
                                                 aLocalPwd, aComponentCount);
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::SetTargetForDefaultLocalAddressLookup(
    const std::string& aTargetIp, uint16_t aTargetPort) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendSetTargetForDefaultLocalAddressLookup(aTargetIp,
                                                            aTargetPort);
        }
      },
      [](const nsCString& aError) {});
}

// We set default-route-only as late as possible because it depends on what
// capture permissions have been granted on the window, which could easily
// change between Init (ie; when the PC is created) and StartIceGathering
// (ie; when we set the local description).
void MediaTransportHandlerIPC::StartIceGathering(
    bool aDefaultRouteOnly, bool aObfuscateHostAddresses,
    // TODO(bug 1522205): It probably makes sense to look this up internally
    const nsTArray<NrIceStunAddr>& aStunAddrs) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, stunAddrs = aStunAddrs.Clone(),
       self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendStartIceGathering(aDefaultRouteOnly,
                                        aObfuscateHostAddresses, stunAddrs);
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::ActivateTransport(
    const std::string& aTransportId, const std::string& aLocalUfrag,
    const std::string& aLocalPwd, size_t aComponentCount,
    const std::string& aUfrag, const std::string& aPassword,
    const nsTArray<uint8_t>& aKeyDer, const nsTArray<uint8_t>& aCertDer,
    SSLKEAType aAuthType, bool aDtlsClient, const DtlsDigestList& aDigests,
    bool aPrivacyRequested) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, keyDer = aKeyDer.Clone(), certDer = aCertDer.Clone(),
       self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendActivateTransport(aTransportId, aLocalUfrag, aLocalPwd,
                                        aComponentCount, aUfrag, aPassword,
                                        keyDer, certDer, aAuthType, aDtlsClient,
                                        aDigests, aPrivacyRequested);
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::RemoveTransportsExcept(
    const std::set<std::string>& aTransportIds) {
  std::vector<std::string> transportIds(aTransportIds.begin(),
                                        aTransportIds.end());
  mInitPromise->Then(
      mThread, __func__,
      [this, self = RefPtr<MediaTransportHandlerIPC>(this),
       transportIds = std::move(transportIds)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendRemoveTransportsExcept(transportIds);
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::StartIceChecks(
    bool aIsControlling, const std::vector<std::string>& aIceOptions) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendStartIceChecks(aIsControlling, aIceOptions);
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::SendPacket(const std::string& aTransportId,
                                          MediaPacket&& aPacket) {
  mInitPromise->Then(
      mThread, __func__,
      [this, self = RefPtr<MediaTransportHandlerIPC>(this), aTransportId,
       aPacket = std::move(aPacket)](bool /*dummy*/) mutable {
        if (mChild) {
          mChild->SendSendPacket(aTransportId, std::move(aPacket));
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::AddIceCandidate(
    const std::string& aTransportId, const std::string& aCandidate,
    const std::string& aUfrag, const std::string& aObfuscatedAddress) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendAddIceCandidate(aTransportId, aCandidate, aUfrag,
                                      aObfuscatedAddress);
        }
      },
      [](const nsCString& aError) {});
}

void MediaTransportHandlerIPC::UpdateNetworkState(bool aOnline) {
  mInitPromise->Then(
      mThread, __func__,
      [=, this, self = RefPtr<MediaTransportHandlerIPC>(this)](bool /*dummy*/) {
        if (mChild) {
          mChild->SendUpdateNetworkState(aOnline);
        }
      },
      [](const nsCString& aError) {});
}

RefPtr<dom::RTCStatsPromise> MediaTransportHandlerIPC::GetIceStats(
    const std::string& aTransportId, DOMHighResTimeStamp aNow) {
  using IPCPromise = dom::PMediaTransportChild::GetIceStatsPromise;
  return mInitPromise
      ->Then(mThread, __func__,
             [aTransportId, aNow, this, self = RefPtr(this)](
                 const InitPromise::ResolveOrRejectValue& aValue) {
               if (aValue.IsReject()) {
                 return IPCPromise::CreateAndResolve(
                     MakeUnique<dom::RTCStatsCollection>(),
                     "MediaTransportHandlerIPC::GetIceStats_1");
               }
               if (!mChild) {
                 return IPCPromise::CreateAndResolve(
                     MakeUnique<dom::RTCStatsCollection>(),
                     "MediaTransportHandlerIPC::GetIceStats_1");
               }
               return mChild->SendGetIceStats(aTransportId, aNow);
             })
      ->Then(mThread, __func__, [](IPCPromise::ResolveOrRejectValue&& aValue) {
        if (aValue.IsReject()) {
          return dom::RTCStatsPromise::CreateAndResolve(
              MakeUnique<dom::RTCStatsCollection>(),
              "MediaTransportHandlerIPC::GetIceStats_2");
        }
        return dom::RTCStatsPromise::CreateAndResolve(
            std::move(aValue.ResolveValue()),
            "MediaTransportHandlerIPC::GetIceStats_2");
      });
}

MediaTransportChild::MediaTransportChild(MediaTransportHandlerIPC* aUser)
    : mMutex("MediaTransportChild"), mUser(aUser) {}

MediaTransportChild::~MediaTransportChild() = default;

mozilla::ipc::IPCResult MediaTransportChild::RecvOnCandidate(
    const string& transportId, CandidateInfo&& candidateInfo) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnCandidate(transportId, std::move(candidateInfo));
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnCandidateError(
    IceCandidateErrorInfo&& errorInfo) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnCandidateError(std::move(errorInfo));
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnAlpnNegotiated(
    const string& alpn) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnAlpnNegotiated(alpn);
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnGatheringStateChange(
    const string& transportId, const RTCIceGathererState& state) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnGatheringStateChange(transportId, state);
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnConnectionStateChange(
    const string& transportId, const RTCIceTransportState& state) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnConnectionStateChange(transportId, state);
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnPacketReceived(
    string&& transportId, MediaPacket&& packet) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnPacketReceived(std::forward<string>(transportId),
                            std::forward<MediaPacket>(packet));
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnEncryptedSending(
    const string& transportId, MediaPacket&& packet) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnEncryptedSending(transportId, std::move(packet));
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnStateChange(
    const string& transportId, const TransportLayer::State& state,
    nsTArray<nsTArray<uint8_t>>&& remoteCerts) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnStateChange(transportId, state, std::move(remoteCerts));
  }
  return ipc::IPCResult::Ok();
}

mozilla::ipc::IPCResult MediaTransportChild::RecvOnRtcpStateChange(
    const string& transportId, const TransportLayer::State& state) {
  MutexAutoLock lock(mMutex);
  if (mUser) {
    mUser->OnRtcpStateChange(transportId, state);
  }
  return ipc::IPCResult::Ok();
}

void MediaTransportChild::Shutdown() {
  MutexAutoLock lock(mMutex);
  mUser = nullptr;
}

}  // namespace mozilla

Messung V0.5 in Prozent
C=89 H=94 G=91

¤ Dauer der Verarbeitung: 0.8 Sekunden  ¤

*© Formatika GbR, Deutschland






Wurzel

Suchen

PVS Prover

Isabelle Prover

NIST Cobol Testsuite

Cephes Mathematical Library

Vienna Development Method

Haftungshinweis

Die Informationen auf dieser Webseite wurden nach bestem Wissen sorgfältig zusammengestellt. Es wird jedoch weder Vollständigkeit, noch Richtigkeit, noch Qualität der bereit gestellten Informationen zugesichert.

Bemerkung:

Die farbliche Syntaxdarstellung und die Messung sind noch experimentell.