1
/**********************************************************************
3
* Copyright (C) Imagination Technologies Ltd. All rights reserved.
5
* This program is free software; you can redistribute it and/or modify it
6
* under the terms and conditions of the GNU General Public License,
7
* version 2, as published by the Free Software Foundation.
9
* This program is distributed in the hope it will be useful but, except
10
* as otherwise stated in writing, without any warranty; without even the
11
* implied warranty of merchantability or fitness for a particular purpose.
12
* See the GNU General Public License for more details.
14
* You should have received a copy of the GNU General Public License along with
15
* this program; if not, write to the Free Software Foundation, Inc.,
16
* 51 Franklin St - Fifth Floor, Boston, MA 02110-1301 USA.
18
* The full GNU General Public License is included in this distribution in
19
* the file called "COPYING".
21
* Contact Information:
22
* Imagination Technologies Ltd. <gpl-support@imgtec.com>
23
* Home Park Estate, Kings Langley, Herts, WD4 8LZ, UK
25
******************************************************************************/
29
#include "services_headers.h"
30
#include "sgx_bridge_km.h"
31
#include "sgxapi_km.h"
33
#include "sgxinfokm.h"
34
#include "pvr_bridge_km.h"
39
#pragma message("TODO: Review use of OS_PAGEABLE vs OS_NON_PAGEABLE")
44
static IMPLEMENT_LIST_INSERT(PVRSRV_STUB_PBDESC)
45
static IMPLEMENT_LIST_REMOVE(PVRSRV_STUB_PBDESC)
47
static PRESMAN_ITEM psResItemCreateSharedPB = IMG_NULL;
48
static PVRSRV_PER_PROCESS_DATA *psPerProcCreateSharedPB = IMG_NULL;
50
static PVRSRV_ERROR SGXCleanupSharedPBDescCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy);
51
static PVRSRV_ERROR SGXCleanupSharedPBDescCreateLockCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy);
53
IMG_EXPORT PVRSRV_ERROR
54
SGXFindSharedPBDescKM(PVRSRV_PER_PROCESS_DATA *psPerProc,
55
IMG_HANDLE hDevCookie,
56
IMG_BOOL bLockOnFailure,
57
IMG_UINT32 ui32TotalPBSize,
58
IMG_HANDLE *phSharedPBDesc,
59
PVRSRV_KERNEL_MEM_INFO **ppsSharedPBDescKernelMemInfo,
60
PVRSRV_KERNEL_MEM_INFO **ppsHWPBDescKernelMemInfo,
61
PVRSRV_KERNEL_MEM_INFO **ppsBlockKernelMemInfo,
62
PVRSRV_KERNEL_MEM_INFO **ppsHWBlockKernelMemInfo,
63
PVRSRV_KERNEL_MEM_INFO ***pppsSharedPBDescSubKernelMemInfos,
64
IMG_UINT32 *ui32SharedPBDescSubKernelMemInfosCount)
66
PVRSRV_STUB_PBDESC *psStubPBDesc;
67
PVRSRV_KERNEL_MEM_INFO **ppsSharedPBDescSubKernelMemInfos=IMG_NULL;
68
PVRSRV_SGXDEV_INFO *psSGXDevInfo;
71
psSGXDevInfo = ((PVRSRV_DEVICE_NODE *)hDevCookie)->pvDevice;
73
psStubPBDesc = psSGXDevInfo->psStubPBDescListKM;
74
if (psStubPBDesc != IMG_NULL)
77
PRESMAN_ITEM psResItem;
79
if(psStubPBDesc->ui32TotalPBSize != ui32TotalPBSize)
81
PVR_DPF((PVR_DBG_WARNING,
82
"SGXFindSharedPBDescKM: Shared PB requested with different size (0x%x) from existing shared PB (0x%x) - requested size ignored",
83
ui32TotalPBSize, psStubPBDesc->ui32TotalPBSize));
86
if(OSAllocMem(PVRSRV_OS_PAGEABLE_HEAP,
87
sizeof(PVRSRV_KERNEL_MEM_INFO *)
88
* psStubPBDesc->ui32SubKernelMemInfosCount,
89
(IMG_VOID **)&ppsSharedPBDescSubKernelMemInfos,
91
"Array of Kernel Memory Info") != PVRSRV_OK)
93
PVR_DPF((PVR_DBG_ERROR, "SGXFindSharedPBDescKM: OSAllocMem failed"));
95
eError = PVRSRV_ERROR_OUT_OF_MEMORY;
99
psResItem = ResManRegisterRes(psPerProc->hResManContext,
100
RESMAN_TYPE_SHARED_PB_DESC,
103
&SGXCleanupSharedPBDescCallback);
105
if (psResItem == IMG_NULL)
107
OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
108
sizeof(PVRSRV_KERNEL_MEM_INFO *) * psStubPBDesc->ui32SubKernelMemInfosCount,
109
ppsSharedPBDescSubKernelMemInfos,
113
PVR_DPF((PVR_DBG_ERROR, "SGXFindSharedPBDescKM: ResManRegisterRes failed"));
115
eError = PVRSRV_ERROR_UNABLE_TO_REGISTER_RESOURCE;
119
*ppsSharedPBDescKernelMemInfo = psStubPBDesc->psSharedPBDescKernelMemInfo;
120
*ppsHWPBDescKernelMemInfo = psStubPBDesc->psHWPBDescKernelMemInfo;
121
*ppsBlockKernelMemInfo = psStubPBDesc->psBlockKernelMemInfo;
122
*ppsHWBlockKernelMemInfo = psStubPBDesc->psHWBlockKernelMemInfo;
124
*ui32SharedPBDescSubKernelMemInfosCount =
125
psStubPBDesc->ui32SubKernelMemInfosCount;
127
*pppsSharedPBDescSubKernelMemInfos = ppsSharedPBDescSubKernelMemInfos;
129
for(i=0; i<psStubPBDesc->ui32SubKernelMemInfosCount; i++)
131
ppsSharedPBDescSubKernelMemInfos[i] =
132
psStubPBDesc->ppsSubKernelMemInfos[i];
135
psStubPBDesc->ui32RefCount++;
136
*phSharedPBDesc = (IMG_HANDLE)psResItem;
143
if (psResItemCreateSharedPB == IMG_NULL)
145
psResItemCreateSharedPB = ResManRegisterRes(psPerProc->hResManContext,
146
RESMAN_TYPE_SHARED_PB_DESC_CREATE_LOCK,
149
&SGXCleanupSharedPBDescCreateLockCallback);
151
if (psResItemCreateSharedPB == IMG_NULL)
153
PVR_DPF((PVR_DBG_ERROR, "SGXFindSharedPBDescKM: ResManRegisterRes failed"));
155
eError = PVRSRV_ERROR_UNABLE_TO_REGISTER_RESOURCE;
158
PVR_ASSERT(psPerProcCreateSharedPB == IMG_NULL);
159
psPerProcCreateSharedPB = psPerProc;
163
eError = PVRSRV_ERROR_PROCESSING_BLOCKED;
167
*phSharedPBDesc = IMG_NULL;
174
SGXCleanupSharedPBDescKM(PVRSRV_STUB_PBDESC *psStubPBDescIn)
178
PVRSRV_DEVICE_NODE *psDeviceNode;
180
psDeviceNode = (PVRSRV_DEVICE_NODE*)psStubPBDescIn->hDevCookie;
185
psStubPBDescIn->ui32RefCount--;
186
if (psStubPBDescIn->ui32RefCount == 0)
188
IMG_DEV_VIRTADDR sHWPBDescDevVAddr = psStubPBDescIn->sHWPBDescDevVAddr;
189
List_PVRSRV_STUB_PBDESC_Remove(psStubPBDescIn);
190
for(i=0 ; i<psStubPBDescIn->ui32SubKernelMemInfosCount; i++)
193
PVRSRVFreeDeviceMemKM(psStubPBDescIn->hDevCookie,
194
psStubPBDescIn->ppsSubKernelMemInfos[i]);
197
OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
198
sizeof(PVRSRV_KERNEL_MEM_INFO *) * psStubPBDescIn->ui32SubKernelMemInfosCount,
199
psStubPBDescIn->ppsSubKernelMemInfos,
201
psStubPBDescIn->ppsSubKernelMemInfos = IMG_NULL;
203
PVRSRVFreeSharedSysMemoryKM(psStubPBDescIn->psBlockKernelMemInfo);
205
PVRSRVFreeDeviceMemKM(psStubPBDescIn->hDevCookie, psStubPBDescIn->psHWBlockKernelMemInfo);
207
PVRSRVFreeDeviceMemKM(psStubPBDescIn->hDevCookie, psStubPBDescIn->psHWPBDescKernelMemInfo);
209
PVRSRVFreeSharedSysMemoryKM(psStubPBDescIn->psSharedPBDescKernelMemInfo);
211
OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
212
sizeof(PVRSRV_STUB_PBDESC),
218
SGXCleanupRequest(psDeviceNode,
220
PVRSRV_CLEANUPCMD_PB,
227
static PVRSRV_ERROR SGXCleanupSharedPBDescCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy)
229
PVRSRV_STUB_PBDESC *psStubPBDesc = (PVRSRV_STUB_PBDESC *)pvParam;
231
PVR_UNREFERENCED_PARAMETER(ui32Param);
232
PVR_UNREFERENCED_PARAMETER(bDummy);
234
return SGXCleanupSharedPBDescKM(psStubPBDesc);
237
static PVRSRV_ERROR SGXCleanupSharedPBDescCreateLockCallback(IMG_PVOID pvParam, IMG_UINT32 ui32Param, IMG_BOOL bDummy)
240
PVRSRV_PER_PROCESS_DATA *psPerProc = (PVRSRV_PER_PROCESS_DATA *)pvParam;
241
PVR_ASSERT(psPerProc == psPerProcCreateSharedPB);
243
PVR_UNREFERENCED_PARAMETER(pvParam);
246
PVR_UNREFERENCED_PARAMETER(ui32Param);
247
PVR_UNREFERENCED_PARAMETER(bDummy);
249
psPerProcCreateSharedPB = IMG_NULL;
250
psResItemCreateSharedPB = IMG_NULL;
256
IMG_EXPORT PVRSRV_ERROR
257
SGXUnrefSharedPBDescKM(IMG_HANDLE hSharedPBDesc)
259
PVR_ASSERT(hSharedPBDesc != IMG_NULL);
261
return ResManFreeResByPtr(hSharedPBDesc, CLEANUP_WITH_POLL);
265
IMG_EXPORT PVRSRV_ERROR
266
SGXAddSharedPBDescKM(PVRSRV_PER_PROCESS_DATA *psPerProc,
267
IMG_HANDLE hDevCookie,
268
PVRSRV_KERNEL_MEM_INFO *psSharedPBDescKernelMemInfo,
269
PVRSRV_KERNEL_MEM_INFO *psHWPBDescKernelMemInfo,
270
PVRSRV_KERNEL_MEM_INFO *psBlockKernelMemInfo,
271
PVRSRV_KERNEL_MEM_INFO *psHWBlockKernelMemInfo,
272
IMG_UINT32 ui32TotalPBSize,
273
IMG_HANDLE *phSharedPBDesc,
274
PVRSRV_KERNEL_MEM_INFO **ppsSharedPBDescSubKernelMemInfos,
275
IMG_UINT32 ui32SharedPBDescSubKernelMemInfosCount,
276
IMG_DEV_VIRTADDR sHWPBDescDevVAddr)
278
PVRSRV_STUB_PBDESC *psStubPBDesc=IMG_NULL;
279
PVRSRV_ERROR eRet = PVRSRV_ERROR_INVALID_PERPROC;
281
PVRSRV_SGXDEV_INFO *psSGXDevInfo;
282
PRESMAN_ITEM psResItem;
285
if (psPerProcCreateSharedPB != psPerProc)
291
PVR_ASSERT(psResItemCreateSharedPB != IMG_NULL);
293
ResManFreeResByPtr(psResItemCreateSharedPB, CLEANUP_WITH_POLL);
295
PVR_ASSERT(psResItemCreateSharedPB == IMG_NULL);
296
PVR_ASSERT(psPerProcCreateSharedPB == IMG_NULL);
299
psSGXDevInfo = (PVRSRV_SGXDEV_INFO *)((PVRSRV_DEVICE_NODE *)hDevCookie)->pvDevice;
301
psStubPBDesc = psSGXDevInfo->psStubPBDescListKM;
302
if (psStubPBDesc != IMG_NULL)
304
if(psStubPBDesc->ui32TotalPBSize != ui32TotalPBSize)
306
PVR_DPF((PVR_DBG_WARNING,
307
"SGXAddSharedPBDescKM: Shared PB requested with different size (0x%x) from existing shared PB (0x%x) - requested size ignored",
308
ui32TotalPBSize, psStubPBDesc->ui32TotalPBSize));
313
psResItem = ResManRegisterRes(psPerProc->hResManContext,
314
RESMAN_TYPE_SHARED_PB_DESC,
317
&SGXCleanupSharedPBDescCallback);
318
if (psResItem == IMG_NULL)
320
PVR_DPF((PVR_DBG_ERROR,
321
"SGXAddSharedPBDescKM: "
322
"Failed to register existing shared "
323
"PBDesc with the resource manager"));
328
psStubPBDesc->ui32RefCount++;
330
*phSharedPBDesc = (IMG_HANDLE)psResItem;
335
if(OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
336
sizeof(PVRSRV_STUB_PBDESC),
337
(IMG_VOID **)&psStubPBDesc,
339
"Stub Parameter Buffer Description") != PVRSRV_OK)
341
PVR_DPF((PVR_DBG_ERROR, "SGXAddSharedPBDescKM: Failed to alloc "
343
eRet = PVRSRV_ERROR_OUT_OF_MEMORY;
348
psStubPBDesc->ppsSubKernelMemInfos = IMG_NULL;
350
if(OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
351
sizeof(PVRSRV_KERNEL_MEM_INFO *)
352
* ui32SharedPBDescSubKernelMemInfosCount,
353
(IMG_VOID **)&psStubPBDesc->ppsSubKernelMemInfos,
355
"Array of Kernel Memory Info") != PVRSRV_OK)
357
PVR_DPF((PVR_DBG_ERROR, "SGXAddSharedPBDescKM: "
359
"StubPBDesc->ppsSubKernelMemInfos"));
360
eRet = PVRSRV_ERROR_OUT_OF_MEMORY;
364
if(PVRSRVDissociateMemFromResmanKM(psSharedPBDescKernelMemInfo)
370
if(PVRSRVDissociateMemFromResmanKM(psHWPBDescKernelMemInfo)
376
if(PVRSRVDissociateMemFromResmanKM(psBlockKernelMemInfo)
382
if(PVRSRVDissociateMemFromResmanKM(psHWBlockKernelMemInfo)
388
psStubPBDesc->ui32RefCount = 1;
389
psStubPBDesc->ui32TotalPBSize = ui32TotalPBSize;
390
psStubPBDesc->psSharedPBDescKernelMemInfo = psSharedPBDescKernelMemInfo;
391
psStubPBDesc->psHWPBDescKernelMemInfo = psHWPBDescKernelMemInfo;
392
psStubPBDesc->psBlockKernelMemInfo = psBlockKernelMemInfo;
393
psStubPBDesc->psHWBlockKernelMemInfo = psHWBlockKernelMemInfo;
395
psStubPBDesc->ui32SubKernelMemInfosCount =
396
ui32SharedPBDescSubKernelMemInfosCount;
397
for(i=0; i<ui32SharedPBDescSubKernelMemInfosCount; i++)
399
psStubPBDesc->ppsSubKernelMemInfos[i] = ppsSharedPBDescSubKernelMemInfos[i];
400
if(PVRSRVDissociateMemFromResmanKM(ppsSharedPBDescSubKernelMemInfos[i])
403
PVR_DPF((PVR_DBG_ERROR, "SGXAddSharedPBDescKM: "
404
"Failed to dissociate shared PBDesc "
410
psStubPBDesc->sHWPBDescDevVAddr = sHWPBDescDevVAddr;
412
psResItem = ResManRegisterRes(psPerProc->hResManContext,
413
RESMAN_TYPE_SHARED_PB_DESC,
416
&SGXCleanupSharedPBDescCallback);
417
if (psResItem == IMG_NULL)
419
PVR_DPF((PVR_DBG_ERROR, "SGXAddSharedPBDescKM: "
420
"Failed to register shared PBDesc "
421
" with the resource manager"));
424
psStubPBDesc->hDevCookie = hDevCookie;
427
List_PVRSRV_STUB_PBDESC_Insert(&(psSGXDevInfo->psStubPBDescListKM),
430
*phSharedPBDesc = (IMG_HANDLE)psResItem;
437
if(psStubPBDesc->ppsSubKernelMemInfos)
439
OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
440
sizeof(PVRSRV_KERNEL_MEM_INFO *) * ui32SharedPBDescSubKernelMemInfosCount,
441
psStubPBDesc->ppsSubKernelMemInfos,
443
psStubPBDesc->ppsSubKernelMemInfos = IMG_NULL;
445
OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
446
sizeof(PVRSRV_STUB_PBDESC),
453
for (i = 0; i < ui32SharedPBDescSubKernelMemInfosCount; i++)
455
PVRSRVFreeDeviceMemKM(hDevCookie, ppsSharedPBDescSubKernelMemInfos[i]);
458
PVRSRVFreeSharedSysMemoryKM(psSharedPBDescKernelMemInfo);
459
PVRSRVFreeDeviceMemKM(hDevCookie, psHWPBDescKernelMemInfo);
461
PVRSRVFreeSharedSysMemoryKM(psBlockKernelMemInfo);
462
PVRSRVFreeDeviceMemKM(hDevCookie, psHWBlockKernelMemInfo);