1 // 2 // Copyright (c) 2021 Travis Geiselbrecht 3 // 4 // Use of this source code is governed by a MIT-style 5 // license that can be found in the LICENSE file or at 6 // https://opensource.org/licenses/MIT 7 // 8 // Copyright 2016 The Fuchsia Authors. All rights reserved. 9 // Use of this source code is governed by a BSD-style license that can be 10 // found in the LICENSE file. 11 #pragma once 12 13 #include <type_traits> 14 15 // Helper routines used in C++ code in LK 16 17 // Macro used to simplify the task of deleting all of the default copy 18 // constructors and assignment operators. 19 #define DISALLOW_COPY_ASSIGN_AND_MOVE(_class_name) \ 20 _class_name(const _class_name&) = delete; \ 21 _class_name(_class_name&&) = delete; \ 22 _class_name& operator=(const _class_name&) = delete; \ 23 _class_name& operator=(_class_name&&) = delete 24 25 // Macro used to simplify the task of deleting the non rvalue reference copy 26 // constructors and assignment operators. (IOW - forcing move semantics) 27 #define DISALLOW_COPY_AND_ASSIGN_ALLOW_MOVE(_class_name) \ 28 _class_name(const _class_name&) = delete; \ 29 _class_name& operator=(const _class_name&) = delete 30 31 // Macro used to simplify the task of deleting the new and new[] 32 // operators. (IOW - disallow heap allocations) 33 #define DISALLOW_NEW \ 34 static void* operator new(size_t) = delete; \ 35 static void* operator new[](size_t) = delete 36 37 // TODO: find a better place for this 38 namespace lk { 39 40 template <typename T> 41 class auto_call { 42 public: auto_call(T c)43 constexpr explicit auto_call(T c) : call_(std::move(c)) {} ~auto_call()44 ~auto_call() { call(); } 45 auto_call(auto_call && c)46 auto_call(auto_call && c) : call_(std::move(c.call_)), armed_(c.armed_) { 47 c.cancel(); 48 } 49 auto_call& operator=(auto_call&& c) { 50 call(); 51 call_ = std::move(c.call_); 52 armed_ = c.armed_; 53 c.cancel(); 54 return *this; 55 } 56 57 DISALLOW_COPY_AND_ASSIGN_ALLOW_MOVE(auto_call); 58 call()59 void call() { 60 bool armed = armed_; 61 cancel(); 62 if (armed) { 63 call_(); 64 } 65 } cancel()66 void cancel() { 67 armed_ = false; 68 } 69 70 private: 71 T call_; 72 bool armed_ = true; 73 }; 74 75 template <typename T> make_auto_call(T c)76inline auto_call<T> make_auto_call(T c) { 77 return auto_call<T>(std::move(c)); 78 } 79 80 } // namespace lk 81 82 83