blob: 04ecb582e482268f3f18a85ab1210b5974e4f707 [file] [log] [blame]
Ian Romanick986b8f72010-03-10 13:58:12 -08001/* -*- c++ -*- */
Ian Romanicka87ac252010-02-22 13:19:34 -08002/*
3 * Copyright © 2010 Intel Corporation
4 *
5 * Permission is hereby granted, free of charge, to any person obtaining a
6 * copy of this software and associated documentation files (the "Software"),
7 * to deal in the Software without restriction, including without limitation
8 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
9 * and/or sell copies of the Software, and to permit persons to whom the
10 * Software is furnished to do so, subject to the following conditions:
11 *
12 * The above copyright notice and this permission notice (including the next
13 * paragraph) shall be included in all copies or substantial portions of the
14 * Software.
15 *
16 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
17 * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
18 * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL
19 * THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
20 * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
21 * FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER
22 * DEALINGS IN THE SOFTWARE.
23 */
24
Ian Romanicke309a602010-03-15 15:20:15 -070025#pragma once
26#ifndef IR_H
27#define IR_H
28
Eric Anholtac95f2f2010-06-22 10:38:52 -070029#include <cstdio>
30#include <cstdlib>
31
Ian Romanick0044e7e2010-03-08 23:44:00 -080032#include "list.h"
Ian Romanick78b51b02010-03-09 16:23:37 -080033#include "ir_visitor.h"
Ian Romanick8895bae2010-05-14 12:39:23 -070034#include "ir_hierarchical_visitor.h"
Ian Romanick0044e7e2010-03-08 23:44:00 -080035
Ian Romanicka87ac252010-02-22 13:19:34 -080036struct ir_program {
37 void *bong_hits;
38};
39
Ian Romanicka87ac252010-02-22 13:19:34 -080040/**
41 * Base class of all IR instructions
42 */
Ian Romanick0044e7e2010-03-08 23:44:00 -080043class ir_instruction : public exec_node {
Ian Romanicka87ac252010-02-22 13:19:34 -080044public:
Ian Romanicka87ac252010-02-22 13:19:34 -080045 const struct glsl_type *type;
46
Ian Romanick1cf43a42010-03-30 16:56:50 -070047 class ir_constant *constant_expression_value();
Eric Anholte46a4542010-06-22 12:09:21 -070048
49 /** ir_print_visitor helper for debugging. */
50 void print(void);
51
Ian Romanick78b51b02010-03-09 16:23:37 -080052 virtual void accept(ir_visitor *) = 0;
Ian Romanick8895bae2010-05-14 12:39:23 -070053 virtual ir_visitor_status accept(ir_hierarchical_visitor *) = 0;
Ian Romanick78b51b02010-03-09 16:23:37 -080054
Kenneth Graunke44e1dfa2010-03-25 23:30:28 -070055 /**
56 * \name IR instruction downcast functions
57 *
58 * These functions either cast the object to a derived class or return
59 * \c NULL if the object's type does not match the specified derived class.
60 * Additional downcast functions will be added as needed.
61 */
62 /*@{*/
63 virtual class ir_variable * as_variable() { return NULL; }
Kenneth Graunke6202cbf2010-04-21 16:02:15 -070064 virtual class ir_function * as_function() { return NULL; }
Kenneth Graunke44e1dfa2010-03-25 23:30:28 -070065 virtual class ir_dereference * as_dereference() { return NULL; }
Eric Anholtb145e902010-05-11 11:31:09 -070066 virtual class ir_dereference_array * as_dereference_array() { return NULL; }
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -070067 virtual class ir_rvalue * as_rvalue() { return NULL; }
Ian Romanick01f8de42010-04-05 17:13:14 -070068 virtual class ir_loop * as_loop() { return NULL; }
Eric Anholtcad97662010-04-07 11:46:26 -070069 virtual class ir_assignment * as_assignment() { return NULL; }
70 virtual class ir_call * as_call() { return NULL; }
71 virtual class ir_return * as_return() { return NULL; }
Eric Anholt5ba94202010-04-14 17:03:03 -070072 virtual class ir_if * as_if() { return NULL; }
Eric Anholt7d211042010-04-16 16:43:47 -070073 virtual class ir_swizzle * as_swizzle() { return NULL; }
Eric Anholt5c89f0e2010-05-04 13:04:40 -070074 virtual class ir_constant * as_constant() { return NULL; }
Kenneth Graunke44e1dfa2010-03-25 23:30:28 -070075 /*@}*/
76
Ian Romanicka87ac252010-02-22 13:19:34 -080077protected:
Kenneth Graunke44e1dfa2010-03-25 23:30:28 -070078 ir_instruction()
Ian Romanickd27ec242010-03-11 14:23:41 -080079 {
80 /* empty */
81 }
Ian Romanicka87ac252010-02-22 13:19:34 -080082};
83
84
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -070085class ir_rvalue : public ir_instruction {
86public:
87 virtual ir_rvalue * as_rvalue()
88 {
89 return this;
90 }
91
92 virtual bool is_lvalue()
93 {
94 return false;
95 }
96
Ian Romanick2b3c4762010-05-14 17:35:42 -070097 /**
98 * Get the variable that is ultimately referenced by an r-value
99 */
100 virtual ir_variable *variable_referenced()
101 {
102 return NULL;
103 }
104
Ian Romanickb067db22010-05-26 11:32:52 -0700105
106 /**
107 * If an r-value is a reference to a whole variable, get that variable
108 *
109 * \return
110 * Pointer to a variable that is completely dereferenced by the r-value. If
111 * the r-value is not a dereference or the dereference does not access the
112 * entire variable (i.e., it's just one array element, struct field), \c NULL
113 * is returned.
114 */
115 virtual ir_variable *whole_variable_referenced()
116 {
117 return NULL;
118 }
119
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700120protected:
Ian Romanickb427c912010-04-07 18:03:50 -0700121 ir_rvalue()
122 {
123 /* empty */
124 }
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700125};
126
127
Ian Romanicka87ac252010-02-22 13:19:34 -0800128enum ir_variable_mode {
129 ir_var_auto = 0,
130 ir_var_uniform,
131 ir_var_in,
132 ir_var_out,
133 ir_var_inout
134};
135
136enum ir_varaible_interpolation {
137 ir_var_smooth = 0,
138 ir_var_flat,
139 ir_var_noperspective
140};
141
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700142
Ian Romanicka87ac252010-02-22 13:19:34 -0800143class ir_variable : public ir_instruction {
144public:
145 ir_variable(const struct glsl_type *, const char *);
146
Kenneth Graunke44e1dfa2010-03-25 23:30:28 -0700147 virtual ir_variable *as_variable()
148 {
149 return this;
150 }
151
Ian Romanick78b51b02010-03-09 16:23:37 -0800152 virtual void accept(ir_visitor *v)
153 {
154 v->visit(this);
155 }
156
Ian Romanick8895bae2010-05-14 12:39:23 -0700157 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
158
Ian Romanick2d394d42010-03-31 17:52:44 -0700159 /**
160 * Duplicate an IR variable
161 *
162 * \note
163 * This will probably be made \c virtual and moved to the base class
164 * eventually.
165 */
166 ir_variable *clone() const
167 {
168 ir_variable *var = new ir_variable(type, name);
169
Ian Romanickb8a21cc2010-04-01 18:31:11 -0700170 var->max_array_access = this->max_array_access;
Ian Romanick2d394d42010-03-31 17:52:44 -0700171 var->read_only = this->read_only;
172 var->centroid = this->centroid;
173 var->invariant = this->invariant;
174 var->mode = this->mode;
175 var->interpolation = this->interpolation;
176
177 return var;
178 }
179
Ian Romanick950ceb22010-06-18 19:00:28 -0700180 /**
181 * Get the string value for the interpolation qualifier
182 *
183 * \return
184 * If none of \c shader_in or \c shader_out is set, an empty string will
185 * be returned. Otherwise the string that would be used in a shader to
186 * specify \c mode will be returned.
187 */
188 const char *interpolation_string() const;
189
Ian Romanicka87ac252010-02-22 13:19:34 -0800190 const char *name;
191
Ian Romanickb8a21cc2010-04-01 18:31:11 -0700192 /**
193 * Highest element accessed with a constant expression array index
194 *
195 * Not used for non-array variables.
196 */
197 unsigned max_array_access;
198
Ian Romanicka87ac252010-02-22 13:19:34 -0800199 unsigned read_only:1;
200 unsigned centroid:1;
201 unsigned invariant:1;
Eric Anholt71df19f2010-04-19 11:10:37 -0700202 /** If the variable is initialized outside of the scope of the shader */
203 unsigned shader_in:1;
204 /**
205 * If the variable value is later used outside of the scope of the shader.
206 */
207 unsigned shader_out:1;
Ian Romanicka87ac252010-02-22 13:19:34 -0800208
209 unsigned mode:3;
210 unsigned interpolation:2;
Ian Romanick9d975372010-04-02 17:17:47 -0700211
212 /**
213 * Flag that the whole array is assignable
214 *
215 * In GLSL 1.20 and later whole arrays are assignable (and comparable for
216 * equality). This flag enables this behavior.
217 */
218 unsigned array_lvalue:1;
Eric Anholt326c6762010-04-06 10:30:54 -0700219
220 /**
Ian Romanickc178c742010-04-07 16:53:54 -0700221 * Emit a warning if this variable is accessed.
222 */
223 const char *warn_extension;
224
225 /**
Eric Anholt326c6762010-04-06 10:30:54 -0700226 * Value assigned in the initializer of a variable declared "const"
227 */
228 ir_constant *constant_value;
Ian Romanicka87ac252010-02-22 13:19:34 -0800229};
230
231
Ian Romanicka87ac252010-02-22 13:19:34 -0800232/*@{*/
Kenneth Graunke9fa99f32010-04-21 12:30:22 -0700233/**
234 * The representation of a function instance; may be the full definition or
235 * simply a prototype.
236 */
Ian Romanicka87ac252010-02-22 13:19:34 -0800237class ir_function_signature : public ir_instruction {
Eric Anholt894ea972010-04-07 13:19:11 -0700238 /* An ir_function_signature will be part of the list of signatures in
239 * an ir_function.
240 */
Ian Romanicka87ac252010-02-22 13:19:34 -0800241public:
Ian Romanicke39cc692010-03-23 12:19:13 -0700242 ir_function_signature(const glsl_type *return_type);
Ian Romanicka87ac252010-02-22 13:19:34 -0800243
Ian Romanick78b51b02010-03-09 16:23:37 -0800244 virtual void accept(ir_visitor *v)
245 {
246 v->visit(this);
247 }
248
Ian Romanick8895bae2010-05-14 12:39:23 -0700249 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
250
Ian Romanicka87ac252010-02-22 13:19:34 -0800251 /**
Ian Romanick0f0ea582010-03-31 16:44:12 -0700252 * Get the name of the function for which this is a signature
253 */
254 const char *function_name() const;
255
256 /**
Kenneth Graunkeabd40b12010-04-28 11:49:12 -0700257 * Check whether the qualifiers match between this signature's parameters
258 * and the supplied parameter list. If not, returns the name of the first
259 * parameter with mismatched qualifiers (for use in error messages).
260 */
261 const char *qualifiers_match(exec_list *params);
262
263 /**
Kenneth Graunkebff60132010-04-28 12:44:24 -0700264 * Replace the current parameter list with the given one. This is useful
265 * if the current information came from a prototype, and either has invalid
266 * or missing parameter names.
267 */
268 void replace_parameters(exec_list *new_params);
269
270 /**
Ian Romanicka87ac252010-02-22 13:19:34 -0800271 * Function return type.
272 *
273 * \note This discards the optional precision qualifier.
274 */
275 const struct glsl_type *return_type;
276
277 /**
Eric Anholtf1ddca92010-04-07 12:35:34 -0700278 * List of ir_variable of function parameters.
279 *
280 * This represents the storage. The paramaters passed in a particular
281 * call will be in ir_call::actual_paramaters.
Ian Romanicka87ac252010-02-22 13:19:34 -0800282 */
Ian Romanick0044e7e2010-03-08 23:44:00 -0800283 struct exec_list parameters;
Ian Romanicka87ac252010-02-22 13:19:34 -0800284
Kenneth Graunke9fa99f32010-04-21 12:30:22 -0700285 /** Whether or not this function has a body (which may be empty). */
286 unsigned is_defined:1;
Ian Romanick6a15d5b2010-03-31 16:37:10 -0700287
Eric Anholt894ea972010-04-07 13:19:11 -0700288 /** Body of instructions in the function. */
289 struct exec_list body;
290
Ian Romanick6a15d5b2010-03-31 16:37:10 -0700291private:
292 /** Function of which this signature is one overload. */
293 class ir_function *function;
294
295 friend class ir_function;
Ian Romanicka87ac252010-02-22 13:19:34 -0800296};
297
298
299/**
Kenneth Graunke9fa99f32010-04-21 12:30:22 -0700300 * Header for tracking multiple overloaded functions with the same name.
301 * Contains a list of ir_function_signatures representing each of the
302 * actual functions.
Ian Romanicka87ac252010-02-22 13:19:34 -0800303 */
304class ir_function : public ir_instruction {
305public:
Ian Romanick882dad72010-03-23 17:42:04 -0700306 ir_function(const char *name);
Ian Romanicka87ac252010-02-22 13:19:34 -0800307
Kenneth Graunke6202cbf2010-04-21 16:02:15 -0700308 virtual ir_function *as_function()
309 {
310 return this;
311 }
312
Ian Romanick78b51b02010-03-09 16:23:37 -0800313 virtual void accept(ir_visitor *v)
314 {
315 v->visit(this);
316 }
317
Ian Romanick8895bae2010-05-14 12:39:23 -0700318 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
319
Ian Romanick6a15d5b2010-03-31 16:37:10 -0700320 void add_signature(ir_function_signature *sig)
321 {
322 sig->function = this;
323 signatures.push_tail(sig);
324 }
325
Ian Romanicka87ac252010-02-22 13:19:34 -0800326 /**
Ian Romanick95cd6cc2010-03-31 16:40:26 -0700327 * Get an iterator for the set of function signatures
328 */
329 exec_list_iterator iterator()
330 {
331 return signatures.iterator();
332 }
333
334 /**
Kenneth Graunke0d605cb2010-04-28 12:04:23 -0700335 * Find a signature that matches a set of actual parameters, taking implicit
336 * conversions into account.
Ian Romanick471471f2010-03-11 14:50:30 -0800337 */
338 const ir_function_signature *matching_signature(exec_list *actual_param);
339
340 /**
Kenneth Graunke0d605cb2010-04-28 12:04:23 -0700341 * Find a signature that exactly matches a set of actual parameters without
342 * any implicit type conversions.
343 */
344 ir_function_signature *exact_matching_signature(exec_list *actual_ps);
345
346 /**
Ian Romanicka87ac252010-02-22 13:19:34 -0800347 * Name of the function.
348 */
349 const char *name;
350
Ian Romanicka4775822010-03-31 16:40:58 -0700351private:
Ian Romanick471471f2010-03-11 14:50:30 -0800352 /**
Eric Anholtf1ddca92010-04-07 12:35:34 -0700353 * List of ir_function_signature for each overloaded function with this name.
Ian Romanick471471f2010-03-11 14:50:30 -0800354 */
Ian Romanick0044e7e2010-03-08 23:44:00 -0800355 struct exec_list signatures;
Ian Romanicka87ac252010-02-22 13:19:34 -0800356};
Ian Romanick0f0ea582010-03-31 16:44:12 -0700357
358inline const char *ir_function_signature::function_name() const
359{
360 return function->name;
361}
Ian Romanicka87ac252010-02-22 13:19:34 -0800362/*@}*/
363
Ian Romanicka87ac252010-02-22 13:19:34 -0800364
Ian Romanick3c6fea32010-03-29 14:11:25 -0700365/**
366 * IR instruction representing high-level if-statements
367 */
368class ir_if : public ir_instruction {
369public:
370 ir_if(ir_rvalue *condition)
371 : condition(condition)
372 {
373 /* empty */
374 }
375
Eric Anholt5ba94202010-04-14 17:03:03 -0700376 virtual ir_if *as_if()
377 {
378 return this;
379 }
380
Ian Romanick3c6fea32010-03-29 14:11:25 -0700381 virtual void accept(ir_visitor *v)
382 {
383 v->visit(this);
384 }
385
Ian Romanick8895bae2010-05-14 12:39:23 -0700386 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
387
Ian Romanick3c6fea32010-03-29 14:11:25 -0700388 ir_rvalue *condition;
Eric Anholtf1ddca92010-04-07 12:35:34 -0700389 /** List of ir_instruction for the body of the then branch */
Ian Romanick3c6fea32010-03-29 14:11:25 -0700390 exec_list then_instructions;
Eric Anholtf1ddca92010-04-07 12:35:34 -0700391 /** List of ir_instruction for the body of the else branch */
Ian Romanick3c6fea32010-03-29 14:11:25 -0700392 exec_list else_instructions;
393};
394
395
Ian Romanickfad607a2010-04-05 16:16:07 -0700396/**
397 * IR instruction representing a high-level loop structure.
398 */
399class ir_loop : public ir_instruction {
400public:
401 ir_loop() : from(NULL), to(NULL), increment(NULL), counter(NULL)
402 {
403 /* empty */
404 }
405
406 virtual void accept(ir_visitor *v)
407 {
408 v->visit(this);
409 }
410
Ian Romanick8895bae2010-05-14 12:39:23 -0700411 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
412
Ian Romanick01f8de42010-04-05 17:13:14 -0700413 virtual ir_loop *as_loop()
414 {
415 return this;
416 }
417
Ian Romanickfad607a2010-04-05 16:16:07 -0700418 /**
419 * Get an iterator for the instructions of the loop body
420 */
421 exec_list_iterator iterator()
422 {
423 return body_instructions.iterator();
424 }
425
Eric Anholtf1ddca92010-04-07 12:35:34 -0700426 /** List of ir_instruction that make up the body of the loop. */
Ian Romanickfad607a2010-04-05 16:16:07 -0700427 exec_list body_instructions;
428
429 /**
430 * \name Loop counter and controls
431 */
432 /*@{*/
433 ir_rvalue *from;
434 ir_rvalue *to;
435 ir_rvalue *increment;
436 ir_variable *counter;
437 /*@}*/
438};
439
440
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700441class ir_assignment : public ir_rvalue {
Ian Romanicka87ac252010-02-22 13:19:34 -0800442public:
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700443 ir_assignment(ir_rvalue *lhs, ir_rvalue *rhs, ir_rvalue *condition);
Ian Romanicka87ac252010-02-22 13:19:34 -0800444
Ian Romanick78b51b02010-03-09 16:23:37 -0800445 virtual void accept(ir_visitor *v)
446 {
447 v->visit(this);
448 }
449
Ian Romanick8895bae2010-05-14 12:39:23 -0700450 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
451
Eric Anholtcad97662010-04-07 11:46:26 -0700452 virtual ir_assignment * as_assignment()
453 {
454 return this;
455 }
456
Ian Romanicka87ac252010-02-22 13:19:34 -0800457 /**
458 * Left-hand side of the assignment.
459 */
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700460 ir_rvalue *lhs;
Ian Romanicka87ac252010-02-22 13:19:34 -0800461
462 /**
463 * Value being assigned
Ian Romanicka87ac252010-02-22 13:19:34 -0800464 */
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700465 ir_rvalue *rhs;
Ian Romanicka87ac252010-02-22 13:19:34 -0800466
467 /**
468 * Optional condition for the assignment.
469 */
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700470 ir_rvalue *condition;
Ian Romanicka87ac252010-02-22 13:19:34 -0800471};
472
Kenneth Graunke3b969962010-04-07 17:18:29 -0700473/* Update ir_expression::num_operands() and operator_strs when
Eric Anholt160d0922010-04-01 18:07:08 -1000474 * updating this list.
Kenneth Graunke3b969962010-04-07 17:18:29 -0700475 */
Ian Romanicka87ac252010-02-22 13:19:34 -0800476enum ir_expression_operation {
477 ir_unop_bit_not,
478 ir_unop_logic_not,
479 ir_unop_neg,
480 ir_unop_abs,
Kenneth Graunkea4b7b5a2010-05-03 20:05:57 -0700481 ir_unop_sign,
Ian Romanicka87ac252010-02-22 13:19:34 -0800482 ir_unop_rcp,
483 ir_unop_rsq,
Eric Anholt44d68fd2010-03-27 13:01:51 -0700484 ir_unop_sqrt,
Ian Romanicka87ac252010-02-22 13:19:34 -0800485 ir_unop_exp,
486 ir_unop_log,
Eric Anholt01665262010-03-27 13:56:35 -0700487 ir_unop_exp2,
488 ir_unop_log2,
Ian Romanicka87ac252010-02-22 13:19:34 -0800489 ir_unop_f2i, /**< Float-to-integer conversion. */
490 ir_unop_i2f, /**< Integer-to-float conversion. */
Eric Anholtdc58b3f2010-04-02 02:13:43 -1000491 ir_unop_f2b, /**< Float-to-boolean conversion */
492 ir_unop_b2f, /**< Boolean-to-float conversion */
Eric Anholtc2cb84e2010-04-02 02:17:08 -1000493 ir_unop_i2b, /**< int-to-boolean conversion */
494 ir_unop_b2i, /**< Boolean-to-int conversion */
Ian Romanick6c86ea82010-03-26 16:11:48 -0700495 ir_unop_u2f, /**< Unsigned-to-float conversion. */
Ian Romanicka87ac252010-02-22 13:19:34 -0800496
497 /**
498 * \name Unary floating-point rounding operations.
499 */
500 /*@{*/
501 ir_unop_trunc,
502 ir_unop_ceil,
503 ir_unop_floor,
504 /*@}*/
505
Kenneth Graunke57e7da12010-05-03 22:11:17 -0700506 /**
507 * \name Trigonometric operations.
508 */
509 /*@{*/
510 ir_unop_sin,
511 ir_unop_cos,
512 /*@}*/
513
Kenneth Graunkeb843c7a2010-06-09 14:42:41 -0700514 /**
515 * \name Partial derivatives.
516 */
517 /*@{*/
518 ir_unop_dFdx,
519 ir_unop_dFdy,
520 /*@}*/
521
Ian Romanicka87ac252010-02-22 13:19:34 -0800522 ir_binop_add,
523 ir_binop_sub,
524 ir_binop_mul,
525 ir_binop_div,
526 ir_binop_mod,
527
528 /**
529 * \name Binary comparison operators
530 */
531 /*@{*/
532 ir_binop_less,
533 ir_binop_greater,
534 ir_binop_lequal,
535 ir_binop_gequal,
536 ir_binop_equal,
537 ir_binop_nequal,
538 /*@}*/
539
540 /**
541 * \name Bit-wise binary operations.
542 */
543 /*@{*/
544 ir_binop_lshift,
545 ir_binop_rshift,
546 ir_binop_bit_and,
547 ir_binop_bit_xor,
548 ir_binop_bit_or,
549 /*@}*/
550
551 ir_binop_logic_and,
552 ir_binop_logic_xor,
553 ir_binop_logic_or,
Ian Romanicka87ac252010-02-22 13:19:34 -0800554
555 ir_binop_dot,
556 ir_binop_min,
557 ir_binop_max,
558
559 ir_binop_pow
560};
561
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700562class ir_expression : public ir_rvalue {
Ian Romanicka87ac252010-02-22 13:19:34 -0800563public:
564 ir_expression(int op, const struct glsl_type *type,
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700565 ir_rvalue *, ir_rvalue *);
Ian Romanicka87ac252010-02-22 13:19:34 -0800566
Kenneth Graunke7dd6adb2010-04-07 16:56:57 -0700567 static unsigned int get_num_operands(ir_expression_operation);
568 unsigned int get_num_operands()
569 {
570 return get_num_operands(operation);
571 }
Eric Anholt160d0922010-04-01 18:07:08 -1000572
Kenneth Graunke3b969962010-04-07 17:18:29 -0700573 /**
574 * Return a string representing this expression's operator.
575 */
576 const char *operator_string();
577
578 /**
579 * Do a reverse-lookup to translate the given string into an operator.
580 */
581 static ir_expression_operation get_operator(const char *);
582
Ian Romanick78b51b02010-03-09 16:23:37 -0800583 virtual void accept(ir_visitor *v)
584 {
585 v->visit(this);
586 }
587
Ian Romanick8895bae2010-05-14 12:39:23 -0700588 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
589
Eric Anholtcad97662010-04-07 11:46:26 -0700590 ir_expression *clone();
591
Ian Romanicka87ac252010-02-22 13:19:34 -0800592 ir_expression_operation operation;
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700593 ir_rvalue *operands[2];
Ian Romanicka87ac252010-02-22 13:19:34 -0800594};
595
596
Ian Romanicked45ec62010-03-11 14:34:27 -0800597/**
598 * IR instruction representing a function call
599 */
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700600class ir_call : public ir_rvalue {
Ian Romanicked45ec62010-03-11 14:34:27 -0800601public:
Ian Romanick471471f2010-03-11 14:50:30 -0800602 ir_call(const ir_function_signature *callee, exec_list *actual_parameters)
Ian Romanickb427c912010-04-07 18:03:50 -0700603 : callee(callee)
Ian Romanicked45ec62010-03-11 14:34:27 -0800604 {
Ian Romanick9e7c34b2010-03-23 12:21:18 -0700605 assert(callee->return_type != NULL);
606 type = callee->return_type;
Ian Romanick471471f2010-03-11 14:50:30 -0800607 actual_parameters->move_nodes_to(& this->actual_parameters);
Ian Romanicked45ec62010-03-11 14:34:27 -0800608 }
609
Eric Anholtcad97662010-04-07 11:46:26 -0700610 virtual ir_call *as_call()
611 {
612 return this;
613 }
614
Ian Romanicked45ec62010-03-11 14:34:27 -0800615 virtual void accept(ir_visitor *v)
616 {
617 v->visit(this);
618 }
619
Ian Romanick8895bae2010-05-14 12:39:23 -0700620 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
621
Ian Romanicked45ec62010-03-11 14:34:27 -0800622 /**
623 * Get a generic ir_call object when an error occurs
624 */
625 static ir_call *get_error_instruction();
626
Ian Romanick9878c652010-03-26 17:19:47 -0700627 /**
628 * Get an iterator for the set of acutal parameters
629 */
630 exec_list_iterator iterator()
631 {
632 return actual_parameters.iterator();
633 }
634
Ian Romanick93614bc2010-03-26 17:29:29 -0700635 /**
636 * Get the name of the function being called.
637 */
638 const char *callee_name() const
639 {
Ian Romanick0f0ea582010-03-31 16:44:12 -0700640 return callee->function_name();
Ian Romanick93614bc2010-03-26 17:29:29 -0700641 }
642
Eric Anholtcad97662010-04-07 11:46:26 -0700643 const ir_function_signature *get_callee()
644 {
645 return callee;
646 }
647
648 /**
649 * Generates an inline version of the function before @ir,
650 * returning the return value of the function.
651 */
652 ir_rvalue *generate_inline(ir_instruction *ir);
653
Ian Romanicked45ec62010-03-11 14:34:27 -0800654private:
Ian Romanick471471f2010-03-11 14:50:30 -0800655 ir_call()
Ian Romanickb427c912010-04-07 18:03:50 -0700656 : callee(NULL)
Ian Romanick471471f2010-03-11 14:50:30 -0800657 {
658 /* empty */
659 }
660
661 const ir_function_signature *callee;
Eric Anholtf1ddca92010-04-07 12:35:34 -0700662
663 /* List of ir_rvalue of paramaters passed in this call. */
Ian Romanicked45ec62010-03-11 14:34:27 -0800664 exec_list actual_parameters;
665};
666
667
Ian Romanick9578c872010-03-19 16:44:52 -0700668/**
669 * \name Jump-like IR instructions.
670 *
671 * These include \c break, \c continue, \c return, and \c discard.
672 */
673/*@{*/
674class ir_jump : public ir_instruction {
675protected:
676 ir_jump()
Ian Romanick9578c872010-03-19 16:44:52 -0700677 {
678 /* empty */
679 }
680};
681
682class ir_return : public ir_jump {
683public:
684 ir_return()
685 : value(NULL)
686 {
687 /* empty */
688 }
689
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700690 ir_return(ir_rvalue *value)
Ian Romanick9578c872010-03-19 16:44:52 -0700691 : value(value)
692 {
693 /* empty */
694 }
695
Eric Anholtcad97662010-04-07 11:46:26 -0700696 virtual ir_return *as_return()
697 {
698 return this;
699 }
700
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700701 ir_rvalue *get_value() const
Ian Romanick9578c872010-03-19 16:44:52 -0700702 {
703 return value;
704 }
705
706 virtual void accept(ir_visitor *v)
707 {
708 v->visit(this);
709 }
710
Ian Romanick8895bae2010-05-14 12:39:23 -0700711 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
712
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700713 ir_rvalue *value;
Ian Romanick9578c872010-03-19 16:44:52 -0700714};
Ian Romanickf8e31e02010-04-05 16:28:15 -0700715
716
717/**
718 * Jump instructions used inside loops
719 *
720 * These include \c break and \c continue. The \c break within a loop is
721 * different from the \c break within a switch-statement.
722 *
723 * \sa ir_switch_jump
724 */
725class ir_loop_jump : public ir_jump {
726public:
727 enum jump_mode {
728 jump_break,
729 jump_continue
730 };
731
732 ir_loop_jump(ir_loop *loop, jump_mode mode)
733 : loop(loop), mode(mode)
734 {
735 /* empty */
736 }
737
738 virtual void accept(ir_visitor *v)
739 {
740 v->visit(this);
741 }
742
Ian Romanick8895bae2010-05-14 12:39:23 -0700743 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
744
Ian Romanickf8e31e02010-04-05 16:28:15 -0700745 bool is_break() const
746 {
747 return mode == jump_break;
748 }
749
750 bool is_continue() const
751 {
752 return mode == jump_continue;
753 }
754
755private:
756 /** Loop containing this break instruction. */
757 ir_loop *loop;
758
759 /** Mode selector for the jump instruction. */
760 enum jump_mode mode;
761};
Ian Romanick9578c872010-03-19 16:44:52 -0700762/*@}*/
763
764
Ian Romanick81377c02010-04-28 18:42:36 -0700765/**
766 * Texture sampling opcodes used in ir_texture
767 */
768enum ir_texture_opcode {
769 ir_tex, /* Regular texture look-up */
770 ir_txb, /* Texture look-up with LOD bias */
771 ir_txl, /* Texture look-up with explicit LOD */
772 ir_txd, /* Texture look-up with partial derivatvies */
773 ir_txf /* Texel fetch with explicit LOD */
774};
775
776
777/**
778 * IR instruction to sample a texture
779 *
780 * The specific form of the IR instruction depends on the \c mode value
781 * selected from \c ir_texture_opcodes. In the printed IR, these will
782 * appear as:
783 *
784 * Texel offset
785 * | Projection divisor
786 * | | Shadow comparitor
787 * | | |
788 * v v v
789 * (tex (sampler) (coordinate) (0 0 0) (1) ( ))
790 * (txb (sampler) (coordinate) (0 0 0) (1) ( ) (bias))
791 * (txl (sampler) (coordinate) (0 0 0) (1) ( ) (lod))
792 * (txd (sampler) (coordinate) (0 0 0) (1) ( ) (dPdx dPdy))
793 * (txf (sampler) (coordinate) (0 0 0) (lod))
794 */
795class ir_texture : public ir_rvalue {
796public:
797 ir_texture(enum ir_texture_opcode op)
Kenneth Graunkeb97efa52010-06-09 11:07:53 -0700798 : op(op), projector(NULL), shadow_comparitor(NULL)
Ian Romanick81377c02010-04-28 18:42:36 -0700799 {
800 /* empty */
801 }
802
Kenneth Graunke26d74cd2010-05-26 17:42:03 -0700803 virtual void accept(ir_visitor *v)
804 {
805 v->visit(this);
806 }
807
808 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
809
Kenneth Graunkec30f6e52010-05-26 16:41:47 -0700810 /**
811 * Return a string representing the ir_texture_opcode.
812 */
813 const char *opcode_string();
814
Kenneth Graunke56d3f6a2010-06-03 15:07:34 -0700815 /** Set the sampler and infer the type. */
816 void set_sampler(ir_dereference *sampler);
817
Kenneth Graunkec30f6e52010-05-26 16:41:47 -0700818 /**
819 * Do a reverse-lookup to translate a string into an ir_texture_opcode.
820 */
821 static ir_texture_opcode get_opcode(const char *);
822
Ian Romanick81377c02010-04-28 18:42:36 -0700823 enum ir_texture_opcode op;
824
825 /** Sampler to use for the texture access. */
826 ir_dereference *sampler;
827
828 /** Texture coordinate to sample */
829 ir_rvalue *coordinate;
830
831 /**
832 * Value used for projective divide.
833 *
834 * If there is no projective divide (the common case), this will be
835 * \c NULL. Optimization passes should check for this to point to a constant
836 * of 1.0 and replace that with \c NULL.
837 */
838 ir_rvalue *projector;
839
840 /**
841 * Coordinate used for comparison on shadow look-ups.
842 *
843 * If there is no shadow comparison, this will be \c NULL. For the
844 * \c ir_txf opcode, this *must* be \c NULL.
845 */
846 ir_rvalue *shadow_comparitor;
847
848 /** Explicit texel offsets. */
849 signed char offsets[3];
850
851 union {
852 ir_rvalue *lod; /**< Floating point LOD */
853 ir_rvalue *bias; /**< Floating point LOD bias */
854 struct {
855 ir_rvalue *dPdx; /**< Partial derivative of coordinate wrt X */
856 ir_rvalue *dPdy; /**< Partial derivative of coordinate wrt Y */
857 } grad;
858 } lod_info;
859};
860
861
Ian Romanicka87ac252010-02-22 13:19:34 -0800862struct ir_swizzle_mask {
863 unsigned x:2;
864 unsigned y:2;
865 unsigned z:2;
866 unsigned w:2;
867
868 /**
869 * Number of components in the swizzle.
870 */
Kenneth Graunkef25a5ad2010-03-25 11:22:42 -0700871 unsigned num_components:3;
Ian Romanicka87ac252010-02-22 13:19:34 -0800872
873 /**
874 * Does the swizzle contain duplicate components?
875 *
876 * L-value swizzles cannot contain duplicate components.
877 */
878 unsigned has_duplicates:1;
879};
880
Kenneth Graunkeaffc1412010-03-26 01:20:08 -0700881
882class ir_swizzle : public ir_rvalue {
883public:
884 ir_swizzle(ir_rvalue *, unsigned x, unsigned y, unsigned z, unsigned w,
885 unsigned count);
Eric Anholt05a4e592010-05-03 17:08:01 -0700886 ir_swizzle(ir_rvalue *val, ir_swizzle_mask mask);
Eric Anholtcad97662010-04-07 11:46:26 -0700887
Eric Anholt7d211042010-04-16 16:43:47 -0700888 virtual ir_swizzle *as_swizzle()
889 {
890 return this;
891 }
892
Eric Anholtcad97662010-04-07 11:46:26 -0700893 ir_swizzle *clone()
894 {
895 return new ir_swizzle(this->val, this->mask);
896 }
897
Kenneth Graunkeaffc1412010-03-26 01:20:08 -0700898 /**
899 * Construct an ir_swizzle from the textual representation. Can fail.
900 */
901 static ir_swizzle *create(ir_rvalue *, const char *, unsigned vector_length);
902
903 virtual void accept(ir_visitor *v)
904 {
905 v->visit(this);
906 }
907
Ian Romanick8895bae2010-05-14 12:39:23 -0700908 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
909
Kenneth Graunkeaffc1412010-03-26 01:20:08 -0700910 bool is_lvalue()
911 {
Eric Anholta9fafc62010-03-28 01:29:18 -0700912 return val->is_lvalue() && !mask.has_duplicates;
Kenneth Graunkeaffc1412010-03-26 01:20:08 -0700913 }
914
Ian Romanick2b3c4762010-05-14 17:35:42 -0700915 /**
916 * Get the variable that is ultimately referenced by an r-value
917 */
918 virtual ir_variable *variable_referenced();
919
Kenneth Graunkeaffc1412010-03-26 01:20:08 -0700920 ir_rvalue *val;
921 ir_swizzle_mask mask;
922};
923
924
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700925class ir_dereference : public ir_rvalue {
Ian Romanicka87ac252010-02-22 13:19:34 -0800926public:
Kenneth Graunke44e1dfa2010-03-25 23:30:28 -0700927 virtual ir_dereference *as_dereference()
928 {
929 return this;
930 }
931
Eric Anholtc7da28b2010-04-01 20:27:35 -1000932 bool is_lvalue();
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -0700933
Ian Romanick2b3c4762010-05-14 17:35:42 -0700934 /**
935 * Get the variable that is ultimately referenced by an r-value
936 */
Ian Romanick70fe8b62010-05-19 11:37:35 +0200937 virtual ir_variable *variable_referenced() = 0;
Ian Romanick70fe8b62010-05-19 11:37:35 +0200938};
939
940
941class ir_dereference_variable : public ir_dereference {
942public:
943 ir_dereference_variable(ir_variable *var);
944
945 /**
946 * Get the variable that is ultimately referenced by an r-value
947 */
948 virtual ir_variable *variable_referenced()
949 {
Ian Romanick36ea2862010-05-19 13:52:29 +0200950 return this->var;
Ian Romanick70fe8b62010-05-19 11:37:35 +0200951 }
Ian Romanickf3a002b2010-05-19 12:02:19 +0200952
Ian Romanickb067db22010-05-26 11:32:52 -0700953 virtual ir_variable *whole_variable_referenced()
954 {
955 /* ir_dereference_variable objects always dereference the entire
956 * variable. However, if this dereference is dereferenced by anything
957 * else, the complete deferefernce chain is not a whole-variable
958 * dereference. This method should only be called on the top most
959 * ir_rvalue in a dereference chain.
960 */
961 return this->var;
962 }
963
Ian Romanickc7b10462010-05-19 13:20:12 +0200964 virtual void accept(ir_visitor *v)
965 {
966 v->visit(this);
967 }
968
Ian Romanickf3a002b2010-05-19 12:02:19 +0200969 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
Ian Romanick36ea2862010-05-19 13:52:29 +0200970
971 /**
972 * Object being dereferenced.
973 */
974 ir_variable *var;
Ian Romanick70fe8b62010-05-19 11:37:35 +0200975};
976
977
978class ir_dereference_array : public ir_dereference {
979public:
980 ir_dereference_array(ir_rvalue *value, ir_rvalue *array_index);
981
982 ir_dereference_array(ir_variable *var, ir_rvalue *array_index);
983
Eric Anholtb145e902010-05-11 11:31:09 -0700984 virtual ir_dereference_array *as_dereference_array()
985 {
986 return this;
987 }
988
Ian Romanick70fe8b62010-05-19 11:37:35 +0200989 /**
990 * Get the variable that is ultimately referenced by an r-value
991 */
992 virtual ir_variable *variable_referenced()
993 {
Ian Romanick36ea2862010-05-19 13:52:29 +0200994 return this->array->variable_referenced();
Ian Romanick70fe8b62010-05-19 11:37:35 +0200995 }
996
Ian Romanickc7b10462010-05-19 13:20:12 +0200997 virtual void accept(ir_visitor *v)
998 {
999 v->visit(this);
1000 }
1001
Ian Romanickf3a002b2010-05-19 12:02:19 +02001002 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
Ian Romanick70fe8b62010-05-19 11:37:35 +02001003
Ian Romanick36ea2862010-05-19 13:52:29 +02001004 ir_rvalue *array;
1005 ir_rvalue *array_index;
1006
Ian Romanick70fe8b62010-05-19 11:37:35 +02001007private:
1008 void set_array(ir_rvalue *value);
1009};
1010
1011
1012class ir_dereference_record : public ir_dereference {
1013public:
1014 ir_dereference_record(ir_rvalue *value, const char *field);
1015
1016 ir_dereference_record(ir_variable *var, const char *field);
1017
1018 /**
1019 * Get the variable that is ultimately referenced by an r-value
1020 */
1021 virtual ir_variable *variable_referenced()
1022 {
Ian Romanick36ea2862010-05-19 13:52:29 +02001023 return this->record->variable_referenced();
Ian Romanick70fe8b62010-05-19 11:37:35 +02001024 }
Ian Romanickf3a002b2010-05-19 12:02:19 +02001025
Ian Romanickc7b10462010-05-19 13:20:12 +02001026 virtual void accept(ir_visitor *v)
1027 {
1028 v->visit(this);
1029 }
1030
Ian Romanickf3a002b2010-05-19 12:02:19 +02001031 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
Ian Romanick36ea2862010-05-19 13:52:29 +02001032
1033 ir_rvalue *record;
1034 const char *field;
Ian Romanicka87ac252010-02-22 13:19:34 -08001035};
1036
1037
Ian Romanickbe1d2bf2010-06-11 14:01:44 -07001038/**
1039 * Data stored in an ir_constant
1040 */
1041union ir_constant_data {
1042 unsigned u[16];
1043 int i[16];
1044 float f[16];
1045 bool b[16];
1046};
1047
1048
Kenneth Graunkefb9fb5f2010-03-26 00:25:36 -07001049class ir_constant : public ir_rvalue {
Ian Romanicka87ac252010-02-22 13:19:34 -08001050public:
Ian Romanick824b6592010-06-11 16:57:47 -07001051 ir_constant(const struct glsl_type *type, const ir_constant_data *data);
Eric Anholt3c36b2d2010-03-26 12:07:44 -07001052 ir_constant(bool b);
1053 ir_constant(unsigned int u);
1054 ir_constant(int i);
1055 ir_constant(float f);
Ian Romanicka87ac252010-02-22 13:19:34 -08001056
Ian Romanick989cfc42010-06-04 16:13:35 -07001057 /**
Ian Romanick756a3fa2010-06-04 16:34:38 -07001058 * Construct an ir_constant from a list of ir_constant values
1059 */
1060 ir_constant(const struct glsl_type *type, exec_list *values);
1061
1062 /**
Ian Romanick989cfc42010-06-04 16:13:35 -07001063 * Construct an ir_constant from a scalar component of another ir_constant
1064 *
1065 * The new \c ir_constant inherits the type of the component from the
1066 * source constant.
1067 *
1068 * \note
1069 * In the case of a matrix constant, the new constant is a scalar, \b not
1070 * a vector.
1071 */
1072 ir_constant(const ir_constant *c, unsigned i);
1073
Eric Anholt5c89f0e2010-05-04 13:04:40 -07001074 virtual ir_constant *as_constant()
1075 {
1076 return this;
1077 }
1078
Ian Romanick78b51b02010-03-09 16:23:37 -08001079 virtual void accept(ir_visitor *v)
1080 {
1081 v->visit(this);
1082 }
1083
Ian Romanick8895bae2010-05-14 12:39:23 -07001084 virtual ir_visitor_status accept(ir_hierarchical_visitor *);
1085
Ian Romanick710919f2010-06-09 17:18:04 -07001086 ir_constant *clone();
Eric Anholtcad97662010-04-07 11:46:26 -07001087
Ian Romanicka87ac252010-02-22 13:19:34 -08001088 /**
Ian Romanick31881902010-06-04 16:30:07 -07001089 * Get a particular component of a constant as a specific type
1090 *
1091 * This is useful, for example, to get a value from an integer constant
1092 * as a float or bool. This appears frequently when constructors are
1093 * called with all constant parameters.
1094 */
1095 /*@{*/
1096 bool get_bool_component(unsigned i) const;
1097 float get_float_component(unsigned i) const;
1098 int get_int_component(unsigned i) const;
1099 unsigned get_uint_component(unsigned i) const;
1100 /*@}*/
1101
Ian Romanickb94c29a2010-06-09 17:28:54 -07001102 ir_constant *get_record_field(const char *name);
1103
Ian Romanick31881902010-06-04 16:30:07 -07001104 /**
Ian Romanick1e8b7a72010-06-17 19:50:36 -07001105 * Determine whether a constant has the same value as another constant
1106 */
1107 bool has_value(const ir_constant *) const;
1108
1109 /**
Ian Romanicka87ac252010-02-22 13:19:34 -08001110 * Value of the constant.
1111 *
1112 * The field used to back the values supplied by the constant is determined
1113 * by the type associated with the \c ir_instruction. Constants may be
1114 * scalars, vectors, or matrices.
1115 */
Ian Romanickbe1d2bf2010-06-11 14:01:44 -07001116 union ir_constant_data value;
Ian Romanick7f1ab832010-06-09 17:11:50 -07001117
1118 exec_list components;
Ian Romanick710919f2010-06-09 17:18:04 -07001119
1120private:
1121 /**
1122 * Parameterless constructor only used by the clone method
1123 */
1124 ir_constant(void);
Ian Romanicka87ac252010-02-22 13:19:34 -08001125};
1126
Eric Anholt70b74922010-04-06 11:52:09 -07001127void
1128visit_exec_list(exec_list *list, ir_visitor *visitor);
Ian Romanickadfb0cd2010-03-10 10:43:16 -08001129
Eric Anholt53cdb7e2010-06-22 12:07:21 -07001130void validate_ir_tree(exec_list *instructions);
1131
Ian Romanickadfb0cd2010-03-10 10:43:16 -08001132extern void
1133_mesa_glsl_initialize_variables(exec_list *instructions,
1134 struct _mesa_glsl_parse_state *state);
Ian Romanicke309a602010-03-15 15:20:15 -07001135
Eric Anholtc22c4002010-03-26 18:20:30 -07001136extern void
1137_mesa_glsl_initialize_functions(exec_list *instructions,
1138 struct _mesa_glsl_parse_state *state);
1139
Ian Romanicke309a602010-03-15 15:20:15 -07001140#endif /* IR_H */