1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */ 2 /* vim: set ts=8 sts=2 et sw=2 tw=80: */ 3 /* This code is made available to you under your choice of the following sets 4 * of licensing terms: 5 */ 6 /* This Source Code Form is subject to the terms of the Mozilla Public 7 * License, v. 2.0. If a copy of the MPL was not distributed with this 8 * file, You can obtain one at http://mozilla.org/MPL/2.0/. 9 */ 10 /* Copyright 2013 Mozilla Contributors 11 * 12 * Licensed under the Apache License, Version 2.0 (the "License"); 13 * you may not use this file except in compliance with the License. 14 * You may obtain a copy of the License at 15 * 16 * http://www.apache.org/licenses/LICENSE-2.0 17 * 18 * Unless required by applicable law or agreed to in writing, software 19 * distributed under the License is distributed on an "AS IS" BASIS, 20 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 21 * See the License for the specific language governing permissions and 22 * limitations under the License. 23 */ 24 25 #ifndef mozilla_pkix_ScopedPtr_h 26 #define mozilla_pkix_ScopedPtr_h 27 28 namespace mozilla { 29 namespace pkix { 30 31 // A subset polyfill of std::unique_ptr that does not support move construction 32 // or move assignment. This is used instead of std::unique_ptr because some 33 // important toolchains still don't provide std::unique_ptr, including in 34 // particular Android NDK projects with APP_STL=stlport_static or 35 // ALL_STL=stlport_shared. 36 template <typename T, void (&Destroyer)(T*)> 37 class ScopedPtr final { 38 public: mValue(value)39 explicit ScopedPtr(T* value = nullptr) : mValue(value) {} 40 41 ScopedPtr(const ScopedPtr&) = delete; 42 ~ScopedPtr()43 ~ScopedPtr() { 44 if (mValue) { 45 Destroyer(mValue); 46 } 47 } 48 49 void operator=(const ScopedPtr&) = delete; 50 51 T& operator*() const { return *mValue; } 52 T* operator->() const { return mValue; } 53 54 explicit operator bool() const { return mValue; } 55 get()56 T* get() const { return mValue; } 57 release()58 T* release() { 59 T* result = mValue; 60 mValue = nullptr; 61 return result; 62 } 63 64 void reset(T* newValue = nullptr) { 65 // The C++ standard requires std::unique_ptr to destroy the old value 66 // pointed to by mValue, if any, *after* assigning the new value to mValue. 67 T* oldValue = mValue; 68 mValue = newValue; 69 if (oldValue) { 70 Destroyer(oldValue); 71 } 72 } 73 74 private: 75 T* mValue; 76 }; 77 78 } // namespace pkix 79 } // namespace mozilla 80 81 #endif // mozilla_pkix_ScopedPtr_h 82