2 Copyright (C) The Weather Channel, Inc. 2002.
3 Copyright (C) 2004 Nicolai Haehnle.
6 The Weather Channel (TM) funded Tungsten Graphics to develop the
7 initial release of the Radeon 8500 driver under the XFree86 license.
8 This notice must be preserved.
10 Permission is hereby granted, free of charge, to any person obtaining
11 a copy of this software and associated documentation files (the
12 "Software"), to deal in the Software without restriction, including
13 without limitation the rights to use, copy, modify, merge, publish,
14 distribute, sublicense, and/or sell copies of the Software, and to
15 permit persons to whom the Software is furnished to do so, subject to
16 the following conditions:
18 The above copyright notice and this permission notice (including the
19 next paragraph) shall be included in all copies or substantial
20 portions of the Software.
22 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
23 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
24 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
25 IN NO EVENT SHALL THE COPYRIGHT OWNER(S) AND/OR ITS SUPPLIERS BE
26 LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
27 OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
28 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
30 **************************************************************************/
35 * \author Nicolai Haehnle <prefect_@gmx.net>
38 #include "main/glheader.h"
39 #include "main/state.h"
40 #include "main/imports.h"
41 #include "main/enums.h"
42 #include "main/macros.h"
43 #include "main/context.h"
45 #include "main/framebuffer.h"
46 #include "main/simple_list.h"
47 #include "main/api_arrayelt.h"
49 #include "drivers/common/meta.h"
50 #include "swrast/swrast.h"
51 #include "swrast_setup/swrast_setup.h"
52 #include "program/prog_parameter.h"
53 #include "program/prog_statevars.h"
57 #include "r300_context.h"
58 #include "r300_state.h"
60 #include "r300_emit.h"
61 #include "r300_fragprog_common.h"
62 #include "r300_render.h"
63 #include "r300_vertprog.h"
65 static void r300BlendColor(struct gl_context
* ctx
, const GLfloat cf
[4])
67 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
69 R300_STATECHANGE(rmesa
, blend_color
);
71 if (rmesa
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
) {
72 GLuint r
= IROUND(cf
[0]*1023.0f
);
73 GLuint g
= IROUND(cf
[1]*1023.0f
);
74 GLuint b
= IROUND(cf
[2]*1023.0f
);
75 GLuint a
= IROUND(cf
[3]*1023.0f
);
77 rmesa
->hw
.blend_color
.cmd
[1] = r
| (a
<< 16);
78 rmesa
->hw
.blend_color
.cmd
[2] = b
| (g
<< 16);
81 CLAMPED_FLOAT_TO_UBYTE(color
[0], cf
[0]);
82 CLAMPED_FLOAT_TO_UBYTE(color
[1], cf
[1]);
83 CLAMPED_FLOAT_TO_UBYTE(color
[2], cf
[2]);
84 CLAMPED_FLOAT_TO_UBYTE(color
[3], cf
[3]);
86 rmesa
->hw
.blend_color
.cmd
[1] = PACK_COLOR_8888(color
[3], color
[0],
92 * Calculate the hardware blend factor setting. This same function is used
93 * for source and destination of both alpha and RGB.
96 * The hardware register value for the specified blend factor. This value
97 * will need to be shifted into the correct position for either source or
101 * Since the two cases where source and destination are handled differently
102 * are essentially error cases, they should never happen. Determine if these
103 * cases can be removed.
105 static int blend_factor(GLenum factor
, GLboolean is_src
)
109 return R300_BLEND_GL_ZERO
;
112 return R300_BLEND_GL_ONE
;
115 return R300_BLEND_GL_DST_COLOR
;
117 case GL_ONE_MINUS_DST_COLOR
:
118 return R300_BLEND_GL_ONE_MINUS_DST_COLOR
;
121 return R300_BLEND_GL_SRC_COLOR
;
123 case GL_ONE_MINUS_SRC_COLOR
:
124 return R300_BLEND_GL_ONE_MINUS_SRC_COLOR
;
127 return R300_BLEND_GL_SRC_ALPHA
;
129 case GL_ONE_MINUS_SRC_ALPHA
:
130 return R300_BLEND_GL_ONE_MINUS_SRC_ALPHA
;
133 return R300_BLEND_GL_DST_ALPHA
;
135 case GL_ONE_MINUS_DST_ALPHA
:
136 return R300_BLEND_GL_ONE_MINUS_DST_ALPHA
;
138 case GL_SRC_ALPHA_SATURATE
:
139 return (is_src
) ? R300_BLEND_GL_SRC_ALPHA_SATURATE
:
142 case GL_CONSTANT_COLOR
:
143 return R300_BLEND_GL_CONST_COLOR
;
145 case GL_ONE_MINUS_CONSTANT_COLOR
:
146 return R300_BLEND_GL_ONE_MINUS_CONST_COLOR
;
148 case GL_CONSTANT_ALPHA
:
149 return R300_BLEND_GL_CONST_ALPHA
;
151 case GL_ONE_MINUS_CONSTANT_ALPHA
:
152 return R300_BLEND_GL_ONE_MINUS_CONST_ALPHA
;
155 fprintf(stderr
, "unknown blend factor %x\n", factor
);
156 return (is_src
) ? R300_BLEND_GL_ONE
: R300_BLEND_GL_ZERO
;
162 * Sets both the blend equation and the blend function.
163 * This is done in a single
164 * function because some blend equations (i.e., \c GL_MIN and \c GL_MAX)
165 * change the interpretation of the blend function.
166 * Also, make sure that blend function and blend equation are set to their
167 * default value if color blending is not enabled, since at least blend
168 * equations GL_MIN and GL_FUNC_REVERSE_SUBTRACT will cause wrong results
169 * otherwise for unknown reasons.
172 /* helper function */
173 static void r300SetBlendCntl(r300ContextPtr r300
, int func
, int eqn
,
174 int cbits
, int funcA
, int eqnA
)
176 GLuint new_ablend
, new_cblend
;
180 "eqnA=%08x funcA=%08x eqn=%08x func=%08x cbits=%08x\n",
181 eqnA
, funcA
, eqn
, func
, cbits
);
183 new_ablend
= eqnA
| funcA
;
184 new_cblend
= eqn
| func
;
186 /* Some blend factor combinations don't seem to work when the
187 * BLEND_NO_SEPARATE bit is set.
189 * Especially problematic candidates are the ONE_MINUS_* flags,
190 * but I can't see a real pattern.
193 if (new_ablend
== new_cblend
) {
194 new_cblend
|= R300_DISCARD_SRC_PIXELS_SRC_ALPHA_0
;
199 if ((new_ablend
!= r300
->hw
.bld
.cmd
[R300_BLD_ABLEND
]) ||
200 (new_cblend
!= r300
->hw
.bld
.cmd
[R300_BLD_CBLEND
])) {
201 R300_STATECHANGE(r300
, bld
);
202 r300
->hw
.bld
.cmd
[R300_BLD_ABLEND
] = new_ablend
;
203 r300
->hw
.bld
.cmd
[R300_BLD_CBLEND
] = new_cblend
;
207 static void r300SetBlendState(struct gl_context
* ctx
)
209 r300ContextPtr r300
= R300_CONTEXT(ctx
);
210 int func
= (R300_BLEND_GL_ONE
<< R300_SRC_BLEND_SHIFT
) |
211 (R300_BLEND_GL_ZERO
<< R300_DST_BLEND_SHIFT
);
212 int eqn
= R300_COMB_FCN_ADD_CLAMP
;
213 int funcA
= (R300_BLEND_GL_ONE
<< R300_SRC_BLEND_SHIFT
) |
214 (R300_BLEND_GL_ZERO
<< R300_DST_BLEND_SHIFT
);
215 int eqnA
= R300_COMB_FCN_ADD_CLAMP
;
217 if (ctx
->Color
.ColorLogicOpEnabled
|| !ctx
->Color
.BlendEnabled
) {
218 r300SetBlendCntl(r300
, func
, eqn
, 0, func
, eqn
);
223 (blend_factor(ctx
->Color
.Blend
[0].SrcRGB
, GL_TRUE
) <<
224 R300_SRC_BLEND_SHIFT
) | (blend_factor(ctx
->Color
.Blend
[0].DstRGB
,
226 R300_DST_BLEND_SHIFT
);
228 switch (ctx
->Color
.Blend
[0].EquationRGB
) {
230 eqn
= R300_COMB_FCN_ADD_CLAMP
;
233 case GL_FUNC_SUBTRACT
:
234 eqn
= R300_COMB_FCN_SUB_CLAMP
;
237 case GL_FUNC_REVERSE_SUBTRACT
:
238 eqn
= R300_COMB_FCN_RSUB_CLAMP
;
242 eqn
= R300_COMB_FCN_MIN
;
243 func
= (R300_BLEND_GL_ONE
<< R300_SRC_BLEND_SHIFT
) |
244 (R300_BLEND_GL_ONE
<< R300_DST_BLEND_SHIFT
);
248 eqn
= R300_COMB_FCN_MAX
;
249 func
= (R300_BLEND_GL_ONE
<< R300_SRC_BLEND_SHIFT
) |
250 (R300_BLEND_GL_ONE
<< R300_DST_BLEND_SHIFT
);
255 "[%s:%u] Invalid RGB blend equation (0x%04x).\n",
256 __FUNCTION__
, __LINE__
, ctx
->Color
.Blend
[0].EquationRGB
);
261 (blend_factor(ctx
->Color
.Blend
[0].SrcA
, GL_TRUE
) <<
262 R300_SRC_BLEND_SHIFT
) | (blend_factor(ctx
->Color
.Blend
[0].DstA
,
264 R300_DST_BLEND_SHIFT
);
266 switch (ctx
->Color
.Blend
[0].EquationA
) {
268 eqnA
= R300_COMB_FCN_ADD_CLAMP
;
271 case GL_FUNC_SUBTRACT
:
272 eqnA
= R300_COMB_FCN_SUB_CLAMP
;
275 case GL_FUNC_REVERSE_SUBTRACT
:
276 eqnA
= R300_COMB_FCN_RSUB_CLAMP
;
280 eqnA
= R300_COMB_FCN_MIN
;
281 funcA
= (R300_BLEND_GL_ONE
<< R300_SRC_BLEND_SHIFT
) |
282 (R300_BLEND_GL_ONE
<< R300_DST_BLEND_SHIFT
);
286 eqnA
= R300_COMB_FCN_MAX
;
287 funcA
= (R300_BLEND_GL_ONE
<< R300_SRC_BLEND_SHIFT
) |
288 (R300_BLEND_GL_ONE
<< R300_DST_BLEND_SHIFT
);
293 "[%s:%u] Invalid A blend equation (0x%04x).\n",
294 __FUNCTION__
, __LINE__
, ctx
->Color
.Blend
[0].EquationA
);
298 r300SetBlendCntl(r300
,
300 (R300_SEPARATE_ALPHA_ENABLE
|
302 R300_ALPHA_BLEND_ENABLE
), funcA
, eqnA
);
305 static void r300BlendEquationSeparate(struct gl_context
* ctx
,
306 GLenum modeRGB
, GLenum modeA
)
308 r300SetBlendState(ctx
);
311 static void r300BlendFuncSeparate(struct gl_context
* ctx
,
312 GLenum sfactorRGB
, GLenum dfactorRGB
,
313 GLenum sfactorA
, GLenum dfactorA
)
315 r300SetBlendState(ctx
);
319 * Translate LogicOp enums into hardware representation.
320 * Both use a very logical bit-wise layout, but unfortunately the order
321 * of bits is reversed.
323 static GLuint
translate_logicop(GLenum logicop
)
325 GLuint bits
= logicop
- GL_CLEAR
;
326 bits
= ((bits
& 1) << 3) | ((bits
& 2) << 1) | ((bits
& 4) >> 1) | ((bits
& 8) >> 3);
327 return bits
<< R300_RB3D_ROPCNTL_ROP_SHIFT
;
331 * Used internally to update the r300->hw hardware state to match the
332 * current OpenGL state.
334 static void r300SetLogicOpState(struct gl_context
*ctx
)
336 r300ContextPtr r300
= R300_CONTEXT(ctx
);
337 R300_STATECHANGE(r300
, rop
);
338 if (ctx
->Color
.ColorLogicOpEnabled
) {
339 r300
->hw
.rop
.cmd
[1] = R300_RB3D_ROPCNTL_ROP_ENABLE
|
340 translate_logicop(ctx
->Color
.LogicOp
);
342 r300
->hw
.rop
.cmd
[1] = 0;
347 * Called by Mesa when an application program changes the LogicOp state
350 static void r300LogicOpcode(struct gl_context
*ctx
, GLenum logicop
)
352 if (ctx
->Color
.ColorLogicOpEnabled
)
353 r300SetLogicOpState(ctx
);
356 static void r300ClipPlane( struct gl_context
*ctx
, GLenum plane
, const GLfloat
*eq
)
358 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
362 /* no VAP UCP on non-TCL chipsets */
363 if (!rmesa
->options
.hw_tcl_enabled
)
366 p
= (GLint
) plane
- (GLint
) GL_CLIP_PLANE0
;
367 ip
= (GLint
*)ctx
->Transform
._ClipUserPlane
[p
];
369 R300_STATECHANGE( rmesa
, vpucp
[p
] );
370 rmesa
->hw
.vpucp
[p
].cmd
[R300_VPUCP_X
] = ip
[0];
371 rmesa
->hw
.vpucp
[p
].cmd
[R300_VPUCP_Y
] = ip
[1];
372 rmesa
->hw
.vpucp
[p
].cmd
[R300_VPUCP_Z
] = ip
[2];
373 rmesa
->hw
.vpucp
[p
].cmd
[R300_VPUCP_W
] = ip
[3];
376 static void r300SetClipPlaneState(struct gl_context
* ctx
, GLenum cap
, GLboolean state
)
378 r300ContextPtr r300
= R300_CONTEXT(ctx
);
381 /* no VAP UCP on non-TCL chipsets */
382 if (!r300
->options
.hw_tcl_enabled
)
385 p
= cap
- GL_CLIP_PLANE0
;
386 R300_STATECHANGE(r300
, vap_clip_cntl
);
388 r300
->hw
.vap_clip_cntl
.cmd
[1] |= (R300_VAP_UCP_ENABLE_0
<< p
);
389 r300ClipPlane(ctx
, cap
, NULL
);
391 r300
->hw
.vap_clip_cntl
.cmd
[1] &= ~(R300_VAP_UCP_ENABLE_0
<< p
);
396 * Update our tracked culling state based on Mesa's state.
398 static void r300UpdateCulling(struct gl_context
* ctx
)
400 r300ContextPtr r300
= R300_CONTEXT(ctx
);
403 if (ctx
->Polygon
.CullFlag
) {
404 switch (ctx
->Polygon
.CullFaceMode
) {
406 val
= R300_CULL_FRONT
;
409 val
= R300_CULL_BACK
;
411 case GL_FRONT_AND_BACK
:
412 val
= R300_CULL_FRONT
| R300_CULL_BACK
;
419 switch (ctx
->Polygon
.FrontFace
) {
421 val
|= R300_FRONT_FACE_CW
;
424 val
|= R300_FRONT_FACE_CCW
;
430 /* Winding is inverted when rendering to FBO */
431 if (ctx
->DrawBuffer
&& ctx
->DrawBuffer
->Name
)
432 val
^= R300_FRONT_FACE_CW
;
434 R300_STATECHANGE(r300
, cul
);
435 r300
->hw
.cul
.cmd
[R300_CUL_CULL
] = val
;
438 static void r300SetPolygonOffsetState(struct gl_context
* ctx
, GLboolean state
)
440 r300ContextPtr r300
= R300_CONTEXT(ctx
);
442 R300_STATECHANGE(r300
, occlusion_cntl
);
444 r300
->hw
.occlusion_cntl
.cmd
[1] |= (3 << 0);
446 r300
->hw
.occlusion_cntl
.cmd
[1] &= ~(3 << 0);
450 static GLboolean
current_fragment_program_writes_depth(struct gl_context
* ctx
)
452 r300ContextPtr r300
= R300_CONTEXT(ctx
);
454 return ctx
->FragmentProgram
._Current
&& r300
->selected_fp
->code
.writes_depth
;
457 static void r300SetEarlyZState(struct gl_context
* ctx
)
459 r300ContextPtr r300
= R300_CONTEXT(ctx
);
460 GLuint topZ
= R300_ZTOP_ENABLE
;
461 GLuint w_fmt
, fgdepthsrc
;
463 if (ctx
->Color
.AlphaEnabled
&& ctx
->Color
.AlphaFunc
!= GL_ALWAYS
)
464 topZ
= R300_ZTOP_DISABLE
;
465 else if (current_fragment_program_writes_depth(ctx
))
466 topZ
= R300_ZTOP_DISABLE
;
467 else if (ctx
->FragmentProgram
._Current
&& ctx
->FragmentProgram
._Current
->UsesKill
)
468 topZ
= R300_ZTOP_DISABLE
;
469 else if (r300
->radeon
.query
.current
)
470 topZ
= R300_ZTOP_DISABLE
;
472 if (topZ
!= r300
->hw
.zstencil_format
.cmd
[2]) {
473 /* Note: This completely reemits the stencil format.
474 * I have not tested whether this is strictly necessary,
475 * or if emitting a write to ZB_ZTOP is enough.
477 R300_STATECHANGE(r300
, zstencil_format
);
478 r300
->hw
.zstencil_format
.cmd
[2] = topZ
;
481 /* w_fmt value is set to get best performance
482 * see p.130 R5xx 3D acceleration guide v1.3 */
483 if (current_fragment_program_writes_depth(ctx
)) {
484 fgdepthsrc
= R300_FG_DEPTH_SRC_SHADER
;
485 w_fmt
= R300_W_FMT_W24
| R300_W_SRC_US
;
487 fgdepthsrc
= R300_FG_DEPTH_SRC_SCAN
;
488 w_fmt
= R300_W_FMT_W0
| R300_W_SRC_US
;
491 if (w_fmt
!= r300
->hw
.us_out_fmt
.cmd
[5]) {
492 R300_STATECHANGE(r300
, us_out_fmt
);
493 r300
->hw
.us_out_fmt
.cmd
[5] = w_fmt
;
496 if (fgdepthsrc
!= r300
->hw
.fg_depth_src
.cmd
[1]) {
497 R300_STATECHANGE(r300
, fg_depth_src
);
498 r300
->hw
.fg_depth_src
.cmd
[1] = fgdepthsrc
;
502 static void r300SetAlphaState(struct gl_context
* ctx
)
504 r300ContextPtr r300
= R300_CONTEXT(ctx
);
506 uint32_t pp_misc
= 0x0;
507 GLboolean really_enabled
= ctx
->Color
.AlphaEnabled
;
509 CLAMPED_FLOAT_TO_UBYTE(refByte
, ctx
->Color
.AlphaRef
);
511 switch (ctx
->Color
.AlphaFunc
) {
513 pp_misc
|= R300_FG_ALPHA_FUNC_NEVER
;
516 pp_misc
|= R300_FG_ALPHA_FUNC_LESS
;
519 pp_misc
|= R300_FG_ALPHA_FUNC_EQUAL
;
522 pp_misc
|= R300_FG_ALPHA_FUNC_LE
;
525 pp_misc
|= R300_FG_ALPHA_FUNC_GREATER
;
528 pp_misc
|= R300_FG_ALPHA_FUNC_NOTEQUAL
;
531 pp_misc
|= R300_FG_ALPHA_FUNC_GE
;
534 /*pp_misc |= FG_ALPHA_FUNC_ALWAYS; */
535 really_enabled
= GL_FALSE
;
539 if (really_enabled
) {
540 pp_misc
|= R300_FG_ALPHA_FUNC_ENABLE
;
541 pp_misc
|= R500_FG_ALPHA_FUNC_8BIT
;
542 pp_misc
|= (refByte
& R300_FG_ALPHA_FUNC_VAL_MASK
);
547 R300_STATECHANGE(r300
, at
);
548 r300
->hw
.at
.cmd
[R300_AT_ALPHA_TEST
] = pp_misc
;
549 r300
->hw
.at
.cmd
[R300_AT_UNKNOWN
] = 0;
552 static void r300AlphaFunc(struct gl_context
* ctx
, GLenum func
, GLfloat ref
)
556 r300SetAlphaState(ctx
);
559 static int translate_func(int func
)
563 return R300_ZS_NEVER
;
567 return R300_ZS_EQUAL
;
569 return R300_ZS_LEQUAL
;
571 return R300_ZS_GREATER
;
573 return R300_ZS_NOTEQUAL
;
575 return R300_ZS_GEQUAL
;
577 return R300_ZS_ALWAYS
;
582 static void r300SetDepthState(struct gl_context
* ctx
)
584 r300ContextPtr r300
= R300_CONTEXT(ctx
);
586 R300_STATECHANGE(r300
, zs
);
587 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] &= (R300_STENCIL_ENABLE
|
588 R300_STENCIL_FRONT_BACK
|
589 R500_STENCIL_REFMASK_FRONT_BACK
);
590 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] &= ~(R300_ZS_MASK
<< R300_Z_FUNC_SHIFT
);
592 if (ctx
->Depth
.Test
&& ctx
->DrawBuffer
->_DepthBuffer
) {
593 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] |= R300_Z_ENABLE
;
595 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] |= R300_Z_WRITE_ENABLE
;
596 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] |=
597 translate_func(ctx
->Depth
.Func
) << R300_Z_FUNC_SHIFT
;
601 static void r300CatchStencilFallback(struct gl_context
*ctx
)
603 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
604 const unsigned back
= ctx
->Stencil
._BackFace
;
606 if (rmesa
->radeon
.radeonScreen
->kernel_mm
&&
607 (rmesa
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
)) {
608 r300SwitchFallback(ctx
, R300_FALLBACK_STENCIL_TWOSIDE
, GL_FALSE
);
609 } else if (ctx
->Stencil
._Enabled
&&
610 (ctx
->Stencil
.Ref
[0] != ctx
->Stencil
.Ref
[back
]
611 || ctx
->Stencil
.ValueMask
[0] != ctx
->Stencil
.ValueMask
[back
]
612 || ctx
->Stencil
.WriteMask
[0] != ctx
->Stencil
.WriteMask
[back
])) {
613 r300SwitchFallback(ctx
, R300_FALLBACK_STENCIL_TWOSIDE
, GL_TRUE
);
615 r300SwitchFallback(ctx
, R300_FALLBACK_STENCIL_TWOSIDE
, GL_FALSE
);
619 static void r300SetStencilState(struct gl_context
* ctx
, GLboolean state
)
621 r300ContextPtr r300
= R300_CONTEXT(ctx
);
622 GLboolean hw_stencil
= GL_FALSE
;
624 r300CatchStencilFallback(ctx
);
626 if (ctx
->DrawBuffer
) {
627 struct radeon_renderbuffer
*rrbStencil
628 = radeon_get_renderbuffer(ctx
->DrawBuffer
, BUFFER_STENCIL
);
629 hw_stencil
= (rrbStencil
&& rrbStencil
->bo
);
633 R300_STATECHANGE(r300
, zs
);
635 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] |=
638 r300
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] &=
639 ~R300_STENCIL_ENABLE
;
644 static void r300UpdatePolygonMode(struct gl_context
* ctx
)
646 r300ContextPtr r300
= R300_CONTEXT(ctx
);
647 uint32_t hw_mode
= R300_GA_POLY_MODE_DISABLE
;
649 /* Only do something if a polygon mode is wanted, default is GL_FILL */
650 if (ctx
->Polygon
.FrontMode
!= GL_FILL
||
651 ctx
->Polygon
.BackMode
!= GL_FILL
) {
654 /* Handle GL_CW (clock wise and GL_CCW (counter clock wise)
655 * correctly by selecting the correct front and back face
657 if (ctx
->Polygon
.FrontFace
== GL_CCW
) {
658 f
= ctx
->Polygon
.FrontMode
;
659 b
= ctx
->Polygon
.BackMode
;
661 f
= ctx
->Polygon
.BackMode
;
662 b
= ctx
->Polygon
.FrontMode
;
665 /* Enable polygon mode */
666 hw_mode
|= R300_GA_POLY_MODE_DUAL
;
670 hw_mode
|= R300_GA_POLY_MODE_FRONT_PTYPE_LINE
;
673 hw_mode
|= R300_GA_POLY_MODE_FRONT_PTYPE_POINT
;
676 hw_mode
|= R300_GA_POLY_MODE_FRONT_PTYPE_TRI
;
682 hw_mode
|= R300_GA_POLY_MODE_BACK_PTYPE_LINE
;
685 hw_mode
|= R300_GA_POLY_MODE_BACK_PTYPE_POINT
;
688 hw_mode
|= R300_GA_POLY_MODE_BACK_PTYPE_TRI
;
693 if (r300
->hw
.polygon_mode
.cmd
[1] != hw_mode
) {
694 R300_STATECHANGE(r300
, polygon_mode
);
695 r300
->hw
.polygon_mode
.cmd
[1] = hw_mode
;
698 r300
->hw
.polygon_mode
.cmd
[2] = 0x00000001;
699 r300
->hw
.polygon_mode
.cmd
[3] = 0x00000000;
703 * Change the culling mode.
705 * \note Mesa already filters redundant calls to this function.
707 static void r300CullFace(struct gl_context
* ctx
, GLenum mode
)
711 r300UpdateCulling(ctx
);
715 * Change the polygon orientation.
717 * \note Mesa already filters redundant calls to this function.
719 static void r300FrontFace(struct gl_context
* ctx
, GLenum mode
)
723 r300UpdateCulling(ctx
);
724 r300UpdatePolygonMode(ctx
);
728 * Change the depth testing function.
730 * \note Mesa already filters redundant calls to this function.
732 static void r300DepthFunc(struct gl_context
* ctx
, GLenum func
)
735 r300SetDepthState(ctx
);
739 * Enable/Disable depth writing.
741 * \note Mesa already filters redundant calls to this function.
743 static void r300DepthMask(struct gl_context
* ctx
, GLboolean mask
)
746 r300SetDepthState(ctx
);
750 * Handle glColorMask()
752 static void r300ColorMask(struct gl_context
* ctx
,
753 GLboolean r
, GLboolean g
, GLboolean b
, GLboolean a
)
755 r300ContextPtr r300
= R300_CONTEXT(ctx
);
756 int mask
= (r
? RB3D_COLOR_CHANNEL_MASK_RED_MASK0
: 0) |
757 (g
? RB3D_COLOR_CHANNEL_MASK_GREEN_MASK0
: 0) |
758 (b
? RB3D_COLOR_CHANNEL_MASK_BLUE_MASK0
: 0) |
759 (a
? RB3D_COLOR_CHANNEL_MASK_ALPHA_MASK0
: 0);
761 if (mask
!= r300
->hw
.cmk
.cmd
[R300_CMK_COLORMASK
]) {
762 R300_STATECHANGE(r300
, cmk
);
763 r300
->hw
.cmk
.cmd
[R300_CMK_COLORMASK
] = mask
;
767 /* =============================================================
770 static void r300PointSize(struct gl_context
* ctx
, GLfloat size
)
772 r300ContextPtr r300
= R300_CONTEXT(ctx
);
774 /* We need to clamp to user defined range here, because
775 * the HW clamping happens only for per vertex point size. */
776 size
= CLAMP(size
, ctx
->Point
.MinSize
, ctx
->Point
.MaxSize
);
778 /* same size limits for AA, non-AA points */
779 size
= CLAMP(size
, ctx
->Const
.MinPointSize
, ctx
->Const
.MaxPointSize
);
781 R300_STATECHANGE(r300
, ps
);
782 r300
->hw
.ps
.cmd
[R300_PS_POINTSIZE
] =
783 ((int)(size
* 6) << R300_POINTSIZE_X_SHIFT
) |
784 ((int)(size
* 6) << R300_POINTSIZE_Y_SHIFT
);
787 static void r300PointParameter(struct gl_context
* ctx
, GLenum pname
, const GLfloat
* param
)
789 r300ContextPtr r300
= R300_CONTEXT(ctx
);
792 case GL_POINT_SIZE_MIN
:
793 R300_STATECHANGE(r300
, ga_point_minmax
);
794 r300
->hw
.ga_point_minmax
.cmd
[1] &= ~R300_GA_POINT_MINMAX_MIN_MASK
;
795 r300
->hw
.ga_point_minmax
.cmd
[1] |= (GLuint
)(ctx
->Point
.MinSize
* 6.0);
796 r300PointSize(ctx
, ctx
->Point
.Size
);
798 case GL_POINT_SIZE_MAX
:
799 R300_STATECHANGE(r300
, ga_point_minmax
);
800 r300
->hw
.ga_point_minmax
.cmd
[1] &= ~R300_GA_POINT_MINMAX_MAX_MASK
;
801 r300
->hw
.ga_point_minmax
.cmd
[1] |= (GLuint
)(ctx
->Point
.MaxSize
* 6.0)
802 << R300_GA_POINT_MINMAX_MAX_SHIFT
;
803 r300PointSize(ctx
, ctx
->Point
.Size
);
805 case GL_POINT_DISTANCE_ATTENUATION
:
807 case GL_POINT_FADE_THRESHOLD_SIZE
:
814 /* =============================================================
817 static void r300LineWidth(struct gl_context
* ctx
, GLfloat widthf
)
819 r300ContextPtr r300
= R300_CONTEXT(ctx
);
821 widthf
= CLAMP(widthf
,
822 ctx
->Const
.MinPointSize
,
823 ctx
->Const
.MaxPointSize
);
824 R300_STATECHANGE(r300
, lcntl
);
825 r300
->hw
.lcntl
.cmd
[1] =
826 R300_LINE_CNT_HO
| R300_LINE_CNT_VE
| (int)(widthf
* 6.0);
829 static void r300PolygonMode(struct gl_context
* ctx
, GLenum face
, GLenum mode
)
834 r300UpdatePolygonMode(ctx
);
837 /* =============================================================
841 static int translate_stencil_op(int op
)
849 return R300_ZS_REPLACE
;
854 case GL_INCR_WRAP_EXT
:
855 return R300_ZS_INCR_WRAP
;
856 case GL_DECR_WRAP_EXT
:
857 return R300_ZS_DECR_WRAP
;
859 return R300_ZS_INVERT
;
861 WARN_ONCE("Do not know how to translate stencil op");
867 static void r300ShadeModel(struct gl_context
* ctx
, GLenum mode
)
869 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
871 R300_STATECHANGE(rmesa
, shade
);
872 rmesa
->hw
.shade
.cmd
[1] = 0x00000002;
873 R300_STATECHANGE(rmesa
, shade2
);
876 rmesa
->hw
.shade2
.cmd
[1] = R300_RE_SHADE_MODEL_FLAT
;
879 rmesa
->hw
.shade2
.cmd
[1] = R300_RE_SHADE_MODEL_SMOOTH
;
884 rmesa
->hw
.shade2
.cmd
[2] = 0x00000000;
885 rmesa
->hw
.shade2
.cmd
[3] = 0x00000000;
888 static void r300StencilFuncSeparate(struct gl_context
* ctx
, GLenum face
,
889 GLenum func
, GLint ref
, GLuint mask
)
891 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
894 const unsigned back
= ctx
->Stencil
._BackFace
;
896 r300CatchStencilFallback(ctx
);
898 refmask
= ((ctx
->Stencil
.Ref
[0] & 0xff) << R300_STENCILREF_SHIFT
)
899 | ((ctx
->Stencil
.ValueMask
[0] & 0xff) << R300_STENCILMASK_SHIFT
);
901 R300_STATECHANGE(rmesa
, zs
);
902 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] |= R300_STENCIL_FRONT_BACK
;
903 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] &= ~((R300_ZS_MASK
<<
904 R300_S_FRONT_FUNC_SHIFT
)
906 R300_S_BACK_FUNC_SHIFT
));
908 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_2
] &=
909 ~((R300_STENCILREF_MASK
<< R300_STENCILREF_SHIFT
) |
910 (R300_STENCILREF_MASK
<< R300_STENCILMASK_SHIFT
));
912 flag
= translate_func(ctx
->Stencil
.Function
[0]);
913 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] |=
914 (flag
<< R300_S_FRONT_FUNC_SHIFT
);
916 flag
= translate_func(ctx
->Stencil
.Function
[back
]);
918 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] |=
919 (flag
<< R300_S_BACK_FUNC_SHIFT
);
920 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_2
] |= refmask
;
922 if (rmesa
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
) {
923 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_0
] |= R500_STENCIL_REFMASK_FRONT_BACK
;
924 R300_STATECHANGE(rmesa
, zsb
);
925 refmask
= ((ctx
->Stencil
.Ref
[back
] & 0xff) << R300_STENCILREF_SHIFT
)
926 | ((ctx
->Stencil
.ValueMask
[back
] & 0xff) << R300_STENCILMASK_SHIFT
);
928 rmesa
->hw
.zsb
.cmd
[R300_ZSB_CNTL_0
] &=
929 ~((R300_STENCILREF_MASK
<< R300_STENCILREF_SHIFT
) |
930 (R300_STENCILREF_MASK
<< R300_STENCILMASK_SHIFT
));
931 rmesa
->hw
.zsb
.cmd
[R300_ZSB_CNTL_0
] |= refmask
;
935 static void r300StencilMaskSeparate(struct gl_context
* ctx
, GLenum face
, GLuint mask
)
937 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
938 const unsigned back
= ctx
->Stencil
._BackFace
;
940 r300CatchStencilFallback(ctx
);
942 R300_STATECHANGE(rmesa
, zs
);
943 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_2
] &=
944 ~(R300_STENCILREF_MASK
<<
945 R300_STENCILWRITEMASK_SHIFT
);
946 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_2
] |=
948 WriteMask
[0] & R300_STENCILREF_MASK
) <<
949 R300_STENCILWRITEMASK_SHIFT
;
950 if (rmesa
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
) {
951 R300_STATECHANGE(rmesa
, zsb
);
952 rmesa
->hw
.zsb
.cmd
[R300_ZSB_CNTL_0
] |=
954 WriteMask
[back
] & R300_STENCILREF_MASK
) <<
955 R300_STENCILWRITEMASK_SHIFT
;
959 static void r300StencilOpSeparate(struct gl_context
* ctx
, GLenum face
,
960 GLenum fail
, GLenum zfail
, GLenum zpass
)
962 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
963 const unsigned back
= ctx
->Stencil
._BackFace
;
965 r300CatchStencilFallback(ctx
);
967 R300_STATECHANGE(rmesa
, zs
);
968 /* It is easier to mask what's left.. */
969 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] &=
970 (R300_ZS_MASK
<< R300_Z_FUNC_SHIFT
) |
971 (R300_ZS_MASK
<< R300_S_FRONT_FUNC_SHIFT
) |
972 (R300_ZS_MASK
<< R300_S_BACK_FUNC_SHIFT
);
974 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] |=
975 (translate_stencil_op(ctx
->Stencil
.FailFunc
[0]) <<
976 R300_S_FRONT_SFAIL_OP_SHIFT
)
977 | (translate_stencil_op(ctx
->Stencil
.ZFailFunc
[0]) <<
978 R300_S_FRONT_ZFAIL_OP_SHIFT
)
979 | (translate_stencil_op(ctx
->Stencil
.ZPassFunc
[0]) <<
980 R300_S_FRONT_ZPASS_OP_SHIFT
);
982 rmesa
->hw
.zs
.cmd
[R300_ZS_CNTL_1
] |=
983 (translate_stencil_op(ctx
->Stencil
.FailFunc
[back
]) <<
984 R300_S_BACK_SFAIL_OP_SHIFT
)
985 | (translate_stencil_op(ctx
->Stencil
.ZFailFunc
[back
]) <<
986 R300_S_BACK_ZFAIL_OP_SHIFT
)
987 | (translate_stencil_op(ctx
->Stencil
.ZPassFunc
[back
]) <<
988 R300_S_BACK_ZPASS_OP_SHIFT
);
991 /* =============================================================
992 * Window position and viewport transformation
995 static void r300UpdateWindow(struct gl_context
* ctx
)
997 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
998 __DRIdrawable
*dPriv
= radeon_get_drawable(&rmesa
->radeon
);
999 GLfloat xoffset
= dPriv
? (GLfloat
) dPriv
->x
: 0;
1000 GLfloat yoffset
= dPriv
? (GLfloat
) dPriv
->y
+ dPriv
->h
: 0;
1001 const GLfloat
*v
= ctx
->Viewport
._WindowMap
.m
;
1002 const GLfloat depthScale
= 1.0F
/ ctx
->DrawBuffer
->_DepthMaxF
;
1003 const GLboolean render_to_fbo
= (ctx
->DrawBuffer
->Name
!= 0);
1004 GLfloat y_scale
, y_bias
;
1006 if (render_to_fbo
) {
1014 GLfloat sx
= v
[MAT_SX
];
1015 GLfloat tx
= v
[MAT_TX
] + xoffset
;
1016 GLfloat sy
= v
[MAT_SY
] * y_scale
;
1017 GLfloat ty
= (v
[MAT_TY
] * y_scale
) + y_bias
;
1018 GLfloat sz
= v
[MAT_SZ
] * depthScale
;
1019 GLfloat tz
= v
[MAT_TZ
] * depthScale
;
1021 R300_STATECHANGE(rmesa
, vpt
);
1023 rmesa
->hw
.vpt
.cmd
[R300_VPT_XSCALE
] = r300PackFloat32(sx
);
1024 rmesa
->hw
.vpt
.cmd
[R300_VPT_XOFFSET
] = r300PackFloat32(tx
);
1025 rmesa
->hw
.vpt
.cmd
[R300_VPT_YSCALE
] = r300PackFloat32(sy
);
1026 rmesa
->hw
.vpt
.cmd
[R300_VPT_YOFFSET
] = r300PackFloat32(ty
);
1027 rmesa
->hw
.vpt
.cmd
[R300_VPT_ZSCALE
] = r300PackFloat32(sz
);
1028 rmesa
->hw
.vpt
.cmd
[R300_VPT_ZOFFSET
] = r300PackFloat32(tz
);
1031 static void r300Viewport(struct gl_context
* ctx
, GLint x
, GLint y
,
1032 GLsizei width
, GLsizei height
)
1034 /* Don't pipeline viewport changes, conflict with window offset
1035 * setting below. Could apply deltas to rescue pipelined viewport
1036 * values, or keep the originals hanging around.
1038 r300UpdateWindow(ctx
);
1040 radeon_viewport(ctx
, x
, y
, width
, height
);
1043 static void r300DepthRange(struct gl_context
* ctx
, GLclampd nearval
, GLclampd farval
)
1045 r300UpdateWindow(ctx
);
1048 void r300UpdateViewportOffset(struct gl_context
* ctx
)
1050 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
1051 __DRIdrawable
*dPriv
= radeon_get_drawable(&rmesa
->radeon
);
1052 GLfloat xoffset
= (GLfloat
) dPriv
->x
;
1053 GLfloat yoffset
= (GLfloat
) dPriv
->y
+ dPriv
->h
;
1054 const GLfloat
*v
= ctx
->Viewport
._WindowMap
.m
;
1056 GLfloat tx
= v
[MAT_TX
] + xoffset
;
1057 GLfloat ty
= (-v
[MAT_TY
]) + yoffset
;
1059 if (rmesa
->hw
.vpt
.cmd
[R300_VPT_XOFFSET
] != r300PackFloat32(tx
) ||
1060 rmesa
->hw
.vpt
.cmd
[R300_VPT_YOFFSET
] != r300PackFloat32(ty
)) {
1061 /* Note: this should also modify whatever data the context reset
1064 R300_STATECHANGE(rmesa
, vpt
);
1065 rmesa
->hw
.vpt
.cmd
[R300_VPT_XOFFSET
] = r300PackFloat32(tx
);
1066 rmesa
->hw
.vpt
.cmd
[R300_VPT_YOFFSET
] = r300PackFloat32(ty
);
1070 radeonUpdateScissor(ctx
);
1074 * Update R300's own internal state parameters.
1075 * For now just STATE_R300_WINDOW_DIMENSION
1077 static void r300UpdateStateParameters(struct gl_context
* ctx
, GLuint new_state
)
1079 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
1080 struct gl_program_parameter_list
*paramList
;
1082 if (!(new_state
& (_NEW_BUFFERS
| _NEW_PROGRAM
| _NEW_PROGRAM_CONSTANTS
)))
1085 if (!ctx
->FragmentProgram
._Current
|| !rmesa
->selected_fp
)
1088 paramList
= ctx
->FragmentProgram
._Current
->Base
.Parameters
;
1093 _mesa_load_state_parameters(ctx
, paramList
);
1096 /* =============================================================
1099 static void r300PolygonOffset(struct gl_context
* ctx
, GLfloat factor
, GLfloat units
)
1101 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
1102 GLfloat constant
= units
;
1104 switch (ctx
->Visual
.depthBits
) {
1115 /* fprintf(stderr, "%s f:%f u:%f\n", __FUNCTION__, factor, constant); */
1117 R300_STATECHANGE(rmesa
, zbs
);
1118 rmesa
->hw
.zbs
.cmd
[R300_ZBS_T_FACTOR
] = r300PackFloat32(factor
);
1119 rmesa
->hw
.zbs
.cmd
[R300_ZBS_T_CONSTANT
] = r300PackFloat32(constant
);
1120 rmesa
->hw
.zbs
.cmd
[R300_ZBS_W_FACTOR
] = r300PackFloat32(factor
);
1121 rmesa
->hw
.zbs
.cmd
[R300_ZBS_W_CONSTANT
] = r300PackFloat32(constant
);
1124 /* Routing and texture-related */
1126 /* r300 doesnt handle GL_CLAMP and GL_MIRROR_CLAMP_EXT correctly when filter is NEAREST.
1127 * Since texwrap produces same results for GL_CLAMP and GL_CLAMP_TO_EDGE we use them instead.
1128 * We need to recalculate wrap modes whenever filter mode is changed because someone might do:
1129 * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_NEAREST);
1130 * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, GL_CLAMP);
1131 * glTexParameteri(GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, GL_LINEAR);
1132 * Since r300 completely ignores R300_TX_CLAMP when either min or mag is nearest it cant handle
1133 * combinations where only one of them is nearest.
1135 static unsigned long gen_fixed_filter(unsigned long f
)
1137 unsigned long mag
, min
, needs_fixing
= 0;
1140 /* We ignore MIRROR bit so we dont have to do everything twice */
1141 if ((f
& ((7 - 1) << R300_TX_WRAP_S_SHIFT
)) ==
1142 (R300_TX_CLAMP
<< R300_TX_WRAP_S_SHIFT
)) {
1145 if ((f
& ((7 - 1) << R300_TX_WRAP_T_SHIFT
)) ==
1146 (R300_TX_CLAMP
<< R300_TX_WRAP_T_SHIFT
)) {
1149 if ((f
& ((7 - 1) << R300_TX_WRAP_R_SHIFT
)) ==
1150 (R300_TX_CLAMP
<< R300_TX_WRAP_R_SHIFT
)) {
1157 mag
= f
& R300_TX_MAG_FILTER_MASK
;
1158 min
= f
& (R300_TX_MIN_FILTER_MASK
|R300_TX_MIN_FILTER_MIP_MASK
);
1160 /* TODO: Check for anisto filters too */
1161 if ((mag
!= R300_TX_MAG_FILTER_NEAREST
)
1162 && (min
!= R300_TX_MIN_FILTER_NEAREST
))
1165 /* r300 cant handle these modes hence we force nearest to linear */
1166 if ((mag
== R300_TX_MAG_FILTER_NEAREST
)
1167 && (min
!= R300_TX_MIN_FILTER_NEAREST
)) {
1168 f
&= ~R300_TX_MAG_FILTER_NEAREST
;
1169 f
|= R300_TX_MAG_FILTER_LINEAR
;
1173 if ((min
== R300_TX_MIN_FILTER_NEAREST
)
1174 && (mag
!= R300_TX_MAG_FILTER_NEAREST
)) {
1175 f
&= ~R300_TX_MIN_FILTER_NEAREST
;
1176 f
|= R300_TX_MIN_FILTER_LINEAR
;
1180 /* Both are nearest */
1181 if (needs_fixing
& 1) {
1182 f
&= ~((7 - 1) << R300_TX_WRAP_S_SHIFT
);
1183 f
|= R300_TX_CLAMP_TO_EDGE
<< R300_TX_WRAP_S_SHIFT
;
1185 if (needs_fixing
& 2) {
1186 f
&= ~((7 - 1) << R300_TX_WRAP_T_SHIFT
);
1187 f
|= R300_TX_CLAMP_TO_EDGE
<< R300_TX_WRAP_T_SHIFT
;
1189 if (needs_fixing
& 4) {
1190 f
&= ~((7 - 1) << R300_TX_WRAP_R_SHIFT
);
1191 f
|= R300_TX_CLAMP_TO_EDGE
<< R300_TX_WRAP_R_SHIFT
;
1196 static void r300SetupFragmentShaderTextures(struct gl_context
*ctx
, int *tmu_mappings
)
1198 r300ContextPtr r300
= R300_CONTEXT(ctx
);
1200 struct r300_fragment_program_code
*code
= &r300
->selected_fp
->code
.code
.r300
;
1202 R300_STATECHANGE(r300
, fpt
);
1204 for (i
= 0; i
< code
->tex
.length
; i
++) {
1209 unit
= code
->tex
.inst
[i
] >> R300_TEX_ID_SHIFT
;
1212 val
= code
->tex
.inst
[i
];
1213 val
&= ~R300_TEX_ID_MASK
;
1216 (val
& R300_TEX_INST_MASK
) >> R300_TEX_INST_SHIFT
;
1217 if (opcode
== R300_TEX_OP_KIL
) {
1218 r300
->hw
.fpt
.cmd
[R300_FPT_INSTR_0
+ i
] = val
;
1220 if (tmu_mappings
[unit
] >= 0) {
1222 tmu_mappings
[unit
] <<
1224 r300
->hw
.fpt
.cmd
[R300_FPT_INSTR_0
+ i
] = val
;
1226 // We get here when the corresponding texture image is incomplete
1227 // (e.g. incomplete mipmaps etc.)
1228 r300
->hw
.fpt
.cmd
[R300_FPT_INSTR_0
+ i
] = val
;
1233 r300
->hw
.fpt
.cmd
[R300_FPT_CMD_0
] =
1234 cmdpacket0(r300
->radeon
.radeonScreen
,
1235 R300_US_TEX_INST_0
, code
->tex
.length
);
1238 static void r500SetupFragmentShaderTextures(struct gl_context
*ctx
, int *tmu_mappings
)
1240 r300ContextPtr r300
= R300_CONTEXT(ctx
);
1242 struct r500_fragment_program_code
*code
= &r300
->selected_fp
->code
.code
.r500
;
1244 /* find all the texture instructions and relocate the texture units */
1245 for (i
= 0; i
< code
->inst_end
+ 1; i
++) {
1246 if ((code
->inst
[i
].inst0
& 0x3) == R500_INST_TYPE_TEX
) {
1248 int unit
, opcode
, new_unit
;
1250 val
= code
->inst
[i
].inst1
;
1252 unit
= (val
>> 16) & 0xf;
1254 val
&= ~(0xf << 16);
1256 opcode
= val
& (0x7 << 22);
1257 if (opcode
== R500_TEX_INST_TEXKILL
) {
1260 if (tmu_mappings
[unit
] >= 0) {
1261 new_unit
= tmu_mappings
[unit
];
1266 val
|= R500_TEX_ID(new_unit
);
1267 code
->inst
[i
].inst1
= val
;
1272 static GLuint
translate_lod_bias(GLfloat bias
)
1274 GLint b
= (int)(bias
*32);
1277 else if (b
< -(1 << 9))
1279 return (((GLuint
)b
) << R300_LOD_BIAS_SHIFT
) & R300_LOD_BIAS_MASK
;
1283 static void r300SetupTextures(struct gl_context
* ctx
)
1286 struct radeon_tex_obj
*t
;
1287 r300ContextPtr r300
= R300_CONTEXT(ctx
);
1289 int last_hw_tmu
= -1; /* -1 translates into no setup costs for fields */
1290 int tmu_mappings
[R300_MAX_TEXTURE_UNITS
] = { -1, };
1292 R300_STATECHANGE(r300
, txe
);
1293 R300_STATECHANGE(r300
, tex
.filter
);
1294 R300_STATECHANGE(r300
, tex
.filter_1
);
1295 R300_STATECHANGE(r300
, tex
.size
);
1296 R300_STATECHANGE(r300
, tex
.format
);
1297 R300_STATECHANGE(r300
, tex
.pitch
);
1298 R300_STATECHANGE(r300
, tex
.offset
);
1299 R300_STATECHANGE(r300
, tex
.chroma_key
);
1300 R300_STATECHANGE(r300
, tex
.border_color
);
1302 r300
->hw
.txe
.cmd
[R300_TXE_ENABLE
] = 0x0;
1304 mtu
= r300
->radeon
.glCtx
->Const
.MaxTextureUnits
;
1305 if (RADEON_DEBUG
& RADEON_STATE
)
1306 fprintf(stderr
, "mtu=%d\n", mtu
);
1308 if (mtu
> R300_MAX_TEXTURE_UNITS
) {
1310 "Aiiee ! mtu=%d is greater than R300_MAX_TEXTURE_UNITS=%d\n",
1311 mtu
, R300_MAX_TEXTURE_UNITS
);
1315 /* We cannot let disabled tmu offsets pass DRM */
1316 for (i
= 0; i
< mtu
; i
++) {
1317 if (ctx
->Texture
.Unit
[i
]._ReallyEnabled
) {
1318 tmu_mappings
[i
] = hw_tmu
;
1320 t
= radeon_tex_obj(ctx
->Texture
.Unit
[i
]._Current
);
1324 if ((t
->pp_txformat
& 0xffffff00) == 0xffffff00) {
1326 ("unknown texture format (entry %x) encountered. Help me !\n",
1327 t
->pp_txformat
& 0xff);
1330 if (RADEON_DEBUG
& RADEON_STATE
)
1332 "Activating texture unit %d\n", i
);
1334 r300
->hw
.txe
.cmd
[R300_TXE_ENABLE
] |= (1 << hw_tmu
);
1336 r300
->hw
.tex
.filter
.cmd
[R300_TEX_VALUE_0
+
1338 gen_fixed_filter(t
->pp_txfilter
) | (hw_tmu
<< 28);
1339 /* Note: There is a LOD bias per texture unit and a LOD bias
1340 * per texture object. We add them here to get the correct behaviour.
1341 * (The per-texture object LOD bias was introduced in OpenGL 1.4
1342 * and is not present in the EXT_texture_object extension).
1344 r300
->hw
.tex
.filter_1
.cmd
[R300_TEX_VALUE_0
+ hw_tmu
] =
1346 translate_lod_bias(ctx
->Texture
.Unit
[i
].LodBias
+ t
->base
.Sampler
.LodBias
);
1347 r300
->hw
.tex
.size
.cmd
[R300_TEX_VALUE_0
+ hw_tmu
] =
1349 r300
->hw
.tex
.format
.cmd
[R300_TEX_VALUE_0
+
1350 hw_tmu
] = t
->pp_txformat
;
1351 r300
->hw
.tex
.pitch
.cmd
[R300_TEX_VALUE_0
+ hw_tmu
] =
1353 r300
->hw
.textures
[hw_tmu
] = t
;
1355 if (t
->tile_bits
& R300_TXO_MACRO_TILE
) {
1356 WARN_ONCE("macro tiling enabled!\n");
1359 if (t
->tile_bits
& R300_TXO_MICRO_TILE
) {
1360 WARN_ONCE("micro tiling enabled!\n");
1363 r300
->hw
.tex
.chroma_key
.cmd
[R300_TEX_VALUE_0
+
1365 r300
->hw
.tex
.border_color
.cmd
[R300_TEX_VALUE_0
+
1369 last_hw_tmu
= hw_tmu
;
1375 /* R3xx and R4xx chips require that the texture unit corresponding to
1376 * KIL instructions is really enabled.
1378 * We do some fakery here and in the state atom emit logic to enable
1379 * the texture without tripping up the CS checker in the kernel.
1381 if (r300
->radeon
.radeonScreen
->chip_family
< CHIP_FAMILY_RV515
) {
1382 if (ctx
->FragmentProgram
._Current
->UsesKill
&& last_hw_tmu
< 0) {
1385 r300
->hw
.txe
.cmd
[R300_TXE_ENABLE
] |= 1;
1387 r300
->hw
.tex
.border_color
.cmd
[R300_TEX_VALUE_0
] = 0;
1388 r300
->hw
.tex
.chroma_key
.cmd
[R300_TEX_VALUE_0
] = 0;
1389 r300
->hw
.tex
.filter
.cmd
[R300_TEX_VALUE_0
] = 0;
1390 r300
->hw
.tex
.filter_1
.cmd
[R300_TEX_VALUE_0
] = 0;
1391 r300
->hw
.tex
.size
.cmd
[R300_TEX_VALUE_0
] = 0; /* 1x1 texture */
1392 r300
->hw
.tex
.format
.cmd
[R300_TEX_VALUE_0
] = 0; /* A8 format */
1393 r300
->hw
.tex
.pitch
.cmd
[R300_TEX_VALUE_0
] = 0;
1397 r300
->hw
.tex
.filter
.cmd
[R300_TEX_CMD_0
] =
1398 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_FILTER0_0
, last_hw_tmu
+ 1);
1399 r300
->hw
.tex
.filter_1
.cmd
[R300_TEX_CMD_0
] =
1400 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_FILTER1_0
, last_hw_tmu
+ 1);
1401 r300
->hw
.tex
.size
.cmd
[R300_TEX_CMD_0
] =
1402 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_SIZE_0
, last_hw_tmu
+ 1);
1403 r300
->hw
.tex
.format
.cmd
[R300_TEX_CMD_0
] =
1404 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_FORMAT_0
, last_hw_tmu
+ 1);
1405 r300
->hw
.tex
.pitch
.cmd
[R300_TEX_CMD_0
] =
1406 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_FORMAT2_0
, last_hw_tmu
+ 1);
1407 r300
->hw
.tex
.offset
.cmd
[R300_TEX_CMD_0
] =
1408 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_OFFSET_0
, last_hw_tmu
+ 1);
1409 r300
->hw
.tex
.chroma_key
.cmd
[R300_TEX_CMD_0
] =
1410 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_CHROMA_KEY_0
, last_hw_tmu
+ 1);
1411 r300
->hw
.tex
.border_color
.cmd
[R300_TEX_CMD_0
] =
1412 cmdpacket0(r300
->radeon
.radeonScreen
, R300_TX_BORDER_COLOR_0
, last_hw_tmu
+ 1);
1414 r300
->vtbl
.SetupFragmentShaderTextures(ctx
, tmu_mappings
);
1416 if (RADEON_DEBUG
& RADEON_STATE
)
1417 fprintf(stderr
, "TX_ENABLE: %08x last_hw_tmu=%d\n",
1418 r300
->hw
.txe
.cmd
[R300_TXE_ENABLE
], last_hw_tmu
);
1421 union r300_outputs_written
{
1422 GLuint vp_outputs
; /* hw_tcl_on */
1423 DECLARE_RENDERINPUTS(index_bitset
); /* !hw_tcl_on */
1426 #define R300_OUTPUTS_WRITTEN_TEST(ow, vp_result, tnl_attrib) \
1427 ((hw_tcl_on) ? (ow).vp_outputs & (1 << (vp_result)) : \
1428 RENDERINPUTS_TEST( (ow.index_bitset), (tnl_attrib) ))
1430 static void r300SetupRSUnit(struct gl_context
* ctx
)
1432 r300ContextPtr r300
= R300_CONTEXT(ctx
);
1433 union r300_outputs_written OutputsWritten
;
1435 int fp_reg
, high_rr
;
1437 int rs_tex_count
= 0;
1438 int i
, col_fmt
, hw_tcl_on
;
1440 hw_tcl_on
= r300
->options
.hw_tcl_enabled
;
1443 OutputsWritten
.vp_outputs
= r300
->selected_vp
->code
.OutputsWritten
;
1445 RENDERINPUTS_COPY(OutputsWritten
.index_bitset
, r300
->render_inputs_bitset
);
1447 InputsRead
= r300
->selected_fp
->InputsRead
;
1449 R300_STATECHANGE(r300
, ri
);
1450 R300_STATECHANGE(r300
, rc
);
1451 R300_STATECHANGE(r300
, rr
);
1453 fp_reg
= col_ip
= tex_ip
= col_fmt
= 0;
1455 r300
->hw
.rc
.cmd
[1] = 0;
1456 r300
->hw
.rc
.cmd
[2] = 0;
1457 for (i
=0; i
<R300_RR_CMDSIZE
-1; ++i
)
1458 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ i
] = 0;
1460 for (i
=0; i
<R300_RI_CMDSIZE
-1; ++i
)
1461 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ i
] = 0;
1464 if (InputsRead
& FRAG_BIT_COL0
) {
1465 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten
, VERT_RESULT_COL0
, _TNL_ATTRIB_COLOR0
)) {
1466 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ col_ip
] = R300_RS_COL_PTR(col_ip
) | R300_RS_COL_FMT(R300_RS_COL_FMT_RGBA
);
1467 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ col_ip
] = R300_RS_INST_COL_ID(col_ip
) | R300_RS_INST_COL_CN_WRITE
| R300_RS_INST_COL_ADDR(fp_reg
);
1468 InputsRead
&= ~FRAG_BIT_COL0
;
1472 WARN_ONCE("fragprog wants col0, vp doesn't provide it\n");
1476 if (InputsRead
& FRAG_BIT_COL1
) {
1477 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten
, VERT_RESULT_COL1
, _TNL_ATTRIB_COLOR1
)) {
1478 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ col_ip
] = R300_RS_COL_PTR(col_ip
) | R300_RS_COL_FMT(R300_RS_COL_FMT_RGBA
);
1479 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ col_ip
] = R300_RS_INST_COL_ID(col_ip
) | R300_RS_INST_COL_CN_WRITE
| R300_RS_INST_COL_ADDR(fp_reg
);
1480 InputsRead
&= ~FRAG_BIT_COL1
;
1484 WARN_ONCE("fragprog wants col1, vp doesn't provide it\n");
1488 /* We always route 4 texcoord components */
1489 for (i
= 0; i
< ctx
->Const
.MaxTextureUnits
; i
++) {
1490 if (! ( InputsRead
& FRAG_BIT_TEX(i
) ) )
1493 if (!R300_OUTPUTS_WRITTEN_TEST(OutputsWritten
, VERT_RESULT_TEX0
+ i
, _TNL_ATTRIB_TEX(i
))) {
1494 WARN_ONCE("fragprog wants coords for tex%d, vp doesn't provide them!\n", i
);
1498 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ tex_ip
] |= R300_RS_SEL_S(0) | R300_RS_SEL_T(1) | R300_RS_SEL_R(2) | R300_RS_SEL_Q(3) | R300_RS_TEX_PTR(rs_tex_count
);
1499 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ tex_ip
] |= R300_RS_INST_TEX_ID(tex_ip
) | R300_RS_INST_TEX_CN_WRITE
| R300_RS_INST_TEX_ADDR(fp_reg
);
1500 InputsRead
&= ~(FRAG_BIT_TEX0
<< i
);
1506 /* Setup default color if no color or tex was set */
1507 if (rs_tex_count
== 0 && col_ip
== 0) {
1508 r300
->hw
.rr
.cmd
[R300_RR_INST_0
] = R300_RS_INST_COL_ID(0) | R300_RS_INST_COL_ADDR(0);
1509 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
] = R300_RS_COL_PTR(0) | R300_RS_COL_FMT(R300_RS_COL_FMT_0001
);
1513 high_rr
= (col_ip
> tex_ip
) ? col_ip
: tex_ip
;
1514 r300
->hw
.rc
.cmd
[1] |= (rs_tex_count
<< R300_IT_COUNT_SHIFT
) | (col_ip
<< R300_IC_COUNT_SHIFT
) | R300_HIRES_EN
;
1515 r300
->hw
.rc
.cmd
[2] |= high_rr
- 1;
1517 r300
->hw
.rr
.cmd
[R300_RR_CMD_0
] = cmdpacket0(r300
->radeon
.radeonScreen
, R300_RS_INST_0
, high_rr
);
1518 r300
->hw
.ri
.cmd
[R300_RI_CMD_0
] = cmdpacket0(r300
->radeon
.radeonScreen
, R300_RS_IP_0
, high_rr
);
1521 WARN_ONCE("Don't know how to satisfy InputsRead=0x%08x\n", InputsRead
);
1524 static void r500SetupRSUnit(struct gl_context
* ctx
)
1526 r300ContextPtr r300
= R300_CONTEXT(ctx
);
1527 union r300_outputs_written OutputsWritten
;
1529 int fp_reg
, high_rr
;
1531 int rs_tex_count
= 0;
1532 int i
, col_fmt
, hw_tcl_on
;
1534 hw_tcl_on
= r300
->options
.hw_tcl_enabled
;
1537 OutputsWritten
.vp_outputs
= r300
->selected_vp
->code
.OutputsWritten
;
1539 RENDERINPUTS_COPY(OutputsWritten
.index_bitset
, r300
->render_inputs_bitset
);
1541 InputsRead
= r300
->selected_fp
->InputsRead
;
1543 R300_STATECHANGE(r300
, ri
);
1544 R300_STATECHANGE(r300
, rc
);
1545 R300_STATECHANGE(r300
, rr
);
1547 fp_reg
= col_ip
= tex_ip
= col_fmt
= 0;
1549 r300
->hw
.rc
.cmd
[1] = 0;
1550 r300
->hw
.rc
.cmd
[2] = 0;
1551 for (i
=0; i
<R300_RR_CMDSIZE
-1; ++i
)
1552 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ i
] = 0;
1554 for (i
=0; i
<R500_RI_CMDSIZE
-1; ++i
)
1555 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ i
] = 0;
1558 if (InputsRead
& FRAG_BIT_COL0
) {
1559 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten
, VERT_RESULT_COL0
, _TNL_ATTRIB_COLOR0
)) {
1560 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ col_ip
] = R500_RS_COL_PTR(col_ip
) | R500_RS_COL_FMT(R300_RS_COL_FMT_RGBA
);
1561 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ col_ip
] = R500_RS_INST_COL_ID(col_ip
) | R500_RS_INST_COL_CN_WRITE
| R500_RS_INST_COL_ADDR(fp_reg
);
1562 InputsRead
&= ~FRAG_BIT_COL0
;
1566 WARN_ONCE("fragprog wants col0, vp doesn't provide it\n");
1570 if (InputsRead
& FRAG_BIT_COL1
) {
1571 if (R300_OUTPUTS_WRITTEN_TEST(OutputsWritten
, VERT_RESULT_COL1
, _TNL_ATTRIB_COLOR1
)) {
1572 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ col_ip
] = R500_RS_COL_PTR(col_ip
) | R500_RS_COL_FMT(R300_RS_COL_FMT_RGBA
);
1573 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ col_ip
] = R500_RS_INST_COL_ID(col_ip
) | R500_RS_INST_COL_CN_WRITE
| R500_RS_INST_COL_ADDR(fp_reg
);
1574 InputsRead
&= ~FRAG_BIT_COL1
;
1578 WARN_ONCE("fragprog wants col1, vp doesn't provide it\n");
1582 /* We always route 4 texcoord components */
1583 for (i
= 0; i
< ctx
->Const
.MaxTextureUnits
; i
++) {
1584 if (! ( InputsRead
& FRAG_BIT_TEX(i
) ) )
1587 if (!R300_OUTPUTS_WRITTEN_TEST(OutputsWritten
, VERT_RESULT_TEX0
+ i
, _TNL_ATTRIB_TEX(i
))) {
1588 WARN_ONCE("fragprog wants coords for tex%d, vp doesn't provide them!\n", i
);
1592 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
+ tex_ip
] |= ((rs_tex_count
+ 0) << R500_RS_IP_TEX_PTR_S_SHIFT
) |
1593 ((rs_tex_count
+ 1) << R500_RS_IP_TEX_PTR_T_SHIFT
) |
1594 ((rs_tex_count
+ 2) << R500_RS_IP_TEX_PTR_R_SHIFT
) |
1595 ((rs_tex_count
+ 3) << R500_RS_IP_TEX_PTR_Q_SHIFT
);
1597 r300
->hw
.rr
.cmd
[R300_RR_INST_0
+ tex_ip
] |= R500_RS_INST_TEX_ID(tex_ip
) | R500_RS_INST_TEX_CN_WRITE
| R500_RS_INST_TEX_ADDR(fp_reg
);
1598 InputsRead
&= ~(FRAG_BIT_TEX0
<< i
);
1604 /* Setup default color if no color or tex was set */
1605 if (rs_tex_count
== 0 && col_ip
== 0) {
1606 r300
->hw
.rr
.cmd
[R300_RR_INST_0
] = R500_RS_INST_COL_ID(0) | R500_RS_INST_COL_ADDR(0);
1607 r300
->hw
.ri
.cmd
[R300_RI_INTERP_0
] = R500_RS_COL_PTR(0) | R500_RS_COL_FMT(R300_RS_COL_FMT_0001
);
1611 high_rr
= (col_ip
> tex_ip
) ? col_ip
: tex_ip
;
1612 r300
->hw
.rc
.cmd
[1] = (rs_tex_count
<< R300_IT_COUNT_SHIFT
) | (col_ip
<< R300_IC_COUNT_SHIFT
) | R300_HIRES_EN
;
1613 r300
->hw
.rc
.cmd
[2] = 0xC0 | (high_rr
- 1);
1615 r300
->hw
.rr
.cmd
[R300_RR_CMD_0
] = cmdpacket0(r300
->radeon
.radeonScreen
, R500_RS_INST_0
, high_rr
);
1616 r300
->hw
.ri
.cmd
[R300_RI_CMD_0
] = cmdpacket0(r300
->radeon
.radeonScreen
, R500_RS_IP_0
, high_rr
);
1619 WARN_ONCE("Don't know how to satisfy InputsRead=0x%08x\n", InputsRead
);
1623 void r300VapCntl(r300ContextPtr rmesa
, GLuint input_count
,
1624 GLuint output_count
, GLuint temp_count
)
1630 /* Flush PVS engine before changing PVS_NUM_SLOTS, PVS_NUM_CNTRLS.
1631 * See r500 docs 6.5.2 - done in emit */
1633 /* avoid division by zero */
1634 if (input_count
== 0) input_count
= 1;
1635 if (output_count
== 0) output_count
= 1;
1636 if (temp_count
== 0) temp_count
= 1;
1638 if (rmesa
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
)
1643 pvs_num_slots
= MIN3(10, vtx_mem_size
/input_count
, vtx_mem_size
/output_count
);
1644 pvs_num_cntrls
= MIN2(6, vtx_mem_size
/temp_count
);
1646 R300_STATECHANGE(rmesa
, vap_cntl
);
1647 if (rmesa
->options
.hw_tcl_enabled
) {
1648 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] =
1649 (pvs_num_slots
<< R300_PVS_NUM_SLOTS_SHIFT
) |
1650 (pvs_num_cntrls
<< R300_PVS_NUM_CNTLRS_SHIFT
) |
1651 (12 << R300_VF_MAX_VTX_NUM_SHIFT
);
1652 if (rmesa
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
)
1653 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] |= R500_TCL_STATE_OPTIMIZATION
;
1655 /* not sure about non-tcl */
1656 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] = ((10 << R300_PVS_NUM_SLOTS_SHIFT
) |
1657 (5 << R300_PVS_NUM_CNTLRS_SHIFT
) |
1658 (5 << R300_VF_MAX_VTX_NUM_SHIFT
));
1660 if ((rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_R300
) ||
1661 (rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_R350
))
1662 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] |= (4 << R300_PVS_NUM_FPUS_SHIFT
);
1663 else if (rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_RV530
)
1664 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] |= (5 << R300_PVS_NUM_FPUS_SHIFT
);
1665 else if ((rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_RV410
) ||
1666 (rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_R420
))
1667 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] |= (6 << R300_PVS_NUM_FPUS_SHIFT
);
1668 else if ((rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_R520
) ||
1669 (rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_R580
) ||
1670 (rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_RV560
) ||
1671 (rmesa
->radeon
.radeonScreen
->chip_family
== CHIP_FAMILY_RV570
))
1672 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] |= (8 << R300_PVS_NUM_FPUS_SHIFT
);
1674 rmesa
->hw
.vap_cntl
.cmd
[R300_VAP_CNTL_INSTR
] |= (2 << R300_PVS_NUM_FPUS_SHIFT
);
1679 * Enable/Disable states.
1681 * \note Mesa already filters redundant calls to this function.
1683 static void r300Enable(struct gl_context
* ctx
, GLenum cap
, GLboolean state
)
1685 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
1686 if (RADEON_DEBUG
& RADEON_STATE
)
1687 fprintf(stderr
, "%s( %s = %s )\n", __FUNCTION__
,
1688 _mesa_lookup_enum_by_nr(cap
),
1689 state
? "GL_TRUE" : "GL_FALSE");
1693 r300SetAlphaState(ctx
);
1695 case GL_COLOR_LOGIC_OP
:
1696 r300SetLogicOpState(ctx
);
1697 /* fall-through, because logic op overrides blending */
1699 r300SetBlendState(ctx
);
1701 case GL_CLIP_PLANE0
:
1702 case GL_CLIP_PLANE1
:
1703 case GL_CLIP_PLANE2
:
1704 case GL_CLIP_PLANE3
:
1705 case GL_CLIP_PLANE4
:
1706 case GL_CLIP_PLANE5
:
1707 r300SetClipPlaneState(ctx
, cap
, state
);
1710 r300UpdateCulling(ctx
);
1713 r300SetDepthState(ctx
);
1715 case GL_LINE_SMOOTH
:
1716 if (rmesa
->options
.conformance_mode
)
1717 r300SwitchFallback(ctx
, R300_FALLBACK_LINE_SMOOTH
, ctx
->Line
.SmoothFlag
);
1719 case GL_LINE_STIPPLE
:
1720 if (rmesa
->options
.conformance_mode
)
1721 r300SwitchFallback(ctx
, R300_FALLBACK_LINE_STIPPLE
, ctx
->Line
.StippleFlag
);
1723 case GL_POINT_SMOOTH
:
1724 if (rmesa
->options
.conformance_mode
)
1725 r300SwitchFallback(ctx
, R300_FALLBACK_POINT_SMOOTH
, ctx
->Point
.SmoothFlag
);
1727 case GL_POLYGON_SMOOTH
:
1728 if (rmesa
->options
.conformance_mode
)
1729 r300SwitchFallback(ctx
, R300_FALLBACK_POLYGON_SMOOTH
, ctx
->Polygon
.SmoothFlag
);
1731 case GL_POLYGON_STIPPLE
:
1732 if (rmesa
->options
.conformance_mode
)
1733 r300SwitchFallback(ctx
, R300_FALLBACK_POLYGON_STIPPLE
, ctx
->Polygon
.StippleFlag
);
1735 case GL_POLYGON_OFFSET_POINT
:
1736 case GL_POLYGON_OFFSET_LINE
:
1737 case GL_POLYGON_OFFSET_FILL
:
1738 r300SetPolygonOffsetState(ctx
, state
);
1740 case GL_SCISSOR_TEST
:
1741 radeon_firevertices(&rmesa
->radeon
);
1742 rmesa
->radeon
.state
.scissor
.enabled
= state
;
1743 radeonUpdateScissor( ctx
);
1745 case GL_STENCIL_TEST
:
1746 r300SetStencilState(ctx
, state
);
1754 * Completely recalculates hardware state based on the Mesa state.
1756 static void r300ResetHwState(r300ContextPtr r300
)
1758 struct gl_context
*ctx
= r300
->radeon
.glCtx
;
1761 has_tcl
= r300
->options
.hw_tcl_enabled
;
1763 if (RADEON_DEBUG
& RADEON_STATE
)
1764 fprintf(stderr
, "%s\n", __FUNCTION__
);
1767 ctx
->Color
.ColorMask
[0][RCOMP
],
1768 ctx
->Color
.ColorMask
[0][GCOMP
],
1769 ctx
->Color
.ColorMask
[0][BCOMP
],
1770 ctx
->Color
.ColorMask
[0][ACOMP
]);
1772 r300Enable(ctx
, GL_DEPTH_TEST
, ctx
->Depth
.Test
);
1773 r300DepthMask(ctx
, ctx
->Depth
.Mask
);
1774 r300DepthFunc(ctx
, ctx
->Depth
.Func
);
1777 r300Enable(ctx
, GL_STENCIL_TEST
, ctx
->Stencil
._Enabled
);
1778 r300StencilMaskSeparate(ctx
, 0, ctx
->Stencil
.WriteMask
[0]);
1779 r300StencilFuncSeparate(ctx
, 0, ctx
->Stencil
.Function
[0],
1780 ctx
->Stencil
.Ref
[0], ctx
->Stencil
.ValueMask
[0]);
1781 r300StencilOpSeparate(ctx
, 0, ctx
->Stencil
.FailFunc
[0],
1782 ctx
->Stencil
.ZFailFunc
[0],
1783 ctx
->Stencil
.ZPassFunc
[0]);
1785 r300UpdateCulling(ctx
);
1787 r300SetBlendState(ctx
);
1788 r300SetLogicOpState(ctx
);
1790 r300AlphaFunc(ctx
, ctx
->Color
.AlphaFunc
, ctx
->Color
.AlphaRef
);
1791 r300Enable(ctx
, GL_ALPHA_TEST
, ctx
->Color
.AlphaEnabled
);
1793 r300
->hw
.vte
.cmd
[1] = R300_VPORT_X_SCALE_ENA
1794 | R300_VPORT_X_OFFSET_ENA
1795 | R300_VPORT_Y_SCALE_ENA
1796 | R300_VPORT_Y_OFFSET_ENA
1797 | R300_VPORT_Z_SCALE_ENA
1798 | R300_VPORT_Z_OFFSET_ENA
| R300_VTX_W0_FMT
;
1799 r300
->hw
.vte
.cmd
[2] = 0x00000008;
1801 r300
->hw
.vap_vf_max_vtx_indx
.cmd
[1] = 0x00FFFFFF;
1802 r300
->hw
.vap_vf_max_vtx_indx
.cmd
[2] = 0x00000000;
1804 #ifdef MESA_LITTLE_ENDIAN
1805 r300
->hw
.vap_cntl_status
.cmd
[1] = R300_VC_NO_SWAP
;
1807 r300
->hw
.vap_cntl_status
.cmd
[1] = R300_VC_32BIT_SWAP
;
1810 /* disable VAP/TCL on non-TCL capable chips */
1812 r300
->hw
.vap_cntl_status
.cmd
[1] |= R300_VAP_TCL_BYPASS
;
1814 r300
->hw
.vap_psc_sgn_norm_cntl
.cmd
[1] = 0xAAAAAAAA;
1816 /* XXX: Other families? */
1818 r300
->hw
.vap_clip_cntl
.cmd
[1] = R300_PS_UCP_MODE_DIST_COP
;
1820 r300
->hw
.vap_clip
.cmd
[1] = r300PackFloat32(1.0); /* X */
1821 r300
->hw
.vap_clip
.cmd
[2] = r300PackFloat32(1.0); /* X */
1822 r300
->hw
.vap_clip
.cmd
[3] = r300PackFloat32(1.0); /* Y */
1823 r300
->hw
.vap_clip
.cmd
[4] = r300PackFloat32(1.0); /* Y */
1825 switch (r300
->radeon
.radeonScreen
->chip_family
) {
1826 case CHIP_FAMILY_R300
:
1827 r300
->hw
.vap_pvs_vtx_timeout_reg
.cmd
[1] = R300_2288_R300
;
1830 r300
->hw
.vap_pvs_vtx_timeout_reg
.cmd
[1] = R300_2288_RV350
;
1835 r300
->hw
.gb_enable
.cmd
[1] = R300_GB_POINT_STUFF_ENABLE
1836 | R300_GB_LINE_STUFF_ENABLE
1837 | R300_GB_TRIANGLE_STUFF_ENABLE
;
1839 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_MSPOS_0
] = 0x66666666;
1840 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_MSPOS_1
] = 0x06666666;
1842 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_TILE_CONFIG
] =
1843 R300_GB_TILE_ENABLE
| R300_GB_TILE_SIZE_16
/*| R300_GB_SUBPIXEL_1_16*/;
1844 switch (r300
->radeon
.radeonScreen
->num_gb_pipes
) {
1847 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_TILE_CONFIG
] |=
1848 R300_GB_TILE_PIPE_COUNT_RV300
;
1851 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_TILE_CONFIG
] |=
1852 R300_GB_TILE_PIPE_COUNT_R300
;
1855 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_TILE_CONFIG
] |=
1856 R300_GB_TILE_PIPE_COUNT_R420_3P
;
1859 r300
->hw
.gb_misc
.cmd
[R300_GB_MISC_TILE_CONFIG
] |=
1860 R300_GB_TILE_PIPE_COUNT_R420
;
1864 /* XXX: Enable anti-aliasing? */
1865 r300
->hw
.gb_misc2
.cmd
[R300_GB_MISC2_AA_CONFIG
] = GB_AA_CONFIG_AA_DISABLE
;
1866 r300
->hw
.gb_misc2
.cmd
[R300_GB_MISC2_SELECT
] = 0;
1868 r300
->hw
.ga_point_s0
.cmd
[1] = r300PackFloat32(0.0);
1869 r300
->hw
.ga_point_s0
.cmd
[2] = r300PackFloat32(0.0);
1870 r300
->hw
.ga_point_s0
.cmd
[3] = r300PackFloat32(1.0);
1871 r300
->hw
.ga_point_s0
.cmd
[4] = r300PackFloat32(1.0);
1873 r300
->hw
.ga_triangle_stipple
.cmd
[1] = 0x00050005;
1875 r300PointSize(ctx
, 1.0);
1877 r300
->hw
.ga_point_minmax
.cmd
[1] = 0x18000006;
1878 r300
->hw
.ga_point_minmax
.cmd
[2] = 0x00020006;
1879 r300
->hw
.ga_point_minmax
.cmd
[3] = r300PackFloat32(1.0 / 192.0);
1881 r300LineWidth(ctx
, 1.0);
1883 r300
->hw
.ga_line_stipple
.cmd
[1] = 0;
1884 r300
->hw
.ga_line_stipple
.cmd
[2] = r300PackFloat32(0.0);
1885 r300
->hw
.ga_line_stipple
.cmd
[3] = r300PackFloat32(1.0);
1887 r300ShadeModel(ctx
, ctx
->Light
.ShadeModel
);
1889 r300PolygonMode(ctx
, GL_FRONT
, ctx
->Polygon
.FrontMode
);
1890 r300PolygonMode(ctx
, GL_BACK
, ctx
->Polygon
.BackMode
);
1891 r300
->hw
.zbias_cntl
.cmd
[1] = 0x00000000;
1893 r300PolygonOffset(ctx
, ctx
->Polygon
.OffsetFactor
,
1894 ctx
->Polygon
.OffsetUnits
);
1895 r300Enable(ctx
, GL_POLYGON_OFFSET_POINT
, ctx
->Polygon
.OffsetPoint
);
1896 r300Enable(ctx
, GL_POLYGON_OFFSET_LINE
, ctx
->Polygon
.OffsetLine
);
1897 r300Enable(ctx
, GL_POLYGON_OFFSET_FILL
, ctx
->Polygon
.OffsetFill
);
1899 r300
->hw
.su_depth_scale
.cmd
[1] = 0x4B7FFFFF;
1900 r300
->hw
.su_depth_scale
.cmd
[2] = 0x00000000;
1902 r300
->hw
.sc_hyperz
.cmd
[1] = 0x0000001C;
1903 r300
->hw
.sc_hyperz
.cmd
[2] = 0x2DA49525;
1905 r300
->hw
.sc_screendoor
.cmd
[1] = 0x00FFFFFF;
1907 r300
->hw
.us_out_fmt
.cmd
[1] = R500_OUT_FMT_C4_8
|
1908 R500_C0_SEL_B
| R500_C1_SEL_G
| R500_C2_SEL_R
| R500_C3_SEL_A
;
1909 r300
->hw
.us_out_fmt
.cmd
[2] = R500_OUT_FMT_UNUSED
|
1910 R500_C0_SEL_B
| R500_C1_SEL_G
| R500_C2_SEL_R
| R500_C3_SEL_A
;
1911 r300
->hw
.us_out_fmt
.cmd
[3] = R500_OUT_FMT_UNUSED
|
1912 R500_C0_SEL_B
| R500_C1_SEL_G
| R500_C2_SEL_R
| R500_C3_SEL_A
;
1913 r300
->hw
.us_out_fmt
.cmd
[4] = R500_OUT_FMT_UNUSED
|
1914 R500_C0_SEL_B
| R500_C1_SEL_G
| R500_C2_SEL_R
| R500_C3_SEL_A
;
1915 r300
->hw
.us_out_fmt
.cmd
[5] = R300_W_FMT_W0
| R300_W_SRC_US
;
1917 /* disable fog unit */
1918 r300
->hw
.fogs
.cmd
[R300_FOGS_STATE
] = 0;
1919 r300
->hw
.fg_depth_src
.cmd
[1] = R300_FG_DEPTH_SRC_SCAN
;
1921 r300
->hw
.rb3d_cctl
.cmd
[1] = 0;
1923 r300BlendColor(ctx
, ctx
->Color
.BlendColor
);
1925 r300
->hw
.rb3d_dither_ctl
.cmd
[1] = 0;
1926 r300
->hw
.rb3d_dither_ctl
.cmd
[2] = 0;
1927 r300
->hw
.rb3d_dither_ctl
.cmd
[3] = 0;
1928 r300
->hw
.rb3d_dither_ctl
.cmd
[4] = 0;
1929 r300
->hw
.rb3d_dither_ctl
.cmd
[5] = 0;
1930 r300
->hw
.rb3d_dither_ctl
.cmd
[6] = 0;
1931 r300
->hw
.rb3d_dither_ctl
.cmd
[7] = 0;
1932 r300
->hw
.rb3d_dither_ctl
.cmd
[8] = 0;
1933 r300
->hw
.rb3d_dither_ctl
.cmd
[9] = 0;
1935 r300
->hw
.rb3d_aaresolve_ctl
.cmd
[1] = 0;
1937 r300
->hw
.rb3d_discard_src_pixel_lte_threshold
.cmd
[1] = 0x00000000;
1938 r300
->hw
.rb3d_discard_src_pixel_lte_threshold
.cmd
[2] = 0xffffffff;
1940 r300
->hw
.zb_depthclearvalue
.cmd
[1] = 0;
1942 r300
->hw
.zstencil_format
.cmd
[2] = R300_ZTOP_DISABLE
;
1943 r300
->hw
.zstencil_format
.cmd
[3] = 0x00000003;
1944 r300
->hw
.zstencil_format
.cmd
[4] = 0x00000000;
1945 r300SetEarlyZState(ctx
);
1947 r300
->hw
.zb_zmask
.cmd
[1] = 0;
1948 r300
->hw
.zb_zmask
.cmd
[2] = 0;
1950 r300
->hw
.zb_hiz_offset
.cmd
[1] = 0;
1952 r300
->hw
.zb_hiz_pitch
.cmd
[1] = 0;
1954 r300VapCntl(r300
, 0, 0, 0);
1956 r300
->hw
.vps
.cmd
[R300_VPS_ZERO_0
] = 0;
1957 r300
->hw
.vps
.cmd
[R300_VPS_ZERO_1
] = 0;
1958 r300
->hw
.vps
.cmd
[R300_VPS_POINTSIZE
] = r300PackFloat32(1.0);
1959 r300
->hw
.vps
.cmd
[R300_VPS_ZERO_3
] = 0;
1962 r300
->radeon
.hw
.all_dirty
= GL_TRUE
;
1965 void r300UpdateShaders(r300ContextPtr rmesa
)
1967 struct gl_context
*ctx
= rmesa
->radeon
.glCtx
;
1969 /* should only happenen once, just after context is created */
1970 /* TODO: shouldn't we fallback to sw here? */
1971 if (!ctx
->FragmentProgram
._Current
) {
1972 fprintf(stderr
, "No ctx->FragmentProgram._Current!!\n");
1977 struct r300_fragment_program
*fp
;
1979 fp
= r300SelectAndTranslateFragmentShader(ctx
);
1981 r300SwitchFallback(ctx
, R300_FALLBACK_FRAGMENT_PROGRAM
, fp
->error
);
1984 if (rmesa
->options
.hw_tcl_enabled
) {
1985 struct r300_vertex_program
*vp
;
1987 vp
= r300SelectAndTranslateVertexShader(ctx
);
1989 r300SwitchFallback(ctx
, R300_FALLBACK_VERTEX_PROGRAM
, vp
->error
);
1992 r300UpdateStateParameters(ctx
, _NEW_PROGRAM
| _NEW_PROGRAM_CONSTANTS
);
1993 rmesa
->radeon
.NewGLState
= 0;
1996 static const GLfloat
*get_fragmentprogram_constant(struct gl_context
*ctx
, GLuint index
, GLfloat
* buffer
)
1998 static const GLfloat dummy
[4] = { 0, 0, 0, 0 };
1999 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
2000 struct rc_constant
* rcc
= &rmesa
->selected_fp
->code
.constants
.Constants
[index
];
2003 case RC_CONSTANT_EXTERNAL
:
2004 return ctx
->FragmentProgram
._Current
->Base
.Parameters
->ParameterValues
[rcc
->u
.External
];
2005 case RC_CONSTANT_IMMEDIATE
:
2006 return rcc
->u
.Immediate
;
2007 case RC_CONSTANT_STATE
:
2008 switch(rcc
->u
.State
[0]) {
2009 case RC_STATE_SHADOW_AMBIENT
: {
2010 const int unit
= (int) rcc
->u
.State
[1];
2011 const struct gl_texture_object
*texObj
= ctx
->Texture
.Unit
[unit
]._Current
;
2016 buffer
[3] = texObj
->Sampler
.CompareFailValue
;
2021 case RC_STATE_R300_WINDOW_DIMENSION
: {
2022 __DRIdrawable
* drawable
= radeon_get_drawable(&rmesa
->radeon
);
2023 buffer
[0] = drawable
->w
* 0.5f
; /* width*0.5 */
2024 buffer
[1] = drawable
->h
* 0.5f
; /* height*0.5 */
2025 buffer
[2] = 0.5F
; /* for moving range [-1 1] -> [0 1] */
2026 buffer
[3] = 1.0F
; /* not used */
2030 case RC_STATE_R300_TEXRECT_FACTOR
: {
2031 struct gl_texture_object
*t
=
2032 ctx
->Texture
.Unit
[rcc
->u
.State
[1]].CurrentTex
[TEXTURE_RECT_INDEX
];
2034 if (t
&& t
->Image
[0][t
->BaseLevel
]) {
2035 struct gl_texture_image
*image
=
2036 t
->Image
[0][t
->BaseLevel
];
2037 buffer
[0] = 1.0 / image
->Width2
;
2038 buffer
[1] = 1.0 / image
->Height2
;
2054 static void r300SetupPixelShader(struct gl_context
*ctx
)
2056 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
2057 struct r300_fragment_program
*fp
= rmesa
->selected_fp
;
2058 struct r300_fragment_program_code
*code
;
2061 code
= &fp
->code
.code
.r300
;
2063 R300_STATECHANGE(rmesa
, fpi
[0]);
2064 R300_STATECHANGE(rmesa
, fpi
[1]);
2065 R300_STATECHANGE(rmesa
, fpi
[2]);
2066 R300_STATECHANGE(rmesa
, fpi
[3]);
2067 rmesa
->hw
.fpi
[0].cmd
[R300_FPI_CMD_0
] = cmdpacket0(rmesa
->radeon
.radeonScreen
, R300_US_ALU_RGB_INST_0
, code
->alu
.length
);
2068 rmesa
->hw
.fpi
[1].cmd
[R300_FPI_CMD_0
] = cmdpacket0(rmesa
->radeon
.radeonScreen
, R300_US_ALU_RGB_ADDR_0
, code
->alu
.length
);
2069 rmesa
->hw
.fpi
[2].cmd
[R300_FPI_CMD_0
] = cmdpacket0(rmesa
->radeon
.radeonScreen
, R300_US_ALU_ALPHA_INST_0
, code
->alu
.length
);
2070 rmesa
->hw
.fpi
[3].cmd
[R300_FPI_CMD_0
] = cmdpacket0(rmesa
->radeon
.radeonScreen
, R300_US_ALU_ALPHA_ADDR_0
, code
->alu
.length
);
2071 for (i
= 0; i
< code
->alu
.length
; i
++) {
2072 rmesa
->hw
.fpi
[0].cmd
[R300_FPI_INSTR_0
+ i
] = code
->alu
.inst
[i
].rgb_inst
;
2073 rmesa
->hw
.fpi
[1].cmd
[R300_FPI_INSTR_0
+ i
] = code
->alu
.inst
[i
].rgb_addr
;
2074 rmesa
->hw
.fpi
[2].cmd
[R300_FPI_INSTR_0
+ i
] = code
->alu
.inst
[i
].alpha_inst
;
2075 rmesa
->hw
.fpi
[3].cmd
[R300_FPI_INSTR_0
+ i
] = code
->alu
.inst
[i
].alpha_addr
;
2078 R300_STATECHANGE(rmesa
, fp
);
2079 rmesa
->hw
.fp
.cmd
[R300_FP_CNTL0
] = code
->config
;
2080 rmesa
->hw
.fp
.cmd
[R300_FP_CNTL1
] = code
->pixsize
;
2081 rmesa
->hw
.fp
.cmd
[R300_FP_CNTL2
] = code
->code_offset
;
2082 for (i
= 0; i
< 4; i
++)
2083 rmesa
->hw
.fp
.cmd
[R300_FP_NODE0
+ i
] = code
->code_addr
[i
];
2085 R300_STATECHANGE(rmesa
, fpp
);
2086 rmesa
->hw
.fpp
.cmd
[R300_FPP_CMD_0
] = cmdpacket0(rmesa
->radeon
.radeonScreen
, R300_PFS_PARAM_0_X
, fp
->code
.constants
.Count
* 4);
2087 for (i
= 0; i
< fp
->code
.constants
.Count
; i
++) {
2089 const GLfloat
*constant
= get_fragmentprogram_constant(ctx
, i
, buffer
);
2090 rmesa
->hw
.fpp
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 0] = r300PackFloat24(constant
[0]);
2091 rmesa
->hw
.fpp
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 1] = r300PackFloat24(constant
[1]);
2092 rmesa
->hw
.fpp
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 2] = r300PackFloat24(constant
[2]);
2093 rmesa
->hw
.fpp
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 3] = r300PackFloat24(constant
[3]);
2097 #define bump_r500fp_count(ptr, new_count) do{\
2098 drm_r300_cmd_header_t* _p=((drm_r300_cmd_header_t*)(ptr));\
2099 int _nc=(new_count)/6; \
2100 assert(_nc < 256); \
2101 if(_nc>_p->r500fp.count)_p->r500fp.count=_nc;\
2104 #define bump_r500fp_const_count(ptr, new_count) do{\
2105 drm_r300_cmd_header_t* _p=((drm_r300_cmd_header_t*)(ptr));\
2106 int _nc=(new_count)/4; \
2107 assert(_nc < 256); \
2108 if(_nc>_p->r500fp.count)_p->r500fp.count=_nc;\
2111 static void r500SetupPixelShader(struct gl_context
*ctx
)
2113 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
2114 struct r300_fragment_program
*fp
= rmesa
->selected_fp
;
2116 struct r500_fragment_program_code
*code
;
2118 ((drm_r300_cmd_header_t
*) rmesa
->hw
.r500fp
.cmd
)->r500fp
.count
= 0;
2119 ((drm_r300_cmd_header_t
*) rmesa
->hw
.r500fp_const
.cmd
)->r500fp
.count
= 0;
2121 code
= &fp
->code
.code
.r500
;
2123 R300_STATECHANGE(rmesa
, fp
);
2124 rmesa
->hw
.fp
.cmd
[R500_FP_PIXSIZE
] = code
->max_temp_idx
;
2126 rmesa
->hw
.fp
.cmd
[R500_FP_CODE_ADDR
] =
2127 R500_US_CODE_START_ADDR(0) |
2128 R500_US_CODE_END_ADDR(code
->inst_end
);
2129 rmesa
->hw
.fp
.cmd
[R500_FP_CODE_RANGE
] =
2130 R500_US_CODE_RANGE_ADDR(0) |
2131 R500_US_CODE_RANGE_SIZE(code
->inst_end
);
2132 rmesa
->hw
.fp
.cmd
[R500_FP_CODE_OFFSET
] =
2133 R500_US_CODE_OFFSET_ADDR(0);
2135 R300_STATECHANGE(rmesa
, r500fp
);
2136 /* Emit our shader... */
2137 for (i
= 0; i
< code
->inst_end
+1; i
++) {
2138 rmesa
->hw
.r500fp
.cmd
[i
*6+1] = code
->inst
[i
].inst0
;
2139 rmesa
->hw
.r500fp
.cmd
[i
*6+2] = code
->inst
[i
].inst1
;
2140 rmesa
->hw
.r500fp
.cmd
[i
*6+3] = code
->inst
[i
].inst2
;
2141 rmesa
->hw
.r500fp
.cmd
[i
*6+4] = code
->inst
[i
].inst3
;
2142 rmesa
->hw
.r500fp
.cmd
[i
*6+5] = code
->inst
[i
].inst4
;
2143 rmesa
->hw
.r500fp
.cmd
[i
*6+6] = code
->inst
[i
].inst5
;
2146 bump_r500fp_count(rmesa
->hw
.r500fp
.cmd
, (code
->inst_end
+ 1) * 6);
2148 R300_STATECHANGE(rmesa
, r500fp_const
);
2149 for (i
= 0; i
< fp
->code
.constants
.Count
; i
++) {
2151 const GLfloat
*constant
= get_fragmentprogram_constant(ctx
, i
, buffer
);
2152 rmesa
->hw
.r500fp_const
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 0] = r300PackFloat32(constant
[0]);
2153 rmesa
->hw
.r500fp_const
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 1] = r300PackFloat32(constant
[1]);
2154 rmesa
->hw
.r500fp_const
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 2] = r300PackFloat32(constant
[2]);
2155 rmesa
->hw
.r500fp_const
.cmd
[R300_FPP_PARAM_0
+ 4 * i
+ 3] = r300PackFloat32(constant
[3]);
2157 bump_r500fp_const_count(rmesa
->hw
.r500fp_const
.cmd
, fp
->code
.constants
.Count
* 4);
2160 void r300SetupVAP(struct gl_context
*ctx
, GLuint InputsRead
, GLuint OutputsWritten
)
2162 r300ContextPtr rmesa
= R300_CONTEXT( ctx
);
2163 struct vertex_attribute
*attrs
= rmesa
->vbuf
.attribs
;
2164 int i
, j
, reg_count
;
2165 uint32_t *vir0
= &rmesa
->hw
.vir
[0].cmd
[1];
2166 uint32_t *vir1
= &rmesa
->hw
.vir
[1].cmd
[1];
2168 for (i
= 0; i
< R300_VIR_CMDSIZE
-1; ++i
)
2169 vir0
[i
] = vir1
[i
] = 0;
2171 for (i
= 0, j
= 0; i
< rmesa
->vbuf
.num_attribs
; ++i
) {
2174 tmp
= attrs
[i
].data_type
| (attrs
[i
].dst_loc
<< R300_DST_VEC_LOC_SHIFT
);
2175 if (attrs
[i
]._signed
)
2177 if (attrs
[i
].normalize
)
2178 tmp
|= R300_NORMALIZE
;
2181 vir0
[j
] = tmp
<< R300_DATA_TYPE_0_SHIFT
;
2182 vir1
[j
] = attrs
[i
].swizzle
| (attrs
[i
].write_mask
<< R300_WRITE_ENA_SHIFT
);
2184 vir0
[j
] |= tmp
<< R300_DATA_TYPE_1_SHIFT
;
2185 vir1
[j
] |= (attrs
[i
].swizzle
| (attrs
[i
].write_mask
<< R300_WRITE_ENA_SHIFT
)) << R300_SWIZZLE1_SHIFT
;
2190 reg_count
= (rmesa
->vbuf
.num_attribs
+ 1) >> 1;
2191 if (rmesa
->vbuf
.num_attribs
% 2 != 0) {
2192 vir0
[reg_count
-1] |= R300_LAST_VEC
<< R300_DATA_TYPE_0_SHIFT
;
2194 vir0
[reg_count
-1] |= R300_LAST_VEC
<< R300_DATA_TYPE_1_SHIFT
;
2197 R300_STATECHANGE(rmesa
, vir
[0]);
2198 R300_STATECHANGE(rmesa
, vir
[1]);
2199 R300_STATECHANGE(rmesa
, vof
);
2200 R300_STATECHANGE(rmesa
, vic
);
2202 if (rmesa
->radeon
.radeonScreen
->kernel_mm
) {
2203 rmesa
->hw
.vir
[0].cmd
[0] &= 0xC000FFFF;
2204 rmesa
->hw
.vir
[1].cmd
[0] &= 0xC000FFFF;
2205 rmesa
->hw
.vir
[0].cmd
[0] |= (reg_count
& 0x3FFF) << 16;
2206 rmesa
->hw
.vir
[1].cmd
[0] |= (reg_count
& 0x3FFF) << 16;
2208 ((drm_r300_cmd_header_t
*) rmesa
->hw
.vir
[0].cmd
)->packet0
.count
= reg_count
;
2209 ((drm_r300_cmd_header_t
*) rmesa
->hw
.vir
[1].cmd
)->packet0
.count
= reg_count
;
2212 rmesa
->hw
.vic
.cmd
[R300_VIC_CNTL_0
] = r300VAPInputCntl0(ctx
, InputsRead
);
2213 rmesa
->hw
.vic
.cmd
[R300_VIC_CNTL_1
] = r300VAPInputCntl1(ctx
, InputsRead
);
2214 rmesa
->hw
.vof
.cmd
[R300_VOF_CNTL_0
] = r300VAPOutputCntl0(ctx
, OutputsWritten
);
2215 rmesa
->hw
.vof
.cmd
[R300_VOF_CNTL_1
] = r300VAPOutputCntl1(ctx
, OutputsWritten
);
2218 void r300UpdateShaderStates(r300ContextPtr rmesa
)
2220 struct gl_context
*ctx
;
2221 ctx
= rmesa
->radeon
.glCtx
;
2223 /* should only happenen once, just after context is created */
2224 if (!ctx
->FragmentProgram
._Current
)
2227 r300SetEarlyZState(ctx
);
2229 r300SetupTextures(ctx
);
2231 rmesa
->vtbl
.SetupPixelShader(ctx
);
2233 rmesa
->vtbl
.SetupRSUnit(ctx
);
2235 if (rmesa
->options
.hw_tcl_enabled
) {
2236 r300SetupVertexProgram(rmesa
);
2240 #define EASY_US_OUT_FMT(comps, c0, c1, c2, c3) \
2241 (R500_OUT_FMT_##comps | R500_C0_SEL_##c0 | R500_C1_SEL_##c1 | \
2242 R500_C2_SEL_##c2 | R500_C3_SEL_##c3)
2243 static void r300SetupUsOutputFormat(struct gl_context
*ctx
)
2245 r300ContextPtr rmesa
= R300_CONTEXT(ctx
);
2247 struct radeon_renderbuffer
*rrb
= radeon_get_colorbuffer(&rmesa
->radeon
);
2253 switch (rrb
->base
.Format
)
2255 case MESA_FORMAT_RGBA5551
:
2256 case MESA_FORMAT_RGBA8888
:
2257 hw_format
= EASY_US_OUT_FMT(C4_8
, A
, B
, G
, R
);
2259 case MESA_FORMAT_RGB565_REV
:
2260 case MESA_FORMAT_RGBA8888_REV
:
2261 hw_format
= EASY_US_OUT_FMT(C4_8
, R
, G
, B
, A
);
2263 case MESA_FORMAT_RGB565
:
2264 case MESA_FORMAT_ARGB4444
:
2265 case MESA_FORMAT_ARGB1555
:
2266 case MESA_FORMAT_XRGB8888
:
2267 case MESA_FORMAT_ARGB8888
:
2268 hw_format
= EASY_US_OUT_FMT(C4_8
, B
, G
, R
, A
);
2270 case MESA_FORMAT_ARGB4444_REV
:
2271 case MESA_FORMAT_ARGB1555_REV
:
2272 case MESA_FORMAT_XRGB8888_REV
:
2273 case MESA_FORMAT_ARGB8888_REV
:
2274 hw_format
= EASY_US_OUT_FMT(C4_8
, A
, R
, G
, B
);
2276 case MESA_FORMAT_SRGBA8
:
2277 hw_format
= EASY_US_OUT_FMT(C4_10_GAMMA
, A
, B
, G
, R
);
2279 case MESA_FORMAT_SARGB8
:
2280 hw_format
= EASY_US_OUT_FMT(C4_10_GAMMA
, B
, G
, R
, A
);
2282 case MESA_FORMAT_SL8
:
2283 hw_format
= EASY_US_OUT_FMT(C4_10_GAMMA
, A
, A
, R
, A
);
2285 case MESA_FORMAT_A8
:
2286 hw_format
= EASY_US_OUT_FMT(C4_8
, A
, A
, A
, A
);
2288 case MESA_FORMAT_L8
:
2289 case MESA_FORMAT_I8
:
2290 hw_format
= EASY_US_OUT_FMT(C4_8
, A
, A
, R
, A
);
2293 assert(!"Unsupported format");
2298 R300_STATECHANGE(rmesa
, us_out_fmt
);
2299 rmesa
->hw
.us_out_fmt
.cmd
[1] = hw_format
;
2301 #undef EASY_US_OUT_FMT
2304 * Called by Mesa after an internal state update.
2306 static void r300InvalidateState(struct gl_context
* ctx
, GLuint new_state
)
2308 r300ContextPtr r300
= R300_CONTEXT(ctx
);
2310 _swrast_InvalidateState(ctx
, new_state
);
2311 _swsetup_InvalidateState(ctx
, new_state
);
2312 _vbo_InvalidateState(ctx
, new_state
);
2313 _tnl_InvalidateState(ctx
, new_state
);
2315 if (new_state
& _NEW_BUFFERS
) {
2316 _mesa_update_framebuffer(ctx
);
2317 /* this updates the DrawBuffer's Width/Height if it's a FBO */
2318 _mesa_update_draw_buffer_bounds(ctx
);
2320 R300_STATECHANGE(r300
, cb
);
2321 R300_STATECHANGE(r300
, zb
);
2324 if (new_state
& (_NEW_LIGHT
)) {
2325 R300_STATECHANGE(r300
, shade2
);
2326 if (ctx
->Light
.ProvokingVertex
== GL_LAST_VERTEX_CONVENTION
)
2327 r300
->hw
.shade2
.cmd
[1] |= R300_GA_COLOR_CONTROL_PROVOKING_VERTEX_LAST
;
2329 r300
->hw
.shade2
.cmd
[1] &= ~R300_GA_COLOR_CONTROL_PROVOKING_VERTEX_LAST
;
2332 if (new_state
& _NEW_BUFFERS
) {
2333 r300SetupUsOutputFormat(ctx
);
2336 r300
->radeon
.NewGLState
|= new_state
;
2340 * Calculate initial hardware state and register state functions.
2341 * Assumes that the command buffer and state atoms have been
2342 * initialized already.
2344 void r300InitState(r300ContextPtr r300
)
2346 r300ResetHwState(r300
);
2349 static void r300RenderMode(struct gl_context
* ctx
, GLenum mode
)
2351 r300SwitchFallback(ctx
, R300_FALLBACK_RENDER_MODE
, ctx
->RenderMode
!= GL_RENDER
);
2355 * Initialize driver's state callback functions
2357 void r300InitStateFuncs(radeonContextPtr radeon
, struct dd_function_table
*functions
)
2360 functions
->UpdateState
= r300InvalidateState
;
2361 functions
->AlphaFunc
= r300AlphaFunc
;
2362 functions
->BlendColor
= r300BlendColor
;
2363 functions
->BlendEquationSeparate
= r300BlendEquationSeparate
;
2364 functions
->BlendFuncSeparate
= r300BlendFuncSeparate
;
2365 functions
->Enable
= r300Enable
;
2366 functions
->ColorMask
= r300ColorMask
;
2367 functions
->DepthFunc
= r300DepthFunc
;
2368 functions
->DepthMask
= r300DepthMask
;
2369 functions
->CullFace
= r300CullFace
;
2370 functions
->FrontFace
= r300FrontFace
;
2371 functions
->ShadeModel
= r300ShadeModel
;
2372 functions
->LogicOpcode
= r300LogicOpcode
;
2374 /* ARB_point_parameters */
2375 functions
->PointParameterfv
= r300PointParameter
;
2377 /* Stencil related */
2378 functions
->StencilFuncSeparate
= r300StencilFuncSeparate
;
2379 functions
->StencilMaskSeparate
= r300StencilMaskSeparate
;
2380 functions
->StencilOpSeparate
= r300StencilOpSeparate
;
2382 /* Viewport related */
2383 functions
->Viewport
= r300Viewport
;
2384 functions
->DepthRange
= r300DepthRange
;
2385 functions
->PointSize
= r300PointSize
;
2386 functions
->LineWidth
= r300LineWidth
;
2388 functions
->PolygonOffset
= r300PolygonOffset
;
2389 functions
->PolygonMode
= r300PolygonMode
;
2391 functions
->RenderMode
= r300RenderMode
;
2393 functions
->ClipPlane
= r300ClipPlane
;
2394 functions
->Scissor
= radeonScissor
;
2396 functions
->DrawBuffer
= radeonDrawBuffer
;
2397 functions
->ReadBuffer
= radeonReadBuffer
;
2399 functions
->CopyPixels
= _mesa_meta_CopyPixels
;
2400 functions
->DrawPixels
= _mesa_meta_DrawPixels
;
2401 if (radeon
->radeonScreen
->kernel_mm
)
2402 functions
->ReadPixels
= radeonReadPixels
;
2405 void r300InitShaderFunctions(r300ContextPtr r300
)
2407 if (r300
->radeon
.radeonScreen
->chip_family
>= CHIP_FAMILY_RV515
) {
2408 r300
->vtbl
.SetupRSUnit
= r500SetupRSUnit
;
2409 r300
->vtbl
.SetupPixelShader
= r500SetupPixelShader
;
2410 r300
->vtbl
.SetupFragmentShaderTextures
= r500SetupFragmentShaderTextures
;
2412 r300
->vtbl
.SetupRSUnit
= r300SetupRSUnit
;
2413 r300
->vtbl
.SetupPixelShader
= r300SetupPixelShader
;
2414 r300
->vtbl
.SetupFragmentShaderTextures
= r300SetupFragmentShaderTextures
;