// Copyright © 2013 The CefSharp Authors. All rights reserved. // // Use of this source code is governed by a BSD-style license that can be found in the LICENSE file. #pragma once namespace CefSharp { namespace Internals { // This class appears to be required in order // to continue reference counting in managed classes // that the compiler won't let contain CefRefPtr<...> template ref class MCefRefPtr sealed { private: T* _ptr; public: MCefRefPtr() : _ptr(nullptr) {} MCefRefPtr(T* p) : _ptr(p) { if (_ptr) { _ptr->AddRef(); } } MCefRefPtr(const MCefRefPtr% r) : _ptr(r._ptr) { if (_ptr) { _ptr->AddRef(); } } MCefRefPtr(const CefRefPtr& r) : _ptr(r.get()) { if (_ptr) { _ptr->AddRef(); } } !MCefRefPtr() { if (_ptr) { _ptr->Release(); // Be paranoid about preventing a double release // from this managed instance. _ptr = nullptr; } } ~MCefRefPtr() { // Normally, we would invoke the finalizer method here // via !classname, however... the overloaded -> operator // prevents that from being feasible. if (_ptr) { _ptr->Release(); // Be paranoid about preventing a double release // from this managed instance. _ptr = nullptr; } } T* get() { return _ptr; } /* * commented out for now as this operator interferes with the * return statement of MCefRefPtr% operator=(T* p) operator T*() { return _ptr; } */ T* operator->() { return _ptr; } MCefRefPtr% operator=(T* p) { // AddRef first so that self assignment should work if (p) { p->AddRef(); } if (_ptr) { _ptr->Release(); } _ptr = p; return *this; } MCefRefPtr% operator=(const MCefRefPtr% r) { return %this = r._ptr; } void swap(T** pp) { T* p = _ptr; _ptr = *pp; *pp = p; } void swap(MCefRefPtr% r) { swap(%r._ptr); } virtual bool Equals(Object^ obj) override { if (obj->GetType() == GetType()) { MCefRefPtr^ other = safe_cast(obj); return (*other)._ptr == _ptr; } return false; } //TODO: Is this used? Disable warnings for now though code can likely be removed #pragma warning( push ) #pragma warning(disable:4302) #pragma warning(disable:4311) virtual int GetHashCode() override { return (int)_ptr; } #pragma warning( pop ) }; } }