IMG_INTERNAL IMG_VOID _DevmemImportStructRelease(DEVMEM_IMPORT *psImport) { PVR_ASSERT(psImport->ui32RefCount != 0); OSLockAcquire(psImport->hLock); DEVMEM_REFCOUNT_PRINT("%s (%p) %d->%d", __FUNCTION__, psImport, psImport->ui32RefCount, psImport->ui32RefCount-1); if (--psImport->ui32RefCount == 0) { OSLockRelease(psImport->hLock); BridgePMRUnrefPMR(psImport->hBridge, psImport->hPMR); OSLockDestroy(psImport->sCPUImport.hLock); OSLockDestroy(psImport->sDeviceImport.hLock); OSLockDestroy(psImport->hLock); OSFreeMem(psImport); } else { OSLockRelease(psImport->hLock); } }
IMG_INTERNAL IMG_VOID _DevmemImportDiscard(DEVMEM_IMPORT *psImport) { PVR_ASSERT(psImport->ui32RefCount == 0); OSLockDestroy(psImport->sCPUImport.hLock); OSLockDestroy(psImport->sDeviceImport.hLock); OSLockDestroy(psImport->hLock); OSFreeMem(psImport); }
IMG_INTERNAL IMG_VOID _DevmemMemDescDiscard(DEVMEM_MEMDESC *psMemDesc) { PVR_ASSERT(psMemDesc->ui32RefCount == 0); OSLockDestroy(psMemDesc->sCPUMemDesc.hLock); OSLockDestroy(psMemDesc->sDeviceMemDesc.hLock); OSLockDestroy(psMemDesc->hLock); OSFreeMem(psMemDesc); }
IMG_VOID ServerSyncDeinit(IMG_VOID) { PVRSRVUnregisterDbgRequestNotify(g_hNotify); OSLockDestroy(g_hListLock); #if defined(PVRSRV_ENABLE_FULL_SYNC_TRACKING) OSLockAcquire(g_hSyncRecordListLock); dllist_foreach_node(&g_sSyncRecordList, _SyncRecordListDestroy, IMG_NULL); OSLockRelease(g_hSyncRecordListLock); PVRSRVUnregisterDbgRequestNotify(g_hSyncRecordNotify); OSLockDestroy(g_hSyncRecordListLock); #endif }
IMG_INTERNAL PVRSRV_ERROR _DevmemMemDescAlloc(DEVMEM_MEMDESC **ppsMemDesc) { DEVMEM_MEMDESC *psMemDesc; PVRSRV_ERROR eError; psMemDesc = OSAllocMem(sizeof(DEVMEM_MEMDESC)); if (psMemDesc == IMG_NULL) { eError = PVRSRV_ERROR_OUT_OF_MEMORY; goto failAlloc; } /* Structure must be zero'd incase it needs to be freed before it is initialised! */ OSMemSet(psMemDesc, 0, sizeof(DEVMEM_MEMDESC)); eError = OSLockCreate(&psMemDesc->hLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto failMDLock; } eError = OSLockCreate(&psMemDesc->sDeviceMemDesc.hLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto failDMDLock; } eError = OSLockCreate(&psMemDesc->sCPUMemDesc.hLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto failCMDLock; } *ppsMemDesc = psMemDesc; return PVRSRV_OK; failCMDLock: OSLockDestroy(psMemDesc->sDeviceMemDesc.hLock); failDMDLock: OSLockDestroy(psMemDesc->hLock); failMDLock: OSFreeMem(psMemDesc); failAlloc: PVR_ASSERT(eError != PVRSRV_OK); return eError; }
IMG_VOID ServerSyncUnref(SERVER_SYNC_PRIMITIVE *psSync) { IMG_UINT32 ui32RefCount; OSLockAcquire(psSync->hLock); ui32RefCount = --psSync->ui32RefCount; OSLockRelease(psSync->hLock); if (ui32RefCount == 0) { SYNC_REFCOUNT_PRINT("%s: Server sync %p, refcount = %d", __FUNCTION__, psSync, ui32RefCount); /* Remove the sync from the global list */ OSLockAcquire(g_hListLock); dllist_remove_node(&psSync->sNode); OSLockRelease(g_hListLock); OSLockDestroy(psSync->hLock); SyncPrimFree(psSync->psSync); OSFreeMem(psSync); } else { SYNC_REFCOUNT_PRINT("%s: Server sync %p, refcount = %d", __FUNCTION__, psSync, ui32RefCount); } }
static IMG_VOID _SyncPrimitiveBlockUnref(SYNC_PRIMITIVE_BLOCK *psSyncBlk) { IMG_UINT32 ui32RefCount; OSLockAcquire(psSyncBlk->hLock); ui32RefCount = --psSyncBlk->ui32RefCount; OSLockRelease(psSyncBlk->hLock); if (ui32RefCount == 0) { PVRSRV_DEVICE_NODE *psDevNode = psSyncBlk->psDevNode; SYNC_REFCOUNT_PRINT("%s: Sync block %p, refcount = %d (remove)", __FUNCTION__, psSyncBlk, ui32RefCount); _SyncConnectionRemoveBlock(psSyncBlk); OSLockDestroy(psSyncBlk->hLock); DevmemUnexport(psSyncBlk->psMemDesc, &psSyncBlk->sExportCookie); DevmemReleaseCpuVirtAddr(psSyncBlk->psMemDesc); psDevNode->pfnFreeUFOBlock(psDevNode, psSyncBlk->psMemDesc); OSFreeMem(psSyncBlk); } else { SYNC_REFCOUNT_PRINT("%s: Sync block %p, refcount = %d", __FUNCTION__, psSyncBlk, ui32RefCount); } }
static PVRSRV_ERROR SyncRecordListInit(IMG_VOID) { PVRSRV_ERROR eError; eError = OSLockCreate(&g_hSyncRecordListLock, LOCK_TYPE_NONE); if (eError != PVRSRV_OK) { goto fail_lock_create; } dllist_init(&g_sSyncRecordList); eError = PVRSRVRegisterDbgRequestNotify(&g_hSyncRecordNotify, _SyncRecordRequest, DEBUG_REQUEST_SERVERSYNC, IMG_NULL); if (eError != PVRSRV_OK) { goto fail_dbg_register; } return PVRSRV_OK; fail_dbg_register: OSLockDestroy(g_hSyncRecordListLock);; fail_lock_create: return eError; }
PVRSRV_ERROR ServerSyncInit(IMG_VOID) { PVRSRV_ERROR eError; eError = OSLockCreate(&g_hListLock, LOCK_TYPE_NONE); if (eError != PVRSRV_OK) { goto fail_lock_create; } dllist_init(&g_sAllServerSyncs); eError = PVRSRVRegisterDbgRequestNotify(&g_hNotify, _ServerSyncDebugRequest, DEBUG_REQUEST_SERVERSYNC, IMG_NULL); if (eError != PVRSRV_OK) { goto fail_dbg_register; } return PVRSRV_OK; fail_dbg_register: OSLockDestroy(g_hListLock);; fail_lock_create: return eError; }
IMG_INTERNAL IMG_VOID _DevmemMemDescRelease(DEVMEM_MEMDESC *psMemDesc) { PVR_ASSERT(psMemDesc != NULL); PVR_ASSERT(psMemDesc->ui32RefCount != 0); OSLockAcquire(psMemDesc->hLock); DEVMEM_REFCOUNT_PRINT("%s (%p) %d->%d", __FUNCTION__, psMemDesc, psMemDesc->ui32RefCount, psMemDesc->ui32RefCount-1); if (--psMemDesc->ui32RefCount == 0) { OSLockRelease(psMemDesc->hLock); if (!psMemDesc->psImport->bExportable) { RA_Free(psMemDesc->psImport->sDeviceImport.psHeap->psSubAllocRA, psMemDesc->psImport->sDeviceImport.sDevVAddr.uiAddr + psMemDesc->uiOffset); } else { _DevmemImportStructRelease(psMemDesc->psImport); } OSLockDestroy(psMemDesc->sCPUMemDesc.hLock); OSLockDestroy(psMemDesc->sDeviceMemDesc.hLock); OSLockDestroy(psMemDesc->hLock); OSFreeMem(psMemDesc); } else { OSLockRelease(psMemDesc->hLock); } }
/* SCPDestroy */ IMG_EXPORT IMG_VOID IMG_CALLCONV SCPDestroy(SCP_CONTEXT *psContext) { /* The caller must ensure that they completed all queued operations before calling this function */ PVR_ASSERT(psContext->ui32ReadOffset == psContext->ui32WriteOffset); PVRSRVServerSyncRequesterUnregisterKM(psContext->psSyncRequesterID); OSLockDestroy(psContext->hLock); psContext->hLock = IMG_NULL; OSFreeMem(psContext->pvCCB); psContext->pvCCB = IMG_NULL; OSFreeMem(psContext); }
IMG_VOID TLDeInit(IMG_VOID) { PVR_DPF_ENTERED; if (sTLGlobalData.uiClientCnt) { PVR_DPF((PVR_DBG_ERROR, "TLDeInit transport layer but %d client streams are still connected", sTLGlobalData.uiClientCnt)); sTLGlobalData.uiClientCnt = 0; } /* Clean up the SNODE list */ if (sTLGlobalData.psHead) { while (sTLGlobalData.psHead) { RemoveAndFreeStreamNode(sTLGlobalData.psHead); } /* Leave psHead NULL on loop exit */ } /* Clean up the TL global event object */ if (sTLGlobalData.hTLEventObj) { OSEventObjectDestroy(sTLGlobalData.hTLEventObj); sTLGlobalData.hTLEventObj = NULL; } /* Destroy the TL global data lock */ if (sTLGlobalData.hTLGDLock) { OSLockDestroy (sTLGlobalData.hTLGDLock); sTLGlobalData.hTLGDLock = NULL; } sTLGlobalData.psRgxDevNode = NULL; PVR_DPF_RETURN; }
PVRSRV_ERROR ServerSyncInit(IMG_VOID) { PVRSRV_ERROR eError; eError = OSLockCreate(&g_hListLock, LOCK_TYPE_NONE); if (eError != PVRSRV_OK) { goto fail_lock_create; } dllist_init(&g_sAllServerSyncs); eError = PVRSRVRegisterDbgRequestNotify(&g_hNotify, _ServerSyncDebugRequest, DEBUG_REQUEST_SERVERSYNC, IMG_NULL); if (eError != PVRSRV_OK) { goto fail_dbg_register; } #if defined(PVRSRV_ENABLE_FULL_SYNC_TRACKING) eError = SyncRecordListInit(); if (eError != PVRSRV_OK) { goto fail_record_list; } #endif return PVRSRV_OK; #if defined(PVRSRV_ENABLE_FULL_SYNC_TRACKING) fail_record_list: PVRSRVUnregisterDbgRequestNotify(g_hNotify); #endif fail_dbg_register: OSLockDestroy(g_hListLock);; fail_lock_create: return eError; }
/* TLInit must only be called once at driver initialisation for one device. * An assert is provided to check this condition on debug builds. */ PVRSRV_ERROR TLInit(PVRSRV_DEVICE_NODE *psDevNode) { PVRSRV_ERROR eError; PVR_DPF_ENTERED; PVR_ASSERT(psDevNode); PVR_ASSERT(sTLGlobalData.psRgxDevNode==0); /* Store the RGX device node for later use in devmem buffer allocations */ sTLGlobalData.psRgxDevNode = (IMG_VOID*)psDevNode; /* Allocate a lock for TL global data, to be used while updating the TL data. * This is for making TL global data muti-thread safe */ eError = OSLockCreate (&sTLGlobalData.hTLGDLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto e0; } /* Allocate the event object used to signal global TL events such as * new stream created */ eError = OSEventObjectCreate("TLGlobalEventObj", &sTLGlobalData.hTLEventObj); if (eError != PVRSRV_OK) { goto e1; } PVR_DPF_RETURN_OK; /* Don't allow the driver to start up on error */ e1: OSLockDestroy (sTLGlobalData.hTLGDLock); sTLGlobalData.hTLGDLock = NULL; e0: PVR_DPF_RETURN_RC (eError); }
static IMG_VOID _SyncConnectionUnref(SYNC_CONNECTION_DATA *psSyncConnectionData) { IMG_UINT32 ui32RefCount; OSLockAcquire(psSyncConnectionData->hLock); ui32RefCount = --psSyncConnectionData->ui32RefCount; OSLockRelease(psSyncConnectionData->hLock); if (ui32RefCount == 0) { SYNC_REFCOUNT_PRINT("%s: Sync connection %p, refcount = %d", __FUNCTION__, psSyncConnectionData, ui32RefCount); PVR_ASSERT(dllist_is_empty(&psSyncConnectionData->sListHead)); OSLockDestroy(psSyncConnectionData->hLock); OSFreeMem(psSyncConnectionData); } else { SYNC_REFCOUNT_PRINT("%s: Sync connection %p, refcount = %d", __FUNCTION__, psSyncConnectionData, ui32RefCount); } }
/* Allocate and init an import structure */ IMG_INTERNAL PVRSRV_ERROR _DevmemImportStructAlloc(IMG_HANDLE hBridge, IMG_BOOL bExportable, DEVMEM_IMPORT **ppsImport) { DEVMEM_IMPORT *psImport; PVRSRV_ERROR eError; psImport = OSAllocMem(sizeof *psImport); if (psImport == IMG_NULL) { return PVRSRV_ERROR_OUT_OF_MEMORY; } /* Setup some known bad values for things we don't have yet */ psImport->sDeviceImport.hReservation = LACK_OF_RESERVATION_POISON; psImport->sDeviceImport.hMapping = LACK_OF_MAPPING_POISON; psImport->sDeviceImport.psHeap = IMG_NULL; psImport->sDeviceImport.bMapped = IMG_FALSE; eError = OSLockCreate(&psImport->sDeviceImport.hLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto failDIOSLockCreate; } psImport->sCPUImport.hOSMMapData = IMG_NULL; psImport->sCPUImport.pvCPUVAddr = IMG_NULL; eError = OSLockCreate(&psImport->sCPUImport.hLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto failCIOSLockCreate; } /* Set up common elements */ psImport->hBridge = hBridge; psImport->bExportable = bExportable; /* Setup refcounts */ psImport->sDeviceImport.ui32RefCount = 0; psImport->sCPUImport.ui32RefCount = 0; psImport->ui32RefCount = 0; /* Create the lock */ eError = OSLockCreate(&psImport->hLock, LOCK_TYPE_PASSIVE); if (eError != PVRSRV_OK) { goto failILockAlloc; } #if !defined(__KERNEL__) && defined(SUPPORT_ION) psImport->sCPUImport.iDmaBufFd = -1; #endif *ppsImport = psImport; return PVRSRV_OK; failILockAlloc: OSLockDestroy(psImport->sCPUImport.hLock); failCIOSLockCreate: OSLockDestroy(psImport->sDeviceImport.hLock); failDIOSLockCreate: OSFreeMem(psImport); PVR_ASSERT(eError != PVRSRV_OK); return eError; }
IMG_VOID ServerSyncDeinit(IMG_VOID) { PVRSRVUnregisterDbgRequestNotify(g_hNotify); OSLockDestroy(g_hListLock); }