LMMS
Loading...
Searching...
No Matches
juce_win32_ComSmartPtr.h
Go to the documentation of this file.
1/*
2 ==============================================================================
3
4 This file is part of the JUCE library.
5 Copyright (c) 2022 - Raw Material Software Limited
6
7 JUCE is an open source library subject to commercial or open-source
8 licensing.
9
10 The code included in this file is provided under the terms of the ISC license
11 http://www.isc.org/downloads/software-support-policy/isc-license. Permission
12 To use, copy, modify, and/or distribute this software for any purpose with or
13 without fee is hereby granted provided that the above copyright notice and
14 this permission notice appear in all copies.
15
16 JUCE IS PROVIDED "AS IS" WITHOUT ANY WARRANTY, AND ALL WARRANTIES, WHETHER
17 EXPRESSED OR IMPLIED, INCLUDING MERCHANTABILITY AND FITNESS FOR PURPOSE, ARE
18 DISCLAIMED.
19
20 ==============================================================================
21*/
22
23namespace juce
24{
25
26#if (! defined (_MSC_VER) && ! defined (__uuidof))
27 #ifdef __uuidof
28 #undef __uuidof
29 #endif
30
31 template <typename Type> struct UUIDGetter { static CLSID get() { jassertfalse; return {}; } };
32 #define __uuidof(x) UUIDGetter<x>::get()
33
34 template <>
35 struct UUIDGetter<::IUnknown>
36 {
37 static CLSID get() { return { 0, 0, 0, { 0xc0, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46 } }; }
38 };
39
40 #define JUCE_DECLARE_UUID_GETTER(name, uuid) \
41 template <> struct UUIDGetter<name> { static CLSID get() { return uuidFromString (uuid); } };
42
43 #define JUCE_COMCLASS(name, guid) \
44 struct name; \
45 JUCE_DECLARE_UUID_GETTER (name, guid) \
46 struct name
47
48#else
49 #define JUCE_DECLARE_UUID_GETTER(name, uuid)
50 #define JUCE_COMCLASS(name, guid) struct DECLSPEC_UUID (guid) name
51#endif
52
53#define JUCE_IUNKNOWNCLASS(name, guid) JUCE_COMCLASS(name, guid) : public IUnknown
54#define JUCE_COMRESULT HRESULT STDMETHODCALLTYPE
55#define JUCE_COMCALL virtual HRESULT STDMETHODCALLTYPE
56
57JUCE_BEGIN_IGNORE_WARNINGS_GCC_LIKE ("-Wlanguage-extension-token")
58
60{
61 uint32 ints[4] = {};
62
63 for (uint32 digitIndex = 0; digitIndex < 32;)
64 {
65 auto c = (uint32) *s++;
66 uint32 digit;
67
68 if (c >= '0' && c <= '9') digit = c - '0';
69 else if (c >= 'a' && c <= 'f') digit = c - 'a' + 10;
70 else if (c >= 'A' && c <= 'F') digit = c - 'A' + 10;
71 else if (c == '-') continue;
72 else break;
73
74 ints[digitIndex / 8] |= (digit << 4 * (7 - (digitIndex & 7)));
75 ++digitIndex;
76 }
77
78 return { ints[0],
79 (uint16) (ints[1] >> 16),
80 (uint16) ints[1],
81 { (uint8) (ints[2] >> 24), (uint8) (ints[2] >> 16), (uint8) (ints[2] >> 8), (uint8) ints[2],
82 (uint8) (ints[3] >> 24), (uint8) (ints[3] >> 16), (uint8) (ints[3] >> 8), (uint8) ints[3] }};
83}
84
85//==============================================================================
90template <class ComClass>
92{
93public:
95 ComSmartPtr (ComClass* obj) : p (obj) { if (p) p->AddRef(); }
96 ComSmartPtr (const ComSmartPtr& other) : p (other.p) { if (p) p->AddRef(); }
98
99 operator ComClass*() const noexcept { return p; }
100 ComClass& operator*() const noexcept { return *p; }
101 ComClass* operator->() const noexcept { return p; }
102
103 ComSmartPtr& operator= (ComClass* const newP)
104 {
105 if (newP != nullptr) newP->AddRef();
106 release();
107 p = newP;
108 return *this;
109 }
110
111 ComSmartPtr& operator= (const ComSmartPtr& newP) { return operator= (newP.p); }
112
113 // Releases and nullifies this pointer and returns its address
115 {
116 release();
117 p = nullptr;
118 return &p;
119 }
120
121 HRESULT CoCreateInstance (REFCLSID classUUID, DWORD dwClsContext = CLSCTX_INPROC_SERVER)
122 {
123 auto hr = ::CoCreateInstance (classUUID, nullptr, dwClsContext, __uuidof (ComClass), (void**) resetAndGetPointerAddress());
124 jassert (hr != CO_E_NOTINITIALIZED); // You haven't called CoInitialize for the current thread!
125 return hr;
126 }
127
128 template <class OtherComClass>
129 HRESULT QueryInterface (REFCLSID classUUID, ComSmartPtr<OtherComClass>& destObject) const
130 {
131 if (p == nullptr)
132 return E_POINTER;
133
134 return p->QueryInterface (classUUID, (void**) destObject.resetAndGetPointerAddress());
135 }
136
137 template <class OtherComClass>
139 {
140 return this->QueryInterface (__uuidof (OtherComClass), destObject);
141 }
142
143 template <class OtherComClass>
145 {
147
148 if (QueryInterface (destObject) == S_OK)
149 return destObject;
150
151 return nullptr;
152 }
153
154private:
155 ComClass* p = nullptr;
156
157 void release() { if (p != nullptr) p->Release(); }
158
159 ComClass** operator&() noexcept; // private to avoid it being used accidentally
160};
161
162//==============================================================================
163template <class First, class... ComClasses>
164class ComBaseClassHelperBase : public First, public ComClasses...
165{
166public:
167 ComBaseClassHelperBase (unsigned int initialRefCount) : refCount (initialRefCount) {}
168 virtual ~ComBaseClassHelperBase() = default;
169
170 ULONG STDMETHODCALLTYPE AddRef() { return ++refCount; }
171 ULONG STDMETHODCALLTYPE Release() { auto r = --refCount; if (r == 0) delete this; return r; }
172
173protected:
175
176 JUCE_COMRESULT QueryInterface (REFIID refId, void** result)
177 {
178 if (refId == __uuidof (IUnknown))
179 return castToType<First> (result);
180
181 *result = nullptr;
182 return E_NOINTERFACE;
183 }
184
185 template <class Type>
187 {
188 this->AddRef();
189 *result = dynamic_cast<Type*> (this);
190
191 return S_OK;
192 }
193};
194
199template <class... ComClasses>
200class ComBaseClassHelper : public ComBaseClassHelperBase<ComClasses...>
201{
202public:
203 explicit ComBaseClassHelper (unsigned int initialRefCount = 1)
204 : ComBaseClassHelperBase<ComClasses...> (initialRefCount) {}
205
206 JUCE_COMRESULT QueryInterface (REFIID refId, void** result)
207 {
208 const std::tuple<IID, void*> bases[]
209 {
210 std::make_tuple (__uuidof (ComClasses),
211 static_cast<void*> (static_cast<ComClasses*> (this)))...
212 };
213
214 for (const auto& base : bases)
215 {
216 if (refId == std::get<0> (base))
217 {
218 this->AddRef();
219 *result = std::get<1> (base);
220 return S_OK;
221 }
222 }
223
225 }
226};
227
229
230} // namespace juce
#define noexcept
Definition DistrhoDefines.h:72
JUCE_COMRESULT QueryInterface(REFIID refId, void **result)
Definition juce_win32_ComSmartPtr.h:176
ULONG refCount
Definition juce_win32_ComSmartPtr.h:174
JUCE_COMRESULT castToType(void **result)
Definition juce_win32_ComSmartPtr.h:186
ComBaseClassHelperBase(unsigned int initialRefCount)
Definition juce_win32_ComSmartPtr.h:167
ULONG STDMETHODCALLTYPE AddRef()
Definition juce_win32_ComSmartPtr.h:170
virtual ~ComBaseClassHelperBase()=default
ULONG STDMETHODCALLTYPE Release()
Definition juce_win32_ComSmartPtr.h:171
ComBaseClassHelper(unsigned int initialRefCount=1)
Definition juce_win32_ComSmartPtr.h:203
JUCE_COMRESULT QueryInterface(REFIID refId, void **result)
Definition juce_win32_ComSmartPtr.h:206
ComSmartPtr() noexcept
Definition juce_win32_ComSmartPtr.h:94
~ComSmartPtr()
Definition juce_win32_ComSmartPtr.h:97
ComClass * operator->() const noexcept
Definition juce_win32_ComSmartPtr.h:101
ComSmartPtr(ComClass *obj)
Definition juce_win32_ComSmartPtr.h:95
ComClass ** resetAndGetPointerAddress()
Definition juce_win32_ComSmartPtr.h:114
HRESULT QueryInterface(ComSmartPtr< OtherComClass > &destObject) const
Definition juce_win32_ComSmartPtr.h:138
ComSmartPtr(const ComSmartPtr &other)
Definition juce_win32_ComSmartPtr.h:96
ComClass ** operator&() noexcept
void release()
Definition juce_win32_ComSmartPtr.h:157
HRESULT CoCreateInstance(REFCLSID classUUID, DWORD dwClsContext=CLSCTX_INPROC_SERVER)
Definition juce_win32_ComSmartPtr.h:121
ComClass & operator*() const noexcept
Definition juce_win32_ComSmartPtr.h:100
ComClass * p
Definition juce_win32_ComSmartPtr.h:155
HRESULT QueryInterface(REFCLSID classUUID, ComSmartPtr< OtherComClass > &destObject) const
Definition juce_win32_ComSmartPtr.h:129
ComSmartPtr< OtherComClass > getInterface() const
Definition juce_win32_ComSmartPtr.h:144
unsigned s
Definition inflate.c:1555
#define JUCE_BEGIN_IGNORE_WARNINGS_GCC_LIKE(...)
Definition juce_CompilerWarnings.h:181
#define JUCE_END_IGNORE_WARNINGS_GCC_LIKE
Definition juce_CompilerWarnings.h:182
#define jassert(expression)
#define jassertfalse
#define JUCE_COMRESULT
Definition juce_win32_ComSmartPtr.h:54
#define __uuidof(x)
Definition juce_win32_ComSmartPtr.h:32
Definition carla_juce.cpp:31
GUID uuidFromString(const char *s) noexcept
Definition juce_win32_ComSmartPtr.h:59
unsigned short uint16
Definition juce_MathsFunctions.h:41
unsigned int uint32
Definition juce_MathsFunctions.h:45
unsigned char uint8
Definition juce_MathsFunctions.h:37
static CLSID get()
Definition juce_win32_ComSmartPtr.h:37
Definition juce_win32_ComSmartPtr.h:31
static CLSID get()
Definition juce_win32_ComSmartPtr.h:31
#define S_OK
Definition swell-types.h:53
signed int HRESULT
Definition swell-types.h:181
unsigned int DWORD
Definition swell-types.h:164
unsigned int ULONG
Definition swell-types.h:183
struct _GUID GUID
return c
Definition crypt.c:175
int r
Definition crypt.c:458
int result
Definition process.c:1455
#define const
Definition zconf.h:137