summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorZhenyu Wang <zhenyu.z.wang@intel.com>2007-11-15 13:56:24 +0800
committerZhenyu Wang <zhenyu.z.wang@intel.com>2007-11-15 13:56:24 +0800
commit4983e3401390654098dbf99dcfb45bab060b068c (patch)
tree1dab2b066de1362988ef02a74690c48a87d0272b
parentbcd656c8dfe7309a5cf02ce1da8bc747ccd6e21c (diff)
xvmc: move locking code into generic place
-rw-r--r--src/xvmc/I915XvMC.c122
-rw-r--r--src/xvmc/I915XvMC.h9
-rw-r--r--src/xvmc/intel_xvmc.c32
-rw-r--r--src/xvmc/intel_xvmc.h33
4 files changed, 95 insertions, 101 deletions
diff --git a/src/xvmc/I915XvMC.c b/src/xvmc/I915XvMC.c
index 1ff3629e..d34808fc 100644
--- a/src/xvmc/I915XvMC.c
+++ b/src/xvmc/I915XvMC.c
@@ -145,64 +145,6 @@ static __inline__ void renderError(void)
XVMC_ERR("Invalid Macroblock Parameters found.");
}
-static void I915XvMCContendedLock(i915XvMCContext *pI915XvMC, drmLockFlags flags)
-{
- drmGetLock(xvmc_driver->fd, pI915XvMC->hHWContext, flags);
-}
-
-#define SET_BLOCKED_SIGSET(pI915XvMC) do { \
- sigset_t bl_mask; \
- sigfillset(&bl_mask); \
- sigdelset(&bl_mask, SIGFPE); \
- sigdelset(&bl_mask, SIGILL); \
- sigdelset(&bl_mask, SIGSEGV); \
- sigdelset(&bl_mask, SIGBUS); \
- sigdelset(&bl_mask, SIGKILL); \
- pthread_sigmask(SIG_SETMASK, &bl_mask, &pI915XvMC->sa_mask); \
- } while (0)
-
-#define RESTORE_BLOCKED_SIGSET(pI915XvMC) do { \
- pthread_sigmask(SIG_SETMASK, &pI915XvMC->sa_mask, NULL); \
- } while (0)
-
-#define PPTHREAD_MUTEX_LOCK(pI915XvMC) do { \
- SET_BLOCKED_SIGSET(pI915XvMC); \
- pthread_mutex_lock(&pI915XvMC->ctxmutex); \
- } while (0)
-
-#define PPTHREAD_MUTEX_UNLOCK(pI915XvMC) do { \
- pthread_mutex_unlock(&pI915XvMC->ctxmutex); \
- RESTORE_BLOCKED_SIGSET(pI915XvMC); \
- } while (0)
-
-/* Lock the hardware and validate our state.
- */
-static void LOCK_HARDWARE(i915XvMCContext *pI915XvMC)
-{
- char __ret = 0;
-
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
- assert(!pI915XvMC->locked);
-
- DRM_CAS(pI915XvMC->driHwLock, pI915XvMC->hHWContext,
- (DRM_LOCK_HELD|pI915XvMC->hHWContext), __ret);
-
- if (__ret)
- I915XvMCContendedLock(pI915XvMC, 0);
-
- pI915XvMC->locked = 1;
-}
-
-/* Unlock the hardware using the global current context
- */
-static void UNLOCK_HARDWARE(i915XvMCContext *pI915XvMC)
-{
- pI915XvMC->locked = 0;
- DRM_UNLOCK(xvmc_driver->fd, pI915XvMC->driHwLock,
- pI915XvMC->hHWContext);
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
-}
-
static void i915_flush(int map, int render)
{
struct i915_mi_flush mi_flush;
@@ -1712,7 +1654,7 @@ static void i915_release_resource(Display *display, XvMCContext *context)
driDestroyHashContents(pI915XvMC->drawHash);
drmHashDestroy(pI915XvMC->drawHash);
- pthread_mutex_destroy(&pI915XvMC->ctxmutex);
+ pthread_mutex_destroy(&xvmc_driver->ctxmutex);
XLockDisplay(display);
uniDRIDestroyContext(display, screen, pI915XvMC->id);
@@ -1806,7 +1748,6 @@ static Status i915_xvmc_mc_create_context(Display *display, XvMCContext *context
priv_data = NULL;
pSAREA = (drm_sarea_t *)xvmc_driver->sarea_address;
- pI915XvMC->driHwLock = (drmLock *)&pSAREA->lock;
pI915XvMC->sarea = (drmI830Sarea*)((char*)pSAREA + pI915XvMC->sarea_priv_offset);
ret = XMatchVisualInfo(display, screen,
(pI915XvMC->depth == 32) ? 24 : pI915XvMC->depth, TrueColor,
@@ -1850,10 +1791,7 @@ static Status i915_xvmc_mc_create_context(Display *display, XvMCContext *context
pI915XvMC->haveXv = 0;
pI915XvMC->dual_prime = 0;
pI915XvMC->last_flip = 0;
- pI915XvMC->locked = 0;
pI915XvMC->port = context->port;
- /* XXX */
- pthread_mutex_init(&pI915XvMC->ctxmutex, NULL);
pI915XvMC->ref = 1;
return Success;
}
@@ -1898,11 +1836,11 @@ static Status i915_xvmc_mc_create_surface(Display *display, XvMCContext *context
if (!(pI915XvMC = context->privData))
return (error_base + XvMCBadContext);
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
+ PPTHREAD_MUTEX_LOCK();
surface->privData = (i915XvMCSurface *)malloc(sizeof(i915XvMCSurface));
if (!(pI915Surface = surface->privData)) {
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadAlloc;
}
@@ -1924,7 +1862,7 @@ static Status i915_xvmc_mc_create_surface(Display *display, XvMCContext *context
XVMC_ERR("Unable to create XvMCSurface.");
free(pI915Surface);
surface->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return ret;
}
@@ -1938,7 +1876,7 @@ static Status i915_xvmc_mc_create_surface(Display *display, XvMCContext *context
free(priv_data);
free(pI915Surface);
surface->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadAlloc;
}
@@ -1957,12 +1895,12 @@ static Status i915_xvmc_mc_create_surface(Display *display, XvMCContext *context
_xvmc_destroy_surface(display, surface);
free(pI915Surface);
surface->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadAlloc;
}
pI915XvMC->ref++;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return 0;
}
@@ -2096,7 +2034,7 @@ static int i915_xvmc_mc_render_surface(Display *display, XvMCContext *context,
picture_coding_type = MPEG_B_PICTURE;
}
- LOCK_HARDWARE(pI915XvMC);
+ LOCK_HARDWARE(pI915XvMC->hHWContext);
corrdata_ptr = pI915XvMC->corrdata.map;
corrdata_size = 0;
@@ -2204,7 +2142,7 @@ static int i915_xvmc_mc_render_surface(Display *display, XvMCContext *context,
xvmc_driver->last_render = xvmc_driver->alloc.irq_emitted;
privTarget->last_render = xvmc_driver->last_render;
- UNLOCK_HARDWARE(pI915XvMC);
+ UNLOCK_HARDWARE(pI915XvMC->hHWContext);
return 0;
}
@@ -2264,12 +2202,12 @@ static int i915_xvmc_mc_put_surface(Display *display,XvMCSurface *surface,
if (!(pI915XvMC = pI915Surface->privContext))
return (error_base + XvMCBadSurface);
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
+ PPTHREAD_MUTEX_LOCK();
/*
if (getDRIDrawableInfoLocked(pI915XvMC->drawHash, display,
pI915XvMC->screen, draw, 0, pI915XvMC->fd, pI915XvMC->hHWContext,
pI915XvMC->sarea_address, FALSE, &drawInfo, sizeof(*drawInfo))) {
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadAccess;
}
*/
@@ -2297,14 +2235,14 @@ static int i915_xvmc_mc_put_surface(Display *display,XvMCSurface *surface,
pI915XvMC->xvImage, srcx, srcy, srcw, srch,
destx, desty, destw, desth))) {
XUnlockDisplay(display);
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return ret;
}
XSync(display, 0);
XUnlockDisplay(display);
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return 0;
}
@@ -2374,13 +2312,13 @@ static int i915_xvmc_mc_get_surface_status(Display *display, XvMCSurface *surfac
if (!(pI915XvMC = pI915Surface->privContext))
return (error_base + XvMCBadSurface);
- // LOCK_HARDWARE(pI915XvMC);
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
+ // LOCK_HARDWARE(pI915XvMC->hHWContext);
+ PPTHREAD_MUTEX_LOCK();
if (pI915Surface->last_flip) {
/* This can not happen */
if (pI915XvMC->last_flip < pI915Surface->last_flip) {
XVMC_ERR("Context last flip is less than surface last flip.");
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadValue;
}
@@ -2404,8 +2342,8 @@ static int i915_xvmc_mc_get_surface_status(Display *display, XvMCSurface *surfac
*stat |= XVMC_RENDERING;
}
- // UNLOCK_HARDWARE(pI915XvMC);
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ // UNLOCK_HARDWARE(pI915XvMC->hHWContext);
+ PPTHREAD_MUTEX_UNLOCK();
return 0;
}
@@ -2505,7 +2443,7 @@ Status XvMCCreateSubpicture(Display *display, XvMCContext *context,
if (!subpicture->privData)
return BadAlloc;
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
+ PPTHREAD_MUTEX_LOCK();
subpicture->context_id = context->context_id;
subpicture->xvimage_id = xvimage_id;
subpicture->width = width;
@@ -2519,7 +2457,7 @@ Status XvMCCreateSubpicture(Display *display, XvMCContext *context,
XVMC_ERR("Unable to create XvMCSubpicture.");
free(pI915Subpicture);
subpicture->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return ret;
}
XUnlockDisplay(display);
@@ -2534,7 +2472,7 @@ Status XvMCCreateSubpicture(Display *display, XvMCContext *context,
free(priv_data);
free(pI915Subpicture);
subpicture->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadAlloc;
}
@@ -2554,7 +2492,7 @@ Status XvMCCreateSubpicture(Display *display, XvMCContext *context,
XUnlockDisplay(display);
free(pI915Subpicture);
subpicture->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadAlloc;
}
@@ -2581,12 +2519,12 @@ Status XvMCCreateSubpicture(Display *display, XvMCContext *context,
XUnlockDisplay(display);
free(pI915Subpicture);
subpicture->privData = NULL;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return BadMatch;
}
pI915XvMC->ref++;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return Success;
}
@@ -2712,7 +2650,7 @@ Status XvMCDestroySubpicture(Display *display, XvMCSubpicture *subpicture)
if (pI915Subpicture->srf.map)
drmUnmap(pI915Subpicture->srf.map, pI915Subpicture->srf.size);
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
+ PPTHREAD_MUTEX_LOCK();
XLockDisplay(display);
_xvmc_destroy_subpicture(display,subpicture);
XUnlockDisplay(display);
@@ -2720,7 +2658,7 @@ Status XvMCDestroySubpicture(Display *display, XvMCSubpicture *subpicture)
free(pI915Subpicture);
subpicture->privData = NULL;
pI915XvMC->ref--;
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ PPTHREAD_MUTEX_UNLOCK();
return Success;
}
@@ -2980,16 +2918,16 @@ Status XvMCGetSubpictureStatus(Display *display, XvMCSubpicture *subpicture,
if (!(pI915XvMC = pI915Subpicture->privContext))
return (error_base + XvMCBadSubpicture);
- // LOCK_HARDWARE(pI915XvMC);
- PPTHREAD_MUTEX_LOCK(pI915XvMC);
+ // LOCK_HARDWARE(pI915XvMC->hHWContext);
+ PPTHREAD_MUTEX_LOCK();
/* FIXME: */
if (pI915Subpicture->last_render &&
(pI915Subpicture->last_render > pI915XvMC->sarea->last_dispatch)) {
*stat |= XVMC_RENDERING;
}
- // UNLOCK_HARDWARE(pI915XvMC);
- PPTHREAD_MUTEX_UNLOCK(pI915XvMC);
+ // UNLOCK_HARDWARE(pI915XvMC->hHWContext);
+ PPTHREAD_MUTEX_UNLOCK();
return Success;
}
diff --git a/src/xvmc/I915XvMC.h b/src/xvmc/I915XvMC.h
index b97dc48a..a470558d 100644
--- a/src/xvmc/I915XvMC.h
+++ b/src/xvmc/I915XvMC.h
@@ -68,12 +68,7 @@ typedef struct _i915XvMCContext {
unsigned int yStride;
unsigned int uvStride;
unsigned short ref;
- pthread_mutex_t ctxmutex;
- int lock; /* Lightweight lock to avoid locking twice */
- int locked;
volatile drmI830Sarea *sarea;
-
- drmLock *driHwLock;
drm_context_t hHWContext; /* drmcontext; */
unsigned int sarea_priv_offset; /* Offset in sarea to private part */
unsigned int depth;
@@ -94,11 +89,7 @@ typedef struct _i915XvMCContext {
i915XvMCDrmMap ssb;
i915XvMCDrmMap psp;
i915XvMCDrmMap psc;
-
i915XvMCDrmMap corrdata;
-
- sigset_t sa_mask;
-
} i915XvMCContext;
/***************************************************************************
diff --git a/src/xvmc/intel_xvmc.c b/src/xvmc/intel_xvmc.c
index 6c9a9501..21eb607d 100644
--- a/src/xvmc/intel_xvmc.c
+++ b/src/xvmc/intel_xvmc.c
@@ -30,6 +30,35 @@ struct _intel_xvmc_driver *xvmc_driver = NULL;
static int error_base;
static int event_base;
+/* locking */
+static void intel_xvmc_try_heavy_lock(drm_context_t ctx)
+{
+ drmGetLock(xvmc_driver->fd, ctx, 0);
+}
+
+void LOCK_HARDWARE(drm_context_t ctx)
+{
+ char __ret = 0;
+
+ PPTHREAD_MUTEX_LOCK();
+ assert(!xvmc_driver->locked);
+
+ DRM_CAS(xvmc_driver->driHwLock, ctx,
+ (DRM_LOCK_HELD | ctx), __ret);
+
+ if (__ret)
+ intel_xvmc_try_heavy_lock(ctx);
+
+ xvmc_driver->locked = 1;
+}
+
+void UNLOCK_HARDWARE(drm_context_t ctx)
+{
+ xvmc_driver->locked = 0;
+ DRM_UNLOCK(xvmc_driver->fd, xvmc_driver->driHwLock, ctx);
+ PPTHREAD_MUTEX_UNLOCK();
+}
+
/*
* Function: XvMCCreateContext
* Description: Create a XvMC context for the given surface parameters.
@@ -196,6 +225,9 @@ Status XvMCCreateContext(Display *display, XvPortID port,
free(priv_data);
return BadAlloc;
}
+ pSAREA = (drm_sarea_t *)xvmc_driver->sarea_address;
+ xvmc_driver->driHwLock = (drmLock *)&pSAREA->lock;
+ pthread_mutex_init(&xvmc_driver->ctxmutex, NULL);
/* call driver hook.
* driver hook should free priv_data after return if success.*/
diff --git a/src/xvmc/intel_xvmc.h b/src/xvmc/intel_xvmc.h
index b5fadb19..28390af6 100644
--- a/src/xvmc/intel_xvmc.h
+++ b/src/xvmc/intel_xvmc.h
@@ -136,6 +136,12 @@ typedef struct _intel_xvmc_driver {
intel_xvmc_drm_map_t batchbuffer;
unsigned int last_render;
+ sigset_t sa_mask;
+ pthread_mutex_t ctxmutex;
+ int lock; /* Lightweight lock to avoid locking twice */
+ int locked;
+ drmLock *driHwLock;
+
void *private;
/* XXX: remove? */
@@ -180,4 +186,31 @@ typedef struct _intel_xvmc_driver {
extern struct _intel_xvmc_driver i915_xvmc_mc_driver;
extern struct _intel_xvmc_driver *xvmc_driver;
+#define SET_BLOCKED_SIGSET() do { \
+ sigset_t bl_mask; \
+ sigfillset(&bl_mask); \
+ sigdelset(&bl_mask, SIGFPE); \
+ sigdelset(&bl_mask, SIGILL); \
+ sigdelset(&bl_mask, SIGSEGV); \
+ sigdelset(&bl_mask, SIGBUS); \
+ sigdelset(&bl_mask, SIGKILL); \
+ pthread_sigmask(SIG_SETMASK, &bl_mask, &xvmc_driver->sa_mask); \
+ } while (0)
+
+#define RESTORE_BLOCKED_SIGSET() do { \
+ pthread_sigmask(SIG_SETMASK, &xvmc_driver->sa_mask, NULL); \
+ } while (0)
+
+#define PPTHREAD_MUTEX_LOCK() do { \
+ SET_BLOCKED_SIGSET(); \
+ pthread_mutex_lock(&xvmc_driver->ctxmutex); \
+ } while (0)
+
+#define PPTHREAD_MUTEX_UNLOCK() do { \
+ pthread_mutex_unlock(&xvmc_driver->ctxmutex); \
+ RESTORE_BLOCKED_SIGSET(); \
+ } while (0)
+
+extern void LOCK_HARDWARE(drm_context_t);
+extern void UNLOCK_HARDWARE(drm_context_t);
#endif