diff options
Diffstat (limited to 'gcc/emit-rtl.c')
-rw-r--r-- | gcc/emit-rtl.c | 807 |
1 files changed, 480 insertions, 327 deletions
diff --git a/gcc/emit-rtl.c b/gcc/emit-rtl.c index 7df9f23..a78a574 100644 --- a/gcc/emit-rtl.c +++ b/gcc/emit-rtl.c @@ -3101,52 +3101,72 @@ try_split (pat, trial, last) if (seq) { - /* SEQ can either be a SEQUENCE or the pattern of a single insn. - The latter case will normally arise only when being done so that - it, in turn, will be split (SFmode on the 29k is an example). */ - if (GET_CODE (seq) == SEQUENCE) + /* SEQ can only be a list of insns. */ + if (! INSN_P (seq)) + abort (); + + /* Sometimes there will be only one insn in that list, this case will + normally arise only when we want it in turn to be split (SFmode on + the 29k is an example). */ + if (NEXT_INSN (seq) != NULL_RTX) { - int i, njumps = 0; + rtx insn_last, insn; + int njumps = 0; /* Avoid infinite loop if any insn of the result matches the original pattern. */ - for (i = 0; i < XVECLEN (seq, 0); i++) - if (GET_CODE (XVECEXP (seq, 0, i)) == INSN - && rtx_equal_p (PATTERN (XVECEXP (seq, 0, i)), pat)) - return trial; + insn_last = seq; + while (1) + { + if (rtx_equal_p (PATTERN (insn_last), pat)) + return trial; + if (NEXT_INSN (insn_last) == NULL_RTX) + break; + insn_last = NEXT_INSN (insn_last); + } /* Mark labels. */ - for (i = XVECLEN (seq, 0) - 1; i >= 0; i--) - if (GET_CODE (XVECEXP (seq, 0, i)) == JUMP_INSN) - { - rtx insn = XVECEXP (seq, 0, i); - mark_jump_label (PATTERN (insn), - XVECEXP (seq, 0, i), 0); - njumps++; - if (probability != -1 - && any_condjump_p (insn) - && !find_reg_note (insn, REG_BR_PROB, 0)) - { - /* We can preserve the REG_BR_PROB notes only if exactly - one jump is created, otherwise the machine description - is responsible for this step using - split_branch_probability variable. */ - if (njumps != 1) - abort (); - REG_NOTES (insn) - = gen_rtx_EXPR_LIST (REG_BR_PROB, - GEN_INT (probability), - REG_NOTES (insn)); - } - } + insn = insn_last; + while (insn != NULL_RTX) + { + if (GET_CODE (insn) == JUMP_INSN) + { + mark_jump_label (PATTERN (insn), insn, 0); + njumps++; + if (probability != -1 + && any_condjump_p (insn) + && !find_reg_note (insn, REG_BR_PROB, 0)) + { + /* We can preserve the REG_BR_PROB notes only if exactly + one jump is created, otherwise the machine description + is responsible for this step using + split_branch_probability variable. */ + if (njumps != 1) + abort (); + REG_NOTES (insn) + = gen_rtx_EXPR_LIST (REG_BR_PROB, + GEN_INT (probability), + REG_NOTES (insn)); + } + } + + insn = PREV_INSN (insn); + } /* If we are splitting a CALL_INSN, look for the CALL_INSN in SEQ and copy our CALL_INSN_FUNCTION_USAGE to it. */ if (GET_CODE (trial) == CALL_INSN) - for (i = XVECLEN (seq, 0) - 1; i >= 0; i--) - if (GET_CODE (XVECEXP (seq, 0, i)) == CALL_INSN) - CALL_INSN_FUNCTION_USAGE (XVECEXP (seq, 0, i)) - = CALL_INSN_FUNCTION_USAGE (trial); + { + insn = insn_last; + while (insn != NULL_RTX) + { + if (GET_CODE (insn) == CALL_INSN) + CALL_INSN_FUNCTION_USAGE (insn) + = CALL_INSN_FUNCTION_USAGE (trial); + + insn = PREV_INSN (insn); + } + } /* Copy notes, particularly those related to the CFG. */ for (note = REG_NOTES (trial); note; note = XEXP (note, 1)) @@ -3154,9 +3174,9 @@ try_split (pat, trial, last) switch (REG_NOTE_KIND (note)) { case REG_EH_REGION: - for (i = XVECLEN (seq, 0) - 1; i >= 0; i--) + insn = insn_last; + while (insn != NULL_RTX) { - rtx insn = XVECEXP (seq, 0, i); if (GET_CODE (insn) == CALL_INSN || (flag_non_call_exceptions && may_trap_p (PATTERN (insn)))) @@ -3164,32 +3184,35 @@ try_split (pat, trial, last) = gen_rtx_EXPR_LIST (REG_EH_REGION, XEXP (note, 0), REG_NOTES (insn)); + insn = PREV_INSN (insn); } break; case REG_NORETURN: case REG_SETJMP: case REG_ALWAYS_RETURN: - for (i = XVECLEN (seq, 0) - 1; i >= 0; i--) + insn = insn_last; + while (insn != NULL_RTX) { - rtx insn = XVECEXP (seq, 0, i); if (GET_CODE (insn) == CALL_INSN) REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_NOTE_KIND (note), XEXP (note, 0), REG_NOTES (insn)); + insn = PREV_INSN (insn); } break; case REG_NON_LOCAL_GOTO: - for (i = XVECLEN (seq, 0) - 1; i >= 0; i--) + insn = insn_last; + while (insn != NULL_RTX) { - rtx insn = XVECEXP (seq, 0, i); if (GET_CODE (insn) == JUMP_INSN) REG_NOTES (insn) = gen_rtx_EXPR_LIST (REG_NOTE_KIND (note), XEXP (note, 0), REG_NOTES (insn)); + insn = PREV_INSN (insn); } break; @@ -3201,9 +3224,16 @@ try_split (pat, trial, last) /* If there are LABELS inside the split insns increment the usage count so we don't delete the label. */ if (GET_CODE (trial) == INSN) - for (i = XVECLEN (seq, 0) - 1; i >= 0; i--) - if (GET_CODE (XVECEXP (seq, 0, i)) == INSN) - mark_label_nuses (PATTERN (XVECEXP (seq, 0, i))); + { + insn = last_insn; + while (insn != NULL_RTX) + { + if (GET_CODE (insn) == INSN) + mark_label_nuses (PATTERN (insn)); + + insn = PREV_INSN (insn); + } + } tem = emit_insn_after_scope (seq, trial, INSN_SCOPE (trial)); @@ -3221,13 +3251,13 @@ try_split (pat, trial, last) tem = try_split (PATTERN (tem), tem, 1); } /* Avoid infinite loop if the result matches the original pattern. */ - else if (rtx_equal_p (seq, pat)) + else if (rtx_equal_p (PATTERN (seq), pat)) return trial; else { - PATTERN (trial) = seq; + PATTERN (trial) = PATTERN (seq); INSN_CODE (trial) = -1; - try_split (seq, trial, last); + try_split (PATTERN (trial), trial, last); } /* Return either the first or the last insn, depending on which was @@ -3274,7 +3304,7 @@ make_insn_raw (pattern) return insn; } -/* Like `make_insn' but make a JUMP_INSN instead of an insn. */ +/* Like `make_insn_raw' but make a JUMP_INSN instead of an insn. */ static rtx make_jump_insn_raw (pattern) @@ -3296,7 +3326,7 @@ make_jump_insn_raw (pattern) return insn; } -/* Like `make_insn' but make a CALL_INSN instead of an insn. */ +/* Like `make_insn_raw' but make a CALL_INSN instead of an insn. */ static rtx make_call_insn_raw (pattern) @@ -3782,97 +3812,173 @@ remove_unnecessary_notes () } -/* Emit an insn of given code and pattern - at a specified place within the doubly-linked list. */ +/* Emit insn(s) of given code and pattern + at a specified place within the doubly-linked list. -/* Make an instruction with body PATTERN - and output it before the instruction BEFORE. */ + All of the emit_foo global entry points accept an object + X which is either an insn list or a PATTERN of a single + instruction. -rtx -emit_insn_before (pattern, before) - rtx pattern, before; -{ - rtx insn = before; + There are thus a few canonical ways to generate code and + emit it at a specific place in the instruction stream. For + example, consider the instruction named SPOT and the fact that + we would like to emit some instructions before SPOT. We might + do it like this: - if (GET_CODE (pattern) == SEQUENCE) - { - int i; + start_sequence (); + ... emit the new instructions ... + insns_head = get_insns (); + end_sequence (); - for (i = 0; i < XVECLEN (pattern, 0); i++) - { - insn = XVECEXP (pattern, 0, i); - add_insn_before (insn, before); - } - } - else - { - insn = make_insn_raw (pattern); - add_insn_before (insn, before); - } + emit_insn_before (insns_head, SPOT); - return insn; -} + It used to be common to generate SEQUENCE rtl instead, but that + is a relic of the past which no longer occurs. The reason is that + SEQUENCE rtl results in much fragmented RTL memory since the SEQUENCE + generated would almost certainly die right after it was created. */ -/* Make an instruction with body PATTERN and code JUMP_INSN - and output it before the instruction BEFORE. */ +/* Make X be output before the instruction BEFORE. */ rtx -emit_jump_insn_before (pattern, before) - rtx pattern, before; +emit_insn_before (x, before) + rtx x, before; { + rtx last = before; rtx insn; - if (GET_CODE (pattern) == SEQUENCE) - insn = emit_insn_before (pattern, before); - else +#ifdef ENABLE_RTL_CHECKING + if (before == NULL_RTX) + abort (); +#endif + + if (x == NULL_RTX) + return last; + + switch (GET_CODE (x)) { - insn = make_jump_insn_raw (pattern); - add_insn_before (insn, before); + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + insn = x; + while (insn) + { + rtx next = NEXT_INSN (insn); + add_insn_before (insn, before); + last = insn; + insn = next; + } + break; + +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif + + default: + last = make_insn_raw (x); + add_insn_before (last, before); + break; } - return insn; + return last; } -/* Make an instruction with body PATTERN and code CALL_INSN +/* Make an instruction with body X and code JUMP_INSN and output it before the instruction BEFORE. */ rtx -emit_call_insn_before (pattern, before) - rtx pattern, before; +emit_jump_insn_before (x, before) + rtx x, before; { - rtx insn; + rtx insn, last; - if (GET_CODE (pattern) == SEQUENCE) - insn = emit_insn_before (pattern, before); - else +#ifdef ENABLE_RTL_CHECKING + if (before == NULL_RTX) + abort (); +#endif + + switch (GET_CODE (x)) { - insn = make_call_insn_raw (pattern); - add_insn_before (insn, before); - PUT_CODE (insn, CALL_INSN); + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + insn = x; + while (insn) + { + rtx next = NEXT_INSN (insn); + add_insn_before (insn, before); + last = insn; + insn = next; + } + break; + +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif + + default: + last = make_jump_insn_raw (x); + add_insn_before (last, before); + break; } - return insn; + return last; } -/* Make an instruction with body PATTERN and code CALL_INSN +/* Make an instruction with body X and code CALL_INSN and output it before the instruction BEFORE. */ rtx -emit_call_insn_after (pattern, before) - rtx pattern, before; +emit_call_insn_before (x, before) + rtx x, before; { - rtx insn; + rtx last, insn; - if (GET_CODE (pattern) == SEQUENCE) - insn = emit_insn_after (pattern, before); - else +#ifdef ENABLE_RTL_CHECKING + if (before == NULL_RTX) + abort (); +#endif + + switch (GET_CODE (x)) { - insn = make_call_insn_raw (pattern); - add_insn_after (insn, before); - PUT_CODE (insn, CALL_INSN); + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + insn = x; + while (insn) + { + rtx next = NEXT_INSN (insn); + add_insn_before (insn, before); + last = insn; + insn = next; + } + break; + +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif + + default: + last = make_call_insn_raw (x); + add_insn_before (last, before); + break; } - return insn; + return last; } /* Make an insn of code BARRIER @@ -3924,45 +4030,100 @@ emit_note_before (subtype, before) return note; } -/* Make an insn of code INSN with body PATTERN - and output it after the insn AFTER. */ +/* Helper for emit_insn_after, handles lists of instructions + efficiently. */ -rtx -emit_insn_after (pattern, after) - rtx pattern, after; +static rtx emit_insn_after_1 PARAMS ((rtx, rtx)); + +static rtx +emit_insn_after_1 (first, after) + rtx first, after; { - rtx insn = after; + rtx last; + rtx after_after; + basic_block bb; - if (GET_CODE (pattern) == SEQUENCE) + if (GET_CODE (after) != BARRIER + && (bb = BLOCK_FOR_INSN (after))) { - int i; - - for (i = 0; i < XVECLEN (pattern, 0); i++) - { - insn = XVECEXP (pattern, 0, i); - add_insn_after (insn, after); - after = insn; - } + bb->flags |= BB_DIRTY; + for (last = first; NEXT_INSN (last); last = NEXT_INSN (last)) + if (GET_CODE (last) != BARRIER) + set_block_for_insn (last, bb); + if (GET_CODE (last) != BARRIER) + set_block_for_insn (last, bb); + if (bb->end == after) + bb->end = last; } else + for (last = first; NEXT_INSN (last); last = NEXT_INSN (last)) + continue; + + after_after = NEXT_INSN (after); + + NEXT_INSN (after) = first; + PREV_INSN (first) = after; + NEXT_INSN (last) = after_after; + if (after_after) + PREV_INSN (after_after) = last; + + if (after == last_insn) + last_insn = last; + return last; +} + +/* Make X be output after the insn AFTER. */ + +rtx +emit_insn_after (x, after) + rtx x, after; +{ + rtx last = after; + +#ifdef ENABLE_RTL_CHECKING + if (after == NULL_RTX) + abort (); +#endif + + if (x == NULL_RTX) + return last; + + switch (GET_CODE (x)) { - insn = make_insn_raw (pattern); - add_insn_after (insn, after); + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + last = emit_insn_after_1 (x, after); + break; + +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif + + default: + last = make_insn_raw (x); + add_insn_after (last, after); + break; } - return insn; + return last; } /* Similar to emit_insn_after, except that line notes are to be inserted so as to act as if this insn were at FROM. */ void -emit_insn_after_with_line_notes (pattern, after, from) - rtx pattern, after, from; +emit_insn_after_with_line_notes (x, after, from) + rtx x, after, from; { rtx from_line = find_line_note (from); rtx after_line = find_line_note (after); - rtx insn = emit_insn_after (pattern, after); + rtx insn = emit_insn_after (x, after); if (from_line) emit_line_note_after (NOTE_SOURCE_FILE (from_line), @@ -3975,24 +4136,84 @@ emit_insn_after_with_line_notes (pattern, after, from) insn); } -/* Make an insn of code JUMP_INSN with body PATTERN +/* Make an insn of code JUMP_INSN with body X and output it after the insn AFTER. */ rtx -emit_jump_insn_after (pattern, after) - rtx pattern, after; +emit_jump_insn_after (x, after) + rtx x, after; { - rtx insn; + rtx last; - if (GET_CODE (pattern) == SEQUENCE) - insn = emit_insn_after (pattern, after); - else +#ifdef ENABLE_RTL_CHECKING + if (after == NULL_RTX) + abort (); +#endif + + switch (GET_CODE (x)) { - insn = make_jump_insn_raw (pattern); - add_insn_after (insn, after); + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + last = emit_insn_after_1 (x, after); + break; + +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif + + default: + last = make_jump_insn_raw (x); + add_insn_after (last, after); + break; } - return insn; + return last; +} + +/* Make an instruction with body X and code CALL_INSN + and output it after the instruction AFTER. */ + +rtx +emit_call_insn_after (x, after) + rtx x, after; +{ + rtx last; + +#ifdef ENABLE_RTL_CHECKING + if (after == NULL_RTX) + abort (); +#endif + + switch (GET_CODE (x)) + { + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + last = emit_insn_after_1 (x, after); + break; + +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif + + default: + last = make_call_insn_raw (x); + add_insn_after (last, after); + break; + } + + return last; } /* Make an insn of code BARRIER @@ -4076,20 +4297,15 @@ emit_insn_after_scope (pattern, after, scope) tree scope; { rtx last = emit_insn_after (pattern, after); - for (after = NEXT_INSN (after); after != last; after = NEXT_INSN (after)) - INSN_SCOPE (after) = scope; - return last; -} -/* Like emit_insns_after, but set INSN_SCOPE according to SCOPE. */ -rtx -emit_insns_after_scope (pattern, after, scope) - rtx pattern, after; - tree scope; -{ - rtx last = emit_insns_after (pattern, after); - for (after = NEXT_INSN (after); after != last; after = NEXT_INSN (after)) - INSN_SCOPE (after) = scope; + after = NEXT_INSN (after); + while (1) + { + INSN_SCOPE (after) = scope; + if (after == last) + break; + after = NEXT_INSN (after); + } return last; } @@ -4100,8 +4316,15 @@ emit_jump_insn_after_scope (pattern, after, scope) tree scope; { rtx last = emit_jump_insn_after (pattern, after); - for (after = NEXT_INSN (after); after != last; after = NEXT_INSN (after)) - INSN_SCOPE (after) = scope; + + after = NEXT_INSN (after); + while (1) + { + INSN_SCOPE (after) = scope; + if (after == last) + break; + after = NEXT_INSN (after); + } return last; } @@ -4112,8 +4335,15 @@ emit_call_insn_after_scope (pattern, after, scope) tree scope; { rtx last = emit_call_insn_after (pattern, after); - for (after = NEXT_INSN (after); after != last; after = NEXT_INSN (after)) - INSN_SCOPE (after) = scope; + + after = NEXT_INSN (after); + while (1) + { + INSN_SCOPE (after) = scope; + if (after == last) + break; + after = NEXT_INSN (after); + } return last; } @@ -4126,178 +4356,140 @@ emit_insn_before_scope (pattern, before, scope) rtx first = PREV_INSN (before); rtx last = emit_insn_before (pattern, before); - for (first = NEXT_INSN (first); first != last; first = NEXT_INSN (first)) - INSN_SCOPE (first) = scope; - return last; -} - -/* Like emit_insns_before, but set INSN_SCOPE according to SCOPE. */ -rtx -emit_insns_before_scope (pattern, before, scope) - rtx pattern, before; - tree scope; -{ - rtx first = PREV_INSN (before); - rtx last = emit_insns_before (pattern, before); - - for (first = NEXT_INSN (first); first != last; first = NEXT_INSN (first)) - INSN_SCOPE (first) = scope; + first = NEXT_INSN (first); + while (1) + { + INSN_SCOPE (first) = scope; + if (first == last) + break; + first = NEXT_INSN (first); + } return last; } -/* Make an insn of code INSN with pattern PATTERN - and add it to the end of the doubly-linked list. - If PATTERN is a SEQUENCE, take the elements of it - and emit an insn for each element. +/* Take X and emit it at the end of the doubly-linked + INSN list. Returns the last insn emitted. */ rtx -emit_insn (pattern) - rtx pattern; +emit_insn (x) + rtx x; { - rtx insn = last_insn; + rtx last = last_insn; + rtx insn; - if (GET_CODE (pattern) == SEQUENCE) - { - int i; + if (x == NULL_RTX) + return last; - for (i = 0; i < XVECLEN (pattern, 0); i++) + switch (GET_CODE (x)) + { + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + insn = x; + while (insn) { - insn = XVECEXP (pattern, 0, i); + rtx next = NEXT_INSN (insn); add_insn (insn); + last = insn; + insn = next; } - } - else - { - insn = make_insn_raw (pattern); - add_insn (insn); - } - - return insn; -} - -/* Emit the insns in a chain starting with INSN. - Return the last insn emitted. */ + break; -rtx -emit_insns (insn) - rtx insn; -{ - rtx last = 0; +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif - while (insn) - { - rtx next = NEXT_INSN (insn); - add_insn (insn); - last = insn; - insn = next; + default: + last = make_insn_raw (x); + add_insn (last); + break; } return last; } -/* Emit the insns in a chain starting with INSN and place them in front of - the insn BEFORE. Return the last insn emitted. */ +/* Make an insn of code JUMP_INSN with pattern X + and add it to the end of the doubly-linked list. */ rtx -emit_insns_before (insn, before) - rtx insn; - rtx before; +emit_jump_insn (x) + rtx x; { - rtx last = 0; + rtx last, insn; - while (insn) + switch (GET_CODE (x)) { - rtx next = NEXT_INSN (insn); - add_insn_before (insn, before); - last = insn; - insn = next; - } - - return last; -} - -/* Emit the insns in a chain starting with FIRST and place them in back of - the insn AFTER. Return the last insn emitted. */ - -rtx -emit_insns_after (first, after) - rtx first; - rtx after; -{ - rtx last; - rtx after_after; - basic_block bb; - - if (!after) - abort (); + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + insn = x; + while (insn) + { + rtx next = NEXT_INSN (insn); + add_insn (insn); + last = insn; + insn = next; + } + break; - if (!first) - return after; +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif - if (GET_CODE (after) != BARRIER - && (bb = BLOCK_FOR_INSN (after))) - { - bb->flags |= BB_DIRTY; - for (last = first; NEXT_INSN (last); last = NEXT_INSN (last)) - if (GET_CODE (last) != BARRIER) - set_block_for_insn (last, bb); - if (GET_CODE (last) != BARRIER) - set_block_for_insn (last, bb); - if (bb->end == after) - bb->end = last; + default: + last = make_jump_insn_raw (x); + add_insn (last); + break; } - else - for (last = first; NEXT_INSN (last); last = NEXT_INSN (last)) - continue; - - after_after = NEXT_INSN (after); - - NEXT_INSN (after) = first; - PREV_INSN (first) = after; - NEXT_INSN (last) = after_after; - if (after_after) - PREV_INSN (after_after) = last; - if (after == last_insn) - last_insn = last; return last; } -/* Make an insn of code JUMP_INSN with pattern PATTERN +/* Make an insn of code CALL_INSN with pattern X and add it to the end of the doubly-linked list. */ rtx -emit_jump_insn (pattern) - rtx pattern; +emit_call_insn (x) + rtx x; { - if (GET_CODE (pattern) == SEQUENCE) - return emit_insn (pattern); - else + rtx insn; + + switch (GET_CODE (x)) { - rtx insn = make_jump_insn_raw (pattern); - add_insn (insn); - return insn; - } -} + case INSN: + case JUMP_INSN: + case CALL_INSN: + case CODE_LABEL: + case BARRIER: + case NOTE: + insn = emit_insn (x); + break; -/* Make an insn of code CALL_INSN with pattern PATTERN - and add it to the end of the doubly-linked list. */ +#ifdef ENABLE_RTL_CHECKING + case SEQUENCE: + abort (); + break; +#endif -rtx -emit_call_insn (pattern) - rtx pattern; -{ - if (GET_CODE (pattern) == SEQUENCE) - return emit_insn (pattern); - else - { - rtx insn = make_call_insn_raw (pattern); + default: + insn = make_call_insn_raw (x); add_insn (insn); - PUT_CODE (insn, CALL_INSN); - return insn; + break; } + + return insn; } /* Add the label LABEL to the end of the doubly-linked list. */ @@ -4634,12 +4826,12 @@ pop_topmost_sequence () /* After emitting to a sequence, restore previous saved state. To get the contents of the sequence just made, you must call - `gen_sequence' *before* calling here. + `get_insns' *before* calling here. If the compiler might have deferred popping arguments while generating this sequence, and this sequence will not be immediately inserted into the instruction stream, use do_pending_stack_adjust - before calling gen_sequence. That will ensure that the deferred + before calling get_insns. That will ensure that the deferred pops are inserted into this sequence, and not into some random location in the instruction stream. See INHIBIT_DEFER_POP for more information about deferred popping of arguments. */ @@ -4678,45 +4870,6 @@ in_sequence_p () { return seq_stack != 0; } - -/* Generate a SEQUENCE rtx containing the insns already emitted - to the current sequence. - - This is how the gen_... function from a DEFINE_EXPAND - constructs the SEQUENCE that it returns. */ - -rtx -gen_sequence () -{ - rtx result; - rtx tem; - int i; - int len; - - /* Count the insns in the chain. */ - len = 0; - for (tem = first_insn; tem; tem = NEXT_INSN (tem)) - len++; - - /* If only one insn, return it rather than a SEQUENCE. - (Now that we cache SEQUENCE expressions, it isn't worth special-casing - the case of an empty list.) - We only return the pattern of an insn if its code is INSN and it - has no notes. This ensures that no information gets lost. */ - if (len == 1 - && GET_CODE (first_insn) == INSN - && ! RTX_FRAME_RELATED_P (first_insn) - /* Don't throw away any reg notes. */ - && REG_NOTES (first_insn) == 0) - return PATTERN (first_insn); - - result = gen_rtx_SEQUENCE (VOIDmode, rtvec_alloc (len)); - - for (i = 0, tem = first_insn; tem; tem = NEXT_INSN (tem), i++) - XVECEXP (result, 0, i) = tem; - - return result; -} /* Put the various virtual registers into REGNO_REG_RTX. */ |