mirror of
				https://gitlab.winehq.org/wine/vkd3d.git
				synced 2025-09-12 18:50:22 -07:00 
			
		
		
		
	libs/vkd3d: Implement D3D12SerializeRootSignature().
This commit is contained in:
		| @@ -68,6 +68,7 @@ interface ID3D10Blob : IUnknown | |||||||
| } | } | ||||||
|  |  | ||||||
| typedef ID3D10Blob ID3DBlob; | typedef ID3D10Blob ID3DBlob; | ||||||
|  | cpp_quote("#define IID_ID3DBlob IID_ID3D10Blob") | ||||||
|  |  | ||||||
| typedef enum D3D_PRIMITIVE_TOPOLOGY | typedef enum D3D_PRIMITIVE_TOPOLOGY | ||||||
| { | { | ||||||
|   | |||||||
| @@ -47,6 +47,7 @@ HRESULT vkd3d_create_device(const struct vkd3d_device_create_info *create_info, | |||||||
|             riid, device); |             riid, device); | ||||||
| } | } | ||||||
|  |  | ||||||
|  | /* ID3D12RootSignatureDeserializer */ | ||||||
| struct d3d12_root_signature_deserializer | struct d3d12_root_signature_deserializer | ||||||
| { | { | ||||||
|     ID3D12RootSignatureDeserializer ID3D12RootSignatureDeserializer_iface; |     ID3D12RootSignatureDeserializer ID3D12RootSignatureDeserializer_iface; | ||||||
| @@ -66,8 +67,9 @@ static HRESULT STDMETHODCALLTYPE d3d12_root_signature_deserializer_QueryInterfac | |||||||
| { | { | ||||||
|     TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object); |     TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object); | ||||||
|  |  | ||||||
|     /* QueryInterface() implementation seems to be broken, E_NOINTERFACE is |     /* QueryInterface() implementation is broken, E_NOINTERFACE is returned for | ||||||
|      * returned for IUnknown. */ |      * IUnknown. | ||||||
|  |      */ | ||||||
|     if (IsEqualGUID(riid, &IID_ID3D12RootSignatureDeserializer)) |     if (IsEqualGUID(riid, &IID_ID3D12RootSignatureDeserializer)) | ||||||
|     { |     { | ||||||
|         ID3D12RootSignatureDeserializer_AddRef(iface); |         ID3D12RootSignatureDeserializer_AddRef(iface); | ||||||
| @@ -166,3 +168,163 @@ HRESULT WINAPI D3D12CreateRootSignatureDeserializer(const void *data, SIZE_T dat | |||||||
|     return return_interface((IUnknown *)&object->ID3D12RootSignatureDeserializer_iface, |     return return_interface((IUnknown *)&object->ID3D12RootSignatureDeserializer_iface, | ||||||
|             &IID_ID3D12RootSignatureDeserializer, riid, deserializer); |             &IID_ID3D12RootSignatureDeserializer, riid, deserializer); | ||||||
| } | } | ||||||
|  |  | ||||||
|  | /* ID3DBlob */ | ||||||
|  | struct d3d_blob | ||||||
|  | { | ||||||
|  |     ID3D10Blob ID3DBlob_iface; | ||||||
|  |     LONG refcount; | ||||||
|  |  | ||||||
|  |     void *buffer; | ||||||
|  |     SIZE_T size; | ||||||
|  | }; | ||||||
|  |  | ||||||
|  | static struct d3d_blob *impl_from_ID3DBlob(ID3DBlob *iface) | ||||||
|  | { | ||||||
|  |     return CONTAINING_RECORD(iface, struct d3d_blob, ID3DBlob_iface); | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static HRESULT STDMETHODCALLTYPE d3d_blob_QueryInterface(ID3DBlob *iface, REFIID riid, void **object) | ||||||
|  | { | ||||||
|  |     TRACE("iface %p, riid %s, object %p.\n", iface, debugstr_guid(riid), object); | ||||||
|  |  | ||||||
|  |     if (IsEqualGUID(riid, &IID_ID3DBlob) | ||||||
|  |             || IsEqualGUID(riid, &IID_IUnknown)) | ||||||
|  |     { | ||||||
|  |         ID3D10Blob_AddRef(iface); | ||||||
|  |         *object = iface; | ||||||
|  |         return S_OK; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     WARN("%s not implemented, returning E_NOINTERFACE.\n", debugstr_guid(riid)); | ||||||
|  |  | ||||||
|  |     *object = NULL; | ||||||
|  |     return E_NOINTERFACE; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static ULONG STDMETHODCALLTYPE d3d_blob_AddRef(ID3DBlob *iface) | ||||||
|  | { | ||||||
|  |     struct d3d_blob *blob = impl_from_ID3DBlob(iface); | ||||||
|  |     ULONG refcount = InterlockedIncrement(&blob->refcount); | ||||||
|  |  | ||||||
|  |     TRACE("%p increasing refcount to %u.\n", blob, refcount); | ||||||
|  |  | ||||||
|  |     return refcount; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static ULONG STDMETHODCALLTYPE d3d_blob_Release(ID3DBlob *iface) | ||||||
|  | { | ||||||
|  |     struct d3d_blob *blob = impl_from_ID3DBlob(iface); | ||||||
|  |     ULONG refcount = InterlockedDecrement(&blob->refcount); | ||||||
|  |  | ||||||
|  |     TRACE("%p decreasing refcount to %u.\n", blob, refcount); | ||||||
|  |  | ||||||
|  |     if (!refcount) | ||||||
|  |     { | ||||||
|  |         vkd3d_free(blob->buffer); | ||||||
|  |  | ||||||
|  |         vkd3d_free(blob); | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     return refcount; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static void * STDMETHODCALLTYPE d3d_blob_GetBufferPointer(ID3DBlob *iface) | ||||||
|  | { | ||||||
|  |     struct d3d_blob *blob = impl_from_ID3DBlob(iface); | ||||||
|  |  | ||||||
|  |     TRACE("iface %p.\n", iface); | ||||||
|  |  | ||||||
|  |     return blob->buffer; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static SIZE_T STDMETHODCALLTYPE d3d_blob_GetBufferSize(ID3DBlob *iface) | ||||||
|  | { | ||||||
|  |     struct d3d_blob *blob = impl_from_ID3DBlob(iface); | ||||||
|  |  | ||||||
|  |     TRACE("iface %p.\n", iface); | ||||||
|  |  | ||||||
|  |     return blob->size; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static const struct ID3D10BlobVtbl d3d_blob_vtbl = | ||||||
|  | { | ||||||
|  |     /* IUnknown methods */ | ||||||
|  |     d3d_blob_QueryInterface, | ||||||
|  |     d3d_blob_AddRef, | ||||||
|  |     d3d_blob_Release, | ||||||
|  |     /* ID3DBlob methods */ | ||||||
|  |     d3d_blob_GetBufferPointer, | ||||||
|  |     d3d_blob_GetBufferSize | ||||||
|  | }; | ||||||
|  |  | ||||||
|  | static void d3d_blob_init(struct d3d_blob *blob, void *buffer, SIZE_T size) | ||||||
|  | { | ||||||
|  |     blob->ID3DBlob_iface.lpVtbl = &d3d_blob_vtbl; | ||||||
|  |     blob->refcount = 1; | ||||||
|  |  | ||||||
|  |     blob->buffer = buffer; | ||||||
|  |     blob->size = size; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | static HRESULT d3d_blob_create(void *buffer, SIZE_T size, struct d3d_blob **blob) | ||||||
|  | { | ||||||
|  |     struct d3d_blob *object; | ||||||
|  |  | ||||||
|  |     if (!(object = vkd3d_malloc(sizeof(*object)))) | ||||||
|  |         return E_OUTOFMEMORY; | ||||||
|  |  | ||||||
|  |     d3d_blob_init(object, buffer, size); | ||||||
|  |  | ||||||
|  |     TRACE("Created blob object %p.\n", object); | ||||||
|  |  | ||||||
|  |     *blob = object; | ||||||
|  |  | ||||||
|  |     return S_OK; | ||||||
|  | } | ||||||
|  |  | ||||||
|  | HRESULT WINAPI D3D12SerializeRootSignature(const D3D12_ROOT_SIGNATURE_DESC *root_signature_desc, | ||||||
|  |         D3D_ROOT_SIGNATURE_VERSION version, ID3DBlob **blob, ID3DBlob **error_blob) | ||||||
|  | { | ||||||
|  |     struct vkd3d_shader_code dxbc; | ||||||
|  |     struct d3d_blob *blob_object; | ||||||
|  |     HRESULT hr; | ||||||
|  |  | ||||||
|  |     TRACE("root_signature_desc %p, version %#x, blob %p, error_blob %p.\n", | ||||||
|  |             root_signature_desc, version, blob, error_blob); | ||||||
|  |  | ||||||
|  |     if (!blob) | ||||||
|  |     { | ||||||
|  |         WARN("Invalid blob parameter.\n"); | ||||||
|  |         return E_INVALIDARG; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     if (version != D3D_ROOT_SIGNATURE_VERSION_1_0) | ||||||
|  |     { | ||||||
|  |         FIXME("Root signature version %#x is not supported.\n", version); | ||||||
|  |         return E_NOTIMPL; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     if (error_blob) | ||||||
|  |     { | ||||||
|  |         FIXME("Ignoring error blob %p.\n", error_blob); | ||||||
|  |         *error_blob = NULL; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     if (FAILED(hr = vkd3d_shader_serialize_root_signature(root_signature_desc, &dxbc))) | ||||||
|  |     { | ||||||
|  |         WARN("Failed to serialize root signature, hr %#x.\n", hr); | ||||||
|  |         return hr; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     if (FAILED(hr = d3d_blob_create((void *)dxbc.code, dxbc.size, &blob_object))) | ||||||
|  |     { | ||||||
|  |         WARN("Failed to create blob object, hr %#x.\n", hr); | ||||||
|  |         vkd3d_shader_free_shader_code(&dxbc); | ||||||
|  |         return hr; | ||||||
|  |     } | ||||||
|  |  | ||||||
|  |     *blob = &blob_object->ID3DBlob_iface; | ||||||
|  |  | ||||||
|  |     return S_OK; | ||||||
|  | } | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user