/* * * Copyright (c) 2020 Project CHIP Authors * * Licensed under the Apache License, Version 2.0 (the "License"); * you may not use this file except in compliance with the License. * You may obtain a copy of the License at * * http://www.apache.org/licenses/LICENSE-2.0 * * Unless required by applicable law or agreed to in writing, software * distributed under the License is distributed on an "AS IS" BASIS, * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. * See the License for the specific language governing permissions and * limitations under the License. */ #pragma once #include #include #include namespace chip { template class UniquePointerReceiver { public: UniquePointerReceiver(std::unique_ptr & target) : mTarget(target) {} ~UniquePointerReceiver() { mTarget.reset(mValue); } T *& Get() { return mValue; } T ** operator&() { return &mValue; } private: std::unique_ptr & mTarget; T * mValue = nullptr; }; template UniquePointerReceiver MakeUniquePointerReceiver(std::unique_ptr & target) { return UniquePointerReceiver(target); } struct GFree { void operator()(gpointer object) { g_free(object); } }; struct GObjectDeleter { void operator()(gpointer object) { g_object_unref(object); } }; struct GErrorDeleter { void operator()(GError * object) { g_error_free(object); } }; struct GIOChannelDeleter { void operator()(GIOChannel * object) { g_io_channel_unref(object); } }; struct GSourceDeleter { void operator()(GSource * object) { g_source_unref(object); } }; struct GVariantDeleter { void operator()(GVariant * object) { g_variant_unref(object); } }; struct GVariantIterDeleter { void operator()(GVariantIter * object) { g_variant_iter_free(object); } }; struct GBytesDeleter { void operator()(GBytes * object) { g_bytes_unref(object); } }; template struct GAutoPtrDeleter { }; template <> struct GAutoPtrDeleter { using deleter = GFree; }; template <> struct GAutoPtrDeleter { using deleter = GFree; }; template <> struct GAutoPtrDeleter { using deleter = GBytesDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GObjectDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GObjectDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GObjectDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GObjectDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GErrorDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GIOChannelDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GSourceDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GVariantDeleter; }; template <> struct GAutoPtrDeleter { using deleter = GVariantIterDeleter; }; template class GAutoPtr : public std::unique_ptr::deleter> { public: using deleter = typename GAutoPtrDeleter::deleter; using std::unique_ptr::unique_ptr; // Convenience method to get a UniquePointerReceiver for this object. UniquePointerReceiver GetReceiver() { return MakeUniquePointerReceiver(*this); } }; } // namespace chip