|
|
1.1 root 1: /* Expands front end tree to back end RTL for GNU C-Compiler 1.1.1.8 ! root 2: Copyright (C) 1987, 88, 89, 92, 93, 94, 1995 Free Software Foundation, Inc. 1.1 root 3: 4: This file is part of GNU CC. 5: 6: GNU CC is free software; you can redistribute it and/or modify 7: it under the terms of the GNU General Public License as published by 8: the Free Software Foundation; either version 2, or (at your option) 9: any later version. 10: 11: GNU CC is distributed in the hope that it will be useful, 12: but WITHOUT ANY WARRANTY; without even the implied warranty of 13: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 14: GNU General Public License for more details. 15: 16: You should have received a copy of the GNU General Public License 17: along with GNU CC; see the file COPYING. If not, write to 1.1.1.8 ! root 18: the Free Software Foundation, 59 Temple Place - Suite 330, ! 19: Boston, MA 02111-1307, USA. */ 1.1 root 20: 21: 22: /* This file handles the generation of rtl code from tree structure 23: above the level of expressions, using subroutines in exp*.c and emit-rtl.c. 24: It also creates the rtl expressions for parameters and auto variables 25: and has full responsibility for allocating stack slots. 26: 27: The functions whose names start with `expand_' are called by the 28: parser to generate RTL instructions for various kinds of constructs. 29: 30: Some control and binding constructs require calling several such 31: functions at different times. For example, a simple if-then 32: is expanded by calling `expand_start_cond' (with the condition-expression 33: as argument) before parsing the then-clause and calling `expand_end_cond' 34: after parsing the then-clause. */ 35: 36: #include "config.h" 37: 38: #include <stdio.h> 39: #include <ctype.h> 40: 41: #include "rtl.h" 42: #include "tree.h" 43: #include "flags.h" 44: #include "function.h" 45: #include "insn-flags.h" 46: #include "insn-config.h" 47: #include "insn-codes.h" 48: #include "expr.h" 49: #include "hard-reg-set.h" 50: #include "obstack.h" 51: #include "loop.h" 52: #include "recog.h" 1.1.1.6 root 53: #include "machmode.h" 54: 55: #include "bytecode.h" 56: #include "bc-typecd.h" 57: #include "bc-opcode.h" 58: #include "bc-optab.h" 59: #include "bc-emit.h" 1.1 root 60: 61: #define obstack_chunk_alloc xmalloc 62: #define obstack_chunk_free free 63: struct obstack stmt_obstack; 64: 65: /* Filename and line number of last line-number note, 66: whether we actually emitted it or not. */ 67: char *emit_filename; 68: int emit_lineno; 69: 70: /* Nonzero if within a ({...}) grouping, in which case we must 71: always compute a value for each expr-stmt in case it is the last one. */ 72: 73: int expr_stmts_for_value; 74: 75: /* Each time we expand an expression-statement, 76: record the expr's type and its RTL value here. */ 77: 78: static tree last_expr_type; 79: static rtx last_expr_value; 80: 1.1.1.4 root 81: /* Each time we expand the end of a binding contour (in `expand_end_bindings') 82: and we emit a new NOTE_INSN_BLOCK_END note, we save a pointer to it here. 83: This is used by the `remember_end_note' function to record the endpoint 84: of each generated block in its associated BLOCK node. */ 85: 86: static rtx last_block_end_note; 87: 1.1 root 88: /* Number of binding contours started so far in this function. */ 89: 90: int block_start_count; 91: 92: /* Nonzero if function being compiled needs to 93: return the address of where it has put a structure value. */ 94: 95: extern int current_function_returns_pcc_struct; 96: 97: /* Label that will go on parm cleanup code, if any. 98: Jumping to this label runs cleanup code for parameters, if 99: such code must be run. Following this code is the logical return label. */ 100: 101: extern rtx cleanup_label; 102: 103: /* Label that will go on function epilogue. 104: Jumping to this label serves as a "return" instruction 105: on machines which require execution of the epilogue on all returns. */ 106: 107: extern rtx return_label; 108: 109: /* List (chain of EXPR_LISTs) of pseudo-regs of SAVE_EXPRs. 110: So we can mark them all live at the end of the function, if nonopt. */ 111: extern rtx save_expr_regs; 112: 113: /* Offset to end of allocated area of stack frame. 114: If stack grows down, this is the address of the last stack slot allocated. 115: If stack grows up, this is the address for the next slot. */ 116: extern int frame_offset; 117: 118: /* Label to jump back to for tail recursion, or 0 if we have 119: not yet needed one for this function. */ 120: extern rtx tail_recursion_label; 121: 122: /* Place after which to insert the tail_recursion_label if we need one. */ 123: extern rtx tail_recursion_reentry; 124: 125: /* Location at which to save the argument pointer if it will need to be 126: referenced. There are two cases where this is done: if nonlocal gotos 127: exist, or if vars whose is an offset from the argument pointer will be 128: needed by inner routines. */ 129: 130: extern rtx arg_pointer_save_area; 131: 132: /* Chain of all RTL_EXPRs that have insns in them. */ 133: extern tree rtl_expr_chain; 134: 135: #if 0 /* Turned off because 0 seems to work just as well. */ 136: /* Cleanup lists are required for binding levels regardless of whether 137: that binding level has cleanups or not. This node serves as the 138: cleanup list whenever an empty list is required. */ 139: static tree empty_cleanup_list; 140: #endif 1.1.1.7 root 141: 142: extern void (*interim_eh_hook) PROTO((tree)); 1.1 root 143: 144: /* Functions and data structures for expanding case statements. */ 145: 146: /* Case label structure, used to hold info on labels within case 147: statements. We handle "range" labels; for a single-value label 148: as in C, the high and low limits are the same. 149: 150: A chain of case nodes is initially maintained via the RIGHT fields 151: in the nodes. Nodes with higher case values are later in the list. 152: 153: Switch statements can be output in one of two forms. A branch table 154: is used if there are more than a few labels and the labels are dense 155: within the range between the smallest and largest case value. If a 156: branch table is used, no further manipulations are done with the case 157: node chain. 158: 159: The alternative to the use of a branch table is to generate a series 160: of compare and jump insns. When that is done, we use the LEFT, RIGHT, 161: and PARENT fields to hold a binary tree. Initially the tree is 162: totally unbalanced, with everything on the right. We balance the tree 163: with nodes on the left having lower case values than the parent 164: and nodes on the right having higher values. We then output the tree 165: in order. */ 166: 167: struct case_node 168: { 169: struct case_node *left; /* Left son in binary tree */ 170: struct case_node *right; /* Right son in binary tree; also node chain */ 171: struct case_node *parent; /* Parent of node in binary tree */ 172: tree low; /* Lowest index value for this label */ 173: tree high; /* Highest index value for this label */ 174: tree code_label; /* Label to jump to when node matches */ 175: }; 176: 177: typedef struct case_node case_node; 178: typedef struct case_node *case_node_ptr; 179: 180: /* These are used by estimate_case_costs and balance_case_nodes. */ 181: 182: /* This must be a signed type, and non-ANSI compilers lack signed char. */ 183: static short *cost_table; 184: static int use_cost_table; 185: 186: /* Stack of control and binding constructs we are currently inside. 187: 188: These constructs begin when you call `expand_start_WHATEVER' 189: and end when you call `expand_end_WHATEVER'. This stack records 190: info about how the construct began that tells the end-function 191: what to do. It also may provide information about the construct 192: to alter the behavior of other constructs within the body. 193: For example, they may affect the behavior of C `break' and `continue'. 194: 195: Each construct gets one `struct nesting' object. 196: All of these objects are chained through the `all' field. 197: `nesting_stack' points to the first object (innermost construct). 198: The position of an entry on `nesting_stack' is in its `depth' field. 199: 200: Each type of construct has its own individual stack. 201: For example, loops have `loop_stack'. Each object points to the 202: next object of the same type through the `next' field. 203: 204: Some constructs are visible to `break' exit-statements and others 205: are not. Which constructs are visible depends on the language. 206: Therefore, the data structure allows each construct to be visible 207: or not, according to the args given when the construct is started. 208: The construct is visible if the `exit_label' field is non-null. 209: In that case, the value should be a CODE_LABEL rtx. */ 210: 211: struct nesting 212: { 213: struct nesting *all; 214: struct nesting *next; 215: int depth; 216: rtx exit_label; 217: union 218: { 219: /* For conds (if-then and if-then-else statements). */ 220: struct 221: { 222: /* Label for the end of the if construct. 223: There is none if EXITFLAG was not set 224: and no `else' has been seen yet. */ 225: rtx endif_label; 226: /* Label for the end of this alternative. 227: This may be the end of the if or the next else/elseif. */ 228: rtx next_label; 229: } cond; 230: /* For loops. */ 231: struct 232: { 233: /* Label at the top of the loop; place to loop back to. */ 234: rtx start_label; 235: /* Label at the end of the whole construct. */ 236: rtx end_label; 1.1.1.7 root 237: /* Label before a jump that branches to the end of the whole 238: construct. This is where destructors go if any. */ 239: rtx alt_end_label; 1.1 root 240: /* Label for `continue' statement to jump to; 241: this is in front of the stepper of the loop. */ 242: rtx continue_label; 243: } loop; 244: /* For variable binding contours. */ 245: struct 246: { 247: /* Sequence number of this binding contour within the function, 248: in order of entry. */ 249: int block_start_count; 1.1.1.6 root 250: /* Nonzero => value to restore stack to on exit. Complemented by 251: bc_stack_level (see below) when generating bytecodes. */ 1.1 root 252: rtx stack_level; 253: /* The NOTE that starts this contour. 254: Used by expand_goto to check whether the destination 255: is within each contour or not. */ 256: rtx first_insn; 257: /* Innermost containing binding contour that has a stack level. */ 258: struct nesting *innermost_stack_block; 259: /* List of cleanups to be run on exit from this contour. 260: This is a list of expressions to be evaluated. 261: The TREE_PURPOSE of each link is the ..._DECL node 262: which the cleanup pertains to. */ 263: tree cleanups; 264: /* List of cleanup-lists of blocks containing this block, 265: as they were at the locus where this block appears. 266: There is an element for each containing block, 267: ordered innermost containing block first. 268: The tail of this list can be 0 (was empty_cleanup_list), 269: if all remaining elements would be empty lists. 270: The element's TREE_VALUE is the cleanup-list of that block, 271: which may be null. */ 272: tree outer_cleanups; 273: /* Chain of labels defined inside this binding contour. 274: For contours that have stack levels or cleanups. */ 275: struct label_chain *label_chain; 276: /* Number of function calls seen, as of start of this block. */ 277: int function_call_count; 1.1.1.6 root 278: /* Bytecode specific: stack level to restore stack to on exit. */ 279: int bc_stack_level; 1.1 root 280: } block; 281: /* For switch (C) or case (Pascal) statements, 282: and also for dummies (see `expand_start_case_dummy'). */ 283: struct 284: { 285: /* The insn after which the case dispatch should finally 286: be emitted. Zero for a dummy. */ 287: rtx start; 1.1.1.6 root 288: /* For bytecodes, the case table is in-lined right in the code. 289: A label is needed for skipping over this block. It is only 290: used when generating bytecodes. */ 291: rtx skip_label; 1.1 root 292: /* A list of case labels, kept in ascending order by value 293: as the list is built. 294: During expand_end_case, this list may be rearranged into a 295: nearly balanced binary tree. */ 296: struct case_node *case_list; 297: /* Label to jump to if no case matches. */ 298: tree default_label; 299: /* The expression to be dispatched on. */ 300: tree index_expr; 301: /* Type that INDEX_EXPR should be converted to. */ 302: tree nominal_type; 303: /* Number of range exprs in case statement. */ 304: int num_ranges; 305: /* Name of this kind of statement, for warnings. */ 306: char *printname; 307: /* Nonzero if a case label has been seen in this case stmt. */ 308: char seenlabel; 309: } case_stmt; 310: } data; 311: }; 312: 313: /* Chain of all pending binding contours. */ 314: struct nesting *block_stack; 315: 1.1.1.4 root 316: /* If any new stacks are added here, add them to POPSTACKS too. */ 317: 1.1 root 318: /* Chain of all pending binding contours that restore stack levels 319: or have cleanups. */ 320: struct nesting *stack_block_stack; 321: 322: /* Chain of all pending conditional statements. */ 323: struct nesting *cond_stack; 324: 325: /* Chain of all pending loops. */ 326: struct nesting *loop_stack; 327: 328: /* Chain of all pending case or switch statements. */ 329: struct nesting *case_stack; 330: 331: /* Separate chain including all of the above, 332: chained through the `all' field. */ 333: struct nesting *nesting_stack; 334: 335: /* Number of entries on nesting_stack now. */ 336: int nesting_depth; 337: 338: /* Allocate and return a new `struct nesting'. */ 339: 340: #define ALLOC_NESTING() \ 341: (struct nesting *) obstack_alloc (&stmt_obstack, sizeof (struct nesting)) 342: 1.1.1.4 root 343: /* Pop the nesting stack element by element until we pop off 344: the element which is at the top of STACK. 345: Update all the other stacks, popping off elements from them 346: as we pop them from nesting_stack. */ 1.1 root 347: 348: #define POPSTACK(STACK) \ 1.1.1.4 root 349: do { struct nesting *target = STACK; \ 350: struct nesting *this; \ 351: do { this = nesting_stack; \ 352: if (loop_stack == this) \ 353: loop_stack = loop_stack->next; \ 354: if (cond_stack == this) \ 355: cond_stack = cond_stack->next; \ 356: if (block_stack == this) \ 357: block_stack = block_stack->next; \ 358: if (stack_block_stack == this) \ 359: stack_block_stack = stack_block_stack->next; \ 360: if (case_stack == this) \ 361: case_stack = case_stack->next; \ 362: nesting_depth = nesting_stack->depth - 1; \ 1.1 root 363: nesting_stack = this->all; \ 364: obstack_free (&stmt_obstack, this); } \ 1.1.1.4 root 365: while (this != target); } while (0) 1.1 root 366: 367: /* In some cases it is impossible to generate code for a forward goto 368: until the label definition is seen. This happens when it may be necessary 369: for the goto to reset the stack pointer: we don't yet know how to do that. 370: So expand_goto puts an entry on this fixup list. 371: Each time a binding contour that resets the stack is exited, 372: we check each fixup. 373: If the target label has now been defined, we can insert the proper code. */ 374: 375: struct goto_fixup 376: { 377: /* Points to following fixup. */ 378: struct goto_fixup *next; 379: /* Points to the insn before the jump insn. 380: If more code must be inserted, it goes after this insn. */ 381: rtx before_jump; 382: /* The LABEL_DECL that this jump is jumping to, or 0 383: for break, continue or return. */ 384: tree target; 1.1.1.4 root 385: /* The BLOCK for the place where this goto was found. */ 386: tree context; 1.1 root 387: /* The CODE_LABEL rtx that this is jumping to. */ 388: rtx target_rtl; 389: /* Number of binding contours started in current function 390: before the label reference. */ 391: int block_start_count; 392: /* The outermost stack level that should be restored for this jump. 393: Each time a binding contour that resets the stack is exited, 394: if the target label is *not* yet defined, this slot is updated. */ 395: rtx stack_level; 396: /* List of lists of cleanup expressions to be run by this goto. 397: There is one element for each block that this goto is within. 398: The tail of this list can be 0 (was empty_cleanup_list), 399: if all remaining elements would be empty. 400: The TREE_VALUE contains the cleanup list of that block as of the 401: time this goto was seen. 402: The TREE_ADDRESSABLE flag is 1 for a block that has been exited. */ 403: tree cleanup_list_list; 1.1.1.6 root 404: 405: /* Bytecode specific members follow */ 406: 407: /* The label that this jump is jumping to, or 0 for break, continue 408: or return. */ 409: struct bc_label *bc_target; 410: 411: /* The label we use for the fixup patch */ 412: struct bc_label *label; 413: 414: /* True (non-0) if fixup has been handled */ 415: int bc_handled:1; 416: 417: /* Like stack_level above, except refers to the interpreter stack */ 418: int bc_stack_level; 1.1 root 419: }; 420: 421: static struct goto_fixup *goto_fixup_chain; 422: 423: /* Within any binding contour that must restore a stack level, 424: all labels are recorded with a chain of these structures. */ 425: 426: struct label_chain 427: { 428: /* Points to following fixup. */ 429: struct label_chain *next; 430: tree label; 431: }; 1.1.1.7 root 432: static void expand_goto_internal PROTO((tree, rtx, rtx)); 433: static void bc_expand_goto_internal PROTO((enum bytecode_opcode, 434: struct bc_label *, tree)); 435: static int expand_fixup PROTO((tree, rtx, rtx)); 436: static void bc_expand_fixup PROTO((enum bytecode_opcode, 437: struct bc_label *, int)); 438: static void fixup_gotos PROTO((struct nesting *, rtx, tree, 439: rtx, int)); 440: static void bc_fixup_gotos PROTO((struct nesting *, int, tree, 441: rtx, int)); 442: static void bc_expand_start_cond PROTO((tree, int)); 443: static void bc_expand_end_cond PROTO((void)); 444: static void bc_expand_start_else PROTO((void)); 445: static void bc_expand_end_loop PROTO((void)); 446: static void bc_expand_end_bindings PROTO((tree, int, int)); 447: static void bc_expand_decl PROTO((tree, tree)); 448: static void bc_expand_variable_local_init PROTO((tree)); 449: static void bc_expand_decl_init PROTO((tree)); 450: static void expand_null_return_1 PROTO((rtx, int)); 1.1.1.8 ! root 451: static void expand_value_return PROTO((rtx)); 1.1.1.7 root 452: static int tail_recursion_args PROTO((tree, tree)); 1.1.1.8 ! root 453: static void expand_cleanups PROTO((tree, tree, int, int)); 1.1.1.7 root 454: static void bc_expand_start_case PROTO((struct nesting *, tree, 455: tree, char *)); 456: static int bc_pushcase PROTO((tree, tree)); 457: static void bc_check_for_full_enumeration_handling PROTO((tree)); 458: static void bc_expand_end_case PROTO((tree)); 459: static void do_jump_if_equal PROTO((rtx, rtx, rtx, int)); 460: static int estimate_case_costs PROTO((case_node_ptr)); 461: static void group_case_nodes PROTO((case_node_ptr)); 462: static void balance_case_nodes PROTO((case_node_ptr *, 463: case_node_ptr)); 464: static int node_has_low_bound PROTO((case_node_ptr, tree)); 465: static int node_has_high_bound PROTO((case_node_ptr, tree)); 466: static int node_is_bounded PROTO((case_node_ptr, tree)); 467: static void emit_jump_if_reachable PROTO((rtx)); 468: static void emit_case_nodes PROTO((rtx, case_node_ptr, rtx, tree)); 469: 470: extern rtx bc_allocate_local (); 471: extern rtx bc_allocate_variable_array (); 1.1 root 472: 473: void 474: init_stmt () 475: { 476: gcc_obstack_init (&stmt_obstack); 477: #if 0 478: empty_cleanup_list = build_tree_list (NULL_TREE, NULL_TREE); 479: #endif 480: } 481: 482: void 483: init_stmt_for_function () 484: { 485: /* We are not currently within any block, conditional, loop or case. */ 486: block_stack = 0; 1.1.1.7 root 487: stack_block_stack = 0; 1.1 root 488: loop_stack = 0; 489: case_stack = 0; 490: cond_stack = 0; 491: nesting_stack = 0; 492: nesting_depth = 0; 493: 494: block_start_count = 0; 495: 496: /* No gotos have been expanded yet. */ 497: goto_fixup_chain = 0; 498: 499: /* We are not processing a ({...}) grouping. */ 500: expr_stmts_for_value = 0; 501: last_expr_type = 0; 502: } 503: 504: void 505: save_stmt_status (p) 506: struct function *p; 507: { 508: p->block_stack = block_stack; 509: p->stack_block_stack = stack_block_stack; 510: p->cond_stack = cond_stack; 511: p->loop_stack = loop_stack; 512: p->case_stack = case_stack; 513: p->nesting_stack = nesting_stack; 514: p->nesting_depth = nesting_depth; 515: p->block_start_count = block_start_count; 516: p->last_expr_type = last_expr_type; 517: p->last_expr_value = last_expr_value; 518: p->expr_stmts_for_value = expr_stmts_for_value; 519: p->emit_filename = emit_filename; 520: p->emit_lineno = emit_lineno; 521: p->goto_fixup_chain = goto_fixup_chain; 522: } 523: 524: void 525: restore_stmt_status (p) 526: struct function *p; 527: { 528: block_stack = p->block_stack; 529: stack_block_stack = p->stack_block_stack; 530: cond_stack = p->cond_stack; 531: loop_stack = p->loop_stack; 532: case_stack = p->case_stack; 533: nesting_stack = p->nesting_stack; 534: nesting_depth = p->nesting_depth; 535: block_start_count = p->block_start_count; 536: last_expr_type = p->last_expr_type; 537: last_expr_value = p->last_expr_value; 538: expr_stmts_for_value = p->expr_stmts_for_value; 539: emit_filename = p->emit_filename; 540: emit_lineno = p->emit_lineno; 541: goto_fixup_chain = p->goto_fixup_chain; 542: } 543: 544: /* Emit a no-op instruction. */ 545: 546: void 547: emit_nop () 548: { 1.1.1.6 root 549: rtx last_insn; 550: 551: if (!output_bytecode) 552: { 553: last_insn = get_last_insn (); 554: if (!optimize 555: && (GET_CODE (last_insn) == CODE_LABEL 1.1.1.8 ! root 556: || (GET_CODE (last_insn) == NOTE ! 557: && prev_real_insn (last_insn) == 0))) 1.1.1.6 root 558: emit_insn (gen_nop ()); 559: } 1.1 root 560: } 561: 562: /* Return the rtx-label that corresponds to a LABEL_DECL, 563: creating it if necessary. */ 564: 565: rtx 566: label_rtx (label) 567: tree label; 568: { 569: if (TREE_CODE (label) != LABEL_DECL) 570: abort (); 571: 572: if (DECL_RTL (label)) 573: return DECL_RTL (label); 574: 575: return DECL_RTL (label) = gen_label_rtx (); 576: } 577: 578: /* Add an unconditional jump to LABEL as the next sequential instruction. */ 579: 580: void 581: emit_jump (label) 582: rtx label; 583: { 584: do_pending_stack_adjust (); 585: emit_jump_insn (gen_jump (label)); 586: emit_barrier (); 587: } 588: 589: /* Emit code to jump to the address 590: specified by the pointer expression EXP. */ 591: 592: void 593: expand_computed_goto (exp) 594: tree exp; 595: { 1.1.1.6 root 596: if (output_bytecode) 597: { 598: bc_expand_expr (exp); 599: bc_emit_instruction (jumpP); 600: } 601: else 602: { 603: rtx x = expand_expr (exp, NULL_RTX, VOIDmode, 0); 1.1.1.8 ! root 604: ! 605: #ifdef POINTERS_EXTEND_UNSIGNED ! 606: x = convert_memory_address (Pmode, x); ! 607: #endif ! 608: 1.1.1.6 root 609: emit_queue (); 1.1.1.8 ! root 610: do_pending_stack_adjust (); 1.1.1.6 root 611: emit_indirect_jump (x); 612: } 1.1 root 613: } 614: 615: /* Handle goto statements and the labels that they can go to. */ 616: 617: /* Specify the location in the RTL code of a label LABEL, 618: which is a LABEL_DECL tree node. 619: 620: This is used for the kind of label that the user can jump to with a 621: goto statement, and for alternatives of a switch or case statement. 622: RTL labels generated for loops and conditionals don't go through here; 623: they are generated directly at the RTL level, by other functions below. 624: 625: Note that this has nothing to do with defining label *names*. 626: Languages vary in how they do that and what that even means. */ 627: 628: void 629: expand_label (label) 630: tree label; 631: { 632: struct label_chain *p; 633: 1.1.1.6 root 634: if (output_bytecode) 635: { 636: if (! DECL_RTL (label)) 637: DECL_RTL (label) = bc_gen_rtx ((char *) 0, 0, bc_get_bytecode_label ()); 638: if (! bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (DECL_RTL (label)))) 639: error ("multiply defined label"); 640: return; 641: } 642: 1.1 root 643: do_pending_stack_adjust (); 644: emit_label (label_rtx (label)); 645: if (DECL_NAME (label)) 646: LABEL_NAME (DECL_RTL (label)) = IDENTIFIER_POINTER (DECL_NAME (label)); 647: 648: if (stack_block_stack != 0) 649: { 650: p = (struct label_chain *) oballoc (sizeof (struct label_chain)); 651: p->next = stack_block_stack->data.block.label_chain; 652: stack_block_stack->data.block.label_chain = p; 653: p->label = label; 654: } 655: } 656: 657: /* Declare that LABEL (a LABEL_DECL) may be used for nonlocal gotos 658: from nested functions. */ 659: 660: void 661: declare_nonlocal_label (label) 662: tree label; 663: { 664: nonlocal_labels = tree_cons (NULL_TREE, label, nonlocal_labels); 665: LABEL_PRESERVE_P (label_rtx (label)) = 1; 666: if (nonlocal_goto_handler_slot == 0) 667: { 668: nonlocal_goto_handler_slot 669: = assign_stack_local (Pmode, GET_MODE_SIZE (Pmode), 0); 1.1.1.3 root 670: emit_stack_save (SAVE_NONLOCAL, 671: &nonlocal_goto_stack_level, 672: PREV_INSN (tail_recursion_reentry)); 1.1 root 673: } 674: } 675: 676: /* Generate RTL code for a `goto' statement with target label LABEL. 677: LABEL should be a LABEL_DECL tree node that was or will later be 678: defined with `expand_label'. */ 679: 680: void 681: expand_goto (label) 682: tree label; 683: { 1.1.1.6 root 684: tree context; 685: 686: if (output_bytecode) 687: { 688: expand_goto_internal (label, label_rtx (label), NULL_RTX); 689: return; 690: } 691: 1.1 root 692: /* Check for a nonlocal goto to a containing function. */ 1.1.1.6 root 693: context = decl_function_context (label); 1.1 root 694: if (context != 0 && context != current_function_decl) 695: { 696: struct function *p = find_function_data (context); 1.1.1.4 root 697: rtx label_ref = gen_rtx (LABEL_REF, Pmode, label_rtx (label)); 1.1 root 698: rtx temp; 1.1.1.4 root 699: 1.1 root 700: p->has_nonlocal_label = 1; 1.1.1.6 root 701: current_function_has_nonlocal_goto = 1; 1.1.1.4 root 702: LABEL_REF_NONLOCAL_P (label_ref) = 1; 1.1.1.3 root 703: 704: /* Copy the rtl for the slots so that they won't be shared in 705: case the virtual stack vars register gets instantiated differently 706: in the parent than in the child. */ 707: 1.1 root 708: #if HAVE_nonlocal_goto 709: if (HAVE_nonlocal_goto) 710: emit_insn (gen_nonlocal_goto (lookup_static_chain (label), 1.1.1.3 root 711: copy_rtx (p->nonlocal_goto_handler_slot), 712: copy_rtx (p->nonlocal_goto_stack_level), 1.1.1.4 root 713: label_ref)); 1.1 root 714: else 715: #endif 716: { 1.1.1.3 root 717: rtx addr; 718: 1.1 root 719: /* Restore frame pointer for containing function. 720: This sets the actual hard register used for the frame pointer 721: to the location of the function's incoming static chain info. 722: The non-local goto handler will then adjust it to contain the 723: proper value and reload the argument pointer, if needed. */ 1.1.1.6 root 724: emit_move_insn (hard_frame_pointer_rtx, lookup_static_chain (label)); 1.1.1.3 root 725: 726: /* We have now loaded the frame pointer hardware register with 727: the address of that corresponds to the start of the virtual 728: stack vars. So replace virtual_stack_vars_rtx in all 729: addresses we use with stack_pointer_rtx. */ 730: 1.1 root 731: /* Get addr of containing function's current nonlocal goto handler, 732: which will do any cleanups and then jump to the label. */ 1.1.1.3 root 733: addr = copy_rtx (p->nonlocal_goto_handler_slot); 734: temp = copy_to_reg (replace_rtx (addr, virtual_stack_vars_rtx, 1.1.1.6 root 735: hard_frame_pointer_rtx)); 1.1.1.3 root 736: 1.1 root 737: /* Restore the stack pointer. Note this uses fp just restored. */ 1.1.1.3 root 738: addr = p->nonlocal_goto_stack_level; 739: if (addr) 740: addr = replace_rtx (copy_rtx (addr), 1.1.1.6 root 741: virtual_stack_vars_rtx, 742: hard_frame_pointer_rtx); 1.1.1.3 root 743: 1.1.1.4 root 744: emit_stack_restore (SAVE_NONLOCAL, addr, NULL_RTX); 1.1.1.3 root 745: 1.1 root 746: /* Put in the static chain register the nonlocal label address. */ 1.1.1.4 root 747: emit_move_insn (static_chain_rtx, label_ref); 1.1.1.6 root 748: /* USE of hard_frame_pointer_rtx added for consistency; not clear if 1.1 root 749: really needed. */ 1.1.1.6 root 750: emit_insn (gen_rtx (USE, VOIDmode, hard_frame_pointer_rtx)); 1.1 root 751: emit_insn (gen_rtx (USE, VOIDmode, stack_pointer_rtx)); 752: emit_insn (gen_rtx (USE, VOIDmode, static_chain_rtx)); 753: emit_indirect_jump (temp); 754: } 755: } 756: else 1.1.1.4 root 757: expand_goto_internal (label, label_rtx (label), NULL_RTX); 1.1 root 758: } 759: 760: /* Generate RTL code for a `goto' statement with target label BODY. 761: LABEL should be a LABEL_REF. 762: LAST_INSN, if non-0, is the rtx we should consider as the last 763: insn emitted (for the purposes of cleaning up a return). */ 764: 765: static void 766: expand_goto_internal (body, label, last_insn) 767: tree body; 768: rtx label; 769: rtx last_insn; 770: { 771: struct nesting *block; 772: rtx stack_level = 0; 773: 1.1.1.6 root 774: /* NOTICE! If a bytecode instruction other than `jump' is needed, 775: then the caller has to call bc_expand_goto_internal() 776: directly. This is rather an exceptional case, and there aren't 777: that many places where this is necessary. */ 778: if (output_bytecode) 779: { 780: expand_goto_internal (body, label, last_insn); 781: return; 782: } 783: 1.1 root 784: if (GET_CODE (label) != CODE_LABEL) 785: abort (); 786: 787: /* If label has already been defined, we can tell now 788: whether and how we must alter the stack level. */ 789: 790: if (PREV_INSN (label) != 0) 791: { 792: /* Find the innermost pending block that contains the label. 793: (Check containment by comparing insn-uids.) 794: Then restore the outermost stack level within that block, 795: and do cleanups of all blocks contained in it. */ 796: for (block = block_stack; block; block = block->next) 797: { 798: if (INSN_UID (block->data.block.first_insn) < INSN_UID (label)) 799: break; 800: if (block->data.block.stack_level != 0) 801: stack_level = block->data.block.stack_level; 802: /* Execute the cleanups for blocks we are exiting. */ 803: if (block->data.block.cleanups != 0) 804: { 1.1.1.8 ! root 805: expand_cleanups (block->data.block.cleanups, NULL_TREE, 1, 1); 1.1 root 806: do_pending_stack_adjust (); 807: } 808: } 809: 810: if (stack_level) 811: { 812: /* Ensure stack adjust isn't done by emit_jump, as this would clobber 813: the stack pointer. This one should be deleted as dead by flow. */ 814: clear_pending_stack_adjust (); 815: do_pending_stack_adjust (); 1.1.1.4 root 816: emit_stack_restore (SAVE_BLOCK, stack_level, NULL_RTX); 1.1 root 817: } 818: 819: if (body != 0 && DECL_TOO_LATE (body)) 820: error ("jump to `%s' invalidly jumps into binding contour", 821: IDENTIFIER_POINTER (DECL_NAME (body))); 822: } 823: /* Label not yet defined: may need to put this goto 824: on the fixup list. */ 825: else if (! expand_fixup (body, label, last_insn)) 826: { 827: /* No fixup needed. Record that the label is the target 828: of at least one goto that has no fixup. */ 829: if (body != 0) 830: TREE_ADDRESSABLE (body) = 1; 831: } 832: 833: emit_jump (label); 834: } 835: 1.1.1.6 root 836: /* Generate a jump with OPCODE to the given bytecode LABEL which is 837: found within BODY. */ 1.1.1.7 root 838: 1.1.1.6 root 839: static void 840: bc_expand_goto_internal (opcode, label, body) 841: enum bytecode_opcode opcode; 842: struct bc_label *label; 843: tree body; 844: { 845: struct nesting *block; 846: int stack_level = -1; 847: 848: /* If the label is defined, adjust the stack as necessary. 849: If it's not defined, we have to push the reference on the 850: fixup list. */ 851: 852: if (label->defined) 853: { 854: 855: /* Find the innermost pending block that contains the label. 856: (Check containment by comparing bytecode uids.) Then restore the 857: outermost stack level within that block. */ 858: 859: for (block = block_stack; block; block = block->next) 860: { 861: if (BYTECODE_BC_LABEL (block->data.block.first_insn)->uid < label->uid) 862: break; 863: if (block->data.block.bc_stack_level) 864: stack_level = block->data.block.bc_stack_level; 865: 866: /* Execute the cleanups for blocks we are exiting. */ 867: if (block->data.block.cleanups != 0) 868: { 1.1.1.8 ! root 869: expand_cleanups (block->data.block.cleanups, NULL_TREE, 1, 1); 1.1.1.6 root 870: do_pending_stack_adjust (); 871: } 872: } 873: 874: /* Restore the stack level. If we need to adjust the stack, we 875: must do so after the jump, since the jump may depend on 876: what's on the stack. Thus, any stack-modifying conditional 877: jumps (these are the only ones that rely on what's on the 878: stack) go into the fixup list. */ 879: 880: if (stack_level >= 0 881: && stack_depth != stack_level 882: && opcode != jump) 883: 884: bc_expand_fixup (opcode, label, stack_level); 885: else 886: { 887: if (stack_level >= 0) 888: bc_adjust_stack (stack_depth - stack_level); 889: 890: if (body && DECL_BIT_FIELD (body)) 891: error ("jump to `%s' invalidly jumps into binding contour", 892: IDENTIFIER_POINTER (DECL_NAME (body))); 893: 894: /* Emit immediate jump */ 895: bc_emit_bytecode (opcode); 896: bc_emit_bytecode_labelref (label); 897: 898: #ifdef DEBUG_PRINT_CODE 899: fputc ('\n', stderr); 900: #endif 901: } 902: } 903: else 904: /* Put goto in the fixup list */ 905: bc_expand_fixup (opcode, label, stack_level); 906: } 907: 1.1 root 908: /* Generate if necessary a fixup for a goto 909: whose target label in tree structure (if any) is TREE_LABEL 910: and whose target in rtl is RTL_LABEL. 911: 912: If LAST_INSN is nonzero, we pretend that the jump appears 913: after insn LAST_INSN instead of at the current point in the insn stream. 914: 1.1.1.4 root 915: The fixup will be used later to insert insns just before the goto. 916: Those insns will restore the stack level as appropriate for the 917: target label, and will (in the case of C++) also invoke any object 918: destructors which have to be invoked when we exit the scopes which 919: are exited by the goto. 1.1 root 920: 921: Value is nonzero if a fixup is made. */ 922: 923: static int 924: expand_fixup (tree_label, rtl_label, last_insn) 925: tree tree_label; 926: rtx rtl_label; 927: rtx last_insn; 928: { 929: struct nesting *block, *end_block; 930: 931: /* See if we can recognize which block the label will be output in. 932: This is possible in some very common cases. 933: If we succeed, set END_BLOCK to that block. 934: Otherwise, set it to 0. */ 935: 936: if (cond_stack 937: && (rtl_label == cond_stack->data.cond.endif_label 938: || rtl_label == cond_stack->data.cond.next_label)) 939: end_block = cond_stack; 940: /* If we are in a loop, recognize certain labels which 941: are likely targets. This reduces the number of fixups 942: we need to create. */ 943: else if (loop_stack 944: && (rtl_label == loop_stack->data.loop.start_label 945: || rtl_label == loop_stack->data.loop.end_label 946: || rtl_label == loop_stack->data.loop.continue_label)) 947: end_block = loop_stack; 948: else 949: end_block = 0; 950: 951: /* Now set END_BLOCK to the binding level to which we will return. */ 952: 953: if (end_block) 954: { 955: struct nesting *next_block = end_block->all; 956: block = block_stack; 957: 958: /* First see if the END_BLOCK is inside the innermost binding level. 959: If so, then no cleanups or stack levels are relevant. */ 960: while (next_block && next_block != block) 961: next_block = next_block->all; 962: 963: if (next_block) 964: return 0; 965: 966: /* Otherwise, set END_BLOCK to the innermost binding level 967: which is outside the relevant control-structure nesting. */ 968: next_block = block_stack->next; 969: for (block = block_stack; block != end_block; block = block->all) 970: if (block == next_block) 971: next_block = next_block->next; 972: end_block = next_block; 973: } 974: 975: /* Does any containing block have a stack level or cleanups? 976: If not, no fixup is needed, and that is the normal case 977: (the only case, for standard C). */ 978: for (block = block_stack; block != end_block; block = block->next) 979: if (block->data.block.stack_level != 0 980: || block->data.block.cleanups != 0) 981: break; 982: 983: if (block != end_block) 984: { 985: /* Ok, a fixup is needed. Add a fixup to the list of such. */ 986: struct goto_fixup *fixup 987: = (struct goto_fixup *) oballoc (sizeof (struct goto_fixup)); 988: /* In case an old stack level is restored, make sure that comes 989: after any pending stack adjust. */ 990: /* ?? If the fixup isn't to come at the present position, 991: doing the stack adjust here isn't useful. Doing it with our 992: settings at that location isn't useful either. Let's hope 993: someone does it! */ 994: if (last_insn == 0) 995: do_pending_stack_adjust (); 996: fixup->target = tree_label; 997: fixup->target_rtl = rtl_label; 1.1.1.4 root 998: 999: /* Create a BLOCK node and a corresponding matched set of 1000: NOTE_INSN_BEGIN_BLOCK and NOTE_INSN_END_BLOCK notes at 1001: this point. The notes will encapsulate any and all fixup 1002: code which we might later insert at this point in the insn 1003: stream. Also, the BLOCK node will be the parent (i.e. the 1004: `SUPERBLOCK') of any other BLOCK nodes which we might create 1005: later on when we are expanding the fixup code. */ 1006: 1007: { 1008: register rtx original_before_jump 1009: = last_insn ? last_insn : get_last_insn (); 1010: 1011: start_sequence (); 1012: pushlevel (0); 1013: fixup->before_jump = emit_note (NULL_PTR, NOTE_INSN_BLOCK_BEG); 1014: last_block_end_note = emit_note (NULL_PTR, NOTE_INSN_BLOCK_END); 1015: fixup->context = poplevel (1, 0, 0); /* Create the BLOCK node now! */ 1016: end_sequence (); 1017: emit_insns_after (fixup->before_jump, original_before_jump); 1018: } 1019: 1.1 root 1020: fixup->block_start_count = block_start_count; 1021: fixup->stack_level = 0; 1022: fixup->cleanup_list_list 1023: = (((block->data.block.outer_cleanups 1024: #if 0 1025: && block->data.block.outer_cleanups != empty_cleanup_list 1026: #endif 1027: ) 1028: || block->data.block.cleanups) 1.1.1.4 root 1029: ? tree_cons (NULL_TREE, block->data.block.cleanups, 1.1 root 1030: block->data.block.outer_cleanups) 1031: : 0); 1032: fixup->next = goto_fixup_chain; 1033: goto_fixup_chain = fixup; 1034: } 1035: 1036: return block != 0; 1037: } 1038: 1.1.1.6 root 1039: 1040: /* Generate bytecode jump with OPCODE to a fixup routine that links to LABEL. 1041: Make the fixup restore the stack level to STACK_LEVEL. */ 1042: 1043: static void 1044: bc_expand_fixup (opcode, label, stack_level) 1045: enum bytecode_opcode opcode; 1046: struct bc_label *label; 1047: int stack_level; 1048: { 1049: struct goto_fixup *fixup 1050: = (struct goto_fixup *) oballoc (sizeof (struct goto_fixup)); 1051: 1052: fixup->label = bc_get_bytecode_label (); 1053: fixup->bc_target = label; 1054: fixup->bc_stack_level = stack_level; 1055: fixup->bc_handled = FALSE; 1056: 1057: fixup->next = goto_fixup_chain; 1058: goto_fixup_chain = fixup; 1059: 1060: /* Insert a jump to the fixup code */ 1061: bc_emit_bytecode (opcode); 1062: bc_emit_bytecode_labelref (fixup->label); 1063: 1064: #ifdef DEBUG_PRINT_CODE 1065: fputc ('\n', stderr); 1066: #endif 1067: } 1.1.1.7 root 1068: 1069: /* Expand any needed fixups in the outputmost binding level of the 1070: function. FIRST_INSN is the first insn in the function. */ 1.1.1.6 root 1071: 1.1.1.7 root 1072: void 1073: expand_fixups (first_insn) 1074: rtx first_insn; 1075: { 1076: fixup_gotos (NULL_PTR, NULL_RTX, NULL_TREE, first_insn, 0); 1077: } 1.1.1.6 root 1078: 1.1 root 1079: /* When exiting a binding contour, process all pending gotos requiring fixups. 1080: THISBLOCK is the structure that describes the block being exited. 1081: STACK_LEVEL is the rtx for the stack level to restore exiting this contour. 1082: CLEANUP_LIST is a list of expressions to evaluate on exiting this contour. 1083: FIRST_INSN is the insn that began this contour. 1084: 1085: Gotos that jump out of this contour must restore the 1086: stack level and do the cleanups before actually jumping. 1087: 1088: DONT_JUMP_IN nonzero means report error there is a jump into this 1089: contour from before the beginning of the contour. 1090: This is also done if STACK_LEVEL is nonzero. */ 1091: 1.1.1.7 root 1092: static void 1.1 root 1093: fixup_gotos (thisblock, stack_level, cleanup_list, first_insn, dont_jump_in) 1094: struct nesting *thisblock; 1095: rtx stack_level; 1096: tree cleanup_list; 1097: rtx first_insn; 1098: int dont_jump_in; 1099: { 1100: register struct goto_fixup *f, *prev; 1101: 1.1.1.6 root 1102: if (output_bytecode) 1103: { 1.1.1.7 root 1104: /* ??? The second arg is the bc stack level, which is not the same 1105: as STACK_LEVEL. I have no idea what should go here, so I'll 1106: just pass 0. */ 1107: bc_fixup_gotos (thisblock, 0, cleanup_list, first_insn, dont_jump_in); 1.1.1.6 root 1108: return; 1109: } 1110: 1.1 root 1111: /* F is the fixup we are considering; PREV is the previous one. */ 1112: /* We run this loop in two passes so that cleanups of exited blocks 1113: are run first, and blocks that are exited are marked so 1114: afterwards. */ 1115: 1116: for (prev = 0, f = goto_fixup_chain; f; prev = f, f = f->next) 1117: { 1118: /* Test for a fixup that is inactive because it is already handled. */ 1119: if (f->before_jump == 0) 1120: { 1121: /* Delete inactive fixup from the chain, if that is easy to do. */ 1122: if (prev != 0) 1123: prev->next = f->next; 1124: } 1125: /* Has this fixup's target label been defined? 1126: If so, we can finalize it. */ 1127: else if (PREV_INSN (f->target_rtl) != 0) 1128: { 1.1.1.4 root 1129: register rtx cleanup_insns; 1130: 1.1 root 1131: /* Get the first non-label after the label 1132: this goto jumps to. If that's before this scope begins, 1133: we don't have a jump into the scope. */ 1134: rtx after_label = f->target_rtl; 1135: while (after_label != 0 && GET_CODE (after_label) == CODE_LABEL) 1136: after_label = NEXT_INSN (after_label); 1137: 1138: /* If this fixup jumped into this contour from before the beginning 1139: of this contour, report an error. */ 1140: /* ??? Bug: this does not detect jumping in through intermediate 1141: blocks that have stack levels or cleanups. 1142: It detects only a problem with the innermost block 1143: around the label. */ 1144: if (f->target != 0 1145: && (dont_jump_in || stack_level || cleanup_list) 1146: /* If AFTER_LABEL is 0, it means the jump goes to the end 1147: of the rtl, which means it jumps into this scope. */ 1148: && (after_label == 0 1149: || INSN_UID (first_insn) < INSN_UID (after_label)) 1150: && INSN_UID (first_insn) > INSN_UID (f->before_jump) 1.1.1.4 root 1151: && ! DECL_REGISTER (f->target)) 1.1 root 1152: { 1153: error_with_decl (f->target, 1154: "label `%s' used before containing binding contour"); 1155: /* Prevent multiple errors for one label. */ 1.1.1.4 root 1156: DECL_REGISTER (f->target) = 1; 1.1 root 1157: } 1158: 1.1.1.4 root 1159: /* We will expand the cleanups into a sequence of their own and 1160: then later on we will attach this new sequence to the insn 1161: stream just ahead of the actual jump insn. */ 1162: 1163: start_sequence (); 1164: 1165: /* Temporarily restore the lexical context where we will 1166: logically be inserting the fixup code. We do this for the 1167: sake of getting the debugging information right. */ 1168: 1169: pushlevel (0); 1170: set_block (f->context); 1171: 1172: /* Expand the cleanups for blocks this jump exits. */ 1.1 root 1173: if (f->cleanup_list_list) 1174: { 1175: tree lists; 1176: for (lists = f->cleanup_list_list; lists; lists = TREE_CHAIN (lists)) 1177: /* Marked elements correspond to blocks that have been closed. 1178: Do their cleanups. */ 1179: if (TREE_ADDRESSABLE (lists) 1180: && TREE_VALUE (lists) != 0) 1.1.1.4 root 1181: { 1.1.1.8 ! root 1182: expand_cleanups (TREE_VALUE (lists), NULL_TREE, 1, 1); 1.1.1.4 root 1183: /* Pop any pushes done in the cleanups, 1184: in case function is about to return. */ 1185: do_pending_stack_adjust (); 1186: } 1.1 root 1187: } 1188: 1189: /* Restore stack level for the biggest contour that this 1190: jump jumps out of. */ 1191: if (f->stack_level) 1.1.1.3 root 1192: emit_stack_restore (SAVE_BLOCK, f->stack_level, f->before_jump); 1.1.1.4 root 1193: 1194: /* Finish up the sequence containing the insns which implement the 1195: necessary cleanups, and then attach that whole sequence to the 1196: insn stream just ahead of the actual jump insn. Attaching it 1197: at that point insures that any cleanups which are in fact 1198: implicit C++ object destructions (which must be executed upon 1199: leaving the block) appear (to the debugger) to be taking place 1200: in an area of the generated code where the object(s) being 1201: destructed are still "in scope". */ 1202: 1203: cleanup_insns = get_insns (); 1204: poplevel (1, 0, 0); 1205: 1206: end_sequence (); 1207: emit_insns_after (cleanup_insns, f->before_jump); 1208: 1209: 1.1 root 1210: f->before_jump = 0; 1211: } 1212: } 1213: 1.1.1.8 ! root 1214: /* For any still-undefined labels, do the cleanups for this block now. ! 1215: We must do this now since items in the cleanup list may go out ! 1216: of scope when the block ends. */ 1.1 root 1217: for (prev = 0, f = goto_fixup_chain; f; prev = f, f = f->next) 1218: if (f->before_jump != 0 1219: && PREV_INSN (f->target_rtl) == 0 1220: /* Label has still not appeared. If we are exiting a block with 1221: a stack level to restore, that started before the fixup, 1222: mark this stack level as needing restoration 1.1.1.8 ! root 1223: when the fixup is later finalized. */ 1.1 root 1224: && thisblock != 0 1.1.1.8 ! root 1225: /* Note: if THISBLOCK == 0 and we have a label that hasn't appeared, it ! 1226: means the label is undefined. That's erroneous, but possible. */ 1.1 root 1227: && (thisblock->data.block.block_start_count 1228: <= f->block_start_count)) 1229: { 1230: tree lists = f->cleanup_list_list; 1.1.1.8 ! root 1231: rtx cleanup_insns; ! 1232: 1.1 root 1233: for (; lists; lists = TREE_CHAIN (lists)) 1234: /* If the following elt. corresponds to our containing block 1235: then the elt. must be for this block. */ 1236: if (TREE_CHAIN (lists) == thisblock->data.block.outer_cleanups) 1.1.1.8 ! root 1237: { ! 1238: start_sequence (); ! 1239: pushlevel (0); ! 1240: set_block (f->context); ! 1241: expand_cleanups (TREE_VALUE (lists), NULL_TREE, 1, 1); ! 1242: do_pending_stack_adjust (); ! 1243: cleanup_insns = get_insns (); ! 1244: poplevel (1, 0, 0); ! 1245: end_sequence (); ! 1246: f->before_jump ! 1247: = emit_insns_after (cleanup_insns, f->before_jump); ! 1248: ! 1249: f->cleanup_list_list = TREE_CHAIN (lists); ! 1250: } 1.1 root 1251: 1252: if (stack_level) 1253: f->stack_level = stack_level; 1254: } 1255: } 1.1.1.6 root 1256: 1257: 1258: /* When exiting a binding contour, process all pending gotos requiring fixups. 1259: Note: STACK_DEPTH is not altered. 1260: 1.1.1.7 root 1261: The arguments are currently not used in the bytecode compiler, but we may 1262: need them one day for languages other than C. 1.1.1.6 root 1263: 1264: THISBLOCK is the structure that describes the block being exited. 1265: STACK_LEVEL is the rtx for the stack level to restore exiting this contour. 1266: CLEANUP_LIST is a list of expressions to evaluate on exiting this contour. 1267: FIRST_INSN is the insn that began this contour. 1268: 1269: Gotos that jump out of this contour must restore the 1270: stack level and do the cleanups before actually jumping. 1271: 1272: DONT_JUMP_IN nonzero means report error there is a jump into this 1273: contour from before the beginning of the contour. 1274: This is also done if STACK_LEVEL is nonzero. */ 1275: 1276: static void 1277: bc_fixup_gotos (thisblock, stack_level, cleanup_list, first_insn, dont_jump_in) 1278: struct nesting *thisblock; 1279: int stack_level; 1280: tree cleanup_list; 1281: rtx first_insn; 1282: int dont_jump_in; 1283: { 1284: register struct goto_fixup *f, *prev; 1285: int saved_stack_depth; 1286: 1287: /* F is the fixup we are considering; PREV is the previous one. */ 1288: 1289: for (prev = 0, f = goto_fixup_chain; f; prev = f, f = f->next) 1290: { 1291: /* Test for a fixup that is inactive because it is already handled. */ 1292: if (f->before_jump == 0) 1293: { 1294: /* Delete inactive fixup from the chain, if that is easy to do. */ 1295: if (prev) 1296: prev->next = f->next; 1297: } 1298: 1299: /* Emit code to restore the stack and continue */ 1300: bc_emit_bytecode_labeldef (f->label); 1301: 1302: /* Save stack_depth across call, since bc_adjust_stack () will alter 1303: the perceived stack depth via the instructions generated. */ 1304: 1305: if (f->bc_stack_level >= 0) 1306: { 1307: saved_stack_depth = stack_depth; 1308: bc_adjust_stack (stack_depth - f->bc_stack_level); 1309: stack_depth = saved_stack_depth; 1310: } 1311: 1312: bc_emit_bytecode (jump); 1313: bc_emit_bytecode_labelref (f->bc_target); 1314: 1315: #ifdef DEBUG_PRINT_CODE 1316: fputc ('\n', stderr); 1317: #endif 1318: } 1319: 1320: goto_fixup_chain = NULL; 1321: } 1.1 root 1322: 1323: /* Generate RTL for an asm statement (explicit assembler code). 1324: BODY is a STRING_CST node containing the assembler code text, 1325: or an ADDR_EXPR containing a STRING_CST. */ 1326: 1327: void 1328: expand_asm (body) 1329: tree body; 1330: { 1.1.1.6 root 1331: if (output_bytecode) 1332: { 1.1.1.8 ! root 1333: error ("`asm' is invalid when generating bytecode"); 1.1.1.6 root 1334: return; 1335: } 1336: 1.1 root 1337: if (TREE_CODE (body) == ADDR_EXPR) 1338: body = TREE_OPERAND (body, 0); 1339: 1340: emit_insn (gen_rtx (ASM_INPUT, VOIDmode, 1341: TREE_STRING_POINTER (body))); 1342: last_expr_type = 0; 1343: } 1344: 1345: /* Generate RTL for an asm statement with arguments. 1346: STRING is the instruction template. 1347: OUTPUTS is a list of output arguments (lvalues); INPUTS a list of inputs. 1348: Each output or input has an expression in the TREE_VALUE and 1349: a constraint-string in the TREE_PURPOSE. 1350: CLOBBERS is a list of STRING_CST nodes each naming a hard register 1351: that is clobbered by this insn. 1352: 1353: Not all kinds of lvalue that may appear in OUTPUTS can be stored directly. 1354: Some elements of OUTPUTS may be replaced with trees representing temporary 1355: values. The caller should copy those temporary values to the originally 1356: specified lvalues. 1357: 1358: VOL nonzero means the insn is volatile; don't optimize it. */ 1359: 1360: void 1361: expand_asm_operands (string, outputs, inputs, clobbers, vol, filename, line) 1362: tree string, outputs, inputs, clobbers; 1363: int vol; 1364: char *filename; 1365: int line; 1366: { 1367: rtvec argvec, constraints; 1368: rtx body; 1369: int ninputs = list_length (inputs); 1370: int noutputs = list_length (outputs); 1.1.1.3 root 1371: int nclobbers; 1.1 root 1372: tree tail; 1373: register int i; 1374: /* Vector of RTX's of evaluated output operands. */ 1375: rtx *output_rtx = (rtx *) alloca (noutputs * sizeof (rtx)); 1376: /* The insn we have emitted. */ 1377: rtx insn; 1378: 1.1.1.6 root 1379: if (output_bytecode) 1380: { 1.1.1.8 ! root 1381: error ("`asm' is invalid when generating bytecode"); 1.1.1.6 root 1382: return; 1383: } 1384: 1.1.1.3 root 1385: /* Count the number of meaningful clobbered registers, ignoring what 1386: we would ignore later. */ 1387: nclobbers = 0; 1388: for (tail = clobbers; tail; tail = TREE_CHAIN (tail)) 1389: { 1390: char *regname = TREE_STRING_POINTER (TREE_VALUE (tail)); 1.1.1.4 root 1391: i = decode_reg_name (regname); 1392: if (i >= 0 || i == -4) 1.1.1.3 root 1393: ++nclobbers; 1.1.1.7 root 1394: else if (i == -2) 1395: error ("unknown register name `%s' in `asm'", regname); 1.1.1.3 root 1396: } 1397: 1.1 root 1398: last_expr_type = 0; 1399: 1400: for (i = 0, tail = outputs; tail; tail = TREE_CHAIN (tail), i++) 1401: { 1402: tree val = TREE_VALUE (tail); 1.1.1.8 ! root 1403: tree type = TREE_TYPE (val); 1.1 root 1404: tree val1; 1405: int j; 1.1.1.8 ! root 1406: int found_equal = 0; ! 1407: int allows_reg = 0; 1.1 root 1408: 1409: /* If there's an erroneous arg, emit no insn. */ 1410: if (TREE_TYPE (val) == error_mark_node) 1411: return; 1412: 1.1.1.8 ! root 1413: /* Make sure constraint has `=' and does not have `+'. Also, see ! 1414: if it allows any register. Be liberal on the latter test, since ! 1415: the worst that happens if we get it wrong is we issue an error ! 1416: message. */ 1.1 root 1417: 1.1.1.8 ! root 1418: for (j = 0; j < TREE_STRING_LENGTH (TREE_PURPOSE (tail)) - 1; j++) ! 1419: switch (TREE_STRING_POINTER (TREE_PURPOSE (tail))[j]) ! 1420: { ! 1421: case '+': ! 1422: error ("output operand constraint contains `+'"); ! 1423: return; ! 1424: ! 1425: case '=': 1.1 root 1426: found_equal = 1; 1.1.1.8 ! root 1427: break; ! 1428: ! 1429: case '?': case '!': case '*': case '%': case '&': ! 1430: case '0': case '1': case '2': case '3': case '4': ! 1431: case 'V': case 'm': case 'o': case '<': case '>': ! 1432: case 'E': case 'F': case 'G': case 'H': case 'X': ! 1433: case 's': case 'i': case 'n': ! 1434: case 'I': case 'J': case 'K': case 'L': case 'M': ! 1435: case 'N': case 'O': case 'P': case ',': ! 1436: #ifdef EXTRA_CONSTRAINT ! 1437: case 'Q': case 'R': case 'S': case 'T': case 'U': ! 1438: #endif ! 1439: break; ! 1440: ! 1441: case 'p': case 'g': case 'r': ! 1442: default: ! 1443: allows_reg = 1; ! 1444: break; ! 1445: } ! 1446: 1.1 root 1447: if (! found_equal) 1448: { 1449: error ("output operand constraint lacks `='"); 1450: return; 1451: } 1452: 1.1.1.8 ! root 1453: /* If an output operand is not a decl or indirect ref and our constraint ! 1454: allows a register, make a temporary to act as an intermediate. ! 1455: Make the asm insn write into that, then our caller will copy it to ! 1456: the real output operand. Likewise for promoted variables. */ ! 1457: ! 1458: if (TREE_CODE (val) == INDIRECT_REF ! 1459: || (TREE_CODE_CLASS (TREE_CODE (val)) == 'd' ! 1460: && ! (GET_CODE (DECL_RTL (val)) == REG ! 1461: && GET_MODE (DECL_RTL (val)) != TYPE_MODE (type))) ! 1462: || ! allows_reg) ! 1463: { ! 1464: if (! allows_reg) ! 1465: mark_addressable (TREE_VALUE (tail)); ! 1466: ! 1467: output_rtx[i] ! 1468: = expand_expr (TREE_VALUE (tail), NULL_RTX, VOIDmode, 0); ! 1469: ! 1470: if (! allows_reg && GET_CODE (output_rtx[i]) != MEM) ! 1471: error ("output number %d not directly addressable", i); ! 1472: } ! 1473: else ! 1474: { ! 1475: if (TYPE_MODE (type) == BLKmode) 1.1.1.5 root 1476: { 1.1.1.8 ! root 1477: output_rtx[i] = assign_stack_temp (BLKmode, ! 1478: int_size_in_bytes (type), 0); ! 1479: MEM_IN_STRUCT_P (output_rtx[i]) = AGGREGATE_TYPE_P (type); 1.1.1.5 root 1480: } 1.1.1.8 ! root 1481: else ! 1482: output_rtx[i] = gen_reg_rtx (TYPE_MODE (type)); 1.1 root 1483: 1.1.1.8 ! root 1484: TREE_VALUE (tail) = make_tree (type, output_rtx[i]); ! 1485: } 1.1 root 1486: } 1487: 1488: if (ninputs + noutputs > MAX_RECOG_OPERANDS) 1489: { 1490: error ("more than %d operands in `asm'", MAX_RECOG_OPERANDS); 1491: return; 1492: } 1493: 1494: /* Make vectors for the expression-rtx and constraint strings. */ 1495: 1496: argvec = rtvec_alloc (ninputs); 1497: constraints = rtvec_alloc (ninputs); 1498: 1499: body = gen_rtx (ASM_OPERANDS, VOIDmode, 1500: TREE_STRING_POINTER (string), "", 0, argvec, constraints, 1501: filename, line); 1502: MEM_VOLATILE_P (body) = vol; 1503: 1504: /* Eval the inputs and put them into ARGVEC. 1505: Put their constraints into ASM_INPUTs and store in CONSTRAINTS. */ 1506: 1507: i = 0; 1508: for (tail = inputs; tail; tail = TREE_CHAIN (tail)) 1509: { 1510: int j; 1.1.1.8 ! root 1511: int allows_reg = 0; 1.1 root 1512: 1513: /* If there's an erroneous arg, emit no insn, 1514: because the ASM_INPUT would get VOIDmode 1515: and that could cause a crash in reload. */ 1516: if (TREE_TYPE (TREE_VALUE (tail)) == error_mark_node) 1517: return; 1518: if (TREE_PURPOSE (tail) == NULL_TREE) 1519: { 1520: error ("hard register `%s' listed as input operand to `asm'", 1521: TREE_STRING_POINTER (TREE_VALUE (tail)) ); 1522: return; 1523: } 1524: 1525: /* Make sure constraint has neither `=' nor `+'. */ 1526: 1.1.1.8 ! root 1527: for (j = 0; j < TREE_STRING_LENGTH (TREE_PURPOSE (tail)) - 1; j++) ! 1528: switch (TREE_STRING_POINTER (TREE_PURPOSE (tail))[j]) 1.1 root 1529: { 1.1.1.8 ! root 1530: case '+': case '=': 1.1 root 1531: error ("input operand constraint contains `%c'", 1532: TREE_STRING_POINTER (TREE_PURPOSE (tail))[j]); 1533: return; 1.1.1.8 ! root 1534: ! 1535: case '?': case '!': case '*': case '%': case '&': ! 1536: case 'V': case 'm': case 'o': case '<': case '>': ! 1537: case 'E': case 'F': case 'G': case 'H': case 'X': ! 1538: case 's': case 'i': case 'n': ! 1539: case 'I': case 'J': case 'K': case 'L': case 'M': ! 1540: case 'N': case 'O': case 'P': case ',': ! 1541: #ifdef EXTRA_CONSTRAINT ! 1542: case 'Q': case 'R': case 'S': case 'T': case 'U': ! 1543: #endif ! 1544: break; ! 1545: ! 1546: case '0': case '1': case '2': case '3': case '4': ! 1547: case 'p': case 'g': case 'r': ! 1548: default: ! 1549: allows_reg = 1; ! 1550: break; 1.1 root 1551: } 1552: 1.1.1.8 ! root 1553: if (! allows_reg) ! 1554: mark_addressable (TREE_VALUE (tail)); ! 1555: 1.1 root 1556: XVECEXP (body, 3, i) /* argvec */ 1.1.1.4 root 1557: = expand_expr (TREE_VALUE (tail), NULL_RTX, VOIDmode, 0); 1.1.1.8 ! root 1558: if (CONSTANT_P (XVECEXP (body, 3, i)) ! 1559: && ! general_operand (XVECEXP (body, 3, i), ! 1560: TYPE_MODE (TREE_TYPE (TREE_VALUE (tail))))) ! 1561: { ! 1562: if (allows_reg) ! 1563: XVECEXP (body, 3, i) ! 1564: = force_reg (TYPE_MODE (TREE_TYPE (TREE_VALUE (tail))), ! 1565: XVECEXP (body, 3, i)); ! 1566: else ! 1567: XVECEXP (body, 3, i) ! 1568: = force_const_mem (TYPE_MODE (TREE_TYPE (TREE_VALUE (tail))), ! 1569: XVECEXP (body, 3, i)); ! 1570: } ! 1571: ! 1572: if (! allows_reg ! 1573: && (GET_CODE (XVECEXP (body, 3, i)) == REG ! 1574: || GET_CODE (XVECEXP (body, 3, i)) == SUBREG ! 1575: || GET_CODE (XVECEXP (body, 3, i)) == CONCAT)) ! 1576: { ! 1577: tree type = TREE_TYPE (TREE_VALUE (tail)); ! 1578: rtx memloc = assign_stack_temp (TYPE_MODE (type), ! 1579: int_size_in_bytes (type), 1); ! 1580: ! 1581: MEM_IN_STRUCT_P (memloc) = AGGREGATE_TYPE_P (type); ! 1582: emit_move_insn (memloc, XVECEXP (body, 3, i)); ! 1583: XVECEXP (body, 3, i) = memloc; ! 1584: } ! 1585: 1.1 root 1586: XVECEXP (body, 4, i) /* constraints */ 1587: = gen_rtx (ASM_INPUT, TYPE_MODE (TREE_TYPE (TREE_VALUE (tail))), 1588: TREE_STRING_POINTER (TREE_PURPOSE (tail))); 1589: i++; 1590: } 1591: 1592: /* Protect all the operands from the queue, 1593: now that they have all been evaluated. */ 1594: 1595: for (i = 0; i < ninputs; i++) 1596: XVECEXP (body, 3, i) = protect_from_queue (XVECEXP (body, 3, i), 0); 1597: 1598: for (i = 0; i < noutputs; i++) 1599: output_rtx[i] = protect_from_queue (output_rtx[i], 1); 1600: 1601: /* Now, for each output, construct an rtx 1602: (set OUTPUT (asm_operands INSN OUTPUTNUMBER OUTPUTCONSTRAINT 1603: ARGVEC CONSTRAINTS)) 1604: If there is more than one, put them inside a PARALLEL. */ 1605: 1606: if (noutputs == 1 && nclobbers == 0) 1607: { 1608: XSTR (body, 1) = TREE_STRING_POINTER (TREE_PURPOSE (outputs)); 1609: insn = emit_insn (gen_rtx (SET, VOIDmode, output_rtx[0], body)); 1610: } 1611: else if (noutputs == 0 && nclobbers == 0) 1612: { 1613: /* No output operands: put in a raw ASM_OPERANDS rtx. */ 1614: insn = emit_insn (body); 1615: } 1616: else 1617: { 1618: rtx obody = body; 1619: int num = noutputs; 1620: if (num == 0) num = 1; 1621: body = gen_rtx (PARALLEL, VOIDmode, rtvec_alloc (num + nclobbers)); 1622: 1623: /* For each output operand, store a SET. */ 1624: 1625: for (i = 0, tail = outputs; tail; tail = TREE_CHAIN (tail), i++) 1626: { 1627: XVECEXP (body, 0, i) 1628: = gen_rtx (SET, VOIDmode, 1629: output_rtx[i], 1630: gen_rtx (ASM_OPERANDS, VOIDmode, 1631: TREE_STRING_POINTER (string), 1632: TREE_STRING_POINTER (TREE_PURPOSE (tail)), 1633: i, argvec, constraints, 1634: filename, line)); 1635: MEM_VOLATILE_P (SET_SRC (XVECEXP (body, 0, i))) = vol; 1636: } 1637: 1638: /* If there are no outputs (but there are some clobbers) 1639: store the bare ASM_OPERANDS into the PARALLEL. */ 1640: 1641: if (i == 0) 1642: XVECEXP (body, 0, i++) = obody; 1643: 1644: /* Store (clobber REG) for each clobbered register specified. */ 1645: 1.1.1.3 root 1646: for (tail = clobbers; tail; tail = TREE_CHAIN (tail)) 1.1 root 1647: { 1648: char *regname = TREE_STRING_POINTER (TREE_VALUE (tail)); 1.1.1.2 root 1649: int j = decode_reg_name (regname); 1.1 root 1650: 1.1.1.2 root 1651: if (j < 0) 1.1 root 1652: { 1.1.1.4 root 1653: if (j == -3) /* `cc', which is not a register */ 1.1.1.3 root 1654: continue; 1655: 1.1.1.4 root 1656: if (j == -4) /* `memory', don't cache memory across asm */ 1657: { 1.1.1.5 root 1658: XVECEXP (body, 0, i++) 1659: = gen_rtx (CLOBBER, VOIDmode, 1.1.1.7 root 1660: gen_rtx (MEM, BLKmode, 1.1.1.5 root 1661: gen_rtx (SCRATCH, VOIDmode, 0))); 1.1.1.4 root 1662: continue; 1663: } 1664: 1.1.1.7 root 1665: /* Ignore unknown register, error already signalled. */ 1.1.1.8 ! root 1666: continue; 1.1 root 1667: } 1668: 1669: /* Use QImode since that's guaranteed to clobber just one reg. */ 1.1.1.3 root 1670: XVECEXP (body, 0, i++) 1.1 root 1671: = gen_rtx (CLOBBER, VOIDmode, gen_rtx (REG, QImode, j)); 1672: } 1673: 1674: insn = emit_insn (body); 1675: } 1676: 1677: free_temp_slots (); 1678: } 1679: 1680: /* Generate RTL to evaluate the expression EXP 1681: and remember it in case this is the VALUE in a ({... VALUE; }) constr. */ 1682: 1683: void 1684: expand_expr_stmt (exp) 1685: tree exp; 1686: { 1.1.1.6 root 1687: if (output_bytecode) 1688: { 1689: int org_stack_depth = stack_depth; 1690: 1691: bc_expand_expr (exp); 1692: 1693: /* Restore stack depth */ 1694: if (stack_depth < org_stack_depth) 1695: abort (); 1696: 1697: bc_emit_instruction (drop); 1698: 1699: last_expr_type = TREE_TYPE (exp); 1700: return; 1701: } 1702: 1.1 root 1703: /* If -W, warn about statements with no side effects, 1704: except for an explicit cast to void (e.g. for assert()), and 1705: except inside a ({...}) where they may be useful. */ 1706: if (expr_stmts_for_value == 0 && exp != error_mark_node) 1707: { 1708: if (! TREE_SIDE_EFFECTS (exp) && (extra_warnings || warn_unused) 1709: && !(TREE_CODE (exp) == CONVERT_EXPR 1710: && TREE_TYPE (exp) == void_type_node)) 1711: warning_with_file_and_line (emit_filename, emit_lineno, 1712: "statement with no effect"); 1713: else if (warn_unused) 1714: warn_if_unused_value (exp); 1715: } 1.1.1.8 ! root 1716: ! 1717: /* If EXP is of function type and we are expanding statements for ! 1718: value, convert it to pointer-to-function. */ ! 1719: if (expr_stmts_for_value && TREE_CODE (TREE_TYPE (exp)) == FUNCTION_TYPE) ! 1720: exp = build1 (ADDR_EXPR, build_pointer_type (TREE_TYPE (exp)), exp); ! 1721: 1.1 root 1722: last_expr_type = TREE_TYPE (exp); 1723: if (! flag_syntax_only) 1.1.1.4 root 1724: last_expr_value = expand_expr (exp, 1725: (expr_stmts_for_value 1726: ? NULL_RTX : const0_rtx), 1.1 root 1727: VOIDmode, 0); 1728: 1729: /* If all we do is reference a volatile value in memory, 1730: copy it to a register to be sure it is actually touched. */ 1731: if (last_expr_value != 0 && GET_CODE (last_expr_value) == MEM 1732: && TREE_THIS_VOLATILE (exp)) 1733: { 1.1.1.5 root 1734: if (TYPE_MODE (TREE_TYPE (exp)) == VOIDmode) 1735: ; 1736: else if (TYPE_MODE (TREE_TYPE (exp)) != BLKmode) 1.1 root 1737: copy_to_reg (last_expr_value); 1738: else 1.1.1.3 root 1739: { 1740: rtx lab = gen_label_rtx (); 1741: 1742: /* Compare the value with itself to reference it. */ 1743: emit_cmp_insn (last_expr_value, last_expr_value, EQ, 1744: expand_expr (TYPE_SIZE (last_expr_type), 1.1.1.4 root 1745: NULL_RTX, VOIDmode, 0), 1.1.1.3 root 1746: BLKmode, 0, 1747: TYPE_ALIGN (last_expr_type) / BITS_PER_UNIT); 1748: emit_jump_insn ((*bcc_gen_fctn[(int) EQ]) (lab)); 1749: emit_label (lab); 1750: } 1.1 root 1751: } 1752: 1753: /* If this expression is part of a ({...}) and is in memory, we may have 1754: to preserve temporaries. */ 1755: preserve_temp_slots (last_expr_value); 1756: 1757: /* Free any temporaries used to evaluate this expression. Any temporary 1758: used as a result of this expression will already have been preserved 1759: above. */ 1760: free_temp_slots (); 1761: 1762: emit_queue (); 1763: } 1764: 1765: /* Warn if EXP contains any computations whose results are not used. 1766: Return 1 if a warning is printed; 0 otherwise. */ 1767: 1.1.1.8 ! root 1768: int 1.1 root 1769: warn_if_unused_value (exp) 1770: tree exp; 1771: { 1772: if (TREE_USED (exp)) 1773: return 0; 1774: 1775: switch (TREE_CODE (exp)) 1776: { 1777: case PREINCREMENT_EXPR: 1778: case POSTINCREMENT_EXPR: 1779: case PREDECREMENT_EXPR: 1780: case POSTDECREMENT_EXPR: 1781: case MODIFY_EXPR: 1782: case INIT_EXPR: 1783: case TARGET_EXPR: 1784: case CALL_EXPR: 1785: case METHOD_CALL_EXPR: 1786: case RTL_EXPR: 1787: case WITH_CLEANUP_EXPR: 1788: case EXIT_EXPR: 1789: /* We don't warn about COND_EXPR because it may be a useful 1790: construct if either arm contains a side effect. */ 1791: case COND_EXPR: 1792: return 0; 1793: 1794: case BIND_EXPR: 1795: /* For a binding, warn if no side effect within it. */ 1796: return warn_if_unused_value (TREE_OPERAND (exp, 1)); 1797: 1.1.1.8 ! root 1798: case SAVE_EXPR: ! 1799: return warn_if_unused_value (TREE_OPERAND (exp, 1)); ! 1800: 1.1 root 1801: case TRUTH_ORIF_EXPR: 1802: case TRUTH_ANDIF_EXPR: 1803: /* In && or ||, warn if 2nd operand has no side effect. */ 1804: return warn_if_unused_value (TREE_OPERAND (exp, 1)); 1805: 1806: case COMPOUND_EXPR: 1.1.1.7 root 1807: if (TREE_NO_UNUSED_WARNING (exp)) 1808: return 0; 1.1 root 1809: if (warn_if_unused_value (TREE_OPERAND (exp, 0))) 1810: return 1; 1.1.1.3 root 1811: /* Let people do `(foo (), 0)' without a warning. */ 1812: if (TREE_CONSTANT (TREE_OPERAND (exp, 1))) 1813: return 0; 1.1 root 1814: return warn_if_unused_value (TREE_OPERAND (exp, 1)); 1815: 1816: case NOP_EXPR: 1817: case CONVERT_EXPR: 1.1.1.2 root 1818: case NON_LVALUE_EXPR: 1.1 root 1819: /* Don't warn about values cast to void. */ 1820: if (TREE_TYPE (exp) == void_type_node) 1821: return 0; 1822: /* Don't warn about conversions not explicit in the user's program. */ 1823: if (TREE_NO_UNUSED_WARNING (exp)) 1824: return 0; 1825: /* Assignment to a cast usually results in a cast of a modify. 1.1.1.6 root 1826: Don't complain about that. There can be an arbitrary number of 1827: casts before the modify, so we must loop until we find the first 1828: non-cast expression and then test to see if that is a modify. */ 1829: { 1830: tree tem = TREE_OPERAND (exp, 0); 1831: 1832: while (TREE_CODE (tem) == CONVERT_EXPR || TREE_CODE (tem) == NOP_EXPR) 1833: tem = TREE_OPERAND (tem, 0); 1834: 1.1.1.8 ! root 1835: if (TREE_CODE (tem) == MODIFY_EXPR || TREE_CODE (tem) == INIT_EXPR ! 1836: || TREE_CODE (tem) == CALL_EXPR) 1.1.1.6 root 1837: return 0; 1838: } 1.1.1.8 ! root 1839: goto warn; 1.1 root 1840: 1.1.1.8 ! root 1841: case INDIRECT_REF: ! 1842: /* Don't warn about automatic dereferencing of references, since ! 1843: the user cannot control it. */ ! 1844: if (TREE_CODE (TREE_TYPE (TREE_OPERAND (exp, 0))) == REFERENCE_TYPE) ! 1845: return warn_if_unused_value (TREE_OPERAND (exp, 0)); ! 1846: /* ... fall through ... */ ! 1847: 1.1 root 1848: default: 1.1.1.3 root 1849: /* Referencing a volatile value is a side effect, so don't warn. */ 1850: if ((TREE_CODE_CLASS (TREE_CODE (exp)) == 'd' 1851: || TREE_CODE_CLASS (TREE_CODE (exp)) == 'r') 1852: && TREE_THIS_VOLATILE (exp)) 1853: return 0; 1.1.1.8 ! root 1854: warn: 1.1 root 1855: warning_with_file_and_line (emit_filename, emit_lineno, 1856: "value computed is not used"); 1857: return 1; 1858: } 1859: } 1860: 1861: /* Clear out the memory of the last expression evaluated. */ 1862: 1863: void 1864: clear_last_expr () 1865: { 1866: last_expr_type = 0; 1867: } 1868: 1869: /* Begin a statement which will return a value. 1870: Return the RTL_EXPR for this statement expr. 1871: The caller must save that value and pass it to expand_end_stmt_expr. */ 1872: 1873: tree 1874: expand_start_stmt_expr () 1875: { 1.1.1.6 root 1876: int momentary; 1877: tree t; 1878: 1879: /* When generating bytecode just note down the stack depth */ 1880: if (output_bytecode) 1881: return (build_int_2 (stack_depth, 0)); 1882: 1.1 root 1883: /* Make the RTL_EXPR node temporary, not momentary, 1884: so that rtl_expr_chain doesn't become garbage. */ 1.1.1.6 root 1885: momentary = suspend_momentary (); 1886: t = make_node (RTL_EXPR); 1.1 root 1887: resume_momentary (momentary); 1.1.1.8 ! root 1888: do_pending_stack_adjust (); 1.1.1.6 root 1889: start_sequence_for_rtl_expr (t); 1.1 root 1890: NO_DEFER_POP; 1891: expr_stmts_for_value++; 1892: return t; 1893: } 1894: 1895: /* Restore the previous state at the end of a statement that returns a value. 1896: Returns a tree node representing the statement's value and the 1897: insns to compute the value. 1898: 1899: The nodes of that expression have been freed by now, so we cannot use them. 1900: But we don't want to do that anyway; the expression has already been 1901: evaluated and now we just want to use the value. So generate a RTL_EXPR 1902: with the proper type and RTL value. 1903: 1904: If the last substatement was not an expression, 1905: return something with type `void'. */ 1906: 1907: tree 1908: expand_end_stmt_expr (t) 1909: tree t; 1910: { 1.1.1.6 root 1911: if (output_bytecode) 1912: { 1913: int i; 1914: tree t; 1915: 1916: 1917: /* At this point, all expressions have been evaluated in order. 1918: However, all expression values have been popped when evaluated, 1919: which means we have to recover the last expression value. This is 1920: the last value removed by means of a `drop' instruction. Instead 1921: of adding code to inhibit dropping the last expression value, it 1922: is here recovered by undoing the `drop'. Since `drop' is 1923: equivalent to `adjustackSI [1]', it can be undone with `adjstackSI 1924: [-1]'. */ 1925: 1926: bc_adjust_stack (-1); 1927: 1928: if (!last_expr_type) 1929: last_expr_type = void_type_node; 1930: 1931: t = make_node (RTL_EXPR); 1932: TREE_TYPE (t) = last_expr_type; 1933: RTL_EXPR_RTL (t) = NULL; 1934: RTL_EXPR_SEQUENCE (t) = NULL; 1935: 1936: /* Don't consider deleting this expr or containing exprs at tree level. */ 1937: TREE_THIS_VOLATILE (t) = 1; 1938: 1939: last_expr_type = 0; 1940: return t; 1941: } 1942: 1.1 root 1943: OK_DEFER_POP; 1944: 1945: if (last_expr_type == 0) 1946: { 1947: last_expr_type = void_type_node; 1948: last_expr_value = const0_rtx; 1949: } 1950: else if (last_expr_value == 0) 1951: /* There are some cases where this can happen, such as when the 1952: statement is void type. */ 1953: last_expr_value = const0_rtx; 1954: else if (GET_CODE (last_expr_value) != REG && ! CONSTANT_P (last_expr_value)) 1955: /* Remove any possible QUEUED. */ 1956: last_expr_value = protect_from_queue (last_expr_value, 0); 1957: 1958: emit_queue (); 1959: 1960: TREE_TYPE (t) = last_expr_type; 1961: RTL_EXPR_RTL (t) = last_expr_value; 1962: RTL_EXPR_SEQUENCE (t) = get_insns (); 1963: 1964: rtl_expr_chain = tree_cons (NULL_TREE, t, rtl_expr_chain); 1965: 1966: end_sequence (); 1967: 1968: /* Don't consider deleting this expr or containing exprs at tree level. */ 1969: TREE_SIDE_EFFECTS (t) = 1; 1970: /* Propagate volatility of the actual RTL expr. */ 1971: TREE_THIS_VOLATILE (t) = volatile_refs_p (last_expr_value); 1972: 1973: last_expr_type = 0; 1974: expr_stmts_for_value--; 1975: 1976: return t; 1977: } 1978: 1979: /* Generate RTL for the start of an if-then. COND is the expression 1980: whose truth should be tested. 1981: 1982: If EXITFLAG is nonzero, this conditional is visible to 1983: `exit_something'. */ 1984: 1985: void 1986: expand_start_cond (cond, exitflag) 1987: tree cond; 1988: int exitflag; 1989: { 1990: struct nesting *thiscond = ALLOC_NESTING (); 1991: 1992: /* Make an entry on cond_stack for the cond we are entering. */ 1993: 1994: thiscond->next = cond_stack; 1995: thiscond->all = nesting_stack; 1996: thiscond->depth = ++nesting_depth; 1997: thiscond->data.cond.next_label = gen_label_rtx (); 1998: /* Before we encounter an `else', we don't need a separate exit label 1999: unless there are supposed to be exit statements 2000: to exit this conditional. */ 2001: thiscond->exit_label = exitflag ? gen_label_rtx () : 0; 2002: thiscond->data.cond.endif_label = thiscond->exit_label; 2003: cond_stack = thiscond; 2004: nesting_stack = thiscond; 2005: 1.1.1.6 root 2006: if (output_bytecode) 2007: bc_expand_start_cond (cond, exitflag); 2008: else 2009: do_jump (cond, thiscond->data.cond.next_label, NULL_RTX); 1.1 root 2010: } 2011: 2012: /* Generate RTL between then-clause and the elseif-clause 2013: of an if-then-elseif-.... */ 2014: 2015: void 2016: expand_start_elseif (cond) 2017: tree cond; 2018: { 2019: if (cond_stack->data.cond.endif_label == 0) 2020: cond_stack->data.cond.endif_label = gen_label_rtx (); 2021: emit_jump (cond_stack->data.cond.endif_label); 2022: emit_label (cond_stack->data.cond.next_label); 2023: cond_stack->data.cond.next_label = gen_label_rtx (); 1.1.1.4 root 2024: do_jump (cond, cond_stack->data.cond.next_label, NULL_RTX); 1.1 root 2025: } 2026: 2027: /* Generate RTL between the then-clause and the else-clause 2028: of an if-then-else. */ 2029: 2030: void 2031: expand_start_else () 2032: { 2033: if (cond_stack->data.cond.endif_label == 0) 2034: cond_stack->data.cond.endif_label = gen_label_rtx (); 1.1.1.6 root 2035: 2036: if (output_bytecode) 2037: { 2038: bc_expand_start_else (); 2039: return; 2040: } 2041: 1.1 root 2042: emit_jump (cond_stack->data.cond.endif_label); 2043: emit_label (cond_stack->data.cond.next_label); 2044: cond_stack->data.cond.next_label = 0; /* No more _else or _elseif calls. */ 2045: } 2046: 1.1.1.7 root 2047: /* After calling expand_start_else, turn this "else" into an "else if" 2048: by providing another condition. */ 2049: 2050: void 2051: expand_elseif (cond) 2052: tree cond; 2053: { 2054: cond_stack->data.cond.next_label = gen_label_rtx (); 2055: do_jump (cond, cond_stack->data.cond.next_label, NULL_RTX); 2056: } 2057: 1.1 root 2058: /* Generate RTL for the end of an if-then. 2059: Pop the record for it off of cond_stack. */ 2060: 2061: void 2062: expand_end_cond () 2063: { 2064: struct nesting *thiscond = cond_stack; 2065: 1.1.1.6 root 2066: if (output_bytecode) 2067: bc_expand_end_cond (); 2068: else 2069: { 2070: do_pending_stack_adjust (); 2071: if (thiscond->data.cond.next_label) 2072: emit_label (thiscond->data.cond.next_label); 2073: if (thiscond->data.cond.endif_label) 2074: emit_label (thiscond->data.cond.endif_label); 2075: } 1.1 root 2076: 2077: POPSTACK (cond_stack); 2078: last_expr_type = 0; 2079: } 1.1.1.6 root 2080: 2081: 2082: /* Generate code for the start of an if-then. COND is the expression 2083: whose truth is to be tested; if EXITFLAG is nonzero this conditional 2084: is to be visible to exit_something. It is assumed that the caller 2085: has pushed the previous context on the cond stack. */ 1.1.1.7 root 2086: 2087: static void 1.1.1.6 root 2088: bc_expand_start_cond (cond, exitflag) 2089: tree cond; 2090: int exitflag; 2091: { 2092: struct nesting *thiscond = cond_stack; 2093: 2094: thiscond->data.case_stmt.nominal_type = cond; 1.1.1.7 root 2095: if (! exitflag) 2096: thiscond->exit_label = gen_label_rtx (); 1.1.1.6 root 2097: bc_expand_expr (cond); 2098: bc_emit_bytecode (xjumpifnot); 2099: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (thiscond->exit_label)); 2100: 2101: #ifdef DEBUG_PRINT_CODE 2102: fputc ('\n', stderr); 2103: #endif 2104: } 2105: 2106: /* Generate the label for the end of an if with 2107: no else- clause. */ 1.1.1.7 root 2108: 2109: static void 1.1.1.6 root 2110: bc_expand_end_cond () 2111: { 2112: struct nesting *thiscond = cond_stack; 2113: 2114: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thiscond->exit_label)); 2115: } 2116: 2117: /* Generate code for the start of the else- clause of 2118: an if-then-else. */ 1.1.1.7 root 2119: 2120: static void 1.1.1.6 root 2121: bc_expand_start_else () 2122: { 2123: struct nesting *thiscond = cond_stack; 2124: 2125: thiscond->data.cond.endif_label = thiscond->exit_label; 2126: thiscond->exit_label = gen_label_rtx (); 2127: bc_emit_bytecode (jump); 2128: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (thiscond->exit_label)); 2129: 2130: #ifdef DEBUG_PRINT_CODE 2131: fputc ('\n', stderr); 2132: #endif 2133: 2134: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thiscond->data.cond.endif_label)); 2135: } 1.1 root 2136: 2137: /* Generate RTL for the start of a loop. EXIT_FLAG is nonzero if this 2138: loop should be exited by `exit_something'. This is a loop for which 2139: `expand_continue' will jump to the top of the loop. 2140: 2141: Make an entry on loop_stack to record the labels associated with 2142: this loop. */ 2143: 2144: struct nesting * 2145: expand_start_loop (exit_flag) 2146: int exit_flag; 2147: { 2148: register struct nesting *thisloop = ALLOC_NESTING (); 2149: 2150: /* Make an entry on loop_stack for the loop we are entering. */ 2151: 2152: thisloop->next = loop_stack; 2153: thisloop->all = nesting_stack; 2154: thisloop->depth = ++nesting_depth; 2155: thisloop->data.loop.start_label = gen_label_rtx (); 2156: thisloop->data.loop.end_label = gen_label_rtx (); 1.1.1.7 root 2157: thisloop->data.loop.alt_end_label = 0; 1.1 root 2158: thisloop->data.loop.continue_label = thisloop->data.loop.start_label; 2159: thisloop->exit_label = exit_flag ? thisloop->data.loop.end_label : 0; 2160: loop_stack = thisloop; 2161: nesting_stack = thisloop; 2162: 1.1.1.6 root 2163: if (output_bytecode) 2164: { 2165: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thisloop->data.loop.start_label)); 2166: return thisloop; 2167: } 2168: 1.1 root 2169: do_pending_stack_adjust (); 2170: emit_queue (); 1.1.1.4 root 2171: emit_note (NULL_PTR, NOTE_INSN_LOOP_BEG); 1.1 root 2172: emit_label (thisloop->data.loop.start_label); 2173: 2174: return thisloop; 2175: } 2176: 2177: /* Like expand_start_loop but for a loop where the continuation point 2178: (for expand_continue_loop) will be specified explicitly. */ 2179: 2180: struct nesting * 2181: expand_start_loop_continue_elsewhere (exit_flag) 2182: int exit_flag; 2183: { 2184: struct nesting *thisloop = expand_start_loop (exit_flag); 2185: loop_stack->data.loop.continue_label = gen_label_rtx (); 2186: return thisloop; 2187: } 2188: 2189: /* Specify the continuation point for a loop started with 2190: expand_start_loop_continue_elsewhere. 2191: Use this at the point in the code to which a continue statement 2192: should jump. */ 2193: 2194: void 2195: expand_loop_continue_here () 2196: { 1.1.1.6 root 2197: if (output_bytecode) 2198: { 2199: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (loop_stack->data.loop.continue_label)); 2200: return; 2201: } 1.1 root 2202: do_pending_stack_adjust (); 1.1.1.4 root 2203: emit_note (NULL_PTR, NOTE_INSN_LOOP_CONT); 1.1 root 2204: emit_label (loop_stack->data.loop.continue_label); 2205: } 2206: 1.1.1.6 root 2207: /* End a loop. */ 1.1.1.7 root 2208: 1.1.1.6 root 2209: static void 2210: bc_expand_end_loop () 2211: { 2212: struct nesting *thisloop = loop_stack; 2213: 2214: bc_emit_bytecode (jump); 2215: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (thisloop->data.loop.start_label)); 2216: 2217: #ifdef DEBUG_PRINT_CODE 2218: fputc ('\n', stderr); 2219: #endif 2220: 2221: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thisloop->exit_label)); 2222: POPSTACK (loop_stack); 2223: last_expr_type = 0; 2224: } 2225: 2226: 1.1 root 2227: /* Finish a loop. Generate a jump back to the top and the loop-exit label. 2228: Pop the block off of loop_stack. */ 2229: 2230: void 2231: expand_end_loop () 2232: { 1.1.1.6 root 2233: register rtx insn; 2234: register rtx start_label; 1.1 root 2235: rtx last_test_insn = 0; 2236: int num_insns = 0; 1.1.1.6 root 2237: 2238: if (output_bytecode) 2239: { 2240: bc_expand_end_loop (); 2241: return; 2242: } 2243: 2244: insn = get_last_insn (); 2245: start_label = loop_stack->data.loop.start_label; 1.1 root 2246: 2247: /* Mark the continue-point at the top of the loop if none elsewhere. */ 2248: if (start_label == loop_stack->data.loop.continue_label) 2249: emit_note_before (NOTE_INSN_LOOP_CONT, start_label); 2250: 2251: do_pending_stack_adjust (); 2252: 2253: /* If optimizing, perhaps reorder the loop. If the loop 2254: starts with a conditional exit, roll that to the end 2255: where it will optimize together with the jump back. 2256: 2257: We look for the last conditional branch to the exit that we encounter 2258: before hitting 30 insns or a CALL_INSN. If we see an unconditional 2259: branch to the exit first, use it. 2260: 2261: We must also stop at NOTE_INSN_BLOCK_BEG and NOTE_INSN_BLOCK_END notes 2262: because moving them is not valid. */ 2263: 2264: if (optimize 2265: && 2266: ! (GET_CODE (insn) == JUMP_INSN 2267: && GET_CODE (PATTERN (insn)) == SET 2268: && SET_DEST (PATTERN (insn)) == pc_rtx 2269: && GET_CODE (SET_SRC (PATTERN (insn))) == IF_THEN_ELSE)) 2270: { 2271: /* Scan insns from the top of the loop looking for a qualified 2272: conditional exit. */ 2273: for (insn = NEXT_INSN (loop_stack->data.loop.start_label); insn; 2274: insn = NEXT_INSN (insn)) 2275: { 2276: if (GET_CODE (insn) == CALL_INSN || GET_CODE (insn) == CODE_LABEL) 2277: break; 2278: 2279: if (GET_CODE (insn) == NOTE 2280: && (NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_BEG 2281: || NOTE_LINE_NUMBER (insn) == NOTE_INSN_BLOCK_END)) 2282: break; 2283: 2284: if (GET_CODE (insn) == JUMP_INSN || GET_CODE (insn) == INSN) 2285: num_insns++; 2286: 2287: if (last_test_insn && num_insns > 30) 2288: break; 2289: 2290: if (GET_CODE (insn) == JUMP_INSN && GET_CODE (PATTERN (insn)) == SET 2291: && SET_DEST (PATTERN (insn)) == pc_rtx 2292: && GET_CODE (SET_SRC (PATTERN (insn))) == IF_THEN_ELSE 2293: && ((GET_CODE (XEXP (SET_SRC (PATTERN (insn)), 1)) == LABEL_REF 1.1.1.7 root 2294: && ((XEXP (XEXP (SET_SRC (PATTERN (insn)), 1), 0) 2295: == loop_stack->data.loop.end_label) 2296: || (XEXP (XEXP (SET_SRC (PATTERN (insn)), 1), 0) 2297: == loop_stack->data.loop.alt_end_label))) 1.1 root 2298: || (GET_CODE (XEXP (SET_SRC (PATTERN (insn)), 2)) == LABEL_REF 1.1.1.7 root 2299: && ((XEXP (XEXP (SET_SRC (PATTERN (insn)), 2), 0) 2300: == loop_stack->data.loop.end_label) 2301: || (XEXP (XEXP (SET_SRC (PATTERN (insn)), 2), 0) 2302: == loop_stack->data.loop.alt_end_label))))) 1.1 root 2303: last_test_insn = insn; 2304: 2305: if (last_test_insn == 0 && GET_CODE (insn) == JUMP_INSN 2306: && GET_CODE (PATTERN (insn)) == SET 2307: && SET_DEST (PATTERN (insn)) == pc_rtx 2308: && GET_CODE (SET_SRC (PATTERN (insn))) == LABEL_REF 1.1.1.7 root 2309: && ((XEXP (SET_SRC (PATTERN (insn)), 0) 2310: == loop_stack->data.loop.end_label) 2311: || (XEXP (SET_SRC (PATTERN (insn)), 0) 2312: == loop_stack->data.loop.alt_end_label))) 1.1 root 2313: /* Include BARRIER. */ 2314: last_test_insn = NEXT_INSN (insn); 2315: } 2316: 2317: if (last_test_insn != 0 && last_test_insn != get_last_insn ()) 2318: { 2319: /* We found one. Move everything from there up 2320: to the end of the loop, and add a jump into the loop 2321: to jump to there. */ 2322: register rtx newstart_label = gen_label_rtx (); 2323: register rtx start_move = start_label; 2324: 1.1.1.2 root 2325: /* If the start label is preceded by a NOTE_INSN_LOOP_CONT note, 1.1 root 2326: then we want to move this note also. */ 2327: if (GET_CODE (PREV_INSN (start_move)) == NOTE 2328: && (NOTE_LINE_NUMBER (PREV_INSN (start_move)) 2329: == NOTE_INSN_LOOP_CONT)) 2330: start_move = PREV_INSN (start_move); 2331: 2332: emit_label_after (newstart_label, PREV_INSN (start_move)); 2333: reorder_insns (start_move, last_test_insn, get_last_insn ()); 2334: emit_jump_insn_after (gen_jump (start_label), 2335: PREV_INSN (newstart_label)); 2336: emit_barrier_after (PREV_INSN (newstart_label)); 2337: start_label = newstart_label; 2338: } 2339: } 2340: 2341: emit_jump (start_label); 1.1.1.4 root 2342: emit_note (NULL_PTR, NOTE_INSN_LOOP_END); 1.1 root 2343: emit_label (loop_stack->data.loop.end_label); 2344: 2345: POPSTACK (loop_stack); 2346: 2347: last_expr_type = 0; 2348: } 2349: 2350: /* Generate a jump to the current loop's continue-point. 2351: This is usually the top of the loop, but may be specified 2352: explicitly elsewhere. If not currently inside a loop, 2353: return 0 and do nothing; caller will print an error message. */ 2354: 2355: int 2356: expand_continue_loop (whichloop) 2357: struct nesting *whichloop; 2358: { 2359: last_expr_type = 0; 2360: if (whichloop == 0) 2361: whichloop = loop_stack; 2362: if (whichloop == 0) 2363: return 0; 1.1.1.4 root 2364: expand_goto_internal (NULL_TREE, whichloop->data.loop.continue_label, 2365: NULL_RTX); 1.1 root 2366: return 1; 2367: } 2368: 2369: /* Generate a jump to exit the current loop. If not currently inside a loop, 2370: return 0 and do nothing; caller will print an error message. */ 2371: 2372: int 2373: expand_exit_loop (whichloop) 2374: struct nesting *whichloop; 2375: { 2376: last_expr_type = 0; 2377: if (whichloop == 0) 2378: whichloop = loop_stack; 2379: if (whichloop == 0) 2380: return 0; 1.1.1.4 root 2381: expand_goto_internal (NULL_TREE, whichloop->data.loop.end_label, NULL_RTX); 1.1 root 2382: return 1; 2383: } 2384: 2385: /* Generate a conditional jump to exit the current loop if COND 2386: evaluates to zero. If not currently inside a loop, 2387: return 0 and do nothing; caller will print an error message. */ 2388: 2389: int 2390: expand_exit_loop_if_false (whichloop, cond) 2391: struct nesting *whichloop; 2392: tree cond; 2393: { 2394: last_expr_type = 0; 2395: if (whichloop == 0) 2396: whichloop = loop_stack; 2397: if (whichloop == 0) 2398: return 0; 1.1.1.6 root 2399: if (output_bytecode) 2400: { 2401: bc_expand_expr (cond); 2402: bc_expand_goto_internal (xjumpifnot, 2403: BYTECODE_BC_LABEL (whichloop->exit_label), 1.1.1.7 root 2404: NULL_TREE); 1.1.1.6 root 2405: } 2406: else 1.1.1.7 root 2407: { 2408: /* In order to handle fixups, we actually create a conditional jump 2409: around a unconditional branch to exit the loop. If fixups are 2410: necessary, they go before the unconditional branch. */ 2411: 2412: rtx label = gen_label_rtx (); 2413: rtx last_insn; 2414: 2415: do_jump (cond, NULL_RTX, label); 2416: last_insn = get_last_insn (); 2417: if (GET_CODE (last_insn) == CODE_LABEL) 2418: whichloop->data.loop.alt_end_label = last_insn; 2419: expand_goto_internal (NULL_TREE, whichloop->data.loop.end_label, 2420: NULL_RTX); 2421: emit_label (label); 2422: } 1.1.1.6 root 2423: 1.1 root 2424: return 1; 2425: } 2426: 2427: /* Return non-zero if we should preserve sub-expressions as separate 2428: pseudos. We never do so if we aren't optimizing. We always do so 2429: if -fexpensive-optimizations. 2430: 2431: Otherwise, we only do so if we are in the "early" part of a loop. I.e., 2432: the loop may still be a small one. */ 2433: 2434: int 2435: preserve_subexpressions_p () 2436: { 2437: rtx insn; 2438: 2439: if (flag_expensive_optimizations) 2440: return 1; 2441: 2442: if (optimize == 0 || loop_stack == 0) 2443: return 0; 2444: 2445: insn = get_last_insn_anywhere (); 2446: 2447: return (insn 2448: && (INSN_UID (insn) - INSN_UID (loop_stack->data.loop.start_label) 2449: < n_non_fixed_regs * 3)); 2450: 2451: } 2452: 2453: /* Generate a jump to exit the current loop, conditional, binding contour 2454: or case statement. Not all such constructs are visible to this function, 2455: only those started with EXIT_FLAG nonzero. Individual languages use 2456: the EXIT_FLAG parameter to control which kinds of constructs you can 2457: exit this way. 2458: 2459: If not currently inside anything that can be exited, 2460: return 0 and do nothing; caller will print an error message. */ 2461: 2462: int 2463: expand_exit_something () 2464: { 2465: struct nesting *n; 2466: last_expr_type = 0; 2467: for (n = nesting_stack; n; n = n->all) 2468: if (n->exit_label != 0) 2469: { 1.1.1.4 root 2470: expand_goto_internal (NULL_TREE, n->exit_label, NULL_RTX); 1.1 root 2471: return 1; 2472: } 2473: 2474: return 0; 2475: } 2476: 2477: /* Generate RTL to return from the current function, with no value. 2478: (That is, we do not do anything about returning any value.) */ 2479: 2480: void 2481: expand_null_return () 2482: { 2483: struct nesting *block = block_stack; 2484: rtx last_insn = 0; 2485: 1.1.1.6 root 2486: if (output_bytecode) 2487: { 2488: bc_emit_instruction (ret); 2489: return; 2490: } 2491: 1.1 root 2492: /* Does any pending block have cleanups? */ 2493: 2494: while (block && block->data.block.cleanups == 0) 2495: block = block->next; 2496: 2497: /* If yes, use a goto to return, since that runs cleanups. */ 2498: 2499: expand_null_return_1 (last_insn, block != 0); 2500: } 2501: 2502: /* Generate RTL to return from the current function, with value VAL. */ 2503: 1.1.1.8 ! root 2504: static void 1.1 root 2505: expand_value_return (val) 2506: rtx val; 2507: { 2508: struct nesting *block = block_stack; 2509: rtx last_insn = get_last_insn (); 2510: rtx return_reg = DECL_RTL (DECL_RESULT (current_function_decl)); 2511: 2512: /* Copy the value to the return location 2513: unless it's already there. */ 2514: 2515: if (return_reg != val) 1.1.1.4 root 2516: { 2517: #ifdef PROMOTE_FUNCTION_RETURN 2518: tree type = TREE_TYPE (DECL_RESULT (current_function_decl)); 2519: int unsignedp = TREE_UNSIGNED (type); 1.1.1.7 root 2520: enum machine_mode mode 2521: = promote_mode (type, DECL_MODE (DECL_RESULT (current_function_decl)), 2522: &unsignedp, 1); 1.1.1.4 root 2523: 2524: if (GET_MODE (val) != VOIDmode && GET_MODE (val) != mode) 1.1.1.5 root 2525: convert_move (return_reg, val, unsignedp); 1.1.1.4 root 2526: else 2527: #endif 2528: emit_move_insn (return_reg, val); 2529: } 1.1 root 2530: if (GET_CODE (return_reg) == REG 2531: && REGNO (return_reg) < FIRST_PSEUDO_REGISTER) 2532: emit_insn (gen_rtx (USE, VOIDmode, return_reg)); 2533: 2534: /* Does any pending block have cleanups? */ 2535: 2536: while (block && block->data.block.cleanups == 0) 2537: block = block->next; 2538: 2539: /* If yes, use a goto to return, since that runs cleanups. 2540: Use LAST_INSN to put cleanups *before* the move insn emitted above. */ 2541: 2542: expand_null_return_1 (last_insn, block != 0); 2543: } 2544: 2545: /* Output a return with no value. If LAST_INSN is nonzero, 2546: pretend that the return takes place after LAST_INSN. 2547: If USE_GOTO is nonzero then don't use a return instruction; 2548: go to the return label instead. This causes any cleanups 2549: of pending blocks to be executed normally. */ 2550: 2551: static void 2552: expand_null_return_1 (last_insn, use_goto) 2553: rtx last_insn; 2554: int use_goto; 2555: { 2556: rtx end_label = cleanup_label ? cleanup_label : return_label; 2557: 2558: clear_pending_stack_adjust (); 2559: do_pending_stack_adjust (); 2560: last_expr_type = 0; 2561: 2562: /* PCC-struct return always uses an epilogue. */ 2563: if (current_function_returns_pcc_struct || use_goto) 2564: { 2565: if (end_label == 0) 2566: end_label = return_label = gen_label_rtx (); 1.1.1.4 root 2567: expand_goto_internal (NULL_TREE, end_label, last_insn); 1.1 root 2568: return; 2569: } 2570: 2571: /* Otherwise output a simple return-insn if one is available, 2572: unless it won't do the job. */ 2573: #ifdef HAVE_return 2574: if (HAVE_return && use_goto == 0 && cleanup_label == 0) 2575: { 2576: emit_jump_insn (gen_return ()); 2577: emit_barrier (); 2578: return; 2579: } 2580: #endif 2581: 2582: /* Otherwise jump to the epilogue. */ 1.1.1.4 root 2583: expand_goto_internal (NULL_TREE, end_label, last_insn); 1.1 root 2584: } 2585: 2586: /* Generate RTL to evaluate the expression RETVAL and return it 2587: from the current function. */ 2588: 2589: void 2590: expand_return (retval) 2591: tree retval; 2592: { 2593: /* If there are any cleanups to be performed, then they will 2594: be inserted following LAST_INSN. It is desirable 2595: that the last_insn, for such purposes, should be the 2596: last insn before computing the return value. Otherwise, cleanups 2597: which call functions can clobber the return value. */ 2598: /* ??? rms: I think that is erroneous, because in C++ it would 2599: run destructors on variables that might be used in the subsequent 2600: computation of the return value. */ 2601: rtx last_insn = 0; 2602: register rtx val = 0; 2603: register rtx op0; 2604: tree retval_rhs; 2605: int cleanups; 2606: struct nesting *block; 2607: 1.1.1.6 root 2608: /* Bytecode returns are quite simple, just leave the result on the 2609: arithmetic stack. */ 2610: if (output_bytecode) 2611: { 2612: bc_expand_expr (retval); 2613: bc_emit_instruction (ret); 2614: return; 2615: } 2616: 1.1 root 2617: /* If function wants no value, give it none. */ 2618: if (TREE_CODE (TREE_TYPE (TREE_TYPE (current_function_decl))) == VOID_TYPE) 2619: { 1.1.1.4 root 2620: expand_expr (retval, NULL_RTX, VOIDmode, 0); 2621: emit_queue (); 1.1 root 2622: expand_null_return (); 2623: return; 2624: } 2625: 2626: /* Are any cleanups needed? E.g. C++ destructors to be run? */ 1.1.1.7 root 2627: /* This is not sufficient. We also need to watch for cleanups of the 2628: expression we are about to expand. Unfortunately, we cannot know 2629: if it has cleanups until we expand it, and we want to change how we 2630: expand it depending upon if we need cleanups. We can't win. */ 2631: #if 0 1.1 root 2632: cleanups = any_pending_cleanups (1); 1.1.1.7 root 2633: #else 2634: cleanups = 1; 2635: #endif 1.1 root 2636: 2637: if (TREE_CODE (retval) == RESULT_DECL) 2638: retval_rhs = retval; 2639: else if ((TREE_CODE (retval) == MODIFY_EXPR || TREE_CODE (retval) == INIT_EXPR) 2640: && TREE_CODE (TREE_OPERAND (retval, 0)) == RESULT_DECL) 2641: retval_rhs = TREE_OPERAND (retval, 1); 2642: else if (TREE_TYPE (retval) == void_type_node) 2643: /* Recognize tail-recursive call to void function. */ 2644: retval_rhs = retval; 2645: else 2646: retval_rhs = NULL_TREE; 2647: 2648: /* Only use `last_insn' if there are cleanups which must be run. */ 2649: if (cleanups || cleanup_label != 0) 2650: last_insn = get_last_insn (); 2651: 2652: /* Distribute return down conditional expr if either of the sides 2653: may involve tail recursion (see test below). This enhances the number 2654: of tail recursions we see. Don't do this always since it can produce 2655: sub-optimal code in some cases and we distribute assignments into 2656: conditional expressions when it would help. */ 2657: 2658: if (optimize && retval_rhs != 0 2659: && frame_offset == 0 2660: && TREE_CODE (retval_rhs) == COND_EXPR 2661: && (TREE_CODE (TREE_OPERAND (retval_rhs, 1)) == CALL_EXPR 2662: || TREE_CODE (TREE_OPERAND (retval_rhs, 2)) == CALL_EXPR)) 2663: { 2664: rtx label = gen_label_rtx (); 1.1.1.6 root 2665: tree expr; 2666: 1.1.1.4 root 2667: do_jump (TREE_OPERAND (retval_rhs, 0), label, NULL_RTX); 1.1.1.6 root 2668: expr = build (MODIFY_EXPR, TREE_TYPE (current_function_decl), 2669: DECL_RESULT (current_function_decl), 2670: TREE_OPERAND (retval_rhs, 1)); 2671: TREE_SIDE_EFFECTS (expr) = 1; 2672: expand_return (expr); 1.1 root 2673: emit_label (label); 1.1.1.6 root 2674: 2675: expr = build (MODIFY_EXPR, TREE_TYPE (current_function_decl), 2676: DECL_RESULT (current_function_decl), 2677: TREE_OPERAND (retval_rhs, 2)); 2678: TREE_SIDE_EFFECTS (expr) = 1; 2679: expand_return (expr); 1.1 root 2680: return; 2681: } 2682: 2683: /* For tail-recursive call to current function, 2684: just jump back to the beginning. 2685: It's unsafe if any auto variable in this function 2686: has its address taken; for simplicity, 2687: require stack frame to be empty. */ 2688: if (optimize && retval_rhs != 0 2689: && frame_offset == 0 2690: && TREE_CODE (retval_rhs) == CALL_EXPR 2691: && TREE_CODE (TREE_OPERAND (retval_rhs, 0)) == ADDR_EXPR 2692: && TREE_OPERAND (TREE_OPERAND (retval_rhs, 0), 0) == current_function_decl 2693: /* Finish checking validity, and if valid emit code 2694: to set the argument variables for the new call. */ 2695: && tail_recursion_args (TREE_OPERAND (retval_rhs, 1), 2696: DECL_ARGUMENTS (current_function_decl))) 2697: { 2698: if (tail_recursion_label == 0) 2699: { 2700: tail_recursion_label = gen_label_rtx (); 2701: emit_label_after (tail_recursion_label, 2702: tail_recursion_reentry); 2703: } 1.1.1.4 root 2704: emit_queue (); 2705: expand_goto_internal (NULL_TREE, tail_recursion_label, last_insn); 1.1 root 2706: emit_barrier (); 2707: return; 2708: } 2709: #ifdef HAVE_return 2710: /* This optimization is safe if there are local cleanups 2711: because expand_null_return takes care of them. 2712: ??? I think it should also be safe when there is a cleanup label, 2713: because expand_null_return takes care of them, too. 2714: Any reason why not? */ 2715: if (HAVE_return && cleanup_label == 0 1.1.1.6 root 2716: && ! current_function_returns_pcc_struct 2717: && BRANCH_COST <= 1) 1.1 root 2718: { 2719: /* If this is return x == y; then generate 2720: if (x == y) return 1; else return 0; 1.1.1.6 root 2721: if we can do it with explicit return insns and 2722: branches are cheap. */ 1.1 root 2723: if (retval_rhs) 2724: switch (TREE_CODE (retval_rhs)) 2725: { 2726: case EQ_EXPR: 2727: case NE_EXPR: 2728: case GT_EXPR: 2729: case GE_EXPR: 2730: case LT_EXPR: 2731: case LE_EXPR: 2732: case TRUTH_ANDIF_EXPR: 2733: case TRUTH_ORIF_EXPR: 2734: case TRUTH_AND_EXPR: 2735: case TRUTH_OR_EXPR: 2736: case TRUTH_NOT_EXPR: 1.1.1.5 root 2737: case TRUTH_XOR_EXPR: 1.1 root 2738: op0 = gen_label_rtx (); 2739: jumpifnot (retval_rhs, op0); 2740: expand_value_return (const1_rtx); 2741: emit_label (op0); 2742: expand_value_return (const0_rtx); 2743: return; 2744: } 2745: } 2746: #endif /* HAVE_return */ 2747: 1.1.1.8 ! root 2748: /* If the result is an aggregate that is being returned in one (or more) ! 2749: registers, load the registers here. The compiler currently can't handle ! 2750: copying a BLKmode value into registers. We could put this code in a ! 2751: more general area (for use by everyone instead of just function ! 2752: call/return), but until this feature is generally usable it is kept here ! 2753: (and in expand_call). The value must go into a pseudo in case there ! 2754: are cleanups that will clobber the real return register. */ ! 2755: ! 2756: if (retval_rhs != 0 ! 2757: && TYPE_MODE (TREE_TYPE (retval_rhs)) == BLKmode ! 2758: && GET_CODE (DECL_RTL (DECL_RESULT (current_function_decl))) == REG) ! 2759: { ! 2760: int i, bitpos, xbitpos; ! 2761: int big_endian_correction = 0; ! 2762: int bytes = int_size_in_bytes (TREE_TYPE (retval_rhs)); ! 2763: int n_regs = (bytes + UNITS_PER_WORD - 1) / UNITS_PER_WORD; ! 2764: int bitsize = MIN (TYPE_ALIGN (TREE_TYPE (retval_rhs)),BITS_PER_WORD); ! 2765: rtx *result_pseudos = (rtx *) alloca (sizeof (rtx) * n_regs); ! 2766: rtx result_reg, src, dst; ! 2767: rtx result_val = expand_expr (retval_rhs, NULL_RTX, VOIDmode, 0); ! 2768: enum machine_mode tmpmode, result_reg_mode; ! 2769: ! 2770: /* Structures whose size is not a multiple of a word are aligned ! 2771: to the least significant byte (to the right). On a BYTES_BIG_ENDIAN ! 2772: machine, this means we must skip the empty high order bytes when ! 2773: calculating the bit offset. */ ! 2774: if (BYTES_BIG_ENDIAN && bytes % UNITS_PER_WORD) ! 2775: big_endian_correction = (BITS_PER_WORD - ((bytes % UNITS_PER_WORD) ! 2776: * BITS_PER_UNIT)); ! 2777: ! 2778: /* Copy the structure BITSIZE bits at a time. */ ! 2779: for (bitpos = 0, xbitpos = big_endian_correction; ! 2780: bitpos < bytes * BITS_PER_UNIT; ! 2781: bitpos += bitsize, xbitpos += bitsize) ! 2782: { ! 2783: /* We need a new destination pseudo each time xbitpos is ! 2784: on a word boundary and when xbitpos == big_endian_correction ! 2785: (the first time through). */ ! 2786: if (xbitpos % BITS_PER_WORD == 0 ! 2787: || xbitpos == big_endian_correction) ! 2788: { ! 2789: /* Generate an appropriate register. */ ! 2790: dst = gen_reg_rtx (word_mode); ! 2791: result_pseudos[xbitpos / BITS_PER_WORD] = dst; ! 2792: ! 2793: /* Clobber the destination before we move anything into it. */ ! 2794: emit_insn (gen_rtx (CLOBBER, VOIDmode, dst)); ! 2795: } ! 2796: ! 2797: /* We need a new source operand each time bitpos is on a word ! 2798: boundary. */ ! 2799: if (bitpos % BITS_PER_WORD == 0) ! 2800: src = operand_subword_force (result_val, ! 2801: bitpos / BITS_PER_WORD, ! 2802: BLKmode); ! 2803: ! 2804: /* Use bitpos for the source extraction (left justified) and ! 2805: xbitpos for the destination store (right justified). */ ! 2806: store_bit_field (dst, bitsize, xbitpos % BITS_PER_WORD, word_mode, ! 2807: extract_bit_field (src, bitsize, ! 2808: bitpos % BITS_PER_WORD, 1, ! 2809: NULL_RTX, word_mode, ! 2810: word_mode, ! 2811: bitsize / BITS_PER_UNIT, ! 2812: BITS_PER_WORD), ! 2813: bitsize / BITS_PER_UNIT, BITS_PER_WORD); ! 2814: } ! 2815: ! 2816: /* Find the smallest integer mode large enough to hold the ! 2817: entire structure and use that mode instead of BLKmode ! 2818: on the USE insn for the return register. */ ! 2819: bytes = int_size_in_bytes (TREE_TYPE (retval_rhs)); ! 2820: for (tmpmode = GET_CLASS_NARROWEST_MODE (MODE_INT); ! 2821: tmpmode != MAX_MACHINE_MODE; ! 2822: tmpmode = GET_MODE_WIDER_MODE (tmpmode)) ! 2823: { ! 2824: /* Have we found a large enough mode? */ ! 2825: if (GET_MODE_SIZE (tmpmode) >= bytes) ! 2826: break; ! 2827: } ! 2828: ! 2829: /* No suitable mode found. */ ! 2830: if (tmpmode == MAX_MACHINE_MODE) ! 2831: abort (); ! 2832: ! 2833: PUT_MODE (DECL_RTL (DECL_RESULT (current_function_decl)), tmpmode); ! 2834: ! 2835: if (GET_MODE_SIZE (tmpmode) < GET_MODE_SIZE (word_mode)) ! 2836: result_reg_mode = word_mode; ! 2837: else ! 2838: result_reg_mode = tmpmode; ! 2839: result_reg = gen_reg_rtx (result_reg_mode); ! 2840: ! 2841: /* Now that the value is in pseudos, copy it to the result reg(s). */ ! 2842: emit_queue (); ! 2843: free_temp_slots (); ! 2844: for (i = 0; i < n_regs; i++) ! 2845: emit_move_insn (operand_subword (result_reg, i, 0, result_reg_mode), ! 2846: result_pseudos[i]); ! 2847: ! 2848: if (tmpmode != result_reg_mode) ! 2849: result_reg = gen_lowpart (tmpmode, result_reg); ! 2850: ! 2851: expand_value_return (result_reg); ! 2852: } ! 2853: else if (cleanups 1.1 root 2854: && retval_rhs != 0 2855: && TREE_TYPE (retval_rhs) != void_type_node 2856: && GET_CODE (DECL_RTL (DECL_RESULT (current_function_decl))) == REG) 2857: { 2858: /* Calculate the return value into a pseudo reg. */ 1.1.1.4 root 2859: val = expand_expr (retval_rhs, NULL_RTX, VOIDmode, 0); 1.1 root 2860: emit_queue (); 2861: /* All temporaries have now been used. */ 2862: free_temp_slots (); 2863: /* Return the calculated value, doing cleanups first. */ 2864: expand_value_return (val); 2865: } 2866: else 2867: { 2868: /* No cleanups or no hard reg used; 2869: calculate value into hard return reg. */ 1.1.1.6 root 2870: expand_expr (retval, const0_rtx, VOIDmode, 0); 1.1 root 2871: emit_queue (); 2872: free_temp_slots (); 2873: expand_value_return (DECL_RTL (DECL_RESULT (current_function_decl))); 2874: } 2875: } 2876: 2877: /* Return 1 if the end of the generated RTX is not a barrier. 2878: This means code already compiled can drop through. */ 2879: 2880: int 2881: drop_through_at_end_p () 2882: { 2883: rtx insn = get_last_insn (); 2884: while (insn && GET_CODE (insn) == NOTE) 2885: insn = PREV_INSN (insn); 2886: return insn && GET_CODE (insn) != BARRIER; 2887: } 2888: 2889: /* Emit code to alter this function's formal parms for a tail-recursive call. 2890: ACTUALS is a list of actual parameter expressions (chain of TREE_LISTs). 2891: FORMALS is the chain of decls of formals. 2892: Return 1 if this can be done; 2893: otherwise return 0 and do not emit any code. */ 2894: 2895: static int 2896: tail_recursion_args (actuals, formals) 2897: tree actuals, formals; 2898: { 2899: register tree a = actuals, f = formals; 2900: register int i; 2901: register rtx *argvec; 2902: 2903: /* Check that number and types of actuals are compatible 2904: with the formals. This is not always true in valid C code. 2905: Also check that no formal needs to be addressable 2906: and that all formals are scalars. */ 2907: 2908: /* Also count the args. */ 2909: 2910: for (a = actuals, f = formals, i = 0; a && f; a = TREE_CHAIN (a), f = TREE_CHAIN (f), i++) 2911: { 2912: if (TREE_TYPE (TREE_VALUE (a)) != TREE_TYPE (f)) 2913: return 0; 2914: if (GET_CODE (DECL_RTL (f)) != REG || DECL_MODE (f) == BLKmode) 2915: return 0; 2916: } 2917: if (a != 0 || f != 0) 2918: return 0; 2919: 2920: /* Compute all the actuals. */ 2921: 2922: argvec = (rtx *) alloca (i * sizeof (rtx)); 2923: 2924: for (a = actuals, i = 0; a; a = TREE_CHAIN (a), i++) 1.1.1.4 root 2925: argvec[i] = expand_expr (TREE_VALUE (a), NULL_RTX, VOIDmode, 0); 1.1 root 2926: 2927: /* Find which actual values refer to current values of previous formals. 2928: Copy each of them now, before any formal is changed. */ 2929: 2930: for (a = actuals, i = 0; a; a = TREE_CHAIN (a), i++) 2931: { 2932: int copy = 0; 2933: register int j; 2934: for (f = formals, j = 0; j < i; f = TREE_CHAIN (f), j++) 2935: if (reg_mentioned_p (DECL_RTL (f), argvec[i])) 2936: { copy = 1; break; } 2937: if (copy) 2938: argvec[i] = copy_to_reg (argvec[i]); 2939: } 2940: 2941: /* Store the values of the actuals into the formals. */ 2942: 2943: for (f = formals, a = actuals, i = 0; f; 2944: f = TREE_CHAIN (f), a = TREE_CHAIN (a), i++) 2945: { 1.1.1.4 root 2946: if (GET_MODE (DECL_RTL (f)) == GET_MODE (argvec[i])) 1.1 root 2947: emit_move_insn (DECL_RTL (f), argvec[i]); 2948: else 2949: convert_move (DECL_RTL (f), argvec[i], 2950: TREE_UNSIGNED (TREE_TYPE (TREE_VALUE (a)))); 2951: } 2952: 2953: free_temp_slots (); 2954: return 1; 2955: } 2956: 2957: /* Generate the RTL code for entering a binding contour. 2958: The variables are declared one by one, by calls to `expand_decl'. 2959: 2960: EXIT_FLAG is nonzero if this construct should be visible to 2961: `exit_something'. */ 2962: 2963: void 2964: expand_start_bindings (exit_flag) 2965: int exit_flag; 2966: { 2967: struct nesting *thisblock = ALLOC_NESTING (); 1.1.1.7 root 2968: rtx note = output_bytecode ? 0 : emit_note (NULL_PTR, NOTE_INSN_BLOCK_BEG); 1.1 root 2969: 2970: /* Make an entry on block_stack for the block we are entering. */ 2971: 2972: thisblock->next = block_stack; 2973: thisblock->all = nesting_stack; 2974: thisblock->depth = ++nesting_depth; 2975: thisblock->data.block.stack_level = 0; 2976: thisblock->data.block.cleanups = 0; 2977: thisblock->data.block.function_call_count = 0; 2978: #if 0 2979: if (block_stack) 2980: { 2981: if (block_stack->data.block.cleanups == NULL_TREE 2982: && (block_stack->data.block.outer_cleanups == NULL_TREE 2983: || block_stack->data.block.outer_cleanups == empty_cleanup_list)) 2984: thisblock->data.block.outer_cleanups = empty_cleanup_list; 2985: else 2986: thisblock->data.block.outer_cleanups 2987: = tree_cons (NULL_TREE, block_stack->data.block.cleanups, 2988: block_stack->data.block.outer_cleanups); 2989: } 2990: else 2991: thisblock->data.block.outer_cleanups = 0; 2992: #endif 2993: #if 1 2994: if (block_stack 2995: && !(block_stack->data.block.cleanups == NULL_TREE 2996: && block_stack->data.block.outer_cleanups == NULL_TREE)) 2997: thisblock->data.block.outer_cleanups 2998: = tree_cons (NULL_TREE, block_stack->data.block.cleanups, 2999: block_stack->data.block.outer_cleanups); 3000: else 3001: thisblock->data.block.outer_cleanups = 0; 3002: #endif 3003: thisblock->data.block.label_chain = 0; 3004: thisblock->data.block.innermost_stack_block = stack_block_stack; 3005: thisblock->data.block.first_insn = note; 3006: thisblock->data.block.block_start_count = ++block_start_count; 3007: thisblock->exit_label = exit_flag ? gen_label_rtx () : 0; 3008: block_stack = thisblock; 3009: nesting_stack = thisblock; 3010: 1.1.1.6 root 3011: if (!output_bytecode) 3012: { 3013: /* Make a new level for allocating stack slots. */ 3014: push_temp_slots (); 3015: } 1.1 root 3016: } 3017: 1.1.1.4 root 3018: /* Given a pointer to a BLOCK node, save a pointer to the most recently 3019: generated NOTE_INSN_BLOCK_END in the BLOCK_END_NOTE field of the given 3020: BLOCK node. */ 3021: 3022: void 3023: remember_end_note (block) 3024: register tree block; 3025: { 3026: BLOCK_END_NOTE (block) = last_block_end_note; 3027: last_block_end_note = NULL_RTX; 3028: } 3029: 1.1 root 3030: /* Generate RTL code to terminate a binding contour. 3031: VARS is the chain of VAR_DECL nodes 3032: for the variables bound in this contour. 3033: MARK_ENDS is nonzero if we should put a note at the beginning 3034: and end of this binding contour. 3035: 3036: DONT_JUMP_IN is nonzero if it is not valid to jump into this contour. 3037: (That is true automatically if the contour has a saved stack level.) */ 3038: 3039: void 3040: expand_end_bindings (vars, mark_ends, dont_jump_in) 3041: tree vars; 3042: int mark_ends; 3043: int dont_jump_in; 3044: { 3045: register struct nesting *thisblock = block_stack; 3046: register tree decl; 3047: 1.1.1.6 root 3048: if (output_bytecode) 3049: { 3050: bc_expand_end_bindings (vars, mark_ends, dont_jump_in); 3051: return; 3052: } 3053: 1.1 root 3054: if (warn_unused) 3055: for (decl = vars; decl; decl = TREE_CHAIN (decl)) 1.1.1.4 root 3056: if (! TREE_USED (decl) && TREE_CODE (decl) == VAR_DECL 3057: && ! DECL_IN_SYSTEM_HEADER (decl)) 1.1 root 3058: warning_with_decl (decl, "unused variable `%s'"); 3059: 3060: if (thisblock->exit_label) 3061: { 3062: do_pending_stack_adjust (); 3063: emit_label (thisblock->exit_label); 3064: } 3065: 3066: /* If necessary, make a handler for nonlocal gotos taking 3067: place in the function calls in this block. */ 3068: if (function_call_count != thisblock->data.block.function_call_count 3069: && nonlocal_labels 3070: /* Make handler for outermost block 3071: if there were any nonlocal gotos to this function. */ 3072: && (thisblock->next == 0 ? current_function_has_nonlocal_label 3073: /* Make handler for inner block if it has something 3074: special to do when you jump out of it. */ 3075: : (thisblock->data.block.cleanups != 0 3076: || thisblock->data.block.stack_level != 0))) 3077: { 3078: tree link; 3079: rtx afterward = gen_label_rtx (); 3080: rtx handler_label = gen_label_rtx (); 3081: rtx save_receiver = gen_reg_rtx (Pmode); 1.1.1.6 root 3082: rtx insns; 1.1 root 3083: 3084: /* Don't let jump_optimize delete the handler. */ 3085: LABEL_PRESERVE_P (handler_label) = 1; 3086: 3087: /* Record the handler address in the stack slot for that purpose, 3088: during this block, saving and restoring the outer value. */ 3089: if (thisblock->next != 0) 3090: { 3091: emit_move_insn (nonlocal_goto_handler_slot, save_receiver); 1.1.1.6 root 3092: 3093: start_sequence (); 3094: emit_move_insn (save_receiver, nonlocal_goto_handler_slot); 3095: insns = get_insns (); 3096: end_sequence (); 3097: emit_insns_before (insns, thisblock->data.block.first_insn); 3098: } 3099: 3100: start_sequence (); 3101: emit_move_insn (nonlocal_goto_handler_slot, 3102: gen_rtx (LABEL_REF, Pmode, handler_label)); 3103: insns = get_insns (); 3104: end_sequence (); 3105: emit_insns_before (insns, thisblock->data.block.first_insn); 1.1 root 3106: 3107: /* Jump around the handler; it runs only when specially invoked. */ 3108: emit_jump (afterward); 3109: emit_label (handler_label); 3110: 3111: #ifdef HAVE_nonlocal_goto 3112: if (! HAVE_nonlocal_goto) 3113: #endif 3114: /* First adjust our frame pointer to its actual value. It was 3115: previously set to the start of the virtual area corresponding to 3116: the stacked variables when we branched here and now needs to be 3117: adjusted to the actual hardware fp value. 3118: 3119: Assignments are to virtual registers are converted by 3120: instantiate_virtual_regs into the corresponding assignment 3121: to the underlying register (fp in this case) that makes 3122: the original assignment true. 3123: So the following insn will actually be 3124: decrementing fp by STARTING_FRAME_OFFSET. */ 1.1.1.7 root 3125: emit_move_insn (virtual_stack_vars_rtx, hard_frame_pointer_rtx); 1.1 root 3126: 1.1.1.6 root 3127: #if ARG_POINTER_REGNUM != HARD_FRAME_POINTER_REGNUM 1.1 root 3128: if (fixed_regs[ARG_POINTER_REGNUM]) 3129: { 1.1.1.4 root 3130: #ifdef ELIMINABLE_REGS 3131: /* If the argument pointer can be eliminated in favor of the 3132: frame pointer, we don't need to restore it. We assume here 3133: that if such an elimination is present, it can always be used. 3134: This is the case on all known machines; if we don't make this 3135: assumption, we do unnecessary saving on many machines. */ 3136: static struct elims {int from, to;} elim_regs[] = ELIMINABLE_REGS; 3137: int i; 3138: 3139: for (i = 0; i < sizeof elim_regs / sizeof elim_regs[0]; i++) 3140: if (elim_regs[i].from == ARG_POINTER_REGNUM 1.1.1.6 root 3141: && elim_regs[i].to == HARD_FRAME_POINTER_REGNUM) 1.1.1.4 root 3142: break; 3143: 3144: if (i == sizeof elim_regs / sizeof elim_regs [0]) 3145: #endif 3146: { 3147: /* Now restore our arg pointer from the address at which it 3148: was saved in our stack frame. 3149: If there hasn't be space allocated for it yet, make 3150: some now. */ 3151: if (arg_pointer_save_area == 0) 3152: arg_pointer_save_area 3153: = assign_stack_local (Pmode, GET_MODE_SIZE (Pmode), 0); 3154: emit_move_insn (virtual_incoming_args_rtx, 3155: /* We need a pseudo here, or else 3156: instantiate_virtual_regs_1 complains. */ 3157: copy_to_reg (arg_pointer_save_area)); 3158: } 1.1 root 3159: } 3160: #endif 3161: 3162: /* The handler expects the desired label address in the static chain 3163: register. It tests the address and does an appropriate jump 3164: to whatever label is desired. */ 3165: for (link = nonlocal_labels; link; link = TREE_CHAIN (link)) 3166: /* Skip any labels we shouldn't be able to jump to from here. */ 3167: if (! DECL_TOO_LATE (TREE_VALUE (link))) 3168: { 3169: rtx not_this = gen_label_rtx (); 3170: rtx this = gen_label_rtx (); 3171: do_jump_if_equal (static_chain_rtx, 3172: gen_rtx (LABEL_REF, Pmode, DECL_RTL (TREE_VALUE (link))), 3173: this, 0); 3174: emit_jump (not_this); 3175: emit_label (this); 3176: expand_goto (TREE_VALUE (link)); 3177: emit_label (not_this); 3178: } 3179: /* If label is not recognized, abort. */ 3180: emit_library_call (gen_rtx (SYMBOL_REF, Pmode, "abort"), 0, 3181: VOIDmode, 0); 1.1.1.8 ! root 3182: emit_barrier (); 1.1 root 3183: emit_label (afterward); 3184: } 3185: 3186: /* Don't allow jumping into a block that has cleanups or a stack level. */ 3187: if (dont_jump_in 3188: || thisblock->data.block.stack_level != 0 3189: || thisblock->data.block.cleanups != 0) 3190: { 3191: struct label_chain *chain; 3192: 3193: /* Any labels in this block are no longer valid to go to. 3194: Mark them to cause an error message. */ 3195: for (chain = thisblock->data.block.label_chain; chain; chain = chain->next) 3196: { 3197: DECL_TOO_LATE (chain->label) = 1; 3198: /* If any goto without a fixup came to this label, 3199: that must be an error, because gotos without fixups 3200: come from outside all saved stack-levels and all cleanups. */ 3201: if (TREE_ADDRESSABLE (chain->label)) 3202: error_with_decl (chain->label, 3203: "label `%s' used before containing binding contour"); 3204: } 3205: } 3206: 3207: /* Restore stack level in effect before the block 3208: (only if variable-size objects allocated). */ 3209: /* Perform any cleanups associated with the block. */ 3210: 3211: if (thisblock->data.block.stack_level != 0 3212: || thisblock->data.block.cleanups != 0) 3213: { 1.1.1.7 root 3214: /* Only clean up here if this point can actually be reached. */ 1.1.1.8 ! root 3215: int reachable = GET_CODE (get_last_insn ()) != BARRIER; 1.1 root 3216: 1.1.1.8 ! root 3217: /* Don't let cleanups affect ({...}) constructs. */ ! 3218: int old_expr_stmts_for_value = expr_stmts_for_value; ! 3219: rtx old_last_expr_value = last_expr_value; ! 3220: tree old_last_expr_type = last_expr_type; ! 3221: expr_stmts_for_value = 0; ! 3222: ! 3223: /* Do the cleanups. */ ! 3224: expand_cleanups (thisblock->data.block.cleanups, NULL_TREE, 0, reachable); ! 3225: if (reachable) ! 3226: do_pending_stack_adjust (); 1.1.1.7 root 3227: 1.1.1.8 ! root 3228: expr_stmts_for_value = old_expr_stmts_for_value; ! 3229: last_expr_value = old_last_expr_value; ! 3230: last_expr_type = old_last_expr_type; ! 3231: ! 3232: /* Restore the stack level. */ ! 3233: ! 3234: if (reachable && thisblock->data.block.stack_level != 0) ! 3235: { ! 3236: emit_stack_restore (thisblock->next ? SAVE_BLOCK : SAVE_FUNCTION, ! 3237: thisblock->data.block.stack_level, NULL_RTX); ! 3238: if (nonlocal_goto_handler_slot != 0) ! 3239: emit_stack_save (SAVE_NONLOCAL, &nonlocal_goto_stack_level, ! 3240: NULL_RTX); 1.1 root 3241: } 3242: 3243: /* Any gotos out of this block must also do these things. 1.1.1.3 root 3244: Also report any gotos with fixups that came to labels in this 3245: level. */ 1.1 root 3246: fixup_gotos (thisblock, 3247: thisblock->data.block.stack_level, 3248: thisblock->data.block.cleanups, 3249: thisblock->data.block.first_insn, 3250: dont_jump_in); 3251: } 3252: 1.1.1.4 root 3253: /* Mark the beginning and end of the scope if requested. 3254: We do this now, after running cleanups on the variables 3255: just going out of scope, so they are in scope for their cleanups. */ 3256: 3257: if (mark_ends) 3258: last_block_end_note = emit_note (NULL_PTR, NOTE_INSN_BLOCK_END); 3259: else 3260: /* Get rid of the beginning-mark if we don't make an end-mark. */ 3261: NOTE_LINE_NUMBER (thisblock->data.block.first_insn) = NOTE_INSN_DELETED; 3262: 1.1 root 3263: /* If doing stupid register allocation, make sure lives of all 3264: register variables declared here extend thru end of scope. */ 3265: 3266: if (obey_regdecls) 3267: for (decl = vars; decl; decl = TREE_CHAIN (decl)) 3268: { 3269: rtx rtl = DECL_RTL (decl); 3270: if (TREE_CODE (decl) == VAR_DECL && rtl != 0) 3271: use_variable (rtl); 3272: } 3273: 3274: /* Restore block_stack level for containing block. */ 3275: 3276: stack_block_stack = thisblock->data.block.innermost_stack_block; 3277: POPSTACK (block_stack); 3278: 3279: /* Pop the stack slot nesting and free any slots at this level. */ 3280: pop_temp_slots (); 3281: } 1.1.1.6 root 3282: 3283: 3284: /* End a binding contour. 3285: VARS is the chain of VAR_DECL nodes for the variables bound 3286: in this contour. MARK_ENDS is nonzer if we should put a note 3287: at the beginning and end of this binding contour. 3288: DONT_JUMP_IN is nonzero if it is not valid to jump into this 3289: contour. */ 3290: 1.1.1.7 root 3291: static void 1.1.1.6 root 3292: bc_expand_end_bindings (vars, mark_ends, dont_jump_in) 3293: tree vars; 3294: int mark_ends; 3295: int dont_jump_in; 3296: { 3297: struct nesting *thisbind = nesting_stack; 3298: tree decl; 3299: 3300: if (warn_unused) 3301: for (decl = vars; decl; decl = TREE_CHAIN (decl)) 3302: if (! TREE_USED (TREE_VALUE (decl)) && TREE_CODE (TREE_VALUE (decl)) == VAR_DECL) 3303: warning_with_decl (decl, "unused variable `%s'"); 3304: 1.1.1.7 root 3305: if (thisbind->exit_label) 3306: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thisbind->exit_label)); 1.1.1.6 root 3307: 3308: /* Pop block/bindings off stack */ 3309: POPSTACK (block_stack); 3310: } 1.1 root 3311: 3312: /* Generate RTL for the automatic variable declaration DECL. 1.1.1.8 ! root 3313: (Other kinds of declarations are simply ignored if seen here.) */ 1.1 root 3314: 3315: void 3316: expand_decl (decl) 3317: register tree decl; 3318: { 3319: struct nesting *thisblock = block_stack; 1.1.1.6 root 3320: tree type; 3321: 3322: if (output_bytecode) 3323: { 3324: bc_expand_decl (decl, 0); 3325: return; 3326: } 3327: 3328: type = TREE_TYPE (decl); 1.1 root 3329: 3330: /* Only automatic variables need any expansion done. 3331: Static and external variables, and external functions, 3332: will be handled by `assemble_variable' (called from finish_decl). 3333: TYPE_DECL and CONST_DECL require nothing. 3334: PARM_DECLs are handled in `assign_parms'. */ 3335: 3336: if (TREE_CODE (decl) != VAR_DECL) 3337: return; 1.1.1.4 root 3338: if (TREE_STATIC (decl) || DECL_EXTERNAL (decl)) 1.1 root 3339: return; 3340: 3341: /* Create the RTL representation for the variable. */ 3342: 3343: if (type == error_mark_node) 3344: DECL_RTL (decl) = gen_rtx (MEM, BLKmode, const0_rtx); 3345: else if (DECL_SIZE (decl) == 0) 3346: /* Variable with incomplete type. */ 3347: { 3348: if (DECL_INITIAL (decl) == 0) 3349: /* Error message was already done; now avoid a crash. */ 3350: DECL_RTL (decl) = assign_stack_temp (DECL_MODE (decl), 0, 1); 3351: else 3352: /* An initializer is going to decide the size of this array. 3353: Until we know the size, represent its address with a reg. */ 3354: DECL_RTL (decl) = gen_rtx (MEM, BLKmode, gen_reg_rtx (Pmode)); 1.1.1.8 ! root 3355: MEM_IN_STRUCT_P (DECL_RTL (decl)) = AGGREGATE_TYPE_P (type); 1.1 root 3356: } 3357: else if (DECL_MODE (decl) != BLKmode 3358: /* If -ffloat-store, don't put explicit float vars 3359: into regs. */ 3360: && !(flag_float_store 3361: && TREE_CODE (type) == REAL_TYPE) 3362: && ! TREE_THIS_VOLATILE (decl) 3363: && ! TREE_ADDRESSABLE (decl) 1.1.1.4 root 3364: && (DECL_REGISTER (decl) || ! obey_regdecls)) 1.1 root 3365: { 3366: /* Automatic variable that can go in a register. */ 1.1.1.4 root 3367: int unsignedp = TREE_UNSIGNED (type); 1.1.1.7 root 3368: enum machine_mode reg_mode 3369: = promote_mode (type, DECL_MODE (decl), &unsignedp, 0); 1.1.1.4 root 3370: 1.1.1.6 root 3371: if (TREE_CODE (type) == COMPLEX_TYPE) 3372: { 3373: rtx realpart, imagpart; 3374: enum machine_mode partmode = TYPE_MODE (TREE_TYPE (type)); 3375: 3376: /* For a complex type variable, make a CONCAT of two pseudos 3377: so that the real and imaginary parts 3378: can be allocated separately. */ 3379: realpart = gen_reg_rtx (partmode); 3380: REG_USERVAR_P (realpart) = 1; 3381: imagpart = gen_reg_rtx (partmode); 3382: REG_USERVAR_P (imagpart) = 1; 3383: DECL_RTL (decl) = gen_rtx (CONCAT, reg_mode, realpart, imagpart); 3384: } 3385: else 3386: { 3387: DECL_RTL (decl) = gen_reg_rtx (reg_mode); 3388: if (TREE_CODE (type) == POINTER_TYPE) 3389: mark_reg_pointer (DECL_RTL (decl)); 3390: REG_USERVAR_P (DECL_RTL (decl)) = 1; 3391: } 1.1 root 3392: } 3393: else if (TREE_CODE (DECL_SIZE (decl)) == INTEGER_CST) 3394: { 3395: /* Variable of fixed size that goes on the stack. */ 3396: rtx oldaddr = 0; 3397: rtx addr; 3398: 3399: /* If we previously made RTL for this decl, it must be an array 3400: whose size was determined by the initializer. 3401: The old address was a register; set that register now 3402: to the proper address. */ 3403: if (DECL_RTL (decl) != 0) 3404: { 3405: if (GET_CODE (DECL_RTL (decl)) != MEM 3406: || GET_CODE (XEXP (DECL_RTL (decl), 0)) != REG) 3407: abort (); 3408: oldaddr = XEXP (DECL_RTL (decl), 0); 3409: } 3410: 3411: DECL_RTL (decl) 3412: = assign_stack_temp (DECL_MODE (decl), 3413: ((TREE_INT_CST_LOW (DECL_SIZE (decl)) 3414: + BITS_PER_UNIT - 1) 3415: / BITS_PER_UNIT), 3416: 1); 1.1.1.8 ! root 3417: MEM_IN_STRUCT_P (DECL_RTL (decl)) = AGGREGATE_TYPE_P (TREE_TYPE (decl)); 1.1 root 3418: 3419: /* Set alignment we actually gave this decl. */ 3420: DECL_ALIGN (decl) = (DECL_MODE (decl) == BLKmode ? BIGGEST_ALIGNMENT 3421: : GET_MODE_BITSIZE (DECL_MODE (decl))); 3422: 3423: if (oldaddr) 3424: { 3425: addr = force_operand (XEXP (DECL_RTL (decl), 0), oldaddr); 3426: if (addr != oldaddr) 3427: emit_move_insn (oldaddr, addr); 3428: } 3429: 3430: /* If this is a memory ref that contains aggregate components, 3431: mark it as such for cse and loop optimize. */ 1.1.1.7 root 3432: MEM_IN_STRUCT_P (DECL_RTL (decl)) = AGGREGATE_TYPE_P (TREE_TYPE (decl)); 1.1 root 3433: #if 0 3434: /* If this is in memory because of -ffloat-store, 3435: set the volatile bit, to prevent optimizations from 3436: undoing the effects. */ 3437: if (flag_float_store && TREE_CODE (type) == REAL_TYPE) 3438: MEM_VOLATILE_P (DECL_RTL (decl)) = 1; 3439: #endif 3440: } 3441: else 3442: /* Dynamic-size object: must push space on the stack. */ 3443: { 3444: rtx address, size; 3445: 3446: /* Record the stack pointer on entry to block, if have 3447: not already done so. */ 3448: if (thisblock->data.block.stack_level == 0) 3449: { 3450: do_pending_stack_adjust (); 1.1.1.3 root 3451: emit_stack_save (thisblock->next ? SAVE_BLOCK : SAVE_FUNCTION, 3452: &thisblock->data.block.stack_level, 3453: thisblock->data.block.first_insn); 1.1 root 3454: stack_block_stack = thisblock; 3455: } 3456: 3457: /* Compute the variable's size, in bytes. */ 3458: size = expand_expr (size_binop (CEIL_DIV_EXPR, 3459: DECL_SIZE (decl), 3460: size_int (BITS_PER_UNIT)), 1.1.1.4 root 3461: NULL_RTX, VOIDmode, 0); 1.1 root 3462: free_temp_slots (); 3463: 3464: /* Allocate space on the stack for the variable. */ 1.1.1.4 root 3465: address = allocate_dynamic_stack_space (size, NULL_RTX, 3466: DECL_ALIGN (decl)); 1.1 root 3467: 3468: /* Reference the variable indirect through that rtx. */ 3469: DECL_RTL (decl) = gen_rtx (MEM, DECL_MODE (decl), address); 3470: 1.1.1.3 root 3471: /* If this is a memory ref that contains aggregate components, 3472: mark it as such for cse and loop optimize. */ 1.1.1.7 root 3473: MEM_IN_STRUCT_P (DECL_RTL (decl)) = AGGREGATE_TYPE_P (TREE_TYPE (decl)); 1.1.1.3 root 3474: 1.1 root 3475: /* Indicate the alignment we actually gave this variable. */ 3476: #ifdef STACK_BOUNDARY 3477: DECL_ALIGN (decl) = STACK_BOUNDARY; 3478: #else 3479: DECL_ALIGN (decl) = BIGGEST_ALIGNMENT; 3480: #endif 3481: } 3482: 3483: if (TREE_THIS_VOLATILE (decl)) 3484: MEM_VOLATILE_P (DECL_RTL (decl)) = 1; 1.1.1.5 root 3485: #if 0 /* A variable is not necessarily unchanging 3486: just because it is const. RTX_UNCHANGING_P 3487: means no change in the function, 3488: not merely no change in the variable's scope. 3489: It is correct to set RTX_UNCHANGING_P if the variable's scope 3490: is the whole function. There's no convenient way to test that. */ 1.1 root 3491: if (TREE_READONLY (decl)) 3492: RTX_UNCHANGING_P (DECL_RTL (decl)) = 1; 1.1.1.5 root 3493: #endif 1.1 root 3494: 3495: /* If doing stupid register allocation, make sure life of any 3496: register variable starts here, at the start of its scope. */ 3497: 3498: if (obey_regdecls) 3499: use_variable (DECL_RTL (decl)); 3500: } 1.1.1.6 root 3501: 3502: 3503: /* Generate code for the automatic variable declaration DECL. For 3504: most variables this just means we give it a stack offset. The 3505: compiler sometimes emits cleanups without variables and we will 3506: have to deal with those too. */ 3507: 1.1.1.7 root 3508: static void 1.1.1.6 root 3509: bc_expand_decl (decl, cleanup) 3510: tree decl; 3511: tree cleanup; 3512: { 3513: tree type; 3514: 3515: if (!decl) 3516: { 3517: /* A cleanup with no variable. */ 3518: if (!cleanup) 3519: abort (); 3520: 3521: return; 3522: } 3523: 3524: /* Only auto variables need any work. */ 3525: if (TREE_CODE (decl) != VAR_DECL || TREE_STATIC (decl) || DECL_EXTERNAL (decl)) 3526: return; 3527: 3528: type = TREE_TYPE (decl); 3529: 3530: if (type == error_mark_node) 3531: DECL_RTL (decl) = bc_gen_rtx ((char *) 0, 0, (struct bc_label *) 0); 3532: 3533: else if (DECL_SIZE (decl) == 0) 3534: 3535: /* Variable with incomplete type. The stack offset herein will be 3536: fixed later in expand_decl_init (). */ 3537: DECL_RTL (decl) = bc_gen_rtx ((char *) 0, 0, (struct bc_label *) 0); 3538: 3539: else if (TREE_CONSTANT (DECL_SIZE (decl))) 3540: { 3541: DECL_RTL (decl) = bc_allocate_local (TREE_INT_CST_LOW (DECL_SIZE (decl)) / BITS_PER_UNIT, 3542: DECL_ALIGN (decl)); 3543: } 3544: else 3545: DECL_RTL (decl) = bc_allocate_variable_array (DECL_SIZE (decl)); 3546: } 1.1 root 3547: 3548: /* Emit code to perform the initialization of a declaration DECL. */ 3549: 3550: void 3551: expand_decl_init (decl) 3552: tree decl; 3553: { 1.1.1.2 root 3554: int was_used = TREE_USED (decl); 3555: 1.1.1.7 root 3556: if (output_bytecode) 3557: { 3558: bc_expand_decl_init (decl); 3559: return; 3560: } 3561: 1.1.1.6 root 3562: /* If this is a CONST_DECL, we don't have to generate any code, but 3563: if DECL_INITIAL is a constant, call expand_expr to force TREE_CST_RTL 3564: to be set while in the obstack containing the constant. If we don't 3565: do this, we can lose if we have functions nested three deep and the middle 3566: function makes a CONST_DECL whose DECL_INITIAL is a STRING_CST while 3567: the innermost function is the first to expand that STRING_CST. */ 3568: if (TREE_CODE (decl) == CONST_DECL) 3569: { 3570: if (DECL_INITIAL (decl) && TREE_CONSTANT (DECL_INITIAL (decl))) 3571: expand_expr (DECL_INITIAL (decl), NULL_RTX, VOIDmode, 3572: EXPAND_INITIALIZER); 3573: return; 3574: } 3575: 1.1 root 3576: if (TREE_STATIC (decl)) 3577: return; 3578: 3579: /* Compute and store the initial value now. */ 3580: 3581: if (DECL_INITIAL (decl) == error_mark_node) 3582: { 3583: enum tree_code code = TREE_CODE (TREE_TYPE (decl)); 3584: if (code == INTEGER_TYPE || code == REAL_TYPE || code == ENUMERAL_TYPE 3585: || code == POINTER_TYPE) 3586: expand_assignment (decl, convert (TREE_TYPE (decl), integer_zero_node), 3587: 0, 0); 3588: emit_queue (); 3589: } 3590: else if (DECL_INITIAL (decl) && TREE_CODE (DECL_INITIAL (decl)) != TREE_LIST) 3591: { 3592: emit_line_note (DECL_SOURCE_FILE (decl), DECL_SOURCE_LINE (decl)); 3593: expand_assignment (decl, DECL_INITIAL (decl), 0, 0); 3594: emit_queue (); 3595: } 3596: 1.1.1.2 root 3597: /* Don't let the initialization count as "using" the variable. */ 3598: TREE_USED (decl) = was_used; 3599: 1.1 root 3600: /* Free any temporaries we made while initializing the decl. */ 1.1.1.8 ! root 3601: preserve_temp_slots (NULL_RTX); 1.1 root 3602: free_temp_slots (); 3603: } 3604: 1.1.1.6 root 3605: /* Expand initialization for variable-sized types. Allocate array 3606: using newlocalSI and set local variable, which is a pointer to the 3607: storage. */ 3608: 1.1.1.7 root 3609: static void 1.1.1.6 root 3610: bc_expand_variable_local_init (decl) 3611: tree decl; 3612: { 3613: /* Evaluate size expression and coerce to SI */ 3614: bc_expand_expr (DECL_SIZE (decl)); 3615: 3616: /* Type sizes are always (?) of TREE_CODE INTEGER_CST, so 3617: no coercion is necessary (?) */ 3618: 3619: /* emit_typecode_conversion (preferred_typecode (TYPE_MODE (DECL_SIZE (decl)), 3620: TREE_UNSIGNED (DECL_SIZE (decl))), SIcode); */ 3621: 3622: /* Emit code to allocate array */ 3623: bc_emit_instruction (newlocalSI); 3624: 3625: /* Store array pointer in local variable. This is the only instance 3626: where we actually want the address of the pointer to the 3627: variable-size block, rather than the pointer itself. We avoid 3628: using expand_address() since that would cause the pointer to be 3629: pushed rather than its address. Hence the hard-coded reference; 3630: notice also that the variable is always local (no global 3631: variable-size type variables). */ 3632: 3633: bc_load_localaddr (DECL_RTL (decl)); 3634: bc_emit_instruction (storeP); 3635: } 3636: 3637: 3638: /* Emit code to initialize a declaration. */ 1.1.1.7 root 3639: 3640: static void 1.1.1.6 root 3641: bc_expand_decl_init (decl) 3642: tree decl; 3643: { 3644: int org_stack_depth; 3645: 3646: /* Statical initializers are handled elsewhere */ 3647: 3648: if (TREE_STATIC (decl)) 3649: return; 3650: 3651: /* Memory original stack depth */ 3652: org_stack_depth = stack_depth; 3653: 3654: /* If the type is variable-size, we first create its space (we ASSUME 3655: it CAN'T be static). We do this regardless of whether there's an 3656: initializer assignment or not. */ 3657: 3658: if (TREE_CODE (DECL_SIZE (decl)) != INTEGER_CST) 3659: bc_expand_variable_local_init (decl); 3660: 3661: /* Expand initializer assignment */ 3662: if (DECL_INITIAL (decl) == error_mark_node) 3663: { 3664: enum tree_code code = TREE_CODE (TREE_TYPE (decl)); 3665: 3666: if (code == INTEGER_TYPE || code == REAL_TYPE || code == ENUMERAL_TYPE 3667: || code == POINTER_TYPE) 3668: 3669: expand_assignment (TREE_TYPE (decl), decl, 0, 0); 3670: } 3671: else if (DECL_INITIAL (decl)) 3672: expand_assignment (TREE_TYPE (decl), decl, 0, 0); 3673: 3674: /* Restore stack depth */ 3675: if (org_stack_depth > stack_depth) 3676: abort (); 3677: 3678: bc_adjust_stack (stack_depth - org_stack_depth); 3679: } 3680: 3681: 1.1 root 3682: /* CLEANUP is an expression to be executed at exit from this binding contour; 3683: for example, in C++, it might call the destructor for this variable. 3684: 3685: If CLEANUP contains any SAVE_EXPRs, then you must preevaluate them 1.1.1.8 ! root 3686: either before or after calling `expand_decl_cleanup' but before compiling 1.1 root 3687: any subsequent expressions. This is because CLEANUP may be expanded 3688: more than once, on different branches of execution. 3689: For the same reason, CLEANUP may not contain a CALL_EXPR 3690: except as its topmost node--else `preexpand_calls' would get confused. 3691: 3692: If CLEANUP is nonzero and DECL is zero, we record a cleanup 3693: that is not associated with any particular variable. */ 3694: 3695: int 3696: expand_decl_cleanup (decl, cleanup) 3697: tree decl, cleanup; 3698: { 3699: struct nesting *thisblock = block_stack; 3700: 3701: /* Error if we are not in any block. */ 3702: if (thisblock == 0) 3703: return 0; 3704: 3705: /* Record the cleanup if there is one. */ 3706: 3707: if (cleanup != 0) 3708: { 3709: thisblock->data.block.cleanups 3710: = temp_tree_cons (decl, cleanup, thisblock->data.block.cleanups); 3711: /* If this block has a cleanup, it belongs in stack_block_stack. */ 3712: stack_block_stack = thisblock; 1.1.1.7 root 3713: (*interim_eh_hook) (NULL_TREE); 1.1 root 3714: } 3715: return 1; 3716: } 3717: 3718: /* DECL is an anonymous union. CLEANUP is a cleanup for DECL. 3719: DECL_ELTS is the list of elements that belong to DECL's type. 3720: In each, the TREE_VALUE is a VAR_DECL, and the TREE_PURPOSE a cleanup. */ 3721: 3722: void 3723: expand_anon_union_decl (decl, cleanup, decl_elts) 3724: tree decl, cleanup, decl_elts; 3725: { 3726: struct nesting *thisblock = block_stack; 3727: rtx x; 3728: 1.1.1.8 ! root 3729: expand_decl (decl); ! 3730: expand_decl_cleanup (decl, cleanup); 1.1 root 3731: x = DECL_RTL (decl); 3732: 3733: while (decl_elts) 3734: { 3735: tree decl_elt = TREE_VALUE (decl_elts); 3736: tree cleanup_elt = TREE_PURPOSE (decl_elts); 3737: enum machine_mode mode = TYPE_MODE (TREE_TYPE (decl_elt)); 3738: 1.1.1.7 root 3739: /* Propagate the union's alignment to the elements. */ 3740: DECL_ALIGN (decl_elt) = DECL_ALIGN (decl); 3741: 3742: /* If the element has BLKmode and the union doesn't, the union is 3743: aligned such that the element doesn't need to have BLKmode, so 3744: change the element's mode to the appropriate one for its size. */ 3745: if (mode == BLKmode && DECL_MODE (decl) != BLKmode) 3746: DECL_MODE (decl_elt) = mode 3747: = mode_for_size (TREE_INT_CST_LOW (DECL_SIZE (decl_elt)), 3748: MODE_INT, 1); 3749: 1.1 root 3750: /* (SUBREG (MEM ...)) at RTL generation time is invalid, so we 3751: instead create a new MEM rtx with the proper mode. */ 3752: if (GET_CODE (x) == MEM) 3753: { 3754: if (mode == GET_MODE (x)) 3755: DECL_RTL (decl_elt) = x; 3756: else 3757: { 3758: DECL_RTL (decl_elt) = gen_rtx (MEM, mode, copy_rtx (XEXP (x, 0))); 3759: MEM_IN_STRUCT_P (DECL_RTL (decl_elt)) = MEM_IN_STRUCT_P (x); 3760: RTX_UNCHANGING_P (DECL_RTL (decl_elt)) = RTX_UNCHANGING_P (x); 3761: } 3762: } 3763: else if (GET_CODE (x) == REG) 3764: { 3765: if (mode == GET_MODE (x)) 3766: DECL_RTL (decl_elt) = x; 3767: else 3768: DECL_RTL (decl_elt) = gen_rtx (SUBREG, mode, x, 0); 3769: } 3770: else 3771: abort (); 3772: 3773: /* Record the cleanup if there is one. */ 3774: 3775: if (cleanup != 0) 3776: thisblock->data.block.cleanups 3777: = temp_tree_cons (decl_elt, cleanup_elt, 3778: thisblock->data.block.cleanups); 3779: 3780: decl_elts = TREE_CHAIN (decl_elts); 3781: } 3782: } 3783: 3784: /* Expand a list of cleanups LIST. 3785: Elements may be expressions or may be nested lists. 3786: 3787: If DONT_DO is nonnull, then any list-element 3788: whose TREE_PURPOSE matches DONT_DO is omitted. 3789: This is sometimes used to avoid a cleanup associated with 1.1.1.8 ! root 3790: a value that is being returned out of the scope. ! 3791: ! 3792: If IN_FIXUP is non-zero, we are generating this cleanup for a fixup ! 3793: goto and handle protection regions specially in that case. ! 3794: ! 3795: If REACHABLE, we emit code, otherwise just inform the exception handling ! 3796: code about this finalization. */ 1.1 root 3797: 3798: static void 1.1.1.8 ! root 3799: expand_cleanups (list, dont_do, in_fixup, reachable) 1.1 root 3800: tree list; 3801: tree dont_do; 1.1.1.8 ! root 3802: int in_fixup; ! 3803: int reachable; 1.1 root 3804: { 3805: tree tail; 3806: for (tail = list; tail; tail = TREE_CHAIN (tail)) 3807: if (dont_do == 0 || TREE_PURPOSE (tail) != dont_do) 3808: { 3809: if (TREE_CODE (TREE_VALUE (tail)) == TREE_LIST) 1.1.1.8 ! root 3810: expand_cleanups (TREE_VALUE (tail), dont_do, in_fixup, reachable); 1.1 root 3811: else 3812: { 1.1.1.8 ! root 3813: if (! in_fixup) ! 3814: (*interim_eh_hook) (TREE_VALUE (tail)); 1.1.1.7 root 3815: 1.1.1.8 ! root 3816: if (reachable) ! 3817: { ! 3818: /* Cleanups may be run multiple times. For example, ! 3819: when exiting a binding contour, we expand the ! 3820: cleanups associated with that contour. When a goto ! 3821: within that binding contour has a target outside that ! 3822: contour, it will expand all cleanups from its scope to ! 3823: the target. Though the cleanups are expanded multiple ! 3824: times, the control paths are non-overlapping so the ! 3825: cleanups will not be executed twice. */ ! 3826: expand_expr (TREE_VALUE (tail), const0_rtx, VOIDmode, 0); ! 3827: free_temp_slots (); ! 3828: } 1.1 root 3829: } 3830: } 3831: } 3832: 3833: /* Move all cleanups from the current block_stack 3834: to the containing block_stack, where they are assumed to 3835: have been created. If anything can cause a temporary to 3836: be created, but not expanded for more than one level of 3837: block_stacks, then this code will have to change. */ 3838: 3839: void 3840: move_cleanups_up () 3841: { 3842: struct nesting *block = block_stack; 3843: struct nesting *outer = block->next; 3844: 3845: outer->data.block.cleanups 3846: = chainon (block->data.block.cleanups, 3847: outer->data.block.cleanups); 3848: block->data.block.cleanups = 0; 3849: } 3850: 3851: tree 3852: last_cleanup_this_contour () 3853: { 3854: if (block_stack == 0) 3855: return 0; 3856: 3857: return block_stack->data.block.cleanups; 3858: } 3859: 3860: /* Return 1 if there are any pending cleanups at this point. 3861: If THIS_CONTOUR is nonzero, check the current contour as well. 3862: Otherwise, look only at the contours that enclose this one. */ 3863: 3864: int 3865: any_pending_cleanups (this_contour) 3866: int this_contour; 3867: { 3868: struct nesting *block; 3869: 3870: if (block_stack == 0) 3871: return 0; 3872: 3873: if (this_contour && block_stack->data.block.cleanups != NULL) 3874: return 1; 3875: if (block_stack->data.block.cleanups == 0 3876: && (block_stack->data.block.outer_cleanups == 0 3877: #if 0 3878: || block_stack->data.block.outer_cleanups == empty_cleanup_list 3879: #endif 3880: )) 3881: return 0; 3882: 3883: for (block = block_stack->next; block; block = block->next) 3884: if (block->data.block.cleanups != 0) 3885: return 1; 3886: 3887: return 0; 3888: } 3889: 3890: /* Enter a case (Pascal) or switch (C) statement. 3891: Push a block onto case_stack and nesting_stack 3892: to accumulate the case-labels that are seen 3893: and to record the labels generated for the statement. 3894: 3895: EXIT_FLAG is nonzero if `exit_something' should exit this case stmt. 3896: Otherwise, this construct is transparent for `exit_something'. 3897: 3898: EXPR is the index-expression to be dispatched on. 3899: TYPE is its nominal type. We could simply convert EXPR to this type, 3900: but instead we take short cuts. */ 3901: 3902: void 3903: expand_start_case (exit_flag, expr, type, printname) 3904: int exit_flag; 3905: tree expr; 3906: tree type; 3907: char *printname; 3908: { 3909: register struct nesting *thiscase = ALLOC_NESTING (); 3910: 3911: /* Make an entry on case_stack for the case we are entering. */ 3912: 3913: thiscase->next = case_stack; 3914: thiscase->all = nesting_stack; 3915: thiscase->depth = ++nesting_depth; 3916: thiscase->exit_label = exit_flag ? gen_label_rtx () : 0; 3917: thiscase->data.case_stmt.case_list = 0; 3918: thiscase->data.case_stmt.index_expr = expr; 3919: thiscase->data.case_stmt.nominal_type = type; 3920: thiscase->data.case_stmt.default_label = 0; 3921: thiscase->data.case_stmt.num_ranges = 0; 3922: thiscase->data.case_stmt.printname = printname; 3923: thiscase->data.case_stmt.seenlabel = 0; 3924: case_stack = thiscase; 3925: nesting_stack = thiscase; 3926: 1.1.1.6 root 3927: if (output_bytecode) 3928: { 3929: bc_expand_start_case (thiscase, expr, type, printname); 3930: return; 3931: } 3932: 1.1 root 3933: do_pending_stack_adjust (); 3934: 3935: /* Make sure case_stmt.start points to something that won't 3936: need any transformation before expand_end_case. */ 3937: if (GET_CODE (get_last_insn ()) != NOTE) 1.1.1.4 root 3938: emit_note (NULL_PTR, NOTE_INSN_DELETED); 1.1 root 3939: 3940: thiscase->data.case_stmt.start = get_last_insn (); 3941: } 3942: 1.1.1.6 root 3943: 3944: /* Enter a case statement. It is assumed that the caller has pushed 3945: the current context onto the case stack. */ 1.1.1.7 root 3946: 3947: static void 1.1.1.6 root 3948: bc_expand_start_case (thiscase, expr, type, printname) 3949: struct nesting *thiscase; 3950: tree expr; 3951: tree type; 3952: char *printname; 3953: { 3954: bc_expand_expr (expr); 3955: bc_expand_conversion (TREE_TYPE (expr), type); 3956: 3957: /* For cases, the skip is a place we jump to that's emitted after 3958: the size of the jump table is known. */ 3959: 3960: thiscase->data.case_stmt.skip_label = gen_label_rtx (); 3961: bc_emit_bytecode (jump); 3962: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (thiscase->data.case_stmt.skip_label)); 3963: 3964: #ifdef DEBUG_PRINT_CODE 3965: fputc ('\n', stderr); 3966: #endif 3967: } 3968: 3969: 1.1 root 3970: /* Start a "dummy case statement" within which case labels are invalid 3971: and are not connected to any larger real case statement. 3972: This can be used if you don't want to let a case statement jump 3973: into the middle of certain kinds of constructs. */ 3974: 3975: void 3976: expand_start_case_dummy () 3977: { 3978: register struct nesting *thiscase = ALLOC_NESTING (); 3979: 3980: /* Make an entry on case_stack for the dummy. */ 3981: 3982: thiscase->next = case_stack; 3983: thiscase->all = nesting_stack; 3984: thiscase->depth = ++nesting_depth; 3985: thiscase->exit_label = 0; 3986: thiscase->data.case_stmt.case_list = 0; 3987: thiscase->data.case_stmt.start = 0; 3988: thiscase->data.case_stmt.nominal_type = 0; 3989: thiscase->data.case_stmt.default_label = 0; 3990: thiscase->data.case_stmt.num_ranges = 0; 3991: case_stack = thiscase; 3992: nesting_stack = thiscase; 3993: } 3994: 3995: /* End a dummy case statement. */ 3996: 3997: void 3998: expand_end_case_dummy () 3999: { 4000: POPSTACK (case_stack); 4001: } 4002: 4003: /* Return the data type of the index-expression 4004: of the innermost case statement, or null if none. */ 4005: 4006: tree 4007: case_index_expr_type () 4008: { 4009: if (case_stack) 4010: return TREE_TYPE (case_stack->data.case_stmt.index_expr); 4011: return 0; 4012: } 4013: 4014: /* Accumulate one case or default label inside a case or switch statement. 4015: VALUE is the value of the case (a null pointer, for a default label). 1.1.1.6 root 4016: The function CONVERTER, when applied to arguments T and V, 4017: converts the value V to the type T. 1.1 root 4018: 4019: If not currently inside a case or switch statement, return 1 and do 4020: nothing. The caller will print a language-specific error message. 4021: If VALUE is a duplicate or overlaps, return 2 and do nothing 4022: except store the (first) duplicate node in *DUPLICATE. 4023: If VALUE is out of range, return 3 and do nothing. 4024: If we are jumping into the scope of a cleaup or var-sized array, return 5. 4025: Return 0 on success. 4026: 4027: Extended to handle range statements. */ 4028: 4029: int 1.1.1.6 root 4030: pushcase (value, converter, label, duplicate) 1.1 root 4031: register tree value; 1.1.1.6 root 4032: tree (*converter) PROTO((tree, tree)); 1.1 root 4033: register tree label; 4034: tree *duplicate; 4035: { 4036: register struct case_node **l; 4037: register struct case_node *n; 4038: tree index_type; 4039: tree nominal_type; 4040: 1.1.1.6 root 4041: if (output_bytecode) 4042: return bc_pushcase (value, label); 4043: 1.1 root 4044: /* Fail if not inside a real case statement. */ 4045: if (! (case_stack && case_stack->data.case_stmt.start)) 4046: return 1; 4047: 4048: if (stack_block_stack 4049: && stack_block_stack->depth > case_stack->depth) 4050: return 5; 4051: 4052: index_type = TREE_TYPE (case_stack->data.case_stmt.index_expr); 4053: nominal_type = case_stack->data.case_stmt.nominal_type; 4054: 4055: /* If the index is erroneous, avoid more problems: pretend to succeed. */ 4056: if (index_type == error_mark_node) 4057: return 0; 4058: 4059: /* Convert VALUE to the type in which the comparisons are nominally done. */ 4060: if (value != 0) 1.1.1.6 root 4061: value = (*converter) (nominal_type, value); 1.1 root 4062: 4063: /* If this is the first label, warn if any insns have been emitted. */ 4064: if (case_stack->data.case_stmt.seenlabel == 0) 4065: { 4066: rtx insn; 4067: for (insn = case_stack->data.case_stmt.start; 4068: insn; 4069: insn = NEXT_INSN (insn)) 4070: { 4071: if (GET_CODE (insn) == CODE_LABEL) 4072: break; 4073: if (GET_CODE (insn) != NOTE 4074: && (GET_CODE (insn) != INSN || GET_CODE (PATTERN (insn)) != USE)) 4075: { 4076: warning ("unreachable code at beginning of %s", 4077: case_stack->data.case_stmt.printname); 4078: break; 4079: } 4080: } 4081: } 4082: case_stack->data.case_stmt.seenlabel = 1; 4083: 4084: /* Fail if this value is out of range for the actual type of the index 4085: (which may be narrower than NOMINAL_TYPE). */ 4086: if (value != 0 && ! int_fits_type_p (value, index_type)) 4087: return 3; 4088: 4089: /* Fail if this is a duplicate or overlaps another entry. */ 4090: if (value == 0) 4091: { 4092: if (case_stack->data.case_stmt.default_label != 0) 4093: { 4094: *duplicate = case_stack->data.case_stmt.default_label; 4095: return 2; 4096: } 4097: case_stack->data.case_stmt.default_label = label; 4098: } 4099: else 4100: { 4101: /* Find the elt in the chain before which to insert the new value, 4102: to keep the chain sorted in increasing order. 4103: But report an error if this element is a duplicate. */ 4104: for (l = &case_stack->data.case_stmt.case_list; 4105: /* Keep going past elements distinctly less than VALUE. */ 4106: *l != 0 && tree_int_cst_lt ((*l)->high, value); 4107: l = &(*l)->right) 4108: ; 4109: if (*l) 4110: { 4111: /* Element we will insert before must be distinctly greater; 4112: overlap means error. */ 4113: if (! tree_int_cst_lt (value, (*l)->low)) 4114: { 4115: *duplicate = (*l)->code_label; 4116: return 2; 4117: } 4118: } 4119: 4120: /* Add this label to the chain, and succeed. 4121: Copy VALUE so it is on temporary rather than momentary 4122: obstack and will thus survive till the end of the case statement. */ 4123: n = (struct case_node *) oballoc (sizeof (struct case_node)); 4124: n->left = 0; 4125: n->right = *l; 4126: n->high = n->low = copy_node (value); 4127: n->code_label = label; 4128: *l = n; 4129: } 4130: 4131: expand_label (label); 4132: return 0; 4133: } 4134: 4135: /* Like pushcase but this case applies to all values 4136: between VALUE1 and VALUE2 (inclusive). 4137: The return value is the same as that of pushcase 4138: but there is one additional error code: 4139: 4 means the specified range was empty. */ 4140: 4141: int 1.1.1.6 root 4142: pushcase_range (value1, value2, converter, label, duplicate) 1.1 root 4143: register tree value1, value2; 1.1.1.6 root 4144: tree (*converter) PROTO((tree, tree)); 1.1 root 4145: register tree label; 4146: tree *duplicate; 4147: { 4148: register struct case_node **l; 4149: register struct case_node *n; 4150: tree index_type; 4151: tree nominal_type; 4152: 4153: /* Fail if not inside a real case statement. */ 4154: if (! (case_stack && case_stack->data.case_stmt.start)) 4155: return 1; 4156: 4157: if (stack_block_stack 4158: && stack_block_stack->depth > case_stack->depth) 4159: return 5; 4160: 4161: index_type = TREE_TYPE (case_stack->data.case_stmt.index_expr); 4162: nominal_type = case_stack->data.case_stmt.nominal_type; 4163: 4164: /* If the index is erroneous, avoid more problems: pretend to succeed. */ 4165: if (index_type == error_mark_node) 4166: return 0; 4167: 4168: /* If this is the first label, warn if any insns have been emitted. */ 4169: if (case_stack->data.case_stmt.seenlabel == 0) 4170: { 4171: rtx insn; 4172: for (insn = case_stack->data.case_stmt.start; 4173: insn; 4174: insn = NEXT_INSN (insn)) 4175: { 4176: if (GET_CODE (insn) == CODE_LABEL) 4177: break; 4178: if (GET_CODE (insn) != NOTE 4179: && (GET_CODE (insn) != INSN || GET_CODE (PATTERN (insn)) != USE)) 4180: { 4181: warning ("unreachable code at beginning of %s", 4182: case_stack->data.case_stmt.printname); 4183: break; 4184: } 4185: } 4186: } 4187: case_stack->data.case_stmt.seenlabel = 1; 4188: 4189: /* Convert VALUEs to type in which the comparisons are nominally done. */ 4190: if (value1 == 0) /* Negative infinity. */ 4191: value1 = TYPE_MIN_VALUE(index_type); 1.1.1.6 root 4192: value1 = (*converter) (nominal_type, value1); 1.1 root 4193: 4194: if (value2 == 0) /* Positive infinity. */ 4195: value2 = TYPE_MAX_VALUE(index_type); 1.1.1.6 root 4196: value2 = (*converter) (nominal_type, value2); 1.1 root 4197: 4198: /* Fail if these values are out of range. */ 4199: if (! int_fits_type_p (value1, index_type)) 4200: return 3; 4201: 4202: if (! int_fits_type_p (value2, index_type)) 4203: return 3; 4204: 4205: /* Fail if the range is empty. */ 4206: if (tree_int_cst_lt (value2, value1)) 4207: return 4; 4208: 4209: /* If the bounds are equal, turn this into the one-value case. */ 4210: if (tree_int_cst_equal (value1, value2)) 1.1.1.6 root 4211: return pushcase (value1, converter, label, duplicate); 1.1 root 4212: 4213: /* Find the elt in the chain before which to insert the new value, 4214: to keep the chain sorted in increasing order. 4215: But report an error if this element is a duplicate. */ 4216: for (l = &case_stack->data.case_stmt.case_list; 4217: /* Keep going past elements distinctly less than this range. */ 4218: *l != 0 && tree_int_cst_lt ((*l)->high, value1); 4219: l = &(*l)->right) 4220: ; 4221: if (*l) 4222: { 4223: /* Element we will insert before must be distinctly greater; 4224: overlap means error. */ 4225: if (! tree_int_cst_lt (value2, (*l)->low)) 4226: { 4227: *duplicate = (*l)->code_label; 4228: return 2; 4229: } 4230: } 4231: 4232: /* Add this label to the chain, and succeed. 4233: Copy VALUE1, VALUE2 so they are on temporary rather than momentary 4234: obstack and will thus survive till the end of the case statement. */ 4235: 4236: n = (struct case_node *) oballoc (sizeof (struct case_node)); 4237: n->left = 0; 4238: n->right = *l; 4239: n->low = copy_node (value1); 4240: n->high = copy_node (value2); 4241: n->code_label = label; 4242: *l = n; 4243: 4244: expand_label (label); 4245: 4246: case_stack->data.case_stmt.num_ranges++; 4247: 4248: return 0; 4249: } 1.1.1.6 root 4250: 4251: 4252: /* Accumulate one case or default label; VALUE is the value of the 4253: case, or nil for a default label. If not currently inside a case, 4254: return 1 and do nothing. If VALUE is a duplicate or overlaps, return 4255: 2 and do nothing. If VALUE is out of range, return 3 and do nothing. 4256: Return 0 on success. This function is a leftover from the earlier 4257: bytecode compiler, which was based on gcc 1.37. It should be 4258: merged into pushcase. */ 4259: 1.1.1.7 root 4260: static int 1.1.1.6 root 4261: bc_pushcase (value, label) 4262: tree value; 4263: tree label; 4264: { 4265: struct nesting *thiscase = case_stack; 4266: struct case_node *case_label, *new_label; 4267: 4268: if (! thiscase) 4269: return 1; 4270: 4271: /* Fail if duplicate, overlap, or out of type range. */ 4272: if (value) 4273: { 4274: value = convert (thiscase->data.case_stmt.nominal_type, value); 4275: if (! int_fits_type_p (value, thiscase->data.case_stmt.nominal_type)) 4276: return 3; 4277: 4278: for (case_label = thiscase->data.case_stmt.case_list; 4279: case_label->left; case_label = case_label->left) 4280: if (! tree_int_cst_lt (case_label->left->high, value)) 4281: break; 4282: 4283: if (case_label != thiscase->data.case_stmt.case_list 4284: && ! tree_int_cst_lt (case_label->high, value) 4285: || case_label->left && ! tree_int_cst_lt (value, case_label->left->low)) 4286: return 2; 4287: 4288: new_label = (struct case_node *) oballoc (sizeof (struct case_node)); 4289: new_label->low = new_label->high = copy_node (value); 4290: new_label->code_label = label; 4291: new_label->left = case_label->left; 4292: 4293: case_label->left = new_label; 4294: thiscase->data.case_stmt.num_ranges++; 4295: } 4296: else 4297: { 4298: if (thiscase->data.case_stmt.default_label) 4299: return 2; 4300: thiscase->data.case_stmt.default_label = label; 4301: } 4302: 4303: expand_label (label); 4304: return 0; 4305: } 1.1 root 4306: 1.1.1.7 root 4307: /* Returns the number of possible values of TYPE. 4308: Returns -1 if the number is unknown or variable. 4309: Returns -2 if the number does not fit in a HOST_WIDE_INT. 4310: Sets *SPARENESS to 2 if TYPE is an ENUMERAL_TYPE whose values 4311: do not increase monotonically (there may be duplicates); 4312: to 1 if the values increase monotonically, but not always by 1; 4313: otherwise sets it to 0. */ 4314: 4315: HOST_WIDE_INT 4316: all_cases_count (type, spareness) 4317: tree type; 4318: int *spareness; 4319: { 4320: HOST_WIDE_INT count, count_high = 0; 4321: *spareness = 0; 4322: 4323: switch (TREE_CODE (type)) 4324: { 4325: tree t; 4326: case BOOLEAN_TYPE: 4327: count = 2; 4328: break; 4329: case CHAR_TYPE: 4330: count = 1 << BITS_PER_UNIT; 4331: break; 4332: default: 4333: case INTEGER_TYPE: 4334: if (TREE_CODE (TYPE_MIN_VALUE (type)) != INTEGER_CST 1.1.1.8 ! root 4335: || TREE_CODE (TYPE_MAX_VALUE (type)) != INTEGER_CST) 1.1.1.7 root 4336: return -1; 4337: else 4338: { 4339: /* count 4340: = TREE_INT_CST_LOW (TYPE_MAX_VALUE (type)) 4341: - TREE_INT_CST_LOW (TYPE_MIN_VALUE (type)) + 1 4342: but with overflow checking. */ 4343: tree mint = TYPE_MIN_VALUE (type); 4344: tree maxt = TYPE_MAX_VALUE (type); 4345: HOST_WIDE_INT lo, hi; 4346: neg_double(TREE_INT_CST_LOW (mint), TREE_INT_CST_HIGH (mint), 4347: &lo, &hi); 4348: add_double(TREE_INT_CST_LOW (maxt), TREE_INT_CST_HIGH (maxt), 4349: lo, hi, &lo, &hi); 4350: add_double (lo, hi, 1, 0, &lo, &hi); 4351: if (hi != 0 || lo < 0) 4352: return -2; 4353: count = lo; 4354: } 4355: break; 4356: case ENUMERAL_TYPE: 4357: count = 0; 4358: for (t = TYPE_VALUES (type); t != NULL_TREE; t = TREE_CHAIN (t)) 4359: { 4360: if (TREE_CODE (TYPE_MIN_VALUE (type)) != INTEGER_CST 4361: || TREE_CODE (TREE_VALUE (t)) != INTEGER_CST 4362: || TREE_INT_CST_LOW (TYPE_MIN_VALUE (type)) + count 4363: != TREE_INT_CST_LOW (TREE_VALUE (t))) 4364: *spareness = 1; 4365: count++; 4366: } 4367: if (*spareness == 1) 4368: { 4369: tree prev = TREE_VALUE (TYPE_VALUES (type)); 4370: for (t = TYPE_VALUES (type); t = TREE_CHAIN (t), t != NULL_TREE; ) 4371: { 4372: if (! tree_int_cst_lt (prev, TREE_VALUE (t))) 4373: { 4374: *spareness = 2; 4375: break; 4376: } 4377: prev = TREE_VALUE (t); 4378: } 4379: 4380: } 4381: } 4382: return count; 4383: } 4384: 4385: 4386: #define BITARRAY_TEST(ARRAY, INDEX) \ 4387: ((ARRAY)[(unsigned)(INDEX) / HOST_BITS_PER_CHAR]\ 4388: & (1 << ((unsigned)(INDEX) % HOST_BITS_PER_CHAR))) 4389: #define BITARRAY_SET(ARRAY, INDEX) \ 4390: ((ARRAY)[(unsigned)(INDEX) / HOST_BITS_PER_CHAR]\ 4391: |= 1 << ((unsigned)(INDEX) % HOST_BITS_PER_CHAR)) 4392: 4393: /* Set the elements of the bitstring CASES_SEEN (which has length COUNT), 4394: with the case values we have seen, assuming the case expression 4395: has the given TYPE. 4396: SPARSENESS is as determined by all_cases_count. 4397: 1.1.1.8 ! root 4398: The time needed is proportional to COUNT, unless 1.1.1.7 root 4399: SPARSENESS is 2, in which case quadratic time is needed. */ 4400: 4401: void 4402: mark_seen_cases (type, cases_seen, count, sparseness) 4403: tree type; 4404: unsigned char *cases_seen; 4405: long count; 4406: int sparseness; 4407: { 4408: long i; 4409: 4410: tree next_node_to_try = NULL_TREE; 4411: long next_node_offset = 0; 4412: 4413: register struct case_node *n; 4414: tree val = make_node (INTEGER_CST); 4415: TREE_TYPE (val) = type; 4416: for (n = case_stack->data.case_stmt.case_list; n; 4417: n = n->right) 4418: { 4419: TREE_INT_CST_LOW (val) = TREE_INT_CST_LOW (n->low); 4420: TREE_INT_CST_HIGH (val) = TREE_INT_CST_HIGH (n->low); 4421: while ( ! tree_int_cst_lt (n->high, val)) 4422: { 4423: /* Calculate (into xlo) the "offset" of the integer (val). 4424: The element with lowest value has offset 0, the next smallest 4425: element has offset 1, etc. */ 4426: 4427: HOST_WIDE_INT xlo, xhi; 4428: tree t; 4429: if (sparseness == 2) 4430: { 4431: /* This less efficient loop is only needed to handle 4432: duplicate case values (multiple enum constants 4433: with the same value). */ 4434: for (t = TYPE_VALUES (type), xlo = 0; t != NULL_TREE; 4435: t = TREE_CHAIN (t), xlo++) 4436: { 4437: if (tree_int_cst_equal (val, TREE_VALUE (t))) 4438: BITARRAY_SET (cases_seen, xlo); 4439: } 4440: } 4441: else 4442: { 4443: if (sparseness && TYPE_VALUES (type) != NULL_TREE) 4444: { 4445: /* The TYPE_VALUES will be in increasing order, so 4446: starting searching where we last ended. */ 4447: t = next_node_to_try; 4448: xlo = next_node_offset; 4449: xhi = 0; 4450: for (;;) 4451: { 4452: if (t == NULL_TREE) 4453: { 4454: t = TYPE_VALUES (type); 4455: xlo = 0; 4456: } 4457: if (tree_int_cst_equal (val, TREE_VALUE (t))) 4458: { 4459: next_node_to_try = TREE_CHAIN (t); 4460: next_node_offset = xlo + 1; 4461: break; 4462: } 4463: xlo++; 4464: t = TREE_CHAIN (t); 4465: if (t == next_node_to_try) 4466: break; 4467: } 4468: } 4469: else 4470: { 4471: t = TYPE_MIN_VALUE (type); 4472: if (t) 4473: neg_double (TREE_INT_CST_LOW (t), TREE_INT_CST_HIGH (t), 4474: &xlo, &xhi); 4475: else 4476: xlo = xhi = 0; 4477: add_double (xlo, xhi, 4478: TREE_INT_CST_LOW (val), TREE_INT_CST_HIGH (val), 4479: &xlo, &xhi); 4480: } 4481: 4482: if (xhi == 0 && xlo >= 0 && xlo < count) 4483: BITARRAY_SET (cases_seen, xlo); 4484: } 4485: add_double (TREE_INT_CST_LOW (val), TREE_INT_CST_HIGH (val), 4486: 1, 0, 4487: &TREE_INT_CST_LOW (val), &TREE_INT_CST_HIGH (val)); 4488: } 4489: } 4490: } 4491: 1.1 root 4492: /* Called when the index of a switch statement is an enumerated type 4493: and there is no default label. 4494: 4495: Checks that all enumeration literals are covered by the case 4496: expressions of a switch. Also, warn if there are any extra 4497: switch cases that are *not* elements of the enumerated type. 4498: 4499: If all enumeration literals were covered by the case expressions, 4500: turn one of the expressions into the default expression since it should 4501: not be possible to fall through such a switch. */ 4502: 4503: void 4504: check_for_full_enumeration_handling (type) 4505: tree type; 4506: { 4507: register struct case_node *n; 4508: register struct case_node **l; 4509: register tree chain; 4510: int all_values = 1; 4511: 1.1.1.7 root 4512: /* True iff the selector type is a numbered set mode. */ 4513: int sparseness = 0; 4514: 4515: /* The number of possible selector values. */ 4516: HOST_WIDE_INT size; 4517: 4518: /* For each possible selector value. a one iff it has been matched 4519: by a case value alternative. */ 4520: unsigned char *cases_seen; 4521: 4522: /* The allocated size of cases_seen, in chars. */ 4523: long bytes_needed; 4524: tree t; 4525: 1.1.1.6 root 4526: if (output_bytecode) 4527: { 4528: bc_check_for_full_enumeration_handling (type); 4529: return; 4530: } 4531: 1.1.1.7 root 4532: if (! warn_switch) 4533: return; 4534: 4535: size = all_cases_count (type, &sparseness); 4536: bytes_needed = (size + HOST_BITS_PER_CHAR) / HOST_BITS_PER_CHAR; 4537: 4538: if (size > 0 && size < 600000 4539: /* We deliberately use malloc here - not xmalloc. */ 4540: && (cases_seen = (unsigned char *) malloc (bytes_needed)) != NULL) 4541: { 4542: long i; 4543: tree v = TYPE_VALUES (type); 4544: bzero (cases_seen, bytes_needed); 4545: 4546: /* The time complexity of this code is normally O(N), where 4547: N being the number of members in the enumerated type. 4548: However, if type is a ENUMERAL_TYPE whose values do not 4549: increase monotonically, quadratic time may be needed. */ 4550: 4551: mark_seen_cases (type, cases_seen, size, sparseness); 1.1 root 4552: 1.1.1.7 root 4553: for (i = 0; v != NULL_TREE && i < size; i++, v = TREE_CHAIN (v)) 1.1 root 4554: { 1.1.1.7 root 4555: if (BITARRAY_TEST(cases_seen, i) == 0) 1.1.1.4 root 4556: warning ("enumeration value `%s' not handled in switch", 1.1.1.7 root 4557: IDENTIFIER_POINTER (TREE_PURPOSE (v))); 1.1 root 4558: } 1.1.1.7 root 4559: 4560: free (cases_seen); 1.1 root 4561: } 4562: 4563: /* Now we go the other way around; we warn if there are case 1.1.1.5 root 4564: expressions that don't correspond to enumerators. This can 1.1 root 4565: occur since C and C++ don't enforce type-checking of 4566: assignments to enumeration variables. */ 4567: 4568: if (warn_switch) 4569: for (n = case_stack->data.case_stmt.case_list; n; n = n->right) 4570: { 4571: for (chain = TYPE_VALUES (type); 4572: chain && !tree_int_cst_equal (n->low, TREE_VALUE (chain)); 4573: chain = TREE_CHAIN (chain)) 4574: ; 4575: 4576: if (!chain) 1.1.1.5 root 4577: { 4578: if (TYPE_NAME (type) == 0) 4579: warning ("case value `%d' not in enumerated type", 4580: TREE_INT_CST_LOW (n->low)); 4581: else 4582: warning ("case value `%d' not in enumerated type `%s'", 4583: TREE_INT_CST_LOW (n->low), 4584: IDENTIFIER_POINTER ((TREE_CODE (TYPE_NAME (type)) 4585: == IDENTIFIER_NODE) 4586: ? TYPE_NAME (type) 4587: : DECL_NAME (TYPE_NAME (type)))); 4588: } 1.1.1.4 root 4589: if (!tree_int_cst_equal (n->low, n->high)) 4590: { 4591: for (chain = TYPE_VALUES (type); 4592: chain && !tree_int_cst_equal (n->high, TREE_VALUE (chain)); 4593: chain = TREE_CHAIN (chain)) 4594: ; 4595: 4596: if (!chain) 1.1.1.5 root 4597: { 4598: if (TYPE_NAME (type) == 0) 4599: warning ("case value `%d' not in enumerated type", 4600: TREE_INT_CST_LOW (n->high)); 4601: else 4602: warning ("case value `%d' not in enumerated type `%s'", 4603: TREE_INT_CST_LOW (n->high), 4604: IDENTIFIER_POINTER ((TREE_CODE (TYPE_NAME (type)) 4605: == IDENTIFIER_NODE) 4606: ? TYPE_NAME (type) 4607: : DECL_NAME (TYPE_NAME (type)))); 4608: } 1.1.1.4 root 4609: } 1.1 root 4610: } 4611: 1.1.1.5 root 4612: #if 0 4613: /* ??? This optimization is disabled because it causes valid programs to 4614: fail. ANSI C does not guarantee that an expression with enum type 1.1.1.8 ! root 4615: will have a value that is the same as one of the enumeration literals. */ 1.1.1.5 root 4616: 1.1 root 4617: /* If all values were found as case labels, make one of them the default 4618: label. Thus, this switch will never fall through. We arbitrarily pick 4619: the last one to make the default since this is likely the most 4620: efficient choice. */ 4621: 4622: if (all_values) 4623: { 4624: for (l = &case_stack->data.case_stmt.case_list; 4625: (*l)->right != 0; 4626: l = &(*l)->right) 4627: ; 4628: 4629: case_stack->data.case_stmt.default_label = (*l)->code_label; 4630: *l = 0; 4631: } 1.1.1.5 root 4632: #endif /* 0 */ 1.1 root 4633: } 1.1.1.6 root 4634: 4635: 4636: /* Check that all enumeration literals are covered by the case 4637: expressions of a switch. Also warn if there are any cases 4638: that are not elements of the enumerated type. */ 1.1.1.7 root 4639: 4640: static void 1.1.1.6 root 4641: bc_check_for_full_enumeration_handling (type) 4642: tree type; 4643: { 4644: struct nesting *thiscase = case_stack; 4645: struct case_node *c; 4646: tree e; 4647: 4648: /* Check for enums not handled. */ 4649: for (e = TYPE_VALUES (type); e; e = TREE_CHAIN (e)) 4650: { 4651: for (c = thiscase->data.case_stmt.case_list->left; 4652: c && tree_int_cst_lt (c->high, TREE_VALUE (e)); 4653: c = c->left) 4654: ; 4655: if (! (c && tree_int_cst_equal (c->low, TREE_VALUE (e)))) 4656: warning ("enumerated value `%s' not handled in switch", 4657: IDENTIFIER_POINTER (TREE_PURPOSE (e))); 4658: } 4659: 4660: /* Check for cases not in the enumeration. */ 4661: for (c = thiscase->data.case_stmt.case_list->left; c; c = c->left) 4662: { 4663: for (e = TYPE_VALUES (type); 4664: e && !tree_int_cst_equal (c->low, TREE_VALUE (e)); 4665: e = TREE_CHAIN (e)) 4666: ; 4667: if (! e) 4668: warning ("case value `%d' not in enumerated type `%s'", 4669: TREE_INT_CST_LOW (c->low), 4670: IDENTIFIER_POINTER (TREE_CODE (TYPE_NAME (type)) == IDENTIFIER_NODE 4671: ? TYPE_NAME (type) 4672: : DECL_NAME (TYPE_NAME (type)))); 4673: } 4674: } 1.1 root 4675: 4676: /* Terminate a case (Pascal) or switch (C) statement 1.1.1.4 root 4677: in which ORIG_INDEX is the expression to be tested. 1.1 root 4678: Generate the code to test it and jump to the right place. */ 4679: 4680: void 4681: expand_end_case (orig_index) 4682: tree orig_index; 4683: { 1.1.1.6 root 4684: tree minval, maxval, range, orig_minval; 1.1 root 4685: rtx default_label = 0; 4686: register struct case_node *n; 4687: int count; 4688: rtx index; 1.1.1.6 root 4689: rtx table_label; 1.1 root 4690: int ncases; 4691: rtx *labelvec; 4692: register int i; 4693: rtx before_case; 4694: register struct nesting *thiscase = case_stack; 1.1.1.7 root 4695: tree index_expr, index_type; 1.1.1.6 root 4696: int unsignedp; 4697: 4698: if (output_bytecode) 4699: { 4700: bc_expand_end_case (orig_index); 4701: return; 4702: } 4703: 4704: table_label = gen_label_rtx (); 4705: index_expr = thiscase->data.case_stmt.index_expr; 1.1.1.7 root 4706: index_type = TREE_TYPE (index_expr); 4707: unsignedp = TREE_UNSIGNED (index_type); 1.1 root 4708: 4709: do_pending_stack_adjust (); 4710: 4711: /* An ERROR_MARK occurs for various reasons including invalid data type. */ 1.1.1.7 root 4712: if (index_type != error_mark_node) 1.1 root 4713: { 4714: /* If switch expression was an enumerated type, check that all 4715: enumeration literals are covered by the cases. 4716: No sense trying this if there's a default case, however. */ 4717: 4718: if (!thiscase->data.case_stmt.default_label 4719: && TREE_CODE (TREE_TYPE (orig_index)) == ENUMERAL_TYPE 4720: && TREE_CODE (index_expr) != INTEGER_CST) 4721: check_for_full_enumeration_handling (TREE_TYPE (orig_index)); 4722: 4723: /* If this is the first label, warn if any insns have been emitted. */ 4724: if (thiscase->data.case_stmt.seenlabel == 0) 4725: { 4726: rtx insn; 4727: for (insn = get_last_insn (); 4728: insn != case_stack->data.case_stmt.start; 4729: insn = PREV_INSN (insn)) 4730: if (GET_CODE (insn) != NOTE 4731: && (GET_CODE (insn) != INSN || GET_CODE (PATTERN (insn))!= USE)) 4732: { 4733: warning ("unreachable code at beginning of %s", 4734: case_stack->data.case_stmt.printname); 4735: break; 4736: } 4737: } 4738: 4739: /* If we don't have a default-label, create one here, 4740: after the body of the switch. */ 4741: if (thiscase->data.case_stmt.default_label == 0) 4742: { 4743: thiscase->data.case_stmt.default_label 4744: = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); 4745: expand_label (thiscase->data.case_stmt.default_label); 4746: } 4747: default_label = label_rtx (thiscase->data.case_stmt.default_label); 4748: 4749: before_case = get_last_insn (); 4750: 4751: /* Simplify the case-list before we count it. */ 4752: group_case_nodes (thiscase->data.case_stmt.case_list); 4753: 4754: /* Get upper and lower bounds of case values. 4755: Also convert all the case values to the index expr's data type. */ 4756: 4757: count = 0; 4758: for (n = thiscase->data.case_stmt.case_list; n; n = n->right) 4759: { 4760: /* Check low and high label values are integers. */ 4761: if (TREE_CODE (n->low) != INTEGER_CST) 4762: abort (); 4763: if (TREE_CODE (n->high) != INTEGER_CST) 4764: abort (); 4765: 1.1.1.7 root 4766: n->low = convert (index_type, n->low); 4767: n->high = convert (index_type, n->high); 1.1 root 4768: 4769: /* Count the elements and track the largest and smallest 4770: of them (treating them as signed even if they are not). */ 4771: if (count++ == 0) 4772: { 4773: minval = n->low; 4774: maxval = n->high; 4775: } 4776: else 4777: { 4778: if (INT_CST_LT (n->low, minval)) 4779: minval = n->low; 4780: if (INT_CST_LT (maxval, n->high)) 4781: maxval = n->high; 4782: } 4783: /* A range counts double, since it requires two compares. */ 4784: if (! tree_int_cst_equal (n->low, n->high)) 4785: count++; 4786: } 4787: 1.1.1.6 root 4788: orig_minval = minval; 4789: 1.1 root 4790: /* Compute span of values. */ 4791: if (count != 0) 1.1.1.7 root 4792: range = fold (build (MINUS_EXPR, index_type, maxval, minval)); 1.1 root 4793: 1.1.1.7 root 4794: if (count == 0) 1.1 root 4795: { 4796: expand_expr (index_expr, const0_rtx, VOIDmode, 0); 4797: emit_queue (); 4798: emit_jump (default_label); 4799: } 1.1.1.6 root 4800: 1.1 root 4801: /* If range of values is much bigger than number of values, 4802: make a sequence of conditional branches instead of a dispatch. 4803: If the switch-index is a constant, do it this way 4804: because we can optimize it. */ 1.1.1.4 root 4805: 4806: #ifndef CASE_VALUES_THRESHOLD 1.1 root 4807: #ifdef HAVE_casesi 1.1.1.4 root 4808: #define CASE_VALUES_THRESHOLD (HAVE_casesi ? 4 : 5) 1.1 root 4809: #else 1.1.1.4 root 4810: /* If machine does not have a case insn that compares the 4811: bounds, this means extra overhead for dispatch tables 4812: which raises the threshold for using them. */ 4813: #define CASE_VALUES_THRESHOLD 5 4814: #endif /* HAVE_casesi */ 4815: #endif /* CASE_VALUES_THRESHOLD */ 4816: 4817: else if (TREE_INT_CST_HIGH (range) != 0 4818: || count < CASE_VALUES_THRESHOLD 4819: || ((unsigned HOST_WIDE_INT) (TREE_INT_CST_LOW (range)) 4820: > 10 * count) 1.1 root 4821: || TREE_CODE (index_expr) == INTEGER_CST 1.1.1.2 root 4822: /* These will reduce to a constant. */ 1.1 root 4823: || (TREE_CODE (index_expr) == CALL_EXPR 4824: && TREE_CODE (TREE_OPERAND (index_expr, 0)) == ADDR_EXPR 4825: && TREE_CODE (TREE_OPERAND (TREE_OPERAND (index_expr, 0), 0)) == FUNCTION_DECL 1.1.1.2 root 4826: && DECL_FUNCTION_CODE (TREE_OPERAND (TREE_OPERAND (index_expr, 0), 0)) == BUILT_IN_CLASSIFY_TYPE) 4827: || (TREE_CODE (index_expr) == COMPOUND_EXPR 4828: && TREE_CODE (TREE_OPERAND (index_expr, 1)) == INTEGER_CST)) 1.1 root 4829: { 1.1.1.4 root 4830: index = expand_expr (index_expr, NULL_RTX, VOIDmode, 0); 1.1 root 4831: 4832: /* If the index is a short or char that we do not have 4833: an insn to handle comparisons directly, convert it to 4834: a full integer now, rather than letting each comparison 4835: generate the conversion. */ 4836: 4837: if (GET_MODE_CLASS (GET_MODE (index)) == MODE_INT 4838: && (cmp_optab->handlers[(int) GET_MODE(index)].insn_code 4839: == CODE_FOR_nothing)) 4840: { 4841: enum machine_mode wider_mode; 4842: for (wider_mode = GET_MODE (index); wider_mode != VOIDmode; 4843: wider_mode = GET_MODE_WIDER_MODE (wider_mode)) 4844: if (cmp_optab->handlers[(int) wider_mode].insn_code 4845: != CODE_FOR_nothing) 4846: { 4847: index = convert_to_mode (wider_mode, index, unsignedp); 4848: break; 4849: } 4850: } 4851: 4852: emit_queue (); 4853: do_pending_stack_adjust (); 4854: 4855: index = protect_from_queue (index, 0); 4856: if (GET_CODE (index) == MEM) 4857: index = copy_to_reg (index); 4858: if (GET_CODE (index) == CONST_INT 4859: || TREE_CODE (index_expr) == INTEGER_CST) 4860: { 4861: /* Make a tree node with the proper constant value 4862: if we don't already have one. */ 4863: if (TREE_CODE (index_expr) != INTEGER_CST) 4864: { 4865: index_expr 4866: = build_int_2 (INTVAL (index), 1.1.1.7 root 4867: unsignedp || INTVAL (index) >= 0 ? 0 : -1); 4868: index_expr = convert (index_type, index_expr); 1.1 root 4869: } 4870: 4871: /* For constant index expressions we need only 4872: issue a unconditional branch to the appropriate 4873: target code. The job of removing any unreachable 4874: code is left to the optimisation phase if the 4875: "-O" option is specified. */ 1.1.1.7 root 4876: for (n = thiscase->data.case_stmt.case_list; n; n = n->right) 4877: if (! tree_int_cst_lt (index_expr, n->low) 4878: && ! tree_int_cst_lt (n->high, index_expr)) 4879: break; 4880: 1.1 root 4881: if (n) 4882: emit_jump (label_rtx (n->code_label)); 4883: else 4884: emit_jump (default_label); 4885: } 4886: else 4887: { 4888: /* If the index expression is not constant we generate 4889: a binary decision tree to select the appropriate 4890: target code. This is done as follows: 4891: 4892: The list of cases is rearranged into a binary tree, 4893: nearly optimal assuming equal probability for each case. 4894: 4895: The tree is transformed into RTL, eliminating 4896: redundant test conditions at the same time. 4897: 4898: If program flow could reach the end of the 4899: decision tree an unconditional jump to the 4900: default code is emitted. */ 4901: 4902: use_cost_table 4903: = (TREE_CODE (TREE_TYPE (orig_index)) != ENUMERAL_TYPE 4904: && estimate_case_costs (thiscase->data.case_stmt.case_list)); 1.1.1.4 root 4905: balance_case_nodes (&thiscase->data.case_stmt.case_list, 4906: NULL_PTR); 1.1 root 4907: emit_case_nodes (index, thiscase->data.case_stmt.case_list, 1.1.1.7 root 4908: default_label, index_type); 1.1 root 4909: emit_jump_if_reachable (default_label); 4910: } 4911: } 4912: else 4913: { 4914: int win = 0; 4915: #ifdef HAVE_casesi 4916: if (HAVE_casesi) 4917: { 1.1.1.3 root 4918: enum machine_mode index_mode = SImode; 4919: int index_bits = GET_MODE_BITSIZE (index_mode); 1.1.1.7 root 4920: rtx op1, op2; 4921: enum machine_mode op_mode; 1.1.1.3 root 4922: 1.1 root 4923: /* Convert the index to SImode. */ 1.1.1.7 root 4924: if (GET_MODE_BITSIZE (TYPE_MODE (index_type)) 1.1.1.3 root 4925: > GET_MODE_BITSIZE (index_mode)) 1.1 root 4926: { 1.1.1.7 root 4927: enum machine_mode omode = TYPE_MODE (index_type); 1.1.1.4 root 4928: rtx rangertx = expand_expr (range, NULL_RTX, VOIDmode, 0); 1.1.1.3 root 4929: 4930: /* We must handle the endpoints in the original mode. */ 1.1.1.7 root 4931: index_expr = build (MINUS_EXPR, index_type, 1.1 root 4932: index_expr, minval); 4933: minval = integer_zero_node; 1.1.1.4 root 4934: index = expand_expr (index_expr, NULL_RTX, VOIDmode, 0); 1.1.1.6 root 4935: emit_cmp_insn (rangertx, index, LTU, NULL_RTX, omode, 1, 0); 1.1.1.3 root 4936: emit_jump_insn (gen_bltu (default_label)); 4937: /* Now we can safely truncate. */ 4938: index = convert_to_mode (index_mode, index, 0); 4939: } 4940: else 4941: { 1.1.1.7 root 4942: if (TYPE_MODE (index_type) != index_mode) 4943: { 4944: index_expr = convert (type_for_size (index_bits, 0), 4945: index_expr); 4946: index_type = TREE_TYPE (index_expr); 4947: } 4948: 1.1.1.4 root 4949: index = expand_expr (index_expr, NULL_RTX, VOIDmode, 0); 1.1 root 4950: } 4951: emit_queue (); 4952: index = protect_from_queue (index, 0); 4953: do_pending_stack_adjust (); 4954: 1.1.1.7 root 4955: op_mode = insn_operand_mode[(int)CODE_FOR_casesi][0]; 4956: if (! (*insn_operand_predicate[(int)CODE_FOR_casesi][0]) 4957: (index, op_mode)) 4958: index = copy_to_mode_reg (op_mode, index); 4959: 4960: op1 = expand_expr (minval, NULL_RTX, VOIDmode, 0); 4961: 4962: op_mode = insn_operand_mode[(int)CODE_FOR_casesi][1]; 4963: if (! (*insn_operand_predicate[(int)CODE_FOR_casesi][1]) 4964: (op1, op_mode)) 4965: op1 = copy_to_mode_reg (op_mode, op1); 4966: 4967: op2 = expand_expr (range, NULL_RTX, VOIDmode, 0); 4968: 4969: op_mode = insn_operand_mode[(int)CODE_FOR_casesi][2]; 4970: if (! (*insn_operand_predicate[(int)CODE_FOR_casesi][2]) 4971: (op2, op_mode)) 4972: op2 = copy_to_mode_reg (op_mode, op2); 4973: 4974: emit_jump_insn (gen_casesi (index, op1, op2, 1.1 root 4975: table_label, default_label)); 4976: win = 1; 4977: } 4978: #endif 4979: #ifdef HAVE_tablejump 4980: if (! win && HAVE_tablejump) 4981: { 4982: index_expr = convert (thiscase->data.case_stmt.nominal_type, 1.1.1.7 root 4983: fold (build (MINUS_EXPR, index_type, 1.1.1.2 root 4984: index_expr, minval))); 1.1.1.7 root 4985: index_type = TREE_TYPE (index_expr); 1.1.1.4 root 4986: index = expand_expr (index_expr, NULL_RTX, VOIDmode, 0); 1.1 root 4987: emit_queue (); 4988: index = protect_from_queue (index, 0); 4989: do_pending_stack_adjust (); 4990: 1.1.1.7 root 4991: do_tablejump (index, TYPE_MODE (index_type), 1.1.1.4 root 4992: expand_expr (range, NULL_RTX, VOIDmode, 0), 1.1 root 4993: table_label, default_label); 4994: win = 1; 4995: } 4996: #endif 4997: if (! win) 4998: abort (); 4999: 5000: /* Get table of labels to jump to, in order of case index. */ 5001: 5002: ncases = TREE_INT_CST_LOW (range) + 1; 5003: labelvec = (rtx *) alloca (ncases * sizeof (rtx)); 1.1.1.7 root 5004: bzero ((char *) labelvec, ncases * sizeof (rtx)); 1.1 root 5005: 5006: for (n = thiscase->data.case_stmt.case_list; n; n = n->right) 5007: { 1.1.1.4 root 5008: register HOST_WIDE_INT i 1.1.1.6 root 5009: = TREE_INT_CST_LOW (n->low) - TREE_INT_CST_LOW (orig_minval); 1.1 root 5010: 5011: while (1) 5012: { 5013: labelvec[i] 5014: = gen_rtx (LABEL_REF, Pmode, label_rtx (n->code_label)); 1.1.1.6 root 5015: if (i + TREE_INT_CST_LOW (orig_minval) 1.1 root 5016: == TREE_INT_CST_LOW (n->high)) 5017: break; 5018: i++; 5019: } 5020: } 5021: 5022: /* Fill in the gaps with the default. */ 5023: for (i = 0; i < ncases; i++) 5024: if (labelvec[i] == 0) 5025: labelvec[i] = gen_rtx (LABEL_REF, Pmode, default_label); 5026: 5027: /* Output the table */ 5028: emit_label (table_label); 5029: 5030: /* This would be a lot nicer if CASE_VECTOR_PC_RELATIVE 1.1.1.4 root 5031: were an expression, instead of an #ifdef/#ifndef. */ 1.1 root 5032: if ( 5033: #ifdef CASE_VECTOR_PC_RELATIVE 5034: 1 || 5035: #endif 5036: flag_pic) 5037: emit_jump_insn (gen_rtx (ADDR_DIFF_VEC, CASE_VECTOR_MODE, 5038: gen_rtx (LABEL_REF, Pmode, table_label), 5039: gen_rtvec_v (ncases, labelvec))); 5040: else 5041: emit_jump_insn (gen_rtx (ADDR_VEC, CASE_VECTOR_MODE, 5042: gen_rtvec_v (ncases, labelvec))); 5043: 5044: /* If the case insn drops through the table, 5045: after the table we must jump to the default-label. 5046: Otherwise record no drop-through after the table. */ 5047: #ifdef CASE_DROPS_THROUGH 5048: emit_jump (default_label); 5049: #else 5050: emit_barrier (); 5051: #endif 5052: } 5053: 1.1.1.3 root 5054: before_case = squeeze_notes (NEXT_INSN (before_case), get_last_insn ()); 5055: reorder_insns (before_case, get_last_insn (), 1.1 root 5056: thiscase->data.case_stmt.start); 5057: } 1.1.1.7 root 5058: 1.1 root 5059: if (thiscase->exit_label) 5060: emit_label (thiscase->exit_label); 5061: 5062: POPSTACK (case_stack); 5063: 5064: free_temp_slots (); 5065: } 5066: 1.1.1.6 root 5067: 5068: /* Terminate a case statement. EXPR is the original index 5069: expression. */ 1.1.1.7 root 5070: 5071: static void 1.1.1.6 root 5072: bc_expand_end_case (expr) 5073: tree expr; 5074: { 5075: struct nesting *thiscase = case_stack; 5076: enum bytecode_opcode opcode; 5077: struct bc_label *jump_label; 5078: struct case_node *c; 5079: 5080: bc_emit_bytecode (jump); 5081: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (thiscase->exit_label)); 5082: 5083: #ifdef DEBUG_PRINT_CODE 5084: fputc ('\n', stderr); 5085: #endif 5086: 5087: /* Now that the size of the jump table is known, emit the actual 5088: indexed jump instruction. */ 5089: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thiscase->data.case_stmt.skip_label)); 5090: 5091: opcode = TYPE_MODE (thiscase->data.case_stmt.nominal_type) == SImode 5092: ? TREE_UNSIGNED (thiscase->data.case_stmt.nominal_type) ? caseSU : caseSI 5093: : TREE_UNSIGNED (thiscase->data.case_stmt.nominal_type) ? caseDU : caseDI; 5094: 5095: bc_emit_bytecode (opcode); 5096: 5097: /* Now emit the case instructions literal arguments, in order. 5098: In addition to the value on the stack, it uses: 5099: 1. The address of the jump table. 5100: 2. The size of the jump table. 5101: 3. The default label. */ 5102: 5103: jump_label = bc_get_bytecode_label (); 5104: bc_emit_bytecode_labelref (jump_label); 5105: bc_emit_bytecode_const ((char *) &thiscase->data.case_stmt.num_ranges, 5106: sizeof thiscase->data.case_stmt.num_ranges); 5107: 5108: if (thiscase->data.case_stmt.default_label) 5109: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (DECL_RTL (thiscase->data.case_stmt.default_label))); 5110: else 5111: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (thiscase->exit_label)); 5112: 5113: /* Output the jump table. */ 5114: 5115: bc_align_bytecode (3 /* PTR_ALIGN */); 5116: bc_emit_bytecode_labeldef (jump_label); 5117: 5118: if (TYPE_MODE (thiscase->data.case_stmt.nominal_type) == SImode) 5119: for (c = thiscase->data.case_stmt.case_list->left; c; c = c->left) 5120: { 5121: opcode = TREE_INT_CST_LOW (c->low); 5122: bc_emit_bytecode_const ((char *) &opcode, sizeof opcode); 5123: 5124: opcode = TREE_INT_CST_LOW (c->high); 5125: bc_emit_bytecode_const ((char *) &opcode, sizeof opcode); 5126: 5127: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (DECL_RTL (c->code_label))); 5128: } 5129: else 5130: if (TYPE_MODE (thiscase->data.case_stmt.nominal_type) == DImode) 5131: for (c = thiscase->data.case_stmt.case_list->left; c; c = c->left) 5132: { 5133: bc_emit_bytecode_DI_const (c->low); 5134: bc_emit_bytecode_DI_const (c->high); 5135: 5136: bc_emit_bytecode_labelref (BYTECODE_BC_LABEL (DECL_RTL (c->code_label))); 5137: } 5138: else 5139: /* Bad mode */ 5140: abort (); 5141: 5142: 5143: bc_emit_bytecode_labeldef (BYTECODE_BC_LABEL (thiscase->exit_label)); 5144: 5145: /* Possibly issue enumeration warnings. */ 5146: 5147: if (!thiscase->data.case_stmt.default_label 5148: && TREE_CODE (TREE_TYPE (expr)) == ENUMERAL_TYPE 5149: && TREE_CODE (expr) != INTEGER_CST 5150: && warn_switch) 5151: check_for_full_enumeration_handling (TREE_TYPE (expr)); 5152: 5153: 5154: #ifdef DEBUG_PRINT_CODE 5155: fputc ('\n', stderr); 5156: #endif 5157: 5158: POPSTACK (case_stack); 5159: } 5160: 5161: 5162: /* Return unique bytecode ID. */ 1.1.1.7 root 5163: 1.1.1.6 root 5164: int 5165: bc_new_uid () 5166: { 5167: static int bc_uid = 0; 5168: 5169: return (++bc_uid); 5170: } 5171: 1.1 root 5172: /* Generate code to jump to LABEL if OP1 and OP2 are equal. */ 5173: 5174: static void 5175: do_jump_if_equal (op1, op2, label, unsignedp) 5176: rtx op1, op2, label; 5177: int unsignedp; 5178: { 5179: if (GET_CODE (op1) == CONST_INT 5180: && GET_CODE (op2) == CONST_INT) 5181: { 5182: if (INTVAL (op1) == INTVAL (op2)) 5183: emit_jump (label); 5184: } 5185: else 5186: { 5187: enum machine_mode mode = GET_MODE (op1); 5188: if (mode == VOIDmode) 5189: mode = GET_MODE (op2); 1.1.1.4 root 5190: emit_cmp_insn (op1, op2, EQ, NULL_RTX, mode, unsignedp, 0); 1.1 root 5191: emit_jump_insn (gen_beq (label)); 5192: } 5193: } 5194: 5195: /* Not all case values are encountered equally. This function 5196: uses a heuristic to weight case labels, in cases where that 5197: looks like a reasonable thing to do. 5198: 5199: Right now, all we try to guess is text, and we establish the 5200: following weights: 5201: 5202: chars above space: 16 5203: digits: 16 5204: default: 12 5205: space, punct: 8 5206: tab: 4 5207: newline: 2 5208: other "\" chars: 1 5209: remaining chars: 0 5210: 5211: If we find any cases in the switch that are not either -1 or in the range 5212: of valid ASCII characters, or are control characters other than those 5213: commonly used with "\", don't treat this switch scanning text. 5214: 5215: Return 1 if these nodes are suitable for cost estimation, otherwise 5216: return 0. */ 5217: 5218: static int 5219: estimate_case_costs (node) 5220: case_node_ptr node; 5221: { 5222: tree min_ascii = build_int_2 (-1, -1); 5223: tree max_ascii = convert (TREE_TYPE (node->high), build_int_2 (127, 0)); 5224: case_node_ptr n; 5225: int i; 5226: 5227: /* If we haven't already made the cost table, make it now. Note that the 5228: lower bound of the table is -1, not zero. */ 5229: 5230: if (cost_table == NULL) 5231: { 5232: cost_table = ((short *) xmalloc (129 * sizeof (short))) + 1; 1.1.1.7 root 5233: bzero ((char *) (cost_table - 1), 129 * sizeof (short)); 1.1 root 5234: 5235: for (i = 0; i < 128; i++) 5236: { 5237: if (isalnum (i)) 5238: cost_table[i] = 16; 5239: else if (ispunct (i)) 5240: cost_table[i] = 8; 5241: else if (iscntrl (i)) 5242: cost_table[i] = -1; 5243: } 5244: 5245: cost_table[' '] = 8; 5246: cost_table['\t'] = 4; 5247: cost_table['\0'] = 4; 5248: cost_table['\n'] = 2; 5249: cost_table['\f'] = 1; 5250: cost_table['\v'] = 1; 5251: cost_table['\b'] = 1; 5252: } 5253: 5254: /* See if all the case expressions look like text. It is text if the 5255: constant is >= -1 and the highest constant is <= 127. Do all comparisons 5256: as signed arithmetic since we don't want to ever access cost_table with a 5257: value less than -1. Also check that none of the constants in a range 5258: are strange control characters. */ 5259: 5260: for (n = node; n; n = n->right) 5261: { 5262: if ((INT_CST_LT (n->low, min_ascii)) || INT_CST_LT (max_ascii, n->high)) 5263: return 0; 5264: 5265: for (i = TREE_INT_CST_LOW (n->low); i <= TREE_INT_CST_LOW (n->high); i++) 5266: if (cost_table[i] < 0) 5267: return 0; 5268: } 5269: 5270: /* All interesting values are within the range of interesting 5271: ASCII characters. */ 5272: return 1; 5273: } 5274: 5275: /* Scan an ordered list of case nodes 5276: combining those with consecutive values or ranges. 5277: 5278: Eg. three separate entries 1: 2: 3: become one entry 1..3: */ 5279: 5280: static void 5281: group_case_nodes (head) 5282: case_node_ptr head; 5283: { 5284: case_node_ptr node = head; 5285: 5286: while (node) 5287: { 5288: rtx lb = next_real_insn (label_rtx (node->code_label)); 5289: case_node_ptr np = node; 5290: 5291: /* Try to group the successors of NODE with NODE. */ 5292: while (((np = np->right) != 0) 5293: /* Do they jump to the same place? */ 5294: && next_real_insn (label_rtx (np->code_label)) == lb 5295: /* Are their ranges consecutive? */ 5296: && tree_int_cst_equal (np->low, 5297: fold (build (PLUS_EXPR, 5298: TREE_TYPE (node->high), 5299: node->high, 5300: integer_one_node))) 5301: /* An overflow is not consecutive. */ 5302: && tree_int_cst_lt (node->high, 5303: fold (build (PLUS_EXPR, 5304: TREE_TYPE (node->high), 5305: node->high, 5306: integer_one_node)))) 5307: { 5308: node->high = np->high; 5309: } 5310: /* NP is the first node after NODE which can't be grouped with it. 5311: Delete the nodes in between, and move on to that node. */ 5312: node->right = np; 5313: node = np; 5314: } 5315: } 5316: 5317: /* Take an ordered list of case nodes 5318: and transform them into a near optimal binary tree, 1.1.1.3 root 5319: on the assumption that any target code selection value is as 1.1 root 5320: likely as any other. 5321: 5322: The transformation is performed by splitting the ordered 5323: list into two equal sections plus a pivot. The parts are 5324: then attached to the pivot as left and right branches. Each 5325: branch is is then transformed recursively. */ 5326: 5327: static void 5328: balance_case_nodes (head, parent) 5329: case_node_ptr *head; 5330: case_node_ptr parent; 5331: { 5332: register case_node_ptr np; 5333: 5334: np = *head; 5335: if (np) 5336: { 5337: int cost = 0; 5338: int i = 0; 5339: int ranges = 0; 5340: register case_node_ptr *npp; 5341: case_node_ptr left; 5342: 5343: /* Count the number of entries on branch. Also count the ranges. */ 5344: 5345: while (np) 5346: { 5347: if (!tree_int_cst_equal (np->low, np->high)) 5348: { 5349: ranges++; 5350: if (use_cost_table) 5351: cost += cost_table[TREE_INT_CST_LOW (np->high)]; 5352: } 5353: 5354: if (use_cost_table) 5355: cost += cost_table[TREE_INT_CST_LOW (np->low)]; 5356: 5357: i++; 5358: np = np->right; 5359: } 5360: 5361: if (i > 2) 5362: { 5363: /* Split this list if it is long enough for that to help. */ 5364: npp = head; 5365: left = *npp; 5366: if (use_cost_table) 5367: { 5368: /* Find the place in the list that bisects the list's total cost, 5369: Here I gets half the total cost. */ 5370: int n_moved = 0; 5371: i = (cost + 1) / 2; 5372: while (1) 5373: { 5374: /* Skip nodes while their cost does not reach that amount. */ 5375: if (!tree_int_cst_equal ((*npp)->low, (*npp)->high)) 5376: i -= cost_table[TREE_INT_CST_LOW ((*npp)->high)]; 5377: i -= cost_table[TREE_INT_CST_LOW ((*npp)->low)]; 5378: if (i <= 0) 5379: break; 5380: npp = &(*npp)->right; 5381: n_moved += 1; 5382: } 5383: if (n_moved == 0) 5384: { 5385: /* Leave this branch lopsided, but optimize left-hand 5386: side and fill in `parent' fields for right-hand side. */ 5387: np = *head; 5388: np->parent = parent; 5389: balance_case_nodes (&np->left, np); 5390: for (; np->right; np = np->right) 5391: np->right->parent = np; 5392: return; 5393: } 5394: } 5395: /* If there are just three nodes, split at the middle one. */ 5396: else if (i == 3) 5397: npp = &(*npp)->right; 5398: else 5399: { 5400: /* Find the place in the list that bisects the list's total cost, 5401: where ranges count as 2. 5402: Here I gets half the total cost. */ 5403: i = (i + ranges + 1) / 2; 5404: while (1) 5405: { 5406: /* Skip nodes while their cost does not reach that amount. */ 5407: if (!tree_int_cst_equal ((*npp)->low, (*npp)->high)) 5408: i--; 5409: i--; 5410: if (i <= 0) 5411: break; 5412: npp = &(*npp)->right; 5413: } 5414: } 5415: *head = np = *npp; 5416: *npp = 0; 5417: np->parent = parent; 5418: np->left = left; 5419: 5420: /* Optimize each of the two split parts. */ 5421: balance_case_nodes (&np->left, np); 5422: balance_case_nodes (&np->right, np); 5423: } 5424: else 5425: { 5426: /* Else leave this branch as one level, 5427: but fill in `parent' fields. */ 5428: np = *head; 5429: np->parent = parent; 5430: for (; np->right; np = np->right) 5431: np->right->parent = np; 5432: } 5433: } 5434: } 5435: 5436: /* Search the parent sections of the case node tree 5437: to see if a test for the lower bound of NODE would be redundant. 5438: INDEX_TYPE is the type of the index expression. 5439: 5440: The instructions to generate the case decision tree are 5441: output in the same order as nodes are processed so it is 5442: known that if a parent node checks the range of the current 5443: node minus one that the current node is bounded at its lower 5444: span. Thus the test would be redundant. */ 5445: 5446: static int 5447: node_has_low_bound (node, index_type) 5448: case_node_ptr node; 5449: tree index_type; 5450: { 5451: tree low_minus_one; 5452: case_node_ptr pnode; 5453: 5454: /* If the lower bound of this node is the lowest value in the index type, 5455: we need not test it. */ 5456: 5457: if (tree_int_cst_equal (node->low, TYPE_MIN_VALUE (index_type))) 5458: return 1; 5459: 5460: /* If this node has a left branch, the value at the left must be less 5461: than that at this node, so it cannot be bounded at the bottom and 5462: we need not bother testing any further. */ 5463: 5464: if (node->left) 5465: return 0; 5466: 5467: low_minus_one = fold (build (MINUS_EXPR, TREE_TYPE (node->low), 5468: node->low, integer_one_node)); 5469: 5470: /* If the subtraction above overflowed, we can't verify anything. 5471: Otherwise, look for a parent that tests our value - 1. */ 5472: 5473: if (! tree_int_cst_lt (low_minus_one, node->low)) 5474: return 0; 5475: 5476: for (pnode = node->parent; pnode; pnode = pnode->parent) 5477: if (tree_int_cst_equal (low_minus_one, pnode->high)) 5478: return 1; 5479: 5480: return 0; 5481: } 5482: 5483: /* Search the parent sections of the case node tree 5484: to see if a test for the upper bound of NODE would be redundant. 5485: INDEX_TYPE is the type of the index expression. 5486: 5487: The instructions to generate the case decision tree are 5488: output in the same order as nodes are processed so it is 5489: known that if a parent node checks the range of the current 5490: node plus one that the current node is bounded at its upper 5491: span. Thus the test would be redundant. */ 5492: 5493: static int 5494: node_has_high_bound (node, index_type) 5495: case_node_ptr node; 5496: tree index_type; 5497: { 5498: tree high_plus_one; 5499: case_node_ptr pnode; 5500: 5501: /* If the upper bound of this node is the highest value in the type 5502: of the index expression, we need not test against it. */ 5503: 5504: if (tree_int_cst_equal (node->high, TYPE_MAX_VALUE (index_type))) 5505: return 1; 5506: 5507: /* If this node has a right branch, the value at the right must be greater 5508: than that at this node, so it cannot be bounded at the top and 5509: we need not bother testing any further. */ 5510: 5511: if (node->right) 5512: return 0; 5513: 5514: high_plus_one = fold (build (PLUS_EXPR, TREE_TYPE (node->high), 5515: node->high, integer_one_node)); 5516: 5517: /* If the addition above overflowed, we can't verify anything. 5518: Otherwise, look for a parent that tests our value + 1. */ 5519: 5520: if (! tree_int_cst_lt (node->high, high_plus_one)) 5521: return 0; 5522: 5523: for (pnode = node->parent; pnode; pnode = pnode->parent) 5524: if (tree_int_cst_equal (high_plus_one, pnode->low)) 5525: return 1; 5526: 5527: return 0; 5528: } 5529: 5530: /* Search the parent sections of the 5531: case node tree to see if both tests for the upper and lower 5532: bounds of NODE would be redundant. */ 5533: 5534: static int 5535: node_is_bounded (node, index_type) 5536: case_node_ptr node; 5537: tree index_type; 5538: { 5539: return (node_has_low_bound (node, index_type) 5540: && node_has_high_bound (node, index_type)); 5541: } 5542: 5543: /* Emit an unconditional jump to LABEL unless it would be dead code. */ 5544: 5545: static void 5546: emit_jump_if_reachable (label) 5547: rtx label; 5548: { 5549: if (GET_CODE (get_last_insn ()) != BARRIER) 5550: emit_jump (label); 5551: } 5552: 5553: /* Emit step-by-step code to select a case for the value of INDEX. 5554: The thus generated decision tree follows the form of the 5555: case-node binary tree NODE, whose nodes represent test conditions. 5556: INDEX_TYPE is the type of the index of the switch. 5557: 5558: Care is taken to prune redundant tests from the decision tree 5559: by detecting any boundary conditions already checked by 5560: emitted rtx. (See node_has_high_bound, node_has_low_bound 5561: and node_is_bounded, above.) 5562: 5563: Where the test conditions can be shown to be redundant we emit 5564: an unconditional jump to the target code. As a further 5565: optimization, the subordinates of a tree node are examined to 5566: check for bounded nodes. In this case conditional and/or 5567: unconditional jumps as a result of the boundary check for the 5568: current node are arranged to target the subordinates associated 5569: code for out of bound conditions on the current node node. 5570: 1.1.1.4 root 5571: We can assume that when control reaches the code generated here, 1.1 root 5572: the index value has already been compared with the parents 5573: of this node, and determined to be on the same side of each parent 5574: as this node is. Thus, if this node tests for the value 51, 5575: and a parent tested for 52, we don't need to consider 5576: the possibility of a value greater than 51. If another parent 5577: tests for the value 50, then this node need not test anything. */ 5578: 5579: static void 5580: emit_case_nodes (index, node, default_label, index_type) 5581: rtx index; 5582: case_node_ptr node; 5583: rtx default_label; 5584: tree index_type; 5585: { 5586: /* If INDEX has an unsigned type, we must make unsigned branches. */ 5587: int unsignedp = TREE_UNSIGNED (index_type); 5588: typedef rtx rtx_function (); 5589: rtx_function *gen_bgt_pat = unsignedp ? gen_bgtu : gen_bgt; 5590: rtx_function *gen_bge_pat = unsignedp ? gen_bgeu : gen_bge; 5591: rtx_function *gen_blt_pat = unsignedp ? gen_bltu : gen_blt; 5592: rtx_function *gen_ble_pat = unsignedp ? gen_bleu : gen_ble; 5593: enum machine_mode mode = GET_MODE (index); 5594: 5595: /* See if our parents have already tested everything for us. 5596: If they have, emit an unconditional jump for this node. */ 5597: if (node_is_bounded (node, index_type)) 5598: emit_jump (label_rtx (node->code_label)); 5599: 5600: else if (tree_int_cst_equal (node->low, node->high)) 5601: { 5602: /* Node is single valued. First see if the index expression matches 5603: this node and then check our children, if any. */ 5604: 1.1.1.4 root 5605: do_jump_if_equal (index, expand_expr (node->low, NULL_RTX, VOIDmode, 0), 1.1 root 5606: label_rtx (node->code_label), unsignedp); 5607: 5608: if (node->right != 0 && node->left != 0) 5609: { 5610: /* This node has children on both sides. 5611: Dispatch to one side or the other 5612: by comparing the index value with this node's value. 5613: If one subtree is bounded, check that one first, 5614: so we can avoid real branches in the tree. */ 5615: 5616: if (node_is_bounded (node->right, index_type)) 5617: { 1.1.1.4 root 5618: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5619: VOIDmode, 0), 5620: GT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5621: 5622: emit_jump_insn ((*gen_bgt_pat) (label_rtx (node->right->code_label))); 5623: emit_case_nodes (index, node->left, default_label, index_type); 5624: } 5625: 5626: else if (node_is_bounded (node->left, index_type)) 5627: { 1.1.1.4 root 5628: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 1.1 root 5629: VOIDmode, 0), 1.1.1.4 root 5630: LT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5631: emit_jump_insn ((*gen_blt_pat) (label_rtx (node->left->code_label))); 5632: emit_case_nodes (index, node->right, default_label, index_type); 5633: } 5634: 5635: else 5636: { 5637: /* Neither node is bounded. First distinguish the two sides; 5638: then emit the code for one side at a time. */ 5639: 5640: tree test_label 5641: = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); 5642: 5643: /* See if the value is on the right. */ 1.1.1.4 root 5644: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 1.1 root 5645: VOIDmode, 0), 1.1.1.4 root 5646: GT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5647: emit_jump_insn ((*gen_bgt_pat) (label_rtx (test_label))); 5648: 5649: /* Value must be on the left. 5650: Handle the left-hand subtree. */ 5651: emit_case_nodes (index, node->left, default_label, index_type); 5652: /* If left-hand subtree does nothing, 5653: go to default. */ 5654: emit_jump_if_reachable (default_label); 5655: 5656: /* Code branches here for the right-hand subtree. */ 5657: expand_label (test_label); 5658: emit_case_nodes (index, node->right, default_label, index_type); 5659: } 5660: } 5661: 5662: else if (node->right != 0 && node->left == 0) 5663: { 5664: /* Here we have a right child but no left so we issue conditional 5665: branch to default and process the right child. 5666: 5667: Omit the conditional branch to default if we it avoid only one 5668: right child; it costs too much space to save so little time. */ 5669: 5670: if (node->right->right || node->right->left 5671: || !tree_int_cst_equal (node->right->low, node->right->high)) 5672: { 5673: if (!node_has_low_bound (node, index_type)) 5674: { 1.1.1.4 root 5675: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5676: VOIDmode, 0), 5677: LT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5678: emit_jump_insn ((*gen_blt_pat) (default_label)); 5679: } 5680: 5681: emit_case_nodes (index, node->right, default_label, index_type); 5682: } 5683: else 5684: /* We cannot process node->right normally 5685: since we haven't ruled out the numbers less than 5686: this node's value. So handle node->right explicitly. */ 5687: do_jump_if_equal (index, 1.1.1.4 root 5688: expand_expr (node->right->low, NULL_RTX, 5689: VOIDmode, 0), 1.1 root 5690: label_rtx (node->right->code_label), unsignedp); 5691: } 5692: 5693: else if (node->right == 0 && node->left != 0) 5694: { 5695: /* Just one subtree, on the left. */ 5696: 5697: #if 0 /* The following code and comment were formerly part 5698: of the condition here, but they didn't work 5699: and I don't understand what the idea was. -- rms. */ 5700: /* If our "most probable entry" is less probable 5701: than the default label, emit a jump to 5702: the default label using condition codes 5703: already lying around. With no right branch, 5704: a branch-greater-than will get us to the default 5705: label correctly. */ 5706: if (use_cost_table 5707: && cost_table[TREE_INT_CST_LOW (node->high)] < 12) 5708: ; 5709: #endif /* 0 */ 5710: if (node->left->left || node->left->right 5711: || !tree_int_cst_equal (node->left->low, node->left->high)) 5712: { 5713: if (!node_has_high_bound (node, index_type)) 5714: { 1.1.1.4 root 5715: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5716: VOIDmode, 0), 5717: GT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5718: emit_jump_insn ((*gen_bgt_pat) (default_label)); 5719: } 5720: 5721: emit_case_nodes (index, node->left, default_label, index_type); 5722: } 5723: else 5724: /* We cannot process node->left normally 5725: since we haven't ruled out the numbers less than 5726: this node's value. So handle node->left explicitly. */ 5727: do_jump_if_equal (index, 1.1.1.4 root 5728: expand_expr (node->left->low, NULL_RTX, 5729: VOIDmode, 0), 1.1 root 5730: label_rtx (node->left->code_label), unsignedp); 5731: } 5732: } 5733: else 5734: { 5735: /* Node is a range. These cases are very similar to those for a single 5736: value, except that we do not start by testing whether this node 5737: is the one to branch to. */ 5738: 5739: if (node->right != 0 && node->left != 0) 5740: { 5741: /* Node has subtrees on both sides. 5742: If the right-hand subtree is bounded, 5743: test for it first, since we can go straight there. 5744: Otherwise, we need to make a branch in the control structure, 5745: then handle the two subtrees. */ 5746: tree test_label = 0; 5747: 1.1.1.4 root 5748: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5749: VOIDmode, 0), 5750: GT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5751: 5752: if (node_is_bounded (node->right, index_type)) 5753: /* Right hand node is fully bounded so we can eliminate any 5754: testing and branch directly to the target code. */ 5755: emit_jump_insn ((*gen_bgt_pat) (label_rtx (node->right->code_label))); 5756: else 5757: { 5758: /* Right hand node requires testing. 5759: Branch to a label where we will handle it later. */ 5760: 5761: test_label = build_decl (LABEL_DECL, NULL_TREE, NULL_TREE); 5762: emit_jump_insn ((*gen_bgt_pat) (label_rtx (test_label))); 5763: } 5764: 5765: /* Value belongs to this node or to the left-hand subtree. */ 5766: 1.1.1.4 root 5767: emit_cmp_insn (index, expand_expr (node->low, NULL_RTX, VOIDmode, 0), 5768: GE, NULL_RTX, mode, unsignedp, 0); 1.1 root 5769: emit_jump_insn ((*gen_bge_pat) (label_rtx (node->code_label))); 5770: 5771: /* Handle the left-hand subtree. */ 5772: emit_case_nodes (index, node->left, default_label, index_type); 5773: 5774: /* If right node had to be handled later, do that now. */ 5775: 5776: if (test_label) 5777: { 5778: /* If the left-hand subtree fell through, 5779: don't let it fall into the right-hand subtree. */ 5780: emit_jump_if_reachable (default_label); 5781: 5782: expand_label (test_label); 5783: emit_case_nodes (index, node->right, default_label, index_type); 5784: } 5785: } 5786: 5787: else if (node->right != 0 && node->left == 0) 5788: { 5789: /* Deal with values to the left of this node, 5790: if they are possible. */ 5791: if (!node_has_low_bound (node, index_type)) 5792: { 1.1.1.4 root 5793: emit_cmp_insn (index, expand_expr (node->low, NULL_RTX, 5794: VOIDmode, 0), 5795: LT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5796: emit_jump_insn ((*gen_blt_pat) (default_label)); 5797: } 5798: 5799: /* Value belongs to this node or to the right-hand subtree. */ 5800: 1.1.1.4 root 5801: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5802: VOIDmode, 0), 5803: LE, NULL_RTX, mode, unsignedp, 0); 1.1 root 5804: emit_jump_insn ((*gen_ble_pat) (label_rtx (node->code_label))); 5805: 5806: emit_case_nodes (index, node->right, default_label, index_type); 5807: } 5808: 5809: else if (node->right == 0 && node->left != 0) 5810: { 5811: /* Deal with values to the right of this node, 5812: if they are possible. */ 5813: if (!node_has_high_bound (node, index_type)) 5814: { 1.1.1.4 root 5815: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5816: VOIDmode, 0), 5817: GT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5818: emit_jump_insn ((*gen_bgt_pat) (default_label)); 5819: } 5820: 5821: /* Value belongs to this node or to the left-hand subtree. */ 5822: 1.1.1.4 root 5823: emit_cmp_insn (index, expand_expr (node->low, NULL_RTX, VOIDmode, 0), 5824: GE, NULL_RTX, mode, unsignedp, 0); 1.1 root 5825: emit_jump_insn ((*gen_bge_pat) (label_rtx (node->code_label))); 5826: 5827: emit_case_nodes (index, node->left, default_label, index_type); 5828: } 5829: 5830: else 5831: { 5832: /* Node has no children so we check low and high bounds to remove 5833: redundant tests. Only one of the bounds can exist, 5834: since otherwise this node is bounded--a case tested already. */ 5835: 5836: if (!node_has_high_bound (node, index_type)) 5837: { 1.1.1.4 root 5838: emit_cmp_insn (index, expand_expr (node->high, NULL_RTX, 5839: VOIDmode, 0), 5840: GT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5841: emit_jump_insn ((*gen_bgt_pat) (default_label)); 5842: } 5843: 5844: if (!node_has_low_bound (node, index_type)) 5845: { 1.1.1.4 root 5846: emit_cmp_insn (index, expand_expr (node->low, NULL_RTX, 5847: VOIDmode, 0), 5848: LT, NULL_RTX, mode, unsignedp, 0); 1.1 root 5849: emit_jump_insn ((*gen_blt_pat) (default_label)); 5850: } 5851: 5852: emit_jump (label_rtx (node->code_label)); 5853: } 5854: } 5855: } 5856: 5857: /* These routines are used by the loop unrolling code. They copy BLOCK trees 5858: so that the debugging info will be correct for the unrolled loop. */ 5859: 1.1.1.4 root 5860: /* Indexed by block number, contains a pointer to the N'th block node. */ 1.1 root 5861: 1.1.1.4 root 5862: static tree *block_vector; 1.1 root 5863: 5864: void 1.1.1.4 root 5865: find_loop_tree_blocks () 1.1 root 5866: { 1.1.1.4 root 5867: tree block = DECL_INITIAL (current_function_decl); 1.1 root 5868: 1.1.1.4 root 5869: /* There first block is for the function body, and does not have 5870: corresponding block notes. Don't include it in the block vector. */ 5871: block = BLOCK_SUBBLOCKS (block); 1.1 root 5872: 1.1.1.4 root 5873: block_vector = identify_blocks (block, get_insns ()); 1.1 root 5874: } 5875: 5876: void 1.1.1.4 root 5877: unroll_block_trees () 1.1 root 5878: { 1.1.1.4 root 5879: tree block = DECL_INITIAL (current_function_decl); 1.1 root 5880: 1.1.1.4 root 5881: reorder_blocks (block_vector, block, get_insns ()); 1.1 root 5882: } 1.1.1.4 root 5883:
This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.