d3d9: Get rid of IDirect3D9Impl.
[wine] / dlls / d3d9 / query.c
1 /*
2  * IDirect3DQuery9 implementation
3  *
4  * Copyright 2002-2003 Raphael Junqueira
5  * Copyright 2002-2003 Jason Edmeades
6  * Copyright 2005 Oliver Stieber
7  *
8  * This library is free software; you can redistribute it and/or
9  * modify it under the terms of the GNU Lesser General Public
10  * License as published by the Free Software Foundation; either
11  * version 2.1 of the License, or (at your option) any later version.
12  *
13  * This library is distributed in the hope that it will be useful,
14  * but WITHOUT ANY WARRANTY; without even the implied warranty of
15  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
16  * Lesser General Public License for more details.
17  *
18  * You should have received a copy of the GNU Lesser General Public
19  * License along with this library; if not, write to the Free Software
20  * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21  */
22
23 #include "config.h"
24 #include "d3d9_private.h"
25
26 WINE_DEFAULT_DEBUG_CHANNEL(d3d9);
27
28 static inline IDirect3DQuery9Impl *impl_from_IDirect3DQuery9(IDirect3DQuery9 *iface)
29 {
30     return CONTAINING_RECORD(iface, IDirect3DQuery9Impl, IDirect3DQuery9_iface);
31 }
32
33 static HRESULT WINAPI IDirect3DQuery9Impl_QueryInterface(IDirect3DQuery9 *iface, REFIID riid,
34         void **ppobj)
35 {
36     TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), ppobj);
37
38     if (IsEqualGUID(riid, &IID_IDirect3DQuery9)
39             || IsEqualGUID(riid, &IID_IUnknown))
40     {
41         IDirect3DQuery9_AddRef(iface);
42         *ppobj = iface;
43         return S_OK;
44     }
45
46     WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid));
47
48     *ppobj = NULL;
49     return E_NOINTERFACE;
50 }
51
52 static ULONG WINAPI IDirect3DQuery9Impl_AddRef(IDirect3DQuery9 *iface)
53 {
54     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
55     ULONG ref = InterlockedIncrement(&This->ref);
56
57     TRACE("%p increasing refcount to %u.\n", iface, ref);
58
59     return ref;
60 }
61
62 static ULONG WINAPI IDirect3DQuery9Impl_Release(IDirect3DQuery9 *iface)
63 {
64     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
65     ULONG ref = InterlockedDecrement(&This->ref);
66
67     TRACE("%p decreasing refcount to %u.\n", iface, ref);
68
69     if (ref == 0) {
70         wined3d_mutex_lock();
71         wined3d_query_decref(This->wineD3DQuery);
72         wined3d_mutex_unlock();
73
74         IDirect3DDevice9Ex_Release(This->parentDevice);
75         HeapFree(GetProcessHeap(), 0, This);
76     }
77     return ref;
78 }
79
80 static HRESULT WINAPI IDirect3DQuery9Impl_GetDevice(IDirect3DQuery9 *iface,
81         IDirect3DDevice9 **device)
82 {
83     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
84
85     TRACE("iface %p, device %p.\n", iface, device);
86
87     *device = (IDirect3DDevice9 *)This->parentDevice;
88     IDirect3DDevice9_AddRef(*device);
89
90     TRACE("Returning device %p.\n", *device);
91
92     return D3D_OK;
93 }
94
95 static D3DQUERYTYPE WINAPI IDirect3DQuery9Impl_GetType(IDirect3DQuery9 *iface)
96 {
97     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
98     D3DQUERYTYPE type;
99
100     TRACE("iface %p.\n", iface);
101
102     wined3d_mutex_lock();
103     type = wined3d_query_get_type(This->wineD3DQuery);
104     wined3d_mutex_unlock();
105
106     return type;
107 }
108
109 static DWORD WINAPI IDirect3DQuery9Impl_GetDataSize(IDirect3DQuery9 *iface)
110 {
111     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
112     DWORD ret;
113
114     TRACE("iface %p.\n", iface);
115
116     wined3d_mutex_lock();
117     ret = wined3d_query_get_data_size(This->wineD3DQuery);
118     wined3d_mutex_unlock();
119
120     return ret;
121 }
122
123 static HRESULT WINAPI IDirect3DQuery9Impl_Issue(IDirect3DQuery9 *iface, DWORD dwIssueFlags)
124 {
125     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
126     HRESULT hr;
127
128     TRACE("iface %p, flags %#x.\n", iface, dwIssueFlags);
129
130     wined3d_mutex_lock();
131     hr = wined3d_query_issue(This->wineD3DQuery, dwIssueFlags);
132     wined3d_mutex_unlock();
133
134     return hr;
135 }
136
137 static HRESULT WINAPI IDirect3DQuery9Impl_GetData(IDirect3DQuery9 *iface, void *pData,
138         DWORD dwSize, DWORD dwGetDataFlags)
139 {
140     IDirect3DQuery9Impl *This = impl_from_IDirect3DQuery9(iface);
141     HRESULT hr;
142
143     TRACE("iface %p, data %p, size %u, flags %#x.\n",
144             iface, pData, dwSize, dwGetDataFlags);
145
146     wined3d_mutex_lock();
147     hr = wined3d_query_get_data(This->wineD3DQuery, pData, dwSize, dwGetDataFlags);
148     wined3d_mutex_unlock();
149
150     return hr;
151 }
152
153
154 static const IDirect3DQuery9Vtbl Direct3DQuery9_Vtbl =
155 {
156     IDirect3DQuery9Impl_QueryInterface,
157     IDirect3DQuery9Impl_AddRef,
158     IDirect3DQuery9Impl_Release,
159     IDirect3DQuery9Impl_GetDevice,
160     IDirect3DQuery9Impl_GetType,
161     IDirect3DQuery9Impl_GetDataSize,
162     IDirect3DQuery9Impl_Issue,
163     IDirect3DQuery9Impl_GetData
164 };
165
166 HRESULT query_init(IDirect3DQuery9Impl *query, IDirect3DDevice9Impl *device, D3DQUERYTYPE type)
167 {
168     HRESULT hr;
169
170     query->IDirect3DQuery9_iface.lpVtbl = &Direct3DQuery9_Vtbl;
171     query->ref = 1;
172
173     wined3d_mutex_lock();
174     hr = wined3d_query_create(device->wined3d_device, type, &query->wineD3DQuery);
175     wined3d_mutex_unlock();
176     if (FAILED(hr))
177     {
178         WARN("Failed to create wined3d query, hr %#x.\n", hr);
179         return hr;
180     }
181
182     query->parentDevice = &device->IDirect3DDevice9Ex_iface;
183     IDirect3DDevice9Ex_AddRef(query->parentDevice);
184
185     return D3D_OK;
186 }