1 #include "nv_include.h"
3 #define NV_NOTIFIER_SIZE 32
4 #define NV_NOTIFY_TIME_0 0x00000000
5 #define NV_NOTIFY_TIME_1 0x00000004
6 #define NV_NOTIFY_RETURN_VALUE 0x00000008
7 #define NV_NOTIFY_STATE 0x0000000C
8 #define NV_NOTIFY_STATE_STATUS_MASK 0xFF000000
9 #define NV_NOTIFY_STATE_STATUS_SHIFT 24
10 #define NV_NOTIFY_STATE_STATUS_COMPLETED 0x00
11 #define NV_NOTIFY_STATE_STATUS_IN_PROCESS 0x01
12 #define NV_NOTIFY_STATE_ERROR_CODE_MASK 0x0000FFFF
13 #define NV_NOTIFY_STATE_ERROR_CODE_SHIFT 0
15 #define NOTIFIER(__v) \
16 NVPtr pNv = NVPTR(pScrn); \
17 volatile uint32_t *__v = (void*)pNv->NotifierBlock + notifier->offset
19 struct drm_nouveau_notifierobj_alloc *
20 NVNotifierAlloc(ScrnInfoPtr pScrn, uint32_t handle)
22 NVPtr pNv = NVPTR(pScrn);
23 struct drm_nouveau_notifierobj_alloc *notifier;
26 notifier = xcalloc(1, sizeof(*notifier));
28 NVNotifierDestroy(pScrn, notifier);
32 notifier->channel = pNv->fifo.channel;
33 notifier->handle = handle;
35 ret = drmCommandWriteRead(pNv->drm_fd, DRM_NOUVEAU_NOTIFIEROBJ_ALLOC,
36 notifier, sizeof(*notifier));
38 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
39 "Failed to create notifier 0x%08x: %d\n",
41 NVNotifierDestroy(pScrn, notifier);
49 NVNotifierDestroy(ScrnInfoPtr pScrn,
50 struct drm_nouveau_notifierobj_alloc *notifier)
53 /*XXX: destroy notifier object */
59 NVNotifierReset(ScrnInfoPtr pScrn,
60 struct drm_nouveau_notifierobj_alloc *notifier)
64 n[NV_NOTIFY_TIME_0 /4] =
65 n[NV_NOTIFY_TIME_1 /4] =
66 n[NV_NOTIFY_RETURN_VALUE/4] = 0;
67 n[NV_NOTIFY_STATE /4] = (NV_NOTIFY_STATE_STATUS_IN_PROCESS <<
68 NV_NOTIFY_STATE_STATUS_SHIFT);
72 NVNotifierStatus(ScrnInfoPtr pScrn,
73 struct drm_nouveau_notifierobj_alloc *notifier)
77 return n[NV_NOTIFY_STATE/4] >> NV_NOTIFY_STATE_STATUS_SHIFT;
81 NVNotifierErrorCode(ScrnInfoPtr pScrn,
82 struct drm_nouveau_notifierobj_alloc *notifier)
86 return n[NV_NOTIFY_STATE/4] & NV_NOTIFY_STATE_ERROR_CODE_MASK;
90 NVNotifierReturnVal(ScrnInfoPtr pScrn,
91 struct drm_nouveau_notifierobj_alloc *notifier)
95 return n[NV_NOTIFY_RETURN_VALUE/4];
99 NVNotifierWaitStatus(ScrnInfoPtr pScrn,
100 struct drm_nouveau_notifierobj_alloc *notifier,
101 unsigned int status, unsigned int timeout)
104 unsigned int t_start, time = 0;
106 t_start = GetTimeInMillis();
107 while (time <= timeout) {
109 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
110 "N(0x%08x)/%d = 0x%08x/0x%08x/0x%08x/0x%08x\n",
111 notifier->handle, time, n[0], n[1], n[2], n[3]);
113 if (n[NV_NOTIFY_STATE/4] & NV_NOTIFY_STATE_ERROR_CODE_MASK) {
114 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
115 "Notifier returned error: 0x%04x\n",
116 NVNotifierErrorCode(pScrn, notifier));
120 if ((n[NV_NOTIFY_STATE/4] >> NV_NOTIFY_STATE_STATUS_SHIFT)
125 time = GetTimeInMillis() - t_start;
128 xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
129 "Notifier (0x%08x) timeout!\n", notifier->handle);