/* * Copyright (c) Facebook, Inc. and its affiliates. * * This source code is licensed under the MIT license found in the * LICENSE file in the root directory of this source tree. */ #include namespace unique_ptr { struct X { int field; int get() { return field; } void set(int value) { field = value; } }; int empty_ptr_access() { std::unique_ptr x; int* p = x.get(); // no dereference if (p) { return 1; } return 0; } int FN_empty_ptr_deref_bad() { std::unique_ptr x; return *x; } int FN_empty_array_ptr_deref_bad() { std::unique_ptr x; return x[0]; } int FN_nullptr_ptr_deref_bad() { std::unique_ptr x(nullptr); return *x; } int FN_nullptr_array_ptr_deref_bad() { std::unique_ptr x(nullptr); return x[2]; } int FN_empty_ptr_field_deref_bad() { std::unique_ptr x; return x.get()->field; } int FN_empty_ptr_field_deref2_bad() { std::unique_ptr x; return x->field; } int FN_empty_ptr_method_deref_bad() { std::unique_ptr x; return x->get(); } // FP is memory leak int FN_FP_reset_ptr_null_deref_bad() { std::unique_ptr x(new int); x.reset(); return *x; } int FN_FP_reset_ptr_null_deref2_bad() { std::unique_ptr x(new int); x.reset(new int); x.reset(); return *x; } int FP_reset_ptr_deref_ok() { std::unique_ptr x; x.reset(new int); return *x; } int FP_reset_ptr_deref2_ok() { std::unique_ptr x; x.reset(); x.reset(new int); return *x; } int FN_unique_ptr_copy_null_deref_bad() { std::unique_ptr p1; std::unique_ptr p2 = std::move(p1); return *p2; } int FN_unique_ptr_assign_null_deref_bad() { std::unique_ptr p1(new int); std::unique_ptr p2; p1 = std::move(p2); return *p1; } int FP_unique_ptr_move_deref_ok() { std::unique_ptr p1(new int); std::unique_ptr p2 = std::move(p1); return *p2; } int unique_ptr_assign_deref_ok() { std::unique_ptr p1(new int); std::unique_ptr p2; p2 = std::move(p1); p1.reset(); return *p2; } int FN_unique_ptr_move_null_deref_bad() { std::unique_ptr p1(new int); std::unique_ptr p2 = std::move(p1); return *p1; } } // namespace unique_ptr namespace unique_ptr_with_deleter { /* This is just a compilation test */ template class Pointer { public: /* No constructor with only one T* argument */ /* implicit */ Pointer(std::nullptr_t = nullptr) noexcept {} Pointer(T* ptr, int n) noexcept {} friend bool operator==(Pointer a, Pointer b) noexcept { return true; } friend bool operator!=(Pointer a, Pointer b) noexcept { return true; } explicit operator bool() const noexcept { return true; } T* operator->() const noexcept { return get(); } T& operator*() const noexcept { return *get(); } T* get() const noexcept { return nullptr; } }; template struct Deleter { using pointer = Pointer; void operator()(pointer ptr) const {} }; template using my_unique_ptr = std::unique_ptr>; bool instantiate() { my_unique_ptr p; my_unique_ptr q; return p != nullptr && q != nullptr; } } // namespace unique_ptr_with_deleter