From: Yedidya Feldblum Date: Thu, 11 Jan 2018 01:52:13 +0000 (-0800) Subject: Move ScopeGuardImpl and ScopeGuardImplBase into the detail namespace X-Git-Tag: v2018.01.15.00~16 X-Git-Url: http://demsky.eecs.uci.edu/git/?a=commitdiff_plain;h=e61c21509306b8bad35427a3a768347d51c25e66;p=folly.git Move ScopeGuardImpl and ScopeGuardImplBase into the detail namespace Summary: [Folly] Move `ScopeGuardImpl` and `ScopeGuardImplBase` into the `detail` namespace. Let them be marked as private implementation details. Reviewed By: andrewjcg Differential Revision: D6665317 fbshipit-source-id: 03e8fee6a16338395ec92c582613b053bd9f74ec --- diff --git a/folly/ScopeGuard.cpp b/folly/ScopeGuard.cpp index 9167a261..e6a916c0 100644 --- a/folly/ScopeGuard.cpp +++ b/folly/ScopeGuard.cpp @@ -1,5 +1,5 @@ /* - * Copyright 2017 Facebook, Inc. + * Copyright 2016-present Facebook, Inc. * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. @@ -18,7 +18,7 @@ #include -/*static*/ void folly::ScopeGuardImplBase::warnAboutToCrash() noexcept { +/*static*/ void folly::detail::ScopeGuardImplBase::warnAboutToCrash() noexcept { // Ensure the availability of std::cerr std::ios_base::Init ioInit; std::cerr diff --git a/folly/ScopeGuard.h b/folly/ScopeGuard.h index 8d8e420d..135d2c4c 100644 --- a/folly/ScopeGuard.h +++ b/folly/ScopeGuard.h @@ -28,47 +28,8 @@ namespace folly { -/** - * ScopeGuard is a general implementation of the "Initialization is - * Resource Acquisition" idiom. Basically, it guarantees that a function - * is executed upon leaving the currrent scope unless otherwise told. - * - * The makeGuard() function is used to create a new ScopeGuard object. - * It can be instantiated with a lambda function, a std::function, - * a functor, or a void(*)() function pointer. - * - * - * Usage example: Add a friend to memory if and only if it is also added - * to the db. - * - * void User::addFriend(User& newFriend) { - * // add the friend to memory - * friends_.push_back(&newFriend); - * - * // If the db insertion that follows fails, we should - * // remove it from memory. - * auto guard = makeGuard([&] { friends_.pop_back(); }); - * - * // this will throw an exception upon error, which - * // makes the ScopeGuard execute UserCont::pop_back() - * // once the Guard's destructor is called. - * db_->addFriend(GetName(), newFriend.GetName()); - * - * // an exception was not thrown, so don't execute - * // the Guard. - * guard.dismiss(); - * } - * - * Examine ScopeGuardTest.cpp for some more sample usage. - * - * Stolen from: - * Andrei's and Petru Marginean's CUJ article: - * http://drdobbs.com/184403758 - * and the loki library: - * http://loki-lib.sourceforge.net/index.php?n=Idioms.ScopeGuardPointer - * and triendl.kj article: - * http://www.codeproject.com/KB/cpp/scope_guard.aspx - */ +namespace detail { + class ScopeGuardImplBase { public: void dismiss() noexcept { @@ -172,19 +133,62 @@ class ScopeGuardImpl : public ScopeGuardImplBase { FunctionType function_; }; -template -ScopeGuardImpl::type> -makeGuard(FunctionType&& fn) noexcept( - std::is_nothrow_constructible::type, - FunctionType>::value) { - return ScopeGuardImpl::type>( - std::forward(fn)); +template +using ScopeGuardImplDecay = ScopeGuardImpl::type>; + +} // namespace detail + +/** + * ScopeGuard is a general implementation of the "Initialization is + * Resource Acquisition" idiom. Basically, it guarantees that a function + * is executed upon leaving the currrent scope unless otherwise told. + * + * The makeGuard() function is used to create a new ScopeGuard object. + * It can be instantiated with a lambda function, a std::function, + * a functor, or a void(*)() function pointer. + * + * + * Usage example: Add a friend to memory if and only if it is also added + * to the db. + * + * void User::addFriend(User& newFriend) { + * // add the friend to memory + * friends_.push_back(&newFriend); + * + * // If the db insertion that follows fails, we should + * // remove it from memory. + * auto guard = makeGuard([&] { friends_.pop_back(); }); + * + * // this will throw an exception upon error, which + * // makes the ScopeGuard execute UserCont::pop_back() + * // once the Guard's destructor is called. + * db_->addFriend(GetName(), newFriend.GetName()); + * + * // an exception was not thrown, so don't execute + * // the Guard. + * guard.dismiss(); + * } + * + * Examine ScopeGuardTest.cpp for some more sample usage. + * + * Stolen from: + * Andrei's and Petru Marginean's CUJ article: + * http://drdobbs.com/184403758 + * and the loki library: + * http://loki-lib.sourceforge.net/index.php?n=Idioms.ScopeGuardPointer + * and triendl.kj article: + * http://www.codeproject.com/KB/cpp/scope_guard.aspx + */ +template +detail::ScopeGuardImplDecay makeGuard(F&& f) noexcept( + noexcept(detail::ScopeGuardImplDecay(static_cast(f)))) { + return detail::ScopeGuardImplDecay(static_cast(f)); } /** * This is largely unneeded if you just use auto for your guards. */ -typedef ScopeGuardImplBase&& ScopeGuard; +typedef detail::ScopeGuardImplBase&& ScopeGuard; namespace detail {