summaryrefslogtreecommitdiff
path: root/src/mesa/drivers/dri/r200
diff options
context:
space:
mode:
Diffstat (limited to 'src/mesa/drivers/dri/r200')
-rw-r--r--src/mesa/drivers/dri/r200/r200_cmdbuf.c2
-rw-r--r--src/mesa/drivers/dri/r200/r200_context.c13
-rw-r--r--src/mesa/drivers/dri/r200/r200_context.h27
-rw-r--r--src/mesa/drivers/dri/r200/r200_reg.h24
-rw-r--r--src/mesa/drivers/dri/r200/r200_state.c98
-rw-r--r--src/mesa/drivers/dri/r200/r200_state_init.c40
-rw-r--r--src/mesa/drivers/dri/r200/r200_swtcl.c20
-rw-r--r--src/mesa/drivers/dri/r200/r200_tcl.c17
-rw-r--r--src/mesa/drivers/dri/r200/r200_tex.c13
9 files changed, 236 insertions, 18 deletions
diff --git a/src/mesa/drivers/dri/r200/r200_cmdbuf.c b/src/mesa/drivers/dri/r200/r200_cmdbuf.c
index 91737d2d33..2920ceafd3 100644
--- a/src/mesa/drivers/dri/r200/r200_cmdbuf.c
+++ b/src/mesa/drivers/dri/r200/r200_cmdbuf.c
@@ -107,8 +107,8 @@ void r200SetUpAtomList( r200ContextPtr rmesa )
insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.mtl[i] );
for (i = 0; i < 6; ++i)
insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.ucp[i] );
- /* FIXME: is this a good place to insert that atom ? */
insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.spr );
+ insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.ptp );
insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.prf );
insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.pvs );
insert_at_tail( &rmesa->hw.atomlist, &rmesa->hw.vpp[0] );
diff --git a/src/mesa/drivers/dri/r200/r200_context.c b/src/mesa/drivers/dri/r200/r200_context.c
index 37abaa38de..2e55ac1f50 100644
--- a/src/mesa/drivers/dri/r200/r200_context.c
+++ b/src/mesa/drivers/dri/r200/r200_context.c
@@ -75,6 +75,7 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#define need_GL_EXT_blend_equation_separate
#define need_GL_EXT_blend_func_separate
#define need_GL_NV_vertex_program
+#define need_GL_ARB_point_parameters
#include "extension_helper.h"
#define DRIVER_DATE "20060602"
@@ -170,7 +171,7 @@ const struct dri_extension blend_extensions[] = {
{ "GL_EXT_blend_func_separate", GL_EXT_blend_func_separate_functions },
{ NULL, NULL }
};
-
+
const struct dri_extension ARB_vp_extension[] = {
{ "GL_ARB_vertex_program", GL_ARB_vertex_program_functions }
};
@@ -183,6 +184,12 @@ const struct dri_extension ATI_fs_extension[] = {
{ "GL_ATI_fragment_shader", GL_ATI_fragment_shader_functions }
};
+const struct dri_extension point_extensions[] = {
+ { "GL_ARB_point_sprite", NULL },
+ { "GL_ARB_point_parameters", GL_ARB_point_parameters_functions },
+ { NULL, NULL }
+};
+
extern const struct tnl_pipeline_stage _r200_render_stage;
extern const struct tnl_pipeline_stage _r200_tcl_stage;
@@ -200,9 +207,9 @@ static const struct tnl_pipeline_stage *r200_pipeline[] = {
&_tnl_fog_coordinate_stage,
&_tnl_texgen_stage,
&_tnl_texture_transform_stage,
+ &_tnl_point_attenuation_stage,
&_tnl_arb_vertex_program_stage,
&_tnl_vertex_program_stage,
-
/* Try again to go to tcl?
* - no good for asymmetric-twoside (do with multipass)
* - no good for asymmetric-unfilled (do with multipass)
@@ -485,6 +492,8 @@ GLboolean r200CreateContext( const __GLcontextModes *glVisual,
if ((ctx->Const.MaxTextureUnits == 6) && rmesa->r200Screen->drmSupportsFragShader)
driInitSingleExtension( ctx, ATI_fs_extension );
+ if (rmesa->r200Screen->drmSupportsPointSprites)
+ driInitExtensions( ctx, point_extensions, GL_FALSE );
#if 0
r200InitDriverFuncs( ctx );
r200InitIoctlFuncs( ctx );
diff --git a/src/mesa/drivers/dri/r200/r200_context.h b/src/mesa/drivers/dri/r200/r200_context.h
index b7ee33aa6c..0d252eceaf 100644
--- a/src/mesa/drivers/dri/r200/r200_context.h
+++ b/src/mesa/drivers/dri/r200/r200_context.h
@@ -445,9 +445,29 @@ struct r200_state_atom {
/* SPR - point sprite state
*/
-#define SPR_CMD_0 0
-#define SPR_POINT_SPRITE_CNTL 1
-#define SPR_STATE_SIZE 2
+#define SPR_CMD_0 0
+#define SPR_POINT_SPRITE_CNTL 1
+#define SPR_STATE_SIZE 2
+
+#define PTP_CMD_0 0
+#define PTP_VPORT_SCALE_0 1
+#define PTP_VPORT_SCALE_1 2
+#define PTP_VPORT_SCALE_PTSIZE 3
+#define PTP_VPORT_SCALE_3 4
+#define PTP_CMD_1 5
+#define PTP_ATT_CONST_QUAD 6
+#define PTP_ATT_CONST_LIN 7
+#define PTP_ATT_CONST_CON 8
+#define PTP_ATT_CONST_3 9
+#define PTP_EYE_X 10
+#define PTP_EYE_Y 11
+#define PTP_EYE_Z 12
+#define PTP_EYE_3 13
+#define PTP_CLAMP_MIN 14
+#define PTP_CLAMP_MAX 15
+#define PTP_CLAMP_2 16
+#define PTP_CLAMP_3 17
+#define PTP_STATE_SIZE 18
#define VTX_COLOR(v,n) (((v)>>(R200_VTX_COLOR_0_SHIFT+(n)*2))&\
R200_VTX_COLOR_MASK)
@@ -614,6 +634,7 @@ struct r200_hw_state {
struct r200_state_atom vpp[2];
struct r200_state_atom atf;
struct r200_state_atom spr;
+ struct r200_state_atom ptp;
int max_state_size; /* Number of bytes necessary for a full state emit. */
GLboolean is_dirty, all_dirty;
diff --git a/src/mesa/drivers/dri/r200/r200_reg.h b/src/mesa/drivers/dri/r200/r200_reg.h
index dab08a9eb7..a88ea4cec2 100644
--- a/src/mesa/drivers/dri/r200/r200_reg.h
+++ b/src/mesa/drivers/dri/r200/r200_reg.h
@@ -250,6 +250,10 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#define R200_ZBIAS_ENABLE_LINE (1 << 17)
#define R200_ZBIAS_ENABLE_TRI (1 << 18)
#define R200_WIDELINE_ENABLE (1 << 20)
+#define R200_DISC_FOG_SHADE_SOLID (0 << 24)
+#define R200_DISC_FOG_SHADE_FLAT (1 << 24)
+#define R200_DISC_FOG_SHADE_GOURAUD (2 << 24)
+#define R200_DISC_FOG_SHADE_MASK (3 << 24)
#define R200_VTX_PIX_CENTER_D3D (0 << 27)
#define R200_VTX_PIX_CENTER_OGL (1 << 27)
#define R200_ROUND_MODE_TRUNC (0 << 28)
@@ -659,7 +663,25 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#define R200_CULL_FRONT (1<<29)
#define R200_CULL_BACK (1<<30)
#define R200_SE_TCL_POINT_SPRITE_CNTL 0x22c4
-#define R200_POINTSIZE_SEL_STATE (1<<16)
+#define R200_PS_MULT_PVATTENCONST (0<<0)
+#define R200_PS_MULT_PVATTEN (1<<0)
+#define R200_PS_MULT_ATTENCONST (2<<0)
+#define R200_PS_MULT_PVCONST (3<<0)
+#define R200_PS_MULT_CONST (4<<0)
+#define R200_PS_MULT_MASK (7<<0)
+#define R200_PS_LIN_ATT_ZERO (1<<3)
+#define R200_PS_USE_MODEL_EYE_VEC (1<<4)
+#define R200_PS_ATT_ALPHA (1<<5)
+#define R200_PS_UCP_MODE_MASK (3<<6)
+#define R200_PS_GEN_TEX_0 (1<<8)
+#define R200_PS_GEN_TEX_1 (1<<9)
+#define R200_PS_GEN_TEX_2 (1<<10)
+#define R200_PS_GEN_TEX_3 (1<<11)
+#define R200_PS_GEN_TEX_4 (1<<12)
+#define R200_PS_GEN_TEX_5 (1<<13)
+#define R200_PS_GEN_TEX_0_SHIFT (8)
+#define R200_PS_GEN_TEX_MASK (0x3f<<8)
+#define R200_PS_SE_SEL_STATE (1<<16)
/* gap */
/* taken from r300, see comments there */
#define R200_VAP_PVS_CNTL_1 0x22d0
diff --git a/src/mesa/drivers/dri/r200/r200_state.c b/src/mesa/drivers/dri/r200/r200_state.c
index ac9e20e28a..3eb0aec441 100644
--- a/src/mesa/drivers/dri/r200/r200_state.c
+++ b/src/mesa/drivers/dri/r200/r200_state.c
@@ -686,10 +686,80 @@ static void r200FrontFace( GLcontext *ctx, GLenum mode )
static void r200PointSize( GLcontext *ctx, GLfloat size )
{
r200ContextPtr rmesa = R200_CONTEXT(ctx);
+ GLfloat *fcmd = (GLfloat *)rmesa->hw.ptp.cmd;
R200_STATECHANGE( rmesa, cst );
+ R200_STATECHANGE( rmesa, ptp );
rmesa->hw.cst.cmd[CST_RE_POINTSIZE] &= ~0xffff;
rmesa->hw.cst.cmd[CST_RE_POINTSIZE] |= ((GLuint)(ctx->Point.Size * 16.0));
+/* this is the size param of the point size calculation (point size reg value
+ is not used when calculation is active). */
+ fcmd[PTP_VPORT_SCALE_PTSIZE] = ctx->Point.Size;
+}
+
+static void r200PointParameter( GLcontext *ctx, GLenum pname, const GLfloat *params)
+{
+ r200ContextPtr rmesa = R200_CONTEXT(ctx);
+ GLfloat *fcmd = (GLfloat *)rmesa->hw.ptp.cmd;
+
+ switch (pname) {
+ case GL_POINT_SIZE_MIN:
+ /* Can clamp both in tcl and setup - just set both (as does fglrx) */
+ R200_STATECHANGE( rmesa, lin );
+ R200_STATECHANGE( rmesa, ptp );
+ rmesa->hw.lin.cmd[LIN_SE_LINE_WIDTH] &= 0xffff;
+ rmesa->hw.lin.cmd[LIN_SE_LINE_WIDTH] |= (GLuint)(ctx->Point.MinSize * 16.0) << 16;
+ fcmd[PTP_CLAMP_MIN] = ctx->Point.MinSize;
+ break;
+ case GL_POINT_SIZE_MAX:
+ R200_STATECHANGE( rmesa, cst );
+ R200_STATECHANGE( rmesa, ptp );
+ rmesa->hw.cst.cmd[CST_RE_POINTSIZE] &= 0xffff;
+ rmesa->hw.cst.cmd[CST_RE_POINTSIZE] |= (GLuint)(ctx->Point.MaxSize * 16.0) << 16;
+ fcmd[PTP_CLAMP_MAX] = ctx->Point.MaxSize;
+ break;
+ case GL_POINT_DISTANCE_ATTENUATION:
+ R200_STATECHANGE( rmesa, vtx );
+ R200_STATECHANGE( rmesa, spr );
+ R200_STATECHANGE( rmesa, ptp );
+ GLfloat *fcmd = (GLfloat *)rmesa->hw.ptp.cmd;
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] &=
+ ~(R200_PS_MULT_MASK | R200_PS_LIN_ATT_ZERO | R200_PS_SE_SEL_STATE);
+ /* can't rely on ctx->Point._Attenuated here and test for NEW_POINT in
+ r200ValidateState looks like overkill */
+ if (ctx->Point.Params[0] != 1.0 ||
+ ctx->Point.Params[1] != 0.0 ||
+ ctx->Point.Params[2] != 0.0 ||
+ (ctx->VertexProgram.Enabled && ctx->VertexProgram.PointSizeEnabled)) {
+ /* all we care for vp would be the ps_se_sel_state setting */
+ fcmd[PTP_ATT_CONST_QUAD] = ctx->Point.Params[2];
+ fcmd[PTP_ATT_CONST_LIN] = ctx->Point.Params[1];
+ fcmd[PTP_ATT_CONST_CON] = ctx->Point.Params[0];
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] |= R200_PS_MULT_ATTENCONST;
+ if (ctx->Point.Params[1] == 0.0)
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] |= R200_PS_LIN_ATT_ZERO;
+/* FIXME: setting this here doesn't look quite ok - we only want to do
+ that if we're actually drawing points probably */
+ rmesa->hw.vtx.cmd[VTX_TCL_OUTPUT_COMPSEL] |= R200_OUTPUT_PT_SIZE;
+ rmesa->hw.vtx.cmd[VTX_TCL_OUTPUT_VTXFMT_0] |= R200_VTX_POINT_SIZE;
+ }
+ else {
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] |=
+ R200_PS_SE_SEL_STATE | R200_PS_MULT_CONST;
+ rmesa->hw.vtx.cmd[VTX_TCL_OUTPUT_COMPSEL] &= ~R200_OUTPUT_PT_SIZE;
+ rmesa->hw.vtx.cmd[VTX_TCL_OUTPUT_VTXFMT_0] &= ~R200_VTX_POINT_SIZE;
+ }
+ break;
+ case GL_POINT_FADE_THRESHOLD_SIZE:
+ /* don't support multisampling, so doesn't matter. */
+ break;
+ /* can't do these but don't need them.
+ case GL_POINT_SPRITE_R_MODE_NV:
+ case GL_POINT_SPRITE_COORD_ORIGIN: */
+ default:
+ fprintf(stderr, "bad pname parameter in r200PointParameter\n");
+ return;
+ }
}
/* =============================================================
@@ -1382,20 +1452,23 @@ static void r200ShadeModel( GLcontext *ctx, GLenum mode )
s &= ~(R200_DIFFUSE_SHADE_MASK |
R200_ALPHA_SHADE_MASK |
R200_SPECULAR_SHADE_MASK |
- R200_FOG_SHADE_MASK);
+ R200_FOG_SHADE_MASK |
+ R200_DISC_FOG_SHADE_MASK);
switch ( mode ) {
case GL_FLAT:
s |= (R200_DIFFUSE_SHADE_FLAT |
R200_ALPHA_SHADE_FLAT |
R200_SPECULAR_SHADE_FLAT |
- R200_FOG_SHADE_FLAT);
+ R200_FOG_SHADE_FLAT |
+ R200_DISC_FOG_SHADE_FLAT);
break;
case GL_SMOOTH:
s |= (R200_DIFFUSE_SHADE_GOURAUD |
R200_ALPHA_SHADE_GOURAUD |
R200_SPECULAR_SHADE_GOURAUD |
- R200_FOG_SHADE_GOURAUD);
+ R200_FOG_SHADE_GOURAUD |
+ R200_DISC_FOG_SHADE_GOURAUD);
break;
default:
return;
@@ -2032,6 +2105,19 @@ static void r200Enable( GLcontext *ctx, GLenum cap, GLboolean state )
break;
#endif
+ case GL_POINT_SPRITE_ARB:
+ R200_STATECHANGE( rmesa, spr );
+ if ( state ) {
+ int i;
+ for (i = 0; i < 6; i++) {
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] |=
+ ctx->Point.CoordReplace[i] << (R200_PS_GEN_TEX_0_SHIFT + i);
+ }
+ } else {
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] &= ~R200_PS_GEN_TEX_MASK;
+ }
+ break;
+
case GL_POLYGON_OFFSET_FILL:
R200_STATECHANGE( rmesa, set );
if ( state ) {
@@ -2165,6 +2251,11 @@ static void r200Enable( GLcontext *ctx, GLenum cap, GLboolean state )
else {
/* picked up later */
}
+ r200PointParameter( ctx, GL_POINT_DISTANCE_ATTENUATION, NULL );
+ break;
+
+ case GL_VERTEX_PROGRAM_POINT_SIZE_ARB:
+ r200PointParameter( ctx, GL_POINT_DISTANCE_ATTENUATION, NULL );
break;
case GL_FRAGMENT_SHADER_ATI:
@@ -2516,6 +2607,7 @@ void r200InitStateFuncs( struct dd_function_table *functions )
functions->PolygonMode = r200PolygonMode;
functions->PolygonOffset = r200PolygonOffset;
functions->PolygonStipple = r200PolygonStipple;
+ functions->PointParameterfv = r200PointParameter;
functions->PointSize = r200PointSize;
functions->RenderMode = r200RenderMode;
functions->Scissor = r200Scissor;
diff --git a/src/mesa/drivers/dri/r200/r200_state_init.c b/src/mesa/drivers/dri/r200/r200_state_init.c
index ffca7ea5fa..d95a80c7bb 100644
--- a/src/mesa/drivers/dri/r200/r200_state_init.c
+++ b/src/mesa/drivers/dri/r200/r200_state_init.c
@@ -398,10 +398,14 @@ void r200InitState( r200ContextPtr rmesa )
else {
ALLOC_STATE( prf, never, PRF_STATE_SIZE, "PRF/performance-tri", 0 );
}
- if (rmesa->r200Screen->drmSupportsPointSprites)
+ if (rmesa->r200Screen->drmSupportsPointSprites) {
ALLOC_STATE( spr, always, SPR_STATE_SIZE, "SPR/pointsprite", 0 );
- else
+ ALLOC_STATE( ptp, tcl, PTP_STATE_SIZE, "PTP/pointparams", 0 );
+ }
+ else {
ALLOC_STATE (spr, never, SPR_STATE_SIZE, "SPR/pointsprite", 0 );
+ ALLOC_STATE (ptp, never, PTP_STATE_SIZE, "PTP/pointparams", 0 );
+ }
r200SetUpAtomList( rmesa );
@@ -546,6 +550,11 @@ void r200InitState( r200ContextPtr rmesa )
cmdvec( R200_VS_UCP_ADDR + i, 1, 4 );
}
+ rmesa->hw.ptp.cmd[PTP_CMD_0] =
+ cmdvec( R200_VS_PNT_SPRITE_VPORT_SCALE, 1, 4 );
+ rmesa->hw.ptp.cmd[PTP_CMD_1] =
+ cmdvec( R200_VS_PNT_SPRITE_ATT_CONST, 1, 12 );
+
/* Initial Harware state:
*/
rmesa->hw.ctx.cmd[CTX_PP_MISC] = (R200_ALPHA_TEST_PASS
@@ -653,6 +662,7 @@ void r200InitState( r200ContextPtr rmesa )
R200_ALPHA_SHADE_GOURAUD |
R200_SPECULAR_SHADE_GOURAUD |
R200_FOG_SHADE_GOURAUD |
+ R200_DISC_FOG_SHADE_GOURAUD |
R200_VTX_PIX_CENTER_OGL |
R200_ROUND_MODE_TRUNC |
R200_ROUND_PREC_8TH_PIX);
@@ -931,7 +941,31 @@ void r200InitState( r200ContextPtr rmesa )
rmesa->hw.eye.cmd[EYE_Z] = IEEE_ONE;
rmesa->hw.eye.cmd[EYE_RESCALE_FACTOR] = IEEE_ONE;
- rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] = R200_POINTSIZE_SEL_STATE;
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] =
+ R200_PS_SE_SEL_STATE | R200_PS_MULT_CONST;
+
+ /* ptp_eye is presumably used to calculate the attenuation wrt a different
+ location? In any case, since point attenuation triggers _needeyecoords,
+ it is constant. Probably ignored as long as R200_PS_USE_MODEL_EYE_VEC
+ isn't set */
+ rmesa->hw.ptp.cmd[PTP_EYE_X] = 0;
+ rmesa->hw.ptp.cmd[PTP_EYE_Y] = 0;
+ rmesa->hw.ptp.cmd[PTP_EYE_Z] = IEEE_ONE | 0x80000000; /* -1.0 */
+ rmesa->hw.ptp.cmd[PTP_EYE_3] = 0;
+ /* no idea what the ptp_vport_scale values are good for, except the
+ PTSIZE one - hopefully doesn't matter */
+ rmesa->hw.ptp.cmd[PTP_VPORT_SCALE_0] = IEEE_ONE;
+ rmesa->hw.ptp.cmd[PTP_VPORT_SCALE_1] = IEEE_ONE;
+ rmesa->hw.ptp.cmd[PTP_VPORT_SCALE_PTSIZE] = IEEE_ONE;
+ rmesa->hw.ptp.cmd[PTP_VPORT_SCALE_3] = IEEE_ONE;
+ rmesa->hw.ptp.cmd[PTP_ATT_CONST_QUAD] = 0;
+ rmesa->hw.ptp.cmd[PTP_ATT_CONST_LIN] = 0;
+ rmesa->hw.ptp.cmd[PTP_ATT_CONST_CON] = IEEE_ONE;
+ rmesa->hw.ptp.cmd[PTP_ATT_CONST_3] = 0;
+ rmesa->hw.ptp.cmd[PTP_CLAMP_MIN] = IEEE_ONE;
+ rmesa->hw.ptp.cmd[PTP_CLAMP_MAX] = 0x44ffe000; /* 2047 */
+ rmesa->hw.ptp.cmd[PTP_CLAMP_2] = 0;
+ rmesa->hw.ptp.cmd[PTP_CLAMP_3] = 0;
r200LightingSpaceChange( ctx );
diff --git a/src/mesa/drivers/dri/r200/r200_swtcl.c b/src/mesa/drivers/dri/r200/r200_swtcl.c
index aa78f38286..c14a275f7a 100644
--- a/src/mesa/drivers/dri/r200/r200_swtcl.c
+++ b/src/mesa/drivers/dri/r200/r200_swtcl.c
@@ -117,6 +117,11 @@ static void r200SetVertexFormat( GLcontext *ctx )
offset = 3;
}
+ if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_POINTSIZE )) {
+ EMIT_ATTR( _TNL_ATTRIB_POINTSIZE, EMIT_1F, R200_VTX_POINT_SIZE );
+ offset += 1;
+ }
+
rmesa->swtcl.coloroffset = offset;
#if MESA_LITTLE_ENDIAN
EMIT_ATTR( _TNL_ATTRIB_COLOR0, EMIT_4UB_4F_RGBA, (R200_VTX_PK_RGBA << R200_VTX_COLOR_0_SHIFT) );
@@ -349,7 +354,9 @@ static INLINE GLuint reduced_hw_prim( GLcontext *ctx, GLuint prim)
{
switch (prim) {
case GL_POINTS:
- return (ctx->_TriangleCaps & DD_POINT_SIZE) ?
+ return (ctx->Point.PointSprite ||
+ ((ctx->_TriangleCaps & (DD_POINT_SIZE | DD_POINT_ATTEN)) &&
+ !(ctx->_TriangleCaps & (DD_POINT_SMOOTH)))) ?
R200_VF_PRIM_POINT_SPRITES : R200_VF_PRIM_POINTS;
case GL_LINES:
/* fallthrough */
@@ -632,6 +639,17 @@ static void r200RasterPrimitive( GLcontext *ctx, GLuint hwprim )
r200ContextPtr rmesa = R200_CONTEXT(ctx);
if (rmesa->swtcl.hw_primitive != hwprim) {
+ /* need to disable perspective-correct texturing for point sprites */
+ if ((hwprim & 0xf) == R200_VF_PRIM_POINT_SPRITES && ctx->Point.PointSprite) {
+ if (rmesa->hw.set.cmd[SET_RE_CNTL] & R200_PERSPECTIVE_ENABLE) {
+ R200_STATECHANGE( rmesa, set );
+ rmesa->hw.set.cmd[SET_RE_CNTL] &= ~R200_PERSPECTIVE_ENABLE;
+ }
+ }
+ else if (!(rmesa->hw.set.cmd[SET_RE_CNTL] & R200_PERSPECTIVE_ENABLE)) {
+ R200_STATECHANGE( rmesa, set );
+ rmesa->hw.set.cmd[SET_RE_CNTL] |= R200_PERSPECTIVE_ENABLE;
+ }
R200_NEWPRIM( rmesa );
rmesa->swtcl.hw_primitive = hwprim;
}
diff --git a/src/mesa/drivers/dri/r200/r200_tcl.c b/src/mesa/drivers/dri/r200/r200_tcl.c
index 18b5458a97..8f50cd99ad 100644
--- a/src/mesa/drivers/dri/r200/r200_tcl.c
+++ b/src/mesa/drivers/dri/r200/r200_tcl.c
@@ -68,7 +68,9 @@ WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
#define HAVE_ELTS 1
-#define HW_POINTS ((ctx->_TriangleCaps & DD_POINT_SIZE) ? \
+#define HW_POINTS ((ctx->Point.PointSprite || \
+ ((ctx->_TriangleCaps & (DD_POINT_SIZE | DD_POINT_ATTEN)) && \
+ !(ctx->_TriangleCaps & (DD_POINT_SMOOTH)))) ? \
R200_VF_PRIM_POINT_SPRITES : R200_VF_PRIM_POINTS)
#define HW_LINES R200_VF_PRIM_LINES
#define HW_LINE_LOOP 0
@@ -268,6 +270,17 @@ void r200TclPrimitive( GLcontext *ctx,
if (newprim != rmesa->tcl.hw_primitive ||
!discrete_prim[hw_prim&0xf]) {
+ /* need to disable perspective-correct texturing for point sprites */
+ if ((prim & PRIM_MODE_MASK) == GL_POINTS && ctx->Point.PointSprite) {
+ if (rmesa->hw.set.cmd[SET_RE_CNTL] & R200_PERSPECTIVE_ENABLE) {
+ R200_STATECHANGE( rmesa, set );
+ rmesa->hw.set.cmd[SET_RE_CNTL] &= ~R200_PERSPECTIVE_ENABLE;
+ }
+ }
+ else if (!(rmesa->hw.set.cmd[SET_RE_CNTL] & R200_PERSPECTIVE_ENABLE)) {
+ R200_STATECHANGE( rmesa, set );
+ rmesa->hw.set.cmd[SET_RE_CNTL] |= R200_PERSPECTIVE_ENABLE;
+ }
R200_NEWPRIM( rmesa );
rmesa->tcl.hw_primitive = newprim;
}
@@ -447,7 +460,7 @@ static GLboolean r200_run_tcl_render( GLcontext *ctx,
out_vtxfmt0 |= R200_VTX_FP_RGBA << R200_VTX_COLOR_1_SHIFT;
out_compsel |= R200_OUTPUT_COLOR_1;
}
- /* FIXME: probably not everything is set up for fogc and psiz to work correctly */
+ /* FIXME: probably not everything is set up for fogc to work correctly */
if (vp_out & (1 << VERT_RESULT_FOGC)) {
out_vtxfmt0 |= R200_VTX_DISCRETE_FOG;
out_compsel |= R200_OUTPUT_DISCRETE_FOG;
diff --git a/src/mesa/drivers/dri/r200/r200_tex.c b/src/mesa/drivers/dri/r200/r200_tex.c
index b3da8cd580..2cfbf3510b 100644
--- a/src/mesa/drivers/dri/r200/r200_tex.c
+++ b/src/mesa/drivers/dri/r200/r200_tex.c
@@ -115,7 +115,7 @@ static void r200SetTexWrap( r200TexObjPtr t, GLenum swrap, GLenum twrap, GLenum
t->pp_txfilter |= R200_CLAMP_T_CLAMP_LAST;
break;
case GL_CLAMP_TO_BORDER:
- t->pp_txfilter |= R200_CLAMP_T_CLAMP_GL | R200_BORDER_MODE_D3D;
+ t->pp_txfilter |= R200_CLAMP_T_CLAMP_GL;
is_clamp_to_border = GL_TRUE;
break;
case GL_MIRRORED_REPEAT:
@@ -1005,7 +1005,16 @@ static void r200TexEnv( GLcontext *ctx, GLenum target,
}
break;
}
-
+ case GL_COORD_REPLACE_ARB:
+ if (ctx->Point.PointSprite) {
+ R200_STATECHANGE( rmesa, spr );
+ if ((GLenum)param[0]) {
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] |= R200_PS_GEN_TEX_0 << unit;
+ } else {
+ rmesa->hw.spr.cmd[SPR_POINT_SPRITE_CNTL] &= ~(R200_PS_GEN_TEX_0 << unit);
+ }
+ }
+ break;
default:
return;
}