Add a Notification Settings Button to all web notifications behind the web platform...
[chromium-blink-merge.git] / base / ios / weak_nsobject.mm
blob36f9d3ea7cdd700da53d77a34245c3bad68a86c1
1 // Copyright 2013 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 #include "base/ios/weak_nsobject.h"
7 #include "base/mac/scoped_nsautorelease_pool.h"
8 #include "base/mac/scoped_nsobject.h"
10 namespace {
11 // The key needed by objc_setAssociatedObject.
12 char sentinelObserverKey_;
15 @interface CRBWeakNSProtocolSentinel ()
16 // Container to notify on dealloc.
17 @property(readonly, assign) scoped_refptr<base::WeakContainer> container;
18 // Designed initializer.
19 - (id)initWithContainer:(scoped_refptr<base::WeakContainer>)container;
20 @end
22 @implementation CRBWeakNSProtocolSentinel
24 @synthesize container = container_;
26 + (scoped_refptr<base::WeakContainer>)containerForObject:(id)object {
27   if (object == nil)
28     return nullptr;
29   // The autoreleasePool is needed here as the call to objc_getAssociatedObject
30   // returns an autoreleased object which is better released sooner than later.
31   base::mac::ScopedNSAutoreleasePool pool;
32   CRBWeakNSProtocolSentinel* sentinel =
33       objc_getAssociatedObject(object, &sentinelObserverKey_);
34   if (!sentinel) {
35     base::scoped_nsobject<CRBWeakNSProtocolSentinel> newSentinel(
36         [[CRBWeakNSProtocolSentinel alloc]
37             initWithContainer:new base::WeakContainer(object)]);
38     sentinel = newSentinel;
39     objc_setAssociatedObject(object, &sentinelObserverKey_, sentinel,
40                              OBJC_ASSOCIATION_RETAIN);
41     // The retain count is 2. One retain is due to the alloc, the other to the
42     // association with the weak object.
43     DCHECK_EQ(2u, [sentinel retainCount]);
44   }
45   return [sentinel container];
48 - (id)initWithContainer:(scoped_refptr<base::WeakContainer>)container {
49   DCHECK(container.get());
50   self = [super init];
51   if (self)
52     container_ = container;
53   return self;
56 - (void)dealloc {
57   self.container->nullify();
58   [super dealloc];
61 @end