什么是RefBase?RefBase是Android中的一个C++类,用于内存管理,相关的类还包括LightRefBase、sp和wp。在Android源码中的许多地方都可以看到RefBase的使用,那么,为什么RefBase这么受欢迎呢?这源于C++的指针与动态内存管理,指针本身就是一个复杂的概念,而动态内存管理又提高了其复杂性,new一般情况下与delete配对使用,防止内存泄漏,但在大型项目中很难保证这一点,于是各种奇奇怪怪的问题就来了;不像其它语言如Java一样,有gc机制,对不再使用的对象会自动回收内存,不必担心内存泄漏问题,但是,C++注重性能,而gc势必会影响性能,所以需要开发者格外注意;这样,RefBase来了,通过引用计数原理,解放开发者对内存泄漏问题的过多担心,自动delete不再使用的对象。
RefBase源码位置在Android中的system/core/libutils目录下,属于libutils库的内容,相关头文件在system/core/include/utils,下面是源码分析。
/**
* @file RefBase.h
* Copyright: Android Open Source Project
* License: Apache 2.0
*/
#ifndef ANDROID_REF_BASE_H
#define ANDROID_REF_BASE_H
// Location: external/libcxx/include
// C++11原子操作
#include <atomic>
// Location: bionic/libc/include
#include <stdint.h>
#include <sys/types.h>
#include <stdlib.h>
#include <string.h>
// Locaion: system/core/include
#include <utils/StrongPointer.h>
#include <utils/TypeHelpers.h>
// ---------------------------------------------------------------------------
namespace android {
// Location: system/libhwbinder
// 抽象类
class TextOutput;
TextOutput& printWeakPointer(TextOutput& to, const void* val);
// ---------------------------------------------------------------------------
// 用于wp的宏
// 简化了比较操作符的定义
#define COMPARE_WEAK(_op_) \
inline bool operator _op_ (const sp<T>& o) const { \
return m_ptr _op_ o.m_ptr; \
} \
inline bool operator _op_ (const T* o) const { \
return m_ptr _op_ o; \
} \
template<typename U> \
inline bool operator _op_ (const sp<U>& o) const { \
return m_ptr _op_ o.m_ptr; \
} \
template<typename U> \
inline bool operator _op_ (const U* o) const { \
return m_ptr _op_ o; \
}
// ---------------------------------------------------------------------------
// 忽略push与pop之间的编译警告
#if defined(__clang__)
#pragma clang diagnostic push
#pragma clang diagnostic ignored "-Wweak-vtables"
#endif
/**
* @class ReferenceRenamer
* operator() 纯虚函数
* 非虚析构函数(故意为之)避免派生类的代码开销
*/
class ReferenceRenamer
{
protected:
~ReferenceRenamer() {}
public:
virtual void operator()(size_t i) const = 0;
};
#if defined(__clang__)
#pragma clang diagnostic pop
#endif
// ---------------------------------------------------------------------------
/**
* @class RefBase
* 引用计数基类
*/
class RefBase
{
public:
void incStrong(const void* id) const; // 增加强引用计数
void decStrong(const void* id) const; // 减少强引用计数
void forceIncStrong(const void* id) const; // 强制增加强引用计数
int32_t getStrongCount() const; // 获取当前强引用计数(只用于debug)
/**
* @class weakref_type
* 弱引用计数类型
*/
class weakref_type
{
public:
RefBase* refBase() const; // 获取引用计数基类指针
void incWeak(const void* id); // 增加弱引用计数
void decWeak(const void* id); // 减少弱引用计数
bool attemptIncStrong(const void* id); // 获取强引用
bool attemptIncWeak(const void* id); // 获取弱引用(可能不安全)
int32_t getWeakCount() const; // 获取当前弱引用计数(只用于debug)
void printRefs() const; // 打印引用计数相关信息(只用于debug)
/**
* @fn trackMe: 跟踪引用计数信息
* @param enable: true-跟踪 false-不跟踪
* @param retain: true-跟踪所有的 false-跟踪最新的
* @note 只用于debug
*/
void trackMe(bool enable, bool retain);
};
weakref_type* createWeak(const void* id) const; // 创建弱引用计数类型
weakref_type* getWeakRefs() const; // 获取弱引用计数类型指针
inline void printRefs() const { getWeakRefs()->printRefs(); } // 打印引用计数相关信息(只用于debug)
inline void trackMe(bool enable, bool retain) // 跟踪引用计数信息(只用于debug)
{
getWeakRefs()->trackMe(enable, retain);
}
typedef RefBase basetype; // typedef别名
protected:
RefBase(); // protected构造(使用时需派生子类)
virtual ~RefBase(); // 虚析构
// 用于extendObjectLifetime()
enum {
OBJECT_LIFETIME_STRONG = 0x0000,
OBJECT_LIFETIME_WEAK = 0x0001,
OBJECT_LIFETIME_MASK = 0x0001
};
void extendObjectLifetime(int32_t mode); // 扩展对象生命期
// 用于 onIncStrongAttempted()
enum {
FIRST_INC_STRONG = 0x0001
};
/**
* 四个回调
* @fn onFirstRef: 强指针/引用初始化后回调
* @fn onLastStrongRef: 最后一个强引用不再使用时或者需要取消不必要的onIncStrongAttempted的影响时
* @fn onIncStrongAttempted: 生命期为OBJECT_LIFETIME_WEAK
* @return true-成功转化为强指针时(可能有副作用)
× @param flags: [TO-BE-REMOVED]FIRST_INC_STRONG
* @fn onLastWeakRef: [TO-BE-REMOVED]生命期为OBJECT_LIFETIME_WEAK且最后一个引用不再使用时
*/
virtual void onFirstRef();
virtual void onLastStrongRef(const void* id);
virtual bool onIncStrongAttempted(uint32_t flags, const void* id);
virtual void onLastWeakRef(const void* id);
private:
friend class weakref_type; // 友元
class weakref_impl; // RefBase.cpp中定义
RefBase(const RefBase& o); // 拷贝构造(无定义-禁止拷贝)
RefBase& operator=(const RefBase& o); // 赋值操作符(无定义-禁止赋值)
private:
friend class ReferenceMover; // 下面有定义
// 三个用于修改引用属性的静态函数
static void renameRefs(size_t n, const ReferenceRenamer& renamer);
static void renameRefId(weakref_type* ref, const void* old_id, const void* new_id);
static void renameRefId(RefBase* ref, const void* old_id, const void* new_id);
weakref_impl* const mRefs; // 唯一的成员变量(定义隐藏在cpp中为常说的句柄)
};
// ---------------------------------------------------------------------------
/**
* @class LightRefBase<T>
* 轻量级的RefBase(少了不少多西)
* 原子操作使用了C++11
*/
template <class T>
class LightRefBase
{
public:
inline LightRefBase() : mCount(0) {}
inline void incStrong(__attribute__((unused)) const void* id) const {
mCount.fetch_add(1, std::memory_order_relaxed);
}
inline void decStrong(__attribute__((unused)) const void* id) const {
if (mCount.fetch_sub(1, std::memory_order_release) == 1) {
std::atomic_thread_fence(std::memory_order_acquire);
delete static_cast<const T*>(this);
}
}
inline int32_t getStrongCount() const { // 只用于debug
return mCount.load(std::memory_order_relaxed);
}
typedef LightRefBase<T> basetype;
protected:
inline ~LightRefBase() {}
private:
friend class ReferenceMover;
inline static void renameRefs(size_t /*n*/, const ReferenceRenamer& /*renamer*/) {}
inline static void renameRefId(T* /*ref*/, const void* /*old_id*/, const void* /*new_id*/) {}
private:
mutable std::atomic<int32_t> mCount;
};
/**
* @class VirtualLightRefBase
* 使用LightRefBase进行包装
* 只是声明了虚析构函数以消除LightRefBase的模板需求
*/
// This is a wrapper around LightRefBase that simply enforces a virtual
// destructor to eliminate the template requirement of LightRefBase
class VirtualLightRefBase : public LightRefBase<VirtualLightRefBase>
{
public:
virtual ~VirtualLightRefBase();
};
// ---------------------------------------------------------------------------
/**
* @class wp<T>
*/
template <typename T>
class wp
{
public:
// 模板中经常使用typename声明其后的内容为一种数据类型
typedef typename RefBase::weakref_type weakref_type;
// 构造
inline wp() : m_ptr(0) {}
// (拷贝)构造
wp(T* other); // NOLINT(implicit)
wp(const wp<T>& other);
explicit wp(const sp<T>& other);
template<typename U> wp(U* other); // NOLINT(implicit)
template<typename U> wp(const sp<U>& other); // NOLINT(implicit)
template<typename U> wp(const wp<U>& other); // NOLINT(implicit)
// 析构
~wp();
// 赋值操作符
wp& operator = (T* other);
wp& operator = (const wp<T>& other);
wp& operator = (const sp<T>& other);
template<typename U> wp& operator = (U* other);
template<typename U> wp& operator = (const wp<U>& other);
template<typename U> wp& operator = (const sp<U>& other);
// 同时设置对象和引用
void set_object_and_refs(T* other, weakref_type* refs);
// 转换为强指针
sp<T> promote() const;
// 清空wp保存的对象指针
void clear();
// 获取弱引用类型指针/获取wp保存的对象指针
inline weakref_type* get_refs() const { return m_refs; }
inline T* unsafe_get() const { return m_ptr; }
// 比较操作符
COMPARE_WEAK(==)
COMPARE_WEAK(!=)
COMPARE_WEAK(>)
COMPARE_WEAK(<)
COMPARE_WEAK(<=)
COMPARE_WEAK(>=)
inline bool operator == (const wp<T>& o) const {
return (m_ptr == o.m_ptr) && (m_refs == o.m_refs);
}
template<typename U>
inline bool operator == (const wp<U>& o) const {
return m_ptr == o.m_ptr;
}
inline bool operator > (const wp<T>& o) const {
return (m_ptr == o.m_ptr) ? (m_refs > o.m_refs) : (m_ptr > o.m_ptr);
}
template<typename U>
inline bool operator > (const wp<U>& o) const {
return (m_ptr == o.m_ptr) ? (m_refs > o.m_refs) : (m_ptr > o.m_ptr);
}
inline bool operator < (const wp<T>& o) const {
return (m_ptr == o.m_ptr) ? (m_refs < o.m_refs) : (m_ptr < o.m_ptr);
}
template<typename U>
inline bool operator < (const wp<U>& o) const {
return (m_ptr == o.m_ptr) ? (m_refs < o.m_refs) : (m_ptr < o.m_ptr);
}
inline bool operator != (const wp<T>& o) const { return m_refs != o.m_refs; }
template<typename U> inline bool operator != (const wp<U>& o) const { return !operator == (o); }
inline bool operator <= (const wp<T>& o) const { return !operator > (o); }
template<typename U> inline bool operator <= (const wp<U>& o) const { return !operator > (o); }
inline bool operator >= (const wp<T>& o) const { return !operator < (o); }
template<typename U> inline bool operator >= (const wp<U>& o) const { return !operator < (o); }
private:
// (其它的)sp<>和wp<>为友元
template<typename Y> friend class sp;
template<typename Y> friend class wp;
// wp保存的对象指针和对应的弱引用类型指针
T* m_ptr;
weakref_type* m_refs;
};
// 为TextOutput重载operator<<
template <typename T>
TextOutput& operator<<(TextOutput& to, const wp<T>& val);
#undef COMPARE_WEAK
// ---------------------------------------------------------------------------
// 下面是(拷贝)构造的几种形式
// 需要注意若引用更新
template<typename T>
wp<T>::wp(T* other)
: m_ptr(other)
{
if (other) m_refs = other->createWeak(this);
}
template<typename T>
wp<T>::wp(const wp<T>& other)
: m_ptr(other.m_ptr), m_refs(other.m_refs)
{
if (m_ptr) m_refs->incWeak(this);
}
template<typename T>
wp<T>::wp(const sp<T>& other)
: m_ptr(other.m_ptr)
{
if (m_ptr) {
m_refs = m_ptr->createWeak(this);
}
}
template<typename T> template<typename U>
wp<T>::wp(U* other)
: m_ptr(other)
{
if (other) m_refs = other->createWeak(this);
}
template<typename T> template<typename U>
wp<T>::wp(const wp<U>& other)
: m_ptr(other.m_ptr)
{
if (m_ptr) {
m_refs = other.m_refs;
m_refs->incWeak(this);
}
}
template<typename T> template<typename U>
wp<T>::wp(const sp<U>& other)
: m_ptr(other.m_ptr)
{
if (m_ptr) {
m_refs = m_ptr->createWeak(this);
}
}
// 析构函数减少弱引用但不直接delete对象指针m_ptr
// 在decWeak中当若引用减少到1时自动delete
template<typename T>
wp<T>::~wp()
{
if (m_ptr) m_refs->decWeak(this);
}
// 下面是重载的operator =的几种形式
// 需要注意新、旧对象的若引用更新
template<typename T>
wp<T>& wp<T>::operator = (T* other)
{
weakref_type* newRefs =
other ? other->createWeak(this) : 0;
if (m_ptr) m_refs->decWeak(this);
m_ptr = other;
m_refs = newRefs;
return *this;
}
template<typename T>
wp<T>& wp<T>::operator = (const wp<T>& other)
{
weakref_type* otherRefs(other.m_refs);
T* otherPtr(other.m_ptr);
if (otherPtr) otherRefs->incWeak(this);
if (m_ptr) m_refs->decWeak(this);
m_ptr = otherPtr;
m_refs = otherRefs;
return *this;
}
template<typename T>
wp<T>& wp<T>::operator = (const sp<T>& other)
{
weakref_type* newRefs =
other != NULL ? other->createWeak(this) : 0;
T* otherPtr(other.m_ptr);
if (m_ptr) m_refs->decWeak(this);
m_ptr = otherPtr;
m_refs = newRefs;
return *this;
}
template<typename T> template<typename U>
wp<T>& wp<T>::operator = (U* other)
{
weakref_type* newRefs =
other ? other->createWeak(this) : 0;
if (m_ptr) m_refs->decWeak(this);
m_ptr = other;
m_refs = newRefs;
return *this;
}
template<typename T> template<typename U>
wp<T>& wp<T>::operator = (const wp<U>& other)
{
weakref_type* otherRefs(other.m_refs);
U* otherPtr(other.m_ptr);
if (otherPtr) otherRefs->incWeak(this);
if (m_ptr) m_refs->decWeak(this);
m_ptr = otherPtr;
m_refs = otherRefs;
return *this;
}
template<typename T> template<typename U>
wp<T>& wp<T>::operator = (const sp<U>& other)
{
weakref_type* newRefs =
other != NULL ? other->createWeak(this) : 0;
U* otherPtr(other.m_ptr);
if (m_ptr) m_refs->decWeak(this);
m_ptr = otherPtr;
m_refs = newRefs;
return *this;
}
// 保存对象指针和若引用类型指针时
// 需要对other和m_ptr分别进行减少、增加弱引用处理
template<typename T>
void wp<T>::set_object_and_refs(T* other, weakref_type* refs)
{
if (other) refs->incWeak(this);
if (m_ptr) m_refs->decWeak(this);
m_ptr = other;
m_refs = refs;
}
// 把对象指针m_ptr提升为强指针
template<typename T>
sp<T> wp<T>::promote() const
{
sp<T> result;
if (m_ptr && m_refs->attemptIncStrong(&result)) {
result.set_pointer(m_ptr);
}
return result;
}
// 清空对象指针m_ptr并减少弱引用
template<typename T>
void wp<T>::clear()
{
if (m_ptr) {
m_refs->decWeak(this);
m_ptr = 0;
}
}
// 重载了TextOutput的operator<<
template <typename T>
inline TextOutput& operator<<(TextOutput& to, const wp<T>& val)
{
return printWeakPointer(to, val.unsafe_get());
}
// ---------------------------------------------------------------------------
/**
* @class ReferenceMover
*/
class ReferenceMover
{
public:
template<typename TYPE> static inline
void move_references(sp<TYPE>* dest, sp<TYPE> const* src, size_t n) {
/**
* @class Renamer
* for sp
*/
class Renamer : public ReferenceRenamer
{
sp<TYPE>* d_;
sp<TYPE> const* s_;
virtual void operator()(size_t i) const {
// The id are known to be the sp<>'s this pointer
TYPE::renameRefId(d_[i].get(), &s_[i], &d_[i]);
}
public:
Renamer(sp<TYPE>* d, sp<TYPE> const* s) : d_(d), s_(s) {}
virtual ~Renamer() {}
};
memmove(dest, src, n * sizeof(sp<TYPE>));
TYPE::renameRefs(n, Renamer(dest, src));
}
template<typename TYPE> static inline
void move_references(wp<TYPE>* dest, wp<TYPE> const* src, size_t n) {
/**
* @class Renamer
* for wp
*/
class Renamer : public ReferenceRenamer {
wp<TYPE>* d_;
wp<TYPE> const* s_;
virtual void operator()(size_t i) const {
TYPE::renameRefId(d_[i].get_refs(), &s_[i], &d_[i]);
}
public:
Renamer(wp<TYPE>* rd, wp<TYPE> const* rs) : d_(rd), s_(rs) {}
virtual ~Renamer() {}
};
memmove(dest, src, n * sizeof(wp<TYPE>));
TYPE::renameRefs(n, Renamer(dest, src));
}
};
template<typename TYPE> inline
void move_forward_type(sp<TYPE>* d, sp<TYPE> const* s, size_t n) {
ReferenceMover::move_references(d, s, n);
}
template<typename TYPE> inline
void move_backward_type(sp<TYPE>* d, sp<TYPE> const* s, size_t n) {
ReferenceMover::move_references(d, s, n);
}
template<typename TYPE> inline
void move_forward_type(wp<TYPE>* d, wp<TYPE> const* s, size_t n) {
ReferenceMover::move_references(d, s, n);
}
template<typename TYPE> inline
void move_backward_type(wp<TYPE>* d, wp<TYPE> const* s, size_t n) {
ReferenceMover::move_references(d, s, n);
}
}; // namespace android
// ---------------------------------------------------------------------------
#endif // ANDROID_REF_BASE_H
/**
* @file StrongPointer.h
* Copyright: Android Open Source Project
* License: Apache 2.0
*/
#ifndef ANDROID_STRONG_POINTER_H
#define ANDROID_STRONG_POINTER_H
// Location: system/core/include
// Android包装的原子操作接口(使用了GCC的原子特性)
#include <cutils/atomic.h>
// Location: bionic/libc/include
#include <stdint.h>
#include <sys/types.h>
#include <stdlib.h>
// ---------------------------------------------------------------------------
namespace android {
// wp<>模板类前置声明
template<typename T> class wp;
// ---------------------------------------------------------------------------
// 用于sp<>的比较操作符
#define COMPARE(_op_) \
inline bool operator _op_ (const sp<T>& o) const { \
return m_ptr _op_ o.m_ptr; \
} \
inline bool operator _op_ (const T* o) const { \
return m_ptr _op_ o; \
} \
template<typename U> \
inline bool operator _op_ (const sp<U>& o) const { \
return m_ptr _op_ o.m_ptr; \
} \
template<typename U> \
inline bool operator _op_ (const U* o) const { \
return m_ptr _op_ o; \
} \
inline bool operator _op_ (const wp<T>& o) const { \
return m_ptr _op_ o.m_ptr; \
} \
template<typename U> \
inline bool operator _op_ (const wp<U>& o) const { \
return m_ptr _op_ o.m_ptr; \
}
// ---------------------------------------------------------------------------
/**
* @class sp<T>
*/
template<typename T>
class sp
{
public:
// 构造
inline sp() : m_ptr(0) {}
// (拷贝)构造
sp(T* other); // NOLINT(implicit)
sp(const sp<T>& other);
sp(sp<T>&& other);
template<typename U> sp(U* other); // NOLINT(implicit)
template<typename U> sp(const sp<U>& other); // NOLINT(implicit)
template<typename U> sp(sp<U>&& other); // NOLINT(implicit)
// 析构
~sp();
// 赋值操作符
sp& operator = (T* other);
sp& operator = (const sp<T>& other);
sp& operator = (sp<T>&& other);
template<typename U> sp& operator = (const sp<U>& other);
template<typename U> sp& operator = (sp<U>&& other);
template<typename U> sp& operator = (U* other);
// 专门用于ProcessState
void force_set(T* other);
// 重置对象指针
void clear();
// 访问对象指针
inline T& operator* () const { return *m_ptr; }
inline T* operator-> () const { return m_ptr; }
inline T* get() const { return m_ptr; }
// 比较操作符
COMPARE(==)
COMPARE(!=)
COMPARE(>)
COMPARE(<)
COMPARE(<=)
COMPARE(>=)
private:
// 友元声明
template<typename Y> friend class sp;
template<typename Y> friend class wp;
// 保存对象指针
void set_pointer(T* ptr);
// 对象指针
T* m_ptr;
};
#undef COMPARE
// ---------------------------------------------------------------------------
// 下面是sp<>的(拷贝)构造的几种形式
// 需要注意C++11的右值引用(移动拷贝)
template<typename T>
sp<T>::sp(T* other)
: m_ptr(other)
{
if (other)
other->incStrong(this);
}
template<typename T>
sp<T>::sp(const sp<T>& other)
: m_ptr(other.m_ptr)
{
if (m_ptr)
m_ptr->incStrong(this);
}
template<typename T>
sp<T>::sp(sp<T>&& other)
: m_ptr(other.m_ptr)
{
other.m_ptr = nullptr;
}
template<typename T> template<typename U>
sp<T>::sp(U* other)
: m_ptr(other)
{
if (other)
(static_cast<T*>(other))->incStrong(this);
}
template<typename T> template<typename U>
sp<T>::sp(const sp<U>& other)
: m_ptr(other.m_ptr)
{
if (m_ptr)
m_ptr->incStrong(this);
}
template<typename T> template<typename U>
sp<T>::sp(sp<U>&& other)
: m_ptr(other.m_ptr)
{
other.m_ptr = nullptr;
}
// 析构时减少强引用但不在这里进行真正地delete对象指针m_ptr
// 当decStrong时强引用计数为1时自动delete
template<typename T>
sp<T>::~sp()
{
if (m_ptr)
m_ptr->decStrong(this);
}
// 下面是operator =的几种形式
// 需要注意强引用计数的更新及右值引用
template<typename T>
sp<T>& sp<T>::operator =(const sp<T>& other)
{
T* otherPtr(other.m_ptr);
if (otherPtr)
otherPtr->incStrong(this);
if (m_ptr)
m_ptr->decStrong(this);
m_ptr = otherPtr;
return *this;
}
template<typename T>
sp<T>& sp<T>::operator =(sp<T>&& other)
{
if (m_ptr)
m_ptr->decStrong(this);
m_ptr = other.m_ptr;
other.m_ptr = nullptr;
return *this;
}
template<typename T>
sp<T>& sp<T>::operator =(T* other)
{
if (other)
other->incStrong(this);
if (m_ptr)
m_ptr->decStrong(this);
m_ptr = other;
return *this;
}
template<typename T> template<typename U>
sp<T>& sp<T>::operator =(const sp<U>& other)
{
T* otherPtr(other.m_ptr);
if (otherPtr)
otherPtr->incStrong(this);
if (m_ptr)
m_ptr->decStrong(this);
m_ptr = otherPtr;
return *this;
}
template<typename T> template<typename U>
sp<T>& sp<T>::operator =(sp<U>&& other)
{
if (m_ptr)
m_ptr->decStrong(this);
m_ptr = other.m_ptr;
other.m_ptr = nullptr;
return *this;
}
template<typename T> template<typename U>
sp<T>& sp<T>::operator =(U* other)
{
if (other)
(static_cast<T*>(other))->incStrong(this);
if (m_ptr)
m_ptr->decStrong(this);
m_ptr = other;
return *this;
}
// 强制保存对象指针并增加强引用计数
template<typename T>
void sp<T>::force_set(T* other)
{
other->forceIncStrong(this);
m_ptr = other;
}
// 重置对象指针并减少强引用计数
template<typename T>
void sp<T>::clear()
{
if (m_ptr) {
m_ptr->decStrong(this);
m_ptr = 0;
}
}
// 简单地保存对象指针
template<typename T>
void sp<T>::set_pointer(T* ptr)
{
m_ptr = ptr;
}
}; // namespace android
// ---------------------------------------------------------------------------
#endif // ANDROID_STRONG_POINTER_H
/**
* @file TypeHelpers.h
* 用于处理C++数据类型相关特性
* Copyright: Android Open Source Project
* License: Apache 2.0
*/
#ifndef ANDROID_TYPE_HELPERS_H
#define ANDROID_TYPE_HELPERS_H
#include <new>
#include <type_traits>
#include <stdint.h>
#include <string.h>
#include <sys/types.h>
// ---------------------------------------------------------------------------
namespace android {
// 类型特性包括ctor/dtor/copy/move/pointer
template <typename T> struct trait_trivial_ctor { enum { value = false }; };
template <typename T> struct trait_trivial_dtor { enum { value = false }; };
template <typename T> struct trait_trivial_copy { enum { value = false }; };
template <typename T> struct trait_trivial_move { enum { value = false }; };
template <typename T> struct trait_pointer { enum { value = false }; };
template <typename T> struct trait_pointer<T*> { enum { value = true }; };
template <typename TYPE>
struct traits {
enum {
// 这个类型是否为指针
is_pointer = trait_pointer<TYPE>::value,
// 这个类型的构造是否为空操作
has_trivial_ctor = is_pointer || trait_trivial_ctor<TYPE>::value,
// 这个类型的析构是否为空操作
has_trivial_dtor = is_pointer || trait_trivial_dtor<TYPE>::value,
// 这个类型是否可以通过memcpy进行拷贝构造
has_trivial_copy = is_pointer || trait_trivial_copy<TYPE>::value,
// 这个类型是否可以通过memmove进行移动构造
has_trivial_move = is_pointer || trait_trivial_move<TYPE>::value
};
};
// 聚合了两种类型
template <typename T, typename U>
struct aggregate_traits {
enum {
is_pointer = false,
has_trivial_ctor =
traits<T>::has_trivial_ctor && traits<U>::has_trivial_ctor,
has_trivial_dtor =
traits<T>::has_trivial_dtor && traits<U>::has_trivial_dtor,
has_trivial_copy =
traits<T>::has_trivial_copy && traits<U>::has_trivial_copy,
has_trivial_move =
traits<T>::has_trivial_move && traits<U>::has_trivial_move
};
};
// 模板特化
#define ANDROID_TRIVIAL_CTOR_TRAIT( T ) \
template<> struct trait_trivial_ctor< T > { enum { value = true }; };
#define ANDROID_TRIVIAL_DTOR_TRAIT( T ) \
template<> struct trait_trivial_dtor< T > { enum { value = true }; };
#define ANDROID_TRIVIAL_COPY_TRAIT( T ) \
template<> struct trait_trivial_copy< T > { enum { value = true }; };
#define ANDROID_TRIVIAL_MOVE_TRAIT( T ) \
template<> struct trait_trivial_move< T > { enum { value = true }; };
#define ANDROID_BASIC_TYPES_TRAITS( T ) \
ANDROID_TRIVIAL_CTOR_TRAIT( T ) \
ANDROID_TRIVIAL_DTOR_TRAIT( T ) \
ANDROID_TRIVIAL_COPY_TRAIT( T ) \
ANDROID_TRIVIAL_MOVE_TRAIT( T )
// ---------------------------------------------------------------------------
// 几种built-in类型
ANDROID_BASIC_TYPES_TRAITS( void )
ANDROID_BASIC_TYPES_TRAITS( bool )
ANDROID_BASIC_TYPES_TRAITS( char )
ANDROID_BASIC_TYPES_TRAITS( unsigned char )
ANDROID_BASIC_TYPES_TRAITS( short )
ANDROID_BASIC_TYPES_TRAITS( unsigned short )
ANDROID_BASIC_TYPES_TRAITS( int )
ANDROID_BASIC_TYPES_TRAITS( unsigned int )
ANDROID_BASIC_TYPES_TRAITS( long )
ANDROID_BASIC_TYPES_TRAITS( unsigned long )
ANDROID_BASIC_TYPES_TRAITS( long long )
ANDROID_BASIC_TYPES_TRAITS( unsigned long long )
ANDROID_BASIC_TYPES_TRAITS( float )
ANDROID_BASIC_TYPES_TRAITS( double )
// ---------------------------------------------------------------------------
// 顺序比较
template<typename TYPE> inline
int strictly_order_type(const TYPE& lhs, const TYPE& rhs) {
return (lhs < rhs) ? 1 : 0;
}
template<typename TYPE> inline
int compare_type(const TYPE& lhs, const TYPE& rhs) {
return strictly_order_type(rhs, lhs) - strictly_order_type(lhs, rhs);
}
// create/destroy/copy/move
template<typename TYPE> inline
void construct_type(TYPE* p, size_t n) {
if (!traits<TYPE>::has_trivial_ctor) {
while (n > 0) {
n--;
new(p++) TYPE;
}
}
}
template<typename TYPE> inline
void destroy_type(TYPE* p, size_t n) {
if (!traits<TYPE>::has_trivial_dtor) {
while (n > 0) {
n--;
p->~TYPE();
p++;
}
}
}
template<typename TYPE>
typename std::enable_if<traits<TYPE>::has_trivial_copy>::type
inline
copy_type(TYPE* d, const TYPE* s, size_t n) {
memcpy(d,s,n * sizeof(TYPE));
}
template<typename TYPE>
typename std::enable_if<!traits<TYPE>::has_trivial_copy>::type
inline
copy_type(TYPE* d, const TYPE* s, size_t n) {
while (n > 0) {
n--;
new(d) TYPE(*s);
d++, s++;
}
}
template<typename TYPE> inline
void splat_type(TYPE* where, const TYPE* what, size_t n) {
if (!traits<TYPE>::has_trivial_copy) {
while (n > 0) {
n--;
new(where) TYPE(*what);
where++;
}
} else {
while (n > 0) {
n--;
*where++ = *what;
}
}
}
template<typename TYPE>
struct use_trivial_move : public std::integral_constant<bool,
(traits<TYPE>::has_trivial_dtor && traits<TYPE>::has_trivial_copy)
|| traits<TYPE>::has_trivial_move
> {};
template<typename TYPE>
typename std::enable_if<use_trivial_move<TYPE>::value>::type
inline
move_forward_type(TYPE* d, const TYPE* s, size_t n = 1) {
memmove(d, s, n * sizeof(TYPE));
}
template<typename TYPE>
typename std::enable_if<!use_trivial_move<TYPE>::value>::type
inline
move_forward_type(TYPE* d, const TYPE* s, size_t n = 1) {
d += n;
s += n;
while (n > 0) {
n--;
--d, --s;
if (!traits<TYPE>::has_trivial_copy) {
new(d) TYPE(*s);
} else {
*d = *s;
}
if (!traits<TYPE>::has_trivial_dtor) {
s->~TYPE();
}
}
}
template<typename TYPE>
typename std::enable_if<use_trivial_move<TYPE>::value>::type
inline
move_backward_type(TYPE* d, const TYPE* s, size_t n = 1) {
memmove(d, s, n * sizeof(TYPE));
}
template<typename TYPE>
typename std::enable_if<!use_trivial_move<TYPE>::value>::type
inline
move_backward_type(TYPE* d, const TYPE* s, size_t n = 1) {
while (n > 0) {
n--;
if (!traits<TYPE>::has_trivial_copy) {
new(d) TYPE(*s);
} else {
*d = *s;
}
if (!traits<TYPE>::has_trivial_dtor) {
s->~TYPE();
}
d++, s++;
}
}
// ---------------------------------------------------------------------------
// 键-值对
template <typename KEY, typename VALUE>
struct key_value_pair_t {
typedef KEY key_t;
typedef VALUE value_t;
KEY key;
VALUE value;
key_value_pair_t() {}
key_value_pair_t(const key_value_pair_t& o) : key(o.key), value(o.value) {}
key_value_pair_t& operator=(const key_value_pair_t& o) {
key = o.key;
value = o.value;
return *this;
}
key_value_pair_t(const KEY& k, const VALUE& v) : key(k), value(v) {}
explicit key_value_pair_t(const KEY& k) : key(k) {}
inline bool operator < (const key_value_pair_t& o) const {
return strictly_order_type(key, o.key);
}
inline const KEY& getKey() const {
return key;
}
inline const VALUE& getValue() const {
return value;
}
};
template <typename K, typename V>
struct trait_trivial_ctor< key_value_pair_t<K, V> >
{ enum { value = aggregate_traits<K,V>::has_trivial_ctor }; };
template <typename K, typename V>
struct trait_trivial_dtor< key_value_pair_t<K, V> >
{ enum { value = aggregate_traits<K,V>::has_trivial_dtor }; };
template <typename K, typename V>
struct trait_trivial_copy< key_value_pair_t<K, V> >
{ enum { value = aggregate_traits<K,V>::has_trivial_copy }; };
template <typename K, typename V>
struct trait_trivial_move< key_value_pair_t<K, V> >
{ enum { value = aggregate_traits<K,V>::has_trivial_move }; };
// ---------------------------------------------------------------------------
// 哈唏类型
typedef uint32_t hash_t;
// 哈唏类型模板
template <typename TKey>
hash_t hash_type(const TKey& key);
// 哈唏类型模板特化
#define ANDROID_INT32_HASH(T) \
template <> inline hash_t hash_type(const T& value) { return hash_t(value); }
#define ANDROID_INT64_HASH(T) \
template <> inline hash_t hash_type(const T& value) { \
return hash_t((value >> 32) ^ value); }
#define ANDROID_REINTERPRET_HASH(T, R) \
template <> inline hash_t hash_type(const T& value) { \
R newValue; \
static_assert(sizeof(newValue) == sizeof(value), "size mismatch"); \
memcpy(&newValue, &value, sizeof(newValue)); \
return hash_type(newValue); \
}
// 几种built-in类型
ANDROID_INT32_HASH(bool)
ANDROID_INT32_HASH(int8_t)
ANDROID_INT32_HASH(uint8_t)
ANDROID_INT32_HASH(int16_t)
ANDROID_INT32_HASH(uint16_t)
ANDROID_INT32_HASH(int32_t)
ANDROID_INT32_HASH(uint32_t)
ANDROID_INT64_HASH(int64_t)
ANDROID_INT64_HASH(uint64_t)
ANDROID_REINTERPRET_HASH(float, uint32_t)
ANDROID_REINTERPRET_HASH(double, uint64_t)
template <typename T> inline hash_t hash_type(T* const & value) {
return hash_type(uintptr_t(value));
}
}; // namespace android
// ---------------------------------------------------------------------------
#endif // ANDROID_TYPE_HELPERS_H
/**
* @file RefBase.cpp
* Copyright: Android Open Source Project
* License: Apache 2.0
*/
#define LOG_TAG "RefBase"
// #define LOG_NDEBUG 0
#include <fcntl.h>
#include <stdio.h>
#include <stdlib.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <typeinfo>
#include <unistd.h>
#include <utils/RefBase.h>
#include <utils/CallStack.h>
#include <utils/Log.h>
#include <utils/threads.h>
// gcc用法表示函数参数未使用否则有编译警告
#ifndef __unused
#define __unused __attribute__((__unused__))
#endif
// 引用计数是否开启debug模式
#define DEBUG_REFS 1
// 是否追踪引用计数信息
#define DEBUG_REFS_ENABLED_BY_DEFAULT 1
// 是否收集函数调用堆栈信息
#define DEBUG_REFS_CALLSTACK_ENABLED 1
// debug信息保存位置
#define DEBUG_REFS_CALLSTACK_PATH "/data/debug"
// 是否打印引用计数操作
#define PRINT_REFS 1
// ---------------------------------------------------------------------------
namespace android {
/********************************************************************************
1. 默认情况下,当最后一个强引用消失时对象被销毁,如果没有强引用,就在最后一个弱引用
消失时销毁对象。但这种行为受OBJECT_LIFETIME_WEAK的影响,在最后一个引用消失前将
无条件地一直拥有对象,而不管是强引用还是弱引用。使用extendObjectLifetime时,我
们需要保证在用于对象释放相关的减少引用计数动作前调用,或者在可能与之依赖的
attemptIncStrong前调用,且支持并发地改变对象的生命期。
2. 对象有强引用时AttemptIncStrong将会成功,或者对象有弱引用且从来没有过强引用时
AttemptIncStrong也会成功。而AttemptIncWeak的成功只有在对象已经有弱引用时才会
发生,但attemptIncStrong成功后AttemptIncWeak可能会失败。
3. mStrong为强引用计数的变量,mWeak为弱引用计数的变量,在函数调用期间,忽略内存有序性
(memory ordering)的影响,mWeak将包括强引用,也就是说mWeak的值大于等于mStrong。
weakref_impl在RefBase对象构造时初始化为mRefs,保存了许多信息,包括两种引用计数,
需要执行wp<>的操作,这样在RefBase对象销毁后仍可以继续执行。
4. 在OBJECT_LIFETIME_STRONG的条件下,weakref_impl在decWeak时释放,因此可以生存到
最后一个弱引用消失为之,如果强引用从没有增加且弱引用为0也可以在RefBase析构中释放,
这时需要在decStrong中调用RefBase析构,若RefBase对象被显式销毁却没有减少强引用计数
的话,应该避免这种操作。在OBJECT_LIFETIME_WEAK的条件下,decWeak总是会调用RefBase
析构,而weakref_impl总是在RefBase析构中释放,显式decStrong则避免了这种销毁策略。
5. 关于内存有序性(memory ordering),我们必须保证访问对象时有inc()操作,之后是对应的
dec()操作。由于内存防护(memory fence)或有序的内存访问可能会损失性能,所以需要限制
内存有序性的原子操作。对mStrong、mWeak、mFlags的显式访问会在某种方式上relax-meory-
order,唯一不会导致memory_order_relaxed的是减少引用计数,对应于释放操作。另外,最后
一个减引用会导致内存释放,随后acquire fence。
********************************************************************************/
// 强引用计数初始值
#define INITIAL_STRONG_VALUE (1<<28)
// 引用计数最大值
#define MAX_COUNT 0xfffff
// 检查强引用计数是否有效(上下限)
#define BAD_STRONG(c) \
((c) == 0 || ((c) & (~(MAX_COUNT | INITIAL_STRONG_VALUE))) != 0)
// 检查弱引用计数是否有效(上下限)
#define BAD_WEAK(c) ((c) == 0 || ((c) & (~MAX_COUNT)) != 0)
// ---------------------------------------------------------------------------
/**
* @class RefBase::weakref_impl
* 弱引用计数类型implementation
* 句柄类
*/
class RefBase::weakref_impl : public RefBase::weakref_type
{
public:
// 使用原子模板类型atomic<int32_t>
// 普通类型int32_t修改时包括read、modify、write
std::atomic<int32_t> mStrong;
std::atomic<int32_t> mWeak;
RefBase* const mBase;
std::atomic<int32_t> mFlags;
#if !DEBUG_REFS
// 非debug模式时全部为空实现
explicit weakref_impl(RefBase* base)
: mStrong(INITIAL_STRONG_VALUE)
, mWeak(0)
, mBase(base)
, mFlags(0)
{
}
void addStrongRef(const void* /*id*/) {}
void removeStrongRef(const void* /*id*/) {}
void renameStrongRefId(const void* /*old_id*/, const void* /*new_id*/) {}
void addWeakRef(const void* /*id*/) {}
void removeWeakRef(const void* /*id*/) {}
void renameWeakRefId(const void* /*old_id*/, const void* /*new_id*/) {}
void printRefs() const {}
void trackMe(bool, bool) {}
#else
// debug模式
weakref_impl(RefBase* base)
: mStrong(INITIAL_STRONG_VALUE) // 强引用计数初始化为INITIAL_STRONG_VALUE
, mWeak(0) // 弱引用计数初始化为0
, mBase(base)
, mFlags(0)
, mStrongRefs(NULL)
, mWeakRefs(NULL)
, mTrackEnabled(!!DEBUG_REFS_ENABLED_BY_DEFAULT)
, mRetain(false)
{
}
~weakref_impl()
{
bool dumpStack = false;
// 打印mStrongRefs堆栈
if (!mRetain && mStrongRefs != NULL) {
dumpStack = true;
ALOGE("Strong references remain:");
ref_entry* refs = mStrongRefs;
while (refs) {
char inc = refs->ref >= 0 ? '+' : '-';
ALOGD("\t%c ID %p (ref %d):", inc, refs->id, refs->ref);
#if DEBUG_REFS_CALLSTACK_ENABLED
refs->stack.log(LOG_TAG);
#endif
refs = refs->next;
}
}
// 打印mWeakRefs堆栈
if (!mRetain && mWeakRefs != NULL) {
dumpStack = true;
ALOGE("Weak references remain!");
ref_entry* refs = mWeakRefs;
while (refs) {
char inc = refs->ref >= 0 ? '+' : '-';
ALOGD("\t%c ID %p (ref %d):", inc, refs->id, refs->ref);
#if DEBUG_REFS_CALLSTACK_ENABLED
refs->stack.log(LOG_TAG);
#endif
refs = refs->next;
}
}
// dumpStack为true说明有内存问题并打印堆栈信息
if (dumpStack) {
ALOGE("above errors at:");
CallStack stack(LOG_TAG);
}
}
// 增加强引用
void addStrongRef(const void* id) {
addRef(&mStrongRefs, id, mStrong.load(std::memory_order_relaxed));
}
// 移除强引用
void removeStrongRef(const void* id) {
//ALOGD_IF(mTrackEnabled,
// "removeStrongRef: RefBase=%p, id=%p", mBase, id);
if (!mRetain) {
removeRef(&mStrongRefs, id);
} else {
addRef(&mStrongRefs, id, -mStrong.load(std::memory_order_relaxed));
}
}
// 修改强引用Id
void renameStrongRefId(const void* old_id, const void* new_id) {
renameRefsId(mStrongRefs, old_id, new_id);
}
// 增加弱引用
void addWeakRef(const void* id) {
addRef(&mWeakRefs, id, mWeak.load(std::memory_order_relaxed));
}
// 移除弱引用
void removeWeakRef(const void* id) {
if (!mRetain) {
removeRef(&mWeakRefs, id);
} else {
addRef(&mWeakRefs, id, -mWeak.load(std::memory_order_relaxed));
}
}
// 修改弱引用Id
void renameWeakRefId(const void* old_id, const void* new_id) {
renameRefsId(mWeakRefs, old_id, new_id);
}
// 跟踪引用计数信息开关
void trackMe(bool track, bool retain)
{
mTrackEnabled = track;
mRetain = retain;
}
// 打印引用信息(写文件)
void printRefs() const
{
String8 text;
{
Mutex::Autolock _l(mMutex);
char buf[128];
snprintf(buf, sizeof(buf),
"Strong references on RefBase %p (weakref_type %p):\n",
mBase, this);
text.append(buf);
printRefsLocked(&text, mStrongRefs);
snprintf(buf, sizeof(buf),
"Weak references on RefBase %p (weakref_type %p):\n",
mBase, this);
text.append(buf);
printRefsLocked(&text, mWeakRefs);
}
{
char name[100];
snprintf(name, sizeof(name), DEBUG_REFS_CALLSTACK_PATH "/%p.stack",
this);
int rc = open(name, O_RDWR | O_CREAT | O_APPEND, 644);
if (rc >= 0) {
write(rc, text.string(), text.length());
close(rc);
ALOGD("STACK TRACE for %p saved in %s", this, name);
}
else ALOGE("FAILED TO PRINT STACK TRACE for %p in %s: %s", this,
name, strerror(errno));
}
}
private:
// 这是一个重要的结构体
// 用于统计引用计数信息
struct ref_entry
{
ref_entry* next;
const void* id;
#if DEBUG_REFS_CALLSTACK_ENABLED
CallStack stack;
#endif
int32_t ref;
};
// 增加引用
void addRef(ref_entry** refs, const void* id, int32_t mRef)
{
if (mTrackEnabled) {
AutoMutex _l(mMutex);
ref_entry* ref = new ref_entry;
ref->ref = mRef;
ref->id = id;
#if DEBUG_REFS_CALLSTACK_ENABLED
ref->stack.update(2);
#endif
ref->next = *refs;
*refs = ref;
}
}
// 移除引用
void removeRef(ref_entry** refs, const void* id)
{
if (mTrackEnabled) {
AutoMutex _l(mMutex);
ref_entry* const head = *refs;
ref_entry* ref = head;
while (ref != NULL) {
if (ref->id == id) {
*refs = ref->next;
delete ref;
return;
}
refs = &ref->next;
ref = *refs;
}
ALOGE("RefBase: removing id %p on RefBase %p"
"(weakref_type %p) that doesn't exist!",
id, mBase, this);
ref = head;
while (ref) {
char inc = ref->ref >= 0 ? '+' : '-';
ALOGD("\t%c ID %p (ref %d):", inc, ref->id, ref->ref);
ref = ref->next;
}
CallStack stack(LOG_TAG);
}
}
// 修改引用计数Id
void renameRefsId(ref_entry* r, const void* old_id, const void* new_id)
{
if (mTrackEnabled) {
AutoMutex _l(mMutex);
ref_entry* ref = r;
while (ref != NULL) {
if (ref->id == old_id) {
ref->id = new_id;
}
ref = ref->next;
}
}
}
// 打印引用计数信息
// 增加引用计数用+表示
// 减少引用计数用-表示
void printRefsLocked(String8* out, const ref_entry* refs) const
{
char buf[128];
while (refs) {
char inc = refs->ref >= 0 ? '+' : '-';
snprintf(buf, sizeof(buf), "\t%c ID %p (ref %d):\n",
inc, refs->id, refs->ref);
out->append(buf);
#if DEBUG_REFS_CALLSTACK_ENABLED
out->append(refs->stack.toString("\t\t"));
#else
out->append("\t\t(call stacks disabled)");
#endif
refs = refs->next;
}
}
mutable Mutex mMutex;
ref_entry* mStrongRefs;
ref_entry* mWeakRefs;
bool mTrackEnabled;
bool mRetain;
#endif
};
// ---------------------------------------------------------------------------
/**
* @fn RefBase::incStrong
*/
void RefBase::incStrong(const void* id) const
{
weakref_impl* const refs = mRefs;
// 因为弱引用包括强引用所以首先增加弱引用
refs->incWeak(id);
// 然后添加强引用
refs->addStrongRef(id);
// 强引用计数原子性地加1并返回原来的值
// 至此任务基本完成
// 下面对强引用计数原来的值进行判断(必须大于0)
// 强引用计数原来的值不同于初始值INITIAL_STRONG_VALUE时操作结束
// 否则说明是第一次访问
const int32_t c = refs->mStrong.fetch_add(1, std::memory_order_relaxed);
ALOG_ASSERT(c > 0, "incStrong() called on %p after last strong ref", refs);
#if PRINT_REFS
ALOGD("incStrong of %p from %p: cnt=%d\n", this, id, c);
#endif
if (c != INITIAL_STRONG_VALUE) {
return;
}
// 第一次访问时直接把强引用计数减INITIAL_STRONG_VALUE变成刚才增加的1
// old应该为INITIAL_STRONG_VALUE+1
int32_t old = refs->mStrong.fetch_sub(INITIAL_STRONG_VALUE,
std::memory_order_relaxed);
ALOG_ASSERT(old > INITIAL_STRONG_VALUE, "0x%x too small", old);
// 第一次访问时回调onFirstRef
// 子类可以重载onFirstRef做想做的事情
refs->mBase->onFirstRef();
}
/**
* @fn RefBase::decStrong
*/
void RefBase::decStrong(const void* id) const
{
weakref_impl* const refs = mRefs;
// 首先移除强引用
refs->removeStrongRef(id);
// 然后给强引用计数原子性地减1并通过BAD_STRONG检查强引用是否合法
const int32_t c = refs->mStrong.fetch_sub(1, std::memory_order_release);
#if PRINT_REFS
ALOGD("decStrong of %p from %p: cnt=%d\n", this, id, c);
#endif
LOG_ALWAYS_FATAL_IF(BAD_STRONG(c), "decStrong() called on %p too many times",
refs);
if (c == 1) {
// 强引用计数原来的值为1说明这是最后一个强引用
// 所以回调onLastStrongRef
// 接着判断对象生命期为strong时delete this
std::atomic_thread_fence(std::memory_order_acquire);
refs->mBase->onLastStrongRef(id);
int32_t flags = refs->mFlags.load(std::memory_order_relaxed);
if ((flags & OBJECT_LIFETIME_MASK) == OBJECT_LIFETIME_STRONG) {
// 这种情况下析构不会删除refs
// refs是在最后一个弱引用时删除的
// 所以最后通过refs减少弱引用
delete this;
}
}
// 最后通过refs减少弱引用
refs->decWeak(id);
}
/**
* @fn RefBase::forceIncStrong
* forceIncStrong与incStrong的唯一区别是允许强引用计数原来的值为0
*/
void RefBase::forceIncStrong(const void* id) const
{
weakref_impl* const refs = mRefs;
refs->incWeak(id);
refs->addStrongRef(id);
const int32_t c = refs->mStrong.fetch_add(1, std::memory_order_relaxed);
ALOG_ASSERT(c >= 0, "forceIncStrong called on %p after ref count underflow",
refs);
#if PRINT_REFS
ALOGD("forceIncStrong of %p from %p: cnt=%d\n", this, id, c);
#endif
switch (c) {
case INITIAL_STRONG_VALUE:
refs->mStrong.fetch_sub(INITIAL_STRONG_VALUE,
std::memory_order_relaxed);
case 0:
refs->mBase->onFirstRef();
}
}
/**
* @fn RefBase::getStrongCount
* 获取强引用计数(只用于debug且不能保证memory order)
*/
int32_t RefBase::getStrongCount() const
{
// Debugging only; No memory ordering guarantees.
return mRefs->mStrong.load(std::memory_order_relaxed);
}
/**
* @fn RefBase::weakref_type::refBase
* 获取RefBase对象指针
*/
RefBase* RefBase::weakref_type::refBase() const
{
return static_cast<const weakref_impl*>(this)->mBase;
}
/**
* @fn RefBase::weakref_type::incWeak
*/
void RefBase::weakref_type::incWeak(const void* id)
{
weakref_impl* const impl = static_cast<weakref_impl*>(this);
// 先增加弱引用
impl->addWeakRef(id);
// 再原子地给弱引用计数加1
const int32_t c __unused = impl->mWeak.fetch_add(1,
std::memory_order_relaxed);
ALOG_ASSERT(c >= 0, "incWeak called on %p after last weak ref", this);
}
/**
* @fn RefBase::weakref_type::decWeak
*/
void RefBase::weakref_type::decWeak(const void* id)
{
weakref_impl* const impl = static_cast<weakref_impl*>(this);
// 首先移除弱引用
impl->removeWeakRef(id);
// 然后原子地给弱引用计数减1并检查弱引用计数原来的值是否有效
const int32_t c = impl->mWeak.fetch_sub(1, std::memory_order_release);
LOG_ALWAYS_FATAL_IF(BAD_WEAK(c), "decWeak called on %p too many times",
this);
// 弱引用计数原来的值不为1时直接return
// 否则说明是最后一个弱引用
if (c != 1) return;
atomic_thread_fence(std::memory_order_acquire);
int32_t flags = impl->mFlags.load(std::memory_order_relaxed);
if ((flags & OBJECT_LIFETIME_MASK) == OBJECT_LIFETIME_STRONG) {
// 对象生命期为strong
// 在这里删除weakref_impl
if (impl->mStrong.load(std::memory_order_relaxed)
== INITIAL_STRONG_VALUE) {
ALOGW("RefBase: Object at %p lost last weak reference "
"before it had a strong reference", impl->mBase);
} else {
delete impl;
}
} else {
// 对象生命期为weak
// 所以回调onLastWeakRef并delete RefBase
impl->mBase->onLastWeakRef(id);
delete impl->mBase;
}
}
/**
* @fn RefBase::weakref_type::attemptIncStrong
*/
bool RefBase::weakref_type::attemptIncStrong(const void* id)
{
// 增加强引用时先增加弱引用
incWeak(id);
weakref_impl* const impl = static_cast<weakref_impl*>(this);
// 获取当前的强引用计数
int32_t curCount = impl->mStrong.load(std::memory_order_relaxed);
ALOG_ASSERT(curCount >= 0,
"attemptIncStrong called on %p after underflow", this);
// 修改强引用计数
while (curCount > 0 && curCount != INITIAL_STRONG_VALUE) {
if (impl->mStrong.compare_exchange_weak(curCount, curCount+1,
std::memory_order_relaxed)) {
break;
}
}
// 所有强引用都被释放或者从来没有过强引用的情况(比较少见)
if (curCount <= 0 || curCount == INITIAL_STRONG_VALUE) {
// 获取对象生命期的标记
int32_t flags = impl->mFlags.load(std::memory_order_relaxed);
// strong
if ((flags & OBJECT_LIFETIME_MASK) == OBJECT_LIFETIME_STRONG) {
// 这个对象的生命期是正常的
// 对象在最后一个强引用消失时已销毁
// 所以减少弱引用并return false
if (curCount <= 0) {
// the last strong-reference got released, the object cannot
// be revived.
decWeak(id);
return false;
}
// 修改强引用计数
// 方法同上
while (curCount > 0) {
if (impl->mStrong.compare_exchange_weak(curCount, curCount+1,
std::memory_order_relaxed)) {
break;
}
}
if (curCount <= 0) {
decWeak(id);
return false;
}
// weak
} else {
// 这个对象的生命期进行了扩展
// 也就是说对象只能从弱引用中复活
// 所以请求对象是否允许复活
// 不允许时减少弱引用并return false
if (!impl->mBase->onIncStrongAttempted(FIRST_INC_STRONG, id)) {
decWeak(id);
return false;
}
// 强引用计数加1
curCount = impl->mStrong.fetch_add(1, std::memory_order_relaxed);
// onIncStrongAttempted()获取了不必要的引用所以通过onLastStrongRef()移除
if (curCount != 0 && curCount != INITIAL_STRONG_VALUE) {
impl->mBase->onLastStrongRef(id);
}
}
}
// 增加强引用
impl->addStrongRef(id);
#if PRINT_REFS
ALOGD("attemptIncStrong of %p from %p: cnt=%d\n", this, id, curCount);
#endif
// curCount为INITIAL_STRONG_VALUE作特殊处理
if (curCount == INITIAL_STRONG_VALUE) {
impl->mStrong.fetch_sub(INITIAL_STRONG_VALUE,
std::memory_order_relaxed);
}
return true;
}
/**
* @fn RefBase::weakref_type::attemptIncWeak
* attemptIncWeak类似于attemptIncStrong
*/
bool RefBase::weakref_type::attemptIncWeak(const void* id)
{
weakref_impl* const impl = static_cast<weakref_impl*>(this);
int32_t curCount = impl->mWeak.load(std::memory_order_relaxed);
ALOG_ASSERT(curCount >= 0, "attemptIncWeak called on %p after underflow",
this);
while (curCount > 0) {
if (impl->mWeak.compare_exchange_weak(curCount, curCount+1,
std::memory_order_relaxed)) {
break;
}
}
if (curCount > 0) {
impl->addWeakRef(id);
}
return curCount > 0;
}
/**
* @fn RefBase::weakref_type::getWeakCount
* 获取弱引用计数(只用于debug)
*/
int32_t RefBase::weakref_type::getWeakCount() const
{
return static_cast<const weakref_impl*>(this)->mWeak
.load(std::memory_order_relaxed);
}
/**
* @fn RefBase::weakref_type::printRefs
* 打印弱引用信息
*/
void RefBase::weakref_type::printRefs() const
{
static_cast<const weakref_impl*>(this)->printRefs();
}
/**
* @fn RefBase::weakref_type::trackMe
* 追踪弱引用信息
*/
void RefBase::weakref_type::trackMe(bool enable, bool retain)
{
static_cast<weakref_impl*>(this)->trackMe(enable, retain);
}
/**
* @fn RefBase::weakref_type::createWeak
* 创建弱引用
*/
RefBase::weakref_type* RefBase::createWeak(const void* id) const
{
mRefs->incWeak(id);
return mRefs;
}
/**
* @fn RefBase::weakref_type::getWeakRefs
* 获取弱引用对象指针
*/
RefBase::weakref_type* RefBase::getWeakRefs() const
{
return mRefs;
}
/**
* @fn RefBase::RefBase
* 构造函数创建weakref_impl
*/
RefBase::RefBase()
: mRefs(new weakref_impl(this))
{
}
/**
* @fn RefBase::~RefBase
*/
RefBase::~RefBase()
{
// 获取对象生命期标记
int32_t flags = mRefs->mFlags.load(std::memory_order_relaxed);
// weak
// 弱引用计数为0时销毁weakref_impl
if ((flags & OBJECT_LIFETIME_MASK) == OBJECT_LIFETIME_WEAK) {
if (mRefs->mWeak.load(std::memory_order_relaxed) == 0) {
delete mRefs;
}
} else if (mRefs->mStrong.load(std::memory_order_relaxed)
== INITIAL_STRONG_VALUE) {
// 从来没有过强引用
// 所以弱引用计数也要为0且销毁weakref_impl
LOG_ALWAYS_FATAL_IF(mRefs->mWeak.load() != 0,
"RefBase: Explicit destruction with non-zero weak "
"reference count");
delete mRefs;
}
const_cast<weakref_impl*&>(mRefs) = NULL;
}
/**
* @fn RefBase::extendObjectLifetime
* 扩展对象生命期
*/
void RefBase::extendObjectLifetime(int32_t mode)
{
mRefs->mFlags.fetch_or(mode, std::memory_order_relaxed);
}
/**
* @fn RefBase::onFirstRef
*/
void RefBase::onFirstRef()
{
}
/**
* @fn RefBase::onLastStrongRef
*/
void RefBase::onLastStrongRef(const void* /*id*/)
{
}
/**
* @fn RefBase::onIncStrongAttempted
*/
bool RefBase::onIncStrongAttempted(uint32_t flags, const void* /*id*/)
{
return (flags & FIRST_INC_STRONG) ? true : false;
}
/**
* @fn RefBase::onLastWeakRef
*/
void RefBase::onLastWeakRef(const void* /*id*/)
{
}
// ---------------------------------------------------------------------------
#if DEBUG_REFS
// debug模式才修改引用计数(通过ReferenceRenamer重载的圆括号完成)
// 否则为空实现
void RefBase::renameRefs(size_t n, const ReferenceRenamer& renamer) {
for (size_t i = 0 ; i < n ; i++) {
renamer(i);
}
}
#else
void RefBase::renameRefs(size_t /*n*/, const ReferenceRenamer& /*renamer*/) {}
#endif
// 同时修改强引用和弱引用的Id
void RefBase::renameRefId(weakref_type* ref,
const void* old_id, const void* new_id) {
weakref_impl* const impl = static_cast<weakref_impl*>(ref);
impl->renameStrongRefId(old_id, new_id);
impl->renameWeakRefId(old_id, new_id);
}
// 同时修改强引用和弱引用的Id
void RefBase::renameRefId(RefBase* ref,
const void* old_id, const void* new_id) {
ref->mRefs->renameStrongRefId(old_id, new_id);
ref->mRefs->renameWeakRefId(old_id, new_id);
}
VirtualLightRefBase::~VirtualLightRefBase() {}
}; // namespace android
下面翻译自RefBase.h中给出的用法说明——
RefBase提供了基本的弱指针类型wp<>和RefBase类,与StrongPointer中的强指针类型sp<>协同工作。
sp<>和wp<>为智能指针,可以看出是模板类,它们定义了一个良好的协议,也就是几个API,当使用它们的对象实现了这些协议时,也就是说继承自RefBase或LightRefBase,智能指针就能正常工作。智能指针需要和RefBase协同工作,不过在Android源码中的一些地方,非RefBase的对象也使用了sp<>,这种智能指针并没有绑定RefBase,所以需要当前对象实现对应的协议。RefBase属于binder,支持强指针、弱指针和一些“magic feature”,所以使用基于RefBase对象的时候就可以通过sp<>和wp<>发挥强指针、弱指针的特性。
一般情况下,当最后一个强指针不使用时,会调到析构函数,对象也就销毁了,然而与之关联的部分内存直到最后一个弱指针被释放时才进行free。弱指针基本上是安全的,可以通过promote()访问,返回强指针,但是当强指针被用尽时这个对象就被销毁而返回nullptr,于是便成为实例cache中键的候选对象。对弱指针来说,即使基本的对象已经销毁了,但仍然是可以作比较目的来使用的,换句话说,当对象A销毁后其内存被对象B使用,A仍保持弱指针,但与B相比的话是不相等的,从而使得弱指针适用于键。
那么,我们应该如何使用强指针、弱指针呢?
有所属关系时建议使用强引用sp<>,如一个对象拥有另一个对象时就用强引用,函数参数用强引用,很少看到函数参数用wp<>的地方。典型的用法是,一个新创建的对象去初始化一个强指针,这个强指针后面就可以用来构造或赋值其它的强指针和弱指针。没有所属关系时使用弱引用wp<>,如cache中的键,这是不能使用原始的指针的,因为没有什么安全的方法可以从“vanilla pointer”中获取强引用。得出一个结论是,两个对象不能或很少互相持有sp<>,因为它们不能同时拥有对方。
引用计数注意点:循环强引用是个很严重的问题,需要避免,导致内存泄漏且难于调试,不过RefBase提供了调试代码,可以发现内存泄漏的地方;另一个问题是析构函数,对于引用计数的对象来说,其析构函数可能在任何时候被调用,如下代码所示:
// void setStuff(const sp<Stuff>& stuff) {
// std::lock_guard<std::mutex> lock(mMutex);
// mStuff = stuff;
// }
这种用法容易导致死锁,必须谨慎使用。上面的代码隐含了一个事实,赋值操作符会导致Stuff析构函数的调用,而且是在mutex的影响范围内发生的,但是,mutex保护的是成员变量mStuff而非析构函数,再者,如果析构函数使用了同一个mutex,很可能导致死锁,更为严重的是Stuff析构函数为虚函数的时候,如果使用的是别人写的Stuff子类,那么代码就不可控了。一种正确的用法如下代码所示:
// void setStuff(const sp<Stuff>& stuff) {
// std::unique_lock<std::mutex> lock(mMutex);
// sp<Stuff> hold = mStuff;
// mStuff = stuff;
// lock.unlock();
// }
更为重要的是,引用计数的对象在其析构函数中应尽可能地少做事情,因为可能在任何时候任何地方被调用。强指针和弱指针在RefBase的onFirstRef回调时成功创建,不过wp<>和sp<>的使用还有一些其它的限制:不要在构造函数中用this指针初始化强指针,因为此时触发的onFirstRef回调基于一个不完整的对象,还没有构建完成;同理,在构造函数中用this指针初始化弱指针也是不好的,不过extendObjectLifetime()不会影响对象的生命期,因此,对于弱指针的这种用法来说,过早地进行内存回收是安全的。
弱指针提供了unsafe_get(),这个接口用于调试,其它情况都不应该使用,除非知道有个生存期更长的sp<>指向了同一个对象,这时可能返回一个内存已被回收的对象,这个内存被重新分配用于其它目的。解引用弱指针时应该通过promote()完成。
继承自RefBase的任何对象都应该在引用计数减少时销毁,而不是通过其它手段来销毁,同时不应该在栈上分配内存,也不能直接作为其它对象的数据成员,构造函数调用成功之后需增加其强引用的计数值,这可以通过sp<>初始化完成,或者是RefBase的incStrong()函数。如果显式地delete使用了wp<>或sp<>的RefBase对象,错误是致命的,将导致系统abort或crash。sp<>与原始指针是不同的,如果RefBase子类对象没有增加强引用计数,而且在函数参数中作为强指针使用,作为临时对象处理,导致构造并析构这个对象,其实这个对象还在使用就过早地销毁了,这将带来内存问题,而且从代码角度来说很难察觉。
RefBase还提供了几个其它的特性:当弱引用仍然存在时,RefBase的extendObjectLifetime()用来防止对象销毁,目的是支持binder。wp的promote()通过attemptIncStrong()成员函数实现,把弱指针转化为强指针,这是通过wp<>获取对象引用的一种方法,而binder有时候则直接调用attemptIncStrong()。RefBase提供了几个回调函数,即onXxx形式的virtual函数,可用于引用计数相关事件的处理或代码调试。RefBase支持调试功能,即DEBUG_REFS宏,在RefBase.cpp中使用。
线程安全性:像std::shared_ptr一样,sp<>和wp<>可以并发地访问不同的sp<>和wp<>实例,这些都指向同一个基本对象,但是,不能并发地访问同一个sp<>或wp<>,至少写访问是不可以的,sp<>和wp<>的线程安全性可以理解为同T一样,而不是atomic<T>。
四个相关类——
class RefBase;
template <class T> class LightRefBase;
template <typename T> class wp;
template <typename T> class sp;
RefBase和LightRefBase作为基类使用,LightRefBase是一个很简单的模板类,引用计数初始化为0,incStrong中引用计数加1,decStrong引用计数减1且当原来的引用计数为1即现在的引用计数为0时执行delete操作销毁对象;而RefBase是一个重量级的类,包括强引用和弱引用,提供了onFirstRef等回调,还有个句柄类weakref_impl,提供了额外的debug信息。wp和sp可以理解为弱指针和强指针,用于普通变量、函数参数、类常用变量等,基本原理都是在构造、析构、拷贝构造、赋值操作符、右值引用等地方操作引用、引用计数。