1 /**************************************************************************
3 Copyright 2000 Silicon Integrated Systems Corp, Inc., HsinChu, Taiwan.
4 Copyright 2003 Eric Anholt
7 Permission is hereby granted, free of charge, to any person obtaining a
8 copy of this software and associated documentation files (the "Software"),
9 to deal in the Software without restriction, including without limitation
10 on the rights to use, copy, modify, merge, publish, distribute, sub
11 license, and/or sell copies of the Software, and to permit persons to whom
12 the Software is furnished to do so, subject to the following conditions:
14 The above copyright notice and this permission notice (including the next
15 paragraph) shall be included in all copies or substantial portions of the
18 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
19 IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
20 FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT. IN NO EVENT SHALL
21 ERIC ANHOLT OR SILICON INTEGRATED SYSTEMS CORP BE LIABLE FOR ANY CLAIM,
22 DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR
23 OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE
24 USE OR OTHER DEALINGS IN THE SOFTWARE.
26 **************************************************************************/
30 * Sung-Ching Lin <sclin@sis.com.tw>
31 * Eric Anholt <anholt@FreeBSD.org>
37 #include "main/context.h"
40 #include "drm_sarea.h"
41 #include "xmlconfig.h"
42 #include "tnl/t_vertex.h"
44 #include "sis_screen.h"
46 #include "sis6326_reg.h"
52 #define PCI_CHIP_SIS300 0x0300
53 #define PCI_CHIP_SIS630 0x6300
54 #define PCI_CHIP_SIS540 0x5300
56 #define NEW_TEXTURING 0x1
57 #define NEW_TEXTURE_ENV 0x2
59 /* Flags for software fallback cases:
61 #define SIS_FALLBACK_TEXTURE 0x0001
62 #define SIS_FALLBACK_TEXTURE0 0x0002
63 #define SIS_FALLBACK_TEXTURE1 0x0004
64 #define SIS_FALLBACK_TEXENV0 0x0008
65 #define SIS_FALLBACK_TEXENV1 0x0010
66 #define SIS_FALLBACK_DRAW_BUFFER 0x0020
67 #define SIS_FALLBACK_STENCIL 0x0040
68 #define SIS_FALLBACK_WRITEMASK 0x0080
69 #define SIS_FALLBACK_DISABLE 0x0100
71 /* Flags for hardware state that needs to be updated */
72 #define GFLAG_ENABLESETTING 0x00000001
73 #define GFLAG_ENABLESETTING2 0x00000002
74 #define GFLAG_ZSETTING 0x00000004
75 #define GFLAG_ALPHASETTING 0x00000008
76 #define GFLAG_DESTSETTING 0x00000010
77 #define GFLAG_LINESETTING 0x00000020
78 #define GFLAG_STENCILSETTING 0x00000040
79 #define GFLAG_FOGSETTING 0x00000080
80 #define GFLAG_DSTBLEND 0x00000100
81 #define GFLAG_CLIPPING 0x00000200
82 #define CFLAG_TEXTURERESET 0x00000400
83 #define GFLAG_TEXTUREMIPMAP 0x00000800
84 #define GFLAG_TEXBORDERCOLOR 0x00001000
85 #define GFLAG_TEXTUREADDRESS 0x00002000
86 #define GFLAG_TEXTUREENV 0x00004000
87 #define CFLAG_TEXTURERESET_1 0x00008000
88 #define GFLAG_TEXTUREMIPMAP_1 0x00010000
89 #define GFLAG_TEXBORDERCOLOR_1 0x00020000
90 #define GFLAG_TEXTUREADDRESS_1 0x00040000
91 #define GFLAG_TEXTUREENV_1 0x00080000
92 #define GFLAG_ALL 0x000fffff
94 #define GFLAG_TEXTURE_STATES (CFLAG_TEXTURERESET | GFLAG_TEXTUREMIPMAP | \
95 GFLAG_TEXBORDERCOLOR | GFLAG_TEXTUREADDRESS | \
96 CFLAG_TEXTURERESET_1 | GFLAG_TEXTUREMIPMAP_1 | \
97 GFLAG_TEXBORDERCOLOR_1 | \
98 GFLAG_TEXTUREADDRESS_1 | \
99 GFLAG_TEXTUREENV | GFLAG_TEXTUREENV_1)
102 #define GFLAG_RENDER_STATES (GFLAG_ENABLESETTING | GFLAG_ENABLESETTING2 | \
103 GFLAG_ZSETTING | GFLAG_ALPHASETTING | \
104 GFLAG_DESTSETTING | GFLAG_FOGSETTING | \
105 GFLAG_STENCILSETTING | GFLAG_DSTBLEND | \
108 /* Use the templated vertex format:
110 #define TAG(x) sis##x
111 #include "tnl_dd/t_dd_vertex.h"
114 /* Subpixel offsets for window coordinates (triangles):
116 #define SUBPIXEL_X (-0.5F)
117 #define SUBPIXEL_Y (-0.5F)
119 #define SIS_MAX_TEXTURE_SIZE 2048
120 #define SIS_MAX_TEXTURES 2
121 #define SIS_MAX_TEXTURE_LEVELS 11
122 #define SIS_MAX_FRAME_LENGTH 3
125 GLubyte
*Data
; /* Pointer to texture in offscreen */
126 GLuint memType
; /* VIDEO_TYPE or AGP_TYPE */
127 void *handle
; /* Handle for sisFree*() */
132 typedef struct sis_tex_obj
{
133 sisTexImage image
[SIS_MAX_TEXTURE_LEVELS
]; /* Image data for each mipmap
135 GLenum format
; /* One of GL_ALPHA, GL_INTENSITY, GL_LUMINANCE,
136 * GL_LUMINANCE_ALPHA, GL_RGB, GL_RGBA
138 GLint hwformat
; /* One of the TEXEL_ defines */
139 GLint numImages
; /* Number of images loaded into .image */
140 } sisTexObj
, *sisTexObjPtr
;
143 ** Device dependent context state
145 typedef struct __GLSiSTextureRec
149 GLint hwTextureClrHigh
;
150 GLint hwTextureClrLow
;
151 GLint hwTexWidthHeight
; /* 6326: Texture Blending Setting */
152 GLint hwTextureBorderColor
;
175 typedef struct __GLSiSHardwareRec
177 GLint hwCapEnable
, hwCapEnable2
; /* Enable Setting */
179 GLint hwOffsetZ
, hwZ
; /* Z Setting */
181 GLint hwZBias
, hwZMask
; /* Z Setting */
183 GLint hwAlpha
; /* Alpha Setting */
185 GLint hwDstSet
, hwDstMask
; /* Destination Setting */
187 GLint hwOffsetDest
; /* Destination Setting */
189 GLint hwLinePattern
; /* Line Setting */
191 GLint hwFog
; /* Fog Setting */
193 GLint hwFogFar
, hwFogInverse
; /* Fog Distance setting */
195 GLint hwFogDensity
; /* Fog factor & density */
197 GLint hwStSetting
, hwStSetting2
; /* Stencil Setting */
199 GLint hwStOffset
; /* Stencil Setting */
201 GLint hwDstSrcBlend
; /* Blending mode Setting */
203 GLint clipTopBottom
; /* Clip for Top & Bottom */
205 GLint clipLeftRight
; /* Clip for Left & Right */
207 struct __GLSiSTextureRec texture
[2];
209 GLint hwTexEnvColor
; /* Texture Blending Setting */
211 GLint hwTexBlendSet
; /* 6326 */
212 GLint hwTexBlendColor0
;
213 GLint hwTexBlendColor1
;
214 GLint hwTexBlendAlpha0
;
215 GLint hwTexBlendAlpha1
;
220 typedef struct sis_context sisContextRec
;
221 typedef struct sis_context
*sisContextPtr
;
223 typedef void (*sis_quad_func
)( sisContextPtr
,
229 typedef void (*sis_tri_func
)( sisContextPtr
,
234 typedef void (*sis_line_func
)( sisContextPtr
,
238 typedef void (*sis_point_func
)( sisContextPtr
,
242 * Derived from gl_renderbuffer.
244 struct sis_renderbuffer
{
245 struct gl_renderbuffer Base
; /* must be first! */
254 /* Device dependent context state */
258 /* This must be first in this structure */
263 struct tnl_attr_map vertex_attrs
[VERT_ATTRIB_MAX
];
264 GLuint vertex_attr_count
;
265 char *verts
; /* points to tnl->clipspace.vertex_buf */
267 /* Vertex buffer (in system memory or AGP) state. */
268 unsigned char *vb
; /* Beginning of vertex buffer */
269 unsigned char *vb_cur
; /* Current write location in vertex buffer */
270 unsigned char *vb_last
; /* Last written location in vertex buffer */
271 unsigned char *vb_end
; /* End of vertex buffer */
273 GLuint vb_agp_offset
;
275 GLint coloroffset
; /* Offset in vertex format of current color */
276 GLint specoffset
; /* Offset in vertex format of specular color */
281 GLfloat hw_viewport
[16];
284 unsigned int virtualX
, virtualY
;
285 unsigned int bytesPerPixel
;
286 unsigned char *IOBase
;
287 unsigned char *FbBase
;
288 unsigned int displayWidth
;
291 unsigned int redMask
, greenMask
, blueMask
, alphaMask
;
292 unsigned int colorFormat
;
295 unsigned int zFormat
;
297 /* Clear patterns, 4 bytes */
298 unsigned int clearColorPattern
;
299 unsigned int clearZStencilPattern
;
301 /* Fallback rasterization functions
303 sis_point_func draw_point
;
304 sis_line_func draw_line
;
305 sis_tri_func draw_tri
;
306 sis_quad_func draw_quad
;
309 GLenum raster_primitive
;
310 GLenum render_primitive
;
316 unsigned int AGPSize
;
317 unsigned char *AGPBase
;
318 unsigned int AGPAddr
;
320 /* register 0x89F4 */
323 /* register 0x89F8 */
324 GLint dwPrimitiveSet
;
326 __GLSiSHardware prev
, current
;
334 DECLARE_RENDERINPUTS(last_tcl_state_bitset
);
338 GLboolean stereoEnabled
;
339 int stereo_drawIndex
;
341 GLboolean irqEnabled
;
343 GLboolean clearTexCache
;
345 GLuint TexStates
[SIS_MAX_TEXTURES
];
346 GLuint PrevTexFormat
[SIS_MAX_TEXTURES
];
348 int *CurrentQueueLenPtr
;
349 unsigned int *FrameCountPtr
;
351 /* Front/back/depth buffer info */
352 GLuint width
, height
; /* size of buffers */
353 GLint bottom
; /* used for FLIP macro */
354 /* XXX These don't belong here. They should be per-drawable state. */
355 struct sis_renderbuffer front
;
356 struct sis_renderbuffer back
;
357 struct sis_renderbuffer depth
;
358 struct sis_renderbuffer stencil
; /* mirrors depth */
360 /* Mirrors of some DRI state
362 __DRIcontextPrivate
*driContext
; /* DRI context */
363 __DRIscreenPrivate
*driScreen
; /* DRI screen */
364 __DRIdrawablePrivate
*driDrawable
; /* DRI drawable bound to this ctx */
366 unsigned int lastStamp
; /* mirror driDrawable->lastStamp */
368 drm_context_t hHWContext
;
369 drm_hw_lock_t
*driHwLock
;
371 sisScreenPtr sisScreen
; /* Screen private DRI data */
372 SISSAREAPrivPtr sarea
; /* Private SAREA data */
374 /* Configuration cache */
375 driOptionCache optionCache
;
379 #define SIS_CONTEXT(ctx) ((sisContextPtr)(ctx->DriverCtx))
382 #define GET_IOBase(x) ((x)->IOBase)
384 #define Y_FLIP(Y) (smesa->bottom - (Y))
386 #define SISPACKCOLOR565( r, g, b ) \
387 ((((r) & 0xf8) << 8) | (((g) & 0xfc) << 3) | (((b) & 0xf8) >> 3))
389 #define SISPACKCOLOR8888( r, g, b, a ) \
390 (((a) << 24) | ((r) << 16) | ((g) << 8) | (b))
392 #define SIS_VERBOSE 0
395 #define MMIO(reg, value) \
397 *(volatile GLint *)(smesa->IOBase + (reg)) = value; \
400 #define MMIO_READ(reg) *(volatile GLint *)(smesa->IOBase + (reg))
401 #define MMIO_READf(reg) *(volatile GLfloat *)(smesa->IOBase + (reg))
403 #if defined(__i386__) || defined(__x86_64__)
404 #define MMIO_WMB() __asm __volatile("" : : : "memory")
405 #elif defined(__ia64__)
406 #define MMIO_WMB() __asm __volatile("mf" : : : "memory")
408 #error platform needs WMB
411 #define mEndPrimitive() \
413 *(volatile GLubyte *)(smesa->IOBase + REG_3D_EndPrimitiveList) = 0xff; \
414 *(volatile GLuint *)(smesa->IOBase + 0x8b60) = 0xffffffff; \
417 #define sis_fatal_error(...) \
419 fprintf(stderr, "[%s:%d]:", __FILE__, __LINE__); \
420 fprintf(stderr, __VA_ARGS__); \
425 #define mWait3DCmdQueue(wLen) \
426 /* Update the mirrored queue pointer if it doesn't indicate enough space */ \
427 if (*(smesa->CurrentQueueLenPtr) < (wLen)) { \
428 *(smesa->CurrentQueueLenPtr) = \
429 (*(GLint *)(GET_IOBase(smesa) + REG_CommandQueue) & MASK_QueueLen) - 20; \
430 /* Spin and wait if the queue is actually too full */ \
431 if (*(smesa->CurrentQueueLenPtr) < (wLen)) \
432 WaitingFor3dIdle(smesa, wLen); \
433 *(smesa->CurrentQueueLenPtr) -= wLen; \
437 VERBOSE_SIS_BUFFER
= 0x1,
438 VERBOSE_SIS_MEMORY
= 0x2
441 extern GLboolean
sisCreateContext( const __GLcontextModes
*glVisual
,
442 __DRIcontextPrivate
*driContextPriv
,
443 void *sharedContextPrivate
);
444 extern void sisDestroyContext( __DRIcontextPrivate
* );
446 void sisReAllocateBuffers(GLcontext
*ctx
, GLframebuffer
*drawbuffer
,
447 GLuint width
, GLuint height
);
449 extern GLboolean
sisMakeCurrent( __DRIcontextPrivate
*driContextPriv
,
450 __DRIdrawablePrivate
*driDrawPriv
,
451 __DRIdrawablePrivate
*driReadPriv
);
453 extern GLboolean
sisUnbindContext( __DRIcontextPrivate
*driContextPriv
);
455 void WaitEngIdle (sisContextPtr smesa
);
456 void Wait2DEngIdle (sisContextPtr smesa
);
457 void WaitingFor3dIdle(sisContextPtr smesa
, int wLen
);
460 extern void sis_update_texture_state( sisContextPtr smesa
);
461 extern void sis_update_render_state( sisContextPtr smesa
);
462 extern void sis6326_update_texture_state( sisContextPtr smesa
);
463 extern void sis6326_update_render_state( sisContextPtr smesa
);
465 /* ================================================================
471 extern int SIS_DEBUG
;
476 #define DEBUG_FALLBACKS 0x01
478 #endif /* _sis_ctx_h_ */