ir.cpp revision b6f15869b324ae64a00d0fe46fa3c8c62c1edb6c
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/core.h" /* for MAX2 */ 25#include "ir.h" 26#include "ir_visitor.h" 27#include "glsl_types.h" 28 29ir_rvalue::ir_rvalue() 30{ 31 this->type = glsl_type::error_type; 32} 33 34/** 35 * Modify the swizzle make to move one component to another 36 * 37 * \param m IR swizzle to be modified 38 * \param from Component in the RHS that is to be swizzled 39 * \param to Desired swizzle location of \c from 40 */ 41static void 42update_rhs_swizzle(ir_swizzle_mask &m, unsigned from, unsigned to) 43{ 44 switch (to) { 45 case 0: m.x = from; break; 46 case 1: m.y = from; break; 47 case 2: m.z = from; break; 48 case 3: m.w = from; break; 49 default: assert(!"Should not get here."); 50 } 51 52 m.num_components = MAX2(m.num_components, (to + 1)); 53} 54 55void 56ir_assignment::set_lhs(ir_rvalue *lhs) 57{ 58 while (lhs != NULL) { 59 ir_swizzle *swiz = lhs->as_swizzle(); 60 61 if (swiz == NULL) 62 break; 63 64 unsigned write_mask = 0; 65 ir_swizzle_mask rhs_swiz = { 0, 0, 0, 0, 0, 0 }; 66 67 for (unsigned i = 0; i < swiz->mask.num_components; i++) { 68 unsigned c = 0; 69 70 switch (i) { 71 case 0: c = swiz->mask.x; break; 72 case 1: c = swiz->mask.y; break; 73 case 2: c = swiz->mask.z; break; 74 case 3: c = swiz->mask.w; break; 75 default: assert(!"Should not get here."); 76 } 77 78 write_mask |= (((this->write_mask >> i) & 1) << c); 79 update_rhs_swizzle(rhs_swiz, i, c); 80 } 81 82 this->write_mask = write_mask; 83 lhs = swiz->val; 84 85 this->rhs = new(this) ir_swizzle(this->rhs, rhs_swiz); 86 } 87 88 assert((lhs == NULL) || lhs->as_dereference()); 89 90 this->lhs = (ir_dereference *) lhs; 91} 92 93ir_variable * 94ir_assignment::whole_variable_written() 95{ 96 ir_variable *v = this->lhs->whole_variable_referenced(); 97 98 if (v == NULL) 99 return NULL; 100 101 if (v->type->is_scalar()) 102 return v; 103 104 if (v->type->is_vector()) { 105 const unsigned mask = (1U << v->type->vector_elements) - 1; 106 107 if (mask != this->write_mask) 108 return NULL; 109 } 110 111 /* Either all the vector components are assigned or the variable is some 112 * composite type (and the whole thing is assigned. 113 */ 114 return v; 115} 116 117ir_assignment::ir_assignment(ir_dereference *lhs, ir_rvalue *rhs, 118 ir_rvalue *condition, unsigned write_mask) 119{ 120 this->ir_type = ir_type_assignment; 121 this->condition = condition; 122 this->rhs = rhs; 123 this->lhs = lhs; 124 this->write_mask = write_mask; 125} 126 127ir_assignment::ir_assignment(ir_rvalue *lhs, ir_rvalue *rhs, 128 ir_rvalue *condition) 129{ 130 this->ir_type = ir_type_assignment; 131 this->condition = condition; 132 this->rhs = rhs; 133 134 /* If the RHS is a vector type, assume that all components of the vector 135 * type are being written to the LHS. The write mask comes from the RHS 136 * because we can have a case where the LHS is a vec4 and the RHS is a 137 * vec3. In that case, the assignment is: 138 * 139 * (assign (...) (xyz) (var_ref lhs) (var_ref rhs)) 140 */ 141 if (rhs->type->is_vector()) 142 this->write_mask = (1U << rhs->type->vector_elements) - 1; 143 else if (rhs->type->is_scalar()) 144 this->write_mask = 1; 145 else 146 this->write_mask = 0; 147 148 this->set_lhs(lhs); 149} 150 151 152ir_expression::ir_expression(int op, const struct glsl_type *type, 153 ir_rvalue *op0, ir_rvalue *op1) 154{ 155 this->ir_type = ir_type_expression; 156 this->type = type; 157 this->operation = ir_expression_operation(op); 158 this->operands[0] = op0; 159 this->operands[1] = op1; 160} 161 162unsigned int 163ir_expression::get_num_operands(ir_expression_operation op) 164{ 165/* Update ir_print_visitor.cpp when updating this list. */ 166 const int num_operands[] = { 167 1, /* ir_unop_bit_not */ 168 1, /* ir_unop_logic_not */ 169 1, /* ir_unop_neg */ 170 1, /* ir_unop_abs */ 171 1, /* ir_unop_sign */ 172 1, /* ir_unop_rcp */ 173 1, /* ir_unop_rsq */ 174 1, /* ir_unop_sqrt */ 175 1, /* ir_unop_exp */ 176 1, /* ir_unop_log */ 177 1, /* ir_unop_exp2 */ 178 1, /* ir_unop_log2 */ 179 1, /* ir_unop_f2i */ 180 1, /* ir_unop_i2f */ 181 1, /* ir_unop_f2b */ 182 1, /* ir_unop_b2f */ 183 1, /* ir_unop_i2b */ 184 1, /* ir_unop_b2i */ 185 1, /* ir_unop_u2f */ 186 1, /* ir_unop_any */ 187 188 1, /* ir_unop_trunc */ 189 1, /* ir_unop_ceil */ 190 1, /* ir_unop_floor */ 191 1, /* ir_unop_fract */ 192 193 1, /* ir_unop_sin */ 194 1, /* ir_unop_cos */ 195 196 1, /* ir_unop_dFdx */ 197 1, /* ir_unop_dFdy */ 198 199 2, /* ir_binop_add */ 200 2, /* ir_binop_sub */ 201 2, /* ir_binop_mul */ 202 2, /* ir_binop_div */ 203 2, /* ir_binop_mod */ 204 205 2, /* ir_binop_less */ 206 2, /* ir_binop_greater */ 207 2, /* ir_binop_lequal */ 208 2, /* ir_binop_gequal */ 209 2, /* ir_binop_equal */ 210 2, /* ir_binop_nequal */ 211 212 2, /* ir_binop_lshift */ 213 2, /* ir_binop_rshift */ 214 2, /* ir_binop_bit_and */ 215 2, /* ir_binop_bit_xor */ 216 2, /* ir_binop_bit_or */ 217 218 2, /* ir_binop_logic_and */ 219 2, /* ir_binop_logic_xor */ 220 2, /* ir_binop_logic_or */ 221 222 2, /* ir_binop_dot */ 223 2, /* ir_binop_cross */ 224 2, /* ir_binop_min */ 225 2, /* ir_binop_max */ 226 227 2, /* ir_binop_pow */ 228 }; 229 230 assert(sizeof(num_operands) / sizeof(num_operands[0]) == ir_binop_pow + 1); 231 232 return num_operands[op]; 233} 234 235static const char *const operator_strs[] = { 236 "~", 237 "!", 238 "neg", 239 "abs", 240 "sign", 241 "rcp", 242 "rsq", 243 "sqrt", 244 "exp", 245 "log", 246 "exp2", 247 "log2", 248 "f2i", 249 "i2f", 250 "f2b", 251 "b2f", 252 "i2b", 253 "b2i", 254 "u2f", 255 "any", 256 "trunc", 257 "ceil", 258 "floor", 259 "fract", 260 "sin", 261 "cos", 262 "dFdx", 263 "dFdy", 264 "+", 265 "-", 266 "*", 267 "/", 268 "%", 269 "<", 270 ">", 271 "<=", 272 ">=", 273 "==", 274 "!=", 275 "<<", 276 ">>", 277 "&", 278 "^", 279 "|", 280 "&&", 281 "^^", 282 "||", 283 "dot", 284 "cross", 285 "min", 286 "max", 287 "pow", 288}; 289 290const char *ir_expression::operator_string() 291{ 292 assert((unsigned int) operation <= 293 sizeof(operator_strs) / sizeof(operator_strs[0])); 294 return operator_strs[operation]; 295} 296 297ir_expression_operation 298ir_expression::get_operator(const char *str) 299{ 300 const int operator_count = sizeof(operator_strs) / sizeof(operator_strs[0]); 301 for (int op = 0; op < operator_count; op++) { 302 if (strcmp(str, operator_strs[op]) == 0) 303 return (ir_expression_operation) op; 304 } 305 return (ir_expression_operation) -1; 306} 307 308ir_constant::ir_constant() 309{ 310 this->ir_type = ir_type_constant; 311} 312 313ir_constant::ir_constant(const struct glsl_type *type, 314 const ir_constant_data *data) 315{ 316 assert((type->base_type >= GLSL_TYPE_UINT) 317 && (type->base_type <= GLSL_TYPE_BOOL)); 318 319 this->ir_type = ir_type_constant; 320 this->type = type; 321 memcpy(& this->value, data, sizeof(this->value)); 322} 323 324ir_constant::ir_constant(float f) 325{ 326 this->ir_type = ir_type_constant; 327 this->type = glsl_type::float_type; 328 this->value.f[0] = f; 329} 330 331ir_constant::ir_constant(unsigned int u) 332{ 333 this->ir_type = ir_type_constant; 334 this->type = glsl_type::uint_type; 335 this->value.u[0] = u; 336} 337 338ir_constant::ir_constant(int i) 339{ 340 this->ir_type = ir_type_constant; 341 this->type = glsl_type::int_type; 342 this->value.i[0] = i; 343} 344 345ir_constant::ir_constant(bool b) 346{ 347 this->ir_type = ir_type_constant; 348 this->type = glsl_type::bool_type; 349 this->value.b[0] = b; 350} 351 352ir_constant::ir_constant(const ir_constant *c, unsigned i) 353{ 354 this->ir_type = ir_type_constant; 355 this->type = c->type->get_base_type(); 356 357 switch (this->type->base_type) { 358 case GLSL_TYPE_UINT: this->value.u[0] = c->value.u[i]; break; 359 case GLSL_TYPE_INT: this->value.i[0] = c->value.i[i]; break; 360 case GLSL_TYPE_FLOAT: this->value.f[0] = c->value.f[i]; break; 361 case GLSL_TYPE_BOOL: this->value.b[0] = c->value.b[i]; break; 362 default: assert(!"Should not get here."); break; 363 } 364} 365 366ir_constant::ir_constant(const struct glsl_type *type, exec_list *value_list) 367{ 368 this->ir_type = ir_type_constant; 369 this->type = type; 370 371 assert(type->is_scalar() || type->is_vector() || type->is_matrix() 372 || type->is_record() || type->is_array()); 373 374 if (type->is_array()) { 375 this->array_elements = talloc_array(this, ir_constant *, type->length); 376 unsigned i = 0; 377 foreach_list(node, value_list) { 378 ir_constant *value = (ir_constant *) node; 379 assert(value->as_constant() != NULL); 380 381 this->array_elements[i++] = value; 382 } 383 return; 384 } 385 386 /* If the constant is a record, the types of each of the entries in 387 * value_list must be a 1-for-1 match with the structure components. Each 388 * entry must also be a constant. Just move the nodes from the value_list 389 * to the list in the ir_constant. 390 */ 391 /* FINISHME: Should there be some type checking and / or assertions here? */ 392 /* FINISHME: Should the new constant take ownership of the nodes from 393 * FINISHME: value_list, or should it make copies? 394 */ 395 if (type->is_record()) { 396 value_list->move_nodes_to(& this->components); 397 return; 398 } 399 400 401 ir_constant *value = (ir_constant *) (value_list->head); 402 403 /* Use each component from each entry in the value_list to initialize one 404 * component of the constant being constructed. 405 */ 406 for (unsigned i = 0; i < type->components(); /* empty */) { 407 assert(value->as_constant() != NULL); 408 assert(!value->is_tail_sentinel()); 409 410 for (unsigned j = 0; j < value->type->components(); j++) { 411 switch (type->base_type) { 412 case GLSL_TYPE_UINT: 413 this->value.u[i] = value->get_uint_component(j); 414 break; 415 case GLSL_TYPE_INT: 416 this->value.i[i] = value->get_int_component(j); 417 break; 418 case GLSL_TYPE_FLOAT: 419 this->value.f[i] = value->get_float_component(j); 420 break; 421 case GLSL_TYPE_BOOL: 422 this->value.b[i] = value->get_bool_component(j); 423 break; 424 default: 425 /* FINISHME: What to do? Exceptions are not the answer. 426 */ 427 break; 428 } 429 430 i++; 431 if (i >= type->components()) 432 break; 433 } 434 435 value = (ir_constant *) value->next; 436 } 437} 438 439ir_constant * 440ir_constant::zero(void *mem_ctx, const glsl_type *type) 441{ 442 assert(type->is_numeric()); 443 444 ir_constant *c = new(mem_ctx) ir_constant; 445 c->type = type; 446 memset(&c->value, 0, sizeof(c->value)); 447 448 return c; 449} 450 451bool 452ir_constant::get_bool_component(unsigned i) const 453{ 454 switch (this->type->base_type) { 455 case GLSL_TYPE_UINT: return this->value.u[i] != 0; 456 case GLSL_TYPE_INT: return this->value.i[i] != 0; 457 case GLSL_TYPE_FLOAT: return ((int)this->value.f[i]) != 0; 458 case GLSL_TYPE_BOOL: return this->value.b[i]; 459 default: assert(!"Should not get here."); break; 460 } 461 462 /* Must return something to make the compiler happy. This is clearly an 463 * error case. 464 */ 465 return false; 466} 467 468float 469ir_constant::get_float_component(unsigned i) const 470{ 471 switch (this->type->base_type) { 472 case GLSL_TYPE_UINT: return (float) this->value.u[i]; 473 case GLSL_TYPE_INT: return (float) this->value.i[i]; 474 case GLSL_TYPE_FLOAT: return this->value.f[i]; 475 case GLSL_TYPE_BOOL: return this->value.b[i] ? 1.0 : 0.0; 476 default: assert(!"Should not get here."); break; 477 } 478 479 /* Must return something to make the compiler happy. This is clearly an 480 * error case. 481 */ 482 return 0.0; 483} 484 485int 486ir_constant::get_int_component(unsigned i) const 487{ 488 switch (this->type->base_type) { 489 case GLSL_TYPE_UINT: return this->value.u[i]; 490 case GLSL_TYPE_INT: return this->value.i[i]; 491 case GLSL_TYPE_FLOAT: return (int) this->value.f[i]; 492 case GLSL_TYPE_BOOL: return this->value.b[i] ? 1 : 0; 493 default: assert(!"Should not get here."); break; 494 } 495 496 /* Must return something to make the compiler happy. This is clearly an 497 * error case. 498 */ 499 return 0; 500} 501 502unsigned 503ir_constant::get_uint_component(unsigned i) const 504{ 505 switch (this->type->base_type) { 506 case GLSL_TYPE_UINT: return this->value.u[i]; 507 case GLSL_TYPE_INT: return this->value.i[i]; 508 case GLSL_TYPE_FLOAT: return (unsigned) this->value.f[i]; 509 case GLSL_TYPE_BOOL: return this->value.b[i] ? 1 : 0; 510 default: assert(!"Should not get here."); break; 511 } 512 513 /* Must return something to make the compiler happy. This is clearly an 514 * error case. 515 */ 516 return 0; 517} 518 519ir_constant * 520ir_constant::get_array_element(unsigned i) const 521{ 522 assert(this->type->is_array()); 523 524 /* From page 35 (page 41 of the PDF) of the GLSL 1.20 spec: 525 * 526 * "Behavior is undefined if a shader subscripts an array with an index 527 * less than 0 or greater than or equal to the size the array was 528 * declared with." 529 * 530 * Most out-of-bounds accesses are removed before things could get this far. 531 * There are cases where non-constant array index values can get constant 532 * folded. 533 */ 534 if (int(i) < 0) 535 i = 0; 536 else if (i >= this->type->length) 537 i = this->type->length - 1; 538 539 return array_elements[i]; 540} 541 542ir_constant * 543ir_constant::get_record_field(const char *name) 544{ 545 int idx = this->type->field_index(name); 546 547 if (idx < 0) 548 return NULL; 549 550 if (this->components.is_empty()) 551 return NULL; 552 553 exec_node *node = this->components.head; 554 for (int i = 0; i < idx; i++) { 555 node = node->next; 556 557 /* If the end of the list is encountered before the element matching the 558 * requested field is found, return NULL. 559 */ 560 if (node->is_tail_sentinel()) 561 return NULL; 562 } 563 564 return (ir_constant *) node; 565} 566 567 568bool 569ir_constant::has_value(const ir_constant *c) const 570{ 571 if (this->type != c->type) 572 return false; 573 574 if (this->type->is_array()) { 575 for (unsigned i = 0; i < this->type->length; i++) { 576 if (this->array_elements[i]->has_value(c->array_elements[i])) 577 return false; 578 } 579 return true; 580 } 581 582 if (this->type->base_type == GLSL_TYPE_STRUCT) { 583 const exec_node *a_node = this->components.head; 584 const exec_node *b_node = c->components.head; 585 586 while (!a_node->is_tail_sentinel()) { 587 assert(!b_node->is_tail_sentinel()); 588 589 const ir_constant *const a_field = (ir_constant *) a_node; 590 const ir_constant *const b_field = (ir_constant *) b_node; 591 592 if (!a_field->has_value(b_field)) 593 return false; 594 595 a_node = a_node->next; 596 b_node = b_node->next; 597 } 598 599 return true; 600 } 601 602 for (unsigned i = 0; i < this->type->components(); i++) { 603 switch (this->type->base_type) { 604 case GLSL_TYPE_UINT: 605 if (this->value.u[i] != c->value.u[i]) 606 return false; 607 break; 608 case GLSL_TYPE_INT: 609 if (this->value.i[i] != c->value.i[i]) 610 return false; 611 break; 612 case GLSL_TYPE_FLOAT: 613 if (this->value.f[i] != c->value.f[i]) 614 return false; 615 break; 616 case GLSL_TYPE_BOOL: 617 if (this->value.b[i] != c->value.b[i]) 618 return false; 619 break; 620 default: 621 assert(!"Should not get here."); 622 return false; 623 } 624 } 625 626 return true; 627} 628 629ir_dereference_variable::ir_dereference_variable(ir_variable *var) 630{ 631 this->ir_type = ir_type_dereference_variable; 632 this->var = var; 633 this->type = (var != NULL) ? var->type : glsl_type::error_type; 634} 635 636 637ir_dereference_array::ir_dereference_array(ir_rvalue *value, 638 ir_rvalue *array_index) 639{ 640 this->ir_type = ir_type_dereference_array; 641 this->array_index = array_index; 642 this->set_array(value); 643} 644 645 646ir_dereference_array::ir_dereference_array(ir_variable *var, 647 ir_rvalue *array_index) 648{ 649 void *ctx = talloc_parent(var); 650 651 this->ir_type = ir_type_dereference_array; 652 this->array_index = array_index; 653 this->set_array(new(ctx) ir_dereference_variable(var)); 654} 655 656 657void 658ir_dereference_array::set_array(ir_rvalue *value) 659{ 660 this->array = value; 661 this->type = glsl_type::error_type; 662 663 if (this->array != NULL) { 664 const glsl_type *const vt = this->array->type; 665 666 if (vt->is_array()) { 667 type = vt->element_type(); 668 } else if (vt->is_matrix()) { 669 type = vt->column_type(); 670 } else if (vt->is_vector()) { 671 type = vt->get_base_type(); 672 } 673 } 674} 675 676 677ir_dereference_record::ir_dereference_record(ir_rvalue *value, 678 const char *field) 679{ 680 this->ir_type = ir_type_dereference_record; 681 this->record = value; 682 this->field = talloc_strdup(this, field); 683 this->type = (this->record != NULL) 684 ? this->record->type->field_type(field) : glsl_type::error_type; 685} 686 687 688ir_dereference_record::ir_dereference_record(ir_variable *var, 689 const char *field) 690{ 691 void *ctx = talloc_parent(var); 692 693 this->ir_type = ir_type_dereference_record; 694 this->record = new(ctx) ir_dereference_variable(var); 695 this->field = talloc_strdup(this, field); 696 this->type = (this->record != NULL) 697 ? this->record->type->field_type(field) : glsl_type::error_type; 698} 699 700bool type_contains_sampler(const glsl_type *type) 701{ 702 if (type->is_array()) { 703 return type_contains_sampler(type->fields.array); 704 } else if (type->is_record()) { 705 for (unsigned int i = 0; i < type->length; i++) { 706 if (type_contains_sampler(type->fields.structure[i].type)) 707 return true; 708 } 709 return false; 710 } else { 711 return type->is_sampler(); 712 } 713} 714 715bool 716ir_dereference::is_lvalue() 717{ 718 ir_variable *var = this->variable_referenced(); 719 720 /* Every l-value derference chain eventually ends in a variable. 721 */ 722 if ((var == NULL) || var->read_only) 723 return false; 724 725 if (this->type->is_array() && !var->array_lvalue) 726 return false; 727 728 /* From page 17 (page 23 of the PDF) of the GLSL 1.20 spec: 729 * 730 * "Samplers cannot be treated as l-values; hence cannot be used 731 * as out or inout function parameters, nor can they be 732 * assigned into." 733 */ 734 if (type_contains_sampler(this->type)) 735 return false; 736 737 return true; 738} 739 740 741const char *tex_opcode_strs[] = { "tex", "txb", "txl", "txd", "txf" }; 742 743const char *ir_texture::opcode_string() 744{ 745 assert((unsigned int) op <= 746 sizeof(tex_opcode_strs) / sizeof(tex_opcode_strs[0])); 747 return tex_opcode_strs[op]; 748} 749 750ir_texture_opcode 751ir_texture::get_opcode(const char *str) 752{ 753 const int count = sizeof(tex_opcode_strs) / sizeof(tex_opcode_strs[0]); 754 for (int op = 0; op < count; op++) { 755 if (strcmp(str, tex_opcode_strs[op]) == 0) 756 return (ir_texture_opcode) op; 757 } 758 return (ir_texture_opcode) -1; 759} 760 761 762void 763ir_texture::set_sampler(ir_dereference *sampler) 764{ 765 assert(sampler != NULL); 766 this->sampler = sampler; 767 768 switch (sampler->type->sampler_type) { 769 case GLSL_TYPE_FLOAT: 770 this->type = glsl_type::vec4_type; 771 break; 772 case GLSL_TYPE_INT: 773 this->type = glsl_type::ivec4_type; 774 break; 775 case GLSL_TYPE_UINT: 776 this->type = glsl_type::uvec4_type; 777 break; 778 } 779} 780 781 782void 783ir_swizzle::init_mask(const unsigned *comp, unsigned count) 784{ 785 assert((count >= 1) && (count <= 4)); 786 787 memset(&this->mask, 0, sizeof(this->mask)); 788 this->mask.num_components = count; 789 790 unsigned dup_mask = 0; 791 switch (count) { 792 case 4: 793 assert(comp[3] <= 3); 794 dup_mask |= (1U << comp[3]) 795 & ((1U << comp[0]) | (1U << comp[1]) | (1U << comp[2])); 796 this->mask.w = comp[3]; 797 798 case 3: 799 assert(comp[2] <= 3); 800 dup_mask |= (1U << comp[2]) 801 & ((1U << comp[0]) | (1U << comp[1])); 802 this->mask.z = comp[2]; 803 804 case 2: 805 assert(comp[1] <= 3); 806 dup_mask |= (1U << comp[1]) 807 & ((1U << comp[0])); 808 this->mask.y = comp[1]; 809 810 case 1: 811 assert(comp[0] <= 3); 812 this->mask.x = comp[0]; 813 } 814 815 this->mask.has_duplicates = dup_mask != 0; 816 817 /* Based on the number of elements in the swizzle and the base type 818 * (i.e., float, int, unsigned, or bool) of the vector being swizzled, 819 * generate the type of the resulting value. 820 */ 821 type = glsl_type::get_instance(val->type->base_type, mask.num_components, 1); 822} 823 824ir_swizzle::ir_swizzle(ir_rvalue *val, unsigned x, unsigned y, unsigned z, 825 unsigned w, unsigned count) 826 : val(val) 827{ 828 const unsigned components[4] = { x, y, z, w }; 829 this->ir_type = ir_type_swizzle; 830 this->init_mask(components, count); 831} 832 833ir_swizzle::ir_swizzle(ir_rvalue *val, const unsigned *comp, 834 unsigned count) 835 : val(val) 836{ 837 this->ir_type = ir_type_swizzle; 838 this->init_mask(comp, count); 839} 840 841ir_swizzle::ir_swizzle(ir_rvalue *val, ir_swizzle_mask mask) 842{ 843 this->ir_type = ir_type_swizzle; 844 this->val = val; 845 this->mask = mask; 846 this->type = glsl_type::get_instance(val->type->base_type, 847 mask.num_components, 1); 848} 849 850#define X 1 851#define R 5 852#define S 9 853#define I 13 854 855ir_swizzle * 856ir_swizzle::create(ir_rvalue *val, const char *str, unsigned vector_length) 857{ 858 void *ctx = talloc_parent(val); 859 860 /* For each possible swizzle character, this table encodes the value in 861 * \c idx_map that represents the 0th element of the vector. For invalid 862 * swizzle characters (e.g., 'k'), a special value is used that will allow 863 * detection of errors. 864 */ 865 static const unsigned char base_idx[26] = { 866 /* a b c d e f g h i j k l m */ 867 R, R, I, I, I, I, R, I, I, I, I, I, I, 868 /* n o p q r s t u v w x y z */ 869 I, I, S, S, R, S, S, I, I, X, X, X, X 870 }; 871 872 /* Each valid swizzle character has an entry in the previous table. This 873 * table encodes the base index encoded in the previous table plus the actual 874 * index of the swizzle character. When processing swizzles, the first 875 * character in the string is indexed in the previous table. Each character 876 * in the string is indexed in this table, and the value found there has the 877 * value form the first table subtracted. The result must be on the range 878 * [0,3]. 879 * 880 * For example, the string "wzyx" will get X from the first table. Each of 881 * the charcaters will get X+3, X+2, X+1, and X+0 from this table. After 882 * subtraction, the swizzle values are { 3, 2, 1, 0 }. 883 * 884 * The string "wzrg" will get X from the first table. Each of the characters 885 * will get X+3, X+2, R+0, and R+1 from this table. After subtraction, the 886 * swizzle values are { 3, 2, 4, 5 }. Since 4 and 5 are outside the range 887 * [0,3], the error is detected. 888 */ 889 static const unsigned char idx_map[26] = { 890 /* a b c d e f g h i j k l m */ 891 R+3, R+2, 0, 0, 0, 0, R+1, 0, 0, 0, 0, 0, 0, 892 /* n o p q r s t u v w x y z */ 893 0, 0, S+2, S+3, R+0, S+0, S+1, 0, 0, X+3, X+0, X+1, X+2 894 }; 895 896 int swiz_idx[4] = { 0, 0, 0, 0 }; 897 unsigned i; 898 899 900 /* Validate the first character in the swizzle string and look up the base 901 * index value as described above. 902 */ 903 if ((str[0] < 'a') || (str[0] > 'z')) 904 return NULL; 905 906 const unsigned base = base_idx[str[0] - 'a']; 907 908 909 for (i = 0; (i < 4) && (str[i] != '\0'); i++) { 910 /* Validate the next character, and, as described above, convert it to a 911 * swizzle index. 912 */ 913 if ((str[i] < 'a') || (str[i] > 'z')) 914 return NULL; 915 916 swiz_idx[i] = idx_map[str[i] - 'a'] - base; 917 if ((swiz_idx[i] < 0) || (swiz_idx[i] >= (int) vector_length)) 918 return NULL; 919 } 920 921 if (str[i] != '\0') 922 return NULL; 923 924 return new(ctx) ir_swizzle(val, swiz_idx[0], swiz_idx[1], swiz_idx[2], 925 swiz_idx[3], i); 926} 927 928#undef X 929#undef R 930#undef S 931#undef I 932 933ir_variable * 934ir_swizzle::variable_referenced() 935{ 936 return this->val->variable_referenced(); 937} 938 939 940ir_variable::ir_variable(const struct glsl_type *type, const char *name, 941 ir_variable_mode mode) 942 : max_array_access(0), read_only(false), centroid(false), invariant(false), 943 mode(mode), interpolation(ir_var_smooth), array_lvalue(false) 944{ 945 this->ir_type = ir_type_variable; 946 this->type = type; 947 this->name = talloc_strdup(this, name); 948 this->location = -1; 949 this->warn_extension = NULL; 950 this->constant_value = NULL; 951 this->origin_upper_left = false; 952 this->pixel_center_integer = false; 953 954 if (type && type->base_type == GLSL_TYPE_SAMPLER) 955 this->read_only = true; 956} 957 958 959const char * 960ir_variable::interpolation_string() const 961{ 962 switch (this->interpolation) { 963 case ir_var_smooth: return "smooth"; 964 case ir_var_flat: return "flat"; 965 case ir_var_noperspective: return "noperspective"; 966 } 967 968 assert(!"Should not get here."); 969 return ""; 970} 971 972 973unsigned 974ir_variable::component_slots() const 975{ 976 /* FINISHME: Sparsely accessed arrays require fewer slots. */ 977 return this->type->component_slots(); 978} 979 980 981ir_function_signature::ir_function_signature(const glsl_type *return_type) 982 : return_type(return_type), is_defined(false), _function(NULL) 983{ 984 this->ir_type = ir_type_function_signature; 985} 986 987 988const char * 989ir_function_signature::qualifiers_match(exec_list *params) 990{ 991 exec_list_iterator iter_a = parameters.iterator(); 992 exec_list_iterator iter_b = params->iterator(); 993 994 /* check that the qualifiers match. */ 995 while (iter_a.has_next()) { 996 ir_variable *a = (ir_variable *)iter_a.get(); 997 ir_variable *b = (ir_variable *)iter_b.get(); 998 999 if (a->read_only != b->read_only || 1000 a->mode != b->mode || 1001 a->interpolation != b->interpolation || 1002 a->centroid != b->centroid) { 1003 1004 /* parameter a's qualifiers don't match */ 1005 return a->name; 1006 } 1007 1008 iter_a.next(); 1009 iter_b.next(); 1010 } 1011 return NULL; 1012} 1013 1014 1015void 1016ir_function_signature::replace_parameters(exec_list *new_params) 1017{ 1018 /* Destroy all of the previous parameter information. If the previous 1019 * parameter information comes from the function prototype, it may either 1020 * specify incorrect parameter names or not have names at all. 1021 */ 1022 foreach_iter(exec_list_iterator, iter, parameters) { 1023 assert(((ir_instruction *) iter.get())->as_variable() != NULL); 1024 1025 iter.remove(); 1026 } 1027 1028 new_params->move_nodes_to(¶meters); 1029} 1030 1031 1032ir_function::ir_function(const char *name) 1033{ 1034 this->ir_type = ir_type_function; 1035 this->name = talloc_strdup(this, name); 1036 this->is_builtin = false; 1037} 1038 1039 1040ir_call * 1041ir_call::get_error_instruction(void *ctx) 1042{ 1043 ir_call *call = new(ctx) ir_call; 1044 1045 call->type = glsl_type::error_type; 1046 return call; 1047} 1048 1049void 1050ir_call::set_callee(ir_function_signature *sig) 1051{ 1052 assert((this->type == NULL) || (this->type == sig->return_type)); 1053 1054 this->callee = sig; 1055} 1056 1057void 1058visit_exec_list(exec_list *list, ir_visitor *visitor) 1059{ 1060 foreach_iter(exec_list_iterator, iter, *list) { 1061 ((ir_instruction *)iter.get())->accept(visitor); 1062 } 1063} 1064 1065 1066static void 1067steal_memory(ir_instruction *ir, void *new_ctx) 1068{ 1069 ir_variable *var = ir->as_variable(); 1070 ir_constant *constant = ir->as_constant(); 1071 if (var != NULL && var->constant_value != NULL) 1072 steal_memory(var->constant_value, ir); 1073 1074 /* The components of aggregate constants are not visited by the normal 1075 * visitor, so steal their values by hand. 1076 */ 1077 if (constant != NULL) { 1078 if (constant->type->is_record()) { 1079 foreach_iter(exec_list_iterator, iter, constant->components) { 1080 ir_constant *field = (ir_constant *)iter.get(); 1081 steal_memory(field, ir); 1082 } 1083 } else if (constant->type->is_array()) { 1084 for (unsigned int i = 0; i < constant->type->length; i++) { 1085 steal_memory(constant->array_elements[i], ir); 1086 } 1087 } 1088 } 1089 1090 talloc_steal(new_ctx, ir); 1091} 1092 1093 1094void 1095reparent_ir(exec_list *list, void *mem_ctx) 1096{ 1097 foreach_list(node, list) { 1098 visit_tree((ir_instruction *) node, steal_memory, mem_ctx); 1099 } 1100} 1101