[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

xserver-xorg-video-nouveau: Changes to 'upstream-unstable'



 configure.ac          |    2 
 src/Makefile.am       |    4 
 src/drmmode_display.c |   30 -
 src/nouveau_dri2.c    |   32 -
 src/nouveau_exa.c     |   29 -
 src/nouveau_local.h   |  186 ++++++---
 src/nouveau_wfb.c     |    4 
 src/nouveau_xv.c      |   69 ++-
 src/nv04_accel.h      |   83 ++++
 src/nv04_exa.c        |  524 ++++++++++++--------------
 src/nv04_xv_blit.c    |  262 ++++++-------
 src/nv10_exa.c        |  857 +++++++++++++++++++------------------------
 src/nv30_exa.c        |  975 +++++++++++++++++++++++++------------------------
 src/nv30_shaders.c    |  347 -----------------
 src/nv30_shaders.h    |   72 ---
 src/nv30_xv_tex.c     |  302 +++++----------
 src/nv40_exa.c        |  994 +++++++++++++++++++++++++++++++-------------------
 src/nv40_xv_tex.c     |  293 ++++++--------
 src/nv50_accel.c      |  670 +++++++++++++++++----------------
 src/nv50_accel.h      |   66 ++-
 src/nv50_exa.c        |  895 ++++++++++++++++++++-------------------------
 src/nv50_xv.c         |  381 +++++++------------
 src/nv_accel_common.c |  582 ++++++++++++++---------------
 src/nv_dma.c          |   77 ++-
 src/nv_dma.h          |    4 
 src/nv_driver.c       |   43 +-
 src/nv_include.h      |   11 
 src/nv_proto.h        |    7 
 src/nv_shadow.c       |    3 
 src/nv_type.h         |   53 +-
 src/nvc0_accel.c      |  841 +++++++++---------------------------------
 src/nvc0_accel.h      |  120 +++---
 src/nvc0_exa.c        |  974 +++++++++++++++++++++++-------------------------
 src/nvc0_shader.h     |  444 ++++++++++++++++++++++
 src/nvc0_xv.c         |  374 +++++++-----------
 src/nve0_shader.h     |  460 +++++++++++++++++++++++
 36 files changed, 5568 insertions(+), 5502 deletions(-)

New commits:
commit 581564466c47ab0435ecca3cf4d82c03e1b30259
Author: Francisco Jerez <currojerez@riseup.net>
Date:   Tue May 8 14:02:44 2012 +0200

    dri2: Don't try to page-flip pixmaps (fdo bug 49351).
    
    Reported-by: Marcin Slusarz <marcin.slusarz@gmail.com>
    Signed-off-by: Francisco Jerez <currojerez@riseup.net>

diff --git a/src/nouveau_dri2.c b/src/nouveau_dri2.c
index 73f2fc1..7e47575 100644
--- a/src/nouveau_dri2.c
+++ b/src/nouveau_dri2.c
@@ -328,7 +328,7 @@ nouveau_dri2_finish_swap(DrawablePtr draw, unsigned int frame,
 		type = DRI2_EXCHANGE_COMPLETE;
 		DamageRegionAppend(draw, &reg);
 
-		if (DRI2CanFlip(draw)) {
+		if (nouveau_exa_pixmap_is_onscreen(dst_pix)) {
 			type = DRI2_FLIP_COMPLETE;
 			ret = drmmode_page_flip(draw, src_pix,
 						violate_oml(draw) ? NULL : s,

commit b1efc807392d372e6a232aad9d16ae6e1b1c1916
Author: Marcin Slusarz <marcin.slusarz@gmail.com>
Date:   Sun Apr 15 13:46:42 2012 +0200

    nv50: add missing pushbuf space check in NV50SyncToVBlank
    
    Regression from "WIP: port to new libdrm".

diff --git a/src/nv50_accel.c b/src/nv50_accel.c
index e140db9..42b27f0 100644
--- a/src/nv50_accel.c
+++ b/src/nv50_accel.c
@@ -44,6 +44,9 @@ NV50SyncToVBlank(PixmapPtr ppix, BoxPtr box)
 	if (!crtcs)
 		return;
 
+	if (!PUSH_SPACE(push, 10))
+		return;
+
 	BEGIN_NV04(push, SUBC_NVSW(0x0060), 2);
 	PUSH_DATA (push, pNv->vblank_sem->handle);
 	PUSH_DATA (push, 0);

commit 174f17072005971fee6e4eb76a273c3cc1aa10d3
Author: Ben Skeggs <bskeggs@redhat.com>
Date:   Tue Apr 24 21:55:03 2012 +1000

    nv40/exa: return false from gradient picture setup
    
    Not implemented yet.  Shouldn't hit this anyway, fallback in check_composite,
    but, best be safe :)
    
    Reported-by: Maarten Maathuis <madman2003@gmail.com>
    Signed-off-by: Ben Skeggs <bskeggs@redhat.com>

diff --git a/src/nv40_exa.c b/src/nv40_exa.c
index 10f15f1..2361552 100644
--- a/src/nv40_exa.c
+++ b/src/nv40_exa.c
@@ -233,7 +233,7 @@ NV40EXAPictSolid(NVPtr pNv, PicturePtr pPict, int unit)
 static Bool
 NV40EXAPictGradient(NVPtr pNv, PicturePtr pPict, int unit)
 {
-	return TRUE;
+	return FALSE;
 }
 
 static Bool

commit 60edf2a87b928f413385443335493cb27da30a48
Author: Ben Skeggs <bskeggs@redhat.com>
Date:   Tue Apr 24 10:54:51 2012 +1000

    nv40/exa: support for solid pictures
    
    Signed-off-by: Ben Skeggs <bskeggs@redhat.com>

diff --git a/src/nv04_accel.h b/src/nv04_accel.h
index 7100e85..e7b76c5 100644
--- a/src/nv04_accel.h
+++ b/src/nv04_accel.h
@@ -17,6 +17,7 @@
 #define PFP_NV12_BILINEAR 0x00000700
 #define PFP_NV12_BICUBIC  0x00000800
 #define XV_TABLE          0x00001000
+#define SOLID(i)         (0x00002000 + (i) * 0x100)
 
 /* subchannel assignments */
 #define SUBC_M2MF(mthd)  0, (mthd)
diff --git a/src/nv40_exa.c b/src/nv40_exa.c
index fb9ec80..10f15f1 100644
--- a/src/nv40_exa.c
+++ b/src/nv40_exa.c
@@ -181,9 +181,64 @@ NV40_SetupBlend(ScrnInfoPtr pScrn, nv_pict_op_t *blend,
 }
 
 static Bool
-NV40EXATexture(ScrnInfoPtr pScrn, PixmapPtr pPix, PicturePtr pPict, int unit)
+NV40EXAPictSolid(NVPtr pNv, PicturePtr pPict, int unit)
+{
+	struct nouveau_pushbuf *push = pNv->pushbuf;
+
+	PUSH_DATAu(push, pNv->scratch, SOLID(unit), 2);
+	PUSH_DATA (push, pPict->pSourcePict->solidFill.color);
+	PUSH_DATA (push, 0);
+	BEGIN_NV04(push, NV30_3D(TEX_OFFSET(unit)), 8);
+	PUSH_MTHDl(push, NV30_3D(TEX_OFFSET(unit)), pNv->scratch, SOLID(unit),
+			 NOUVEAU_BO_VRAM | NOUVEAU_BO_RD);
+	PUSH_DATA (push, NV40_3D_TEX_FORMAT_FORMAT_A8R8G8B8 | 0x8000 |
+			 NV40_3D_TEX_FORMAT_LINEAR |
+			 NV30_3D_TEX_FORMAT_DIMS_2D |
+			 NV30_3D_TEX_FORMAT_NO_BORDER |
+			 (1 << NV40_3D_TEX_FORMAT_MIPMAP_COUNT__SHIFT) |
+			 NV30_3D_TEX_FORMAT_DMA0);
+	PUSH_DATA (push, NV30_3D_TEX_WRAP_S_REPEAT |
+			 NV30_3D_TEX_WRAP_T_REPEAT |
+			 NV30_3D_TEX_WRAP_R_REPEAT);
+	PUSH_DATA (push, NV40_3D_TEX_ENABLE_ENABLE);
+	PUSH_DATA (push, 0x0000aae4);
+	PUSH_DATA (push, NV30_3D_TEX_FILTER_MIN_NEAREST |
+			 NV30_3D_TEX_FILTER_MAG_NEAREST | 0x3fd6);
+	PUSH_DATA (push, 0x00010001);
+	PUSH_DATA (push, 0x00000000);
+	BEGIN_NV04(push, NV40_3D(TEX_SIZE1(unit)), 1);
+	PUSH_DATA (push, 0x00100040);
+
+	BEGIN_NV04(push, NV30_3D(VP_UPLOAD_CONST_ID), 17);
+	PUSH_DATA (push, unit * 4);
+	PUSH_DATAf(push, 1.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 1.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 1.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 1.0);
+	PUSH_DATAf(push, 1.0);
+	PUSH_DATAf(push, 0.0);
+	PUSH_DATAf(push, 0.0);
+	return TRUE;
+}
+
+static Bool
+NV40EXAPictGradient(NVPtr pNv, PicturePtr pPict, int unit)
+{
+	return TRUE;
+}
+
+static Bool
+NV40EXAPictTexture(NVPtr pNv, PixmapPtr pPix, PicturePtr pPict, int unit)
 {
-	NVPtr pNv = NVPTR(pScrn);
 	unsigned reloc = NOUVEAU_BO_VRAM | NOUVEAU_BO_GART | NOUVEAU_BO_WR;
 	struct nouveau_pushbuf *push = pNv->pushbuf;
 	struct nouveau_bo *bo = nouveau_pixmap_bo(pPix);
@@ -279,6 +334,24 @@ NV40EXATexture(ScrnInfoPtr pScrn, PixmapPtr pPix, PicturePtr pPict, int unit)
 }
 
 static Bool
+NV40EXAPicture(NVPtr pNv, PixmapPtr ppix, PicturePtr ppict, int unit)
+{
+	if (ppict->pDrawable)
+		return NV40EXAPictTexture(pNv, ppix, ppict, unit);
+
+	switch (ppict->pSourcePict->type) {
+	case SourcePictTypeSolidFill:
+		return NV40EXAPictSolid(pNv, ppict, unit);
+	case SourcePictTypeLinear:
+		return NV40EXAPictGradient(pNv, ppict, unit);
+	default:
+		break;
+	}
+
+	return FALSE;
+}
+
+static Bool
 NV40_SetupSurface(ScrnInfoPtr pScrn, PixmapPtr pPix, PictFormatShort format)
 {
 	NVPtr pNv = NVPTR(pScrn);
@@ -305,13 +378,19 @@ static Bool
 NV40EXACheckCompositeTexture(PicturePtr pPict, PicturePtr pdPict, int op)
 {
 	nv_pict_texture_format_t *fmt;
-	int w, h;
-
-	if (!pPict->pDrawable)
-		NOUVEAU_FALLBACK("Solid and gradient pictures unsupported\n");
+	int w = 1, h = 1;
 
-	w = pPict->pDrawable->width;
-	h = pPict->pDrawable->height;
+	if (pPict->pDrawable) {
+		w = pPict->pDrawable->width;
+		h = pPict->pDrawable->height;
+	} else {
+		switch (pPict->pSourcePict->type) {
+		case SourcePictTypeSolidFill:
+			break;
+		default:
+			NOUVEAU_FALLBACK("gradient\n");
+		}
+	}
 
 	if ((w > 4096) || (h > 4096))
 		NOUVEAU_FALLBACK("picture too large, %dx%d\n", w, h);
@@ -377,7 +456,7 @@ NV40EXAPrepareComposite(int op, PicturePtr psPict,
 				PixmapPtr  pmPix,
 				PixmapPtr  pdPix)
 {
-	ScrnInfoPtr pScrn = xf86Screens[psPix->drawable.pScreen->myNum];
+	ScrnInfoPtr pScrn = xf86Screens[pdPix->drawable.pScreen->myNum];
 	NVPtr pNv = NVPTR(pScrn);
 	nv_pict_op_t *blend = NV40_GetPictOpRec(op);
 	struct nouveau_pushbuf *push = pNv->pushbuf;
@@ -392,11 +471,11 @@ NV40EXAPrepareComposite(int op, PicturePtr psPict,
 			 PICT_FORMAT_RGB(pmPict->format)));
 
 	if (!NV40_SetupSurface(pScrn, pdPix, pdPict->format) ||
-	    !NV40EXATexture(pScrn, psPix, psPict, 0))
+	    !NV40EXAPicture(pNv, psPix, psPict, 0))
 		return FALSE;
 
 	if (pmPict) {
-		if (!NV40EXATexture(pScrn, pmPix, pmPict, 1))
+		if (!NV40EXAPicture(pNv, pmPix, pmPict, 1))
 			return FALSE;
 
 		if (pdPict->format == PICT_a8) {

commit 067b8416ad1ab3e71ebbb8db8bfb82ff6041939b
Author: Ben Skeggs <bskeggs@redhat.com>
Date:   Mon Apr 23 17:49:57 2012 +1000

    nv30/exa: implement support for solid pictures using register combiners
    
    Signed-off-by: Ben Skeggs <bskeggs@redhat.com>

diff --git a/src/nv30_exa.c b/src/nv30_exa.c
index 1b875ee..57979c2 100644
--- a/src/nv30_exa.c
+++ b/src/nv30_exa.c
@@ -320,6 +320,51 @@ NV30EXATexture(ScrnInfoPtr pScrn, PixmapPtr pPix, PicturePtr pPict, int unit)
 	return TRUE;
 }
 
+#define RCSRC_COL(i)  (0x01 + (unit))
+#define RCSRC_TEX(i)  (0x08 + (unit)) /* fragprog register */
+#define RCSEL_COLOR   (0x00)
+#define RCSEL_ALPHA   (0x10)
+#define RCINP_ZERO    (0x00)
+#define RCINP_ONE     (0x20)
+#define RCINP_A__SHIFT 24
+#define RCINP_B__SHIFT 16
+
+static Bool
+NV30EXAPicture(ScrnInfoPtr pScrn, PixmapPtr pPix, PicturePtr pPict, int unit,
+	       uint32_t *color, uint32_t *alpha, uint32_t *solid)
+{
+	uint32_t shift, source;
+
+	if (pPict && pPict->pDrawable) {
+		if (!NV30EXATexture(pScrn, pPix, pPict, unit))
+			return FALSE;
+		*solid = 0x00000000;
+		source = RCSRC_TEX(unit);
+	} else
+	if (pPict) {
+		*solid = pPict->pSourcePict->solidFill.color;
+		source = RCSRC_COL(unit);
+	}
+
+	if (pPict && PICT_FORMAT_RGB(pPict->format))
+		*color = RCSEL_COLOR | source;
+	else
+		*color = RCSEL_ALPHA | RCINP_ZERO;
+
+	if (pPict && PICT_FORMAT_A(pPict->format))
+		*alpha = RCSEL_ALPHA | source;
+	else
+		*alpha = RCSEL_ALPHA | RCINP_ONE;
+
+	if (unit)
+		shift = RCINP_B__SHIFT;
+	else
+		shift = RCINP_A__SHIFT;
+	*color <<= shift;
+	*alpha <<= shift;
+	return TRUE;
+}
+
 static Bool
 NV30_SetupSurface(ScrnInfoPtr pScrn, PixmapPtr pPix, PicturePtr pPict)
 {
@@ -347,13 +392,15 @@ static Bool
 NV30EXACheckCompositeTexture(PicturePtr pPict, PicturePtr pdPict, int op)
 {
 	nv_pict_texture_format_t *fmt;
-	int w, h;
+	int w = 1, h = 1;
 
-	if (!pPict->pDrawable)
-		NOUVEAU_FALLBACK("Solid and gradient pictures unsupported\n");
-
-	w = pPict->pDrawable->width;
-	h = pPict->pDrawable->height;
+	if (pPict->pDrawable) {
+		w = pPict->pDrawable->width;
+		h = pPict->pDrawable->height;
+	} else {
+		if (pPict->pSourcePict->type != SourcePictTypeSolidFill)
+			NOUVEAU_FALLBACK("gradient pictures unsupported\n");
+	}
 
 	if ((w > 4096) || (h > 4096))
 		NOUVEAU_FALLBACK("picture too large, %dx%d\n", w, h);
@@ -423,48 +470,56 @@ NV30EXAPrepareComposite(int op, PicturePtr psPict,
 		PixmapPtr  pmPix,
 		PixmapPtr  pdPix)
 {
-	ScrnInfoPtr pScrn = xf86Screens[psPix->drawable.pScreen->myNum];
+	ScrnInfoPtr pScrn = xf86Screens[pdPix->drawable.pScreen->myNum];
 	NVPtr pNv = NVPTR(pScrn);
 	nv_pict_op_t *blend = NV30_GetPictOpRec(op);
 	struct nouveau_pushbuf *push = pNv->pushbuf;
-	uint32_t fragprog;
+	uint32_t sc, sa, mc, ma, solid[2];
 
 	if (!PUSH_SPACE(push, 128))
 		return FALSE;
 	PUSH_RESET(push);
 
+	/* setup render target and blending */
+	if (!NV30_SetupSurface(pScrn, pdPix, pdPict))
+		return FALSE;
 	NV30_SetupBlend(pScrn, blend, pdPict->format,
 			(pmPict && pmPict->componentAlpha &&
 			 PICT_FORMAT_RGB(pmPict->format)));
 
-	if (!NV30_SetupSurface(pScrn, pdPix, pdPict) ||
-	    !NV30EXATexture(pScrn, psPix, psPict, 0))
+	/* select picture sources */
+	if (!NV30EXAPicture(pScrn, psPix, psPict, 0, &sc, &sa, &solid[0]))
+		return FALSE;
+	if (!NV30EXAPicture(pScrn, pmPix, pmPict, 1, &mc, &ma, &solid[1]))
 		return FALSE;
 
-	if (pmPict) {
-		if (!NV30EXATexture(pScrn, pmPix, pmPict, 1))
-			return FALSE;
-
-		if (pdPict->format == PICT_a8) {
-			fragprog = PFP_C_A8;
-		} else
-		if (pmPict->componentAlpha && PICT_FORMAT_RGB(pmPict->format)) {
-			if (blend->src_alpha)
-				fragprog = PFP_CCASA;
-			else
-				fragprog = PFP_CCA;
-		} else {
-			fragprog = PFP_C;
-		}
-	} else {
-		if (pdPict->format == PICT_a8)
-			fragprog = PFP_S_A8;
+	/* configure register combiners */
+	BEGIN_NV04(push, NV30_3D(RC_IN_ALPHA(0)), 6);
+	PUSH_DATA (push, sa | ma);
+	if (pmPict &&
+	    pmPict->componentAlpha && PICT_FORMAT_RGB(pmPict->format)) {
+		if (blend->src_alpha)
+			PUSH_DATA(push, sa | mc);
 		else
-			fragprog = PFP_S;
+			PUSH_DATA(push, sc | mc);
+	} else {
+		PUSH_DATA(push, sc | ma);
 	}
+	PUSH_DATA (push, solid[0]);
+	PUSH_DATA (push, solid[1]);
+	PUSH_DATA (push, 0x00000c00);
+	PUSH_DATA (push, 0x00000c00);
+	BEGIN_NV04(push, NV30_3D(RC_FINAL0), 3);
+	if (pdPict->format != PICT_a8)
+		PUSH_DATA (push, 0x0000000c);
+	else
+		PUSH_DATA (push, 0x0000001c);
+	PUSH_DATA (push, 0x00001c00);
+	PUSH_DATA (push, 0x01000101);
 
+	/* select fragprog which just sources textures for combiners */
 	BEGIN_NV04(push, NV30_3D(FP_ACTIVE_PROGRAM), 1);
-	PUSH_MTHD (push, NV30_3D(FP_ACTIVE_PROGRAM), pNv->scratch, fragprog,
+	PUSH_MTHD (push, NV30_3D(FP_ACTIVE_PROGRAM), pNv->scratch, PFP_PASS,
 			 NOUVEAU_BO_VRAM | NOUVEAU_BO_RD | NOUVEAU_BO_LOW |
 			 NOUVEAU_BO_OR,
 			 NV30_3D_FP_ACTIVE_PROGRAM_DMA0,
@@ -474,7 +529,7 @@ NV30EXAPrepareComposite(int op, PicturePtr psPict,
 	BEGIN_NV04(push, NV30_3D(FP_CONTROL), 1);
 	PUSH_DATA (push, 0x00000000);
 	BEGIN_NV04(push, NV30_3D(TEX_UNITS_ENABLE), 1);
-	PUSH_DATA (push, pmPict ? 3 : 1);
+	PUSH_DATA (push, 3);
 
 	nouveau_pushbuf_bufctx(push, pNv->bufctx);
 	if (nouveau_pushbuf_validate(push)) {
@@ -630,8 +685,6 @@ NVAccelInitNV30TCL(ScrnInfoPtr pScrn)
 
 	BEGIN_NV04(push, NV30_3D(MULTISAMPLE_CONTROL), 1);
 	PUSH_DATA (push, 0xffff0000);
-	BEGIN_NV04(push, NV30_3D(RC_ENABLE), 1);
-	PUSH_DATA (push, 0);
 
 	/* Attempt to setup a known state.. Probably missing a heap of
 	 * stuff here..
@@ -766,87 +819,15 @@ NVAccelInitNV30TCL(ScrnInfoPtr pScrn)
 	PUSH_DATA (push, 4096<<16);
 	PUSH_DATA (push, 4096<<16);
 
-	PUSH_DATAu(push, pNv->scratch, PFP_PASS, 1 * 4);
-	PUSH_DATA (push, 0x01403e81); /* mov r0, a[col0] */
+	PUSH_DATAu(push, pNv->scratch, PFP_PASS, 2 * 4);
+	PUSH_DATA (push, 0x18009e80); /* txph r0, a[tex0], t[0] */
 	PUSH_DATA (push, 0x1c9dc801);
 	PUSH_DATA (push, 0x0001c800);
 	PUSH_DATA (push, 0x3fe1c800);
-
-	PUSH_DATAu(push, pNv->scratch, PFP_S, 2 * 4);
-	PUSH_DATA (push, 0x18009e00); /* txp r0, a[tex0], t[0] */
-	PUSH_DATA (push, 0x1c9dc801);
+	PUSH_DATA (push, 0x1802be83); /* txph r1, a[tex1], t[1] */
+	PUSH_DATA (push, 0x1c9dc801); /* exit */
 	PUSH_DATA (push, 0x0001c800);
 	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x01401e81); /* mov r0, r0 */
-	PUSH_DATA (push, 0x1c9dc800);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x0001c800);
-
-	PUSH_DATAu(push, pNv->scratch, PFP_S_A8, 2 * 4);
-	PUSH_DATA (push, 0x18009000); /* txp r0.w, a[tex0], t[0] */
-	PUSH_DATA (push, 0x1c9dc801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x01401e81); /* mov r0, r0.w */
-	PUSH_DATA (push, 0x1c9dfe00);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x0001c800);
-
-	PUSH_DATAu(push, pNv->scratch, PFP_C, 3 * 4);
-	PUSH_DATA (push, 0x1802b102); /* txpc0 r1.w, a[tex1], t[1] */
-	PUSH_DATA (push, 0x1c9dc801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x18009e00); /* txp r0 (ne0.w), a[tex0], t[0] */
-	PUSH_DATA (push, 0x1ff5c801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x02001e81); /* mul r0, r0, r1.w */
-	PUSH_DATA (push, 0x1c9dc800);
-	PUSH_DATA (push, 0x0001fe04);
-	PUSH_DATA (push, 0x0001c800);
-
-	PUSH_DATAu(push, pNv->scratch, PFP_C_A8, 3 * 4);
-	PUSH_DATA (push, 0x1802b102); /* txpc0 r1.w, a[tex1], t[1] */
-	PUSH_DATA (push, 0x1c9dc801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x18009000); /* txp r0.w (ne0.w), a[tex0], t[0] */
-	PUSH_DATA (push, 0x1ff5c801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x02001e81); /* mul r0, r0.w, r1.w */
-	PUSH_DATA (push, 0x1c9dfe00);
-	PUSH_DATA (push, 0x0001fe04);
-	PUSH_DATA (push, 0x0001c800);
-
-	PUSH_DATAu(push, pNv->scratch, PFP_CCA, 3 * 4);
-	PUSH_DATA (push, 0x18009f00); /* txpc0 r0, a[tex0], t[0] */
-	PUSH_DATA (push, 0x1c9dc801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x1802be02); /* txp r1 (ne0), a[tex1], t[1] */
-	PUSH_DATA (push, 0x1c95c801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x02001e81); /* mul r0, r0, r1 */
-	PUSH_DATA (push, 0x1c9dc800);
-	PUSH_DATA (push, 0x0001c804);
-	PUSH_DATA (push, 0x0001c800);
-
-	PUSH_DATAu(push, pNv->scratch, PFP_CCASA, 3 * 4);
-	PUSH_DATA (push, 0x18009102); /* txpc0 r1.w, a[tex0], t[0] */
-	PUSH_DATA (push, 0x1c9dc801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x1802be00); /* txp r0 (ne0.w), a[tex1], t[1] */
-	PUSH_DATA (push, 0x1ff5c801);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x3fe1c800);
-	PUSH_DATA (push, 0x02001e81); /* mul r0, r1.w, r0 */
-	PUSH_DATA (push, 0x1c9dfe04);
-	PUSH_DATA (push, 0x0001c800);
-	PUSH_DATA (push, 0x0001c800);
 
 	PUSH_DATAu(push, pNv->scratch, PFP_NV12_BILINEAR, 8 * 4);
 	PUSH_DATA (push, 0x17028200); /* texr r0.x, a[tex0], t[1] */
diff --git a/src/nv30_xv_tex.c b/src/nv30_xv_tex.c
index 52517c4..33c5602 100644
--- a/src/nv30_xv_tex.c
+++ b/src/nv30_xv_tex.c
@@ -271,6 +271,8 @@ NV30PutTextureImage(ScrnInfoPtr pScrn, struct nouveau_bo *src, int src_offset,
 	PUSH_DATA (push, 0x0001000f);
 	BEGIN_NV04(push, NV30_3D(FP_CONTROL), 1);
 	PUSH_DATA (push, 0x00000001);
+	BEGIN_NV04(push, NV30_3D(RC_ENABLE), 1);
+	PUSH_DATA (push, 0x00000000);
 
 	nouveau_pushbuf_bufctx(push, pNv->bufctx);
 	if (nouveau_pushbuf_validate(push)) {

commit b09a61780ea6710b679a6a099e35987e7a5f559f
Author: Ben Skeggs <bskeggs@redhat.com>
Date:   Mon Apr 23 14:49:22 2012 +1000

    nv10/exa: implement support for solid pictures
    
    Signed-off-by: Ben Skeggs <bskeggs@redhat.com>

diff --git a/src/nv10_exa.c b/src/nv10_exa.c
index b562e97..2da8cf6 100644
--- a/src/nv10_exa.c
+++ b/src/nv10_exa.c
@@ -66,11 +66,8 @@ static struct pict_format {
 };
 
 static int
-get_tex_format(PicturePtr pict)
+get_tex_format(NVPtr pNv, PicturePtr pict)
 {
-	ScrnInfoPtr pScrn = xf86Screens[pict->pDrawable->pScreen->myNum];
-	NVPtr pNv = NVPTR(pScrn);
-
 	/* If repeat is set we're always handling a 1x1 texture with
 	 * ARGB/XRGB destination, in that case we change the format to
 	 * use the POT (swizzled) matching format.
@@ -145,20 +142,22 @@ effective_component_alpha(PicturePtr mask)
 }
 
 static Bool
-check_texture(PicturePtr pict)
+check_texture(NVPtr pNv, PicturePtr pict)
 {
-	int w, h;
+	int w = 1, h = 1;
 
-	if (!pict->pDrawable)
-		NOUVEAU_FALLBACK("Solid and gradient pictures unsupported\n");
-
-	w = pict->pDrawable->width;
-	h = pict->pDrawable->height;
+	if (pict->pDrawable) {
+		w = pict->pDrawable->width;
+		h = pict->pDrawable->height;
+	} else {
+		if (pict->pSourcePict->type != SourcePictTypeSolidFill)
+			NOUVEAU_FALLBACK("gradient pictures unsupported\n");
+	}
 
 	if (w > 2046 || h > 2046)
 		NOUVEAU_FALLBACK("picture too large, %dx%d\n", w, h);
 
-	if (!get_tex_format(pict))
+	if (!get_tex_format(pNv, pict))
 		return FALSE;
 
 	if (pict->filter != PictFilterNearest &&
@@ -338,6 +337,9 @@ print_fallback_info(char *reason, int op, PicturePtr src, PicturePtr mask,
 Bool
 NV10EXACheckComposite(int op, PicturePtr src, PicturePtr mask, PicturePtr dst)
 {
+	ScrnInfoPtr pScrn = xf86Screens[dst->pDrawable->pScreen->myNum];
+	NVPtr pNv = NVPTR(pScrn);
+
 	if (!check_pict_op(op)) {
 		print_fallback_info("pictop", op, src, mask, dst);
 		return FALSE;
@@ -348,13 +350,13 @@ NV10EXACheckComposite(int op, PicturePtr src, PicturePtr mask, PicturePtr dst)
 		return FALSE;
 	}
 
-	if (!check_texture(src)) {
+	if (!check_texture(pNv, src)) {
 		print_fallback_info("src", op, src, mask, dst);
 		return FALSE;
 	}
 
 	if (mask) {
-		if (!check_texture(mask)) {
+		if (!check_texture(pNv, mask)) {
 			print_fallback_info("mask", op, src,
 					    mask, dst);
 			return FALSE;
@@ -386,7 +388,7 @@ setup_texture(NVPtr pNv, int unit, PicturePtr pict, PixmapPtr pixmap)
 		 NV10_3D_TEX_FORMAT_WRAP_S_CLAMP_TO_EDGE |
 		 log2i(w) << 20 | log2i(h) << 16 |
 		 1 << 12 | /* lod == 1 */
-		 get_tex_format(pict) |
+		 get_tex_format(pNv, pict) |
 		 0x50 /* UNK */;
 
 	/* NPOT_SIZE expects an even number for width, we can round up uneven
@@ -458,96 +460,6 @@ setup_render_target(NVPtr pNv, PicturePtr pict, PixmapPtr pixmap)
 	return TRUE;
 }
 
-/*
- * This can be a bit difficult to understand at first glance.  Reg
- * combiners are described here:
- * http://icps.u-strasbg.fr/~marchesin/perso/extensions/NV/register_combiners.html
- *
- * Single texturing setup, without honoring vertex colors (non default
- * setup) is: Alpha RC 0 : a_0 * 1 + 0 * 0 RGB RC 0 : rgb_0 * 1 + 0 *
- * 0 RC 1s are unused Final combiner uses default setup
- *
- * Default setup uses vertex rgb/alpha in place of 1s above, but we
- * don't need that in 2D.
- *
- * Multi texturing setup, where we do TEX0 in TEX1 (masking) is:
- * Alpha RC 0 : a_0 * a_1 + 0 * 0
- * RGB RC0 : rgb_0 * a_1 + 0 * 0
- * RC 1s are unused
- * Final combiner uses default setup
- */
-
-/* Bind the combiner variable <input> to a constant 1. */
-#define RC_IN_ONE(input)						\
-	(NV10_3D_RC_IN_RGB_##input##_INPUT_ZERO |			\
-	 NV10_3D_RC_IN_RGB_##input##_COMPONENT_USAGE_ALPHA |		\
-	 NV10_3D_RC_IN_RGB_##input##_MAPPING_UNSIGNED_INVERT)
-
-/* Bind the combiner variable <input> to the specified channel from
- * the texture unit <unit>. */
-#define RC_IN_TEX(input, chan, unit)					\
-	(NV10_3D_RC_IN_RGB_##input##_INPUT_TEXTURE##unit |		\
-	 NV10_3D_RC_IN_RGB_##input##_COMPONENT_USAGE_##chan)
-
-/* Bind the combiner variable <input> to the specified channel from
- * the constant color <unit>. */
-#define RC_IN_COLOR(input, chan, unit)					\
-	(NV10_3D_RC_IN_RGB_##input##_INPUT_CONSTANT_COLOR##unit |	\
-	 NV10_3D_RC_IN_RGB_##input##_COMPONENT_USAGE_##chan)
-
-static void
-setup_combiners(NVPtr pNv, PicturePtr src, PicturePtr mask, int alu)
-{
-	struct nouveau_pushbuf *push = pNv->pushbuf;
-	uint32_t rc_in_alpha = 0, rc_in_rgb = 0;
-
-	if (PICT_FORMAT_A(src->format))
-		rc_in_alpha |= RC_IN_TEX(A, ALPHA, 0);
-	else
-		rc_in_alpha |= RC_IN_ONE(A);
-
-	if (mask && PICT_FORMAT_A(mask->format))
-		rc_in_alpha |= RC_IN_TEX(B, ALPHA, 1);
-	else
-		rc_in_alpha |= RC_IN_ONE(B);
-
-	if (effective_component_alpha(mask)) {
-		if (!needs_src_alpha(alu)) {
-			/* The alpha channels won't be used for blending. Drop
-			 * them, as our pixels only have 4 components...
-			 * output_i = src_i * mask_i
-			 */
-			if (PICT_FORMAT_RGB(src->format))
-				rc_in_rgb |= RC_IN_TEX(A, RGB, 0);
-		} else {
-			/* The RGB channels won't be used for blending. Drop
-			 * them.
-			 * output_i = src_alpha * mask_i
-			 */
-			if (PICT_FORMAT_A(src->format))
-				rc_in_rgb |= RC_IN_TEX(A, ALPHA, 0);
-			else
-				rc_in_rgb |= RC_IN_ONE(A);
-		}
-
-		rc_in_rgb |= RC_IN_TEX(B, RGB, 1);
-
-	} else {
-		if (PICT_FORMAT_RGB(src->format))
-			rc_in_rgb |= RC_IN_TEX(A, RGB, 0);
-
-		if (mask && PICT_FORMAT_A(mask->format))
-			rc_in_rgb |= RC_IN_TEX(B, ALPHA, 1);
-		else
-			rc_in_rgb |= RC_IN_ONE(B);
-	}
-
-	BEGIN_NV04(push, NV10_3D(RC_IN_ALPHA(0)), 1);
-	PUSH_DATA (push, rc_in_alpha);
-	BEGIN_NV04(push, NV10_3D(RC_IN_RGB(0)), 1);
-	PUSH_DATA (push, rc_in_rgb);
-}
-
 static void
 setup_blend_function(NVPtr pNv, PicturePtr pdpict, int alu)
 {
@@ -578,6 +490,52 @@ setup_blend_function(NVPtr pNv, PicturePtr pdpict, int alu)
 	PUSH_DATA (push, 1);
 }
 
+#define RCSRC_COL(i)  (0x01 + (unit))
+#define RCSRC_TEX(i)  (0x08 + (unit))
+#define RCSEL_COLOR   (0x00)
+#define RCSEL_ALPHA   (0x10)
+#define RCINP_ZERO    (0x00)
+#define RCINP_ONE     (0x20)
+#define RCINP_A__SHIFT 24
+#define RCINP_B__SHIFT 16
+
+static Bool
+setup_picture(NVPtr pNv, PicturePtr pict, PixmapPtr pixmap, int unit,
+	      uint32_t *color, uint32_t *alpha)
+{
+	struct nouveau_pushbuf *push = pNv->pushbuf;
+	uint32_t shift, source;
+
+	if (pict && pict->pDrawable) {
+		if (!setup_texture(pNv, unit, pict, pixmap))
+			return FALSE;
+		source = RCSRC_TEX(unit);
+	} else
+	if (pict) {
+		BEGIN_NV04(push, NV10_3D(RC_COLOR(unit)), 1);
+		PUSH_DATA (push, pict->pSourcePict->solidFill.color);
+		source = RCSRC_COL(unit);
+	}
+
+	if (pict && PICT_FORMAT_RGB(pict->format))
+		*color = RCSEL_COLOR | source;
+	else
+		*color = RCSEL_ALPHA | RCINP_ZERO;
+
+	if (pict && PICT_FORMAT_A(pict->format))
+		*alpha = RCSEL_ALPHA | source;
+	else
+		*alpha = RCSEL_ALPHA | RCINP_ONE;
+
+	if (unit)
+		shift = RCINP_B__SHIFT;
+	else
+		shift = RCINP_A__SHIFT;
+	*color <<= shift;
+	*alpha <<= shift;
+	return TRUE;
+}
+
 Bool
 NV10EXAPrepareComposite(int op,
 			PicturePtr pict_src,
@@ -590,28 +548,35 @@ NV10EXAPrepareComposite(int op,
 	ScrnInfoPtr pScrn = xf86Screens[dst->drawable.pScreen->myNum];
 	NVPtr pNv = NVPTR(pScrn);
 	struct nouveau_pushbuf *push = pNv->pushbuf;
+	uint32_t sc, sa, mc, ma;
 
 	if (!PUSH_SPACE(push, 128))
 		return FALSE;
 	PUSH_RESET(push);
 
-	/* Set dst format */
+	/* setup render target and blending */
 	if (!setup_render_target(pNv, pict_dst, dst))
 		return FALSE;
+	setup_blend_function(pNv, pict_dst, op);
 
-	/* Set src format */
-	if (!setup_texture(pNv, 0, pict_src, src))
+	/* select picture sources */
+	if (!setup_picture(pNv, pict_src, src, 0, &sc, &sa))
 		return FALSE;
-
-	/* Set mask format */
-	if (mask && !setup_texture(pNv, 1, pict_mask, mask))
+	if (!setup_picture(pNv, pict_mask, mask, 1, &mc, &ma))
 		return FALSE;
 
-	/* Set the register combiners up. */
-	setup_combiners(pNv, pict_src, pict_mask, op);
-
-	/* Set PictOp */
-	setup_blend_function(pNv, pict_dst, op);
+	/* configure register combiners */
+	BEGIN_NV04(push, NV10_3D(RC_IN_ALPHA(0)), 1);
+	PUSH_DATA (push, sa | ma);
+	BEGIN_NV04(push, NV10_3D(RC_IN_RGB(0)), 1);
+	if (effective_component_alpha(pict_mask)) {
+		if (needs_src_alpha(op))
+			PUSH_DATA(push, sa | mc);
+		else
+			PUSH_DATA(push, sc | mc);
+	} else {
+		PUSH_DATA(push, sc | ma);
+	}
 
 	nouveau_pushbuf_bufctx(push, pNv->bufctx);
 	if (nouveau_pushbuf_validate(push)) {

commit 9583753a205c585ec844dfb7168513a2c2a157ba
Author: Ben Skeggs <bskeggs@redhat.com>
Date:   Fri Apr 20 20:52:01 2012 +1000

    nv10/exa: use fixed-function texture matrix for transforms
    
    Signed-off-by: Ben Skeggs <bskeggs@redhat.com>

diff --git a/src/nv10_exa.c b/src/nv10_exa.c
index 16b6d1c..b562e97 100644
--- a/src/nv10_exa.c
+++ b/src/nv10_exa.c
@@ -394,9 +394,7 @@ setup_texture(NVPtr pNv, int unit, PicturePtr pict, PixmapPtr pixmap)
 	 * for all formats we support 64 bytes represents an even number of
 	 * pixels
 	 */
-//	if (pict->repeat == RepeatNone)
-		w = (w + 1) &~ 1;
-
+	w = (w + 1) & ~1;
 
 	BEGIN_NV04(push, NV10_3D(TEX_OFFSET(unit)), 1);
 	PUSH_MTHDl(push, NV10_3D(TEX_OFFSET(unit)), bo, 0, reloc);
@@ -417,6 +415,31 @@ setup_texture(NVPtr pNv, int unit, PicturePtr pict, PixmapPtr pixmap)
 	else
 		PUSH_DATA(push, NV10_3D_TEX_FILTER_MAGNIFY_LINEAR |
 				NV10_3D_TEX_FILTER_MINIFY_LINEAR);
+	if (pict->transform) {
+		BEGIN_NV04(push, NV10_3D(TEX_MATRIX_ENABLE(unit)), 1);
+		PUSH_DATA (push, 1);
+		BEGIN_NV04(push, NV10_3D(TEX_MATRIX(unit, 0)), 16);
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[0][0]));
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[0][1]));
+		PUSH_DATAf(push, 0.f);
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[0][2]));
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[1][0]));
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[1][1]));
+		PUSH_DATAf(push, 0.f);
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[1][2]));
+		PUSH_DATAf(push, 0.0f);
+		PUSH_DATAf(push, 0.0f);
+		PUSH_DATAf(push, 0.0f);
+		PUSH_DATAf(push, 0.0f);
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[2][0]));
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[2][1]));
+		PUSH_DATAf(push, 0.0f);
+		PUSH_DATAf(push, xFixedToFloat(pict->transform->matrix[2][2]));
+	} else {
+		BEGIN_NV04(push, NV10_3D(TEX_MATRIX_ENABLE(unit)), 1);
+		PUSH_DATA (push, 0);
+	}
+
 	return TRUE;
 }
 
@@ -601,76 +624,37 @@ NV10EXAPrepareComposite(int op,
 	return TRUE;
 }
 
-#define QUAD(x, y, w, h)					\
-	{{{ IntToxFixed(x),     IntToxFixed(y),     xFixed1 }},	\
-	 {{ IntToxFixed(x + w), IntToxFixed(y),     xFixed1 }},	\
-	 {{ IntToxFixed(x + w), IntToxFixed(y + h), xFixed1 }},	\
-	 {{ IntToxFixed(x),     IntToxFixed(y + h), xFixed1 }}}
-
-#define MAP(f, p, v, ...) do {						\
-		int __i;						\
-		for (__i = 0; __i < sizeof(v)/sizeof((v)[0]); __i++)	\
-			f(p, __i, v, ## __VA_ARGS__);			\
-	} while (0);
-
-#define PUSH_DATAi(push, v, i)				\
-	PUSH_DATAf(push, xFixedToFloat((v).vector[i]))
-
 static inline void
-emit_vertex(NVPtr pNv, int i, PictVector pos[],
-	    PictVector tex0[], PictVector tex1[])
+PUSH_VTX2s(struct nouveau_pushbuf *push,
+	   int x1, int y1, int x2, int y2, int dx, int dy)
 {
-	struct nouveau_pushbuf *push = pNv->pushbuf;
-
-	BEGIN_NV04(push, NV10_3D(VERTEX_TX0_2F_S), 2);
-	PUSH_DATAi(push, tex0[i], 0);
-	PUSH_DATAi(push, tex0[i], 1);
-
-	if (tex1) {
-		BEGIN_NV04(push, NV10_3D(VERTEX_TX1_2F_S), 2);
-		PUSH_DATAi(push, tex1[i], 0);
-		PUSH_DATAi(push, tex1[i], 1);
-	}
-
+	BEGIN_NV04(push, NV10_3D(VERTEX_TX0_2I), 1);
+	PUSH_DATA (push, (y1 << 16) | x1);
+	BEGIN_NV04(push, NV10_3D(VERTEX_TX1_2I), 1);
+	PUSH_DATA (push, (y2 << 16) | x2);
 	BEGIN_NV04(push, NV10_3D(VERTEX_POS_3F_X), 3);
-	PUSH_DATAi(push, pos[i], 0);
-	PUSH_DATAi(push, pos[i], 1);
+	PUSH_DATAf(push, dx);
+	PUSH_DATAf(push, dy);
 	PUSH_DATAf(push, 0.0);
 }
 
-static inline void
-transform_vertex(PictTransformPtr t, int i, PictVector vs[])
-{
-	if  (t)
-		PictureTransformPoint(t, &vs[i]);
-}
-
 void
 NV10EXAComposite(PixmapPtr pix_dst,
-		 int srcX, int srcY,
-		 int maskX, int maskY,
-		 int dstX, int dstY,
-		 int width, int height)
+		 int sx, int sy, int mx, int my, int dx, int dy, int w, int h)
 {
 	ScrnInfoPtr pScrn = xf86Screens[pix_dst->drawable.pScreen->myNum];
 	NVPtr pNv = NVPTR(pScrn);
 	struct nouveau_pushbuf *push = pNv->pushbuf;
-	PicturePtr mask = pNv->pmpict,
-		src = pNv->pspict;
-	PictVector dstq[4] = QUAD(dstX, dstY, width, height),
-		maskq[4] = QUAD(maskX, maskY, width, height),
-		srcq[4] = QUAD(srcX, srcY, width, height);
-
-	MAP(transform_vertex, src->transform, srcq);
-	if (mask)
-		MAP(transform_vertex, mask->transform, maskq);
 
 	if (!PUSH_SPACE(push, 64))
 		return;
 
 	BEGIN_NV04(push, NV10_3D(VERTEX_BEGIN_END), 1);
 	PUSH_DATA (push, NV10_3D_VERTEX_BEGIN_END_QUADS);
-	MAP(emit_vertex, pNv, dstq, srcq, mask ? maskq : NULL);
+	PUSH_VTX2s(push, sx, sy, mx, my, dx, dy);
+	PUSH_VTX2s(push, sx + w, sy, mx + w, my, dx + w, dy);
+	PUSH_VTX2s(push, sx + w, sy + h, mx + w, my + h, dx + w, dy + h);
+	PUSH_VTX2s(push, sx, sy + h, mx, my + h, dx, dy + h);
 	BEGIN_NV04(push, NV10_3D(VERTEX_BEGIN_END), 1);


Reply to: