1*635a8641SAndroid Build Coastguard Worker // Copyright (c) 2011 The Chromium Authors. All rights reserved. 2*635a8641SAndroid Build Coastguard Worker // Use of this source code is governed by a BSD-style license that can be 3*635a8641SAndroid Build Coastguard Worker // found in the LICENSE file. 4*635a8641SAndroid Build Coastguard Worker 5*635a8641SAndroid Build Coastguard Worker #include "base/memory/weak_ptr.h" 6*635a8641SAndroid Build Coastguard Worker 7*635a8641SAndroid Build Coastguard Worker namespace base { 8*635a8641SAndroid Build Coastguard Worker namespace internal { 9*635a8641SAndroid Build Coastguard Worker Flag()10*635a8641SAndroid Build Coastguard WorkerWeakReference::Flag::Flag() : is_valid_(true) { 11*635a8641SAndroid Build Coastguard Worker // Flags only become bound when checked for validity, or invalidated, 12*635a8641SAndroid Build Coastguard Worker // so that we can check that later validity/invalidation operations on 13*635a8641SAndroid Build Coastguard Worker // the same Flag take place on the same sequenced thread. 14*635a8641SAndroid Build Coastguard Worker sequence_checker_.DetachFromSequence(); 15*635a8641SAndroid Build Coastguard Worker } 16*635a8641SAndroid Build Coastguard Worker Invalidate()17*635a8641SAndroid Build Coastguard Workervoid WeakReference::Flag::Invalidate() { 18*635a8641SAndroid Build Coastguard Worker // The flag being invalidated with a single ref implies that there are no 19*635a8641SAndroid Build Coastguard Worker // weak pointers in existence. Allow deletion on other thread in this case. 20*635a8641SAndroid Build Coastguard Worker DCHECK(sequence_checker_.CalledOnValidSequence() || HasOneRef()) 21*635a8641SAndroid Build Coastguard Worker << "WeakPtrs must be invalidated on the same sequenced thread."; 22*635a8641SAndroid Build Coastguard Worker is_valid_ = false; 23*635a8641SAndroid Build Coastguard Worker } 24*635a8641SAndroid Build Coastguard Worker IsValid() const25*635a8641SAndroid Build Coastguard Workerbool WeakReference::Flag::IsValid() const { 26*635a8641SAndroid Build Coastguard Worker DCHECK(sequence_checker_.CalledOnValidSequence()) 27*635a8641SAndroid Build Coastguard Worker << "WeakPtrs must be checked on the same sequenced thread."; 28*635a8641SAndroid Build Coastguard Worker return is_valid_; 29*635a8641SAndroid Build Coastguard Worker } 30*635a8641SAndroid Build Coastguard Worker 31*635a8641SAndroid Build Coastguard Worker WeakReference::Flag::~Flag() = default; 32*635a8641SAndroid Build Coastguard Worker 33*635a8641SAndroid Build Coastguard Worker WeakReference::WeakReference() = default; 34*635a8641SAndroid Build Coastguard Worker WeakReference(const scoped_refptr<Flag> & flag)35*635a8641SAndroid Build Coastguard WorkerWeakReference::WeakReference(const scoped_refptr<Flag>& flag) : flag_(flag) {} 36*635a8641SAndroid Build Coastguard Worker 37*635a8641SAndroid Build Coastguard Worker WeakReference::~WeakReference() = default; 38*635a8641SAndroid Build Coastguard Worker 39*635a8641SAndroid Build Coastguard Worker WeakReference::WeakReference(WeakReference&& other) = default; 40*635a8641SAndroid Build Coastguard Worker 41*635a8641SAndroid Build Coastguard Worker WeakReference::WeakReference(const WeakReference& other) = default; 42*635a8641SAndroid Build Coastguard Worker is_valid() const43*635a8641SAndroid Build Coastguard Workerbool WeakReference::is_valid() const { 44*635a8641SAndroid Build Coastguard Worker return flag_ && flag_->IsValid(); 45*635a8641SAndroid Build Coastguard Worker } 46*635a8641SAndroid Build Coastguard Worker 47*635a8641SAndroid Build Coastguard Worker WeakReferenceOwner::WeakReferenceOwner() = default; 48*635a8641SAndroid Build Coastguard Worker ~WeakReferenceOwner()49*635a8641SAndroid Build Coastguard WorkerWeakReferenceOwner::~WeakReferenceOwner() { 50*635a8641SAndroid Build Coastguard Worker Invalidate(); 51*635a8641SAndroid Build Coastguard Worker } 52*635a8641SAndroid Build Coastguard Worker GetRef() const53*635a8641SAndroid Build Coastguard WorkerWeakReference WeakReferenceOwner::GetRef() const { 54*635a8641SAndroid Build Coastguard Worker // If we hold the last reference to the Flag then create a new one. 55*635a8641SAndroid Build Coastguard Worker if (!HasRefs()) 56*635a8641SAndroid Build Coastguard Worker flag_ = new WeakReference::Flag(); 57*635a8641SAndroid Build Coastguard Worker 58*635a8641SAndroid Build Coastguard Worker return WeakReference(flag_); 59*635a8641SAndroid Build Coastguard Worker } 60*635a8641SAndroid Build Coastguard Worker Invalidate()61*635a8641SAndroid Build Coastguard Workervoid WeakReferenceOwner::Invalidate() { 62*635a8641SAndroid Build Coastguard Worker if (flag_) { 63*635a8641SAndroid Build Coastguard Worker flag_->Invalidate(); 64*635a8641SAndroid Build Coastguard Worker flag_ = nullptr; 65*635a8641SAndroid Build Coastguard Worker } 66*635a8641SAndroid Build Coastguard Worker } 67*635a8641SAndroid Build Coastguard Worker WeakPtrBase()68*635a8641SAndroid Build Coastguard WorkerWeakPtrBase::WeakPtrBase() : ptr_(0) {} 69*635a8641SAndroid Build Coastguard Worker 70*635a8641SAndroid Build Coastguard Worker WeakPtrBase::~WeakPtrBase() = default; 71*635a8641SAndroid Build Coastguard Worker WeakPtrBase(const WeakReference & ref,uintptr_t ptr)72*635a8641SAndroid Build Coastguard WorkerWeakPtrBase::WeakPtrBase(const WeakReference& ref, uintptr_t ptr) 73*635a8641SAndroid Build Coastguard Worker : ref_(ref), ptr_(ptr) { 74*635a8641SAndroid Build Coastguard Worker DCHECK(ptr_); 75*635a8641SAndroid Build Coastguard Worker } 76*635a8641SAndroid Build Coastguard Worker WeakPtrFactoryBase(uintptr_t ptr)77*635a8641SAndroid Build Coastguard WorkerWeakPtrFactoryBase::WeakPtrFactoryBase(uintptr_t ptr) : ptr_(ptr) { 78*635a8641SAndroid Build Coastguard Worker DCHECK(ptr_); 79*635a8641SAndroid Build Coastguard Worker } 80*635a8641SAndroid Build Coastguard Worker ~WeakPtrFactoryBase()81*635a8641SAndroid Build Coastguard WorkerWeakPtrFactoryBase::~WeakPtrFactoryBase() { 82*635a8641SAndroid Build Coastguard Worker ptr_ = 0; 83*635a8641SAndroid Build Coastguard Worker } 84*635a8641SAndroid Build Coastguard Worker 85*635a8641SAndroid Build Coastguard Worker } // namespace internal 86*635a8641SAndroid Build Coastguard Worker } // namespace base 87