tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

ref_counted_base.h (3156B)


      1 /*
      2 *  Copyright 2017 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 API_REF_COUNTED_BASE_H_
     11 #define API_REF_COUNTED_BASE_H_
     12 
     13 #include <type_traits>
     14 
     15 #include "api/ref_count.h"
     16 #include "rtc_base/ref_counter.h"
     17 
     18 namespace webrtc {
     19 
     20 class RefCountedBase {
     21 public:
     22  RefCountedBase() = default;
     23 
     24  RefCountedBase(const RefCountedBase&) = delete;
     25  RefCountedBase& operator=(const RefCountedBase&) = delete;
     26 
     27  void AddRef() const { ref_count_.IncRef(); }
     28  RefCountReleaseStatus Release() const {
     29    const auto status = ref_count_.DecRef();
     30    if (status == RefCountReleaseStatus::kDroppedLastRef) {
     31      delete this;
     32    }
     33    return status;
     34  }
     35 
     36 protected:
     37  // Provided for internal webrtc subclasses for corner cases where it's
     38  // necessary to know whether or not a reference is exclusively held.
     39  bool HasOneRef() const { return ref_count_.HasOneRef(); }
     40 
     41  virtual ~RefCountedBase() = default;
     42 
     43 private:
     44  mutable webrtc_impl::RefCounter ref_count_{0};
     45 };
     46 
     47 // Template based version of `RefCountedBase` for simple implementations that do
     48 // not need (or want) destruction via virtual destructor or the overhead of a
     49 // vtable.
     50 //
     51 // To use:
     52 //   struct MyInt : public RefCountedNonVirtual<MyInt>  {
     53 //     int foo_ = 0;
     54 //   };
     55 //
     56 //   scoped_refptr<MyInt> my_int(new MyInt());
     57 //
     58 // sizeof(MyInt) on a 32 bit system would then be 8, int + refcount and no
     59 // vtable generated.
     60 template <typename T>
     61 class RefCountedNonVirtual {
     62 public:
     63  RefCountedNonVirtual() = default;
     64 
     65  RefCountedNonVirtual(const RefCountedNonVirtual&) = delete;
     66  RefCountedNonVirtual& operator=(const RefCountedNonVirtual&) = delete;
     67 
     68  void AddRef() const { ref_count_.IncRef(); }
     69  RefCountReleaseStatus Release() const {
     70    // If you run into this assert, T has virtual methods. There are two
     71    // options:
     72    // 1) The class doesn't actually need virtual methods, the type is complete
     73    //    so the virtual attribute(s) can be removed.
     74    // 2) The virtual methods are a part of the design of the class. In this
     75    //    case you can consider using `RefCountedBase` instead or alternatively
     76    //    use `RefCountedObject`.
     77    static_assert(!std::is_polymorphic<T>::value,
     78                  "T has virtual methods. RefCountedBase is a better fit.");
     79    const auto status = ref_count_.DecRef();
     80    if (status == RefCountReleaseStatus::kDroppedLastRef) {
     81      delete static_cast<const T*>(this);
     82    }
     83    return status;
     84  }
     85 
     86 protected:
     87  // Provided for internal webrtc subclasses for corner cases where it's
     88  // necessary to know whether or not a reference is exclusively held.
     89  bool HasOneRef() const { return ref_count_.HasOneRef(); }
     90 
     91  ~RefCountedNonVirtual() = default;
     92 
     93 private:
     94  mutable webrtc_impl::RefCounter ref_count_{0};
     95 };
     96 
     97 }  // namespace webrtc
     98 
     99 
    100 #endif  // API_REF_COUNTED_BASE_H_