~mmach/netext73/mesa-haswell

« back to all changes in this revision

Viewing changes to src/gallium/tests/graw/fs-test.c

  • Committer: mmach
  • Date: 2022-09-22 19:56:13 UTC
  • Revision ID: netbit73@gmail.com-20220922195613-wtik9mmy20tmor0i
2022-09-22 21:17:09

Show diffs side-by-side

added added

removed removed

Lines of Context:
1
 
/* Display a cleared blue window.  This demo has no dependencies on
2
 
 * any utility code, just the graw interface and gallium.
3
 
 */
4
 
 
5
 
#include "frontend/graw.h"
6
 
#include "pipe/p_screen.h"
7
 
#include "pipe/p_context.h"
8
 
#include "pipe/p_shader_tokens.h"
9
 
#include "pipe/p_state.h"
10
 
#include "pipe/p_defines.h"
11
 
#include <stdio.h>              /* for fread(), etc */
12
 
 
13
 
#include "util/u_inlines.h"
14
 
#include "util/u_memory.h"      /* Offset() */
15
 
#include "util/u_draw_quad.h"
16
 
#include "util/u_box.h"    
17
 
 
18
 
static const char *filename = NULL;
19
 
unsigned show_fps = 0;
20
 
 
21
 
 
22
 
static void usage(char *name)
23
 
{
24
 
   fprintf(stderr, "usage: %s [ options ] shader_filename\n", name);
25
 
#ifndef _WIN32
26
 
   fprintf(stderr, "\n" );
27
 
   fprintf(stderr, "options:\n");
28
 
   fprintf(stderr, "    -fps  show frames per second\n");
29
 
#endif
30
 
}
31
 
 
32
 
 
33
 
enum pipe_format formats[] = {
34
 
   PIPE_FORMAT_RGBA8888_UNORM,
35
 
   PIPE_FORMAT_BGRA8888_UNORM,
36
 
   PIPE_FORMAT_NONE
37
 
};
38
 
 
39
 
static const int WIDTH = 250;
40
 
static const int HEIGHT = 250;
41
 
 
42
 
static struct pipe_screen *screen = NULL;
43
 
static struct pipe_context *ctx = NULL;
44
 
static struct pipe_resource *rttex = NULL;
45
 
static struct pipe_surface *surf = NULL;
46
 
static struct pipe_sampler_view *sv = NULL;
47
 
static void *sampler = NULL;
48
 
static void *window = NULL;
49
 
static struct pipe_resource *samptex = NULL;
50
 
 
51
 
struct vertex {
52
 
   float position[4];
53
 
   float color[4];
54
 
   float texcoord[4];
55
 
};
56
 
 
57
 
/* Vertex data matches progs/fp/fp-tri.c, but flipped in Y dimension
58
 
 * so that the final images are the same.
59
 
 */
60
 
static struct vertex vertices[] =
61
 
{
62
 
   { { 0.9, 0.9, 0.0, 1.0 },
63
 
     { 0, 0, 1, 1 },
64
 
     { 1, 1, 0, 1 } },
65
 
 
66
 
   { { 0.9,  -0.9, 0.0, 1.0 },
67
 
     { 1, 0, 0, 1 },
68
 
     { 1, -1, 0, 1 } },
69
 
 
70
 
   { {-0.9,  0.0, 0.0, 1.0 },
71
 
     { 0, 1, 0, 1 },
72
 
     { -1, 0, 0, 1 } },
73
 
};
74
 
 
75
 
static float constants1[] = 
76
 
{  0.4, 0, 0,  1,
77
 
   1,   1, 1,  1,
78
 
   2,   2, 2,  2,
79
 
   4,   8, 16, 32,
80
 
 
81
 
   3,  0, 0, 0,
82
 
   0, .5, 0, 0,
83
 
   1,  0, 0, 1,
84
 
   0,  0, 0, 1,
85
 
 
86
 
   1, 0, 0, 0.5,
87
 
   0, 1, 0, 0.5,
88
 
   0, 0, 1, 0,
89
 
   0, 0, 0, 1,
90
 
};
91
 
 
92
 
 
93
 
static float constants2[] = 
94
 
{  1, 0, 0,  1,
95
 
   0, 1, 0,  1,
96
 
   0, 0, 1,  1,
97
 
   0, 0, 0,  0,
98
 
 
99
 
   1,  1, 0, 1,
100
 
   1, .5, 0, 1,
101
 
   1,  0, 0, 1,
102
 
   0,  0, 0, 1,
103
 
 
104
 
   1, 0, 0, 0.5,
105
 
   0, 1, 0, 0.5,
106
 
   0, 0, 1, 0,
107
 
   0, 0, 0, 1,
108
 
};
109
 
 
110
 
static void init_fs_constbuf( void )
111
 
{
112
 
   struct pipe_constant_buffer cb1;
113
 
   struct pipe_constant_buffer cb2;
114
 
 
115
 
   memset(&cb1, 0, sizeof cb1);
116
 
   cb1.buffer_size = sizeof constants1;
117
 
   cb1.user_buffer = constants1;
118
 
 
119
 
   ctx->set_constant_buffer(ctx,
120
 
                            PIPE_SHADER_FRAGMENT, 0, false,
121
 
                            &cb1);
122
 
 
123
 
   memset(&cb2, 0, sizeof cb2);
124
 
   cb2.buffer_size = sizeof constants2;
125
 
   cb2.user_buffer = constants2;
126
 
 
127
 
   ctx->set_constant_buffer(ctx,
128
 
                            PIPE_SHADER_FRAGMENT, 1, false,
129
 
                            &cb2);
130
 
}
131
 
 
132
 
 
133
 
static void set_viewport( float x, float y,
134
 
                          float width, float height,
135
 
                          float zNear, float zFar)
136
 
{
137
 
   float z = zFar;
138
 
   float half_width = (float)width / 2.0f;
139
 
   float half_height = (float)height / 2.0f;
140
 
   float half_depth = ((float)zFar - (float)zNear) / 2.0f;
141
 
   struct pipe_viewport_state vp;
142
 
 
143
 
   vp.scale[0] = half_width;
144
 
   vp.scale[1] = half_height;
145
 
   vp.scale[2] = half_depth;
146
 
 
147
 
   vp.translate[0] = half_width + x;
148
 
   vp.translate[1] = half_height + y;
149
 
   vp.translate[2] = half_depth + z;
150
 
 
151
 
   vp.swizzle_x = PIPE_VIEWPORT_SWIZZLE_POSITIVE_X;
152
 
   vp.swizzle_y = PIPE_VIEWPORT_SWIZZLE_POSITIVE_Y;
153
 
   vp.swizzle_z = PIPE_VIEWPORT_SWIZZLE_POSITIVE_Z;
154
 
   vp.swizzle_w = PIPE_VIEWPORT_SWIZZLE_POSITIVE_W;
155
 
 
156
 
   ctx->set_viewport_states( ctx, 0, 1, &vp );
157
 
}
158
 
 
159
 
static void set_vertices( void )
160
 
{
161
 
   struct pipe_vertex_element ve[3];
162
 
   struct pipe_vertex_buffer vbuf;
163
 
   void *handle;
164
 
 
165
 
   memset(ve, 0, sizeof ve);
166
 
 
167
 
   ve[0].src_offset = Offset(struct vertex, position);
168
 
   ve[0].src_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
169
 
   ve[1].src_offset = Offset(struct vertex, color);
170
 
   ve[1].src_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
171
 
   ve[2].src_offset = Offset(struct vertex, texcoord);
172
 
   ve[2].src_format = PIPE_FORMAT_R32G32B32A32_FLOAT;
173
 
 
174
 
   handle = ctx->create_vertex_elements_state(ctx, 3, ve);
175
 
   ctx->bind_vertex_elements_state(ctx, handle);
176
 
 
177
 
   memset(&vbuf, 0, sizeof vbuf);
178
 
 
179
 
   vbuf.stride = sizeof( struct vertex );
180
 
   vbuf.buffer_offset = 0;
181
 
   vbuf.buffer.resource = pipe_buffer_create_with_data(ctx,
182
 
                                              PIPE_BIND_VERTEX_BUFFER,
183
 
                                              PIPE_USAGE_DEFAULT,
184
 
                                              sizeof(vertices),
185
 
                                              vertices);
186
 
 
187
 
   ctx->set_vertex_buffers(ctx, 0, 1, 0, false, &vbuf);
188
 
}
189
 
 
190
 
static void set_vertex_shader( void )
191
 
{
192
 
   void *handle;
193
 
   const char *text =
194
 
      "VERT\n"
195
 
      "DCL IN[0]\n"
196
 
      "DCL IN[1]\n"
197
 
      "DCL IN[2]\n"
198
 
      "DCL OUT[0], POSITION\n"
199
 
      "DCL OUT[1], COLOR[0]\n"
200
 
      "DCL OUT[2], GENERIC[0]\n"
201
 
      "  MOV OUT[0], IN[0]\n"
202
 
      "  MOV OUT[1], IN[1]\n"
203
 
      "  MOV OUT[2], IN[2]\n"
204
 
      "  END\n";
205
 
 
206
 
   handle = graw_parse_vertex_shader(ctx, text);
207
 
   ctx->bind_vs_state(ctx, handle);
208
 
}
209
 
 
210
 
static void set_fragment_shader( const char *filename )
211
 
{
212
 
   FILE *f;
213
 
   char buf[50000];
214
 
   void *handle;
215
 
   int sz;
216
 
 
217
 
   if ((f = fopen(filename, "r")) == NULL) {
218
 
      fprintf(stderr, "Couldn't open %s\n", filename);
219
 
      exit(1);
220
 
   }
221
 
 
222
 
   sz = fread(buf, 1, sizeof(buf), f);
223
 
   if (!feof(f)) {
224
 
      printf("file too long\n");
225
 
      exit(1);
226
 
   }
227
 
   printf("%.*s\n", sz, buf);
228
 
   buf[sz] = 0;
229
 
 
230
 
   handle = graw_parse_fragment_shader(ctx, buf);
231
 
   ctx->bind_fs_state(ctx, handle);
232
 
   fclose(f);
233
 
}
234
 
 
235
 
 
236
 
static void draw( void )
237
 
{
238
 
   union pipe_color_union clear_color = { {.1,.3,.5,0} };
239
 
 
240
 
   ctx->clear(ctx, PIPE_CLEAR_COLOR, NULL, &clear_color, 0, 0);
241
 
   util_draw_arrays(ctx, PIPE_PRIM_TRIANGLES, 0, 3);
242
 
   ctx->flush(ctx, NULL, 0);
243
 
 
244
 
   graw_save_surface_to_file(ctx, surf, NULL);
245
 
 
246
 
   screen->flush_frontbuffer(screen, ctx, rttex, 0, 0, window, NULL);
247
 
}
248
 
 
249
 
#define SIZE 16
250
 
 
251
 
static void init_tex( void )
252
 
253
 
   struct pipe_sampler_view sv_template;
254
 
   struct pipe_sampler_state sampler_desc;
255
 
   struct pipe_resource templat;
256
 
   struct pipe_box box;
257
 
   ubyte tex2d[SIZE][SIZE][4];
258
 
   int s, t;
259
 
 
260
 
#if (SIZE != 2)
261
 
   for (s = 0; s < SIZE; s++) {
262
 
      for (t = 0; t < SIZE; t++) {
263
 
         if (0) {
264
 
            int x = (s ^ t) & 1;
265
 
            tex2d[t][s][0] = (x) ? 0 : 63;
266
 
            tex2d[t][s][1] = (x) ? 0 : 128;
267
 
            tex2d[t][s][2] = 0;
268
 
            tex2d[t][s][3] = 0xff;
269
 
         }
270
 
         else {
271
 
            int x = ((s ^ t) >> 2) & 1;
272
 
            tex2d[t][s][0] = s*255/(SIZE-1);
273
 
            tex2d[t][s][1] = t*255/(SIZE-1);
274
 
            tex2d[t][s][2] = (x) ? 0 : 128;
275
 
            tex2d[t][s][3] = 0xff;
276
 
         }
277
 
      }
278
 
   }
279
 
#else
280
 
   tex2d[0][0][0] = 0;
281
 
   tex2d[0][0][1] = 255;
282
 
   tex2d[0][0][2] = 255;
283
 
   tex2d[0][0][3] = 0;
284
 
 
285
 
   tex2d[0][1][0] = 0;
286
 
   tex2d[0][1][1] = 0;
287
 
   tex2d[0][1][2] = 255;
288
 
   tex2d[0][1][3] = 255;
289
 
 
290
 
   tex2d[1][0][0] = 255;
291
 
   tex2d[1][0][1] = 255;
292
 
   tex2d[1][0][2] = 0;
293
 
   tex2d[1][0][3] = 255;
294
 
 
295
 
   tex2d[1][1][0] = 255;
296
 
   tex2d[1][1][1] = 0;
297
 
   tex2d[1][1][2] = 0;
298
 
   tex2d[1][1][3] = 255;
299
 
#endif
300
 
 
301
 
   memset(&templat, 0, sizeof(templat));
302
 
   templat.target = PIPE_TEXTURE_2D;
303
 
   templat.format = PIPE_FORMAT_B8G8R8A8_UNORM;
304
 
   templat.width0 = SIZE;
305
 
   templat.height0 = SIZE;
306
 
   templat.depth0 = 1;
307
 
   templat.array_size = 1;
308
 
   templat.last_level = 0;
309
 
   templat.bind = PIPE_BIND_SAMPLER_VIEW;
310
 
 
311
 
   
312
 
   samptex = screen->resource_create(screen,
313
 
                                 &templat);
314
 
   if (samptex == NULL)
315
 
      exit(4);
316
 
 
317
 
   u_box_2d(0,0,SIZE,SIZE, &box);
318
 
 
319
 
   ctx->texture_subdata(ctx,
320
 
                        samptex,
321
 
                        0,
322
 
                        PIPE_MAP_WRITE,
323
 
                        &box,
324
 
                        tex2d,
325
 
                        sizeof tex2d[0],
326
 
                        sizeof tex2d);
327
 
 
328
 
   /* Possibly read back & compare against original data:
329
 
    */
330
 
   if (0)
331
 
   {
332
 
      struct pipe_transfer *t;
333
 
      uint32_t *ptr;
334
 
      ptr = pipe_texture_map(ctx, samptex,
335
 
                              0, 0, /* level, layer */
336
 
                              PIPE_MAP_READ,
337
 
                              0, 0, SIZE, SIZE, &t); /* x, y, width, height */
338
 
 
339
 
      if (memcmp(ptr, tex2d, sizeof tex2d) != 0) {
340
 
         assert(0);
341
 
         exit(9);
342
 
      }
343
 
 
344
 
      ctx->texture_unmap(ctx, t);
345
 
   }
346
 
 
347
 
   memset(&sv_template, 0, sizeof sv_template);
348
 
   sv_template.format = samptex->format;
349
 
   sv_template.texture = samptex;
350
 
   sv_template.swizzle_r = 0;
351
 
   sv_template.swizzle_g = 1;
352
 
   sv_template.swizzle_b = 2;
353
 
   sv_template.swizzle_a = 3;
354
 
   sv = ctx->create_sampler_view(ctx, samptex, &sv_template);
355
 
   if (sv == NULL)
356
 
      exit(5);
357
 
 
358
 
   ctx->set_sampler_views(ctx, PIPE_SHADER_FRAGMENT, 0, 1, 0, false, &sv);
359
 
   
360
 
 
361
 
   memset(&sampler_desc, 0, sizeof sampler_desc);
362
 
   sampler_desc.wrap_s = PIPE_TEX_WRAP_REPEAT;
363
 
   sampler_desc.wrap_t = PIPE_TEX_WRAP_REPEAT;
364
 
   sampler_desc.wrap_r = PIPE_TEX_WRAP_REPEAT;
365
 
   sampler_desc.min_img_filter = PIPE_TEX_FILTER_NEAREST;
366
 
   sampler_desc.min_mip_filter = PIPE_TEX_MIPFILTER_NONE;
367
 
   sampler_desc.mag_img_filter = PIPE_TEX_FILTER_NEAREST;
368
 
   sampler_desc.compare_mode = PIPE_TEX_COMPARE_NONE;
369
 
   sampler_desc.compare_func = 0;
370
 
   sampler_desc.normalized_coords = 1;
371
 
   sampler_desc.max_anisotropy = 0;
372
 
   
373
 
   sampler = ctx->create_sampler_state(ctx, &sampler_desc);
374
 
   if (sampler == NULL)
375
 
      exit(6);
376
 
 
377
 
   ctx->bind_sampler_states(ctx, PIPE_SHADER_FRAGMENT, 0, 1, &sampler);
378
 
   
379
 
}
380
 
 
381
 
static void init( void )
382
 
{
383
 
   struct pipe_framebuffer_state fb;
384
 
   struct pipe_resource templat;
385
 
   struct pipe_surface surf_tmpl;
386
 
   int i;
387
 
 
388
 
   /* It's hard to say whether window or screen should be created
389
 
    * first.  Different environments would prefer one or the other.
390
 
    *
391
 
    * Also, no easy way of querying supported formats if the screen
392
 
    * cannot be created first.
393
 
    */
394
 
   for (i = 0; formats[i] != PIPE_FORMAT_NONE; i++) {
395
 
      screen = graw_create_window_and_screen(0, 0, 300, 300,
396
 
                                             formats[i],
397
 
                                             &window);
398
 
      if (window && screen)
399
 
         break;
400
 
   }
401
 
   if (!screen || !window) {
402
 
      fprintf(stderr, "Unable to create window\n");
403
 
      exit(1);
404
 
   }
405
 
 
406
 
   ctx = screen->context_create(screen, NULL, 0);
407
 
   if (ctx == NULL)
408
 
      exit(3);
409
 
 
410
 
   memset(&templat, 0, sizeof(templat));
411
 
   templat.target = PIPE_TEXTURE_2D;
412
 
   templat.format = formats[i];
413
 
   templat.width0 = WIDTH;
414
 
   templat.height0 = HEIGHT;
415
 
   templat.depth0 = 1;
416
 
   templat.array_size = 1;
417
 
   templat.last_level = 0;
418
 
   templat.bind = (PIPE_BIND_RENDER_TARGET |
419
 
                   PIPE_BIND_DISPLAY_TARGET);
420
 
   
421
 
   rttex = screen->resource_create(screen,
422
 
                                 &templat);
423
 
   if (rttex == NULL)
424
 
      exit(4);
425
 
 
426
 
   surf_tmpl.format = templat.format;
427
 
   surf_tmpl.u.tex.level = 0;
428
 
   surf_tmpl.u.tex.first_layer = 0;
429
 
   surf_tmpl.u.tex.last_layer = 0;
430
 
   surf = ctx->create_surface(ctx, rttex, &surf_tmpl);
431
 
   if (surf == NULL)
432
 
      exit(5);
433
 
 
434
 
   memset(&fb, 0, sizeof fb);
435
 
   fb.nr_cbufs = 1;
436
 
   fb.width = WIDTH;
437
 
   fb.height = HEIGHT;
438
 
   fb.cbufs[0] = surf;
439
 
 
440
 
   ctx->set_framebuffer_state(ctx, &fb);
441
 
   
442
 
   {
443
 
      struct pipe_blend_state blend;
444
 
      void *handle;
445
 
      memset(&blend, 0, sizeof blend);
446
 
      blend.rt[0].colormask = PIPE_MASK_RGBA;
447
 
      handle = ctx->create_blend_state(ctx, &blend);
448
 
      ctx->bind_blend_state(ctx, handle);
449
 
   }
450
 
 
451
 
   {
452
 
      struct pipe_depth_stencil_alpha_state depthstencil;
453
 
      void *handle;
454
 
      memset(&depthstencil, 0, sizeof depthstencil);
455
 
      handle = ctx->create_depth_stencil_alpha_state(ctx, &depthstencil);
456
 
      ctx->bind_depth_stencil_alpha_state(ctx, handle);
457
 
   }
458
 
 
459
 
   {
460
 
      struct pipe_rasterizer_state rasterizer;
461
 
      void *handle;
462
 
      memset(&rasterizer, 0, sizeof rasterizer);
463
 
      rasterizer.cull_face = PIPE_FACE_NONE;
464
 
      rasterizer.half_pixel_center = 1;
465
 
      rasterizer.bottom_edge_rule = 1;
466
 
      rasterizer.depth_clip_near = 1;
467
 
      rasterizer.depth_clip_far = 1;
468
 
      handle = ctx->create_rasterizer_state(ctx, &rasterizer);
469
 
      ctx->bind_rasterizer_state(ctx, handle);
470
 
   }
471
 
 
472
 
   set_viewport(0, 0, WIDTH, HEIGHT, 30, 1000);
473
 
 
474
 
   init_tex();
475
 
   init_fs_constbuf();
476
 
 
477
 
   set_vertices();
478
 
   set_vertex_shader();
479
 
   set_fragment_shader(filename);
480
 
}
481
 
 
482
 
static void args(int argc, char *argv[])
483
 
{
484
 
   int i;
485
 
 
486
 
   for (i = 1; i < argc;) {
487
 
      if (graw_parse_args(&i, argc, argv)) {
488
 
         continue;
489
 
      }
490
 
      if (strcmp(argv[i], "-fps") == 0) {
491
 
         show_fps = 1;
492
 
         i++;
493
 
      }
494
 
      else if (i == argc - 1) {
495
 
         filename = argv[i];
496
 
         i++;
497
 
      }
498
 
      else {
499
 
         usage(argv[0]);
500
 
         exit(1);
501
 
      }
502
 
   }
503
 
 
504
 
   if (!filename) {
505
 
      usage(argv[0]);
506
 
      exit(1);
507
 
   }
508
 
}
509
 
 
510
 
int main( int argc, char *argv[] )
511
 
{
512
 
   args(argc,argv);
513
 
   init();
514
 
 
515
 
   graw_set_display_func( draw );
516
 
   graw_main_loop();
517
 
   return 0;
518
 
}