Subversion Repositories Kolibri OS

Rev

Details | Last modification | View Log | RSS feed

Rev Author Line No. Line
5564 serge 1
 
2
3
 
4
#include "nv50/nv50_defs.xml.h"
5
6
 
7
static void
8
nvc0_validate_zcull(struct nvc0_context *nvc0)
9
{
10
    struct nouveau_pushbuf *push = nvc0->base.pushbuf;
11
    struct pipe_framebuffer_state *fb = &nvc0->framebuffer;
12
    struct nv50_surface *sf = nv50_surface(fb->zsbuf);
13
    struct nv50_miptree *mt = nv50_miptree(sf->base.texture);
14
    struct nouveau_bo *bo = mt->base.bo;
15
    uint32_t size;
16
    uint32_t offset = align(mt->total_size, 1 << 17);
17
    unsigned width, height;
18
19
 
20
21
 
22
23
 
24
    width = fb->width % 224;
25
    if (width)
26
       width = fb->width + (224 - width);
27
    else
28
       width = fb->width;
29
30
 
31
    PUSH_DATA (push, 0);
32
    BEGIN_NVC0(push, NVC0_3D(ZCULL_ADDRESS_HIGH), 2);
33
    PUSH_DATAh(push, bo->offset + offset);
34
    PUSH_DATA (push, bo->offset + offset);
35
    offset += 1 << 17;
36
    BEGIN_NVC0(push, NVC0_3D(ZCULL_LIMIT_HIGH), 2);
37
    PUSH_DATAh(push, bo->offset + offset);
38
    PUSH_DATA (push, bo->offset + offset);
39
    BEGIN_NVC0(push, SUBC_3D(0x07e0), 2);
40
    PUSH_DATA (push, size);
41
    PUSH_DATA (push, size >> 16);
42
    BEGIN_NVC0(push, SUBC_3D(0x15c8), 1); /* bits 0x3 */
43
    PUSH_DATA (push, 2);
44
    BEGIN_NVC0(push, NVC0_3D(ZCULL_WIDTH), 4);
45
    PUSH_DATA (push, width);
46
    PUSH_DATA (push, height);
47
    PUSH_DATA (push, 1);
48
    PUSH_DATA (push, 0);
49
    BEGIN_NVC0(push, NVC0_3D(ZCULL_WINDOW_OFFSET_X), 2);
50
    PUSH_DATA (push, 0);
51
    PUSH_DATA (push, 0);
52
    BEGIN_NVC0(push, NVC0_3D(ZCULL_INVALIDATE), 1);
53
    PUSH_DATA (push, 0);
54
}
55
#endif
56
57
 
58
nvc0_fb_set_null_rt(struct nouveau_pushbuf *push, unsigned i)
59
{
60
   BEGIN_NVC0(push, NVC0_3D(RT_ADDRESS_HIGH(i)), 6);
61
   PUSH_DATA (push, 0);
62
   PUSH_DATA (push, 0);
63
   PUSH_DATA (push, 64);
64
   PUSH_DATA (push, 0);
65
   PUSH_DATA (push, 0);
66
   PUSH_DATA (push, 0);
67
}
68
69
 
70
nvc0_validate_fb(struct nvc0_context *nvc0)
71
{
72
    struct nouveau_pushbuf *push = nvc0->base.pushbuf;
73
    struct pipe_framebuffer_state *fb = &nvc0->framebuffer;
74
    unsigned i, ms;
75
    unsigned ms_mode = NVC0_3D_MULTISAMPLE_MODE_MS1;
76
    boolean serialize = FALSE;
77
78
 
79
80
 
81
    PUSH_DATA (push, (076543210 << 4) | fb->nr_cbufs);
82
    BEGIN_NVC0(push, NVC0_3D(SCREEN_SCISSOR_HORIZ), 2);
83
    PUSH_DATA (push, fb->width << 16);
84
    PUSH_DATA (push, fb->height << 16);
85
86
 
87
        struct nv50_surface *sf;
88
        struct nv04_resource *res;
89
        struct nouveau_bo *bo;
90
91
 
92
           nvc0_fb_set_null_rt(push, i);
93
           continue;
94
        }
95
96
 
97
        res = nv04_resource(sf->base.texture);
98
        bo = res->bo;
99
100
 
101
        PUSH_DATAh(push, res->address + sf->offset);
102
        PUSH_DATA (push, res->address + sf->offset);
103
        if (likely(nouveau_bo_memtype(bo))) {
104
           struct nv50_miptree *mt = nv50_miptree(sf->base.texture);
105
106
 
107
108
 
109
           PUSH_DATA(push, sf->height);
110
           PUSH_DATA(push, nvc0_format_table[sf->base.format].rt);
111
           PUSH_DATA(push, (mt->layout_3d << 16) |
112
                    mt->level[sf->base.u.tex.level].tile_mode);
113
           PUSH_DATA(push, sf->base.u.tex.first_layer + sf->depth);
114
           PUSH_DATA(push, mt->layer_stride >> 2);
115
           PUSH_DATA(push, sf->base.u.tex.first_layer);
116
117
 
118
        } else {
119
           if (res->base.target == PIPE_BUFFER) {
120
              PUSH_DATA(push, 262144);
121
              PUSH_DATA(push, 1);
122
           } else {
123
              PUSH_DATA(push, nv50_miptree(sf->base.texture)->level[0].pitch);
124
              PUSH_DATA(push, sf->height);
125
           }
126
           PUSH_DATA(push, nvc0_format_table[sf->base.format].rt);
127
           PUSH_DATA(push, 1 << 12);
128
           PUSH_DATA(push, 1);
129
           PUSH_DATA(push, 0);
130
           PUSH_DATA(push, 0);
131
132
 
133
134
 
135
        }
136
137
 
138
           serialize = TRUE;
139
        res->status |=  NOUVEAU_BUFFER_STATUS_GPU_WRITING;
140
        res->status &= ~NOUVEAU_BUFFER_STATUS_GPU_READING;
141
142
 
143
        BCTX_REFN(nvc0->bufctx_3d, FB, res, WR);
144
    }
145
146
 
147
        struct nv50_miptree *mt = nv50_miptree(fb->zsbuf->texture);
148
        struct nv50_surface *sf = nv50_surface(fb->zsbuf);
149
        int unk = mt->base.base.target == PIPE_TEXTURE_2D;
150
151
 
152
        PUSH_DATAh(push, mt->base.address + sf->offset);
153
        PUSH_DATA (push, mt->base.address + sf->offset);
154
        PUSH_DATA (push, nvc0_format_table[fb->zsbuf->format].rt);
155
        PUSH_DATA (push, mt->level[sf->base.u.tex.level].tile_mode);
156
        PUSH_DATA (push, mt->layer_stride >> 2);
157
        BEGIN_NVC0(push, NVC0_3D(ZETA_ENABLE), 1);
158
        PUSH_DATA (push, 1);
159
        BEGIN_NVC0(push, NVC0_3D(ZETA_HORIZ), 3);
160
        PUSH_DATA (push, sf->width);
161
        PUSH_DATA (push, sf->height);
162
        PUSH_DATA (push, (unk << 16) |
163
                   (sf->base.u.tex.first_layer + sf->depth));
164
        BEGIN_NVC0(push, NVC0_3D(ZETA_BASE_LAYER), 1);
165
        PUSH_DATA (push, sf->base.u.tex.first_layer);
166
167
 
168
169
 
170
           serialize = TRUE;
171
        mt->base.status |=  NOUVEAU_BUFFER_STATUS_GPU_WRITING;
172
        mt->base.status &= ~NOUVEAU_BUFFER_STATUS_GPU_READING;
173
174
 
175
    } else {
176
        BEGIN_NVC0(push, NVC0_3D(ZETA_ENABLE), 1);
177
        PUSH_DATA (push, 0);
178
    }
179
180
 
181
182
 
183
    BEGIN_NVC0(push, NVC0_3D(CB_SIZE), 3);
184
    PUSH_DATA (push, 512);
185
    PUSH_DATAh(push, nvc0->screen->uniform_bo->offset + (5 << 16) + (4 << 9));
186
    PUSH_DATA (push, nvc0->screen->uniform_bo->offset + (5 << 16) + (4 << 9));
187
    BEGIN_1IC0(push, NVC0_3D(CB_POS), 1 + 2 * ms);
188
    PUSH_DATA (push, 256 + 128);
189
    for (i = 0; i < ms; i++) {
190
       float xy[2];
191
       nvc0->base.pipe.get_sample_position(&nvc0->base.pipe, ms, i, xy);
192
       PUSH_DATAf(push, xy[0]);
193
       PUSH_DATAf(push, xy[1]);
194
    }
195
196
 
197
       IMMED_NVC0(push, NVC0_3D(SERIALIZE), 0);
198
199
 
200
}
201
202
 
203
nvc0_validate_blend_colour(struct nvc0_context *nvc0)
204
{
205
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
206
207
 
208
   PUSH_DATAf(push, nvc0->blend_colour.color[0]);
209
   PUSH_DATAf(push, nvc0->blend_colour.color[1]);
210
   PUSH_DATAf(push, nvc0->blend_colour.color[2]);
211
   PUSH_DATAf(push, nvc0->blend_colour.color[3]);
212
}
213
214
 
215
nvc0_validate_stencil_ref(struct nvc0_context *nvc0)
216
{
217
    struct nouveau_pushbuf *push = nvc0->base.pushbuf;
218
    const ubyte *ref = &nvc0->stencil_ref.ref_value[0];
219
220
 
221
    IMMED_NVC0(push, NVC0_3D(STENCIL_BACK_FUNC_REF), ref[1]);
222
}
223
224
 
225
nvc0_validate_stipple(struct nvc0_context *nvc0)
226
{
227
    struct nouveau_pushbuf *push = nvc0->base.pushbuf;
228
    unsigned i;
229
230
 
231
    for (i = 0; i < 32; ++i)
232
        PUSH_DATA(push, util_bswap32(nvc0->stipple.stipple[i]));
233
}
234
235
 
236
nvc0_validate_scissor(struct nvc0_context *nvc0)
237
{
238
   int i;
239
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
240
241
 
242
      nvc0->rast->pipe.scissor == nvc0->state.scissor)
243
      return;
244
245
 
246
      nvc0->scissors_dirty = (1 << NVC0_MAX_VIEWPORTS) - 1;
247
248
 
249
250
 
251
      struct pipe_scissor_state *s = &nvc0->scissors[i];
252
      if (!(nvc0->scissors_dirty & (1 << i)))
253
         continue;
254
255
 
256
      if (nvc0->rast->pipe.scissor) {
257
         PUSH_DATA(push, (s->maxx << 16) | s->minx);
258
         PUSH_DATA(push, (s->maxy << 16) | s->miny);
259
      } else {
260
         PUSH_DATA(push, (0xffff << 16) | 0);
261
         PUSH_DATA(push, (0xffff << 16) | 0);
262
      }
263
   }
264
   nvc0->scissors_dirty = 0;
265
}
266
267
 
268
nvc0_validate_viewport(struct nvc0_context *nvc0)
269
{
270
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
271
   int x, y, w, h, i;
272
   float zmin, zmax;
273
274
 
275
      struct pipe_viewport_state *vp = &nvc0->viewports[i];
276
277
 
278
         continue;
279
280
 
281
      PUSH_DATAf(push, vp->translate[0]);
282
      PUSH_DATAf(push, vp->translate[1]);
283
      PUSH_DATAf(push, vp->translate[2]);
284
285
 
286
      PUSH_DATAf(push, vp->scale[0]);
287
      PUSH_DATAf(push, vp->scale[1]);
288
      PUSH_DATAf(push, vp->scale[2]);
289
290
 
291
292
 
293
      y = util_iround(MAX2(0.0f, vp->translate[1] - fabsf(vp->scale[1])));
294
      w = util_iround(vp->translate[0] + fabsf(vp->scale[0])) - x;
295
      h = util_iround(vp->translate[1] + fabsf(vp->scale[1])) - y;
296
297
 
298
      PUSH_DATA (push, (w << 16) | x);
299
      PUSH_DATA (push, (h << 16) | y);
300
301
 
302
      zmax = vp->translate[2] + fabsf(vp->scale[2]);
303
304
 
305
      PUSH_DATAf(push, zmin);
306
      PUSH_DATAf(push, zmax);
307
   }
308
   nvc0->viewports_dirty = 0;
309
}
310
311
 
312
nvc0_upload_uclip_planes(struct nvc0_context *nvc0, unsigned s)
313
{
314
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
315
   struct nouveau_bo *bo = nvc0->screen->uniform_bo;
316
317
 
318
   PUSH_DATA (push, 512);
319
   PUSH_DATAh(push, bo->offset + (5 << 16) + (s << 9));
320
   PUSH_DATA (push, bo->offset + (5 << 16) + (s << 9));
321
   BEGIN_1IC0(push, NVC0_3D(CB_POS), PIPE_MAX_CLIP_PLANES * 4 + 1);
322
   PUSH_DATA (push, 256);
323
   PUSH_DATAp(push, &nvc0->clip.ucp[0][0], PIPE_MAX_CLIP_PLANES * 4);
324
}
325
326
 
327
nvc0_check_program_ucps(struct nvc0_context *nvc0,
328
                        struct nvc0_program *vp, uint8_t mask)
329
{
330
   const unsigned n = util_logbase2(mask) + 1;
331
332
 
333
      return;
334
   nvc0_program_destroy(nvc0, vp);
335
336
 
337
   if (likely(vp == nvc0->vertprog))
338
      nvc0_vertprog_validate(nvc0);
339
   else
340
   if (likely(vp == nvc0->gmtyprog))
341
      nvc0_vertprog_validate(nvc0);
342
   else
343
      nvc0_tevlprog_validate(nvc0);
344
}
345
346
 
347
nvc0_validate_clip(struct nvc0_context *nvc0)
348
{
349
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
350
   struct nvc0_program *vp;
351
   unsigned stage;
352
   uint8_t clip_enable = nvc0->rast->pipe.clip_plane_enable;
353
354
 
355
      stage = 3;
356
      vp = nvc0->gmtyprog;
357
   } else
358
   if (nvc0->tevlprog) {
359
      stage = 2;
360
      vp = nvc0->tevlprog;
361
   } else {
362
      stage = 0;
363
      vp = nvc0->vertprog;
364
   }
365
366
 
367
      nvc0_check_program_ucps(nvc0, vp, clip_enable);
368
369
 
370
      if (vp->vp.num_ucps > 0 && vp->vp.num_ucps <= PIPE_MAX_CLIP_PLANES)
371
         nvc0_upload_uclip_planes(nvc0, stage);
372
373
 
374
375
 
376
      nvc0->state.clip_enable = clip_enable;
377
      IMMED_NVC0(push, NVC0_3D(CLIP_DISTANCE_ENABLE), clip_enable);
378
   }
379
   if (nvc0->state.clip_mode != vp->vp.clip_mode) {
380
      nvc0->state.clip_mode = vp->vp.clip_mode;
381
      BEGIN_NVC0(push, NVC0_3D(CLIP_DISTANCE_MODE), 1);
382
      PUSH_DATA (push, vp->vp.clip_mode);
383
   }
384
}
385
386
 
387
nvc0_validate_blend(struct nvc0_context *nvc0)
388
{
389
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
390
391
 
392
   PUSH_DATAp(push, nvc0->blend->state, nvc0->blend->size);
393
}
394
395
 
396
nvc0_validate_zsa(struct nvc0_context *nvc0)
397
{
398
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
399
400
 
401
   PUSH_DATAp(push, nvc0->zsa->state, nvc0->zsa->size);
402
}
403
404
 
405
nvc0_validate_rasterizer(struct nvc0_context *nvc0)
406
{
407
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
408
409
 
410
   PUSH_DATAp(push, nvc0->rast->state, nvc0->rast->size);
411
}
412
413
 
414
nvc0_constbufs_validate(struct nvc0_context *nvc0)
415
{
416
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
417
   unsigned s;
418
419
 
420
      while (nvc0->constbuf_dirty[s]) {
421
         int i = ffs(nvc0->constbuf_dirty[s]) - 1;
422
         nvc0->constbuf_dirty[s] &= ~(1 << i);
423
424
 
425
            struct nouveau_bo *bo = nvc0->screen->uniform_bo;
426
            const unsigned base = s << 16;
427
            const unsigned size = nvc0->constbuf[s][0].size;
428
            assert(i == 0); /* we really only want OpenGL uniforms here */
429
            assert(nvc0->constbuf[s][0].u.data);
430
431
 
432
               nvc0->state.uniform_buffer_bound[s] = align(size, 0x100);
433
434
 
435
               PUSH_DATA (push, nvc0->state.uniform_buffer_bound[s]);
436
               PUSH_DATAh(push, bo->offset + base);
437
               PUSH_DATA (push, bo->offset + base);
438
               BEGIN_NVC0(push, NVC0_3D(CB_BIND(s)), 1);
439
               PUSH_DATA (push, (0 << 4) | 1);
440
            }
441
            nvc0_cb_push(&nvc0->base, bo, NOUVEAU_BO_VRAM,
442
                         base, nvc0->state.uniform_buffer_bound[s],
443
                         0, (size + 3) / 4,
444
                         nvc0->constbuf[s][0].u.data);
445
         } else {
446
            struct nv04_resource *res =
447
               nv04_resource(nvc0->constbuf[s][i].u.buf);
448
            if (res) {
449
               BEGIN_NVC0(push, NVC0_3D(CB_SIZE), 3);
450
               PUSH_DATA (push, nvc0->constbuf[s][i].size);
451
               PUSH_DATAh(push, res->address + nvc0->constbuf[s][i].offset);
452
               PUSH_DATA (push, res->address + nvc0->constbuf[s][i].offset);
453
               BEGIN_NVC0(push, NVC0_3D(CB_BIND(s)), 1);
454
               PUSH_DATA (push, (i << 4) | 1);
455
456
 
457
            } else {
458
               BEGIN_NVC0(push, NVC0_3D(CB_BIND(s)), 1);
459
               PUSH_DATA (push, (i << 4) | 0);
460
            }
461
            if (i == 0)
462
               nvc0->state.uniform_buffer_bound[s] = 0;
463
         }
464
      }
465
   }
466
}
467
468
 
469
nvc0_validate_sample_mask(struct nvc0_context *nvc0)
470
{
471
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
472
473
 
474
   {
475
      nvc0->sample_mask & 0xffff,
476
      nvc0->sample_mask & 0xffff,
477
      nvc0->sample_mask & 0xffff,
478
      nvc0->sample_mask & 0xffff
479
   };
480
481
 
482
   PUSH_DATA (push, mask[0]);
483
   PUSH_DATA (push, mask[1]);
484
   PUSH_DATA (push, mask[2]);
485
   PUSH_DATA (push, mask[3]);
486
}
487
488
 
489
nvc0_validate_min_samples(struct nvc0_context *nvc0)
490
{
491
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
492
   int samples;
493
494
 
495
   if (samples > 1)
496
      samples |= NVC0_3D_SAMPLE_SHADING_ENABLE;
497
498
 
499
}
500
501
 
502
nvc0_validate_global_residents(struct nvc0_context *nvc0,
503
                               struct nouveau_bufctx *bctx, int bin)
504
{
505
   unsigned i;
506
507
 
508
        ++i) {
509
      struct pipe_resource *res = *util_dynarray_element(
510
         &nvc0->global_residents, struct pipe_resource *, i);
511
      if (res)
512
         nvc0_add_resident(bctx, bin, nv04_resource(res), NOUVEAU_BO_RDWR);
513
   }
514
}
515
516
 
517
nvc0_validate_derived_1(struct nvc0_context *nvc0)
518
{
519
   struct nouveau_pushbuf *push = nvc0->base.pushbuf;
520
   boolean rasterizer_discard;
521
522
 
523
      rasterizer_discard = TRUE;
524
   } else {
525
      boolean zs = nvc0->zsa &&
526
         (nvc0->zsa->pipe.depth.enabled || nvc0->zsa->pipe.stencil[0].enabled);
527
      rasterizer_discard = !zs &&
528
         (!nvc0->fragprog || !nvc0->fragprog->hdr[18]);
529
   }
530
531
 
532
      nvc0->state.rasterizer_discard = rasterizer_discard;
533
      IMMED_NVC0(push, NVC0_3D(RASTERIZE_ENABLE), !rasterizer_discard);
534
   }
535
}
536
537
 
538
nvc0_switch_pipe_context(struct nvc0_context *ctx_to)
539
{
540
   struct nvc0_context *ctx_from = ctx_to->screen->cur_ctx;
541
   unsigned s;
542
543
 
544
      ctx_to->state = ctx_from->state;
545
   else
546
      ctx_to->state = ctx_to->screen->save_state;
547
548
 
549
   ctx_to->viewports_dirty = ~0;
550
   ctx_to->scissors_dirty = ~0;
551
552
 
553
      ctx_to->samplers_dirty[s] = ~0;
554
      ctx_to->textures_dirty[s] = ~0;
555
      ctx_to->constbuf_dirty[s] = (1 << NVC0_MAX_PIPE_CONSTBUFS) - 1;
556
   }
557
558
 
559
      ctx_to->dirty &= ~(NVC0_NEW_VERTEX | NVC0_NEW_ARRAYS);
560
   if (!ctx_to->idxbuf.buffer)
561
      ctx_to->dirty &= ~NVC0_NEW_IDXBUF;
562
563
 
564
      ctx_to->dirty &= ~NVC0_NEW_VERTPROG;
565
   if (!ctx_to->fragprog)
566
      ctx_to->dirty &= ~NVC0_NEW_FRAGPROG;
567
568
 
569
      ctx_to->dirty &= ~NVC0_NEW_BLEND;
570
   if (!ctx_to->rast)
571
      ctx_to->dirty &= ~(NVC0_NEW_RASTERIZER | NVC0_NEW_SCISSOR);
572
   if (!ctx_to->zsa)
573
      ctx_to->dirty &= ~NVC0_NEW_ZSA;
574
575
 
576
}
577
578
 
579
    void (*func)(struct nvc0_context *);
580
    uint32_t states;
581
} validate_list[] = {
582
    { nvc0_validate_fb,            NVC0_NEW_FRAMEBUFFER },
583
    { nvc0_validate_blend,         NVC0_NEW_BLEND },
584
    { nvc0_validate_zsa,           NVC0_NEW_ZSA },
585
    { nvc0_validate_sample_mask,   NVC0_NEW_SAMPLE_MASK },
586
    { nvc0_validate_rasterizer,    NVC0_NEW_RASTERIZER },
587
    { nvc0_validate_blend_colour,  NVC0_NEW_BLEND_COLOUR },
588
    { nvc0_validate_stencil_ref,   NVC0_NEW_STENCIL_REF },
589
    { nvc0_validate_stipple,       NVC0_NEW_STIPPLE },
590
    { nvc0_validate_scissor,       NVC0_NEW_SCISSOR | NVC0_NEW_RASTERIZER },
591
    { nvc0_validate_viewport,      NVC0_NEW_VIEWPORT },
592
    { nvc0_vertprog_validate,      NVC0_NEW_VERTPROG },
593
    { nvc0_tctlprog_validate,      NVC0_NEW_TCTLPROG },
594
    { nvc0_tevlprog_validate,      NVC0_NEW_TEVLPROG },
595
    { nvc0_gmtyprog_validate,      NVC0_NEW_GMTYPROG },
596
    { nvc0_fragprog_validate,      NVC0_NEW_FRAGPROG },
597
    { nvc0_validate_derived_1,     NVC0_NEW_FRAGPROG | NVC0_NEW_ZSA |
598
                                   NVC0_NEW_RASTERIZER },
599
    { nvc0_validate_clip,          NVC0_NEW_CLIP | NVC0_NEW_RASTERIZER |
600
                                   NVC0_NEW_VERTPROG |
601
                                   NVC0_NEW_TEVLPROG |
602
                                   NVC0_NEW_GMTYPROG },
603
    { nvc0_constbufs_validate,     NVC0_NEW_CONSTBUF },
604
    { nvc0_validate_textures,      NVC0_NEW_TEXTURES },
605
    { nvc0_validate_samplers,      NVC0_NEW_SAMPLERS },
606
    { nve4_set_tex_handles,        NVC0_NEW_TEXTURES | NVC0_NEW_SAMPLERS },
607
    { nvc0_vertex_arrays_validate, NVC0_NEW_VERTEX | NVC0_NEW_ARRAYS },
608
    { nvc0_validate_surfaces,      NVC0_NEW_SURFACES },
609
    { nvc0_idxbuf_validate,        NVC0_NEW_IDXBUF },
610
    { nvc0_tfb_validate,           NVC0_NEW_TFB_TARGETS | NVC0_NEW_GMTYPROG },
611
    { nvc0_validate_min_samples,   NVC0_NEW_MIN_SAMPLES },
612
};
613
#define validate_list_len (sizeof(validate_list) / sizeof(validate_list[0]))
614
615
 
616
nvc0_state_validate(struct nvc0_context *nvc0, uint32_t mask, unsigned words)
617
{
618
   uint32_t state_mask;
619
   int ret;
620
   unsigned i;
621
622
 
623
      nvc0_switch_pipe_context(nvc0);
624
625
 
626
627
 
628
      for (i = 0; i < validate_list_len; ++i) {
629
         struct state_validate *validate = &validate_list[i];
630
631
 
632
            validate->func(nvc0);
633
      }
634
      nvc0->dirty &= ~state_mask;
635
636
 
637
   }
638
639
 
640
   ret = nouveau_pushbuf_validate(nvc0->base.pushbuf);
641
642
 
643
      nvc0->state.flushed = FALSE;
644
      nvc0_bufctx_fence(nvc0, nvc0->bufctx_3d, TRUE);
645
   }
646
   return !ret;
647
}
648