alpha.c (xfloating_ops, [...]): New.

* config/alpha/alpha.c (xfloating_ops, vax_cvt_ops): New.
        (alpha_lookup_xfloating_lib_func): Use them, return rtx.
        (alpha_emit_xfloating_arith): Update to match.
        (alpha_emit_xfloating_compare): Likewise.
        (alpha_emit_xfloating_cvt): Likewise.
        (alpha_emit_xfloating_libcall): Take already built symbol,
        mark call const.
        * config/alpha/alpha.md (extendsftf2, extenddftf2): Take
        op1 in a register.

From-SVN: r79371
This commit is contained in:
Richard Henderson 2004-03-11 23:14:56 -08:00 committed by Richard Henderson
parent 009368dba6
commit 75959f0a1d
3 changed files with 76 additions and 80 deletions

View file

@ -1,3 +1,15 @@
2004-03-11 Richard Henderson <rth@redhat.com>
* config/alpha/alpha.c (xfloating_ops, vax_cvt_ops): New.
(alpha_lookup_xfloating_lib_func): Use them, return rtx.
(alpha_emit_xfloating_arith): Update to match.
(alpha_emit_xfloating_compare): Likewise.
(alpha_emit_xfloating_cvt): Likewise.
(alpha_emit_xfloating_libcall): Take already built symbol,
mark call const.
* config/alpha/alpha.md (extendsftf2, extenddftf2): Take
op1 in a register.
2004-03-11 Richard Henderson <rth@redhat.com>
PR target/14539

View file

@ -3564,85 +3564,65 @@ alpha_split_conditional_move (enum rtx_code code, rtx dest, rtx cond,
/* Look up the function X_floating library function name for the
given operation. */
static const char *
struct xfloating_op GTY(())
{
const enum rtx_code code;
const char *const GTY((skip(""))) osf_func;
const char *const GTY((skip(""))) vms_func;
rtx libcall;
};
static GTY(()) struct xfloating_op xfloating_ops[] =
{
{ PLUS, "_OtsAddX", "OTS$ADD_X", 0 },
{ MINUS, "_OtsSubX", "OTS$SUB_X", 0 },
{ MULT, "_OtsMulX", "OTS$MUL_X", 0 },
{ DIV, "_OtsDivX", "OTS$DIV_X", 0 },
{ EQ, "_OtsEqlX", "OTS$EQL_X", 0 },
{ NE, "_OtsNeqX", "OTS$NEQ_X", 0 },
{ LT, "_OtsLssX", "OTS$LSS_X", 0 },
{ LE, "_OtsLeqX", "OTS$LEQ_X", 0 },
{ GT, "_OtsGtrX", "OTS$GTR_X", 0 },
{ GE, "_OtsGeqX", "OTS$GEQ_X", 0 },
{ FIX, "_OtsCvtXQ", "OTS$CVTXQ", 0 },
{ FLOAT, "_OtsCvtQX", "OTS$CVTQX", 0 },
{ UNSIGNED_FLOAT, "_OtsCvtQUX", "OTS$CVTQUX", 0 },
{ FLOAT_EXTEND, "_OtsConvertFloatTX", "OTS$CVT_FLOAT_T_X", 0 },
{ FLOAT_TRUNCATE, "_OtsConvertFloatXT", "OTS$CVT_FLOAT_X_T", 0 }
};
static GTY(()) struct xfloating_op vax_cvt_ops[] =
{
{ FLOAT_EXTEND, "_OtsConvertFloatGX", "OTS$CVT_FLOAT_G_X", 0 },
{ FLOAT_TRUNCATE, "_OtsConvertFloatXG", "OTS$CVT_FLOAT_X_G", 0 }
};
static rtx
alpha_lookup_xfloating_lib_func (enum rtx_code code)
{
struct xfloating_op
{
const enum rtx_code code;
const char *const func;
};
static const struct xfloating_op vms_xfloating_ops[] =
{
{ PLUS, "OTS$ADD_X" },
{ MINUS, "OTS$SUB_X" },
{ MULT, "OTS$MUL_X" },
{ DIV, "OTS$DIV_X" },
{ EQ, "OTS$EQL_X" },
{ NE, "OTS$NEQ_X" },
{ LT, "OTS$LSS_X" },
{ LE, "OTS$LEQ_X" },
{ GT, "OTS$GTR_X" },
{ GE, "OTS$GEQ_X" },
{ FIX, "OTS$CVTXQ" },
{ FLOAT, "OTS$CVTQX" },
{ UNSIGNED_FLOAT, "OTS$CVTQUX" },
{ FLOAT_EXTEND, "OTS$CVT_FLOAT_T_X" },
{ FLOAT_TRUNCATE, "OTS$CVT_FLOAT_X_T" },
};
static const struct xfloating_op osf_xfloating_ops[] =
{
{ PLUS, "_OtsAddX" },
{ MINUS, "_OtsSubX" },
{ MULT, "_OtsMulX" },
{ DIV, "_OtsDivX" },
{ EQ, "_OtsEqlX" },
{ NE, "_OtsNeqX" },
{ LT, "_OtsLssX" },
{ LE, "_OtsLeqX" },
{ GT, "_OtsGtrX" },
{ GE, "_OtsGeqX" },
{ FIX, "_OtsCvtXQ" },
{ FLOAT, "_OtsCvtQX" },
{ UNSIGNED_FLOAT, "_OtsCvtQUX" },
{ FLOAT_EXTEND, "_OtsConvertFloatTX" },
{ FLOAT_TRUNCATE, "_OtsConvertFloatXT" },
};
const struct xfloating_op *ops;
const long n = ARRAY_SIZE (osf_xfloating_ops);
struct xfloating_op *ops = xfloating_ops;
long n = ARRAY_SIZE (xfloating_ops);
long i;
/* How irritating. Nothing to key off for the table. Hardcode
knowledge of the G_floating routines. */
if (TARGET_FLOAT_VAX)
/* How irritating. Nothing to key off for the main table. */
if (TARGET_FLOAT_VAX && (code == FLOAT_EXTEND || code == FLOAT_TRUNCATE))
{
if (TARGET_ABI_OPEN_VMS)
{
if (code == FLOAT_EXTEND)
return "OTS$CVT_FLOAT_G_X";
if (code == FLOAT_TRUNCATE)
return "OTS$CVT_FLOAT_X_G";
}
else
{
if (code == FLOAT_EXTEND)
return "_OtsConvertFloatGX";
if (code == FLOAT_TRUNCATE)
return "_OtsConvertFloatXG";
}
ops = vax_cvt_ops;
n = ARRAY_SIZE (vax_cvt_ops);
}
if (TARGET_ABI_OPEN_VMS)
ops = vms_xfloating_ops;
else
ops = osf_xfloating_ops;
for (i = 0; i < n; ++i)
if (ops[i].code == code)
return ops[i].func;
for (i = 0; i < n; ++i, ++ops)
if (ops->code == code)
{
rtx func = ops->libcall;
if (!func)
{
func = init_one_libfunc (TARGET_ABI_OPEN_VMS
? ops->vms_func : ops->osf_func);
ops->libcall = func;
}
return func;
}
abort();
}
@ -3688,7 +3668,7 @@ alpha_compute_xfloating_mode_arg (enum rtx_code code,
TFmode arguments are passed in two integer registers (as opposed to
indirect); TFmode return values appear in R16+R17.
FUNC is the function name to call.
FUNC is the function to call.
TARGET is where the output belongs.
OPERANDS are the inputs.
NOPERANDS is the count of inputs.
@ -3696,7 +3676,7 @@ alpha_compute_xfloating_mode_arg (enum rtx_code code,
*/
static void
alpha_emit_xfloating_libcall (const char *func, rtx target, rtx operands[],
alpha_emit_xfloating_libcall (rtx func, rtx target, rtx operands[],
int noperands, rtx equiv)
{
rtx usage = NULL_RTX, tmp, reg;
@ -3750,10 +3730,11 @@ alpha_emit_xfloating_libcall (const char *func, rtx target, rtx operands[],
abort ();
}
tmp = gen_rtx_MEM (QImode, init_one_libfunc (func));
tmp = gen_rtx_MEM (QImode, func);
tmp = emit_call_insn (GEN_CALL_VALUE (reg, tmp, const0_rtx,
const0_rtx, const0_rtx));
CALL_INSN_FUNCTION_USAGE (tmp) = usage;
CONST_OR_PURE_CALL_P (tmp) = 1;
tmp = get_insns ();
end_sequence ();
@ -3766,7 +3747,7 @@ alpha_emit_xfloating_libcall (const char *func, rtx target, rtx operands[],
void
alpha_emit_xfloating_arith (enum rtx_code code, rtx operands[])
{
const char *func;
rtx func;
int mode;
rtx out_operands[3];
@ -3786,7 +3767,7 @@ alpha_emit_xfloating_arith (enum rtx_code code, rtx operands[])
static rtx
alpha_emit_xfloating_compare (enum rtx_code code, rtx op0, rtx op1)
{
const char *func;
rtx func;
rtx out, operands[2];
func = alpha_lookup_xfloating_lib_func (code);
@ -3810,7 +3791,7 @@ alpha_emit_xfloating_cvt (enum rtx_code orig_code, rtx operands[])
{
int noperands = 1, mode;
rtx out_operands[2];
const char *func;
rtx func;
enum rtx_code code = orig_code;
if (code == UNSIGNED_FIX)

View file

@ -2630,9 +2630,12 @@
st%- %1,%0"
[(set_attr "type" "fcpys,fld,fst")])
;; Use register_operand for operand 1 to prevent compress_float_constant
;; from doing something silly. When optimizing we'll put things back
;; together anyway.
(define_expand "extendsftf2"
[(use (match_operand:TF 0 "register_operand" ""))
(use (match_operand:SF 1 "general_operand" ""))]
(use (match_operand:SF 1 "register_operand" ""))]
"TARGET_HAS_XFLOATING_LIBS"
{
rtx tmp = gen_reg_rtx (DFmode);
@ -2643,7 +2646,7 @@
(define_expand "extenddftf2"
[(use (match_operand:TF 0 "register_operand" ""))
(use (match_operand:DF 1 "general_operand" ""))]
(use (match_operand:DF 1 "register_operand" ""))]
"TARGET_HAS_XFLOATING_LIBS"
"alpha_emit_xfloating_cvt (FLOAT_EXTEND, operands); DONE;")