/*
 * libjingle
 * Copyright 2004--2011, Google Inc.
 *
 * Redistribution and use in source and binary forms, with or without
 * modification, are permitted provided that the following conditions are met:
 *
 *  1. Redistributions of source code must retain the above copyright notice,
 *     this list of conditions and the following disclaimer.
 *  2. Redistributions in binary form must reproduce the above copyright notice,
 *     this list of conditions and the following disclaimer in the documentation
 *     and/or other materials provided with the distribution.
 *  3. The name of the author may not be used to endorse or promote products
 *     derived from this software without specific prior written permission.
 *
 * THIS SOFTWARE IS PROVIDED BY THE AUTHOR ``AS IS'' AND ANY EXPRESS OR IMPLIED
 * WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF
 * MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO
 * EVENT SHALL THE AUTHOR BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
 * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
 * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
 * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
 * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
 * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
 */


#ifndef TALK_SESSION_PHONE_WEBRTCVIE_H_
#define TALK_SESSION_PHONE_WEBRTCVIE_H_

#include "talk/base/common.h"
#include "talk/session/phone/webrtccommon.h"

#ifdef WEBRTC_RELATIVE_PATH
#include "common_types.h"
#include "modules/interface/module_common_types.h"
#include "modules/video_capture/main/interface/video_capture.h"
#include "modules/video_render/main/interface/video_render.h"
#include "video_engine/include/vie_base.h"
#include "video_engine/include/vie_capture.h"
#include "video_engine/include/vie_codec.h"
#include "video_engine/include/vie_errors.h"
#include "video_engine/include/vie_image_process.h"
#include "video_engine/include/vie_network.h"
#include "video_engine/include/vie_render.h"
#include "video_engine/include/vie_rtp_rtcp.h"
#else
#include "third_party/webrtc/files/include/common_types.h"
#include "third_party/webrtc/files/include/module_common_types.h"
#include "third_party/webrtc/files/include/video_capture.h"
#include "third_party/webrtc/files/include/video_render.h"
#include "third_party/webrtc/files/include/vie_base.h"
#include "third_party/webrtc/files/include/vie_capture.h"
#include "third_party/webrtc/files/include/vie_codec.h"
#include "third_party/webrtc/files/include/vie_errors.h"
#include "third_party/webrtc/files/include/vie_image_process.h"
#include "third_party/webrtc/files/include/vie_network.h"
#include "third_party/webrtc/files/include/vie_render.h"
#include "third_party/webrtc/files/include/vie_rtp_rtcp.h"
#endif  // WEBRTC_RELATIVE_PATH

namespace cricket {

// all tracing macros should go to a common file

// automatically handles lifetime of VideoEngine
class scoped_vie_engine {
 public:
  explicit scoped_vie_engine(webrtc::VideoEngine* e) : ptr(e) {}
  // VERIFY, to ensure that there are no leaks at shutdown
  ~scoped_vie_engine() {
    if (ptr) {
      webrtc::VideoEngine::Delete(ptr);
    }
  }
  webrtc::VideoEngine* get() const { return ptr; }
 private:
  webrtc::VideoEngine* ptr;
};

// scoped_ptr class to handle obtaining and releasing VideoEngine
// interface pointers
template<class T> class scoped_vie_ptr {
 public:
  explicit scoped_vie_ptr(const scoped_vie_engine& e)
       : ptr(T::GetInterface(e.get())) {}
  explicit scoped_vie_ptr(T* p) : ptr(p) {}
  ~scoped_vie_ptr() { if (ptr) ptr->Release(); }
  T* operator->() const { return ptr; }
  T* get() const { return ptr; }
 private:
  T* ptr;
};

// Utility class for aggregating the various WebRTC interface.
// Fake implementations can also be injected for testing.
class ViEWrapper {
 public:
  ViEWrapper()
      : engine_(webrtc::VideoEngine::Create()),
        base_(engine_), codec_(engine_), capture_(engine_),
        network_(engine_), render_(engine_), rtp_(engine_),
        image_(engine_) {
  }

  ViEWrapper(webrtc::ViEBase* base, webrtc::ViECodec* codec,
             webrtc::ViECapture* capture, webrtc::ViENetwork* network,
             webrtc::ViERender* render, webrtc::ViERTP_RTCP* rtp,
             webrtc::ViEImageProcess* image)
      : engine_(NULL),
        base_(base),
        codec_(codec),
        capture_(capture),
        network_(network),
        render_(render),
        rtp_(rtp),
        image_(image) {
  }

  virtual ~ViEWrapper() {}
  webrtc::VideoEngine* engine() { return engine_.get(); }
  webrtc::ViEBase* base() { return base_.get(); }
  webrtc::ViECodec* codec() { return codec_.get(); }
  webrtc::ViECapture* capture() { return capture_.get(); }
  webrtc::ViENetwork* network() { return network_.get(); }
  webrtc::ViERender* render() { return render_.get(); }
  webrtc::ViERTP_RTCP* rtp() { return rtp_.get(); }
  webrtc::ViEImageProcess* image() { return image_.get(); }
  int error() { return base_->LastError(); }

 private:
  scoped_vie_engine engine_;
  scoped_vie_ptr<webrtc::ViEBase> base_;
  scoped_vie_ptr<webrtc::ViECodec> codec_;
  scoped_vie_ptr<webrtc::ViECapture> capture_;
  scoped_vie_ptr<webrtc::ViENetwork> network_;
  scoped_vie_ptr<webrtc::ViERender> render_;
  scoped_vie_ptr<webrtc::ViERTP_RTCP> rtp_;
  scoped_vie_ptr<webrtc::ViEImageProcess> image_;
};

// Adds indirection to static WebRtc functions, allowing them to be mocked.
class ViETraceWrapper {
 public:
  virtual ~ViETraceWrapper() {}

  virtual int SetTraceFilter(const unsigned int filter) {
    return webrtc::VideoEngine::SetTraceFilter(filter);
  }
  virtual int SetTraceFile(const char* fileNameUTF8) {
    return webrtc::VideoEngine::SetTraceFile(fileNameUTF8);
  }
  virtual int SetTraceCallback(webrtc::TraceCallback* callback) {
    return webrtc::VideoEngine::SetTraceCallback(callback);
  }
};

}  // namespace cricket

#endif  // TALK_SESSION_PHONE_WEBRTCVIE_H_
