2 * Copyright 2009 Henri Verbeet for CodeWeavers
3 * Copyright 2015 Józef Kucia for CodeWeavers
5 * This library is free software; you can redistribute it and/or
6 * modify it under the terms of the GNU Lesser General Public
7 * License as published by the Free Software Foundation; either
8 * version 2.1 of the License, or (at your option) any later version.
10 * This library is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
13 * Lesser General Public License for more details.
15 * You should have received a copy of the GNU Lesser General Public
16 * License along with this library; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
21 #include "d3d11_private.h"
23 WINE_DEFAULT_DEBUG_CHANNEL(d3d11
);
25 /* ID3D11Texture1D methods */
27 static inline struct d3d_texture1d
*impl_from_ID3D11Texture1D(ID3D11Texture1D
*iface
)
29 return CONTAINING_RECORD(iface
, struct d3d_texture1d
, ID3D11Texture1D_iface
);
32 static HRESULT STDMETHODCALLTYPE
d3d11_texture1d_QueryInterface(ID3D11Texture1D
*iface
, REFIID iid
, void **out
)
34 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
36 TRACE("iface %p, iid %s, out %p.\n", iface
, debugstr_guid(iid
), out
);
38 if (IsEqualGUID(iid
, &IID_ID3D11Texture1D
)
39 || IsEqualGUID(iid
, &IID_ID3D11Resource
)
40 || IsEqualGUID(iid
, &IID_ID3D11DeviceChild
)
41 || IsEqualGUID(iid
, &IID_IUnknown
))
44 IUnknown_AddRef(iface
);
48 if (IsEqualGUID(iid
, &IID_ID3D10Texture1D
)
49 || IsEqualGUID(iid
, &IID_ID3D10Resource
)
50 || IsEqualGUID(iid
, &IID_ID3D10DeviceChild
))
52 *out
= &texture
->ID3D10Texture1D_iface
;
53 IUnknown_AddRef((IUnknown
*)*out
);
57 if (texture
->dxgi_surface
)
59 TRACE("Forwarding to dxgi surface.\n");
60 return IUnknown_QueryInterface(texture
->dxgi_surface
, iid
, out
);
63 WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(iid
));
69 static ULONG STDMETHODCALLTYPE
d3d11_texture1d_AddRef(ID3D11Texture1D
*iface
)
71 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
72 ULONG refcount
= InterlockedIncrement(&texture
->refcount
);
74 TRACE("%p increasing refcount to %u.\n", texture
, refcount
);
78 ID3D11Device2_AddRef(texture
->device
);
80 wined3d_texture_incref(texture
->wined3d_texture
);
81 wined3d_mutex_unlock();
87 static ULONG STDMETHODCALLTYPE
d3d11_texture1d_Release(ID3D11Texture1D
*iface
)
89 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
90 ULONG refcount
= InterlockedDecrement(&texture
->refcount
);
92 TRACE("%p decreasing refcount to %u.\n", texture
, refcount
);
96 ID3D11Device2
*device
= texture
->device
;
99 wined3d_texture_decref(texture
->wined3d_texture
);
100 wined3d_mutex_unlock();
101 /* Release the device last, it may cause the wined3d device to be
103 ID3D11Device2_Release(device
);
109 static void STDMETHODCALLTYPE
d3d11_texture1d_GetDevice(ID3D11Texture1D
*iface
, ID3D11Device
**device
)
111 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
113 TRACE("iface %p, device %p.\n", iface
, device
);
115 *device
= (ID3D11Device
*)texture
->device
;
116 ID3D11Device_AddRef(*device
);
119 static HRESULT STDMETHODCALLTYPE
d3d11_texture1d_GetPrivateData(ID3D11Texture1D
*iface
,
120 REFGUID guid
, UINT
*data_size
, void *data
)
122 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
123 IDXGISurface
*dxgi_surface
;
126 TRACE("iface %p, guid %s, data_size %p, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
128 if (texture
->dxgi_surface
129 && SUCCEEDED(IUnknown_QueryInterface(texture
->dxgi_surface
, &IID_IDXGISurface
, (void **)&dxgi_surface
)))
131 hr
= IDXGISurface_GetPrivateData(dxgi_surface
, guid
, data_size
, data
);
132 IDXGISurface_Release(dxgi_surface
);
136 return d3d_get_private_data(&texture
->private_store
, guid
, data_size
, data
);
139 static HRESULT STDMETHODCALLTYPE
d3d11_texture1d_SetPrivateData(ID3D11Texture1D
*iface
,
140 REFGUID guid
, UINT data_size
, const void *data
)
142 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
143 IDXGISurface
*dxgi_surface
;
146 TRACE("iface %p, guid %s, data_size %u, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
148 if (texture
->dxgi_surface
149 && SUCCEEDED(IUnknown_QueryInterface(texture
->dxgi_surface
, &IID_IDXGISurface
, (void **)&dxgi_surface
)))
151 hr
= IDXGISurface_SetPrivateData(dxgi_surface
, guid
, data_size
, data
);
152 IDXGISurface_Release(dxgi_surface
);
156 return d3d_set_private_data(&texture
->private_store
, guid
, data_size
, data
);
159 static HRESULT STDMETHODCALLTYPE
d3d11_texture1d_SetPrivateDataInterface(ID3D11Texture1D
*iface
,
160 REFGUID guid
, const IUnknown
*data
)
162 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
163 IDXGISurface
*dxgi_surface
;
166 TRACE("iface %p, guid %s, data %p.\n", iface
, debugstr_guid(guid
), data
);
168 if (texture
->dxgi_surface
169 && SUCCEEDED(IUnknown_QueryInterface(texture
->dxgi_surface
, &IID_IDXGISurface
, (void **)&dxgi_surface
)))
171 hr
= IDXGISurface_SetPrivateDataInterface(dxgi_surface
, guid
, data
);
172 IDXGISurface_Release(dxgi_surface
);
176 return d3d_set_private_data_interface(&texture
->private_store
, guid
, data
);
179 static void STDMETHODCALLTYPE
d3d11_texture1d_GetType(ID3D11Texture1D
*iface
,
180 D3D11_RESOURCE_DIMENSION
*resource_dimension
)
182 TRACE("iface %p, resource_dimension %p.\n", iface
, resource_dimension
);
184 *resource_dimension
= D3D11_RESOURCE_DIMENSION_TEXTURE1D
;
187 static void STDMETHODCALLTYPE
d3d11_texture1d_SetEvictionPriority(ID3D11Texture1D
*iface
, UINT eviction_priority
)
189 FIXME("iface %p, eviction_priority %#x stub!\n", iface
, eviction_priority
);
192 static UINT STDMETHODCALLTYPE
d3d11_texture1d_GetEvictionPriority(ID3D11Texture1D
*iface
)
194 FIXME("iface %p stub!\n", iface
);
199 static void STDMETHODCALLTYPE
d3d11_texture1d_GetDesc(ID3D11Texture1D
*iface
, D3D11_TEXTURE1D_DESC
*desc
)
201 struct d3d_texture1d
*texture
= impl_from_ID3D11Texture1D(iface
);
203 TRACE("iface %p, desc %p.\n", iface
, desc
);
205 *desc
= texture
->desc
;
208 static const struct ID3D11Texture1DVtbl d3d11_texture1d_vtbl
=
210 /* IUnknown methods */
211 d3d11_texture1d_QueryInterface
,
212 d3d11_texture1d_AddRef
,
213 d3d11_texture1d_Release
,
214 /* ID3D11DeviceChild methods */
215 d3d11_texture1d_GetDevice
,
216 d3d11_texture1d_GetPrivateData
,
217 d3d11_texture1d_SetPrivateData
,
218 d3d11_texture1d_SetPrivateDataInterface
,
219 /* ID3D11Resource methods */
220 d3d11_texture1d_GetType
,
221 d3d11_texture1d_SetEvictionPriority
,
222 d3d11_texture1d_GetEvictionPriority
,
223 /* ID3D11Texture1D methods */
224 d3d11_texture1d_GetDesc
,
227 struct d3d_texture1d
*unsafe_impl_from_ID3D11Texture1D(ID3D11Texture1D
*iface
)
231 assert(iface
->lpVtbl
== &d3d11_texture1d_vtbl
);
232 return CONTAINING_RECORD(iface
, struct d3d_texture1d
, ID3D11Texture1D_iface
);
235 static inline struct d3d_texture1d
*impl_from_ID3D10Texture1D(ID3D10Texture1D
*iface
)
237 return CONTAINING_RECORD(iface
, struct d3d_texture1d
, ID3D10Texture1D_iface
);
240 /* IUnknown methods */
242 static HRESULT STDMETHODCALLTYPE
d3d10_texture1d_QueryInterface(ID3D10Texture1D
*iface
, REFIID iid
, void **out
)
244 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
246 TRACE("iface %p, iid %s, out %p.\n", iface
, debugstr_guid(iid
), out
);
248 return d3d11_texture1d_QueryInterface(&texture
->ID3D11Texture1D_iface
, iid
, out
);
251 static ULONG STDMETHODCALLTYPE
d3d10_texture1d_AddRef(ID3D10Texture1D
*iface
)
253 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
255 TRACE("iface %p.\n", iface
);
257 return d3d11_texture1d_AddRef(&texture
->ID3D11Texture1D_iface
);
260 static void STDMETHODCALLTYPE
d3d_texture1d_wined3d_object_released(void *parent
)
262 struct d3d_texture1d
*texture
= parent
;
264 if (texture
->dxgi_surface
)
265 IUnknown_Release(texture
->dxgi_surface
);
266 wined3d_private_store_cleanup(&texture
->private_store
);
270 static ULONG STDMETHODCALLTYPE
d3d10_texture1d_Release(ID3D10Texture1D
*iface
)
272 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
274 TRACE("iface %p.\n", iface
);
276 return d3d11_texture1d_Release(&texture
->ID3D11Texture1D_iface
);
279 /* ID3D10DeviceChild methods */
281 static void STDMETHODCALLTYPE
d3d10_texture1d_GetDevice(ID3D10Texture1D
*iface
, ID3D10Device
**device
)
283 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
285 TRACE("iface %p, device %p.\n", iface
, device
);
287 ID3D11Device2_QueryInterface(texture
->device
, &IID_ID3D10Device
, (void **)device
);
290 static HRESULT STDMETHODCALLTYPE
d3d10_texture1d_GetPrivateData(ID3D10Texture1D
*iface
,
291 REFGUID guid
, UINT
*data_size
, void *data
)
293 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
295 TRACE("iface %p, guid %s, data_size %p, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
297 return d3d11_texture1d_GetPrivateData(&texture
->ID3D11Texture1D_iface
, guid
, data_size
, data
);
300 static HRESULT STDMETHODCALLTYPE
d3d10_texture1d_SetPrivateData(ID3D10Texture1D
*iface
,
301 REFGUID guid
, UINT data_size
, const void *data
)
303 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
305 TRACE("iface %p, guid %s, data_size %u, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
307 return d3d11_texture1d_SetPrivateData(&texture
->ID3D11Texture1D_iface
, guid
, data_size
, data
);
310 static HRESULT STDMETHODCALLTYPE
d3d10_texture1d_SetPrivateDataInterface(ID3D10Texture1D
*iface
,
311 REFGUID guid
, const IUnknown
*data
)
313 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
315 TRACE("iface %p, guid %s, data %p.\n", iface
, debugstr_guid(guid
), data
);
317 return d3d11_texture1d_SetPrivateDataInterface(&texture
->ID3D11Texture1D_iface
, guid
, data
);
320 /* ID3D10Resource methods */
322 static void STDMETHODCALLTYPE
d3d10_texture1d_GetType(ID3D10Texture1D
*iface
,
323 D3D10_RESOURCE_DIMENSION
*resource_dimension
)
325 TRACE("iface %p, resource_dimension %p\n", iface
, resource_dimension
);
327 *resource_dimension
= D3D10_RESOURCE_DIMENSION_TEXTURE1D
;
330 static void STDMETHODCALLTYPE
d3d10_texture1d_SetEvictionPriority(ID3D10Texture1D
*iface
, UINT eviction_priority
)
332 FIXME("iface %p, eviction_priority %u stub!\n", iface
, eviction_priority
);
335 static UINT STDMETHODCALLTYPE
d3d10_texture1d_GetEvictionPriority(ID3D10Texture1D
*iface
)
337 FIXME("iface %p stub!\n", iface
);
342 /* ID3D10Texture1D methods */
344 static HRESULT STDMETHODCALLTYPE
d3d10_texture1d_Map(ID3D10Texture1D
*iface
, UINT sub_resource_idx
,
345 D3D10_MAP map_type
, UINT map_flags
, void **data
)
347 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
348 struct wined3d_map_desc wined3d_map_desc
;
351 TRACE("iface %p, sub_resource_idx %u, map_type %u, map_flags %#x, data %p.\n",
352 iface
, sub_resource_idx
, map_type
, map_flags
, data
);
355 FIXME("Ignoring map_flags %#x.\n", map_flags
);
357 wined3d_mutex_lock();
358 if (SUCCEEDED(hr
= wined3d_resource_map(wined3d_texture_get_resource(texture
->wined3d_texture
), sub_resource_idx
,
359 &wined3d_map_desc
, NULL
, wined3d_map_flags_from_d3d10_map_type(map_type
))))
361 *data
= wined3d_map_desc
.data
;
363 wined3d_mutex_unlock();
368 static void STDMETHODCALLTYPE
d3d10_texture1d_Unmap(ID3D10Texture1D
*iface
, UINT sub_resource_idx
)
370 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
372 TRACE("iface %p, sub_resource_idx %u.\n", iface
, sub_resource_idx
);
374 wined3d_mutex_lock();
375 wined3d_resource_unmap(wined3d_texture_get_resource(texture
->wined3d_texture
), sub_resource_idx
);
376 wined3d_mutex_unlock();
379 static void STDMETHODCALLTYPE
d3d10_texture1d_GetDesc(ID3D10Texture1D
*iface
, D3D10_TEXTURE1D_DESC
*desc
)
381 struct d3d_texture1d
*texture
= impl_from_ID3D10Texture1D(iface
);
382 D3D11_TEXTURE1D_DESC d3d11_desc
;
384 TRACE("iface %p, desc %p.\n", iface
, desc
);
386 d3d11_texture1d_GetDesc(&texture
->ID3D11Texture1D_iface
, &d3d11_desc
);
388 desc
->Width
= d3d11_desc
.Width
;
389 desc
->MipLevels
= d3d11_desc
.MipLevels
;
390 desc
->ArraySize
= d3d11_desc
.ArraySize
;
391 desc
->Format
= d3d11_desc
.Format
;
392 desc
->Usage
= d3d10_usage_from_d3d11_usage(d3d11_desc
.Usage
);
393 desc
->BindFlags
= d3d10_bind_flags_from_d3d11_bind_flags(d3d11_desc
.BindFlags
);
394 desc
->CPUAccessFlags
= d3d10_cpu_access_flags_from_d3d11_cpu_access_flags(d3d11_desc
.CPUAccessFlags
);
395 desc
->MiscFlags
= d3d10_resource_misc_flags_from_d3d11_resource_misc_flags(d3d11_desc
.MiscFlags
);
398 static const struct ID3D10Texture1DVtbl d3d10_texture1d_vtbl
=
400 /* IUnknown methods */
401 d3d10_texture1d_QueryInterface
,
402 d3d10_texture1d_AddRef
,
403 d3d10_texture1d_Release
,
404 /* ID3D10DeviceChild methods */
405 d3d10_texture1d_GetDevice
,
406 d3d10_texture1d_GetPrivateData
,
407 d3d10_texture1d_SetPrivateData
,
408 d3d10_texture1d_SetPrivateDataInterface
,
409 /* ID3D10Resource methods */
410 d3d10_texture1d_GetType
,
411 d3d10_texture1d_SetEvictionPriority
,
412 d3d10_texture1d_GetEvictionPriority
,
413 /* ID3D10Texture1D methods */
415 d3d10_texture1d_Unmap
,
416 d3d10_texture1d_GetDesc
,
419 struct d3d_texture1d
*unsafe_impl_from_ID3D10Texture1D(ID3D10Texture1D
*iface
)
423 assert(iface
->lpVtbl
== &d3d10_texture1d_vtbl
);
424 return CONTAINING_RECORD(iface
, struct d3d_texture1d
, ID3D10Texture1D_iface
);
427 static const struct wined3d_parent_ops d3d_texture1d_wined3d_parent_ops
=
429 d3d_texture1d_wined3d_object_released
,
432 HRESULT
d3d_texture1d_create(struct d3d_device
*device
, const D3D11_TEXTURE1D_DESC
*desc
,
433 const D3D11_SUBRESOURCE_DATA
*data
, struct d3d_texture1d
**out
)
435 struct wined3d_resource_desc wined3d_desc
;
436 struct d3d_texture1d
*texture
;
441 if (!(texture
= heap_alloc_zero(sizeof(*texture
))))
442 return E_OUTOFMEMORY
;
444 texture
->ID3D11Texture1D_iface
.lpVtbl
= &d3d11_texture1d_vtbl
;
445 texture
->ID3D10Texture1D_iface
.lpVtbl
= &d3d10_texture1d_vtbl
;
446 texture
->refcount
= 1;
447 wined3d_private_store_init(&texture
->private_store
);
448 texture
->desc
= *desc
;
449 levels
= desc
->MipLevels
? desc
->MipLevels
: wined3d_log2i(desc
->Width
) + 1;
450 texture
->desc
.MipLevels
= levels
;
452 wined3d_desc
.resource_type
= WINED3D_RTYPE_TEXTURE_1D
;
453 wined3d_desc
.format
= wined3dformat_from_dxgi_format(desc
->Format
);
454 wined3d_desc
.multisample_type
= WINED3D_MULTISAMPLE_NONE
;
455 wined3d_desc
.multisample_quality
= 0;
456 wined3d_desc
.usage
= wined3d_usage_from_d3d11(desc
->Usage
);
457 wined3d_desc
.bind_flags
= wined3d_bind_flags_from_d3d11(desc
->BindFlags
, desc
->MiscFlags
);
458 wined3d_desc
.access
= wined3d_access_from_d3d11(desc
->Usage
,
459 desc
->Usage
== D3D11_USAGE_DEFAULT
? 0 : desc
->CPUAccessFlags
);
460 wined3d_desc
.width
= desc
->Width
;
461 wined3d_desc
.height
= 1;
462 wined3d_desc
.depth
= 1;
463 wined3d_desc
.size
= 0;
465 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GDI_COMPATIBLE
)
466 flags
|= WINED3D_TEXTURE_CREATE_GET_DC
;
467 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GENERATE_MIPS
)
468 flags
|= WINED3D_TEXTURE_CREATE_GENERATE_MIPMAPS
;
470 wined3d_mutex_lock();
471 if (FAILED(hr
= wined3d_texture_create(device
->wined3d_device
, &wined3d_desc
,
472 desc
->ArraySize
, levels
, flags
, (struct wined3d_sub_resource_data
*)data
,
473 texture
, &d3d_texture1d_wined3d_parent_ops
, &texture
->wined3d_texture
)))
475 WARN("Failed to create wined3d texture, hr %#x.\n", hr
);
476 wined3d_private_store_cleanup(&texture
->private_store
);
478 wined3d_mutex_unlock();
479 if (hr
== WINED3DERR_NOTAVAILABLE
|| hr
== WINED3DERR_INVALIDCALL
)
484 if (desc
->MipLevels
== 1 && desc
->ArraySize
== 1)
486 IWineDXGIDevice
*wine_device
;
488 if (FAILED(hr
= ID3D10Device1_QueryInterface(&device
->ID3D10Device1_iface
, &IID_IWineDXGIDevice
,
489 (void **)&wine_device
)))
491 ERR("Device should implement IWineDXGIDevice.\n");
492 wined3d_texture_decref(texture
->wined3d_texture
);
493 wined3d_mutex_unlock();
497 hr
= IWineDXGIDevice_create_surface(wine_device
, texture
->wined3d_texture
, 0, NULL
,
498 (IUnknown
*)&texture
->ID3D10Texture1D_iface
, (void **)&texture
->dxgi_surface
);
499 IWineDXGIDevice_Release(wine_device
);
502 ERR("Failed to create DXGI surface, returning %#.x\n", hr
);
503 texture
->dxgi_surface
= NULL
;
504 wined3d_texture_decref(texture
->wined3d_texture
);
505 wined3d_mutex_unlock();
509 wined3d_mutex_unlock();
511 ID3D11Device2_AddRef(texture
->device
= &device
->ID3D11Device2_iface
);
513 TRACE("Created texture %p.\n", texture
);
519 /* ID3D11Texture2D methods */
521 static HRESULT STDMETHODCALLTYPE
d3d11_texture2d_QueryInterface(ID3D11Texture2D
*iface
, REFIID riid
, void **object
)
523 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
525 TRACE("iface %p, riid %s, object %p.\n", iface
, debugstr_guid(riid
), object
);
527 if (IsEqualGUID(riid
, &IID_ID3D11Texture2D
)
528 || IsEqualGUID(riid
, &IID_ID3D11Resource
)
529 || IsEqualGUID(riid
, &IID_ID3D11DeviceChild
)
530 || IsEqualGUID(riid
, &IID_IUnknown
))
532 *object
= &texture
->ID3D11Texture2D_iface
;
533 IUnknown_AddRef((IUnknown
*)*object
);
536 else if (IsEqualGUID(riid
, &IID_ID3D10Texture2D
)
537 || IsEqualGUID(riid
, &IID_ID3D10Resource
)
538 || IsEqualGUID(riid
, &IID_ID3D10DeviceChild
))
540 *object
= &texture
->ID3D10Texture2D_iface
;
541 IUnknown_AddRef((IUnknown
*)*object
);
545 if (texture
->dxgi_surface
)
547 TRACE("Forwarding to dxgi surface.\n");
548 return IUnknown_QueryInterface(texture
->dxgi_surface
, riid
, object
);
551 WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid
));
554 return E_NOINTERFACE
;
557 static ULONG STDMETHODCALLTYPE
d3d11_texture2d_AddRef(ID3D11Texture2D
*iface
)
559 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
560 ULONG refcount
= InterlockedIncrement(&texture
->refcount
);
562 TRACE("%p increasing refcount to %u.\n", texture
, refcount
);
566 ID3D11Device2_AddRef(texture
->device
);
567 wined3d_mutex_lock();
568 wined3d_texture_incref(texture
->wined3d_texture
);
569 wined3d_mutex_unlock();
575 static ULONG STDMETHODCALLTYPE
d3d11_texture2d_Release(ID3D11Texture2D
*iface
)
577 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
578 ULONG refcount
= InterlockedDecrement(&texture
->refcount
);
580 TRACE("%p decreasing refcount to %u.\n", texture
, refcount
);
584 ID3D11Device2
*device
= texture
->device
;
586 wined3d_mutex_lock();
587 wined3d_texture_decref(texture
->wined3d_texture
);
588 wined3d_mutex_unlock();
589 /* Release the device last, it may cause the wined3d device to be
591 ID3D11Device2_Release(device
);
597 static void STDMETHODCALLTYPE
d3d11_texture2d_GetDevice(ID3D11Texture2D
*iface
, ID3D11Device
**device
)
599 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
601 TRACE("iface %p, device %p.\n", iface
, device
);
603 *device
= (ID3D11Device
*)texture
->device
;
604 ID3D11Device_AddRef(*device
);
607 static HRESULT STDMETHODCALLTYPE
d3d11_texture2d_GetPrivateData(ID3D11Texture2D
*iface
,
608 REFGUID guid
, UINT
*data_size
, void *data
)
610 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
611 IDXGISurface
*dxgi_surface
;
614 TRACE("iface %p, guid %s, data_size %p, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
616 if (texture
->dxgi_surface
617 && SUCCEEDED(IUnknown_QueryInterface(texture
->dxgi_surface
, &IID_IDXGISurface
, (void **)&dxgi_surface
)))
619 hr
= IDXGISurface_GetPrivateData(dxgi_surface
, guid
, data_size
, data
);
620 IDXGISurface_Release(dxgi_surface
);
624 return d3d_get_private_data(&texture
->private_store
, guid
, data_size
, data
);
627 static HRESULT STDMETHODCALLTYPE
d3d11_texture2d_SetPrivateData(ID3D11Texture2D
*iface
,
628 REFGUID guid
, UINT data_size
, const void *data
)
630 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
631 IDXGISurface
*dxgi_surface
;
634 TRACE("iface %p, guid %s, data_size %u, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
636 if (texture
->dxgi_surface
637 && SUCCEEDED(IUnknown_QueryInterface(texture
->dxgi_surface
, &IID_IDXGISurface
, (void **)&dxgi_surface
)))
639 hr
= IDXGISurface_SetPrivateData(dxgi_surface
, guid
, data_size
, data
);
640 IDXGISurface_Release(dxgi_surface
);
644 return d3d_set_private_data(&texture
->private_store
, guid
, data_size
, data
);
647 static HRESULT STDMETHODCALLTYPE
d3d11_texture2d_SetPrivateDataInterface(ID3D11Texture2D
*iface
,
648 REFGUID guid
, const IUnknown
*data
)
650 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
651 IDXGISurface
*dxgi_surface
;
654 TRACE("iface %p, guid %s, data %p.\n", iface
, debugstr_guid(guid
), data
);
656 if (texture
->dxgi_surface
657 && SUCCEEDED(IUnknown_QueryInterface(texture
->dxgi_surface
, &IID_IDXGISurface
, (void **)&dxgi_surface
)))
659 hr
= IDXGISurface_SetPrivateDataInterface(dxgi_surface
, guid
, data
);
660 IDXGISurface_Release(dxgi_surface
);
664 return d3d_set_private_data_interface(&texture
->private_store
, guid
, data
);
667 static void STDMETHODCALLTYPE
d3d11_texture2d_GetType(ID3D11Texture2D
*iface
,
668 D3D11_RESOURCE_DIMENSION
*resource_dimension
)
670 TRACE("iface %p, resource_dimension %p.\n", iface
, resource_dimension
);
672 *resource_dimension
= D3D11_RESOURCE_DIMENSION_TEXTURE2D
;
675 static void STDMETHODCALLTYPE
d3d11_texture2d_SetEvictionPriority(ID3D11Texture2D
*iface
, UINT eviction_priority
)
677 FIXME("iface %p, eviction_priority %#x stub!\n", iface
, eviction_priority
);
680 static UINT STDMETHODCALLTYPE
d3d11_texture2d_GetEvictionPriority(ID3D11Texture2D
*iface
)
682 FIXME("iface %p stub!\n", iface
);
687 static void STDMETHODCALLTYPE
d3d11_texture2d_GetDesc(ID3D11Texture2D
*iface
, D3D11_TEXTURE2D_DESC
*desc
)
689 struct d3d_texture2d
*texture
= impl_from_ID3D11Texture2D(iface
);
690 struct wined3d_resource_desc wined3d_desc
;
692 TRACE("iface %p, desc %p.\n", iface
, desc
);
694 *desc
= texture
->desc
;
696 wined3d_mutex_lock();
697 wined3d_resource_get_desc(wined3d_texture_get_resource(texture
->wined3d_texture
), &wined3d_desc
);
698 wined3d_mutex_unlock();
700 /* FIXME: Resizing swapchain buffers can cause these to change. We'd like
701 * to get everything from wined3d, but e.g. bind flags don't exist as such
703 desc
->Width
= wined3d_desc
.width
;
704 desc
->Height
= wined3d_desc
.height
;
705 desc
->Format
= dxgi_format_from_wined3dformat(wined3d_desc
.format
);
706 desc
->SampleDesc
.Count
= wined3d_desc
.multisample_type
== WINED3D_MULTISAMPLE_NONE
707 ? 1 : wined3d_desc
.multisample_type
;
708 desc
->SampleDesc
.Quality
= wined3d_desc
.multisample_quality
;
711 static const struct ID3D11Texture2DVtbl d3d11_texture2d_vtbl
=
713 /* IUnknown methods */
714 d3d11_texture2d_QueryInterface
,
715 d3d11_texture2d_AddRef
,
716 d3d11_texture2d_Release
,
717 /* ID3D11DeviceChild methods */
718 d3d11_texture2d_GetDevice
,
719 d3d11_texture2d_GetPrivateData
,
720 d3d11_texture2d_SetPrivateData
,
721 d3d11_texture2d_SetPrivateDataInterface
,
722 /* ID3D11Resource methods */
723 d3d11_texture2d_GetType
,
724 d3d11_texture2d_SetEvictionPriority
,
725 d3d11_texture2d_GetEvictionPriority
,
726 /* ID3D11Texture2D methods */
727 d3d11_texture2d_GetDesc
,
730 struct d3d_texture2d
*unsafe_impl_from_ID3D11Texture2D(ID3D11Texture2D
*iface
)
734 assert(iface
->lpVtbl
== &d3d11_texture2d_vtbl
);
735 return CONTAINING_RECORD(iface
, struct d3d_texture2d
, ID3D11Texture2D_iface
);
738 /* IUnknown methods */
740 static inline struct d3d_texture2d
*impl_from_ID3D10Texture2D(ID3D10Texture2D
*iface
)
742 return CONTAINING_RECORD(iface
, struct d3d_texture2d
, ID3D10Texture2D_iface
);
745 static HRESULT STDMETHODCALLTYPE
d3d10_texture2d_QueryInterface(ID3D10Texture2D
*iface
, REFIID riid
, void **object
)
747 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
749 TRACE("iface %p, riid %s, object %p.\n", iface
, debugstr_guid(riid
), object
);
751 return d3d11_texture2d_QueryInterface(&texture
->ID3D11Texture2D_iface
, riid
, object
);
754 static ULONG STDMETHODCALLTYPE
d3d10_texture2d_AddRef(ID3D10Texture2D
*iface
)
756 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
758 TRACE("iface %p.\n", iface
);
760 return d3d11_texture2d_AddRef(&texture
->ID3D11Texture2D_iface
);
763 static void STDMETHODCALLTYPE
d3d_texture2d_wined3d_object_released(void *parent
)
765 struct d3d_texture2d
*texture
= parent
;
767 if (texture
->dxgi_surface
) IUnknown_Release(texture
->dxgi_surface
);
768 wined3d_private_store_cleanup(&texture
->private_store
);
772 static ULONG STDMETHODCALLTYPE
d3d10_texture2d_Release(ID3D10Texture2D
*iface
)
774 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
776 TRACE("iface %p.\n", iface
);
778 return d3d11_texture2d_Release(&texture
->ID3D11Texture2D_iface
);
781 /* ID3D10DeviceChild methods */
783 static void STDMETHODCALLTYPE
d3d10_texture2d_GetDevice(ID3D10Texture2D
*iface
, ID3D10Device
**device
)
785 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
787 TRACE("iface %p, device %p.\n", iface
, device
);
789 ID3D11Device2_QueryInterface(texture
->device
, &IID_ID3D10Device
, (void **)device
);
792 static HRESULT STDMETHODCALLTYPE
d3d10_texture2d_GetPrivateData(ID3D10Texture2D
*iface
,
793 REFGUID guid
, UINT
*data_size
, void *data
)
795 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
797 TRACE("iface %p, guid %s, data_size %p, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
799 return d3d11_texture2d_GetPrivateData(&texture
->ID3D11Texture2D_iface
, guid
, data_size
, data
);
802 static HRESULT STDMETHODCALLTYPE
d3d10_texture2d_SetPrivateData(ID3D10Texture2D
*iface
,
803 REFGUID guid
, UINT data_size
, const void *data
)
805 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
807 TRACE("iface %p, guid %s, data_size %u, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
809 return d3d11_texture2d_SetPrivateData(&texture
->ID3D11Texture2D_iface
, guid
, data_size
, data
);
812 static HRESULT STDMETHODCALLTYPE
d3d10_texture2d_SetPrivateDataInterface(ID3D10Texture2D
*iface
,
813 REFGUID guid
, const IUnknown
*data
)
815 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
817 TRACE("iface %p, guid %s, data %p.\n", iface
, debugstr_guid(guid
), data
);
819 return d3d11_texture2d_SetPrivateDataInterface(&texture
->ID3D11Texture2D_iface
, guid
, data
);
822 /* ID3D10Resource methods */
824 static void STDMETHODCALLTYPE
d3d10_texture2d_GetType(ID3D10Texture2D
*iface
,
825 D3D10_RESOURCE_DIMENSION
*resource_dimension
)
827 TRACE("iface %p, resource_dimension %p\n", iface
, resource_dimension
);
829 *resource_dimension
= D3D10_RESOURCE_DIMENSION_TEXTURE2D
;
832 static void STDMETHODCALLTYPE
d3d10_texture2d_SetEvictionPriority(ID3D10Texture2D
*iface
, UINT eviction_priority
)
834 FIXME("iface %p, eviction_priority %u stub!\n", iface
, eviction_priority
);
837 static UINT STDMETHODCALLTYPE
d3d10_texture2d_GetEvictionPriority(ID3D10Texture2D
*iface
)
839 FIXME("iface %p stub!\n", iface
);
844 /* ID3D10Texture2D methods */
846 static HRESULT STDMETHODCALLTYPE
d3d10_texture2d_Map(ID3D10Texture2D
*iface
, UINT sub_resource_idx
,
847 D3D10_MAP map_type
, UINT map_flags
, D3D10_MAPPED_TEXTURE2D
*mapped_texture
)
849 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
850 struct wined3d_map_desc wined3d_map_desc
;
853 TRACE("iface %p, sub_resource_idx %u, map_type %u, map_flags %#x, mapped_texture %p.\n",
854 iface
, sub_resource_idx
, map_type
, map_flags
, mapped_texture
);
857 FIXME("Ignoring map_flags %#x.\n", map_flags
);
859 wined3d_mutex_lock();
860 if (SUCCEEDED(hr
= wined3d_resource_map(wined3d_texture_get_resource(texture
->wined3d_texture
), sub_resource_idx
,
861 &wined3d_map_desc
, NULL
, wined3d_map_flags_from_d3d10_map_type(map_type
))))
863 mapped_texture
->pData
= wined3d_map_desc
.data
;
864 mapped_texture
->RowPitch
= wined3d_map_desc
.row_pitch
;
866 wined3d_mutex_unlock();
871 static void STDMETHODCALLTYPE
d3d10_texture2d_Unmap(ID3D10Texture2D
*iface
, UINT sub_resource_idx
)
873 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
875 TRACE("iface %p, sub_resource_idx %u.\n", iface
, sub_resource_idx
);
877 wined3d_mutex_lock();
878 wined3d_resource_unmap(wined3d_texture_get_resource(texture
->wined3d_texture
), sub_resource_idx
);
879 wined3d_mutex_unlock();
882 static void STDMETHODCALLTYPE
d3d10_texture2d_GetDesc(ID3D10Texture2D
*iface
, D3D10_TEXTURE2D_DESC
*desc
)
884 struct d3d_texture2d
*texture
= impl_from_ID3D10Texture2D(iface
);
885 D3D11_TEXTURE2D_DESC d3d11_desc
;
887 TRACE("iface %p, desc %p\n", iface
, desc
);
889 d3d11_texture2d_GetDesc(&texture
->ID3D11Texture2D_iface
, &d3d11_desc
);
891 desc
->Width
= d3d11_desc
.Width
;
892 desc
->Height
= d3d11_desc
.Height
;
893 desc
->MipLevels
= d3d11_desc
.MipLevels
;
894 desc
->ArraySize
= d3d11_desc
.ArraySize
;
895 desc
->Format
= d3d11_desc
.Format
;
896 desc
->SampleDesc
= d3d11_desc
.SampleDesc
;
897 desc
->Usage
= d3d10_usage_from_d3d11_usage(d3d11_desc
.Usage
);
898 desc
->BindFlags
= d3d10_bind_flags_from_d3d11_bind_flags(d3d11_desc
.BindFlags
);
899 desc
->CPUAccessFlags
= d3d10_cpu_access_flags_from_d3d11_cpu_access_flags(d3d11_desc
.CPUAccessFlags
);
900 desc
->MiscFlags
= d3d10_resource_misc_flags_from_d3d11_resource_misc_flags(d3d11_desc
.MiscFlags
);
903 static const struct ID3D10Texture2DVtbl d3d10_texture2d_vtbl
=
905 /* IUnknown methods */
906 d3d10_texture2d_QueryInterface
,
907 d3d10_texture2d_AddRef
,
908 d3d10_texture2d_Release
,
909 /* ID3D10DeviceChild methods */
910 d3d10_texture2d_GetDevice
,
911 d3d10_texture2d_GetPrivateData
,
912 d3d10_texture2d_SetPrivateData
,
913 d3d10_texture2d_SetPrivateDataInterface
,
914 /* ID3D10Resource methods */
915 d3d10_texture2d_GetType
,
916 d3d10_texture2d_SetEvictionPriority
,
917 d3d10_texture2d_GetEvictionPriority
,
918 /* ID3D10Texture2D methods */
920 d3d10_texture2d_Unmap
,
921 d3d10_texture2d_GetDesc
,
924 struct d3d_texture2d
*unsafe_impl_from_ID3D10Texture2D(ID3D10Texture2D
*iface
)
928 assert(iface
->lpVtbl
== &d3d10_texture2d_vtbl
);
929 return CONTAINING_RECORD(iface
, struct d3d_texture2d
, ID3D10Texture2D_iface
);
932 static const struct wined3d_parent_ops d3d_texture2d_wined3d_parent_ops
=
934 d3d_texture2d_wined3d_object_released
,
937 static BOOL
is_gdi_compatible_texture(const D3D11_TEXTURE2D_DESC
*desc
)
939 if (!(desc
->Format
== DXGI_FORMAT_B8G8R8A8_UNORM
940 || desc
->Format
== DXGI_FORMAT_B8G8R8A8_TYPELESS
941 || desc
->Format
== DXGI_FORMAT_B8G8R8A8_UNORM_SRGB
))
944 if (desc
->Usage
!= D3D11_USAGE_DEFAULT
)
950 static BOOL
validate_texture2d_desc(const D3D11_TEXTURE2D_DESC
*desc
, D3D_FEATURE_LEVEL feature_level
)
952 if (!validate_d3d11_resource_access_flags(D3D11_RESOURCE_DIMENSION_TEXTURE2D
,
953 desc
->Usage
, desc
->BindFlags
, desc
->CPUAccessFlags
, feature_level
))
956 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_TEXTURECUBE
957 && desc
->ArraySize
< 6)
959 WARN("Invalid array size %u for cube texture.\n", desc
->ArraySize
);
963 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GDI_COMPATIBLE
964 && !is_gdi_compatible_texture(desc
))
966 WARN("Incompatible description used to create GDI compatible texture.\n");
970 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GENERATE_MIPS
971 && (~desc
->BindFlags
& (D3D11_BIND_RENDER_TARGET
| D3D11_BIND_SHADER_RESOURCE
)))
973 WARN("D3D11_RESOURCE_MISC_GENERATE_MIPS used without D3D11_BIND_RENDER_TARGET and "
974 "D3D11_BIND_SHADER_RESOURCE.\n");
981 HRESULT
d3d_texture2d_create(struct d3d_device
*device
, const D3D11_TEXTURE2D_DESC
*desc
,
982 const D3D11_SUBRESOURCE_DATA
*data
, struct d3d_texture2d
**out
)
984 struct wined3d_resource_desc wined3d_desc
;
985 struct d3d_texture2d
*texture
;
990 if (!validate_texture2d_desc(desc
, device
->state
->feature_level
))
992 WARN("Failed to validate texture desc.\n");
996 if (!(texture
= heap_alloc_zero(sizeof(*texture
))))
997 return E_OUTOFMEMORY
;
999 texture
->ID3D11Texture2D_iface
.lpVtbl
= &d3d11_texture2d_vtbl
;
1000 texture
->ID3D10Texture2D_iface
.lpVtbl
= &d3d10_texture2d_vtbl
;
1001 texture
->refcount
= 1;
1002 wined3d_mutex_lock();
1003 wined3d_private_store_init(&texture
->private_store
);
1004 texture
->desc
= *desc
;
1006 wined3d_desc
.resource_type
= WINED3D_RTYPE_TEXTURE_2D
;
1007 wined3d_desc
.format
= wined3dformat_from_dxgi_format(desc
->Format
);
1008 wined3d_desc
.multisample_type
= desc
->SampleDesc
.Count
> 1 ? desc
->SampleDesc
.Count
: WINED3D_MULTISAMPLE_NONE
;
1009 wined3d_desc
.multisample_quality
= desc
->SampleDesc
.Quality
;
1010 wined3d_desc
.usage
= wined3d_usage_from_d3d11(desc
->Usage
);
1011 wined3d_desc
.bind_flags
= wined3d_bind_flags_from_d3d11(desc
->BindFlags
, desc
->MiscFlags
);
1012 wined3d_desc
.access
= wined3d_access_from_d3d11(desc
->Usage
,
1013 desc
->Usage
== D3D11_USAGE_DEFAULT
? 0 : desc
->CPUAccessFlags
);
1014 wined3d_desc
.width
= desc
->Width
;
1015 wined3d_desc
.height
= desc
->Height
;
1016 wined3d_desc
.depth
= 1;
1017 wined3d_desc
.size
= 0;
1019 levels
= desc
->MipLevels
? desc
->MipLevels
: wined3d_log2i(max(desc
->Width
, desc
->Height
)) + 1;
1021 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GDI_COMPATIBLE
)
1022 flags
|= WINED3D_TEXTURE_CREATE_GET_DC
;
1023 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GENERATE_MIPS
)
1024 flags
|= WINED3D_TEXTURE_CREATE_GENERATE_MIPMAPS
;
1026 if (FAILED(hr
= wined3d_texture_create(device
->wined3d_device
, &wined3d_desc
,
1027 desc
->ArraySize
, levels
, flags
, (struct wined3d_sub_resource_data
*)data
,
1028 texture
, &d3d_texture2d_wined3d_parent_ops
, &texture
->wined3d_texture
)))
1030 WARN("Failed to create wined3d texture, hr %#x.\n", hr
);
1031 wined3d_private_store_cleanup(&texture
->private_store
);
1033 wined3d_mutex_unlock();
1034 if (hr
== WINED3DERR_NOTAVAILABLE
|| hr
== WINED3DERR_INVALIDCALL
)
1038 texture
->desc
.MipLevels
= levels
;
1040 if (desc
->MipLevels
== 1 && desc
->ArraySize
== 1)
1042 IWineDXGIDevice
*wine_device
;
1044 if (FAILED(hr
= ID3D10Device1_QueryInterface(&device
->ID3D10Device1_iface
, &IID_IWineDXGIDevice
,
1045 (void **)&wine_device
)))
1047 ERR("Device should implement IWineDXGIDevice.\n");
1048 wined3d_texture_decref(texture
->wined3d_texture
);
1049 wined3d_mutex_unlock();
1053 hr
= IWineDXGIDevice_create_surface(wine_device
, texture
->wined3d_texture
, 0, NULL
,
1054 (IUnknown
*)&texture
->ID3D10Texture2D_iface
, (void **)&texture
->dxgi_surface
);
1055 IWineDXGIDevice_Release(wine_device
);
1058 ERR("Failed to create DXGI surface, returning %#.x\n", hr
);
1059 texture
->dxgi_surface
= NULL
;
1060 wined3d_texture_decref(texture
->wined3d_texture
);
1061 wined3d_mutex_unlock();
1065 wined3d_mutex_unlock();
1067 ID3D11Device2_AddRef(texture
->device
= &device
->ID3D11Device2_iface
);
1069 TRACE("Created texture %p.\n", texture
);
1075 /* ID3D11Texture3D methods */
1077 static inline struct d3d_texture3d
*impl_from_ID3D11Texture3D(ID3D11Texture3D
*iface
)
1079 return CONTAINING_RECORD(iface
, struct d3d_texture3d
, ID3D11Texture3D_iface
);
1082 static HRESULT STDMETHODCALLTYPE
d3d11_texture3d_QueryInterface(ID3D11Texture3D
*iface
, REFIID riid
, void **object
)
1084 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1086 TRACE("iface %p, riid %s, object %p.\n", iface
, debugstr_guid(riid
), object
);
1088 if (IsEqualGUID(riid
, &IID_ID3D11Texture3D
)
1089 || IsEqualGUID(riid
, &IID_ID3D11Resource
)
1090 || IsEqualGUID(riid
, &IID_ID3D11DeviceChild
)
1091 || IsEqualGUID(riid
, &IID_IUnknown
))
1093 IUnknown_AddRef(iface
);
1097 else if (IsEqualGUID(riid
, &IID_ID3D10Texture3D
)
1098 || IsEqualGUID(riid
, &IID_ID3D10Resource
)
1099 || IsEqualGUID(riid
, &IID_ID3D10DeviceChild
))
1101 IUnknown_AddRef(iface
);
1102 *object
= &texture
->ID3D10Texture3D_iface
;
1106 WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid
));
1109 return E_NOINTERFACE
;
1112 static ULONG STDMETHODCALLTYPE
d3d11_texture3d_AddRef(ID3D11Texture3D
*iface
)
1114 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1115 ULONG refcount
= InterlockedIncrement(&texture
->refcount
);
1117 TRACE("%p increasing refcount to %u.\n", texture
, refcount
);
1121 ID3D11Device2_AddRef(texture
->device
);
1122 wined3d_mutex_lock();
1123 wined3d_texture_incref(texture
->wined3d_texture
);
1124 wined3d_mutex_unlock();
1130 static void STDMETHODCALLTYPE
d3d_texture3d_wined3d_object_released(void *parent
)
1132 struct d3d_texture3d
*texture
= parent
;
1134 wined3d_private_store_cleanup(&texture
->private_store
);
1138 static ULONG STDMETHODCALLTYPE
d3d11_texture3d_Release(ID3D11Texture3D
*iface
)
1140 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1141 ULONG refcount
= InterlockedDecrement(&texture
->refcount
);
1143 TRACE("%p decreasing refcount to %u.\n", texture
, refcount
);
1147 ID3D11Device2
*device
= texture
->device
;
1149 wined3d_mutex_lock();
1150 wined3d_texture_decref(texture
->wined3d_texture
);
1151 wined3d_mutex_unlock();
1152 /* Release the device last, it may cause the wined3d device to be
1154 ID3D11Device2_Release(device
);
1160 static void STDMETHODCALLTYPE
d3d11_texture3d_GetDevice(ID3D11Texture3D
*iface
, ID3D11Device
**device
)
1162 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1164 TRACE("iface %p, device %p.\n", iface
, device
);
1166 *device
= (ID3D11Device
*)texture
->device
;
1167 ID3D11Device_AddRef(*device
);
1170 static HRESULT STDMETHODCALLTYPE
d3d11_texture3d_GetPrivateData(ID3D11Texture3D
*iface
,
1171 REFGUID guid
, UINT
*data_size
, void *data
)
1173 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1175 TRACE("iface %p, guid %s, data_size %p, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
1177 return d3d_get_private_data(&texture
->private_store
, guid
, data_size
, data
);
1180 static HRESULT STDMETHODCALLTYPE
d3d11_texture3d_SetPrivateData(ID3D11Texture3D
*iface
,
1181 REFGUID guid
, UINT data_size
, const void *data
)
1183 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1185 TRACE("iface %p, guid %s, data_size %u, data %p.\n", iface
, debugstr_guid(guid
), data_size
, data
);
1187 return d3d_set_private_data(&texture
->private_store
, guid
, data_size
, data
);
1190 static HRESULT STDMETHODCALLTYPE
d3d11_texture3d_SetPrivateDataInterface(ID3D11Texture3D
*iface
,
1191 REFGUID guid
, const IUnknown
*data
)
1193 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1195 TRACE("iface %p, guid %s, data %p.\n", iface
, debugstr_guid(guid
), data
);
1197 return d3d_set_private_data_interface(&texture
->private_store
, guid
, data
);
1200 static void STDMETHODCALLTYPE
d3d11_texture3d_GetType(ID3D11Texture3D
*iface
,
1201 D3D11_RESOURCE_DIMENSION
*resource_dimension
)
1203 TRACE("iface %p, resource_dimension %p.\n", iface
, resource_dimension
);
1205 *resource_dimension
= D3D11_RESOURCE_DIMENSION_TEXTURE3D
;
1208 static void STDMETHODCALLTYPE
d3d11_texture3d_SetEvictionPriority(ID3D11Texture3D
*iface
, UINT eviction_priority
)
1210 FIXME("iface %p, eviction_priority %#x stub!\n", iface
, eviction_priority
);
1213 static UINT STDMETHODCALLTYPE
d3d11_texture3d_GetEvictionPriority(ID3D11Texture3D
*iface
)
1215 FIXME("iface %p stub!\n", iface
);
1220 static void STDMETHODCALLTYPE
d3d11_texture3d_GetDesc(ID3D11Texture3D
*iface
, D3D11_TEXTURE3D_DESC
*desc
)
1222 struct d3d_texture3d
*texture
= impl_from_ID3D11Texture3D(iface
);
1224 TRACE("iface %p, desc %p.\n", iface
, desc
);
1226 *desc
= texture
->desc
;
1229 static const struct ID3D11Texture3DVtbl d3d11_texture3d_vtbl
=
1231 /* IUnknown methods */
1232 d3d11_texture3d_QueryInterface
,
1233 d3d11_texture3d_AddRef
,
1234 d3d11_texture3d_Release
,
1235 /* ID3D11DeviceChild methods */
1236 d3d11_texture3d_GetDevice
,
1237 d3d11_texture3d_GetPrivateData
,
1238 d3d11_texture3d_SetPrivateData
,
1239 d3d11_texture3d_SetPrivateDataInterface
,
1240 /* ID3D11Resource methods */
1241 d3d11_texture3d_GetType
,
1242 d3d11_texture3d_SetEvictionPriority
,
1243 d3d11_texture3d_GetEvictionPriority
,
1244 /* ID3D11Texture3D methods */
1245 d3d11_texture3d_GetDesc
,
1248 /* ID3D10Texture3D methods */
1250 static inline struct d3d_texture3d
*impl_from_ID3D10Texture3D(ID3D10Texture3D
*iface
)
1252 return CONTAINING_RECORD(iface
, struct d3d_texture3d
, ID3D10Texture3D_iface
);
1255 static HRESULT STDMETHODCALLTYPE
d3d10_texture3d_QueryInterface(ID3D10Texture3D
*iface
, REFIID riid
, void **object
)
1257 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1259 TRACE("iface %p, riid %s, object %p.\n", iface
, debugstr_guid(riid
), object
);
1261 return d3d11_texture3d_QueryInterface(&texture
->ID3D11Texture3D_iface
, riid
, object
);
1264 static ULONG STDMETHODCALLTYPE
d3d10_texture3d_AddRef(ID3D10Texture3D
*iface
)
1266 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1268 TRACE("iface %p.\n", iface
);
1270 return d3d11_texture3d_AddRef(&texture
->ID3D11Texture3D_iface
);
1273 static ULONG STDMETHODCALLTYPE
d3d10_texture3d_Release(ID3D10Texture3D
*iface
)
1275 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1277 TRACE("iface %p.\n", iface
);
1279 return d3d11_texture3d_Release(&texture
->ID3D11Texture3D_iface
);
1282 static void STDMETHODCALLTYPE
d3d10_texture3d_GetDevice(ID3D10Texture3D
*iface
, ID3D10Device
**device
)
1284 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1286 TRACE("iface %p, device %p.\n", iface
, device
);
1288 ID3D11Device2_QueryInterface(texture
->device
, &IID_ID3D10Device
, (void **)device
);
1291 static HRESULT STDMETHODCALLTYPE
d3d10_texture3d_GetPrivateData(ID3D10Texture3D
*iface
,
1292 REFGUID guid
, UINT
*data_size
, void *data
)
1294 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1296 TRACE("iface %p, guid %s, data_size %p, data %p.\n",
1297 iface
, debugstr_guid(guid
), data_size
, data
);
1299 return d3d_get_private_data(&texture
->private_store
, guid
, data_size
, data
);
1302 static HRESULT STDMETHODCALLTYPE
d3d10_texture3d_SetPrivateData(ID3D10Texture3D
*iface
,
1303 REFGUID guid
, UINT data_size
, const void *data
)
1305 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1307 TRACE("iface %p, guid %s, data_size %u, data %p.\n",
1308 iface
, debugstr_guid(guid
), data_size
, data
);
1310 return d3d_set_private_data(&texture
->private_store
, guid
, data_size
, data
);
1313 static HRESULT STDMETHODCALLTYPE
d3d10_texture3d_SetPrivateDataInterface(ID3D10Texture3D
*iface
,
1314 REFGUID guid
, const IUnknown
*data
)
1316 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1318 TRACE("iface %p, guid %s, data %p.\n", iface
, debugstr_guid(guid
), data
);
1320 return d3d_set_private_data_interface(&texture
->private_store
, guid
, data
);
1323 static void STDMETHODCALLTYPE
d3d10_texture3d_GetType(ID3D10Texture3D
*iface
,
1324 D3D10_RESOURCE_DIMENSION
*resource_dimension
)
1326 TRACE("iface %p, resource_dimension %p.\n", iface
, resource_dimension
);
1328 *resource_dimension
= D3D10_RESOURCE_DIMENSION_TEXTURE3D
;
1331 static void STDMETHODCALLTYPE
d3d10_texture3d_SetEvictionPriority(ID3D10Texture3D
*iface
, UINT eviction_priority
)
1333 FIXME("iface %p, eviction_priority %u stub!\n", iface
, eviction_priority
);
1336 static UINT STDMETHODCALLTYPE
d3d10_texture3d_GetEvictionPriority(ID3D10Texture3D
*iface
)
1338 FIXME("iface %p stub!\n", iface
);
1343 static HRESULT STDMETHODCALLTYPE
d3d10_texture3d_Map(ID3D10Texture3D
*iface
, UINT sub_resource_idx
,
1344 D3D10_MAP map_type
, UINT map_flags
, D3D10_MAPPED_TEXTURE3D
*mapped_texture
)
1346 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1347 struct wined3d_map_desc wined3d_map_desc
;
1350 TRACE("iface %p, sub_resource_idx %u, map_type %u, map_flags %#x, mapped_texture %p.\n",
1351 iface
, sub_resource_idx
, map_type
, map_flags
, mapped_texture
);
1354 FIXME("Ignoring map_flags %#x.\n", map_flags
);
1356 wined3d_mutex_lock();
1357 if (SUCCEEDED(hr
= wined3d_resource_map(wined3d_texture_get_resource(texture
->wined3d_texture
), sub_resource_idx
,
1358 &wined3d_map_desc
, NULL
, wined3d_map_flags_from_d3d10_map_type(map_type
))))
1360 mapped_texture
->pData
= wined3d_map_desc
.data
;
1361 mapped_texture
->RowPitch
= wined3d_map_desc
.row_pitch
;
1362 mapped_texture
->DepthPitch
= wined3d_map_desc
.slice_pitch
;
1364 wined3d_mutex_unlock();
1369 static void STDMETHODCALLTYPE
d3d10_texture3d_Unmap(ID3D10Texture3D
*iface
, UINT sub_resource_idx
)
1371 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1373 TRACE("iface %p, sub_resource_idx %u.\n", iface
, sub_resource_idx
);
1375 wined3d_mutex_lock();
1376 wined3d_resource_unmap(wined3d_texture_get_resource(texture
->wined3d_texture
), sub_resource_idx
);
1377 wined3d_mutex_unlock();
1380 static void STDMETHODCALLTYPE
d3d10_texture3d_GetDesc(ID3D10Texture3D
*iface
, D3D10_TEXTURE3D_DESC
*desc
)
1382 struct d3d_texture3d
*texture
= impl_from_ID3D10Texture3D(iface
);
1383 D3D11_TEXTURE3D_DESC d3d11_desc
;
1385 TRACE("iface %p, desc %p.\n", iface
, desc
);
1387 d3d11_texture3d_GetDesc(&texture
->ID3D11Texture3D_iface
, &d3d11_desc
);
1389 desc
->Width
= d3d11_desc
.Width
;
1390 desc
->Height
= d3d11_desc
.Height
;
1391 desc
->Depth
= d3d11_desc
.Depth
;
1392 desc
->MipLevels
= d3d11_desc
.MipLevels
;
1393 desc
->Format
= d3d11_desc
.Format
;
1394 desc
->Usage
= d3d10_usage_from_d3d11_usage(d3d11_desc
.Usage
);
1395 desc
->BindFlags
= d3d10_bind_flags_from_d3d11_bind_flags(d3d11_desc
.BindFlags
);
1396 desc
->CPUAccessFlags
= d3d10_cpu_access_flags_from_d3d11_cpu_access_flags(d3d11_desc
.CPUAccessFlags
);
1397 desc
->MiscFlags
= d3d10_resource_misc_flags_from_d3d11_resource_misc_flags(d3d11_desc
.MiscFlags
);
1400 static const struct ID3D10Texture3DVtbl d3d10_texture3d_vtbl
=
1402 /* IUnknown methods */
1403 d3d10_texture3d_QueryInterface
,
1404 d3d10_texture3d_AddRef
,
1405 d3d10_texture3d_Release
,
1406 /* ID3D10DeviceChild methods */
1407 d3d10_texture3d_GetDevice
,
1408 d3d10_texture3d_GetPrivateData
,
1409 d3d10_texture3d_SetPrivateData
,
1410 d3d10_texture3d_SetPrivateDataInterface
,
1411 /* ID3D10Resource methods */
1412 d3d10_texture3d_GetType
,
1413 d3d10_texture3d_SetEvictionPriority
,
1414 d3d10_texture3d_GetEvictionPriority
,
1415 /* ID3D10Texture3D methods */
1416 d3d10_texture3d_Map
,
1417 d3d10_texture3d_Unmap
,
1418 d3d10_texture3d_GetDesc
,
1421 struct d3d_texture3d
*unsafe_impl_from_ID3D10Texture3D(ID3D10Texture3D
*iface
)
1425 assert(iface
->lpVtbl
== &d3d10_texture3d_vtbl
);
1426 return CONTAINING_RECORD(iface
, struct d3d_texture3d
, ID3D10Texture3D_iface
);
1429 struct d3d_texture3d
*unsafe_impl_from_ID3D11Texture3D(ID3D11Texture3D
*iface
)
1433 assert(iface
->lpVtbl
== &d3d11_texture3d_vtbl
);
1434 return impl_from_ID3D11Texture3D(iface
);
1437 static const struct wined3d_parent_ops d3d_texture3d_wined3d_parent_ops
=
1439 d3d_texture3d_wined3d_object_released
,
1442 static HRESULT
d3d_texture3d_init(struct d3d_texture3d
*texture
, struct d3d_device
*device
,
1443 const D3D11_TEXTURE3D_DESC
*desc
, const D3D11_SUBRESOURCE_DATA
*data
)
1445 struct wined3d_resource_desc wined3d_desc
;
1446 unsigned int levels
;
1450 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GENERATE_MIPS
1451 && (~desc
->BindFlags
& (D3D11_BIND_RENDER_TARGET
| D3D11_BIND_SHADER_RESOURCE
)))
1453 WARN("D3D11_RESOURCE_MISC_GENERATE_MIPS used without D3D11_BIND_RENDER_TARGET "
1454 "and D3D11_BIND_SHADER_RESOURCE.\n");
1455 return E_INVALIDARG
;
1458 texture
->ID3D11Texture3D_iface
.lpVtbl
= &d3d11_texture3d_vtbl
;
1459 texture
->ID3D10Texture3D_iface
.lpVtbl
= &d3d10_texture3d_vtbl
;
1460 texture
->refcount
= 1;
1461 wined3d_mutex_lock();
1462 wined3d_private_store_init(&texture
->private_store
);
1463 texture
->desc
= *desc
;
1465 wined3d_desc
.resource_type
= WINED3D_RTYPE_TEXTURE_3D
;
1466 wined3d_desc
.format
= wined3dformat_from_dxgi_format(desc
->Format
);
1467 wined3d_desc
.multisample_type
= WINED3D_MULTISAMPLE_NONE
;
1468 wined3d_desc
.multisample_quality
= 0;
1469 wined3d_desc
.usage
= wined3d_usage_from_d3d11(desc
->Usage
);
1470 wined3d_desc
.bind_flags
= wined3d_bind_flags_from_d3d11(desc
->BindFlags
, desc
->MiscFlags
);
1471 wined3d_desc
.access
= wined3d_access_from_d3d11(desc
->Usage
,
1472 desc
->Usage
== D3D11_USAGE_DEFAULT
? 0 : desc
->CPUAccessFlags
);
1473 wined3d_desc
.width
= desc
->Width
;
1474 wined3d_desc
.height
= desc
->Height
;
1475 wined3d_desc
.depth
= desc
->Depth
;
1476 wined3d_desc
.size
= 0;
1478 levels
= desc
->MipLevels
? desc
->MipLevels
: wined3d_log2i(max(max(desc
->Width
, desc
->Height
), desc
->Depth
)) + 1;
1480 if (desc
->MiscFlags
& D3D11_RESOURCE_MISC_GENERATE_MIPS
)
1481 flags
|= WINED3D_TEXTURE_CREATE_GENERATE_MIPMAPS
;
1483 if (FAILED(hr
= wined3d_texture_create(device
->wined3d_device
, &wined3d_desc
,
1484 1, levels
, flags
, (struct wined3d_sub_resource_data
*)data
, texture
,
1485 &d3d_texture3d_wined3d_parent_ops
, &texture
->wined3d_texture
)))
1487 WARN("Failed to create wined3d texture, hr %#x.\n", hr
);
1488 wined3d_private_store_cleanup(&texture
->private_store
);
1489 wined3d_mutex_unlock();
1490 if (hr
== WINED3DERR_INVALIDCALL
)
1494 wined3d_mutex_unlock();
1495 texture
->desc
.MipLevels
= levels
;
1497 ID3D11Device2_AddRef(texture
->device
= &device
->ID3D11Device2_iface
);
1502 HRESULT
d3d_texture3d_create(struct d3d_device
*device
, const D3D11_TEXTURE3D_DESC
*desc
,
1503 const D3D11_SUBRESOURCE_DATA
*data
, struct d3d_texture3d
**texture
)
1505 struct d3d_texture3d
*object
;
1508 if (!(object
= heap_alloc_zero(sizeof(*object
))))
1509 return E_OUTOFMEMORY
;
1511 if (FAILED(hr
= d3d_texture3d_init(object
, device
, desc
, data
)))
1513 WARN("Failed to initialize texture, hr %#x.\n", hr
);
1518 TRACE("Created texture %p.\n", object
);