1 /**********************************************************************
3 * Copyright(c) 2008 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 "buffer_manager.h"
31 #include "pvr_bridge_km.h"
36 #include "pvr_events.h"
38 #include "pvrversion.h"
40 #define HASH_TAB_INIT_SIZE 32
41 enum PVRSRV_ERROR AllocateDeviceID(struct SYS_DATA *psSysData, u32 *pui32DevID)
43 struct SYS_DEVICE_ID *psDeviceWalker;
44 struct SYS_DEVICE_ID *psDeviceEnd;
46 psDeviceWalker = &psSysData->sDeviceID[0];
47 psDeviceEnd = psDeviceWalker + psSysData->ui32NumDevices;
49 while (psDeviceWalker < psDeviceEnd) {
50 if (!psDeviceWalker->bInUse) {
51 psDeviceWalker->bInUse = IMG_TRUE;
52 *pui32DevID = psDeviceWalker->uiID;
58 PVR_DPF(PVR_DBG_ERROR,
59 "AllocateDeviceID: No free and valid device IDs available!");
61 PVR_ASSERT(psDeviceWalker < psDeviceEnd);
63 return PVRSRV_ERROR_GENERIC;
66 enum PVRSRV_ERROR FreeDeviceID(struct SYS_DATA *psSysData, u32 ui32DevID)
68 struct SYS_DEVICE_ID *psDeviceWalker;
69 struct SYS_DEVICE_ID *psDeviceEnd;
71 psDeviceWalker = &psSysData->sDeviceID[0];
72 psDeviceEnd = psDeviceWalker + psSysData->ui32NumDevices;
74 while (psDeviceWalker < psDeviceEnd) {
75 if ((psDeviceWalker->uiID == ui32DevID) &&
76 (psDeviceWalker->bInUse)) {
77 psDeviceWalker->bInUse = IMG_FALSE;
83 PVR_DPF(PVR_DBG_ERROR,
84 "FreeDeviceID: no matching dev ID that is in use!");
86 PVR_ASSERT(psDeviceWalker < psDeviceEnd);
88 return PVRSRV_ERROR_GENERIC;
91 enum PVRSRV_ERROR PVRSRVEnumerateDevicesKM(u32 *pui32NumDevices,
92 struct PVRSRV_DEVICE_IDENTIFIER *psDevIdList)
94 enum PVRSRV_ERROR eError;
95 struct SYS_DATA *psSysData;
96 struct PVRSRV_DEVICE_NODE *psDeviceNode;
99 if (!pui32NumDevices || !psDevIdList) {
100 PVR_DPF(PVR_DBG_ERROR,
101 "PVRSRVEnumerateDevicesKM: Invalid params");
102 return PVRSRV_ERROR_INVALID_PARAMS;
105 eError = SysAcquireData(&psSysData);
106 if (eError != PVRSRV_OK) {
107 PVR_DPF(PVR_DBG_ERROR,
108 "PVRSRVEnumerateDevicesKM: Failed to get SysData");
112 for (i = 0; i < PVRSRV_MAX_DEVICES; i++)
113 psDevIdList[i].eDeviceType = PVRSRV_DEVICE_TYPE_UNKNOWN;
115 *pui32NumDevices = 0;
117 psDeviceNode = psSysData->psDeviceNodeList;
118 for (i = 0; psDeviceNode != NULL; i++) {
119 if (psDeviceNode->sDevId.eDeviceType !=
120 PVRSRV_DEVICE_TYPE_EXT) {
121 *psDevIdList++ = psDeviceNode->sDevId;
122 (*pui32NumDevices)++;
124 psDeviceNode = psDeviceNode->psNext;
130 enum PVRSRV_ERROR PVRSRVInit(struct SYS_DATA *psSysData)
132 enum PVRSRV_ERROR eError;
134 eError = ResManInit();
135 if (eError != PVRSRV_OK)
138 eError = PVRSRVPerProcessDataInit();
139 if (eError != PVRSRV_OK)
142 eError = PVRSRVHandleInit();
143 if (eError != PVRSRV_OK)
146 psSysData->eCurrentPowerState = PVRSRV_POWER_STATE_D0;
147 psSysData->eFailedPowerState = PVRSRV_POWER_Unspecified;
150 psSysData->bPowerUpPDumped = IMG_FALSE;
153 if (OSAllocMem(PVRSRV_PAGEABLE_SELECT,
154 sizeof(struct PVRSRV_EVENTOBJECT),
155 (void **) &psSysData->psGlobalEventObject,
160 if (OSEventObjectCreate("PVRSRV_GLOBAL_EVENTOBJECT",
161 psSysData->psGlobalEventObject) != PVRSRV_OK)
167 PVRSRVDeInit(psSysData);
171 void PVRSRVDeInit(struct SYS_DATA *psSysData)
173 enum PVRSRV_ERROR eError;
175 PVR_UNREFERENCED_PARAMETER(psSysData);
177 if (psSysData == NULL) {
178 PVR_DPF(PVR_DBG_ERROR, "PVRSRVDeInit: "
179 "PVRSRVHandleDeInit failed - invalid param");
183 if (psSysData->psGlobalEventObject) {
184 OSEventObjectDestroy(psSysData->psGlobalEventObject);
185 OSFreeMem(PVRSRV_PAGEABLE_SELECT,
186 sizeof(struct PVRSRV_EVENTOBJECT),
187 psSysData->psGlobalEventObject, NULL);
190 eError = PVRSRVHandleDeInit();
191 if (eError != PVRSRV_OK)
192 PVR_DPF(PVR_DBG_ERROR,
193 "PVRSRVDeInit: PVRSRVHandleDeInit failed");
195 eError = PVRSRVPerProcessDataDeInit();
196 if (eError != PVRSRV_OK)
197 PVR_DPF(PVR_DBG_ERROR,
198 "PVRSRVDeInit: PVRSRVPerProcessDataDeInit failed");
203 enum PVRSRV_ERROR PVRSRVRegisterDevice(struct SYS_DATA *psSysData,
204 enum PVRSRV_ERROR(*pfnRegisterDevice)
205 (struct PVRSRV_DEVICE_NODE *),
206 u32 ui32SOCInterruptBit,
207 u32 *pui32DeviceIndex)
209 enum PVRSRV_ERROR eError;
210 struct PVRSRV_DEVICE_NODE *psDeviceNode;
212 if (OSAllocMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
213 sizeof(struct PVRSRV_DEVICE_NODE),
214 (void **) &psDeviceNode, NULL) != PVRSRV_OK) {
215 PVR_DPF(PVR_DBG_ERROR, "PVRSRVRegisterDevice : "
216 "Failed to alloc memory for psDeviceNode");
217 return PVRSRV_ERROR_OUT_OF_MEMORY;
219 OSMemSet(psDeviceNode, 0, sizeof(struct PVRSRV_DEVICE_NODE));
221 eError = pfnRegisterDevice(psDeviceNode);
222 if (eError != PVRSRV_OK) {
223 OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
224 sizeof(struct PVRSRV_DEVICE_NODE), psDeviceNode,
226 PVR_DPF(PVR_DBG_ERROR, "PVRSRVRegisterDevice : "
227 "Failed to register device");
228 return PVRSRV_ERROR_DEVICE_REGISTER_FAILED;
231 psDeviceNode->ui32RefCount = 1;
232 psDeviceNode->psSysData = psSysData;
233 psDeviceNode->ui32SOCInterruptBit = ui32SOCInterruptBit;
235 AllocateDeviceID(psSysData, &psDeviceNode->sDevId.ui32DeviceIndex);
237 psDeviceNode->psNext = psSysData->psDeviceNodeList;
238 psSysData->psDeviceNodeList = psDeviceNode;
240 *pui32DeviceIndex = psDeviceNode->sDevId.ui32DeviceIndex;
245 enum PVRSRV_ERROR PVRSRVInitialiseDevice(u32 ui32DevIndex)
247 struct PVRSRV_DEVICE_NODE *psDeviceNode;
248 struct SYS_DATA *psSysData;
249 enum PVRSRV_ERROR eError;
251 PVR_DPF(PVR_DBG_MESSAGE, "PVRSRVInitialiseDevice");
253 eError = SysAcquireData(&psSysData);
254 if (eError != PVRSRV_OK) {
255 PVR_DPF(PVR_DBG_ERROR,
256 "PVRSRVInitialiseDevice: Failed to get SysData");
260 psDeviceNode = psSysData->psDeviceNodeList;
262 while (psDeviceNode) {
263 if (psDeviceNode->sDevId.ui32DeviceIndex == ui32DevIndex)
265 psDeviceNode = psDeviceNode->psNext;
268 PVR_DPF(PVR_DBG_ERROR,
269 "PVRSRVInitialiseDevice: requested device is not present");
270 return PVRSRV_ERROR_INIT_FAILURE;
274 PVR_ASSERT(psDeviceNode->ui32RefCount > 0);
276 eError = PVRSRVResManConnect(NULL, &psDeviceNode->hResManContext);
277 if (eError != PVRSRV_OK) {
278 PVR_DPF(PVR_DBG_ERROR, "PVRSRVInitialiseDevice: "
279 "Failed PVRSRVResManConnect call");
283 if (psDeviceNode->pfnInitDevice != NULL) {
284 eError = psDeviceNode->pfnInitDevice(psDeviceNode);
285 if (eError != PVRSRV_OK) {
286 PVR_DPF(PVR_DBG_ERROR, "PVRSRVInitialiseDevice: "
287 "Failed InitDevice call");
292 psDeviceNode->sync_table = HASH_Create(HASH_TAB_INIT_SIZE);
293 if (psDeviceNode->sync_table == NULL) {
294 PVR_DPF(PVR_DBG_ERROR, "InitDevInfo: "
295 "Couldn't create syncobject hash table");
296 eError = PVRSRV_ERROR_GENERIC;
303 enum PVRSRV_ERROR PVRSRVFinaliseSystem(IMG_BOOL bInitSuccessful)
305 struct PVRSRV_DEVICE_NODE *psDeviceNode;
306 struct SYS_DATA *psSysData;
307 enum PVRSRV_ERROR eError;
309 PVR_DPF(PVR_DBG_MESSAGE, "PVRSRVFinaliseSystem");
311 eError = SysAcquireData(&psSysData);
312 if (eError != PVRSRV_OK) {
313 PVR_DPF(PVR_DBG_ERROR,
314 "PVRSRVFinaliseSystem: Failed to get SysData");
318 if (bInitSuccessful) {
319 eError = SysFinalise();
320 if (eError != PVRSRV_OK) {
321 PVR_DPF(PVR_DBG_ERROR,
322 "PVRSRVFinaliseSystem: SysFinalise failed (%d)",
327 psDeviceNode = psSysData->psDeviceNodeList;
328 while (psDeviceNode) {
330 PVRSRVSetDevicePowerStateKM(
331 psDeviceNode->sDevId.ui32DeviceIndex,
332 PVRSRV_POWER_Unspecified);
333 if (eError != PVRSRV_OK)
334 PVR_DPF(PVR_DBG_ERROR, "PVRSRVFinaliseSystem: "
335 "Failed PVRSRVSetDevicePowerStateKM "
336 "call (device index: %d)",
337 psDeviceNode->sDevId.ui32DeviceIndex);
338 psDeviceNode = psDeviceNode->psNext;
341 psDeviceNode = psSysData->psDeviceNodeList;
342 while (psDeviceNode) {
343 if (psDeviceNode->pfnInitDeviceCompatCheck) {
344 eError = PVRSRVDevInitCompatCheck(psDeviceNode);
345 if (eError != PVRSRV_OK) {
346 PVR_DPF(PVR_DBG_ERROR,
347 "PVRSRVFinaliseSystem: "
348 "Failed PVRSRVDevInitCompatCheck "
349 "call (device index: %d)",
350 psDeviceNode->sDevId.
355 psDeviceNode = psDeviceNode->psNext;
364 enum PVRSRV_ERROR PVRSRVDevInitCompatCheck(struct PVRSRV_DEVICE_NODE
368 return psDeviceNode->pfnInitDeviceCompatCheck(psDeviceNode);
371 enum PVRSRV_ERROR PVRSRVAcquireDeviceDataKM(u32 ui32DevIndex,
372 enum PVRSRV_DEVICE_TYPE eDeviceType,
375 struct PVRSRV_DEVICE_NODE *psDeviceNode;
376 struct SYS_DATA *psSysData;
377 enum PVRSRV_ERROR eError;
379 PVR_DPF(PVR_DBG_MESSAGE, "PVRSRVAcquireDeviceDataKM");
381 eError = SysAcquireData(&psSysData);
382 if (eError != PVRSRV_OK) {
383 PVR_DPF(PVR_DBG_ERROR,
384 "PVRSRVAcquireDeviceDataKM: Failed to get SysData");
388 psDeviceNode = psSysData->psDeviceNodeList;
390 if (eDeviceType != PVRSRV_DEVICE_TYPE_UNKNOWN) {
391 while (psDeviceNode) {
392 if (psDeviceNode->sDevId.eDeviceType == eDeviceType)
394 psDeviceNode = psDeviceNode->psNext;
397 while (psDeviceNode) {
398 if (psDeviceNode->sDevId.ui32DeviceIndex ==
402 psDeviceNode = psDeviceNode->psNext;
406 PVR_DPF(PVR_DBG_ERROR,
407 "PVRSRVAcquireDeviceDataKM: requested device is not present");
408 return PVRSRV_ERROR_INIT_FAILURE;
412 PVR_ASSERT(psDeviceNode->ui32RefCount > 0);
415 *phDevCookie = (void *) psDeviceNode;
420 enum PVRSRV_ERROR PVRSRVDeinitialiseDevice(u32 ui32DevIndex)
422 struct PVRSRV_DEVICE_NODE *psDeviceNode;
423 struct PVRSRV_DEVICE_NODE **ppsDevNode;
424 struct SYS_DATA *psSysData;
425 enum PVRSRV_ERROR eError;
427 eError = SysAcquireData(&psSysData);
428 if (eError != PVRSRV_OK) {
429 PVR_DPF(PVR_DBG_ERROR,
430 "PVRSRVDeinitialiseDevice: Failed to get SysData");
434 ppsDevNode = &psSysData->psDeviceNodeList;
435 while (*ppsDevNode) {
436 if ((*ppsDevNode)->sDevId.ui32DeviceIndex == ui32DevIndex) {
437 psDeviceNode = *ppsDevNode;
440 ppsDevNode = &((*ppsDevNode)->psNext);
443 PVR_DPF(PVR_DBG_ERROR,
444 "PVRSRVDeinitialiseDevice: requested device %d is not present",
447 return PVRSRV_ERROR_GENERIC;
451 eError = PVRSRVSetDevicePowerStateKM(ui32DevIndex,
452 PVRSRV_POWER_STATE_D3);
453 if (eError != PVRSRV_OK) {
454 PVR_DPF(PVR_DBG_ERROR, "PVRSRVDeinitialiseDevice: "
455 "Failed PVRSRVSetDevicePowerStateKM call");
459 HASH_Delete(psDeviceNode->sync_table);
461 ResManFreeResByCriteria(psDeviceNode->hResManContext,
462 RESMAN_CRITERIA_RESTYPE,
463 RESMAN_TYPE_DEVICEMEM_ALLOCATION,
466 if (psDeviceNode->pfnDeInitDevice != NULL) {
467 eError = psDeviceNode->pfnDeInitDevice(psDeviceNode);
468 if (eError != PVRSRV_OK) {
469 PVR_DPF(PVR_DBG_ERROR, "PVRSRVDeinitialiseDevice: "
470 "Failed DeInitDevice call");
475 PVRSRVResManDisconnect(psDeviceNode->hResManContext, IMG_TRUE);
476 psDeviceNode->hResManContext = NULL;
478 *ppsDevNode = psDeviceNode->psNext;
480 FreeDeviceID(psSysData, ui32DevIndex);
481 OSFreeMem(PVRSRV_OS_NON_PAGEABLE_HEAP,
482 sizeof(struct PVRSRV_DEVICE_NODE), psDeviceNode, NULL);
487 enum PVRSRV_ERROR PollForValueKM(u32 __iomem *pui32LinMemAddr,
488 u32 ui32Value, u32 ui32Mask, u32 ui32Waitus,
493 uiMaxTime = ui32Tries * ui32Waitus;
495 LOOP_UNTIL_TIMEOUT(uiMaxTime) {
496 if ((readl(pui32LinMemAddr) & ui32Mask) == ui32Value)
499 END_LOOP_UNTIL_TIMEOUT();
501 return PVRSRV_ERROR_GENERIC;
505 enum PVRSRV_ERROR PVRSRVGetMiscInfoKM(struct PVRSRV_MISC_INFO *psMiscInfo)
507 struct SYS_DATA *psSysData;
508 enum PVRSRV_ERROR eError;
511 PVR_DPF(PVR_DBG_ERROR,
512 "PVRSRVGetMiscInfoKM: invalid parameters");
513 return PVRSRV_ERROR_INVALID_PARAMS;
516 psMiscInfo->ui32StatePresent = 0;
518 if (psMiscInfo->ui32StateRequest & ~(
519 PVRSRV_MISC_INFO_TIMER_PRESENT |
520 PVRSRV_MISC_INFO_CLOCKGATE_PRESENT |
521 PVRSRV_MISC_INFO_MEMSTATS_PRESENT |
522 PVRSRV_MISC_INFO_GLOBALEVENTOBJECT_PRESENT |
523 PVRSRV_MISC_INFO_DDKVERSION_PRESENT)) {
524 PVR_DPF(PVR_DBG_ERROR,
525 "PVRSRVGetMiscInfoKM: invalid state request flags");
526 return PVRSRV_ERROR_INVALID_PARAMS;
529 eError = SysAcquireData(&psSysData);
530 if (eError != PVRSRV_OK) {
531 PVR_DPF(PVR_DBG_ERROR,
532 "PVRSRVGetMiscInfoKM: Failed to get SysData");
536 if (((psMiscInfo->ui32StateRequest &
537 PVRSRV_MISC_INFO_TIMER_PRESENT) != 0UL) &&
538 (psSysData->pvSOCTimerRegisterKM != NULL)) {
539 psMiscInfo->ui32StatePresent |= PVRSRV_MISC_INFO_TIMER_PRESENT;
540 psMiscInfo->pvSOCTimerRegisterKM =
541 psSysData->pvSOCTimerRegisterKM;
542 psMiscInfo->hSOCTimerRegisterOSMemHandle =
543 psSysData->hSOCTimerRegisterOSMemHandle;
545 psMiscInfo->pvSOCTimerRegisterKM = NULL;
546 psMiscInfo->hSOCTimerRegisterOSMemHandle = NULL;
549 if (((psMiscInfo->ui32StateRequest &
550 PVRSRV_MISC_INFO_CLOCKGATE_PRESENT) != 0UL) &&
551 (psSysData->pvSOCClockGateRegsBase != NULL)) {
552 psMiscInfo->ui32StatePresent |=
553 PVRSRV_MISC_INFO_CLOCKGATE_PRESENT;
554 psMiscInfo->pvSOCClockGateRegs =
555 psSysData->pvSOCClockGateRegsBase;
556 psMiscInfo->ui32SOCClockGateRegsSize =
557 psSysData->ui32SOCClockGateRegsSize;
560 if (((psMiscInfo->ui32StateRequest &
561 PVRSRV_MISC_INFO_MEMSTATS_PRESENT) != 0UL) &&
562 (psMiscInfo->pszMemoryStr != NULL)) {
563 struct RA_ARENA **ppArena;
564 struct BM_HEAP *psBMHeap;
565 struct BM_CONTEXT *psBMContext;
566 struct PVRSRV_DEVICE_NODE *psDeviceNode;
571 pszStr = psMiscInfo->pszMemoryStr;
572 ui32StrLen = psMiscInfo->ui32MemoryStrLen;
574 psMiscInfo->ui32StatePresent |=
575 PVRSRV_MISC_INFO_MEMSTATS_PRESENT;
577 ppArena = &psSysData->apsLocalDevMemArena[0];
579 CHECK_SPACE(ui32StrLen);
581 OSSNPrintf(pszStr, 100, "\nLocal Backing Store:\n");
582 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
584 RA_GetStats(*ppArena, &pszStr, &ui32StrLen);
589 psDeviceNode = psSysData->psDeviceNodeList;
590 while (psDeviceNode) {
591 CHECK_SPACE(ui32StrLen);
593 OSSNPrintf(pszStr, 100, "\n\nDevice Type %d:\n",
594 psDeviceNode->sDevId.eDeviceType);
595 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
597 if (psDeviceNode->sDevMemoryInfo.pBMKernelContext) {
598 CHECK_SPACE(ui32StrLen);
600 OSSNPrintf(pszStr, 100,
601 "\nKernel Context:\n");
602 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
605 psDeviceNode->sDevMemoryInfo.
606 pBMKernelContext->psBMHeap;
608 if (psBMHeap->pImportArena) {
609 RA_GetStats(psBMHeap->
615 if (psBMHeap->pVMArena) {
616 RA_GetStats(psBMHeap->pVMArena,
620 psBMHeap = psBMHeap->psNext;
624 psBMContext = psDeviceNode->sDevMemoryInfo.pBMContext;
625 while (psBMContext) {
626 CHECK_SPACE(ui32StrLen);
628 OSSNPrintf(pszStr, 100,
629 "\nApplication Context (hDevMemContext) 0x%08X:\n",
630 (void *)psBMContext);
631 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
633 psBMHeap = psBMContext->psBMHeap;
635 if (psBMHeap->pImportArena) {
636 RA_GetStats(psBMHeap->
642 if (psBMHeap->pVMArena) {
643 RA_GetStats(psBMHeap->pVMArena,
647 psBMHeap = psBMHeap->psNext;
649 psBMContext = psBMContext->psNext;
651 psDeviceNode = psDeviceNode->psNext;
654 i32Count = OSSNPrintf(pszStr, 100, "\n\0");
655 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
658 if (((psMiscInfo->ui32StateRequest &
659 PVRSRV_MISC_INFO_GLOBALEVENTOBJECT_PRESENT) != 0UL) &&
660 (psSysData->psGlobalEventObject != NULL)) {
661 psMiscInfo->ui32StatePresent |=
662 PVRSRV_MISC_INFO_GLOBALEVENTOBJECT_PRESENT;
663 psMiscInfo->sGlobalEventObject =
664 *psSysData->psGlobalEventObject;
667 if (((psMiscInfo->ui32StateRequest &
668 PVRSRV_MISC_INFO_DDKVERSION_PRESENT) != 0UL) &&
669 ((psMiscInfo->ui32StateRequest &
670 PVRSRV_MISC_INFO_MEMSTATS_PRESENT) == 0UL) &&
671 (psMiscInfo->pszMemoryStr != NULL)) {
674 u32 ui32LenStrPerNum = 12;
677 psMiscInfo->ui32StatePresent |=
678 PVRSRV_MISC_INFO_DDKVERSION_PRESENT;
680 psMiscInfo->aui32DDKVersion[0] = PVRVERSION_MAJ;
681 psMiscInfo->aui32DDKVersion[1] = PVRVERSION_MIN;
682 psMiscInfo->aui32DDKVersion[2] = PVRVERSION_BRANCH;
683 psMiscInfo->aui32DDKVersion[3] = PVRVERSION_BUILD;
685 pszStr = psMiscInfo->pszMemoryStr;
686 ui32StrLen = psMiscInfo->ui32MemoryStrLen;
688 for (i = 0; i < 4; i++) {
689 if (ui32StrLen < ui32LenStrPerNum)
690 return PVRSRV_ERROR_INVALID_PARAMS;
692 i32Count = OSSNPrintf(pszStr, ui32LenStrPerNum, "%ld",
693 psMiscInfo->aui32DDKVersion[i]);
694 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
696 i32Count = OSSNPrintf(pszStr, 2, ".");
697 UPDATE_SPACE(pszStr, i32Count, ui32StrLen);
705 enum PVRSRV_ERROR PVRSRVGetFBStatsKM(u32 *pui32Total, u32 *pui32Available)
707 u32 ui32Total = 0, i = 0;
708 u32 ui32Available = 0;
713 while (BM_ContiguousStatistics(i, &ui32Total, &ui32Available) ==
715 *pui32Total += ui32Total;
716 *pui32Available += ui32Available;
724 IMG_BOOL PVRSRVDeviceLISR(struct PVRSRV_DEVICE_NODE *psDeviceNode)
726 struct SYS_DATA *psSysData;
727 IMG_BOOL bStatus = IMG_FALSE;
728 u32 ui32InterruptSource;
731 PVR_DPF(PVR_DBG_ERROR, "PVRSRVDeviceLISR: Invalid params\n");
734 psSysData = psDeviceNode->psSysData;
736 ui32InterruptSource = SysGetInterruptSource(psSysData, psDeviceNode);
737 if (ui32InterruptSource & psDeviceNode->ui32SOCInterruptBit) {
738 if (psDeviceNode->pfnDeviceISR != NULL)
740 (*psDeviceNode->pfnDeviceISR) (psDeviceNode->
743 SysClearInterrupts(psSysData,
744 psDeviceNode->ui32SOCInterruptBit);
751 IMG_BOOL PVRSRVSystemLISR(void *pvSysData)
753 struct SYS_DATA *psSysData = pvSysData;
754 IMG_BOOL bStatus = IMG_FALSE;
755 u32 ui32InterruptSource;
756 u32 ui32ClearInterrupts = 0;
757 struct PVRSRV_DEVICE_NODE *psDeviceNode;
760 PVR_DPF(PVR_DBG_ERROR, "PVRSRVSystemLISR: Invalid params\n");
764 ui32InterruptSource = SysGetInterruptSource(psSysData, NULL);
766 if (ui32InterruptSource == 0)
769 psDeviceNode = psSysData->psDeviceNodeList;
770 while (psDeviceNode != NULL) {
771 if (psDeviceNode->pfnDeviceISR != NULL)
772 if (ui32InterruptSource & psDeviceNode->
773 ui32SOCInterruptBit) {
774 if ((*psDeviceNode->pfnDeviceISR)
775 (psDeviceNode->pvISRData))
778 ui32ClearInterrupts |=
779 psDeviceNode->ui32SOCInterruptBit;
781 psDeviceNode = psDeviceNode->psNext;
784 SysClearInterrupts(psSysData, ui32ClearInterrupts);
790 void PVRSRVMISR(void *pvSysData)
792 struct SYS_DATA *psSysData = pvSysData;
793 struct PVRSRV_DEVICE_NODE *psDeviceNode;
796 PVR_DPF(PVR_DBG_ERROR, "PVRSRVMISR: Invalid params\n");
802 if (pvr_is_disabled()) {
807 psDeviceNode = psSysData->psDeviceNodeList;
808 while (psDeviceNode != NULL) {
809 if (psDeviceNode->pfnDeviceMISR != NULL)
810 (*psDeviceNode->pfnDeviceMISR)(psDeviceNode->
812 psDeviceNode = psDeviceNode->psNext;
815 PVRSRVProcessQueues(IMG_FALSE);
817 if (psSysData->psGlobalEventObject) {
819 psSysData->psGlobalEventObject->hOSEventKM;
821 OSEventObjectSignal(hOSEventKM);
824 pvr_handle_sync_events();
829 enum PVRSRV_ERROR PVRSRVProcessConnect(u32 ui32PID)
831 return PVRSRVPerProcessDataConnect(ui32PID);
834 void PVRSRVProcessDisconnect(u32 ui32PID)
836 PVRSRVPerProcessDataDisconnect(ui32PID);
839 enum PVRSRV_ERROR PVRSRVSaveRestoreLiveSegments(void *hArena, u8 *pbyBuffer,
840 u32 *puiBufSize, IMG_BOOL bSave)
842 u32 uiBytesSaved = 0;
843 void *pvLocalMemCPUVAddr;
844 struct RA_SEGMENT_DETAILS sSegDetails;
847 return PVRSRV_ERROR_INVALID_PARAMS;
849 sSegDetails.uiSize = 0;
850 sSegDetails.sCpuPhyAddr.uiAddr = 0;
851 sSegDetails.hSegment = NULL;
853 while (RA_GetNextLiveSegment(hArena, &sSegDetails))
854 if (pbyBuffer == NULL) {
856 sizeof(sSegDetails.uiSize) + sSegDetails.uiSize;
858 if ((uiBytesSaved + sizeof(sSegDetails.uiSize) +
859 sSegDetails.uiSize) > *puiBufSize)
860 return PVRSRV_ERROR_OUT_OF_MEMORY;
862 PVR_DPF(PVR_DBG_MESSAGE,
863 "PVRSRVSaveRestoreLiveSegments: "
864 "Base %08x size %08x",
865 sSegDetails.sCpuPhyAddr.uiAddr,
868 pvLocalMemCPUVAddr = (void __force *)
869 OSMapPhysToLin(sSegDetails.sCpuPhyAddr,
871 PVRSRV_HAP_KERNEL_ONLY |
872 PVRSRV_HAP_UNCACHED, NULL);
873 if (pvLocalMemCPUVAddr == NULL) {
874 PVR_DPF(PVR_DBG_ERROR,
875 "PVRSRVSaveRestoreLiveSegments: "
876 "Failed to map local memory to host");
877 return PVRSRV_ERROR_OUT_OF_MEMORY;
881 OSMemCopy(pbyBuffer, &sSegDetails.uiSize,
882 sizeof(sSegDetails.uiSize));
883 pbyBuffer += sizeof(sSegDetails.uiSize);
885 OSMemCopy(pbyBuffer, pvLocalMemCPUVAddr,
887 pbyBuffer += sSegDetails.uiSize;
891 OSMemCopy(&uiSize, pbyBuffer,
892 sizeof(sSegDetails.uiSize));
894 if (uiSize != sSegDetails.uiSize) {
895 PVR_DPF(PVR_DBG_ERROR,
896 "PVRSRVSaveRestoreLiveSegments:"
897 " Segment size error");
899 pbyBuffer += sizeof(sSegDetails.uiSize);
901 OSMemCopy(pvLocalMemCPUVAddr, pbyBuffer,
903 pbyBuffer += sSegDetails.uiSize;
908 sizeof(sSegDetails.uiSize) + sSegDetails.uiSize;
910 OSUnMapPhysToLin((void __force __iomem *)
913 PVRSRV_HAP_KERNEL_ONLY |
914 PVRSRV_HAP_UNCACHED, NULL);
917 if (pbyBuffer == NULL)
918 *puiBufSize = uiBytesSaved;