15821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Copyright (c) 2012 The Chromium Authors. All rights reserved.
25821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Use of this source code is governed by a BSD-style license that can be
35821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// found in the LICENSE file.
45821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
55821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#ifndef BASE_REFCOUNTED_H_
65821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#define BASE_REFCOUNTED_H_
75821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
85821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace base {
95821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
105821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template <typename T>
115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class RefCounted {
125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RefCounted() {}
142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~RefCounted() {}
165821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template <typename T>
195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class RefCountedThreadSafe {
205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RefCountedThreadSafe() {}
222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~RefCountedThreadSafe() {}
245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace base
275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Ignore classes whose inheritance tree ends in WebKit's RefCounted base
295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// class. Though prone to error, this pattern is very prevalent in WebKit
305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// code, so do not issue any warnings.
315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)namespace WebKit {
325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)template <typename T>
345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class RefCounted {
355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  RefCounted() {}
375821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~RefCounted() {}
385821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
395821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
405821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)}  // namespace WebKit
415821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
425821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Unsafe; should error.
435821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class PublicRefCountedDtorInHeader
445821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public base::RefCounted<PublicRefCountedDtorInHeader> {
455821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
465821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PublicRefCountedDtorInHeader() {}
475821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~PublicRefCountedDtorInHeader() {}
485821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
495821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
505821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  friend class base::RefCounted<PublicRefCountedDtorInHeader>;
515821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
525821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
535821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Unsafe; should error.
545821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class PublicRefCountedThreadSafeDtorInHeader
555821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public base::RefCountedThreadSafe<
565821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)          PublicRefCountedThreadSafeDtorInHeader> {
575821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
585821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PublicRefCountedThreadSafeDtorInHeader() {}
595821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~PublicRefCountedThreadSafeDtorInHeader() {}
605821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
615821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
625821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  friend class base::RefCountedThreadSafe<
635821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)      PublicRefCountedThreadSafeDtorInHeader>;
645821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
655821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Unsafe; should error.
675821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ProtectedRefCountedDtorInHeader
685821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public base::RefCounted<ProtectedRefCountedDtorInHeader> {
695821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
705821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ProtectedRefCountedDtorInHeader() {}
715821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
725821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) protected:
735821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~ProtectedRefCountedDtorInHeader() {}
745821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
755821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
765821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  friend class base::RefCounted<ProtectedRefCountedDtorInHeader>;
775821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
785821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Safe; should not have errors
802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class ProtectedRefCountedVirtualDtorInHeader
812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : public base::RefCounted<ProtectedRefCountedVirtualDtorInHeader> {
822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ProtectedRefCountedVirtualDtorInHeader() {}
842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~ProtectedRefCountedVirtualDtorInHeader() {}
872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private:
892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  friend class base::RefCounted<ProtectedRefCountedVirtualDtorInHeader>;
902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
935821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Safe; should not have errors.
945821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class PrivateRefCountedDtorInHeader
955821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public base::RefCounted<PrivateRefCountedDtorInHeader> {
965821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
975821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  PrivateRefCountedDtorInHeader() {}
985821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
995821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) private:
1005821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~PrivateRefCountedDtorInHeader() {}
1015821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  friend class base::RefCounted<PrivateRefCountedDtorInHeader>;
1025821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
1035821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1045821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Unsafe; A grandchild class ends up exposing their parent and grandparent's
1055821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// destructors.
1065821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class DerivedProtectedToPublicInHeader
1072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : public ProtectedRefCountedVirtualDtorInHeader {
1085821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
1095821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  DerivedProtectedToPublicInHeader() {}
1102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~DerivedProtectedToPublicInHeader() {}
1115821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
1125821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1135821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Unsafe; A grandchild ends up implicitly exposing their parent and
1145821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// grantparent's destructors.
1155821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class ImplicitDerivedProtectedToPublicInHeader
1162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : public ProtectedRefCountedVirtualDtorInHeader {
1175821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
1185821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ImplicitDerivedProtectedToPublicInHeader() {}
1195821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
1205821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1215821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Unsafe-but-ignored; should not have errors.
1225821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class WebKitPublicDtorInHeader
1235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public WebKit::RefCounted<WebKitPublicDtorInHeader> {
1245821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
1255821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKitPublicDtorInHeader() {}
1265821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~WebKitPublicDtorInHeader() {}
1275821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
1285821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1295821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)// Unsafe-but-ignored; should not have errors.
1305821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)class WebKitDerivedPublicDtorInHeader
1315821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)    : public WebKitPublicDtorInHeader {
1325821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles) public:
1335821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  WebKitDerivedPublicDtorInHeader() {}
1345821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)  ~WebKitDerivedPublicDtorInHeader() {}
1355821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)};
1365821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)
1372a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class APublicInterface {
1382a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1392a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~APublicInterface() {}
1402a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoFoo() = 0;
1412a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1422a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1432a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Unsafe. "ImplementsAPublicInterface* foo" can be deleted via
1442a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// "delete (APublicInterface*)foo;".
1452a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class ImplementsAPublicInterface
1462a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : public APublicInterface,
1472a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      public base::RefCounted<ImplementsAPublicInterface> {
1482a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1492a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoFoo() override {}
1502a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1512a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
1522a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~ImplementsAPublicInterface() {}
1532a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1542a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private:
1552a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  friend class base::RefCounted<ImplementsAPublicInterface>;
1562a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1572a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1582a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class AnImplicitInterface {
1592a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1602a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoBar() {}
1612a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1622a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1632a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Unsafe.
1642a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class ImplementsAnImplicitInterface
1652a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : public AnImplicitInterface,
1662a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      public base::RefCounted<ImplementsAnImplicitInterface> {
1672a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1682a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoBar() override {}
1692a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1702a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private:
1712a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  friend class base::RefCounted<ImplementsAnImplicitInterface>;
1722a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ~ImplementsAnImplicitInterface() {}
1732a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1742a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1752a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Safe. Private inheritance does not expose the base destructor.
1762a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class PrivatelyImplementsAPublicInterface
1772a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : private APublicInterface,
1782a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      public base::RefCounted<PrivatelyImplementsAPublicInterface> {
1792a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1802a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoFoo() override {}
1812a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1822a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private:
1832a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  friend class base::RefCounted<PrivatelyImplementsAPublicInterface>;
1842a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~PrivatelyImplementsAPublicInterface() {}
1852a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1862a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
1872a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)// Unsafe.
1882a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class BaseInterface {
1892a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1902a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~BaseInterface() {}
1912a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoFoo() {}
1922a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1932a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class DerivedInterface : public BaseInterface {
1942a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
1952a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~DerivedInterface() {}
1962a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
1972a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class SomeOtherInterface {
1982a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
1992a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~SomeOtherInterface() {}
2002a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoBar() {}
2012a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
2022a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class RefcountedType : public base::RefCounted<RefcountedType> {
2032a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
2042a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  ~RefcountedType() {}
2052a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) private:
2062a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  friend class base::RefCounted<RefcountedType>;
2072a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
2082a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)class UnsafeInheritanceChain
2092a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)    : public DerivedInterface,
2102a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      public SomeOtherInterface,
2112a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)      public RefcountedType {
2122a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) public:
2132a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // DerivedInterface
2142a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoFoo() override {}
2152a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2162a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  // SomeOtherInterface
2172a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual void DoBar() override {}
2182a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2192a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles) protected:
2202a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)  virtual ~UnsafeInheritanceChain() {}
2212a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)};
2222a99a7e74a7f215066514fe81d2bfa6639d9edddTorne (Richard Coles)
2235821806d5e7f356e8fa4b058a389a808ea183019Torne (Richard Coles)#endif  // BASE_REFCOUNTED_H_
224