1 /* RTL utility routines. 2 Copyright (C) 1987-2019 Free Software Foundation, Inc. 3 4 This file is part of GCC. 5 6 GCC is free software; you can redistribute it and/or modify it under 7 the terms of the GNU General Public License as published by the Free 8 Software Foundation; either version 3, or (at your option) any later 9 version. 10 11 GCC is distributed in the hope that it will be useful, but WITHOUT ANY 12 WARRANTY; without even the implied warranty of MERCHANTABILITY or 13 FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License 14 for more details. 15 16 You should have received a copy of the GNU General Public License 17 along with GCC; see the file COPYING3. If not see 18 <http://www.gnu.org/licenses/>. */ 19 20 /* This file is compiled twice: once for the generator programs 21 once for the compiler. */ 22 #ifdef GENERATOR_FILE 23 #include "bconfig.h" 24 #else 25 #include "config.h" 26 #endif 27 28 #include "system.h" 29 #include "coretypes.h" 30 #include "tm.h" 31 #include "rtl.h" 32 #ifdef GENERATOR_FILE 33 # include "errors.h" 34 #else 35 # include "rtlhash.h" 36 # include "diagnostic-core.h" 37 #endif 38 39 40 /* Indexed by rtx code, gives number of operands for an rtx with that code. 41 Does NOT include rtx header data (code and links). */ 42 43 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) sizeof FORMAT - 1 , 44 45 const unsigned char rtx_length[NUM_RTX_CODE] = { 46 #include "rtl.def" 47 }; 48 49 #undef DEF_RTL_EXPR 50 51 /* Indexed by rtx code, gives the name of that kind of rtx, as a C string. */ 52 53 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) NAME , 54 55 const char * const rtx_name[NUM_RTX_CODE] = { 56 #include "rtl.def" /* rtl expressions are documented here */ 57 }; 58 59 #undef DEF_RTL_EXPR 60 61 /* Indexed by rtx code, gives a sequence of operand-types for 62 rtx's of that code. The sequence is a C string in which 63 each character describes one operand. */ 64 65 const char * const rtx_format[NUM_RTX_CODE] = { 66 /* "*" undefined. 67 can cause a warning message 68 "0" field is unused (or used in a phase-dependent manner) 69 prints nothing 70 "i" an integer 71 prints the integer 72 "n" like "i", but prints entries from `note_insn_name' 73 "w" an integer of width HOST_BITS_PER_WIDE_INT 74 prints the integer 75 "s" a pointer to a string 76 prints the string 77 "S" like "s", but optional: 78 the containing rtx may end before this operand 79 "T" like "s", but treated specially by the RTL reader; 80 only found in machine description patterns. 81 "e" a pointer to an rtl expression 82 prints the expression 83 "E" a pointer to a vector that points to a number of rtl expressions 84 prints a list of the rtl expressions 85 "V" like "E", but optional: 86 the containing rtx may end before this operand 87 "u" a pointer to another insn 88 prints the uid of the insn. 89 "b" is a pointer to a bitmap header. 90 "B" is a basic block pointer. 91 "t" is a tree pointer. 92 "r" a register. 93 "p" is a poly_uint16 offset. */ 94 95 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) FORMAT , 96 #include "rtl.def" /* rtl expressions are defined here */ 97 #undef DEF_RTL_EXPR 98 }; 99 100 /* Indexed by rtx code, gives a character representing the "class" of 101 that rtx code. See rtl.def for documentation on the defined classes. */ 102 103 const enum rtx_class rtx_class[NUM_RTX_CODE] = { 104 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) CLASS, 105 #include "rtl.def" /* rtl expressions are defined here */ 106 #undef DEF_RTL_EXPR 107 }; 108 109 /* Whether rtxs with the given code code store data in the hwint field. */ 110 111 #define RTX_CODE_HWINT_P_1(ENUM) \ 112 ((ENUM) == CONST_INT || (ENUM) == CONST_DOUBLE \ 113 || (ENUM) == CONST_FIXED || (ENUM) == CONST_WIDE_INT) 114 #ifdef GENERATOR_FILE 115 #define RTX_CODE_HWINT_P(ENUM) \ 116 (RTX_CODE_HWINT_P_1 (ENUM) || (ENUM) == EQ_ATTR_ALT) 117 #else 118 #define RTX_CODE_HWINT_P RTX_CODE_HWINT_P_1 119 #endif 120 121 /* Indexed by rtx code, gives the size of the rtx in bytes. */ 122 123 const unsigned char rtx_code_size[NUM_RTX_CODE] = { 124 #define DEF_RTL_EXPR(ENUM, NAME, FORMAT, CLASS) \ 125 (RTX_CODE_HWINT_P (ENUM) \ 126 ? RTX_HDR_SIZE + (sizeof FORMAT - 1) * sizeof (HOST_WIDE_INT) \ 127 : (ENUM) == REG \ 128 ? RTX_HDR_SIZE + sizeof (reg_info) \ 129 : RTX_HDR_SIZE + (sizeof FORMAT - 1) * sizeof (rtunion)), 130 131 #include "rtl.def" 132 #undef DEF_RTL_EXPR 133 }; 134 135 /* Names for kinds of NOTEs and REG_NOTEs. */ 136 137 const char * const note_insn_name[NOTE_INSN_MAX] = 138 { 139 #define DEF_INSN_NOTE(NAME) #NAME, 140 #include "insn-notes.def" 141 #undef DEF_INSN_NOTE 142 }; 143 144 const char * const reg_note_name[REG_NOTE_MAX] = 145 { 146 #define DEF_REG_NOTE(NAME) #NAME, 147 #include "reg-notes.def" 148 #undef DEF_REG_NOTE 149 }; 150 151 static size_t rtx_alloc_counts[(int) LAST_AND_UNUSED_RTX_CODE]; 152 static size_t rtx_alloc_sizes[(int) LAST_AND_UNUSED_RTX_CODE]; 153 static size_t rtvec_alloc_counts; 154 static size_t rtvec_alloc_sizes; 155 156 157 /* Allocate an rtx vector of N elements. 158 Store the length, and initialize all elements to zero. */ 159 160 rtvec 161 rtvec_alloc (int n) 162 { 163 rtvec rt; 164 165 rt = ggc_alloc_rtvec_sized (n); 166 /* Clear out the vector. */ 167 memset (&rt->elem[0], 0, n * sizeof (rtx)); 168 169 PUT_NUM_ELEM (rt, n); 170 171 if (GATHER_STATISTICS) 172 { 173 rtvec_alloc_counts++; 174 rtvec_alloc_sizes += n * sizeof (rtx); 175 } 176 177 return rt; 178 } 179 180 /* Create a bitwise copy of VEC. */ 181 182 rtvec 183 shallow_copy_rtvec (rtvec vec) 184 { 185 rtvec newvec; 186 int n; 187 188 n = GET_NUM_ELEM (vec); 189 newvec = rtvec_alloc (n); 190 memcpy (&newvec->elem[0], &vec->elem[0], sizeof (rtx) * n); 191 return newvec; 192 } 193 194 /* Return the number of bytes occupied by rtx value X. */ 195 196 unsigned int 197 rtx_size (const_rtx x) 198 { 199 if (CONST_WIDE_INT_P (x)) 200 return (RTX_HDR_SIZE 201 + sizeof (struct hwivec_def) 202 + ((CONST_WIDE_INT_NUNITS (x) - 1) 203 * sizeof (HOST_WIDE_INT))); 204 if (CONST_POLY_INT_P (x)) 205 return (RTX_HDR_SIZE 206 + sizeof (struct const_poly_int_def) 207 + CONST_POLY_INT_COEFFS (x).extra_size ()); 208 if (GET_CODE (x) == SYMBOL_REF && SYMBOL_REF_HAS_BLOCK_INFO_P (x)) 209 return RTX_HDR_SIZE + sizeof (struct block_symbol); 210 return RTX_CODE_SIZE (GET_CODE (x)); 211 } 212 213 /* Allocate an rtx of code CODE with EXTRA bytes in it. The CODE is 214 stored in the rtx; all the rest is initialized to zero. */ 215 216 rtx 217 rtx_alloc_stat_v (RTX_CODE code MEM_STAT_DECL, int extra) 218 { 219 rtx rt = ggc_alloc_rtx_def_stat (RTX_CODE_SIZE (code) + extra 220 PASS_MEM_STAT); 221 222 /* We want to clear everything up to the FLD array. Normally, this 223 is one int, but we don't want to assume that and it isn't very 224 portable anyway; this is. */ 225 226 memset (rt, 0, RTX_HDR_SIZE); 227 PUT_CODE (rt, code); 228 229 if (GATHER_STATISTICS) 230 { 231 rtx_alloc_counts[code]++; 232 rtx_alloc_sizes[code] += RTX_CODE_SIZE (code); 233 } 234 235 return rt; 236 } 237 238 /* Allocate an rtx of code CODE. The CODE is stored in the rtx; 239 all the rest is initialized to zero. */ 240 241 rtx 242 rtx_alloc (RTX_CODE code MEM_STAT_DECL) 243 { 244 return rtx_alloc_stat_v (code PASS_MEM_STAT, 0); 245 } 246 247 /* Write the wide constant X to OUTFILE. */ 248 249 void 250 cwi_output_hex (FILE *outfile, const_rtx x) 251 { 252 int i = CWI_GET_NUM_ELEM (x); 253 gcc_assert (i > 0); 254 if (CWI_ELT (x, i - 1) == 0) 255 /* The HOST_WIDE_INT_PRINT_HEX prepends a 0x only if the val is 256 non zero. We want all numbers to have a 0x prefix. */ 257 fprintf (outfile, "0x"); 258 fprintf (outfile, HOST_WIDE_INT_PRINT_HEX, CWI_ELT (x, --i)); 259 while (--i >= 0) 260 fprintf (outfile, HOST_WIDE_INT_PRINT_PADDED_HEX, CWI_ELT (x, i)); 261 } 262 263 264 /* Return true if ORIG is a sharable CONST. */ 265 266 bool 267 shared_const_p (const_rtx orig) 268 { 269 gcc_assert (GET_CODE (orig) == CONST); 270 271 /* CONST can be shared if it contains a SYMBOL_REF. If it contains 272 a LABEL_REF, it isn't sharable. */ 273 poly_int64 offset; 274 return (GET_CODE (XEXP (orig, 0)) == PLUS 275 && GET_CODE (XEXP (XEXP (orig, 0), 0)) == SYMBOL_REF 276 && poly_int_rtx_p (XEXP (XEXP (orig, 0), 1), &offset)); 277 } 278 279 280 /* Create a new copy of an rtx. 281 Recursively copies the operands of the rtx, 282 except for those few rtx codes that are sharable. */ 283 284 rtx 285 copy_rtx (rtx orig) 286 { 287 rtx copy; 288 int i, j; 289 RTX_CODE code; 290 const char *format_ptr; 291 292 code = GET_CODE (orig); 293 294 switch (code) 295 { 296 case REG: 297 case DEBUG_EXPR: 298 case VALUE: 299 CASE_CONST_ANY: 300 case SYMBOL_REF: 301 case CODE_LABEL: 302 case PC: 303 case CC0: 304 case RETURN: 305 case SIMPLE_RETURN: 306 case SCRATCH: 307 /* SCRATCH must be shared because they represent distinct values. */ 308 return orig; 309 case CLOBBER: 310 /* Share clobbers of hard registers (like cc0), but do not share pseudo reg 311 clobbers or clobbers of hard registers that originated as pseudos. 312 This is needed to allow safe register renaming. */ 313 if (REG_P (XEXP (orig, 0)) && REGNO (XEXP (orig, 0)) < FIRST_PSEUDO_REGISTER 314 && ORIGINAL_REGNO (XEXP (orig, 0)) == REGNO (XEXP (orig, 0))) 315 return orig; 316 break; 317 318 case CLOBBER_HIGH: 319 gcc_assert (REG_P (XEXP (orig, 0))); 320 return orig; 321 322 case CONST: 323 if (shared_const_p (orig)) 324 return orig; 325 break; 326 327 /* A MEM with a constant address is not sharable. The problem is that 328 the constant address may need to be reloaded. If the mem is shared, 329 then reloading one copy of this mem will cause all copies to appear 330 to have been reloaded. */ 331 332 default: 333 break; 334 } 335 336 /* Copy the various flags, fields, and other information. We assume 337 that all fields need copying, and then clear the fields that should 338 not be copied. That is the sensible default behavior, and forces 339 us to explicitly document why we are *not* copying a flag. */ 340 copy = shallow_copy_rtx (orig); 341 342 format_ptr = GET_RTX_FORMAT (GET_CODE (copy)); 343 344 for (i = 0; i < GET_RTX_LENGTH (GET_CODE (copy)); i++) 345 switch (*format_ptr++) 346 { 347 case 'e': 348 if (XEXP (orig, i) != NULL) 349 XEXP (copy, i) = copy_rtx (XEXP (orig, i)); 350 break; 351 352 case 'E': 353 case 'V': 354 if (XVEC (orig, i) != NULL) 355 { 356 XVEC (copy, i) = rtvec_alloc (XVECLEN (orig, i)); 357 for (j = 0; j < XVECLEN (copy, i); j++) 358 XVECEXP (copy, i, j) = copy_rtx (XVECEXP (orig, i, j)); 359 } 360 break; 361 362 case 't': 363 case 'w': 364 case 'i': 365 case 'p': 366 case 's': 367 case 'S': 368 case 'T': 369 case 'u': 370 case 'B': 371 case '0': 372 /* These are left unchanged. */ 373 break; 374 375 default: 376 gcc_unreachable (); 377 } 378 return copy; 379 } 380 381 /* Create a new copy of an rtx. Only copy just one level. */ 382 383 rtx 384 shallow_copy_rtx (const_rtx orig MEM_STAT_DECL) 385 { 386 const unsigned int size = rtx_size (orig); 387 rtx const copy = ggc_alloc_rtx_def_stat (size PASS_MEM_STAT); 388 memcpy (copy, orig, size); 389 switch (GET_CODE (orig)) 390 { 391 /* RTX codes copy_rtx_if_shared_1 considers are shareable, 392 the used flag is often used for other purposes. */ 393 case REG: 394 case DEBUG_EXPR: 395 case VALUE: 396 CASE_CONST_ANY: 397 case SYMBOL_REF: 398 case CODE_LABEL: 399 case PC: 400 case CC0: 401 case RETURN: 402 case SIMPLE_RETURN: 403 case SCRATCH: 404 break; 405 default: 406 /* For all other RTXes clear the used flag on the copy. */ 407 RTX_FLAG (copy, used) = 0; 408 break; 409 } 410 return copy; 411 } 412 413 /* Nonzero when we are generating CONCATs. */ 414 int generating_concat_p; 415 416 /* Nonzero when we are expanding trees to RTL. */ 417 int currently_expanding_to_rtl; 418 419 420 421 /* Same as rtx_equal_p, but call CB on each pair of rtx if CB is not NULL. 422 When the callback returns true, we continue with the new pair. 423 Whenever changing this function check if rtx_equal_p below doesn't need 424 changing as well. */ 425 426 int 427 rtx_equal_p_cb (const_rtx x, const_rtx y, rtx_equal_p_callback_function cb) 428 { 429 int i; 430 int j; 431 enum rtx_code code; 432 const char *fmt; 433 rtx nx, ny; 434 435 if (x == y) 436 return 1; 437 if (x == 0 || y == 0) 438 return 0; 439 440 /* Invoke the callback first. */ 441 if (cb != NULL 442 && ((*cb) (&x, &y, &nx, &ny))) 443 return rtx_equal_p_cb (nx, ny, cb); 444 445 code = GET_CODE (x); 446 /* Rtx's of different codes cannot be equal. */ 447 if (code != GET_CODE (y)) 448 return 0; 449 450 /* (MULT:SI x y) and (MULT:HI x y) are NOT equivalent. 451 (REG:SI x) and (REG:HI x) are NOT equivalent. */ 452 453 if (GET_MODE (x) != GET_MODE (y)) 454 return 0; 455 456 /* MEMs referring to different address space are not equivalent. */ 457 if (code == MEM && MEM_ADDR_SPACE (x) != MEM_ADDR_SPACE (y)) 458 return 0; 459 460 /* Some RTL can be compared nonrecursively. */ 461 switch (code) 462 { 463 case REG: 464 return (REGNO (x) == REGNO (y)); 465 466 case LABEL_REF: 467 return label_ref_label (x) == label_ref_label (y); 468 469 case SYMBOL_REF: 470 return XSTR (x, 0) == XSTR (y, 0); 471 472 case DEBUG_EXPR: 473 case VALUE: 474 case SCRATCH: 475 CASE_CONST_UNIQUE: 476 return 0; 477 478 case DEBUG_IMPLICIT_PTR: 479 return DEBUG_IMPLICIT_PTR_DECL (x) 480 == DEBUG_IMPLICIT_PTR_DECL (y); 481 482 case DEBUG_PARAMETER_REF: 483 return DEBUG_PARAMETER_REF_DECL (x) 484 == DEBUG_PARAMETER_REF_DECL (y); 485 486 case ENTRY_VALUE: 487 return rtx_equal_p_cb (ENTRY_VALUE_EXP (x), ENTRY_VALUE_EXP (y), cb); 488 489 default: 490 break; 491 } 492 493 /* Compare the elements. If any pair of corresponding elements 494 fail to match, return 0 for the whole thing. */ 495 496 fmt = GET_RTX_FORMAT (code); 497 for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--) 498 { 499 switch (fmt[i]) 500 { 501 case 'w': 502 if (XWINT (x, i) != XWINT (y, i)) 503 return 0; 504 break; 505 506 case 'n': 507 case 'i': 508 if (XINT (x, i) != XINT (y, i)) 509 { 510 #ifndef GENERATOR_FILE 511 if (((code == ASM_OPERANDS && i == 6) 512 || (code == ASM_INPUT && i == 1)) 513 && XINT (x, i) == XINT (y, i)) 514 break; 515 #endif 516 return 0; 517 } 518 break; 519 520 case 'p': 521 if (maybe_ne (SUBREG_BYTE (x), SUBREG_BYTE (y))) 522 return 0; 523 break; 524 525 case 'V': 526 case 'E': 527 /* Two vectors must have the same length. */ 528 if (XVECLEN (x, i) != XVECLEN (y, i)) 529 return 0; 530 531 /* And the corresponding elements must match. */ 532 for (j = 0; j < XVECLEN (x, i); j++) 533 if (rtx_equal_p_cb (XVECEXP (x, i, j), 534 XVECEXP (y, i, j), cb) == 0) 535 return 0; 536 break; 537 538 case 'e': 539 if (rtx_equal_p_cb (XEXP (x, i), XEXP (y, i), cb) == 0) 540 return 0; 541 break; 542 543 case 'S': 544 case 's': 545 if ((XSTR (x, i) || XSTR (y, i)) 546 && (! XSTR (x, i) || ! XSTR (y, i) 547 || strcmp (XSTR (x, i), XSTR (y, i)))) 548 return 0; 549 break; 550 551 case 'u': 552 /* These are just backpointers, so they don't matter. */ 553 break; 554 555 case '0': 556 case 't': 557 break; 558 559 /* It is believed that rtx's at this level will never 560 contain anything but integers and other rtx's, 561 except for within LABEL_REFs and SYMBOL_REFs. */ 562 default: 563 gcc_unreachable (); 564 } 565 } 566 return 1; 567 } 568 569 /* Return 1 if X and Y are identical-looking rtx's. 570 This is the Lisp function EQUAL for rtx arguments. 571 Whenever changing this function check if rtx_equal_p_cb above doesn't need 572 changing as well. */ 573 574 int 575 rtx_equal_p (const_rtx x, const_rtx y) 576 { 577 int i; 578 int j; 579 enum rtx_code code; 580 const char *fmt; 581 582 if (x == y) 583 return 1; 584 if (x == 0 || y == 0) 585 return 0; 586 587 code = GET_CODE (x); 588 /* Rtx's of different codes cannot be equal. */ 589 if (code != GET_CODE (y)) 590 return 0; 591 592 /* (MULT:SI x y) and (MULT:HI x y) are NOT equivalent. 593 (REG:SI x) and (REG:HI x) are NOT equivalent. */ 594 595 if (GET_MODE (x) != GET_MODE (y)) 596 return 0; 597 598 /* MEMs referring to different address space are not equivalent. */ 599 if (code == MEM && MEM_ADDR_SPACE (x) != MEM_ADDR_SPACE (y)) 600 return 0; 601 602 /* Some RTL can be compared nonrecursively. */ 603 switch (code) 604 { 605 case REG: 606 return (REGNO (x) == REGNO (y)); 607 608 case LABEL_REF: 609 return label_ref_label (x) == label_ref_label (y); 610 611 case SYMBOL_REF: 612 return XSTR (x, 0) == XSTR (y, 0); 613 614 case DEBUG_EXPR: 615 case VALUE: 616 case SCRATCH: 617 CASE_CONST_UNIQUE: 618 return 0; 619 620 case DEBUG_IMPLICIT_PTR: 621 return DEBUG_IMPLICIT_PTR_DECL (x) 622 == DEBUG_IMPLICIT_PTR_DECL (y); 623 624 case DEBUG_PARAMETER_REF: 625 return DEBUG_PARAMETER_REF_DECL (x) 626 == DEBUG_PARAMETER_REF_DECL (y); 627 628 case ENTRY_VALUE: 629 return rtx_equal_p (ENTRY_VALUE_EXP (x), ENTRY_VALUE_EXP (y)); 630 631 default: 632 break; 633 } 634 635 /* Compare the elements. If any pair of corresponding elements 636 fail to match, return 0 for the whole thing. */ 637 638 fmt = GET_RTX_FORMAT (code); 639 for (i = GET_RTX_LENGTH (code) - 1; i >= 0; i--) 640 { 641 switch (fmt[i]) 642 { 643 case 'w': 644 if (XWINT (x, i) != XWINT (y, i)) 645 return 0; 646 break; 647 648 case 'n': 649 case 'i': 650 if (XINT (x, i) != XINT (y, i)) 651 { 652 #ifndef GENERATOR_FILE 653 if (((code == ASM_OPERANDS && i == 6) 654 || (code == ASM_INPUT && i == 1)) 655 && XINT (x, i) == XINT (y, i)) 656 break; 657 #endif 658 return 0; 659 } 660 break; 661 662 case 'p': 663 if (maybe_ne (SUBREG_BYTE (x), SUBREG_BYTE (y))) 664 return 0; 665 break; 666 667 case 'V': 668 case 'E': 669 /* Two vectors must have the same length. */ 670 if (XVECLEN (x, i) != XVECLEN (y, i)) 671 return 0; 672 673 /* And the corresponding elements must match. */ 674 for (j = 0; j < XVECLEN (x, i); j++) 675 if (rtx_equal_p (XVECEXP (x, i, j), XVECEXP (y, i, j)) == 0) 676 return 0; 677 break; 678 679 case 'e': 680 if (rtx_equal_p (XEXP (x, i), XEXP (y, i)) == 0) 681 return 0; 682 break; 683 684 case 'S': 685 case 's': 686 if ((XSTR (x, i) || XSTR (y, i)) 687 && (! XSTR (x, i) || ! XSTR (y, i) 688 || strcmp (XSTR (x, i), XSTR (y, i)))) 689 return 0; 690 break; 691 692 case 'u': 693 /* These are just backpointers, so they don't matter. */ 694 break; 695 696 case '0': 697 case 't': 698 break; 699 700 /* It is believed that rtx's at this level will never 701 contain anything but integers and other rtx's, 702 except for within LABEL_REFs and SYMBOL_REFs. */ 703 default: 704 gcc_unreachable (); 705 } 706 } 707 return 1; 708 } 709 710 /* Return true if all elements of VEC are equal. */ 711 712 bool 713 rtvec_all_equal_p (const_rtvec vec) 714 { 715 const_rtx first = RTVEC_ELT (vec, 0); 716 /* Optimize the important special case of a vector of constants. 717 The main use of this function is to detect whether every element 718 of CONST_VECTOR is the same. */ 719 switch (GET_CODE (first)) 720 { 721 CASE_CONST_UNIQUE: 722 for (int i = 1, n = GET_NUM_ELEM (vec); i < n; ++i) 723 if (first != RTVEC_ELT (vec, i)) 724 return false; 725 return true; 726 727 default: 728 for (int i = 1, n = GET_NUM_ELEM (vec); i < n; ++i) 729 if (!rtx_equal_p (first, RTVEC_ELT (vec, i))) 730 return false; 731 return true; 732 } 733 } 734 735 /* Return an indication of which type of insn should have X as a body. 736 In generator files, this can be UNKNOWN if the answer is only known 737 at (GCC) runtime. Otherwise the value is CODE_LABEL, INSN, CALL_INSN 738 or JUMP_INSN. */ 739 740 enum rtx_code 741 classify_insn (rtx x) 742 { 743 if (LABEL_P (x)) 744 return CODE_LABEL; 745 if (GET_CODE (x) == CALL) 746 return CALL_INSN; 747 if (ANY_RETURN_P (x)) 748 return JUMP_INSN; 749 if (GET_CODE (x) == ASM_OPERANDS && ASM_OPERANDS_LABEL_VEC (x)) 750 return JUMP_INSN; 751 if (GET_CODE (x) == SET) 752 { 753 if (GET_CODE (SET_DEST (x)) == PC) 754 return JUMP_INSN; 755 else if (GET_CODE (SET_SRC (x)) == CALL) 756 return CALL_INSN; 757 else 758 return INSN; 759 } 760 if (GET_CODE (x) == PARALLEL) 761 { 762 int j; 763 bool has_return_p = false; 764 for (j = XVECLEN (x, 0) - 1; j >= 0; j--) 765 if (GET_CODE (XVECEXP (x, 0, j)) == CALL) 766 return CALL_INSN; 767 else if (ANY_RETURN_P (XVECEXP (x, 0, j))) 768 has_return_p = true; 769 else if (GET_CODE (XVECEXP (x, 0, j)) == SET 770 && GET_CODE (SET_DEST (XVECEXP (x, 0, j))) == PC) 771 return JUMP_INSN; 772 else if (GET_CODE (XVECEXP (x, 0, j)) == SET 773 && GET_CODE (SET_SRC (XVECEXP (x, 0, j))) == CALL) 774 return CALL_INSN; 775 if (has_return_p) 776 return JUMP_INSN; 777 if (GET_CODE (XVECEXP (x, 0, 0)) == ASM_OPERANDS 778 && ASM_OPERANDS_LABEL_VEC (XVECEXP (x, 0, 0))) 779 return JUMP_INSN; 780 } 781 #ifdef GENERATOR_FILE 782 if (GET_CODE (x) == MATCH_OPERAND 783 || GET_CODE (x) == MATCH_OPERATOR 784 || GET_CODE (x) == MATCH_PARALLEL 785 || GET_CODE (x) == MATCH_OP_DUP 786 || GET_CODE (x) == MATCH_DUP 787 || GET_CODE (x) == PARALLEL) 788 return UNKNOWN; 789 #endif 790 return INSN; 791 } 792 793 /* Comparator of indices based on rtx_alloc_counts. */ 794 795 static int 796 rtx_count_cmp (const void *p1, const void *p2) 797 { 798 const unsigned *n1 = (const unsigned *)p1; 799 const unsigned *n2 = (const unsigned *)p2; 800 801 return rtx_alloc_counts[*n1] - rtx_alloc_counts[*n2]; 802 } 803 804 void 805 dump_rtx_statistics (void) 806 { 807 int total_counts = 0; 808 int total_sizes = 0; 809 810 if (! GATHER_STATISTICS) 811 { 812 fprintf (stderr, "No RTX statistics\n"); 813 return; 814 } 815 816 fprintf (stderr, "\nRTX Kind Count Bytes\n"); 817 fprintf (stderr, "-------------------------------------------\n"); 818 819 auto_vec<unsigned> indices (LAST_AND_UNUSED_RTX_CODE); 820 for (unsigned i = 0; i < LAST_AND_UNUSED_RTX_CODE; i++) 821 indices.quick_push (i); 822 indices.qsort (rtx_count_cmp); 823 824 for (unsigned i = 0; i < LAST_AND_UNUSED_RTX_CODE; i++) 825 { 826 unsigned j = indices[i]; 827 if (rtx_alloc_counts[j]) 828 { 829 fprintf (stderr, "%-24s " PRsa (6) " " PRsa (9) "\n", 830 GET_RTX_NAME (j), 831 SIZE_AMOUNT (rtx_alloc_counts[j]), 832 SIZE_AMOUNT (rtx_alloc_sizes[j])); 833 total_counts += rtx_alloc_counts[j]; 834 total_sizes += rtx_alloc_sizes[j]; 835 } 836 } 837 838 if (rtvec_alloc_counts) 839 { 840 fprintf (stderr, "%-24s " PRsa (6) " " PRsa (9) "\n", "rtvec", 841 SIZE_AMOUNT (rtvec_alloc_counts), 842 SIZE_AMOUNT (rtvec_alloc_sizes)); 843 total_counts += rtvec_alloc_counts; 844 total_sizes += rtvec_alloc_sizes; 845 } 846 fprintf (stderr, "-----------------------------------------------\n"); 847 fprintf (stderr, "%-24s " PRsa (6) " " PRsa (9) "\n", 848 "Total", SIZE_AMOUNT (total_counts), 849 SIZE_AMOUNT (total_sizes)); 850 fprintf (stderr, "-----------------------------------------------\n"); 851 } 852 853 #if defined ENABLE_RTL_CHECKING && (GCC_VERSION >= 2007) 854 void 855 rtl_check_failed_bounds (const_rtx r, int n, const char *file, int line, 856 const char *func) 857 { 858 internal_error 859 ("RTL check: access of elt %d of '%s' with last elt %d in %s, at %s:%d", 860 n, GET_RTX_NAME (GET_CODE (r)), GET_RTX_LENGTH (GET_CODE (r)) - 1, 861 func, trim_filename (file), line); 862 } 863 864 void 865 rtl_check_failed_type1 (const_rtx r, int n, int c1, const char *file, int line, 866 const char *func) 867 { 868 internal_error 869 ("RTL check: expected elt %d type '%c', have '%c' (rtx %s) in %s, at %s:%d", 870 n, c1, GET_RTX_FORMAT (GET_CODE (r))[n], GET_RTX_NAME (GET_CODE (r)), 871 func, trim_filename (file), line); 872 } 873 874 void 875 rtl_check_failed_type2 (const_rtx r, int n, int c1, int c2, const char *file, 876 int line, const char *func) 877 { 878 internal_error 879 ("RTL check: expected elt %d type '%c' or '%c', have '%c' (rtx %s) in %s, at %s:%d", 880 n, c1, c2, GET_RTX_FORMAT (GET_CODE (r))[n], GET_RTX_NAME (GET_CODE (r)), 881 func, trim_filename (file), line); 882 } 883 884 void 885 rtl_check_failed_code1 (const_rtx r, enum rtx_code code, const char *file, 886 int line, const char *func) 887 { 888 internal_error ("RTL check: expected code '%s', have '%s' in %s, at %s:%d", 889 GET_RTX_NAME (code), GET_RTX_NAME (GET_CODE (r)), func, 890 trim_filename (file), line); 891 } 892 893 void 894 rtl_check_failed_code2 (const_rtx r, enum rtx_code code1, enum rtx_code code2, 895 const char *file, int line, const char *func) 896 { 897 internal_error 898 ("RTL check: expected code '%s' or '%s', have '%s' in %s, at %s:%d", 899 GET_RTX_NAME (code1), GET_RTX_NAME (code2), GET_RTX_NAME (GET_CODE (r)), 900 func, trim_filename (file), line); 901 } 902 903 void 904 rtl_check_failed_code3 (const_rtx r, enum rtx_code code1, enum rtx_code code2, 905 enum rtx_code code3, const char *file, int line, 906 const char *func) 907 { 908 internal_error 909 ("RTL check: expected code '%s', '%s' or '%s', have '%s' in %s, at %s:%d", 910 GET_RTX_NAME (code1), GET_RTX_NAME (code2), GET_RTX_NAME (code3), 911 GET_RTX_NAME (GET_CODE (r)), func, trim_filename (file), line); 912 } 913 914 void 915 rtl_check_failed_code_mode (const_rtx r, enum rtx_code code, machine_mode mode, 916 bool not_mode, const char *file, int line, 917 const char *func) 918 { 919 internal_error ((not_mode 920 ? ("RTL check: expected code '%s' and not mode '%s', " 921 "have code '%s' and mode '%s' in %s, at %s:%d") 922 : ("RTL check: expected code '%s' and mode '%s', " 923 "have code '%s' and mode '%s' in %s, at %s:%d")), 924 GET_RTX_NAME (code), GET_MODE_NAME (mode), 925 GET_RTX_NAME (GET_CODE (r)), GET_MODE_NAME (GET_MODE (r)), 926 func, trim_filename (file), line); 927 } 928 929 /* Report that line LINE of FILE tried to access the block symbol fields 930 of a non-block symbol. FUNC is the function that contains the line. */ 931 932 void 933 rtl_check_failed_block_symbol (const char *file, int line, const char *func) 934 { 935 internal_error 936 ("RTL check: attempt to treat non-block symbol as a block symbol " 937 "in %s, at %s:%d", func, trim_filename (file), line); 938 } 939 940 /* XXX Maybe print the vector? */ 941 void 942 cwi_check_failed_bounds (const_rtx x, int n, const char *file, int line, 943 const char *func) 944 { 945 internal_error 946 ("RTL check: access of hwi elt %d of vector with last elt %d in %s, at %s:%d", 947 n, CWI_GET_NUM_ELEM (x) - 1, func, trim_filename (file), line); 948 } 949 950 /* XXX Maybe print the vector? */ 951 void 952 rtvec_check_failed_bounds (const_rtvec r, int n, const char *file, int line, 953 const char *func) 954 { 955 internal_error 956 ("RTL check: access of elt %d of vector with last elt %d in %s, at %s:%d", 957 n, GET_NUM_ELEM (r) - 1, func, trim_filename (file), line); 958 } 959 #endif /* ENABLE_RTL_CHECKING */ 960 961 #if defined ENABLE_RTL_FLAG_CHECKING 962 void 963 rtl_check_failed_flag (const char *name, const_rtx r, const char *file, 964 int line, const char *func) 965 { 966 internal_error 967 ("RTL flag check: %s used with unexpected rtx code '%s' in %s, at %s:%d", 968 name, GET_RTX_NAME (GET_CODE (r)), func, trim_filename (file), line); 969 } 970 #endif /* ENABLE_RTL_FLAG_CHECKING */ 971