Implement "sin" and "cos" builtins via new expression operators.
[mesa.git] / ir.cpp
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 #include <string.h>
24 #include "main/imports.h"
25 #include "ir.h"
26 #include "ir_visitor.h"
27 #include "glsl_types.h"
28
29 ir_assignment::ir_assignment(ir_rvalue *lhs, ir_rvalue *rhs,
30 ir_rvalue *condition)
31 {
32 this->lhs = lhs;
33 this->rhs = rhs;
34 this->condition = condition;
35 }
36
37
38 ir_expression::ir_expression(int op, const struct glsl_type *type,
39 ir_rvalue *op0, ir_rvalue *op1)
40 {
41 this->type = type;
42 this->operation = ir_expression_operation(op);
43 this->operands[0] = op0;
44 this->operands[1] = op1;
45 }
46
47 unsigned int
48 ir_expression::get_num_operands(ir_expression_operation op)
49 {
50 /* Update ir_print_visitor.cpp when updating this list. */
51 const int num_operands[] = {
52 1, /* ir_unop_bit_not */
53 1, /* ir_unop_logic_not */
54 1, /* ir_unop_neg */
55 1, /* ir_unop_abs */
56 1, /* ir_unop_sign */
57 1, /* ir_unop_rcp */
58 1, /* ir_unop_rsq */
59 1, /* ir_unop_sqrt */
60 1, /* ir_unop_exp */
61 1, /* ir_unop_log */
62 1, /* ir_unop_exp2 */
63 1, /* ir_unop_log2 */
64 1, /* ir_unop_f2i */
65 1, /* ir_unop_i2f */
66 1, /* ir_unop_f2b */
67 1, /* ir_unop_b2f */
68 1, /* ir_unop_i2b */
69 1, /* ir_unop_b2i */
70 1, /* ir_unop_u2f */
71
72 1, /* ir_unop_trunc */
73 1, /* ir_unop_ceil */
74 1, /* ir_unop_floor */
75
76 1, /* ir_unop_sin */
77 1, /* ir_unop_cos */
78
79 2, /* ir_binop_add */
80 2, /* ir_binop_sub */
81 2, /* ir_binop_mul */
82 2, /* ir_binop_div */
83 2, /* ir_binop_mod */
84
85 2, /* ir_binop_less */
86 2, /* ir_binop_greater */
87 2, /* ir_binop_lequal */
88 2, /* ir_binop_gequal */
89 2, /* ir_binop_equal */
90 2, /* ir_binop_nequal */
91
92 2, /* ir_binop_lshift */
93 2, /* ir_binop_rshift */
94 2, /* ir_binop_bit_and */
95 2, /* ir_binop_bit_xor */
96 2, /* ir_binop_bit_or */
97
98 2, /* ir_binop_logic_and */
99 2, /* ir_binop_logic_xor */
100 2, /* ir_binop_logic_or */
101
102 2, /* ir_binop_dot */
103 2, /* ir_binop_min */
104 2, /* ir_binop_max */
105
106 2, /* ir_binop_pow */
107 };
108
109 assert(sizeof(num_operands) / sizeof(num_operands[0]) == ir_binop_pow + 1);
110
111 return num_operands[op];
112 }
113
114 static const char *const operator_strs[] = {
115 "~",
116 "!",
117 "neg",
118 "abs",
119 "sign",
120 "rcp",
121 "rsq",
122 "sqrt",
123 "exp",
124 "log",
125 "exp2",
126 "log2",
127 "f2i",
128 "i2f",
129 "f2b",
130 "b2f",
131 "i2b",
132 "b2i",
133 "u2f",
134 "trunc",
135 "ceil",
136 "floor",
137 "sin",
138 "cos",
139 "+",
140 "-",
141 "*",
142 "/",
143 "%",
144 "<",
145 ">",
146 "<=",
147 ">=",
148 "==",
149 "!=",
150 "<<",
151 ">>",
152 "&",
153 "^",
154 "|",
155 "&&",
156 "^^",
157 "||",
158 "dot",
159 "min",
160 "max",
161 "pow",
162 };
163
164 const char *ir_expression::operator_string()
165 {
166 assert((unsigned int) operation <=
167 sizeof(operator_strs) / sizeof(operator_strs[0]));
168 return operator_strs[operation];
169 }
170
171 ir_expression_operation
172 ir_expression::get_operator(const char *str)
173 {
174 const int operator_count = sizeof(operator_strs) / sizeof(operator_strs[0]);
175 for (int op = 0; op < operator_count; op++) {
176 if (strcmp(str, operator_strs[op]) == 0)
177 return (ir_expression_operation) op;
178 }
179 return (ir_expression_operation) -1;
180 }
181
182 ir_constant::ir_constant(const struct glsl_type *type, const void *data)
183 {
184 unsigned size = 0;
185
186 this->type = type;
187 switch (type->base_type) {
188 case GLSL_TYPE_UINT: size = sizeof(this->value.u[0]); break;
189 case GLSL_TYPE_INT: size = sizeof(this->value.i[0]); break;
190 case GLSL_TYPE_FLOAT: size = sizeof(this->value.f[0]); break;
191 case GLSL_TYPE_BOOL: size = sizeof(this->value.b[0]); break;
192 default:
193 /* FINISHME: What to do? Exceptions are not the answer.
194 */
195 break;
196 }
197
198 memcpy(& this->value, data, size * type->components());
199 }
200
201 ir_constant::ir_constant(float f)
202 {
203 this->type = glsl_type::float_type;
204 this->value.f[0] = f;
205 }
206
207 ir_constant::ir_constant(unsigned int u)
208 {
209 this->type = glsl_type::uint_type;
210 this->value.u[0] = u;
211 }
212
213 ir_constant::ir_constant(int i)
214 {
215 this->type = glsl_type::int_type;
216 this->value.i[0] = i;
217 }
218
219 ir_constant::ir_constant(bool b)
220 {
221 this->type = glsl_type::bool_type;
222 this->value.b[0] = b;
223 }
224
225
226 ir_dereference::ir_dereference(ir_instruction *var)
227 {
228 this->mode = ir_reference_variable;
229 this->var = var;
230 this->type = (var != NULL) ? var->type : glsl_type::error_type;
231 }
232
233
234 ir_dereference::ir_dereference(ir_instruction *var,
235 ir_rvalue *array_index)
236 : mode(ir_reference_array), var(var)
237 {
238 type = glsl_type::error_type;
239
240 if (var != NULL) {
241 const glsl_type *const vt = var->type;
242
243 if (vt->is_array()) {
244 type = vt->element_type();
245 } else if (vt->is_matrix()) {
246 type = vt->column_type();
247 } else if (vt->is_vector()) {
248 type = vt->get_base_type();
249 }
250 }
251
252 this->selector.array_index = array_index;
253 }
254
255 ir_dereference::ir_dereference(ir_instruction *variable, const char *field)
256 : mode(ir_reference_record), var(variable)
257 {
258 this->selector.field = field;
259 this->type = (var != NULL)
260 ? var->type->field_type(field) : glsl_type::error_type;
261 }
262
263 bool
264 ir_dereference::is_lvalue()
265 {
266 if (var == NULL)
267 return false;
268
269 ir_variable *const as_var = var->as_variable();
270 if (mode == ir_reference_variable) {
271 if (as_var == NULL)
272 return false;
273
274 if (as_var->type->is_array() && !as_var->array_lvalue)
275 return false;
276 }
277
278 if (as_var != NULL)
279 return !as_var->read_only;
280
281 /* Walk up the dereference chain and figure out if the variable is read-only.
282 */
283 return this->var->as_rvalue()->is_lvalue();
284 }
285
286 ir_swizzle::ir_swizzle(ir_rvalue *val, unsigned x, unsigned y, unsigned z,
287 unsigned w, unsigned count)
288 : val(val)
289 {
290 assert((count >= 1) && (count <= 4));
291
292 const unsigned dup_mask = 0
293 | ((count > 1) ? ((1U << y) & ((1U << x) )) : 0)
294 | ((count > 2) ? ((1U << z) & ((1U << x) | (1U << y) )) : 0)
295 | ((count > 3) ? ((1U << w) & ((1U << x) | (1U << y) | (1U << z))) : 0);
296
297 assert(x <= 3);
298 assert(y <= 3);
299 assert(z <= 3);
300 assert(w <= 3);
301
302 mask.x = x;
303 mask.y = y;
304 mask.z = z;
305 mask.w = w;
306 mask.num_components = count;
307 mask.has_duplicates = dup_mask != 0;
308
309 /* Based on the number of elements in the swizzle and the base type
310 * (i.e., float, int, unsigned, or bool) of the vector being swizzled,
311 * generate the type of the resulting value.
312 */
313 type = glsl_type::get_instance(val->type->base_type, mask.num_components, 1);
314 }
315
316 ir_swizzle::ir_swizzle(ir_rvalue *val, ir_swizzle_mask mask)
317 {
318 this->val = val;
319 this->mask = mask;
320 this->type = glsl_type::get_instance(val->type->base_type,
321 mask.num_components, 1);
322 }
323
324 #define X 1
325 #define R 5
326 #define S 9
327 #define I 13
328
329 ir_swizzle *
330 ir_swizzle::create(ir_rvalue *val, const char *str, unsigned vector_length)
331 {
332 /* For each possible swizzle character, this table encodes the value in
333 * \c idx_map that represents the 0th element of the vector. For invalid
334 * swizzle characters (e.g., 'k'), a special value is used that will allow
335 * detection of errors.
336 */
337 static const unsigned char base_idx[26] = {
338 /* a b c d e f g h i j k l m */
339 R, R, I, I, I, I, R, I, I, I, I, I, I,
340 /* n o p q r s t u v w x y z */
341 I, I, S, S, R, S, S, I, I, X, X, X, X
342 };
343
344 /* Each valid swizzle character has an entry in the previous table. This
345 * table encodes the base index encoded in the previous table plus the actual
346 * index of the swizzle character. When processing swizzles, the first
347 * character in the string is indexed in the previous table. Each character
348 * in the string is indexed in this table, and the value found there has the
349 * value form the first table subtracted. The result must be on the range
350 * [0,3].
351 *
352 * For example, the string "wzyx" will get X from the first table. Each of
353 * the charcaters will get X+3, X+2, X+1, and X+0 from this table. After
354 * subtraction, the swizzle values are { 3, 2, 1, 0 }.
355 *
356 * The string "wzrg" will get X from the first table. Each of the characters
357 * will get X+3, X+2, R+0, and R+1 from this table. After subtraction, the
358 * swizzle values are { 3, 2, 4, 5 }. Since 4 and 5 are outside the range
359 * [0,3], the error is detected.
360 */
361 static const unsigned char idx_map[26] = {
362 /* a b c d e f g h i j k l m */
363 R+3, R+2, 0, 0, 0, 0, R+1, 0, 0, 0, 0, 0, 0,
364 /* n o p q r s t u v w x y z */
365 0, 0, S+2, S+3, R+0, S+0, S+1, 0, 0, X+3, X+0, X+1, X+2
366 };
367
368 int swiz_idx[4] = { 0, 0, 0, 0 };
369 unsigned i;
370
371
372 /* Validate the first character in the swizzle string and look up the base
373 * index value as described above.
374 */
375 if ((str[0] < 'a') || (str[0] > 'z'))
376 return NULL;
377
378 const unsigned base = base_idx[str[0] - 'a'];
379
380
381 for (i = 0; (i < 4) && (str[i] != '\0'); i++) {
382 /* Validate the next character, and, as described above, convert it to a
383 * swizzle index.
384 */
385 if ((str[i] < 'a') || (str[i] > 'z'))
386 return NULL;
387
388 swiz_idx[i] = idx_map[str[i] - 'a'] - base;
389 if ((swiz_idx[i] < 0) || (swiz_idx[i] >= (int) vector_length))
390 return NULL;
391 }
392
393 if (str[i] != '\0')
394 return NULL;
395
396 return new ir_swizzle(val, swiz_idx[0], swiz_idx[1], swiz_idx[2],
397 swiz_idx[3], i);
398 }
399
400 #undef X
401 #undef R
402 #undef S
403 #undef I
404
405
406 ir_variable::ir_variable(const struct glsl_type *type, const char *name)
407 : max_array_access(0), read_only(false), centroid(false), invariant(false),
408 mode(ir_var_auto), interpolation(ir_var_smooth)
409 {
410 this->type = type;
411 this->name = name;
412 this->constant_value = NULL;
413
414 if (type && type->base_type == GLSL_TYPE_SAMPLER)
415 this->read_only = true;
416 }
417
418
419 ir_function_signature::ir_function_signature(const glsl_type *return_type)
420 : return_type(return_type), is_defined(false)
421 {
422 /* empty */
423 }
424
425
426 const char *
427 ir_function_signature::qualifiers_match(exec_list *params)
428 {
429 exec_list_iterator iter_a = parameters.iterator();
430 exec_list_iterator iter_b = params->iterator();
431
432 /* check that the qualifiers match. */
433 while (iter_a.has_next()) {
434 ir_variable *a = (ir_variable *)iter_a.get();
435 ir_variable *b = (ir_variable *)iter_b.get();
436
437 if (a->read_only != b->read_only ||
438 a->interpolation != b->interpolation ||
439 a->centroid != b->centroid) {
440
441 /* parameter a's qualifiers don't match */
442 return a->name;
443 }
444
445 iter_a.next();
446 iter_b.next();
447 }
448 return NULL;
449 }
450
451
452 void
453 ir_function_signature::replace_parameters(exec_list *new_params)
454 {
455 /* Destroy all of the previous parameter information. If the previous
456 * parameter information comes from the function prototype, it may either
457 * specify incorrect parameter names or not have names at all.
458 */
459 foreach_iter(exec_list_iterator, iter, parameters) {
460 assert(((ir_instruction *) iter.get())->as_variable() != NULL);
461
462 iter.remove();
463 delete (ir_instruction*) iter.get();
464 }
465
466 new_params->move_nodes_to(&parameters);
467 }
468
469
470 ir_function::ir_function(const char *name)
471 : name(name)
472 {
473 /* empty */
474 }
475
476
477 ir_call *
478 ir_call::get_error_instruction()
479 {
480 ir_call *call = new ir_call;
481
482 call->type = glsl_type::error_type;
483 return call;
484 }
485
486 void
487 visit_exec_list(exec_list *list, ir_visitor *visitor)
488 {
489 foreach_iter(exec_list_iterator, iter, *list) {
490 ((ir_instruction *)iter.get())->accept(visitor);
491 }
492 }
493