ir_constant_expression.cpp revision 2d0ef6bfee64b6889cbfb69762f167a6dfc20131
1/*
2 * Copyright © 2010 Intel Corporation
3 *
4 * Permission is hereby granted, free of charge, to any person obtaining a
5 * copy of this software and associated documentation files (the "Software"),
6 * to deal in the Software without restriction, including without limitation
7 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
8 * and/or sell copies of the Software, and to permit persons to whom the
9 * Software is furnished to do so, subject to the following conditions:
10 *
11 * The above copyright notice and this permission notice (including the next
12 * paragraph) shall be included in all copies or substantial portions of the
13 * Software.
14 *
15 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
16 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
17 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL
18 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
19 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
20 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
21 * DEALINGS IN THE SOFTWARE.
22 */
23
24/**
25 * \file ir_constant_expression.cpp
26 * Evaluate and process constant valued expressions
27 *
28 * In GLSL, constant valued expressions are used in several places.  These
29 * must be processed and evaluated very early in the compilation process.
30 *
31 *    * Sizes of arrays
32 *    * Initializers for uniforms
33 *    * Initializers for \c const variables
34 */
35
36#include <math.h>
37#include "main/core.h" /* for MAX2, MIN2, CLAMP */
38#include "ir.h"
39#include "ir_visitor.h"
40#include "glsl_types.h"
41
42static float
43dot(ir_constant *op0, ir_constant *op1)
44{
45   assert(op0->type->is_float() && op1->type->is_float());
46
47   float result = 0;
48   for (unsigned c = 0; c < op0->type->components(); c++)
49      result += op0->value.f[c] * op1->value.f[c];
50
51   return result;
52}
53
54ir_constant *
55ir_expression::constant_expression_value()
56{
57   ir_constant *op[2] = { NULL, NULL };
58   ir_constant_data data;
59
60   memset(&data, 0, sizeof(data));
61
62   for (unsigned operand = 0; operand < this->get_num_operands(); operand++) {
63      op[operand] = this->operands[operand]->constant_expression_value();
64      if (!op[operand])
65	 return NULL;
66   }
67
68   if (op[1] != NULL)
69      assert(op[0]->type->base_type == op[1]->type->base_type);
70
71   bool op0_scalar = op[0]->type->is_scalar();
72   bool op1_scalar = op[1] != NULL && op[1]->type->is_scalar();
73
74   /* When iterating over a vector or matrix's components, we want to increase
75    * the loop counter.  However, for scalars, we want to stay at 0.
76    */
77   unsigned c0_inc = op0_scalar ? 0 : 1;
78   unsigned c1_inc = op1_scalar ? 0 : 1;
79   unsigned components;
80   if (op1_scalar || !op[1]) {
81      components = op[0]->type->components();
82   } else {
83      components = op[1]->type->components();
84   }
85
86   void *ctx = talloc_parent(this);
87
88   /* Handle array operations here, rather than below. */
89   if (op[0]->type->is_array()) {
90      assert(op[1] != NULL && op[1]->type->is_array());
91      switch (this->operation) {
92      case ir_binop_equal:
93	 return new(ctx) ir_constant(op[0]->has_value(op[1]));
94      case ir_binop_nequal:
95	 return new(ctx) ir_constant(!op[0]->has_value(op[1]));
96      default:
97	 break;
98      }
99      return NULL;
100   }
101
102   switch (this->operation) {
103   case ir_unop_logic_not:
104      assert(op[0]->type->base_type == GLSL_TYPE_BOOL);
105      for (unsigned c = 0; c < op[0]->type->components(); c++)
106	 data.b[c] = !op[0]->value.b[c];
107      break;
108
109   case ir_unop_f2i:
110      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
111      for (unsigned c = 0; c < op[0]->type->components(); c++) {
112	 data.i[c] = op[0]->value.f[c];
113      }
114      break;
115   case ir_unop_i2f:
116      assert(op[0]->type->base_type == GLSL_TYPE_INT);
117      for (unsigned c = 0; c < op[0]->type->components(); c++) {
118	 data.f[c] = op[0]->value.i[c];
119      }
120      break;
121   case ir_unop_u2f:
122      assert(op[0]->type->base_type == GLSL_TYPE_UINT);
123      for (unsigned c = 0; c < op[0]->type->components(); c++) {
124	 data.f[c] = op[0]->value.u[c];
125      }
126      break;
127   case ir_unop_b2f:
128      assert(op[0]->type->base_type == GLSL_TYPE_BOOL);
129      for (unsigned c = 0; c < op[0]->type->components(); c++) {
130	 data.f[c] = op[0]->value.b[c] ? 1.0 : 0.0;
131      }
132      break;
133   case ir_unop_f2b:
134      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
135      for (unsigned c = 0; c < op[0]->type->components(); c++) {
136	 data.b[c] = bool(op[0]->value.f[c]);
137      }
138      break;
139   case ir_unop_b2i:
140      assert(op[0]->type->base_type == GLSL_TYPE_BOOL);
141      for (unsigned c = 0; c < op[0]->type->components(); c++) {
142	 data.u[c] = op[0]->value.b[c] ? 1 : 0;
143      }
144      break;
145   case ir_unop_i2b:
146      assert(op[0]->type->is_integer());
147      for (unsigned c = 0; c < op[0]->type->components(); c++) {
148	 data.b[c] = bool(op[0]->value.u[c]);
149      }
150      break;
151
152   case ir_unop_any:
153      assert(op[0]->type->is_boolean());
154      data.b[0] = false;
155      for (unsigned c = 0; c < op[0]->type->components(); c++) {
156	 if (op[0]->value.b[c])
157	    data.b[0] = true;
158      }
159      break;
160
161   case ir_unop_trunc:
162      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
163      for (unsigned c = 0; c < op[0]->type->components(); c++) {
164	 data.f[c] = truncf(op[0]->value.f[c]);
165      }
166      break;
167
168   case ir_unop_ceil:
169      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
170      for (unsigned c = 0; c < op[0]->type->components(); c++) {
171	 data.f[c] = ceilf(op[0]->value.f[c]);
172      }
173      break;
174
175   case ir_unop_floor:
176      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
177      for (unsigned c = 0; c < op[0]->type->components(); c++) {
178	 data.f[c] = floorf(op[0]->value.f[c]);
179      }
180      break;
181
182   case ir_unop_fract:
183      for (unsigned c = 0; c < op[0]->type->components(); c++) {
184	 switch (this->type->base_type) {
185	 case GLSL_TYPE_UINT:
186	    data.u[c] = 0;
187	    break;
188	 case GLSL_TYPE_INT:
189	    data.i[c] = 0;
190	    break;
191	 case GLSL_TYPE_FLOAT:
192	    data.f[c] = op[0]->value.f[c] - floor(op[0]->value.f[c]);
193	    break;
194	 default:
195	    assert(0);
196	 }
197      }
198      break;
199
200   case ir_unop_sin:
201      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
202      for (unsigned c = 0; c < op[0]->type->components(); c++) {
203	 data.f[c] = sinf(op[0]->value.f[c]);
204      }
205      break;
206
207   case ir_unop_cos:
208      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
209      for (unsigned c = 0; c < op[0]->type->components(); c++) {
210	 data.f[c] = cosf(op[0]->value.f[c]);
211      }
212      break;
213
214   case ir_unop_neg:
215      for (unsigned c = 0; c < op[0]->type->components(); c++) {
216	 switch (this->type->base_type) {
217	 case GLSL_TYPE_UINT:
218	    data.u[c] = -op[0]->value.u[c];
219	    break;
220	 case GLSL_TYPE_INT:
221	    data.i[c] = -op[0]->value.i[c];
222	    break;
223	 case GLSL_TYPE_FLOAT:
224	    data.f[c] = -op[0]->value.f[c];
225	    break;
226	 default:
227	    assert(0);
228	 }
229      }
230      break;
231
232   case ir_unop_abs:
233      for (unsigned c = 0; c < op[0]->type->components(); c++) {
234	 switch (this->type->base_type) {
235	 case GLSL_TYPE_UINT:
236	    data.u[c] = op[0]->value.u[c];
237	    break;
238	 case GLSL_TYPE_INT:
239	    data.i[c] = op[0]->value.i[c];
240	    if (data.i[c] < 0)
241	       data.i[c] = -data.i[c];
242	    break;
243	 case GLSL_TYPE_FLOAT:
244	    data.f[c] = fabs(op[0]->value.f[c]);
245	    break;
246	 default:
247	    assert(0);
248	 }
249      }
250      break;
251
252   case ir_unop_sign:
253      for (unsigned c = 0; c < op[0]->type->components(); c++) {
254	 switch (this->type->base_type) {
255	 case GLSL_TYPE_UINT:
256	    data.u[c] = op[0]->value.i[c] > 0;
257	    break;
258	 case GLSL_TYPE_INT:
259	    data.i[c] = (op[0]->value.i[c] > 0) - (op[0]->value.i[c] < 0);
260	    break;
261	 case GLSL_TYPE_FLOAT:
262	    data.f[c] = float((op[0]->value.f[c] > 0)-(op[0]->value.f[c] < 0));
263	    break;
264	 default:
265	    assert(0);
266	 }
267      }
268      break;
269
270   case ir_unop_rcp:
271      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
272      for (unsigned c = 0; c < op[0]->type->components(); c++) {
273	 switch (this->type->base_type) {
274	 case GLSL_TYPE_UINT:
275	    if (op[0]->value.u[c] != 0.0)
276	       data.u[c] = 1 / op[0]->value.u[c];
277	    break;
278	 case GLSL_TYPE_INT:
279	    if (op[0]->value.i[c] != 0.0)
280	       data.i[c] = 1 / op[0]->value.i[c];
281	    break;
282	 case GLSL_TYPE_FLOAT:
283	    if (op[0]->value.f[c] != 0.0)
284	       data.f[c] = 1.0 / op[0]->value.f[c];
285	    break;
286	 default:
287	    assert(0);
288	 }
289      }
290      break;
291
292   case ir_unop_rsq:
293      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
294      for (unsigned c = 0; c < op[0]->type->components(); c++) {
295	 data.f[c] = 1.0 / sqrtf(op[0]->value.f[c]);
296      }
297      break;
298
299   case ir_unop_sqrt:
300      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
301      for (unsigned c = 0; c < op[0]->type->components(); c++) {
302	 data.f[c] = sqrtf(op[0]->value.f[c]);
303      }
304      break;
305
306   case ir_unop_exp:
307      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
308      for (unsigned c = 0; c < op[0]->type->components(); c++) {
309	 data.f[c] = expf(op[0]->value.f[c]);
310      }
311      break;
312
313   case ir_unop_exp2:
314      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
315      for (unsigned c = 0; c < op[0]->type->components(); c++) {
316	 data.f[c] = exp2f(op[0]->value.f[c]);
317      }
318      break;
319
320   case ir_unop_log:
321      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
322      for (unsigned c = 0; c < op[0]->type->components(); c++) {
323	 data.f[c] = logf(op[0]->value.f[c]);
324      }
325      break;
326
327   case ir_unop_log2:
328      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
329      for (unsigned c = 0; c < op[0]->type->components(); c++) {
330	 data.f[c] = log2f(op[0]->value.f[c]);
331      }
332      break;
333
334   case ir_unop_dFdx:
335   case ir_unop_dFdy:
336      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
337      for (unsigned c = 0; c < op[0]->type->components(); c++) {
338	 data.f[c] = 0.0;
339      }
340      break;
341
342   case ir_binop_pow:
343      assert(op[0]->type->base_type == GLSL_TYPE_FLOAT);
344      for (unsigned c = 0; c < op[0]->type->components(); c++) {
345	 data.f[c] = powf(op[0]->value.f[c], op[1]->value.f[c]);
346      }
347      break;
348
349   case ir_binop_dot:
350      data.f[0] = dot(op[0], op[1]);
351      break;
352
353   case ir_binop_min:
354      assert(op[0]->type == op[1]->type || op0_scalar || op1_scalar);
355      for (unsigned c = 0, c0 = 0, c1 = 0;
356	   c < components;
357	   c0 += c0_inc, c1 += c1_inc, c++) {
358
359	 switch (op[0]->type->base_type) {
360	 case GLSL_TYPE_UINT:
361	    data.u[c] = MIN2(op[0]->value.u[c0], op[1]->value.u[c1]);
362	    break;
363	 case GLSL_TYPE_INT:
364	    data.i[c] = MIN2(op[0]->value.i[c0], op[1]->value.i[c1]);
365	    break;
366	 case GLSL_TYPE_FLOAT:
367	    data.f[c] = MIN2(op[0]->value.f[c0], op[1]->value.f[c1]);
368	    break;
369	 default:
370	    assert(0);
371	 }
372      }
373
374      break;
375   case ir_binop_max:
376      assert(op[0]->type == op[1]->type || op0_scalar || op1_scalar);
377      for (unsigned c = 0, c0 = 0, c1 = 0;
378	   c < components;
379	   c0 += c0_inc, c1 += c1_inc, c++) {
380
381	 switch (op[0]->type->base_type) {
382	 case GLSL_TYPE_UINT:
383	    data.u[c] = MAX2(op[0]->value.u[c0], op[1]->value.u[c1]);
384	    break;
385	 case GLSL_TYPE_INT:
386	    data.i[c] = MAX2(op[0]->value.i[c0], op[1]->value.i[c1]);
387	    break;
388	 case GLSL_TYPE_FLOAT:
389	    data.f[c] = MAX2(op[0]->value.f[c0], op[1]->value.f[c1]);
390	    break;
391	 default:
392	    assert(0);
393	 }
394      }
395      break;
396
397   case ir_binop_cross:
398      assert(op[0]->type == glsl_type::vec3_type);
399      assert(op[1]->type == glsl_type::vec3_type);
400      data.f[0] = (op[0]->value.f[1] * op[1]->value.f[2] -
401		   op[1]->value.f[1] * op[0]->value.f[2]);
402      data.f[1] = (op[0]->value.f[2] * op[1]->value.f[0] -
403		   op[1]->value.f[2] * op[0]->value.f[0]);
404      data.f[2] = (op[0]->value.f[0] * op[1]->value.f[1] -
405		   op[1]->value.f[0] * op[0]->value.f[1]);
406      break;
407
408   case ir_binop_add:
409      assert(op[0]->type == op[1]->type || op0_scalar || op1_scalar);
410      for (unsigned c = 0, c0 = 0, c1 = 0;
411	   c < components;
412	   c0 += c0_inc, c1 += c1_inc, c++) {
413
414	 switch (op[0]->type->base_type) {
415	 case GLSL_TYPE_UINT:
416	    data.u[c] = op[0]->value.u[c0] + op[1]->value.u[c1];
417	    break;
418	 case GLSL_TYPE_INT:
419	    data.i[c] = op[0]->value.i[c0] + op[1]->value.i[c1];
420	    break;
421	 case GLSL_TYPE_FLOAT:
422	    data.f[c] = op[0]->value.f[c0] + op[1]->value.f[c1];
423	    break;
424	 default:
425	    assert(0);
426	 }
427      }
428
429      break;
430   case ir_binop_sub:
431      assert(op[0]->type == op[1]->type || op0_scalar || op1_scalar);
432      for (unsigned c = 0, c0 = 0, c1 = 0;
433	   c < components;
434	   c0 += c0_inc, c1 += c1_inc, c++) {
435
436	 switch (op[0]->type->base_type) {
437	 case GLSL_TYPE_UINT:
438	    data.u[c] = op[0]->value.u[c0] - op[1]->value.u[c1];
439	    break;
440	 case GLSL_TYPE_INT:
441	    data.i[c] = op[0]->value.i[c0] - op[1]->value.i[c1];
442	    break;
443	 case GLSL_TYPE_FLOAT:
444	    data.f[c] = op[0]->value.f[c0] - op[1]->value.f[c1];
445	    break;
446	 default:
447	    assert(0);
448	 }
449      }
450
451      break;
452   case ir_binop_mul:
453      /* Check for equal types, or unequal types involving scalars */
454      if ((op[0]->type == op[1]->type && !op[0]->type->is_matrix())
455	  || op0_scalar || op1_scalar) {
456	 for (unsigned c = 0, c0 = 0, c1 = 0;
457	      c < components;
458	      c0 += c0_inc, c1 += c1_inc, c++) {
459
460	    switch (op[0]->type->base_type) {
461	    case GLSL_TYPE_UINT:
462	       data.u[c] = op[0]->value.u[c0] * op[1]->value.u[c1];
463	       break;
464	    case GLSL_TYPE_INT:
465	       data.i[c] = op[0]->value.i[c0] * op[1]->value.i[c1];
466	       break;
467	    case GLSL_TYPE_FLOAT:
468	       data.f[c] = op[0]->value.f[c0] * op[1]->value.f[c1];
469	       break;
470	    default:
471	       assert(0);
472	    }
473	 }
474      } else {
475	 assert(op[0]->type->is_matrix() || op[1]->type->is_matrix());
476
477	 /* Multiply an N-by-M matrix with an M-by-P matrix.  Since either
478	  * matrix can be a GLSL vector, either N or P can be 1.
479	  *
480	  * For vec*mat, the vector is treated as a row vector.  This
481	  * means the vector is a 1-row x M-column matrix.
482	  *
483	  * For mat*vec, the vector is treated as a column vector.  Since
484	  * matrix_columns is 1 for vectors, this just works.
485	  */
486	 const unsigned n = op[0]->type->is_vector()
487	    ? 1 : op[0]->type->vector_elements;
488	 const unsigned m = op[1]->type->vector_elements;
489	 const unsigned p = op[1]->type->matrix_columns;
490	 for (unsigned j = 0; j < p; j++) {
491	    for (unsigned i = 0; i < n; i++) {
492	       for (unsigned k = 0; k < m; k++) {
493		  data.f[i+n*j] += op[0]->value.f[i+n*k]*op[1]->value.f[k+m*j];
494	       }
495	    }
496	 }
497      }
498
499      break;
500   case ir_binop_div:
501      assert(op[0]->type == op[1]->type || op0_scalar || op1_scalar);
502      for (unsigned c = 0, c0 = 0, c1 = 0;
503	   c < components;
504	   c0 += c0_inc, c1 += c1_inc, c++) {
505
506	 switch (op[0]->type->base_type) {
507	 case GLSL_TYPE_UINT:
508	    data.u[c] = op[0]->value.u[c0] / op[1]->value.u[c1];
509	    break;
510	 case GLSL_TYPE_INT:
511	    data.i[c] = op[0]->value.i[c0] / op[1]->value.i[c1];
512	    break;
513	 case GLSL_TYPE_FLOAT:
514	    data.f[c] = op[0]->value.f[c0] / op[1]->value.f[c1];
515	    break;
516	 default:
517	    assert(0);
518	 }
519      }
520
521      break;
522   case ir_binop_mod:
523      assert(op[0]->type == op[1]->type || op0_scalar || op1_scalar);
524      for (unsigned c = 0, c0 = 0, c1 = 0;
525	   c < components;
526	   c0 += c0_inc, c1 += c1_inc, c++) {
527
528	 switch (op[0]->type->base_type) {
529	 case GLSL_TYPE_UINT:
530	    data.u[c] = op[0]->value.u[c0] % op[1]->value.u[c1];
531	    break;
532	 case GLSL_TYPE_INT:
533	    data.i[c] = op[0]->value.i[c0] % op[1]->value.i[c1];
534	    break;
535	 case GLSL_TYPE_FLOAT:
536	    /* We don't use fmod because it rounds toward zero; GLSL specifies
537	     * the use of floor.
538	     */
539	    data.f[c] = op[0]->value.f[c0] - op[1]->value.f[c1]
540	       * floorf(op[0]->value.f[c0] / op[1]->value.f[c1]);
541	    break;
542	 default:
543	    assert(0);
544	 }
545      }
546
547      break;
548
549   case ir_binop_logic_and:
550      assert(op[0]->type->base_type == GLSL_TYPE_BOOL);
551      for (unsigned c = 0; c < op[0]->type->components(); c++)
552	 data.b[c] = op[0]->value.b[c] && op[1]->value.b[c];
553      break;
554   case ir_binop_logic_xor:
555      assert(op[0]->type->base_type == GLSL_TYPE_BOOL);
556      for (unsigned c = 0; c < op[0]->type->components(); c++)
557	 data.b[c] = op[0]->value.b[c] ^ op[1]->value.b[c];
558      break;
559   case ir_binop_logic_or:
560      assert(op[0]->type->base_type == GLSL_TYPE_BOOL);
561      for (unsigned c = 0; c < op[0]->type->components(); c++)
562	 data.b[c] = op[0]->value.b[c] || op[1]->value.b[c];
563      break;
564
565   case ir_binop_less:
566      switch (op[0]->type->base_type) {
567      case GLSL_TYPE_UINT:
568	 data.b[0] = op[0]->value.u[0] < op[1]->value.u[0];
569	 break;
570      case GLSL_TYPE_INT:
571	 data.b[0] = op[0]->value.i[0] < op[1]->value.i[0];
572	 break;
573      case GLSL_TYPE_FLOAT:
574	 data.b[0] = op[0]->value.f[0] < op[1]->value.f[0];
575	 break;
576      default:
577	 assert(0);
578      }
579      break;
580   case ir_binop_greater:
581      switch (op[0]->type->base_type) {
582      case GLSL_TYPE_UINT:
583	 data.b[0] = op[0]->value.u[0] > op[1]->value.u[0];
584	 break;
585      case GLSL_TYPE_INT:
586	 data.b[0] = op[0]->value.i[0] > op[1]->value.i[0];
587	 break;
588      case GLSL_TYPE_FLOAT:
589	 data.b[0] = op[0]->value.f[0] > op[1]->value.f[0];
590	 break;
591      default:
592	 assert(0);
593      }
594      break;
595   case ir_binop_lequal:
596      switch (op[0]->type->base_type) {
597      case GLSL_TYPE_UINT:
598	 data.b[0] = op[0]->value.u[0] <= op[1]->value.u[0];
599	 break;
600      case GLSL_TYPE_INT:
601	 data.b[0] = op[0]->value.i[0] <= op[1]->value.i[0];
602	 break;
603      case GLSL_TYPE_FLOAT:
604	 data.b[0] = op[0]->value.f[0] <= op[1]->value.f[0];
605	 break;
606      default:
607	 assert(0);
608      }
609      break;
610   case ir_binop_gequal:
611      switch (op[0]->type->base_type) {
612      case GLSL_TYPE_UINT:
613	 data.b[0] = op[0]->value.u[0] >= op[1]->value.u[0];
614	 break;
615      case GLSL_TYPE_INT:
616	 data.b[0] = op[0]->value.i[0] >= op[1]->value.i[0];
617	 break;
618      case GLSL_TYPE_FLOAT:
619	 data.b[0] = op[0]->value.f[0] >= op[1]->value.f[0];
620	 break;
621      default:
622	 assert(0);
623      }
624      break;
625
626   case ir_binop_equal:
627      data.b[0] = op[0]->has_value(op[1]);
628      break;
629   case ir_binop_nequal:
630      data.b[0] = !op[0]->has_value(op[1]);
631      break;
632
633   default:
634      /* FINISHME: Should handle all expression types. */
635      return NULL;
636   }
637
638   return new(ctx) ir_constant(this->type, &data);
639}
640
641
642ir_constant *
643ir_texture::constant_expression_value()
644{
645   /* texture lookups aren't constant expressions */
646   return NULL;
647}
648
649
650ir_constant *
651ir_swizzle::constant_expression_value()
652{
653   ir_constant *v = this->val->constant_expression_value();
654
655   if (v != NULL) {
656      ir_constant_data data = { { 0 } };
657
658      const unsigned swiz_idx[4] = {
659	 this->mask.x, this->mask.y, this->mask.z, this->mask.w
660      };
661
662      for (unsigned i = 0; i < this->mask.num_components; i++) {
663	 switch (v->type->base_type) {
664	 case GLSL_TYPE_UINT:
665	 case GLSL_TYPE_INT:   data.u[i] = v->value.u[swiz_idx[i]]; break;
666	 case GLSL_TYPE_FLOAT: data.f[i] = v->value.f[swiz_idx[i]]; break;
667	 case GLSL_TYPE_BOOL:  data.b[i] = v->value.b[swiz_idx[i]]; break;
668	 default:              assert(!"Should not get here."); break;
669	 }
670      }
671
672      void *ctx = talloc_parent(this);
673      return new(ctx) ir_constant(this->type, &data);
674   }
675   return NULL;
676}
677
678
679ir_constant *
680ir_dereference_variable::constant_expression_value()
681{
682   /* This may occur during compile and var->type is glsl_type::error_type */
683   if (!var)
684      return NULL;
685
686   /* The constant_value of a uniform variable is its initializer,
687    * not the lifetime constant value of the uniform.
688    */
689   if (var->mode == ir_var_uniform)
690      return NULL;
691
692   if (!var->constant_value)
693      return NULL;
694
695   return var->constant_value->clone(talloc_parent(var), NULL);
696}
697
698
699ir_constant *
700ir_dereference_array::constant_expression_value()
701{
702   ir_constant *array = this->array->constant_expression_value();
703   ir_constant *idx = this->array_index->constant_expression_value();
704
705   if ((array != NULL) && (idx != NULL)) {
706      void *ctx = talloc_parent(this);
707      if (array->type->is_matrix()) {
708	 /* Array access of a matrix results in a vector.
709	  */
710	 const unsigned column = idx->value.u[0];
711
712	 const glsl_type *const column_type = array->type->column_type();
713
714	 /* Offset in the constant matrix to the first element of the column
715	  * to be extracted.
716	  */
717	 const unsigned mat_idx = column * column_type->vector_elements;
718
719	 ir_constant_data data;
720
721	 switch (column_type->base_type) {
722	 case GLSL_TYPE_UINT:
723	 case GLSL_TYPE_INT:
724	    for (unsigned i = 0; i < column_type->vector_elements; i++)
725	       data.u[i] = array->value.u[mat_idx + i];
726
727	    break;
728
729	 case GLSL_TYPE_FLOAT:
730	    for (unsigned i = 0; i < column_type->vector_elements; i++)
731	       data.f[i] = array->value.f[mat_idx + i];
732
733	    break;
734
735	 default:
736	    assert(!"Should not get here.");
737	    break;
738	 }
739
740	 return new(ctx) ir_constant(column_type, &data);
741      } else if (array->type->is_vector()) {
742	 const unsigned component = idx->value.u[0];
743
744	 return new(ctx) ir_constant(array, component);
745      } else {
746	 const unsigned index = idx->value.u[0];
747	 return array->get_array_element(index)->clone(ctx, NULL);
748      }
749   }
750   return NULL;
751}
752
753
754ir_constant *
755ir_dereference_record::constant_expression_value()
756{
757   ir_constant *v = this->record->constant_expression_value();
758
759   return (v != NULL) ? v->get_record_field(this->field) : NULL;
760}
761
762
763ir_constant *
764ir_assignment::constant_expression_value()
765{
766   /* FINISHME: Handle CEs involving assignment (return RHS) */
767   return NULL;
768}
769
770
771ir_constant *
772ir_constant::constant_expression_value()
773{
774   return this;
775}
776
777
778ir_constant *
779ir_call::constant_expression_value()
780{
781   if (this->type == glsl_type::error_type)
782      return NULL;
783
784   /* From the GLSL 1.20 spec, page 23:
785    * "Function calls to user-defined functions (non-built-in functions)
786    *  cannot be used to form constant expressions."
787    */
788   if (!this->callee->function()->is_builtin)
789      return NULL;
790
791   unsigned num_parameters = 0;
792
793   /* Check if all parameters are constant */
794   ir_constant *op[3];
795   foreach_list(n, &this->actual_parameters) {
796      ir_constant *constant = ((ir_rvalue *) n)->constant_expression_value();
797      if (constant == NULL)
798	 return NULL;
799
800      op[num_parameters] = constant;
801
802      assert(num_parameters < 3);
803      num_parameters++;
804   }
805
806   /* Individual cases below can either:
807    * - Assign "expr" a new ir_expression to evaluate (for basic opcodes)
808    * - Fill "data" with appopriate constant data
809    * - Return an ir_constant directly.
810    */
811   void *mem_ctx = talloc_parent(this);
812   ir_expression *expr = NULL;
813
814   ir_constant_data data;
815   memset(&data, 0, sizeof(data));
816
817   const char *callee = this->callee_name();
818   if (strcmp(callee, "abs") == 0) {
819      expr = new(mem_ctx) ir_expression(ir_unop_abs, type, op[0], NULL);
820   } else if (strcmp(callee, "all") == 0) {
821      assert(op[0]->type->is_boolean());
822      for (unsigned c = 0; c < op[0]->type->components(); c++) {
823	 if (!op[0]->value.b[c])
824	    return new(mem_ctx) ir_constant(false);
825      }
826      return new(mem_ctx) ir_constant(true);
827   } else if (strcmp(callee, "any") == 0) {
828      assert(op[0]->type->is_boolean());
829      for (unsigned c = 0; c < op[0]->type->components(); c++) {
830	 if (op[0]->value.b[c])
831	    return new(mem_ctx) ir_constant(true);
832      }
833      return new(mem_ctx) ir_constant(false);
834   } else if (strcmp(callee, "acos") == 0) {
835      assert(op[0]->type->is_float());
836      for (unsigned c = 0; c < op[0]->type->components(); c++)
837	 data.f[c] = acosf(op[0]->value.f[c]);
838   } else if (strcmp(callee, "asin") == 0) {
839      assert(op[0]->type->is_float());
840      for (unsigned c = 0; c < op[0]->type->components(); c++)
841	 data.f[c] = asinf(op[0]->value.f[c]);
842   } else if (strcmp(callee, "atan") == 0) {
843      assert(op[0]->type->is_float());
844      if (num_parameters == 2) {
845	 assert(op[1]->type->is_float());
846	 for (unsigned c = 0; c < op[0]->type->components(); c++)
847	    data.f[c] = atan2f(op[0]->value.f[c], op[1]->value.f[c]);
848      } else {
849	 for (unsigned c = 0; c < op[0]->type->components(); c++)
850	    data.f[c] = atanf(op[0]->value.f[c]);
851      }
852   } else if (strcmp(callee, "dFdx") == 0 || strcmp(callee, "dFdy") == 0) {
853      return ir_constant::zero(mem_ctx, this->type);
854   } else if (strcmp(callee, "ceil") == 0) {
855      expr = new(mem_ctx) ir_expression(ir_unop_ceil, type, op[0], NULL);
856   } else if (strcmp(callee, "clamp") == 0) {
857      assert(num_parameters == 3);
858      unsigned c1_inc = op[1]->type->is_scalar() ? 0 : 1;
859      unsigned c2_inc = op[2]->type->is_scalar() ? 0 : 1;
860      for (unsigned c = 0, c1 = 0, c2 = 0;
861	   c < op[0]->type->components();
862	   c1 += c1_inc, c2 += c2_inc, c++) {
863
864	 switch (op[0]->type->base_type) {
865	 case GLSL_TYPE_UINT:
866	    data.u[c] = CLAMP(op[0]->value.u[c], op[1]->value.u[c1],
867			      op[2]->value.u[c2]);
868	    break;
869	 case GLSL_TYPE_INT:
870	    data.i[c] = CLAMP(op[0]->value.i[c], op[1]->value.i[c1],
871			      op[2]->value.i[c2]);
872	    break;
873	 case GLSL_TYPE_FLOAT:
874	    data.f[c] = CLAMP(op[0]->value.f[c], op[1]->value.f[c1],
875			      op[2]->value.f[c2]);
876	    break;
877	 default:
878	    assert(!"Should not get here.");
879	 }
880      }
881   } else if (strcmp(callee, "cos") == 0) {
882      expr = new(mem_ctx) ir_expression(ir_unop_cos, type, op[0], NULL);
883   } else if (strcmp(callee, "cosh") == 0) {
884      assert(op[0]->type->is_float());
885      for (unsigned c = 0; c < op[0]->type->components(); c++)
886	 data.f[c] = coshf(op[0]->value.f[c]);
887   } else if (strcmp(callee, "cross") == 0) {
888      expr = new(mem_ctx) ir_expression(ir_binop_cross, type, op[0], op[1]);
889   } else if (strcmp(callee, "degrees") == 0) {
890      assert(op[0]->type->is_float());
891      for (unsigned c = 0; c < op[0]->type->components(); c++)
892	 data.f[c] = 180.0/M_PI * op[0]->value.f[c];
893   } else if (strcmp(callee, "distance") == 0) {
894      assert(op[0]->type->is_float() && op[1]->type->is_float());
895      float length_squared = 0.0;
896      for (unsigned c = 0; c < op[0]->type->components(); c++) {
897	 float t = op[0]->value.f[c] - op[1]->value.f[c];
898	 length_squared += t * t;
899      }
900      return new(mem_ctx) ir_constant(sqrtf(length_squared));
901   } else if (strcmp(callee, "dot") == 0) {
902      return new(mem_ctx) ir_constant(dot(op[0], op[1]));
903   } else if (strcmp(callee, "equal") == 0) {
904      assert(op[0]->type->is_vector() && op[1] && op[1]->type->is_vector());
905      for (unsigned c = 0; c < op[0]->type->components(); c++) {
906	 switch (op[0]->type->base_type) {
907	 case GLSL_TYPE_UINT:
908	    data.b[c] = op[0]->value.u[c] == op[1]->value.u[c];
909	    break;
910	 case GLSL_TYPE_INT:
911	    data.b[c] = op[0]->value.i[c] == op[1]->value.i[c];
912	    break;
913	 case GLSL_TYPE_FLOAT:
914	    data.b[c] = op[0]->value.f[c] == op[1]->value.f[c];
915	    break;
916	 case GLSL_TYPE_BOOL:
917	    data.b[c] = op[0]->value.b[c] == op[1]->value.b[c];
918	    break;
919	 default:
920	    assert(!"Should not get here.");
921	 }
922      }
923   } else if (strcmp(callee, "exp") == 0) {
924      expr = new(mem_ctx) ir_expression(ir_unop_exp, type, op[0], NULL);
925   } else if (strcmp(callee, "exp2") == 0) {
926      expr = new(mem_ctx) ir_expression(ir_unop_exp2, type, op[0], NULL);
927   } else if (strcmp(callee, "faceforward") == 0) {
928      if (dot(op[2], op[1]) < 0)
929	 return op[0];
930      for (unsigned c = 0; c < op[0]->type->components(); c++)
931	 data.f[c] = -op[0]->value.f[c];
932   } else if (strcmp(callee, "floor") == 0) {
933      expr = new(mem_ctx) ir_expression(ir_unop_floor, type, op[0], NULL);
934   } else if (strcmp(callee, "fract") == 0) {
935      expr = new(mem_ctx) ir_expression(ir_unop_fract, type, op[0], NULL);
936   } else if (strcmp(callee, "fwidth") == 0) {
937      return ir_constant::zero(mem_ctx, this->type);
938   } else if (strcmp(callee, "greaterThan") == 0) {
939      assert(op[0]->type->is_vector() && op[1] && op[1]->type->is_vector());
940      for (unsigned c = 0; c < op[0]->type->components(); c++) {
941	 switch (op[0]->type->base_type) {
942	 case GLSL_TYPE_UINT:
943	    data.b[c] = op[0]->value.u[c] > op[1]->value.u[c];
944	    break;
945	 case GLSL_TYPE_INT:
946	    data.b[c] = op[0]->value.i[c] > op[1]->value.i[c];
947	    break;
948	 case GLSL_TYPE_FLOAT:
949	    data.b[c] = op[0]->value.f[c] > op[1]->value.f[c];
950	    break;
951	 default:
952	    assert(!"Should not get here.");
953	 }
954      }
955   } else if (strcmp(callee, "greaterThanEqual") == 0) {
956      assert(op[0]->type->is_vector() && op[1] && op[1]->type->is_vector());
957      for (unsigned c = 0; c < op[0]->type->components(); c++) {
958	 switch (op[0]->type->base_type) {
959	 case GLSL_TYPE_UINT:
960	    data.b[c] = op[0]->value.u[c] >= op[1]->value.u[c];
961	    break;
962	 case GLSL_TYPE_INT:
963	    data.b[c] = op[0]->value.i[c] >= op[1]->value.i[c];
964	    break;
965	 case GLSL_TYPE_FLOAT:
966	    data.b[c] = op[0]->value.f[c] >= op[1]->value.f[c];
967	    break;
968	 default:
969	    assert(!"Should not get here.");
970	 }
971      }
972   } else if (strcmp(callee, "inversesqrt") == 0) {
973      expr = new(mem_ctx) ir_expression(ir_unop_rsq, type, op[0], NULL);
974   } else if (strcmp(callee, "length") == 0) {
975      return new(mem_ctx) ir_constant(sqrtf(dot(op[0], op[0])));
976   } else if (strcmp(callee, "lessThan") == 0) {
977      assert(op[0]->type->is_vector() && op[1] && op[1]->type->is_vector());
978      for (unsigned c = 0; c < op[0]->type->components(); c++) {
979	 switch (op[0]->type->base_type) {
980	 case GLSL_TYPE_UINT:
981	    data.b[c] = op[0]->value.u[c] < op[1]->value.u[c];
982	    break;
983	 case GLSL_TYPE_INT:
984	    data.b[c] = op[0]->value.i[c] < op[1]->value.i[c];
985	    break;
986	 case GLSL_TYPE_FLOAT:
987	    data.b[c] = op[0]->value.f[c] < op[1]->value.f[c];
988	    break;
989	 default:
990	    assert(!"Should not get here.");
991	 }
992      }
993   } else if (strcmp(callee, "lessThanEqual") == 0) {
994      assert(op[0]->type->is_vector() && op[1] && op[1]->type->is_vector());
995      for (unsigned c = 0; c < op[0]->type->components(); c++) {
996	 switch (op[0]->type->base_type) {
997	 case GLSL_TYPE_UINT:
998	    data.b[c] = op[0]->value.u[c] <= op[1]->value.u[c];
999	    break;
1000	 case GLSL_TYPE_INT:
1001	    data.b[c] = op[0]->value.i[c] <= op[1]->value.i[c];
1002	    break;
1003	 case GLSL_TYPE_FLOAT:
1004	    data.b[c] = op[0]->value.f[c] <= op[1]->value.f[c];
1005	    break;
1006	 default:
1007	    assert(!"Should not get here.");
1008	 }
1009      }
1010   } else if (strcmp(callee, "log") == 0) {
1011      expr = new(mem_ctx) ir_expression(ir_unop_log, type, op[0], NULL);
1012   } else if (strcmp(callee, "log2") == 0) {
1013      expr = new(mem_ctx) ir_expression(ir_unop_log2, type, op[0], NULL);
1014   } else if (strcmp(callee, "matrixCompMult") == 0) {
1015      assert(op[0]->type->is_float() && op[1]->type->is_float());
1016      for (unsigned c = 0; c < op[0]->type->components(); c++)
1017	 data.f[c] = op[0]->value.f[c] * op[1]->value.f[c];
1018   } else if (strcmp(callee, "max") == 0) {
1019      expr = new(mem_ctx) ir_expression(ir_binop_max, type, op[0], op[1]);
1020   } else if (strcmp(callee, "min") == 0) {
1021      expr = new(mem_ctx) ir_expression(ir_binop_min, type, op[0], op[1]);
1022   } else if (strcmp(callee, "mix") == 0) {
1023      assert(op[0]->type->is_float() && op[1]->type->is_float());
1024      if (op[2]->type->is_float()) {
1025	 unsigned c2_inc = op[2]->type->is_scalar() ? 0 : 1;
1026	 unsigned components = op[0]->type->components();
1027	 for (unsigned c = 0, c2 = 0; c < components; c2 += c2_inc, c++) {
1028	    data.f[c] = op[0]->value.f[c] * (1 - op[2]->value.f[c2]) +
1029			op[1]->value.f[c] * op[2]->value.f[c2];
1030	 }
1031      } else {
1032	 assert(op[2]->type->is_boolean());
1033	 for (unsigned c = 0; c < op[0]->type->components(); c++)
1034	    data.f[c] = op[op[2]->value.b[c] ? 1 : 0]->value.f[c];
1035      }
1036   } else if (strcmp(callee, "mod") == 0) {
1037      expr = new(mem_ctx) ir_expression(ir_binop_mod, type, op[0], op[1]);
1038   } else if (strcmp(callee, "normalize") == 0) {
1039      assert(op[0]->type->is_float());
1040      float length = sqrtf(dot(op[0], op[0]));
1041
1042      if (length == 0)
1043	 return ir_constant::zero(mem_ctx, this->type);
1044
1045      for (unsigned c = 0; c < op[0]->type->components(); c++)
1046	 data.f[c] = op[0]->value.f[c] / length;
1047   } else if (strcmp(callee, "not") == 0) {
1048      expr = new(mem_ctx) ir_expression(ir_unop_logic_not, type, op[0], NULL);
1049   } else if (strcmp(callee, "notEqual") == 0) {
1050      assert(op[0]->type->is_vector() && op[1] && op[1]->type->is_vector());
1051      for (unsigned c = 0; c < op[0]->type->components(); c++) {
1052	 switch (op[0]->type->base_type) {
1053	 case GLSL_TYPE_UINT:
1054	    data.b[c] = op[0]->value.u[c] != op[1]->value.u[c];
1055	    break;
1056	 case GLSL_TYPE_INT:
1057	    data.b[c] = op[0]->value.i[c] != op[1]->value.i[c];
1058	    break;
1059	 case GLSL_TYPE_FLOAT:
1060	    data.b[c] = op[0]->value.f[c] != op[1]->value.f[c];
1061	    break;
1062	 case GLSL_TYPE_BOOL:
1063	    data.b[c] = op[0]->value.b[c] != op[1]->value.b[c];
1064	    break;
1065	 default:
1066	    assert(!"Should not get here.");
1067	 }
1068      }
1069   } else if (strcmp(callee, "outerProduct") == 0) {
1070      assert(op[0]->type->is_vector() && op[1]->type->is_vector());
1071      const unsigned m = op[0]->type->vector_elements;
1072      const unsigned n = op[1]->type->vector_elements;
1073      for (unsigned j = 0; j < n; j++) {
1074	 for (unsigned i = 0; i < m; i++) {
1075	    data.f[i+m*j] = op[0]->value.f[i] * op[1]->value.f[j];
1076	 }
1077      }
1078   } else if (strcmp(callee, "pow") == 0) {
1079      expr = new(mem_ctx) ir_expression(ir_binop_pow, type, op[0], op[1]);
1080   } else if (strcmp(callee, "radians") == 0) {
1081      assert(op[0]->type->is_float());
1082      for (unsigned c = 0; c < op[0]->type->components(); c++)
1083	 data.f[c] = M_PI/180.0 * op[0]->value.f[c];
1084   } else if (strcmp(callee, "reflect") == 0) {
1085      assert(op[0]->type->is_float());
1086      float dot_NI = dot(op[1], op[0]);
1087      for (unsigned c = 0; c < op[0]->type->components(); c++)
1088	 data.f[c] = op[0]->value.f[c] - 2 * dot_NI * op[1]->value.f[c];
1089   } else if (strcmp(callee, "refract") == 0) {
1090      const float eta = op[2]->value.f[0];
1091      const float dot_NI = dot(op[1], op[0]);
1092      const float k = 1.0 - eta * eta * (1.0 - dot_NI * dot_NI);
1093      if (k < 0.0) {
1094	 return ir_constant::zero(mem_ctx, this->type);
1095      } else {
1096	 for (unsigned c = 0; c < type->components(); c++) {
1097	    data.f[c] = eta * op[0]->value.f[c] - (eta * dot_NI + sqrtf(k))
1098			    * op[1]->value.f[c];
1099	 }
1100      }
1101   } else if (strcmp(callee, "sign") == 0) {
1102      expr = new(mem_ctx) ir_expression(ir_unop_sign, type, op[0], NULL);
1103   } else if (strcmp(callee, "sin") == 0) {
1104      expr = new(mem_ctx) ir_expression(ir_unop_sin, type, op[0], NULL);
1105   } else if (strcmp(callee, "sinh") == 0) {
1106      assert(op[0]->type->is_float());
1107      for (unsigned c = 0; c < op[0]->type->components(); c++)
1108	 data.f[c] = sinhf(op[0]->value.f[c]);
1109   } else if (strcmp(callee, "smoothstep") == 0) {
1110      assert(num_parameters == 3);
1111      assert(op[1]->type == op[0]->type);
1112      unsigned edge_inc = op[0]->type->is_scalar() ? 0 : 1;
1113      for (unsigned c = 0, e = 0; c < type->components(); e += edge_inc, c++) {
1114	 const float edge0 = op[0]->value.f[e];
1115	 const float edge1 = op[1]->value.f[e];
1116	 if (edge0 == edge1) {
1117	    data.f[c] = 0.0; /* Avoid a crash - results are undefined anyway */
1118	 } else {
1119	    const float numerator = op[2]->value.f[c] - edge0;
1120	    const float denominator = edge1 - edge0;
1121	    const float t = CLAMP(numerator/denominator, 0, 1);
1122	    data.f[c] = t * t * (3 - 2 * t);
1123	 }
1124      }
1125   } else if (strcmp(callee, "sqrt") == 0) {
1126      expr = new(mem_ctx) ir_expression(ir_unop_sqrt, type, op[0], NULL);
1127   } else if (strcmp(callee, "step") == 0) {
1128      assert(op[0]->type->is_float() && op[1]->type->is_float());
1129      /* op[0] (edge) may be either a scalar or a vector */
1130      const unsigned c0_inc = op[0]->type->is_scalar() ? 0 : 1;
1131      for (unsigned c = 0, c0 = 0; c < type->components(); c0 += c0_inc, c++)
1132	 data.f[c] = (op[1]->value.f[c] < op[0]->value.f[c0]) ? 0.0 : 1.0;
1133   } else if (strcmp(callee, "tan") == 0) {
1134      assert(op[0]->type->is_float());
1135      for (unsigned c = 0; c < op[0]->type->components(); c++)
1136	 data.f[c] = tanf(op[0]->value.f[c]);
1137   } else if (strcmp(callee, "tanh") == 0) {
1138      assert(op[0]->type->is_float());
1139      for (unsigned c = 0; c < op[0]->type->components(); c++)
1140	 data.f[c] = tanhf(op[0]->value.f[c]);
1141   } else if (strcmp(callee, "transpose") == 0) {
1142      assert(op[0]->type->is_matrix());
1143      const unsigned n = op[0]->type->vector_elements;
1144      const unsigned m = op[0]->type->matrix_columns;
1145      for (unsigned j = 0; j < m; j++) {
1146	 for (unsigned i = 0; i < n; i++) {
1147	    data.f[m*i+j] += op[0]->value.f[i+n*j];
1148	 }
1149      }
1150   } else {
1151      /* Unsupported builtin - some are not allowed in constant expressions. */
1152      return NULL;
1153   }
1154
1155   if (expr != NULL)
1156      return expr->constant_expression_value();
1157
1158   return new(mem_ctx) ir_constant(this->type, &data);
1159}
1160