add tdfx DRI driver
This commit is contained in:
@@ -0,0 +1,64 @@
|
||||
REMOVE THIS FILE BEFORE MERGING WITH TRUNK
|
||||
------------------------------------------
|
||||
|
||||
OUTSTANDING BUGS
|
||||
|
||||
demos/reflect - reading back Z on Voodoo3, image offset to right
|
||||
Fixed in latest Glide.
|
||||
|
||||
Q3 - some polygons drawn as vertical strips, similar to bug that was
|
||||
seen in demos/fire. Voodoo3 only. May be related to glDepthMask
|
||||
or glColorMask.
|
||||
|
||||
book/fog - not fogging
|
||||
Fog in orthograph mode still not implemented. Checking with
|
||||
3dfx engineers for ideas.
|
||||
|
||||
Q3 demo crashes after changing display settings
|
||||
but the full Q3 game version seems OK.
|
||||
|
||||
|
||||
|
||||
MORE OUTSTANDING BUGS
|
||||
|
||||
private context was NULL! causing immediate failure of any glx prog. cant
|
||||
reproduce after restarting the X server. putting it down as halluc.
|
||||
|
||||
texture object image was NULL, causing segmentation failure. happens with
|
||||
prboom. ive put a check in tdfx_texstate.c but this isn't a fix.
|
||||
|
||||
prboom, wall textures near first chainsaw aren't bound properly. sideways
|
||||
movements causes the wall textures to move with you. prboom busted?
|
||||
|
||||
16bpp mode, quake3, windowed, q3dm1, floor under rocketlauncher bands. it
|
||||
looks like multitexturing gone wrong. i'll disable a tmu and test.
|
||||
|
||||
sof, polygons appear at wrong x,y,z positions, intermittent, have not yet
|
||||
found reliable way of reproducing. culling? sometimes polys disappear.
|
||||
|
||||
descent3 is all black in 16bpp mode - FIXED (palette problems)
|
||||
|
||||
smeared pixels in quake3 - FIXED (texture memory overlapped FB)
|
||||
|
||||
|
||||
|
||||
PERFORMANCE COMPARISON (Brian / Alan)
|
||||
|
||||
V3/16 is Voodoo3 in 16bpp on a P3/500
|
||||
V5/16 is Voodoo5 in 16bpp on a P3/600
|
||||
V5/32 is Voodoo5 in 32bpp on a P3/600
|
||||
V5A/16 is Voodoo5 in 16bpp on an Alpha AXP/600
|
||||
V5A/32 is Voodoo5 in 32bpp on an Alpha AXP/600
|
||||
|
||||
tdfx-2-1-branch tdfx-3-0-0-branch
|
||||
demo V3/16 V5/16 V5/32 V3/16 V5/16 V5/32 V5A/16 V5A/32
|
||||
------------------------------------------------------------------------
|
||||
gloss 257 183 174 320 308 177 313 167
|
||||
fire 42 39 52 41
|
||||
fire (no help) 98 80 50 106 113 73 124 80
|
||||
tunnel 61 50 70 58
|
||||
tunnel (no help) 167 142 57 138 152 113 171 122
|
||||
gears 663 554 540 881 1232 776 1484 830
|
||||
teapot 20 21 37 36
|
||||
teapot (no help) 22 14 14 24 30 30 43 42
|
||||
|
||||
@@ -0,0 +1,128 @@
|
||||
|
||||
# Mesa 3-D graphics library
|
||||
# Version: 5.0
|
||||
# Copyright (C) 1995-2002 Brian Paul
|
||||
|
||||
TOP = ../../../../..
|
||||
|
||||
default: linux-solo
|
||||
|
||||
SHARED_INCLUDES = $(INCLUDE_DIRS) -I. -I../common -Iserver
|
||||
MINIGLX_INCLUDES = -I$(TOP)/src/glx/mini
|
||||
|
||||
DEFINES += \
|
||||
-D_HAVE_SWRAST=1 \
|
||||
-D_HAVE_SWTNL=1 \
|
||||
-D_HAVE_SANITY=1 \
|
||||
-D_HAVE_CODEGEN=1 \
|
||||
-D_HAVE_LIGHTING=1 \
|
||||
-D_HAVE_TEXGEN=1 \
|
||||
-D_HAVE_USERCLIP=1 \
|
||||
-DGLX_DIRECT_RENDERING
|
||||
|
||||
# not yet
|
||||
# MINIGLX_SOURCES = server/tdfx_dri.c
|
||||
|
||||
DRIVER_SOURCES = tdfx_context.c \
|
||||
../common/mm.c \
|
||||
../common/utils.c \
|
||||
../common/texmem.c \
|
||||
../common/vblank.c \
|
||||
../common/xmlconfig.c \
|
||||
tdfx_dd.c \
|
||||
tdfx_lock.c \
|
||||
tdfx_pixels.c \
|
||||
tdfx_render.c \
|
||||
tdfx_screen.c \
|
||||
tdfx_span.c \
|
||||
tdfx_state.c \
|
||||
tdfx_tex.c \
|
||||
tdfx_texman.c \
|
||||
tdfx_texstate.c \
|
||||
tdfx_tris.c \
|
||||
tdfx_vb.c
|
||||
|
||||
INCLUDES = $(MINIGLX_INCLUDES) \
|
||||
$(SHARED_INCLUDES)
|
||||
|
||||
|
||||
C_SOURCES = $(DRIVER_SOURCES) \
|
||||
$(MINIGLX_SOURCES)
|
||||
|
||||
MESA_MODULES = $(TOP)/src/mesa/mesa.a
|
||||
|
||||
|
||||
ifeq ($(WINDOW_SYSTEM),dri)
|
||||
WINOBJ=$(MESABUILDDIR)/dri/dri.a
|
||||
WINLIB=
|
||||
else
|
||||
WINOBJ=
|
||||
WINLIB=-L$(MESA)/src/glx/mini
|
||||
endif
|
||||
|
||||
ASM_SOURCES =
|
||||
OBJECTS = $(C_SOURCES:.c=.o) \
|
||||
$(ASM_SOURCES:.S=.o)
|
||||
|
||||
$(SYMLINKS):
|
||||
mkdir -p server
|
||||
cd server
|
||||
rm -f $@ && ln -s ../../radeon/$@ $@
|
||||
|
||||
|
||||
### Include directories
|
||||
|
||||
INCLUDE_DIRS = \
|
||||
-I$(TOP)/include \
|
||||
-I$(TOP)/src/mesa \
|
||||
-I$(TOP)/src/mesa/main \
|
||||
-I$(TOP)/src/mesa/glapi \
|
||||
-I$(TOP)/src/mesa/math \
|
||||
-I$(TOP)/src/mesa/transform \
|
||||
-I$(TOP)/src/mesa/swrast \
|
||||
-I$(TOP)/src/mesa/swrast_setup
|
||||
|
||||
|
||||
##### RULES #####
|
||||
|
||||
.c.o:
|
||||
$(CC) -c $(SHARED_INCLUDES) $(MINIGLX_INCLUDES) $(CFLAGS) $(DEFINES) $< -o $@
|
||||
|
||||
.S.o:
|
||||
$(CC) -c $(SHARED_INCLUDES) $(MINIGLX_INCLUDES) $(CFLAGS) $(DEFINES) $< -o $@
|
||||
|
||||
|
||||
##### TARGETS #####
|
||||
|
||||
targets: depend tdfx_dri.so
|
||||
|
||||
tdfx_dri.so: $(SYMLINKS) $(OBJECTS) $(MESA_MODULES) $(WINOBJ) Makefile.X11
|
||||
rm -f $@ && gcc -o $@ -shared $(OBJECTS) $(MESA_MODULES) $(WINOBJ) $(WINLIB) -lc $(GL_LIB_DEPS)
|
||||
rm -f $(TOP)/lib/tdfx_dri.so && \
|
||||
install tdfx_dri.so $(TOP)/lib/tdfx_dri.so
|
||||
|
||||
$(TOP)/lib/tdfx_dri.so: tdfx_dri.so
|
||||
rm -f $(TOP)/lib/tdfx_dri.so && \
|
||||
install tdfx_dri.so $(TOP)/lib/tdfx_dri.so
|
||||
|
||||
# Run 'make -f Makefile.X11 dep' to update the dependencies if you change
|
||||
# what's included by any source file.
|
||||
depend: $(C_SOURCES) $(ASM_SOURCES)
|
||||
makedepend -fdepend -Y $(SHARED_INCLUDES) $(MINIGLX_INCLUDES) \
|
||||
$(C_SOURCES) $(ASM_SOURCES)
|
||||
|
||||
|
||||
# Emacs tags
|
||||
tags:
|
||||
etags `find . -name \*.[ch]` `find ../include`
|
||||
|
||||
|
||||
# Remove .o and backup files
|
||||
clean:
|
||||
-rm -f *.o */*.o *~ *.o *~ *.so server/*.o
|
||||
-rm -f $(SYMLINKS)
|
||||
|
||||
|
||||
include $(TOP)/Make-config
|
||||
|
||||
include depend
|
||||
@@ -0,0 +1,84 @@
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/X86/fx_3dnow_fastpath.S,v 1.2 2000/09/26 15:56:51 tsi Exp $ */
|
||||
|
||||
#include "../../X86/assyntax.h"
|
||||
|
||||
#define SETUP_RGBA 0x1
|
||||
#define SETUP_TMU0 0x2
|
||||
#define SETUP_TMU1 0x4
|
||||
|
||||
|
||||
/* Pack either rgba or texture into the remaining half of a 32 byte vertex.
|
||||
*/
|
||||
#define CLIP_R 24
|
||||
#define CLIP_G 16
|
||||
#define CLIP_B 20
|
||||
#define CLIP_A 28 /* defined inf fxdrv.h */
|
||||
|
||||
#define CLIP_S0 16
|
||||
#define CLIP_T0 20
|
||||
#define CLIP_S1 24
|
||||
#define CLIP_T1 28
|
||||
|
||||
#define SIZE 4
|
||||
#define TYPE (0)
|
||||
#define TAG(x) x
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
#define SIZE 8
|
||||
#define TYPE (SETUP_RGBA)
|
||||
#define TAG(x) x##_RGBA
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
#define SIZE 6
|
||||
#define TYPE (SETUP_TMU0)
|
||||
#define TAG(x) x##_TMU0
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
#define SIZE 8
|
||||
#define TYPE (SETUP_TMU0|SETUP_TMU1)
|
||||
#define TAG(x) x##_TMU0_TMU1
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
#undef CLIP_S1
|
||||
#undef CLIP_T1
|
||||
#define CLIP_S1 16
|
||||
#define CLIP_T1 20
|
||||
|
||||
#define SIZE 6
|
||||
#define TYPE (SETUP_TMU1)
|
||||
#define TAG(x) x##_TMU1
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
/* These three need to use a full 64 byte clip-space vertex.
|
||||
*/
|
||||
#undef CLIP_S0
|
||||
#undef CLIP_T0
|
||||
#undef CLIP_S1
|
||||
#undef CLIP_T1
|
||||
|
||||
#define CLIP_S0 32
|
||||
#define CLIP_T0 36
|
||||
#define CLIP_S1 40
|
||||
#define CLIP_T1 44
|
||||
|
||||
#define SIZE 10
|
||||
#define TYPE (SETUP_RGBA|SETUP_TMU0)
|
||||
#define TAG(x) x##_RGBA_TMU0
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
#define SIZE 12
|
||||
#define TYPE (SETUP_RGBA|SETUP_TMU0|SETUP_TMU1)
|
||||
#define TAG(x) x##_RGBA_TMU0_TMU1
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
#undef CLIP_S1
|
||||
#undef CLIP_T1
|
||||
#define CLIP_S1 32
|
||||
#define CLIP_T1 36
|
||||
|
||||
#define SIZE 10
|
||||
#define TYPE (SETUP_RGBA|SETUP_TMU1)
|
||||
#define TAG(x) x##_RGBA_TMU1
|
||||
#include "fx_3dnow_fasttmp.h"
|
||||
|
||||
|
||||
@@ -0,0 +1,314 @@
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/X86/fx_3dnow_fasttmp.h,v 1.2 2000/09/26 15:56:51 tsi Exp $ */
|
||||
|
||||
#if !defined(NASM_ASSEMBLER) && !defined(MASM_ASSEMBLER)
|
||||
#define TAGLLBL(a) TAG(.L##a)
|
||||
#else
|
||||
#define TAGLLBL(a) TAG(a)
|
||||
#endif
|
||||
|
||||
#if !GLIDE3
|
||||
|
||||
#define GR_VERTEX_X_OFFSET 0
|
||||
#define GR_VERTEX_Y_OFFSET 4
|
||||
#define GR_VERTEX_Z_OFFSET 8
|
||||
#define GR_VERTEX_R_OFFSET 12
|
||||
#define GR_VERTEX_G_OFFSET 16
|
||||
#define GR_VERTEX_B_OFFSET 20
|
||||
#define GR_VERTEX_OOZ_OFFSET 24
|
||||
#define GR_VERTEX_A_OFFSET 28
|
||||
#define GR_VERTEX_OOW_OFFSET 32
|
||||
|
||||
#else /* GLIDE3 */
|
||||
|
||||
#define GR_VERTEX_X_OFFSET 0
|
||||
#define GR_VERTEX_Y_OFFSET 4
|
||||
#define GR_VERTEX_OOZ_OFFSET 8
|
||||
#define GR_VERTEX_OOW_OFFSET 12
|
||||
#define GR_VERTEX_R_OFFSET 16
|
||||
#define GR_VERTEX_G_OFFSET 20
|
||||
#define GR_VERTEX_B_OFFSET 24
|
||||
#define GR_VERTEX_A_OFFSET 28
|
||||
#define GR_VERTEX_Z_OFFSET 32
|
||||
|
||||
#endif /* GLIDE3 */
|
||||
|
||||
#define GR_VERTEX_SOW_TMU0_OFFSET 36
|
||||
#define GR_VERTEX_TOW_TMU0_OFFSET 40
|
||||
#define GR_VERTEX_OOW_TMU0_OFFSET 44
|
||||
#define GR_VERTEX_SOW_TMU1_OFFSET 48
|
||||
#define GR_VERTEX_TOW_TMU1_OFFSET 52
|
||||
#define GR_VERTEX_OOW_TMU1_OFFSET 56
|
||||
|
||||
|
||||
|
||||
|
||||
/*#define MAT_SX 0 /* accessed by REGIND !! */
|
||||
#define MAT_SY 20
|
||||
#define MAT_SZ 40
|
||||
#define MAT_TX 48
|
||||
#define MAT_TY 52
|
||||
#define MAT_TZ 56
|
||||
|
||||
|
||||
|
||||
|
||||
/* Do viewport map, device scale and perspective projection.
|
||||
*
|
||||
* void project_verts( GLfloat *first,
|
||||
* GLfloat *last,
|
||||
* const GLfloat *m,
|
||||
* GLuint stride )
|
||||
*
|
||||
*
|
||||
* Rearrange fxVertices to look like grVertices.
|
||||
*/
|
||||
|
||||
GLOBL GLNAME( TAG(fx_3dnow_project_vertices) )
|
||||
GLNAME( TAG(fx_3dnow_project_vertices) ):
|
||||
|
||||
PUSH_L ( EBP )
|
||||
|
||||
MOV_L ( REGOFF(8, ESP), ECX ) /* first_vert */
|
||||
MOV_L ( REGOFF(12, ESP), EDX ) /* last_vert */
|
||||
|
||||
CMP_L ( ECX, EDX )
|
||||
JE ( TAGLLBL(FXPV_end) )
|
||||
|
||||
FEMMS
|
||||
|
||||
PREFETCH ( REGIND(ECX) ) /* fetch the first vertex */
|
||||
|
||||
MOV_L ( REGOFF(16, ESP), EBP ) /* matrix */
|
||||
MOV_L ( REGOFF(20, ESP), EAX ) /* stride */
|
||||
|
||||
MOVD ( REGOFF(MAT_TX, EBP), MM6 ) /* | tx */
|
||||
PUNPCKLDQ ( REGOFF(MAT_TY, EBP), MM6 ) /* ty | tx */
|
||||
|
||||
#if !defined(FX_V2)
|
||||
MOV_L ( CONST(0x49400000), REGOFF(-8, ESP) ) /* snapper */
|
||||
MOV_L ( CONST(0x49400000), REGOFF(-4, ESP) ) /* snapper */
|
||||
#endif
|
||||
|
||||
MOVQ ( REGOFF(-8, ESP), MM4 ) /* snapper | snapper */
|
||||
PFADD ( MM4, MM6 ) /* ty+snapper | tx+snapper */
|
||||
|
||||
MOVD ( REGIND(EBP), MM5 )
|
||||
PUNPCKLDQ ( REGOFF(MAT_SY, EBP), MM5 ) /* vsy | vsx */
|
||||
|
||||
MOVD ( REGOFF(MAT_SZ, EBP), MM1 ) /* | vsz */
|
||||
|
||||
|
||||
ALIGNTEXT32
|
||||
TAGLLBL(FXPV_loop_start):
|
||||
|
||||
PREFETCH ( REGOFF(64, ECX) ) /* fetch the next-ish vertex */
|
||||
|
||||
|
||||
MOVD ( REGOFF(12, ECX), MM0 ) /* | f[3] */
|
||||
PFRCP ( MM0, MM0 ) /* oow = 1/f[3] */
|
||||
|
||||
MOVD ( REGOFF(12, ECX), MM7 ) /* | f[3] */
|
||||
PFRCPIT1 ( MM0, MM7 )
|
||||
PFRCPIT2 ( MM0, MM7 ) /* oow | oow */
|
||||
|
||||
PUNPCKLDQ ( MM7, MM7 )
|
||||
|
||||
|
||||
#if (TYPE & SETUP_RGBA)
|
||||
MOVD ( REGOFF(CLIP_R, ECX ), MM0 ) /* f[RCOORD] = f[CLIP_R]; */
|
||||
MOVD ( MM0, REGOFF(GR_VERTEX_R_OFFSET, ECX) )
|
||||
#endif
|
||||
|
||||
#if (TYPE & SETUP_TMU1)
|
||||
MOVQ ( REGOFF(CLIP_S1, ECX), MM0 ) /* f[S1COORD] = f[CLIP_S1] * oow */
|
||||
PFMUL ( MM7, MM0 ) /* f[T1COORD] = f[CLIP_T1] * oow */
|
||||
MOVQ ( MM0, REGOFF(GR_VERTEX_SOW_TMU1_OFFSET, ECX) )
|
||||
#endif
|
||||
|
||||
|
||||
#if (TYPE & SETUP_TMU0)
|
||||
MOVQ ( REGOFF(CLIP_S0, ECX), MM0 ) /* f[S0COORD] = f[CLIP_S0] * oow */
|
||||
PFMUL ( MM7, MM0 ) /* f[T0COORD] = f[CLIP_T0] * oow */
|
||||
MOVQ ( MM0, REGOFF(GR_VERTEX_SOW_TMU0_OFFSET, ECX) )
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/* DO_SETUP_XYZ */
|
||||
|
||||
MOVQ ( REGIND(ECX), MM2 ) /* f[1] | f[0] */
|
||||
PFMUL ( MM7, MM2 ) /* f[1] * oow | f[0] * oow */
|
||||
|
||||
MOVD ( REGOFF(8, ECX), MM3 ) /* | f[2] */
|
||||
PFMUL ( MM7, MM3 ) /* | f[2] * oow */
|
||||
|
||||
MOVD ( REGOFF(MAT_TZ, EBP), MM0 ) /* | vtz */
|
||||
PFMUL ( MM1, MM3 ) /* | f[2] *= vsz */
|
||||
|
||||
PFADD ( MM0, MM3 ) /* | f[2] += vtz */
|
||||
PFMUL ( MM5, MM2 ) /* f[1] *= vsy | f[0] *= vsx */
|
||||
|
||||
PFADD ( MM6, MM2 ) /* f[1] += vty | f[0] += vtx */
|
||||
|
||||
#if !defined(FX_V2)
|
||||
PFSUB ( MM4, MM2 ) /* f[0,1] -= snapper */
|
||||
#endif
|
||||
|
||||
MOVQ ( MM2, REGOFF(GR_VERTEX_X_OFFSET, ECX) )
|
||||
MOVD ( MM3, REGOFF(GR_VERTEX_OOZ_OFFSET, ECX) )
|
||||
|
||||
|
||||
/* end of DO_SETUP_XYZ */
|
||||
|
||||
MOVD ( MM7, REGOFF(GR_VERTEX_OOW_OFFSET, ECX) ) /* f[OOWCOORD] = oow */
|
||||
ADD_L ( EAX, ECX ) /* f += stride */
|
||||
|
||||
CMP_L ( ECX, EDX ) /* stall??? */
|
||||
JA ( TAGLLBL(FXPV_loop_start) )
|
||||
|
||||
TAGLLBL(FXPV_end):
|
||||
FEMMS
|
||||
POP_L ( EBP )
|
||||
RET
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/* void project_verts( GLfloat *first,
|
||||
* GLfloat *last,
|
||||
* const GLfloat *m,
|
||||
* GLuint stride,
|
||||
* const GLubyte *mask )
|
||||
*
|
||||
*/
|
||||
|
||||
GLOBL GLNAME( TAG(fx_3dnow_project_clipped_vertices) )
|
||||
GLNAME( TAG(fx_3dnow_project_clipped_vertices) ):
|
||||
|
||||
PUSH_L ( EBP )
|
||||
|
||||
MOV_L ( REGOFF(8, ESP), ECX ) /* first FXDRIVER(VB)->verts*/
|
||||
MOV_L ( REGOFF(12, ESP), EDX ) /* last FXDRIVER(VB)->last_vert */
|
||||
|
||||
FEMMS
|
||||
|
||||
PUSH_L ( EDI )
|
||||
PUSH_L ( ESI )
|
||||
|
||||
PREFETCH ( REGIND(ECX) ) /* fetch the first vertex */
|
||||
|
||||
MOV_L ( REGOFF(24, ESP), EBP ) /* mat ctx->Viewport.WindowMap.M */
|
||||
MOV_L ( REGOFF(28, ESP), EAX ) /* stride */
|
||||
MOV_L ( REGOFF(32, ESP), ESI ) /* VB->ClipMask */
|
||||
|
||||
MOVD ( REGOFF(MAT_TX, EBP), MM6 ) /* | tx */
|
||||
PUNPCKLDQ ( REGOFF(MAT_TY, EBP), MM6 ) /* ty | tx */
|
||||
|
||||
#if !defined(FX_V2)
|
||||
MOV_L ( CONST(0x49400000), REGOFF(-8, ESP) ) /* snapper */
|
||||
MOV_L ( CONST(0x49400000), REGOFF(-4, ESP) ) /* snapper */
|
||||
#endif
|
||||
|
||||
MOVQ ( REGOFF(-8, ESP), MM4 ) /* snapper | snapper */
|
||||
PFADD ( MM4, MM6 ) /* ty+snapper | tx+snapper */
|
||||
|
||||
MOVD ( REGIND(EBP), MM5 )
|
||||
PUNPCKLDQ ( REGOFF(MAT_SY, EBP), MM5 ) /* vsy | vsx */
|
||||
|
||||
MOVD ( REGOFF(MAT_SZ, EBP), MM1 ) /* | vsz */
|
||||
|
||||
|
||||
|
||||
ALIGNTEXT32
|
||||
TAGLLBL(FXPCV_loop_start):
|
||||
|
||||
PREFETCH ( REGOFF(64, ECX) ) /* fetch the next-ish vertex */
|
||||
|
||||
CMP_B ( CONST(0), REGIND(ESI) )
|
||||
JNE ( TAGLLBL(FXPCV_skip) )
|
||||
|
||||
MOVD ( REGOFF(12, ECX), MM0) /* | f[3] */
|
||||
PFRCP ( MM0, MM0 ) /* oow = 1/f[3] */
|
||||
|
||||
MOVD ( REGOFF(12, ECX), MM7) /* | f[3] */
|
||||
PFRCPIT1 ( MM0, MM7 )
|
||||
PFRCPIT2 ( MM0, MM7 ) /* oow | oow */
|
||||
|
||||
PUNPCKLDQ ( MM7, MM7 )
|
||||
|
||||
|
||||
#if (TYPE & SETUP_RGBA)
|
||||
MOVD ( REGOFF(CLIP_R, ECX ), MM0 ) /* f[RCOORD] = f[CLIP_R]; */
|
||||
MOVD ( MM0, REGOFF(GR_VERTEX_R_OFFSET, ECX) )
|
||||
#endif
|
||||
|
||||
#if (TYPE & SETUP_TMU1)
|
||||
MOVQ ( REGOFF(CLIP_S1, ECX), MM0 ) /* f[S1COORD] = f[CLIP_S1] * oow */
|
||||
PFMUL ( MM7, MM0 ) /* f[T1COORD] = f[CLIP_T1] * oow */
|
||||
MOVQ ( MM0, REGOFF(GR_VERTEX_SOW_TMU1_OFFSET, ECX) )
|
||||
#endif
|
||||
|
||||
|
||||
#if (TYPE & SETUP_TMU0)
|
||||
MOVQ ( REGOFF(CLIP_S0, ECX), MM0 ) /* f[S0COORD] = f[CLIP_S0] * oow */
|
||||
PFMUL ( MM7, MM0 ) /* f[T0COORD] = f[CLIP_T0] * oow */
|
||||
MOVQ ( MM0, REGOFF(GR_VERTEX_SOW_TMU0_OFFSET, ECX) )
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
/* DO_SETUP_XYZ */
|
||||
|
||||
MOVQ ( REGIND(ECX), MM2 ) /* f[1] | f[0] */
|
||||
PFMUL ( MM7, MM2 ) /* f[1] * oow | f[0] * oow */
|
||||
|
||||
MOVD ( REGOFF(8, ECX), MM3 ) /* | f[2] */
|
||||
PFMUL ( MM7, MM3 ) /* | f[2] * oow */
|
||||
|
||||
MOVD ( REGOFF(MAT_TZ, EBP), MM0 ) /* | vtz */
|
||||
PFMUL ( MM1, MM3 ) /* | f[2] *= vsz */
|
||||
|
||||
PFADD ( MM0, MM3 ) /* | f[2] += vtz */
|
||||
PFMUL ( MM5, MM2 ) /* f[1] *= vsy | f[0] *= vsx */
|
||||
|
||||
PFADD ( MM6, MM2 ) /* f[1] += vty | f[0] += vtx */
|
||||
|
||||
#if !defined(FX_V2)
|
||||
PFSUB ( MM4, MM2 ) /* f[0,1] -= snapper */
|
||||
#endif
|
||||
|
||||
MOVQ ( MM2, REGOFF(GR_VERTEX_X_OFFSET, ECX) )
|
||||
MOVD ( MM3, REGOFF(GR_VERTEX_OOZ_OFFSET, ECX) )
|
||||
|
||||
|
||||
/* end of DO_SETUP_XYZ */
|
||||
|
||||
MOVD ( MM7, REGOFF(GR_VERTEX_OOW_OFFSET, ECX) ) /* f[OOWCOORD] = oow */
|
||||
|
||||
TAGLLBL(FXPCV_skip):
|
||||
ADD_L ( EAX, ECX ) /* f += stride */
|
||||
|
||||
INC_L ( ESI ) /* next ClipMask */
|
||||
CMP_L ( ECX, EDX )
|
||||
JA ( TAGLLBL(FXPCV_loop_start) )
|
||||
|
||||
POP_L ( ESI )
|
||||
POP_L ( EDI )
|
||||
|
||||
TAGLLBL(FXPCV_end):
|
||||
FEMMS
|
||||
POP_L ( EBP )
|
||||
RET
|
||||
|
||||
|
||||
|
||||
#undef TYPE
|
||||
#undef TAG
|
||||
#undef SIZE
|
||||
|
||||
@@ -0,0 +1,63 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/dri_glide.h,v 1.1 2001/03/21 16:14:26 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __DRI_GLIDE_H__
|
||||
#define __DRI_GLIDE_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
#include <glide.h>
|
||||
#include "dri_mesaint.h"
|
||||
|
||||
/*
|
||||
* This is the private interface between Glide and the DRI.
|
||||
*/
|
||||
extern void grDRIOpen( char *pFB, char *pRegs, int deviceID,
|
||||
int width, int height,
|
||||
int mem, int cpp, int stride,
|
||||
int fifoOffset, int fifoSize,
|
||||
int fbOffset, int backOffset, int depthOffset,
|
||||
int textureOffset, int textureSize,
|
||||
volatile int *fifoPtr, volatile int *fifoRead );
|
||||
extern void grDRIPosition( int x, int y, int w, int h,
|
||||
int numClip, XF86DRIClipRectPtr pClip );
|
||||
extern void grDRILostContext( void );
|
||||
extern void grDRIImportFifo( int fifoPtr, int fifoRead );
|
||||
extern void grDRIInvalidateAll( void );
|
||||
extern void grDRIResetSAREA( void );
|
||||
extern void grDRIBufferSwap( FxU32 swapInterval );
|
||||
#endif
|
||||
#endif
|
||||
@@ -0,0 +1,897 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_context.c,v 1.12 2003/05/08 09:25:35 herrb Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include <dlfcn.h>
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_dd.h"
|
||||
#include "tdfx_state.h"
|
||||
#include "tdfx_vb.h"
|
||||
#include "tdfx_tris.h"
|
||||
#include "tdfx_render.h"
|
||||
#include "tdfx_span.h"
|
||||
#include "tdfx_texman.h"
|
||||
#include "extensions.h"
|
||||
|
||||
|
||||
#include "swrast/swrast.h"
|
||||
#include "swrast_setup/swrast_setup.h"
|
||||
#include "array_cache/acache.h"
|
||||
|
||||
#include "tnl/tnl.h"
|
||||
#include "tnl/t_pipeline.h"
|
||||
|
||||
|
||||
/*
|
||||
* Enable/Disable the extensions for this context.
|
||||
*/
|
||||
static void tdfxDDInitExtensions( GLcontext *ctx )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
|
||||
_mesa_enable_extension( ctx, "GL_HP_occlusion_test" );
|
||||
_mesa_enable_extension( ctx, "GL_EXT_paletted_texture" );
|
||||
_mesa_enable_extension( ctx, "GL_EXT_texture_lod_bias" );
|
||||
|
||||
if ( fxMesa->haveTwoTMUs ) {
|
||||
_mesa_enable_extension( ctx, "GL_EXT_texture_env_add" );
|
||||
_mesa_enable_extension( ctx, "GL_ARB_multitexture" );
|
||||
}
|
||||
|
||||
if ( TDFX_IS_NAPALM( fxMesa ) ) {
|
||||
#if 0
|
||||
_mesa_enable_extension( ctx, "GL_ARB_texture_compression" );
|
||||
_mesa_enable_extension( ctx, "GL_3DFX_texture_compression_FXT1" );
|
||||
#endif
|
||||
_mesa_enable_extension( ctx, "GL_EXT_texture_env_combine" );
|
||||
}
|
||||
|
||||
#if 0
|
||||
_mesa_enable_extension( ctx, "GL_ARB_texture_cube_map");
|
||||
_mesa_enable_extension( ctx, "GL_NV_texture_rectangle");
|
||||
#endif
|
||||
|
||||
if (fxMesa->haveHwStencil) {
|
||||
_mesa_enable_extension( ctx, "GL_EXT_stencil_wrap" );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
static const struct gl_pipeline_stage *tdfx_pipeline[] = {
|
||||
&_tnl_vertex_transform_stage,
|
||||
&_tnl_normal_transform_stage,
|
||||
&_tnl_lighting_stage, /* REMOVE: fog coord stage */
|
||||
&_tnl_texgen_stage,
|
||||
&_tnl_texture_transform_stage,
|
||||
/* REMOVE: point attenuation stage */
|
||||
&_tnl_render_stage,
|
||||
0,
|
||||
};
|
||||
|
||||
|
||||
GLboolean tdfxCreateContext( const __GLcontextModes *mesaVis,
|
||||
__DRIcontextPrivate *driContextPriv,
|
||||
void *sharedContextPrivate )
|
||||
{
|
||||
tdfxContextPtr fxMesa;
|
||||
GLcontext *ctx, *shareCtx;
|
||||
__DRIscreenPrivate *sPriv = driContextPriv->driScreenPriv;
|
||||
tdfxScreenPrivate *fxScreen = (tdfxScreenPrivate *) sPriv->private;
|
||||
TDFXSAREAPriv *saPriv = (TDFXSAREAPriv *) ((char *) sPriv->pSAREA +
|
||||
sizeof(XF86DRISAREARec));
|
||||
|
||||
/* Allocate tdfx context */
|
||||
fxMesa = (tdfxContextPtr) CALLOC( sizeof(tdfxContextRec) );
|
||||
if (!fxMesa)
|
||||
return GL_FALSE;
|
||||
|
||||
/* Allocate the Mesa context */
|
||||
if (sharedContextPrivate)
|
||||
shareCtx = ((tdfxContextPtr) sharedContextPrivate)->glCtx;
|
||||
else
|
||||
shareCtx = NULL;
|
||||
|
||||
fxMesa->glCtx = _mesa_create_context(mesaVis, shareCtx, (void *) fxMesa, GL_TRUE);
|
||||
if (!fxMesa->glCtx) {
|
||||
FREE(fxMesa);
|
||||
return GL_FALSE;
|
||||
}
|
||||
driContextPriv->driverPrivate = fxMesa;
|
||||
|
||||
/* Mirror some important DRI state
|
||||
*/
|
||||
fxMesa->hHWContext = driContextPriv->hHWContext;
|
||||
fxMesa->driHwLock = &sPriv->pSAREA->lock;
|
||||
fxMesa->driFd = sPriv->fd;
|
||||
|
||||
fxMesa->driScreen = sPriv;
|
||||
fxMesa->driContext = driContextPriv;
|
||||
fxMesa->fxScreen = fxScreen;
|
||||
fxMesa->sarea = saPriv;
|
||||
|
||||
fxMesa->haveHwStencil = ( TDFX_IS_NAPALM( fxMesa ) &&
|
||||
mesaVis->stencilBits &&
|
||||
mesaVis->depthBits == 24 );
|
||||
|
||||
fxMesa->screen_width = fxScreen->width;
|
||||
fxMesa->screen_height = fxScreen->height;
|
||||
|
||||
fxMesa->new_gl_state = ~0;
|
||||
fxMesa->new_state = ~0;
|
||||
fxMesa->dirty = ~0;
|
||||
|
||||
/* NOTE: This must be here before any Glide calls! */
|
||||
if (!tdfxInitGlide( fxMesa )) {
|
||||
FREE(fxMesa);
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
fxMesa->Glide.grDRIOpen( (char*) sPriv->pFB, fxScreen->regs.map, fxScreen->deviceID,
|
||||
fxScreen->width, fxScreen->height, fxScreen->mem, fxScreen->cpp,
|
||||
fxScreen->stride, fxScreen->fifoOffset, fxScreen->fifoSize,
|
||||
fxScreen->fbOffset, fxScreen->backOffset, fxScreen->depthOffset,
|
||||
fxScreen->textureOffset, fxScreen->textureSize, &saPriv->fifoPtr,
|
||||
&saPriv->fifoRead );
|
||||
|
||||
if ( getenv( "FX_GLIDE_SWAPINTERVAL" ) ) {
|
||||
fxMesa->Glide.SwapInterval = atoi( getenv( "FX_GLIDE_SWAPINTERVAL" ) );
|
||||
} else {
|
||||
fxMesa->Glide.SwapInterval = 0;
|
||||
}
|
||||
if ( getenv( "FX_MAX_PENDING_SWAPS" ) ) {
|
||||
fxMesa->Glide.MaxPendingSwaps = atoi( getenv( "FX_MAX_PENDING_SWAPS" ) );
|
||||
} else {
|
||||
fxMesa->Glide.MaxPendingSwaps = 2;
|
||||
}
|
||||
|
||||
fxMesa->Glide.Initialized = GL_FALSE;
|
||||
fxMesa->Glide.Board = 0;
|
||||
|
||||
|
||||
if (getenv("FX_EMULATE_SINGLE_TMU")) {
|
||||
fxMesa->haveTwoTMUs = GL_FALSE;
|
||||
}
|
||||
else {
|
||||
if ( TDFX_IS_BANSHEE( fxMesa ) ) {
|
||||
fxMesa->haveTwoTMUs = GL_FALSE;
|
||||
} else {
|
||||
fxMesa->haveTwoTMUs = GL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
fxMesa->stats.swapBuffer = 0;
|
||||
fxMesa->stats.reqTexUpload = 0;
|
||||
fxMesa->stats.texUpload = 0;
|
||||
fxMesa->stats.memTexUpload = 0;
|
||||
|
||||
fxMesa->tmuSrc = TDFX_TMU_NONE;
|
||||
|
||||
ctx = fxMesa->glCtx;
|
||||
if ( TDFX_IS_NAPALM( fxMesa ) ) {
|
||||
ctx->Const.MaxTextureLevels = 12;
|
||||
} else {
|
||||
ctx->Const.MaxTextureLevels = 9;
|
||||
}
|
||||
ctx->Const.MaxTextureUnits = TDFX_IS_BANSHEE( fxMesa ) ? 1 : 2;
|
||||
|
||||
/* No wide points.
|
||||
*/
|
||||
ctx->Const.MinPointSize = 1.0;
|
||||
ctx->Const.MinPointSizeAA = 1.0;
|
||||
ctx->Const.MaxPointSize = 1.0;
|
||||
ctx->Const.MaxPointSizeAA = 1.0;
|
||||
|
||||
/* Disable wide lines as we can't antialias them correctly in
|
||||
* hardware.
|
||||
*/
|
||||
ctx->Const.MinLineWidth = 1.0;
|
||||
ctx->Const.MinLineWidthAA = 1.0;
|
||||
ctx->Const.MaxLineWidth = 1.0;
|
||||
ctx->Const.MaxLineWidthAA = 1.0;
|
||||
ctx->Const.LineWidthGranularity = 1.0;
|
||||
|
||||
/* Initialize the software rasterizer and helper modules.
|
||||
*/
|
||||
_swrast_CreateContext( ctx );
|
||||
_ac_CreateContext( ctx );
|
||||
_tnl_CreateContext( ctx );
|
||||
_swsetup_CreateContext( ctx );
|
||||
|
||||
/* Install the customized pipeline:
|
||||
*/
|
||||
_tnl_destroy_pipeline( ctx );
|
||||
_tnl_install_pipeline( ctx, tdfx_pipeline );
|
||||
|
||||
/* Configure swrast to match hardware characteristics:
|
||||
*/
|
||||
_swrast_allow_pixel_fog( ctx, GL_TRUE );
|
||||
_swrast_allow_vertex_fog( ctx, GL_FALSE );
|
||||
|
||||
tdfxDDInitExtensions( ctx );
|
||||
tdfxDDInitDriverFuncs( ctx );
|
||||
tdfxDDInitStateFuncs( ctx );
|
||||
tdfxDDInitRenderFuncs( ctx );
|
||||
tdfxDDInitSpanFuncs( ctx );
|
||||
tdfxDDInitTriFuncs( ctx );
|
||||
tdfxInitVB( ctx );
|
||||
tdfxInitState( fxMesa );
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
static GLboolean tdfxInitVertexFormats( tdfxContextPtr fxMesa )
|
||||
{
|
||||
FxI32 result;
|
||||
int i;
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
|
||||
fxMesa->Glide.grGet( GR_GLIDE_VERTEXLAYOUT_SIZE, sizeof(FxI32), &result );
|
||||
for ( i = 0 ; i < TDFX_NUM_LAYOUTS ; i++ ) {
|
||||
fxMesa->layout[i] = MALLOC( result );
|
||||
if ( !fxMesa->layout[i] ) {
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
return GL_FALSE;
|
||||
}
|
||||
}
|
||||
|
||||
/* Tiny vertex format - 16 bytes.
|
||||
*/
|
||||
fxMesa->Glide.grReset( GR_VERTEX_PARAMETER );
|
||||
fxMesa->Glide.grCoordinateSpace( GR_WINDOW_COORDS );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_XY, TDFX_XY_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Z, TDFX_Z_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_PARGB, TDFX_Q_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grGlideGetVertexLayout( fxMesa->layout[TDFX_LAYOUT_TINY] );
|
||||
|
||||
/* Non textured vertex format - 24 bytes (Need w for table fog)
|
||||
*/
|
||||
fxMesa->Glide.grReset( GR_VERTEX_PARAMETER );
|
||||
fxMesa->Glide.grCoordinateSpace( GR_WINDOW_COORDS );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_XY, TDFX_XY_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Z, TDFX_Z_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Q, TDFX_Q_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_PARGB, TDFX_ARGB_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grGlideGetVertexLayout( fxMesa->layout[TDFX_LAYOUT_NOTEX] );
|
||||
|
||||
/* Single textured vertex format - 32 bytes.
|
||||
*/
|
||||
fxMesa->Glide.grReset( GR_VERTEX_PARAMETER );
|
||||
fxMesa->Glide.grCoordinateSpace( GR_WINDOW_COORDS );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_XY, TDFX_XY_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Z, TDFX_Z_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Q, TDFX_Q_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_PARGB, TDFX_ARGB_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_ST0, TDFX_ST0_OFFSET, GR_PARAM_ENABLE );
|
||||
/*grVertexLayout( GR_PARAM_FOG_EXT, TDFX_FOG_OFFSET, GR_PARAM_ENABLE );*/
|
||||
fxMesa->Glide.grGlideGetVertexLayout( fxMesa->layout[TDFX_LAYOUT_SINGLE] );
|
||||
|
||||
/* Multitextured vertex format - 40 bytes.
|
||||
*/
|
||||
fxMesa->Glide.grReset( GR_VERTEX_PARAMETER );
|
||||
fxMesa->Glide.grCoordinateSpace( GR_WINDOW_COORDS );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_XY, TDFX_XY_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Z, TDFX_Z_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Q, TDFX_Q_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_PARGB, TDFX_ARGB_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_ST0, TDFX_ST0_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_ST1, TDFX_ST1_OFFSET, GR_PARAM_ENABLE );
|
||||
/*fxMesa->Glide.grVertexLayout( GR_PARAM_FOG_EXT, TDFX_FOG_OFFSET, GR_PARAM_ENABLE );*/
|
||||
fxMesa->Glide.grGlideGetVertexLayout( fxMesa->layout[TDFX_LAYOUT_MULTI] );
|
||||
|
||||
/* Projected texture vertex format - 48 bytes.
|
||||
*/
|
||||
fxMesa->Glide.grReset( GR_VERTEX_PARAMETER );
|
||||
fxMesa->Glide.grCoordinateSpace( GR_WINDOW_COORDS );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_XY, TDFX_XY_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Z, TDFX_Z_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Q, TDFX_Q_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_PARGB, TDFX_ARGB_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_ST0, TDFX_ST0_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Q0, TDFX_Q0_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_ST1, TDFX_ST1_OFFSET, GR_PARAM_ENABLE );
|
||||
fxMesa->Glide.grVertexLayout( GR_PARAM_Q1, TDFX_Q1_OFFSET, GR_PARAM_ENABLE );
|
||||
/*fxMesa->Glide.grVertexLayout( GR_PARAM_FOG_EXT, TDFX_FOG_OFFSET, GR_PARAM_ENABLE );*/
|
||||
fxMesa->Glide.grGlideGetVertexLayout( fxMesa->layout[TDFX_LAYOUT_PROJECT] );
|
||||
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Initialize the state in an tdfxContextPtr struct.
|
||||
*/
|
||||
static GLboolean
|
||||
tdfxInitContext( __DRIdrawablePrivate *driDrawPriv, tdfxContextPtr fxMesa )
|
||||
{
|
||||
/* KW: Would be nice to make one of these a member of the other.
|
||||
*/
|
||||
FxI32 result[2];
|
||||
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_DRI ) {
|
||||
fprintf( stderr, "%s( %p )\n", __FUNCTION__, fxMesa );
|
||||
}
|
||||
|
||||
#if DEBUG_LOCKING
|
||||
fprintf(stderr, "Debug locking enabled\n");
|
||||
#endif
|
||||
|
||||
if ( fxMesa->Glide.Initialized )
|
||||
return GL_TRUE;
|
||||
|
||||
fxMesa->width = driDrawPriv->w;
|
||||
fxMesa->height = driDrawPriv->h;
|
||||
|
||||
/* We have to use a light lock here, because we can't do any glide
|
||||
* operations yet. No use of FX_* functions in this function.
|
||||
*/
|
||||
DRM_LIGHT_LOCK( fxMesa->driFd, fxMesa->driHwLock, fxMesa->hHWContext );
|
||||
|
||||
fxMesa->Glide.grGlideInit();
|
||||
fxMesa->Glide.grSstSelect( fxMesa->Glide.Board );
|
||||
|
||||
fxMesa->Glide.Context = fxMesa->Glide.grSstWinOpen( (FxU32) -1,
|
||||
GR_RESOLUTION_NONE,
|
||||
GR_REFRESH_NONE,
|
||||
fxMesa->Glide.ColorFormat,
|
||||
fxMesa->Glide.Origin,
|
||||
2, 1 );
|
||||
|
||||
fxMesa->Glide.grDRIResetSAREA();
|
||||
|
||||
DRM_UNLOCK( fxMesa->driFd, fxMesa->driHwLock, fxMesa->hHWContext );
|
||||
|
||||
if ( !fxMesa->Glide.Context )
|
||||
return GL_FALSE;
|
||||
|
||||
|
||||
/* Perform the Glide-dependant part of the context initialization.
|
||||
*/
|
||||
FX_grColorMaskv( fxMesa->glCtx, true4 );
|
||||
|
||||
tdfxTMInit( fxMesa );
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
|
||||
if ( fxMesa->glCtx->Visual.depthBits > 0 ) {
|
||||
fxMesa->Glide.grDepthBufferMode(GR_DEPTHBUFFER_ZBUFFER);
|
||||
} else {
|
||||
fxMesa->Glide.grDepthBufferMode(GR_DEPTHBUFFER_DISABLE);
|
||||
}
|
||||
|
||||
fxMesa->Glide.grLfbWriteColorFormat( GR_COLORFORMAT_ABGR );
|
||||
|
||||
fxMesa->Glide.grGet( GR_TEXTURE_ALIGN, sizeof(FxI32), result );
|
||||
fxMesa->Glide.TextureAlign = result[0];
|
||||
|
||||
fxMesa->Glide.State = NULL;
|
||||
fxMesa->Glide.grGet( GR_GLIDE_STATE_SIZE, sizeof(FxI32), result );
|
||||
fxMesa->Glide.State = MALLOC( result[0] );
|
||||
|
||||
fxMesa->Fog.Table = NULL;
|
||||
fxMesa->Glide.grGet( GR_FOG_TABLE_ENTRIES, sizeof(FxI32), result );
|
||||
fxMesa->Fog.Table = MALLOC( result[0] * sizeof(GrFog_t) );
|
||||
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
|
||||
if ( !fxMesa->Glide.State || !fxMesa->Fog.Table ) {
|
||||
if ( fxMesa->Glide.State )
|
||||
FREE( fxMesa->Glide.State );
|
||||
if ( fxMesa->Fog.Table )
|
||||
FREE( fxMesa->Fog.Table );
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
if ( !tdfxInitVertexFormats( fxMesa ) ) {
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
|
||||
fxMesa->Glide.grGlideGetState( fxMesa->Glide.State );
|
||||
|
||||
if ( getenv( "FX_GLIDE_INFO" ) ) {
|
||||
printf( "GR_RENDERER = %s\n", (char *) fxMesa->Glide.grGetString( GR_RENDERER ) );
|
||||
printf( "GR_VERSION = %s\n", (char *) fxMesa->Glide.grGetString( GR_VERSION ) );
|
||||
printf( "GR_VENDOR = %s\n", (char *) fxMesa->Glide.grGetString( GR_VENDOR ) );
|
||||
printf( "GR_HARDWARE = %s\n", (char *) fxMesa->Glide.grGetString( GR_HARDWARE ) );
|
||||
printf( "GR_EXTENSION = %s\n", (char *) fxMesa->Glide.grGetString( GR_EXTENSION ) );
|
||||
}
|
||||
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
|
||||
{
|
||||
const char *debug = getenv("LIBGL_DEBUG");
|
||||
if (debug && strstr(debug, "fallbacks")) {
|
||||
fxMesa->debugFallbacks = GL_TRUE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
fxMesa->numClipRects = 0;
|
||||
fxMesa->pClipRects = NULL;
|
||||
fxMesa->scissoredClipRects = GL_FALSE;
|
||||
|
||||
fxMesa->Glide.Initialized = GL_TRUE;
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
tdfxDestroyContext( __DRIcontextPrivate *driContextPriv )
|
||||
{
|
||||
tdfxContextPtr fxMesa = (tdfxContextPtr) driContextPriv->driverPrivate;
|
||||
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_DRI ) {
|
||||
fprintf( stderr, "%s( %p )\n", __FUNCTION__, fxMesa );
|
||||
}
|
||||
|
||||
if ( fxMesa ) {
|
||||
if (fxMesa->glCtx->Shared->RefCount == 1 && fxMesa->driDrawable) {
|
||||
/* This share group is about to go away, free our private
|
||||
* texture object data.
|
||||
*/
|
||||
struct gl_texture_object *tObj;
|
||||
tObj = fxMesa->glCtx->Shared->TexObjectList;
|
||||
while (tObj) {
|
||||
tdfxTMFreeTexture(fxMesa, tObj);
|
||||
tObj = tObj->Next;
|
||||
}
|
||||
}
|
||||
|
||||
tdfxTMClose(fxMesa); /* free texture memory */
|
||||
|
||||
_swsetup_DestroyContext( fxMesa->glCtx );
|
||||
_tnl_DestroyContext( fxMesa->glCtx );
|
||||
_ac_DestroyContext( fxMesa->glCtx );
|
||||
_swrast_DestroyContext( fxMesa->glCtx );
|
||||
|
||||
tdfxFreeVB( fxMesa->glCtx );
|
||||
|
||||
/* Free Mesa context */
|
||||
fxMesa->glCtx->DriverCtx = NULL;
|
||||
_mesa_destroy_context(fxMesa->glCtx);
|
||||
|
||||
/* free the tdfx context */
|
||||
XFree( fxMesa );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
GLboolean
|
||||
tdfxUnbindContext( __DRIcontextPrivate *driContextPriv )
|
||||
{
|
||||
GET_CURRENT_CONTEXT(ctx);
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_DRI ) {
|
||||
fprintf( stderr, "%s( %p )\n", __FUNCTION__, driContextPriv );
|
||||
}
|
||||
|
||||
if ( driContextPriv && (tdfxContextPtr) driContextPriv == fxMesa ) {
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
fxMesa->Glide.grGlideGetState(fxMesa->Glide.State);
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
GLboolean
|
||||
tdfxMakeCurrent( __DRIcontextPrivate *driContextPriv,
|
||||
__DRIdrawablePrivate *driDrawPriv,
|
||||
__DRIdrawablePrivate *driReadPriv )
|
||||
{
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_DRI ) {
|
||||
fprintf( stderr, "%s( %p )\n", __FUNCTION__, driContextPriv );
|
||||
}
|
||||
|
||||
if ( driContextPriv ) {
|
||||
tdfxContextPtr newFx = (tdfxContextPtr) driContextPriv->driverPrivate;
|
||||
GLcontext *newCtx = newFx->glCtx;
|
||||
GET_CURRENT_CONTEXT(curCtx);
|
||||
|
||||
if ( newFx->driDrawable != driDrawPriv ) {
|
||||
newFx->driDrawable = driDrawPriv;
|
||||
newFx->dirty = ~0;
|
||||
}
|
||||
else if (curCtx == newCtx) {
|
||||
/* same drawable, same context -> no-op */
|
||||
/* Need to call _mesa_make_current2() in order to make sure API
|
||||
* dispatch is set correctly.
|
||||
*/
|
||||
_mesa_make_current2( newCtx,
|
||||
(GLframebuffer *) driDrawPriv->driverPrivate,
|
||||
(GLframebuffer *) driReadPriv->driverPrivate );
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
if ( !newFx->Glide.Initialized ) {
|
||||
if ( !tdfxInitContext( driDrawPriv, newFx ) )
|
||||
return GL_FALSE;
|
||||
|
||||
LOCK_HARDWARE( newFx );
|
||||
|
||||
/* FIXME: Force loading of window information */
|
||||
newFx->width = 0;
|
||||
tdfxUpdateClipping(newCtx);
|
||||
tdfxUploadClipping(newFx);
|
||||
|
||||
UNLOCK_HARDWARE( newFx );
|
||||
} else {
|
||||
LOCK_HARDWARE( newFx );
|
||||
|
||||
newFx->Glide.grSstSelect( newFx->Glide.Board );
|
||||
newFx->Glide.grGlideSetState( newFx->Glide.State );
|
||||
|
||||
tdfxUpdateClipping(newCtx);
|
||||
tdfxUploadClipping(newFx);
|
||||
|
||||
UNLOCK_HARDWARE( newFx );
|
||||
}
|
||||
|
||||
_mesa_make_current2( newCtx,
|
||||
(GLframebuffer *) driDrawPriv->driverPrivate,
|
||||
(GLframebuffer *) driReadPriv->driverPrivate );
|
||||
|
||||
if ( !newCtx->Viewport.Width ) {
|
||||
_mesa_set_viewport( newCtx, 0, 0, driDrawPriv->w, driDrawPriv->h );
|
||||
}
|
||||
} else {
|
||||
_mesa_make_current( 0, 0 );
|
||||
}
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Enable this to trace calls to various Glide functions.
|
||||
*/
|
||||
/*#define DEBUG_TRAP*/
|
||||
#ifdef DEBUG_TRAP
|
||||
static void (*real_grDrawTriangle)( const void *a, const void *b, const void *c );
|
||||
static void (*real_grDrawPoint)( const void *a );
|
||||
static void (*real_grDrawVertexArray)(FxU32 mode, FxU32 Count, void *pointers);
|
||||
static void (*real_grDrawVertexArrayContiguous)(FxU32 mode, FxU32 Count,
|
||||
void *pointers, FxU32 stride);
|
||||
static void (*real_grClipWindow)( FxU32 minx, FxU32 miny, FxU32 maxx, FxU32 maxy );
|
||||
|
||||
static void (*real_grVertexLayout)(FxU32 param, FxI32 offset, FxU32 mode);
|
||||
static void (*real_grGlideGetVertexLayout)( void *layout );
|
||||
static void (*real_grGlideSetVertexLayout)( const void *layout );
|
||||
|
||||
static void (*real_grTexDownloadMipMapLevel)( GrChipID_t tmu,
|
||||
FxU32 startAddress,
|
||||
GrLOD_t thisLod,
|
||||
GrLOD_t largeLod,
|
||||
GrAspectRatio_t aspectRatio,
|
||||
GrTextureFormat_t format,
|
||||
FxU32 evenOdd,
|
||||
void *data );
|
||||
|
||||
|
||||
static void debug_grDrawTriangle( const void *a, const void *b, const void *c )
|
||||
{
|
||||
printf("%s\n", __FUNCTION__);
|
||||
(*real_grDrawTriangle)(a, b, c);
|
||||
}
|
||||
|
||||
static void debug_grDrawPoint( const void *a )
|
||||
{
|
||||
const float *f = (const float *) a;
|
||||
printf("%s %g %g\n", __FUNCTION__, f[0], f[1]);
|
||||
(*real_grDrawPoint)(a);
|
||||
}
|
||||
|
||||
static void debug_grDrawVertexArray(FxU32 mode, FxU32 Count, void *pointers)
|
||||
{
|
||||
printf("%s count=%d\n", __FUNCTION__, (int) Count);
|
||||
(*real_grDrawVertexArray)(mode, Count, pointers);
|
||||
}
|
||||
|
||||
static void debug_grDrawVertexArrayContiguous(FxU32 mode, FxU32 Count,
|
||||
void *pointers, FxU32 stride)
|
||||
{
|
||||
printf("%s mode=0x%x count=%d\n", __FUNCTION__, (int) mode, (int) Count);
|
||||
(*real_grDrawVertexArrayContiguous)(mode, Count, pointers, stride);
|
||||
}
|
||||
|
||||
static void debug_grClipWindow( FxU32 minx, FxU32 miny, FxU32 maxx, FxU32 maxy )
|
||||
{
|
||||
printf("%s %d,%d .. %d,%d\n", __FUNCTION__,
|
||||
(int) minx, (int) miny, (int) maxx, (int) maxy);
|
||||
(*real_grClipWindow)(minx, miny, maxx, maxy);
|
||||
}
|
||||
|
||||
static void debug_grVertexLayout(FxU32 param, FxI32 offset, FxU32 mode)
|
||||
{
|
||||
(*real_grVertexLayout)(param, offset, mode);
|
||||
}
|
||||
|
||||
static void debug_grGlideGetVertexLayout( void *layout )
|
||||
{
|
||||
(*real_grGlideGetVertexLayout)(layout);
|
||||
}
|
||||
|
||||
static void debug_grGlideSetVertexLayout( const void *layout )
|
||||
{
|
||||
(*real_grGlideSetVertexLayout)(layout);
|
||||
}
|
||||
|
||||
static void debug_grTexDownloadMipMapLevel( GrChipID_t tmu,
|
||||
FxU32 startAddress,
|
||||
GrLOD_t thisLod,
|
||||
GrLOD_t largeLod,
|
||||
GrAspectRatio_t aspectRatio,
|
||||
GrTextureFormat_t format,
|
||||
FxU32 evenOdd,
|
||||
void *data )
|
||||
{
|
||||
(*real_grTexDownloadMipMapLevel)(tmu, startAddress, thisLod, largeLod,
|
||||
aspectRatio, format, evenOdd, data);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Examine the context's deviceID to determine what kind of 3dfx hardware
|
||||
* is installed. dlopen() the appropriate Glide library and initialize
|
||||
* this context's Glide function pointers.
|
||||
* Return: true/false = success/failure
|
||||
*/
|
||||
GLboolean tdfxInitGlide(tdfxContextPtr tmesa)
|
||||
{
|
||||
static const char *defaultGlide = "libglide3.so";
|
||||
const char *libName;
|
||||
void *libHandle;
|
||||
|
||||
/*
|
||||
* XXX this code which selects a Glide library filename given the
|
||||
* deviceID may need to be cleaned up a bit.
|
||||
* Non-Linux systems may have different filenames, for example.
|
||||
*/
|
||||
switch (tmesa->fxScreen->deviceID) {
|
||||
case PCI_CHIP_BANSHEE:
|
||||
case PCI_CHIP_VOODOO3:
|
||||
libName = "libglide3-v3.so";
|
||||
break;
|
||||
case PCI_CHIP_VOODOO5: /* same as PCI_CHIP_VOODOO4 */
|
||||
libName = "libglide3-v5.so";
|
||||
break;
|
||||
default:
|
||||
{
|
||||
__driUtilMessage("unrecognized 3dfx deviceID: 0x%x",
|
||||
tmesa->fxScreen->deviceID);
|
||||
}
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
libHandle = dlopen(libName, RTLD_NOW);
|
||||
if (!libHandle) {
|
||||
/* The device-specific Glide library filename didn't work, try the
|
||||
* old, generic libglide3.so library.
|
||||
*/
|
||||
libHandle = dlopen(defaultGlide, RTLD_NOW);
|
||||
if (!libHandle) {
|
||||
__driUtilMessage(
|
||||
"can't find Glide library, dlopen(%s) and dlopen(%s) both failed.",
|
||||
libName, defaultGlide);
|
||||
__driUtilMessage("dlerror() message: %s", dlerror());
|
||||
return GL_FALSE;
|
||||
}
|
||||
libName = defaultGlide;
|
||||
}
|
||||
|
||||
{
|
||||
const char *env = getenv("LIBGL_DEBUG");
|
||||
if (env && strstr(env, "verbose")) {
|
||||
fprintf(stderr, "libGL: using Glide library %s\n", libName);
|
||||
}
|
||||
}
|
||||
|
||||
#define GET_FUNCTION(PTR, NAME) \
|
||||
tmesa->Glide.PTR = dlsym(libHandle, NAME); \
|
||||
if (!tmesa->Glide.PTR) { \
|
||||
__driUtilMessage("couldn't find Glide function %s in %s.", \
|
||||
NAME, libName); \
|
||||
}
|
||||
|
||||
GET_FUNCTION(grDrawPoint, "grDrawPoint");
|
||||
GET_FUNCTION(grDrawLine, "grDrawLine");
|
||||
GET_FUNCTION(grDrawTriangle, "grDrawTriangle");
|
||||
GET_FUNCTION(grVertexLayout, "grVertexLayout");
|
||||
GET_FUNCTION(grDrawVertexArray, "grDrawVertexArray");
|
||||
GET_FUNCTION(grDrawVertexArrayContiguous, "grDrawVertexArrayContiguous");
|
||||
GET_FUNCTION(grBufferClear, "grBufferClear");
|
||||
/*GET_FUNCTION(grBufferSwap, "grBufferSwap");*/
|
||||
GET_FUNCTION(grRenderBuffer, "grRenderBuffer");
|
||||
GET_FUNCTION(grErrorSetCallback, "grErrorSetCallback");
|
||||
GET_FUNCTION(grFinish, "grFinish");
|
||||
GET_FUNCTION(grFlush, "grFlush");
|
||||
GET_FUNCTION(grSstWinOpen, "grSstWinOpen");
|
||||
GET_FUNCTION(grSstWinClose, "grSstWinClose");
|
||||
#if 0
|
||||
/* Not in V3 lib, and not used anyway. */
|
||||
GET_FUNCTION(grSetNumPendingBuffers, "grSetNumPendingBuffers");
|
||||
#endif
|
||||
GET_FUNCTION(grSelectContext, "grSelectContext");
|
||||
GET_FUNCTION(grSstOrigin, "grSstOrigin");
|
||||
GET_FUNCTION(grSstSelect, "grSstSelect");
|
||||
GET_FUNCTION(grAlphaBlendFunction, "grAlphaBlendFunction");
|
||||
GET_FUNCTION(grAlphaCombine, "grAlphaCombine");
|
||||
GET_FUNCTION(grAlphaControlsITRGBLighting, "grAlphaControlsITRGBLighting");
|
||||
GET_FUNCTION(grAlphaTestFunction, "grAlphaTestFunction");
|
||||
GET_FUNCTION(grAlphaTestReferenceValue, "grAlphaTestReferenceValue");
|
||||
GET_FUNCTION(grChromakeyMode, "grChromakeyMode");
|
||||
GET_FUNCTION(grChromakeyValue, "grChromakeyValue");
|
||||
GET_FUNCTION(grClipWindow, "grClipWindow");
|
||||
GET_FUNCTION(grColorCombine, "grColorCombine");
|
||||
GET_FUNCTION(grColorMask, "grColorMask");
|
||||
GET_FUNCTION(grCullMode, "grCullMode");
|
||||
GET_FUNCTION(grConstantColorValue, "grConstantColorValue");
|
||||
GET_FUNCTION(grDepthBiasLevel, "grDepthBiasLevel");
|
||||
GET_FUNCTION(grDepthBufferFunction, "grDepthBufferFunction");
|
||||
GET_FUNCTION(grDepthBufferMode, "grDepthBufferMode");
|
||||
GET_FUNCTION(grDepthMask, "grDepthMask");
|
||||
GET_FUNCTION(grDisableAllEffects, "grDisableAllEffects");
|
||||
GET_FUNCTION(grDitherMode, "grDitherMode");
|
||||
GET_FUNCTION(grFogColorValue, "grFogColorValue");
|
||||
GET_FUNCTION(grFogMode, "grFogMode");
|
||||
GET_FUNCTION(grFogTable, "grFogTable");
|
||||
GET_FUNCTION(grLoadGammaTable, "grLoadGammaTable");
|
||||
GET_FUNCTION(grSplash, "grSplash");
|
||||
GET_FUNCTION(grGet, "grGet");
|
||||
GET_FUNCTION(grGetString, "grGetString");
|
||||
GET_FUNCTION(grQueryResolutions, "grQueryResolutions");
|
||||
GET_FUNCTION(grReset, "grReset");
|
||||
GET_FUNCTION(grGetProcAddress, "grGetProcAddress");
|
||||
GET_FUNCTION(grEnable, "grEnable");
|
||||
GET_FUNCTION(grDisable, "grDisable");
|
||||
GET_FUNCTION(grCoordinateSpace, "grCoordinateSpace");
|
||||
GET_FUNCTION(grDepthRange, "grDepthRange");
|
||||
GET_FUNCTION(grStippleMode, "grStippleMode");
|
||||
GET_FUNCTION(grStipplePattern, "grStipplePattern");
|
||||
GET_FUNCTION(grViewport, "grViewport");
|
||||
GET_FUNCTION(grTexCalcMemRequired, "grTexCalcMemRequired");
|
||||
GET_FUNCTION(grTexTextureMemRequired, "grTexTextureMemRequired");
|
||||
GET_FUNCTION(grTexMinAddress, "grTexMinAddress");
|
||||
GET_FUNCTION(grTexMaxAddress, "grTexMaxAddress");
|
||||
GET_FUNCTION(grTexNCCTable, "grTexNCCTable");
|
||||
GET_FUNCTION(grTexSource, "grTexSource");
|
||||
GET_FUNCTION(grTexClampMode, "grTexClampMode");
|
||||
GET_FUNCTION(grTexCombine, "grTexCombine");
|
||||
GET_FUNCTION(grTexDetailControl, "grTexDetailControl");
|
||||
GET_FUNCTION(grTexFilterMode, "grTexFilterMode");
|
||||
GET_FUNCTION(grTexLodBiasValue, "grTexLodBiasValue");
|
||||
GET_FUNCTION(grTexDownloadMipMap, "grTexDownloadMipMap");
|
||||
GET_FUNCTION(grTexDownloadMipMapLevel, "grTexDownloadMipMapLevel");
|
||||
GET_FUNCTION(grTexDownloadMipMapLevelPartial, "grTexDownloadMipMapLevelPartial");
|
||||
GET_FUNCTION(grTexDownloadTable, "grTexDownloadTable");
|
||||
GET_FUNCTION(grTexDownloadTablePartial, "grTexDownloadTablePartial");
|
||||
GET_FUNCTION(grTexMipMapMode, "grTexMipMapMode");
|
||||
GET_FUNCTION(grTexMultibase, "grTexMultibase");
|
||||
GET_FUNCTION(grTexMultibaseAddress, "grTexMultibaseAddress");
|
||||
GET_FUNCTION(grLfbLock, "grLfbLock");
|
||||
GET_FUNCTION(grLfbUnlock, "grLfbUnlock");
|
||||
GET_FUNCTION(grLfbConstantAlpha, "grLfbConstantAlpha");
|
||||
GET_FUNCTION(grLfbConstantDepth, "grLfbConstantDepth");
|
||||
GET_FUNCTION(grLfbWriteColorSwizzle, "grLfbWriteColorSwizzle");
|
||||
GET_FUNCTION(grLfbWriteColorFormat, "grLfbWriteColorFormat");
|
||||
GET_FUNCTION(grLfbWriteRegion, "grLfbWriteRegion");
|
||||
GET_FUNCTION(grLfbReadRegion, "grLfbReadRegion");
|
||||
GET_FUNCTION(grGlideInit, "grGlideInit");
|
||||
GET_FUNCTION(grGlideShutdown, "grGlideShutdown");
|
||||
GET_FUNCTION(grGlideGetState, "grGlideGetState");
|
||||
GET_FUNCTION(grGlideSetState, "grGlideSetState");
|
||||
GET_FUNCTION(grGlideGetVertexLayout, "grGlideGetVertexLayout");
|
||||
GET_FUNCTION(grGlideSetVertexLayout, "grGlideSetVertexLayout");
|
||||
|
||||
/* Glide utility functions */
|
||||
GET_FUNCTION(guFogGenerateExp, "guFogGenerateExp");
|
||||
GET_FUNCTION(guFogGenerateExp2, "guFogGenerateExp2");
|
||||
GET_FUNCTION(guFogGenerateLinear, "guFogGenerateLinear");
|
||||
|
||||
/* DRI functions */
|
||||
GET_FUNCTION(grDRIOpen, "grDRIOpen");
|
||||
GET_FUNCTION(grDRIPosition, "grDRIPosition");
|
||||
/*GET_FUNCTION(grDRILostContext, "grDRILostContext");*/
|
||||
GET_FUNCTION(grDRIImportFifo, "grDRIImportFifo");
|
||||
GET_FUNCTION(grDRIInvalidateAll, "grDRIInvalidateAll");
|
||||
GET_FUNCTION(grDRIResetSAREA, "grDRIResetSAREA");
|
||||
GET_FUNCTION(grDRIBufferSwap, "grDRIBufferSwap");
|
||||
|
||||
/*
|
||||
* Extension functions:
|
||||
* Just use dlysm() because we want a NULL pointer if the function is
|
||||
* not found.
|
||||
*/
|
||||
/* PIXEXT extension */
|
||||
tmesa->Glide.grStencilFunc = dlsym(libHandle, "grStencilFunc");
|
||||
tmesa->Glide.grStencilMask = dlsym(libHandle, "grStencilMask");
|
||||
tmesa->Glide.grStencilOp = dlsym(libHandle, "grStencilOp");
|
||||
tmesa->Glide.grBufferClearExt = dlsym(libHandle, "grBufferClearExt");
|
||||
tmesa->Glide.grColorMaskExt = dlsym(libHandle, "grColorMaskExt");
|
||||
/* COMBINE extension */
|
||||
tmesa->Glide.grColorCombineExt = dlsym(libHandle, "grColorCombineExt");
|
||||
tmesa->Glide.grTexColorCombineExt = dlsym(libHandle, "grTexColorCombineExt");
|
||||
tmesa->Glide.grAlphaCombineExt = dlsym(libHandle, "grAlphaCombineExt");
|
||||
tmesa->Glide.grTexAlphaCombineExt = dlsym(libHandle, "grTexAlphaCombineExt");
|
||||
tmesa->Glide.grAlphaBlendFunctionExt = dlsym(libHandle, "grAlphaBlendFunctionExt");
|
||||
tmesa->Glide.grConstantColorValueExt = dlsym(libHandle, "grConstantColorValueExt");
|
||||
/* Texus 2 */
|
||||
tmesa->Glide.txImgQuantize = dlsym(libHandle, "txImgQuantize");
|
||||
tmesa->Glide.txImgDequantizeFXT1 = dlsym(libHandle, "_txImgDequantizeFXT1");
|
||||
tmesa->Glide.txErrorSetCallback = dlsym(libHandle, "txErrorSetCallback");
|
||||
|
||||
#ifdef DEBUG_TRAP
|
||||
/* wrap the drawing functions so we can trap them */
|
||||
real_grDrawTriangle = tmesa->Glide.grDrawTriangle;
|
||||
tmesa->Glide.grDrawTriangle = debug_grDrawTriangle;
|
||||
|
||||
real_grDrawPoint = tmesa->Glide.grDrawPoint;
|
||||
tmesa->Glide.grDrawPoint = debug_grDrawPoint;
|
||||
|
||||
real_grDrawVertexArray = tmesa->Glide.grDrawVertexArray;
|
||||
tmesa->Glide.grDrawVertexArray = debug_grDrawVertexArray;
|
||||
|
||||
real_grDrawVertexArrayContiguous = tmesa->Glide.grDrawVertexArrayContiguous;
|
||||
tmesa->Glide.grDrawVertexArrayContiguous = debug_grDrawVertexArrayContiguous;
|
||||
|
||||
real_grClipWindow = tmesa->Glide.grClipWindow;
|
||||
tmesa->Glide.grClipWindow = debug_grClipWindow;
|
||||
|
||||
real_grVertexLayout = tmesa->Glide.grVertexLayout;
|
||||
tmesa->Glide.grVertexLayout = debug_grVertexLayout;
|
||||
|
||||
real_grGlideGetVertexLayout = tmesa->Glide.grGlideGetVertexLayout;
|
||||
tmesa->Glide.grGlideGetVertexLayout = debug_grGlideGetVertexLayout;
|
||||
|
||||
real_grGlideSetVertexLayout = tmesa->Glide.grGlideSetVertexLayout;
|
||||
tmesa->Glide.grGlideSetVertexLayout = debug_grGlideSetVertexLayout;
|
||||
|
||||
real_grTexDownloadMipMapLevel = tmesa->Glide.grTexDownloadMipMapLevel;
|
||||
tmesa->Glide.grTexDownloadMipMapLevel = debug_grTexDownloadMipMapLevel;
|
||||
|
||||
#endif
|
||||
return GL_TRUE;
|
||||
}
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,330 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_dd.c,v 1.10 2002/10/30 12:52:00 alanh Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_dd.h"
|
||||
#include "tdfx_lock.h"
|
||||
#include "tdfx_vb.h"
|
||||
#include "tdfx_pixels.h"
|
||||
|
||||
#include "context.h"
|
||||
#include "enums.h"
|
||||
#include "swrast/swrast.h"
|
||||
#if defined(USE_X86_ASM)
|
||||
#include "X86/common_x86_asm.h"
|
||||
#endif
|
||||
|
||||
|
||||
#define TDFX_DATE "20021125"
|
||||
|
||||
|
||||
/* These are used in calls to FX_grColorMaskv() */
|
||||
const GLboolean false4[4] = { GL_FALSE, GL_FALSE, GL_FALSE, GL_FALSE };
|
||||
const GLboolean true4[4] = { GL_TRUE, GL_TRUE, GL_TRUE, GL_TRUE };
|
||||
|
||||
|
||||
|
||||
/* KW: Put the word Mesa in the render string because quakeworld
|
||||
* checks for this rather than doing a glGet(GL_MAX_TEXTURE_SIZE).
|
||||
* Why?
|
||||
*/
|
||||
static const GLubyte *tdfxDDGetString( GLcontext *ctx, GLenum name )
|
||||
{
|
||||
tdfxContextPtr fxMesa = (tdfxContextPtr) ctx->DriverCtx;
|
||||
|
||||
switch ( name ) {
|
||||
case GL_RENDERER:
|
||||
{
|
||||
/* The renderer string must be per-context state to handle
|
||||
* multihead correctly.
|
||||
*/
|
||||
char *buffer = fxMesa->rendererString;
|
||||
char hardware[100];
|
||||
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
strcpy( hardware, fxMesa->Glide.grGetString(GR_HARDWARE) );
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
|
||||
strcpy( buffer, "Mesa DRI " );
|
||||
strcat( buffer, TDFX_DATE );
|
||||
strcat( buffer, " " );
|
||||
|
||||
if ( strcmp( hardware, "Voodoo3 (tm)" ) == 0 ) {
|
||||
strcat( buffer, "Voodoo3" );
|
||||
}
|
||||
else if ( strcmp( hardware, "Voodoo Banshee (tm)" ) == 0 ) {
|
||||
strcat( buffer, "VoodooBanshee" );
|
||||
}
|
||||
else if ( strcmp( hardware, "Voodoo4 (tm)" ) == 0 ) {
|
||||
strcat( buffer, "Voodoo4" );
|
||||
}
|
||||
else if ( strcmp( hardware, "Voodoo5 (tm)" ) == 0 ) {
|
||||
strcat( buffer, "Voodoo5" );
|
||||
}
|
||||
else {
|
||||
/* unexpected result: replace spaces with hyphens */
|
||||
int i;
|
||||
for ( i = 0 ; hardware[i] && i < 60 ; i++ ) {
|
||||
if ( hardware[i] == ' ' || hardware[i] == '\t' )
|
||||
hardware[i] = '-';
|
||||
}
|
||||
strcat( buffer, hardware );
|
||||
}
|
||||
|
||||
/* Append any CPU-specific information.
|
||||
*/
|
||||
#ifdef USE_X86_ASM
|
||||
if ( _mesa_x86_cpu_features ) {
|
||||
strncat( buffer, " x86", 4 );
|
||||
}
|
||||
#endif
|
||||
#ifdef USE_MMX_ASM
|
||||
if ( cpu_has_mmx ) {
|
||||
strncat( buffer, "/MMX", 4 );
|
||||
}
|
||||
#endif
|
||||
#ifdef USE_3DNOW_ASM
|
||||
if ( cpu_has_3dnow ) {
|
||||
strncat( buffer, "/3DNow!", 7 );
|
||||
}
|
||||
#endif
|
||||
#ifdef USE_SSE_ASM
|
||||
if ( cpu_has_xmm ) {
|
||||
strncat( buffer, "/SSE", 4 );
|
||||
}
|
||||
#endif
|
||||
return (const GLubyte *) buffer;
|
||||
}
|
||||
case GL_VENDOR:
|
||||
return (const GLubyte *)"VA Linux Systems, Inc.";
|
||||
default:
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/* Return uptodate buffer size information.
|
||||
*/
|
||||
static void tdfxDDGetBufferSize( GLframebuffer *buffer,
|
||||
GLuint *width, GLuint *height )
|
||||
{
|
||||
GET_CURRENT_CONTEXT(ctx);
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
*width = fxMesa->width;
|
||||
*height = fxMesa->height;
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* Return the current value of the occlusion test flag and
|
||||
* reset the flag (hardware counters) to false.
|
||||
*/
|
||||
static GLboolean get_occlusion_result( GLcontext *ctx )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GLboolean result;
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
fxMesa->Glide.grFinish(); /* required to flush the FIFO - FB 21-01-2002 */
|
||||
|
||||
if (ctx->Depth.OcclusionTest) {
|
||||
if (ctx->OcclusionResult) {
|
||||
result = GL_TRUE; /* result of software rendering */
|
||||
}
|
||||
else {
|
||||
FxI32 zfail, in;
|
||||
fxMesa->Glide.grGet(GR_STATS_PIXELS_DEPTHFUNC_FAIL, 4, &zfail);
|
||||
fxMesa->Glide.grGet(GR_STATS_PIXELS_IN, 4, &in);
|
||||
/* Geometry is occluded if there is no input (in == 0) */
|
||||
/* or if all pixels failed the depth test (zfail == in) */
|
||||
/* The < 1 is there because I have empirically seen cases where */
|
||||
/* zfail > in.... go figure. FB - 21-01-2002. */
|
||||
result = ((in - zfail) < 1 || in == 0) ? GL_FALSE : GL_TRUE;
|
||||
}
|
||||
}
|
||||
else {
|
||||
result = ctx->OcclusionResultSaved;
|
||||
}
|
||||
|
||||
/* reset results now */
|
||||
fxMesa->Glide.grReset(GR_STATS_PIXELS);
|
||||
ctx->OcclusionResult = GL_FALSE;
|
||||
ctx->OcclusionResultSaved = GL_FALSE;
|
||||
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* We're only implementing this function to handle the
|
||||
* GL_OCCLUSTION_TEST_RESULT_HP case. It's special because it
|
||||
* has a side-effect: resetting the occlustion result flag.
|
||||
*/
|
||||
static GLboolean tdfxDDGetBooleanv( GLcontext *ctx, GLenum pname,
|
||||
GLboolean *result )
|
||||
{
|
||||
if ( pname == GL_OCCLUSION_TEST_RESULT_HP ) {
|
||||
*result = get_occlusion_result( ctx );
|
||||
return GL_TRUE;
|
||||
}
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
static GLboolean tdfxDDGetDoublev( GLcontext *ctx, GLenum pname,
|
||||
GLdouble *result )
|
||||
{
|
||||
if ( pname == GL_OCCLUSION_TEST_RESULT_HP ) {
|
||||
*result = (GLdouble) get_occlusion_result( ctx );
|
||||
return GL_TRUE;
|
||||
}
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
static GLboolean tdfxDDGetFloatv( GLcontext *ctx, GLenum pname,
|
||||
GLfloat *result )
|
||||
{
|
||||
if ( pname == GL_OCCLUSION_TEST_RESULT_HP ) {
|
||||
*result = (GLfloat) get_occlusion_result( ctx );
|
||||
return GL_TRUE;
|
||||
}
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
static GLboolean tdfxDDGetIntegerv( GLcontext *ctx, GLenum pname,
|
||||
GLint *result )
|
||||
{
|
||||
if ( pname == GL_OCCLUSION_TEST_RESULT_HP ) {
|
||||
*result = (GLint) get_occlusion_result( ctx );
|
||||
return GL_TRUE;
|
||||
}
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define VISUAL_EQUALS_RGBA(vis, r, g, b, a) \
|
||||
((vis.redBits == r) && \
|
||||
(vis.greenBits == g) && \
|
||||
(vis.blueBits == b) && \
|
||||
(vis.alphaBits == a))
|
||||
|
||||
void tdfxDDInitDriverFuncs( GLcontext *ctx )
|
||||
{
|
||||
if ( MESA_VERBOSE & VERBOSE_DRIVER ) {
|
||||
fprintf( stderr, "tdfx: %s()\n", __FUNCTION__ );
|
||||
}
|
||||
|
||||
ctx->Driver.GetString = tdfxDDGetString;
|
||||
ctx->Driver.GetBufferSize = tdfxDDGetBufferSize;
|
||||
ctx->Driver.ResizeBuffers = _swrast_alloc_buffers;
|
||||
ctx->Driver.Error = NULL;
|
||||
|
||||
/* Pixel path fallbacks.
|
||||
*/
|
||||
ctx->Driver.Accum = _swrast_Accum;
|
||||
ctx->Driver.Bitmap = _swrast_Bitmap;
|
||||
ctx->Driver.CopyPixels = _swrast_CopyPixels;
|
||||
ctx->Driver.DrawPixels = _swrast_DrawPixels;
|
||||
ctx->Driver.ReadPixels = _swrast_ReadPixels;
|
||||
|
||||
/* Accelerated paths
|
||||
*/
|
||||
if ( VISUAL_EQUALS_RGBA(ctx->Visual, 8, 8, 8, 8) )
|
||||
{
|
||||
ctx->Driver.DrawPixels = tdfx_drawpixels_R8G8B8A8;
|
||||
ctx->Driver.ReadPixels = tdfx_readpixels_R8G8B8A8;
|
||||
}
|
||||
else if ( VISUAL_EQUALS_RGBA(ctx->Visual, 5, 6, 5, 0) )
|
||||
{
|
||||
ctx->Driver.ReadPixels = tdfx_readpixels_R5G6B5;
|
||||
}
|
||||
|
||||
ctx->Driver.GetBooleanv = tdfxDDGetBooleanv;
|
||||
ctx->Driver.GetDoublev = tdfxDDGetDoublev;
|
||||
ctx->Driver.GetFloatv = tdfxDDGetFloatv;
|
||||
ctx->Driver.GetIntegerv = tdfxDDGetIntegerv;
|
||||
ctx->Driver.GetPointerv = NULL;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* These are here for lack of a better place.
|
||||
*/
|
||||
|
||||
void
|
||||
FX_grColorMaskv(GLcontext *ctx, const GLboolean rgba[4])
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
if (ctx->Visual.redBits == 8) {
|
||||
/* 32bpp mode */
|
||||
ASSERT( fxMesa->Glide.grColorMaskExt );
|
||||
fxMesa->Glide.grColorMaskExt(rgba[RCOMP], rgba[GCOMP],
|
||||
rgba[BCOMP], rgba[ACOMP]);
|
||||
}
|
||||
else {
|
||||
/* 16 bpp mode */
|
||||
/* we never have an alpha buffer */
|
||||
fxMesa->Glide.grColorMask(rgba[RCOMP] || rgba[GCOMP] || rgba[BCOMP],
|
||||
GL_FALSE);
|
||||
}
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
|
||||
void
|
||||
FX_grColorMaskv_NoLock(GLcontext *ctx, const GLboolean rgba[4])
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
if (ctx->Visual.redBits == 8) {
|
||||
/* 32bpp mode */
|
||||
ASSERT( fxMesa->Glide.grColorMaskExt );
|
||||
fxMesa->Glide.grColorMaskExt(rgba[RCOMP], rgba[GCOMP],
|
||||
rgba[BCOMP], rgba[ACOMP]);
|
||||
}
|
||||
else {
|
||||
/* 16 bpp mode */
|
||||
/* we never have an alpha buffer */
|
||||
fxMesa->Glide.grColorMask(rgba[RCOMP] || rgba[GCOMP] || rgba[BCOMP],
|
||||
GL_FALSE);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,47 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_dd.h,v 1.1 2001/03/21 16:14:27 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_DD_H__
|
||||
#define __TDFX_DD_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
#include "context.h"
|
||||
|
||||
extern void tdfxDDInitDriverFuncs( GLcontext *ctx );
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -0,0 +1,606 @@
|
||||
/*
|
||||
* This file defines macros and types necessary for accessing glide3.
|
||||
*/
|
||||
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_glide.h,v 1.1 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
#ifndef NEWGLIDE_H
|
||||
#define NEWGLIDE_H
|
||||
|
||||
#define FX_CALL
|
||||
|
||||
typedef unsigned char FxU8;
|
||||
typedef signed char FxI8;
|
||||
typedef unsigned short FxU16;
|
||||
typedef signed short FxI16;
|
||||
#if defined(__alpha__) || defined (__LP64__)
|
||||
typedef signed int FxI32;
|
||||
typedef unsigned int FxU32;
|
||||
#else
|
||||
typedef signed long FxI32;
|
||||
typedef unsigned long FxU32;
|
||||
#endif
|
||||
typedef unsigned long AnyPtr;
|
||||
typedef int FxBool;
|
||||
typedef float FxFloat;
|
||||
typedef double FxDouble;
|
||||
|
||||
typedef unsigned long FxColor_t;
|
||||
typedef struct
|
||||
{
|
||||
float r, g, b, a;
|
||||
}
|
||||
FxColor4;
|
||||
|
||||
typedef FxU32 GrColor_t;
|
||||
typedef FxU8 GrAlpha_t;
|
||||
typedef FxU32 GrMipMapId_t;
|
||||
typedef FxU32 GrStipplePattern_t;
|
||||
typedef FxU8 GrFog_t;
|
||||
typedef FxU32 GrContext_t;
|
||||
typedef int (FX_CALL * GrProc) (void);
|
||||
|
||||
#define FXTRUE 1
|
||||
#define FXFALSE 0
|
||||
|
||||
#define FXBIT(i) (1L << (i))
|
||||
|
||||
#define GR_NULL_MIPMAP_HANDLE ((GrMipMapId_t) -1)
|
||||
|
||||
#define GR_MIPMAPLEVELMASK_EVEN FXBIT(0)
|
||||
#define GR_MIPMAPLEVELMASK_ODD FXBIT(1)
|
||||
#define GR_MIPMAPLEVELMASK_BOTH (GR_MIPMAPLEVELMASK_EVEN | GR_MIPMAPLEVELMASK_ODD )
|
||||
|
||||
typedef FxI32 GrChipID_t;
|
||||
#define GR_TMU0 0x0
|
||||
#define GR_TMU1 0x1
|
||||
#define GR_TMU2 0x2
|
||||
|
||||
#define GR_FBI 0x0
|
||||
|
||||
typedef FxI32 GrCombineFunction_t;
|
||||
#define GR_COMBINE_FUNCTION_ZERO 0x0
|
||||
#define GR_COMBINE_FUNCTION_NONE GR_COMBINE_FUNCTION_ZERO
|
||||
#define GR_COMBINE_FUNCTION_LOCAL 0x1
|
||||
#define GR_COMBINE_FUNCTION_LOCAL_ALPHA 0x2
|
||||
#define GR_COMBINE_FUNCTION_SCALE_OTHER 0x3
|
||||
#define GR_COMBINE_FUNCTION_BLEND_OTHER GR_COMBINE_FUNCTION_SCALE_OTHER
|
||||
#define GR_COMBINE_FUNCTION_SCALE_OTHER_ADD_LOCAL 0x4
|
||||
#define GR_COMBINE_FUNCTION_SCALE_OTHER_ADD_LOCAL_ALPHA 0x5
|
||||
#define GR_COMBINE_FUNCTION_SCALE_OTHER_MINUS_LOCAL 0x6
|
||||
#define GR_COMBINE_FUNCTION_SCALE_OTHER_MINUS_LOCAL_ADD_LOCAL 0x7
|
||||
#define GR_COMBINE_FUNCTION_BLEND GR_COMBINE_FUNCTION_SCALE_OTHER_MINUS_LOCAL_ADD_LOCAL
|
||||
#define GR_COMBINE_FUNCTION_SCALE_OTHER_MINUS_LOCAL_ADD_LOCAL_ALPHA 0x8
|
||||
#define GR_COMBINE_FUNCTION_SCALE_MINUS_LOCAL_ADD_LOCAL 0x9
|
||||
#define GR_COMBINE_FUNCTION_BLEND_LOCAL GR_COMBINE_FUNCTION_SCALE_MINUS_LOCAL_ADD_LOCAL
|
||||
#define GR_COMBINE_FUNCTION_SCALE_MINUS_LOCAL_ADD_LOCAL_ALPHA 0x10
|
||||
|
||||
typedef FxI32 GrCombineFactor_t;
|
||||
#define GR_COMBINE_FACTOR_ZERO 0x0
|
||||
#define GR_COMBINE_FACTOR_NONE GR_COMBINE_FACTOR_ZERO
|
||||
#define GR_COMBINE_FACTOR_LOCAL 0x1
|
||||
#define GR_COMBINE_FACTOR_OTHER_ALPHA 0x2
|
||||
#define GR_COMBINE_FACTOR_LOCAL_ALPHA 0x3
|
||||
#define GR_COMBINE_FACTOR_TEXTURE_ALPHA 0x4
|
||||
#define GR_COMBINE_FACTOR_TEXTURE_RGB 0x5
|
||||
#define GR_COMBINE_FACTOR_DETAIL_FACTOR GR_COMBINE_FACTOR_TEXTURE_ALPHA
|
||||
#define GR_COMBINE_FACTOR_LOD_FRACTION 0x5
|
||||
#define GR_COMBINE_FACTOR_ONE 0x8
|
||||
#define GR_COMBINE_FACTOR_ONE_MINUS_LOCAL 0x9
|
||||
#define GR_COMBINE_FACTOR_ONE_MINUS_OTHER_ALPHA 0xa
|
||||
#define GR_COMBINE_FACTOR_ONE_MINUS_LOCAL_ALPHA 0xb
|
||||
#define GR_COMBINE_FACTOR_ONE_MINUS_TEXTURE_ALPHA 0xc
|
||||
#define GR_COMBINE_FACTOR_ONE_MINUS_DETAIL_FACTOR GR_COMBINE_FACTOR_ONE_MINUS_TEXTURE_ALPHA
|
||||
#define GR_COMBINE_FACTOR_ONE_MINUS_LOD_FRACTION 0xd
|
||||
|
||||
typedef FxI32 GrCombineLocal_t;
|
||||
#define GR_COMBINE_LOCAL_ITERATED 0x0
|
||||
#define GR_COMBINE_LOCAL_CONSTANT 0x1
|
||||
#define GR_COMBINE_LOCAL_NONE GR_COMBINE_LOCAL_CONSTANT
|
||||
#define GR_COMBINE_LOCAL_DEPTH 0x2
|
||||
|
||||
typedef FxI32 GrCombineOther_t;
|
||||
#define GR_COMBINE_OTHER_ITERATED 0x0
|
||||
#define GR_COMBINE_OTHER_TEXTURE 0x1
|
||||
#define GR_COMBINE_OTHER_CONSTANT 0x2
|
||||
#define GR_COMBINE_OTHER_NONE GR_COMBINE_OTHER_CONSTANT
|
||||
|
||||
typedef FxI32 GrAlphaSource_t;
|
||||
#define GR_ALPHASOURCE_CC_ALPHA 0x0
|
||||
#define GR_ALPHASOURCE_ITERATED_ALPHA 0x1
|
||||
#define GR_ALPHASOURCE_TEXTURE_ALPHA 0x2
|
||||
#define GR_ALPHASOURCE_TEXTURE_ALPHA_TIMES_ITERATED_ALPHA 0x3
|
||||
|
||||
typedef FxI32 GrColorCombineFnc_t;
|
||||
#define GR_COLORCOMBINE_ZERO 0x0
|
||||
#define GR_COLORCOMBINE_CCRGB 0x1
|
||||
#define GR_COLORCOMBINE_ITRGB 0x2
|
||||
#define GR_COLORCOMBINE_ITRGB_DELTA0 0x3
|
||||
#define GR_COLORCOMBINE_DECAL_TEXTURE 0x4
|
||||
#define GR_COLORCOMBINE_TEXTURE_TIMES_CCRGB 0x5
|
||||
#define GR_COLORCOMBINE_TEXTURE_TIMES_ITRGB 0x6
|
||||
#define GR_COLORCOMBINE_TEXTURE_TIMES_ITRGB_DELTA0 0x7
|
||||
#define GR_COLORCOMBINE_TEXTURE_TIMES_ITRGB_ADD_ALPHA 0x8
|
||||
#define GR_COLORCOMBINE_TEXTURE_TIMES_ALPHA 0x9
|
||||
#define GR_COLORCOMBINE_TEXTURE_TIMES_ALPHA_ADD_ITRGB 0xa
|
||||
#define GR_COLORCOMBINE_TEXTURE_ADD_ITRGB 0xb
|
||||
#define GR_COLORCOMBINE_TEXTURE_SUB_ITRGB 0xc
|
||||
#define GR_COLORCOMBINE_CCRGB_BLEND_ITRGB_ON_TEXALPHA 0xd
|
||||
#define GR_COLORCOMBINE_DIFF_SPEC_A 0xe
|
||||
#define GR_COLORCOMBINE_DIFF_SPEC_B 0xf
|
||||
#define GR_COLORCOMBINE_ONE 0x10
|
||||
|
||||
typedef FxI32 GrAlphaBlendFnc_t;
|
||||
#define GR_BLEND_ZERO 0x0
|
||||
#define GR_BLEND_SRC_ALPHA 0x1
|
||||
#define GR_BLEND_SRC_COLOR 0x2
|
||||
#define GR_BLEND_DST_COLOR GR_BLEND_SRC_COLOR
|
||||
#define GR_BLEND_DST_ALPHA 0x3
|
||||
#define GR_BLEND_ONE 0x4
|
||||
#define GR_BLEND_ONE_MINUS_SRC_ALPHA 0x5
|
||||
#define GR_BLEND_ONE_MINUS_SRC_COLOR 0x6
|
||||
#define GR_BLEND_ONE_MINUS_DST_COLOR GR_BLEND_ONE_MINUS_SRC_COLOR
|
||||
#define GR_BLEND_ONE_MINUS_DST_ALPHA 0x7
|
||||
#define GR_BLEND_RESERVED_8 0x8
|
||||
#define GR_BLEND_RESERVED_9 0x9
|
||||
#define GR_BLEND_RESERVED_A 0xa
|
||||
#define GR_BLEND_RESERVED_B 0xb
|
||||
#define GR_BLEND_RESERVED_C 0xc
|
||||
#define GR_BLEND_RESERVED_D 0xd
|
||||
#define GR_BLEND_RESERVED_E 0xe
|
||||
#define GR_BLEND_ALPHA_SATURATE 0xf
|
||||
#define GR_BLEND_PREFOG_COLOR GR_BLEND_ALPHA_SATURATE
|
||||
#define GR_BLEND_SAME_COLOR_EXT 0x08
|
||||
#define GR_BLEND_ONE_MINUS_SAME_COLOR_EXT 0x09
|
||||
|
||||
typedef FxI32 GrAspectRatio_t;
|
||||
#define GR_ASPECT_LOG2_8x1 3
|
||||
#define GR_ASPECT_LOG2_4x1 2
|
||||
#define GR_ASPECT_LOG2_2x1 1
|
||||
#define GR_ASPECT_LOG2_1x1 0
|
||||
#define GR_ASPECT_LOG2_1x2 -1
|
||||
#define GR_ASPECT_LOG2_1x4 -2
|
||||
#define GR_ASPECT_LOG2_1x8 -3
|
||||
|
||||
typedef FxI32 GrBuffer_t;
|
||||
#define GR_BUFFER_FRONTBUFFER 0x0
|
||||
#define GR_BUFFER_BACKBUFFER 0x1
|
||||
#define GR_BUFFER_AUXBUFFER 0x2
|
||||
#define GR_BUFFER_DEPTHBUFFER 0x3
|
||||
#define GR_BUFFER_ALPHABUFFER 0x4
|
||||
#define GR_BUFFER_TRIPLEBUFFER 0x5
|
||||
|
||||
typedef FxI32 GrChromakeyMode_t;
|
||||
#define GR_CHROMAKEY_DISABLE 0x0
|
||||
#define GR_CHROMAKEY_ENABLE 0x1
|
||||
|
||||
typedef FxI32 GrChromaRangeMode_t;
|
||||
#define GR_CHROMARANGE_RGB_ALL_EXT 0x0
|
||||
|
||||
#define GR_CHROMARANGE_DISABLE_EXT 0x00
|
||||
#define GR_CHROMARANGE_ENABLE_EXT 0x01
|
||||
|
||||
typedef FxI32 GrTexChromakeyMode_t;
|
||||
#define GR_TEXCHROMA_DISABLE_EXT 0x0
|
||||
#define GR_TEXCHROMA_ENABLE_EXT 0x1
|
||||
|
||||
#define GR_TEXCHROMARANGE_RGB_ALL_EXT 0x0
|
||||
|
||||
typedef FxI32 GrCmpFnc_t;
|
||||
#define GR_CMP_NEVER 0x0
|
||||
#define GR_CMP_LESS 0x1
|
||||
#define GR_CMP_EQUAL 0x2
|
||||
#define GR_CMP_LEQUAL 0x3
|
||||
#define GR_CMP_GREATER 0x4
|
||||
#define GR_CMP_NOTEQUAL 0x5
|
||||
#define GR_CMP_GEQUAL 0x6
|
||||
#define GR_CMP_ALWAYS 0x7
|
||||
|
||||
typedef FxI32 GrColorFormat_t;
|
||||
#define GR_COLORFORMAT_ARGB 0x0
|
||||
#define GR_COLORFORMAT_ABGR 0x1
|
||||
|
||||
#define GR_COLORFORMAT_RGBA 0x2
|
||||
#define GR_COLORFORMAT_BGRA 0x3
|
||||
|
||||
typedef FxI32 GrCullMode_t;
|
||||
#define GR_CULL_DISABLE 0x0
|
||||
#define GR_CULL_NEGATIVE 0x1
|
||||
#define GR_CULL_POSITIVE 0x2
|
||||
|
||||
typedef FxI32 GrDepthBufferMode_t;
|
||||
#define GR_DEPTHBUFFER_DISABLE 0x0
|
||||
#define GR_DEPTHBUFFER_ZBUFFER 0x1
|
||||
#define GR_DEPTHBUFFER_WBUFFER 0x2
|
||||
#define GR_DEPTHBUFFER_ZBUFFER_COMPARE_TO_BIAS 0x3
|
||||
#define GR_DEPTHBUFFER_WBUFFER_COMPARE_TO_BIAS 0x4
|
||||
|
||||
typedef FxI32 GrDitherMode_t;
|
||||
#define GR_DITHER_DISABLE 0x0
|
||||
#define GR_DITHER_2x2 0x1
|
||||
#define GR_DITHER_4x4 0x2
|
||||
|
||||
typedef FxI32 GrStippleMode_t;
|
||||
#define GR_STIPPLE_DISABLE 0x0
|
||||
#define GR_STIPPLE_PATTERN 0x1
|
||||
#define GR_STIPPLE_ROTATE 0x2
|
||||
|
||||
typedef FxI32 GrFogMode_t;
|
||||
#define GR_FOG_DISABLE 0x0
|
||||
#define GR_FOG_WITH_TABLE_ON_FOGCOORD_EXT 0x1
|
||||
#define GR_FOG_WITH_TABLE_ON_Q 0x2
|
||||
#define GR_FOG_WITH_TABLE_ON_W GR_FOG_WITH_TABLE_ON_Q
|
||||
#define GR_FOG_WITH_ITERATED_Z 0x3
|
||||
#define GR_FOG_WITH_ITERATED_ALPHA_EXT 0x4
|
||||
#define GR_FOG_MULT2 0x100
|
||||
#define GR_FOG_ADD2 0x200
|
||||
|
||||
typedef FxU32 GrLock_t;
|
||||
#define GR_LFB_READ_ONLY 0x00
|
||||
#define GR_LFB_WRITE_ONLY 0x01
|
||||
#define GR_LFB_IDLE 0x00
|
||||
#define GR_LFB_NOIDLE 0x10
|
||||
|
||||
typedef FxI32 GrLfbBypassMode_t;
|
||||
#define GR_LFBBYPASS_DISABLE 0x0
|
||||
#define GR_LFBBYPASS_ENABLE 0x1
|
||||
|
||||
typedef FxI32 GrLfbWriteMode_t;
|
||||
#define GR_LFBWRITEMODE_565 0x0
|
||||
#define GR_LFBWRITEMODE_555 0x1
|
||||
#define GR_LFBWRITEMODE_1555 0x2
|
||||
#define GR_LFBWRITEMODE_RESERVED1 0x3
|
||||
#define GR_LFBWRITEMODE_888 0x4
|
||||
#define GR_LFBWRITEMODE_8888 0x5
|
||||
#define GR_LFBWRITEMODE_RESERVED2 0x6
|
||||
#define GR_LFBWRITEMODE_RESERVED3 0x7
|
||||
#define GR_LFBWRITEMODE_RESERVED4 0x8
|
||||
#define GR_LFBWRITEMODE_RESERVED5 0x9
|
||||
#define GR_LFBWRITEMODE_RESERVED6 0xa
|
||||
#define GR_LFBWRITEMODE_RESERVED7 0xb
|
||||
#define GR_LFBWRITEMODE_565_DEPTH 0xc
|
||||
#define GR_LFBWRITEMODE_555_DEPTH 0xd
|
||||
#define GR_LFBWRITEMODE_1555_DEPTH 0xe
|
||||
#define GR_LFBWRITEMODE_ZA16 0xf
|
||||
#define GR_LFBWRITEMODE_ANY 0xFF
|
||||
|
||||
typedef FxI32 GrOriginLocation_t;
|
||||
#define GR_ORIGIN_UPPER_LEFT 0x0
|
||||
#define GR_ORIGIN_LOWER_LEFT 0x1
|
||||
#define GR_ORIGIN_ANY 0xFF
|
||||
|
||||
typedef struct
|
||||
{
|
||||
int size;
|
||||
void *lfbPtr;
|
||||
FxU32 strideInBytes;
|
||||
GrLfbWriteMode_t writeMode;
|
||||
GrOriginLocation_t origin;
|
||||
}
|
||||
GrLfbInfo_t;
|
||||
|
||||
typedef FxI32 GrLOD_t;
|
||||
#define GR_LOD_LOG2_2048 0xb
|
||||
#define GR_LOD_LOG2_1024 0xa
|
||||
#define GR_LOD_LOG2_512 0x9
|
||||
#define GR_LOD_LOG2_256 0x8
|
||||
#define GR_LOD_LOG2_128 0x7
|
||||
#define GR_LOD_LOG2_64 0x6
|
||||
#define GR_LOD_LOG2_32 0x5
|
||||
#define GR_LOD_LOG2_16 0x4
|
||||
#define GR_LOD_LOG2_8 0x3
|
||||
#define GR_LOD_LOG2_4 0x2
|
||||
#define GR_LOD_LOG2_2 0x1
|
||||
#define GR_LOD_LOG2_1 0x0
|
||||
|
||||
typedef FxI32 GrMipMapMode_t;
|
||||
#define GR_MIPMAP_DISABLE 0x0
|
||||
#define GR_MIPMAP_NEAREST 0x1
|
||||
#define GR_MIPMAP_NEAREST_DITHER 0x2
|
||||
|
||||
typedef FxI32 GrSmoothingMode_t;
|
||||
#define GR_SMOOTHING_DISABLE 0x0
|
||||
#define GR_SMOOTHING_ENABLE 0x1
|
||||
|
||||
typedef FxI32 GrTextureClampMode_t;
|
||||
#define GR_TEXTURECLAMP_WRAP 0x0
|
||||
#define GR_TEXTURECLAMP_CLAMP 0x1
|
||||
#define GR_TEXTURECLAMP_MIRROR_EXT 0x2
|
||||
|
||||
typedef FxI32 GrTextureCombineFnc_t;
|
||||
#define GR_TEXTURECOMBINE_ZERO 0x0
|
||||
#define GR_TEXTURECOMBINE_DECAL 0x1
|
||||
#define GR_TEXTURECOMBINE_OTHER 0x2
|
||||
#define GR_TEXTURECOMBINE_ADD 0x3
|
||||
#define GR_TEXTURECOMBINE_MULTIPLY 0x4
|
||||
#define GR_TEXTURECOMBINE_SUBTRACT 0x5
|
||||
#define GR_TEXTURECOMBINE_DETAIL 0x6
|
||||
#define GR_TEXTURECOMBINE_DETAIL_OTHER 0x7
|
||||
#define GR_TEXTURECOMBINE_TRILINEAR_ODD 0x8
|
||||
#define GR_TEXTURECOMBINE_TRILINEAR_EVEN 0x9
|
||||
#define GR_TEXTURECOMBINE_ONE 0xa
|
||||
|
||||
typedef FxI32 GrTextureFilterMode_t;
|
||||
#define GR_TEXTUREFILTER_POINT_SAMPLED 0x0
|
||||
#define GR_TEXTUREFILTER_BILINEAR 0x1
|
||||
|
||||
typedef FxI32 GrTextureFormat_t;
|
||||
#define GR_TEXFMT_8BIT 0x0
|
||||
#define GR_TEXFMT_RGB_332 GR_TEXFMT_8BIT
|
||||
#define GR_TEXFMT_YIQ_422 0x1
|
||||
#define GR_TEXFMT_ALPHA_8 0x2
|
||||
#define GR_TEXFMT_INTENSITY_8 0x3
|
||||
#define GR_TEXFMT_ALPHA_INTENSITY_44 0x4
|
||||
#define GR_TEXFMT_P_8 0x5
|
||||
#define GR_TEXFMT_RSVD0 0x6
|
||||
#define GR_TEXFMT_RSVD1 0x7
|
||||
#define GR_TEXFMT_16BIT 0x8
|
||||
#define GR_TEXFMT_ARGB_8332 GR_TEXFMT_16BIT
|
||||
#define GR_TEXFMT_AYIQ_8422 0x9
|
||||
#define GR_TEXFMT_RGB_565 0xa
|
||||
#define GR_TEXFMT_ARGB_1555 0xb
|
||||
#define GR_TEXFMT_ARGB_4444 0xc
|
||||
#define GR_TEXFMT_ALPHA_INTENSITY_88 0xd
|
||||
#define GR_TEXFMT_AP_88 0xe
|
||||
#define GR_TEXFMT_RSVD2 0xf
|
||||
#define GR_TEXFMT_ARGB_CMP_FXT1 0x11
|
||||
#define GR_TEXFMT_ARGB_8888 0x12
|
||||
#define GR_TEXFMT_YUYV_422 0x13
|
||||
#define GR_TEXFMT_UYVY_422 0x14
|
||||
#define GR_TEXFMT_AYUV_444 0x15
|
||||
#define GR_TEXFMT_ARGB_CMP_DXT1 0x16
|
||||
#define GR_TEXFMT_ARGB_CMP_DXT2 0x17
|
||||
#define GR_TEXFMT_ARGB_CMP_DXT3 0x18
|
||||
#define GR_TEXFMT_ARGB_CMP_DXT4 0x19
|
||||
#define GR_TEXFMT_ARGB_CMP_DXT5 0x1A
|
||||
|
||||
typedef FxU32 GrTexTable_t;
|
||||
#define GR_TEXTABLE_NCC0 0x0
|
||||
#define GR_TEXTABLE_NCC1 0x1
|
||||
#define GR_TEXTABLE_PALETTE 0x2
|
||||
#define GR_TEXTABLE_PALETTE_6666_EXT 0x3
|
||||
|
||||
typedef FxU32 GrNCCTable_t;
|
||||
#define GR_NCCTABLE_NCC0 0x0
|
||||
#define GR_NCCTABLE_NCC1 0x1
|
||||
|
||||
typedef FxU32 GrTexBaseRange_t;
|
||||
#define GR_TEXBASE_256 0x3
|
||||
#define GR_TEXBASE_128 0x2
|
||||
#define GR_TEXBASE_64 0x1
|
||||
#define GR_TEXBASE_32_TO_1 0x0
|
||||
#define GR_TEXBASE_2048 0x7
|
||||
#define GR_TEXBASE_1024 0x6
|
||||
#define GR_TEXBASE_512 0x5
|
||||
#define GR_TEXBASE_256_TO_1 0x4
|
||||
|
||||
typedef FxU32 GrEnableMode_t;
|
||||
#define GR_MODE_DISABLE 0x0
|
||||
#define GR_MODE_ENABLE 0x1
|
||||
|
||||
#define GR_AA_ORDERED 0x01
|
||||
#define GR_ALLOW_MIPMAP_DITHER 0x02
|
||||
#define GR_PASSTHRU 0x03
|
||||
#define GR_SHAMELESS_PLUG 0x04
|
||||
#define GR_VIDEO_SMOOTHING 0x05
|
||||
|
||||
typedef FxU32 GrCoordinateSpaceMode_t;
|
||||
#define GR_WINDOW_COORDS 0x00
|
||||
#define GR_CLIP_COORDS 0x01
|
||||
|
||||
/* Parameters for strips */
|
||||
#define GR_PARAM_XY 0x01
|
||||
#define GR_PARAM_Z 0x02
|
||||
#define GR_PARAM_W 0x03
|
||||
#define GR_PARAM_Q 0x04
|
||||
#define GR_PARAM_FOG_EXT 0x05
|
||||
|
||||
#define GR_PARAM_A 0x10
|
||||
|
||||
#define GR_PARAM_RGB 0x20
|
||||
|
||||
#define GR_PARAM_PARGB 0x30
|
||||
|
||||
#define GR_PARAM_ST0 0x40
|
||||
#define GR_PARAM_ST1 GR_PARAM_ST0+1
|
||||
#define GR_PARAM_ST2 GR_PARAM_ST0+2
|
||||
|
||||
#define GR_PARAM_Q0 0x50
|
||||
#define GR_PARAM_Q1 GR_PARAM_Q0+1
|
||||
#define GR_PARAM_Q2 GR_PARAM_Q0+2
|
||||
|
||||
#define GR_PARAM_DISABLE 0x00
|
||||
#define GR_PARAM_ENABLE 0x01
|
||||
|
||||
/* grDrawVertexArray/grDrawVertexArrayContiguous */
|
||||
#define GR_POINTS 0
|
||||
#define GR_LINE_STRIP 1
|
||||
#define GR_LINES 2
|
||||
#define GR_POLYGON 3
|
||||
#define GR_TRIANGLE_STRIP 4
|
||||
#define GR_TRIANGLE_FAN 5
|
||||
#define GR_TRIANGLES 6
|
||||
#define GR_TRIANGLE_STRIP_CONTINUE 7
|
||||
#define GR_TRIANGLE_FAN_CONTINUE 8
|
||||
|
||||
/* grGet/grReset */
|
||||
#define GR_BITS_DEPTH 0x01
|
||||
#define GR_BITS_RGBA 0x02
|
||||
#define GR_FIFO_FULLNESS 0x03
|
||||
#define GR_FOG_TABLE_ENTRIES 0x04
|
||||
#define GR_GAMMA_TABLE_ENTRIES 0x05
|
||||
#define GR_GLIDE_STATE_SIZE 0x06
|
||||
#define GR_GLIDE_VERTEXLAYOUT_SIZE 0x07
|
||||
#define GR_IS_BUSY 0x08
|
||||
#define GR_LFB_PIXEL_PIPE 0x09
|
||||
#define GR_MAX_TEXTURE_SIZE 0x0a
|
||||
#define GR_MAX_TEXTURE_ASPECT_RATIO 0x0b
|
||||
#define GR_MEMORY_FB 0x0c
|
||||
#define GR_MEMORY_TMU 0x0d
|
||||
#define GR_MEMORY_UMA 0x0e
|
||||
#define GR_NUM_BOARDS 0x0f
|
||||
#define GR_NON_POWER_OF_TWO_TEXTURES 0x10
|
||||
#define GR_NUM_FB 0x11
|
||||
#define GR_NUM_SWAP_HISTORY_BUFFER 0x12
|
||||
#define GR_NUM_TMU 0x13
|
||||
#define GR_PENDING_BUFFERSWAPS 0x14
|
||||
#define GR_REVISION_FB 0x15
|
||||
#define GR_REVISION_TMU 0x16
|
||||
#define GR_STATS_LINES 0x17
|
||||
#define GR_STATS_PIXELS_AFUNC_FAIL 0x18
|
||||
#define GR_STATS_PIXELS_CHROMA_FAIL 0x19
|
||||
#define GR_STATS_PIXELS_DEPTHFUNC_FAIL 0x1a
|
||||
#define GR_STATS_PIXELS_IN 0x1b
|
||||
#define GR_STATS_PIXELS_OUT 0x1c
|
||||
#define GR_STATS_PIXELS 0x1d
|
||||
#define GR_STATS_POINTS 0x1e
|
||||
#define GR_STATS_TRIANGLES_IN 0x1f
|
||||
#define GR_STATS_TRIANGLES_OUT 0x20
|
||||
#define GR_STATS_TRIANGLES 0x21
|
||||
#define GR_SWAP_HISTORY 0x22
|
||||
#define GR_SUPPORTS_PASSTHRU 0x23
|
||||
#define GR_TEXTURE_ALIGN 0x24
|
||||
#define GR_VIDEO_POSITION 0x25
|
||||
#define GR_VIEWPORT 0x26
|
||||
#define GR_WDEPTH_MIN_MAX 0x27
|
||||
#define GR_ZDEPTH_MIN_MAX 0x28
|
||||
#define GR_VERTEX_PARAMETER 0x29
|
||||
#define GR_BITS_GAMMA 0x2a
|
||||
#define GR_GET_RESERVED_1 0x1000
|
||||
|
||||
/* grGetString types */
|
||||
#define GR_EXTENSION 0xa0
|
||||
#define GR_HARDWARE 0xa1
|
||||
#define GR_RENDERER 0xa2
|
||||
#define GR_VENDOR 0xa3
|
||||
#define GR_VERSION 0xa4
|
||||
|
||||
typedef FxI32 GrScreenRefresh_t;
|
||||
#define GR_REFRESH_NONE 0xff
|
||||
|
||||
typedef FxI32 GrScreenResolution_t;
|
||||
#define GR_RESOLUTION_NONE 0xff
|
||||
|
||||
typedef struct
|
||||
{
|
||||
GrLOD_t smallLodLog2;
|
||||
GrLOD_t largeLodLog2;
|
||||
GrAspectRatio_t aspectRatioLog2;
|
||||
GrTextureFormat_t format;
|
||||
void *data;
|
||||
}
|
||||
GrTexInfo;
|
||||
|
||||
typedef struct GrSstPerfStats_s
|
||||
{
|
||||
FxU32 pixelsIn;
|
||||
FxU32 chromaFail;
|
||||
FxU32 zFuncFail;
|
||||
FxU32 aFuncFail;
|
||||
FxU32 pixelsOut;
|
||||
}
|
||||
GrSstPerfStats_t;
|
||||
|
||||
typedef struct
|
||||
{
|
||||
GrScreenResolution_t resolution;
|
||||
GrScreenRefresh_t refresh;
|
||||
int numColorBuffers;
|
||||
int numAuxBuffers;
|
||||
}
|
||||
GrResolution;
|
||||
|
||||
typedef GrResolution GlideResolution;
|
||||
#define GR_QUERY_ANY ((FxU32)(~0))
|
||||
|
||||
typedef FxU32 GrLfbSrcFmt_t;
|
||||
#define GR_LFB_SRC_FMT_565 0x00
|
||||
#define GR_LFB_SRC_FMT_555 0x01
|
||||
#define GR_LFB_SRC_FMT_1555 0x02
|
||||
#define GR_LFB_SRC_FMT_888 0x04
|
||||
#define GR_LFB_SRC_FMT_8888 0x05
|
||||
#define GR_LFB_SRC_FMT_565_DEPTH 0x0c
|
||||
#define GR_LFB_SRC_FMT_555_DEPTH 0x0d
|
||||
#define GR_LFB_SRC_FMT_1555_DEPTH 0x0e
|
||||
#define GR_LFB_SRC_FMT_ZA16 0x0f
|
||||
#define GR_LFB_SRC_FMT_RLE16 0x80
|
||||
|
||||
typedef FxU32 GrPixelFormat_t;
|
||||
#define GR_PIXFMT_I_8 0x0001
|
||||
#define GR_PIXFMT_AI_88 0x0002
|
||||
#define GR_PIXFMT_RGB_565 0x0003
|
||||
#define GR_PIXFMT_ARGB_1555 0x0004
|
||||
#define GR_PIXFMT_ARGB_8888 0x0005
|
||||
#define GR_PIXFMT_AA_2_RGB_565 0x0006
|
||||
#define GR_PIXFMT_AA_2_ARGB_1555 0x0007
|
||||
#define GR_PIXFMT_AA_2_ARGB_8888 0x0008
|
||||
#define GR_PIXFMT_AA_4_RGB_565 0x0009
|
||||
#define GR_PIXFMT_AA_4_ARGB_1555 0x000a
|
||||
#define GR_PIXFMT_AA_4_ARGB_8888 0x000b
|
||||
|
||||
#define GR_LFBWRITEMODE_Z32 0x0008
|
||||
|
||||
typedef FxU32 GrAAMode_t;
|
||||
#define GR_AA_NONE 0x0000
|
||||
#define GR_AA_4SAMPLES 0x0001
|
||||
|
||||
typedef FxU8 GrStencil_t;
|
||||
|
||||
typedef FxU32 GrStencilOp_t;
|
||||
#define GR_STENCILOP_KEEP 0x00
|
||||
#define GR_STENCILOP_ZERO 0x01
|
||||
#define GR_STENCILOP_REPLACE 0x02
|
||||
#define GR_STENCILOP_INCR_CLAMP 0x03
|
||||
#define GR_STENCILOP_DECR_CLAMP 0x04
|
||||
#define GR_STENCILOP_INVERT 0x05
|
||||
#define GR_STENCILOP_INCR_WRAP 0x06
|
||||
#define GR_STENCILOP_DECR_WRAP 0x07
|
||||
|
||||
#define GR_TEXTURE_UMA_EXT 0x06
|
||||
#define GR_STENCIL_MODE_EXT 0x07
|
||||
#define GR_OPENGL_MODE_EXT 0x08
|
||||
|
||||
typedef FxU32 GrCCUColor_t;
|
||||
typedef FxU32 GrACUColor_t;
|
||||
typedef FxU32 GrTCCUColor_t;
|
||||
typedef FxU32 GrTACUColor_t;
|
||||
#define GR_CMBX_ZERO 0x00
|
||||
#define GR_CMBX_TEXTURE_ALPHA 0x01
|
||||
#define GR_CMBX_ALOCAL 0x02
|
||||
#define GR_CMBX_AOTHER 0x03
|
||||
#define GR_CMBX_B 0x04
|
||||
#define GR_CMBX_CONSTANT_ALPHA 0x05
|
||||
#define GR_CMBX_CONSTANT_COLOR 0x06
|
||||
#define GR_CMBX_DETAIL_FACTOR 0x07
|
||||
#define GR_CMBX_ITALPHA 0x08
|
||||
#define GR_CMBX_ITRGB 0x09
|
||||
#define GR_CMBX_LOCAL_TEXTURE_ALPHA 0x0a
|
||||
#define GR_CMBX_LOCAL_TEXTURE_RGB 0x0b
|
||||
#define GR_CMBX_LOD_FRAC 0x0c
|
||||
#define GR_CMBX_OTHER_TEXTURE_ALPHA 0x0d
|
||||
#define GR_CMBX_OTHER_TEXTURE_RGB 0x0e
|
||||
#define GR_CMBX_TEXTURE_RGB 0x0f
|
||||
#define GR_CMBX_TMU_CALPHA 0x10
|
||||
#define GR_CMBX_TMU_CCOLOR 0x11
|
||||
|
||||
typedef FxU32 GrCombineMode_t;
|
||||
#define GR_FUNC_MODE_ZERO 0x00
|
||||
#define GR_FUNC_MODE_X 0x01
|
||||
#define GR_FUNC_MODE_ONE_MINUS_X 0x02
|
||||
#define GR_FUNC_MODE_NEGATIVE_X 0x03
|
||||
#define GR_FUNC_MODE_X_MINUS_HALF 0x04
|
||||
|
||||
typedef FxU32 GrAlphaBlendOp_t;
|
||||
#define GR_BLEND_OP_ADD 0x00
|
||||
#define GR_BLEND_OP_SUB 0x01
|
||||
#define GR_BLEND_OP_REVSUB 0x02
|
||||
|
||||
typedef struct
|
||||
{
|
||||
FxU32 data[256];
|
||||
}
|
||||
GuTexPalette;
|
||||
|
||||
typedef void (*GrErrorCallbackFnc_t) (const char *string, FxBool fatal);
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,90 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_lock.c,v 1.5 2002/12/16 16:19:00 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_lock.h"
|
||||
#include "tdfx_state.h"
|
||||
#include "tdfx_render.h"
|
||||
#include "tdfx_texman.h"
|
||||
#include "tdfx_tris.h"
|
||||
|
||||
|
||||
void tdfxGetLock( tdfxContextPtr fxMesa )
|
||||
{
|
||||
__DRIcontextPrivate *cPriv = fxMesa->driContext;
|
||||
__DRIdrawablePrivate *dPriv = cPriv->driDrawablePriv;
|
||||
__DRIscreenPrivate *sPriv = dPriv->driScreenPriv;
|
||||
TDFXSAREAPriv *saPriv = (TDFXSAREAPriv *) (((char *) sPriv->pSAREA) +
|
||||
fxMesa->fxScreen->sarea_priv_offset);
|
||||
unsigned int stamp = dPriv->lastStamp;
|
||||
|
||||
drmGetLock( fxMesa->driFd, fxMesa->hHWContext, 0 );
|
||||
|
||||
/* This macro will update dPriv's cliprects if needed */
|
||||
DRI_VALIDATE_DRAWABLE_INFO( sPriv, dPriv );
|
||||
|
||||
if ( saPriv->fifoOwner != fxMesa->hHWContext ) {
|
||||
fxMesa->Glide.grDRIImportFifo( saPriv->fifoPtr, saPriv->fifoRead );
|
||||
}
|
||||
|
||||
if ( saPriv->ctxOwner != fxMesa->hHWContext ) {
|
||||
/* This sequence looks a little odd. Glide mirrors the state, and
|
||||
* when you get the state you are forcing the mirror to be up to
|
||||
* date, and then getting a copy from the mirror. You can then force
|
||||
* that state onto the hardware when you set the state.
|
||||
*/
|
||||
void *state;
|
||||
FxI32 stateSize;
|
||||
fxMesa->Glide.grGet(GR_GLIDE_STATE_SIZE, 4, &stateSize);
|
||||
state = malloc(stateSize);
|
||||
fxMesa->Glide.grGlideGetState( state );
|
||||
fxMesa->Glide.grGlideSetState( state );
|
||||
free( state );
|
||||
}
|
||||
|
||||
#if 0
|
||||
if ( saPriv->texOwner != fxMesa->hHWContext ) {
|
||||
tdfxTMRestoreTextures_NoLock( fxMesa );
|
||||
}
|
||||
#endif
|
||||
|
||||
if ( *dPriv->pStamp != stamp || saPriv->ctxOwner != fxMesa->hHWContext ) {
|
||||
tdfxUpdateClipping(fxMesa->glCtx);
|
||||
tdfxUploadClipping(fxMesa);
|
||||
}
|
||||
|
||||
DEBUG_LOCK();
|
||||
}
|
||||
@@ -0,0 +1,149 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_lock.h,v 1.3 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_LOCK_H__
|
||||
#define __TDFX_LOCK_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
/* You can turn this on to find locking conflicts.
|
||||
*/
|
||||
#define DEBUG_LOCKING 0
|
||||
|
||||
#if DEBUG_LOCKING
|
||||
extern char *prevLockFile;
|
||||
extern int prevLockLine;
|
||||
|
||||
#define DEBUG_LOCK() \
|
||||
do { \
|
||||
prevLockFile = (__FILE__); \
|
||||
prevLockLine = (__LINE__); \
|
||||
} while (0)
|
||||
|
||||
#define DEBUG_RESET() \
|
||||
do { \
|
||||
prevLockFile = 0; \
|
||||
prevLockLine = 0; \
|
||||
} while (0)
|
||||
|
||||
#define DEBUG_CHECK_LOCK() \
|
||||
do { \
|
||||
if ( prevLockFile ) { \
|
||||
fprintf( stderr, \
|
||||
"LOCK SET!\n\tPrevious %s:%d\n\tCurrent: %s:%d\n", \
|
||||
prevLockFile, prevLockLine, __FILE__, __LINE__ ); \
|
||||
exit( 1 ); \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#else
|
||||
|
||||
#define DEBUG_LOCK()
|
||||
#define DEBUG_RESET()
|
||||
#define DEBUG_CHECK_LOCK()
|
||||
|
||||
#endif /* DEBUG_LOCKING */
|
||||
|
||||
|
||||
extern void tdfxGetLock( tdfxContextPtr fxMesa );
|
||||
|
||||
|
||||
/* !!! We may want to separate locks from locks with validation.
|
||||
This could be used to improve performance for those things
|
||||
commands that do not do any drawing !!! */
|
||||
|
||||
#define DRM_LIGHT_LOCK_RETURN(fd,lock,context,__ret) \
|
||||
do { \
|
||||
DRM_CAS(lock,context,DRM_LOCK_HELD|context,__ret); \
|
||||
if (__ret) drmGetLock(fd,context,0); \
|
||||
} while(0)
|
||||
|
||||
#define LOCK_HARDWARE( fxMesa ) \
|
||||
do { \
|
||||
char __ret = 0; \
|
||||
\
|
||||
DEBUG_CHECK_LOCK(); \
|
||||
DRM_CAS( fxMesa->driHwLock, fxMesa->hHWContext, \
|
||||
DRM_LOCK_HELD | fxMesa->hHWContext, __ret ); \
|
||||
if ( __ret ) { \
|
||||
tdfxGetLock( fxMesa ); \
|
||||
} \
|
||||
DEBUG_LOCK(); \
|
||||
} while (0)
|
||||
|
||||
/* Unlock the hardware using the global current context */
|
||||
#define UNLOCK_HARDWARE( fxMesa ) \
|
||||
do { \
|
||||
DRM_UNLOCK( fxMesa->driFd, fxMesa->driHwLock, fxMesa->hHWContext ); \
|
||||
DEBUG_RESET(); \
|
||||
} while (0)
|
||||
|
||||
/*
|
||||
* This pair of macros makes a loop over the drawing operations
|
||||
* so it is not self contained and doesn't have the nice single
|
||||
* statement semantics of most macros.
|
||||
*/
|
||||
#define BEGIN_CLIP_LOOP(fxMesa) \
|
||||
do { \
|
||||
LOCK_HARDWARE( fxMesa ); \
|
||||
BEGIN_CLIP_LOOP_LOCKED( fxMesa )
|
||||
|
||||
#define BEGIN_CLIP_LOOP_LOCKED(fxMesa) \
|
||||
do { \
|
||||
int _nc = fxMesa->numClipRects; \
|
||||
while (_nc--) { \
|
||||
if (fxMesa->numClipRects > 1) { \
|
||||
int _height = fxMesa->screen_height; \
|
||||
fxMesa->Glide.grClipWindow(fxMesa->pClipRects[_nc].x1, \
|
||||
_height - fxMesa->pClipRects[_nc].y2, \
|
||||
fxMesa->pClipRects[_nc].x2, \
|
||||
_height - fxMesa->pClipRects[_nc].y1); \
|
||||
}
|
||||
|
||||
|
||||
#define END_CLIP_LOOP_LOCKED( fxMesa ) \
|
||||
} \
|
||||
} while (0)
|
||||
|
||||
#define END_CLIP_LOOP( fxMesa ) \
|
||||
END_CLIP_LOOP_LOCKED( fxMesa ); \
|
||||
UNLOCK_HARDWARE( fxMesa ); \
|
||||
} while (0)
|
||||
|
||||
|
||||
#endif /* GLX_DIRECT_RENDERING */
|
||||
|
||||
#endif /* __TDFX_LOCK_H__ */
|
||||
@@ -0,0 +1,689 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_pixels.c,v 1.4 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
* Nathan Hand <nhand@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_dd.h"
|
||||
#include "tdfx_lock.h"
|
||||
#include "tdfx_vb.h"
|
||||
#include "tdfx_pixels.h"
|
||||
#include "tdfx_render.h"
|
||||
|
||||
#include "swrast/swrast.h"
|
||||
|
||||
#include "image.h"
|
||||
|
||||
|
||||
#define FX_grLfbWriteRegion(fxMesa,dst_buffer,dst_x,dst_y,src_format,src_width,src_height,src_stride,src_data) \
|
||||
do { \
|
||||
LOCK_HARDWARE(fxMesa); \
|
||||
fxMesa->Glide.grLfbWriteRegion(dst_buffer,dst_x,dst_y,src_format,src_width,src_height,FXFALSE,src_stride,src_data); \
|
||||
UNLOCK_HARDWARE(fxMesa); \
|
||||
} while(0)
|
||||
|
||||
|
||||
#define FX_grLfbReadRegion(fxMesa,src_buffer,src_x,src_y,src_width,src_height,dst_stride,dst_data) \
|
||||
do { \
|
||||
LOCK_HARDWARE(fxMesa); \
|
||||
fxMesa->Glide.grLfbReadRegion(src_buffer,src_x,src_y,src_width,src_height,dst_stride,dst_data); \
|
||||
UNLOCK_HARDWARE(fxMesa); \
|
||||
} while (0);
|
||||
|
||||
|
||||
#if 0
|
||||
static FxBool
|
||||
FX_grLfbLock(tdfxContextPtr fxMesa, GrLock_t type, GrBuffer_t buffer,
|
||||
GrLfbWriteMode_t writeMode, GrOriginLocation_t origin,
|
||||
FxBool pixelPipeline, GrLfbInfo_t * info)
|
||||
{
|
||||
FxBool result;
|
||||
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
result = fxMesa->Glide.grLfbLock(type, buffer, writeMode, origin, pixelPipeline, info);
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
return result;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#define FX_grLfbUnlock(fxMesa, t, b) \
|
||||
do { \
|
||||
LOCK_HARDWARE(fxMesa); \
|
||||
fxMesa->Glide.grLfbUnlock(t, b); \
|
||||
UNLOCK_HARDWARE(fxMesa); \
|
||||
} while (0)
|
||||
|
||||
|
||||
|
||||
#if 0
|
||||
/* test if window coord (px,py) is visible */
|
||||
static GLboolean
|
||||
inClipRects(tdfxContextPtr fxMesa, int px, int py)
|
||||
{
|
||||
int i;
|
||||
for (i = 0; i < fxMesa->numClipRects; i++) {
|
||||
if ((px >= fxMesa->pClipRects[i].x1) &&
|
||||
(px < fxMesa->pClipRects[i].x2) &&
|
||||
(py >= fxMesa->pClipRects[i].y1) &&
|
||||
(py < fxMesa->pClipRects[i].y2)) return GL_TRUE;
|
||||
}
|
||||
return GL_FALSE;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* test if rectangle of pixels (px,py) (px+width,py+height) is visible */
|
||||
static GLboolean
|
||||
inClipRects_Region(tdfxContextPtr fxMesa, int x, int y, int width, int height)
|
||||
{
|
||||
int i;
|
||||
int x1, y1, x2, y2;
|
||||
int xmin, xmax, ymin, ymax, pixelsleft;
|
||||
|
||||
y1 = y - height + 1; y2 = y;
|
||||
x1 = x; x2 = x + width - 1;
|
||||
pixelsleft = width * height;
|
||||
|
||||
for (i = 0; i < fxMesa->numClipRects; i++)
|
||||
{
|
||||
/* algorithm requires x1 < x2 and y1 < y2 */
|
||||
if ((fxMesa->pClipRects[i].x1 < fxMesa->pClipRects[i].x2)) {
|
||||
xmin = fxMesa->pClipRects[i].x1;
|
||||
xmax = fxMesa->pClipRects[i].x2-1;
|
||||
} else {
|
||||
xmin = fxMesa->pClipRects[i].x2;
|
||||
xmax = fxMesa->pClipRects[i].x1-1;
|
||||
}
|
||||
if ((fxMesa->pClipRects[i].y1 < fxMesa->pClipRects[i].y2)) {
|
||||
ymin = fxMesa->pClipRects[i].y1;
|
||||
ymax = fxMesa->pClipRects[i].y2-1;
|
||||
} else {
|
||||
ymin = fxMesa->pClipRects[i].y2;
|
||||
ymax = fxMesa->pClipRects[i].y1-1;
|
||||
}
|
||||
|
||||
/* reject trivial cases */
|
||||
if (xmax < x1) continue;
|
||||
if (ymax < y1) continue;
|
||||
if (xmin > x2) continue;
|
||||
if (ymin > y2) continue;
|
||||
|
||||
/* find the intersection */
|
||||
if (xmin < x1) xmin = x1;
|
||||
if (ymin < y1) ymin = y1;
|
||||
if (xmax > x2) xmax = x2;
|
||||
if (ymax > y2) ymax = y2;
|
||||
|
||||
pixelsleft -= (xmax-xmin+1) * (ymax-ymin+1);
|
||||
}
|
||||
|
||||
return pixelsleft == 0;
|
||||
}
|
||||
|
||||
#if 0
|
||||
GLboolean
|
||||
tdfx_bitmap_R5G6B5(GLcontext * ctx, GLint px, GLint py,
|
||||
GLsizei width, GLsizei height,
|
||||
const struct gl_pixelstore_attrib *unpack,
|
||||
const GLubyte * bitmap)
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GrLfbInfo_t info;
|
||||
TdfxU16 color;
|
||||
const struct gl_pixelstore_attrib *finalUnpack;
|
||||
struct gl_pixelstore_attrib scissoredUnpack;
|
||||
|
||||
/* check if there's any raster operations enabled which we can't handle */
|
||||
if (ctx->RasterMask & (ALPHATEST_BIT |
|
||||
BLEND_BIT |
|
||||
DEPTH_BIT |
|
||||
FOG_BIT |
|
||||
LOGIC_OP_BIT |
|
||||
SCISSOR_BIT |
|
||||
STENCIL_BIT |
|
||||
MASKING_BIT |
|
||||
ALPHABUF_BIT | MULTI_DRAW_BIT)) return GL_FALSE;
|
||||
|
||||
if (ctx->Scissor.Enabled) {
|
||||
/* This is a bit tricky, but by carefully adjusting the px, py,
|
||||
* width, height, skipPixels and skipRows values we can do
|
||||
* scissoring without special code in the rendering loop.
|
||||
*/
|
||||
|
||||
/* we'll construct a new pixelstore struct */
|
||||
finalUnpack = &scissoredUnpack;
|
||||
scissoredUnpack = *unpack;
|
||||
if (scissoredUnpack.RowLength == 0)
|
||||
scissoredUnpack.RowLength = width;
|
||||
|
||||
/* clip left */
|
||||
if (px < ctx->Scissor.X) {
|
||||
scissoredUnpack.SkipPixels += (ctx->Scissor.X - px);
|
||||
width -= (ctx->Scissor.X - px);
|
||||
px = ctx->Scissor.X;
|
||||
}
|
||||
/* clip right */
|
||||
if (px + width >= ctx->Scissor.X + ctx->Scissor.Width) {
|
||||
width -= (px + width - (ctx->Scissor.X + ctx->Scissor.Width));
|
||||
}
|
||||
/* clip bottom */
|
||||
if (py < ctx->Scissor.Y) {
|
||||
scissoredUnpack.SkipRows += (ctx->Scissor.Y - py);
|
||||
height -= (ctx->Scissor.Y - py);
|
||||
py = ctx->Scissor.Y;
|
||||
}
|
||||
/* clip top */
|
||||
if (py + height >= ctx->Scissor.Y + ctx->Scissor.Height) {
|
||||
height -= (py + height - (ctx->Scissor.Y + ctx->Scissor.Height));
|
||||
}
|
||||
|
||||
if (width <= 0 || height <= 0)
|
||||
return GL_TRUE; /* totally scissored away */
|
||||
}
|
||||
else {
|
||||
finalUnpack = unpack;
|
||||
}
|
||||
|
||||
/* compute pixel value */
|
||||
{
|
||||
GLint r = (GLint) (ctx->Current.RasterColor[0] * 255.0f);
|
||||
GLint g = (GLint) (ctx->Current.RasterColor[1] * 255.0f);
|
||||
GLint b = (GLint) (ctx->Current.RasterColor[2] * 255.0f);
|
||||
/*GLint a = (GLint)(ctx->Current.RasterColor[3]*255.0f); */
|
||||
if (fxMesa->bgrOrder) {
|
||||
color = (TdfxU16)
|
||||
(((TdfxU16) 0xf8 & b) << (11 - 3)) |
|
||||
(((TdfxU16) 0xfc & g) << (5 - 3 + 1)) |
|
||||
(((TdfxU16) 0xf8 & r) >> 3);
|
||||
}
|
||||
else
|
||||
color = (TdfxU16)
|
||||
(((TdfxU16) 0xf8 & r) << (11 - 3)) |
|
||||
(((TdfxU16) 0xfc & g) << (5 - 3 + 1)) |
|
||||
(((TdfxU16) 0xf8 & b) >> 3);
|
||||
}
|
||||
|
||||
info.size = sizeof(info);
|
||||
if (!TDFX_grLfbLock(fxMesa,
|
||||
GR_LFB_WRITE_ONLY,
|
||||
fxMesa->currentFB,
|
||||
GR_LFBWRITEMODE_565,
|
||||
GR_ORIGIN_UPPER_LEFT, FXFALSE, &info)) {
|
||||
#ifndef TDFX_SILENT
|
||||
fprintf(stderr, "tdfx Driver: error locking the linear frame buffer\n");
|
||||
#endif
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
{
|
||||
const GLint winX = fxMesa->x_offset;
|
||||
const GLint winY = fxMesa->y_offset + fxMesa->height - 1;
|
||||
/* The dest stride depends on the hardware and whether we're drawing
|
||||
* to the front or back buffer. This compile-time test seems to do
|
||||
* the job for now.
|
||||
*/
|
||||
const GLint dstStride = (fxMesa->glCtx->Color.DrawBuffer == GL_FRONT)
|
||||
? (fxMesa->screen_width) : (info.strideInBytes / 2);
|
||||
GLint row;
|
||||
/* compute dest address of bottom-left pixel in bitmap */
|
||||
GLushort *dst = (GLushort *) info.lfbPtr
|
||||
+ (winY - py) * dstStride + (winX + px);
|
||||
|
||||
for (row = 0; row < height; row++) {
|
||||
const GLubyte *src =
|
||||
(const GLubyte *) _mesa_image_address(finalUnpack,
|
||||
bitmap, width, height,
|
||||
GL_COLOR_INDEX,
|
||||
GL_BITMAP, 0, row, 0);
|
||||
if (finalUnpack->LsbFirst) {
|
||||
/* least significan bit first */
|
||||
GLubyte mask = 1U << (finalUnpack->SkipPixels & 0x7);
|
||||
GLint col;
|
||||
for (col = 0; col < width; col++) {
|
||||
if (*src & mask) {
|
||||
if (inClipRects(fxMesa, winX + px + col, winY - py - row))
|
||||
dst[col] = color;
|
||||
}
|
||||
if (mask == 128U) {
|
||||
src++;
|
||||
mask = 1U;
|
||||
}
|
||||
else {
|
||||
mask = mask << 1;
|
||||
}
|
||||
}
|
||||
if (mask != 1)
|
||||
src++;
|
||||
}
|
||||
else {
|
||||
/* most significan bit first */
|
||||
GLubyte mask = 128U >> (finalUnpack->SkipPixels & 0x7);
|
||||
GLint col;
|
||||
for (col = 0; col < width; col++) {
|
||||
if (*src & mask) {
|
||||
if (inClipRects(fxMesa, winX + px + col, winY - py - row))
|
||||
dst[col] = color;
|
||||
}
|
||||
if (mask == 1U) {
|
||||
src++;
|
||||
mask = 128U;
|
||||
}
|
||||
else {
|
||||
mask = mask >> 1;
|
||||
}
|
||||
}
|
||||
if (mask != 128)
|
||||
src++;
|
||||
}
|
||||
dst -= dstStride;
|
||||
}
|
||||
}
|
||||
|
||||
TDFX_grLfbUnlock(fxMesa, GR_LFB_WRITE_ONLY, fxMesa->currentFB);
|
||||
return GL_TRUE;
|
||||
}
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
GLboolean
|
||||
tdfx_bitmap_R8G8B8A8(GLcontext * ctx, GLint px, GLint py,
|
||||
GLsizei width, GLsizei height,
|
||||
const struct gl_pixelstore_attrib *unpack,
|
||||
const GLubyte * bitmap)
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GrLfbInfo_t info;
|
||||
GLuint color;
|
||||
const struct gl_pixelstore_attrib *finalUnpack;
|
||||
struct gl_pixelstore_attrib scissoredUnpack;
|
||||
|
||||
/* check if there's any raster operations enabled which we can't handle */
|
||||
if (ctx->RasterMask & (ALPHATEST_BIT |
|
||||
BLEND_BIT |
|
||||
DEPTH_BIT |
|
||||
FOG_BIT |
|
||||
LOGIC_OP_BIT |
|
||||
SCISSOR_BIT |
|
||||
STENCIL_BIT |
|
||||
MASKING_BIT |
|
||||
ALPHABUF_BIT | MULTI_DRAW_BIT)) return GL_FALSE;
|
||||
|
||||
if (ctx->Scissor.Enabled) {
|
||||
/* This is a bit tricky, but by carefully adjusting the px, py,
|
||||
* width, height, skipPixels and skipRows values we can do
|
||||
* scissoring without special code in the rendering loop.
|
||||
*/
|
||||
|
||||
/* we'll construct a new pixelstore struct */
|
||||
finalUnpack = &scissoredUnpack;
|
||||
scissoredUnpack = *unpack;
|
||||
if (scissoredUnpack.RowLength == 0)
|
||||
scissoredUnpack.RowLength = width;
|
||||
|
||||
/* clip left */
|
||||
if (px < ctx->Scissor.X) {
|
||||
scissoredUnpack.SkipPixels += (ctx->Scissor.X - px);
|
||||
width -= (ctx->Scissor.X - px);
|
||||
px = ctx->Scissor.X;
|
||||
}
|
||||
/* clip right */
|
||||
if (px + width >= ctx->Scissor.X + ctx->Scissor.Width) {
|
||||
width -= (px + width - (ctx->Scissor.X + ctx->Scissor.Width));
|
||||
}
|
||||
/* clip bottom */
|
||||
if (py < ctx->Scissor.Y) {
|
||||
scissoredUnpack.SkipRows += (ctx->Scissor.Y - py);
|
||||
height -= (ctx->Scissor.Y - py);
|
||||
py = ctx->Scissor.Y;
|
||||
}
|
||||
/* clip top */
|
||||
if (py + height >= ctx->Scissor.Y + ctx->Scissor.Height) {
|
||||
height -= (py + height - (ctx->Scissor.Y + ctx->Scissor.Height));
|
||||
}
|
||||
|
||||
if (width <= 0 || height <= 0)
|
||||
return GL_TRUE; /* totally scissored away */
|
||||
}
|
||||
else {
|
||||
finalUnpack = unpack;
|
||||
}
|
||||
|
||||
/* compute pixel value */
|
||||
{
|
||||
GLint r = (GLint) (ctx->Current.RasterColor[0] * 255.0f);
|
||||
GLint g = (GLint) (ctx->Current.RasterColor[1] * 255.0f);
|
||||
GLint b = (GLint) (ctx->Current.RasterColor[2] * 255.0f);
|
||||
GLint a = (GLint) (ctx->Current.RasterColor[3] * 255.0f);
|
||||
color = PACK_BGRA32(r, g, b, a);
|
||||
}
|
||||
|
||||
info.size = sizeof(info);
|
||||
if (!TDFX_grLfbLock(fxMesa, GR_LFB_WRITE_ONLY,
|
||||
fxMesa->currentFB, GR_LFBWRITEMODE_8888,
|
||||
GR_ORIGIN_UPPER_LEFT, FXFALSE, &info)) {
|
||||
#ifndef TDFX_SILENT
|
||||
fprintf(stderr, "tdfx Driver: error locking the linear frame buffer\n");
|
||||
#endif
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
{
|
||||
const GLint winX = fxMesa->x_offset;
|
||||
const GLint winY = fxMesa->y_offset + fxMesa->height - 1;
|
||||
GLint dstStride;
|
||||
GLuint *dst;
|
||||
GLint row;
|
||||
|
||||
if (fxMesa->glCtx->Color.DrawBuffer == GL_FRONT) {
|
||||
dstStride = fxMesa->screen_width;
|
||||
dst =
|
||||
(GLuint *) info.lfbPtr + (winY - py) * dstStride + (winX +
|
||||
px);
|
||||
}
|
||||
else {
|
||||
dstStride = info.strideInBytes / 4;
|
||||
dst =
|
||||
(GLuint *) info.lfbPtr + (winY - py) * dstStride + (winX +
|
||||
px);
|
||||
}
|
||||
|
||||
/* compute dest address of bottom-left pixel in bitmap */
|
||||
for (row = 0; row < height; row++) {
|
||||
const GLubyte *src =
|
||||
(const GLubyte *) _mesa_image_address(finalUnpack,
|
||||
bitmap, width, height,
|
||||
GL_COLOR_INDEX,
|
||||
GL_BITMAP, 0, row, 0);
|
||||
if (finalUnpack->LsbFirst) {
|
||||
/* least significan bit first */
|
||||
GLubyte mask = 1U << (finalUnpack->SkipPixels & 0x7);
|
||||
GLint col;
|
||||
for (col = 0; col < width; col++) {
|
||||
if (*src & mask) {
|
||||
if (inClipRects(fxMesa, winX + px + col, winY - py - row))
|
||||
dst[col] = color;
|
||||
}
|
||||
if (mask == 128U) {
|
||||
src++;
|
||||
mask = 1U;
|
||||
}
|
||||
else {
|
||||
mask = mask << 1;
|
||||
}
|
||||
}
|
||||
if (mask != 1)
|
||||
src++;
|
||||
}
|
||||
else {
|
||||
/* most significan bit first */
|
||||
GLubyte mask = 128U >> (finalUnpack->SkipPixels & 0x7);
|
||||
GLint col;
|
||||
for (col = 0; col < width; col++) {
|
||||
if (*src & mask) {
|
||||
if (inClipRects(fxMesa, winX + px + col, winY - py - row))
|
||||
dst[col] = color;
|
||||
}
|
||||
if (mask == 1U) {
|
||||
src++;
|
||||
mask = 128U;
|
||||
}
|
||||
else {
|
||||
mask = mask >> 1;
|
||||
}
|
||||
}
|
||||
if (mask != 128)
|
||||
src++;
|
||||
}
|
||||
dst -= dstStride;
|
||||
}
|
||||
}
|
||||
|
||||
TDFX_grLfbUnlock(fxMesa, GR_LFB_WRITE_ONLY, fxMesa->currentFB);
|
||||
return GL_TRUE;
|
||||
}
|
||||
#endif
|
||||
|
||||
void
|
||||
tdfx_readpixels_R5G6B5(GLcontext * ctx, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const struct gl_pixelstore_attrib *packing,
|
||||
GLvoid * dstImage)
|
||||
{
|
||||
if (format != GL_RGB ||
|
||||
type != GL_UNSIGNED_SHORT_5_6_5 ||
|
||||
(ctx->_ImageTransferState & (IMAGE_SCALE_BIAS_BIT|
|
||||
IMAGE_MAP_COLOR_BIT)))
|
||||
{
|
||||
_swrast_ReadPixels( ctx, x, y, width, height, format, type, packing,
|
||||
dstImage );
|
||||
return;
|
||||
}
|
||||
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GrLfbInfo_t info;
|
||||
|
||||
const GLint winX = fxMesa->x_offset;
|
||||
const GLint winY = fxMesa->y_offset + fxMesa->height - 1;
|
||||
const GLint scrX = winX + x;
|
||||
const GLint scrY = winY - y;
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
info.size = sizeof(info);
|
||||
if (fxMesa->Glide.grLfbLock(GR_LFB_READ_ONLY,
|
||||
fxMesa->ReadBuffer,
|
||||
GR_LFBWRITEMODE_ANY,
|
||||
GR_ORIGIN_UPPER_LEFT, FXFALSE, &info)) {
|
||||
const GLint srcStride = (fxMesa->glCtx->Color.DrawBuffer ==
|
||||
GL_FRONT) ? (fxMesa->screen_width) : (info.strideInBytes / 2);
|
||||
const GLushort *src = (const GLushort *) info.lfbPtr
|
||||
+ scrY * srcStride + scrX;
|
||||
GLubyte *dst = (GLubyte *) _mesa_image_address(packing,
|
||||
dstImage, width, height, format, type, 0, 0, 0);
|
||||
const GLint dstStride = _mesa_image_row_stride(packing,
|
||||
width, format, type);
|
||||
|
||||
/* directly memcpy 5R6G5B pixels into client's buffer */
|
||||
const GLint widthInBytes = width * 2;
|
||||
GLint row;
|
||||
for (row = 0; row < height; row++) {
|
||||
MEMCPY(dst, src, widthInBytes);
|
||||
dst += dstStride;
|
||||
src -= srcStride;
|
||||
}
|
||||
|
||||
fxMesa->Glide.grLfbUnlock(GR_LFB_READ_ONLY, fxMesa->ReadBuffer);
|
||||
}
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
tdfx_readpixels_R8G8B8A8(GLcontext * ctx, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const struct gl_pixelstore_attrib *packing,
|
||||
GLvoid * dstImage)
|
||||
{
|
||||
if ((!(format == GL_BGRA && type == GL_UNSIGNED_INT_8_8_8_8) &&
|
||||
!(format == GL_BGRA && type == GL_UNSIGNED_BYTE)) ||
|
||||
(ctx->_ImageTransferState & (IMAGE_SCALE_BIAS_BIT|
|
||||
IMAGE_MAP_COLOR_BIT)))
|
||||
{
|
||||
_swrast_ReadPixels( ctx, x, y, width, height, format, type, packing,
|
||||
dstImage );
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GrLfbInfo_t info;
|
||||
|
||||
const GLint winX = fxMesa->x_offset;
|
||||
const GLint winY = fxMesa->y_offset + fxMesa->height - 1;
|
||||
const GLint scrX = winX + x;
|
||||
const GLint scrY = winY - y;
|
||||
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
info.size = sizeof(info);
|
||||
if (fxMesa->Glide.grLfbLock(GR_LFB_READ_ONLY,
|
||||
fxMesa->ReadBuffer,
|
||||
GR_LFBWRITEMODE_ANY,
|
||||
GR_ORIGIN_UPPER_LEFT, FXFALSE, &info))
|
||||
{
|
||||
const GLint srcStride = (fxMesa->glCtx->Color.DrawBuffer == GL_FRONT)
|
||||
? (fxMesa->screen_width) : (info.strideInBytes / 4);
|
||||
const GLuint *src = (const GLuint *) info.lfbPtr
|
||||
+ scrY * srcStride + scrX;
|
||||
const GLint dstStride =
|
||||
_mesa_image_row_stride(packing, width, format, type);
|
||||
GLubyte *dst = (GLubyte *) _mesa_image_address(packing,
|
||||
dstImage, width, height, format, type, 0, 0, 0);
|
||||
const GLint widthInBytes = width * 4;
|
||||
|
||||
{
|
||||
GLint row;
|
||||
for (row = 0; row < height; row++) {
|
||||
MEMCPY(dst, src, widthInBytes);
|
||||
dst += dstStride;
|
||||
src -= srcStride;
|
||||
}
|
||||
}
|
||||
|
||||
fxMesa->Glide.grLfbUnlock(GR_LFB_READ_ONLY, fxMesa->ReadBuffer);
|
||||
}
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
}
|
||||
|
||||
void
|
||||
tdfx_drawpixels_R8G8B8A8(GLcontext * ctx, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const struct gl_pixelstore_attrib *unpack,
|
||||
const GLvoid * pixels)
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
|
||||
if ((!(format == GL_BGRA && type == GL_UNSIGNED_INT_8_8_8_8) &&
|
||||
!(format == GL_BGRA && type == GL_UNSIGNED_BYTE)) ||
|
||||
ctx->Pixel.ZoomX != 1.0F ||
|
||||
ctx->Pixel.ZoomY != 1.0F ||
|
||||
(ctx->_ImageTransferState & (IMAGE_SCALE_BIAS_BIT|
|
||||
IMAGE_MAP_COLOR_BIT)) ||
|
||||
ctx->Color.AlphaEnabled ||
|
||||
ctx->Depth.Test ||
|
||||
ctx->Fog.Enabled ||
|
||||
ctx->Scissor.Enabled ||
|
||||
ctx->Stencil.Enabled ||
|
||||
!ctx->Color.ColorMask[0] ||
|
||||
!ctx->Color.ColorMask[1] ||
|
||||
!ctx->Color.ColorMask[2] ||
|
||||
!ctx->Color.ColorMask[3] ||
|
||||
ctx->Color.ColorLogicOpEnabled ||
|
||||
ctx->Texture._EnabledUnits ||
|
||||
ctx->Depth.OcclusionTest ||
|
||||
fxMesa->Fallback)
|
||||
{
|
||||
_swrast_DrawPixels( ctx, x, y, width, height, format, type,
|
||||
unpack, pixels );
|
||||
return;
|
||||
}
|
||||
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GrLfbInfo_t info;
|
||||
GLboolean result = GL_FALSE;
|
||||
|
||||
const GLint winX = fxMesa->x_offset;
|
||||
const GLint winY = fxMesa->y_offset + fxMesa->height - 1;
|
||||
const GLint scrX = winX + x;
|
||||
const GLint scrY = winY - y;
|
||||
|
||||
/* lock early to make sure cliprects are right */
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
|
||||
/* make sure hardware has latest blend funcs */
|
||||
if (ctx->Color.BlendEnabled) {
|
||||
fxMesa->dirty |= TDFX_UPLOAD_BLEND_FUNC;
|
||||
tdfxEmitHwStateLocked( fxMesa );
|
||||
}
|
||||
|
||||
/* look for clipmasks, giveup if region obscured */
|
||||
if (fxMesa->glCtx->Color.DrawBuffer == GL_FRONT) {
|
||||
if (!inClipRects_Region(fxMesa, scrX, scrY, width, height)) {
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
_swrast_DrawPixels( ctx, x, y, width, height, format, type,
|
||||
unpack, pixels );
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
info.size = sizeof(info);
|
||||
if (fxMesa->Glide.grLfbLock(GR_LFB_WRITE_ONLY,
|
||||
fxMesa->DrawBuffer,
|
||||
GR_LFBWRITEMODE_8888,
|
||||
GR_ORIGIN_UPPER_LEFT, FXTRUE, &info))
|
||||
{
|
||||
const GLint dstStride = (fxMesa->glCtx->Color.DrawBuffer == GL_FRONT)
|
||||
? (fxMesa->screen_width * 4) : (info.strideInBytes);
|
||||
GLubyte *dst = (GLubyte *) info.lfbPtr
|
||||
+ scrY * dstStride + scrX * 4;
|
||||
const GLint srcStride =
|
||||
_mesa_image_row_stride(unpack, width, format, type);
|
||||
const GLubyte *src = (GLubyte *) _mesa_image_address(unpack,
|
||||
pixels, width, height, format, type, 0, 0, 0);
|
||||
const GLint widthInBytes = width * 4;
|
||||
|
||||
if ((format == GL_BGRA && type == GL_UNSIGNED_INT_8_8_8_8) ||
|
||||
(format == GL_BGRA && type == GL_UNSIGNED_BYTE)) {
|
||||
GLint row;
|
||||
for (row = 0; row < height; row++) {
|
||||
MEMCPY(dst, src, widthInBytes);
|
||||
dst -= dstStride;
|
||||
src += srcStride;
|
||||
}
|
||||
result = GL_TRUE;
|
||||
}
|
||||
|
||||
fxMesa->Glide.grLfbUnlock(GR_LFB_WRITE_ONLY, fxMesa->DrawBuffer);
|
||||
}
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,80 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_pixels.h,v 1.2 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
* Nathan Hand <nhand@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_PIXELS_H__
|
||||
#define __TDFX_PIXELS_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
#include "context.h"
|
||||
|
||||
extern void
|
||||
tdfx_bitmap_R5G6B5( GLcontext *ctx, GLint px, GLint py,
|
||||
GLsizei width, GLsizei height,
|
||||
const struct gl_pixelstore_attrib *unpack,
|
||||
const GLubyte *bitmap );
|
||||
|
||||
extern void
|
||||
tdfx_bitmap_R8G8B8A8( GLcontext *ctx, GLint px, GLint py,
|
||||
GLsizei width, GLsizei height,
|
||||
const struct gl_pixelstore_attrib *unpack,
|
||||
const GLubyte *bitmap );
|
||||
|
||||
extern void
|
||||
tdfx_readpixels_R5G6B5( GLcontext *ctx, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const struct gl_pixelstore_attrib *packing,
|
||||
GLvoid *dstImage );
|
||||
|
||||
extern void
|
||||
tdfx_readpixels_R8G8B8A8( GLcontext *ctx, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const struct gl_pixelstore_attrib *packing,
|
||||
GLvoid *dstImage );
|
||||
|
||||
extern void
|
||||
tdfx_drawpixels_R8G8B8A8( GLcontext *ctx, GLint x, GLint y,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const struct gl_pixelstore_attrib *unpack,
|
||||
const GLvoid *pixels );
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -0,0 +1,802 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_render.c,v 1.4 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_render.h"
|
||||
#include "tdfx_state.h"
|
||||
#include "tdfx_texman.h"
|
||||
#include "swrast/swrast.h"
|
||||
|
||||
/* Clear the color and/or depth buffers.
|
||||
*/
|
||||
static void tdfxDDClear( GLcontext *ctx,
|
||||
GLbitfield mask, GLboolean all,
|
||||
GLint x, GLint y, GLint width, GLint height )
|
||||
{
|
||||
tdfxContextPtr fxMesa = (tdfxContextPtr) ctx->DriverCtx;
|
||||
GLbitfield softwareMask = mask & (DD_ACCUM_BIT);
|
||||
const GLuint stencil_size =
|
||||
fxMesa->haveHwStencil ? fxMesa->glCtx->Visual.stencilBits : 0;
|
||||
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_API ) {
|
||||
fprintf( stderr, "%s( %d, %d, %d, %d )\n",
|
||||
__FUNCTION__, (int) x, (int) y, (int) width, (int) height );
|
||||
}
|
||||
|
||||
/* Need this check to respond to glScissor and clipping updates */
|
||||
if ((fxMesa->new_state & (TDFX_NEW_CLIP | TDFX_NEW_DEPTH)) ||
|
||||
(fxMesa->dirty & TDFX_UPLOAD_COLOR_MASK)) {
|
||||
tdfxDDUpdateHwState(ctx);
|
||||
}
|
||||
|
||||
/* we can't clear accum buffers */
|
||||
mask &= ~(DD_ACCUM_BIT);
|
||||
|
||||
if (mask & DD_STENCIL_BIT) {
|
||||
if (!fxMesa->haveHwStencil || ctx->Stencil.WriteMask[0] != 0xff) {
|
||||
/* Napalm seems to have trouble with stencil write masks != 0xff */
|
||||
/* do stencil clear in software */
|
||||
mask &= ~(DD_STENCIL_BIT);
|
||||
softwareMask |= DD_STENCIL_BIT;
|
||||
}
|
||||
}
|
||||
|
||||
if (fxMesa->glCtx->Visual.redBits != 8) {
|
||||
/* can only do color masking if running in 24/32bpp on Napalm */
|
||||
if (ctx->Color.ColorMask[RCOMP] != ctx->Color.ColorMask[GCOMP] ||
|
||||
ctx->Color.ColorMask[GCOMP] != ctx->Color.ColorMask[BCOMP]) {
|
||||
softwareMask |= (mask & (DD_FRONT_LEFT_BIT | DD_BACK_LEFT_BIT));
|
||||
mask &= ~(DD_FRONT_LEFT_BIT | DD_BACK_LEFT_BIT);
|
||||
}
|
||||
}
|
||||
|
||||
if (fxMesa->haveHwStencil) {
|
||||
/*
|
||||
* If we want to clear stencil, it must be enabled
|
||||
* in the HW, even if the stencil test is not enabled
|
||||
* in the OGL state.
|
||||
*/
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
if (mask & DD_STENCIL_BIT) {
|
||||
fxMesa->Glide.grStencilMask(/*ctx->Stencil.WriteMask*/ 0xff);
|
||||
/* set stencil ref value = desired clear value */
|
||||
fxMesa->Glide.grStencilFunc(GR_CMP_ALWAYS,
|
||||
ctx->Stencil.Clear, 0xff);
|
||||
fxMesa->Glide.grStencilOp(GR_STENCILOP_REPLACE,
|
||||
GR_STENCILOP_REPLACE, GR_STENCILOP_REPLACE);
|
||||
fxMesa->Glide.grEnable(GR_STENCIL_MODE_EXT);
|
||||
}
|
||||
else {
|
||||
fxMesa->Glide.grDisable(GR_STENCIL_MODE_EXT);
|
||||
}
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
|
||||
/*
|
||||
* This may be ugly, but it's needed in order to work around a number
|
||||
* of Glide bugs.
|
||||
*/
|
||||
BEGIN_CLIP_LOOP(fxMesa);
|
||||
{
|
||||
/*
|
||||
* This could probably be done fancier but doing each possible case
|
||||
* explicitly is less error prone.
|
||||
*/
|
||||
switch (mask & ~DD_STENCIL_BIT) {
|
||||
case DD_BACK_LEFT_BIT | DD_DEPTH_BIT:
|
||||
/* back buffer & depth */
|
||||
FX_grColorMaskv_NoLock(ctx, true4); /* work around Voodoo3 bug */
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
if (stencil_size > 0) {
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
}
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
if (!ctx->Depth.Mask || !ctx->Depth.Test) {
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
}
|
||||
break;
|
||||
case DD_FRONT_LEFT_BIT | DD_DEPTH_BIT:
|
||||
/* XXX it appears that the depth buffer isn't cleared when
|
||||
* glRenderBuffer(GR_BUFFER_FRONTBUFFER) is set.
|
||||
* This is a work-around/
|
||||
*/
|
||||
/* clear depth */
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
FX_grColorMaskv_NoLock(ctx, false4);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
/* clear front */
|
||||
FX_grColorMaskv_NoLock(ctx, true4);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_FRONTBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
if (!ctx->Depth.Mask || !ctx->Depth.Test) {
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
}
|
||||
break;
|
||||
case DD_BACK_LEFT_BIT:
|
||||
/* back buffer only */
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
if (ctx->Depth.Mask && ctx->Depth.Test) {
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
}
|
||||
break;
|
||||
case DD_FRONT_LEFT_BIT:
|
||||
/* front buffer only */
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_FRONTBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
if (ctx->Depth.Mask && ctx->Depth.Test) {
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
}
|
||||
break;
|
||||
case DD_FRONT_LEFT_BIT | DD_BACK_LEFT_BIT:
|
||||
/* front and back */
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_FRONTBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
if (ctx->Depth.Mask && ctx->Depth.Test) {
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
}
|
||||
break;
|
||||
case DD_FRONT_LEFT_BIT | DD_BACK_LEFT_BIT | DD_DEPTH_BIT:
|
||||
/* clear front */
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_FRONTBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
/* clear back and depth */
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
if (!ctx->Depth.Mask || !ctx->Depth.Mask) {
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
}
|
||||
break;
|
||||
case DD_DEPTH_BIT:
|
||||
/* just the depth buffer */
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
FX_grColorMaskv_NoLock(ctx, false4);
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
if (stencil_size > 0)
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
else
|
||||
fxMesa->Glide.grBufferClear(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear);
|
||||
FX_grColorMaskv_NoLock(ctx, true4);
|
||||
if (ctx->Color._DrawDestMask & FRONT_LEFT_BIT)
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_FRONTBUFFER);
|
||||
if (!ctx->Depth.Test || !ctx->Depth.Mask)
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
break;
|
||||
default:
|
||||
/* clear no color buffers or depth buffer but might clear stencil */
|
||||
if (stencil_size > 0 && (mask & DD_STENCIL_BIT)) {
|
||||
/* XXX need this RenderBuffer call to work around Glide bug */
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_BACKBUFFER);
|
||||
fxMesa->Glide.grDepthMask(FXFALSE);
|
||||
FX_grColorMaskv_NoLock(ctx, false4);
|
||||
fxMesa->Glide.grBufferClearExt(fxMesa->Color.ClearColor,
|
||||
fxMesa->Color.ClearAlpha,
|
||||
fxMesa->Depth.Clear,
|
||||
(FxU32) ctx->Stencil.Clear);
|
||||
if (ctx->Depth.Mask && ctx->Depth.Test) {
|
||||
fxMesa->Glide.grDepthMask(FXTRUE);
|
||||
}
|
||||
FX_grColorMaskv_NoLock(ctx, true4);
|
||||
if (ctx->Color._DrawDestMask & FRONT_LEFT_BIT)
|
||||
fxMesa->Glide.grRenderBuffer(GR_BUFFER_FRONTBUFFER);
|
||||
}
|
||||
}
|
||||
}
|
||||
END_CLIP_LOOP(fxMesa);
|
||||
|
||||
if (fxMesa->haveHwStencil && (mask & DD_STENCIL_BIT)) {
|
||||
/* We changed the stencil state above. Signal that we need to
|
||||
* upload it again.
|
||||
*/
|
||||
fxMesa->dirty |= TDFX_UPLOAD_STENCIL;
|
||||
}
|
||||
|
||||
if (softwareMask)
|
||||
_swrast_Clear( ctx, softwareMask, all, x, y, width, height );
|
||||
}
|
||||
|
||||
|
||||
|
||||
static void tdfxDDFinish( GLcontext *ctx )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
|
||||
FLUSH_BATCH( fxMesa );
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
fxMesa->Glide.grFinish();
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
}
|
||||
|
||||
static void tdfxDDFlush( GLcontext *ctx )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
|
||||
FLUSH_BATCH( fxMesa );
|
||||
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
fxMesa->Glide.grFlush();
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
}
|
||||
|
||||
|
||||
#if 0
|
||||
static const char *texSource(int k)
|
||||
{
|
||||
switch (k) {
|
||||
case GR_CMBX_ZERO:
|
||||
return "GR_CMBX_ZERO";
|
||||
case GR_CMBX_TEXTURE_ALPHA:
|
||||
return "GR_CMBX_TEXTURE_ALPHA";
|
||||
case GR_CMBX_ALOCAL:
|
||||
return "GR_CMBX_ALOCAL";
|
||||
case GR_CMBX_AOTHER:
|
||||
return "GR_CMBX_AOTHER";
|
||||
case GR_CMBX_B:
|
||||
return "GR_CMBX_B";
|
||||
case GR_CMBX_CONSTANT_ALPHA:
|
||||
return "GR_CMBX_CONSTANT_ALPHA";
|
||||
case GR_CMBX_CONSTANT_COLOR:
|
||||
return "GR_CMBX_CONSTANT_COLOR";
|
||||
case GR_CMBX_DETAIL_FACTOR:
|
||||
return "GR_CMBX_DETAIL_FACTOR";
|
||||
case GR_CMBX_ITALPHA:
|
||||
return "GR_CMBX_ITALPHA";
|
||||
case GR_CMBX_ITRGB:
|
||||
return "GR_CMBX_ITRGB";
|
||||
case GR_CMBX_LOCAL_TEXTURE_ALPHA:
|
||||
return "GR_CMBX_LOCAL_TEXTURE_ALPHA";
|
||||
case GR_CMBX_LOCAL_TEXTURE_RGB:
|
||||
return "GR_CMBX_LOCAL_TEXTURE_RGB";
|
||||
case GR_CMBX_LOD_FRAC:
|
||||
return "GR_CMBX_LOD_FRAC";
|
||||
case GR_CMBX_OTHER_TEXTURE_ALPHA:
|
||||
return "GR_CMBX_OTHER_TEXTURE_ALPHA";
|
||||
case GR_CMBX_OTHER_TEXTURE_RGB:
|
||||
return "GR_CMBX_OTHER_TEXTURE_RGB";
|
||||
case GR_CMBX_TEXTURE_RGB:
|
||||
return "GR_CMBX_TEXTURE_RGB";
|
||||
case GR_CMBX_TMU_CALPHA:
|
||||
return "GR_CMBX_TMU_CALPHA";
|
||||
case GR_CMBX_TMU_CCOLOR:
|
||||
return "GR_CMBX_TMU_CCOLOR";
|
||||
default:
|
||||
return "";
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
static const char *texMode(int k)
|
||||
{
|
||||
switch (k) {
|
||||
case GR_FUNC_MODE_ZERO:
|
||||
return "GR_FUNC_MODE_ZERO";
|
||||
case GR_FUNC_MODE_X:
|
||||
return "GR_FUNC_MODE_X";
|
||||
case GR_FUNC_MODE_ONE_MINUS_X:
|
||||
return "GR_FUNC_MODE_ONE_MINUS_X";
|
||||
case GR_FUNC_MODE_NEGATIVE_X:
|
||||
return "GR_FUNC_MODE_NEGATIVE_X";
|
||||
case GR_FUNC_MODE_X_MINUS_HALF:
|
||||
return "GR_FUNC_MODE_X_MINUS_HALF";
|
||||
default:
|
||||
return "";
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
#if 0
|
||||
static const char *texInvert(int k)
|
||||
{
|
||||
return k ? "FXTRUE" : "FXFALSE";
|
||||
}
|
||||
#endif
|
||||
|
||||
static void uploadTextureEnv( tdfxContextPtr fxMesa )
|
||||
{
|
||||
if (TDFX_IS_NAPALM(fxMesa)) {
|
||||
int unit;
|
||||
for (unit = 0; unit < TDFX_NUM_TMU; unit++) {
|
||||
#if 0
|
||||
printf("upload env %d\n", unit);
|
||||
printf(" cSourceA = %s\t", texSource(fxMesa->TexCombineExt[unit].Color.SourceA));
|
||||
printf(" cModeA = %s\n", texMode(fxMesa->TexCombineExt[unit].Color.ModeA));
|
||||
printf(" cSourceB = %s\t", texSource(fxMesa->TexCombineExt[unit].Color.SourceB));
|
||||
printf(" cModeB = %s\n", texMode(fxMesa->TexCombineExt[unit].Color.ModeB));
|
||||
printf(" cSourceC = %s\t", texSource(fxMesa->TexCombineExt[unit].Color.SourceC));
|
||||
printf(" cInvertC = %s\n", texInvert(fxMesa->TexCombineExt[unit].Color.InvertC));
|
||||
printf(" cSourceD = %s\t", texSource(fxMesa->TexCombineExt[unit].Color.SourceD));
|
||||
printf(" cInvertD = %s\n", texInvert(fxMesa->TexCombineExt[unit].Color.InvertD));
|
||||
printf(" cShift = %d\t", fxMesa->TexCombineExt[unit].Color.Shift);
|
||||
printf(" cInvert = %d\n", fxMesa->TexCombineExt[unit].Color.Invert);
|
||||
printf(" aSourceA = %s\t", texSource(fxMesa->TexCombineExt[unit].Alpha.SourceA));
|
||||
printf(" aModeA = %s\n", texMode(fxMesa->TexCombineExt[unit].Alpha.ModeA));
|
||||
printf(" aSourceB = %s\t", texSource(fxMesa->TexCombineExt[unit].Alpha.SourceB));
|
||||
printf(" aModeB = %s\n", texMode(fxMesa->TexCombineExt[unit].Alpha.ModeB));
|
||||
printf(" aSourceC = %s\t", texSource(fxMesa->TexCombineExt[unit].Alpha.SourceC));
|
||||
printf(" aInvertC = %s\n", texInvert(fxMesa->TexCombineExt[unit].Alpha.InvertC));
|
||||
printf(" aSourceD = %s\t", texSource(fxMesa->TexCombineExt[unit].Alpha.SourceD));
|
||||
printf(" aInvertD = %s\n", texInvert(fxMesa->TexCombineExt[unit].Alpha.InvertD));
|
||||
printf(" aShift = %d\t", fxMesa->TexCombineExt[unit].Alpha.Shift);
|
||||
printf(" aInvert = %d\n", fxMesa->TexCombineExt[unit].Alpha.Invert);
|
||||
printf(" Color = 0x%08x\n", fxMesa->TexCombineExt[unit].EnvColor);
|
||||
#endif
|
||||
fxMesa->Glide.grTexColorCombineExt(TDFX_TMU0 + unit,
|
||||
fxMesa->TexCombineExt[unit].Color.SourceA,
|
||||
fxMesa->TexCombineExt[unit].Color.ModeA,
|
||||
fxMesa->TexCombineExt[unit].Color.SourceB,
|
||||
fxMesa->TexCombineExt[unit].Color.ModeB,
|
||||
fxMesa->TexCombineExt[unit].Color.SourceC,
|
||||
fxMesa->TexCombineExt[unit].Color.InvertC,
|
||||
fxMesa->TexCombineExt[unit].Color.SourceD,
|
||||
fxMesa->TexCombineExt[unit].Color.InvertD,
|
||||
fxMesa->TexCombineExt[unit].Color.Shift,
|
||||
fxMesa->TexCombineExt[unit].Color.Invert);
|
||||
fxMesa->Glide.grTexAlphaCombineExt(TDFX_TMU0 + unit,
|
||||
fxMesa->TexCombineExt[unit].Alpha.SourceA,
|
||||
fxMesa->TexCombineExt[unit].Alpha.ModeA,
|
||||
fxMesa->TexCombineExt[unit].Alpha.SourceB,
|
||||
fxMesa->TexCombineExt[unit].Alpha.ModeB,
|
||||
fxMesa->TexCombineExt[unit].Alpha.SourceC,
|
||||
fxMesa->TexCombineExt[unit].Alpha.InvertC,
|
||||
fxMesa->TexCombineExt[unit].Alpha.SourceD,
|
||||
fxMesa->TexCombineExt[unit].Alpha.InvertD,
|
||||
fxMesa->TexCombineExt[unit].Alpha.Shift,
|
||||
fxMesa->TexCombineExt[unit].Alpha.Invert);
|
||||
fxMesa->Glide.grConstantColorValueExt(TDFX_TMU0 + unit,
|
||||
fxMesa->TexCombineExt[unit].EnvColor);
|
||||
}
|
||||
}
|
||||
else {
|
||||
/* Voodoo3 */
|
||||
int unit;
|
||||
for (unit = 0; unit < TDFX_NUM_TMU; unit++) {
|
||||
struct tdfx_texcombine *comb = &fxMesa->TexCombine[unit];
|
||||
fxMesa->Glide.grTexCombine(TDFX_TMU0 + unit,
|
||||
comb->FunctionRGB,
|
||||
comb->FactorRGB,
|
||||
comb->FunctionAlpha,
|
||||
comb->FactorAlpha,
|
||||
comb->InvertRGB,
|
||||
comb->InvertAlpha);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void uploadTextureParams( tdfxContextPtr fxMesa )
|
||||
{
|
||||
int unit;
|
||||
for (unit = 0; unit < TDFX_NUM_TMU; unit++) {
|
||||
const struct tdfx_texparams *p = &fxMesa->TexParams[unit];
|
||||
/*
|
||||
printf("upload params %d\n", unit);
|
||||
printf(" clamp %x %x\n", env->sClamp, env->tClamp);
|
||||
printf(" filter %x %x\n", env->minFilt, env->magFilt);
|
||||
printf(" mipmap %x %x\n", env->mmMode, env->LODblend);
|
||||
printf(" lod bias %f\n", env->LodBias);
|
||||
*/
|
||||
fxMesa->Glide.grTexClampMode(GR_TMU0 + unit, p->sClamp, p->tClamp);
|
||||
fxMesa->Glide.grTexFilterMode(GR_TMU0 + unit, p->minFilt, p->magFilt);
|
||||
fxMesa->Glide.grTexMipMapMode(GR_TMU0 + unit, p->mmMode, p->LODblend);
|
||||
fxMesa->Glide.grTexLodBiasValue(GR_TMU0 + unit, p->LodBias);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void uploadTextureSource( tdfxContextPtr fxMesa )
|
||||
{
|
||||
int unit;
|
||||
for (unit = 0; unit < TDFX_NUM_TMU; unit++) {
|
||||
const struct tdfx_texsource *src = &fxMesa->TexSource[unit];
|
||||
/*
|
||||
printf("upload source %d @ %d %p\n", unit, src->StartAddress, src->Info);
|
||||
*/
|
||||
if (src->Info) {
|
||||
/*
|
||||
printf(" smallLodLog2=%d largeLodLog2=%d ar=%d format=%d data=%p\n",
|
||||
src->Info->smallLodLog2, src->Info->largeLodLog2,
|
||||
src->Info->aspectRatioLog2, src->Info->format,
|
||||
src->Info->data);
|
||||
*/
|
||||
fxMesa->Glide.grTexSource(GR_TMU0 + unit,
|
||||
src->StartAddress,
|
||||
src->EvenOdd,
|
||||
src->Info);
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void uploadTextureImages( tdfxContextPtr fxMesa )
|
||||
{
|
||||
GLcontext *ctx = fxMesa->glCtx;
|
||||
int unit;
|
||||
for (unit = 0; unit < TDFX_NUM_TMU; unit++) {
|
||||
if (ctx->Texture.Unit[unit]._ReallyEnabled == TEXTURE_2D_BIT) {
|
||||
struct gl_texture_object *tObj = ctx->Texture.Unit[unit].Current2D;
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA(tObj);
|
||||
if (ti && ti->reloadImages && ti->whichTMU != TDFX_TMU_NONE) {
|
||||
/*
|
||||
printf("download texture image on unit %d\n", unit);
|
||||
*/
|
||||
tdfxTMDownloadTexture(fxMesa, tObj);
|
||||
ti->reloadImages = GL_FALSE;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* If scissoring is enabled, compute intersection of scissor region
|
||||
* with all X clip rects, resulting in new cliprect list.
|
||||
* If number of cliprects is zero or one, call grClipWindow to setup
|
||||
* the clip region. Otherwise we'll call grClipWindow inside the
|
||||
* BEGIN_CLIP_LOOP macro.
|
||||
*/
|
||||
void tdfxUploadClipping( tdfxContextPtr fxMesa )
|
||||
{
|
||||
__DRIdrawablePrivate *dPriv = fxMesa->driDrawable;
|
||||
|
||||
assert(dPriv);
|
||||
|
||||
if (fxMesa->numClipRects == 0) {
|
||||
/* all drawing clipped away */
|
||||
fxMesa->Glide.grClipWindow(0, 0, 0, 0);
|
||||
}
|
||||
else if (fxMesa->numClipRects == 1) {
|
||||
fxMesa->Glide.grClipWindow(fxMesa->pClipRects[0].x1,
|
||||
fxMesa->screen_height - fxMesa->pClipRects[0].y2,
|
||||
fxMesa->pClipRects[0].x2,
|
||||
fxMesa->screen_height - fxMesa->pClipRects[0].y1);
|
||||
}
|
||||
/* else, we'll do a cliprect loop around all drawing */
|
||||
|
||||
fxMesa->Glide.grDRIPosition( dPriv->x, dPriv->y, dPriv->w, dPriv->h,
|
||||
fxMesa->numClipRects, fxMesa->pClipRects );
|
||||
}
|
||||
|
||||
|
||||
void tdfxEmitHwStateLocked( tdfxContextPtr fxMesa )
|
||||
{
|
||||
if ( !fxMesa->dirty )
|
||||
return;
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_COLOR_COMBINE ) {
|
||||
if (TDFX_IS_NAPALM(fxMesa)) {
|
||||
fxMesa->Glide.grColorCombineExt(fxMesa->ColorCombineExt.SourceA,
|
||||
fxMesa->ColorCombineExt.ModeA,
|
||||
fxMesa->ColorCombineExt.SourceB,
|
||||
fxMesa->ColorCombineExt.ModeB,
|
||||
fxMesa->ColorCombineExt.SourceC,
|
||||
fxMesa->ColorCombineExt.InvertC,
|
||||
fxMesa->ColorCombineExt.SourceD,
|
||||
fxMesa->ColorCombineExt.InvertD,
|
||||
fxMesa->ColorCombineExt.Shift,
|
||||
fxMesa->ColorCombineExt.Invert);
|
||||
}
|
||||
else {
|
||||
/* Voodoo 3 */
|
||||
fxMesa->Glide.grColorCombine( fxMesa->ColorCombine.Function,
|
||||
fxMesa->ColorCombine.Factor,
|
||||
fxMesa->ColorCombine.Local,
|
||||
fxMesa->ColorCombine.Other,
|
||||
fxMesa->ColorCombine.Invert );
|
||||
}
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_COLOR_COMBINE;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_ALPHA_COMBINE ) {
|
||||
if (TDFX_IS_NAPALM(fxMesa)) {
|
||||
fxMesa->Glide.grAlphaCombineExt(fxMesa->AlphaCombineExt.SourceA,
|
||||
fxMesa->AlphaCombineExt.ModeA,
|
||||
fxMesa->AlphaCombineExt.SourceB,
|
||||
fxMesa->AlphaCombineExt.ModeB,
|
||||
fxMesa->AlphaCombineExt.SourceC,
|
||||
fxMesa->AlphaCombineExt.InvertC,
|
||||
fxMesa->AlphaCombineExt.SourceD,
|
||||
fxMesa->AlphaCombineExt.InvertD,
|
||||
fxMesa->AlphaCombineExt.Shift,
|
||||
fxMesa->AlphaCombineExt.Invert);
|
||||
}
|
||||
else {
|
||||
/* Voodoo 3 */
|
||||
fxMesa->Glide.grAlphaCombine( fxMesa->AlphaCombine.Function,
|
||||
fxMesa->AlphaCombine.Factor,
|
||||
fxMesa->AlphaCombine.Local,
|
||||
fxMesa->AlphaCombine.Other,
|
||||
fxMesa->AlphaCombine.Invert );
|
||||
}
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_ALPHA_COMBINE;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_RENDER_BUFFER ) {
|
||||
fxMesa->Glide.grRenderBuffer( fxMesa->DrawBuffer );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_RENDER_BUFFER;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_STIPPLE) {
|
||||
fxMesa->Glide.grStipplePattern( fxMesa->Stipple.Pattern );
|
||||
fxMesa->Glide.grStippleMode( fxMesa->Stipple.Mode );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_STIPPLE;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_ALPHA_TEST ) {
|
||||
fxMesa->Glide.grAlphaTestFunction( fxMesa->Color.AlphaFunc );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_ALPHA_TEST;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_ALPHA_REF ) {
|
||||
fxMesa->Glide.grAlphaTestReferenceValue( fxMesa->Color.AlphaRef );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_ALPHA_REF;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_BLEND_FUNC ) {
|
||||
if (fxMesa->Glide.grAlphaBlendFunctionExt) {
|
||||
fxMesa->Glide.grAlphaBlendFunctionExt( fxMesa->Color.BlendSrcRGB,
|
||||
fxMesa->Color.BlendDstRGB,
|
||||
GR_BLEND_OP_ADD,
|
||||
fxMesa->Color.BlendSrcA,
|
||||
fxMesa->Color.BlendDstA,
|
||||
GR_BLEND_OP_ADD );
|
||||
}
|
||||
else {
|
||||
fxMesa->Glide.grAlphaBlendFunction( fxMesa->Color.BlendSrcRGB,
|
||||
fxMesa->Color.BlendDstRGB,
|
||||
fxMesa->Color.BlendSrcA,
|
||||
fxMesa->Color.BlendDstA );
|
||||
}
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_BLEND_FUNC;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_DEPTH_MODE ) {
|
||||
fxMesa->Glide.grDepthBufferMode( fxMesa->Depth.Mode );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_DEPTH_MODE;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_DEPTH_BIAS ) {
|
||||
fxMesa->Glide.grDepthBiasLevel( fxMesa->Depth.Bias );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_DEPTH_BIAS;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_DEPTH_FUNC ) {
|
||||
fxMesa->Glide.grDepthBufferFunction( fxMesa->Depth.Func );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_DEPTH_FUNC;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_DEPTH_MASK ) {
|
||||
fxMesa->Glide.grDepthMask( fxMesa->Depth.Mask );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_DEPTH_MASK;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_DITHER) {
|
||||
fxMesa->Glide.grDitherMode( fxMesa->Color.Dither );
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_FOG_MODE ) {
|
||||
fxMesa->Glide.grFogMode( fxMesa->Fog.Mode );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_FOG_MODE;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_FOG_COLOR ) {
|
||||
fxMesa->Glide.grFogColorValue( fxMesa->Fog.Color );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_FOG_COLOR;
|
||||
}
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_FOG_TABLE ) {
|
||||
fxMesa->Glide.grFogTable( fxMesa->Fog.Table );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_FOG_TABLE;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_CULL ) {
|
||||
fxMesa->Glide.grCullMode( fxMesa->CullMode );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_CULL;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_CLIP ) {
|
||||
tdfxUploadClipping( fxMesa );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_CLIP;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_COLOR_MASK ) {
|
||||
if ( fxMesa->Glide.grColorMaskExt
|
||||
&& fxMesa->glCtx->Visual.redBits == 8) {
|
||||
fxMesa->Glide.grColorMaskExt( fxMesa->Color.ColorMask[RCOMP],
|
||||
fxMesa->Color.ColorMask[GCOMP],
|
||||
fxMesa->Color.ColorMask[BCOMP],
|
||||
fxMesa->Color.ColorMask[ACOMP] );
|
||||
} else {
|
||||
fxMesa->Glide.grColorMask( fxMesa->Color.ColorMask[RCOMP] ||
|
||||
fxMesa->Color.ColorMask[GCOMP] ||
|
||||
fxMesa->Color.ColorMask[BCOMP],
|
||||
fxMesa->Color.ColorMask[ACOMP] );
|
||||
}
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_COLOR_MASK;
|
||||
}
|
||||
|
||||
/* if ( fxMesa->dirty & TDFX_UPLOAD_CONSTANT_COLOR ) { */
|
||||
/* grConstantColorValue( fxMesa->Color.MonoColor ); */
|
||||
/* fxMesa->dirty &= ~TDFX_UPLOAD_CONSTANT_COLOR; */
|
||||
/* } */
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_LINE ) {
|
||||
if (fxMesa->glCtx->Line.SmoothFlag && fxMesa->glCtx->Line.Width == 1.0)
|
||||
fxMesa->Glide.grEnable(GR_AA_ORDERED);
|
||||
else
|
||||
fxMesa->Glide.grDisable(GR_AA_ORDERED);
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_LINE;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_STENCIL ) {
|
||||
if (fxMesa->glCtx->Stencil.Enabled) {
|
||||
fxMesa->Glide.grEnable(GR_STENCIL_MODE_EXT);
|
||||
fxMesa->Glide.grStencilOp(fxMesa->Stencil.FailFunc,
|
||||
fxMesa->Stencil.ZFailFunc,
|
||||
fxMesa->Stencil.ZPassFunc);
|
||||
fxMesa->Glide.grStencilFunc(fxMesa->Stencil.Function,
|
||||
fxMesa->Stencil.RefValue,
|
||||
fxMesa->Stencil.ValueMask);
|
||||
fxMesa->Glide.grStencilMask(fxMesa->Stencil.WriteMask);
|
||||
}
|
||||
else {
|
||||
fxMesa->Glide.grDisable(GR_STENCIL_MODE_EXT);
|
||||
}
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_STENCIL;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_VERTEX_LAYOUT ) {
|
||||
fxMesa->Glide.grGlideSetVertexLayout( fxMesa->layout[fxMesa->vertexFormat] );
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_VERTEX_LAYOUT;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_TEXTURE_ENV ) {
|
||||
uploadTextureEnv(fxMesa);
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_TEXTURE_ENV;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_TEXTURE_PARAMS ) {
|
||||
uploadTextureParams(fxMesa);
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_TEXTURE_PARAMS;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_TEXTURE_PALETTE ) {
|
||||
if (fxMesa->TexPalette.Data) {
|
||||
fxMesa->Glide.grTexDownloadTable(fxMesa->TexPalette.Type, fxMesa->TexPalette.Data);
|
||||
}
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_TEXTURE_PALETTE;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_TEXTURE_SOURCE ) {
|
||||
uploadTextureSource(fxMesa);
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_TEXTURE_SOURCE;
|
||||
}
|
||||
|
||||
if ( fxMesa->dirty & TDFX_UPLOAD_TEXTURE_IMAGES ) {
|
||||
uploadTextureImages(fxMesa);
|
||||
fxMesa->dirty &= ~TDFX_UPLOAD_TEXTURE_IMAGES;
|
||||
}
|
||||
|
||||
fxMesa->dirty = 0;
|
||||
}
|
||||
|
||||
|
||||
|
||||
void tdfxDDInitRenderFuncs( GLcontext *ctx )
|
||||
{
|
||||
ctx->Driver.Clear = tdfxDDClear;
|
||||
ctx->Driver.Finish = tdfxDDFinish;
|
||||
ctx->Driver.Flush = tdfxDDFlush;
|
||||
}
|
||||
@@ -0,0 +1,54 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_render.h,v 1.1 2001/03/21 16:14:28 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_RENDER_H__
|
||||
#define __TDFX_RENDER_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
#include "tdfx_context.h"
|
||||
|
||||
extern void tdfxDDInitRenderFuncs( GLcontext *ctx );
|
||||
|
||||
extern void tdfxEmitHwStateLocked( tdfxContextPtr fxMesa );
|
||||
|
||||
extern void tdfxUploadClipping( tdfxContextPtr fxMesa );
|
||||
|
||||
#define FLUSH_BATCH( fxMesa )
|
||||
|
||||
|
||||
#endif
|
||||
#endif
|
||||
@@ -0,0 +1,331 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_screen.c,v 1.3 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tdfx_dri.h"
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_lock.h"
|
||||
#include "tdfx_vb.h"
|
||||
#include "tdfx_tris.h"
|
||||
|
||||
|
||||
#ifdef DEBUG_LOCKING
|
||||
char *prevLockFile = 0;
|
||||
int prevLockLine = 0;
|
||||
#endif
|
||||
|
||||
#ifndef TDFX_DEBUG
|
||||
int TDFX_DEBUG = (0
|
||||
/* | DEBUG_ALWAYS_SYNC */
|
||||
/* | DEBUG_VERBOSE_API */
|
||||
/* | DEBUG_VERBOSE_MSG */
|
||||
/* | DEBUG_VERBOSE_LRU */
|
||||
/* | DEBUG_VERBOSE_DRI */
|
||||
/* | DEBUG_VERBOSE_IOCTL */
|
||||
/* | DEBUG_VERBOSE_2D */
|
||||
);
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
static GLboolean
|
||||
tdfxCreateScreen( __DRIscreenPrivate *sPriv )
|
||||
{
|
||||
tdfxScreenPrivate *fxScreen;
|
||||
TDFXDRIPtr fxDRIPriv = (TDFXDRIPtr) sPriv->pDevPriv;
|
||||
|
||||
/* Allocate the private area */
|
||||
fxScreen = (tdfxScreenPrivate *) Xmalloc( sizeof(tdfxScreenPrivate) );
|
||||
if ( !fxScreen )
|
||||
return GL_FALSE;
|
||||
|
||||
fxScreen->driScrnPriv = sPriv;
|
||||
sPriv->private = (void *) fxScreen;
|
||||
|
||||
fxScreen->regs.handle = fxDRIPriv->regs;
|
||||
fxScreen->regs.size = fxDRIPriv->regsSize;
|
||||
fxScreen->deviceID = fxDRIPriv->deviceID;
|
||||
fxScreen->width = fxDRIPriv->width;
|
||||
fxScreen->height = fxDRIPriv->height;
|
||||
fxScreen->mem = fxDRIPriv->mem;
|
||||
fxScreen->cpp = fxDRIPriv->cpp;
|
||||
fxScreen->stride = fxDRIPriv->stride;
|
||||
fxScreen->fifoOffset = fxDRIPriv->fifoOffset;
|
||||
fxScreen->fifoSize = fxDRIPriv->fifoSize;
|
||||
fxScreen->fbOffset = fxDRIPriv->fbOffset;
|
||||
fxScreen->backOffset = fxDRIPriv->backOffset;
|
||||
fxScreen->depthOffset = fxDRIPriv->depthOffset;
|
||||
fxScreen->textureOffset = fxDRIPriv->textureOffset;
|
||||
fxScreen->textureSize = fxDRIPriv->textureSize;
|
||||
fxScreen->sarea_priv_offset = fxDRIPriv->sarea_priv_offset;
|
||||
|
||||
if ( drmMap( sPriv->fd, fxScreen->regs.handle,
|
||||
fxScreen->regs.size, &fxScreen->regs.map ) ) {
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
tdfxDestroyScreen( __DRIscreenPrivate *sPriv )
|
||||
{
|
||||
tdfxScreenPrivate *fxScreen = (tdfxScreenPrivate *) sPriv->private;
|
||||
|
||||
if ( fxScreen ) {
|
||||
drmUnmap( fxScreen->regs.map, fxScreen->regs.size );
|
||||
|
||||
Xfree( fxScreen );
|
||||
sPriv->private = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static GLboolean
|
||||
tdfxInitDriver( __DRIscreenPrivate *sPriv )
|
||||
{
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_DRI ) {
|
||||
fprintf( stderr, "%s( %p )\n", __FUNCTION__, sPriv );
|
||||
}
|
||||
|
||||
/* Check the DRI externsion version */
|
||||
if ( sPriv->driMajor != 4 || sPriv->driMinor < 0 ) {
|
||||
__driUtilMessage( "tdfx DRI driver expected DRI version 4.0.x "
|
||||
"but got version %d.%d.%d",
|
||||
sPriv->driMajor, sPriv->driMinor, sPriv->driPatch );
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
/* Check that the DDX driver version is compatible */
|
||||
if ( sPriv->ddxMajor != 1 ||
|
||||
sPriv->ddxMinor < 0 ) {
|
||||
__driUtilMessage(
|
||||
"3dfx DRI driver expected DDX driver version 1.0.x "
|
||||
"but got version %d.%d.%d",
|
||||
sPriv->ddxMajor, sPriv->ddxMinor, sPriv->ddxPatch );
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
/* Check that the DRM driver version is compatible */
|
||||
if ( sPriv->drmMajor != 1 ||
|
||||
sPriv->drmMinor < 0 ) {
|
||||
__driUtilMessage(
|
||||
"3dfx DRI driver expected DRM driver version 1.0.x "
|
||||
"but got version %d.%d.%d",
|
||||
sPriv->drmMajor, sPriv->drmMinor, sPriv->drmPatch );
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
if ( !tdfxCreateScreen( sPriv ) ) {
|
||||
tdfxDestroyScreen( sPriv );
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
static GLboolean
|
||||
tdfxCreateBuffer( __DRIscreenPrivate *driScrnPriv,
|
||||
__DRIdrawablePrivate *driDrawPriv,
|
||||
const __GLcontextModes *mesaVis,
|
||||
GLboolean isPixmap )
|
||||
{
|
||||
if (isPixmap) {
|
||||
return GL_FALSE; /* not implemented */
|
||||
}
|
||||
else {
|
||||
driDrawPriv->driverPrivate = (void *)
|
||||
_mesa_create_framebuffer( mesaVis,
|
||||
GL_FALSE, /* software depth buffer? */
|
||||
mesaVis->stencilBits > 0,
|
||||
mesaVis->accumRedBits > 0,
|
||||
GL_FALSE /* software alpha channel? */ );
|
||||
return (driDrawPriv->driverPrivate != NULL);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
tdfxDestroyBuffer(__DRIdrawablePrivate *driDrawPriv)
|
||||
{
|
||||
_mesa_destroy_framebuffer((GLframebuffer *) (driDrawPriv->driverPrivate));
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
tdfxSwapBuffers( __DRIdrawablePrivate *driDrawPriv )
|
||||
|
||||
{
|
||||
GET_CURRENT_CONTEXT(ctx);
|
||||
tdfxContextPtr fxMesa = 0;
|
||||
GLframebuffer *mesaBuffer;
|
||||
|
||||
if ( TDFX_DEBUG & DEBUG_VERBOSE_DRI ) {
|
||||
fprintf( stderr, "%s( %p )\n", __FUNCTION__, driDrawPriv );
|
||||
}
|
||||
|
||||
mesaBuffer = (GLframebuffer *) driDrawPriv->driverPrivate;
|
||||
if ( !mesaBuffer->Visual.doubleBufferMode )
|
||||
return; /* can't swap a single-buffered window */
|
||||
|
||||
/* If the current context's drawable matches the given drawable
|
||||
* we have to do a glFinish (per the GLX spec).
|
||||
*/
|
||||
if ( ctx ) {
|
||||
__DRIdrawablePrivate *curDrawPriv;
|
||||
fxMesa = TDFX_CONTEXT(ctx);
|
||||
curDrawPriv = fxMesa->driContext->driDrawablePriv;
|
||||
|
||||
if ( curDrawPriv == driDrawPriv ) {
|
||||
/* swapping window bound to current context, flush first */
|
||||
_mesa_notifySwapBuffers( ctx );
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
}
|
||||
else {
|
||||
/* find the fxMesa context previously bound to the window */
|
||||
fxMesa = (tdfxContextPtr) driDrawPriv->driContextPriv->driverPrivate;
|
||||
if (!fxMesa)
|
||||
return;
|
||||
LOCK_HARDWARE( fxMesa );
|
||||
fxMesa->Glide.grSstSelect( fxMesa->Glide.Board );
|
||||
printf("SwapBuf SetState 1\n");
|
||||
fxMesa->Glide.grGlideSetState(fxMesa->Glide.State );
|
||||
}
|
||||
}
|
||||
|
||||
#ifdef STATS
|
||||
{
|
||||
int stalls;
|
||||
static int prevStalls = 0;
|
||||
|
||||
stalls = fxMesa->Glide.grFifoGetStalls();
|
||||
|
||||
fprintf( stderr, "%s:\n", __FUNCTION__ );
|
||||
if ( stalls != prevStalls ) {
|
||||
fprintf( stderr, " %d stalls occurred\n",
|
||||
stalls - prevStalls );
|
||||
prevStalls = stalls;
|
||||
}
|
||||
if ( fxMesa && fxMesa->texSwaps ) {
|
||||
fprintf( stderr, " %d texture swaps occurred\n",
|
||||
fxMesa->texSwaps );
|
||||
fxMesa->texSwaps = 0;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
if (fxMesa->scissoredClipRects) {
|
||||
/* restore clip rects without scissor box */
|
||||
fxMesa->Glide.grDRIPosition( driDrawPriv->x, driDrawPriv->y,
|
||||
driDrawPriv->w, driDrawPriv->h,
|
||||
driDrawPriv->numClipRects,
|
||||
driDrawPriv->pClipRects );
|
||||
}
|
||||
|
||||
fxMesa->Glide.grDRIBufferSwap( fxMesa->Glide.SwapInterval );
|
||||
|
||||
if (fxMesa->scissoredClipRects) {
|
||||
/* restore clip rects WITH scissor box */
|
||||
fxMesa->Glide.grDRIPosition( driDrawPriv->x, driDrawPriv->y,
|
||||
driDrawPriv->w, driDrawPriv->h,
|
||||
fxMesa->numClipRects, fxMesa->pClipRects );
|
||||
}
|
||||
|
||||
|
||||
#if 0
|
||||
{
|
||||
FxI32 result;
|
||||
do {
|
||||
FxI32 result;
|
||||
fxMesa->Glide.grGet(GR_PENDING_BUFFERSWAPS, 4, &result);
|
||||
} while ( result > fxMesa->maxPendingSwapBuffers );
|
||||
}
|
||||
#endif
|
||||
|
||||
fxMesa->stats.swapBuffer++;
|
||||
|
||||
if (ctx) {
|
||||
if (ctx->DriverCtx != fxMesa) {
|
||||
fxMesa = TDFX_CONTEXT(ctx);
|
||||
fxMesa->Glide.grSstSelect( fxMesa->Glide.Board );
|
||||
printf("SwapBuf SetState 2\n");
|
||||
fxMesa->Glide.grGlideSetState(fxMesa->Glide.State );
|
||||
}
|
||||
UNLOCK_HARDWARE( fxMesa );
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
static GLboolean
|
||||
tdfxOpenCloseFullScreen(__DRIcontextPrivate *driContextPriv)
|
||||
{
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
|
||||
static const struct __DriverAPIRec tdfxAPI = {
|
||||
.InitDriver = tdfxInitDriver,
|
||||
.DestroyScreen = tdfxDestroyScreen,
|
||||
.CreateContext = tdfxCreateContext,
|
||||
.DestroyContext = tdfxDestroyContext,
|
||||
.CreateBuffer = tdfxCreateBuffer,
|
||||
.DestroyBuffer = tdfxDestroyBuffer,
|
||||
.SwapBuffers = tdfxSwapBuffers,
|
||||
.MakeCurrent = tdfxMakeCurrent,
|
||||
.UnbindContext = tdfxUnbindContext,
|
||||
.OpenFullScreen = tdfxOpenCloseFullScreen,
|
||||
.CloseFullScreen = tdfxOpenCloseFullScreen,
|
||||
.GetSwapInfo = NULL,
|
||||
.GetMSC = NULL,
|
||||
.WaitForMSC = NULL,
|
||||
.WaitForSBC = NULL,
|
||||
.SwapBuffersMSC = NULL
|
||||
};
|
||||
|
||||
|
||||
/*
|
||||
* This is the bootstrap function for the driver.
|
||||
* The __driCreateScreen name is the symbol that libGL.so fetches.
|
||||
* Return: pointer to a __DRIscreenPrivate.
|
||||
*/
|
||||
void *__driCreateScreen(Display *dpy, int scrn, __DRIscreen *psc,
|
||||
int numConfigs, __GLXvisualConfig *config)
|
||||
{
|
||||
__DRIscreenPrivate *psp;
|
||||
psp = __driUtilCreateScreen(dpy, scrn, psc, numConfigs, config, &tdfxAPI);
|
||||
return (void *) psp;
|
||||
}
|
||||
@@ -0,0 +1,73 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_screen.h,v 1.2 2002/02/22 21:45:03 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_SCREEN_H__
|
||||
#define __TDFX_SCREEN_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
typedef struct {
|
||||
drmHandle handle;
|
||||
drmSize size;
|
||||
drmAddress map;
|
||||
} tdfxRegion, *tdfxRegionPtr;
|
||||
|
||||
typedef struct {
|
||||
tdfxRegion regs;
|
||||
|
||||
int deviceID;
|
||||
int width;
|
||||
int height;
|
||||
int mem;
|
||||
int cpp;
|
||||
int stride;
|
||||
|
||||
int fifoOffset;
|
||||
int fifoSize;
|
||||
|
||||
int fbOffset;
|
||||
int backOffset;
|
||||
int depthOffset;
|
||||
int textureOffset;
|
||||
int textureSize;
|
||||
|
||||
__DRIscreenPrivate *driScrnPriv;
|
||||
unsigned int sarea_priv_offset;
|
||||
} tdfxScreenPrivate;
|
||||
|
||||
|
||||
#endif
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,48 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_span.h,v 1.1 2001/03/21 16:14:28 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_SPAN_H__
|
||||
#define __TDFX_SPAN_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
#include "context.h"
|
||||
|
||||
extern void tdfxDDInitSpanFuncs( GLcontext *ctx );
|
||||
|
||||
#endif
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,64 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_state.h,v 1.2 2002/02/22 21:45:04 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_STATE_H__
|
||||
#define __TDFX_STATE_H__
|
||||
|
||||
#ifdef GLX_DIRECT_RENDERING
|
||||
|
||||
#include "context.h"
|
||||
#include "tdfx_context.h"
|
||||
|
||||
extern void tdfxDDInitStateFuncs( GLcontext *ctx );
|
||||
|
||||
extern void tdfxDDUpdateHwState( GLcontext *ctx );
|
||||
|
||||
extern void tdfxInitState( tdfxContextPtr fxMesa );
|
||||
|
||||
extern void tdfxUpdateClipping( GLcontext *ctx );
|
||||
|
||||
|
||||
extern void tdfxFallback( GLcontext *ctx, GLuint bit, GLboolean mode );
|
||||
#define FALLBACK( rmesa, bit, mode ) tdfxFallback( rmesa->glCtx, bit, mode )
|
||||
|
||||
extern void tdfxUpdateCull( GLcontext *ctx );
|
||||
extern void tdfxUpdateStipple( GLcontext *ctx );
|
||||
extern void tdfxUpdateViewport( GLcontext *ctx );
|
||||
|
||||
|
||||
#endif
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,165 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_tex.h,v 1.2 2002/02/22 21:45:04 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef _TDFX_TEX_H_
|
||||
#define _TDFX_TEX_H_
|
||||
|
||||
|
||||
#include "texutil.h"
|
||||
|
||||
|
||||
#define tdfxDDIsCompressedFormatMacro(internalFormat) \
|
||||
(((internalFormat) == GL_COMPRESSED_RGB_FXT1_3DFX) || \
|
||||
((internalFormat) == GL_COMPRESSED_RGBA_FXT1_3DFX))
|
||||
#define tdfxDDIsCompressedGlideFormatMacro(internalFormat) \
|
||||
((internalFormat) == GR_TEXFMT_ARGB_CMP_FXT1)
|
||||
|
||||
|
||||
|
||||
extern void
|
||||
tdfxTexValidate(GLcontext * ctx, struct gl_texture_object *tObj);
|
||||
|
||||
extern void
|
||||
tdfxDDBindTexture(GLcontext * ctx, GLenum target,
|
||||
struct gl_texture_object *tObj);
|
||||
|
||||
extern void
|
||||
tdfxDDDeleteTexture(GLcontext * ctx, struct gl_texture_object *tObj);
|
||||
|
||||
extern GLboolean
|
||||
tdfxDDIsTextureResident(GLcontext *ctx, struct gl_texture_object *tObj);
|
||||
|
||||
extern void
|
||||
tdfxDDTexturePalette(GLcontext * ctx, struct gl_texture_object *tObj);
|
||||
|
||||
#if 000 /* DEAD? */
|
||||
extern void
|
||||
fxDDTexUseGlobalPalette(GLcontext * ctx, GLboolean state);
|
||||
#endif
|
||||
|
||||
extern void
|
||||
tdfxDDTexEnv(GLcontext * ctx, GLenum target, GLenum pname,
|
||||
const GLfloat * param);
|
||||
|
||||
extern void
|
||||
tdfxDDTexParameter(GLcontext * ctx, GLenum target,
|
||||
struct gl_texture_object *tObj,
|
||||
GLenum pname, const GLfloat * params);
|
||||
|
||||
extern const struct gl_texture_format *
|
||||
tdfxDDChooseTextureFormat( GLcontext *ctx, GLint internalFormat,
|
||||
GLenum srcFormat, GLenum srcType );
|
||||
|
||||
extern void
|
||||
tdfxDDTexImage2D(GLcontext * ctx, GLenum target, GLint level,
|
||||
GLint internalFormat, GLint width, GLint height,
|
||||
GLint border,
|
||||
GLenum format, GLenum type, const GLvoid * pixels,
|
||||
const struct gl_pixelstore_attrib * packing,
|
||||
struct gl_texture_object * texObj,
|
||||
struct gl_texture_image * texImage);
|
||||
|
||||
extern void
|
||||
tdfxDDTexSubImage2D(GLcontext *ctx, GLenum target, GLint level,
|
||||
GLint xoffset, GLint yoffset,
|
||||
GLsizei width, GLsizei height,
|
||||
GLenum format, GLenum type,
|
||||
const GLvoid *pixels,
|
||||
const struct gl_pixelstore_attrib *packing,
|
||||
struct gl_texture_object *texObj,
|
||||
struct gl_texture_image *texImage );
|
||||
|
||||
#if 000
|
||||
extern GLboolean
|
||||
tdfxDDCompressedTexImage2D( GLcontext *ctx, GLenum target,
|
||||
GLint level, GLsizei imageSize,
|
||||
const GLvoid *data,
|
||||
struct gl_texture_object *texObj,
|
||||
struct gl_texture_image *texImage,
|
||||
GLboolean *retainInternalCopy);
|
||||
|
||||
extern GLboolean
|
||||
tdfxDDCompressedTexSubImage2D( GLcontext *ctx, GLenum target,
|
||||
GLint level, GLint xoffset,
|
||||
GLint yoffset, GLsizei width,
|
||||
GLint height, GLenum format,
|
||||
GLsizei imageSize, const GLvoid *data,
|
||||
struct gl_texture_object *texObj,
|
||||
struct gl_texture_image *texImage );
|
||||
#endif
|
||||
|
||||
extern GLboolean
|
||||
tdfxDDTestProxyTexImage(GLcontext *ctx, GLenum target,
|
||||
GLint level, GLint internalFormat,
|
||||
GLenum format, GLenum type,
|
||||
GLint width, GLint height,
|
||||
GLint depth, GLint border);
|
||||
|
||||
extern GLvoid *
|
||||
tdfxDDGetTexImage(GLcontext * ctx, GLenum target, GLint level,
|
||||
const struct gl_texture_object *texObj,
|
||||
GLenum * formatOut, GLenum * typeOut,
|
||||
GLboolean * freeImageOut);
|
||||
|
||||
extern void
|
||||
tdfxDDGetCompressedTexImage( GLcontext *ctx, GLenum target,
|
||||
GLint lod, void *image,
|
||||
const struct gl_texture_object *texObj,
|
||||
struct gl_texture_image *texImage );
|
||||
|
||||
extern GLint
|
||||
tdfxDDSpecificCompressedTexFormat(GLcontext *ctx,
|
||||
GLint internalFormat,
|
||||
GLint numDimensions);
|
||||
|
||||
extern GLint
|
||||
tdfxDDBaseCompressedTexFormat(GLcontext *ctx,
|
||||
GLint internalFormat);
|
||||
|
||||
extern GLboolean
|
||||
tdfxDDIsCompressedFormat(GLcontext *ctx, GLint internalFormat);
|
||||
|
||||
extern GLsizei
|
||||
tdfxDDCompressedImageSize(GLcontext *ctx,
|
||||
GLenum intFormat,
|
||||
GLuint numDimensions,
|
||||
GLuint width,
|
||||
GLuint height,
|
||||
GLuint depth);
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,970 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_texman.c,v 1.5 2002/02/22 21:45:04 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_tex.h"
|
||||
#include "tdfx_texman.h"
|
||||
|
||||
|
||||
#define BAD_ADDRESS ((FxU32) -1)
|
||||
|
||||
|
||||
#if 0 /* DEBUG use */
|
||||
/*
|
||||
* Verify the consistancy of the texture memory manager.
|
||||
* This involves:
|
||||
* Traversing all texture objects and computing total memory used.
|
||||
* Traverse the free block list and computing total memory free.
|
||||
* Compare the total free and total used amounts to the total memory size.
|
||||
* Make various assertions about the results.
|
||||
*/
|
||||
static void
|
||||
VerifyFreeList(tdfxContextPtr fxMesa, FxU32 tmu)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
tdfxMemRange *block;
|
||||
int prevStart = -1, prevEnd = -1;
|
||||
int totalFree = 0;
|
||||
int numObj = 0, numRes = 0;
|
||||
int totalUsed = 0;
|
||||
|
||||
for (block = shared->tmFree[tmu]; block; block = block->next) {
|
||||
assert( block->endAddr > 0 );
|
||||
assert( block->startAddr <= shared->totalTexMem[tmu] );
|
||||
assert( block->endAddr <= shared->totalTexMem[tmu] );
|
||||
assert( (int) block->startAddr > prevStart );
|
||||
assert( (int) block->startAddr >= prevEnd );
|
||||
prevStart = (int) block->startAddr;
|
||||
prevEnd = (int) block->endAddr;
|
||||
totalFree += (block->endAddr - block->startAddr);
|
||||
}
|
||||
assert(totalFree == shared->freeTexMem[tmu]);
|
||||
|
||||
{
|
||||
struct gl_texture_object *obj;
|
||||
for (obj = mesaShared->TexObjectList; obj; obj = obj->Next) {
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA(obj);
|
||||
numObj++;
|
||||
if (ti) {
|
||||
if (ti->isInTM) {
|
||||
numRes++;
|
||||
assert(ti->tm[0]);
|
||||
if (ti->tm[tmu])
|
||||
totalUsed += (ti->tm[tmu]->endAddr - ti->tm[tmu]->startAddr);
|
||||
}
|
||||
else {
|
||||
assert(!ti->tm[0]);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
printf("totalFree: %d totalUsed: %d totalMem: %d #objs=%d #res=%d\n",
|
||||
shared->freeTexMem[tmu], totalUsed, shared->totalTexMem[tmu],
|
||||
numObj, numRes);
|
||||
|
||||
assert(totalUsed + totalFree == shared->totalTexMem[tmu]);
|
||||
}
|
||||
|
||||
|
||||
static void
|
||||
dump_texmem(tdfxContextPtr fxMesa)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
struct gl_texture_object *oldestObj, *obj, *lowestPriorityObj;
|
||||
tdfxMemRange *r;
|
||||
FxU32 prev;
|
||||
|
||||
printf("DUMP Objects:\n");
|
||||
for (obj = mesaShared->TexObjectList; obj; obj = obj->Next) {
|
||||
tdfxTexInfo *info = TDFX_TEXTURE_DATA(obj);
|
||||
|
||||
if (info && info->isInTM) {
|
||||
printf("Obj %8p: %4d info = %p\n", obj, obj->Name, info);
|
||||
|
||||
printf(" isInTM=%d whichTMU=%d lastTimeUsed=%d\n",
|
||||
info->isInTM, info->whichTMU, info->lastTimeUsed);
|
||||
printf(" tm[0] = %p", info->tm[0]);
|
||||
assert(info->tm[0]);
|
||||
if (info->tm[0]) {
|
||||
printf(" tm startAddr = %d endAddr = %d",
|
||||
info->tm[0]->startAddr,
|
||||
info->tm[0]->endAddr);
|
||||
}
|
||||
printf("\n");
|
||||
printf(" tm[1] = %p", info->tm[1]);
|
||||
if (info->tm[1]) {
|
||||
printf(" tm startAddr = %d endAddr = %d",
|
||||
info->tm[1]->startAddr,
|
||||
info->tm[1]->endAddr);
|
||||
}
|
||||
printf("\n");
|
||||
}
|
||||
}
|
||||
|
||||
VerifyFreeList(fxMesa, 0);
|
||||
VerifyFreeList(fxMesa, 1);
|
||||
|
||||
printf("Free memory unit 0: %d bytes\n", shared->freeTexMem[0]);
|
||||
prev = 0;
|
||||
for (r = shared->tmFree[0]; r; r = r->next) {
|
||||
printf("%8p: start %8d end %8d size %8d gap %8d\n", r, r->startAddr, r->endAddr, r->endAddr - r->startAddr, r->startAddr - prev);
|
||||
prev = r->endAddr;
|
||||
}
|
||||
|
||||
printf("Free memory unit 1: %d bytes\n", shared->freeTexMem[1]);
|
||||
prev = 0;
|
||||
for (r = shared->tmFree[1]; r; r = r->next) {
|
||||
printf("%8p: start %8d end %8d size %8d gap %8d\n", r, r->startAddr, r->endAddr, r->endAddr - r->startAddr, r->startAddr - prev);
|
||||
prev = r->endAddr;
|
||||
}
|
||||
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
#ifdef TEXSANITY
|
||||
static void
|
||||
fubar(void)
|
||||
{
|
||||
}
|
||||
|
||||
/*
|
||||
* Sanity Check
|
||||
*/
|
||||
static void
|
||||
sanity(tdfxContextPtr fxMesa)
|
||||
{
|
||||
tdfxMemRange *tmp, *prev, *pos;
|
||||
|
||||
prev = 0;
|
||||
tmp = fxMesa->tmFree[0];
|
||||
while (tmp) {
|
||||
if (!tmp->startAddr && !tmp->endAddr) {
|
||||
fprintf(stderr, "Textures fubar\n");
|
||||
fubar();
|
||||
}
|
||||
if (tmp->startAddr >= tmp->endAddr) {
|
||||
fprintf(stderr, "Node fubar\n");
|
||||
fubar();
|
||||
}
|
||||
if (prev && (prev->startAddr >= tmp->startAddr ||
|
||||
prev->endAddr > tmp->startAddr)) {
|
||||
fprintf(stderr, "Sorting fubar\n");
|
||||
fubar();
|
||||
}
|
||||
prev = tmp;
|
||||
tmp = tmp->next;
|
||||
}
|
||||
prev = 0;
|
||||
tmp = fxMesa->tmFree[1];
|
||||
while (tmp) {
|
||||
if (!tmp->startAddr && !tmp->endAddr) {
|
||||
fprintf(stderr, "Textures fubar\n");
|
||||
fubar();
|
||||
}
|
||||
if (tmp->startAddr >= tmp->endAddr) {
|
||||
fprintf(stderr, "Node fubar\n");
|
||||
fubar();
|
||||
}
|
||||
if (prev && (prev->startAddr >= tmp->startAddr ||
|
||||
prev->endAddr > tmp->startAddr)) {
|
||||
fprintf(stderr, "Sorting fubar\n");
|
||||
fubar();
|
||||
}
|
||||
prev = tmp;
|
||||
tmp = tmp->next;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* Allocate and initialize a new MemRange struct.
|
||||
* Try to allocate it from the pool of free MemRange nodes rather than malloc.
|
||||
*/
|
||||
static tdfxMemRange *
|
||||
NewRangeNode(tdfxContextPtr fxMesa, FxU32 start, FxU32 end)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
tdfxMemRange *result;
|
||||
|
||||
_glthread_LOCK_MUTEX(mesaShared->Mutex);
|
||||
if (shared && shared->tmPool) {
|
||||
result = shared->tmPool;
|
||||
shared->tmPool = shared->tmPool->next;
|
||||
}
|
||||
else {
|
||||
result = MALLOC(sizeof(tdfxMemRange));
|
||||
|
||||
}
|
||||
_glthread_UNLOCK_MUTEX(mesaShared->Mutex);
|
||||
|
||||
if (!result) {
|
||||
/*fprintf(stderr, "fxDriver: out of memory!\n");*/
|
||||
return NULL;
|
||||
}
|
||||
|
||||
result->startAddr = start;
|
||||
result->endAddr = end;
|
||||
result->next = NULL;
|
||||
|
||||
return result;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Initialize texture memory.
|
||||
* We take care of one or both TMU's here.
|
||||
*/
|
||||
void
|
||||
tdfxTMInit(tdfxContextPtr fxMesa)
|
||||
{
|
||||
if (!fxMesa->glCtx->Shared->DriverData) {
|
||||
const char *extensions;
|
||||
struct tdfxSharedState *shared = CALLOC_STRUCT(tdfxSharedState);
|
||||
if (!shared)
|
||||
return;
|
||||
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
extensions = fxMesa->Glide.grGetString(GR_EXTENSION);
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
if (strstr(extensions, "TEXUMA")) {
|
||||
FxU32 start, end;
|
||||
shared->umaTexMemory = GL_TRUE;
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
fxMesa->Glide.grEnable(GR_TEXTURE_UMA_EXT);
|
||||
start = fxMesa->Glide.grTexMinAddress(0);
|
||||
end = fxMesa->Glide.grTexMaxAddress(0);
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
shared->totalTexMem[0] = end - start;
|
||||
shared->totalTexMem[1] = 0;
|
||||
shared->freeTexMem[0] = end - start;
|
||||
shared->freeTexMem[1] = 0;
|
||||
shared->tmFree[0] = NewRangeNode(fxMesa, start, end);
|
||||
shared->tmFree[1] = NULL;
|
||||
/*printf("UMA tex memory: %d\n", (int) (end - start));*/
|
||||
}
|
||||
else {
|
||||
const int numTMUs = fxMesa->haveTwoTMUs ? 2 : 1;
|
||||
int tmu;
|
||||
shared->umaTexMemory = GL_FALSE;
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
for (tmu = 0; tmu < numTMUs; tmu++) {
|
||||
FxU32 start = fxMesa->Glide.grTexMinAddress(tmu);
|
||||
FxU32 end = fxMesa->Glide.grTexMaxAddress(tmu);
|
||||
shared->totalTexMem[tmu] = end - start;
|
||||
shared->freeTexMem[tmu] = end - start;
|
||||
shared->tmFree[tmu] = NewRangeNode(fxMesa, start, end);
|
||||
/*printf("Split tex memory: %d\n", (int) (end - start));*/
|
||||
}
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
|
||||
shared->tmPool = NULL;
|
||||
fxMesa->glCtx->Shared->DriverData = shared;
|
||||
/*printf("Texture memory init UMA: %d\n", shared->umaTexMemory);*/
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Clean-up texture memory before destroying context.
|
||||
*/
|
||||
void
|
||||
tdfxTMClose(tdfxContextPtr fxMesa)
|
||||
{
|
||||
if (fxMesa->glCtx->Shared->RefCount == 1 && fxMesa->driDrawable) {
|
||||
/* refcount will soon go to zero, free our 3dfx stuff */
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) fxMesa->glCtx->Shared->DriverData;
|
||||
|
||||
const int numTMUs = fxMesa->haveTwoTMUs ? 2 : 1;
|
||||
int tmu;
|
||||
tdfxMemRange *tmp, *next;
|
||||
|
||||
/* Deallocate the pool of free tdfxMemRange nodes */
|
||||
tmp = shared->tmPool;
|
||||
while (tmp) {
|
||||
next = tmp->next;
|
||||
FREE(tmp);
|
||||
tmp = next;
|
||||
}
|
||||
|
||||
/* Delete the texture memory block tdfxMemRange nodes */
|
||||
for (tmu = 0; tmu < numTMUs; tmu++) {
|
||||
tmp = shared->tmFree[tmu];
|
||||
while (tmp) {
|
||||
next = tmp->next;
|
||||
FREE(tmp);
|
||||
tmp = next;
|
||||
}
|
||||
}
|
||||
|
||||
FREE(shared);
|
||||
fxMesa->glCtx->Shared->DriverData = NULL;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* Delete a tdfxMemRange struct.
|
||||
* We keep a linked list of free/available tdfxMemRange structs to
|
||||
* avoid extra malloc/free calls.
|
||||
*/
|
||||
#if 0
|
||||
static void
|
||||
DeleteRangeNode_NoLock(struct TdfxSharedState *shared, tdfxMemRange *range)
|
||||
{
|
||||
/* insert at head of list */
|
||||
range->next = shared->tmPool;
|
||||
shared->tmPool = range;
|
||||
}
|
||||
#endif
|
||||
|
||||
#define DELETE_RANGE_NODE(shared, range) \
|
||||
(range)->next = (shared)->tmPool; \
|
||||
(shared)->tmPool = (range)
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* When we've run out of texture memory we have to throw out an
|
||||
* existing texture to make room for the new one. This function
|
||||
* determins the texture to throw out.
|
||||
*/
|
||||
static struct gl_texture_object *
|
||||
FindOldestObject(tdfxContextPtr fxMesa, FxU32 tmu)
|
||||
{
|
||||
const GLuint bindnumber = fxMesa->texBindNumber;
|
||||
struct gl_texture_object *oldestObj, *obj, *lowestPriorityObj;
|
||||
GLfloat lowestPriority;
|
||||
GLuint oldestAge;
|
||||
|
||||
oldestObj = NULL;
|
||||
oldestAge = 0;
|
||||
|
||||
lowestPriority = 1.0F;
|
||||
lowestPriorityObj = NULL;
|
||||
|
||||
for (obj = fxMesa->glCtx->Shared->TexObjectList; obj; obj = obj->Next) {
|
||||
tdfxTexInfo *info = TDFX_TEXTURE_DATA(obj);
|
||||
|
||||
if (info && info->isInTM &&
|
||||
((info->whichTMU == tmu) || (info->whichTMU == TDFX_TMU_BOTH) ||
|
||||
(info->whichTMU == TDFX_TMU_SPLIT))) {
|
||||
GLuint age, lasttime;
|
||||
|
||||
assert(info->tm[0]);
|
||||
lasttime = info->lastTimeUsed;
|
||||
|
||||
if (lasttime > bindnumber)
|
||||
age = bindnumber + (UINT_MAX - lasttime + 1); /* TO DO: check wrap around */
|
||||
else
|
||||
age = bindnumber - lasttime;
|
||||
|
||||
if (age >= oldestAge) {
|
||||
oldestAge = age;
|
||||
oldestObj = obj;
|
||||
}
|
||||
|
||||
/* examine priority */
|
||||
if (obj->Priority < lowestPriority) {
|
||||
lowestPriority = obj->Priority;
|
||||
lowestPriorityObj = obj;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
if (lowestPriority < 1.0) {
|
||||
ASSERT(lowestPriorityObj);
|
||||
/*
|
||||
printf("discard %d pri=%f\n", lowestPriorityObj->Name, lowestPriority);
|
||||
*/
|
||||
return lowestPriorityObj;
|
||||
}
|
||||
else {
|
||||
/*
|
||||
printf("discard %d age=%d\n", oldestObj->Name, oldestAge);
|
||||
*/
|
||||
return oldestObj;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#if 0
|
||||
static void
|
||||
FlushTexMemory(tdfxContextPtr fxMesa)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
struct gl_texture_object *obj;
|
||||
|
||||
for (obj = mesaShared->TexObjectList; obj; obj = obj->Next) {
|
||||
if (obj->RefCount < 2) {
|
||||
/* don't flush currently bound textures */
|
||||
tdfxTMMoveOutTM_NoLock(fxMesa, obj);
|
||||
}
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Find the address (offset?) at which we can store a new texture.
|
||||
* <tmu> is the texture unit.
|
||||
* <size> is the texture size in bytes.
|
||||
*/
|
||||
static FxU32
|
||||
FindStartAddr(tdfxContextPtr fxMesa, FxU32 tmu, FxU32 size)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
tdfxMemRange *prev, *block;
|
||||
FxU32 result;
|
||||
#if 0
|
||||
int discardedCount = 0;
|
||||
#define MAX_DISCARDS 10
|
||||
#endif
|
||||
|
||||
if (shared->umaTexMemory) {
|
||||
assert(tmu == TDFX_TMU0);
|
||||
}
|
||||
|
||||
_glthread_LOCK_MUTEX(mesaShared->Mutex);
|
||||
while (1) {
|
||||
prev = NULL;
|
||||
block = shared->tmFree[tmu];
|
||||
while (block) {
|
||||
if (block->endAddr - block->startAddr >= size) {
|
||||
/* The texture will fit here */
|
||||
result = block->startAddr;
|
||||
block->startAddr += size;
|
||||
if (block->startAddr == block->endAddr) {
|
||||
/* Remove this node since it's empty */
|
||||
if (prev) {
|
||||
prev->next = block->next;
|
||||
}
|
||||
else {
|
||||
shared->tmFree[tmu] = block->next;
|
||||
}
|
||||
DELETE_RANGE_NODE(shared, block);
|
||||
}
|
||||
shared->freeTexMem[tmu] -= size;
|
||||
_glthread_UNLOCK_MUTEX(mesaShared->Mutex);
|
||||
return result;
|
||||
}
|
||||
prev = block;
|
||||
block = block->next;
|
||||
}
|
||||
/* We failed to find a block large enough to accomodate <size> bytes.
|
||||
* Find the oldest texObject and free it.
|
||||
*/
|
||||
#if 0
|
||||
discardedCount++;
|
||||
if (discardedCount > MAX_DISCARDS + 1) {
|
||||
_mesa_problem(NULL, "%s: extreme texmem fragmentation", __FUNCTION__);
|
||||
_glthread_UNLOCK_MUTEX(mesaShared->Mutex);
|
||||
return BAD_ADDRESS;
|
||||
}
|
||||
else if (discardedCount > MAX_DISCARDS) {
|
||||
/* texture memory is probably really fragmented, flush it */
|
||||
FlushTexMemory(fxMesa);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
{
|
||||
struct gl_texture_object *obj = FindOldestObject(fxMesa, tmu);
|
||||
if (obj) {
|
||||
tdfxTMMoveOutTM_NoLock(fxMesa, obj);
|
||||
fxMesa->stats.texSwaps++;
|
||||
}
|
||||
else {
|
||||
_mesa_problem(NULL, "%s: extreme texmem fragmentation", __FUNCTION__);
|
||||
_glthread_UNLOCK_MUTEX(mesaShared->Mutex);
|
||||
return BAD_ADDRESS;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
/* never get here, but play it safe */
|
||||
_glthread_UNLOCK_MUTEX(mesaShared->Mutex);
|
||||
return BAD_ADDRESS;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Remove the given tdfxMemRange node from hardware texture memory.
|
||||
*/
|
||||
static void
|
||||
RemoveRange_NoLock(tdfxContextPtr fxMesa, FxU32 tmu, tdfxMemRange *range)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
tdfxMemRange *block, *prev;
|
||||
|
||||
if (shared->umaTexMemory) {
|
||||
assert(tmu == TDFX_TMU0);
|
||||
}
|
||||
|
||||
if (!range)
|
||||
return;
|
||||
|
||||
if (range->startAddr == range->endAddr) {
|
||||
DELETE_RANGE_NODE(shared, range);
|
||||
return;
|
||||
}
|
||||
shared->freeTexMem[tmu] += range->endAddr - range->startAddr;
|
||||
|
||||
/* find position in linked list to insert this tdfxMemRange node */
|
||||
prev = NULL;
|
||||
block = shared->tmFree[tmu];
|
||||
while (block) {
|
||||
assert(range->startAddr != block->startAddr);
|
||||
if (range->startAddr > block->startAddr) {
|
||||
prev = block;
|
||||
block = block->next;
|
||||
}
|
||||
else {
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/* Insert the free block, combine with adjacent blocks when possible */
|
||||
range->next = block;
|
||||
if (block) {
|
||||
if (range->endAddr == block->startAddr) {
|
||||
/* Combine */
|
||||
block->startAddr = range->startAddr;
|
||||
DELETE_RANGE_NODE(shared, range);
|
||||
range = block;
|
||||
}
|
||||
}
|
||||
if (prev) {
|
||||
if (prev->endAddr == range->startAddr) {
|
||||
/* Combine */
|
||||
prev->endAddr = range->endAddr;
|
||||
prev->next = range->next;
|
||||
DELETE_RANGE_NODE(shared, range);
|
||||
}
|
||||
else {
|
||||
prev->next = range;
|
||||
}
|
||||
}
|
||||
else {
|
||||
shared->tmFree[tmu] = range;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#if 0 /* NOT USED */
|
||||
static void
|
||||
RemoveRange(tdfxContextPtr fxMesa, FxU32 tmu, tdfxMemRange *range)
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
_glthread_LOCK_MUTEX(mesaShared->Mutex);
|
||||
RemoveRange_NoLock(fxMesa, tmu, range);
|
||||
_glthread_UNLOCK_MUTEX(mesaShared->Mutex);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/*
|
||||
* Allocate space for a texture image.
|
||||
* <tmu> is the texture unit
|
||||
* <texmemsize> is the number of bytes to allocate
|
||||
*/
|
||||
static tdfxMemRange *
|
||||
AllocTexMem(tdfxContextPtr fxMesa, FxU32 tmu, FxU32 texmemsize)
|
||||
{
|
||||
FxU32 startAddr;
|
||||
startAddr = FindStartAddr(fxMesa, tmu, texmemsize);
|
||||
if (startAddr == BAD_ADDRESS) {
|
||||
_mesa_problem(fxMesa->glCtx, "%s returned NULL! tmu=%d texmemsize=%d",
|
||||
__FUNCTION__, (int) tmu, (int) texmemsize);
|
||||
return NULL;
|
||||
}
|
||||
else {
|
||||
tdfxMemRange *range;
|
||||
range = NewRangeNode(fxMesa, startAddr, startAddr + texmemsize);
|
||||
return range;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Download (copy) the given texture data (all mipmap levels) into the
|
||||
* Voodoo's texture memory.
|
||||
* The texture memory must have already been allocated.
|
||||
*/
|
||||
void
|
||||
tdfxTMDownloadTexture(tdfxContextPtr fxMesa, struct gl_texture_object *tObj)
|
||||
{
|
||||
tdfxTexInfo *ti;
|
||||
GLint l;
|
||||
FxU32 targetTMU;
|
||||
|
||||
assert(tObj);
|
||||
ti = TDFX_TEXTURE_DATA(tObj);
|
||||
assert(ti);
|
||||
targetTMU = ti->whichTMU;
|
||||
|
||||
switch (targetTMU) {
|
||||
case TDFX_TMU0:
|
||||
case TDFX_TMU1:
|
||||
if (ti->tm[targetTMU]) {
|
||||
for (l = ti->minLevel; l <= ti->maxLevel
|
||||
&& tObj->Image[l]->Data; l++) {
|
||||
GrLOD_t glideLod = ti->info.largeLodLog2 - l + tObj->BaseLevel;
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(targetTMU,
|
||||
ti->tm[targetTMU]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_BOTH,
|
||||
tObj->Image[l]->Data);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case TDFX_TMU_SPLIT:
|
||||
if (ti->tm[TDFX_TMU0] && ti->tm[TDFX_TMU1]) {
|
||||
for (l = ti->minLevel; l <= ti->maxLevel
|
||||
&& tObj->Image[l]->Data; l++) {
|
||||
GrLOD_t glideLod = ti->info.largeLodLog2 - l + tObj->BaseLevel;
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU0,
|
||||
ti->tm[TDFX_TMU0]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_ODD,
|
||||
tObj->Image[l]->Data);
|
||||
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU1,
|
||||
ti->tm[TDFX_TMU1]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_EVEN,
|
||||
tObj->Image[l]->Data);
|
||||
}
|
||||
}
|
||||
break;
|
||||
case TDFX_TMU_BOTH:
|
||||
if (ti->tm[TDFX_TMU0] && ti->tm[TDFX_TMU1]) {
|
||||
for (l = ti->minLevel; l <= ti->maxLevel
|
||||
&& tObj->Image[l]->Data; l++) {
|
||||
GrLOD_t glideLod = ti->info.largeLodLog2 - l + tObj->BaseLevel;
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU0,
|
||||
ti->tm[TDFX_TMU0]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_BOTH,
|
||||
tObj->Image[l]->Data);
|
||||
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU1,
|
||||
ti->tm[TDFX_TMU1]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_BOTH,
|
||||
tObj->Image[l]->Data);
|
||||
}
|
||||
}
|
||||
break;
|
||||
default:
|
||||
_mesa_problem(NULL, "%s: bad tmu (%d)", __FUNCTION__, (int)targetTMU);
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
tdfxTMReloadMipMapLevel(GLcontext *ctx, struct gl_texture_object *tObj,
|
||||
GLint level)
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA(tObj);
|
||||
GrLOD_t glideLod;
|
||||
FxU32 tmu;
|
||||
|
||||
tmu = ti->whichTMU;
|
||||
glideLod = ti->info.largeLodLog2 - level + tObj->BaseLevel;
|
||||
ASSERT(ti->isInTM);
|
||||
|
||||
LOCK_HARDWARE(fxMesa);
|
||||
|
||||
switch (tmu) {
|
||||
case TDFX_TMU0:
|
||||
case TDFX_TMU1:
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(tmu,
|
||||
ti->tm[tmu]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_BOTH,
|
||||
tObj->Image[level]->Data);
|
||||
break;
|
||||
case TDFX_TMU_SPLIT:
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU0,
|
||||
ti->tm[GR_TMU0]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_ODD,
|
||||
tObj->Image[level]->Data);
|
||||
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU1,
|
||||
ti->tm[GR_TMU1]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_EVEN,
|
||||
tObj->Image[level]->Data);
|
||||
break;
|
||||
case TDFX_TMU_BOTH:
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU0,
|
||||
ti->tm[GR_TMU0]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_BOTH,
|
||||
tObj->Image[level]->Data);
|
||||
|
||||
fxMesa->Glide.grTexDownloadMipMapLevel(GR_TMU1,
|
||||
ti->tm[GR_TMU1]->startAddr,
|
||||
glideLod,
|
||||
ti->info.largeLodLog2,
|
||||
ti->info.aspectRatioLog2,
|
||||
ti->info.format,
|
||||
GR_MIPMAPLEVELMASK_BOTH,
|
||||
tObj->Image[level]->Data);
|
||||
break;
|
||||
|
||||
default:
|
||||
_mesa_problem(ctx, "%s: bad tmu (%d)", __FUNCTION__, (int)tmu);
|
||||
break;
|
||||
}
|
||||
UNLOCK_HARDWARE(fxMesa);
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Allocate space for the given texture in texture memory then
|
||||
* download (copy) it into that space.
|
||||
*/
|
||||
void
|
||||
tdfxTMMoveInTM_NoLock( tdfxContextPtr fxMesa, struct gl_texture_object *tObj,
|
||||
FxU32 targetTMU )
|
||||
{
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA(tObj);
|
||||
FxU32 texmemsize;
|
||||
|
||||
fxMesa->stats.reqTexUpload++;
|
||||
|
||||
if (ti->isInTM) {
|
||||
if (ti->whichTMU == targetTMU)
|
||||
return;
|
||||
if (targetTMU == TDFX_TMU_SPLIT || ti->whichTMU == TDFX_TMU_SPLIT) {
|
||||
tdfxTMMoveOutTM_NoLock(fxMesa, tObj);
|
||||
}
|
||||
else {
|
||||
if (ti->whichTMU == TDFX_TMU_BOTH)
|
||||
return;
|
||||
targetTMU = TDFX_TMU_BOTH;
|
||||
}
|
||||
}
|
||||
|
||||
ti->whichTMU = targetTMU;
|
||||
|
||||
switch (targetTMU) {
|
||||
case TDFX_TMU0:
|
||||
case TDFX_TMU1:
|
||||
texmemsize = fxMesa->Glide.grTexTextureMemRequired(GR_MIPMAPLEVELMASK_BOTH,
|
||||
&(ti->info));
|
||||
ti->tm[targetTMU] = AllocTexMem(fxMesa, targetTMU, texmemsize);
|
||||
break;
|
||||
case TDFX_TMU_SPLIT:
|
||||
texmemsize = fxMesa->Glide.grTexTextureMemRequired(GR_MIPMAPLEVELMASK_ODD,
|
||||
&(ti->info));
|
||||
ti->tm[TDFX_TMU0] = AllocTexMem(fxMesa, TDFX_TMU0, texmemsize);
|
||||
if (ti->tm[TDFX_TMU0])
|
||||
fxMesa->stats.memTexUpload += texmemsize;
|
||||
|
||||
texmemsize = fxMesa->Glide.grTexTextureMemRequired(GR_MIPMAPLEVELMASK_EVEN,
|
||||
&(ti->info));
|
||||
ti->tm[TDFX_TMU1] = AllocTexMem(fxMesa, TDFX_TMU1, texmemsize);
|
||||
break;
|
||||
case TDFX_TMU_BOTH:
|
||||
texmemsize = fxMesa->Glide.grTexTextureMemRequired(GR_MIPMAPLEVELMASK_BOTH,
|
||||
&(ti->info));
|
||||
ti->tm[TDFX_TMU0] = AllocTexMem(fxMesa, TDFX_TMU0, texmemsize);
|
||||
if (ti->tm[TDFX_TMU0])
|
||||
fxMesa->stats.memTexUpload += texmemsize;
|
||||
|
||||
texmemsize = fxMesa->Glide.grTexTextureMemRequired(GR_MIPMAPLEVELMASK_BOTH,
|
||||
&(ti->info));
|
||||
ti->tm[TDFX_TMU1] = AllocTexMem(fxMesa, TDFX_TMU1, texmemsize);
|
||||
break;
|
||||
default:
|
||||
_mesa_problem(NULL, "%s: bad tmu (%d)", __FUNCTION__, (int)targetTMU);
|
||||
return;
|
||||
}
|
||||
|
||||
ti->reloadImages = GL_TRUE;
|
||||
ti->isInTM = GL_TRUE;
|
||||
|
||||
fxMesa->stats.texUpload++;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Move the given texture out of hardware texture memory.
|
||||
* This deallocates the texture's memory space.
|
||||
*/
|
||||
void
|
||||
tdfxTMMoveOutTM_NoLock( tdfxContextPtr fxMesa, struct gl_texture_object *tObj )
|
||||
{
|
||||
struct gl_shared_state *mesaShared = fxMesa->glCtx->Shared;
|
||||
struct tdfxSharedState *shared = (struct tdfxSharedState *) mesaShared->DriverData;
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA(tObj);
|
||||
|
||||
if (MESA_VERBOSE & VERBOSE_DRIVER) {
|
||||
fprintf(stderr, "fxmesa: %s(%p (%d))\n", __FUNCTION__, tObj, tObj->Name);
|
||||
}
|
||||
|
||||
/*
|
||||
VerifyFreeList(fxMesa, 0);
|
||||
VerifyFreeList(fxMesa, 1);
|
||||
*/
|
||||
|
||||
if (!ti || !ti->isInTM)
|
||||
return;
|
||||
|
||||
switch (ti->whichTMU) {
|
||||
case TDFX_TMU0:
|
||||
case TDFX_TMU1:
|
||||
RemoveRange_NoLock(fxMesa, ti->whichTMU, ti->tm[ti->whichTMU]);
|
||||
break;
|
||||
case TDFX_TMU_SPLIT:
|
||||
case TDFX_TMU_BOTH:
|
||||
assert(!shared->umaTexMemory);
|
||||
RemoveRange_NoLock(fxMesa, TDFX_TMU0, ti->tm[TDFX_TMU0]);
|
||||
RemoveRange_NoLock(fxMesa, TDFX_TMU1, ti->tm[TDFX_TMU1]);
|
||||
break;
|
||||
default:
|
||||
_mesa_problem(NULL, "%s: bad tmu (%d)", __FUNCTION__, (int)ti->whichTMU);
|
||||
return;
|
||||
}
|
||||
|
||||
ti->isInTM = GL_FALSE;
|
||||
ti->tm[0] = NULL;
|
||||
ti->tm[1] = NULL;
|
||||
ti->whichTMU = TDFX_TMU_NONE;
|
||||
|
||||
/*
|
||||
VerifyFreeList(fxMesa, 0);
|
||||
VerifyFreeList(fxMesa, 1);
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
* Called via glDeleteTexture to delete a texture object.
|
||||
*/
|
||||
void
|
||||
tdfxTMFreeTexture(tdfxContextPtr fxMesa, struct gl_texture_object *tObj)
|
||||
{
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA(tObj);
|
||||
if (ti) {
|
||||
tdfxTMMoveOutTM(fxMesa, tObj);
|
||||
FREE(ti);
|
||||
tObj->DriverData = NULL;
|
||||
}
|
||||
/*
|
||||
VerifyFreeList(fxMesa, 0);
|
||||
VerifyFreeList(fxMesa, 1);
|
||||
*/
|
||||
}
|
||||
|
||||
|
||||
|
||||
/*
|
||||
* After a context switch this function will be called to restore
|
||||
* texture memory for the new context.
|
||||
*/
|
||||
void tdfxTMRestoreTextures_NoLock( tdfxContextPtr fxMesa )
|
||||
{
|
||||
GLcontext *ctx = fxMesa->glCtx;
|
||||
struct gl_texture_object *tObj;
|
||||
int i;
|
||||
|
||||
for ( tObj = ctx->Shared->TexObjectList ; tObj ; tObj = tObj->Next ) {
|
||||
tdfxTexInfo *ti = TDFX_TEXTURE_DATA( tObj );
|
||||
if ( ti && ti->isInTM ) {
|
||||
for ( i = 0 ; i < MAX_TEXTURE_UNITS ; i++ ) {
|
||||
if ( ctx->Texture.Unit[i]._Current == tObj ) {
|
||||
tdfxTMDownloadTexture( fxMesa, tObj );
|
||||
break;
|
||||
}
|
||||
}
|
||||
if ( i == MAX_TEXTURE_UNITS ) {
|
||||
tdfxTMMoveOutTM_NoLock( fxMesa, tObj );
|
||||
}
|
||||
}
|
||||
}
|
||||
/*
|
||||
VerifyFreeList(fxMesa, 0);
|
||||
VerifyFreeList(fxMesa, 1);
|
||||
*/
|
||||
}
|
||||
@@ -0,0 +1,84 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_texman.h,v 1.2 2002/02/22 21:45:04 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_TEXMAN_H__
|
||||
#define __TDFX_TEXMAN_H__
|
||||
|
||||
|
||||
#include "tdfx_lock.h"
|
||||
|
||||
|
||||
extern void tdfxTMInit( tdfxContextPtr fxMesa );
|
||||
|
||||
extern void tdfxTMClose( tdfxContextPtr fxMesa );
|
||||
|
||||
extern void tdfxTMDownloadTexture(tdfxContextPtr fxMesa,
|
||||
struct gl_texture_object *tObj);
|
||||
|
||||
extern void tdfxTMReloadMipMapLevel( GLcontext *ctx,
|
||||
struct gl_texture_object *tObj,
|
||||
GLint level );
|
||||
|
||||
extern void tdfxTMMoveInTM_NoLock( tdfxContextPtr fxMesa,
|
||||
struct gl_texture_object *tObj,
|
||||
FxU32 targetTMU );
|
||||
|
||||
extern void tdfxTMMoveOutTM_NoLock( tdfxContextPtr fxMesa,
|
||||
struct gl_texture_object *tObj );
|
||||
|
||||
extern void tdfxTMFreeTexture( tdfxContextPtr fxMesa,
|
||||
struct gl_texture_object *tObj );
|
||||
|
||||
extern void tdfxTMRestoreTextures_NoLock( tdfxContextPtr fxMesa );
|
||||
|
||||
|
||||
#define tdfxTMMoveInTM( fxMesa, tObj, targetTMU ) \
|
||||
do { \
|
||||
LOCK_HARDWARE( fxMesa ); \
|
||||
tdfxTMMoveInTM_NoLock( fxMesa, tObj, targetTMU ); \
|
||||
UNLOCK_HARDWARE( fxMesa ); \
|
||||
} while (0)
|
||||
|
||||
#define tdfxTMMoveOutTM( fxMesa, tObj ) \
|
||||
do { \
|
||||
LOCK_HARDWARE( fxMesa ); \
|
||||
tdfxTMMoveOutTM_NoLock( fxMesa, tObj ); \
|
||||
UNLOCK_HARDWARE( fxMesa ); \
|
||||
} while (0)
|
||||
|
||||
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,44 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_texstate.h,v 1.1 2002/02/22 21:45:04 dawes Exp $ */
|
||||
|
||||
/*
|
||||
* Original rewrite:
|
||||
* Gareth Hughes <gareth@valinux.com>, 29 Sep - 1 Oct 2000
|
||||
*
|
||||
* Authors:
|
||||
* Gareth Hughes <gareth@valinux.com>
|
||||
* Brian Paul <brianp@valinux.com>
|
||||
*
|
||||
*/
|
||||
|
||||
#ifndef __TDFX_TEXSTATE_H__
|
||||
#define __TDFX_TEXSTATE_H__
|
||||
|
||||
extern void tdfxUpdateTextureState( GLcontext *ctx );
|
||||
extern void tdfxUpdateTextureBinding( GLcontext *ctx );
|
||||
|
||||
#endif
|
||||
File diff suppressed because it is too large
Load Diff
@@ -0,0 +1,42 @@
|
||||
/* -*- mode: c; c-basic-offset: 3 -*-
|
||||
*
|
||||
* Copyright 2000 VA Linux Systems Inc., Fremont, California.
|
||||
*
|
||||
* All Rights Reserved.
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice (including the next
|
||||
* paragraph) shall be included in all copies or substantial portions of the
|
||||
* Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
|
||||
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* VA LINUX SYSTEMS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
|
||||
* WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF
|
||||
* OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
|
||||
* SOFTWARE.
|
||||
*/
|
||||
|
||||
/*
|
||||
* Authors:
|
||||
* Keith Whitwell <keith@tungstengraphics.com>
|
||||
*
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_tris.h,v 1.5 2002/10/30 12:52:01 alanh Exp $ */
|
||||
|
||||
#ifndef TDFX_TRIS_INC
|
||||
#define TDFX_TRIS_INC
|
||||
|
||||
#include "mtypes.h"
|
||||
|
||||
extern void tdfxDDInitTriFuncs( GLcontext *ctx );
|
||||
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,365 @@
|
||||
/*
|
||||
* GLX Hardware Device Driver for Intel i810
|
||||
* Copyright (C) 1999 Keith Whitwell
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included
|
||||
* in all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* KEITH WHITWELL, OR ANY OTHER CONTRIBUTORS BE LIABLE FOR ANY CLAIM,
|
||||
* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||
* OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
|
||||
* OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
*
|
||||
*
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_vb.c,v 1.3 2002/10/30 12:52:01 alanh Exp $ */
|
||||
|
||||
#include "glheader.h"
|
||||
#include "mtypes.h"
|
||||
#include "imports.h"
|
||||
#include "macros.h"
|
||||
#include "colormac.h"
|
||||
|
||||
#include "math/m_translate.h"
|
||||
#include "swrast_setup/swrast_setup.h"
|
||||
|
||||
#include "tdfx_context.h"
|
||||
#include "tdfx_vb.h"
|
||||
#include "tdfx_tris.h"
|
||||
#include "tdfx_state.h"
|
||||
#include "tdfx_render.h"
|
||||
|
||||
static void copy_pv_rgba4( GLcontext *ctx, GLuint edst, GLuint esrc )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT( ctx );
|
||||
GLubyte *tdfxverts = (GLubyte *)fxMesa->verts;
|
||||
GLuint shift = fxMesa->vertex_stride_shift;
|
||||
tdfxVertex *dst = (tdfxVertex *)(tdfxverts + (edst << shift));
|
||||
tdfxVertex *src = (tdfxVertex *)(tdfxverts + (esrc << shift));
|
||||
dst->ui[4] = src->ui[4];
|
||||
}
|
||||
|
||||
static void copy_pv_rgba3( GLcontext *ctx, GLuint edst, GLuint esrc )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT( ctx );
|
||||
GLubyte *tdfxverts = (GLubyte *)fxMesa->verts;
|
||||
GLuint shift = fxMesa->vertex_stride_shift;
|
||||
tdfxVertex *dst = (tdfxVertex *)(tdfxverts + (edst << shift));
|
||||
tdfxVertex *src = (tdfxVertex *)(tdfxverts + (esrc << shift));
|
||||
dst->ui[3] = src->ui[3];
|
||||
}
|
||||
|
||||
typedef void (*emit_func)( GLcontext *, GLuint, GLuint, void *, GLuint );
|
||||
|
||||
static struct {
|
||||
emit_func emit;
|
||||
interp_func interp;
|
||||
copy_pv_func copy_pv;
|
||||
GLboolean (*check_tex_sizes)( GLcontext *ctx );
|
||||
GLuint vertex_size;
|
||||
GLuint vertex_stride_shift;
|
||||
GLuint vertex_format;
|
||||
} setup_tab[TDFX_MAX_SETUP];
|
||||
|
||||
|
||||
static void import_float_colors( GLcontext *ctx )
|
||||
{
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
struct gl_client_array *from = VB->ColorPtr[0];
|
||||
struct gl_client_array *to = &TDFX_CONTEXT(ctx)->UbyteColor;
|
||||
GLuint count = VB->Count;
|
||||
|
||||
if (!to->Ptr) {
|
||||
to->Ptr = ALIGN_MALLOC( VB->Size * 4 * sizeof(GLubyte), 32 );
|
||||
to->Type = GL_UNSIGNED_BYTE;
|
||||
}
|
||||
|
||||
/* No need to transform the same value 3000 times.
|
||||
*/
|
||||
if (!from->StrideB) {
|
||||
to->StrideB = 0;
|
||||
count = 1;
|
||||
}
|
||||
else
|
||||
to->StrideB = 4 * sizeof(GLubyte);
|
||||
|
||||
_math_trans_4ub( (GLubyte (*)[4]) to->Ptr,
|
||||
from->Ptr,
|
||||
from->StrideB,
|
||||
from->Type,
|
||||
from->Size,
|
||||
0,
|
||||
count);
|
||||
|
||||
VB->ColorPtr[0] = to;
|
||||
}
|
||||
|
||||
|
||||
#define GET_COLOR(ptr, idx) (((GLchan (*)[4])((ptr)->Ptr))[idx])
|
||||
|
||||
|
||||
static void interp_extras( GLcontext *ctx,
|
||||
GLfloat t,
|
||||
GLuint dst, GLuint out, GLuint in,
|
||||
GLboolean force_boundary )
|
||||
{
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
|
||||
/*fprintf(stderr, "%s\n", __FUNCTION__);*/
|
||||
|
||||
if (VB->ColorPtr[1]) {
|
||||
INTERP_4CHAN( t,
|
||||
GET_COLOR(VB->ColorPtr[1], dst),
|
||||
GET_COLOR(VB->ColorPtr[1], out),
|
||||
GET_COLOR(VB->ColorPtr[1], in) );
|
||||
}
|
||||
|
||||
if (VB->EdgeFlag) {
|
||||
VB->EdgeFlag[dst] = VB->EdgeFlag[out] || force_boundary;
|
||||
}
|
||||
|
||||
setup_tab[TDFX_CONTEXT(ctx)->SetupIndex].interp(ctx, t, dst, out, in,
|
||||
force_boundary);
|
||||
}
|
||||
|
||||
static void copy_pv_extras( GLcontext *ctx, GLuint dst, GLuint src )
|
||||
{
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
|
||||
if (VB->ColorPtr[1]) {
|
||||
COPY_CHAN4( GET_COLOR(VB->ColorPtr[1], dst),
|
||||
GET_COLOR(VB->ColorPtr[1], src) );
|
||||
}
|
||||
|
||||
setup_tab[TDFX_CONTEXT(ctx)->SetupIndex].copy_pv(ctx, dst, src);
|
||||
}
|
||||
|
||||
|
||||
|
||||
#define IND (TDFX_XYZ_BIT|TDFX_RGBA_BIT)
|
||||
#define TAG(x) x##_wg
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
/* Special for tdfx: fog requires w
|
||||
*/
|
||||
#define IND (TDFX_XYZ_BIT|TDFX_RGBA_BIT|TDFX_W_BIT)
|
||||
#define TAG(x) x##_wg_fog
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_XYZ_BIT|TDFX_RGBA_BIT|TDFX_W_BIT|TDFX_TEX0_BIT)
|
||||
#define TAG(x) x##_wgt0
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_XYZ_BIT|TDFX_RGBA_BIT|TDFX_W_BIT|TDFX_TEX0_BIT|TDFX_TEX1_BIT)
|
||||
#define TAG(x) x##_wgt0t1
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_XYZ_BIT|TDFX_RGBA_BIT|TDFX_W_BIT|TDFX_TEX0_BIT|TDFX_PTEX_BIT)
|
||||
#define TAG(x) x##_wgpt0
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_XYZ_BIT|TDFX_RGBA_BIT|TDFX_W_BIT|TDFX_TEX0_BIT|TDFX_TEX1_BIT|\
|
||||
TDFX_PTEX_BIT)
|
||||
#define TAG(x) x##_wgpt0t1
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_RGBA_BIT)
|
||||
#define TAG(x) x##_g
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_TEX0_BIT)
|
||||
#define TAG(x) x##_t0
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_TEX0_BIT|TDFX_TEX1_BIT)
|
||||
#define TAG(x) x##_t0t1
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_RGBA_BIT|TDFX_TEX0_BIT)
|
||||
#define TAG(x) x##_gt0
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
#define IND (TDFX_RGBA_BIT|TDFX_TEX0_BIT|TDFX_TEX1_BIT)
|
||||
#define TAG(x) x##_gt0t1
|
||||
#include "tdfx_vbtmp.h"
|
||||
|
||||
|
||||
|
||||
static void init_setup_tab( void )
|
||||
{
|
||||
init_wg();
|
||||
init_wg_fog();
|
||||
init_wgt0();
|
||||
init_wgt0t1();
|
||||
init_wgpt0();
|
||||
init_wgpt0t1();
|
||||
|
||||
init_g();
|
||||
init_t0();
|
||||
init_t0t1();
|
||||
init_gt0();
|
||||
init_gt0t1();
|
||||
}
|
||||
|
||||
|
||||
void tdfxPrintSetupFlags(char *msg, GLuint flags )
|
||||
{
|
||||
fprintf(stderr, "%s(%x): %s%s%s%s%s\n",
|
||||
msg,
|
||||
(int)flags,
|
||||
(flags & TDFX_XYZ_BIT) ? " xyz," : "",
|
||||
(flags & TDFX_W_BIT) ? " w," : "",
|
||||
(flags & TDFX_RGBA_BIT) ? " rgba," : "",
|
||||
(flags & TDFX_TEX0_BIT) ? " tex-0," : "",
|
||||
(flags & TDFX_TEX1_BIT) ? " tex-1," : "");
|
||||
}
|
||||
|
||||
|
||||
|
||||
void tdfxCheckTexSizes( GLcontext *ctx )
|
||||
{
|
||||
TNLcontext *tnl = TNL_CONTEXT(ctx);
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT( ctx );
|
||||
|
||||
if (!setup_tab[fxMesa->SetupIndex].check_tex_sizes(ctx)) {
|
||||
GLuint ind = fxMesa->SetupIndex |= (TDFX_PTEX_BIT|TDFX_RGBA_BIT);
|
||||
|
||||
/* Tdfx handles projective textures nicely; just have to change
|
||||
* up to the new vertex format.
|
||||
*/
|
||||
if (setup_tab[ind].vertex_format != fxMesa->vertexFormat) {
|
||||
FLUSH_BATCH(fxMesa);
|
||||
fxMesa->dirty |= TDFX_UPLOAD_VERTEX_LAYOUT;
|
||||
fxMesa->vertexFormat = setup_tab[ind].vertex_format;
|
||||
fxMesa->vertex_stride_shift = setup_tab[ind].vertex_stride_shift;
|
||||
|
||||
/* This is required as we have just changed the vertex
|
||||
* format, so the interp and copy routines must also change.
|
||||
* In the unfilled and twosided cases we are using the
|
||||
* swrast_setup ones anyway, so leave them in place.
|
||||
*/
|
||||
if (!(ctx->_TriangleCaps & (DD_TRI_LIGHT_TWOSIDE|DD_TRI_UNFILLED))) {
|
||||
tnl->Driver.Render.Interp = setup_tab[fxMesa->SetupIndex].interp;
|
||||
tnl->Driver.Render.CopyPV = setup_tab[fxMesa->SetupIndex].copy_pv;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void tdfxBuildVertices( GLcontext *ctx, GLuint start, GLuint count,
|
||||
GLuint newinputs )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT( ctx );
|
||||
GLubyte *v = (fxMesa->verts + (start<<fxMesa->vertex_stride_shift));
|
||||
GLuint stride = 1<<fxMesa->vertex_stride_shift;
|
||||
|
||||
newinputs |= fxMesa->SetupNewInputs;
|
||||
fxMesa->SetupNewInputs = 0;
|
||||
|
||||
if (!newinputs)
|
||||
return;
|
||||
|
||||
if (newinputs & VERT_BIT_CLIP) {
|
||||
setup_tab[fxMesa->SetupIndex].emit( ctx, start, count, v, stride );
|
||||
} else {
|
||||
GLuint ind = 0;
|
||||
|
||||
if (newinputs & VERT_BIT_COLOR0)
|
||||
ind |= TDFX_RGBA_BIT;
|
||||
|
||||
if (newinputs & VERT_BIT_TEX0)
|
||||
ind |= TDFX_TEX0_BIT;
|
||||
|
||||
if (newinputs & VERT_BIT_TEX1)
|
||||
ind |= TDFX_TEX0_BIT|TDFX_TEX1_BIT;
|
||||
|
||||
if (fxMesa->SetupIndex & TDFX_PTEX_BIT)
|
||||
ind = ~0;
|
||||
|
||||
ind &= fxMesa->SetupIndex;
|
||||
|
||||
if (ind) {
|
||||
setup_tab[ind].emit( ctx, start, count, v, stride );
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
void tdfxChooseVertexState( GLcontext *ctx )
|
||||
{
|
||||
TNLcontext *tnl = TNL_CONTEXT(ctx);
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT( ctx );
|
||||
GLuint ind = TDFX_XYZ_BIT|TDFX_RGBA_BIT;
|
||||
|
||||
if (ctx->Texture._EnabledUnits & 0x2)
|
||||
/* unit 1 enabled */
|
||||
ind |= TDFX_W_BIT|TDFX_TEX1_BIT|TDFX_TEX0_BIT;
|
||||
else if (ctx->Texture._EnabledUnits & 0x1)
|
||||
/* unit 0 enabled */
|
||||
ind |= TDFX_W_BIT|TDFX_TEX0_BIT;
|
||||
else if (ctx->Fog.Enabled)
|
||||
ind |= TDFX_W_BIT;
|
||||
|
||||
fxMesa->SetupIndex = ind;
|
||||
|
||||
if (ctx->_TriangleCaps & (DD_TRI_LIGHT_TWOSIDE|DD_TRI_UNFILLED)) {
|
||||
tnl->Driver.Render.Interp = interp_extras;
|
||||
tnl->Driver.Render.CopyPV = copy_pv_extras;
|
||||
} else {
|
||||
tnl->Driver.Render.Interp = setup_tab[ind].interp;
|
||||
tnl->Driver.Render.CopyPV = setup_tab[ind].copy_pv;
|
||||
}
|
||||
|
||||
if (setup_tab[ind].vertex_format != fxMesa->vertexFormat) {
|
||||
FLUSH_BATCH(fxMesa);
|
||||
fxMesa->dirty |= TDFX_UPLOAD_VERTEX_LAYOUT;
|
||||
fxMesa->vertexFormat = setup_tab[ind].vertex_format;
|
||||
fxMesa->vertex_stride_shift = setup_tab[ind].vertex_stride_shift;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
|
||||
void tdfxInitVB( GLcontext *ctx )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
GLuint size = TNL_CONTEXT(ctx)->vb.Size;
|
||||
static int firsttime = 1;
|
||||
if (firsttime) {
|
||||
init_setup_tab();
|
||||
firsttime = 0;
|
||||
}
|
||||
|
||||
fxMesa->verts = (GLubyte *)ALIGN_MALLOC(size * sizeof(tdfxVertex), 32);
|
||||
fxMesa->vertexFormat = setup_tab[TDFX_XYZ_BIT|TDFX_RGBA_BIT].vertex_format;
|
||||
fxMesa->vertex_stride_shift = setup_tab[(TDFX_XYZ_BIT|
|
||||
TDFX_RGBA_BIT)].vertex_stride_shift;
|
||||
fxMesa->SetupIndex = TDFX_XYZ_BIT|TDFX_RGBA_BIT;
|
||||
}
|
||||
|
||||
|
||||
void tdfxFreeVB( GLcontext *ctx )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
if (fxMesa->verts) {
|
||||
ALIGN_FREE(fxMesa->verts);
|
||||
fxMesa->verts = 0;
|
||||
}
|
||||
|
||||
if (fxMesa->UbyteColor.Ptr) {
|
||||
ALIGN_FREE(fxMesa->UbyteColor.Ptr);
|
||||
fxMesa->UbyteColor.Ptr = 0;
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,68 @@
|
||||
/*
|
||||
* GLX Hardware Device Driver for Intel tdfx
|
||||
* Copyright (C) 1999 Keith Whitwell
|
||||
*
|
||||
* Permission is hereby granted, free of charge, to any person obtaining a
|
||||
* copy of this software and associated documentation files (the "Software"),
|
||||
* to deal in the Software without restriction, including without limitation
|
||||
* the rights to use, copy, modify, merge, publish, distribute, sublicense,
|
||||
* and/or sell copies of the Software, and to permit persons to whom the
|
||||
* Software is furnished to do so, subject to the following conditions:
|
||||
*
|
||||
* The above copyright notice and this permission notice shall be included
|
||||
* in all copies or substantial portions of the Software.
|
||||
*
|
||||
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
|
||||
* OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
|
||||
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
|
||||
* KEITH WHITWELL, OR ANY OTHER CONTRIBUTORS BE LIABLE FOR ANY CLAIM,
|
||||
* DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
|
||||
* OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE
|
||||
* OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
|
||||
*
|
||||
*
|
||||
*/
|
||||
/* $XFree86: xc/lib/GL/mesa/src/drv/tdfx/tdfx_vb.h,v 1.2 2002/02/22 21:45:04 dawes Exp $ */
|
||||
|
||||
#ifndef TDFXVB_INC
|
||||
#define TDFXVB_INC
|
||||
|
||||
#include "mtypes.h"
|
||||
|
||||
#include "tnl/tnl.h"
|
||||
#include "tnl/t_context.h"
|
||||
#include "math/m_xform.h"
|
||||
|
||||
#define TDFX_XYZ_BIT 0x1
|
||||
#define TDFX_W_BIT 0x2
|
||||
#define TDFX_RGBA_BIT 0x4
|
||||
#define TDFX_TEX1_BIT 0x8
|
||||
#define TDFX_TEX0_BIT 0x10
|
||||
#define TDFX_PTEX_BIT 0x20
|
||||
#define TDFX_MAX_SETUP 0x40
|
||||
|
||||
#define _TDFX_NEW_RASTERSETUP (_NEW_TEXTURE | \
|
||||
_DD_NEW_SEPARATE_SPECULAR | \
|
||||
_DD_NEW_TRI_UNFILLED | \
|
||||
_DD_NEW_TRI_LIGHT_TWOSIDE | \
|
||||
_NEW_FOG)
|
||||
|
||||
|
||||
extern void tdfxValidateBuildProjVerts(GLcontext *ctx,
|
||||
GLuint start, GLuint count,
|
||||
GLuint newinputs );
|
||||
|
||||
extern void tdfxPrintSetupFlags(char *msg, GLuint flags );
|
||||
|
||||
extern void tdfxInitVB( GLcontext *ctx );
|
||||
|
||||
extern void tdfxFreeVB( GLcontext *ctx );
|
||||
|
||||
extern void tdfxCheckTexSizes( GLcontext *ctx );
|
||||
|
||||
extern void tdfxChooseVertexState( GLcontext *ctx );
|
||||
|
||||
extern void tdfxBuildVertices( GLcontext *ctx, GLuint start, GLuint count,
|
||||
GLuint newinputs );
|
||||
|
||||
#endif
|
||||
@@ -0,0 +1,442 @@
|
||||
|
||||
#if (IND & (TDFX_W_BIT|TDFX_TEX0_BIT|TDFX_TEX1_BIT))
|
||||
|
||||
static void TAG(emit)( GLcontext *ctx,
|
||||
GLuint start, GLuint end,
|
||||
void *dest,
|
||||
GLuint stride )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
GLfloat (*tc0)[4], (*tc1)[4];
|
||||
GLubyte (*col)[4];
|
||||
GLuint tc0_stride, tc1_stride, col_stride;
|
||||
GLuint tc0_size, tc1_size;
|
||||
GLfloat (*proj)[4] = VB->NdcPtr->data;
|
||||
GLuint proj_stride = VB->NdcPtr->stride;
|
||||
tdfxVertex *v = (tdfxVertex *)dest;
|
||||
GLfloat u0scale,v0scale,u1scale,v1scale;
|
||||
const GLubyte *mask = VB->ClipMask;
|
||||
const GLfloat *s = fxMesa->hw_viewport;
|
||||
int i;
|
||||
|
||||
/* fprintf(stderr, "%s\n", __FUNCTION__); */
|
||||
ASSERT(stride > 16);
|
||||
|
||||
|
||||
if (IND & TDFX_TEX0_BIT) {
|
||||
tc0_stride = VB->TexCoordPtr[0]->stride;
|
||||
tc0 = VB->TexCoordPtr[0]->data;
|
||||
u0scale = fxMesa->sScale0;
|
||||
v0scale = fxMesa->tScale0;
|
||||
if (IND & TDFX_PTEX_BIT)
|
||||
tc0_size = VB->TexCoordPtr[0]->size;
|
||||
}
|
||||
|
||||
if (IND & TDFX_TEX1_BIT) {
|
||||
tc1 = VB->TexCoordPtr[1]->data;
|
||||
tc1_stride = VB->TexCoordPtr[1]->stride;
|
||||
u1scale = fxMesa->sScale1;
|
||||
v1scale = fxMesa->tScale1;
|
||||
if (IND & TDFX_PTEX_BIT)
|
||||
tc1_size = VB->TexCoordPtr[1]->size;
|
||||
}
|
||||
|
||||
if (IND & TDFX_RGBA_BIT) {
|
||||
if (VB->ColorPtr[0]->Type != GL_UNSIGNED_BYTE)
|
||||
import_float_colors( ctx );
|
||||
col = VB->ColorPtr[0]->Ptr;
|
||||
col_stride = VB->ColorPtr[0]->StrideB;
|
||||
}
|
||||
|
||||
if (VB->importable_data) {
|
||||
/* May have nonstandard strides:
|
||||
*/
|
||||
if (start) {
|
||||
proj = (GLfloat (*)[4])((GLubyte *)proj + start * proj_stride);
|
||||
if (IND & TDFX_TEX0_BIT)
|
||||
tc0 = (GLfloat (*)[4])((GLubyte *)tc0 + start * tc0_stride);
|
||||
if (IND & TDFX_TEX1_BIT)
|
||||
tc1 = (GLfloat (*)[4])((GLubyte *)tc1 + start * tc1_stride);
|
||||
if (IND & TDFX_RGBA_BIT)
|
||||
STRIDE_4UB(col, start * col_stride);
|
||||
}
|
||||
|
||||
for (i=start; i < end; i++, v = (tdfxVertex *)((GLubyte *)v + stride)) {
|
||||
if (IND & TDFX_XYZ_BIT) {
|
||||
if (mask[i] == 0) {
|
||||
/* unclipped */
|
||||
v->v.x = s[0] * proj[0][0] + s[12];
|
||||
v->v.y = s[5] * proj[0][1] + s[13];
|
||||
v->v.z = s[10] * proj[0][2] + s[14];
|
||||
v->v.rhw = proj[0][3];
|
||||
} else {
|
||||
/* clipped */
|
||||
v->v.rhw = 1.0;
|
||||
}
|
||||
proj = (GLfloat (*)[4])((GLubyte *)proj + proj_stride);
|
||||
}
|
||||
if (IND & TDFX_RGBA_BIT) {
|
||||
#if 0
|
||||
*(GLuint *)&v->v.color = *(GLuint *)col;
|
||||
#else
|
||||
GLubyte *b = (GLubyte *) &v->v.color;
|
||||
b[0] = col[0][2];
|
||||
b[1] = col[0][1];
|
||||
b[2] = col[0][0];
|
||||
b[3] = col[0][3];
|
||||
|
||||
#endif
|
||||
STRIDE_4UB(col, col_stride);
|
||||
}
|
||||
if (IND & TDFX_TEX0_BIT) {
|
||||
GLfloat w = v->v.rhw;
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
v->pv.tu0 = tc0[0][0] * u0scale * w;
|
||||
v->pv.tv0 = tc0[0][1] * v0scale * w;
|
||||
v->pv.tq0 = w;
|
||||
if (tc0_size == 4)
|
||||
v->pv.tq0 = tc0[0][3] * w;
|
||||
}
|
||||
else {
|
||||
v->v.tu0 = tc0[0][0] * u0scale * w;
|
||||
v->v.tv0 = tc0[0][1] * v0scale * w;
|
||||
}
|
||||
tc0 = (GLfloat (*)[4])((GLubyte *)tc0 + tc0_stride);
|
||||
}
|
||||
if (IND & TDFX_TEX1_BIT) {
|
||||
GLfloat w = v->v.rhw;
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
v->pv.tu1 = tc1[0][0] * u1scale * w;
|
||||
v->pv.tv1 = tc1[0][1] * v1scale * w;
|
||||
v->pv.tq1 = w;
|
||||
if (tc1_size == 4)
|
||||
v->pv.tq1 = tc1[0][3] * w;
|
||||
}
|
||||
else {
|
||||
v->v.tu1 = tc1[0][0] * u1scale * w;
|
||||
v->v.tv1 = tc1[0][1] * v1scale * w;
|
||||
}
|
||||
tc1 = (GLfloat (*)[4])((GLubyte *)tc1 + tc1_stride);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
for (i=start; i < end; i++, v = (tdfxVertex *)((GLubyte *)v + stride)) {
|
||||
if (IND & TDFX_XYZ_BIT) {
|
||||
if (mask[i] == 0) {
|
||||
v->v.x = s[0] * proj[i][0] + s[12];
|
||||
v->v.y = s[5] * proj[i][1] + s[13];
|
||||
v->v.z = s[10] * proj[i][2] + s[14];
|
||||
v->v.rhw = proj[i][3];
|
||||
} else {
|
||||
v->v.rhw = 1.0;
|
||||
}
|
||||
}
|
||||
if (IND & TDFX_RGBA_BIT) {
|
||||
#if 0
|
||||
*(GLuint *)&v->v.color = *(GLuint *)&col[i];
|
||||
#else
|
||||
GLubyte *b = (GLubyte *) &v->v.color;
|
||||
b[0] = col[i][2];
|
||||
b[1] = col[i][1];
|
||||
b[2] = col[i][0];
|
||||
b[3] = col[i][3];
|
||||
|
||||
#endif
|
||||
}
|
||||
if (IND & TDFX_TEX0_BIT) {
|
||||
GLfloat w = v->v.rhw;
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
v->pv.tu0 = tc0[i][0] * u0scale * w;
|
||||
v->pv.tv0 = tc0[i][1] * v0scale * w;
|
||||
v->pv.tq0 = w;
|
||||
if (tc0_size == 4)
|
||||
v->pv.tq0 = tc0[i][3] * w;
|
||||
}
|
||||
else {
|
||||
v->v.tu0 = tc0[i][0] * u0scale * w;
|
||||
v->v.tv0 = tc0[i][1] * v0scale * w;
|
||||
}
|
||||
}
|
||||
if (IND & TDFX_TEX1_BIT) {
|
||||
GLfloat w = v->v.rhw;
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
v->pv.tu1 = tc1[i][0] * u1scale * w;
|
||||
v->pv.tv1 = tc1[i][1] * v1scale * w;
|
||||
v->pv.tq1 = w;
|
||||
if (tc1_size == 4)
|
||||
v->pv.tq1 = tc1[i][3] * w;
|
||||
}
|
||||
else {
|
||||
v->v.tu1 = tc1[i][0] * u1scale * w;
|
||||
v->v.tv1 = tc1[i][1] * v1scale * w;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#else
|
||||
#if (IND & TDFX_XYZ_BIT)
|
||||
static void TAG(emit)( GLcontext *ctx, GLuint start, GLuint end,
|
||||
void *dest, GLuint stride )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
GLubyte (*col)[4];
|
||||
GLuint col_stride;
|
||||
GLfloat (*proj)[4] = VB->NdcPtr->data;
|
||||
GLuint proj_stride = VB->NdcPtr->stride;
|
||||
GLfloat *v = (GLfloat *)dest;
|
||||
const GLubyte *mask = VB->ClipMask;
|
||||
const GLfloat *s = fxMesa->hw_viewport;
|
||||
int i;
|
||||
|
||||
/* fprintf(stderr, "%s %d..%d dest %p stride %d\n", __FUNCTION__, */
|
||||
/* start, end, dest, stride); */
|
||||
|
||||
ASSERT(fxMesa->SetupIndex == (TDFX_XYZ_BIT|TDFX_RGBA_BIT));
|
||||
ASSERT(stride == 16);
|
||||
|
||||
if (VB->ColorPtr[0]->Type != GL_UNSIGNED_BYTE)
|
||||
import_float_colors( ctx );
|
||||
|
||||
col = (GLubyte (*)[4])VB->ColorPtr[0]->Ptr;
|
||||
col_stride = VB->ColorPtr[0]->StrideB;
|
||||
ASSERT(VB->ColorPtr[0]->Type == GL_UNSIGNED_BYTE);
|
||||
|
||||
/* Pack what's left into a 4-dword vertex. Color is in a different
|
||||
* place, and there is no 'w' coordinate.
|
||||
*/
|
||||
if (VB->importable_data) {
|
||||
if (start) {
|
||||
proj = (GLfloat (*)[4])((GLubyte *)proj + start * proj_stride);
|
||||
STRIDE_4UB(col, start * col_stride);
|
||||
}
|
||||
|
||||
for (i=start; i < end; i++, v+=4) {
|
||||
if (mask[i] == 0) {
|
||||
v[0] = s[0] * proj[0][0] + s[12];
|
||||
v[1] = s[5] * proj[0][1] + s[13];
|
||||
v[2] = s[10] * proj[0][2] + s[14];
|
||||
}
|
||||
proj = (GLfloat (*)[4])((GLubyte *)proj + proj_stride);
|
||||
{
|
||||
GLubyte *b = (GLubyte *)&v[3];
|
||||
b[0] = col[0][2];
|
||||
b[1] = col[0][1];
|
||||
b[2] = col[0][0];
|
||||
b[3] = col[0][3];
|
||||
STRIDE_4UB(col, col_stride);
|
||||
}
|
||||
}
|
||||
}
|
||||
else {
|
||||
for (i=start; i < end; i++, v+=4) {
|
||||
if (mask[i] == 0) {
|
||||
v[0] = s[0] * proj[i][0] + s[12];
|
||||
v[1] = s[5] * proj[i][1] + s[13];
|
||||
v[2] = s[10] * proj[i][2] + s[14];
|
||||
}
|
||||
{
|
||||
GLubyte *b = (GLubyte *)&v[3];
|
||||
b[0] = col[i][2];
|
||||
b[1] = col[i][1];
|
||||
b[2] = col[i][0];
|
||||
b[3] = col[i][3];
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
#else
|
||||
static void TAG(emit)( GLcontext *ctx, GLuint start, GLuint end,
|
||||
void *dest, GLuint stride )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT(ctx);
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
GLubyte (*col)[4];
|
||||
GLuint col_stride;
|
||||
GLfloat *v = (GLfloat *)dest;
|
||||
int i;
|
||||
|
||||
if (VB->ColorPtr[0]->Type != GL_UNSIGNED_BYTE)
|
||||
import_float_colors( ctx );
|
||||
|
||||
col = VB->ColorPtr[0]->Ptr;
|
||||
col_stride = VB->ColorPtr[0]->StrideB;
|
||||
|
||||
if (start)
|
||||
STRIDE_4UB(col, col_stride * start);
|
||||
|
||||
/* Need to figure out where color is:
|
||||
*/
|
||||
if (fxMesa->SetupIndex & TDFX_W_BIT )
|
||||
v += 4;
|
||||
else
|
||||
v += 3;
|
||||
|
||||
for (i=start; i < end; i++, STRIDE_F(v, stride)) {
|
||||
GLubyte *b = (GLubyte *)v;
|
||||
b[0] = col[0][2];
|
||||
b[1] = col[0][1];
|
||||
b[2] = col[0][0];
|
||||
b[3] = col[0][3];
|
||||
STRIDE_4UB( col, col_stride );
|
||||
}
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
|
||||
#if (IND & TDFX_XYZ_BIT) && (IND & TDFX_RGBA_BIT)
|
||||
|
||||
static GLboolean TAG(check_tex_sizes)( GLcontext *ctx )
|
||||
{
|
||||
/* fprintf(stderr, "%s\n", __FUNCTION__); */
|
||||
|
||||
if (IND & TDFX_PTEX_BIT)
|
||||
return GL_TRUE;
|
||||
|
||||
if (IND & TDFX_TEX0_BIT) {
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
|
||||
if (IND & TDFX_TEX1_BIT) {
|
||||
if (VB->TexCoordPtr[0] == 0)
|
||||
VB->TexCoordPtr[0] = VB->TexCoordPtr[1];
|
||||
|
||||
if (VB->TexCoordPtr[1]->size == 4)
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
if (VB->TexCoordPtr[0]->size == 4)
|
||||
return GL_FALSE;
|
||||
}
|
||||
|
||||
return GL_TRUE;
|
||||
}
|
||||
|
||||
static void TAG(interp)( GLcontext *ctx,
|
||||
GLfloat t,
|
||||
GLuint edst, GLuint eout, GLuint ein,
|
||||
GLboolean force_boundary )
|
||||
{
|
||||
tdfxContextPtr fxMesa = TDFX_CONTEXT( ctx );
|
||||
struct vertex_buffer *VB = &TNL_CONTEXT(ctx)->vb;
|
||||
const GLuint shift = fxMesa->vertex_stride_shift;
|
||||
const GLfloat *dstclip = VB->ClipPtr->data[edst];
|
||||
const GLfloat oow = (dstclip[3] == 0.0F) ? 1.0F : (1.0F / dstclip[3]);
|
||||
const GLfloat *s = fxMesa->hw_viewport;
|
||||
GLubyte *tdfxverts = (GLubyte *)fxMesa->verts;
|
||||
tdfxVertex *dst = (tdfxVertex *) (tdfxverts + (edst << shift));
|
||||
const tdfxVertex *out = (const tdfxVertex *) (tdfxverts + (eout << shift));
|
||||
const tdfxVertex *in = (const tdfxVertex *) (tdfxverts + (ein << shift));
|
||||
const GLfloat wout = 1.0F / out->v.rhw;
|
||||
const GLfloat win = 1.0F / in->v.rhw;
|
||||
|
||||
dst->v.x = s[0] * dstclip[0] * oow + s[12];
|
||||
dst->v.y = s[5] * dstclip[1] * oow + s[13];
|
||||
dst->v.z = s[10] * dstclip[2] * oow + s[14];
|
||||
|
||||
if (IND & (TDFX_W_BIT|TDFX_TEX0_BIT|TDFX_TEX1_BIT)) {
|
||||
dst->v.rhw = oow;
|
||||
|
||||
INTERP_UB( t, dst->ub4[4][0], out->ub4[4][0], in->ub4[4][0] );
|
||||
INTERP_UB( t, dst->ub4[4][1], out->ub4[4][1], in->ub4[4][1] );
|
||||
INTERP_UB( t, dst->ub4[4][2], out->ub4[4][2], in->ub4[4][2] );
|
||||
INTERP_UB( t, dst->ub4[4][3], out->ub4[4][3], in->ub4[4][3] );
|
||||
|
||||
if (IND & TDFX_TEX0_BIT) {
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
INTERP_F( t, dst->pv.tu0, out->pv.tu0 * wout, in->pv.tu0 * win );
|
||||
INTERP_F( t, dst->pv.tv0, out->pv.tv0 * wout, in->pv.tv0 * win );
|
||||
INTERP_F( t, dst->pv.tq0, out->pv.tq0 * wout, in->pv.tq0 * win );
|
||||
dst->pv.tu0 *= oow;
|
||||
dst->pv.tv0 *= oow;
|
||||
dst->pv.tq0 *= oow;
|
||||
} else {
|
||||
INTERP_F( t, dst->v.tu0, out->v.tu0 * wout, in->v.tu0 * win );
|
||||
INTERP_F( t, dst->v.tv0, out->v.tv0 * wout, in->v.tv0 * win );
|
||||
dst->v.tu0 *= oow;
|
||||
dst->v.tv0 *= oow;
|
||||
}
|
||||
}
|
||||
if (IND & TDFX_TEX1_BIT) {
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
INTERP_F( t, dst->pv.tu1, out->pv.tu1 * wout, in->pv.tu1 * win );
|
||||
INTERP_F( t, dst->pv.tv1, out->pv.tv1 * wout, in->pv.tv1 * win );
|
||||
INTERP_F( t, dst->pv.tq1, out->pv.tq1 * wout, in->pv.tq1 * win );
|
||||
dst->pv.tu1 *= oow;
|
||||
dst->pv.tv1 *= oow;
|
||||
dst->pv.tq1 *= oow;
|
||||
} else {
|
||||
INTERP_F( t, dst->v.tu1, out->v.tu1 * wout, in->v.tu1 * win );
|
||||
INTERP_F( t, dst->v.tv1, out->v.tv1 * wout, in->v.tv1 * win );
|
||||
dst->v.tu1 *= oow;
|
||||
dst->v.tv1 *= oow;
|
||||
}
|
||||
}
|
||||
} else {
|
||||
/* 4-dword vertex. Color is in v[3] and there is no oow coordinate.
|
||||
*/
|
||||
INTERP_UB( t, dst->ub4[3][0], out->ub4[3][0], in->ub4[3][0] );
|
||||
INTERP_UB( t, dst->ub4[3][1], out->ub4[3][1], in->ub4[3][1] );
|
||||
INTERP_UB( t, dst->ub4[3][2], out->ub4[3][2], in->ub4[3][2] );
|
||||
INTERP_UB( t, dst->ub4[3][3], out->ub4[3][3], in->ub4[3][3] );
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
static void TAG(init)( void )
|
||||
{
|
||||
/* fprintf(stderr, "%s\n", __FUNCTION__); */
|
||||
|
||||
setup_tab[IND].emit = TAG(emit);
|
||||
|
||||
#if ((IND & TDFX_XYZ_BIT) && (IND & TDFX_RGBA_BIT))
|
||||
setup_tab[IND].check_tex_sizes = TAG(check_tex_sizes);
|
||||
setup_tab[IND].interp = TAG(interp);
|
||||
|
||||
if (IND & (TDFX_W_BIT|TDFX_TEX0_BIT|TDFX_TEX1_BIT))
|
||||
setup_tab[IND].copy_pv = copy_pv_rgba4;
|
||||
else
|
||||
setup_tab[IND].copy_pv = copy_pv_rgba3;
|
||||
|
||||
|
||||
if (IND & TDFX_TEX1_BIT) {
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
setup_tab[IND].vertex_format = TDFX_LAYOUT_PROJECT;
|
||||
setup_tab[IND].vertex_size = 12;
|
||||
setup_tab[IND].vertex_stride_shift = 6;
|
||||
}
|
||||
else {
|
||||
setup_tab[IND].vertex_format = TDFX_LAYOUT_MULTI;
|
||||
setup_tab[IND].vertex_size = 10;
|
||||
setup_tab[IND].vertex_stride_shift = 6;
|
||||
}
|
||||
}
|
||||
else if (IND & TDFX_TEX0_BIT) {
|
||||
if (IND & TDFX_PTEX_BIT) {
|
||||
setup_tab[IND].vertex_format = TDFX_LAYOUT_PROJECT;
|
||||
setup_tab[IND].vertex_size = 12;
|
||||
setup_tab[IND].vertex_stride_shift = 6;
|
||||
} else {
|
||||
setup_tab[IND].vertex_format = TDFX_LAYOUT_SINGLE;
|
||||
setup_tab[IND].vertex_size = 8;
|
||||
setup_tab[IND].vertex_stride_shift = 5;
|
||||
}
|
||||
}
|
||||
else if (IND & TDFX_W_BIT) {
|
||||
setup_tab[IND].vertex_format = TDFX_LAYOUT_NOTEX;
|
||||
setup_tab[IND].vertex_size = 6;
|
||||
setup_tab[IND].vertex_stride_shift = 5;
|
||||
} else {
|
||||
setup_tab[IND].vertex_format = TDFX_LAYOUT_TINY;
|
||||
setup_tab[IND].vertex_size = 4;
|
||||
setup_tab[IND].vertex_stride_shift = 4;
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
#undef IND
|
||||
#undef TAG
|
||||
Reference in New Issue
Block a user