enable XvMC for i915

This commit is contained in:
Xiang, Haihao 2007-06-25 10:17:08 +08:00
parent c7920a0e81
commit 934da9f2b8
20 changed files with 7072 additions and 2 deletions

View File

@ -59,6 +59,8 @@ INTEL_DRI_SRCS = \
i810_dri.h \
i830_dri.c \
i810_hwmc.c \
i915_hwmc.c \
i915_hwmc.h \
i830_dri.h
intel_drv_la_SOURCES = \

View File

@ -309,6 +309,11 @@ typedef struct _I830Rec {
/* For Xvideo */
i830_memory *overlay_regs;
#endif
/* For XvMC */
void *xvmc;
Bool XvMCEnabled;
XF86ModReqInfo shadowReq; /* to test for later libshadow */
Rotation rotation;
void (*PointerMoved)(int, int, int);
@ -644,7 +649,10 @@ extern long I830CheckAvailableMemory(ScrnInfoPtr pScrn);
Bool i830_allocate_2d_memory(ScrnInfoPtr pScrn);
Bool i830_allocate_texture_memory(ScrnInfoPtr pScrn);
Bool i830_allocate_3d_memory(ScrnInfoPtr pScrn);
Bool i830_allocate_xvmc_surface(ScrnInfoPtr pScrn, i830_memory **surface,
unsigned long size);
Bool i830_allocate_xvmc_buffer(ScrnInfoPtr pScrn, const char *name,
i830_memory **buffer, unsigned long size);
extern Bool I830IsPrimary(ScrnInfoPtr pScrn);
extern Bool I830I2CInit(ScrnInfoPtr pScrn, I2CBusPtr *bus_ptr, int i2c_reg,
@ -738,6 +746,11 @@ static inline int i830_fb_compression_supported(I830Ptr pI830)
return TRUE;
}
/* i915 XvMC */
int I915XvMCInitXv(ScrnInfoPtr, XF86VideoAdaptorPtr);
void I915InitMC(ScreenPtr);
unsigned long I915XvMCPutImageSize(ScrnInfoPtr);
extern const int I830PatternROP[16];
extern const int I830CopyROP[16];

View File

@ -2720,6 +2720,12 @@ I830ScreenInit(int scrnIndex, ScreenPtr pScreen, int argc, char **argv)
if (pI830->directRenderingEnabled) {
pI830->directRenderingEnabled = I830DRIFinishScreenInit(pScreen);
}
#ifdef XvMCExtension
if ((pI830->directRenderingEnabled) && IS_I9XX(pI830)) {
I915InitMC(pScreen);
}
#endif
#endif
/* Setup 3D engine, needed for rotation too */

View File

@ -1758,4 +1758,42 @@ i830_xf86AllocateOffscreenLinear(ScreenPtr pScreen, int length,
return linear;
}
/*
* Allocate memory for XvMC surface
*/
Bool
i830_allocate_xvmc_surface(ScrnInfoPtr pScrn, i830_memory **surface, unsigned long size)
{
I830Ptr pI830 = I830PTR(pScrn);
*surface = i830_allocate_memory(pScrn, "XvMC surface", size,
GTT_PAGE_SIZE, ALIGN_BOTH_ENDS);
if (!*surface) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Failed to allocate XvMC surface space.\n");
return FALSE;
}
return TRUE;
}
/*
* Allocate memory for MC compensation
*/
Bool i830_allocate_xvmc_buffer(ScrnInfoPtr pScrn, const char *name, i830_memory **buffer, unsigned long size)
{
I830Ptr pI830 = I830PTR(pScrn);
*buffer = i830_allocate_memory(pScrn, name, size,
GTT_PAGE_SIZE, ALIGN_BOTH_ENDS);
if (!*buffer) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Failed to allocate memory for %s.\n", name);
return FALSE;
}
return TRUE;
}
#endif

View File

@ -74,6 +74,8 @@
#include "dixstruct.h"
#include "fourcc.h"
#include "i915_hwmc.h"
#ifndef USE_USLEEP_FOR_VIDEO
#define USE_USLEEP_FOR_VIDEO 0
#endif
@ -576,6 +578,11 @@ I830InitVideo(ScreenPtr pScreen)
if (texturedAdaptor != NULL) {
adaptors[num_adaptors++] = texturedAdaptor;
xf86DrvMsg(pScrn->scrnIndex, X_INFO, "Set up textured video\n");
#ifdef XF86DRI
if (pI830->XvMCEnabled && IS_I9XX(pI830))
I915XvMCInitXv(pScrn, texturedAdaptor);
#endif
} else {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"Failed to set up textured video\n");
@ -2587,6 +2594,16 @@ I830QueryImageAttributes(ScrnInfoPtr pScrn,
ErrorF("size is %d\n", size);
#endif
break;
case FOURCC_XVMC:
*h = (*h + 1) & ~1;
#ifdef XF86DRI
size = I915XvMCPutImageSize(pScrn);
#else
size = 0;
#endif
if (pitches)
pitches[0] = size;
break;
case FOURCC_UYVY:
case FOURCC_YUY2:
default:

View File

@ -77,6 +77,7 @@ typedef struct {
int oneLineMode;
int scaleRatio;
Bool textured;
void *xvmc_priv;
} I830PortPrivRec, *I830PortPrivPtr;
#define GET_PORT_PRIVATE(pScrn) \

932
src/i915_hwmc.c Normal file
View File

@ -0,0 +1,932 @@
#ifdef HAVE_CONFIG_H
#include "config.h"
#endif
#include <string.h>
#include "xf86.h"
#include "xf86_OSproc.h"
#include "xf86Resources.h"
#include "compiler.h"
#include "xf86PciInfo.h"
#include "xf86Pci.h"
#include "xf86fbman.h"
#include "regionstr.h"
#include "i830.h"
#include "i830_dri.h"
#include "i830_video.h"
#include "xf86xv.h"
#include "xf86xvmc.h"
#include <X11/extensions/Xv.h>
#include <X11/extensions/XvMC.h>
#include "xaa.h"
#include "xaalocal.h"
#include "dixstruct.h"
#include "fourcc.h"
#if defined(X_NEED_XVPRIV_H) || defined (_XF86_FOURCC_H_)
#include "xf86xvpriv.h"
#endif
#include "i915_hwmc.h"
#define MAKE_ATOM(a) MakeAtom(a, strlen(a), TRUE)
/*
* List Attributes for the XvMC extension to handle:
* As long as the attribute is supported by the Xv adaptor, it needs only to
* be added here to be supported also by XvMC.
* Currently, only colorkey seems to be supported by Xv for Putimage.
*/
static char *attrXvMC[I915_NUM_XVMC_ATTRIBUTES] = {
"XV_BRIGHTNESS",
"XV_CONTRAST",
};
static Atom attrAtoms[I915_NUM_XVMC_ATTRIBUTES];
typedef struct
{
unsigned ctxDisplaying;
int xvmc_port;
I915XvMCAttrHolder xvAttr;
int newAttribute;
SetPortAttributeFuncPtr SetPortAttribute;
GetPortAttributeFuncPtr GetPortAttribute;
PutImageFuncPtr PutImage;
} I915XvMCXVPriv;
#define I915_XVMC_MAX_BUFFERS 2
#define I915_XVMC_MAX_CONTEXTS 4
#define I915_XVMC_MAX_SURFACES 20
typedef struct _I915XvMCSurfacePriv
{
i830_memory *surface;
unsigned long offsets[I915_XVMC_MAX_BUFFERS];
} I915XvMCSurfacePriv;
typedef struct _I915XvMCContextPriv
{
i830_memory *mcStaticIndirectState;
drm_handle_t sis_handle;
i830_memory *mcMapState;
drm_handle_t msb_handle;
i830_memory *mcSamplerState;
drm_handle_t ssb_handle;
i830_memory *mcPixelShaderProgram;
drm_handle_t psp_handle;
i830_memory *mcPixelShaderConstants;
drm_handle_t psc_handle;
i830_memory *mcCorrdata;
drm_handle_t corrdata_handle;
} I915XvMCContextPriv;
typedef struct _I915XvMC
{
XID contexts[I915_XVMC_MAX_CONTEXTS];
XID surfaces[I915_XVMC_MAX_SURFACES];
I915XvMCSurfacePriv *sfprivs[I915_XVMC_MAX_SURFACES];
I915XvMCContextPriv *ctxprivs[I915_XVMC_MAX_CONTEXTS];
int ncontexts,nsurfaces;
} I915XvMC, *I915XvMCPtr;
#define ARRARY_SIZE(a) (sizeof(a) / sizeof(a[0]))
static int I915XvMCCreateContext (ScrnInfoPtr pScrn, XvMCContextPtr pContext,
int *num_priv, long **priv );
static void I915XvMCDestroyContext (ScrnInfoPtr pScrn, XvMCContextPtr pContext);
static int I915XvMCCreateSurface (ScrnInfoPtr pScrn, XvMCSurfacePtr pSurf,
int *num_priv, long **priv );
static void I915XvMCDestroySurface (ScrnInfoPtr pScrn, XvMCSurfacePtr pSurf);
static int I915XvMCCreateSubpicture (ScrnInfoPtr pScrn, XvMCSubpicturePtr pSurf,
int *num_priv, long **priv );
static void I915XvMCDestroySubpicture (ScrnInfoPtr pScrn, XvMCSubpicturePtr pSurf);
static int yv12_subpicture_index_list[2] =
{
FOURCC_IA44,
FOURCC_AI44
};
static XF86MCImageIDList yv12_subpicture_list =
{
ARRARY_SIZE(yv12_subpicture_index_list),
yv12_subpicture_index_list
};
static XF86MCSurfaceInfoRec i915_YV12_mpg2_surface =
{
FOURCC_YV12,
XVMC_CHROMA_FORMAT_420,
0,
720,
576,
720,
576,
XVMC_MPEG_2,
XVMC_OVERLAID_SURFACE | XVMC_SUBPICTURE_INDEPENDENT_SCALING |
XVMC_INTRA_UNSIGNED,
&yv12_subpicture_list
};
static XF86MCSurfaceInfoRec i915_YV12_mpg1_surface =
{
FOURCC_YV12,
XVMC_CHROMA_FORMAT_420,
0,
720,
576,
720,
576,
XVMC_MPEG_1,
XVMC_OVERLAID_SURFACE | XVMC_SUBPICTURE_INDEPENDENT_SCALING |
XVMC_INTRA_UNSIGNED,
&yv12_subpicture_list
};
static XF86MCSurfaceInfoPtr ppSI[2] =
{
(XF86MCSurfaceInfoPtr)&i915_YV12_mpg2_surface,
(XF86MCSurfaceInfoPtr)&i915_YV12_mpg1_surface
};
/* List of subpicture types that we support */
static XF86ImageRec ia44_subpicture = XVIMAGE_IA44;
static XF86ImageRec ai44_subpicture = XVIMAGE_AI44;
static XF86ImagePtr i915_subpicture_list[2] =
{
(XF86ImagePtr)&ia44_subpicture,
(XF86ImagePtr)&ai44_subpicture
};
/* Fill in the device dependent adaptor record.
* This is named "Intel(R) Textured Video" because this code falls under the
* XV extenstion, the name must match or it won't be used.
*
* Surface and Subpicture - see above
* Function pointers to functions below
*/
static XF86MCAdaptorRec pAdapt =
{
"Intel(R) Textured Video", /* name */
ARRARY_SIZE(ppSI), /* num_surfaces */
ppSI, /* surfaces */
ARRARY_SIZE(i915_subpicture_list), /* num_subpictures */
i915_subpicture_list, /* subpictures */
(xf86XvMCCreateContextProcPtr)I915XvMCCreateContext,
(xf86XvMCDestroyContextProcPtr)I915XvMCDestroyContext,
(xf86XvMCCreateSurfaceProcPtr)I915XvMCCreateSurface,
(xf86XvMCDestroySurfaceProcPtr)I915XvMCDestroySurface,
(xf86XvMCCreateSubpictureProcPtr)I915XvMCCreateSubpicture,
(xf86XvMCDestroySubpictureProcPtr)I915XvMCDestroySubpicture
};
static XF86MCAdaptorPtr ppAdapt[1] =
{
(XF86MCAdaptorPtr)&pAdapt
};
static unsigned int stride(int w)
{
return (w + 31) & ~31;
}
static unsigned long size_yuv420(int w, int h)
{
unsigned yPitch = stride(w);
return h * (yPitch + (yPitch >> 1));
}
static unsigned long size_xx44(int w, int h)
{
return h * stride(w);
}
/*
* Init and clean up the screen private parts of XvMC.
*/
static void initI915XvMC(I915XvMCPtr xvmc)
{
unsigned int i;
for (i = 0; i < I915_XVMC_MAX_CONTEXTS; i++) {
xvmc->contexts[i] = 0;
xvmc->ctxprivs[i] = NULL;
}
for (i = 0; i < I915_XVMC_MAX_SURFACES; i++) {
xvmc->surfaces[i] = 0;
xvmc->sfprivs[i] = NULL;
}
}
static void cleanupI915XvMC(I915XvMCPtr xvmc, XF86VideoAdaptorPtr * XvAdaptors, int XvAdaptorCount)
{
unsigned int i;
for (i = 0; i < I915_XVMC_MAX_CONTEXTS; i++) {
xvmc->contexts[i] = 0;
if (xvmc->ctxprivs[i]) {
xfree(xvmc->ctxprivs[i]);
xvmc->ctxprivs[i] = NULL;
}
}
for (i = 0; i < I915_XVMC_MAX_SURFACES; i++) {
xvmc->surfaces[i] = 0;
if (xvmc->sfprivs[i]) {
xfree(xvmc->sfprivs[i]);
xvmc->sfprivs[i] = NULL;
}
}
}
static Bool i915_map_xvmc_buffers(ScrnInfoPtr pScrn, I915XvMCContextPriv *ctxpriv)
{
I830Ptr pI830 = I830PTR(pScrn);
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)(ctxpriv->mcStaticIndirectState->offset + pI830->LinearAddr),
ctxpriv->mcStaticIndirectState->size, DRM_AGP, 0,
(drmAddress)&ctxpriv->sis_handle) < 0) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[drm] drmAddMap(sis_handle) failed!\n");
return FALSE;
}
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)(ctxpriv->mcMapState->offset + pI830->LinearAddr),
ctxpriv->mcMapState->size, DRM_AGP, 0,
(drmAddress)&ctxpriv->msb_handle) < 0) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[drm] drmAddMap(msb_handle) failed!\n");
return FALSE;
}
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)(ctxpriv->mcSamplerState->offset + pI830->LinearAddr),
ctxpriv->mcSamplerState->size, DRM_AGP, 0,
(drmAddress)&ctxpriv->ssb_handle) < 0) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[drm] drmAddress(ssb_handle) failed!\n");
return FALSE;
}
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)(ctxpriv->mcPixelShaderProgram->offset + pI830->LinearAddr),
ctxpriv->mcPixelShaderProgram->size, DRM_AGP, 0,
(drmAddress)&ctxpriv->psp_handle) < 0) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[drm] drmAddress(psp_handle) failed!\n");
return FALSE;
}
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)(ctxpriv->mcPixelShaderConstants->offset + pI830->LinearAddr),
ctxpriv->mcPixelShaderConstants->size, DRM_AGP, 0,
(drmAddress)&ctxpriv->psc_handle) < 0) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[drm] drmAddress(psc_handle) failed!\n");
return FALSE;
}
if (drmAddMap(pI830->drmSubFD,
(drm_handle_t)(ctxpriv->mcCorrdata->offset + pI830->LinearAddr),
ctxpriv->mcCorrdata->size, DRM_AGP, 0,
(drmAddress)&ctxpriv->corrdata_handle) < 0) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[drm] drmAddMap(corrdata_handle) failed!\n");
return FALSE;
}
return TRUE;
}
static void i915_unmap_xvmc_buffers(ScrnInfoPtr pScrn, I915XvMCContextPriv *ctxpriv)
{
I830Ptr pI830 = I830PTR(pScrn);
if (ctxpriv->sis_handle) {
drmRmMap(pI830->drmSubFD, ctxpriv->sis_handle);
ctxpriv->sis_handle = 0;
}
if (ctxpriv->msb_handle) {
drmRmMap(pI830->drmSubFD, ctxpriv->msb_handle);
ctxpriv->msb_handle = 0;
}
if (ctxpriv->ssb_handle) {
drmRmMap(pI830->drmSubFD, ctxpriv->ssb_handle);
ctxpriv->ssb_handle = 0;
}
if (ctxpriv->psp_handle) {
drmRmMap(pI830->drmSubFD, ctxpriv->psp_handle);
ctxpriv->psp_handle = 0;
}
if (ctxpriv->psc_handle) {
drmRmMap(pI830->drmSubFD, ctxpriv->psc_handle);
ctxpriv->psc_handle = 0;
}
if (ctxpriv->corrdata_handle) {
drmRmMap(pI830->drmSubFD, ctxpriv->corrdata_handle);
ctxpriv->corrdata_handle = 0;
}
}
static Bool i915_allocate_xvmc_buffers(ScrnInfoPtr pScrn, I915XvMCContextPriv *ctxpriv)
{
if (!i830_allocate_xvmc_buffer(pScrn, "Static Indirect State",
&(ctxpriv->mcStaticIndirectState), 512)) {
return FALSE;
}
if (!i830_allocate_xvmc_buffer(pScrn, "Map State",
&(ctxpriv->mcMapState), 512)) {
return FALSE;
}
if (!i830_allocate_xvmc_buffer(pScrn, "Sampler State",
&(ctxpriv->mcSamplerState), 512)) {
return FALSE;
}
if (!i830_allocate_xvmc_buffer(pScrn, "Pixel Shader Program",
&(ctxpriv->mcPixelShaderProgram), 512)) {
return FALSE;
}
if (!i830_allocate_xvmc_buffer(pScrn, "Pixel Shader Constants",
&(ctxpriv->mcPixelShaderConstants), 128)) {
return FALSE;
}
if (!i830_allocate_xvmc_buffer(pScrn, "Correction Data Buffer",
&(ctxpriv->mcCorrdata), 2 * 1024 * 1024)) {
return FALSE;
}
return TRUE;
}
static void i915_free_xvmc_buffers(ScrnInfoPtr pScrn, I915XvMCContextPriv *ctxpriv)
{
if (ctxpriv->mcStaticIndirectState) {
i830_free_memory(pScrn, ctxpriv->mcStaticIndirectState);
ctxpriv->mcStaticIndirectState = NULL;
}
if (ctxpriv->mcMapState) {
i830_free_memory(pScrn, ctxpriv->mcMapState);
ctxpriv->mcMapState = NULL;
}
if (ctxpriv->mcSamplerState) {
i830_free_memory(pScrn, ctxpriv->mcSamplerState);
ctxpriv->mcSamplerState = NULL;
}
if (ctxpriv->mcPixelShaderProgram) {
i830_free_memory(pScrn, ctxpriv->mcPixelShaderProgram);
ctxpriv->mcPixelShaderProgram = NULL;
}
if (ctxpriv->mcPixelShaderConstants) {
i830_free_memory(pScrn, ctxpriv->mcPixelShaderConstants);
ctxpriv->mcPixelShaderConstants = NULL;
}
if (ctxpriv->mcCorrdata) {
i830_free_memory(pScrn, ctxpriv->mcCorrdata);
ctxpriv->mcCorrdata = NULL;
}
}
/**************************************************************************
*
* I915XvMCCreateContext
*
* Some info about the private data:
*
* Set *num_priv to the number of 32bit words that make up the size of
* of the data that priv will point to.
*
* *priv = (long *) xcalloc (elements, sizeof(element))
* *num_priv = (elements * sizeof(element)) >> 2;
*
**************************************************************************/
static int I915XvMCCreateContext (ScrnInfoPtr pScrn, XvMCContextPtr pContext,
int *num_priv, long **priv )
{
I830Ptr pI830 = I830PTR(pScrn);
DRIInfoPtr pDRIInfo = pI830->pDRIInfo;
I915XvMCCreateContextRec *contextRec = NULL;
I915XvMCPtr pXvMC = pI830->xvmc;
I915XvMCContextPriv *ctxpriv = NULL;
XvPortRecPrivatePtr portPriv = (XvPortRecPrivatePtr)pContext->port_priv;
I830PortPrivPtr pPriv = (I830PortPrivPtr)portPriv->DevPriv.ptr;
I915XvMCXVPriv *vx = (I915XvMCXVPriv *)pPriv->xvmc_priv;
int i;
*priv = NULL;
*num_priv = 0;
if (!pI830->directRenderingEnabled) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateContext: Cannot use XvMC without DRI!\n");
return BadAlloc;
}
if (pXvMC->ncontexts >= I915_XVMC_MAX_CONTEXTS) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateContext: Out of contexts.\n");
return BadAlloc;
}
*priv = xcalloc(1, sizeof(I915XvMCCreateContextRec));
contextRec = (I915XvMCCreateContextRec *)*priv;
if (!*priv) {
*num_priv = 0;
return BadAlloc;
}
*num_priv = sizeof(I915XvMCCreateContextRec) >> 2;
for (i = 0; i < I915_XVMC_MAX_CONTEXTS; i++) {
if (!pXvMC->contexts[i])
break;
}
ctxpriv = (I915XvMCContextPriv *)xcalloc(1, sizeof(I915XvMCContextPriv));
if (!ctxpriv) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateContext: Unable to allocate memory!\n");
xfree(*priv);
*priv = NULL;
*num_priv = 0;
return BadAlloc;
}
if (!i915_allocate_xvmc_buffers(pScrn, ctxpriv)) {
i915_free_xvmc_buffers(pScrn, ctxpriv);
xfree(ctxpriv);
ctxpriv = NULL;
xfree(*priv);
*priv = NULL;
*num_priv = 0;
return BadAlloc;
}
if (!i915_map_xvmc_buffers(pScrn, ctxpriv)) {
i915_unmap_xvmc_buffers(pScrn, ctxpriv);
i915_free_xvmc_buffers(pScrn, ctxpriv);
xfree(ctxpriv);
ctxpriv = NULL;
xfree(*priv);
*priv = NULL;
*num_priv = 0;
return BadAlloc;
}
contextRec->ctxno = i;
contextRec->sis.handle = ctxpriv->sis_handle;
contextRec->sis.offset = ctxpriv->mcStaticIndirectState->offset;
contextRec->sis.size = ctxpriv->mcStaticIndirectState->size;
contextRec->msb.handle = ctxpriv->msb_handle;
contextRec->msb.offset = ctxpriv->mcMapState->offset;
contextRec->msb.size = ctxpriv->mcMapState->size;
contextRec->ssb.handle = ctxpriv->ssb_handle;
contextRec->ssb.offset = ctxpriv->mcSamplerState->offset;
contextRec->ssb.size = ctxpriv->mcSamplerState->size;
contextRec->psp.handle = ctxpriv->psp_handle;
contextRec->psp.offset = ctxpriv->mcPixelShaderProgram->offset;
contextRec->psp.size = ctxpriv->mcPixelShaderProgram->size;
contextRec->psc.handle = ctxpriv->psc_handle;
contextRec->psc.offset = ctxpriv->mcPixelShaderConstants->offset;
contextRec->psc.size = ctxpriv->mcPixelShaderConstants->size;
contextRec->corrdata.handle = ctxpriv->corrdata_handle;
contextRec->corrdata.offset = ctxpriv->mcCorrdata->offset;
contextRec->corrdata.size = ctxpriv->mcCorrdata->size;
contextRec->sarea_size = pDRIInfo->SAREASize;
contextRec->sarea_priv_offset = sizeof(XF86DRISAREARec);
contextRec->screen = pScrn->pScreen->myNum;
contextRec->depth = pScrn->bitsPerPixel;
contextRec->initAttrs = vx->xvAttr;
pXvMC->ncontexts++;
pXvMC->contexts[i] = pContext->context_id;
pXvMC->ctxprivs[i] = ctxpriv;
return Success;
}
static int I915XvMCCreateSurface(ScrnInfoPtr pScrn, XvMCSurfacePtr pSurf,
int *num_priv, long **priv )
{
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = pI830->xvmc;
I915XvMCSurfacePriv *sfpriv = NULL;
XvMCContextPtr ctx = NULL;
unsigned int sfno, i, nbuffers;
unsigned long bufsize;
*priv = NULL;
*num_priv = 0;
if (pXvMC->nsurfaces >= I915_XVMC_MAX_SURFACES) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSurface: Too many surfaces !\n");
return BadAlloc;
}
sfpriv = (I915XvMCSurfacePriv *)xcalloc(1, sizeof(I915XvMCSurfacePriv));
if (!sfpriv) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSurface: Unable to allocate memory!\n");
return BadAlloc;
}
nbuffers = 1;
*num_priv = nbuffers + 2;
*priv = (long *)xcalloc(*num_priv, sizeof(unsigned long));
if (!*priv) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSurface: Unable to allocate memory!\n");
xfree(sfpriv);
*num_priv = 0;
return BadAlloc;
}
ctx = pSurf->context;
bufsize = size_yuv420(ctx->width, ctx->height);
if (!i830_allocate_xvmc_surface(pScrn, &(sfpriv->surface), nbuffers * bufsize)) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSurface: Failed to allocate XvMC surface space!\n");
xfree(sfpriv);
xfree(*priv);
*priv = NULL;
*num_priv = 0;
return BadAlloc;
}
for (sfno = 0; sfno < I915_XVMC_MAX_SURFACES; ++sfno) {
if (!pXvMC->surfaces[sfno])
break;
}
(*priv)[0] = sfno;
(*priv)[1] = nbuffers;
(*priv)[2] = sfpriv->offsets[0] = sfpriv->surface->offset;
for (i = 1; i < nbuffers; ++i) {
(*priv)[i + 2] = sfpriv->offsets[i] = sfpriv->offsets[i - 1] + bufsize;
}
pXvMC->surfaces[sfno] = pSurf->surface_id;
pXvMC->sfprivs[sfno]= sfpriv;
pXvMC->nsurfaces++;
return Success;
}
static int I915XvMCCreateSubpicture (ScrnInfoPtr pScrn, XvMCSubpicturePtr pSubp,
int *num_priv, long **priv )
{
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = pI830->xvmc;
I915XvMCSurfacePriv *sfpriv = NULL;
XvMCContextPtr ctx = NULL;
unsigned srfno;
unsigned bufsize;
if (I915_XVMC_MAX_SURFACES == pXvMC->nsurfaces) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSubpicture: Too many surfaces !\n");
return BadAlloc;
}
sfpriv = (I915XvMCSurfacePriv *)xcalloc(1, sizeof(I915XvMCSurfacePriv));
if (!sfpriv) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSubpicture: Unable to allocate memory!\n");
*num_priv = 0;
return BadAlloc;
}
*priv = (INT32 *)xcalloc(3, sizeof(INT32));
if (!*priv) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSubpicture: Unable to allocate memory!\n");
*num_priv = 0;
xfree(sfpriv);
return BadAlloc;
}
*num_priv = 2;
ctx = pSubp->context;
bufsize = size_xx44(ctx->width, ctx->height);
if (!i830_allocate_xvmc_surface(pScrn, &(sfpriv->surface), bufsize)) {
xf86DrvMsg(pScrn->scrnIndex, X_ERROR,
"[XvMC] I915XvMCCreateSurface: Failed to allocate XvMC surface space!\n");
xfree(sfpriv);
sfpriv = NULL;
xfree(*priv);
*priv = NULL;
*num_priv = 0;
return BadAlloc;
}
for (srfno = 0; srfno < I915_XVMC_MAX_SURFACES; ++srfno) {
if (0 == pXvMC->sfprivs[srfno])
break;
}
(*priv)[0] = srfno;
(*priv)[1] = sfpriv->offsets[0] = sfpriv->surface->offset;
pXvMC->sfprivs[srfno] = sfpriv;
pXvMC->surfaces[srfno] = pSubp->subpicture_id;
pXvMC->nsurfaces++;
return Success;
}
static void I915XvMCDestroyContext (ScrnInfoPtr pScrn, XvMCContextPtr pContext)
{
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = pI830->xvmc;
int i;
for (i = 0; i < I915_XVMC_MAX_CONTEXTS; i++) {
if (pXvMC->contexts[i] == pContext->context_id) {
i915_unmap_xvmc_buffers(pScrn, pXvMC->ctxprivs[i]);
i915_free_xvmc_buffers(pScrn, pXvMC->ctxprivs[i]);
xfree(pXvMC->ctxprivs[i]);
pXvMC->ctxprivs[i] = 0;
pXvMC->ncontexts--;
pXvMC->contexts[i] = 0;
return;
}
}
return;
}
static void I915XvMCDestroySurface (ScrnInfoPtr pScrn, XvMCSurfacePtr pSurf)
{
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = pI830->xvmc;
int i;
for (i = 0; i < I915_XVMC_MAX_SURFACES; i++) {
if (pXvMC->surfaces[i] == pSurf->surface_id) {
i830_free_memory(pScrn, pXvMC->sfprivs[i]->surface);
xfree(pXvMC->sfprivs[i]);
pXvMC->nsurfaces--;
pXvMC->sfprivs[i] = 0;
pXvMC->surfaces[i] = 0;
return;
}
}
return;
}
static void I915XvMCDestroySubpicture (ScrnInfoPtr pScrn, XvMCSubpicturePtr pSubp)
{
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = pI830->xvmc;
int i;
for (i = 0; i < I915_XVMC_MAX_SURFACES; i++) {
if (pXvMC->surfaces[i] == pSubp->subpicture_id) {
i830_free_memory(pScrn, pXvMC->sfprivs[i]->surface);
xfree(pXvMC->sfprivs[i]);
pXvMC->nsurfaces--;
pXvMC->sfprivs[i] = 0;
pXvMC->surfaces[i] = 0;
return;
}
}
return;
}
/*
*
*/
static int I915XvMCInterceptXvGetAttribute(ScrnInfoPtr pScrn, Atom attribute,
INT32 * value, pointer data)
{
unsigned i;
I830PortPrivPtr pPriv = (I830PortPrivPtr)data;
I915XvMCXVPriv *vx = (I915XvMCXVPriv *)pPriv->xvmc_priv;
if (I830PTR(pScrn)->XvMCEnabled) {
for (i = 0; i < vx->xvAttr.numAttr; ++i) {
if (vx->xvAttr.attributes[i].attribute == attribute) {
*value = vx->xvAttr.attributes[i].value;
return Success;
}
}
}
return vx->GetPortAttribute(pScrn, attribute, value, data);
}
static int I915XvMCInterceptXvAttribute(ScrnInfoPtr pScrn, Atom attribute,
INT32 value, pointer data)
{
unsigned i;
I830PortPrivPtr pPriv = (I830PortPrivPtr)data;
I915XvMCXVPriv *vx = (I915XvMCXVPriv *)pPriv->xvmc_priv;
if (I830PTR(pScrn)->XvMCEnabled) {
for (i = 0; i < vx->xvAttr.numAttr; ++i) {
if (vx->xvAttr.attributes[i].attribute == attribute) {
vx->xvAttr.attributes[i].value = value;
return Success;
}
}
}
return vx->SetPortAttribute(pScrn, attribute, value, data);
}
static int I915XvMCDisplayAttributes(ScrnInfoPtr pScrn,
const I915XvMCAttrHolder * ah, I830PortPrivPtr pPriv)
{
I915XvMCXVPriv *vx = (I915XvMCXVPriv *) pPriv->xvmc_priv;
unsigned i;
int ret;
for (i = 0; i < ah->numAttr; ++i) {
ret = vx->SetPortAttribute(pScrn, ah->attributes[i].attribute,
ah->attributes[i].value, pPriv);
if (ret)
return ret;
}
return Success;
}
static int I915XvMCInterceptPutImage(ScrnInfoPtr pScrn, short src_x, short src_y,
short drw_x, short drw_y, short src_w,
short src_h, short drw_w, short drw_h,
int id, unsigned char *buf, short width,
short height, Bool sync, RegionPtr clipBoxes, pointer data,
DrawablePtr pDraw)
{
I830PortPrivPtr pPriv = (I830PortPrivPtr)data;
I915XvMCXVPriv *vx = (I915XvMCXVPriv *)pPriv->xvmc_priv;
if (I830PTR(pScrn)->XvMCEnabled) {
if (FOURCC_XVMC == id) {
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = pI830->xvmc;
I915XvMCCommandBuffer *i915XvMCData = (I915XvMCCommandBuffer *)buf;
int i;
switch (i915XvMCData->command) {
case I915_XVMC_COMMAND_ATTRIBUTES:
if ((i915XvMCData->ctxNo | I915_XVMC_VALID) != vx->ctxDisplaying)
return 1;
I915XvMCDisplayAttributes(pScrn, &i915XvMCData->attrib, pPriv);
return 0;
case I915_XVMC_COMMAND_DISPLAY:
for (i = 0; i < I915_XVMC_MAX_SURFACES; i++) {
if (pXvMC->surfaces[i] == i915XvMCData->srfNo) {
i830_memory *mem = pXvMC->sfprivs[i]->surface;
buf = pI830 + mem->offset;
id = i915XvMCData->real_id;
break;
}
}
if (i >= I915_XVMC_MAX_SURFACES)
return 1;
break;
default:
return 0;
}
}
}
return vx->PutImage(pScrn, src_x, src_y, drw_x, drw_y, src_w, src_h,
drw_w, drw_h, id, buf, width, height, sync, clipBoxes, data, pDraw);
}
/*********************************** Public Function **************************************/
/**************************************************************************
*
* I915InitMC
*
* Inputs:
* Screen pointer
*
* Outputs:
* None
*
**************************************************************************/
void I915InitMC(ScreenPtr pScreen)
{
ScrnInfoPtr pScrn = xf86Screens[pScreen->myNum];
I830Ptr pI830 = I830PTR(pScrn);
I915XvMCPtr pXvMC = NULL;
pI830->XvMCEnabled = FALSE;
if (!pI830->directRenderingEnabled) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"[XvMC] Cannot use XvMC without DRI!\n");
return;
}
pXvMC = (I915XvMCPtr)calloc(1, sizeof(I915XvMC));
if (!pXvMC) {
xf86DrvMsg(pScrn->scrnIndex, X_WARNING,
"[XvMC] Failure!\n");
return;
}
pI830->xvmc = pXvMC;
initI915XvMC(pXvMC);
xf86XvMCScreenInit(pScreen, 1, ppAdapt);
xf86DrvMsg(pScrn->scrnIndex, X_INFO,
"[XvMC] Initialized XvMC extension.\n");
pI830->XvMCEnabled = TRUE;
}
int I915XvMCInitXv(ScrnInfoPtr pScrn, XF86VideoAdaptorPtr XvAdapt)
{
I830PortPrivPtr pPriv;
I915XvMCXVPriv *vx;
unsigned i, j;
for (j = 0; j < XvAdapt->nPorts; ++j) {
pPriv = (I830PortPrivPtr) XvAdapt->pPortPrivates[j].ptr;
if (NULL == (pPriv->xvmc_priv = xcalloc(1, sizeof(I915XvMCXVPriv)))) {
return BadAlloc;
}
for (i = 0; i < I915_NUM_XVMC_ATTRIBUTES; ++i) {
attrAtoms[i] = MAKE_ATOM(attrXvMC[i]);
}
vx = (I915XvMCXVPriv *) pPriv->xvmc_priv;
vx->ctxDisplaying = 0;
vx->xvAttr.numAttr = I915_NUM_XVMC_ATTRIBUTES;
vx->xvmc_port = -1;
vx->newAttribute = 1;
/* set up wrappers */
vx->GetPortAttribute = XvAdapt->GetPortAttribute;
vx->SetPortAttribute = XvAdapt->SetPortAttribute;
vx->PutImage = XvAdapt->PutImage;
XvAdapt->GetPortAttribute = I915XvMCInterceptXvGetAttribute;
XvAdapt->SetPortAttribute = I915XvMCInterceptXvAttribute;
XvAdapt->PutImage = I915XvMCInterceptPutImage;
for (i = 0; i < I915_NUM_XVMC_ATTRIBUTES; ++i) {
vx->xvAttr.attributes[i].attribute = attrAtoms[i];
vx->xvAttr.attributes[i].value = 0;
vx->GetPortAttribute(pScrn, attrAtoms[i],
&(vx->xvAttr.attributes[i].value), pPriv);
}
}
return Success;
}
unsigned long I915XvMCPutImageSize(ScrnInfoPtr pScrn)
{
if (I830PTR(pScrn)->XvMCEnabled)
return sizeof(I915XvMCCommandBuffer);
return 0;
}

64
src/i915_hwmc.h Normal file
View File

@ -0,0 +1,64 @@
#ifndef _I915_HWMC_H
#define _I915_HWMC_H
#define FOURCC_XVMC (('C' << 24) + ('M' << 16) + ('V' << 8) + 'X')
#define I915_NUM_XVMC_ATTRIBUTES 0x02
#define I915_XVMC_VALID 0x80000000
/*
* Commands that client submits through XvPutImage:
*/
#define I915_XVMC_COMMAND_DISPLAY 0x00
#define I915_XVMC_COMMAND_UNDISPLAY 0x01
#define I915_XVMC_COMMAND_ATTRIBUTES 0x02
typedef struct
{
INT32 attribute;
INT32 value;
} I915AttrPair;
typedef struct
{
unsigned numAttr;
I915AttrPair attributes[I915_NUM_XVMC_ATTRIBUTES];
} I915XvMCAttrHolder;
typedef struct
{
unsigned command;
unsigned ctxNo;
unsigned srfNo;
unsigned subPicNo;
I915XvMCAttrHolder attrib;
int real_id;
unsigned pad;
} I915XvMCCommandBuffer;
struct hwmc_buffer
{
unsigned handle;
unsigned offset;
unsigned size;
};
typedef struct
{
unsigned ctxno; /* XvMC private context reference number */
drm_context_t drmcontext;
struct hwmc_buffer sis; /* Static Indirect State Buffer */
struct hwmc_buffer msb; /* Map State Block */
struct hwmc_buffer ssb; /* Sampler State Block */
struct hwmc_buffer psp; /* Pixel Shader Program Buffer */
struct hwmc_buffer psc; /* Pixel Shader Constants Buffer */
struct hwmc_buffer corrdata;/* Correction Data Buffer */
unsigned sarea_size;
unsigned sarea_priv_offset;
unsigned screen;
unsigned depth;
I915XvMCAttrHolder initAttrs;
} I915XvMCCreateContextRec;
#endif /* _I915_HWMC_H */

3056
src/xvmc/I915XvMC.c Normal file

File diff suppressed because it is too large Load Diff

178
src/xvmc/I915XvMC.h Normal file
View File

@ -0,0 +1,178 @@
/***************************************************************************
Copyright 2001 Intel Corporation. All Rights Reserved.
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sub license, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice (including the
next paragraph) shall be included in all copies or substantial portions
of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
IN NO EVENT SHALL INTEL, AND/OR ITS SUPPLIERS BE LIABLE FOR ANY CLAIM,
DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR
THE USE OR OTHER DEALINGS IN THE SOFTWARE.
**************************************************************************/
#ifndef _I915XVMC_H
#define _I915XVMC_H
/* #define XVMC_DEBUG(x) do {x; }while(0); */
#define XVMC_DEBUG(x)
#include "xf86drm.h"
#include "i830_common.h"
#include "i915_hwmc.h"
#include <X11/Xlibint.h>
#include <X11/Xutil.h>
#define I915_SUBPIC_PALETTE_SIZE 16
/***************************************************************************
// i915XvMCDrmMap: Holds the data about the DRM maps
***************************************************************************/
typedef struct _i915XvMCDrmMap {
drm_handle_t handle;
unsigned offset;
unsigned size;
drmAddress map;
} i915XvMCDrmMap, *i915XvMCDrmMapPtr;
/***************************************************************************
// i915XvMCContext: Private Context data referenced via the privData
// pointer in the XvMCContext structure.
***************************************************************************/
typedef struct _i915XvMCContext {
unsigned ctxno;
int fd; /* File descriptor for /dev/dri */
unsigned last_render;
unsigned last_flip;
unsigned dual_prime; /* Flag to identify when dual prime is in use. */
unsigned yStride;
unsigned short ref;
pthread_mutex_t ctxmutex;
char busIdString[21]; /* PCI:0:1:0 or PCI:0:2:0 */
int lock; /* Lightweight lock to avoid locking twice */
int locked;
volatile drmI830Sarea *sarea;
drmLock *driHwLock;
drm_context_t hHWContext; /* drmcontext; */
drm_handle_t hsarea; /* Handle to drm shared memory area */
drmAddress sarea_address; /* Virtual address of shared memory area */
unsigned sarea_size; /* Size of drm shared memory area */
unsigned sarea_priv_offset; /* Offset in sarea to private part */
unsigned screen;
unsigned depth;
XvPortID port; /* Xv Port ID when displaying */
I915XvMCAttrHolder attrib; /* This contexts attributes and their values */
XvAttribute attribDesc[I915_NUM_XVMC_ATTRIBUTES]; /* Attribute decriptions */
int haveXv; /* Have I initialized the Xv
* connection for this surface? */
XvImage *xvImage; /* Fake Xv Image used for command
* buffer transport to the X server */
int attribChanged; /* Attributes have changed and need to
* be uploaded to Xv at next frame
* display */
GC gc; /* X GC needed for displaying */
Drawable draw; /* Drawable to undisplay from */
XID id;
XVisualInfo visualInfo;
void *drawHash;
i915XvMCDrmMap sis;
i915XvMCDrmMap msb;
i915XvMCDrmMap ssb;
i915XvMCDrmMap psp;
i915XvMCDrmMap psc;
i915XvMCDrmMap corrdata;
struct {
unsigned start_offset;
unsigned size;
unsigned space;
unsigned char *ptr;
} batch;
struct
{
void *ptr;
unsigned size;
unsigned offset;
unsigned active_buf;
unsigned irq_emitted;
} alloc;
} i915XvMCContext;
/***************************************************************************
// i915XvMCSubpicture: Private data structure for each XvMCSubpicture. This
// structure is referenced by the privData pointer in the XvMCSubpicture
// structure.
***************************************************************************/
typedef struct _i915XvMCSubpicture {
unsigned srfNo;
unsigned last_render;
unsigned last_flip;
unsigned offset;
unsigned pitch;
unsigned char palette[3][16];
i915XvMCContext *privContext;
} i915XvMCSubpicture;
/***************************************************************************
// i915XvMCSurface: Private data structure for each XvMCSurface. This
// structure is referenced by the privData pointer in the XvMCSurface
// structure.
***************************************************************************/
#define I830_MAX_BUFS 2 /*Number of YUV buffers per surface */
typedef struct _i915XvMCSurface {
unsigned srfNo; /* XvMC private surface numbers */
unsigned num_buffers; /* Number of picture buffers */
unsigned curbuf; /* Which is the current buffer? */
unsigned offsets[I830_MAX_BUFS]; /* Offsets of picture buffers */
unsigned last_render;
unsigned last_flip;
unsigned yStride; /* Stride of YUV420 Y component. */
unsigned width; /* Dimensions */
unsigned height;
i915XvMCContext *privContext;
i915XvMCSubpicture *privSubPic; /* Subpicture to be blended when
* displaying. NULL if none. */
} i915XvMCSurface;
/* Subpicture fourcc */
#define FOURCC_IA44 0x34344149
/*
Definitions for temporary wire protocol hooks to be replaced
when a HW independent libXvMC is created.
*/
extern Status _xvmc_create_context(Display *dpy, XvMCContext *context,
int *priv_count, uint **priv_data);
extern Status _xvmc_destroy_context(Display *dpy, XvMCContext *context);
extern Status _xvmc_create_surface(Display *dpy, XvMCContext *context,
XvMCSurface *surface, int *priv_count,
uint **priv_data);
extern Status _xvmc_destroy_surface(Display *dpy, XvMCSurface *surface);
extern Status _xvmc_create_subpicture(Display *dpy, XvMCContext *context,
XvMCSubpicture *subpicture,
int *priv_count, uint **priv_data);
extern Status _xvmc_destroy_subpicture(Display *dpy,
XvMCSubpicture *subpicture);
#endif /* _I915XVMC_H */

View File

@ -1,5 +1,6 @@
if DRI
lib_LTLIBRARIES=libI810XvMC.la
lib_LTLIBRARIES=libI810XvMC.la libI915XvMC.la
libI810XvMC_la_SOURCES = I810XvMC.c \
I810XvMC.h
@ -7,4 +8,17 @@ libI810XvMC_la_CFLAGS = @WARN_CFLAGS@ @XORG_CFLAGS@ @DRI_CFLAGS@ \
-I$(top_srcdir)/src -DTRUE=1 -DFALSE=0
libI810XvMC_la_LDFLAGS = -version-number 1:0:0
libI810XvMC_la_LIBADD = @DRI_LIBS@
libI915XvMC_la_SOURCES = I915XvMC.c \
I915XvMC.h \
intel_batchbuffer.c \
intel_batchbuffer.h \
xf86dri.c \
xf86dri.h \
xf86dristr.h \
driDrawable.c \
driDrawable.h
libI915XvMC_la_CFLAGS = @XORG_CFLAGS@ @DRI_CFLAGS@ -I$(top_srcdir)/src -DTRUE=1 -DFALSE=0
libI915XvMC_la_LDFLAGS = -version-number 1:0:0
libI915XvMC_la_LIBADD = @DRI_LIBS@
endif

174
src/xvmc/driDrawable.c Normal file
View File

@ -0,0 +1,174 @@
/*****************************************************************************
* driDrawable.c: Lean Version of DRI utilities.
*
* Copyright (c) 2005 Thomas Hellstrom. All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHOR(S) OR COPYRIGHT HOLDER(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
*/
#include <X11/Xlibint.h>
#include <X11/Xutil.h>
#include "xf86drm.h"
#include "drm.h"
#include "xf86dri.h"
#include "drm_sarea.h"
#include "driDrawable.h"
static unsigned
drawStamp(volatile drm_sarea_t * pSarea, int index)
{
return pSarea->drawableTable[index].stamp;
}
int
getDRIDrawableInfoLocked(void *drawHash, Display * display, int screen,
Drawable draw, unsigned lockFlags, int drmFD, drm_context_t drmContext,
drmAddress sarea, Bool updateInfo, drawableInfo ** info,
unsigned long infoSize)
{
drawableInfo *drawInfo;
void *res;
drm_drawable_t drmDraw = 0;
volatile drm_sarea_t *pSarea = (drm_sarea_t *) sarea;
drm_clip_rect_t *clipFront, *clipBack;
int ret;
if (drmHashLookup(drawHash, (unsigned long)draw, &res)) {
/*
* The drawable is unknown to us. Create it and put it in the
* hash table.
*/
DRM_UNLOCK(drmFD, &pSarea->lock, drmContext);
if (!uniDRICreateDrawable(display, screen, draw, &drmDraw)) {
DRM_LOCK(drmFD, &pSarea->lock, drmContext, lockFlags);
return 1;
}
DRM_LOCK(drmFD, &pSarea->lock, drmContext, lockFlags);
drawInfo = (drawableInfo *) malloc(infoSize);
if (!drawInfo)
return 1;
drawInfo->drmDraw = drmDraw;
drawInfo->stamp = 0;
drawInfo->clipFront = 0;
drawInfo->clipBack = 0;
drmHashInsert(drawHash, (unsigned long)draw, drawInfo);
} else {
drawInfo = res;
}
drawInfo->touched = FALSE;
while (!drawInfo->clipFront
|| drawInfo->stamp != drawStamp(pSarea, drawInfo->index)) {
/*
* The drawable has been touched since we last got info about it.
* obtain new info from the X server.
*/
drawInfo->touched = TRUE;
if (updateInfo || !drawInfo->clipFront) {
DRM_UNLOCK(drmFD, &pSarea->lock, drmContext);
ret = uniDRIGetDrawableInfo(display, screen, draw,
&drawInfo->index, &drawInfo->stamp, &drawInfo->x,
&drawInfo->y, &drawInfo->w, &drawInfo->h,
&drawInfo->numClipFront, &clipFront,
&drawInfo->backX, &drawInfo->backY,
&drawInfo->numClipBack, &clipBack);
DRM_LIGHT_LOCK(drmFD, &pSarea->lock, drmContext);
/*
* Error. Probably the drawable is destroyed. Return error and old values.
*/
if (!ret) {
free(drawInfo);
drawInfo = NULL;
drmHashDelete(drawHash, (unsigned long)draw);
DRM_UNLOCK(drmFD, &pSarea->lock, drmContext);
uniDRIDestroyDrawable(display, screen, draw);
DRM_LOCK(drmFD, &pSarea->lock, drmContext, lockFlags);
return 1;
}
if (drawInfo->stamp != drawStamp(pSarea, drawInfo->index)) {
/*
* The info is already outdated. Sigh. Have another go.
*/
XFree(clipFront);
XFree(clipBack);
continue;
}
if (drawInfo->clipFront)
XFree(drawInfo->clipFront);
drawInfo->clipFront = clipFront;
if (drawInfo->clipBack)
XFree(drawInfo->clipBack);
drawInfo->clipBack = clipBack;
} else {
if (!drawInfo->clipFront)
drawInfo->clipFront = (drm_clip_rect_t *) ~ 0UL;
drawInfo->stamp = drawStamp(pSarea, drawInfo->index);
}
}
*info = drawInfo;
return 0;
}
void
driDestroyHashContents(void *drawHash)
{
unsigned long key;
void *content;
drawableInfo *drawInfo;
if (drmHashFirst(drawHash, &key, &content) < 1)
return;
drawInfo = (drawableInfo *) content;
if (drawInfo->clipBack)
XFree(drawInfo->clipBack);
if (drawInfo->clipFront)
XFree(drawInfo->clipFront);
free(drawInfo);
while (drmHashNext(drawHash, &key, &content) == 1) {
drawInfo = (drawableInfo *) content;
if (drawInfo->clipBack)
XFree(drawInfo->clipBack);
if (drawInfo->clipFront)
XFree(drawInfo->clipFront);
free(drawInfo);
}
return;
}

64
src/xvmc/driDrawable.h Normal file
View File

@ -0,0 +1,64 @@
/*****************************************************************************
* driDrawable.h: Lean Version of DRI utilities.
*
* Copyright (c) 2005 Thomas Hellstrom. All rights reserved.
*
* Permission is hereby granted, free of charge, to any person obtaining a
* copy of this software and associated documentation files (the "Software"),
* to deal in the Software without restriction, including without limitation
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
* and/or sell copies of the Software, and to permit persons to whom the
* Software is furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHOR(S) OR COPYRIGHT HOLDER(S) BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
* DEALINGS IN THE SOFTWARE.
*/
#ifndef _DRIDRAWABLE_H
#define _DRIDRAWABLE_H
typedef struct _drawableInfo
{
drm_drawable_t drmDraw;
unsigned stamp;
unsigned index;
drm_clip_rect_t *clipFront;
drm_clip_rect_t *clipBack;
int x;
int y;
int w;
int h;
int backX;
int backY;
int numClipFront;
int numClipBack;
Bool touched;
} drawableInfo;
/*
* Get updated info about the drawable "draw". The drawableInfo record returned is malloced
* and administrated internally. Never free it unless you know exactly what you are doing.
* The drm hash table "drawHash" needs to be initialized externally.
*/
extern int
getDRIDrawableInfoLocked(void *drawHash, Display * display, int screen,
Drawable draw, unsigned lockFlags, int drmFD, drm_context_t drmContext,
drmAddress sarea, Bool updateInfo, drawableInfo ** info,
unsigned long infoSize);
/*
* Free all resources created by the above function. Typically done on exit.
*/
extern void driDestroyHashContents(void *drawHash);
#endif

276
src/xvmc/i915_program.h Normal file
View File

@ -0,0 +1,276 @@
#ifndef _I915_PROGRAM_H
#define _I915_PROGRAM_H
#define REG_TYPE_R 0 /* temporary regs, no need to
* dcl, must be written before
* read -- Preserved between
* phases.
*/
#define REG_TYPE_T 1 /* Interpolated values, must be
* dcl'ed before use.
*
* 0..7: texture coord,
* 8: diffuse spec,
* 9: specular color,
* 10: fog parameter in w.
*/
#define REG_TYPE_CONST 2 /* Restriction: only one const
* can be referenced per
* instruction, though it may be
* selected for multiple inputs.
* Constants not initialized
* default to zero.
*/
#define REG_TYPE_S 3 /* sampler */
#define REG_TYPE_OC 4 /* output color (rgba) */
#define REG_TYPE_OD 5 /* output depth (w), xyz are
* temporaries. If not written,
* interpolated depth is used?
*/
#define REG_TYPE_U 6 /* unpreserved temporaries */
#define REG_TYPE_MASK 0x7
#define REG_NR_MASK 0xf
/* REG_TYPE_T:
*/
#define T_TEX0 0
#define T_TEX1 1
#define T_TEX2 2
#define T_TEX3 3
#define T_TEX4 4
#define T_TEX5 5
#define T_TEX6 6
#define T_TEX7 7
#define T_DIFFUSE 8
#define T_SPECULAR 9
#define T_FOG_W 10 /* interpolated fog is in W coord */
/* Arithmetic instructions */
/* .replicate_swizzle == selection and replication of a particular
* scalar channel, ie., .xxxx, .yyyy, .zzzz or .wwww
*/
#define A0_NOP (0x0<<24) /* no operation */
#define A0_ADD (0x1<<24) /* dst = src0 + src1 */
#define A0_MOV (0x2<<24) /* dst = src0 */
#define A0_MUL (0x3<<24) /* dst = src0 * src1 */
#define A0_MAD (0x4<<24) /* dst = src0 * src1 + src2 */
#define A0_DP2ADD (0x5<<24) /* dst.xyzw = src0.xy dot src1.xy + src2.replicate_swizzle */
#define A0_DP3 (0x6<<24) /* dst.xyzw = src0.xyz dot src1.xyz */
#define A0_DP4 (0x7<<24) /* dst.xyzw = src0.xyzw dot src1.xyzw */
#define A0_FRC (0x8<<24) /* dst = src0 - floor(src0) */
#define A0_RCP (0x9<<24) /* dst.xyzw = 1/(src0.replicate_swizzle) */
#define A0_RSQ (0xa<<24) /* dst.xyzw = 1/(sqrt(abs(src0.replicate_swizzle))) */
#define A0_EXP (0xb<<24) /* dst.xyzw = exp2(src0.replicate_swizzle) */
#define A0_LOG (0xc<<24) /* dst.xyzw = log2(abs(src0.replicate_swizzle)) */
#define A0_CMP (0xd<<24) /* dst = (src0 >= 0.0) ? src1 : src2 */
#define A0_MIN (0xe<<24) /* dst = (src0 < src1) ? src0 : src1 */
#define A0_MAX (0xf<<24) /* dst = (src0 >= src1) ? src0 : src1 */
#define A0_FLR (0x10<<24) /* dst = floor(src0) */
#define A0_MOD (0x11<<24) /* dst = src0 fmod 1.0 */
#define A0_TRC (0x12<<24) /* dst = int(src0) */
#define A0_SGE (0x13<<24) /* dst = src0 >= src1 ? 1.0 : 0.0 */
#define A0_SLT (0x14<<24) /* dst = src0 < src1 ? 1.0 : 0.0 */
#define A0_DEST_SATURATE (1<<22)
#define A0_DEST_TYPE_SHIFT 19
/* Allow: R, OC, OD, U */
#define A0_DEST_NR_SHIFT 14
/* Allow R: 0..15, OC,OD: 0..0, U: 0..2 */
#define A0_DEST_CHANNEL_X (1<<10)
#define A0_DEST_CHANNEL_Y (2<<10)
#define A0_DEST_CHANNEL_Z (4<<10)
#define A0_DEST_CHANNEL_W (8<<10)
#define A0_DEST_CHANNEL_ALL (0xf<<10)
#define A0_DEST_CHANNEL_SHIFT 10
#define A0_SRC0_TYPE_SHIFT 7
#define A0_SRC0_NR_SHIFT 2
#define A0_DEST_CHANNEL_XY (A0_DEST_CHANNEL_X|A0_DEST_CHANNEL_Y)
#define A0_DEST_CHANNEL_XYZ (A0_DEST_CHANNEL_XY|A0_DEST_CHANNEL_Z)
#define SRC_X 0
#define SRC_Y 1
#define SRC_Z 2
#define SRC_W 3
#define SRC_ZERO 4
#define SRC_ONE 5
#define A1_SRC0_CHANNEL_X_NEGATE (1<<31)
#define A1_SRC0_CHANNEL_X_SHIFT 28
#define A1_SRC0_CHANNEL_Y_NEGATE (1<<27)
#define A1_SRC0_CHANNEL_Y_SHIFT 24
#define A1_SRC0_CHANNEL_Z_NEGATE (1<<23)
#define A1_SRC0_CHANNEL_Z_SHIFT 20
#define A1_SRC0_CHANNEL_W_NEGATE (1<<19)
#define A1_SRC0_CHANNEL_W_SHIFT 16
#define A1_SRC1_TYPE_SHIFT 13
#define A1_SRC1_NR_SHIFT 8
#define A1_SRC1_CHANNEL_X_NEGATE (1<<7)
#define A1_SRC1_CHANNEL_X_SHIFT 4
#define A1_SRC1_CHANNEL_Y_NEGATE (1<<3)
#define A1_SRC1_CHANNEL_Y_SHIFT 0
#define A2_SRC1_CHANNEL_Z_NEGATE (1<<31)
#define A2_SRC1_CHANNEL_Z_SHIFT 28
#define A2_SRC1_CHANNEL_W_NEGATE (1<<27)
#define A2_SRC1_CHANNEL_W_SHIFT 24
#define A2_SRC2_TYPE_SHIFT 21
#define A2_SRC2_NR_SHIFT 16
#define A2_SRC2_CHANNEL_X_NEGATE (1<<15)
#define A2_SRC2_CHANNEL_X_SHIFT 12
#define A2_SRC2_CHANNEL_Y_NEGATE (1<<11)
#define A2_SRC2_CHANNEL_Y_SHIFT 8
#define A2_SRC2_CHANNEL_Z_NEGATE (1<<7)
#define A2_SRC2_CHANNEL_Z_SHIFT 4
#define A2_SRC2_CHANNEL_W_NEGATE (1<<3)
#define A2_SRC2_CHANNEL_W_SHIFT 0
/* Declaration instructions */
#define D0_DCL (0x19<<24) /* Declare a t (interpolated attrib)
* register or an s (sampler)
* register. */
#define D0_SAMPLE_TYPE_SHIFT 22
#define D0_SAMPLE_TYPE_2D (0x0<<22)
#define D0_SAMPLE_TYPE_CUBE (0x1<<22)
#define D0_SAMPLE_TYPE_VOLUME (0x2<<22)
#define D0_SAMPLE_TYPE_MASK (0x3<<22)
#define D0_TYPE_SHIFT 19
/* Allow: T, S */
#define D0_NR_SHIFT 14
/* Allow T: 0..10, S: 0..15 */
#define D0_CHANNEL_X (1<<10)
#define D0_CHANNEL_Y (2<<10)
#define D0_CHANNEL_Z (4<<10)
#define D0_CHANNEL_W (8<<10)
#define D0_CHANNEL_ALL (0xf<<10)
#define D0_CHANNEL_NONE (0<<10)
#define D0_CHANNEL_XY (D0_CHANNEL_X|D0_CHANNEL_Y)
#define D0_CHANNEL_XYZ (D0_CHANNEL_XY|D0_CHANNEL_Z)
/* I915 Errata: Do not allow (xz), (xw), (xzw) combinations for diffuse
* or specular declarations.
*
* For T dcls, only allow: (x), (xy), (xyz), (w), (xyzw)
*
* Must be zero for S (sampler) dcls
*/
#define D1_MBZ 0
#define D2_MBZ 0
/* Texture instructions */
#define T0_TEXLD (0x15<<24) /* Sample texture using predeclared
* sampler and address, and output
* filtered texel data to destination
* register */
#define T0_TEXLDP (0x16<<24) /* Same as texld but performs a
* perspective divide of the texture
* coordinate .xyz values by .w before
* sampling. */
#define T0_TEXLDB (0x17<<24) /* Same as texld but biases the
* computed LOD by w. Only S4.6 two's
* comp is used. This implies that a
* float to fixed conversion is
* done. */
#define T0_TEXKILL (0x18<<24) /* Does not perform a sampling
* operation. Simply kills the pixel
* if any channel of the address
* register is < 0.0. */
#define T0_DEST_TYPE_SHIFT 19
/* Allow: R, OC, OD, U */
/* Note: U (unpreserved) regs do not retain their values between
* phases (cannot be used for feedback)
*
* Note: oC and OD registers can only be used as the destination of a
* texture instruction once per phase (this is an implementation
* restriction).
*/
#define T0_DEST_NR_SHIFT 14
/* Allow R: 0..15, OC,OD: 0..0, U: 0..2 */
#define T0_SAMPLER_NR_SHIFT 0 /* This field ignored for TEXKILL */
#define T0_SAMPLER_NR_MASK (0xf<<0)
#define T1_ADDRESS_REG_TYPE_SHIFT 24 /* Reg to use as texture coord */
/* Allow R, T, OC, OD -- R, OC, OD are 'dependent' reads, new program phase */
#define T1_ADDRESS_REG_NR_SHIFT 17
#define T2_MBZ 0
/* Having zero and one in here makes the definition of swizzle a lot
* easier.
*/
#define UREG_TYPE_SHIFT 29
#define UREG_NR_SHIFT 24
#define UREG_CHANNEL_X_NEGATE_SHIFT 23
#define UREG_CHANNEL_X_SHIFT 20
#define UREG_CHANNEL_Y_NEGATE_SHIFT 19
#define UREG_CHANNEL_Y_SHIFT 16
#define UREG_CHANNEL_Z_NEGATE_SHIFT 15
#define UREG_CHANNEL_Z_SHIFT 12
#define UREG_CHANNEL_W_NEGATE_SHIFT 11
#define UREG_CHANNEL_W_SHIFT 8
#define UREG_CHANNEL_ZERO_NEGATE_MBZ 5
#define UREG_CHANNEL_ZERO_SHIFT 4
#define UREG_CHANNEL_ONE_NEGATE_MBZ 1
#define UREG_CHANNEL_ONE_SHIFT 0
#define UREG_BAD 0xffffffff /* not a valid ureg */
#define X SRC_X
#define Y SRC_Y
#define Z SRC_Z
#define W SRC_W
#define ZERO SRC_ZERO
#define ONE SRC_ONE
/* Construct a ureg:
*/
#define UREG(type, nr) (((type) << UREG_TYPE_SHIFT) | \
((nr) << UREG_NR_SHIFT) | \
(X << UREG_CHANNEL_X_SHIFT) | \
(Y << UREG_CHANNEL_Y_SHIFT) | \
(Z << UREG_CHANNEL_Z_SHIFT) | \
(W << UREG_CHANNEL_W_SHIFT) | \
(ZERO << UREG_CHANNEL_ZERO_SHIFT) | \
(ONE << UREG_CHANNEL_ONE_SHIFT))
#define GET_CHANNEL_SRC( reg, channel ) ((reg<<(channel*4)) & (0xf<<20))
#define CHANNEL_SRC( src, channel ) (src>>(channel*4))
#define GET_UREG_TYPE(reg) (((reg)>>UREG_TYPE_SHIFT)&REG_TYPE_MASK)
#define GET_UREG_NR(reg) (((reg)>>UREG_NR_SHIFT)&REG_NR_MASK)
#define UREG_XYZW_CHANNEL_MASK 0x00ffff00
#define A0_DEST(reg) (((reg) & UREG_TYPE_NR_MASK)>>UREG_A0_DEST_SHIFT_LEFT)
#define D0_DEST(reg) (((reg) & UREG_TYPE_NR_MASK)>>UREG_A0_DEST_SHIFT_LEFT)
#define T0_DEST(reg) (((reg) & UREG_TYPE_NR_MASK)>>UREG_A0_DEST_SHIFT_LEFT)
#define A0_SRC0(reg) (((reg) & UREG_MASK)>>UREG_A0_SRC0_SHIFT_LEFT)
#define A1_SRC0(reg) (((reg) & UREG_MASK)<<UREG_A1_SRC0_SHIFT_RIGHT)
#define A1_SRC1(reg) (((reg) & UREG_MASK)>>UREG_A1_SRC1_SHIFT_LEFT)
#define A2_SRC1(reg) (((reg) & UREG_MASK)<<UREG_A2_SRC1_SHIFT_RIGHT)
#define A2_SRC2(reg) (((reg) & UREG_MASK)>>UREG_A2_SRC2_SHIFT_LEFT)
/* These are special, and don't have swizzle/negate bits.
*/
#define T0_SAMPLER( reg ) (GET_UREG_NR(reg)<<T0_SAMPLER_NR_SHIFT)
#define T1_ADDRESS_REG( reg ) ((GET_UREG_NR(reg)<<T1_ADDRESS_REG_NR_SHIFT) | \
(GET_UREG_TYPE(reg)<<T1_ADDRESS_REG_TYPE_SHIFT))
/* Macros for translating UREG's into the various register fields used
* by the I915 programmable unit.
*/
#define UREG_A0_DEST_SHIFT_LEFT (UREG_TYPE_SHIFT - A0_DEST_TYPE_SHIFT)
#define UREG_A0_SRC0_SHIFT_LEFT (UREG_TYPE_SHIFT - A0_SRC0_TYPE_SHIFT)
#define UREG_A1_SRC0_SHIFT_RIGHT (A1_SRC0_CHANNEL_W_SHIFT - UREG_CHANNEL_W_SHIFT)
#define UREG_A1_SRC1_SHIFT_LEFT (UREG_TYPE_SHIFT - A1_SRC1_TYPE_SHIFT)
#define UREG_A2_SRC1_SHIFT_RIGHT (A2_SRC1_CHANNEL_W_SHIFT - UREG_CHANNEL_W_SHIFT)
#define UREG_A2_SRC2_SHIFT_LEFT (UREG_TYPE_SHIFT - A2_SRC2_TYPE_SHIFT)
#define UREG_MASK 0xffffff00
#define UREG_TYPE_NR_MASK ((REG_TYPE_MASK << UREG_TYPE_SHIFT) | \
(REG_NR_MASK << UREG_NR_SHIFT))
#endif

898
src/xvmc/i915_structs.h Normal file
View File

@ -0,0 +1,898 @@
#ifndef _I915_STRUCTS_H
#define _I915_STRUCTS_H
/* MI_INSTRUCTION */
#define CMD_MI 0x00
#define OPC_MI_FLUSH (0x04)
struct i915_mi_flush
{
struct {
unsigned map_cache_invalidate : 1;
unsigned pad0 : 1;
unsigned render_cache_flush_inhibit : 1;
unsigned scene_count : 1;
unsigned end_scene : 1;
unsigned pad1 : 18;
unsigned opcode : 6;
unsigned type : 3;
} dw0;
};
/* 3D_INSTRUCTION */
#define CMD_3D 0x03
#define OPC_3DMPEG_MACROBLOCK_IPICTURE (0x01 + (0x1e << 5))
#define OPC_3DMPEG_SET_ORIGIN (0x10 + (0x1e << 5))
#define OPC_3DMPEG_MACROBLOCK (0x11 + (0x1e << 5))
#define OPC_3DMPEG_SLICE (0x12 + (0x1e << 5))
#define OPC_3DMPEG_QM_PALETTE_LOAD (0x13 + (0x1e << 5))
#define OPC_3DSTATE_MAP_STATE (0x00 + (0x1d << 8))
#define OPC_3DSTATE_SAMPLER_STATE (0x01 + (0x1d << 8))
#define OPC_3DSTATE_LOAD_STATE_IMMEDIATE_1 (0x04 + (0x1d << 8))
#define OPC_3DSTATE_PIXEL_SHADER_PROGRAM (0x05 + (0x1d << 8))
#define OPC_3DSTATE_PIXEL_SHADER_CONSTANTS (0x06 + (0x1d << 8))
#define OPC_3DSTATE_LOAD_INDIRECT (0x07 + (0x1d << 8))
#define OPC_3DPRIMITIVE (0x1f)
#define OPC_3DSTATE_SCISSOR_RECTANGLE (0x81 + (0x1d << 8))
#define OPC_3DSTATE_DEST_BUFFER_VARIABLES (0x85 + (0x1d << 8))
#define OPC_3DSTATE_DEST_BUFFER_VARIABLES_MPEG (0x87 + (0x1d << 8))
#define OPC_3DSTATE_BUFFER_INFO (0x8e + (0x1d << 8))
/*
* 3DMPEG instructions
*/
struct i915_3dmpeg_macroblock_header
{
struct {
unsigned length : 19;
unsigned opcode : 10;
unsigned type : 3;
} dw0;
struct {
unsigned intra : 1;
unsigned forward : 1;
unsigned backward : 1;
unsigned h263_4mv : 1;
unsigned pad0 : 1;
unsigned dct_type : 1;
unsigned pad1 : 2;
unsigned motion_type : 2;
unsigned pad2 : 2;
unsigned vertical_field_select : 4;
unsigned coded_block_pattern : 6;
unsigned pad3 : 2;
unsigned skipped_macroblocks : 7;
unsigned pad4 : 1;
} dw1;
};
struct i915_3dmpeg_macroblock_0mv
{
struct i915_3dmpeg_macroblock_header header;
};
struct i915_3dmpeg_macroblock_1fbmv
{
struct i915_3dmpeg_macroblock_header header;
unsigned dw2;
unsigned dw3;
};
struct i915_3dmpeg_macroblock_2fbmv
{
struct i915_3dmpeg_macroblock_header header;
unsigned dw2;
unsigned dw3;
unsigned dw4;
unsigned dw5;
};
struct i915_3dmpeg_macroblock_5fmv
{
struct i915_3dmpeg_macroblock_header header;
unsigned dw2;
unsigned dw3;
unsigned dw4;
unsigned dw5;
unsigned dw6;
};
struct i915_3dmpeg_macroblock_ipicture
{
struct {
unsigned pad0 : 5;
unsigned dct_type : 1;
unsigned pad1 : 13;
unsigned opcode : 10;
unsigned type : 3;
} dw0;
};
struct i915_3dmpeg_set_origin
{
struct {
unsigned length : 19;
unsigned opcode : 10;
unsigned type : 3;
} dw0;
struct {
unsigned v_origin : 7;
unsigned pad0 : 1;
unsigned h_origin : 7;
unsigned pad1 : 17;
} dw1;
};
struct i915_3dmpeg_slice
{
struct {
unsigned length : 19;
unsigned opcode : 10;
unsigned type : 3;
} dw0;
struct {
unsigned fst_mb_bit_off : 3;
unsigned pad0 : 5;
unsigned mb_count : 7;
unsigned pad1 : 1;
unsigned v_position : 7;
unsigned pad2 : 1;
unsigned h_position : 7;
unsigned pad3 : 1;
} dw1;
struct {
unsigned length_minus_one : 17;
unsigned pad0 : 7;
unsigned qt_scale_code : 5;
unsigned pad1 : 3;
} dw2;
};
struct i915_3dmpeg_qm_palette_load
{
struct {
unsigned length : 4;
unsigned pad0 : 15;
unsigned opcode : 10;
unsigned type : 3;
} dw0;
unsigned quantmatrix[16];
};
/*
* 3DSTATE instruction
*/
#define BUFFERID_COLOR_BACK 3
#define BUFFERID_COLOR_AUX 4
#define BUFFERID_MC_INTRA_CORR 5
#define TILEWALK_XMAJOR 0
#define TILEWALK_YMAJOR 1
struct i915_3dstate_buffer_info
{
struct {
unsigned length : 16;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned pad0 : 2;
unsigned pitch : 12;
unsigned pad1 : 7;
unsigned walk : 1;
unsigned tiled_surface : 1;
unsigned fence_regs : 1;
unsigned buffer_id : 4;
unsigned aux_id : 1;
unsigned pad2 : 3;
} dw1;
struct {
unsigned pad0 : 2;
unsigned base_address : 27;
unsigned pad1 : 3;
} dw2;
};
#define COLORBUFFER_X1R5G5B5 0x01
#define COLORBUFFER_R5G6B5 0x02
#define COLORBUFFER_A8R8G8B8 0x03
#define COLORBUFFER_YCRCB_SWAP 0x04
#define COLORBUFFER_YCRCB_NORMAL 0x05
#define COLORBUFFER_YCRCB_SWAPUV 0x06
#define COLORBUFFER_YCRCB_SWAPUVY 0x07
#define COLORBUFFER_A4R4G4B4 0x08
#define COLORBUFFER_A1R5G5B5 0x09
#define COLORBUFFER_A2R10G10B10 0x0a
struct i915_3dstate_dest_buffer_variables
{
struct {
unsigned length : 16;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned v_ls_offset : 1;
unsigned v_ls : 1;
unsigned depth_fmt : 2;
unsigned pad0 : 4;
unsigned color_fmt : 4;
unsigned yuv422_select : 3;
unsigned pad1 : 1;
unsigned dest_v_bias : 4;
unsigned dest_h_bias : 4;
unsigned dither_enhancement : 1;
unsigned linear_gamma : 1;
unsigned dither_pattern : 2;
unsigned lod_preclamp : 1;
unsigned edt_zone : 1; /* early depth test in zone rendering */
unsigned texture_default_color : 1;
unsigned edt_classic : 1; /* early depth test in classic mode */
} dw1;
};
#define MPEG_DECODE_MC 0
#define MPEG_DECODE_VLD_IDCT_MC 1
#define MPEG_I_PICTURE 1
#define MPEG_P_PICTURE 2
#define MPEG_B_PICTURE 3
struct i915_3dstate_dest_buffer_variables_mpeg
{
struct {
unsigned length : 16;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned picture_width : 7;
unsigned pad0 : 1;
unsigned v_subsample_factor : 2;
unsigned h_subsample_factor : 2;
unsigned tff : 1;
unsigned mismatch : 1;
unsigned pad1 : 1;
unsigned intra8 : 1;
unsigned abort_on_error : 8;
unsigned pad2 : 4;
unsigned bidir_avrg_control : 1;
unsigned rcontrol : 1;
unsigned decoder_mode : 2;
} dw1;
struct {
unsigned pad0 : 1;
unsigned picture_coding_type : 2;
unsigned pad1 : 2;
unsigned scan_order : 1;
unsigned pad2 : 2;
unsigned q_scale_type : 1;
unsigned concealment : 1;
unsigned fpf_dct : 1;
unsigned pad3 : 2;
unsigned intra_dc : 2;
unsigned intra_vlc : 1;
unsigned f_code00 : 4;
unsigned f_code01 : 4;
unsigned f_code10 : 4;
unsigned f_code11 : 4;
} dw2;
};
#define MAP_MAP0 0x0001
#define MAP_MAP1 0x0002
#define MAP_MAP2 0x0004
#define MAP_MAP3 0x0008
#define MAP_MAP4 0x0010
#define MAP_MAP5 0x0020
#define MAP_MAP6 0x0040
#define MAP_MAP7 0x0080
#define MAP_MAP8 0x0100
#define MAP_MAP9 0x0200
#define MAP_MAP10 0x0400
#define MAP_MAP11 0x0800
#define MAP_MAP12 0x1000
#define MAP_MAP13 0x2000
#define MAP_MAP14 0x4000
#define MAP_MAP15 0x8000
struct texture_map
{
struct {
unsigned v_ls_offset : 1;
unsigned v_ls : 1;
unsigned base_address : 27;
unsigned pad0 : 2;
unsigned untrusted : 1;
} tm0;
struct {
unsigned tile_walk : 1;
unsigned tiled_surface : 1;
unsigned utilize_fence_regs : 1;
unsigned texel_fmt : 4;
unsigned surface_fmt : 3;
unsigned width : 11;
unsigned height : 11;
} tm1;
struct {
unsigned depth : 8;
unsigned mipmap_layout : 1;
unsigned max_lod : 6;
unsigned cube_face : 6;
unsigned pitch : 11;
} tm2;
};
struct i915_3dstate_map_state
{
struct {
unsigned length : 6;
unsigned pad0 : 9;
unsigned retain : 1;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned pad0 : 16;
unsigned map_mask : 16;
} dw1;
// struct texture_map *tms;
};
#define SAMPLER_SAMPLER0 0x0001
#define SAMPLER_SAMPLER1 0x0002
#define SAMPLER_SAMPLER2 0x0004
#define SAMPLER_SAMPLER3 0x0008
#define SAMPLER_SAMPLER4 0x0010
#define SAMPLER_SAMPLER5 0x0020
#define SAMPLER_SAMPLER6 0x0040
#define SAMPLER_SAMPLER7 0x0080
#define SAMPLER_SAMPLER8 0x0100
#define SAMPLER_SAMPLER9 0x0200
#define SAMPLER_SAMPLER10 0x0400
#define SAMPLER_SAMPLER11 0x0800
#define SAMPLER_SAMPLER12 0x1000
#define SAMPLER_SAMPLER13 0x2000
#define SAMPLER_SAMPLER14 0x4000
#define SAMPLER_SAMPLER15 0x8000
#define MIPFILTER_NONE 0
#define MIPFILTER_NEAREST 1
#define MIPFILTER_LINEAR 3
#define MAPFILTER_NEAREST 0
#define MAPFILTER_LINEAR 1
#define MAPFILTER_ANISOTROPIC 2
#define MAPFILTER_4X4_1 3
#define MAPFILTER_4X4_2 4
#define MAPFILTER_4X4_FLAT 5
#define MAPFILTER_MONO 6
#define ANISORATIO_2 0
#define ANISORATIO_4 1
#define PREFILTEROP_ALWAYS 0
#define PREFILTEROP_NEVER 1
#define PREFILTEROP_LESS 2
#define PREFILTEROP_EQUAL 3
#define PREFILTEROP_LEQUAL 4
#define PREFILTEROP_GREATER 5
#define PREFILTEROP_NOTEQUAL 6
#define PREFILTEROP_GEQUAL 7
#define TEXCOORDMODE_WRAP 0
#define TEXCOORDMODE_MIRROR 1
#define TEXCOORDMODE_CLAMP 2
#define TEXCOORDMODE_CUBE 3
#define TEXCOORDMODE_CLAMP_BORDER 4
#define TEXCOORDMODE_MIRROR_ONCE 5
struct texture_sampler
{
struct {
unsigned shadow_function : 3;
unsigned max_anisotropy : 1;
unsigned shadow_enable : 1;
unsigned lod_bias : 9;
unsigned min_filter : 3;
unsigned mag_filter : 3;
unsigned mip_filter : 2;
unsigned base_level : 5;
unsigned chromakey_index : 2;
unsigned color_conversion : 1;
unsigned planar2packet : 1;
unsigned reverse_gamma : 1;
} ts0;
struct {
unsigned east_deinterlacer : 1;
unsigned map_index : 4;
unsigned normalized_coor : 1;
unsigned tcz_control : 3;
unsigned tcy_control : 3;
unsigned tcx_control : 3;
unsigned chromakey_enable : 1;
unsigned keyed_texture_filter : 1;
unsigned kill_pixel : 1;
unsigned pad0 : 6;
unsigned min_lod : 8;
} ts1;
struct {
unsigned default_color;
} ts2;
};
struct i915_3dstate_sampler_state
{
struct {
unsigned length : 6;
unsigned pad0 : 10;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned sampler_masker : 16;
unsigned pad0 : 16;
} dw1;
};
struct arithmetic_inst
{
struct {
unsigned pad0 : 2;
unsigned src0_reg : 5;
unsigned src0_reg_t : 3;
unsigned dest_channel_mask : 4;
unsigned dest_reg : 4;
unsigned pad1 : 1;
unsigned dest_reg_t: 3;
unsigned dest_saturate : 1;
unsigned pad2 : 1;
unsigned opcode : 5;
unsigned pad3 : 3;
} dw0;
struct {
unsigned src1_y_select : 3;
unsigned src1_y_negate : 1;
unsigned src1_x_select : 3;
unsigned src1_x_negate : 1;
unsigned src1_reg : 5;
unsigned src1_reg_t : 3;
unsigned src0_w_select : 3;
unsigned src0_w_negate : 1;
unsigned src0_z_select : 3;
unsigned src0_z_negate : 1;
unsigned src0_y_select : 3;
unsigned src0_y_negate : 1;
unsigned src0_x_select : 3;
unsigned src0_x_negate : 1;
} dw1;
struct {
unsigned src2_w_select : 3;
unsigned src2_w_negate : 1;
unsigned src2_z_select : 3;
unsigned src2_z_negate : 1;
unsigned src2_y_select : 3;
unsigned src2_y_negate : 1;
unsigned src2_x_select : 3;
unsigned src2_x_negate : 1;
unsigned src2_reg : 5;
unsigned src2_reg_t : 3;
unsigned src1_w_select : 3;
unsigned src1_w_negate : 1;
unsigned src1_z_select : 3;
unsigned src1_z_negate : 1;
} dw2;
};
struct texture_inst
{
struct {
unsigned sampler_reg : 4;
unsigned pad0 : 10;
unsigned dest_reg : 4;
unsigned pad1 : 1;
unsigned dest_reg_t : 3;
unsigned pad2 : 2;
unsigned opcode : 5;
unsigned pad3 : 3;
} dw0;
struct {
unsigned pad0 : 16;
unsigned address_reg : 5;
unsigned pad1 : 3;
unsigned address_reg_t : 3;
unsigned pad2 : 5;
} dw1;
struct {
unsigned pad0;
} dw2;
};
struct declaration_inst
{
struct {
unsigned pad0 : 10;
unsigned decl_channel_mask : 4;
unsigned decl_reg : 4;
unsigned pad1 : 1;
unsigned decl_reg_t : 2;
unsigned pad2 : 1;
unsigned sampler_type : 2;
unsigned opcode : 5;
unsigned pad3 : 3;
} dw0;
struct {
unsigned pad0;
} dw1;
struct {
unsigned pad0;
} dw2;
};
union shader_inst
{
struct arithmetic_inst a;
struct texture_inst t;
struct declaration_inst d;
};
struct i915_3dstate_pixel_shader_program
{
struct {
unsigned length : 9;
unsigned pad0 : 6;
unsigned retain : 1;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
// union shader_inst *insts;
};
#define REG_CR0 0x00000001
#define REG_CR1 0x00000002
#define REG_CR2 0x00000004
#define REG_CR3 0x00000008
#define REG_CR4 0x00000010
#define REG_CR5 0x00000020
#define REG_CR6 0x00000040
#define REG_CR7 0x00000080
#define REG_CR8 0x00000100
#define REG_CR9 0x00000200
#define REG_CR10 0x00000400
#define REG_CR11 0x00000800
#define REG_CR12 0x00001000
#define REG_CR13 0x00002000
#define REG_CR14 0x00004000
#define REG_CR15 0x00008000
#define REG_CR16 0x00010000
#define REG_CR17 0x00020000
#define REG_CR18 0x00040000
#define REG_CR19 0x00080000
#define REG_CR20 0x00100000
#define REG_CR21 0x00200000
#define REG_CR22 0x00400000
#define REG_CR23 0x00800000
#define REG_CR24 0x01000000
#define REG_CR25 0x02000000
#define REG_CR26 0x04000000
#define REG_CR27 0x08000000
#define REG_CR28 0x10000000
#define REG_CR29 0x20000000
#define REG_CR30 0x40000000
#define REG_CR31 0x80000000
struct shader_constant
{
float x;
float y;
float z;
float w;
};
struct i915_3dstate_pixel_shader_constants
{
struct {
unsigned length : 8;
unsigned pad0 : 8;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned reg_mask;
} dw1;
// struct shader_constant *consts;
};
#define BLOCK_SIS 0x01
#define BLOCK_DIS 0x02
#define BLOCK_SSB 0x04
#define BLOCK_MSB 0x08
#define BLOCK_PSP 0x10
#define BLOCK_PSC 0x20
typedef struct _state_ddword
{
struct {
unsigned valid : 1;
unsigned force : 1;
unsigned buffer_address : 30;
} dw0;
struct {
unsigned length : 9;
unsigned pad0 : 23;
} dw1;
} sis_state, ssb_state, msb_state, psp_state, psc_state;
typedef struct _state_dword
{
struct {
unsigned valid : 1;
unsigned reset : 1;
unsigned buffer_address : 30;
} dw0;
} dis_state;
struct i915_3dstate_load_indirect
{
struct {
unsigned length : 8;
unsigned block_mask : 6;
unsigned mem_select : 1;
unsigned pad0 : 1;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
};
#define TEXCOORDFMT_2FP 0x00
#define TEXCOORDFMT_3FP 0x01
#define TEXCOORDFMT_4FP 0x02
#define TEXCOORDFMT_1FP 0x03
#define TEXCOORDFMT_2FP_16 0x04
#define TEXCOORDFMT_4FP_16 0x05
#define TEXCOORDFMT_NOT_PRESENT 0x0f
struct s2_dword
{
unsigned set0_texcoord_fmt : 4;
unsigned set1_texcoord_fmt : 4;
unsigned set2_texcoord_fmt : 4;
unsigned set3_texcoord_fmt : 4;
unsigned set4_texcoord_fmt : 4;
unsigned set5_texcoord_fmt : 4;
unsigned set6_texcoord_fmt : 4;
unsigned set7_texcoord_fmt : 4;
};
struct s3_dword
{
unsigned set0_pcd : 1;
unsigned set0_ws_tcz : 1;
unsigned set0_ws_tcy : 1;
unsigned set0_ws_tcx : 1;
unsigned set1_pcd : 1;
unsigned set1_ws_tcz : 1;
unsigned set1_ws_tcy : 1;
unsigned set1_ws_tcx : 1;
unsigned set2_pcd : 1;
unsigned set2_ws_tcz : 1;
unsigned set2_ws_tcy : 1;
unsigned set2_ws_tcx : 1;
unsigned set3_pcd : 1;
unsigned set3_ws_tcz : 1;
unsigned set3_ws_tcy : 1;
unsigned set3_ws_tcx : 1;
unsigned set4_pcd : 1;
unsigned set4_ws_tcz : 1;
unsigned set4_ws_tcy : 1;
unsigned set4_ws_tcx : 1;
unsigned set5_pcd : 1;
unsigned set5_ws_tcz : 1;
unsigned set5_ws_tcy : 1;
unsigned set5_ws_tcx : 1;
unsigned set6_pcd : 1;
unsigned set6_ws_tcz : 1;
unsigned set6_ws_tcy : 1;
unsigned set6_ws_tcx : 1;
unsigned set7_pcd : 1;
unsigned set7_ws_tcz : 1;
unsigned set7_ws_tcy : 1;
unsigned set7_ws_tcx : 1;
};
#define VERTEXHAS_XYZ 1
#define VERTEXHAS_XYZW 2
#define VERTEXHAS_XY 3
#define VERTEXHAS_XYW 4
#define CULLMODE_BOTH 0
#define CULLMODE_NONE 1
#define CULLMODE_CW 2
#define CULLMODE_CCW 3
#define SHADEMODE_LINEAR 0
#define SHADEMODE_FLAT 1
struct s4_dword
{
unsigned anti_aliasing_enable : 1;
unsigned sprite_point_enable : 1;
unsigned fog_parameter_present : 1;
unsigned local_depth_offset_enable : 1;
unsigned force_specular_diffuse_color : 1;
unsigned force_default_diffuse_color : 1;
unsigned position_mask : 3;
unsigned local_depth_offset_present : 1;
unsigned diffuse_color_presetn : 1;
unsigned specular_color_fog_factor_present : 1;
unsigned point_width_present : 1;
unsigned cull_mode : 2;
unsigned color_shade_mode : 1;
unsigned specular_shade_mode : 1;
unsigned fog_shade_mode : 1;
unsigned alpha_shade_mode : 1;
unsigned line_width : 4;
unsigned point_width : 9;
};
struct s5_dword
{
unsigned logic_op_enable : 1;
unsigned color_dither_enable : 1;
unsigned stencil_test_enable : 1;
unsigned stencil_buffer_write_enable : 1;
unsigned stencil_pass_depth_pass_op : 3;
unsigned stencil_pass_depth_fail_op : 3;
unsigned stencil_fail_op : 3;
unsigned stencil_test_function : 3;
unsigned stencil_reference_value : 8;
unsigned fog_enable : 1;
unsigned global_depth_offset_enable : 1;
unsigned last_pixel_enable : 1;
unsigned force_default_point_width : 1;
unsigned color_buffer_component_write_disable : 4;
};
struct s6_dword
{
unsigned triangle_pv : 2;
unsigned color_buffer_write : 1;
unsigned depth_buffer_write : 1;
unsigned dest_blend_factor : 4;
unsigned src_blend_factor : 4;
unsigned color_blend_function : 3;
unsigned color_buffer_blend : 1;
unsigned depth_test_function : 3;
unsigned depth_test_enable : 1;
unsigned alpha_reference_value : 8;
unsigned alpha_test_function : 3;
unsigned alpha_test_enable : 1;
};
struct s7_dword
{
unsigned global_depth_offset_const;
};
struct i915_3dstate_load_state_immediate_1
{
struct {
unsigned length : 4;
unsigned load_s0 : 1;
unsigned load_s1 : 1;
unsigned load_s2 : 1;
unsigned load_s3 : 1;
unsigned load_s4 : 1;
unsigned load_s5 : 1;
unsigned load_s6 : 1;
unsigned load_s7 : 1;
unsigned pad0 : 4;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
};
struct i915_3dstate_scissor_rectangle
{
struct {
unsigned length : 16;
unsigned opcode : 13;
unsigned type : 3;
} dw0;
struct {
unsigned min_x : 16;
unsigned min_y : 16;
} dw1;
struct {
unsigned max_x : 16;
unsigned max_y : 16;
} dw2;
};
#define VERTEX_INLINE 0x00
#define VERTEX_INDIRECT 0x01
#define PRIM_TRILIST 0x00
#define PRIM_TRISTRIP 0x01
#define PRIM_TRISTRIP_REVERSE 0x02
#define PRIM_TRIFAN 0x03
#define PRIM_POLYGON 0x04
#define PRIM_LINELIST 0x05
#define PRIM_LINESTRIP 0x06
#define PRIM_RECTLIST 0x07
#define PRIM_POINTLIST 0x08
#define PRIM_DIB 0x09
#define PRIM_CLEAR_RECT 0x0a
#define PRIM_ZONE_INIT 0x0d
struct texture_coordinate_set
{
unsigned tcx;
unsigned tcy;
};
struct vertex_data
{
unsigned x;
unsigned y;
struct texture_coordinate_set tc0;
struct texture_coordinate_set tc1;
};
struct i915_3dprimitive
{
union {
struct {
unsigned length : 18;
unsigned prim : 5;
unsigned vertex_location : 1;
unsigned opcode : 5;
unsigned type : 3;
} inline_prim;
struct {
unsigned vertex_count : 16;
unsigned pad0 : 1;
unsigned vertex_access_mode : 1;
unsigned prim : 5;
unsigned vertex_location : 1;
unsigned opcode : 5;
unsigned type : 3;
} indirect_prim;
} dw0;
};
#endif /*_I915_STRUCTS_H */

View File

@ -0,0 +1,197 @@
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <errno.h>
#include <signal.h>
#include <fcntl.h>
#include <dirent.h>
#include <string.h>
#include <sys/ioctl.h>
#include <X11/Xlibint.h>
#include <fourcc.h>
#include <X11/extensions/Xv.h>
#include <X11/extensions/Xvlib.h>
#include <X11/extensions/XvMC.h>
#include <X11/extensions/XvMClib.h>
#include "I915XvMC.h"
#include "intel_batchbuffer.h"
int intelEmitIrqLocked(i915XvMCContext *pI915XvMC)
{
drmI830IrqEmit ie;
int ret, seq;
ie.irq_seq = &seq;
ret = drmCommandWriteRead(pI915XvMC->fd, DRM_I830_IRQ_EMIT,
&ie, sizeof(ie));
if ( ret ) {
fprintf(stderr, "%s: drmI830IrqEmit: %d\n", __FUNCTION__, ret);
exit(1);
}
return seq;
}
void intelWaitIrq(i915XvMCContext *pI915XvMC, int seq)
{
int ret;
drmI830IrqWait iw;
iw.irq_seq = seq;
do {
ret = drmCommandWrite(pI915XvMC->fd, DRM_I830_IRQ_WAIT, &iw, sizeof(iw) );
} while (ret == -EAGAIN || ret == -EINTR);
if (ret) {
fprintf(stderr, "%s: drmI830IrqWait: %d\n", __FUNCTION__, ret);
exit(1);
}
}
void intelDestroyBatchBuffer(i915XvMCContext *pI915XvMC)
{
if (pI915XvMC->alloc.offset) {
// FIXME: free the memory allocated from AGP
} else if (pI915XvMC->alloc.ptr) {
free(pI915XvMC->alloc.ptr);
pI915XvMC->alloc.ptr = NULL;
}
memset(&pI915XvMC->batch, 0, sizeof(pI915XvMC->batch));
}
void intelInitBatchBuffer(i915XvMCContext *pI915XvMC)
{
pI915XvMC->alloc.offset = 0;
pI915XvMC->alloc.size = 16 * 1024;
pI915XvMC->alloc.ptr = malloc(pI915XvMC->alloc.size);
pI915XvMC->alloc.active_buf = 0;
assert(pI915XvMC->alloc.ptr);
}
void intelBatchbufferRequireSpace(i915XvMCContext *pI915XvMC, unsigned sz)
{
if (pI915XvMC->batch.space < sz)
intelFlushBatch(pI915XvMC, TRUE);
}
void intelBatchbufferData(i915XvMCContext *pI915XvMC, const void *data,
unsigned bytes, unsigned flags)
{
assert((bytes & 3) == 0);
intelBatchbufferRequireSpace(pI915XvMC, bytes);
memcpy(pI915XvMC->batch.ptr, data, bytes);
pI915XvMC->batch.ptr += bytes;
pI915XvMC->batch.space -= bytes;
assert(pI915XvMC->batch.space >= 0);
}
void intelRefillBatchLocked(i915XvMCContext *pI915XvMC, Bool allow_unlock )
{
unsigned last_irq = pI915XvMC->alloc.irq_emitted;
unsigned half = pI915XvMC->alloc.size >> 1;
unsigned buf = (pI915XvMC->alloc.active_buf ^= 1);
pI915XvMC->alloc.irq_emitted = intelEmitIrqLocked(pI915XvMC);
if (last_irq) {
intelWaitIrq(pI915XvMC, last_irq);
}
pI915XvMC->batch.start_offset = pI915XvMC->alloc.offset + buf * half;
pI915XvMC->batch.ptr = (unsigned char *)pI915XvMC->alloc.ptr + buf * half;
pI915XvMC->batch.size = half - 8;
pI915XvMC->batch.space = half - 8;
assert(pI915XvMC->batch.space >= 0);
}
void intelFlushBatchLocked(i915XvMCContext *pI915XvMC,
Bool ignore_cliprects,
Bool refill,
Bool allow_unlock)
{
drmI830BatchBuffer batch;
if (pI915XvMC->batch.space != pI915XvMC->batch.size) {
batch.start = pI915XvMC->batch.start_offset;
batch.used = pI915XvMC->batch.size - pI915XvMC->batch.space;
batch.cliprects = 0;
batch.num_cliprects = 0;
batch.DR1 = 0;
batch.DR4 = 0;
if (pI915XvMC->alloc.offset) {
// FIXME: MI_BATCH_BUFFER_END
}
pI915XvMC->batch.start_offset += batch.used;
pI915XvMC->batch.size -= batch.used;
if (pI915XvMC->batch.size < 8) {
refill = TRUE;
pI915XvMC->batch.space = pI915XvMC->batch.size = 0;
}
else {
pI915XvMC->batch.size -= 8;
pI915XvMC->batch.space = pI915XvMC->batch.size;
}
assert(pI915XvMC->batch.space >= 0);
assert(batch.start >= pI915XvMC->alloc.offset);
assert(batch.start < pI915XvMC->alloc.offset + pI915XvMC->alloc.size);
assert(batch.start + batch.used > pI915XvMC->alloc.offset);
assert(batch.start + batch.used <= pI915XvMC->alloc.offset + pI915XvMC->alloc.size);
if (pI915XvMC->alloc.offset) {
// DRM_I830_BATCHBUFFER
} else {
drmI830CmdBuffer cmd;
cmd.buf = (char *)pI915XvMC->alloc.ptr + batch.start;
cmd.sz = batch.used;
cmd.DR1 = batch.DR1;
cmd.DR4 = batch.DR4;
cmd.num_cliprects = batch.num_cliprects;
cmd.cliprects = batch.cliprects;
if (drmCommandWrite(pI915XvMC->fd, DRM_I830_CMDBUFFER,
&cmd, sizeof(cmd))) {
fprintf(stderr, "DRM_I915_CMDBUFFER: %d\n", -errno);
exit(1);
}
}
}
if (refill)
intelRefillBatchLocked(pI915XvMC, allow_unlock);
}
void intelFlushBatch(i915XvMCContext *pI915XvMC, Bool refill )
{
intelFlushBatchLocked(pI915XvMC, FALSE, refill, TRUE);
}
void intelCmdIoctl(i915XvMCContext *pI915XvMC, char *buf, unsigned used)
{
drmI830CmdBuffer cmd;
cmd.buf = buf;
cmd.sz = used;
cmd.cliprects = 0;
cmd.num_cliprects = 0;
cmd.DR1 = 0;
cmd.DR4 = 0;
if (drmCommandWrite(pI915XvMC->fd, DRM_I830_CMDBUFFER,
&cmd, sizeof(cmd))) {
fprintf(stderr, "DRM_I830_CMDBUFFER: %d\n", -errno);
exit(1);
}
}

View File

@ -0,0 +1,42 @@
#ifndef _INTEL_BATCHBUFFER_H
#define _INTEL_BATCHBUFFER_H
/* #define VERBOSE 0 */
#ifndef VERBOSE
extern int VERBOSE;
#endif
#define BATCH_LOCALS char *batch_ptr;
#define BEGIN_BATCH(n) \
do { \
if (VERBOSE) fprintf(stderr, \
"BEGIN_BATCH(%ld) in %s, %d dwords free\n", \
((unsigned long)n), __FUNCTION__, \
pI915XvMC->batch.space/4); \
if (pI915XvMC->batch.space < (n)*4) \
intelFlushBatch(pI915XvMC, TRUE); \
batch_ptr = pI915XvMC->batch.ptr; \
} while (0)
#define OUT_BATCH(n) \
do { \
*(GLuint *)batch_ptr = (n); \
if (VERBOSE) fprintf(stderr, " -- %08x at %s/%d\n", (n), __FILE__, __LINE__); \
batch_ptr += 4; \
} while (0)
#define ADVANCE_BATCH() \
do { \
if (VERBOSE) fprintf(stderr, "ADVANCE_BATCH()\n"); \
pI915XvMC->batch.space -= (batch_ptr - pI915XvMC->batch.ptr); \
pI915XvMC->batch.ptr = batch_ptr; \
assert(pI915XvMC->batch.space >= 0); \
} while(0)
extern void intelFlushBatch(i915XvMCContext *, Bool);
extern void intelBatchbufferData(i915XvMCContext *, const void *, unsigned, unsigned);
extern void intelInitBatchBuffer(i915XvMCContext *);
extern void intelDestroyBatchBuffer(i915XvMCContext *);
extern void intelCmdIoctl(i915XvMCContext *, char *, unsigned);
#endif /* _INTEL_BATCHBUFFER_H */

599
src/xvmc/xf86dri.c Normal file
View File

@ -0,0 +1,599 @@
/* $XFree86: xc/lib/GL/dri/XF86dri.c,v 1.13 2002/10/30 12:51:25 alanh Exp $ */
/**************************************************************************
Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
Copyright 2000 VA Linux Systems, Inc.
All Rights Reserved.
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sub license, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice (including the
next paragraph) shall be included in all copies or substantial portions
of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
**************************************************************************/
/*
* Authors:
* Kevin E. Martin <martin@valinux.com>
* Jens Owen <jens@tungstengraphics.com>
* Rickard E. (Rik) Faith <faith@valinux.com>
*
*/
/* THIS IS NOT AN X CONSORTIUM STANDARD */
#define NEED_REPLIES
#include <X11/Xlibint.h>
#include <X11/extensions/Xext.h>
#include <X11/extensions/extutil.h>
#include "xf86dristr.h"
static XExtensionInfo _xf86dri_info_data;
static XExtensionInfo *xf86dri_info = &_xf86dri_info_data;
static char xf86dri_extension_name[] = XF86DRINAME;
#define uniDRICheckExtension(dpy,i,val) \
XextCheckExtension (dpy, i, xf86dri_extension_name, val)
/*****************************************************************************
* *
* private utility routines *
* *
*****************************************************************************/
static int close_display(Display * dpy, XExtCodes * extCodes);
static /* const */ XExtensionHooks xf86dri_extension_hooks = {
NULL, /* create_gc */
NULL, /* copy_gc */
NULL, /* flush_gc */
NULL, /* free_gc */
NULL, /* create_font */
NULL, /* free_font */
close_display, /* close_display */
NULL, /* wire_to_event */
NULL, /* event_to_wire */
NULL, /* error */
NULL, /* error_string */
};
static
XEXT_GENERATE_FIND_DISPLAY(find_display, xf86dri_info,
xf86dri_extension_name, &xf86dri_extension_hooks, 0, NULL)
static XEXT_GENERATE_CLOSE_DISPLAY(close_display, xf86dri_info)
/*****************************************************************************
* *
* public XFree86-DRI Extension routines *
* *
*****************************************************************************/
#if 0
#include <stdio.h>
#define TRACE(msg) fprintf(stderr,"uniDRI%s\n", msg);
#else
#define TRACE(msg)
#endif
Bool uniDRIQueryExtension(dpy, event_basep, error_basep)
Display *dpy;
int *event_basep, *error_basep;
{
XExtDisplayInfo *info = find_display(dpy);
TRACE("QueryExtension...");
if (XextHasExtension(info)) {
*event_basep = info->codes->first_event;
*error_basep = info->codes->first_error;
TRACE("QueryExtension... return True");
return True;
} else {
TRACE("QueryExtension... return False");
return False;
}
}
Bool
uniDRIQueryVersion(dpy, majorVersion, minorVersion, patchVersion)
Display *dpy;
int *majorVersion;
int *minorVersion;
int *patchVersion;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIQueryVersionReply rep;
xXF86DRIQueryVersionReq *req;
TRACE("QueryVersion...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIQueryVersion, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIQueryVersion;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("QueryVersion... return False");
return False;
}
*majorVersion = rep.majorVersion;
*minorVersion = rep.minorVersion;
*patchVersion = rep.patchVersion;
UnlockDisplay(dpy);
SyncHandle();
TRACE("QueryVersion... return True");
return True;
}
Bool
uniDRIQueryDirectRenderingCapable(dpy, screen, isCapable)
Display *dpy;
int screen;
Bool *isCapable;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIQueryDirectRenderingCapableReply rep;
xXF86DRIQueryDirectRenderingCapableReq *req;
TRACE("QueryDirectRenderingCapable...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIQueryDirectRenderingCapable, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIQueryDirectRenderingCapable;
req->screen = screen;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("QueryDirectRenderingCapable... return False");
return False;
}
*isCapable = rep.isCapable;
UnlockDisplay(dpy);
SyncHandle();
TRACE("QueryDirectRenderingCapable... return True");
return True;
}
Bool
uniDRIOpenConnection(dpy, screen, hSAREA, busIdString)
Display *dpy;
int screen;
drm_handle_t *hSAREA;
char **busIdString;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIOpenConnectionReply rep;
xXF86DRIOpenConnectionReq *req;
TRACE("OpenConnection...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIOpenConnection, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIOpenConnection;
req->screen = screen;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("OpenConnection... return False");
return False;
}
*hSAREA = rep.hSAREALow;
#ifdef LONG64
if (sizeof(drm_handle_t) == 8) {
*hSAREA |= ((unsigned long)rep.hSAREAHigh) << 32;
}
#endif
if (rep.length) {
if (!(*busIdString = (char *)Xcalloc(rep.busIdStringLength + 1, 1))) {
_XEatData(dpy, ((rep.busIdStringLength + 3) & ~3));
UnlockDisplay(dpy);
SyncHandle();
TRACE("OpenConnection... return False");
return False;
}
_XReadPad(dpy, *busIdString, rep.busIdStringLength);
} else {
*busIdString = NULL;
}
UnlockDisplay(dpy);
SyncHandle();
TRACE("OpenConnection... return True");
return True;
}
Bool
uniDRIAuthConnection(dpy, screen, magic)
Display *dpy;
int screen;
drm_magic_t magic;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIAuthConnectionReq *req;
xXF86DRIAuthConnectionReply rep;
TRACE("AuthConnection...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIAuthConnection, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIAuthConnection;
req->screen = screen;
req->magic = magic;
rep.authenticated = 0;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse) || !rep.authenticated) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("AuthConnection... return False");
return False;
}
UnlockDisplay(dpy);
SyncHandle();
TRACE("AuthConnection... return True");
return True;
}
Bool
uniDRICloseConnection(dpy, screen)
Display *dpy;
int screen;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRICloseConnectionReq *req;
TRACE("CloseConnection...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRICloseConnection, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRICloseConnection;
req->screen = screen;
UnlockDisplay(dpy);
SyncHandle();
TRACE("CloseConnection... return True");
return True;
}
Bool
uniDRIGetClientDriverName(dpy, screen, ddxDriverMajorVersion,
ddxDriverMinorVersion, ddxDriverPatchVersion, clientDriverName)
Display *dpy;
int screen;
int *ddxDriverMajorVersion;
int *ddxDriverMinorVersion;
int *ddxDriverPatchVersion;
char **clientDriverName;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIGetClientDriverNameReply rep;
xXF86DRIGetClientDriverNameReq *req;
TRACE("GetClientDriverName...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIGetClientDriverName, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIGetClientDriverName;
req->screen = screen;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetClientDriverName... return False");
return False;
}
*ddxDriverMajorVersion = rep.ddxDriverMajorVersion;
*ddxDriverMinorVersion = rep.ddxDriverMinorVersion;
*ddxDriverPatchVersion = rep.ddxDriverPatchVersion;
if (rep.length) {
if (!(*clientDriverName =
(char *)Xcalloc(rep.clientDriverNameLength + 1, 1))) {
_XEatData(dpy, ((rep.clientDriverNameLength + 3) & ~3));
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetClientDriverName... return False");
return False;
}
_XReadPad(dpy, *clientDriverName, rep.clientDriverNameLength);
} else {
*clientDriverName = NULL;
}
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetClientDriverName... return True");
return True;
}
Bool
uniDRICreateContextWithConfig(dpy, screen, configID, context, hHWContext)
Display *dpy;
int screen;
int configID;
XID *context;
drm_context_t *hHWContext;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRICreateContextReply rep;
xXF86DRICreateContextReq *req;
TRACE("CreateContext...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRICreateContext, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRICreateContext;
req->visual = configID;
req->screen = screen;
*context = XAllocID(dpy);
req->context = *context;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("CreateContext... return False");
return False;
}
*hHWContext = rep.hHWContext;
UnlockDisplay(dpy);
SyncHandle();
TRACE("CreateContext... return True");
return True;
}
Bool
uniDRICreateContext(dpy, screen, visual, context, hHWContext)
Display *dpy;
int screen;
Visual *visual;
XID *context;
drm_context_t *hHWContext;
{
return uniDRICreateContextWithConfig(dpy, screen, visual->visualid,
context, hHWContext);
}
Bool
uniDRIDestroyContext(Display * ndpy, int screen, XID context)
{
Display *const dpy = (Display *) ndpy;
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIDestroyContextReq *req;
TRACE("DestroyContext...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIDestroyContext, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIDestroyContext;
req->screen = screen;
req->context = context;
UnlockDisplay(dpy);
SyncHandle();
TRACE("DestroyContext... return True");
return True;
}
Bool
uniDRICreateDrawable(Display * ndpy, int screen,
Drawable drawable, drm_drawable_t * hHWDrawable)
{
Display *const dpy = (Display *) ndpy;
XExtDisplayInfo *info = find_display(dpy);
xXF86DRICreateDrawableReply rep;
xXF86DRICreateDrawableReq *req;
TRACE("CreateDrawable...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRICreateDrawable, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRICreateDrawable;
req->screen = screen;
req->drawable = drawable;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("CreateDrawable... return False");
return False;
}
*hHWDrawable = rep.hHWDrawable;
UnlockDisplay(dpy);
SyncHandle();
TRACE("CreateDrawable... return True");
return True;
}
Bool
uniDRIDestroyDrawable(Display * ndpy, int screen, Drawable drawable)
{
Display *const dpy = (Display *) ndpy;
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIDestroyDrawableReq *req;
TRACE("DestroyDrawable...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIDestroyDrawable, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIDestroyDrawable;
req->screen = screen;
req->drawable = drawable;
UnlockDisplay(dpy);
SyncHandle();
TRACE("DestroyDrawable... return True");
return True;
}
Bool
uniDRIGetDrawableInfo(Display * dpy, int screen, Drawable drawable,
unsigned int *index, unsigned int *stamp,
int *X, int *Y, int *W, int *H,
int *numClipRects, drm_clip_rect_t ** pClipRects,
int *backX, int *backY,
int *numBackClipRects, drm_clip_rect_t ** pBackClipRects)
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIGetDrawableInfoReply rep;
xXF86DRIGetDrawableInfoReq *req;
int total_rects;
TRACE("GetDrawableInfo...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIGetDrawableInfo, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIGetDrawableInfo;
req->screen = screen;
req->drawable = drawable;
if (!_XReply(dpy, (xReply *) & rep, 1, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetDrawableInfo... return False");
return False;
}
*index = rep.drawableTableIndex;
*stamp = rep.drawableTableStamp;
*X = (int)rep.drawableX;
*Y = (int)rep.drawableY;
*W = (int)rep.drawableWidth;
*H = (int)rep.drawableHeight;
*numClipRects = rep.numClipRects;
total_rects = *numClipRects;
*backX = rep.backX;
*backY = rep.backY;
*numBackClipRects = rep.numBackClipRects;
total_rects += *numBackClipRects;
#if 0
/* Because of the fix in Xserver/GL/dri/xf86dri.c, this check breaks
* backwards compatibility (Because of the >> 2 shift) but the fix
* enables multi-threaded apps to work.
*/
if (rep.length != ((((SIZEOF(xXF86DRIGetDrawableInfoReply) -
SIZEOF(xGenericReply) +
total_rects * sizeof(drm_clip_rect_t)) +
3) & ~3) >> 2)) {
_XEatData(dpy, rep.length);
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetDrawableInfo... return False");
return False;
}
#endif
if (*numClipRects) {
int len = sizeof(drm_clip_rect_t) * (*numClipRects);
*pClipRects = (drm_clip_rect_t *) Xcalloc(len, 1);
if (*pClipRects)
_XRead(dpy, (char *)*pClipRects, len);
} else {
*pClipRects = NULL;
}
if (*numBackClipRects) {
int len = sizeof(drm_clip_rect_t) * (*numBackClipRects);
*pBackClipRects = (drm_clip_rect_t *) Xcalloc(len, 1);
if (*pBackClipRects)
_XRead(dpy, (char *)*pBackClipRects, len);
} else {
*pBackClipRects = NULL;
}
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetDrawableInfo... return True");
return True;
}
Bool
uniDRIGetDeviceInfo(dpy, screen, hFrameBuffer,
fbOrigin, fbSize, fbStride, devPrivateSize, pDevPrivate)
Display *dpy;
int screen;
drm_handle_t *hFrameBuffer;
int *fbOrigin;
int *fbSize;
int *fbStride;
int *devPrivateSize;
void **pDevPrivate;
{
XExtDisplayInfo *info = find_display(dpy);
xXF86DRIGetDeviceInfoReply rep;
xXF86DRIGetDeviceInfoReq *req;
TRACE("GetDeviceInfo...");
uniDRICheckExtension(dpy, info, False);
LockDisplay(dpy);
GetReq(XF86DRIGetDeviceInfo, req);
req->reqType = info->codes->major_opcode;
req->driReqType = X_XF86DRIGetDeviceInfo;
req->screen = screen;
if (!_XReply(dpy, (xReply *) & rep, 0, xFalse)) {
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetDeviceInfo... return False");
return False;
}
*hFrameBuffer = rep.hFrameBufferLow;
#ifdef LONG64
if (sizeof(drm_handle_t) == 8) {
*hFrameBuffer |= ((unsigned long)rep.hFrameBufferHigh) << 32;
}
#endif
*fbOrigin = rep.framebufferOrigin;
*fbSize = rep.framebufferSize;
*fbStride = rep.framebufferStride;
*devPrivateSize = rep.devPrivateSize;
if (rep.length) {
if (!(*pDevPrivate = (void *)Xcalloc(rep.devPrivateSize, 1))) {
_XEatData(dpy, ((rep.devPrivateSize + 3) & ~3));
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetDeviceInfo... return False");
return False;
}
_XRead(dpy, (char *)*pDevPrivate, rep.devPrivateSize);
} else {
*pDevPrivate = NULL;
}
UnlockDisplay(dpy);
SyncHandle();
TRACE("GetDeviceInfo... return True");
return True;
}

109
src/xvmc/xf86dri.h Normal file
View File

@ -0,0 +1,109 @@
/* $XFree86: xc/lib/GL/dri/xf86dri.h,v 1.8 2002/10/30 12:51:25 alanh Exp $ */
/**************************************************************************
Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
Copyright 2000 VA Linux Systems, Inc.
All Rights Reserved.
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sub license, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice (including the
next paragraph) shall be included in all copies or substantial portions
of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
**************************************************************************/
/**
* \file xf86dri.h
* Protocol numbers and function prototypes for DRI X protocol.
*
* \author Kevin E. Martin <martin@valinux.com>
* \author Jens Owen <jens@tungstengraphics.com>
* \author Rickard E. (Rik) Faith <faith@valinux.com>
*/
#ifndef _XF86DRI_H_
#define _XF86DRI_H_
#include <X11/Xfuncproto.h>
#include <xf86drm.h>
#define X_XF86DRIQueryVersion 0
#define X_XF86DRIQueryDirectRenderingCapable 1
#define X_XF86DRIOpenConnection 2
#define X_XF86DRICloseConnection 3
#define X_XF86DRIGetClientDriverName 4
#define X_XF86DRICreateContext 5
#define X_XF86DRIDestroyContext 6
#define X_XF86DRICreateDrawable 7
#define X_XF86DRIDestroyDrawable 8
#define X_XF86DRIGetDrawableInfo 9
#define X_XF86DRIGetDeviceInfo 10
#define X_XF86DRIAuthConnection 11
#define X_XF86DRIOpenFullScreen 12 /* Deprecated */
#define X_XF86DRICloseFullScreen 13 /* Deprecated */
#define XF86DRINumberEvents 0
#define XF86DRIClientNotLocal 0
#define XF86DRIOperationNotSupported 1
#define XF86DRINumberErrors (XF86DRIOperationNotSupported + 1)
#ifndef _XF86DRI_SERVER_
_XFUNCPROTOBEGIN
Bool uniDRIQueryExtension(Display * dpy, int *event_base,
int *error_base);
Bool uniDRIQueryVersion(Display * dpy, int *majorVersion, int *minorVersion,
int *patchVersion);
Bool uniDRIQueryDirectRenderingCapable(Display * dpy, int screen,
Bool * isCapable);
Bool uniDRIOpenConnection(Display * dpy, int screen, drm_handle_t * hSAREA,
char **busIDString);
Bool uniDRIAuthConnection(Display * dpy, int screen, drm_magic_t magic);
Bool uniDRICloseConnection(Display * dpy, int screen);
Bool uniDRIGetClientDriverName(Display * dpy, int screen,
int *ddxDriverMajorVersion, int *ddxDriverMinorVersion,
int *ddxDriverPatchVersion, char **clientDriverName);
Bool uniDRICreateContext(Display * dpy, int screen, Visual * visual,
XID * ptr_to_returned_context_id, drm_context_t * hHWContext);
Bool uniDRICreateContextWithConfig(Display * dpy, int screen, int configID,
XID * ptr_to_returned_context_id, drm_context_t * hHWContext);
extern Bool uniDRIDestroyContext(Display * dpy, int screen, XID context_id);
extern Bool uniDRICreateDrawable(Display * dpy, int screen,
Drawable drawable, drm_drawable_t * hHWDrawable);
extern Bool uniDRIDestroyDrawable(Display * dpy, int screen,
Drawable drawable);
Bool uniDRIGetDeviceInfo(Display * dpy, int screen,
drm_handle_t * hFrameBuffer, int *fbOrigin, int *fbSize,
int *fbStride, int *devPrivateSize, void **pDevPrivate);
_XFUNCPROTOEND
#endif /* _XF86DRI_SERVER_ */
#endif /* _XF86DRI_H_ */

390
src/xvmc/xf86dristr.h Normal file
View File

@ -0,0 +1,390 @@
/* $XFree86: xc/lib/GL/dri/xf86dristr.h,v 1.10 2002/10/30 12:51:25 alanh Exp $ */
/**************************************************************************
Copyright 1998-1999 Precision Insight, Inc., Cedar Park, Texas.
Copyright 2000 VA Linux Systems, Inc.
All Rights Reserved.
Permission is hereby granted, free of charge, to any person obtaining a
copy of this software and associated documentation files (the
"Software"), to deal in the Software without restriction, including
without limitation the rights to use, copy, modify, merge, publish,
distribute, sub license, and/or sell copies of the Software, and to
permit persons to whom the Software is furnished to do so, subject to
the following conditions:
The above copyright notice and this permission notice (including the
next paragraph) shall be included in all copies or substantial portions
of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT.
IN NO EVENT SHALL PRECISION INSIGHT AND/OR ITS SUPPLIERS BE LIABLE FOR
ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT,
TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE
SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
**************************************************************************/
/*
* Authors:
* Kevin E. Martin <martin@valinux.com>
* Jens Owen <jens@tungstengraphics.com>
* Rickard E. (Rik) Fiath <faith@valinux.com>
*
*/
#ifndef _XF86DRISTR_H_
#define _XF86DRISTR_H_
#include "xf86dri.h"
#define XF86DRINAME "XFree86-DRI"
/* The DRI version number. This was originally set to be the same of the
* XFree86 version number. However, this version is really indepedent of
* the XFree86 version.
*
* Version History:
* 4.0.0: Original
* 4.0.1: Patch to bump clipstamp when windows are destroyed, 28 May 02
* 4.1.0: Add transition from single to multi in DRMInfo rec, 24 Jun 02
*/
#define XF86DRI_MAJOR_VERSION 4
#define XF86DRI_MINOR_VERSION 1
#define XF86DRI_PATCH_VERSION 0
typedef struct _XF86DRIQueryVersion
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIQueryVersion */
CARD16 length B16;
} xXF86DRIQueryVersionReq;
#define sz_xXF86DRIQueryVersionReq 4
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD16 majorVersion B16; /* major version of DRI protocol */
CARD16 minorVersion B16; /* minor version of DRI protocol */
CARD32 patchVersion B32; /* patch version of DRI protocol */
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xXF86DRIQueryVersionReply;
#define sz_xXF86DRIQueryVersionReply 32
typedef struct _XF86DRIQueryDirectRenderingCapable
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* X_DRIQueryDirectRenderingCapable */
CARD16 length B16;
CARD32 screen B32;
} xXF86DRIQueryDirectRenderingCapableReq;
#define sz_xXF86DRIQueryDirectRenderingCapableReq 8
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
BOOL isCapable;
BOOL pad2;
BOOL pad3;
BOOL pad4;
CARD32 pad5 B32;
CARD32 pad6 B32;
CARD32 pad7 B32;
CARD32 pad8 B32;
CARD32 pad9 B32;
} xXF86DRIQueryDirectRenderingCapableReply;
#define sz_xXF86DRIQueryDirectRenderingCapableReply 32
typedef struct _XF86DRIOpenConnection
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIOpenConnection */
CARD16 length B16;
CARD32 screen B32;
} xXF86DRIOpenConnectionReq;
#define sz_xXF86DRIOpenConnectionReq 8
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 hSAREALow B32;
CARD32 hSAREAHigh B32;
CARD32 busIdStringLength B32;
CARD32 pad6 B32;
CARD32 pad7 B32;
CARD32 pad8 B32;
} xXF86DRIOpenConnectionReply;
#define sz_xXF86DRIOpenConnectionReply 32
typedef struct _XF86DRIAuthConnection
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRICloseConnection */
CARD16 length B16;
CARD32 screen B32;
CARD32 magic B32;
} xXF86DRIAuthConnectionReq;
#define sz_xXF86DRIAuthConnectionReq 12
typedef struct
{
BYTE type;
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 authenticated B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xXF86DRIAuthConnectionReply;
#define zx_xXF86DRIAuthConnectionReply 32
typedef struct _XF86DRICloseConnection
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRICloseConnection */
CARD16 length B16;
CARD32 screen B32;
} xXF86DRICloseConnectionReq;
#define sz_xXF86DRICloseConnectionReq 8
typedef struct _XF86DRIGetClientDriverName
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIGetClientDriverName */
CARD16 length B16;
CARD32 screen B32;
} xXF86DRIGetClientDriverNameReq;
#define sz_xXF86DRIGetClientDriverNameReq 8
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 ddxDriverMajorVersion B32;
CARD32 ddxDriverMinorVersion B32;
CARD32 ddxDriverPatchVersion B32;
CARD32 clientDriverNameLength B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xXF86DRIGetClientDriverNameReply;
#define sz_xXF86DRIGetClientDriverNameReply 32
typedef struct _XF86DRICreateContext
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRICreateContext */
CARD16 length B16;
CARD32 screen B32;
CARD32 visual B32;
CARD32 context B32;
} xXF86DRICreateContextReq;
#define sz_xXF86DRICreateContextReq 16
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 hHWContext B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xXF86DRICreateContextReply;
#define sz_xXF86DRICreateContextReply 32
typedef struct _XF86DRIDestroyContext
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIDestroyContext */
CARD16 length B16;
CARD32 screen B32;
CARD32 context B32;
} xXF86DRIDestroyContextReq;
#define sz_xXF86DRIDestroyContextReq 12
typedef struct _XF86DRICreateDrawable
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRICreateDrawable */
CARD16 length B16;
CARD32 screen B32;
CARD32 drawable B32;
} xXF86DRICreateDrawableReq;
#define sz_xXF86DRICreateDrawableReq 12
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 hHWDrawable B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xXF86DRICreateDrawableReply;
#define sz_xXF86DRICreateDrawableReply 32
typedef struct _XF86DRIDestroyDrawable
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIDestroyDrawable */
CARD16 length B16;
CARD32 screen B32;
CARD32 drawable B32;
} xXF86DRIDestroyDrawableReq;
#define sz_xXF86DRIDestroyDrawableReq 12
typedef struct _XF86DRIGetDrawableInfo
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIGetDrawableInfo */
CARD16 length B16;
CARD32 screen B32;
CARD32 drawable B32;
} xXF86DRIGetDrawableInfoReq;
#define sz_xXF86DRIGetDrawableInfoReq 12
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 drawableTableIndex B32;
CARD32 drawableTableStamp B32;
INT16 drawableX B16;
INT16 drawableY B16;
INT16 drawableWidth B16;
INT16 drawableHeight B16;
CARD32 numClipRects B32;
INT16 backX B16;
INT16 backY B16;
CARD32 numBackClipRects B32;
} xXF86DRIGetDrawableInfoReply;
#define sz_xXF86DRIGetDrawableInfoReply 36
typedef struct _XF86DRIGetDeviceInfo
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIGetDeviceInfo */
CARD16 length B16;
CARD32 screen B32;
} xXF86DRIGetDeviceInfoReq;
#define sz_xXF86DRIGetDeviceInfoReq 8
typedef struct
{
BYTE type; /* X_Reply */
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 hFrameBufferLow B32;
CARD32 hFrameBufferHigh B32;
CARD32 framebufferOrigin B32;
CARD32 framebufferSize B32;
CARD32 framebufferStride B32;
CARD32 devPrivateSize B32;
} xXF86DRIGetDeviceInfoReply;
#define sz_xXF86DRIGetDeviceInfoReply 32
typedef struct _XF86DRIOpenFullScreen
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRIOpenFullScreen */
CARD16 length B16;
CARD32 screen B32;
CARD32 drawable B32;
} xXF86DRIOpenFullScreenReq;
#define sz_xXF86DRIOpenFullScreenReq 12
typedef struct
{
BYTE type;
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 isFullScreen B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
} xXF86DRIOpenFullScreenReply;
#define sz_xXF86DRIOpenFullScreenReply 32
typedef struct _XF86DRICloseFullScreen
{
CARD8 reqType; /* always DRIReqCode */
CARD8 driReqType; /* always X_DRICloseFullScreen */
CARD16 length B16;
CARD32 screen B32;
CARD32 drawable B32;
} xXF86DRICloseFullScreenReq;
#define sz_xXF86DRICloseFullScreenReq 12
typedef struct
{
BYTE type;
BOOL pad1;
CARD16 sequenceNumber B16;
CARD32 length B32;
CARD32 pad2 B32;
CARD32 pad3 B32;
CARD32 pad4 B32;
CARD32 pad5 B32;
CARD32 pad6 B32;
CARD32 pad7 B32;
} xXF86DRICloseFullScreenReply;
#define sz_xXF86DRICloseFullScreenReply 32
#endif /* _XF86DRISTR_H_ */