Initialize permedia engine for acceleration to work.

This commit is contained in:
Carlos Romero 2004-05-30 13:51:18 +00:00
parent ea1bbf8d83
commit 8124810950
3 changed files with 311 additions and 219 deletions

View File

@ -57,12 +57,6 @@ pmMapReg(KdCardInfo *card, PM2CardInfo *pm2c)
if (pm2c->reg_base == NULL)
return FALSE;
// pm2c->render = (PMRender *) (pm2c->reg_base + RENDER_UNIT);
// pm2c->rect = (PMRectangle *) (pm2c->reg_base + RECT_UNIT);
// pm2c->mode = (PMMode *) (pm2c->reg_base + MODE_UNIT);
// pm2c->color = (PMColor *) (pm2c->reg_base + COLOR_UNIT);
// pm2c->scissor = (PMScissor *) (pm2c->reg_base + SCISSOR_UNIT);
KdSetMappedMode(PM2_REG_BASE(card), PM2_REG_SIZE(card),
KD_MAPPED_MODE_REGISTERS);
@ -99,8 +93,10 @@ pmCardInit (KdCardInfo *card)
xfree (pm2c);
return FALSE;
}
pm2c->InFifoSpace = 0;
card->driver = pm2c;
card->driver = pm2c;
return TRUE;
}
@ -159,6 +155,21 @@ pmScreenInit (KdScreenInfo *screen)
pm2s->off_screen_size = 0;
}
switch (screen->fb[0].bitsPerPixel) {
case 8:
pm2c->BppShift = 2;
break;
case 16:
pm2c->BppShift = 1;
break;
case 24:
pm2c->BppShift = 2;
break;
case 32:
pm2c->BppShift = 0;
break;
}
screen->driver = pm2s;
return TRUE;

View File

@ -10,140 +10,55 @@ typedef volatile CARD8 VOL8;
typedef volatile CARD16 VOL16;
typedef volatile CARD32 VOL32;
#if 0
typedef struct {
VOL32 StartXDom;
VOL32 dXDom;
VOL32 StartXSub;
VOL32 dXSub;
VOL32 StartY;
VOL32 dY;
VOL32 GLINTCount;
VOL32 Render;
VOL32 ContinueNewLine;
VOL32 ContinueNewDom;
VOL32 ContinueNewSub;
VOL32 Continue;
VOL32 FlushSpan;
VOL32 BitMaskPattern;
} PMRender;
typedef struct {
VOL32 PointTable0;
VOL32 PointTable1;
VOL32 PointTable2;
VOL32 PointTable3;
VOL32 RasterizerMode;
VOL32 YLimits;
VOL32 ScanLineOwnership;
VOL32 WaitForCompletion;
VOL32 PixelSize;
VOL32 XLimits;
VOL32 RectangleOrigin;
VOL32 RectangleSize;
} PMRectangle;
typedef struct {
VOL32 FilterMode;
VOL32 StatisticMode;
VOL32 MinRegion;
VOL32 MaxRegion;
VOL32 ResetPickResult;
VOL32 MitHitRegion;
VOL32 MaxHitRegion;
VOL32 PickResult;
VOL32 GlintSync;
VOL32 reserved00;
VOL32 reserved01;
VOL32 reserved02;
VOL32 reserved03;
VOL32 FBBlockColorU;
VOL32 FBBlockColorL;
VOL32 SuspendUntilFrameBlank;
} PMMode;
typedef struct {
VOL32 ScissorMode;
VOL32 ScissorMinXY;
VOL32 ScissorMaxXY;
VOL32 ScreenSize;
VOL32 AreaStippleMode;
VOL32 LineStippleMode;
VOL32 LoadLineStippleCounters;
VOL32 UpdateLineStippleCounters;
VOL32 SaveLineStippleState;
VOL32 WindowOrigin;
} PMScissor;
typedef struct {
VOL32 RStart;
VOL32 dRdx;
VOL32 dRdyDom;
VOL32 GStart;
VOL32 dGdx;
VOL32 dGdyDom;
VOL32 BStart;
VOL32 dBdx;
VOL32 dBdyDom;
VOL32 AStart;
VOL32 dAdx;
VOL32 dAdyDom;
VOL32 ColorDDAMode;
VOL32 ConstantColor;
VOL32 GLINTColor;
} PMColor;
#endif
#define PM2_REG_BASE(c) ((c)->attr.address[0] & 0xFFFFC000)
#define PM2_REG_SIZE(c) (0x10000)
#define minb(p) *(volatile CARD8 *)(pm2c->reg_base + (p))
#define moutb(p,v) *(volatile CARD8 *)(pm2c->reg_base + (p)) = (v)
/* Memory mapped register access macros */
#define INREG8(addr) *(volatile CARD8 *)(pm2c->reg_base + (addr))
#define INREG16(addr) *(volatile CARD16 *)(pm2c->reg_base + (addr))
#define INREG(addr) *(volatile CARD32 *)(pm2c->reg_base + (addr))
#define OUTREG8(addr, val) do { \
*(volatile CARD8 *)(pm2c->reg_base + (addr)) = (val); \
} while (0)
#define OUTREG16(addr, val) do { \
*(volatile CARD16 *)(pm2c->reg_base + (addr)) = (val); \
} while (0)
#define OUTREG(addr, val) do { \
*(volatile CARD32 *)(pm2c->reg_base + (addr)) = (val); \
} while (0)
typedef struct _PM2CardInfo {
VesaCardPrivRec vesa;
CARD8 *reg_base;
VesaCardPrivRec vesa;
CARD8 *reg_base;
int in_fifo_space;
int fifo_size;
int InFifoSpace;
int FIFOSize;
int pprod;
int bppalign;
int pprod;
int bppalign;
int clipping_on;
int ClippingOn;
int ROP;
int ROP;
int x;
int y;
int w;
int h;
int FrameBufferReadMode;
int BppShift;
int BltScanDirection;
int RasterizerSwap;
int PixelWidth;
int TexMapFormat;
int startxdom;
int startxsub;
int starty;
int count;
int dy;
int dxdom;
int planemask;
} PM2CardInfo;
#define getPM2CardInfo(kd) ((PM2CardInfo *) ((kd)->card->driver))
#define pmCardInfo(kd) PM2CardInfo *pm2c = getPM2CardInfo(kd)
typedef struct _PM2ScreenInfo {
VesaScreenPrivRec vesa;
CARD8 *cursor_base;
CARD8 *screen;
CARD8 *off_screen;
int off_screen_size;
KdVideoAdaptorPtr pAdaptor;
VesaScreenPrivRec vesa;
CARD8 *cursor_base;
CARD8 *screen;
CARD8 *off_screen;
int off_screen_size;
KdVideoAdaptorPtr pAdaptor;
} PM2ScreenInfo;
#define getPM2ScreenInfo(kd) ((PM2ScreenInfo *) ((kd)->screen->driver))
@ -173,12 +88,77 @@ pmDrawFini (ScreenPtr);
extern KdCardFuncs PM2Funcs;
#define PM2R_MEM_CONFIG 0x10c0
#define MMIO_OUT32(base, offset, val) \
do { \
*(volatile CARD32 *)(void *)(((CARD8*)(base)) + (offset)) = (val); \
} while (0)
#define PM2F_MEM_CONFIG_RAM_MASK (3L<<29)
#define PM2F_MEM_BANKS_1 0L
#define PM2F_MEM_BANKS_2 (1L<<29)
#define PM2F_MEM_BANKS_3 (2L<<29)
#define PM2F_MEM_BANKS_4 (3L<<29)
# define MMIO_IN32(base, offset) \
*(volatile CARD32 *)(void *)(((CARD8*)(base)) + (offset))
#define GLINT_WRITE_REG(v,r) \
MMIO_OUT32(mmio,(unsigned long)(r), (v))
#define GLINT_READ_REG(r) \
MMIO_IN32(mmio,(unsigned long)(r))
#define GLINT_SLOW_WRITE_REG(v,r) \
do{ \
GLINT_WAIT(card->FIFOSize); \
GLINT_WRITE_REG(v,r); \
}while(0)
#define REPLICATE(r) \
{ \
if (pScreenPriv->screen->fb[0].bitsPerPixel == 16) { \
r &= 0xFFFF; \
r |= (r<<16); \
} else \
if (pScreenPriv->screen->fb[0].bitsPerPixel == 8) { \
r &= 0xFF; \
r |= (r<<8); \
r |= (r<<16); \
} \
}
#define DO_PLANEMASK(planemask) \
{ \
if (planemask != card->planemask) { \
card->planemask = planemask; \
REPLICATE(planemask); \
GLINT_WRITE_REG(planemask, FBHardwareWriteMask);\
} \
}
#define LOADROP(rop) \
{ \
if (card->ROP != rop) { \
GLINT_WRITE_REG(rop<<1|UNIT_ENABLE, LogicalOpMode); \
card->ROP = rop; \
} \
}
#define GLINT_WAIT(n) \
do{ \
if (card->InFifoSpace>=(n)) \
card->InFifoSpace -= (n); \
else { \
int tmp; \
while((tmp=GLINT_READ_REG(InFIFOSpace))<(n)); \
/* Clamp value due to bugs in PM3 */ \
if (tmp > card->FIFOSize) \
tmp = card->FIFOSize; \
card->InFifoSpace = tmp - (n); \
} \
}while(0)
#define CHECKCLIPPING \
{ \
if (card->ClippingOn) { \
card->ClippingOn = FALSE; \
GLINT_WAIT(1); \
GLINT_WRITE_REG(0, ScissorMode); \
} \
}
#endif /* _PM2_H_ */

View File

@ -8,50 +8,39 @@
static PM2CardInfo *card;
static VOL8 *mmio;
static void pmWait (PM2CardInfo *card, int n);
static void
pmWait (PM2CardInfo *card, int n)
{
if (card->in_fifo_space >= n)
card->in_fifo_space -= n;
else {
int tmp;
while((tmp = *(VOL32 *) (mmio + InFIFOSpace)) < n);
/* Clamp value due to bugs in PM3 */
if (tmp > card->fifo_size)
tmp = card->fifo_size;
card->in_fifo_space = tmp - n;
}
}
static void Permedia2LoadCoord(int x, int y, int w, int h);
static Bool
pmPrepareSolid (PixmapPtr pPixmap,
int alu,
Pixel pm,
Pixel fg)
int rop,
Pixel planemask,
Pixel color)
{
ScreenPtr pScreen = pPixmap->drawable.pScreen;
KdScreenPriv(pScreen);
pmCardInfo(pScreenPriv);
card = pm2c;
if (~pm & FbFullMask(pPixmap->drawable.depth))
mmio = pm2c->reg_base;
if (~planemask & FbFullMask(pPixmap->drawable.depth))
return FALSE;
pmWait(card, 6);
*(VOL32 *) (mmio + FBHardwareWriteMask) = pm;
if (alu == GXcopy) {
*(VOL32 *) (mmio + ColorDDAMode) = UNIT_DISABLE;
*(VOL32 *) (mmio + FBReadMode) = card->pprod;
*(VOL32 *) (mmio + FBBlockColor) = fg;
REPLICATE(color);
GLINT_WAIT(6);
DO_PLANEMASK(planemask);
if (rop == GXcopy) {
GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
GLINT_WRITE_REG(card->pprod, FBReadMode);
GLINT_WRITE_REG(color, FBBlockColor);
} else {
*(VOL32 *) (mmio + ColorDDAMode) = UNIT_ENABLE;
*(VOL32 *) (mmio + ConstantColor) = fg;
*(VOL32 *) (mmio + FBReadMode) = card->pprod|FBRM_DstEnable|FBRM_Packed;
GLINT_WRITE_REG(UNIT_ENABLE, ColorDDAMode);
GLINT_WRITE_REG(color, ConstantColor);
/* We can use Packed mode for filling solid non-GXcopy rasters */
GLINT_WRITE_REG(card->pprod|FBRM_DstEnable|FBRM_Packed, FBReadMode);
}
*(VOL32 *) (mmio + LogicalOpMode) = alu<<1|UNIT_ENABLE;
card->ROP = alu;
LOADROP(rop);
return TRUE;
}
@ -62,21 +51,19 @@ pmSolid (int x1, int y1, int x2, int y2)
int speed = 0;
if (card->ROP == GXcopy) {
pmWait(card, 3);
*(VOL32 *) (mmio + RectangleOrigin) = GLINT_XY(x1, y1);
*(VOL32 *) (mmio + RectangleSize) = GLINT_XY(x2-x1, y2-y1);
GLINT_WAIT(3);
Permedia2LoadCoord(x1, y1, x2-x1, y2-y1);
speed = FastFillEnable;
} else {
pmWait(card, 4);
*(VOL32 *) (mmio + RectangleOrigin) = GLINT_XY(x1, y1);
*(VOL32 *) (mmio + RectangleSize) = GLINT_XY((x2-x1)+7, y2-y1);
*(VOL32 *) (mmio + PackedDataLimits) = x1<<16|(x1+(x2-x1));
GLINT_WAIT(4);
Permedia2LoadCoord(x1>>card->BppShift, y1,
((x2-x1)+7)>>card->BppShift, y2-y1);
GLINT_WRITE_REG(x1<<16|(x1+(x2-x1)), PackedDataLimits);
speed = 0;
}
*(VOL32 *) (mmio + Render) = PrimitiveRectangle | XPositive | YPositive | speed;
GLINT_WRITE_REG(PrimitiveRectangle | XPositive | YPositive | speed, Render);
}
static void
pmDoneSolid (void)
{
@ -87,58 +74,91 @@ pmPrepareCopy (PixmapPtr pSrcPixmap,
PixmapPtr pDstPixmap,
int dx,
int dy,
int alu,
Pixel pm)
int rop,
Pixel planemask)
{
ScreenPtr pScreen = pDstPixmap->drawable.pScreen;
KdScreenPriv(pScreen);
pmCardInfo(pScreenPriv);
ErrorF ("pmPrepareCopy\n");
card = pm2c;
if (~pm & FbFullMask(pDstPixmap->drawable.depth))
mmio = pm2c->reg_base;
if (~planemask & FbFullMask(pDstPixmap->drawable.depth))
return FALSE;
pmWait(card, 5);
*(VOL32 *) (mmio + FBHardwareWriteMask) = pm;
*(VOL32 *) (mmio + ColorDDAMode) = UNIT_DISABLE;
if ((alu == GXset) || (alu == GXclear)) {
*(VOL32 *) (mmio + FBReadMode) = card->pprod;
card->BltScanDirection = ((dx >= 0 ? XPositive : 0) | (dy >= 0 ? YPositive : 0));
GLINT_WAIT(4);
DO_PLANEMASK(planemask);
GLINT_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
if ((rop == GXset) || (rop == GXclear)) {
card->FrameBufferReadMode = card->pprod;
} else
if ((rop == GXcopy) || (rop == GXcopyInverted)) {
card->FrameBufferReadMode = card->pprod |FBRM_SrcEnable;
} else {
if ((alu == GXcopy) || (alu == GXcopyInverted)) {
*(VOL32 *) (mmio + FBReadMode) = card->pprod|FBRM_SrcEnable;
} else {
*(VOL32 *) (mmio + FBReadMode) = card->pprod|FBRM_SrcEnable|FBRM_DstEnable;
}
card->FrameBufferReadMode = card->pprod | FBRM_SrcEnable |
FBRM_DstEnable;
}
*(VOL32 *) (mmio + LogicalOpMode) = alu<<1|UNIT_ENABLE;
card->ROP = alu;
LOADROP(rop);
return TRUE;
}
static void
pmCopy (int srcX,
int srcY,
int dstX,
int dstY,
pmCopy (int x1,
int y1,
int x2,
int y2,
int w,
int h)
{
ErrorF ("pmCopy %d %d %d %d %d %d\n", srcX, srcY, dstX, dstY, w, h);
pmWait(card, 4);
*(VOL32 *) (mmio + RectangleOrigin) = GLINT_XY(dstX, dstY);
*(VOL32 *) (mmio + RectangleSize) = GLINT_XY(w, h);
*(VOL32 *) (mmio + FBSourceDelta) = ((srcY-dstY)&0x0FFF)<<16 | (srcX-dstX)&0x0FFF;
*(VOL32 *) (mmio + Render) = PrimitiveRectangle | XPositive | YPositive;
char align;
/* We can only use GXcopy for Packed modes */
if (card->ROP != GXcopy) {
GLINT_WAIT(5);
GLINT_WRITE_REG(card->FrameBufferReadMode, FBReadMode);
Permedia2LoadCoord(x2, y2, w, h);
GLINT_WRITE_REG(((y1-y2)&0x0FFF)<<16 | ((x1-x2)&0x0FFF), FBSourceDelta);
} else {
align = (x2 & card->bppalign) - (x1 & card->bppalign);
GLINT_WAIT(6);
GLINT_WRITE_REG(card->FrameBufferReadMode|FBRM_Packed, FBReadMode);
Permedia2LoadCoord(x2>>card->BppShift, y2,
(w+7)>>card->BppShift, h);
GLINT_WRITE_REG(align<<29|x2<<16|(x2+w), PackedDataLimits);
GLINT_WRITE_REG(((y1-y2)&0x0FFF)<<16 | (((x1 & ~card->bppalign)-(x2 & ~card->bppalign))&0x0FFF), FBSourceDelta);
}
GLINT_WRITE_REG(PrimitiveRectangle | card->BltScanDirection, Render);
}
static void
pmDoneCopy (void)
{
}
static void
Permedia2LoadCoord(int x, int y,
int w, int h)
{
if ((h != card->h) || (w != card->w)) {
card->w = w;
card->h = h;
GLINT_WRITE_REG(((h&0x0FFF)<<16)|(w&0x0FFF), RectangleSize);
}
if ((y != card->y) || (x != card->x)) {
card->x = x;
card->y = y;
GLINT_WRITE_REG(((y&0x0FFF)<<16)|(x&0x0FFF), RectangleOrigin);
}
}
KaaScreenInfoRec pmKaa = {
pmPrepareSolid,
pmSolid,
@ -159,10 +179,6 @@ pmDrawInit (ScreenPtr pScreen)
card = pm2c;
mmio = pm2c->reg_base;
if (pScreenPriv->screen->fb[0].depth <= 16) {
ErrorF ("depth(%d) <= 16 \n", pScreenPriv->screen->fb[0].depth);
ret = FALSE;
}
if (ret && !kaaDrawInit (pScreen, &pmKaa))
{
ErrorF ("kaaDrawInit failed\n");
@ -172,13 +188,105 @@ pmDrawInit (ScreenPtr pScreen)
return ret;
}
void
pmDrawEnable (ScreenPtr pScreen)
{
KdScreenPriv(pScreen);
pmCardInfo(pScreenPriv);
pm2c->in_fifo_space = 0;
card = pm2c;
mmio = pm2c->reg_base;
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ScissorMode);
GLINT_SLOW_WRITE_REG(UNIT_ENABLE, FBWriteMode);
GLINT_SLOW_WRITE_REG(0, dXSub);
GLINT_SLOW_WRITE_REG(GWIN_DisableLBUpdate, GLINTWindow);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DitherMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, ColorDDAMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureColorMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TextureAddressMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, PMTextureReadMode);
GLINT_SLOW_WRITE_REG(card->pprod, LBReadMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaBlendMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, TexelLUTMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, YUVMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RouterMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FogMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AntialiasMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AlphaTestMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StencilMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, AreaStippleMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LogicalOpMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, DepthMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, StatisticMode);
GLINT_SLOW_WRITE_REG(0x400, FilterMode);
GLINT_SLOW_WRITE_REG(0xffffffff, FBHardwareWriteMask);
GLINT_SLOW_WRITE_REG(0xffffffff, FBSoftwareWriteMask);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, RasterizerMode);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, GLINTDepth);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceOffset);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBPixelOffset);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBSourceOffset);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, WindowOrigin);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBWindowBase);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, FBSourceBase);
GLINT_SLOW_WRITE_REG(UNIT_DISABLE, LBWindowBase);
#if X_BYTE_ORDER == X_BIG_ENDIAN
card->RasterizerSwap = 1;
#else
card->RasterizerSwap = 0;
#endif
switch (pScreenPriv->screen->fb[0].bitsPerPixel) {
case 8:
card->PixelWidth = 0x0; /* 8 Bits */
card->TexMapFormat = card->pprod;
#if X_BYTE_ORDER == X_BIG_ENDIAN
card->RasterizerSwap |= 3<<15; /* Swap host data */
#endif
break;
case 16:
card->PixelWidth = 0x1; /* 16 Bits */
card->TexMapFormat = card->pprod | 1<<19;
#if X_BYTE_ORDER == X_BIG_ENDIAN
card->RasterizerSwap |= 2<<15; /* Swap host data */
#endif
break;
case 24:
card->PixelWidth = 0x4; /* 24 Bits */
card->TexMapFormat = card->pprod | 2<<19;
break;
case 32:
card->PixelWidth = 0x2; /* 32 Bits */
card->TexMapFormat = card->pprod | 2<<19;
break;
}
card->ClippingOn = FALSE;
card->startxdom = 0;
card->startxsub = 0;
card->starty = 0;
card->count = 0;
card->dy = 1<<16;
card->dxdom = 0;
card->x = 0;
card->y = 0;
card->h = 0;
card->w = 0;
card->ROP = 0xFF;
GLINT_SLOW_WRITE_REG(card->PixelWidth, FBReadPixel);
GLINT_SLOW_WRITE_REG(card->TexMapFormat, PMTextureMapFormat);
GLINT_SLOW_WRITE_REG(0, RectangleSize);
GLINT_SLOW_WRITE_REG(0, RectangleOrigin);
GLINT_SLOW_WRITE_REG(0, dXDom);
GLINT_SLOW_WRITE_REG(1<<16, dY);
GLINT_SLOW_WRITE_REG(0, StartXDom);
GLINT_SLOW_WRITE_REG(0, StartXSub);
GLINT_SLOW_WRITE_REG(0, StartY);
GLINT_SLOW_WRITE_REG(0, GLINTCount);
KdMarkSync (pScreen);
}
@ -196,20 +304,13 @@ pmDrawFini (ScreenPtr pScreen)
void
pmDrawSync (ScreenPtr pScreen)
{
if (card->clipping_on) {
card->clipping_on = FALSE;
pmWait(card, 1);
*(VOL32 *) (mmio + ScissorMode) = 0;
}
while (*(VOL32 *) (mmio + DMACount) != 0);
pmWait(card, 2);
*(VOL32 *) (mmio + FilterMode) = 0x400;
*(VOL32 *) (mmio + GlintSync) = 0;
CHECKCLIPPING;
while (GLINT_READ_REG(DMACount) != 0);
GLINT_WAIT(2);
GLINT_WRITE_REG(0x400, FilterMode);
GLINT_WRITE_REG(0, GlintSync);
do {
while(*(VOL32 *) (mmio + OutFIFOWords) == 0);
} while (*(VOL32 *) (mmio + OutputFIFO) != Sync_tag);
while(GLINT_READ_REG(OutFIFOWords) == 0);
} while (GLINT_READ_REG(OutputFIFO) != Sync_tag);
}