Merge branch 'gallium-polygon-stipple'
[mesa.git] / src / gallium / drivers / nvfx / nvfx_context.h
1 #ifndef __NVFX_CONTEXT_H__
2 #define __NVFX_CONTEXT_H__
3
4 #include <stdio.h>
5
6 #include "pipe/p_context.h"
7 #include "pipe/p_defines.h"
8 #include "pipe/p_state.h"
9 #include "pipe/p_compiler.h"
10
11 #include "util/u_memory.h"
12 #include "util/u_math.h"
13 #include "util/u_inlines.h"
14 #include "util/u_double_list.h"
15
16 #include "draw/draw_vertex.h"
17 #include "util/u_blitter.h"
18
19 #include "nouveau/nouveau_winsys.h"
20 #include "nouveau/nouveau_gldefs.h"
21 #include "nouveau/nouveau_resource.h"
22 #include "nv30-40_3d.xml.h"
23 #include "nvfx_state.h"
24
25 #define NOUVEAU_ERR(fmt, args...) \
26 fprintf(stderr, "%s:%d - "fmt, __func__, __LINE__, ##args);
27 #define NOUVEAU_MSG(fmt, args...) \
28 fprintf(stderr, "nouveau: "fmt, ##args);
29
30 #include "nvfx_screen.h"
31
32 #define NVFX_NEW_BLEND (1 << 0)
33 #define NVFX_NEW_RAST (1 << 1)
34 #define NVFX_NEW_ZSA (1 << 2)
35 #define NVFX_NEW_SAMPLER (1 << 3)
36 #define NVFX_NEW_FB (1 << 4)
37 #define NVFX_NEW_STIPPLE (1 << 5)
38 #define NVFX_NEW_SCISSOR (1 << 6)
39 #define NVFX_NEW_VIEWPORT (1 << 7)
40 #define NVFX_NEW_BCOL (1 << 8)
41 #define NVFX_NEW_VERTPROG (1 << 9)
42 #define NVFX_NEW_FRAGPROG (1 << 10)
43 #define NVFX_NEW_ARRAYS (1 << 11)
44 #define NVFX_NEW_UCP (1 << 12)
45 #define NVFX_NEW_SR (1 << 13)
46 #define NVFX_NEW_VERTCONST (1 << 14)
47 #define NVFX_NEW_FRAGCONST (1 << 15)
48 #define NVFX_NEW_INDEX (1 << 16)
49 #define NVFX_NEW_SPRITE (1 << 17)
50
51 #define NVFX_RELOCATE_FRAMEBUFFER (1 << 0)
52 #define NVFX_RELOCATE_FRAGTEX (1 << 1)
53 #define NVFX_RELOCATE_FRAGPROG (1 << 2)
54 #define NVFX_RELOCATE_VTXBUF (1 << 3)
55 #define NVFX_RELOCATE_IDXBUF (1 << 4)
56 #define NVFX_RELOCATE_ALL 0x1f
57
58 struct nvfx_rasterizer_state {
59 struct pipe_rasterizer_state pipe;
60 unsigned sb_len;
61 uint32_t sb[34];
62 };
63
64 struct nvfx_zsa_state {
65 struct pipe_depth_stencil_alpha_state pipe;
66 unsigned sb_len;
67 uint32_t sb[24];
68 };
69
70 struct nvfx_blend_state {
71 struct pipe_blend_state pipe;
72 unsigned sb_len;
73 uint32_t sb[13];
74 };
75
76
77 struct nvfx_state {
78 unsigned scissor_enabled;
79 unsigned fp_samplers;
80 unsigned render_temps;
81 };
82
83 struct nvfx_per_vertex_element {
84 unsigned idx;
85 unsigned vertex_buffer_index;
86 unsigned src_offset;
87 };
88
89 struct nvfx_low_frequency_element {
90 unsigned idx;
91 unsigned vertex_buffer_index;
92 unsigned src_offset;
93 void (*fetch_rgba_float)(float *dst, const uint8_t *src, unsigned i, unsigned j);
94 unsigned ncomp;
95 };
96
97 struct nvfx_per_instance_element {
98 struct nvfx_low_frequency_element base;
99 unsigned instance_divisor;
100 };
101
102 struct nvfx_per_vertex_buffer_info
103 {
104 unsigned vertex_buffer_index;
105 unsigned per_vertex_size;
106 };
107
108 struct nvfx_vtxelt_state {
109 struct pipe_vertex_element pipe[16];
110 unsigned num_elements;
111 unsigned vtxfmt[16];
112
113 unsigned num_per_vertex_buffer_infos;
114 struct nvfx_per_vertex_buffer_info per_vertex_buffer_info[16];
115
116 unsigned num_per_vertex;
117 struct nvfx_per_vertex_element per_vertex[16];
118
119 unsigned num_per_instance;
120 struct nvfx_per_instance_element per_instance[16];
121
122 unsigned num_constant;
123 struct nvfx_low_frequency_element constant[16];
124
125 boolean needs_translate;
126 struct translate* translate;
127
128 unsigned vertex_length;
129 unsigned max_vertices_per_packet;
130 };
131
132 struct nvfx_render_target {
133 struct nouveau_bo* bo;
134 unsigned offset;
135 unsigned pitch;
136 };
137
138 struct nvfx_context {
139 struct pipe_context pipe;
140
141 struct nouveau_winsys *nvws;
142 struct nvfx_screen *screen;
143
144 unsigned is_nv4x; /* either 0 or ~0 */
145 unsigned use_nv4x; /* either 0 or ~0 */
146 boolean use_vp_clipping;
147
148 struct draw_context *draw;
149 /* one is for user-requested operations, the other is for temporary copying inside them */
150 struct blitter_context* blitter[2];
151 unsigned blitters_in_use;
152 struct list_head render_cache;
153
154 /* HW state derived from pipe states */
155 struct nvfx_state state;
156
157 enum {
158 HW, SWTNL, SWRAST
159 } render_mode;
160 unsigned fallback_swtnl;
161
162 /* Context state */
163 unsigned dirty, draw_dirty;
164 struct pipe_scissor_state scissor;
165 unsigned stipple[32];
166 struct pipe_clip_state clip;
167 struct nvfx_pipe_vertex_program *vertprog;
168 struct nvfx_pipe_fragment_program *fragprog;
169 struct pipe_resource *constbuf[PIPE_SHADER_TYPES];
170 unsigned constbuf_nr[PIPE_SHADER_TYPES];
171 struct nvfx_rasterizer_state *rasterizer;
172 struct nvfx_zsa_state *zsa;
173 struct nvfx_blend_state *blend;
174 struct pipe_blend_color blend_colour;
175 struct pipe_stencil_ref stencil_ref;
176 struct pipe_viewport_state viewport;
177 struct pipe_framebuffer_state framebuffer;
178 struct pipe_index_buffer idxbuf;
179 struct nvfx_sampler_state *tex_sampler[PIPE_MAX_SAMPLERS];
180 struct pipe_sampler_view *fragment_sampler_views[PIPE_MAX_SAMPLERS];
181 struct nvfx_pipe_fragment_program* dummy_fs;
182 struct pipe_query* query;
183
184 unsigned nr_samplers;
185 unsigned nr_textures;
186 unsigned dirty_samplers;
187 struct pipe_vertex_buffer vtxbuf[PIPE_MAX_ATTRIBS];
188 unsigned vtxbuf_nr;
189 struct nvfx_vtxelt_state *vtxelt;
190 int base_vertex;
191 boolean use_index_buffer;
192 /* -1 = hardware input setup is outdated
193 * 0 = hardware input setup is for inline vertices
194 * 1 = hardware input setup is for hardware vertices
195 */
196 int use_vertex_buffers;
197
198 unsigned hw_vtxelt_nr;
199 unsigned hw_samplers;
200 uint32_t hw_txf[16];
201 struct nvfx_render_target hw_rt[4];
202 struct nvfx_render_target hw_zeta;
203 int hw_pointsprite_control;
204 int hw_vp_output;
205 struct nvfx_fragment_program* hw_fragprog;
206 struct nvfx_vertex_program* hw_vertprog;
207
208 unsigned relocs_needed;
209 };
210
211 static INLINE struct nvfx_context *
212 nvfx_context(struct pipe_context *pipe)
213 {
214 return (struct nvfx_context *)pipe;
215 }
216
217 extern struct nvfx_state_entry nvfx_state_blend;
218 extern struct nvfx_state_entry nvfx_state_blend_colour;
219 extern struct nvfx_state_entry nvfx_state_fragprog;
220 extern struct nvfx_state_entry nvfx_state_fragtex;
221 extern struct nvfx_state_entry nvfx_state_framebuffer;
222 extern struct nvfx_state_entry nvfx_state_rasterizer;
223 extern struct nvfx_state_entry nvfx_state_scissor;
224 extern struct nvfx_state_entry nvfx_state_sr;
225 extern struct nvfx_state_entry nvfx_state_stipple;
226 extern struct nvfx_state_entry nvfx_state_vbo;
227 extern struct nvfx_state_entry nvfx_state_vertprog;
228 extern struct nvfx_state_entry nvfx_state_viewport;
229 extern struct nvfx_state_entry nvfx_state_vtxfmt;
230 extern struct nvfx_state_entry nvfx_state_zsa;
231
232 extern void nvfx_init_query_functions(struct nvfx_context *nvfx);
233 extern void nvfx_init_surface_functions(struct nvfx_context *nvfx);
234
235 /* nvfx_context.c */
236 struct pipe_context *
237 nvfx_create(struct pipe_screen *pscreen, void *priv);
238
239 /* nvfx_clear.c */
240 extern void nvfx_clear(struct pipe_context *pipe, unsigned buffers,
241 const float *rgba, double depth, unsigned stencil);
242
243 /* nvfx_draw.c */
244 extern struct draw_stage *nvfx_draw_render_stage(struct nvfx_context *nvfx);
245 extern void nvfx_draw_vbo_swtnl(struct pipe_context *pipe, const struct pipe_draw_info* info);
246 extern void nvfx_vtxfmt_validate(struct nvfx_context *nvfx);
247
248 /* nvfx_fb.c */
249 extern int nvfx_framebuffer_prepare(struct nvfx_context *nvfx);
250 extern void nvfx_framebuffer_validate(struct nvfx_context *nvfx, unsigned prepare_result);
251 void
252 nvfx_framebuffer_relocate(struct nvfx_context *nvfx);
253
254 /* nvfx_fragprog.c */
255 extern void nvfx_fragprog_destroy(struct nvfx_context *,
256 struct nvfx_fragment_program *);
257 extern void nvfx_fragprog_validate(struct nvfx_context *nvfx);
258 extern void nvfx_fragprog_relocate(struct nvfx_context *nvfx);
259 extern void nvfx_init_fragprog_functions(struct nvfx_context *nvfx);
260
261 /* nvfx_fragtex.c */
262 extern void nvfx_init_sampling_functions(struct nvfx_context *nvfx);
263 extern void nvfx_fragtex_validate(struct nvfx_context *nvfx);
264 extern void nvfx_fragtex_relocate(struct nvfx_context *nvfx);
265
266 struct nvfx_sampler_view;
267
268 /* nv30_fragtex.c */
269 extern void
270 nv30_sampler_state_init(struct pipe_context *pipe,
271 struct nvfx_sampler_state *ps,
272 const struct pipe_sampler_state *cso);
273 extern void
274 nv30_sampler_view_init(struct pipe_context *pipe,
275 struct nvfx_sampler_view *sv);
276 extern void nv30_fragtex_set(struct nvfx_context *nvfx, int unit);
277
278 /* nv40_fragtex.c */
279 extern void
280 nv40_sampler_state_init(struct pipe_context *pipe,
281 struct nvfx_sampler_state *ps,
282 const struct pipe_sampler_state *cso);
283 extern void
284 nv40_sampler_view_init(struct pipe_context *pipe,
285 struct nvfx_sampler_view *sv);
286 extern void nv40_fragtex_set(struct nvfx_context *nvfx, int unit);
287
288 /* nvfx_state.c */
289 extern void nvfx_init_state_functions(struct nvfx_context *nvfx);
290 extern void nvfx_state_scissor_validate(struct nvfx_context *nvfx);
291 extern void nvfx_state_stipple_validate(struct nvfx_context *nvfx);
292 extern void nvfx_state_blend_validate(struct nvfx_context *nvfx);
293 extern void nvfx_state_blend_colour_validate(struct nvfx_context *nvfx);
294 extern void nvfx_state_viewport_validate(struct nvfx_context *nvfx);
295 extern void nvfx_state_rasterizer_validate(struct nvfx_context *nvfx);
296 extern void nvfx_state_sr_validate(struct nvfx_context *nvfx);
297 extern void nvfx_state_zsa_validate(struct nvfx_context *nvfx);
298
299 /* nvfx_state_emit.c */
300 extern void nvfx_state_relocate(struct nvfx_context *nvfx, unsigned relocs);
301 extern boolean nvfx_state_validate(struct nvfx_context *nvfx);
302 extern boolean nvfx_state_validate_swtnl(struct nvfx_context *nvfx);
303
304 static inline void
305 nvfx_state_emit(struct nvfx_context *nvfx)
306 {
307 unsigned relocs = NVFX_RELOCATE_FRAMEBUFFER | NVFX_RELOCATE_FRAGTEX | NVFX_RELOCATE_FRAGPROG;
308 if (nvfx->render_mode == HW)
309 {
310 relocs |= NVFX_RELOCATE_VTXBUF;
311 if(nvfx->use_index_buffer)
312 relocs |= NVFX_RELOCATE_IDXBUF;
313 }
314
315 relocs &= nvfx->relocs_needed;
316 if(relocs)
317 nvfx_state_relocate(nvfx, relocs);
318 }
319
320 /* nvfx_transfer.c */
321 extern void nvfx_init_transfer_functions(struct pipe_context *pipe);
322
323 /* nvfx_vbo.c */
324 extern boolean nvfx_vbo_validate(struct nvfx_context *nvfx);
325 extern void nvfx_vbo_swtnl_validate(struct nvfx_context *nvfx);
326 extern void nvfx_vbo_relocate(struct nvfx_context *nvfx);
327 extern void nvfx_idxbuf_validate(struct nvfx_context* nvfx);
328 extern void nvfx_idxbuf_relocate(struct nvfx_context* nvfx);
329 extern void nvfx_draw_vbo(struct pipe_context *pipe,
330 const struct pipe_draw_info *info);
331 extern void nvfx_init_vbo_functions(struct nvfx_context *nvfx);
332 extern unsigned nvfx_vertex_formats[];
333
334 /* nvfx_vertprog.c */
335 extern boolean nvfx_vertprog_validate(struct nvfx_context *nvfx);
336 extern void nvfx_vertprog_destroy(struct nvfx_context *,
337 struct nvfx_vertex_program *);
338 extern void nvfx_init_vertprog_functions(struct nvfx_context *nvfx);
339
340 /* nvfx_push.c */
341 extern void nvfx_push_vbo(struct pipe_context *pipe, const struct pipe_draw_info *info);
342
343 static inline void nvfx_emit_vtx_attr(struct nouveau_channel* chan,
344 struct nouveau_grobj *eng3d, unsigned attrib, const float* v,
345 unsigned ncomp)
346 {
347 switch (ncomp) {
348 case 4:
349 BEGIN_RING(chan, eng3d, NV30_3D_VTX_ATTR_4F_X(attrib), 4);
350 OUT_RING(chan, fui(v[0]));
351 OUT_RING(chan, fui(v[1]));
352 OUT_RING(chan, fui(v[2]));
353 OUT_RING(chan, fui(v[3]));
354 break;
355 case 3:
356 BEGIN_RING(chan, eng3d, NV30_3D_VTX_ATTR_3F_X(attrib), 3);
357 OUT_RING(chan, fui(v[0]));
358 OUT_RING(chan, fui(v[1]));
359 OUT_RING(chan, fui(v[2]));
360 break;
361 case 2:
362 BEGIN_RING(chan, eng3d, NV30_3D_VTX_ATTR_2F_X(attrib), 2);
363 OUT_RING(chan, fui(v[0]));
364 OUT_RING(chan, fui(v[1]));
365 break;
366 case 1:
367 BEGIN_RING(chan, eng3d, NV30_3D_VTX_ATTR_1F(attrib), 1);
368 OUT_RING(chan, fui(v[0]));
369 break;
370 }
371 }
372
373 #endif