/* 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 _JSEPSESSIONIMPL_H_ #define _JSEPSESSIONIMPL_H_ #include #include #include #include "signaling/src/jsep/JsepCodecDescription.h" #include "signaling/src/jsep/JsepTrack.h" #include "signaling/src/jsep/JsepSession.h" #include "signaling/src/jsep/JsepTrack.h" #include "signaling/src/sdp/SipccSdpParser.h" #include "signaling/src/sdp/SdpHelper.h" #include "signaling/src/common/PtrVector.h" namespace mozilla { class JsepUuidGenerator { public: virtual ~JsepUuidGenerator() {} virtual bool Generate(std::string* id) = 0; }; class JsepSessionImpl : public JsepSession { public: JsepSessionImpl(const std::string& name, UniquePtr uuidgen) : JsepSession(name), mIsOfferer(false), mWasOffererLastTime(false), mIceControlling(false), mRemoteIsIceLite(false), mRemoteIceIsRestarting(false), mBundlePolicy(kBundleBalanced), mSessionId(0), mSessionVersion(0), mUuidGen(Move(uuidgen)), mSdpHelper(&mLastError) { } // Implement JsepSession methods. virtual nsresult Init() override; virtual nsresult AddTrack(const RefPtr& track) override; virtual nsresult RemoveTrack(const std::string& streamId, const std::string& trackId) override; virtual nsresult SetIceCredentials(const std::string& ufrag, const std::string& pwd) override; virtual const std::string& GetUfrag() const override { return mIceUfrag; } virtual const std::string& GetPwd() const override { return mIcePwd; } nsresult SetBundlePolicy(JsepBundlePolicy policy) override; virtual bool RemoteIsIceLite() const override { return mRemoteIsIceLite; } virtual bool RemoteIceIsRestarting() const override { return mRemoteIceIsRestarting; } virtual std::vector GetIceOptions() const override { return mIceOptions; } virtual nsresult AddDtlsFingerprint(const std::string& algorithm, const std::vector& value) override; nsresult AddRtpExtension(std::vector& extensions, const std::string& extensionName, SdpDirectionAttribute::Direction direction); virtual nsresult AddAudioRtpExtension( const std::string& extensionName, SdpDirectionAttribute::Direction direction = SdpDirectionAttribute::Direction::kSendrecv) override; virtual nsresult AddVideoRtpExtension( const std::string& extensionName, SdpDirectionAttribute::Direction direction = SdpDirectionAttribute::Direction::kSendrecv) override; virtual std::vector& Codecs() override { return mSupportedCodecs.values; } virtual nsresult ReplaceTrack(const std::string& oldStreamId, const std::string& oldTrackId, const std::string& newStreamId, const std::string& newTrackId) override; virtual nsresult SetParameters( const std::string& streamId, const std::string& trackId, const std::vector& constraints) override; virtual nsresult GetParameters( const std::string& streamId, const std::string& trackId, std::vector* outConstraints) override; virtual std::vector> GetLocalTracks() const override; virtual std::vector> GetRemoteTracks() const override; virtual std::vector> GetRemoteTracksAdded() const override; virtual std::vector> GetRemoteTracksRemoved() const override; virtual nsresult CreateOffer(const JsepOfferOptions& options, std::string* offer) override; virtual nsresult CreateAnswer(const JsepAnswerOptions& options, std::string* answer) override; virtual std::string GetLocalDescription() const override; virtual std::string GetRemoteDescription() const override; virtual nsresult SetLocalDescription(JsepSdpType type, const std::string& sdp) override; virtual nsresult SetRemoteDescription(JsepSdpType type, const std::string& sdp) override; virtual nsresult AddRemoteIceCandidate(const std::string& candidate, const std::string& mid, uint16_t level) override; virtual nsresult AddLocalIceCandidate(const std::string& candidate, uint16_t level, std::string* mid, bool* skipped) override; virtual nsresult UpdateDefaultCandidate( const std::string& defaultCandidateAddr, uint16_t defaultCandidatePort, const std::string& defaultRtcpCandidateAddr, uint16_t defaultRtcpCandidatePort, uint16_t level) override; virtual nsresult EndOfLocalCandidates(uint16_t level) override; virtual nsresult Close() override; virtual const std::string GetLastError() const override; virtual bool IsIceControlling() const override { return mIceControlling; } virtual bool IsOfferer() const { return mIsOfferer; } // Access transports. virtual std::vector> GetTransports() const override { return mTransports; } virtual std::vector GetNegotiatedTrackPairs() const override { return mNegotiatedTrackPairs; } virtual bool AllLocalTracksAreAssigned() const override; private: struct JsepDtlsFingerprint { std::string mAlgorithm; std::vector mValue; }; struct JsepSendingTrack { RefPtr mTrack; Maybe mAssignedMLine; }; struct JsepReceivingTrack { RefPtr mTrack; Maybe mAssignedMLine; }; // Non-const so it can set mLastError nsresult CreateGenericSDP(UniquePtr* sdp); void AddExtmap(SdpMediaSection* msection) const; void AddMid(const std::string& mid, SdpMediaSection* msection) const; const std::vector* GetRtpExtensions( SdpMediaSection::MediaType type) const; void AddCommonExtmaps(const SdpMediaSection& remoteMsection, SdpMediaSection* msection); nsresult SetupIds(); nsresult CreateSsrc(uint32_t* ssrc); void SetupDefaultCodecs(); void SetupDefaultRtpExtensions(); void SetState(JsepSignalingState state); // Non-const so it can set mLastError nsresult ParseSdp(const std::string& sdp, UniquePtr* parsedp); nsresult SetLocalDescriptionOffer(UniquePtr offer); nsresult SetLocalDescriptionAnswer(JsepSdpType type, UniquePtr answer); nsresult SetRemoteDescriptionOffer(UniquePtr offer); nsresult SetRemoteDescriptionAnswer(JsepSdpType type, UniquePtr answer); nsresult ValidateLocalDescription(const Sdp& description); nsresult ValidateRemoteDescription(const Sdp& description); nsresult ValidateAnswer(const Sdp& offer, const Sdp& answer); nsresult SetRemoteTracksFromDescription(const Sdp* remoteDescription); // Non-const because we use our Uuid generator nsresult CreateReceivingTrack(size_t mline, const Sdp& sdp, const SdpMediaSection& msection, RefPtr* track); nsresult HandleNegotiatedSession(const UniquePtr& local, const UniquePtr& remote); nsresult AddTransportAttributes(SdpMediaSection* msection, SdpSetupAttribute::Role dtlsRole); nsresult CopyPreviousTransportParams(const Sdp& oldAnswer, const Sdp& offerersPreviousSdp, const Sdp& newOffer, Sdp* newLocal); nsresult SetupOfferMSections(const JsepOfferOptions& options, Sdp* sdp); // Non-const so it can assign m-line index to tracks nsresult SetupOfferMSectionsByType(SdpMediaSection::MediaType type, Maybe offerToReceive, Sdp* sdp); nsresult BindLocalTracks(SdpMediaSection::MediaType mediatype, Sdp* sdp); nsresult BindRemoteTracks(SdpMediaSection::MediaType mediatype, Sdp* sdp, size_t* offerToReceive); nsresult SetRecvAsNeededOrDisable(SdpMediaSection::MediaType mediatype, Sdp* sdp, size_t* offerToRecv); void SetupOfferToReceiveMsection(SdpMediaSection* offer); nsresult AddRecvonlyMsections(SdpMediaSection::MediaType mediatype, size_t count, Sdp* sdp); nsresult AddReofferMsections(const Sdp& oldLocalSdp, const Sdp& oldAnswer, Sdp* newSdp); void SetupBundle(Sdp* sdp) const; nsresult GetRemoteIds(const Sdp& sdp, const SdpMediaSection& msection, std::string* streamId, std::string* trackId); nsresult CreateOfferMSection(SdpMediaSection::MediaType type, SdpMediaSection::Protocol proto, SdpDirectionAttribute::Direction direction, Sdp* sdp); nsresult GetFreeMsectionForSend(SdpMediaSection::MediaType type, Sdp* sdp, SdpMediaSection** msection); nsresult CreateAnswerMSection(const JsepAnswerOptions& options, size_t mlineIndex, const SdpMediaSection& remoteMsection, Sdp* sdp); nsresult SetRecvonlySsrc(SdpMediaSection* msection); nsresult BindMatchingLocalTrackToAnswer(SdpMediaSection* msection); nsresult BindMatchingRemoteTrackToAnswer(SdpMediaSection* msection); nsresult DetermineAnswererSetupRole(const SdpMediaSection& remoteMsection, SdpSetupAttribute::Role* rolep); nsresult MakeNegotiatedTrackPair(const SdpMediaSection& remote, const SdpMediaSection& local, const RefPtr& transport, bool usingBundle, size_t transportLevel, JsepTrackPair* trackPairOut); void InitTransport(const SdpMediaSection& msection, JsepTransport* transport); nsresult FinalizeTransport(const SdpAttributeList& remote, const SdpAttributeList& answer, const RefPtr& transport); nsresult GetNegotiatedBundledMids(SdpHelper::BundledMids* bundledMids); nsresult EnableOfferMsection(SdpMediaSection* msection); mozilla::Sdp* GetParsedLocalDescription() const; mozilla::Sdp* GetParsedRemoteDescription() const; const Sdp* GetAnswer() const; std::vector mLocalTracks; std::vector mRemoteTracks; // By the most recent SetRemoteDescription std::vector mRemoteTracksAdded; std::vector mRemoteTracksRemoved; std::vector > mTransports; // So we can rollback std::vector > mOldTransports; std::vector mNegotiatedTrackPairs; bool mIsOfferer; bool mWasOffererLastTime; bool mIceControlling; std::string mIceUfrag; std::string mIcePwd; bool mRemoteIsIceLite; bool mRemoteIceIsRestarting; std::vector mIceOptions; JsepBundlePolicy mBundlePolicy; std::vector mDtlsFingerprints; uint64_t mSessionId; uint64_t mSessionVersion; std::vector mAudioRtpExtensions; std::vector mVideoRtpExtensions; UniquePtr mUuidGen; std::string mDefaultRemoteStreamId; std::map mDefaultRemoteTrackIdsByLevel; std::string mCNAME; // Used to prevent duplicate local SSRCs. Not used to prevent local/remote or // remote-only duplication, which will be important for EKT but not now. std::set mSsrcs; // When an m-section doesn't have a local track, it still needs an ssrc, which // is stored here. std::vector mRecvonlySsrcs; UniquePtr mGeneratedLocalDescription; // Created but not set. UniquePtr mCurrentLocalDescription; UniquePtr mCurrentRemoteDescription; UniquePtr mPendingLocalDescription; UniquePtr mPendingRemoteDescription; PtrVector mSupportedCodecs; std::string mLastError; SipccSdpParser mParser; SdpHelper mSdpHelper; }; } // namespace mozilla #endif