/*
 *  Copyright (c) 2012 The WebRTC project authors. All Rights Reserved.
 *
 *  Use of this source code is governed by a BSD-style license
 *  that can be found in the LICENSE file in the root of the source
 *  tree. An additional intellectual property rights grant can be found
 *  in the file PATENTS.  All contributing project authors may
 *  be found in the AUTHORS file in the root of the source tree.
 */

#ifndef WEBRTC_SYSTEM_WRAPPERS_INCLUDE_STATIC_INSTANCE_H_
#define WEBRTC_SYSTEM_WRAPPERS_INCLUDE_STATIC_INSTANCE_H_

#include <assert.h>

#include "webrtc/rtc_base/criticalsection.h"
#ifdef _WIN32
#include "webrtc/system_wrappers/include/fix_interlocked_exchange_pointer_win.h"
#endif

namespace webrtc {

enum CountOperation {
  kRelease,
  kAddRef,
  kAddRefNoCreate
};
enum CreateOperation {
  kInstanceExists,
  kCreate,
  kDestroy
};

template <class T>
// Construct On First Use idiom. Avoids
// "static initialization order fiasco".
static T* GetStaticInstance(CountOperation count_operation) {
  // TODO (hellner): use atomic wrapper instead.
  static volatile long instance_count = 0;
  static T* volatile instance = NULL;
  CreateOperation state = kInstanceExists;
#ifndef _WIN32
  static rtc::CriticalSection crit_sect;
  rtc::CritScope lock(&crit_sect);

  if (count_operation ==
      kAddRefNoCreate && instance_count == 0) {
    return NULL;
  }
  if (count_operation ==
      kAddRef ||
      count_operation == kAddRefNoCreate) {
    instance_count++;
    if (instance_count == 1) {
      state = kCreate;
    }
  } else {
    instance_count--;
    if (instance_count == 0) {
      state = kDestroy;
    }
  }
  if (state == kCreate) {
    instance = T::CreateInstance();
  } else if (state == kDestroy) {
    T* old_instance = instance;
    instance = NULL;
    // The state will not change past this point. Release the critical
    // section while deleting the object in case it would be blocking on
    // access back to this object. (This is the case for the tracing class
    // since the thread owned by the tracing class also traces).
    // TODO(hellner): this is a bit out of place but here goes, de-couple
    // thread implementation with trace implementation.
    crit_sect.Leave();
    if (old_instance) {
      delete old_instance;
    }
    // Re-acquire the lock since the scoped critical section will release
    // it.
    crit_sect.Enter();
    return NULL;
  }
#else  // _WIN32
  if (count_operation ==
      kAddRefNoCreate && instance_count == 0) {
    return NULL;
  }
  if (count_operation == kAddRefNoCreate) {
    if (1 == InterlockedIncrement(&instance_count)) {
      // The instance has been destroyed by some other thread. Rollback.
      InterlockedDecrement(&instance_count);
      assert(false);
      return NULL;
    }
    // Sanity to catch corrupt state.
    if (instance == NULL) {
      assert(false);
      InterlockedDecrement(&instance_count);
      return NULL;
    }
  } else if (count_operation == kAddRef) {
    if (instance_count == 0) {
      state = kCreate;
    } else {
      if (1 == InterlockedIncrement(&instance_count)) {
        // InterlockedDecrement because reference count should not be
        // updated just yet (that's done when the instance is created).
        InterlockedDecrement(&instance_count);
        state = kCreate;
      }
    }
  } else {
    int new_value = InterlockedDecrement(&instance_count);
    if (new_value == 0) {
      state = kDestroy;
    }
  }

  if (state == kCreate) {
    // Create instance and let whichever thread finishes first assign its
    // local copy to the global instance. All other threads reclaim their
    // local copy.
    T* new_instance = T::CreateInstance();
    if (1 == InterlockedIncrement(&instance_count)) {
      InterlockedExchangePointer(reinterpret_cast<void * volatile*>(&instance),
                                 new_instance);
    } else {
      InterlockedDecrement(&instance_count);
      if (new_instance) {
        delete static_cast<T*>(new_instance);
      }
    }
  } else if (state == kDestroy) {
    T* old_value = static_cast<T*>(InterlockedExchangePointer(
        reinterpret_cast<void * volatile*>(&instance), NULL));
    if (old_value) {
      delete static_cast<T*>(old_value);
    }
    return NULL;
  }
#endif  // #ifndef _WIN32
  return instance;
}

}  // namspace webrtc

#endif  // WEBRTC_SYSTEM_WRAPPERS_INCLUDE_STATIC_INSTANCE_H_
