// Copyright 2013 The Flutter Authors. All rights reserved. // Use of this source code is governed by a BSD-style license that can be // found in the LICENSE file. #ifndef FLUTTER_FML_CLOSURE_H_ #define FLUTTER_FML_CLOSURE_H_ #include #include "flutter/fml/macros.h" namespace fml { using closure = std::function; //------------------------------------------------------------------------------ /// @brief Wraps a closure that is invoked in the destructor unless /// released by the caller. /// /// This is especially useful in dealing with APIs that return a /// resource by accepting ownership of a sub-resource and a closure /// that releases that resource. When such APIs are chained, each /// link in the chain must check that the next member in the chain /// has accepted the resource. If not, it must invoke the closure /// eagerly. Not doing this results in a resource leak in the /// erroneous case. Using this wrapper, the closure can be released /// once the next call in the chain has successfully accepted /// ownership of the resource. If not, the closure gets invoked /// automatically at the end of the scope. This covers the cases /// where there are early returns as well. /// class ScopedCleanupClosure { public: ScopedCleanupClosure(const fml::closure& closure) : closure_(closure) {} ~ScopedCleanupClosure() { if (closure_) { closure_(); } } fml::closure Release() { fml::closure closure = closure_; closure_ = nullptr; return closure; } private: fml::closure closure_; FML_DISALLOW_COPY_AND_ASSIGN(ScopedCleanupClosure); }; } // namespace fml #endif // FLUTTER_FML_CLOSURE_H_