// Copyright 2018 The Fuchsia Authors. All rights reserved.
// Use of this source code is governed by a BSD-style license that can be
// found in the LICENSE file.

#ifndef FBL_REF_COUNTED_UPGRADEABLE_H_
#define FBL_REF_COUNTED_UPGRADEABLE_H_

#include <zircon/assert.h>
#include <fbl/macros.h>
#include <fbl/ref_counted_internal.h>
#include <fbl/ref_ptr.h>

#include <atomic>

namespace fbl {
namespace internal {

// A variant of the standard RefCouted base class which allows an
// "UpgradeFromRaw" operation which can be used to give weak-pointer like
// behavior for very specific use cases.
//
template <bool EnableAdoptionValidator>
class RefCountedUpgradeableBase : public RefCountedBase<EnableAdoptionValidator> {
public:
    RefCountedUpgradeableBase() = default;
    ~RefCountedUpgradeableBase() = default;

    // RefCountedUpgradeableBase<> instances may not be copied, assigned or moved.
    DISALLOW_COPY_ASSIGN_AND_MOVE(RefCountedUpgradeableBase);

    // This method must only be called from MakeRefPtrUpgradeFromRaw.  See its
    // comments for details in the proper use of this method. The actual job of
    // this function is to atomically increment the refcount if the refcount is
    // greater than zero.
    //
    // This method returns false if the object was found with an invalid
    // refcount (refcount was <= 0), and true if the refcount was not zero and
    // it was incremented.
    //
    // The procedure used is the while-CAS loop with the advantage that
    // compare_exchange on failure updates |old| on failure (to exchange) so the
    // loop does not have to do a separate load.
    //
    bool AddRefMaybeInDestructor() const __WARN_UNUSED_RESULT {
        int32_t old = this->ref_count_.load(std::memory_order_acquire);
        do {
            if (old <= 0) {
                return false;
            }
        } while (!this->ref_count_.compare_exchange_weak(old,
                                                         old + 1,
                                                         std::memory_order_acq_rel,
                                                         std::memory_order_acquire));
        return true;
    }
};

}  // namespace internal

// A variant of the standard RefCouted base class which allows an
// "UpgradeFromRaw" operation which can be used to give weak-pointer like
// behavior for a very specific use case in the kernel.
//
template <typename T,
          bool EnableAdoptionValidator = ZX_DEBUG_ASSERT_IMPLEMENTED>
class RefCountedUpgradeable : private internal::RefCountedUpgradeableBase<EnableAdoptionValidator> {
public:
    RefCountedUpgradeable() = default;
    ~RefCountedUpgradeable() = default;

    using internal::RefCountedBase<EnableAdoptionValidator>::AddRef;
    using internal::RefCountedBase<EnableAdoptionValidator>::Release;
    using internal::RefCountedBase<EnableAdoptionValidator>::Adopt;
    using internal::RefCountedBase<EnableAdoptionValidator>::ref_count_debug;
    using internal::RefCountedUpgradeableBase<EnableAdoptionValidator>::AddRefMaybeInDestructor;

    // RefCountedUpgradeable<> instances may not be copied, assigned or moved.
    DISALLOW_COPY_ASSIGN_AND_MOVE(RefCountedUpgradeable);
};

// Constructs a RefPtr from a raw T* which is being held alive by RefPtr
// with the caveat that the existing RefPtr might be in the process of
// destructing the T object. When the T object is in the destructor, the
// resulting RefPtr is null, otherwise the resulting RefPtr points to T*
// with the updated reference count.
//
// The only way for this to be a valid pattern is that the call is made
// while holding |lock| and that the same lock also is used to protect the
// value of T* .
//
// This pattern is needed in collaborating objects which cannot hold a
// RefPtr to each other because it would cause a reference cycle. Instead
// there is a raw pointer from one to the other and a RefPtr in the
// other direction. When needed the raw pointer can be upgraded via
// MakeRefPtrUpgradeFromRaw() and operated outside |lock|.
//
// For example:
//
//  class Holder: public RefCounted<Holder> {
//  public:
//      void add_client(Client* c) {
//          Autolock al(&lock_);
//          client_ = c;
//      }
//
//      void remove_client() {
//          Autolock al(&lock_);
//          client_ = nullptr;
//      }
//
//      void PassClient(Bar* bar) {
//          fbl::RefPtr<Client> rc_client;
//          {
//              Autolock al(&lock_);
//              if (client_) {
//                  rc_client = fbl::internal::MakeRefPtrUpgradeFromRaw(client_, lock_);
//              }
//          }
//
//          if (rc_client) {
//              bar->Client(std::move(rc_client));  // Bar might keep a ref to client.
//          } else {
//              bar->OnNoClient();
//          }
//      }
//
//  private:
//      fbl::Mutex lock_;
//      Client* client __TA_REQUIRES(lock_);
//  };
//
//  class Client: public RefCounted<Client> {
//  public:
//      Client(RefPtr<Holder> holder) : holder_(std::move(holder)) {
//          holder_->add_client(this);
//      }
//
//      ~Client() {
//          holder_->remove_client();
//      }
//  private:
//      fbl::RefPtr<Holder> holder_;
//  };
//
//

template <typename T, typename LockCapability>
inline RefPtr<T> MakeRefPtrUpgradeFromRaw(T* ptr, const LockCapability& lock) __TA_REQUIRES(lock) {
    if (!ptr->AddRefMaybeInDestructor()) {
        return nullptr;
    }

    return internal::MakeRefPtrNoAdopt(ptr);
}

}  // namespace fbl

#endif  // FBL_REF_COUNTED_UPGRADEABLE_H_
