You should have received a copy of the GNU General Public License
along with GCC; see the file COPYING. If not, write to the Free
-Software Foundation, 59 Temple Place - Suite 330, Boston, MA
-02111-1307, USA. */
+Software Foundation, 51 Franklin Street, Fifth Floor, Boston, MA
+02110-1301, USA. */
#include "config.h"
#include "system.h"
#include "ggc.h"
#include "target.h"
#include "langhooks.h"
+#include "tree-pass.h"
/* Round to the next highest integer that meets the alignment. */
#define CEIL_ROUND(VALUE,ALIGN) (((VALUE) + (ALIGN) - 1) & ~((ALIGN)- 1))
return true;
}
\f
-/* Copy NODE (which must be a DECL). The DECL originally was in the FROM_FN,
- but now it will be in the TO_FN. */
-
-tree
-copy_decl_for_inlining (tree decl, tree from_fn, tree to_fn)
-{
- tree copy;
-
- /* Copy the declaration. */
- if (TREE_CODE (decl) == PARM_DECL || TREE_CODE (decl) == RESULT_DECL)
- {
- tree type = TREE_TYPE (decl);
-
- /* For a parameter or result, we must make an equivalent VAR_DECL, not a
- new PARM_DECL. */
- copy = build_decl (VAR_DECL, DECL_NAME (decl), type);
- TREE_ADDRESSABLE (copy) = TREE_ADDRESSABLE (decl);
- TREE_READONLY (copy) = TREE_READONLY (decl);
- TREE_THIS_VOLATILE (copy) = TREE_THIS_VOLATILE (decl);
- DECL_COMPLEX_GIMPLE_REG_P (copy) = DECL_COMPLEX_GIMPLE_REG_P (decl);
- }
- else
- {
- copy = copy_node (decl);
- /* The COPY is not abstract; it will be generated in TO_FN. */
- DECL_ABSTRACT (copy) = 0;
- lang_hooks.dup_lang_specific_decl (copy);
-
- /* TREE_ADDRESSABLE isn't used to indicate that a label's
- address has been taken; it's for internal bookkeeping in
- expand_goto_internal. */
- if (TREE_CODE (copy) == LABEL_DECL)
- {
- TREE_ADDRESSABLE (copy) = 0;
- LABEL_DECL_UID (copy) = -1;
- }
- }
-
- /* Don't generate debug information for the copy if we wouldn't have
- generated it for the copy either. */
- DECL_ARTIFICIAL (copy) = DECL_ARTIFICIAL (decl);
- DECL_IGNORED_P (copy) = DECL_IGNORED_P (decl);
-
- /* Set the DECL_ABSTRACT_ORIGIN so the debugging routines know what
- declaration inspired this copy. */
- DECL_ABSTRACT_ORIGIN (copy) = DECL_ORIGIN (decl);
-
- /* The new variable/label has no RTL, yet. */
- if (!TREE_STATIC (copy) && !DECL_EXTERNAL (copy))
- SET_DECL_RTL (copy, NULL_RTX);
-
- /* These args would always appear unused, if not for this. */
- TREE_USED (copy) = 1;
-
- /* Set the context for the new declaration. */
- if (!DECL_CONTEXT (decl))
- /* Globals stay global. */
- ;
- else if (DECL_CONTEXT (decl) != from_fn)
- /* Things that weren't in the scope of the function we're inlining
- from aren't in the scope we're inlining to, either. */
- ;
- else if (TREE_STATIC (decl))
- /* Function-scoped static variables should stay in the original
- function. */
- ;
- else
- /* Ordinary automatic local variables are now in the scope of the
- new function. */
- DECL_CONTEXT (copy) = to_fn;
-
- return copy;
-}
-
-\f
/* Given a pointer to some BLOCK node, if the BLOCK_ABSTRACT_ORIGIN for the
given BLOCK node is NULL, set the BLOCK_ABSTRACT_ORIGIN for the node so
that it points to the node itself, thus indicating that the node is its
return NULL_RTX;
}
-void
+unsigned int
emit_initial_value_sets (void)
{
struct initial_value_struct *ivs = cfun->hard_reg_initial_vals;
rtx seq;
if (ivs == 0)
- return;
+ return 0;
start_sequence ();
for (i = 0; i < ivs->num_entries; i++)
seq = get_insns ();
end_sequence ();
- emit_insn_after (seq, entry_of_function ());
+ emit_insn_at_entry (seq);
+ return 0;
}
+struct tree_opt_pass pass_initial_value_sets =
+{
+ "initvals", /* name */
+ NULL, /* gate */
+ emit_initial_value_sets, /* execute */
+ NULL, /* sub */
+ NULL, /* next */
+ 0, /* static_pass_number */
+ 0, /* tv_id */
+ 0, /* properties_required */
+ 0, /* properties_provided */
+ 0, /* properties_destroyed */
+ 0, /* todo_flags_start */
+ TODO_dump_func, /* todo_flags_finish */
+ 0 /* letter */
+};
+
/* If the backend knows where to allocate pseudos for hard
register initial values, register these allocations now. */
void
allocate_initial_values (rtx *reg_equiv_memory_loc ATTRIBUTE_UNUSED)
{
-#ifdef ALLOCATE_INITIAL_VALUE
- struct initial_value_struct *ivs = cfun->hard_reg_initial_vals;
- int i;
-
- if (ivs == 0)
- return;
-
- for (i = 0; i < ivs->num_entries; i++)
+ if (targetm.allocate_initial_value)
{
- int regno = REGNO (ivs->entries[i].pseudo);
- rtx x = ALLOCATE_INITIAL_VALUE (ivs->entries[i].hard_reg);
+ struct initial_value_struct *ivs = cfun->hard_reg_initial_vals;
+ int i;
+
+ if (ivs == 0)
+ return;
- if (x && REG_N_SETS (REGNO (ivs->entries[i].pseudo)) <= 1)
+ for (i = 0; i < ivs->num_entries; i++)
{
- if (MEM_P (x))
- reg_equiv_memory_loc[regno] = x;
- else
+ int regno = REGNO (ivs->entries[i].pseudo);
+ rtx x = targetm.allocate_initial_value (ivs->entries[i].hard_reg);
+
+ if (x && REG_N_SETS (REGNO (ivs->entries[i].pseudo)) <= 1)
{
- basic_block bb;
- int new_regno;
-
- gcc_assert (REG_P (x));
- new_regno = REGNO (x);
- reg_renumber[regno] = new_regno;
- /* Poke the regno right into regno_reg_rtx so that even
- fixed regs are accepted. */
- REGNO (ivs->entries[i].pseudo) = new_regno;
- /* Update global register liveness information. */
- FOR_EACH_BB (bb)
+ if (MEM_P (x))
+ reg_equiv_memory_loc[regno] = x;
+ else
{
- if (REGNO_REG_SET_P(bb->global_live_at_start, regno))
- SET_REGNO_REG_SET (bb->global_live_at_start, new_regno);
- if (REGNO_REG_SET_P(bb->global_live_at_end, regno))
- SET_REGNO_REG_SET (bb->global_live_at_end, new_regno);
+ basic_block bb;
+ int new_regno;
+
+ gcc_assert (REG_P (x));
+ new_regno = REGNO (x);
+ reg_renumber[regno] = new_regno;
+ /* Poke the regno right into regno_reg_rtx so that even
+ fixed regs are accepted. */
+ REGNO (ivs->entries[i].pseudo) = new_regno;
+ /* Update global register liveness information. */
+ FOR_EACH_BB (bb)
+ {
+ struct rtl_bb_info *info = bb->il.rtl;
+
+ if (REGNO_REG_SET_P(info->global_live_at_start, regno))
+ SET_REGNO_REG_SET (info->global_live_at_start,
+ new_regno);
+ if (REGNO_REG_SET_P(info->global_live_at_end, regno))
+ SET_REGNO_REG_SET (info->global_live_at_end,
+ new_regno);
+ }
}
}
}
}
-#endif
}
#include "gt-integrate.h"