*/
void r300InitCmdBuf(r300ContextPtr r300)
{
- int size;
+ int size, i, mtu;
r300->hw.max_state_size = 0;
+
+ mtu = r300->radeon.glCtx->Const.MaxTextureUnits;
+ fprintf(stderr, "Using %d maximum texture units..\n", mtu);
/* Initialize state atoms */
ALLOC_STATE( vpt, always, R300_VPT_CMDSIZE, "vpt", 0 );
ALLOC_STATE( vps, vpu, R300_VPS_CMDSIZE, "vps", 0 );
r300->hw.vps.cmd[R300_VPS_CMD_0] = cmdvpu(R300_PVS_UPLOAD_POINTSIZE, 1);
+ /* Textures */
+ ALLOC_STATE( tex.filter, always, mtu, "tex_filter", 0 );
+ r300->hw.tex.filter.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_FILTER_0, mtu-1);
+
+ ALLOC_STATE( tex.unknown1, always, mtu, "tex_unknown1", 0 );
+ r300->hw.tex.unknown1.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_UNK1_0, mtu-1);
+
+ ALLOC_STATE( tex.size, always, mtu, "tex_size", 0 );
+ r300->hw.tex.size.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_SIZE_0, mtu-1);
+
+ ALLOC_STATE( tex.format, always, mtu, "tex_format", 0 );
+ r300->hw.tex.format.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_FORMAT_0, mtu-1);
+
+ ALLOC_STATE( tex.offset, always, mtu, "tex_offset", 0 );
+ r300->hw.tex.offset.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_OFFSET_0, mtu-1);
+
+ ALLOC_STATE( tex.unknown4, always, mtu, "tex_unknown4", 0 );
+ r300->hw.tex.unknown4.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_UNK4_0, mtu-1);
+
+ ALLOC_STATE( tex.unknown5, always, mtu, "tex_unknown5", 0 );
+ r300->hw.tex.unknown5.cmd[R300_TEX_CMD_0] = cmducs(R300_TX_UNK5_0, mtu-1);
+
+
/* Setup the atom linked list */
make_empty_list(&r300->hw.atomlist);
r300->hw.atomlist.name = "atom-list";
insert_at_tail(&r300->hw.atomlist, &r300->hw.vpp);
insert_at_tail(&r300->hw.atomlist, &r300->hw.vps);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.filter);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.unknown1);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.size);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.format);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.offset);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.unknown4);
+ insert_at_tail(&r300->hw.atomlist, &r300->hw.tex.unknown5);
+
r300->hw.is_dirty = GL_TRUE;
r300->hw.all_dirty = GL_TRUE;
return u.u;
}
+ /* Texture related */
+
+#define TEX_0 0x1
+#define TEX_1 0x2
+#define TEX_2 0x4
+#define TEX_3 0x8
+#define TEX_4 0x10
+#define TEX_5 0x20
+#define TEX_6 0x20
+#define TEX_7 0x20
+#define TEX_ALL 0xff
+
+typedef struct r300_tex_obj r300TexObj, *r300TexObjPtr;
+
+/* Texture object in locally shared texture space.
+ */
+struct r300_tex_obj {
+ driTextureObject base;
+
+ GLuint bufAddr; /* Offset to start of locally
+ shared texture block */
+
+ GLuint dirty_state; /* Flags (1 per texunit) for
+ whether or not this texobj
+ has dirty hardware state
+ (pp_*) that needs to be
+ brought into the
+ texunit. */
+
+ drm_radeon_tex_image_t image[6][RADEON_MAX_TEXTURE_LEVELS];
+ /* Six, for the cube faces */
+
+
+ /* hardware register values */
+ /* Note that R200 has 8 registers per texture and R300 only 7 */
+ GLuint filter;
+ GLuint pitch; /* one of the unknown registers.. unknown 1 ?*/
+ GLuint size; /* npot only */
+ GLuint format;
+ GLuint offset; /* Image location in texmem.
+ All cube faces follow. */
+ GLuint unknown4;
+ GLuint unknown5;
+ /* end hardware registers */
+
+ GLboolean border_fallback;
+};
+
+
/**
* A block of hardware state.
*
#define R300_VPS_ZERO_3 4
#define R300_VPS_CMDSIZE 5
+ /* the layout is common for all fields inside tex */
+#define R300_TEX_CMD_0 0
+#define R300_TEX_VALUE_0 1
+/* We don't really use this, instead specify mtu+1 dynamically
+#define R300_TEX_CMDSIZE (MAX_TEXTURE_UNITS+1)
+*/
+
/**
* Cache for hardware register state.
*/
struct r300_state_atom vpi; /* vp instructions */
struct r300_state_atom vpp; /* vp parameters */
struct r300_state_atom vps; /* vertex point size (?) */
+
+ /* 8 texture units */
+ /* the state is grouped by function and not by
+ texture unit. This makes single unit updates
+ really awkward - we are much better off
+ updating the whole thing at once */
+ struct {
+ struct r300_state_atom filter;
+ struct r300_state_atom unknown1;
+ struct r300_state_atom size;
+ struct r300_state_atom format;
+ struct r300_state_atom offset;
+ struct r300_state_atom unknown4;
+ struct r300_state_atom unknown5;
+ } tex;
};
r300->hw.vps.cmd[R300_VPS_ZERO_1] = 0;
r300->hw.vps.cmd[R300_VPS_POINTSIZE] = r300PackFloat32(1.0);
r300->hw.vps.cmd[R300_VPS_ZERO_3] = 0;
+
+ /* Initialize texture units */
+ for(i=0;i<r300->radeon.glCtx->Const.MaxTextureUnits;i++){
+ r300->hw.tex.filter.cmd[R300_TEX_VALUE_0+i]=0x0;
+ r300->hw.tex.unknown1.cmd[R300_TEX_VALUE_0+i]=0x0;
+ r300->hw.tex.size.cmd[R300_TEX_VALUE_0+i]=0x0;
+ r300->hw.tex.format.cmd[R300_TEX_VALUE_0+i]=0x0;
+ r300->hw.tex.offset.cmd[R300_TEX_VALUE_0+i]=0x0;
+ r300->hw.tex.unknown4.cmd[R300_TEX_VALUE_0+i]=0x0;
+ r300->hw.tex.unknown5.cmd[R300_TEX_VALUE_0+i]=0x0;
+ }
//END: TODO
-
+
r300->hw.all_dirty = GL_TRUE;
}