1 #include "nv10_context.h"
2 #include "nv10_state.h"
4 static void nv10_state_emit_blend(struct nv10_context
* nv10
)
6 struct nv10_blend_state
*b
= nv10
->blend
;
7 struct nv10_screen
*screen
= nv10
->screen
;
8 struct nouveau_channel
*chan
= screen
->base
.channel
;
9 struct nouveau_grobj
*celsius
= screen
->celsius
;
11 BEGIN_RING(chan
, celsius
, NV10TCL_DITHER_ENABLE
, 1);
12 OUT_RING (chan
, b
->d_enable
);
14 BEGIN_RING(chan
, celsius
, NV10TCL_BLEND_FUNC_ENABLE
, 3);
15 OUT_RING (chan
, b
->b_enable
);
16 OUT_RING (chan
, b
->b_srcfunc
);
17 OUT_RING (chan
, b
->b_dstfunc
);
19 BEGIN_RING(chan
, celsius
, NV10TCL_COLOR_MASK
, 1);
20 OUT_RING (chan
, b
->c_mask
);
23 static void nv10_state_emit_blend_color(struct nv10_context
* nv10
)
25 struct pipe_blend_color
*c
= nv10
->blend_color
;
26 struct nv10_screen
*screen
= nv10
->screen
;
27 struct nouveau_channel
*chan
= screen
->base
.channel
;
28 struct nouveau_grobj
*celsius
= screen
->celsius
;
30 BEGIN_RING(chan
, celsius
, NV10TCL_BLEND_COLOR
, 1);
32 (float_to_ubyte(c
->color
[3]) << 24)|
33 (float_to_ubyte(c
->color
[0]) << 16)|
34 (float_to_ubyte(c
->color
[1]) << 8) |
35 (float_to_ubyte(c
->color
[2]) << 0));
38 static void nv10_state_emit_rast(struct nv10_context
* nv10
)
40 struct nv10_rasterizer_state
*r
= nv10
->rast
;
41 struct nv10_screen
*screen
= nv10
->screen
;
42 struct nouveau_channel
*chan
= screen
->base
.channel
;
43 struct nouveau_grobj
*celsius
= screen
->celsius
;
45 BEGIN_RING(chan
, celsius
, NV10TCL_SHADE_MODEL
, 2);
46 OUT_RING (chan
, r
->shade_model
);
47 OUT_RING (chan
, r
->line_width
);
50 BEGIN_RING(chan
, celsius
, NV10TCL_POINT_SIZE
, 1);
51 OUT_RING (chan
, r
->point_size
);
53 BEGIN_RING(chan
, celsius
, NV10TCL_POLYGON_MODE_FRONT
, 2);
54 OUT_RING (chan
, r
->poly_mode_front
);
55 OUT_RING (chan
, r
->poly_mode_back
);
58 BEGIN_RING(chan
, celsius
, NV10TCL_CULL_FACE
, 2);
59 OUT_RING (chan
, r
->cull_face
);
60 OUT_RING (chan
, r
->front_face
);
62 BEGIN_RING(chan
, celsius
, NV10TCL_LINE_SMOOTH_ENABLE
, 2);
63 OUT_RING (chan
, r
->line_smooth_en
);
64 OUT_RING (chan
, r
->poly_smooth_en
);
66 BEGIN_RING(chan
, celsius
, NV10TCL_CULL_FACE_ENABLE
, 1);
67 OUT_RING (chan
, r
->cull_face_en
);
70 static void nv10_state_emit_dsa(struct nv10_context
* nv10
)
72 struct nv10_depth_stencil_alpha_state
*d
= nv10
->dsa
;
73 struct nv10_screen
*screen
= nv10
->screen
;
74 struct nouveau_channel
*chan
= screen
->base
.channel
;
75 struct nouveau_grobj
*celsius
= screen
->celsius
;
77 BEGIN_RING(chan
, celsius
, NV10TCL_DEPTH_FUNC
, 1);
78 OUT_RING (chan
, d
->depth
.func
);
80 BEGIN_RING(chan
, celsius
, NV10TCL_DEPTH_WRITE_ENABLE
, 1);
81 OUT_RING (chan
, d
->depth
.write_enable
);
83 BEGIN_RING(chan
, celsius
, NV10TCL_DEPTH_TEST_ENABLE
, 1);
84 OUT_RING (chan
, d
->depth
.test_enable
);
87 BEGIN_RING(chan
, celsius
, NV10TCL_STENCIL_ENABLE
, 1);
88 OUT_RING (chan
, d
->stencil
.enable
);
89 BEGIN_RING(chan
, celsius
, NV10TCL_STENCIL_MASK
, 7);
90 OUT_RINGp (chan
, (uint32_t *)&(d
->stencil
.wmask
), 7);
93 BEGIN_RING(chan
, celsius
, NV10TCL_ALPHA_FUNC_ENABLE
, 1);
94 OUT_RING (chan
, d
->alpha
.enabled
);
96 BEGIN_RING(chan
, celsius
, NV10TCL_ALPHA_FUNC_FUNC
, 1);
97 OUT_RING (chan
, d
->alpha
.func
);
99 BEGIN_RING(chan
, celsius
, NV10TCL_ALPHA_FUNC_REF
, 1);
100 OUT_RING (chan
, d
->alpha
.ref
);
103 static void nv10_state_emit_viewport(struct nv10_context
* nv10
)
107 static void nv10_state_emit_scissor(struct nv10_context
* nv10
)
109 // XXX this is so not working
110 /* struct pipe_scissor_state *s = nv10->scissor;
111 BEGIN_RING(celsius, NV10TCL_SCISSOR_HORIZ, 2);
112 OUT_RING (((s->maxx - s->minx) << 16) | s->minx);
113 OUT_RING (((s->maxy - s->miny) << 16) | s->miny);*/
116 static void nv10_state_emit_framebuffer(struct nv10_context
* nv10
)
118 struct pipe_framebuffer_state
* fb
= nv10
->framebuffer
;
119 struct nv04_surface
*rt
, *zeta
= NULL
;
120 uint32_t rt_format
, w
, h
;
121 int colour_format
= 0, zeta_format
= 0;
122 struct nv10_miptree
*nv10mt
= 0;
124 struct nv10_screen
*screen
= nv10
->screen
;
125 struct nouveau_channel
*chan
= screen
->base
.channel
;
126 struct nouveau_grobj
*celsius
= screen
->celsius
;
128 w
= fb
->cbufs
[0]->width
;
129 h
= fb
->cbufs
[0]->height
;
130 colour_format
= fb
->cbufs
[0]->format
;
131 rt
= (struct nv04_surface
*)fb
->cbufs
[0];
135 assert(w
== fb
->zsbuf
->width
);
136 assert(h
== fb
->zsbuf
->height
);
138 w
= fb
->zsbuf
->width
;
139 h
= fb
->zsbuf
->height
;
142 zeta_format
= fb
->zsbuf
->format
;
143 zeta
= (struct nv04_surface
*)fb
->zsbuf
;
146 rt_format
= NV10TCL_RT_FORMAT_TYPE_LINEAR
;
148 switch (colour_format
) {
149 case PIPE_FORMAT_X8R8G8B8_UNORM
:
150 rt_format
|= NV10TCL_RT_FORMAT_COLOR_X8R8G8B8
;
152 case PIPE_FORMAT_A8R8G8B8_UNORM
:
154 rt_format
|= NV10TCL_RT_FORMAT_COLOR_A8R8G8B8
;
156 case PIPE_FORMAT_R5G6B5_UNORM
:
157 rt_format
|= NV10TCL_RT_FORMAT_COLOR_R5G6B5
;
164 BEGIN_RING(chan
, celsius
, NV10TCL_RT_PITCH
, 1);
165 OUT_RING (chan
, rt
->pitch
| (zeta
->pitch
<< 16));
167 BEGIN_RING(chan
, celsius
, NV10TCL_RT_PITCH
, 1);
168 OUT_RING (chan
, rt
->pitch
| (rt
->pitch
<< 16));
171 nv10mt
= (struct nv10_miptree
*)rt
->base
.texture
;
172 nv10
->rt
[0] = nv10mt
->buffer
;
176 nv10mt
= (struct nv10_miptree
*)zeta
->base
.texture
;
177 nv10
->zeta
= nv10mt
->buffer
;
180 BEGIN_RING(chan
, celsius
, NV10TCL_RT_HORIZ
, 3);
181 OUT_RING (chan
, (w
<< 16) | 0);
182 OUT_RING (chan
, (h
<< 16) | 0);
183 OUT_RING (chan
, rt_format
);
184 BEGIN_RING(chan
, celsius
, NV10TCL_VIEWPORT_CLIP_HORIZ(0), 2);
185 OUT_RING (chan
, ((w
- 1) << 16) | 0 | 0x08000800);
186 OUT_RING (chan
, ((h
- 1) << 16) | 0 | 0x08000800);
189 static void nv10_vertex_layout(struct nv10_context
*nv10
)
191 struct nv10_fragment_program
*fp
= nv10
->fragprog
.current
;
194 struct vertex_info vinfo
;
196 memset(&vinfo
, 0, sizeof(vinfo
));
198 for (i
= 0; i
< fp
->info
.num_inputs
; i
++) {
199 switch (fp
->info
.input_semantic_name
[i
]) {
200 case TGSI_SEMANTIC_POSITION
:
201 draw_emit_vertex_attr(&vinfo
, EMIT_4F
, INTERP_LINEAR
, src
++);
203 case TGSI_SEMANTIC_COLOR
:
204 draw_emit_vertex_attr(&vinfo
, EMIT_4F
, INTERP_LINEAR
, src
++);
207 case TGSI_SEMANTIC_GENERIC
:
208 draw_emit_vertex_attr(&vinfo
, EMIT_4F
, INTERP_PERSPECTIVE
, src
++);
210 case TGSI_SEMANTIC_FOG
:
211 draw_emit_vertex_attr(&vinfo
, EMIT_4F
, INTERP_PERSPECTIVE
, src
++);
215 draw_compute_vertex_size(&vinfo
);
219 nv10_emit_hw_state(struct nv10_context
*nv10
)
221 struct nv10_screen
*screen
= nv10
->screen
;
222 struct nouveau_channel
*chan
= screen
->base
.channel
;
223 struct nouveau_grobj
*celsius
= screen
->celsius
;
224 struct nouveau_bo
*rt_bo
;
227 if (nv10
->dirty
& NV10_NEW_VERTPROG
) {
228 //nv10_vertprog_bind(nv10, nv10->vertprog.current);
229 nv10
->dirty
&= ~NV10_NEW_VERTPROG
;
232 if (nv10
->dirty
& NV10_NEW_FRAGPROG
) {
233 nv10_fragprog_bind(nv10
, nv10
->fragprog
.current
);
234 /*XXX: clear NV10_NEW_FRAGPROG if no new program uploaded */
235 nv10
->dirty_samplers
|= (1<<10);
236 nv10
->dirty_samplers
= 0;
239 if (nv10
->dirty_samplers
|| (nv10
->dirty
& NV10_NEW_FRAGPROG
)) {
240 nv10_fragtex_bind(nv10
);
241 nv10
->dirty
&= ~NV10_NEW_FRAGPROG
;
244 if (nv10
->dirty
& NV10_NEW_VTXARRAYS
) {
245 nv10
->dirty
&= ~NV10_NEW_VTXARRAYS
;
246 nv10_vertex_layout(nv10
);
247 nv10_vtxbuf_bind(nv10
);
250 if (nv10
->dirty
& NV10_NEW_BLEND
) {
251 nv10
->dirty
&= ~NV10_NEW_BLEND
;
252 nv10_state_emit_blend(nv10
);
255 if (nv10
->dirty
& NV10_NEW_BLENDCOL
) {
256 nv10
->dirty
&= ~NV10_NEW_BLENDCOL
;
257 nv10_state_emit_blend_color(nv10
);
260 if (nv10
->dirty
& NV10_NEW_RAST
) {
261 nv10
->dirty
&= ~NV10_NEW_RAST
;
262 nv10_state_emit_rast(nv10
);
265 if (nv10
->dirty
& NV10_NEW_DSA
) {
266 nv10
->dirty
&= ~NV10_NEW_DSA
;
267 nv10_state_emit_dsa(nv10
);
270 if (nv10
->dirty
& NV10_NEW_VIEWPORT
) {
271 nv10
->dirty
&= ~NV10_NEW_VIEWPORT
;
272 nv10_state_emit_viewport(nv10
);
275 if (nv10
->dirty
& NV10_NEW_SCISSOR
) {
276 nv10
->dirty
&= ~NV10_NEW_SCISSOR
;
277 nv10_state_emit_scissor(nv10
);
280 if (nv10
->dirty
& NV10_NEW_FRAMEBUFFER
) {
281 nv10
->dirty
&= ~NV10_NEW_FRAMEBUFFER
;
282 nv10_state_emit_framebuffer(nv10
);
285 /* Emit relocs for every referenced buffer.
286 * This is to ensure the bufmgr has an accurate idea of how
287 * the buffer is used. This isn't very efficient, but we don't
288 * seem to take a significant performance hit. Will be improved
289 * at some point. Vertex arrays are emitted by nv10_vbo.c
293 rt_bo
= nouveau_bo(nv10
->rt
[0]);
294 // XXX figre out who's who for NV10TCL_DMA_* and fill accordingly
295 // BEGIN_RING(chan, celsius, NV10TCL_DMA_COLOR0, 1);
296 // OUT_RELOCo(chan, rt_bo, NOUVEAU_BO_VRAM | NOUVEAU_BO_WR);
297 BEGIN_RING(chan
, celsius
, NV10TCL_COLOR_OFFSET
, 1);
298 OUT_RELOCl(chan
, rt_bo
, 0, NOUVEAU_BO_VRAM
| NOUVEAU_BO_WR
);
301 struct nouveau_bo
*zeta_bo
= nouveau_bo(nv10
->zeta
);
303 // BEGIN_RING(chan, celsius, NV10TCL_DMA_ZETA, 1);
304 // OUT_RELOCo(chan, zeta_bo, NOUVEAU_BO_VRAM | NOUVEAU_BO_WR);
305 BEGIN_RING(chan
, celsius
, NV10TCL_ZETA_OFFSET
, 1);
306 OUT_RELOCl(chan
, zeta_bo
, 0, NOUVEAU_BO_VRAM
| NOUVEAU_BO_WR
);
307 /* XXX for when we allocate LMA on nv17 */
308 /* BEGIN_RING(chan, celsius, NV10TCL_LMA_DEPTH_BUFFER_OFFSET, 1);
309 OUT_RELOCl(chan, nouveau_bo(nv10->zeta + lma_offset));*/
313 BEGIN_RING(chan
, celsius
, NV10TCL_DMA_VTXBUF0
, 1);
314 OUT_RELOCo(chan
, rt_bo
, NOUVEAU_BO_VRAM
| NOUVEAU_BO_WR
);
315 BEGIN_RING(chan
, celsius
, NV10TCL_COLOR_OFFSET
, 1);
316 OUT_RELOCl(chan
, rt_bo
, 0, NOUVEAU_BO_VRAM
| NOUVEAU_BO_WR
);
319 for (i
= 0; i
< 2; i
++) {
320 if (!(nv10
->fp_samplers
& (1 << i
)))
322 struct nouveau_bo
*bo
= nouveau_bo(nv10
->tex
[i
].buffer
);
323 BEGIN_RING(chan
, celsius
, NV10TCL_TX_OFFSET(i
), 1);
324 OUT_RELOCl(chan
, bo
, 0, NOUVEAU_BO_VRAM
|
325 NOUVEAU_BO_GART
| NOUVEAU_BO_RD
);
326 BEGIN_RING(chan
, celsius
, NV10TCL_TX_FORMAT(i
), 1);
327 OUT_RELOCd(chan
, bo
, nv10
->tex
[i
].format
,
328 NOUVEAU_BO_VRAM
| NOUVEAU_BO_GART
| NOUVEAU_BO_RD
|
329 NOUVEAU_BO_OR
, NV10TCL_TX_FORMAT_DMA0
,
330 NV10TCL_TX_FORMAT_DMA1
);