webrtc proxy 分析

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/liwenlong_only/article/details/80166016

webrtc proxy 分析

在webrtc中,许多重要的对象实际上都是“代理对象”,如PeerConnection, PeerConnectionFactory,等等,可以看下PeerConnectionFactory的源代码:

rtc::scoped_refptr<PeerConnectionFactoryInterface>
CreatePeerConnectionFactory() {
  rtc::scoped_refptr<PeerConnectionFactory> pc_factory(    
      new rtc::RefCountedObject<PeerConnectionFactory>()); 

  RTC_CHECK(rtc::Thread::Current() == pc_factory->signaling_thread());

  if (!pc_factory->Initialize()) {  
    return nullptr;
  }
  return PeerConnectionFactoryProxy::Create(pc_factory->signaling_thread(),pc_factory);   
}

从代码可以看出,创建PeerConnectionFactory实际上返回的是PeerConnectionFactoryProxy对象。那这么做有什么用呢?从PeerConnectionFactoryProxy::Create(pc_factory→signaling_thread(), pc_factory); 中可以看到,Create的还有一个参数是pc_factory→signaling_thread(),猜一下也知道,这是为了解决多线程问题的。其实,他是为了保证所有的proxy对象的操作都在singaling线程中,当在另一个线程调用了proxy对象的方法时,proxy对象会将该方法的操作包装成一个message,发送给singaling线程,然后阻塞等待singaling线程中执行完成。

下面可以看一下它的源码是如何实现的,为了简单起见,使用MediaStream为例说明:

rtc::scoped_refptr<MediaStreamInterface>
PeerConnectionFactory::CreateLocalMediaStream(const std::string& label) {
  RTC_DCHECK(signaling_thread_->IsCurrent());
  return MediaStreamProxy::Create(signaling_thread_,
                                  MediaStream::Create(label));
}

MediaStreamProxy实际上是由一个宏生成的,如下:

BEGIN_SIGNALING_PROXY_MAP(MediaStream)
  PROXY_CONSTMETHOD0(std::string, label)
  PROXY_METHOD0(AudioTrackVector, GetAudioTracks)
  PROXY_METHOD0(VideoTrackVector, GetVideoTracks)
  PROXY_METHOD1(rtc::scoped_refptr<AudioTrackInterface>,
                FindAudioTrack, const std::string&)
  PROXY_METHOD1(rtc::scoped_refptr<VideoTrackInterface>,
                FindVideoTrack, const std::string&)
  PROXY_METHOD1(bool, AddTrack, AudioTrackInterface*)
  PROXY_METHOD1(bool, AddTrack, VideoTrackInterface*)
  PROXY_METHOD1(bool, RemoveTrack, AudioTrackInterface*)
  PROXY_METHOD1(bool, RemoveTrack, VideoTrackInterface*)
  PROXY_METHOD1(void, RegisterObserver, ObserverInterface*)
  PROXY_METHOD1(void, UnregisterObserver, ObserverInterface*)
END_SIGNALING_PROXY()
}

把这些宏都展开,如下(为避免太长砍掉了很多函数):

class MediaStreamProxy : public MediaStreamInterface {                                  \
protected:                                                             
    typedef MediaStreamInterface C;  

    MediaStreamProxy(rtc::Thread* signaling_thread, C* c)                      
      : signaling_thread_(signaling_thread), c_(c) {}                    
    ~MediaStreamProxy() {                                                        
      MethodCall0<MediaStreamProxy, void> call(                                 
        this, &MediaStreamProxy::Release_s);                                 
        call.Marshal(signaling_thread_);                                   
    }                                                                    

public:                                                              
    static rtc::scoped_refptr<C> Create(rtc::Thread* signaling_thread, C* c) { 
        return new rtc::RefCountedObject<MediaStreamProxy>(                         
            signaling_thread, c);                                         
    }

    std::string label() const override {                         
        ConstMethodCall0<C, std::string> call(c_.get(), &C::label); 
        return call.Marshal(signaling_thread_);            
    }

    AudioTrackVector GetAudioTracks() override {                           
        MethodCall0<C, AudioTrackVector> call(c_.get(), &C::GetAudioTracks); 
        return call.Marshal(signaling_thread_);       
    }

private:
    void Release_s() {
        c_ = NULL;
    }
    mutable rtc::Thread* signaling_thread_;
    rtc::scoped_refptr<C> c_;
};

猜你喜欢

转载自blog.csdn.net/liwenlong_only/article/details/80166016