LLDB mainline
NonNullSharedPtr.h
Go to the documentation of this file.
1//===----------------------------------------------------------------------===//
2//
3// Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions.
4// See https://llvm.org/LICENSE.txt for license information.
5// SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception
6//
7//===----------------------------------------------------------------------===//
8
9#ifndef LLDB_UTILITY_NONNULLSHAREDPTR_H
10#define LLDB_UTILITY_NONNULLSHAREDPTR_H
11
12#include <memory>
13#include <utility>
14
15namespace lldb_private {
16
17/// A non-nullable shared pointer that always holds a valid object.
18///
19/// NonNullSharedPtr is a smart pointer wrapper around std::shared_ptr that
20/// guarantees the pointer is never null.
21///
22/// This class is used for enforcing invariants at the type level and
23/// eliminating entire classes of null pointer bugs.
24///
25/// @tparam T The type of object to manage. Must be default-constructible.
26template <typename T> class NonNullSharedPtr : private std::shared_ptr<T> {
27 using Base = std::shared_ptr<T>;
28
29public:
30 NonNullSharedPtr(const std::shared_ptr<T> &t)
31 : Base(t ? t : std::make_shared<T>()) {
32 assert(t && "NonNullSharedPtr constructed from nullptr");
33 }
34
35 NonNullSharedPtr(std::shared_ptr<T> &&t) : Base(std::move(t)) {
36 const auto b = static_cast<bool>(*this);
37 assert(b && "NonNullSharedPtr constructed from nullptr");
38 if (!b)
39 Base::operator=(std::make_shared<T>());
40 }
41
42 NonNullSharedPtr(const NonNullSharedPtr &other) : Base(other) {}
43
44 NonNullSharedPtr(NonNullSharedPtr &&other) : Base(std::move(other)) {}
45
47 Base::operator=(other);
48 return *this;
49 }
50
52 Base::operator=(std::move(other));
53 return *this;
54 }
55
56 using Base::operator*;
57 using Base::operator->;
58 using Base::get;
59 using Base::use_count;
60 using Base::operator bool;
61
62 void swap(NonNullSharedPtr &other) { Base::swap(other); }
63
64 /// Explicitly deleted operations that could introduce nullptr.
65 /// @{
66 void reset() = delete;
67 void reset(T *ptr) = delete;
68 /// @}
69};
70
71} // namespace lldb_private
72
73/// Specialized swap function for NonNullSharedPtr to enable argument-dependent
74/// lookup (ADL) and efficient swapping.
75template <typename T>
80
81#endif
void swap(lldb_private::NonNullSharedPtr< T > &lhs, lldb_private::NonNullSharedPtr< T > &rhs)
Specialized swap function for NonNullSharedPtr to enable argument-dependent lookup (ADL) and efficien...
A non-nullable shared pointer that always holds a valid object.
NonNullSharedPtr(const std::shared_ptr< T > &t)
NonNullSharedPtr(NonNullSharedPtr &&other)
void swap(NonNullSharedPtr &other)
void reset()=delete
Explicitly deleted operations that could introduce nullptr.
void reset(T *ptr)=delete
NonNullSharedPtr(const NonNullSharedPtr &other)
NonNullSharedPtr(std::shared_ptr< T > &&t)
NonNullSharedPtr & operator=(NonNullSharedPtr &&other)
NonNullSharedPtr & operator=(const NonNullSharedPtr &other)
A class that represents a running process on the host machine.