Home | History | Annotate | Download | only in test
      1 /*
      2  *  Copyright (c) 2013 The WebRTC project authors. All Rights Reserved.
      3  *
      4  *  Use of this source code is governed by a BSD-style license
      5  *  that can be found in the LICENSE file in the root of the source
      6  *  tree. An additional intellectual property rights grant can be found
      7  *  in the file PATENTS.  All contributing project authors may
      8  *  be found in the AUTHORS file in the root of the source tree.
      9  */
     10 #ifndef WEBRTC_VIDEO_ENGINE_TEST_COMMON_RTP_RTCP_OBSERVER_H_
     11 #define WEBRTC_VIDEO_ENGINE_TEST_COMMON_RTP_RTCP_OBSERVER_H_
     12 
     13 #include <map>
     14 #include <vector>
     15 
     16 #include "testing/gtest/include/gtest/gtest.h"
     17 
     18 #include "webrtc/modules/rtp_rtcp/interface/rtp_header_parser.h"
     19 #include "webrtc/test/direct_transport.h"
     20 #include "webrtc/typedefs.h"
     21 #include "webrtc/video_send_stream.h"
     22 
     23 namespace webrtc {
     24 namespace test {
     25 
     26 class RtpRtcpObserver {
     27  public:
     28   virtual ~RtpRtcpObserver() {}
     29   newapi::Transport* SendTransport() {
     30     return &send_transport_;
     31   }
     32 
     33   newapi::Transport* ReceiveTransport() {
     34     return &receive_transport_;
     35   }
     36 
     37   virtual void SetReceivers(PacketReceiver* send_transport_receiver,
     38                             PacketReceiver* receive_transport_receiver) {
     39     send_transport_.SetReceiver(send_transport_receiver);
     40     receive_transport_.SetReceiver(receive_transport_receiver);
     41   }
     42 
     43   void StopSending() {
     44     send_transport_.StopSending();
     45     receive_transport_.StopSending();
     46   }
     47 
     48   virtual EventTypeWrapper Wait() {
     49     EventTypeWrapper result = observation_complete_->Wait(timeout_ms_);
     50     observation_complete_->Reset();
     51     return result;
     52   }
     53 
     54  protected:
     55   RtpRtcpObserver(unsigned int event_timeout_ms,
     56       const FakeNetworkPipe::Config& configuration)
     57       : crit_(CriticalSectionWrapper::CreateCriticalSection()),
     58         observation_complete_(EventWrapper::Create()),
     59         parser_(RtpHeaderParser::Create()),
     60         send_transport_(crit_.get(),
     61                         this,
     62                         &RtpRtcpObserver::OnSendRtp,
     63                         &RtpRtcpObserver::OnSendRtcp,
     64                         configuration),
     65         receive_transport_(crit_.get(),
     66                            this,
     67                            &RtpRtcpObserver::OnReceiveRtp,
     68                            &RtpRtcpObserver::OnReceiveRtcp,
     69                            configuration),
     70         timeout_ms_(event_timeout_ms) {}
     71 
     72   explicit RtpRtcpObserver(unsigned int event_timeout_ms)
     73       : crit_(CriticalSectionWrapper::CreateCriticalSection()),
     74         observation_complete_(EventWrapper::Create()),
     75         parser_(RtpHeaderParser::Create()),
     76         send_transport_(crit_.get(),
     77                         this,
     78                         &RtpRtcpObserver::OnSendRtp,
     79                         &RtpRtcpObserver::OnSendRtcp,
     80                         FakeNetworkPipe::Config()),
     81         receive_transport_(crit_.get(),
     82                            this,
     83                            &RtpRtcpObserver::OnReceiveRtp,
     84                            &RtpRtcpObserver::OnReceiveRtcp,
     85                            FakeNetworkPipe::Config()),
     86         timeout_ms_(event_timeout_ms) {}
     87 
     88   enum Action {
     89     SEND_PACKET,
     90     DROP_PACKET,
     91   };
     92 
     93   virtual Action OnSendRtp(const uint8_t* packet, size_t length)
     94       EXCLUSIVE_LOCKS_REQUIRED(crit_) {
     95     return SEND_PACKET;
     96   }
     97 
     98   virtual Action OnSendRtcp(const uint8_t* packet, size_t length)
     99       EXCLUSIVE_LOCKS_REQUIRED(crit_) {
    100     return SEND_PACKET;
    101   }
    102 
    103   virtual Action OnReceiveRtp(const uint8_t* packet, size_t length)
    104       EXCLUSIVE_LOCKS_REQUIRED(crit_) {
    105     return SEND_PACKET;
    106   }
    107 
    108   virtual Action OnReceiveRtcp(const uint8_t* packet, size_t length)
    109       EXCLUSIVE_LOCKS_REQUIRED(crit_) {
    110     return SEND_PACKET;
    111   }
    112 
    113  private:
    114   class PacketTransport : public test::DirectTransport {
    115    public:
    116     typedef Action (RtpRtcpObserver::*PacketTransportAction)(const uint8_t*,
    117                                                              size_t);
    118 
    119     PacketTransport(CriticalSectionWrapper* lock,
    120                     RtpRtcpObserver* observer,
    121                     PacketTransportAction on_rtp,
    122                     PacketTransportAction on_rtcp,
    123                     const FakeNetworkPipe::Config& configuration)
    124         : test::DirectTransport(configuration),
    125           crit_(lock),
    126           observer_(observer),
    127           on_rtp_(on_rtp),
    128           on_rtcp_(on_rtcp) {}
    129 
    130   private:
    131     virtual bool SendRtp(const uint8_t* packet, size_t length) OVERRIDE {
    132       EXPECT_FALSE(RtpHeaderParser::IsRtcp(packet, length));
    133       Action action;
    134       {
    135         CriticalSectionScoped lock(crit_);
    136         action = (observer_->*on_rtp_)(packet, length);
    137       }
    138       switch (action) {
    139         case DROP_PACKET:
    140           // Drop packet silently.
    141           return true;
    142         case SEND_PACKET:
    143           return test::DirectTransport::SendRtp(packet, length);
    144       }
    145       return true;  // Will never happen, makes compiler happy.
    146     }
    147 
    148     virtual bool SendRtcp(const uint8_t* packet, size_t length) OVERRIDE {
    149       EXPECT_TRUE(RtpHeaderParser::IsRtcp(packet, length));
    150       Action action;
    151       {
    152         CriticalSectionScoped lock(crit_);
    153         action = (observer_->*on_rtcp_)(packet, length);
    154       }
    155       switch (action) {
    156         case DROP_PACKET:
    157           // Drop packet silently.
    158           return true;
    159         case SEND_PACKET:
    160           return test::DirectTransport::SendRtcp(packet, length);
    161       }
    162       return true;  // Will never happen, makes compiler happy.
    163     }
    164 
    165     // Pointer to shared lock instance protecting on_rtp_/on_rtcp_ calls.
    166     CriticalSectionWrapper* const crit_;
    167 
    168     RtpRtcpObserver* const observer_;
    169     const PacketTransportAction on_rtp_, on_rtcp_;
    170   };
    171 
    172  protected:
    173   const scoped_ptr<CriticalSectionWrapper> crit_;
    174   const scoped_ptr<EventWrapper> observation_complete_;
    175   const scoped_ptr<RtpHeaderParser> parser_;
    176 
    177  private:
    178   PacketTransport send_transport_, receive_transport_;
    179   unsigned int timeout_ms_;
    180 };
    181 }  // namespace test
    182 }  // namespace webrtc
    183 
    184 #endif  // WEBRTC_VIDEO_ENGINE_TEST_COMMON_RTP_RTCP_OBSERVER_H_
    185