1bf215546Sopenharmony_ci/**************************************************************************
2bf215546Sopenharmony_ci *
3bf215546Sopenharmony_ci * Copyright 2012-2021 VMware, Inc.
4bf215546Sopenharmony_ci * All Rights Reserved.
5bf215546Sopenharmony_ci *
6bf215546Sopenharmony_ci * Permission is hereby granted, free of charge, to any person obtaining a
7bf215546Sopenharmony_ci * copy of this software and associated documentation files (the
8bf215546Sopenharmony_ci * "Software"), to deal in the Software without restriction, including
9bf215546Sopenharmony_ci * without limitation the rights to use, copy, modify, merge, publish,
10bf215546Sopenharmony_ci * distribute, sub license, and/or sell copies of the Software, and to
11bf215546Sopenharmony_ci * permit persons to whom the Software is furnished to do so, subject to
12bf215546Sopenharmony_ci * the following conditions:
13bf215546Sopenharmony_ci *
14bf215546Sopenharmony_ci * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
15bf215546Sopenharmony_ci * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
16bf215546Sopenharmony_ci * FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
17bf215546Sopenharmony_ci * THE COPYRIGHT HOLDERS, AUTHORS AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
18bf215546Sopenharmony_ci * DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
19bf215546Sopenharmony_ci * OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
20bf215546Sopenharmony_ci * USE OR OTHER DEALINGS IN THE SOFTWARE.
21bf215546Sopenharmony_ci *
22bf215546Sopenharmony_ci * The above copyright notice and this permission notice (including the
23bf215546Sopenharmony_ci * next paragraph) shall be included in all copies or substantial portions
24bf215546Sopenharmony_ci * of the Software.
25bf215546Sopenharmony_ci *
26bf215546Sopenharmony_ci **************************************************************************/
27bf215546Sopenharmony_ci
28bf215546Sopenharmony_ci/*
29bf215546Sopenharmony_ci * Resource.cpp --
30bf215546Sopenharmony_ci *    Functions that manipulate GPU resources.
31bf215546Sopenharmony_ci */
32bf215546Sopenharmony_ci
33bf215546Sopenharmony_ci
34bf215546Sopenharmony_ci#include "Resource.h"
35bf215546Sopenharmony_ci#include "Format.h"
36bf215546Sopenharmony_ci#include "State.h"
37bf215546Sopenharmony_ci#include "Query.h"
38bf215546Sopenharmony_ci
39bf215546Sopenharmony_ci#include "Debug.h"
40bf215546Sopenharmony_ci
41bf215546Sopenharmony_ci#include "util/u_math.h"
42bf215546Sopenharmony_ci#include "util/u_rect.h"
43bf215546Sopenharmony_ci#include "util/u_surface.h"
44bf215546Sopenharmony_ci
45bf215546Sopenharmony_ci
46bf215546Sopenharmony_ci/*
47bf215546Sopenharmony_ci * ----------------------------------------------------------------------
48bf215546Sopenharmony_ci *
49bf215546Sopenharmony_ci * CalcPrivateResourceSize --
50bf215546Sopenharmony_ci *
51bf215546Sopenharmony_ci *    The CalcPrivateResourceSize function determines the size of
52bf215546Sopenharmony_ci *    the user-mode display driver's private region of memory
53bf215546Sopenharmony_ci *    (that is, the size of internal driver structures, not the
54bf215546Sopenharmony_ci *    size of the resource video memory).
55bf215546Sopenharmony_ci *
56bf215546Sopenharmony_ci * ----------------------------------------------------------------------
57bf215546Sopenharmony_ci */
58bf215546Sopenharmony_ci
59bf215546Sopenharmony_ciSIZE_T APIENTRY
60bf215546Sopenharmony_ciCalcPrivateResourceSize(D3D10DDI_HDEVICE hDevice,                                // IN
61bf215546Sopenharmony_ci                        __in const D3D10DDIARG_CREATERESOURCE *pCreateResource)  // IN
62bf215546Sopenharmony_ci{
63bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
64bf215546Sopenharmony_ci   return sizeof(Resource);
65bf215546Sopenharmony_ci}
66bf215546Sopenharmony_ci
67bf215546Sopenharmony_ci
68bf215546Sopenharmony_cistatic unsigned
69bf215546Sopenharmony_citranslate_resource_usage( unsigned usage )
70bf215546Sopenharmony_ci{
71bf215546Sopenharmony_ci   unsigned resource_usage = 0;
72bf215546Sopenharmony_ci
73bf215546Sopenharmony_ci   switch (usage) {
74bf215546Sopenharmony_ci   case D3D10_DDI_USAGE_DEFAULT:
75bf215546Sopenharmony_ci      resource_usage = PIPE_USAGE_DEFAULT;
76bf215546Sopenharmony_ci      break;
77bf215546Sopenharmony_ci   case D3D10_DDI_USAGE_IMMUTABLE:
78bf215546Sopenharmony_ci      resource_usage = PIPE_USAGE_IMMUTABLE;
79bf215546Sopenharmony_ci      break;
80bf215546Sopenharmony_ci   case D3D10_DDI_USAGE_DYNAMIC:
81bf215546Sopenharmony_ci      resource_usage = PIPE_USAGE_DYNAMIC;
82bf215546Sopenharmony_ci      break;
83bf215546Sopenharmony_ci   case D3D10_DDI_USAGE_STAGING:
84bf215546Sopenharmony_ci      resource_usage = PIPE_USAGE_STAGING;
85bf215546Sopenharmony_ci      break;
86bf215546Sopenharmony_ci   default:
87bf215546Sopenharmony_ci      assert(0);
88bf215546Sopenharmony_ci      break;
89bf215546Sopenharmony_ci   }
90bf215546Sopenharmony_ci
91bf215546Sopenharmony_ci   return resource_usage;
92bf215546Sopenharmony_ci}
93bf215546Sopenharmony_ci
94bf215546Sopenharmony_ci
95bf215546Sopenharmony_cistatic unsigned
96bf215546Sopenharmony_citranslate_resource_flags(UINT flags)
97bf215546Sopenharmony_ci{
98bf215546Sopenharmony_ci   unsigned bind = 0;
99bf215546Sopenharmony_ci
100bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_VERTEX_BUFFER)
101bf215546Sopenharmony_ci      bind |= PIPE_BIND_VERTEX_BUFFER;
102bf215546Sopenharmony_ci
103bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_INDEX_BUFFER)
104bf215546Sopenharmony_ci      bind |= PIPE_BIND_INDEX_BUFFER;
105bf215546Sopenharmony_ci
106bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_CONSTANT_BUFFER)
107bf215546Sopenharmony_ci      bind |= PIPE_BIND_CONSTANT_BUFFER;
108bf215546Sopenharmony_ci
109bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_SHADER_RESOURCE)
110bf215546Sopenharmony_ci      bind |= PIPE_BIND_SAMPLER_VIEW;
111bf215546Sopenharmony_ci
112bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_RENDER_TARGET)
113bf215546Sopenharmony_ci      bind |= PIPE_BIND_RENDER_TARGET;
114bf215546Sopenharmony_ci
115bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_DEPTH_STENCIL)
116bf215546Sopenharmony_ci      bind |= PIPE_BIND_DEPTH_STENCIL;
117bf215546Sopenharmony_ci
118bf215546Sopenharmony_ci   if (flags & D3D10_DDI_BIND_STREAM_OUTPUT)
119bf215546Sopenharmony_ci      bind |= PIPE_BIND_STREAM_OUTPUT;
120bf215546Sopenharmony_ci
121bf215546Sopenharmony_ci   return bind;
122bf215546Sopenharmony_ci}
123bf215546Sopenharmony_ci
124bf215546Sopenharmony_ci
125bf215546Sopenharmony_cistatic enum pipe_texture_target
126bf215546Sopenharmony_citranslate_texture_target( D3D10DDIRESOURCE_TYPE ResourceDimension,
127bf215546Sopenharmony_ci                             UINT ArraySize)
128bf215546Sopenharmony_ci{
129bf215546Sopenharmony_ci   assert(ArraySize >= 1);
130bf215546Sopenharmony_ci   switch(ResourceDimension) {
131bf215546Sopenharmony_ci   case D3D10DDIRESOURCE_BUFFER:
132bf215546Sopenharmony_ci      assert(ArraySize == 1);
133bf215546Sopenharmony_ci      return PIPE_BUFFER;
134bf215546Sopenharmony_ci   case D3D10DDIRESOURCE_TEXTURE1D:
135bf215546Sopenharmony_ci      return ArraySize > 1 ? PIPE_TEXTURE_1D_ARRAY : PIPE_TEXTURE_1D;
136bf215546Sopenharmony_ci   case D3D10DDIRESOURCE_TEXTURE2D:
137bf215546Sopenharmony_ci      return ArraySize > 1 ? PIPE_TEXTURE_2D_ARRAY : PIPE_TEXTURE_2D;
138bf215546Sopenharmony_ci   case D3D10DDIRESOURCE_TEXTURE3D:
139bf215546Sopenharmony_ci      assert(ArraySize == 1);
140bf215546Sopenharmony_ci      return PIPE_TEXTURE_3D;
141bf215546Sopenharmony_ci   case D3D10DDIRESOURCE_TEXTURECUBE:
142bf215546Sopenharmony_ci      assert(ArraySize % 6 == 0);
143bf215546Sopenharmony_ci      return ArraySize > 6 ? PIPE_TEXTURE_CUBE_ARRAY : PIPE_TEXTURE_CUBE;
144bf215546Sopenharmony_ci   default:
145bf215546Sopenharmony_ci      assert(0);
146bf215546Sopenharmony_ci      return PIPE_TEXTURE_1D;
147bf215546Sopenharmony_ci   }
148bf215546Sopenharmony_ci}
149bf215546Sopenharmony_ci
150bf215546Sopenharmony_ci
151bf215546Sopenharmony_cistatic void
152bf215546Sopenharmony_cisubResourceBox(struct pipe_resource *resource, // IN
153bf215546Sopenharmony_ci                 UINT SubResource,  // IN
154bf215546Sopenharmony_ci                 unsigned *pLevel, // OUT
155bf215546Sopenharmony_ci                 struct pipe_box *pBox)   // OUT
156bf215546Sopenharmony_ci{
157bf215546Sopenharmony_ci   UINT MipLevels = resource->last_level + 1;
158bf215546Sopenharmony_ci   unsigned layer;
159bf215546Sopenharmony_ci   unsigned width;
160bf215546Sopenharmony_ci   unsigned height;
161bf215546Sopenharmony_ci   unsigned depth;
162bf215546Sopenharmony_ci
163bf215546Sopenharmony_ci   *pLevel = SubResource % MipLevels;
164bf215546Sopenharmony_ci   layer = SubResource / MipLevels;
165bf215546Sopenharmony_ci
166bf215546Sopenharmony_ci   width  = u_minify(resource->width0,  *pLevel);
167bf215546Sopenharmony_ci   height = u_minify(resource->height0, *pLevel);
168bf215546Sopenharmony_ci   depth  = u_minify(resource->depth0,  *pLevel);
169bf215546Sopenharmony_ci
170bf215546Sopenharmony_ci   pBox->x = 0;
171bf215546Sopenharmony_ci   pBox->y = 0;
172bf215546Sopenharmony_ci   pBox->z = 0 + layer;
173bf215546Sopenharmony_ci   pBox->width  = width;
174bf215546Sopenharmony_ci   pBox->height = height;
175bf215546Sopenharmony_ci   pBox->depth  = depth;
176bf215546Sopenharmony_ci}
177bf215546Sopenharmony_ci
178bf215546Sopenharmony_ci
179bf215546Sopenharmony_ci/*
180bf215546Sopenharmony_ci * ----------------------------------------------------------------------
181bf215546Sopenharmony_ci *
182bf215546Sopenharmony_ci * CreateResource --
183bf215546Sopenharmony_ci *
184bf215546Sopenharmony_ci *    The CreateResource function creates a resource.
185bf215546Sopenharmony_ci *
186bf215546Sopenharmony_ci * ----------------------------------------------------------------------
187bf215546Sopenharmony_ci */
188bf215546Sopenharmony_ci
189bf215546Sopenharmony_civoid APIENTRY
190bf215546Sopenharmony_ciCreateResource(D3D10DDI_HDEVICE hDevice,                                // IN
191bf215546Sopenharmony_ci               __in const D3D10DDIARG_CREATERESOURCE *pCreateResource,  // IN
192bf215546Sopenharmony_ci               D3D10DDI_HRESOURCE hResource,                            // IN
193bf215546Sopenharmony_ci               D3D10DDI_HRTRESOURCE hRTResource)                        // IN
194bf215546Sopenharmony_ci{
195bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
196bf215546Sopenharmony_ci
197bf215546Sopenharmony_ci   if ((pCreateResource->MiscFlags & D3D10_DDI_RESOURCE_MISC_SHARED) ||
198bf215546Sopenharmony_ci       (pCreateResource->pPrimaryDesc &&
199bf215546Sopenharmony_ci        pCreateResource->pPrimaryDesc->DriverFlags & DXGI_DDI_PRIMARY_OPTIONAL)) {
200bf215546Sopenharmony_ci
201bf215546Sopenharmony_ci      DebugPrintf("%s(%dx%dx%d hResource=%p)\n",
202bf215546Sopenharmony_ci	       __FUNCTION__,
203bf215546Sopenharmony_ci	       pCreateResource->pMipInfoList[0].TexelWidth,
204bf215546Sopenharmony_ci	       pCreateResource->pMipInfoList[0].TexelHeight,
205bf215546Sopenharmony_ci	       pCreateResource->pMipInfoList[0].TexelDepth,
206bf215546Sopenharmony_ci	       hResource.pDrvPrivate);
207bf215546Sopenharmony_ci      DebugPrintf("  ResourceDimension = %u\n",
208bf215546Sopenharmony_ci	       pCreateResource->ResourceDimension);
209bf215546Sopenharmony_ci      DebugPrintf("  Usage = %u\n",
210bf215546Sopenharmony_ci	       pCreateResource->Usage);
211bf215546Sopenharmony_ci      DebugPrintf("  BindFlags = 0x%x\n",
212bf215546Sopenharmony_ci	       pCreateResource->BindFlags);
213bf215546Sopenharmony_ci      DebugPrintf("  MapFlags = 0x%x\n",
214bf215546Sopenharmony_ci	       pCreateResource->MapFlags);
215bf215546Sopenharmony_ci      DebugPrintf("  MiscFlags = 0x%x\n",
216bf215546Sopenharmony_ci	       pCreateResource->MiscFlags);
217bf215546Sopenharmony_ci      DebugPrintf("  Format = %s\n",
218bf215546Sopenharmony_ci	       FormatToName(pCreateResource->Format));
219bf215546Sopenharmony_ci      DebugPrintf("  SampleDesc.Count = %u\n", pCreateResource->SampleDesc.Count);
220bf215546Sopenharmony_ci      DebugPrintf("  SampleDesc.Quality = %u\n", pCreateResource->SampleDesc.Quality);
221bf215546Sopenharmony_ci      DebugPrintf("  MipLevels = %u\n", pCreateResource->MipLevels);
222bf215546Sopenharmony_ci      DebugPrintf("  ArraySize = %u\n", pCreateResource->ArraySize);
223bf215546Sopenharmony_ci      DebugPrintf("  pPrimaryDesc = %p\n", pCreateResource->pPrimaryDesc);
224bf215546Sopenharmony_ci      if (pCreateResource->pPrimaryDesc) {
225bf215546Sopenharmony_ci	 DebugPrintf("    Flags = 0x%x\n",
226bf215546Sopenharmony_ci		  pCreateResource->pPrimaryDesc->Flags);
227bf215546Sopenharmony_ci	 DebugPrintf("    VidPnSourceId = %u\n", pCreateResource->pPrimaryDesc->VidPnSourceId);
228bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.Width = %u\n", pCreateResource->pPrimaryDesc->ModeDesc.Width);
229bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.Height = %u\n", pCreateResource->pPrimaryDesc->ModeDesc.Height);
230bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.Format = %u)\n",
231bf215546Sopenharmony_ci		  pCreateResource->pPrimaryDesc->ModeDesc.Format);
232bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.RefreshRate.Numerator = %u\n", pCreateResource->pPrimaryDesc->ModeDesc.RefreshRate.Numerator);
233bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.RefreshRate.Denominator = %u\n", pCreateResource->pPrimaryDesc->ModeDesc.RefreshRate.Denominator);
234bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.ScanlineOrdering = %u\n",
235bf215546Sopenharmony_ci		  pCreateResource->pPrimaryDesc->ModeDesc.ScanlineOrdering);
236bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.Rotation = %u\n",
237bf215546Sopenharmony_ci		  pCreateResource->pPrimaryDesc->ModeDesc.Rotation);
238bf215546Sopenharmony_ci	 DebugPrintf("    ModeDesc.Scaling = %u\n",
239bf215546Sopenharmony_ci		  pCreateResource->pPrimaryDesc->ModeDesc.Scaling);
240bf215546Sopenharmony_ci	 DebugPrintf("    DriverFlags = 0x%x\n",
241bf215546Sopenharmony_ci		  pCreateResource->pPrimaryDesc->DriverFlags);
242bf215546Sopenharmony_ci      }
243bf215546Sopenharmony_ci
244bf215546Sopenharmony_ci   }
245bf215546Sopenharmony_ci
246bf215546Sopenharmony_ci   struct pipe_context *pipe = CastPipeContext(hDevice);
247bf215546Sopenharmony_ci   struct pipe_screen *screen = pipe->screen;
248bf215546Sopenharmony_ci
249bf215546Sopenharmony_ci   Resource *pResource = CastResource(hResource);
250bf215546Sopenharmony_ci
251bf215546Sopenharmony_ci   memset(pResource, 0, sizeof *pResource);
252bf215546Sopenharmony_ci
253bf215546Sopenharmony_ci#if 0
254bf215546Sopenharmony_ci   if (pCreateResource->pPrimaryDesc) {
255bf215546Sopenharmony_ci      pCreateResource->pPrimaryDesc->DriverFlags = DXGI_DDI_PRIMARY_DRIVER_FLAG_NO_SCANOUT;
256bf215546Sopenharmony_ci      if (!(pCreateResource->pPrimaryDesc->DriverFlags & DXGI_DDI_PRIMARY_OPTIONAL)) {
257bf215546Sopenharmony_ci         // http://msdn.microsoft.com/en-us/library/windows/hardware/ff568846.aspx
258bf215546Sopenharmony_ci         SetError(hDevice, DXGI_DDI_ERR_UNSUPPORTED);
259bf215546Sopenharmony_ci         return;
260bf215546Sopenharmony_ci      }
261bf215546Sopenharmony_ci   }
262bf215546Sopenharmony_ci#endif
263bf215546Sopenharmony_ci
264bf215546Sopenharmony_ci   pResource->Format = pCreateResource->Format;
265bf215546Sopenharmony_ci   pResource->MipLevels = pCreateResource->MipLevels;
266bf215546Sopenharmony_ci
267bf215546Sopenharmony_ci   struct pipe_resource templat;
268bf215546Sopenharmony_ci
269bf215546Sopenharmony_ci   memset(&templat, 0, sizeof templat);
270bf215546Sopenharmony_ci
271bf215546Sopenharmony_ci   templat.target     = translate_texture_target( pCreateResource->ResourceDimension,
272bf215546Sopenharmony_ci                                                  pCreateResource->ArraySize );
273bf215546Sopenharmony_ci   pResource->buffer = templat.target == PIPE_BUFFER;
274bf215546Sopenharmony_ci
275bf215546Sopenharmony_ci   if (pCreateResource->Format == DXGI_FORMAT_UNKNOWN) {
276bf215546Sopenharmony_ci      assert(pCreateResource->ResourceDimension == D3D10DDIRESOURCE_BUFFER);
277bf215546Sopenharmony_ci      templat.format = PIPE_FORMAT_R8_UINT;
278bf215546Sopenharmony_ci   } else {
279bf215546Sopenharmony_ci      BOOL bindDepthStencil = !!(pCreateResource->BindFlags & D3D10_DDI_BIND_DEPTH_STENCIL);
280bf215546Sopenharmony_ci      templat.format = FormatTranslate(pCreateResource->Format, bindDepthStencil);
281bf215546Sopenharmony_ci   }
282bf215546Sopenharmony_ci
283bf215546Sopenharmony_ci   templat.width0     = pCreateResource->pMipInfoList[0].TexelWidth;
284bf215546Sopenharmony_ci   templat.height0    = pCreateResource->pMipInfoList[0].TexelHeight;
285bf215546Sopenharmony_ci   templat.depth0     = pCreateResource->pMipInfoList[0].TexelDepth;
286bf215546Sopenharmony_ci   templat.array_size = pCreateResource->ArraySize;
287bf215546Sopenharmony_ci   templat.last_level = pCreateResource->MipLevels - 1;
288bf215546Sopenharmony_ci   templat.nr_samples = pCreateResource->SampleDesc.Count;
289bf215546Sopenharmony_ci   templat.nr_storage_samples = pCreateResource->SampleDesc.Count;
290bf215546Sopenharmony_ci   templat.bind       = translate_resource_flags(pCreateResource->BindFlags);
291bf215546Sopenharmony_ci   templat.usage      = translate_resource_usage(pCreateResource->Usage);
292bf215546Sopenharmony_ci
293bf215546Sopenharmony_ci   if (templat.target != PIPE_BUFFER) {
294bf215546Sopenharmony_ci      if (!screen->is_format_supported(screen,
295bf215546Sopenharmony_ci                                       templat.format,
296bf215546Sopenharmony_ci                                       templat.target,
297bf215546Sopenharmony_ci                                       templat.nr_samples,
298bf215546Sopenharmony_ci                                       templat.nr_storage_samples,
299bf215546Sopenharmony_ci                                       templat.bind)) {
300bf215546Sopenharmony_ci         debug_printf("%s: unsupported format %s\n",
301bf215546Sopenharmony_ci                     __FUNCTION__, util_format_name(templat.format));
302bf215546Sopenharmony_ci         SetError(hDevice, E_OUTOFMEMORY);
303bf215546Sopenharmony_ci         return;
304bf215546Sopenharmony_ci      }
305bf215546Sopenharmony_ci   }
306bf215546Sopenharmony_ci
307bf215546Sopenharmony_ci   pResource->resource = screen->resource_create(screen, &templat);
308bf215546Sopenharmony_ci   if (!pResource) {
309bf215546Sopenharmony_ci      DebugPrintf("%s: failed to create resource\n", __FUNCTION__);
310bf215546Sopenharmony_ci      SetError(hDevice, E_OUTOFMEMORY);
311bf215546Sopenharmony_ci      return;
312bf215546Sopenharmony_ci   }
313bf215546Sopenharmony_ci
314bf215546Sopenharmony_ci   pResource->NumSubResources = pCreateResource->MipLevels * pCreateResource->ArraySize;
315bf215546Sopenharmony_ci   pResource->transfers = (struct pipe_transfer **)calloc(pResource->NumSubResources,
316bf215546Sopenharmony_ci                                                          sizeof *pResource->transfers);
317bf215546Sopenharmony_ci
318bf215546Sopenharmony_ci   if (pCreateResource->pInitialDataUP) {
319bf215546Sopenharmony_ci      if (pResource->buffer) {
320bf215546Sopenharmony_ci         assert(pResource->NumSubResources == 1);
321bf215546Sopenharmony_ci         const D3D10_DDIARG_SUBRESOURCE_UP* pInitialDataUP =
322bf215546Sopenharmony_ci               &pCreateResource->pInitialDataUP[0];
323bf215546Sopenharmony_ci
324bf215546Sopenharmony_ci         unsigned level;
325bf215546Sopenharmony_ci         struct pipe_box box;
326bf215546Sopenharmony_ci         subResourceBox(pResource->resource, 0, &level, &box);
327bf215546Sopenharmony_ci
328bf215546Sopenharmony_ci         struct pipe_transfer *transfer;
329bf215546Sopenharmony_ci         void *map;
330bf215546Sopenharmony_ci         map = pipe->buffer_map(pipe,
331bf215546Sopenharmony_ci                                pResource->resource,
332bf215546Sopenharmony_ci                                level,
333bf215546Sopenharmony_ci                                PIPE_MAP_WRITE |
334bf215546Sopenharmony_ci                                PIPE_MAP_UNSYNCHRONIZED,
335bf215546Sopenharmony_ci                                &box,
336bf215546Sopenharmony_ci                                &transfer);
337bf215546Sopenharmony_ci         assert(map);
338bf215546Sopenharmony_ci         if (map) {
339bf215546Sopenharmony_ci            memcpy(map, pInitialDataUP->pSysMem, box.width);
340bf215546Sopenharmony_ci            pipe_buffer_unmap(pipe, transfer);
341bf215546Sopenharmony_ci         }
342bf215546Sopenharmony_ci      } else {
343bf215546Sopenharmony_ci         for (UINT SubResource = 0; SubResource < pResource->NumSubResources; ++SubResource) {
344bf215546Sopenharmony_ci            const D3D10_DDIARG_SUBRESOURCE_UP* pInitialDataUP =
345bf215546Sopenharmony_ci                  &pCreateResource->pInitialDataUP[SubResource];
346bf215546Sopenharmony_ci
347bf215546Sopenharmony_ci            unsigned level;
348bf215546Sopenharmony_ci            struct pipe_box box;
349bf215546Sopenharmony_ci            subResourceBox(pResource->resource, SubResource, &level, &box);
350bf215546Sopenharmony_ci
351bf215546Sopenharmony_ci            struct pipe_transfer *transfer;
352bf215546Sopenharmony_ci            void *map;
353bf215546Sopenharmony_ci            map = pipe->texture_map(pipe,
354bf215546Sopenharmony_ci                                    pResource->resource,
355bf215546Sopenharmony_ci                                    level,
356bf215546Sopenharmony_ci                                    PIPE_MAP_WRITE |
357bf215546Sopenharmony_ci                                    PIPE_MAP_UNSYNCHRONIZED,
358bf215546Sopenharmony_ci                                    &box,
359bf215546Sopenharmony_ci                                    &transfer);
360bf215546Sopenharmony_ci            assert(map);
361bf215546Sopenharmony_ci            if (map) {
362bf215546Sopenharmony_ci               for (int z = 0; z < box.depth; ++z) {
363bf215546Sopenharmony_ci                  ubyte *dst = (ubyte*)map + z*transfer->layer_stride;
364bf215546Sopenharmony_ci                  const ubyte *src = (const ubyte*)pInitialDataUP->pSysMem + z*pInitialDataUP->SysMemSlicePitch;
365bf215546Sopenharmony_ci                  util_copy_rect(dst,
366bf215546Sopenharmony_ci                                 templat.format,
367bf215546Sopenharmony_ci                                 transfer->stride,
368bf215546Sopenharmony_ci                                 0, 0, box.width, box.height,
369bf215546Sopenharmony_ci                                 src,
370bf215546Sopenharmony_ci                                 pInitialDataUP->SysMemPitch,
371bf215546Sopenharmony_ci                                 0, 0);
372bf215546Sopenharmony_ci               }
373bf215546Sopenharmony_ci               pipe_texture_unmap(pipe, transfer);
374bf215546Sopenharmony_ci            }
375bf215546Sopenharmony_ci         }
376bf215546Sopenharmony_ci      }
377bf215546Sopenharmony_ci   }
378bf215546Sopenharmony_ci}
379bf215546Sopenharmony_ci
380bf215546Sopenharmony_ci
381bf215546Sopenharmony_ci/*
382bf215546Sopenharmony_ci * ----------------------------------------------------------------------
383bf215546Sopenharmony_ci *
384bf215546Sopenharmony_ci * CalcPrivateOpenedResourceSize --
385bf215546Sopenharmony_ci *
386bf215546Sopenharmony_ci *    The CalcPrivateOpenedResourceSize function determines the size
387bf215546Sopenharmony_ci *    of the user-mode display driver's private shared region of memory
388bf215546Sopenharmony_ci *    (that is, the size of internal driver structures, not the size
389bf215546Sopenharmony_ci *    of the resource video memory) for an opened resource.
390bf215546Sopenharmony_ci *
391bf215546Sopenharmony_ci * ----------------------------------------------------------------------
392bf215546Sopenharmony_ci */
393bf215546Sopenharmony_ci
394bf215546Sopenharmony_ciSIZE_T APIENTRY
395bf215546Sopenharmony_ciCalcPrivateOpenedResourceSize(D3D10DDI_HDEVICE hDevice,                             // IN
396bf215546Sopenharmony_ci                              __in const D3D10DDIARG_OPENRESOURCE *pOpenResource)   // IN
397bf215546Sopenharmony_ci{
398bf215546Sopenharmony_ci   return sizeof(Resource);
399bf215546Sopenharmony_ci}
400bf215546Sopenharmony_ci
401bf215546Sopenharmony_ci
402bf215546Sopenharmony_ci/*
403bf215546Sopenharmony_ci * ----------------------------------------------------------------------
404bf215546Sopenharmony_ci *
405bf215546Sopenharmony_ci * OpenResource --
406bf215546Sopenharmony_ci *
407bf215546Sopenharmony_ci *    The OpenResource function opens a shared resource.
408bf215546Sopenharmony_ci *
409bf215546Sopenharmony_ci * ----------------------------------------------------------------------
410bf215546Sopenharmony_ci */
411bf215546Sopenharmony_ci
412bf215546Sopenharmony_civoid APIENTRY
413bf215546Sopenharmony_ciOpenResource(D3D10DDI_HDEVICE hDevice,                            // IN
414bf215546Sopenharmony_ci             __in const D3D10DDIARG_OPENRESOURCE *pOpenResource,  // IN
415bf215546Sopenharmony_ci             D3D10DDI_HRESOURCE hResource,                        // IN
416bf215546Sopenharmony_ci             D3D10DDI_HRTRESOURCE hRTResource)                    // IN
417bf215546Sopenharmony_ci{
418bf215546Sopenharmony_ci   LOG_UNSUPPORTED_ENTRYPOINT();
419bf215546Sopenharmony_ci   SetError(hDevice, E_OUTOFMEMORY);
420bf215546Sopenharmony_ci}
421bf215546Sopenharmony_ci
422bf215546Sopenharmony_ci
423bf215546Sopenharmony_ci/*
424bf215546Sopenharmony_ci * ----------------------------------------------------------------------
425bf215546Sopenharmony_ci *
426bf215546Sopenharmony_ci * DestroyResource --
427bf215546Sopenharmony_ci *
428bf215546Sopenharmony_ci *    The DestroyResource function destroys the specified resource
429bf215546Sopenharmony_ci *    object. The resource object can be destoyed only if it is not
430bf215546Sopenharmony_ci *    currently bound to a display device, and if all views that
431bf215546Sopenharmony_ci *    refer to the resource are also destroyed.
432bf215546Sopenharmony_ci *
433bf215546Sopenharmony_ci * ----------------------------------------------------------------------
434bf215546Sopenharmony_ci */
435bf215546Sopenharmony_ci
436bf215546Sopenharmony_ci
437bf215546Sopenharmony_civoid APIENTRY
438bf215546Sopenharmony_ciDestroyResource(D3D10DDI_HDEVICE hDevice,       // IN
439bf215546Sopenharmony_ci                D3D10DDI_HRESOURCE hResource)   // IN
440bf215546Sopenharmony_ci{
441bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
442bf215546Sopenharmony_ci
443bf215546Sopenharmony_ci   struct pipe_context *pipe = CastPipeContext(hDevice);
444bf215546Sopenharmony_ci   Resource *pResource = CastResource(hResource);
445bf215546Sopenharmony_ci
446bf215546Sopenharmony_ci   if (pResource->so_target) {
447bf215546Sopenharmony_ci      pipe_so_target_reference(&pResource->so_target, NULL);
448bf215546Sopenharmony_ci   }
449bf215546Sopenharmony_ci
450bf215546Sopenharmony_ci   for (UINT SubResource = 0; SubResource < pResource->NumSubResources; ++SubResource) {
451bf215546Sopenharmony_ci      if (pResource->transfers[SubResource]) {
452bf215546Sopenharmony_ci         if (pResource->buffer) {
453bf215546Sopenharmony_ci            pipe_buffer_unmap(pipe, pResource->transfers[SubResource]);
454bf215546Sopenharmony_ci         } else {
455bf215546Sopenharmony_ci            pipe_texture_unmap(pipe, pResource->transfers[SubResource]);
456bf215546Sopenharmony_ci         }
457bf215546Sopenharmony_ci         pResource->transfers[SubResource] = NULL;
458bf215546Sopenharmony_ci      }
459bf215546Sopenharmony_ci   }
460bf215546Sopenharmony_ci   free(pResource->transfers);
461bf215546Sopenharmony_ci
462bf215546Sopenharmony_ci   pipe_resource_reference(&pResource->resource, NULL);
463bf215546Sopenharmony_ci}
464bf215546Sopenharmony_ci
465bf215546Sopenharmony_ci
466bf215546Sopenharmony_ci/*
467bf215546Sopenharmony_ci * ----------------------------------------------------------------------
468bf215546Sopenharmony_ci *
469bf215546Sopenharmony_ci * ResourceMap --
470bf215546Sopenharmony_ci *
471bf215546Sopenharmony_ci *    The ResourceMap function maps a subresource of a resource.
472bf215546Sopenharmony_ci *
473bf215546Sopenharmony_ci * ----------------------------------------------------------------------
474bf215546Sopenharmony_ci */
475bf215546Sopenharmony_ci
476bf215546Sopenharmony_civoid APIENTRY
477bf215546Sopenharmony_ciResourceMap(D3D10DDI_HDEVICE hDevice,                                // IN
478bf215546Sopenharmony_ci            D3D10DDI_HRESOURCE hResource,                            // IN
479bf215546Sopenharmony_ci            UINT SubResource,                                        // IN
480bf215546Sopenharmony_ci            D3D10_DDI_MAP DDIMap,                                    // IN
481bf215546Sopenharmony_ci            UINT Flags,                                              // IN
482bf215546Sopenharmony_ci            __out D3D10DDI_MAPPED_SUBRESOURCE *pMappedSubResource)   // OUT
483bf215546Sopenharmony_ci{
484bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
485bf215546Sopenharmony_ci
486bf215546Sopenharmony_ci   struct pipe_context *pipe = CastPipeContext(hDevice);
487bf215546Sopenharmony_ci   Resource *pResource = CastResource(hResource);
488bf215546Sopenharmony_ci   struct pipe_resource *resource = pResource->resource;
489bf215546Sopenharmony_ci
490bf215546Sopenharmony_ci   unsigned usage;
491bf215546Sopenharmony_ci   switch (DDIMap) {
492bf215546Sopenharmony_ci   case D3D10_DDI_MAP_READ:
493bf215546Sopenharmony_ci      usage = PIPE_MAP_READ;
494bf215546Sopenharmony_ci      break;
495bf215546Sopenharmony_ci   case D3D10_DDI_MAP_READWRITE:
496bf215546Sopenharmony_ci      usage = PIPE_MAP_READ | PIPE_MAP_WRITE;
497bf215546Sopenharmony_ci      break;
498bf215546Sopenharmony_ci   case D3D10_DDI_MAP_WRITE:
499bf215546Sopenharmony_ci      usage = PIPE_MAP_WRITE;
500bf215546Sopenharmony_ci      break;
501bf215546Sopenharmony_ci   case D3D10_DDI_MAP_WRITE_DISCARD:
502bf215546Sopenharmony_ci      usage = PIPE_MAP_WRITE;
503bf215546Sopenharmony_ci      if (resource->last_level == 0 && resource->array_size == 1) {
504bf215546Sopenharmony_ci         usage |= PIPE_MAP_DISCARD_WHOLE_RESOURCE;
505bf215546Sopenharmony_ci      } else {
506bf215546Sopenharmony_ci         usage |= PIPE_MAP_DISCARD_RANGE;
507bf215546Sopenharmony_ci      }
508bf215546Sopenharmony_ci      break;
509bf215546Sopenharmony_ci   case D3D10_DDI_MAP_WRITE_NOOVERWRITE:
510bf215546Sopenharmony_ci      usage = PIPE_MAP_WRITE | PIPE_MAP_UNSYNCHRONIZED;
511bf215546Sopenharmony_ci      break;
512bf215546Sopenharmony_ci   default:
513bf215546Sopenharmony_ci      assert(0);
514bf215546Sopenharmony_ci      return;
515bf215546Sopenharmony_ci   }
516bf215546Sopenharmony_ci
517bf215546Sopenharmony_ci   assert(SubResource < pResource->NumSubResources);
518bf215546Sopenharmony_ci
519bf215546Sopenharmony_ci   unsigned level;
520bf215546Sopenharmony_ci   struct pipe_box box;
521bf215546Sopenharmony_ci   subResourceBox(resource, SubResource, &level, &box);
522bf215546Sopenharmony_ci
523bf215546Sopenharmony_ci   assert(!pResource->transfers[SubResource]);
524bf215546Sopenharmony_ci
525bf215546Sopenharmony_ci   void *map;
526bf215546Sopenharmony_ci   if (pResource->buffer) {
527bf215546Sopenharmony_ci      map = pipe->buffer_map(pipe,
528bf215546Sopenharmony_ci                             resource,
529bf215546Sopenharmony_ci                             level,
530bf215546Sopenharmony_ci                             usage,
531bf215546Sopenharmony_ci                             &box,
532bf215546Sopenharmony_ci                             &pResource->transfers[SubResource]);
533bf215546Sopenharmony_ci   } else {
534bf215546Sopenharmony_ci      map = pipe->texture_map(pipe,
535bf215546Sopenharmony_ci                              resource,
536bf215546Sopenharmony_ci                              level,
537bf215546Sopenharmony_ci                              usage,
538bf215546Sopenharmony_ci                              &box,
539bf215546Sopenharmony_ci                              &pResource->transfers[SubResource]);
540bf215546Sopenharmony_ci   }
541bf215546Sopenharmony_ci   if (!map) {
542bf215546Sopenharmony_ci      DebugPrintf("%s: failed to map resource\n", __FUNCTION__);
543bf215546Sopenharmony_ci      SetError(hDevice, E_FAIL);
544bf215546Sopenharmony_ci      return;
545bf215546Sopenharmony_ci   }
546bf215546Sopenharmony_ci
547bf215546Sopenharmony_ci   pMappedSubResource->pData = map;
548bf215546Sopenharmony_ci   pMappedSubResource->RowPitch = pResource->transfers[SubResource]->stride;
549bf215546Sopenharmony_ci   pMappedSubResource->DepthPitch = pResource->transfers[SubResource]->layer_stride;
550bf215546Sopenharmony_ci}
551bf215546Sopenharmony_ci
552bf215546Sopenharmony_ci
553bf215546Sopenharmony_ci/*
554bf215546Sopenharmony_ci * ----------------------------------------------------------------------
555bf215546Sopenharmony_ci *
556bf215546Sopenharmony_ci * ResourceUnmap --
557bf215546Sopenharmony_ci *
558bf215546Sopenharmony_ci *    The ResourceUnmap function unmaps a subresource of a resource.
559bf215546Sopenharmony_ci *
560bf215546Sopenharmony_ci * ----------------------------------------------------------------------
561bf215546Sopenharmony_ci */
562bf215546Sopenharmony_ci
563bf215546Sopenharmony_civoid APIENTRY
564bf215546Sopenharmony_ciResourceUnmap(D3D10DDI_HDEVICE hDevice,      // IN
565bf215546Sopenharmony_ci              D3D10DDI_HRESOURCE hResource,  // IN
566bf215546Sopenharmony_ci              UINT SubResource)              // IN
567bf215546Sopenharmony_ci{
568bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
569bf215546Sopenharmony_ci
570bf215546Sopenharmony_ci   struct pipe_context *pipe = CastPipeContext(hDevice);
571bf215546Sopenharmony_ci   Resource *pResource = CastResource(hResource);
572bf215546Sopenharmony_ci
573bf215546Sopenharmony_ci   assert(SubResource < pResource->NumSubResources);
574bf215546Sopenharmony_ci
575bf215546Sopenharmony_ci   if (pResource->transfers[SubResource]) {
576bf215546Sopenharmony_ci      if (pResource->buffer) {
577bf215546Sopenharmony_ci         pipe_buffer_unmap(pipe, pResource->transfers[SubResource]);
578bf215546Sopenharmony_ci      } else {
579bf215546Sopenharmony_ci         pipe_texture_unmap(pipe, pResource->transfers[SubResource]);
580bf215546Sopenharmony_ci      }
581bf215546Sopenharmony_ci      pResource->transfers[SubResource] = NULL;
582bf215546Sopenharmony_ci   }
583bf215546Sopenharmony_ci}
584bf215546Sopenharmony_ci
585bf215546Sopenharmony_ci
586bf215546Sopenharmony_ci/*
587bf215546Sopenharmony_ci *----------------------------------------------------------------------
588bf215546Sopenharmony_ci *
589bf215546Sopenharmony_ci * areResourcesCompatible --
590bf215546Sopenharmony_ci *
591bf215546Sopenharmony_ci *      Check whether two resources can be safely passed to
592bf215546Sopenharmony_ci *      pipe_context::resource_copy_region method.
593bf215546Sopenharmony_ci *
594bf215546Sopenharmony_ci * Results:
595bf215546Sopenharmony_ci *      As above.
596bf215546Sopenharmony_ci *
597bf215546Sopenharmony_ci * Side effects:
598bf215546Sopenharmony_ci *      None.
599bf215546Sopenharmony_ci *
600bf215546Sopenharmony_ci *----------------------------------------------------------------------
601bf215546Sopenharmony_ci */
602bf215546Sopenharmony_ci
603bf215546Sopenharmony_cistatic bool
604bf215546Sopenharmony_ciareResourcesCompatible(const struct pipe_resource *src_resource, // IN
605bf215546Sopenharmony_ci                       const struct pipe_resource *dst_resource) // IN
606bf215546Sopenharmony_ci{
607bf215546Sopenharmony_ci   if (src_resource->format == dst_resource->format) {
608bf215546Sopenharmony_ci      /*
609bf215546Sopenharmony_ci       * Trivial.
610bf215546Sopenharmony_ci       */
611bf215546Sopenharmony_ci
612bf215546Sopenharmony_ci      return TRUE;
613bf215546Sopenharmony_ci   } else if (src_resource->target == PIPE_BUFFER &&
614bf215546Sopenharmony_ci              dst_resource->target == PIPE_BUFFER) {
615bf215546Sopenharmony_ci      /*
616bf215546Sopenharmony_ci       * Buffer resources are merely a collection of bytes.
617bf215546Sopenharmony_ci       */
618bf215546Sopenharmony_ci
619bf215546Sopenharmony_ci      return TRUE;
620bf215546Sopenharmony_ci   } else {
621bf215546Sopenharmony_ci      /*
622bf215546Sopenharmony_ci       * Check whether the formats are supported by
623bf215546Sopenharmony_ci       * the resource_copy_region method.
624bf215546Sopenharmony_ci       */
625bf215546Sopenharmony_ci
626bf215546Sopenharmony_ci      const struct util_format_description *src_format_desc;
627bf215546Sopenharmony_ci      const struct util_format_description *dst_format_desc;
628bf215546Sopenharmony_ci
629bf215546Sopenharmony_ci      src_format_desc = util_format_description(src_resource->format);
630bf215546Sopenharmony_ci      dst_format_desc = util_format_description(dst_resource->format);
631bf215546Sopenharmony_ci
632bf215546Sopenharmony_ci      assert(src_format_desc->block.width  == dst_format_desc->block.width);
633bf215546Sopenharmony_ci      assert(src_format_desc->block.height == dst_format_desc->block.height);
634bf215546Sopenharmony_ci      assert(src_format_desc->block.bits   == dst_format_desc->block.bits);
635bf215546Sopenharmony_ci
636bf215546Sopenharmony_ci      return util_is_format_compatible(src_format_desc, dst_format_desc);
637bf215546Sopenharmony_ci   }
638bf215546Sopenharmony_ci}
639bf215546Sopenharmony_ci
640bf215546Sopenharmony_ci
641bf215546Sopenharmony_ci/*
642bf215546Sopenharmony_ci * ----------------------------------------------------------------------
643bf215546Sopenharmony_ci *
644bf215546Sopenharmony_ci * ResourceCopy --
645bf215546Sopenharmony_ci *
646bf215546Sopenharmony_ci *    The ResourceCopy function copies an entire source
647bf215546Sopenharmony_ci *    resource to a destination resource.
648bf215546Sopenharmony_ci *
649bf215546Sopenharmony_ci * ----------------------------------------------------------------------
650bf215546Sopenharmony_ci */
651bf215546Sopenharmony_ci
652bf215546Sopenharmony_civoid APIENTRY
653bf215546Sopenharmony_ciResourceCopy(D3D10DDI_HDEVICE hDevice,          // IN
654bf215546Sopenharmony_ci             D3D10DDI_HRESOURCE hDstResource,   // IN
655bf215546Sopenharmony_ci             D3D10DDI_HRESOURCE hSrcResource)   // IN
656bf215546Sopenharmony_ci{
657bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
658bf215546Sopenharmony_ci
659bf215546Sopenharmony_ci   Device *pDevice = CastDevice(hDevice);
660bf215546Sopenharmony_ci   if (!CheckPredicate(pDevice)) {
661bf215546Sopenharmony_ci      return;
662bf215546Sopenharmony_ci   }
663bf215546Sopenharmony_ci
664bf215546Sopenharmony_ci   struct pipe_context *pipe = pDevice->pipe;
665bf215546Sopenharmony_ci   Resource *pDstResource = CastResource(hDstResource);
666bf215546Sopenharmony_ci   Resource *pSrcResource = CastResource(hSrcResource);
667bf215546Sopenharmony_ci   struct pipe_resource *dst_resource = pDstResource->resource;
668bf215546Sopenharmony_ci   struct pipe_resource *src_resource = pSrcResource->resource;
669bf215546Sopenharmony_ci   bool compatible;
670bf215546Sopenharmony_ci
671bf215546Sopenharmony_ci   assert(dst_resource->target == src_resource->target);
672bf215546Sopenharmony_ci   assert(dst_resource->width0 == src_resource->width0);
673bf215546Sopenharmony_ci   assert(dst_resource->height0 == src_resource->height0);
674bf215546Sopenharmony_ci   assert(dst_resource->depth0 == src_resource->depth0);
675bf215546Sopenharmony_ci   assert(dst_resource->last_level == src_resource->last_level);
676bf215546Sopenharmony_ci   assert(dst_resource->array_size == src_resource->array_size);
677bf215546Sopenharmony_ci
678bf215546Sopenharmony_ci   compatible = areResourcesCompatible(src_resource, dst_resource);
679bf215546Sopenharmony_ci
680bf215546Sopenharmony_ci   /* could also use one 3d copy for arrays */
681bf215546Sopenharmony_ci   for (unsigned layer = 0; layer < dst_resource->array_size; ++layer) {
682bf215546Sopenharmony_ci      for (unsigned level = 0; level <= dst_resource->last_level; ++level) {
683bf215546Sopenharmony_ci         struct pipe_box box;
684bf215546Sopenharmony_ci         box.x = 0;
685bf215546Sopenharmony_ci         box.y = 0;
686bf215546Sopenharmony_ci         box.z = 0 + layer;
687bf215546Sopenharmony_ci         box.width  = u_minify(dst_resource->width0,  level);
688bf215546Sopenharmony_ci         box.height = u_minify(dst_resource->height0, level);
689bf215546Sopenharmony_ci         box.depth  = u_minify(dst_resource->depth0,  level);
690bf215546Sopenharmony_ci
691bf215546Sopenharmony_ci	 if (compatible) {
692bf215546Sopenharmony_ci            pipe->resource_copy_region(pipe,
693bf215546Sopenharmony_ci                                       dst_resource, level,
694bf215546Sopenharmony_ci                                       0, 0, layer,
695bf215546Sopenharmony_ci                                       src_resource, level,
696bf215546Sopenharmony_ci                                       &box);
697bf215546Sopenharmony_ci         } else {
698bf215546Sopenharmony_ci            util_resource_copy_region(pipe,
699bf215546Sopenharmony_ci                                      dst_resource, level,
700bf215546Sopenharmony_ci                                      0, 0, layer,
701bf215546Sopenharmony_ci                                      src_resource, level,
702bf215546Sopenharmony_ci                                      &box);
703bf215546Sopenharmony_ci         }
704bf215546Sopenharmony_ci      }
705bf215546Sopenharmony_ci   }
706bf215546Sopenharmony_ci}
707bf215546Sopenharmony_ci
708bf215546Sopenharmony_ci
709bf215546Sopenharmony_ci/*
710bf215546Sopenharmony_ci * ----------------------------------------------------------------------
711bf215546Sopenharmony_ci *
712bf215546Sopenharmony_ci * ResourceCopyRegion --
713bf215546Sopenharmony_ci *
714bf215546Sopenharmony_ci *    The ResourceCopyRegion function copies a source subresource
715bf215546Sopenharmony_ci *    region to a location on a destination subresource.
716bf215546Sopenharmony_ci *
717bf215546Sopenharmony_ci * ----------------------------------------------------------------------
718bf215546Sopenharmony_ci */
719bf215546Sopenharmony_ci
720bf215546Sopenharmony_civoid APIENTRY
721bf215546Sopenharmony_ciResourceCopyRegion(D3D10DDI_HDEVICE hDevice,                // IN
722bf215546Sopenharmony_ci                   D3D10DDI_HRESOURCE hDstResource,         // IN
723bf215546Sopenharmony_ci                   UINT DstSubResource,                     // IN
724bf215546Sopenharmony_ci                   UINT DstX,                               // IN
725bf215546Sopenharmony_ci                   UINT DstY,                               // IN
726bf215546Sopenharmony_ci                   UINT DstZ,                               // IN
727bf215546Sopenharmony_ci                   D3D10DDI_HRESOURCE hSrcResource,         // IN
728bf215546Sopenharmony_ci                   UINT SrcSubResource,                     // IN
729bf215546Sopenharmony_ci                   __in_opt const D3D10_DDI_BOX *pSrcBox)   // IN (optional)
730bf215546Sopenharmony_ci{
731bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
732bf215546Sopenharmony_ci
733bf215546Sopenharmony_ci   Device *pDevice = CastDevice(hDevice);
734bf215546Sopenharmony_ci   if (!CheckPredicate(pDevice)) {
735bf215546Sopenharmony_ci      return;
736bf215546Sopenharmony_ci   }
737bf215546Sopenharmony_ci
738bf215546Sopenharmony_ci   struct pipe_context *pipe = pDevice->pipe;
739bf215546Sopenharmony_ci   Resource *pDstResource = CastResource(hDstResource);
740bf215546Sopenharmony_ci   Resource *pSrcResource = CastResource(hSrcResource);
741bf215546Sopenharmony_ci   struct pipe_resource *dst_resource = pDstResource->resource;
742bf215546Sopenharmony_ci   struct pipe_resource *src_resource = pSrcResource->resource;
743bf215546Sopenharmony_ci
744bf215546Sopenharmony_ci   unsigned dst_level = DstSubResource % (dst_resource->last_level + 1);
745bf215546Sopenharmony_ci   unsigned dst_layer = DstSubResource / (dst_resource->last_level + 1);
746bf215546Sopenharmony_ci   unsigned src_level = SrcSubResource % (src_resource->last_level + 1);
747bf215546Sopenharmony_ci   unsigned src_layer = SrcSubResource / (src_resource->last_level + 1);
748bf215546Sopenharmony_ci
749bf215546Sopenharmony_ci   struct pipe_box src_box;
750bf215546Sopenharmony_ci   if (pSrcBox) {
751bf215546Sopenharmony_ci      src_box.x = pSrcBox->left;
752bf215546Sopenharmony_ci      src_box.y = pSrcBox->top;
753bf215546Sopenharmony_ci      src_box.z = pSrcBox->front + src_layer;
754bf215546Sopenharmony_ci      src_box.width  = pSrcBox->right  - pSrcBox->left;
755bf215546Sopenharmony_ci      src_box.height = pSrcBox->bottom - pSrcBox->top;
756bf215546Sopenharmony_ci      src_box.depth  = pSrcBox->back   - pSrcBox->front;
757bf215546Sopenharmony_ci   } else {
758bf215546Sopenharmony_ci      src_box.x = 0;
759bf215546Sopenharmony_ci      src_box.y = 0;
760bf215546Sopenharmony_ci      src_box.z = 0 + src_layer;
761bf215546Sopenharmony_ci      src_box.width  = u_minify(src_resource->width0,  src_level);
762bf215546Sopenharmony_ci      src_box.height = u_minify(src_resource->height0, src_level);
763bf215546Sopenharmony_ci      src_box.depth  = u_minify(src_resource->depth0,  src_level);
764bf215546Sopenharmony_ci   }
765bf215546Sopenharmony_ci
766bf215546Sopenharmony_ci   if (areResourcesCompatible(src_resource, dst_resource)) {
767bf215546Sopenharmony_ci      pipe->resource_copy_region(pipe,
768bf215546Sopenharmony_ci                                 dst_resource, dst_level,
769bf215546Sopenharmony_ci                                 DstX, DstY, DstZ + dst_layer,
770bf215546Sopenharmony_ci                                 src_resource, src_level,
771bf215546Sopenharmony_ci                                 &src_box);
772bf215546Sopenharmony_ci   } else {
773bf215546Sopenharmony_ci      util_resource_copy_region(pipe,
774bf215546Sopenharmony_ci                                dst_resource, dst_level,
775bf215546Sopenharmony_ci                                DstX, DstY, DstZ + dst_layer,
776bf215546Sopenharmony_ci                                src_resource, src_level,
777bf215546Sopenharmony_ci                                &src_box);
778bf215546Sopenharmony_ci   }
779bf215546Sopenharmony_ci}
780bf215546Sopenharmony_ci
781bf215546Sopenharmony_ci
782bf215546Sopenharmony_ci/*
783bf215546Sopenharmony_ci * ----------------------------------------------------------------------
784bf215546Sopenharmony_ci *
785bf215546Sopenharmony_ci * ResourceResolveSubResource --
786bf215546Sopenharmony_ci *
787bf215546Sopenharmony_ci *    The ResourceResolveSubResource function resolves
788bf215546Sopenharmony_ci *    multiple samples to one pixel.
789bf215546Sopenharmony_ci *
790bf215546Sopenharmony_ci * ----------------------------------------------------------------------
791bf215546Sopenharmony_ci */
792bf215546Sopenharmony_ci
793bf215546Sopenharmony_civoid APIENTRY
794bf215546Sopenharmony_ciResourceResolveSubResource(D3D10DDI_HDEVICE hDevice,        // IN
795bf215546Sopenharmony_ci                           D3D10DDI_HRESOURCE hDstResource, // IN
796bf215546Sopenharmony_ci                           UINT DstSubResource,             // IN
797bf215546Sopenharmony_ci                           D3D10DDI_HRESOURCE hSrcResource, // IN
798bf215546Sopenharmony_ci                           UINT SrcSubResource,             // IN
799bf215546Sopenharmony_ci                           DXGI_FORMAT ResolveFormat)       // IN
800bf215546Sopenharmony_ci{
801bf215546Sopenharmony_ci   LOG_UNSUPPORTED_ENTRYPOINT();
802bf215546Sopenharmony_ci}
803bf215546Sopenharmony_ci
804bf215546Sopenharmony_ci
805bf215546Sopenharmony_ci/*
806bf215546Sopenharmony_ci * ----------------------------------------------------------------------
807bf215546Sopenharmony_ci *
808bf215546Sopenharmony_ci * ResourceIsStagingBusy --
809bf215546Sopenharmony_ci *
810bf215546Sopenharmony_ci *    The ResourceIsStagingBusy function determines whether a
811bf215546Sopenharmony_ci *    resource is currently being used by the graphics pipeline.
812bf215546Sopenharmony_ci *
813bf215546Sopenharmony_ci * ----------------------------------------------------------------------
814bf215546Sopenharmony_ci */
815bf215546Sopenharmony_ci
816bf215546Sopenharmony_ciBOOL APIENTRY
817bf215546Sopenharmony_ciResourceIsStagingBusy(D3D10DDI_HDEVICE hDevice,       // IN
818bf215546Sopenharmony_ci                      D3D10DDI_HRESOURCE hResource)   // IN
819bf215546Sopenharmony_ci{
820bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
821bf215546Sopenharmony_ci
822bf215546Sopenharmony_ci   /* ignore */
823bf215546Sopenharmony_ci
824bf215546Sopenharmony_ci   return FALSE;
825bf215546Sopenharmony_ci}
826bf215546Sopenharmony_ci
827bf215546Sopenharmony_ci
828bf215546Sopenharmony_ci/*
829bf215546Sopenharmony_ci * ----------------------------------------------------------------------
830bf215546Sopenharmony_ci *
831bf215546Sopenharmony_ci * ResourceReadAfterWriteHazard --
832bf215546Sopenharmony_ci *
833bf215546Sopenharmony_ci *    The ResourceReadAfterWriteHazard function informs the user-mode
834bf215546Sopenharmony_ci *    display driver that the specified resource was used as an output
835bf215546Sopenharmony_ci *    from the graphics processing unit (GPU) and that the resource
836bf215546Sopenharmony_ci *    will be used as an input to the GPU.
837bf215546Sopenharmony_ci *
838bf215546Sopenharmony_ci * ----------------------------------------------------------------------
839bf215546Sopenharmony_ci */
840bf215546Sopenharmony_ci
841bf215546Sopenharmony_civoid APIENTRY
842bf215546Sopenharmony_ciResourceReadAfterWriteHazard(D3D10DDI_HDEVICE hDevice,      // IN
843bf215546Sopenharmony_ci                             D3D10DDI_HRESOURCE hResource)  // IN
844bf215546Sopenharmony_ci{
845bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
846bf215546Sopenharmony_ci
847bf215546Sopenharmony_ci   /* Not actually necessary */
848bf215546Sopenharmony_ci}
849bf215546Sopenharmony_ci
850bf215546Sopenharmony_ci
851bf215546Sopenharmony_ci/*
852bf215546Sopenharmony_ci * ----------------------------------------------------------------------
853bf215546Sopenharmony_ci *
854bf215546Sopenharmony_ci * ResourceUpdateSubResourceUP --
855bf215546Sopenharmony_ci *
856bf215546Sopenharmony_ci *    The ResourceUpdateSubresourceUP function updates a
857bf215546Sopenharmony_ci *    destination subresource region from a source
858bf215546Sopenharmony_ci *    system memory region.
859bf215546Sopenharmony_ci *
860bf215546Sopenharmony_ci * ----------------------------------------------------------------------
861bf215546Sopenharmony_ci */
862bf215546Sopenharmony_ci
863bf215546Sopenharmony_civoid APIENTRY
864bf215546Sopenharmony_ciResourceUpdateSubResourceUP(D3D10DDI_HDEVICE hDevice,                // IN
865bf215546Sopenharmony_ci                            D3D10DDI_HRESOURCE hDstResource,         // IN
866bf215546Sopenharmony_ci                            UINT DstSubResource,                     // IN
867bf215546Sopenharmony_ci                            __in_opt const D3D10_DDI_BOX *pDstBox,   // IN
868bf215546Sopenharmony_ci                            __in const void *pSysMemUP,              // IN
869bf215546Sopenharmony_ci                            UINT RowPitch,                           // IN
870bf215546Sopenharmony_ci                            UINT DepthPitch)                         // IN
871bf215546Sopenharmony_ci{
872bf215546Sopenharmony_ci   LOG_ENTRYPOINT();
873bf215546Sopenharmony_ci
874bf215546Sopenharmony_ci   Device *pDevice = CastDevice(hDevice);
875bf215546Sopenharmony_ci   if (!CheckPredicate(pDevice)) {
876bf215546Sopenharmony_ci      return;
877bf215546Sopenharmony_ci   }
878bf215546Sopenharmony_ci
879bf215546Sopenharmony_ci   struct pipe_context *pipe = pDevice->pipe;
880bf215546Sopenharmony_ci   Resource *pDstResource = CastResource(hDstResource);
881bf215546Sopenharmony_ci   struct pipe_resource *dst_resource = pDstResource->resource;
882bf215546Sopenharmony_ci
883bf215546Sopenharmony_ci   unsigned level;
884bf215546Sopenharmony_ci   struct pipe_box box;
885bf215546Sopenharmony_ci
886bf215546Sopenharmony_ci   if (pDstBox) {
887bf215546Sopenharmony_ci      UINT DstMipLevels = dst_resource->last_level + 1;
888bf215546Sopenharmony_ci      level = DstSubResource % DstMipLevels;
889bf215546Sopenharmony_ci      unsigned dst_layer = DstSubResource / DstMipLevels;
890bf215546Sopenharmony_ci      box.x = pDstBox->left;
891bf215546Sopenharmony_ci      box.y = pDstBox->top;
892bf215546Sopenharmony_ci      box.z = pDstBox->front + dst_layer;
893bf215546Sopenharmony_ci      box.width  = pDstBox->right  - pDstBox->left;
894bf215546Sopenharmony_ci      box.height = pDstBox->bottom - pDstBox->top;
895bf215546Sopenharmony_ci      box.depth  = pDstBox->back   - pDstBox->front;
896bf215546Sopenharmony_ci   } else {
897bf215546Sopenharmony_ci      subResourceBox(dst_resource, DstSubResource, &level, &box);
898bf215546Sopenharmony_ci   }
899bf215546Sopenharmony_ci
900bf215546Sopenharmony_ci   struct pipe_transfer *transfer;
901bf215546Sopenharmony_ci   void *map;
902bf215546Sopenharmony_ci   if (pDstResource->buffer) {
903bf215546Sopenharmony_ci      map = pipe->buffer_map(pipe,
904bf215546Sopenharmony_ci                              dst_resource,
905bf215546Sopenharmony_ci                              level,
906bf215546Sopenharmony_ci                              PIPE_MAP_WRITE | PIPE_MAP_DISCARD_RANGE,
907bf215546Sopenharmony_ci                              &box,
908bf215546Sopenharmony_ci                              &transfer);
909bf215546Sopenharmony_ci   } else {
910bf215546Sopenharmony_ci      map = pipe->texture_map(pipe,
911bf215546Sopenharmony_ci                              dst_resource,
912bf215546Sopenharmony_ci                              level,
913bf215546Sopenharmony_ci                              PIPE_MAP_WRITE | PIPE_MAP_DISCARD_RANGE,
914bf215546Sopenharmony_ci                              &box,
915bf215546Sopenharmony_ci                              &transfer);
916bf215546Sopenharmony_ci   }
917bf215546Sopenharmony_ci   assert(map);
918bf215546Sopenharmony_ci   if (map) {
919bf215546Sopenharmony_ci      for (int z = 0; z < box.depth; ++z) {
920bf215546Sopenharmony_ci         ubyte *dst = (ubyte*)map + z*transfer->layer_stride;
921bf215546Sopenharmony_ci         const ubyte *src = (const ubyte*)pSysMemUP + z*DepthPitch;
922bf215546Sopenharmony_ci         util_copy_rect(dst,
923bf215546Sopenharmony_ci                        dst_resource->format,
924bf215546Sopenharmony_ci                        transfer->stride,
925bf215546Sopenharmony_ci                        0, 0, box.width, box.height,
926bf215546Sopenharmony_ci                        src,
927bf215546Sopenharmony_ci                        RowPitch,
928bf215546Sopenharmony_ci                        0, 0);
929bf215546Sopenharmony_ci      }
930bf215546Sopenharmony_ci      if (pDstResource->buffer) {
931bf215546Sopenharmony_ci         pipe_buffer_unmap(pipe, transfer);
932bf215546Sopenharmony_ci      } else {
933bf215546Sopenharmony_ci         pipe_texture_unmap(pipe, transfer);
934bf215546Sopenharmony_ci      }
935bf215546Sopenharmony_ci   }
936bf215546Sopenharmony_ci}
937bf215546Sopenharmony_ci
938