Merge branch 'mesa_7_7_branch'
[mesa.git] / src / gallium / drivers / nv10 / nv10_context.c
1 #include "draw/draw_context.h"
2 #include "pipe/p_defines.h"
3 #include "pipe/internal/p_winsys_screen.h"
4
5 #include "nv10_context.h"
6 #include "nv10_screen.h"
7
8 static void
9 nv10_flush(struct pipe_context *pipe, unsigned flags,
10 struct pipe_fence_handle **fence)
11 {
12 struct nv10_context *nv10 = nv10_context(pipe);
13 struct nv10_screen *screen = nv10->screen;
14 struct nouveau_channel *chan = screen->base.channel;
15
16 draw_flush(nv10->draw);
17
18 FIRE_RING(chan);
19 if (fence)
20 *fence = NULL;
21 }
22
23 static void
24 nv10_destroy(struct pipe_context *pipe)
25 {
26 struct nv10_context *nv10 = nv10_context(pipe);
27
28 if (nv10->draw)
29 draw_destroy(nv10->draw);
30
31 FREE(nv10);
32 }
33
34 static void nv10_init_hwctx(struct nv10_context *nv10)
35 {
36 struct nv10_screen *screen = nv10->screen;
37 struct nouveau_channel *chan = screen->base.channel;
38 struct nouveau_grobj *celsius = screen->celsius;
39 int i;
40 float projectionmatrix[16];
41
42 BEGIN_RING(chan, celsius, NV10TCL_DMA_NOTIFY, 1);
43 OUT_RING (chan, screen->sync->handle);
44 BEGIN_RING(chan, celsius, NV10TCL_DMA_IN_MEMORY0, 2);
45 OUT_RING (chan, chan->vram->handle);
46 OUT_RING (chan, chan->gart->handle);
47 BEGIN_RING(chan, celsius, NV10TCL_DMA_IN_MEMORY2, 2);
48 OUT_RING (chan, chan->vram->handle);
49 OUT_RING (chan, chan->vram->handle);
50
51 BEGIN_RING(chan, celsius, NV10TCL_NOP, 1);
52 OUT_RING (chan, 0);
53
54 BEGIN_RING(chan, celsius, NV10TCL_RT_HORIZ, 2);
55 OUT_RING (chan, 0);
56 OUT_RING (chan, 0);
57
58 BEGIN_RING(chan, celsius, NV10TCL_VIEWPORT_CLIP_HORIZ(0), 1);
59 OUT_RING (chan, (0x7ff<<16)|0x800);
60 BEGIN_RING(chan, celsius, NV10TCL_VIEWPORT_CLIP_VERT(0), 1);
61 OUT_RING (chan, (0x7ff<<16)|0x800);
62
63 for (i=1;i<8;i++) {
64 BEGIN_RING(chan, celsius, NV10TCL_VIEWPORT_CLIP_HORIZ(i), 1);
65 OUT_RING (chan, 0);
66 BEGIN_RING(chan, celsius, NV10TCL_VIEWPORT_CLIP_VERT(i), 1);
67 OUT_RING (chan, 0);
68 }
69
70 BEGIN_RING(chan, celsius, 0x290, 1);
71 OUT_RING (chan, (0x10<<16)|1);
72 BEGIN_RING(chan, celsius, 0x3f4, 1);
73 OUT_RING (chan, 0);
74
75 BEGIN_RING(chan, celsius, NV10TCL_NOP, 1);
76 OUT_RING (chan, 0);
77
78 if (nv10->screen->celsius->grclass != NV10TCL) {
79 /* For nv11, nv17 */
80 BEGIN_RING(chan, celsius, 0x120, 3);
81 OUT_RING (chan, 0);
82 OUT_RING (chan, 1);
83 OUT_RING (chan, 2);
84
85 BEGIN_RING(chan, celsius, NV10TCL_NOP, 1);
86 OUT_RING (chan, 0);
87 }
88
89 BEGIN_RING(chan, celsius, NV10TCL_NOP, 1);
90 OUT_RING (chan, 0);
91
92 /* Set state */
93 BEGIN_RING(chan, celsius, NV10TCL_FOG_ENABLE, 1);
94 OUT_RING (chan, 0);
95 BEGIN_RING(chan, celsius, NV10TCL_ALPHA_FUNC_ENABLE, 1);
96 OUT_RING (chan, 0);
97 BEGIN_RING(chan, celsius, NV10TCL_ALPHA_FUNC_FUNC, 2);
98 OUT_RING (chan, 0x207);
99 OUT_RING (chan, 0);
100 BEGIN_RING(chan, celsius, NV10TCL_TX_ENABLE(0), 2);
101 OUT_RING (chan, 0);
102 OUT_RING (chan, 0);
103
104 BEGIN_RING(chan, celsius, NV10TCL_RC_IN_ALPHA(0), 12);
105 OUT_RING (chan, 0x30141010);
106 OUT_RING (chan, 0);
107 OUT_RING (chan, 0x20040000);
108 OUT_RING (chan, 0);
109 OUT_RING (chan, 0);
110 OUT_RING (chan, 0);
111 OUT_RING (chan, 0x00000c00);
112 OUT_RING (chan, 0);
113 OUT_RING (chan, 0x00000c00);
114 OUT_RING (chan, 0x18000000);
115 OUT_RING (chan, 0x300e0300);
116 OUT_RING (chan, 0x0c091c80);
117
118 BEGIN_RING(chan, celsius, NV10TCL_BLEND_FUNC_ENABLE, 1);
119 OUT_RING (chan, 0);
120 BEGIN_RING(chan, celsius, NV10TCL_DITHER_ENABLE, 2);
121 OUT_RING (chan, 1);
122 OUT_RING (chan, 0);
123 BEGIN_RING(chan, celsius, NV10TCL_LINE_SMOOTH_ENABLE, 1);
124 OUT_RING (chan, 0);
125 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_WEIGHT_ENABLE, 2);
126 OUT_RING (chan, 0);
127 OUT_RING (chan, 0);
128 BEGIN_RING(chan, celsius, NV10TCL_BLEND_FUNC_SRC, 4);
129 OUT_RING (chan, 1);
130 OUT_RING (chan, 0);
131 OUT_RING (chan, 0);
132 OUT_RING (chan, 0x8006);
133 BEGIN_RING(chan, celsius, NV10TCL_STENCIL_MASK, 8);
134 OUT_RING (chan, 0xff);
135 OUT_RING (chan, 0x207);
136 OUT_RING (chan, 0);
137 OUT_RING (chan, 0xff);
138 OUT_RING (chan, 0x1e00);
139 OUT_RING (chan, 0x1e00);
140 OUT_RING (chan, 0x1e00);
141 OUT_RING (chan, 0x1d01);
142 BEGIN_RING(chan, celsius, NV10TCL_NORMALIZE_ENABLE, 1);
143 OUT_RING (chan, 0);
144 BEGIN_RING(chan, celsius, NV10TCL_FOG_ENABLE, 2);
145 OUT_RING (chan, 0);
146 OUT_RING (chan, 0);
147 BEGIN_RING(chan, celsius, NV10TCL_LIGHT_MODEL, 1);
148 OUT_RING (chan, 0);
149 BEGIN_RING(chan, celsius, NV10TCL_COLOR_CONTROL, 1);
150 OUT_RING (chan, 0);
151 BEGIN_RING(chan, celsius, NV10TCL_ENABLED_LIGHTS, 1);
152 OUT_RING (chan, 0);
153 BEGIN_RING(chan, celsius, NV10TCL_POLYGON_OFFSET_POINT_ENABLE, 3);
154 OUT_RING (chan, 0);
155 OUT_RING (chan, 0);
156 OUT_RING (chan, 0);
157 BEGIN_RING(chan, celsius, NV10TCL_DEPTH_FUNC, 1);
158 OUT_RING (chan, 0x201);
159 BEGIN_RING(chan, celsius, NV10TCL_DEPTH_WRITE_ENABLE, 1);
160 OUT_RING (chan, 0);
161 BEGIN_RING(chan, celsius, NV10TCL_DEPTH_TEST_ENABLE, 1);
162 OUT_RING (chan, 0);
163 BEGIN_RING(chan, celsius, NV10TCL_POLYGON_OFFSET_FACTOR, 2);
164 OUT_RING (chan, 0);
165 OUT_RING (chan, 0);
166 BEGIN_RING(chan, celsius, NV10TCL_POINT_SIZE, 1);
167 OUT_RING (chan, 8);
168 BEGIN_RING(chan, celsius, NV10TCL_POINT_PARAMETERS_ENABLE, 2);
169 OUT_RING (chan, 0);
170 OUT_RING (chan, 0);
171 BEGIN_RING(chan, celsius, NV10TCL_LINE_WIDTH, 1);
172 OUT_RING (chan, 8);
173 BEGIN_RING(chan, celsius, NV10TCL_LINE_SMOOTH_ENABLE, 1);
174 OUT_RING (chan, 0);
175 BEGIN_RING(chan, celsius, NV10TCL_POLYGON_MODE_FRONT, 2);
176 OUT_RING (chan, 0x1b02);
177 OUT_RING (chan, 0x1b02);
178 BEGIN_RING(chan, celsius, NV10TCL_CULL_FACE, 2);
179 OUT_RING (chan, 0x405);
180 OUT_RING (chan, 0x901);
181 BEGIN_RING(chan, celsius, NV10TCL_POLYGON_SMOOTH_ENABLE, 1);
182 OUT_RING (chan, 0);
183 BEGIN_RING(chan, celsius, NV10TCL_CULL_FACE_ENABLE, 1);
184 OUT_RING (chan, 0);
185 BEGIN_RING(chan, celsius, NV10TCL_TX_GEN_S(0), 8);
186 for (i=0;i<8;i++) {
187 OUT_RING (chan, 0);
188 }
189 BEGIN_RING(chan, celsius, NV10TCL_FOG_EQUATION_CONSTANT, 3);
190 OUT_RING (chan, 0x3fc00000); /* -1.50 */
191 OUT_RING (chan, 0xbdb8aa0a); /* -0.09 */
192 OUT_RING (chan, 0); /* 0.00 */
193
194 BEGIN_RING(chan, celsius, NV10TCL_NOP, 1);
195 OUT_RING (chan, 0);
196
197 BEGIN_RING(chan, celsius, NV10TCL_FOG_MODE, 2);
198 OUT_RING (chan, 0x802);
199 OUT_RING (chan, 2);
200 /* for some reason VIEW_MATRIX_ENABLE need to be 6 instead of 4 when
201 * using texturing, except when using the texture matrix
202 */
203 BEGIN_RING(chan, celsius, NV10TCL_VIEW_MATRIX_ENABLE, 1);
204 OUT_RING (chan, 6);
205 BEGIN_RING(chan, celsius, NV10TCL_COLOR_MASK, 1);
206 OUT_RING (chan, 0x01010101);
207
208 /* Set vertex component */
209 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_COL_4F_R, 4);
210 OUT_RINGf (chan, 1.0);
211 OUT_RINGf (chan, 1.0);
212 OUT_RINGf (chan, 1.0);
213 OUT_RINGf (chan, 1.0);
214 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_COL2_3F_R, 3);
215 OUT_RING (chan, 0);
216 OUT_RING (chan, 0);
217 OUT_RING (chan, 0);
218 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_NOR_3F_X, 3);
219 OUT_RING (chan, 0);
220 OUT_RING (chan, 0);
221 OUT_RINGf (chan, 1.0);
222 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_TX0_4F_S, 4);
223 OUT_RINGf (chan, 0.0);
224 OUT_RINGf (chan, 0.0);
225 OUT_RINGf (chan, 0.0);
226 OUT_RINGf (chan, 1.0);
227 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_TX1_4F_S, 4);
228 OUT_RINGf (chan, 0.0);
229 OUT_RINGf (chan, 0.0);
230 OUT_RINGf (chan, 0.0);
231 OUT_RINGf (chan, 1.0);
232 BEGIN_RING(chan, celsius, NV10TCL_VERTEX_FOG_1F, 1);
233 OUT_RINGf (chan, 0.0);
234 BEGIN_RING(chan, celsius, NV10TCL_EDGEFLAG_ENABLE, 1);
235 OUT_RING (chan, 1);
236
237 memset(projectionmatrix, 0, sizeof(projectionmatrix));
238 BEGIN_RING(chan, celsius, NV10TCL_PROJECTION_MATRIX(0), 16);
239 projectionmatrix[0*4+0] = 1.0;
240 projectionmatrix[1*4+1] = 1.0;
241 projectionmatrix[2*4+2] = 1.0;
242 projectionmatrix[3*4+3] = 1.0;
243 for (i=0;i<16;i++) {
244 OUT_RINGf (chan, projectionmatrix[i]);
245 }
246
247 BEGIN_RING(chan, celsius, NV10TCL_DEPTH_RANGE_NEAR, 2);
248 OUT_RING (chan, 0.0);
249 OUT_RINGf (chan, 16777216.0);
250
251 BEGIN_RING(chan, celsius, NV10TCL_VIEWPORT_TRANSLATE_X, 4);
252 OUT_RINGf (chan, -2048.0);
253 OUT_RINGf (chan, -2048.0);
254 OUT_RINGf (chan, 16777215.0 * 0.5);
255 OUT_RING (chan, 0);
256
257 FIRE_RING (chan);
258 }
259
260 struct pipe_context *
261 nv10_create(struct pipe_screen *pscreen, unsigned pctx_id)
262 {
263 struct nv10_screen *screen = nv10_screen(pscreen);
264 struct pipe_winsys *ws = pscreen->winsys;
265 struct nv10_context *nv10;
266 struct nouveau_winsys *nvws = screen->nvws;
267
268 nv10 = CALLOC(1, sizeof(struct nv10_context));
269 if (!nv10)
270 return NULL;
271 nv10->screen = screen;
272 nv10->pctx_id = pctx_id;
273
274 nv10->nvws = nvws;
275
276 nv10->pipe.winsys = ws;
277 nv10->pipe.screen = pscreen;
278 nv10->pipe.destroy = nv10_destroy;
279 nv10->pipe.draw_arrays = nv10_draw_arrays;
280 nv10->pipe.draw_elements = nv10_draw_elements;
281 nv10->pipe.clear = nv10_clear;
282 nv10->pipe.flush = nv10_flush;
283
284 nv10->pipe.is_texture_referenced = nouveau_is_texture_referenced;
285 nv10->pipe.is_buffer_referenced = nouveau_is_buffer_referenced;
286
287 nv10_init_surface_functions(nv10);
288 nv10_init_state_functions(nv10);
289
290 nv10->draw = draw_create();
291 assert(nv10->draw);
292 draw_set_rasterize_stage(nv10->draw, nv10_draw_vbuf_stage(nv10));
293
294 nv10_init_hwctx(nv10);
295
296 return &nv10->pipe;
297 }
298