static void radeonRasterPrimitive( struct gl_context *ctx, GLuint hwprim ) { r100ContextPtr rmesa = R100_CONTEXT(ctx); if (rmesa->radeon.swtcl.hw_primitive != hwprim) { RADEON_NEWPRIM( rmesa ); rmesa->radeon.swtcl.hw_primitive = hwprim; } }
static void radeonSetVertexFormat( struct gl_context *ctx ) { r100ContextPtr rmesa = R100_CONTEXT( ctx ); TNLcontext *tnl = TNL_CONTEXT(ctx); struct vertex_buffer *VB = &tnl->vb; GLbitfield64 index_bitset = tnl->render_inputs_bitset; int fmt_0 = 0; int offset = 0; /* Important: */ if ( VB->NdcPtr != NULL ) { VB->AttribPtr[VERT_ATTRIB_POS] = VB->NdcPtr; } else { VB->AttribPtr[VERT_ATTRIB_POS] = VB->ClipPtr; } assert( VB->AttribPtr[VERT_ATTRIB_POS] != NULL ); rmesa->radeon.swtcl.vertex_attr_count = 0; /* EMIT_ATTR's must be in order as they tell t_vertex.c how to * build up a hardware vertex. */ if ( !rmesa->swtcl.needproj || (index_bitset & BITFIELD64_RANGE(_TNL_ATTRIB_TEX0, _TNL_NUM_TEX))) { /* for projtex */ EMIT_ATTR( _TNL_ATTRIB_POS, EMIT_4F, RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_Z | RADEON_CP_VC_FRMT_W0 ); offset = 4; } else { EMIT_ATTR( _TNL_ATTRIB_POS, EMIT_3F, RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_Z ); offset = 3; } rmesa->swtcl.coloroffset = offset; #if MESA_LITTLE_ENDIAN EMIT_ATTR( _TNL_ATTRIB_COLOR0, EMIT_4UB_4F_RGBA, RADEON_CP_VC_FRMT_PKCOLOR ); #else EMIT_ATTR( _TNL_ATTRIB_COLOR0, EMIT_4UB_4F_ABGR, RADEON_CP_VC_FRMT_PKCOLOR ); #endif offset += 1; rmesa->swtcl.specoffset = 0; if (index_bitset & (BITFIELD64_BIT(_TNL_ATTRIB_COLOR1) | BITFIELD64_BIT(_TNL_ATTRIB_FOG))) { #if MESA_LITTLE_ENDIAN if (index_bitset & BITFIELD64_BIT(_TNL_ATTRIB_COLOR1)) { rmesa->swtcl.specoffset = offset; EMIT_ATTR( _TNL_ATTRIB_COLOR1, EMIT_3UB_3F_RGB, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 3 ); } if (index_bitset & BITFIELD64_BIT(_TNL_ATTRIB_FOG)) { EMIT_ATTR( _TNL_ATTRIB_FOG, EMIT_1UB_1F, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 1 ); } #else if (index_bitset & BITFIELD64_BIT(_TNL_ATTRIB_FOG)) { EMIT_ATTR( _TNL_ATTRIB_FOG, EMIT_1UB_1F, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 1 ); } if (index_bitset & BITFIELD64_BIT(_TNL_ATTRIB_COLOR1)) { rmesa->swtcl.specoffset = offset; EMIT_ATTR( _TNL_ATTRIB_COLOR1, EMIT_3UB_3F_BGR, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 3 ); } #endif } if (index_bitset & BITFIELD64_RANGE(_TNL_ATTRIB_TEX0, _TNL_NUM_TEX)) { int i; for (i = 0; i < ctx->Const.MaxTextureUnits; i++) { if (index_bitset & BITFIELD64_BIT(_TNL_ATTRIB_TEX(i))) { GLuint sz = VB->AttribPtr[_TNL_ATTRIB_TEX0 + i]->size; switch (sz) { case 1: case 2: EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_2F, radeon_cp_vc_frmts[i][0] ); break; case 3: if (ctx->Texture.Unit[i]._Current && ctx->Texture.Unit[i]._Current->Target == GL_TEXTURE_CUBE_MAP) { EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_3F, radeon_cp_vc_frmts[i][1] ); } else { EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_2F, radeon_cp_vc_frmts[i][0] ); } break; case 4: if (ctx->Texture.Unit[i]._Current && ctx->Texture.Unit[i]._Current->Target == GL_TEXTURE_CUBE_MAP) { EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_3F, radeon_cp_vc_frmts[i][1] ); } else { EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_3F_XYW, radeon_cp_vc_frmts[i][1] ); } break; default: continue; }; } } } if (rmesa->radeon.tnl_index_bitset != index_bitset || fmt_0 != rmesa->swtcl.vertex_format) { RADEON_NEWPRIM(rmesa); rmesa->swtcl.vertex_format = fmt_0; rmesa->radeon.swtcl.vertex_size = _tnl_install_attrs( ctx, rmesa->radeon.swtcl.vertex_attrs, rmesa->radeon.swtcl.vertex_attr_count, NULL, 0 ); rmesa->radeon.swtcl.vertex_size /= 4; rmesa->radeon.tnl_index_bitset = index_bitset; radeon_print(RADEON_SWRENDER, RADEON_VERBOSE, "%s: vertex_size= %d floats\n", __func__, rmesa->radeon.swtcl.vertex_size); } }
static void radeonSetVertexFormat( GLcontext *ctx ) { radeonContextPtr rmesa = RADEON_CONTEXT( ctx ); TNLcontext *tnl = TNL_CONTEXT(ctx); struct vertex_buffer *VB = &tnl->vb; DECLARE_RENDERINPUTS(index_bitset); int fmt_0 = 0; int offset = 0; RENDERINPUTS_COPY( index_bitset, tnl->render_inputs_bitset ); /* Important: */ if ( VB->NdcPtr != NULL ) { VB->AttribPtr[VERT_ATTRIB_POS] = VB->NdcPtr; } else { VB->AttribPtr[VERT_ATTRIB_POS] = VB->ClipPtr; } assert( VB->AttribPtr[VERT_ATTRIB_POS] != NULL ); rmesa->swtcl.vertex_attr_count = 0; /* EMIT_ATTR's must be in order as they tell t_vertex.c how to * build up a hardware vertex. */ if ( !rmesa->swtcl.needproj || RENDERINPUTS_TEST_RANGE( index_bitset, _TNL_FIRST_TEX, _TNL_LAST_TEX )) { /* for projtex */ EMIT_ATTR( _TNL_ATTRIB_POS, EMIT_4F, RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_Z | RADEON_CP_VC_FRMT_W0 ); offset = 4; } else { EMIT_ATTR( _TNL_ATTRIB_POS, EMIT_3F, RADEON_CP_VC_FRMT_XY | RADEON_CP_VC_FRMT_Z ); offset = 3; } rmesa->swtcl.coloroffset = offset; #if MESA_LITTLE_ENDIAN EMIT_ATTR( _TNL_ATTRIB_COLOR0, EMIT_4UB_4F_RGBA, RADEON_CP_VC_FRMT_PKCOLOR ); #else EMIT_ATTR( _TNL_ATTRIB_COLOR0, EMIT_4UB_4F_ABGR, RADEON_CP_VC_FRMT_PKCOLOR ); #endif offset += 1; rmesa->swtcl.specoffset = 0; if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_COLOR1 ) || RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_FOG )) { #if MESA_LITTLE_ENDIAN if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_COLOR1 )) { rmesa->swtcl.specoffset = offset; EMIT_ATTR( _TNL_ATTRIB_COLOR1, EMIT_3UB_3F_RGB, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 3 ); } if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_FOG )) { EMIT_ATTR( _TNL_ATTRIB_FOG, EMIT_1UB_1F, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 1 ); } #else if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_FOG )) { EMIT_ATTR( _TNL_ATTRIB_FOG, EMIT_1UB_1F, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 1 ); } if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_COLOR1 )) { rmesa->swtcl.specoffset = offset; EMIT_ATTR( _TNL_ATTRIB_COLOR1, EMIT_3UB_3F_BGR, RADEON_CP_VC_FRMT_PKSPEC ); } else { EMIT_PAD( 3 ); } #endif } if (RENDERINPUTS_TEST_RANGE( index_bitset, _TNL_FIRST_TEX, _TNL_LAST_TEX )) { int i; for (i = 0; i < ctx->Const.MaxTextureUnits; i++) { if (RENDERINPUTS_TEST( index_bitset, _TNL_ATTRIB_TEX(i) )) { GLuint sz = VB->TexCoordPtr[i]->size; switch (sz) { case 1: case 2: EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_2F, radeon_cp_vc_frmts[i][0] ); break; case 3: case 4: if (ctx->Texture.Unit[i]._ReallyEnabled & (TEXTURE_CUBE_BIT) ) { EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_3F, radeon_cp_vc_frmts[i][1] ); } else { EMIT_ATTR( _TNL_ATTRIB_TEX0+i, EMIT_3F_XYW, radeon_cp_vc_frmts[i][1] ); } break; default: continue; }; } } } if (!RENDERINPUTS_EQUAL( rmesa->tnl_index_bitset, index_bitset ) || fmt_0 != rmesa->swtcl.vertex_format) { RADEON_NEWPRIM(rmesa); rmesa->swtcl.vertex_format = fmt_0; rmesa->swtcl.vertex_size = _tnl_install_attrs( ctx, rmesa->swtcl.vertex_attrs, rmesa->swtcl.vertex_attr_count, NULL, 0 ); rmesa->swtcl.vertex_size /= 4; RENDERINPUTS_COPY( rmesa->tnl_index_bitset, index_bitset ); if (RADEON_DEBUG & DEBUG_VERTS) fprintf( stderr, "%s: vertex_size= %d floats\n", __FUNCTION__, rmesa->swtcl.vertex_size); } }
/* Begin/End */ static void radeon_Begin( GLenum mode ) { GET_CURRENT_CONTEXT(ctx); radeonContextPtr rmesa = RADEON_CONTEXT(ctx); if (RADEON_DEBUG & DEBUG_VFMT) fprintf(stderr, "%s( %s )\n", __FUNCTION__, _mesa_lookup_enum_by_nr( mode )); if (mode > GL_POLYGON) { _mesa_error( ctx, GL_INVALID_ENUM, "glBegin" ); return; } if (rmesa->vb.prim[0] != GL_POLYGON+1) { _mesa_error( ctx, GL_INVALID_OPERATION, "glBegin" ); return; } if (ctx->NewState) _mesa_update_state( ctx ); if (rmesa->NewGLState) radeonValidateState( ctx ); if (rmesa->vb.recheck) radeonVtxfmtValidate( ctx ); if (!rmesa->vb.installed) { CALL_Begin(GET_DISPATCH(), (mode)); return; } if (rmesa->dma.flush && rmesa->vb.counter < 12) { if (RADEON_DEBUG & DEBUG_VFMT) fprintf(stderr, "%s: flush almost-empty buffers\n", __FUNCTION__); flush_prims( rmesa ); } /* Need to arrange to save vertices here? Or always copy from dma (yuk)? */ if (!rmesa->dma.flush) { /* FIXME: what are these constants? */ if (rmesa->dma.current.ptr + 12*rmesa->vb.vertex_size*4 > rmesa->dma.current.end) { RADEON_NEWPRIM( rmesa ); radeonRefillCurrentDmaRegion( rmesa ); } rmesa->vb.dmaptr = (int *)(rmesa->dma.current.address + rmesa->dma.current.ptr); rmesa->vb.counter = (rmesa->dma.current.end - rmesa->dma.current.ptr) / (rmesa->vb.vertex_size * 4); rmesa->vb.counter--; rmesa->vb.initial_counter = rmesa->vb.counter; rmesa->vb.notify = wrap_buffer; rmesa->dma.flush = flush_prims; ctx->Driver.NeedFlush |= FLUSH_STORED_VERTICES; } rmesa->vb.prim[0] = mode; start_prim( rmesa, mode | PRIM_BEGIN ); }
static GLboolean check_vtx_fmt( GLcontext *ctx ) { radeonContextPtr rmesa = RADEON_CONTEXT(ctx); GLuint ind = RADEON_CP_VC_FRMT_Z; GLuint unit; if (rmesa->TclFallback || rmesa->vb.fell_back || ctx->CompileFlag || (ctx->Fog.Enabled && (ctx->Fog.FogCoordinateSource == GL_FOG_COORD))) return GL_FALSE; if (ctx->Driver.NeedFlush & FLUSH_UPDATE_CURRENT) ctx->Driver.FlushVertices( ctx, FLUSH_UPDATE_CURRENT ); /* Make all this event-driven: */ if (ctx->Light.Enabled) { ind |= RADEON_CP_VC_FRMT_N0; /* TODO: make this data driven: If we receive only ubytes, send * color as ubytes. Also check if converting (with free * checking for overflow) is cheaper than sending floats * directly. */ if (ctx->Light.ColorMaterialEnabled) { ind |= (RADEON_CP_VC_FRMT_FPCOLOR | RADEON_CP_VC_FRMT_FPALPHA); } else ind |= RADEON_CP_VC_FRMT_PKCOLOR; /* for alpha? */ } else { /* TODO: make this data driven? */ ind |= RADEON_CP_VC_FRMT_PKCOLOR; if (ctx->_TriangleCaps & DD_SEPARATE_SPECULAR) { ind |= RADEON_CP_VC_FRMT_PKSPEC; } } if ( ctx->Fog.FogCoordinateSource == GL_FOG_COORD ) { ind |= RADEON_CP_VC_FRMT_PKSPEC; } for (unit = 0 ; unit < ctx->Const.MaxTextureUnits; unit++) { if (ctx->Texture.Unit[unit]._ReallyEnabled) { if (ctx->Texture.Unit[unit].TexGenEnabled) { if (rmesa->TexGenNeedNormals[unit]) { ind |= RADEON_CP_VC_FRMT_N0; } } else { if (ctx->Current.Attrib[VERT_ATTRIB_TEX(unit)][3] != 1.0) { if (RADEON_DEBUG & (DEBUG_VFMT|DEBUG_FALLBACKS)) fprintf(stderr, "%s: q%u\n", __FUNCTION__, unit); return GL_FALSE; } ind |= RADEON_ST_BIT(unit); } } } if (RADEON_DEBUG & (DEBUG_VFMT|DEBUG_STATE)) fprintf(stderr, "%s: format: 0x%x\n", __FUNCTION__, ind ); RADEON_NEWPRIM(rmesa); rmesa->vb.vertex_format = ind; rmesa->vb.vertex_size = 3; rmesa->vb.prim = &ctx->Driver.CurrentExecPrimitive; rmesa->vb.normalptr = ctx->Current.Attrib[VERT_ATTRIB_NORMAL]; rmesa->vb.colorptr = NULL; rmesa->vb.floatcolorptr = ctx->Current.Attrib[VERT_ATTRIB_COLOR0]; rmesa->vb.specptr = NULL; rmesa->vb.floatspecptr = ctx->Current.Attrib[VERT_ATTRIB_COLOR1]; rmesa->vb.texcoordptr[0] = ctx->Current.Attrib[VERT_ATTRIB_TEX0]; rmesa->vb.texcoordptr[1] = ctx->Current.Attrib[VERT_ATTRIB_TEX1]; rmesa->vb.texcoordptr[2] = ctx->Current.Attrib[VERT_ATTRIB_TEX2]; rmesa->vb.texcoordptr[3] = ctx->Current.Attrib[VERT_ATTRIB_TEX0]; /* dummy */ /* Run through and initialize the vertex components in the order * the hardware understands: */ if (ind & RADEON_CP_VC_FRMT_N0) { rmesa->vb.normalptr = &rmesa->vb.vertex[rmesa->vb.vertex_size].f; rmesa->vb.vertex_size += 3; rmesa->vb.normalptr[0] = ctx->Current.Attrib[VERT_ATTRIB_NORMAL][0]; rmesa->vb.normalptr[1] = ctx->Current.Attrib[VERT_ATTRIB_NORMAL][1]; rmesa->vb.normalptr[2] = ctx->Current.Attrib[VERT_ATTRIB_NORMAL][2]; } if (ind & RADEON_CP_VC_FRMT_PKCOLOR) { rmesa->vb.colorptr = &rmesa->vb.vertex[rmesa->vb.vertex_size].color; rmesa->vb.vertex_size += 1; UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.colorptr->red, ctx->Current.Attrib[VERT_ATTRIB_COLOR0][0] ); UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.colorptr->green, ctx->Current.Attrib[VERT_ATTRIB_COLOR0][1] ); UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.colorptr->blue, ctx->Current.Attrib[VERT_ATTRIB_COLOR0][2] ); UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.colorptr->alpha, ctx->Current.Attrib[VERT_ATTRIB_COLOR0][3] ); } if (ind & RADEON_CP_VC_FRMT_FPCOLOR) { assert(!(ind & RADEON_CP_VC_FRMT_PKCOLOR)); rmesa->vb.floatcolorptr = &rmesa->vb.vertex[rmesa->vb.vertex_size].f; rmesa->vb.vertex_size += 3; rmesa->vb.floatcolorptr[0] = ctx->Current.Attrib[VERT_ATTRIB_COLOR0][0]; rmesa->vb.floatcolorptr[1] = ctx->Current.Attrib[VERT_ATTRIB_COLOR0][1]; rmesa->vb.floatcolorptr[2] = ctx->Current.Attrib[VERT_ATTRIB_COLOR0][2]; if (ind & RADEON_CP_VC_FRMT_FPALPHA) { rmesa->vb.vertex_size += 1; rmesa->vb.floatcolorptr[3] = ctx->Current.Attrib[VERT_ATTRIB_COLOR0][3]; } } if (ind & RADEON_CP_VC_FRMT_PKSPEC) { rmesa->vb.specptr = &rmesa->vb.vertex[rmesa->vb.vertex_size].color; rmesa->vb.vertex_size += 1; UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.specptr->red, ctx->Current.Attrib[VERT_ATTRIB_COLOR1][0] ); UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.specptr->green, ctx->Current.Attrib[VERT_ATTRIB_COLOR1][1] ); UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.specptr->blue, ctx->Current.Attrib[VERT_ATTRIB_COLOR1][2] ); /* fog ??? */ /* UNCLAMPED_FLOAT_TO_CHAN( rmesa->vb.specptr->alpha, radeonComputeFogFactor(ctx->Current.Attrib[VERT_ATTRIB_FOG][0]) ); */ } for (unit = 0 ; unit < ctx->Const.MaxTextureUnits; unit++) { if (ind & RADEON_ST_BIT(unit)) { rmesa->vb.texcoordptr[unit] = &rmesa->vb.vertex[rmesa->vb.vertex_size].f; rmesa->vb.vertex_size += 2; rmesa->vb.texcoordptr[unit][0] = ctx->Current.Attrib[VERT_ATTRIB_TEX(unit)][0]; rmesa->vb.texcoordptr[unit][1] = ctx->Current.Attrib[VERT_ATTRIB_TEX(unit)][1]; } } if (rmesa->vb.installed_vertex_format != rmesa->vb.vertex_format) { if (RADEON_DEBUG & DEBUG_VFMT) fprintf(stderr, "reinstall on vertex_format change\n"); _mesa_install_exec_vtxfmt( ctx, &rmesa->vb.vtxfmt ); rmesa->vb.installed_vertex_format = rmesa->vb.vertex_format; } if (RADEON_DEBUG & DEBUG_VFMT) fprintf(stderr, "%s -- success\n", __FUNCTION__); return GL_TRUE; }