1 #include "pipe/p_state.h"
2 #include "pipe/p_defines.h"
3 #include "pipe/p_util.h"
5 #include "nv40_context.h"
6 #include "nv40_state.h"
9 nv40_blend_state_create(struct pipe_context
*pipe
,
10 const struct pipe_blend_state
*cso
)
12 struct nv40_context
*nv40
= nv40_context(pipe
);
13 struct nouveau_grobj
*curie
= nv40
->hw
->curie
;
14 struct nouveau_stateobj
*so
= so_new(16, 0);
16 if (cso
->blend_enable
) {
17 so_method(so
, curie
, NV40TCL_BLEND_ENABLE
, 3);
19 so_data (so
, (nvgl_blend_func(cso
->alpha_src_factor
) << 16) |
20 nvgl_blend_func(cso
->rgb_src_factor
));
21 so_data (so
, nvgl_blend_func(cso
->alpha_dst_factor
) << 16 |
22 nvgl_blend_func(cso
->rgb_dst_factor
));
23 so_method(so
, curie
, NV40TCL_BLEND_EQUATION
, 1);
24 so_data (so
, nvgl_blend_eqn(cso
->alpha_func
) << 16 |
25 nvgl_blend_eqn(cso
->rgb_func
));
27 so_method(so
, curie
, NV40TCL_BLEND_ENABLE
, 1);
31 so_method(so
, curie
, NV40TCL_COLOR_MASK
, 1);
32 so_data (so
, (((cso
->colormask
& PIPE_MASK_A
) ? (0x01 << 24) : 0) |
33 ((cso
->colormask
& PIPE_MASK_R
) ? (0x01 << 16) : 0) |
34 ((cso
->colormask
& PIPE_MASK_G
) ? (0x01 << 8) : 0) |
35 ((cso
->colormask
& PIPE_MASK_B
) ? (0x01 << 0) : 0)));
37 if (cso
->logicop_enable
) {
38 so_method(so
, curie
, NV40TCL_COLOR_LOGIC_OP_ENABLE
, 2);
40 so_data (so
, nvgl_logicop_func(cso
->logicop_func
));
42 so_method(so
, curie
, NV40TCL_COLOR_LOGIC_OP_ENABLE
, 1);
46 so_method(so
, curie
, NV40TCL_DITHER_ENABLE
, 1);
47 so_data (so
, cso
->dither
? 1 : 0);
53 nv40_blend_state_bind(struct pipe_context
*pipe
, void *hwcso
)
55 struct nv40_context
*nv40
= nv40_context(pipe
);
57 so_ref(hwcso
, &nv40
->so_blend
);
58 nv40
->dirty
|= NV40_NEW_BLEND
;
62 nv40_blend_state_delete(struct pipe_context
*pipe
, void *hwcso
)
64 struct nouveau_stateobj
*so
= hwcso
;
70 static INLINE
unsigned
71 wrap_mode(unsigned wrap
) {
75 case PIPE_TEX_WRAP_REPEAT
:
76 ret
= NV40TCL_TEX_WRAP_S_REPEAT
;
78 case PIPE_TEX_WRAP_MIRROR_REPEAT
:
79 ret
= NV40TCL_TEX_WRAP_S_MIRRORED_REPEAT
;
81 case PIPE_TEX_WRAP_CLAMP_TO_EDGE
:
82 ret
= NV40TCL_TEX_WRAP_S_CLAMP_TO_EDGE
;
84 case PIPE_TEX_WRAP_CLAMP_TO_BORDER
:
85 ret
= NV40TCL_TEX_WRAP_S_CLAMP_TO_BORDER
;
87 case PIPE_TEX_WRAP_CLAMP
:
88 ret
= NV40TCL_TEX_WRAP_S_CLAMP
;
90 case PIPE_TEX_WRAP_MIRROR_CLAMP_TO_EDGE
:
91 ret
= NV40TCL_TEX_WRAP_S_MIRROR_CLAMP_TO_EDGE
;
93 case PIPE_TEX_WRAP_MIRROR_CLAMP_TO_BORDER
:
94 ret
= NV40TCL_TEX_WRAP_S_MIRROR_CLAMP_TO_BORDER
;
96 case PIPE_TEX_WRAP_MIRROR_CLAMP
:
97 ret
= NV40TCL_TEX_WRAP_S_MIRROR_CLAMP
;
100 NOUVEAU_ERR("unknown wrap mode: %d\n", wrap
);
101 ret
= NV40TCL_TEX_WRAP_S_REPEAT
;
105 return ret
>> NV40TCL_TEX_WRAP_S_SHIFT
;
109 nv40_sampler_state_create(struct pipe_context
*pipe
,
110 const struct pipe_sampler_state
*cso
)
112 struct nv40_sampler_state
*ps
;
115 ps
= MALLOC(sizeof(struct nv40_sampler_state
));
118 if (!cso
->normalized_coords
)
119 ps
->fmt
|= NV40TCL_TEX_FORMAT_RECT
;
121 ps
->wrap
= ((wrap_mode(cso
->wrap_s
) << NV40TCL_TEX_WRAP_S_SHIFT
) |
122 (wrap_mode(cso
->wrap_t
) << NV40TCL_TEX_WRAP_T_SHIFT
) |
123 (wrap_mode(cso
->wrap_r
) << NV40TCL_TEX_WRAP_R_SHIFT
));
126 if (cso
->max_anisotropy
>= 2.0) {
127 /* no idea, binary driver sets it, works without it.. meh.. */
128 ps
->wrap
|= (1 << 5);
130 if (cso
->max_anisotropy
>= 16.0) {
131 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_16X
;
133 if (cso
->max_anisotropy
>= 12.0) {
134 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_12X
;
136 if (cso
->max_anisotropy
>= 10.0) {
137 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_10X
;
139 if (cso
->max_anisotropy
>= 8.0) {
140 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_8X
;
142 if (cso
->max_anisotropy
>= 6.0) {
143 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_6X
;
145 if (cso
->max_anisotropy
>= 4.0) {
146 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_4X
;
148 ps
->en
|= NV40TCL_TEX_ENABLE_ANISO_2X
;
152 switch (cso
->mag_img_filter
) {
153 case PIPE_TEX_FILTER_LINEAR
:
154 filter
|= NV40TCL_TEX_FILTER_MAG_LINEAR
;
156 case PIPE_TEX_FILTER_NEAREST
:
158 filter
|= NV40TCL_TEX_FILTER_MAG_NEAREST
;
162 switch (cso
->min_img_filter
) {
163 case PIPE_TEX_FILTER_LINEAR
:
164 switch (cso
->min_mip_filter
) {
165 case PIPE_TEX_MIPFILTER_NEAREST
:
166 filter
|= NV40TCL_TEX_FILTER_MIN_LINEAR_MIPMAP_NEAREST
;
168 case PIPE_TEX_MIPFILTER_LINEAR
:
169 filter
|= NV40TCL_TEX_FILTER_MIN_LINEAR_MIPMAP_LINEAR
;
171 case PIPE_TEX_MIPFILTER_NONE
:
173 filter
|= NV40TCL_TEX_FILTER_MIN_LINEAR
;
177 case PIPE_TEX_FILTER_NEAREST
:
179 switch (cso
->min_mip_filter
) {
180 case PIPE_TEX_MIPFILTER_NEAREST
:
181 filter
|= NV40TCL_TEX_FILTER_MIN_NEAREST_MIPMAP_NEAREST
;
183 case PIPE_TEX_MIPFILTER_LINEAR
:
184 filter
|= NV40TCL_TEX_FILTER_MIN_NEAREST_MIPMAP_LINEAR
;
186 case PIPE_TEX_MIPFILTER_NONE
:
188 filter
|= NV40TCL_TEX_FILTER_MIN_NEAREST
;
199 limit
= CLAMP(cso
->lod_bias
, -16.0, 15.0);
200 ps
->filt
|= (int)(cso
->lod_bias
* 256.0) & 0x1fff;
202 limit
= CLAMP(cso
->max_lod
, 0.0, 15.0);
203 ps
->en
|= (int)(limit
* 256.0) << 7;
205 limit
= CLAMP(cso
->min_lod
, 0.0, 15.0);
206 ps
->en
|= (int)(limit
* 256.0) << 19;
210 if (cso
->compare_mode
== PIPE_TEX_COMPARE_R_TO_TEXTURE
) {
211 switch (cso
->compare_func
) {
212 case PIPE_FUNC_NEVER
:
213 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_NEVER
;
215 case PIPE_FUNC_GREATER
:
216 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_GREATER
;
218 case PIPE_FUNC_EQUAL
:
219 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_EQUAL
;
221 case PIPE_FUNC_GEQUAL
:
222 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_GEQUAL
;
225 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_LESS
;
227 case PIPE_FUNC_NOTEQUAL
:
228 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_NOTEQUAL
;
230 case PIPE_FUNC_LEQUAL
:
231 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_LEQUAL
;
233 case PIPE_FUNC_ALWAYS
:
234 ps
->wrap
|= NV40TCL_TEX_WRAP_RCOMP_ALWAYS
;
241 ps
->bcol
= ((float_to_ubyte(cso
->border_color
[3]) << 24) |
242 (float_to_ubyte(cso
->border_color
[0]) << 16) |
243 (float_to_ubyte(cso
->border_color
[1]) << 8) |
244 (float_to_ubyte(cso
->border_color
[2]) << 0));
250 nv40_sampler_state_bind(struct pipe_context
*pipe
, unsigned unit
,
253 struct nv40_context
*nv40
= nv40_context(pipe
);
254 struct nv40_sampler_state
*ps
= hwcso
;
256 nv40
->tex_sampler
[unit
] = ps
;
257 nv40
->dirty_samplers
|= (1 << unit
);
261 nv40_sampler_state_delete(struct pipe_context
*pipe
, void *hwcso
)
267 nv40_set_sampler_texture(struct pipe_context
*pipe
, unsigned unit
,
268 struct pipe_texture
*miptree
)
270 struct nv40_context
*nv40
= nv40_context(pipe
);
272 nv40
->tex_miptree
[unit
] = (struct nv40_miptree
*)miptree
;
273 nv40
->dirty_samplers
|= (1 << unit
);
277 nv40_rasterizer_state_create(struct pipe_context
*pipe
,
278 const struct pipe_rasterizer_state
*cso
)
280 struct nv40_context
*nv40
= nv40_context(pipe
);
281 struct nouveau_stateobj
*so
= so_new(32, 0);
285 * offset_cw/ccw -nohw
289 * offset_units / offset_scale
292 so_method(so
, nv40
->hw
->curie
, NV40TCL_SHADE_MODEL
, 1);
293 so_data (so
, cso
->flatshade
? NV40TCL_SHADE_MODEL_FLAT
:
294 NV40TCL_SHADE_MODEL_SMOOTH
);
296 so_method(so
, nv40
->hw
->curie
, NV40TCL_LINE_WIDTH
, 2);
297 so_data (so
, (unsigned char)(cso
->line_width
* 8.0) & 0xff);
298 so_data (so
, cso
->line_smooth
? 1 : 0);
299 so_method(so
, nv40
->hw
->curie
, NV40TCL_LINE_STIPPLE_ENABLE
, 2);
300 so_data (so
, cso
->line_stipple_enable
? 1 : 0);
301 so_data (so
, (cso
->line_stipple_pattern
<< 16) |
302 cso
->line_stipple_factor
);
304 so_method(so
, nv40
->hw
->curie
, NV40TCL_POINT_SIZE
, 1);
305 so_data (so
, fui(cso
->point_size
));
307 so_method(so
, nv40
->hw
->curie
, NV40TCL_POLYGON_MODE_FRONT
, 6);
308 if (cso
->front_winding
== PIPE_WINDING_CCW
) {
309 so_data(so
, nvgl_polygon_mode(cso
->fill_ccw
));
310 so_data(so
, nvgl_polygon_mode(cso
->fill_cw
));
311 switch (cso
->cull_mode
) {
312 case PIPE_WINDING_CCW
:
313 so_data(so
, NV40TCL_CULL_FACE_FRONT
);
315 case PIPE_WINDING_CW
:
316 so_data(so
, NV40TCL_CULL_FACE_BACK
);
318 case PIPE_WINDING_BOTH
:
319 so_data(so
, NV40TCL_CULL_FACE_FRONT_AND_BACK
);
325 so_data(so
, NV40TCL_FRONT_FACE_CCW
);
327 so_data(so
, nvgl_polygon_mode(cso
->fill_cw
));
328 so_data(so
, nvgl_polygon_mode(cso
->fill_ccw
));
329 switch (cso
->cull_mode
) {
330 case PIPE_WINDING_CCW
:
331 so_data(so
, NV40TCL_CULL_FACE_BACK
);
333 case PIPE_WINDING_CW
:
334 so_data(so
, NV40TCL_CULL_FACE_FRONT
);
336 case PIPE_WINDING_BOTH
:
337 so_data(so
, NV40TCL_CULL_FACE_FRONT_AND_BACK
);
343 so_data(so
, NV40TCL_FRONT_FACE_CW
);
345 so_data(so
, cso
->poly_smooth
? 1 : 0);
346 so_data(so
, cso
->cull_mode
!= PIPE_WINDING_NONE
? 1 : 0);
348 so_method(so
, nv40
->hw
->curie
, NV40TCL_POLYGON_STIPPLE_ENABLE
, 1);
349 so_data (so
, cso
->poly_stipple_enable
? 1 : 0);
351 so_method(so
, nv40
->hw
->curie
, NV40TCL_POINT_SPRITE
, 1);
352 if (cso
->point_sprite
) {
353 unsigned psctl
= (1 << 0), i
;
355 for (i
= 0; i
< 8; i
++) {
356 if (cso
->sprite_coord_mode
[i
] != PIPE_SPRITE_COORD_NONE
)
357 psctl
|= (1 << (8 + i
));
369 nv40_rasterizer_state_bind(struct pipe_context
*pipe
, void *hwcso
)
371 struct nv40_context
*nv40
= nv40_context(pipe
);
373 so_ref(hwcso
, &nv40
->so_rast
);
374 nv40
->dirty
|= NV40_NEW_RAST
;
378 nv40_rasterizer_state_delete(struct pipe_context
*pipe
, void *hwcso
)
380 struct nouveau_stateobj
*so
= hwcso
;
386 nv40_depth_stencil_alpha_state_create(struct pipe_context
*pipe
,
387 const struct pipe_depth_stencil_alpha_state
*cso
)
389 struct nv40_context
*nv40
= nv40_context(pipe
);
390 struct nouveau_stateobj
*so
= so_new(32, 0);
392 so_method(so
, nv40
->hw
->curie
, NV40TCL_DEPTH_FUNC
, 3);
393 so_data (so
, nvgl_comparison_op(cso
->depth
.func
));
394 so_data (so
, cso
->depth
.writemask
? 1 : 0);
395 so_data (so
, cso
->depth
.enabled
? 1 : 0);
397 so_method(so
, nv40
->hw
->curie
, NV40TCL_ALPHA_TEST_ENABLE
, 3);
398 so_data (so
, cso
->alpha
.enabled
? 1 : 0);
399 so_data (so
, nvgl_comparison_op(cso
->alpha
.func
));
400 so_data (so
, float_to_ubyte(cso
->alpha
.ref
));
402 if (cso
->stencil
[0].enabled
) {
403 so_method(so
, nv40
->hw
->curie
, NV40TCL_STENCIL_FRONT_ENABLE
, 8);
404 so_data (so
, cso
->stencil
[0].enabled
? 1 : 0);
405 so_data (so
, cso
->stencil
[0].write_mask
);
406 so_data (so
, nvgl_comparison_op(cso
->stencil
[0].func
));
407 so_data (so
, cso
->stencil
[0].ref_value
);
408 so_data (so
, cso
->stencil
[0].value_mask
);
409 so_data (so
, nvgl_stencil_op(cso
->stencil
[0].fail_op
));
410 so_data (so
, nvgl_stencil_op(cso
->stencil
[0].zfail_op
));
411 so_data (so
, nvgl_stencil_op(cso
->stencil
[0].zpass_op
));
413 so_method(so
, nv40
->hw
->curie
, NV40TCL_STENCIL_FRONT_ENABLE
, 1);
417 if (cso
->stencil
[1].enabled
) {
418 so_method(so
, nv40
->hw
->curie
, NV40TCL_STENCIL_BACK_ENABLE
, 8);
419 so_data (so
, cso
->stencil
[1].enabled
? 1 : 0);
420 so_data (so
, cso
->stencil
[1].write_mask
);
421 so_data (so
, nvgl_comparison_op(cso
->stencil
[1].func
));
422 so_data (so
, cso
->stencil
[1].ref_value
);
423 so_data (so
, cso
->stencil
[1].value_mask
);
424 so_data (so
, nvgl_stencil_op(cso
->stencil
[1].fail_op
));
425 so_data (so
, nvgl_stencil_op(cso
->stencil
[1].zfail_op
));
426 so_data (so
, nvgl_stencil_op(cso
->stencil
[1].zpass_op
));
428 so_method(so
, nv40
->hw
->curie
, NV40TCL_STENCIL_BACK_ENABLE
, 1);
436 nv40_depth_stencil_alpha_state_bind(struct pipe_context
*pipe
, void *hwcso
)
438 struct nv40_context
*nv40
= nv40_context(pipe
);
440 so_ref(hwcso
, &nv40
->so_zsa
);
441 nv40
->dirty
|= NV40_NEW_ZSA
;
445 nv40_depth_stencil_alpha_state_delete(struct pipe_context
*pipe
, void *hwcso
)
447 struct nouveau_stateobj
*so
= hwcso
;
453 nv40_vp_state_create(struct pipe_context
*pipe
,
454 const struct pipe_shader_state
*cso
)
456 struct nv40_vertex_program
*vp
;
458 vp
= CALLOC(1, sizeof(struct nv40_vertex_program
));
465 nv40_vp_state_bind(struct pipe_context
*pipe
, void *hwcso
)
467 struct nv40_context
*nv40
= nv40_context(pipe
);
468 struct nv40_vertex_program
*vp
= hwcso
;
470 nv40
->vertprog
.current
= vp
;
471 nv40
->dirty
|= NV40_NEW_VERTPROG
;
475 nv40_vp_state_delete(struct pipe_context
*pipe
, void *hwcso
)
477 struct nv40_context
*nv40
= nv40_context(pipe
);
478 struct nv40_vertex_program
*vp
= hwcso
;
480 nv40_vertprog_destroy(nv40
, vp
);
485 nv40_fp_state_create(struct pipe_context
*pipe
,
486 const struct pipe_shader_state
*cso
)
488 struct nv40_fragment_program
*fp
;
490 fp
= CALLOC(1, sizeof(struct nv40_fragment_program
));
497 nv40_fp_state_bind(struct pipe_context
*pipe
, void *hwcso
)
499 struct nv40_context
*nv40
= nv40_context(pipe
);
500 struct nv40_fragment_program
*fp
= hwcso
;
502 nv40
->fragprog
.current
= fp
;
503 nv40
->dirty
|= NV40_NEW_FRAGPROG
;
507 nv40_fp_state_delete(struct pipe_context
*pipe
, void *hwcso
)
509 struct nv40_context
*nv40
= nv40_context(pipe
);
510 struct nv40_fragment_program
*fp
= hwcso
;
512 nv40_fragprog_destroy(nv40
, fp
);
517 nv40_set_blend_color(struct pipe_context
*pipe
,
518 const struct pipe_blend_color
*bcol
)
520 struct nv40_context
*nv40
= nv40_context(pipe
);
521 struct nouveau_stateobj
*so
= so_new(2, 0);
523 so_method(so
, nv40
->hw
->curie
, NV40TCL_BLEND_COLOR
, 1);
524 so_data (so
, ((float_to_ubyte(bcol
->color
[3]) << 24) |
525 (float_to_ubyte(bcol
->color
[0]) << 16) |
526 (float_to_ubyte(bcol
->color
[1]) << 8) |
527 (float_to_ubyte(bcol
->color
[2]) << 0)));
529 so_ref(so
, &nv40
->so_bcol
);
531 nv40
->dirty
|= NV40_NEW_BCOL
;
535 nv40_set_clip_state(struct pipe_context
*pipe
,
536 const struct pipe_clip_state
*clip
)
541 nv40_set_constant_buffer(struct pipe_context
*pipe
, uint shader
, uint index
,
542 const struct pipe_constant_buffer
*buf
)
544 struct nv40_context
*nv40
= nv40_context(pipe
);
546 if (shader
== PIPE_SHADER_VERTEX
) {
547 nv40
->vertprog
.constant_buf
= buf
->buffer
;
548 nv40
->dirty
|= NV40_NEW_VERTPROG
;
550 if (shader
== PIPE_SHADER_FRAGMENT
) {
551 nv40
->fragprog
.constant_buf
= buf
->buffer
;
552 nv40
->dirty
|= NV40_NEW_FRAGPROG
;
557 nv40_set_framebuffer_state(struct pipe_context
*pipe
,
558 const struct pipe_framebuffer_state
*fb
)
560 struct nv40_context
*nv40
= nv40_context(pipe
);
561 struct pipe_surface
*rt
[4], *zeta
;
562 uint32_t rt_enable
, rt_format
, w
, h
;
563 int i
, colour_format
= 0, zeta_format
= 0;
564 struct nouveau_stateobj
*so
= so_new(64, 10);
565 unsigned rt_flags
= NOUVEAU_BO_RDWR
| NOUVEAU_BO_VRAM
;
568 for (i
= 0; i
< 4; i
++) {
573 assert(w
== fb
->cbufs
[i
]->width
);
574 assert(h
== fb
->cbufs
[i
]->height
);
575 assert(colour_format
== fb
->cbufs
[i
]->format
);
577 w
= fb
->cbufs
[i
]->width
;
578 h
= fb
->cbufs
[i
]->height
;
579 colour_format
= fb
->cbufs
[i
]->format
;
580 rt_enable
|= (NV40TCL_RT_ENABLE_COLOR0
<< i
);
581 rt
[i
] = fb
->cbufs
[i
];
585 if (rt_enable
& (NV40TCL_RT_ENABLE_COLOR1
| NV40TCL_RT_ENABLE_COLOR2
|
586 NV40TCL_RT_ENABLE_COLOR3
))
587 rt_enable
|= NV40TCL_RT_ENABLE_MRT
;
591 assert(w
== fb
->zsbuf
->width
);
592 assert(h
== fb
->zsbuf
->height
);
594 w
= fb
->zsbuf
->width
;
595 h
= fb
->zsbuf
->height
;
598 zeta_format
= fb
->zsbuf
->format
;
602 rt_format
= NV40TCL_RT_FORMAT_TYPE_LINEAR
;
604 switch (colour_format
) {
605 case PIPE_FORMAT_A8R8G8B8_UNORM
:
607 rt_format
|= NV40TCL_RT_FORMAT_COLOR_A8R8G8B8
;
609 case PIPE_FORMAT_R5G6B5_UNORM
:
610 rt_format
|= NV40TCL_RT_FORMAT_COLOR_R5G6B5
;
616 switch (zeta_format
) {
617 case PIPE_FORMAT_Z16_UNORM
:
618 rt_format
|= NV40TCL_RT_FORMAT_ZETA_Z16
;
620 case PIPE_FORMAT_Z24S8_UNORM
:
622 rt_format
|= NV40TCL_RT_FORMAT_ZETA_Z24S8
;
628 if (rt_enable
& NV40TCL_RT_ENABLE_COLOR0
) {
629 so_method(so
, nv40
->hw
->curie
, NV40TCL_DMA_COLOR0
, 1);
630 so_reloc (so
, rt
[0]->buffer
, 0, rt_flags
| NOUVEAU_BO_OR
,
631 nv40
->nvws
->channel
->vram
->handle
,
632 nv40
->nvws
->channel
->gart
->handle
);
633 so_method(so
, nv40
->hw
->curie
, NV40TCL_COLOR0_PITCH
, 2);
634 so_data (so
, rt
[0]->pitch
* rt
[0]->cpp
);
635 so_reloc (so
, rt
[0]->buffer
, rt
[0]->offset
, rt_flags
|
636 NOUVEAU_BO_LOW
, 0, 0);
639 if (rt_enable
& NV40TCL_RT_ENABLE_COLOR1
) {
640 so_method(so
, nv40
->hw
->curie
, NV40TCL_DMA_COLOR1
, 1);
641 so_reloc (so
, rt
[1]->buffer
, 0, rt_flags
| NOUVEAU_BO_OR
,
642 nv40
->nvws
->channel
->vram
->handle
,
643 nv40
->nvws
->channel
->gart
->handle
);
644 so_method(so
, nv40
->hw
->curie
, NV40TCL_COLOR1_OFFSET
, 2);
645 so_reloc (so
, rt
[1]->buffer
, rt
[1]->offset
, rt_flags
|
646 NOUVEAU_BO_LOW
, 0, 0);
647 so_data (so
, rt
[1]->pitch
* rt
[1]->cpp
);
650 if (rt_enable
& NV40TCL_RT_ENABLE_COLOR2
) {
651 so_method(so
, nv40
->hw
->curie
, NV40TCL_DMA_COLOR2
, 1);
652 so_reloc (so
, rt
[2]->buffer
, 0, rt_flags
| NOUVEAU_BO_OR
,
653 nv40
->nvws
->channel
->vram
->handle
,
654 nv40
->nvws
->channel
->gart
->handle
);
655 so_method(so
, nv40
->hw
->curie
, NV40TCL_COLOR2_OFFSET
, 1);
656 so_reloc (so
, rt
[2]->buffer
, rt
[2]->offset
, rt_flags
|
657 NOUVEAU_BO_LOW
, 0, 0);
658 so_method(so
, nv40
->hw
->curie
, NV40TCL_COLOR2_PITCH
, 1);
659 so_data (so
, rt
[2]->pitch
* rt
[2]->cpp
);
662 if (rt_enable
& NV40TCL_RT_ENABLE_COLOR3
) {
663 so_method(so
, nv40
->hw
->curie
, NV40TCL_DMA_COLOR3
, 1);
664 so_reloc (so
, rt
[3]->buffer
, 0, rt_flags
| NOUVEAU_BO_OR
,
665 nv40
->nvws
->channel
->vram
->handle
,
666 nv40
->nvws
->channel
->gart
->handle
);
667 so_method(so
, nv40
->hw
->curie
, NV40TCL_COLOR3_OFFSET
, 1);
668 so_reloc (so
, rt
[3]->buffer
, rt
[3]->offset
, rt_flags
|
669 NOUVEAU_BO_LOW
, 0, 0);
670 so_method(so
, nv40
->hw
->curie
, NV40TCL_COLOR3_PITCH
, 1);
671 so_data (so
, rt
[3]->pitch
* rt
[3]->cpp
);
675 so_method(so
, nv40
->hw
->curie
, NV40TCL_DMA_ZETA
, 1);
676 so_reloc (so
, zeta
->buffer
, 0, rt_flags
| NOUVEAU_BO_OR
,
677 nv40
->nvws
->channel
->vram
->handle
,
678 nv40
->nvws
->channel
->gart
->handle
);
679 so_method(so
, nv40
->hw
->curie
, NV40TCL_ZETA_OFFSET
, 1);
680 so_reloc (so
, zeta
->buffer
, zeta
->offset
, rt_flags
|
681 NOUVEAU_BO_LOW
, 0, 0);
682 so_method(so
, nv40
->hw
->curie
, NV40TCL_ZETA_PITCH
, 1);
683 so_data (so
, zeta
->pitch
* zeta
->cpp
);
686 so_method(so
, nv40
->hw
->curie
, NV40TCL_RT_ENABLE
, 1);
687 so_data (so
, rt_enable
);
688 so_method(so
, nv40
->hw
->curie
, NV40TCL_RT_HORIZ
, 3);
689 so_data (so
, (w
<< 16) | 0);
690 so_data (so
, (h
<< 16) | 0);
691 so_data (so
, rt_format
);
692 so_method(so
, nv40
->hw
->curie
, NV40TCL_VIEWPORT_HORIZ
, 2);
693 so_data (so
, (w
<< 16) | 0);
694 so_data (so
, (h
<< 16) | 0);
695 so_method(so
, nv40
->hw
->curie
, NV40TCL_VIEWPORT_CLIP_HORIZ(0), 2);
696 so_data (so
, ((w
- 1) << 16) | 0);
697 so_data (so
, ((h
- 1) << 16) | 0);
699 so_ref(so
, &nv40
->so_framebuffer
);
701 nv40
->dirty
|= NV40_NEW_FB
;
705 nv40_set_polygon_stipple(struct pipe_context
*pipe
,
706 const struct pipe_poly_stipple
*stipple
)
708 struct nv40_context
*nv40
= nv40_context(pipe
);
709 struct nouveau_stateobj
*so
= so_new(33, 0);
712 so_method(so
, nv40
->hw
->curie
, NV40TCL_POLYGON_STIPPLE_PATTERN(0), 32);
713 for (i
= 0; i
< 32; i
++)
714 so_data(so
, stipple
->stipple
[i
]);
716 so_ref(so
, &nv40
->so_stipple
);
718 nv40
->dirty
|= NV40_NEW_STIPPLE
;
722 nv40_set_scissor_state(struct pipe_context
*pipe
,
723 const struct pipe_scissor_state
*s
)
725 struct nv40_context
*nv40
= nv40_context(pipe
);
726 struct nouveau_stateobj
*so
= so_new(3, 0);
728 so_method(so
, nv40
->hw
->curie
, NV40TCL_SCISSOR_HORIZ
, 2);
729 so_data (so
, ((s
->maxx
- s
->minx
) << 16) | s
->minx
);
730 so_data (so
, ((s
->maxy
- s
->miny
) << 16) | s
->miny
);
732 so_ref(so
, &nv40
->so_scissor
);
734 nv40
->dirty
|= NV40_NEW_SCISSOR
;
738 nv40_set_viewport_state(struct pipe_context
*pipe
,
739 const struct pipe_viewport_state
*vpt
)
741 struct nv40_context
*nv40
= nv40_context(pipe
);
742 struct nouveau_stateobj
*so
= so_new(9, 0);
744 so_method(so
, nv40
->hw
->curie
, NV40TCL_VIEWPORT_TRANSLATE_X
, 8);
745 so_data (so
, fui(vpt
->translate
[0]));
746 so_data (so
, fui(vpt
->translate
[1]));
747 so_data (so
, fui(vpt
->translate
[2]));
748 so_data (so
, fui(vpt
->translate
[3]));
749 so_data (so
, fui(vpt
->scale
[0]));
750 so_data (so
, fui(vpt
->scale
[1]));
751 so_data (so
, fui(vpt
->scale
[2]));
752 so_data (so
, fui(vpt
->scale
[3]));
754 so_ref(so
, &nv40
->so_viewport
);
756 nv40
->dirty
|= NV40_NEW_VIEWPORT
;
760 nv40_set_vertex_buffer(struct pipe_context
*pipe
, unsigned index
,
761 const struct pipe_vertex_buffer
*vb
)
763 struct nv40_context
*nv40
= nv40_context(pipe
);
765 nv40
->vtxbuf
[index
] = *vb
;
767 nv40
->dirty
|= NV40_NEW_ARRAYS
;
771 nv40_set_vertex_element(struct pipe_context
*pipe
, unsigned index
,
772 const struct pipe_vertex_element
*ve
)
774 struct nv40_context
*nv40
= nv40_context(pipe
);
776 nv40
->vtxelt
[index
] = *ve
;
778 nv40
->dirty
|= NV40_NEW_ARRAYS
;
782 nv40_init_state_functions(struct nv40_context
*nv40
)
784 nv40
->pipe
.create_blend_state
= nv40_blend_state_create
;
785 nv40
->pipe
.bind_blend_state
= nv40_blend_state_bind
;
786 nv40
->pipe
.delete_blend_state
= nv40_blend_state_delete
;
788 nv40
->pipe
.create_sampler_state
= nv40_sampler_state_create
;
789 nv40
->pipe
.bind_sampler_state
= nv40_sampler_state_bind
;
790 nv40
->pipe
.delete_sampler_state
= nv40_sampler_state_delete
;
791 nv40
->pipe
.set_sampler_texture
= nv40_set_sampler_texture
;
793 nv40
->pipe
.create_rasterizer_state
= nv40_rasterizer_state_create
;
794 nv40
->pipe
.bind_rasterizer_state
= nv40_rasterizer_state_bind
;
795 nv40
->pipe
.delete_rasterizer_state
= nv40_rasterizer_state_delete
;
797 nv40
->pipe
.create_depth_stencil_alpha_state
=
798 nv40_depth_stencil_alpha_state_create
;
799 nv40
->pipe
.bind_depth_stencil_alpha_state
=
800 nv40_depth_stencil_alpha_state_bind
;
801 nv40
->pipe
.delete_depth_stencil_alpha_state
=
802 nv40_depth_stencil_alpha_state_delete
;
804 nv40
->pipe
.create_vs_state
= nv40_vp_state_create
;
805 nv40
->pipe
.bind_vs_state
= nv40_vp_state_bind
;
806 nv40
->pipe
.delete_vs_state
= nv40_vp_state_delete
;
808 nv40
->pipe
.create_fs_state
= nv40_fp_state_create
;
809 nv40
->pipe
.bind_fs_state
= nv40_fp_state_bind
;
810 nv40
->pipe
.delete_fs_state
= nv40_fp_state_delete
;
812 nv40
->pipe
.set_blend_color
= nv40_set_blend_color
;
813 nv40
->pipe
.set_clip_state
= nv40_set_clip_state
;
814 nv40
->pipe
.set_constant_buffer
= nv40_set_constant_buffer
;
815 nv40
->pipe
.set_framebuffer_state
= nv40_set_framebuffer_state
;
816 nv40
->pipe
.set_polygon_stipple
= nv40_set_polygon_stipple
;
817 nv40
->pipe
.set_scissor_state
= nv40_set_scissor_state
;
818 nv40
->pipe
.set_viewport_state
= nv40_set_viewport_state
;
820 nv40
->pipe
.set_vertex_buffer
= nv40_set_vertex_buffer
;
821 nv40
->pipe
.set_vertex_element
= nv40_set_vertex_element
;