}
else
{
+ /* For this we treat the H8/300 and H8/S the same. */
cpu_type = (int) CPU_H8300H;
h8_reg_names = names_extended;
}
char *op;
unsigned int size;
{
- /* On the h8300h, for sizes <= 8 bytes it is as good or
+ /* On the h8300h and h8300s, for sizes <= 8 bytes it is as good or
better to use adds/subs insns rather than add.l/sub.l
with an immediate value. */
- if (size > 4 && size <= 8 && TARGET_H8300H)
+ if (size > 4 && size <= 8 && (TARGET_H8300H || TARGET_H8300S))
{
/* Crank the size down to <= 4 */
fprintf (file, "\t%ss\t#%d,sp\n", op, 4);
switch (size)
{
case 4:
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
{
fprintf (file, "\t%ss\t#%d,sp\n", op, 4);
size = 0;
/* Output assembly language code for the function prologue. */
static int push_order[FIRST_PSEUDO_REGISTER] =
-{6, 5, 4, 3, 2, 1, 0, -1, -1};
-static int pop_order[FIRST_PSEUDO_REGISTER] =
{0, 1, 2, 3, 4, 5, 6, -1, -1};
+static int pop_order[FIRST_PSEUDO_REGISTER] =
+{6, 5, 4, 3, 2, 1, 0, -1, -1};
/* This is what the stack looks like after the prolog of
a function with a frame has been set up:
fprintf (file, "\torc\t#128,ccr\n");
fprintf (file, "\tmov.b\tr0l,@(4,sp)\n");
}
- else if (TARGET_H8300H)
+ else
{
fprintf (file, "\tpush\ter0\n");
fprintf (file, "\tstc\tccr,r0l\n");
fprintf (file, "\t%s\t%s,%s\n", h8_mov_op,
h8_reg_names[STACK_POINTER_REGNUM],
h8_reg_names[FRAME_POINTER_REGNUM]);
+ }
- /* leave room for locals */
- dosize (file, "sub", fsize);
-
- /* Push the rest of the registers */
- for (idx = 0; idx < FIRST_PSEUDO_REGISTER; idx++)
- {
- int regno = push_order[idx];
+ /* leave room for locals */
+ dosize (file, "sub", fsize);
- if (regno >= 0 && WORD_REG_USED (regno) && regno != FRAME_POINTER_REGNUM)
- fprintf (file, "\t%s\t%s\n", h8_push_op, h8_reg_names[regno]);
- }
- }
- else
+ /* Push the rest of the registers */
+ for (idx = 0; idx < FIRST_PSEUDO_REGISTER; idx++)
{
- dosize (file, "sub", fsize);
- for (idx = 0; idx < FIRST_PSEUDO_REGISTER; idx++)
- {
- int regno = push_order[idx];
+ int regno = push_order[idx];
- if (regno >= 0 && WORD_REG_USED (regno))
- fprintf (file, "\t%s\t%s\n", h8_push_op, h8_reg_names[regno]);
+ if (regno >= 0
+ && WORD_REG_USED (regno)
+ && (!frame_pointer_needed || regno != FRAME_POINTER_REGNUM))
+ {
+ if (TARGET_H8300S)
+ {
+ /* Try to push multiple registers. */
+ if (regno == 0 || regno == 4)
+ {
+ int second_regno = push_order[idx + 1];
+ int third_regno = push_order[idx + 2];
+ int fourth_regno = push_order[idx + 3];
+
+ if (fourth_regno >= 0
+ && WORD_REG_USED (fourth_regno)
+ && (!frame_pointer_needed
+ || fourth_regno != FRAME_POINTER_REGNUM)
+ && third_regno >= 0
+ && WORD_REG_USED (third_regno)
+ && (!frame_pointer_needed
+ || third_regno != FRAME_POINTER_REGNUM)
+ && second_regno >= 0
+ && WORD_REG_USED (second_regno)
+ && (!frame_pointer_needed
+ || second_regno != FRAME_POINTER_REGNUM))
+ {
+ fprintf (file, "\tstm.l %s-%s,@-sp\n",
+ h8_reg_names[regno],
+ h8_reg_names[fourth_regno]);
+ idx += 3;
+ continue;
+ }
+ }
+ if (regno == 0 || regno == 4)
+ {
+ int second_regno = push_order[idx + 1];
+ int third_regno = push_order[idx + 2];
+
+ if (third_regno >= 0
+ && WORD_REG_USED (third_regno)
+ && (!frame_pointer_needed
+ || third_regno != FRAME_POINTER_REGNUM)
+ && second_regno >= 0
+ && WORD_REG_USED (second_regno)
+ && (!frame_pointer_needed
+ || second_regno != FRAME_POINTER_REGNUM))
+ {
+ fprintf (file, "\tstm.l %s-%s,@-sp\n",
+ h8_reg_names[regno],
+ h8_reg_names[third_regno]);
+ idx += 2;
+ continue;
+ }
+ }
+ if (regno == 0 || regno == 2 || regno == 4 || regno == 6)
+ {
+ int second_regno = push_order[idx + 1];
+
+ if (second_regno >= 0
+ && WORD_REG_USED (second_regno)
+ && (!frame_pointer_needed
+ || second_regno != FRAME_POINTER_REGNUM))
+ {
+ fprintf (file, "\tstm.l %s-%s,@-sp\n",
+ h8_reg_names[regno],
+ h8_reg_names[second_regno]);
+ idx += 1;
+ continue;
+ }
+ }
+ }
+ fprintf (file, "\t%s\t%s\n", h8_push_op, h8_reg_names[regno]);
}
}
}
register int regno;
register int mask = 0;
int fsize = (size + STACK_BOUNDARY / 8 - 1) & -STACK_BOUNDARY / 8;
- int nregs;
- int offset;
int idx;
rtx insn = get_last_insn ();
if (insn && GET_CODE (insn) == BARRIER)
return;
- nregs = 0;
-
- if (frame_pointer_needed)
+ /* Pop the saved registers. */
+ for (idx = 0; idx < FIRST_PSEUDO_REGISTER; idx++)
{
- /* Pop saved registers */
- for (idx = 0; idx < FIRST_PSEUDO_REGISTER; idx++)
- {
- regno = pop_order[idx];
- if (regno >= 0 && regno != FRAME_POINTER_REGNUM && WORD_REG_USED (regno))
- fprintf (file, "\t%s\t%s\n", h8_pop_op, h8_reg_names[regno]);
- }
- /* deallocate locals */
- dosize (file, "add", fsize);
- /* pop frame pointer */
- fprintf (file, "\t%s\t%s\n", h8_pop_op, h8_reg_names[FRAME_POINTER_REGNUM]);
- }
- else
- {
- /* pop saved registers */
- for (idx = 0; idx < FIRST_PSEUDO_REGISTER; idx++)
+ int regno = pop_order[idx];
+
+ if (regno >= 0
+ && WORD_REG_USED (regno)
+ && (!frame_pointer_needed || regno != FRAME_POINTER_REGNUM))
{
- regno = pop_order[idx];
- if (regno >= 0 && WORD_REG_USED (regno))
- fprintf (file, "\t%s\t%s\n", h8_pop_op, h8_reg_names[regno]);
+ if (TARGET_H8300S)
+ {
+ /* Try to pop multiple registers. */
+ if (regno == 7 || regno == 3)
+ {
+ int second_regno = pop_order[idx + 1];
+ int third_regno = pop_order[idx + 2];
+ int fourth_regno = pop_order[idx + 3];
+
+ if (fourth_regno >= 0
+ && WORD_REG_USED (fourth_regno)
+ && (!frame_pointer_needed
+ || fourth_regno != FRAME_POINTER_REGNUM)
+ && third_regno >= 0
+ && WORD_REG_USED (third_regno)
+ && (!frame_pointer_needed
+ || third_regno != FRAME_POINTER_REGNUM)
+ && second_regno >= 0
+ && WORD_REG_USED (second_regno)
+ && (!frame_pointer_needed
+ || second_regno != FRAME_POINTER_REGNUM))
+ {
+ fprintf (file, "\tldm.l @sp+,%s-%s\n",
+ h8_reg_names[fourth_regno],
+ h8_reg_names[regno]);
+ idx += 3;
+ continue;
+ }
+ }
+ if (regno == 6 || regno == 2)
+ {
+ int second_regno = pop_order[idx + 1];
+ int third_regno = pop_order[idx + 2];
+
+ if (third_regno >= 0
+ && WORD_REG_USED (third_regno)
+ && (!frame_pointer_needed
+ || third_regno != FRAME_POINTER_REGNUM)
+ && second_regno >= 0
+ && WORD_REG_USED (second_regno)
+ && (!frame_pointer_needed
+ || second_regno != FRAME_POINTER_REGNUM))
+ {
+ fprintf (file, "\tldm.l @sp+,%s-%s\n",
+ h8_reg_names[third_regno],
+ h8_reg_names[regno]);
+ idx += 2;
+ continue;
+ }
+ }
+ if (regno == 7 || regno == 5 || regno == 3 || regno == 1)
+ {
+ int second_regno = pop_order[idx + 1];
+
+ if (second_regno >= 0
+ && WORD_REG_USED (second_regno)
+ && (!frame_pointer_needed
+ || second_regno != FRAME_POINTER_REGNUM))
+ {
+ fprintf (file, "\tldm.l @sp+,%s-%s\n",
+ h8_reg_names[second_regno],
+ h8_reg_names[regno]);
+ idx += 1;
+ continue;
+ }
+ }
+ }
+ fprintf (file, "\t%s\t%s\n", h8_pop_op, h8_reg_names[regno]);
}
- /* deallocate locals */
- dosize (file, "add", fsize);
}
+ /* deallocate locals */
+ dosize (file, "add", fsize);
+
+ /* pop frame pointer if we had one. */
+ if (frame_pointer_needed)
+ fprintf (file, "\t%s\t%s\n", h8_pop_op, h8_reg_names[FRAME_POINTER_REGNUM]);
+
/* If this is a monitor function, there is one register still left on
the stack. */
if (monitor)
fprintf (file, "; -O%d\n", optimize);
if (TARGET_H8300H)
fprintf (file, "\n\t.h8300h\n");
+ else if (TARGET_H8300S)
+ fprintf (file, "\n\t.h8300s\n");
else
fprintf (file, "\n\n");
output_file_directive (file, main_input_filename);
return 1;
if (INTVAL (op) >= -4 && INTVAL (op) <= 0)
return 1;
- if (TARGET_H8300H
+ if ((TARGET_H8300H || TARGET_H8300S)
&& INTVAL (op) != 7
&& (INTVAL (op) <= 8 && INTVAL (op) >= 0))
return 1;
- if (TARGET_H8300H
+ if ((TARGET_H8300H || TARGET_H8300S)
&& INTVAL (op) != -7
&& (INTVAL (op) >= -8 && INTVAL (op) <= 0))
return 1;
if (val == 1 || val == -1
|| val == 2 || val == -2
- || (TARGET_H8300H
+ || ((TARGET_H8300H || TARGET_H8300S)
&& (val == 4 || val == -4)))
return 1;
return 0;
/* First get the value into the range -4..4 inclusive.
The only way it can be out of this range is when TARGET_H8300H
- is true, thus it is safe to use adds #4 and subs #4. */
+ or TARGET_H8300S is true, thus it is safe to use adds #4 and subs #4. */
if (val > 4)
{
output_asm_insn ("adds #4,%A0", operands);
}
/* Handle case were val == 4 or val == -4 and we're compiling
- for TARGET_H8300H. */
- if (TARGET_H8300H && val == 4)
+ for TARGET_H8300H or TARGET_H8300S. */
+ if ((TARGET_H8300H || TARGET_H8300S)
+ && val == 4)
return "adds #4,%A0";
- if (TARGET_H8300H && val == -4)
+ if ((TARGET_H8300H || TARGET_H8300S)
+ && val == -4)
return "subs #4,%A0";
if (val > 2)
return 0;
case 4:
case -4:
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return 0;
else
return 1;
if (GET_CODE (x) == CONST_INT)
fprintf (file, "#%d", INTVAL (x) & 0xff);
else
- fprintf (file, "%s", byte_reg (x, TARGET_H8300 ? 2 : 0));
+ fprintf (file, "%s",
+ byte_reg (x, TARGET_H8300 ? 2 : 0));
break;
case 'x':
if (GET_CODE (x) == CONST_INT)
fprintf (file, "#%d", (INTVAL (x) >> 8) & 0xff);
else
- fprintf (file, "%s", byte_reg (x, TARGET_H8300 ? 3 : 1));
+ fprintf (file, "%s",
+ byte_reg (x, TARGET_H8300 ? 3 : 1));
break;
case 'y':
if (GET_CODE (x) == CONST_INT)
rtx operands[];
{
/* Clear the destination register. */
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
output_asm_insn ("sub.l\t%S0,%S0", operands);
else
output_asm_insn ("sub.w\t%e0,%e0\n\tsub.w\t%f0,%f0", operands);
if (TARGET_H8300 && GET_CODE (addr) == REG)
return -2;
- /* On the H8/300H, register indirect is 6 bytes shorter than
+ /* On the H8/300H and H8/S, register indirect is 6 bytes shorter than
indicated in the machine description. */
- if (TARGET_H8300H && GET_CODE (addr) == REG)
+ if ((TARGET_H8300H || TARGET_H8300S)
+ && GET_CODE (addr) == REG)
return -6;
- /* On the H8/300H, reg + d, for small displacements is 4 bytes
- shorter than indicated in the machine description. */
- if (TARGET_H8300H
+ /* On the H8/300H and H8/300S, reg + d, for small displacements is 4
+ bytes shorter than indicated in the machine description. */
+ if ((TARGET_H8300H || TARGET_H8300S)
&& GET_CODE (addr) == PLUS
&& GET_CODE (XEXP (addr, 0)) == REG
&& GET_CODE (XEXP (addr, 1)) == CONST_INT
&& INTVAL (XEXP (addr, 1)) < 32767)
return -4;
- /* On the H8/300H, abs:16 is two bytes shorter than the
+ /* On the H8/300H and H8/300S, abs:16 is two bytes shorter than the
more general abs:24. */
- if (TARGET_H8300H
+ if ((TARGET_H8300H || TARGET_H8300S)
&& GET_CODE (addr) == SYMBOL_REF
&& TINY_DATA_NAME_P (XSTR (addr, 0)))
return -2;
|| ((INTVAL (SET_SRC (pat)) >> 16) & 0xffff) == 0))
return -2;
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
{
int val = INTVAL (SET_SRC (pat));
return -(20 - INTVAL (XEXP (src, 1)) * 2);
/* Similarly for HImode and SImode shifts by
- small constants on the H8/300H. */
- if (TARGET_H8300H
+ small constants on the H8/300H and H8/300S. */
+ if ((TARGET_H8300H || TARGET_H8300S)
&& (mode == HImode || mode == SImode)
&& INTVAL (XEXP (src, 1)) <= 4)
return -(20 - INTVAL (XEXP (src, 1)) * 2);
"-D__LONG_MAX__=2147483647L -D__LONG_LONG_MAX__=2147483647L"
#define CPP_SPEC \
- "%{!mh:-D__H8300__} %{mh:-D__H8300H__} \
- %{!mh:-D__SIZE_TYPE__=unsigned\\ int -D__PTRDIFF_TYPE__=int} \
+ "%{!mh:%{!ms:-D__H8300__}} %{mh:-D__H8300H__} %{ms:-D__H8300S__} \
+ %{!mh:%{!ms:-D__SIZE_TYPE__=unsigned\\ int -D__PTRDIFF_TYPE__=int}} \
%{mh:-D__SIZE_TYPE__=unsigned\\ long -D__PTRDIFF_TYPE__=long} \
- %{!mh:-Acpu(h8300) -Amachine(h8300)} %{mh:-Acpu(h8300h) -Amachine(h8300h)} \
+ %{ms:-D__SIZE_TYPE__=unsigned\\ long -D__PTRDIFF_TYPE__=long} \
+ %{!mh:%{!ms:-Acpu(h8300) -Amachine(h8300)}} \
+ %{mh:-Acpu(h8300h) -Amachine(h8300h)} \
+ %{ms:-Acpu(h8300s) -Amachine(h8300s)} \
%{!mint32:-D__INT_MAX__=32767} %{mint32:-D__INT_MAX__=2147483647}"
-#define LINK_SPEC "%{mh:-m h8300h}"
+#define LINK_SPEC "%{mh:-m h8300h} %{ms:-m h8300s}"
#define LIB_SPEC "%{mrelax:-relax} %{g:-lg} %{!p:%{!pg:-lc}}%{p:-lc_p}%{pg:-lc_p}"
#define TARGET_RTL_DUMP (target_flags & 2048)
/* Select between the h8/300 and h8/300h cpus. */
-#define TARGET_H8300 (! TARGET_H8300H)
+#define TARGET_H8300 (! TARGET_H8300H && ! TARGET_H8300S)
#define TARGET_H8300H (target_flags & 4096)
+#define TARGET_H8300S (target_flags & 1)
/* Align all values on the h8/300h the same way as the h8/300. Specifically,
32 bit and larger values are aligned on 16 bit boundaries.
An empty string NAME is used to identify the default VALUE. */
#define TARGET_SWITCHES \
- { {"int32",8}, \
+ { {"s",1 }, \
+ {"no-s",-1}, \
+ {"int32",8}, \
{"addresses",64 }, \
{"quickcall",128}, \
{"no-quickcall",-128}, \
Note that this is not necessarily the width of data type `int';
if using 16-bit ints on a 68000, this would still be 32.
But on a machine with 16-bit registers, this would be 16. */
-#define BITS_PER_WORD (TARGET_H8300H ? 32 : 16)
+#define BITS_PER_WORD (TARGET_H8300H || TARGET_H8300S ? 32 : 16)
#define MAX_BITS_PER_WORD 32
/* Width of a word, in units (bytes). */
-#define UNITS_PER_WORD (TARGET_H8300H ? 4 : 2)
+#define UNITS_PER_WORD (TARGET_H8300H || TARGET_H8300S ? 4 : 2)
#define MIN_UNITS_PER_WORD 2
/* Width in bits of a pointer.
See also the macro `Pmode' defined below. */
-#define POINTER_SIZE (TARGET_H8300H ? 32 : 16)
+#define POINTER_SIZE (TARGET_H8300H || TARGET_H8300S ? 32 : 16)
#define SHORT_TYPE_SIZE 16
#define INT_TYPE_SIZE (TARGET_INT32 ? 32 : 16)
#define MAX_FIXED_MODE_SIZE 32
/* Allocation boundary (in *bits*) for storing arguments in argument list. */
-#define PARM_BOUNDARY (TARGET_H8300H ? 32 : 16)
+#define PARM_BOUNDARY (TARGET_H8300H || TARGET_H8300S ? 32 : 16)
/* Allocation boundary (in *bits*) for the code of a function. */
#define FUNCTION_BOUNDARY 16
/* No data type wants to be aligned rounder than this.
32 bit values are aligned as such on the 300h for speed. */
#define BIGGEST_ALIGNMENT \
-((TARGET_H8300H && ! TARGET_ALIGN_300) ? 32 : 16)
+(((TARGET_H8300H || TARGET_H8300S) && ! TARGET_ALIGN_300) ? 32 : 16)
/* No structure field wants to be aligned rounder than this. */
#define BIGGEST_FIELD_ALIGNMENT \
-((TARGET_H8300H && ! TARGET_ALIGN_300) ? 32 : 16)
+(((TARGET_H8300H || TARGET_H8300S) && ! TARGET_ALIGN_300) ? 32 : 16)
/* The stack goes in 16/32 bit lumps. */
#define STACK_BOUNDARY (TARGET_H8300 ? 16 : 32)
#define INITIALIZE_TRAMPOLINE(TRAMP, FNADDR, CXT) \
{ \
- enum machine_mode mode = TARGET_H8300H ? SImode : HImode; \
- emit_move_insn (gen_rtx (MEM, mode, plus_constant ((TRAMP), 2)), CXT); \
- emit_move_insn (gen_rtx (MEM, mode, plus_constant ((TRAMP), 6)), FNADDR); \
- if (TARGET_H8300H) \
+ enum machine_mode mode = TARGET_H8300H || TARGET_H8300S? SImode : HImode; \
+ emit_move_insn (gen_rtx (MEM, mode, plus_constant ((TRAMP), 2)), CXT); \
+ emit_move_insn (gen_rtx (MEM, mode, plus_constant ((TRAMP), 6)), FNADDR); \
+ if (TARGET_H8300H || TARGET_H8300S) \
emit_move_insn (gen_rtx (MEM, QImode, plus_constant ((TRAMP), 6)), GEN_INT (0x5A)); \
}
\f
/* Max number of bytes we can move from memory to memory
in one reasonably fast instruction. */
-#define MOVE_MAX (TARGET_H8300H ? 4 : 2)
+#define MOVE_MAX (TARGET_H8300H || TARGET_H8300S ? 4 : 2)
#define MAX_MOVE_MAX 4
/* Define this if zero-extension is slow (more than one real instruction). */
/* Specify the machine mode that pointers have.
After generation of rtl, the compiler makes no further distinction
between pointers and any other objects of this machine mode. */
-#define Pmode (TARGET_H8300H ? SImode : HImode)
+#define Pmode (TARGET_H8300H || TARGET_H8300S ? SImode : HImode)
/* ANSI C types.
We use longs for the 300h because ints can be 16 or 32.
if (do_movsi (operands))
DONE;
}
- else /* TARGET_H8300H */
+ else
{
/* One of the ops has to be in a register. */
if (!register_operand (operand1, SImode)
if (do_movsi (operands))
DONE;
}
- else /* TARGET_H8300H */
+ else
{
/* One of the ops has to be in a register. */
if (!register_operand (operand1, SFmode)
(define_insn "movsi_h8300h"
[(set (match_operand:SI 0 "general_operand_dst" "=r,r,r,m,<,r")
(match_operand:SI 1 "general_operand_src" "I,r,im,r,r,>"))]
- "TARGET_H8300H
+ "(TARGET_H8300H || TARGET_H8300S)
&& (register_operand (operands[0], SImode)
|| register_operand (operands[1], SImode))"
"*
(define_insn "movsf_h8300h"
[(set (match_operand:SF 0 "general_operand_dst" "=r,r,r,m,<,r")
(match_operand:SF 1 "general_operand_src" "I,r,im,r,r,>"))]
- "TARGET_H8300H
+ "(TARGET_H8300H || TARGET_H8300S)
&& (register_operand (operands[0], SFmode)
|| register_operand (operands[1], SFmode))"
"@
(define_insn "tstsi"
[(set (cc0) (match_operand:SI 0 "register_operand" "r"))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"mov.l %S0,%S0"
[(set_attr "length" "2")
(set_attr "cc" "set")])
{
/* Force operand1 into a register if we're compiling
for the h8/300. */
- if (GET_CODE (operands[1]) != REG && !TARGET_H8300H)
+ if (GET_CODE (operands[1]) != REG && TARGET_H8300)
operands[1] = force_reg (HImode, operands[1]);
}")
[(set (cc0)
(compare:HI (match_operand:HI 0 "register_operand" "r,r")
(match_operand:HI 1 "nonmemory_operand" "r,n")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"cmp.w %T1,%T0"
[(set_attr "length" "2,4")
(set_attr "cc" "compare,compare")])
[(set (cc0)
(compare:SI (match_operand:SI 0 "register_operand" "r,r")
(match_operand:SI 1 "nonmemory_operand" "r,i")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"cmp.l %S1,%S0"
[(set_attr "length" "2,6")
(set_attr "cc" "compare,compare")])
[(set (match_operand:HI 0 "register_operand" "=r,r")
(plus:HI (match_operand:HI 1 "register_operand" "%0,0")
(match_operand:HI 2 "nonmemory_operand" "n,r")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
add.w %T2,%T0
add.w %T2,%T0"
[(set (match_operand:SI 0 "register_operand" "=r")
(plus:SI (match_operand:SI 1 "register_operand" "%0")
(match_operand:SI 2 "adds_subs_operand" "n")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"* return output_adds_subs (operands);"
[(set_attr "cc" "none_0hit")
(set (attr "length")
[(set (match_operand:SI 0 "register_operand" "=r,r")
(plus:SI (match_operand:SI 1 "register_operand" "%0,0")
(match_operand:SI 2 "nonmemory_operand" "i,r")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
add.l %S2,%S0
add.l %S2,%S0"
[(set (match_operand:HI 0 "register_operand" "=r,&r")
(minus:HI (match_operand:HI 1 "general_operand" "0,0")
(match_operand:HI 2 "nonmemory_operand" "r,n")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
sub.w %T2,%T0
sub.w %T2,%T0"
[(set (match_operand:SI 0 "register_operand" "=r")
(minus:SI (match_operand:SI 1 "general_operand" "0")
(match_operand:SI 2 "adds_subs_operand" "n")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"*
{
operands[2] = GEN_INT (-INTVAL (operands[2]));
[(set (match_operand:SI 0 "register_operand" "=r,r")
(minus:SI (match_operand:SI 1 "general_operand" "0,0")
(match_operand:SI 2 "nonmemory_operand" "r,i")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
sub.l %S2,%S0
sub.l %S2,%S0"
[(set (match_operand:HI 0 "register_operand" "=r")
(mult:HI (sign_extend:HI (match_operand:QI 1 "general_operand" "%0"))
(sign_extend:HI (match_operand:QI 2 "register_operand" "r"))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"mulxs.b %X2,%T0"
[(set_attr "length" "4")
(set_attr "cc" "set_zn_c0")])
[(set (match_operand:SI 0 "register_operand" "=r")
(mult:SI (sign_extend:SI (match_operand:HI 1 "general_operand" "%0"))
(sign_extend:SI (match_operand:HI 2 "register_operand" "r"))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"mulxs.w %T2,%S0"
[(set_attr "length" "4")
(set_attr "cc" "set_zn_c0")])
[(set (match_operand:SI 0 "register_operand" "=r")
(mult:SI (zero_extend:SI (match_operand:HI 1 "general_operand" "%0"))
(zero_extend:SI (match_operand:HI 2 "register_operand" "r"))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"mulxu.w %T2,%S0"
[(set_attr "length" "2")
(set_attr "cc" "none_0hit")])
(udiv:SI
(match_operand:SI 1 "general_operand" "0")
(zero_extend:SI (match_operand:HI 2 "register_operand" "r")))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"divxu.w %T2,%S0"
[(set_attr "length" "2")
(set_attr "cc" "clobber")])
(div:SI
(match_operand:SI 1 "general_operand" "0")
(sign_extend:SI (match_operand:HI 2 "register_operand" "r")))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"divxs.w %T2,%S0"
[(set_attr "length" "4")
(set_attr "cc" "clobber")])
(mod:HI
(match_operand:HI 1 "general_operand" "0")
(sign_extend:HI (match_operand:QI 2 "register_operand" "r")))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"divxs.b %X2,%T0\;mov %t0,%s0"
[(set_attr "length" "6")
(set_attr "cc" "clobber")])
(umod:SI
(match_operand:SI 1 "general_operand" "0")
(zero_extend:SI (match_operand:HI 2 "register_operand" "r")))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"divxu.w %T2,%S0\;mov %e0,%f0"
[(set_attr "length" "4")
(set_attr "cc" "clobber")])
(mod:SI
(match_operand:SI 1 "general_operand" "0")
(sign_extend:SI (match_operand:HI 2 "register_operand" "r")))))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"divxs.w %T2,%S0\;mov %e0,%f0"
[(set_attr "length" "6")
(set_attr "cc" "clobber")])
output_asm_insn (\"and %t2,%t0\", operands);
return \"\";
}
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return \"and.w %T2,%T0\";
return \"and %s2,%s0\;and %t2,%t0;\";
}"
those bits aren't going to change, or they're
going to be zero'd out, then we can work on the
low-order bits. */
- if (TARGET_H8300H
+ if ((TARGET_H8300H || TARGET_H8300S)
&& ((i & 0xffff0000) != 0xffff0000
|| (i & 0xffff0000) == 0x00000000))
return \"and.l %S2,%S0\";
output_asm_insn (\"and %z2,%z0\", operands);
return \"\";
}
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return \"and.l %S2,%S0\";
return \"and %w2,%w0\;and %x2,%x0\;and %y2,%y0\;and %z2,%z0\;\";
}"
output_asm_insn (\"or %t2,%t0\", operands);
return \"\";
}
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return \"or.w %T2,%T0\";
return \"or %s2,%s0\;or %t2,%t0; %2 or2\";
}"
upper 16bits of 32bit registers. However, if
those bits aren't going to change, then we can
work on the low-order bits. */
- if (TARGET_H8300H
+ if ((TARGET_H8300H || TARGET_H8300S)
&& (i & 0xffff0000) != 0x00000000)
return \"or.l %S2,%S0\";
output_asm_insn (\"or %z2,%z0\", operands);
return \"\";
}
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return \"or.l %S2,%S0\";
return \"or %w2,%w0\;or %x2,%x0\;or %y2,%y0\;or %z2,%z0\;\";
}"
output_asm_insn (\"xor %t2,%t0\", operands);
return \"\";
}
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return \"xor.w %T2,%T0\";
return \"xor %s2,%s0\;xor %t2,%t0\";
}"
upper 16bits of 32bit registers. However, if
those bits aren't going to change, then we can
work on the low-order bits. */
- if (TARGET_H8300H
+ if ((TARGET_H8300H || TARGET_H8300S)
&& (i & 0xffff0000) != 0x00000000)
return \"xor.l %S2,%S0\";
output_asm_insn (\"xor %z2,%z0\", operands);
return \"\";
}
- if (TARGET_H8300H)
+ if (TARGET_H8300H || TARGET_H8300S)
return \"xor.l %S2,%S0\";
return \"xor %w2,%w0\;xor %x2,%x0\;xor %y2,%y0\;xor %z2,%z0\;\";
}"
(define_insn "neghi2_h8300h"
[(set (match_operand:HI 0 "register_operand" "=r")
(neg:HI (match_operand:HI 1 "general_operand" "0")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"neg %T0"
[(set_attr "length" "2")
(set_attr "cc" "set_zn_c0")])
(define_insn "negsi2_h8300h"
[(set (match_operand:SI 0 "register_operand" "=r")
(neg:SI (match_operand:SI 1 "general_operand" "0")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"neg %S0"
[(set_attr "length" "2")
(set_attr "cc" "set_zn_c0")])
}"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 4)
(const_int 2)))])
}"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 8)
(const_int 2)))])
(define_insn "tablejump_h8300h"
[(set (pc) (match_operand:SI 0 "register_operand" "r"))
(use (label_ref (match_operand 1 "" "")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"jmp @%0"
[(set_attr "cc" "none")
(set_attr "length" "2")])
(define_insn "indirect_jump_h8300h"
[(set (pc) (match_operand:SI 0 "jump_address_operand" "Vr"))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"jmp @%0"
[(set_attr "cc" "none")
(set_attr "length" "2")])
(define_insn ""
[(set (match_operand:SI 0 "register_operand" "=r,r")
(zero_extend:SI (match_operand:HI 1 "general_operand_src" "0,g>")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
extu.l %S0
mov.w %T1,%T0\;extu.l %S0"
(define_insn ""
[(set (match_operand:HI 0 "register_operand" "=r,r")
(sign_extend:HI (match_operand:QI 1 "general_operand_src" "0,g>")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
exts.w %T0
mov.b %R1,%s0\;exts.w %T0"
(define_insn ""
[(set (match_operand:SI 0 "register_operand" "=r,r")
(sign_extend:SI (match_operand:HI 1 "general_operand_src" "0,g>")))]
- "TARGET_H8300H"
+ "TARGET_H8300H || TARGET_H8300S"
"@
exts.l %S0
mov.w %T1,%T0\;exts.l %S0"
(match_operand:SI 1 "bit_operand" "Ur")
(match_operand:SI 2 "const_int_operand" "n")) 0))
(const_int 1)))]
- "TARGET_H8300H && INTVAL (operands[2]) < 16"
+ "(TARGET_H8300H || TARGET_H8300S)
+ && INTVAL (operands[2]) < 16"
"sub.w %0,%0\;bild %Z2,%Y1\;bst #0,%X0"
[(set_attr "cc" "clobber")
(set_attr "length" "8")])
"* return output_simode_bld (0, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
"* return output_simode_bld (0, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
"* return output_simode_bld (0, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
"* return output_simode_bld (1, 1, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
(define_insn ""
"* return output_simode_bld (1, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
"* return output_simode_bld (1, 1, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
(define_insn ""
"* return output_simode_bld (1, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
"* return output_simode_bld (1, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
"* return output_simode_bld (1, 0, operands);"
[(set_attr "cc" "clobber")
(set (attr "length")
- (if_then_else (eq (symbol_ref "TARGET_H8300H") (const_int 0))
+ (if_then_else (eq (symbol_ref "TARGET_H8300H || TARGET_H8300S")
+ (const_int 0))
(const_int 10)
(const_int 8)))])
#define S2P r6
#endif
-#ifdef __H8300H__
+#if defined (__H8300H__) || defined (__H8300S__)
#define MOVP mov.l /* pointers are 32 bits */
#define ADDP add.l
#define CMPP cmp.l
.h8300h
#endif
+#ifdef __H8300S__
+ .h8300s
+#endif
+
.section .text
.align 2
#else /* __H8300H__ */
+#ifdef __H8300H__
.h8300h
+#endif
+
+#ifdef __H8300S__
+ .h8300s
+#endif
.global ___mulsi3
___mulsi3:
echo '#endif' >> fp-bit.c
cat $(srcdir)/config/fp-bit.c >> fp-bit.c
-MULTILIB_OPTIONS = mh mint32
-MULTILIB_DIRNAMES = h8300h int32
+MULTILIB_OPTIONS = mh/ms mint32
+MULTILIB_DIRNAMES = h8300h h8300s int32
LIBGCC = stmp-multilib
INSTALL_LIBGCC = install-multilib