OSDN Git Service

*** empty log message ***
[pf3gnuchains/gcc-fork.git] / gcc / optabs.c
1 /* Expand the basic unary and binary arithmetic operations, for GNU compiler.
2    Copyright (C) 1987, 1988, 1992 Free Software Foundation, Inc.
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
18 the Free Software Foundation, 675 Mass Ave, Cambridge, MA 02139, USA.  */
19
20
21 #include "config.h"
22 #include "rtl.h"
23 #include "tree.h"
24 #include "flags.h"
25 #include "insn-flags.h"
26 #include "insn-codes.h"
27 #include "expr.h"
28 #include "insn-config.h"
29 #include "recog.h"
30
31 /* Each optab contains info on how this target machine
32    can perform a particular operation
33    for all sizes and kinds of operands.
34
35    The operation to be performed is often specified
36    by passing one of these optabs as an argument.
37
38    See expr.h for documentation of these optabs.  */
39
40 optab add_optab;
41 optab sub_optab;
42 optab smul_optab;
43 optab smul_widen_optab;
44 optab umul_widen_optab;
45 optab sdiv_optab;
46 optab sdivmod_optab;
47 optab udiv_optab;
48 optab udivmod_optab;
49 optab smod_optab;
50 optab umod_optab;
51 optab flodiv_optab;
52 optab ftrunc_optab;
53 optab and_optab;
54 optab ior_optab;
55 optab xor_optab;
56 optab ashl_optab;
57 optab lshr_optab;
58 optab lshl_optab;
59 optab ashr_optab;
60 optab rotl_optab;
61 optab rotr_optab;
62 optab smin_optab;
63 optab smax_optab;
64 optab umin_optab;
65 optab umax_optab;
66
67 optab mov_optab;
68 optab movstrict_optab;
69
70 optab neg_optab;
71 optab abs_optab;
72 optab one_cmpl_optab;
73 optab ffs_optab;
74 optab sqrt_optab;
75
76 optab cmp_optab;
77 optab ucmp_optab;  /* Used only for libcalls for unsigned comparisons.  */
78 optab tst_optab;
79
80 optab strlen_optab;
81
82 /* SYMBOL_REF rtx's for the library functions that are called
83    implicitly and not via optabs.  */
84
85 rtx extendsfdf2_libfunc;
86 rtx truncdfsf2_libfunc;
87 rtx memcpy_libfunc;
88 rtx bcopy_libfunc;
89 rtx memcmp_libfunc;
90 rtx bcmp_libfunc;
91 rtx memset_libfunc;
92 rtx bzero_libfunc;
93 rtx eqsf2_libfunc;
94 rtx nesf2_libfunc;
95 rtx gtsf2_libfunc;
96 rtx gesf2_libfunc;
97 rtx ltsf2_libfunc;
98 rtx lesf2_libfunc;
99 rtx eqdf2_libfunc;
100 rtx nedf2_libfunc;
101 rtx gtdf2_libfunc;
102 rtx gedf2_libfunc;
103 rtx ltdf2_libfunc;
104 rtx ledf2_libfunc;
105 rtx floatdisf_libfunc;
106 rtx floatsisf_libfunc;
107 rtx floatdidf_libfunc;
108 rtx floatsidf_libfunc;
109 rtx fixsfsi_libfunc;
110 rtx fixsfdi_libfunc;
111 rtx fixdfsi_libfunc;
112 rtx fixdfdi_libfunc;
113 rtx fixunssfsi_libfunc;
114 rtx fixunssfdi_libfunc;
115 rtx fixunsdfsi_libfunc;
116 rtx fixunsdfdi_libfunc;
117
118 /* Indexed by the rtx-code for a conditional (eg. EQ, LT,...)
119    gives the gen_function to make a branch to test that condition.  */
120
121 rtxfun bcc_gen_fctn[NUM_RTX_CODE];
122
123 /* Indexed by the rtx-code for a conditional (eg. EQ, LT,...)
124    gives the insn code to make a store-condition insn
125    to test that condition.  */
126
127 enum insn_code setcc_gen_code[NUM_RTX_CODE];
128
129 static void emit_float_lib_cmp ();
130 \f
131 /* Add a REG_EQUAL note to the last insn in SEQ.  TARGET is being set to
132    the result of operation CODE applied to OP0 (and OP1 if it is a binary
133    operation).
134
135    If the last insn does not set TARGET, don't do anything, but return 1.
136
137    If a previous insn sets TARGET and TARGET is one of OP0 or OP1,
138    don't add the REG_EQUAL note but return 0.  Our caller can then try
139    again, ensuring that TARGET is not one of the operands.  */
140
141 static int
142 add_equal_note (seq, target, code, op0, op1)
143      rtx seq;
144      rtx target;
145      enum rtx_code code;
146      rtx op0, op1;
147 {
148   rtx set;
149   int i;
150   rtx note;
151
152   if ((GET_RTX_CLASS (code) != '1' && GET_RTX_CLASS (code) != '2'
153        && GET_RTX_CLASS (code) != 'c' && GET_RTX_CLASS (code) != '<')
154       || GET_CODE (seq) != SEQUENCE
155       || (set = single_set (XVECEXP (seq, 0, XVECLEN (seq, 0) - 1))) == 0
156       || GET_CODE (target) == ZERO_EXTRACT
157       || (! rtx_equal_p (SET_DEST (set), target)
158           /* For a STRICT_LOW_PART, the REG_NOTE applies to what is inside the
159              SUBREG.  */
160           && (GET_CODE (SET_DEST (set)) != STRICT_LOW_PART
161               || ! rtx_equal_p (SUBREG_REG (XEXP (SET_DEST (set), 0)),
162                                 target))))
163     return 1;
164
165   /* If TARGET is in OP0 or OP1, check if anything in SEQ sets TARGET
166      besides the last insn.  */
167   if (reg_overlap_mentioned_p (target, op0)
168       || (op1 && reg_overlap_mentioned_p (target, op1)))
169     for (i = XVECLEN (seq, 0) - 2; i >= 0; i--)
170       if (reg_set_p (target, XVECEXP (seq, 0, i)))
171         return 0;
172
173   if (GET_RTX_CLASS (code) == '1')
174     note = gen_rtx (code, GET_MODE (target), op0);
175   else
176     note = gen_rtx (code, GET_MODE (target), op0, op1);
177
178   REG_NOTES (XVECEXP (seq, 0, XVECLEN (seq, 0) - 1))
179     = gen_rtx (EXPR_LIST, REG_EQUAL, note,
180                REG_NOTES (XVECEXP (seq, 0, XVECLEN (seq, 0) - 1)));
181
182   return 1;
183 }
184 \f
185 /* Generate code to perform an operation specified by BINOPTAB
186    on operands OP0 and OP1, with result having machine-mode MODE.
187
188    UNSIGNEDP is for the case where we have to widen the operands
189    to perform the operation.  It says to use zero-extension.
190
191    If TARGET is nonzero, the value
192    is generated there, if it is convenient to do so.
193    In all cases an rtx is returned for the locus of the value;
194    this may or may not be TARGET.  */
195
196 rtx
197 expand_binop (mode, binoptab, op0, op1, target, unsignedp, methods)
198      enum machine_mode mode;
199      optab binoptab;
200      rtx op0, op1;
201      rtx target;
202      int unsignedp;
203      enum optab_methods methods;
204 {
205   enum mode_class class;
206   enum machine_mode wider_mode;
207   register rtx temp;
208   int commutative_op = 0;
209   int shift_op = (binoptab->code ==  ASHIFT
210                   || binoptab->code == ASHIFTRT
211                   || binoptab->code == LSHIFT
212                   || binoptab->code == LSHIFTRT
213                   || binoptab->code == ROTATE
214                   || binoptab->code == ROTATERT);
215   rtx last;
216
217   class = GET_MODE_CLASS (mode);
218
219   op0 = protect_from_queue (op0, 0);
220   op1 = protect_from_queue (op1, 0);
221   if (target)
222     target = protect_from_queue (target, 1);
223
224   if (flag_force_mem)
225     {
226       op0 = force_not_mem (op0);
227       op1 = force_not_mem (op1);
228     }
229
230   /* If we are inside an appropriately-short loop and one operand is an
231      expensive constant, force it into a register.  */
232   if (CONSTANT_P (op0) && preserve_subexpressions_p () && rtx_cost (op0) > 2)
233     op0 = force_reg (mode, op0);
234
235   if (CONSTANT_P (op1) && preserve_subexpressions_p () && rtx_cost (op1) > 2)
236     op1 = force_reg (shift_op ? word_mode : mode, op1);
237
238 #if 0  /* Turned off because it seems to be a kludgy method.  */
239   /* If subtracting integer from pointer, and the pointer has a special mode,
240      then change it to an add.  We use the add insn of Pmode for combining
241      integers with pointers, and the sub insn to subtract two pointers.  */
242
243   if (binoptab == sub_optab
244       && GET_MODE (op0) == Pmode && GET_MODE (op1) != Pmode)
245     {
246       op1 = negate_rtx (GET_MODE(op1), op1);
247       binoptab = add_optab;
248     }
249 #endif /* 0 */
250
251   /* Record where to delete back to if we backtrack.  */
252   last = get_last_insn ();
253
254   /* If operation is commutative,
255      try to make the first operand a register.
256      Even better, try to make it the same as the target.
257      Also try to make the last operand a constant.  */
258   if (GET_RTX_CLASS (binoptab->code) == 'c'
259       || binoptab == smul_widen_optab
260       || binoptab == umul_widen_optab)
261     {
262       commutative_op = 1;
263
264       if (((target == 0 || GET_CODE (target) == REG)
265            ? ((GET_CODE (op1) == REG
266                && GET_CODE (op0) != REG)
267               || target == op1)
268            : rtx_equal_p (op1, target))
269           || GET_CODE (op0) == CONST_INT)
270         {
271           temp = op1;
272           op1 = op0;
273           op0 = temp;
274         }
275     }
276
277   /* If we can do it with a three-operand insn, do so.  */
278
279   if (methods != OPTAB_MUST_WIDEN
280       && binoptab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
281     {
282       int icode = (int) binoptab->handlers[(int) mode].insn_code;
283       enum machine_mode mode0 = insn_operand_mode[icode][1];
284       enum machine_mode mode1 = insn_operand_mode[icode][2];
285       rtx pat;
286       rtx xop0 = op0, xop1 = op1;
287
288       if (target)
289         temp = target;
290       else
291         temp = gen_reg_rtx (mode);
292
293       /* If it is a commutative operator and the modes would match
294          if we would swap the operands, we can save the conversions. */
295       if (commutative_op)
296         {
297           if (GET_MODE (op0) != mode0 && GET_MODE (op1) != mode1
298               && GET_MODE (op0) == mode1 && GET_MODE (op1) == mode0)
299             {
300               register rtx tmp;
301
302               tmp = op0; op0 = op1; op1 = tmp;
303               tmp = xop0; xop0 = xop1; xop1 = tmp;
304             }
305         }
306
307       /* In case the insn wants input operands in modes different from
308          the result, convert the operands.  */
309
310       if (GET_MODE (op0) != VOIDmode
311           && GET_MODE (op0) != mode0)
312         xop0 = convert_to_mode (mode0, xop0, unsignedp);
313
314       if (GET_MODE (xop1) != VOIDmode
315           && GET_MODE (xop1) != mode1)
316         xop1 = convert_to_mode (mode1, xop1, unsignedp);
317
318       /* Now, if insn's predicates don't allow our operands, put them into
319          pseudo regs.  */
320
321       if (! (*insn_operand_predicate[icode][1]) (xop0, mode0))
322         xop0 = copy_to_mode_reg (mode0, xop0);
323
324       if (! (*insn_operand_predicate[icode][2]) (xop1, mode1))
325         xop1 = copy_to_mode_reg (mode1, xop1);
326
327       if (! (*insn_operand_predicate[icode][0]) (temp, mode))
328         temp = gen_reg_rtx (mode);
329
330       pat = GEN_FCN (icode) (temp, xop0, xop1);
331       if (pat)
332         {
333           /* If PAT is a multi-insn sequence, try to add an appropriate
334              REG_EQUAL note to it.  If we can't because TEMP conflicts with an
335              operand, call ourselves again, this time without a target.  */
336           if (GET_CODE (pat) == SEQUENCE
337               && ! add_equal_note (pat, temp, binoptab->code, xop0, xop1))
338             {
339               delete_insns_since (last);
340               return expand_binop (mode, binoptab, op0, op1, 0, unsignedp,
341                                    methods);
342             }
343
344           emit_insn (pat);
345           return temp;
346         }
347       else
348         delete_insns_since (last);
349     }
350
351   /* These can be done a word at a time.  */
352   if ((binoptab == and_optab || binoptab == ior_optab || binoptab == xor_optab)
353       && class == MODE_INT
354       && GET_MODE_SIZE (mode) > UNITS_PER_WORD
355       && binoptab->handlers[(int) word_mode].insn_code != CODE_FOR_nothing)
356     {
357       int i;
358       rtx insns;
359       rtx equiv_value;
360
361       /* If TARGET is the same as one of the operands, the REG_EQUAL note
362          won't be accurate, so use a new target.  */
363       if (target == 0 || target == op0 || target == op1)
364         target = gen_reg_rtx (mode);
365
366       start_sequence ();
367
368       /* Do the actual arithmetic.  */
369       for (i = 0; i < GET_MODE_BITSIZE (mode) / BITS_PER_WORD; i++)
370         {
371           rtx target_piece = operand_subword (target, i, 1, mode);
372           rtx x = expand_binop (word_mode, binoptab,
373                                 operand_subword_force (op0, i, mode),
374                                 operand_subword_force (op1, i, mode),
375                                 target_piece, unsignedp, methods);
376           if (target_piece != x)
377             emit_move_insn (target_piece, x);
378         }
379
380       insns = get_insns ();
381       end_sequence ();
382
383       if (binoptab->code != UNKNOWN)
384         equiv_value = gen_rtx (binoptab->code, mode, op0, op1);
385       else
386         equiv_value = 0;
387
388       emit_no_conflict_block (insns, target, op0, op1, equiv_value);
389       return target;
390     }
391
392   /* These can be done a word at a time by propagating carries.  */
393   if ((binoptab == add_optab || binoptab == sub_optab)
394       && class == MODE_INT
395       && GET_MODE_SIZE (mode) >= 2 * UNITS_PER_WORD
396       && binoptab->handlers[(int) word_mode].insn_code != CODE_FOR_nothing)
397     {
398       int i;
399       rtx carry_tmp = gen_reg_rtx (word_mode);
400       optab otheroptab = binoptab == add_optab ? sub_optab : add_optab;
401       int nwords = GET_MODE_BITSIZE (mode) / BITS_PER_WORD;
402       rtx carry_in, carry_out;
403
404       /* We can handle either a 1 or -1 value for the carry.  If STORE_FLAG
405          value is one of those, use it.  Otherwise, use 1 since it is the
406          one easiest to get.  */
407 #if STORE_FLAG_VALUE == 1 || STORE_FLAG_VALUE == -1
408       int normalizep = STORE_FLAG_VALUE;
409 #else
410       int normalizep = 1;
411 #endif
412
413       /* Prepare the operands.  */
414       op0 = force_reg (mode, op0);
415       op1 = force_reg (mode, op1);
416
417       if (target == 0 || GET_CODE (target) != REG
418           || target == op0 || target == op1)
419         target = gen_reg_rtx (mode);
420
421       /* Do the actual arithmetic.  */
422       for (i = 0; i < nwords; i++)
423         {
424           int index = (WORDS_BIG_ENDIAN ? nwords - i - 1 : i);
425           rtx target_piece = operand_subword (target, index, 1, mode);
426           rtx op0_piece = operand_subword_force (op0, index, mode);
427           rtx op1_piece = operand_subword_force (op1, index, mode);
428           rtx x;
429
430           /* Main add/subtract of the input operands.  */
431           x = expand_binop (word_mode, binoptab,
432                             op0_piece, op1_piece,
433                             target_piece, unsignedp, methods);
434           if (x == 0)
435             break;
436
437           if (i + 1 < nwords)
438             {
439               /* Store carry from main add/subtract.  */
440               carry_out = gen_reg_rtx (word_mode);
441               carry_out = emit_store_flag (carry_out,
442                                            binoptab == add_optab ? LTU : GTU,
443                                            x, op0_piece,
444                                            word_mode, 1, normalizep);
445               if (!carry_out)
446                 break;
447             }
448
449           if (i > 0)
450             {
451               /* Add/subtract previous carry to main result.  */
452               x = expand_binop (word_mode,
453                                 normalizep == 1 ? binoptab : otheroptab,
454                                 x, carry_in,
455                                 target_piece, 1, methods);
456               if (target_piece != x)
457                 emit_move_insn (target_piece, x);
458
459               if (i + 1 < nwords)
460                 {
461                   /* THIS CODE HAS NOT BEEN TESTED.  */
462                   /* Get out carry from adding/subtracting carry in.  */
463                   carry_tmp = emit_store_flag (carry_tmp,
464                                                binoptab == add_optab
465                                                  ? LTU : GTU,
466                                                x, carry_in,
467                                                word_mode, 1, normalizep);
468                   /* Logical-ior the two poss. carry together.  */
469                   carry_out = expand_binop (word_mode, ior_optab,
470                                             carry_out, carry_tmp,
471                                             carry_out, 0, methods);
472                   if (!carry_out)
473                     break;
474                 }
475             }
476
477           carry_in = carry_out;
478         }       
479
480       if (i == GET_MODE_BITSIZE (mode) / BITS_PER_WORD)
481         {
482           rtx temp;
483           
484           temp = emit_move_insn (target, target);
485           REG_NOTES (temp) = gen_rtx (EXPR_LIST, REG_EQUAL,
486                                       gen_rtx (binoptab->code, mode, op0, op1),
487                                       REG_NOTES (temp));
488           return target;
489         }
490       else
491         delete_insns_since (last);
492     }
493
494   /* If we want to multiply two two-word values and have normal and widening
495      multiplies of single-word values, we can do this with three smaller
496      multiplications.  Note that we do not make a REG_NO_CONFLICT block here
497      because we are not operating on one word at a time. 
498
499      The multiplication proceeds as follows:
500                                  _______________________
501                                 [__op0_high_|__op0_low__]
502                                  _______________________
503         *                           [__op1_high_|__op1_low__]
504         _______________________________________________
505                                  _______________________
506     (1)                     [__op0_low__*__op1_low__]
507                      _______________________
508     (2a)                [__op0_low__*__op1_high_]
509                      _______________________
510     (2b)                [__op0_high_*__op1_low__]
511          _______________________
512     (3) [__op0_high_*__op1_high_]
513
514
515     This gives a 4-word result.  Since we are only interested in the
516     lower 2 words, partial result (3) and the upper words of (2a) and
517     (2b) don't need to be calculated.  Hence (2a) and (2b) can be
518     calculated using non-widening multiplication.
519
520     (1), however, needs to be calculated with an unsigned widening
521     multiplication.  If this operation is not directly supported we
522     try using a signed widening multiplication and adjust the result.
523     This adjustment works as follows:
524
525       If both operands are positive then no adjustment is needed.
526
527       If the operands have different signs, for example op0_low < 0 and
528       op1_low >= 0, the instruction treats the most significant bit of
529       op0_low as a sign bit instead of a bit with significance
530       2**(BITS_PER_WORD-1), i.e. the instruction multiplies op1_low
531       with 2**BITS_PER_WORD - op0_low, and two's complements the
532       result.  Conclusion: We need to add op1_low * 2**BITS_PER_WORD to
533       the result.
534
535       Similarly, if both operands are negative, we need to add
536       (op0_low + op1_low) * 2**BITS_PER_WORD.
537
538       We use a trick to adjust quickly.  We logically shift op0_low right
539       (op1_low) BITS_PER_WORD-1 steps to get 0 or 1, and add this to
540       op0_high (op1_high) before it is used to calculate 2b (2a).  If no
541       logical shift exists, we do an arithmetic right shift and subtract
542       the 0 or -1.  */
543
544   if (binoptab == smul_optab
545       && class == MODE_INT
546       && GET_MODE_SIZE (mode) == 2 * UNITS_PER_WORD
547       && smul_optab->handlers[(int) word_mode].insn_code != CODE_FOR_nothing
548       && add_optab->handlers[(int) word_mode].insn_code != CODE_FOR_nothing
549       && ((umul_widen_optab->handlers[(int) mode].insn_code
550            != CODE_FOR_nothing)
551           || (smul_widen_optab->handlers[(int) mode].insn_code
552               != CODE_FOR_nothing)))
553     {
554       int low = (WORDS_BIG_ENDIAN ? 1 : 0);
555       int high = (WORDS_BIG_ENDIAN ? 0 : 1);
556       rtx op0_high = operand_subword_force (op0, high, mode);
557       rtx op0_low = operand_subword_force (op0, low, mode);
558       rtx op1_high = operand_subword_force (op1, high, mode);
559       rtx op1_low = operand_subword_force (op1, low, mode);
560       rtx product = 0;
561       rtx op0_xhigh;
562       rtx op1_xhigh;
563
564       /* If the target is the same as one of the inputs, don't use it.  This
565          prevents problems with the REG_EQUAL note.  */
566       if (target == op0 || target == op1)
567         target = 0;
568
569       /* Multiply the two lower words to get a double-word product.
570          If unsigned widening multiplication is available, use that;
571          otherwise use the signed form and compensate.  */
572
573       if (umul_widen_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
574         {
575           product = expand_binop (mode, umul_widen_optab, op0_low, op1_low,
576                                   target, 1, OPTAB_DIRECT);
577
578           /* If we didn't succeed, delete everything we did so far.  */
579           if (product == 0)
580             delete_insns_since (last);
581           else
582             op0_xhigh = op0_high, op1_xhigh = op1_high;
583         }
584
585       if (product == 0
586           && smul_widen_optab->handlers[(int) mode].insn_code
587                != CODE_FOR_nothing)
588         {
589           rtx wordm1 = gen_rtx (CONST_INT, VOIDmode, BITS_PER_WORD - 1);
590           product = expand_binop (mode, smul_widen_optab, op0_low, op1_low,
591                                   target, 1, OPTAB_DIRECT);
592           op0_xhigh = expand_binop (word_mode, lshr_optab, op0_low, wordm1,
593                                     0, 1, OPTAB_DIRECT);
594           if (op0_xhigh)
595             op0_xhigh = expand_binop (word_mode, add_optab, op0_high,
596                                       op0_xhigh, op0_xhigh, 0, OPTAB_DIRECT);
597           else
598             {
599               op0_xhigh = expand_binop (word_mode, ashr_optab, op0_low, wordm1,
600                                         0, 0, OPTAB_DIRECT);
601               if (op0_xhigh)
602                 op0_xhigh = expand_binop (word_mode, sub_optab, op0_high,
603                                           op0_xhigh, op0_xhigh, 0,
604                                           OPTAB_DIRECT);
605             }
606
607           op1_xhigh = expand_binop (word_mode, lshr_optab, op1_low, wordm1,
608                                     0, 1, OPTAB_DIRECT);
609           if (op1_xhigh)
610             op1_xhigh = expand_binop (word_mode, add_optab, op1_high,
611                                       op1_xhigh, op1_xhigh, 0, OPTAB_DIRECT);
612           else
613             {
614               op1_xhigh = expand_binop (word_mode, ashr_optab, op1_low, wordm1,
615                                         0, 0, OPTAB_DIRECT);
616               if (op1_xhigh)
617                 op1_xhigh = expand_binop (word_mode, sub_optab, op1_high,
618                                           op1_xhigh, op1_xhigh, 0,
619                                           OPTAB_DIRECT);
620             }
621         }
622
623       /* If we have been able to directly compute the product of the
624          low-order words of the operands and perform any required adjustments
625          of the operands, we proceed by trying two more multiplications
626          and then computing the appropriate sum.
627
628          We have checked above that the required addition is provided.
629          Full-word addition will normally always succeed, especially if
630          it is provided at all, so we don't worry about its failure.  The
631          multiplication may well fail, however, so we do handle that.  */
632
633       if (product && op0_xhigh && op1_xhigh)
634         {
635           rtx product_piece;
636           rtx product_high = operand_subword (product, high, 1, mode);
637           rtx temp = expand_binop (word_mode, binoptab, op0_low, op1_xhigh, 0,
638                                    0, OPTAB_DIRECT);
639
640           if (temp)
641             {
642               product_piece = expand_binop (word_mode, add_optab, temp,
643                                             product_high, product_high,
644                                             0, OPTAB_LIB_WIDEN);
645               if (product_piece != product_high)
646                 emit_move_insn (product_high, product_piece);
647
648               temp = expand_binop (word_mode, binoptab, op1_low, op0_xhigh, 0,
649                                    0, OPTAB_DIRECT);
650
651               product_piece = expand_binop (word_mode, add_optab, temp,
652                                             product_high, product_high,
653                                             0, OPTAB_LIB_WIDEN);
654               if (product_piece != product_high)
655                 emit_move_insn (product_high, product_piece);
656
657               temp = emit_move_insn (product, product);
658               REG_NOTES (temp) = gen_rtx (EXPR_LIST, REG_EQUAL,
659                                           gen_rtx (MULT, mode, op0, op1),
660                                           REG_NOTES (temp));
661
662               return product;
663             }
664         }
665
666       /* If we get here, we couldn't do it for some reason even though we
667          originally thought we could.  Delete anything we've emitted in
668          trying to do it.  */
669
670       delete_insns_since (last);
671     }
672
673   /* It can't be open-coded in this mode.
674      Use a library call if one is available and caller says that's ok.  */
675
676   if (binoptab->handlers[(int) mode].libfunc
677       && (methods == OPTAB_LIB || methods == OPTAB_LIB_WIDEN))
678     {
679       rtx insns;
680       rtx funexp = binoptab->handlers[(int) mode].libfunc;
681
682       start_sequence ();
683
684       /* Pass 1 for NO_QUEUE so we don't lose any increments
685          if the libcall is cse'd or moved.  */
686       emit_library_call (binoptab->handlers[(int) mode].libfunc,
687                          1, mode, 2, op0, mode, op1,
688                          (shift_op ? word_mode : mode));
689
690       insns = get_insns ();
691       end_sequence ();
692
693       target = gen_reg_rtx (mode);
694       emit_libcall_block (insns, target, hard_libcall_value (mode),
695                           gen_rtx (binoptab->code, mode, op0, op1));
696
697       return target;
698     }
699
700   delete_insns_since (last);
701
702   /* It can't be done in this mode.  Can we do it in a wider mode?  */
703
704   if (! (methods == OPTAB_WIDEN || methods == OPTAB_LIB_WIDEN
705          || methods == OPTAB_MUST_WIDEN))
706     return 0;                   /* Caller says, don't even try.  */
707
708   /* Compute the value of METHODS to pass to recursive calls.
709      Don't allow widening to be tried recursively.  */
710
711   methods = (methods == OPTAB_LIB_WIDEN ? OPTAB_LIB : OPTAB_DIRECT);
712
713   /* Look for a wider mode of the same class for which it appears we can do
714      the operation.  */
715
716   if (class == MODE_INT || class == MODE_FLOAT || class == MODE_COMPLEX_FLOAT)
717     {
718       for (wider_mode = GET_MODE_WIDER_MODE (mode); wider_mode != VOIDmode;
719            wider_mode = GET_MODE_WIDER_MODE (wider_mode))
720         {
721           if ((binoptab->handlers[(int) wider_mode].insn_code
722                != CODE_FOR_nothing)
723               || (methods == OPTAB_LIB
724                   && binoptab->handlers[(int) wider_mode].libfunc))
725             {
726               rtx xop0 = op0, xop1 = op1;
727               int no_extend = 0;
728
729               /* For certain integer operations, we need not actually extend
730                  the narrow operands, as long as we will truncate
731                  the results to the same narrowness.  */
732
733               if ((binoptab == ior_optab || binoptab == and_optab
734                    || binoptab == xor_optab
735                    || binoptab == add_optab || binoptab == sub_optab
736                    || binoptab == smul_optab
737                    || binoptab == ashl_optab || binoptab == lshl_optab)
738                   && class == MODE_INT)
739                 no_extend = 1;
740
741               /* If an operand is a constant integer, we might as well
742                  convert it since that is more efficient than using a SUBREG,
743                  unlike the case for other operands.  */
744
745               if (no_extend && GET_MODE (xop0) != VOIDmode)
746                 xop0 = gen_rtx (SUBREG, wider_mode,
747                                 force_reg (GET_MODE (xop0), xop0), 0);
748               else
749                 xop0 = convert_to_mode (wider_mode, xop0, unsignedp);
750
751               if (no_extend && GET_MODE (xop1) != VOIDmode)
752                 xop1 = gen_rtx (SUBREG, wider_mode,
753                                 force_reg (GET_MODE (xop1), xop1), 0);
754               else
755                 xop1 = convert_to_mode (wider_mode, xop1, unsignedp);
756
757               temp = expand_binop (wider_mode, binoptab, xop0, xop1, 0,
758                                    unsignedp, methods);
759               if (temp)
760                 {
761                   if (class != MODE_INT)
762                     {
763                       if (target == 0)
764                         target = gen_reg_rtx (mode);
765                       convert_move (target, temp, 0);
766                       return target;
767                     }
768                   else
769                     return gen_lowpart (mode, temp);
770                 }
771               else
772                 delete_insns_since (last);
773             }
774         }
775     }
776
777   return 0;
778 }
779 \f
780 /* Expand a binary operator which has both signed and unsigned forms.
781    UOPTAB is the optab for unsigned operations, and SOPTAB is for
782    signed operations.
783
784    If we widen unsigned operands, we may use a signed wider operation instead
785    of an unsigned wider operation, since the result would be the same.  */
786
787 rtx
788 sign_expand_binop (mode, uoptab, soptab, op0, op1, target, unsignedp, methods)
789     enum machine_mode mode;
790     optab uoptab, soptab;
791     rtx op0, op1, target;
792     int unsignedp;
793     enum optab_methods methods;
794 {
795   register rtx temp;
796   optab direct_optab = unsignedp ? uoptab : soptab;
797   struct optab wide_soptab;
798
799   /* Do it without widening, if possible.  */
800   temp = expand_binop (mode, direct_optab, op0, op1, target,
801                        unsignedp, OPTAB_DIRECT);
802   if (temp || methods == OPTAB_DIRECT)
803     return temp;
804
805   /* Try widening to a signed int.  Make a fake signed optab that
806      hides any signed insn for direct use.  */
807   wide_soptab = *soptab;
808   wide_soptab.handlers[(int) mode].insn_code = CODE_FOR_nothing;
809   wide_soptab.handlers[(int) mode].libfunc = 0;
810
811   temp = expand_binop (mode, &wide_soptab, op0, op1, target,
812                        unsignedp, OPTAB_WIDEN);
813
814   /* For unsigned operands, try widening to an unsigned int.  */
815   if (temp == 0 && unsignedp)
816     temp = expand_binop (mode, uoptab, op0, op1, target,
817                          unsignedp, OPTAB_WIDEN);
818   if (temp || methods == OPTAB_WIDEN)
819     return temp;
820
821   /* Use the right width lib call if that exists.  */
822   temp = expand_binop (mode, direct_optab, op0, op1, target, unsignedp, OPTAB_LIB);
823   if (temp || methods == OPTAB_LIB)
824     return temp;
825
826   /* Must widen and use a lib call, use either signed or unsigned.  */
827   temp = expand_binop (mode, &wide_soptab, op0, op1, target,
828                        unsignedp, methods);
829   if (temp != 0)
830     return temp;
831   if (unsignedp)
832     return expand_binop (mode, uoptab, op0, op1, target,
833                          unsignedp, methods);
834   return 0;
835 }
836 \f
837 /* Generate code to perform an operation specified by BINOPTAB
838    on operands OP0 and OP1, with two results to TARG1 and TARG2.
839    We assume that the order of the operands for the instruction
840    is TARG0, OP0, OP1, TARG1, which would fit a pattern like
841    [(set TARG0 (operate OP0 OP1)) (set TARG1 (operate ...))].
842
843    Either TARG0 or TARG1 may be zero, but what that means is that
844    that result is not actually wanted.  We will generate it into
845    a dummy pseudo-reg and discard it.  They may not both be zero.
846
847    Returns 1 if this operation can be performed; 0 if not.  */
848
849 int
850 expand_twoval_binop (binoptab, op0, op1, targ0, targ1, unsignedp)
851      optab binoptab;
852      rtx op0, op1;
853      rtx targ0, targ1;
854      int unsignedp;
855 {
856   enum machine_mode mode = GET_MODE (targ0 ? targ0 : targ1);
857   enum mode_class class;
858   enum machine_mode wider_mode;
859   rtx last;
860
861   class = GET_MODE_CLASS (mode);
862
863   op0 = protect_from_queue (op0, 0);
864   op1 = protect_from_queue (op1, 0);
865
866   if (flag_force_mem)
867     {
868       op0 = force_not_mem (op0);
869       op1 = force_not_mem (op1);
870     }
871
872   /* If we are inside an appropriately-short loop and one operand is an
873      expensive constant, force it into a register.  */
874   if (CONSTANT_P (op0) && preserve_subexpressions_p () && rtx_cost (op0) > 2)
875     op0 = force_reg (mode, op0);
876
877   if (CONSTANT_P (op1) && preserve_subexpressions_p () && rtx_cost (op1) > 2)
878     op1 = force_reg (mode, op1);
879
880   if (targ0)
881     targ0 = protect_from_queue (targ0, 1);
882   else
883     targ0 = gen_reg_rtx (mode);
884   if (targ1)
885     targ1 = protect_from_queue (targ1, 1);
886   else
887     targ1 = gen_reg_rtx (mode);
888
889   /* Record where to go back to if we fail.  */
890   last = get_last_insn ();
891
892   if (binoptab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
893     {
894       int icode = (int) binoptab->handlers[(int) mode].insn_code;
895       enum machine_mode mode0 = insn_operand_mode[icode][1];
896       enum machine_mode mode1 = insn_operand_mode[icode][2];
897       rtx pat;
898       rtx xop0 = op0, xop1 = op1;
899
900       /* In case this insn wants input operands in modes different from the
901          result, convert the operands.  */
902       if (GET_MODE (op0) != VOIDmode && GET_MODE (op0) != mode0)
903         xop0 = convert_to_mode (mode0, xop0, unsignedp);
904
905       if (GET_MODE (op1) != VOIDmode && GET_MODE (op1) != mode1)
906         xop1 = convert_to_mode (mode1, xop1, unsignedp);
907
908       /* Now, if insn doesn't accept these operands, put them into pseudos.  */
909       if (! (*insn_operand_predicate[icode][1]) (xop0, mode0))
910         xop0 = copy_to_mode_reg (mode0, xop0);
911
912       if (! (*insn_operand_predicate[icode][2]) (xop1, mode1))
913         xop1 = copy_to_mode_reg (mode1, xop1);
914
915       /* We could handle this, but we should always be called with a pseudo
916          for our targets and all insns should take them as outputs.  */
917       if (! (*insn_operand_predicate[icode][0]) (targ0, mode)
918           || ! (*insn_operand_predicate[icode][3]) (targ1, mode))
919         abort ();
920         
921       pat = GEN_FCN (icode) (targ0, xop0, xop1, targ1);
922       if (pat)
923         {
924           emit_insn (pat);
925           return 1;
926         }
927       else
928         delete_insns_since (last);
929     }
930
931   /* It can't be done in this mode.  Can we do it in a wider mode?  */
932
933   if (class == MODE_INT || class == MODE_FLOAT || class == MODE_COMPLEX_FLOAT)
934     {
935       for (wider_mode = GET_MODE_WIDER_MODE (mode); wider_mode != VOIDmode;
936            wider_mode = GET_MODE_WIDER_MODE (wider_mode))
937         {
938           if (binoptab->handlers[(int) wider_mode].insn_code
939               != CODE_FOR_nothing)
940             {
941               register rtx t0 = gen_reg_rtx (wider_mode);
942               register rtx t1 = gen_reg_rtx (wider_mode);
943
944               if (expand_twoval_binop (binoptab,
945                                        convert_to_mode (wider_mode, op0,
946                                                         unsignedp),
947                                        convert_to_mode (wider_mode, op1,
948                                                         unsignedp),
949                                        t0, t1, unsignedp))
950                 {
951                   convert_move (targ0, t0, unsignedp);
952                   convert_move (targ1, t1, unsignedp);
953                   return 1;
954                 }
955               else
956                 delete_insns_since (last);
957             }
958         }
959     }
960
961   return 0;
962 }
963 \f
964 /* Generate code to perform an operation specified by UNOPTAB
965    on operand OP0, with result having machine-mode MODE.
966
967    UNSIGNEDP is for the case where we have to widen the operands
968    to perform the operation.  It says to use zero-extension.
969
970    If TARGET is nonzero, the value
971    is generated there, if it is convenient to do so.
972    In all cases an rtx is returned for the locus of the value;
973    this may or may not be TARGET.  */
974
975 rtx
976 expand_unop (mode, unoptab, op0, target, unsignedp)
977      enum machine_mode mode;
978      optab unoptab;
979      rtx op0;
980      rtx target;
981      int unsignedp;
982 {
983   enum mode_class class;
984   enum machine_mode wider_mode;
985   register rtx temp;
986   rtx last = get_last_insn ();
987   rtx pat;
988
989   class = GET_MODE_CLASS (mode);
990
991   op0 = protect_from_queue (op0, 0);
992
993   if (flag_force_mem)
994     {
995       op0 = force_not_mem (op0);
996     }
997
998   if (target)
999     target = protect_from_queue (target, 1);
1000
1001   if (unoptab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
1002     {
1003       int icode = (int) unoptab->handlers[(int) mode].insn_code;
1004       enum machine_mode mode0 = insn_operand_mode[icode][1];
1005       rtx xop0 = op0;
1006
1007       if (target)
1008         temp = target;
1009       else
1010         temp = gen_reg_rtx (mode);
1011
1012       if (GET_MODE (xop0) != VOIDmode
1013           && GET_MODE (xop0) != mode0)
1014         xop0 = convert_to_mode (mode0, xop0, unsignedp);
1015
1016       /* Now, if insn doesn't accept our operand, put it into a pseudo.  */
1017
1018       if (! (*insn_operand_predicate[icode][1]) (xop0, mode0))
1019         xop0 = copy_to_mode_reg (mode0, xop0);
1020
1021       if (! (*insn_operand_predicate[icode][0]) (temp, mode))
1022         temp = gen_reg_rtx (mode);
1023
1024       pat = GEN_FCN (icode) (temp, xop0);
1025       if (pat)
1026         {
1027           if (GET_CODE (pat) == SEQUENCE
1028               && ! add_equal_note (pat, temp, unoptab->code, xop0, 0))
1029             {
1030               delete_insns_since (last);
1031               return expand_unop (mode, unoptab, op0, 0, unsignedp);
1032             }
1033
1034           emit_insn (pat);
1035           
1036           return temp;
1037         }
1038       else
1039         delete_insns_since (last);
1040     }
1041
1042   /* These can be done a word at a time.  */
1043   if (unoptab == one_cmpl_optab
1044       && class == MODE_INT
1045       && GET_MODE_SIZE (mode) > UNITS_PER_WORD
1046       && unoptab->handlers[(int) word_mode].insn_code != CODE_FOR_nothing)
1047     {
1048       int i;
1049       rtx insns;
1050
1051       if (target == 0 || target == op0)
1052         target = gen_reg_rtx (mode);
1053
1054       start_sequence ();
1055
1056       /* Do the actual arithmetic.  */
1057       for (i = 0; i < GET_MODE_BITSIZE (mode) / BITS_PER_WORD; i++)
1058         {
1059           rtx target_piece = operand_subword (target, i, 1, mode);
1060           rtx x = expand_unop (word_mode, unoptab,
1061                                operand_subword_force (op0, i, mode),
1062                                target_piece, unsignedp);
1063           if (target_piece != x)
1064             emit_move_insn (target_piece, x);
1065         }
1066
1067       insns = get_insns ();
1068       end_sequence ();
1069
1070       emit_no_conflict_block (insns, target, op0, 0,
1071                               gen_rtx (unoptab->code, mode, op0));
1072       return target;
1073     }
1074
1075   if (unoptab->handlers[(int) mode].libfunc)
1076     {
1077       rtx insns;
1078       rtx funexp = unoptab->handlers[(int) mode].libfunc;
1079
1080       start_sequence ();
1081
1082       /* Pass 1 for NO_QUEUE so we don't lose any increments
1083          if the libcall is cse'd or moved.  */
1084       emit_library_call (unoptab->handlers[(int) mode].libfunc,
1085                          1, mode, 1, op0, mode);
1086       insns = get_insns ();
1087       end_sequence ();
1088
1089       target = gen_reg_rtx (mode);
1090       emit_libcall_block (insns, target, hard_libcall_value (mode),
1091                           gen_rtx (unoptab->code, mode, op0));
1092
1093       return target;
1094     }
1095
1096   /* It can't be done in this mode.  Can we do it in a wider mode?  */
1097
1098   if (class == MODE_INT || class == MODE_FLOAT || class == MODE_COMPLEX_FLOAT)
1099     {
1100       for (wider_mode = GET_MODE_WIDER_MODE (mode); wider_mode != VOIDmode;
1101            wider_mode = GET_MODE_WIDER_MODE (wider_mode))
1102         {
1103           if ((unoptab->handlers[(int) wider_mode].insn_code
1104                != CODE_FOR_nothing)
1105               || unoptab->handlers[(int) wider_mode].libfunc)
1106             {
1107               rtx xop0 = op0;
1108
1109               /* For certain operations, we need not actually extend
1110                  the narrow operand, as long as we will truncate the
1111                  results to the same narrowness.  */
1112
1113               if ((unoptab == neg_optab || unoptab == one_cmpl_optab)
1114                   && class == MODE_INT)
1115                 xop0 = gen_rtx (SUBREG, wider_mode, force_reg (mode, xop0), 0);
1116               else
1117                 xop0 = convert_to_mode (wider_mode, xop0, unsignedp);
1118               
1119               temp = expand_unop (wider_mode, unoptab, xop0, 0, unsignedp);
1120
1121               if (temp)
1122                 {
1123                   if (class != MODE_INT)
1124                     {
1125                       if (target == 0)
1126                         target = gen_reg_rtx (mode);
1127                       convert_move (target, temp, 0);
1128                       return target;
1129                     }
1130                   else
1131                     return gen_lowpart (mode, temp);
1132                 }
1133               else
1134                 delete_insns_since (last);
1135             }
1136         }
1137     }
1138
1139   return 0;
1140 }
1141 \f
1142 /* Generate an instruction whose insn-code is INSN_CODE,
1143    with two operands: an output TARGET and an input OP0.
1144    TARGET *must* be nonzero, and the output is always stored there.
1145    CODE is an rtx code such that (CODE OP0) is an rtx that describes
1146    the value that is stored into TARGET.  */
1147
1148 void
1149 emit_unop_insn (icode, target, op0, code)
1150      int icode;
1151      rtx target;
1152      rtx op0;
1153      enum rtx_code code;
1154 {
1155   register rtx temp;
1156   enum machine_mode mode0 = insn_operand_mode[icode][1];
1157   rtx pat;
1158
1159   temp = target = protect_from_queue (target, 1);
1160
1161   op0 = protect_from_queue (op0, 0);
1162
1163   if (flag_force_mem)
1164     op0 = force_not_mem (op0);
1165
1166   /* Now, if insn does not accept our operands, put them into pseudos.  */
1167
1168   if (! (*insn_operand_predicate[icode][1]) (op0, mode0))
1169     op0 = copy_to_mode_reg (mode0, op0);
1170
1171   if (! (*insn_operand_predicate[icode][0]) (temp, GET_MODE (temp))
1172       || (flag_force_mem && GET_CODE (temp) == MEM))
1173     temp = gen_reg_rtx (GET_MODE (temp));
1174
1175   pat = GEN_FCN (icode) (temp, op0);
1176
1177   if (GET_CODE (pat) == SEQUENCE && code != UNKNOWN)
1178     add_equal_note (pat, temp, code, op0, 0);
1179   
1180   emit_insn (pat);
1181
1182   if (temp != target)
1183     emit_move_insn (target, temp);
1184 }
1185 \f
1186 /* Emit code to perform a series of operations on a multi-word quantity, one
1187    word at a time.
1188
1189    Such a block is preceded by a CLOBBER of the output, consists of multiple
1190    insns, each setting one word of the output, and followed by a SET copying
1191    the output to itself.
1192
1193    Each of the insns setting words of the output receives a REG_NO_CONFLICT
1194    note indicating that it doesn't conflict with the (also multi-word)
1195    inputs.  The entire block is surrounded by REG_LIBCALL and REG_RETVAL
1196    notes.
1197
1198    INSNS is a block of code generated to perform the operation, not including
1199    the CLOBBER and final copy.  All insns that compute intermediate values
1200    are first emitted, followed by the block as described above.  Only
1201    INSNs are allowed in the block; no library calls or jumps may be
1202    present.
1203
1204    TARGET, OP0, and OP1 are the output and inputs of the operations,
1205    respectively.  OP1 may be zero for a unary operation.
1206
1207    EQUIV, if non-zero, is an expression to be placed into a REG_EQUAL note
1208    on the last insn.
1209
1210    If TARGET is not a register, INSNS is simply emitted with no special
1211    processing.
1212
1213    The final insn emitted is returned.  */
1214
1215 rtx
1216 emit_no_conflict_block (insns, target, op0, op1, equiv)
1217      rtx insns;
1218      rtx target;
1219      rtx op0, op1;
1220      rtx equiv;
1221 {
1222   rtx prev, next, first, last, insn;
1223
1224   if (GET_CODE (target) != REG || reload_in_progress)
1225     return emit_insns (insns);
1226
1227   /* First emit all insns that do not store into words of the output and remove
1228      these from the list.  */
1229   for (insn = insns; insn; insn = next)
1230     {
1231       rtx set = 0;
1232       int i;
1233
1234       next = NEXT_INSN (insn);
1235
1236       if (GET_CODE (insn) != INSN)
1237         abort ();
1238
1239       if (GET_CODE (PATTERN (insn)) == SET)
1240         set = PATTERN (insn);
1241       else if (GET_CODE (PATTERN (insn)) == PARALLEL)
1242         {
1243           for (i = 0; i < XVECLEN (PATTERN (insn), 0); i++)
1244             if (GET_CODE (XVECEXP (PATTERN (insn), 0, i)) == SET)
1245               {
1246                 set = XVECEXP (PATTERN (insn), 0, i);
1247                 break;
1248               }
1249         }
1250
1251       if (set == 0)
1252         abort ();
1253
1254       if (! reg_overlap_mentioned_p (target, SET_DEST (set)))
1255         {
1256           if (PREV_INSN (insn))
1257             NEXT_INSN (PREV_INSN (insn)) = next;
1258           else
1259             insns = next;
1260
1261           if (next)
1262             PREV_INSN (next) = PREV_INSN (insn);
1263
1264           add_insn (insn);
1265         }
1266     }
1267
1268   prev = get_last_insn ();
1269
1270   /* Now write the CLOBBER of the output, followed by the setting of each
1271      of the words, followed by the final copy.  */
1272   if (target != op0 && target != op1)
1273     emit_insn (gen_rtx (CLOBBER, VOIDmode, target));
1274
1275   for (insn = insns; insn; insn = next)
1276     {
1277       next = NEXT_INSN (insn);
1278       add_insn (insn);
1279
1280       if (op1 && GET_CODE (op1) == REG)
1281         REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_NO_CONFLICT, op1,
1282                                     REG_NOTES (insn));
1283
1284       if (op0 && GET_CODE (op0) == REG)
1285         REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_NO_CONFLICT, op0,
1286                                     REG_NOTES (insn));
1287     }
1288
1289   last = emit_move_insn (target, target);
1290   if (equiv)
1291     REG_NOTES (last) = gen_rtx (EXPR_LIST, REG_EQUAL, equiv, REG_NOTES (last));
1292
1293   if (prev == 0)
1294     first = get_insns ();
1295   else
1296     first = NEXT_INSN (prev);
1297
1298   /* Encapsulate the block so it gets manipulated as a unit.  */
1299   REG_NOTES (first) = gen_rtx (INSN_LIST, REG_LIBCALL, last,
1300                                REG_NOTES (first));
1301   REG_NOTES (last) = gen_rtx (INSN_LIST, REG_RETVAL, first, REG_NOTES (last));
1302
1303   return last;
1304 }
1305 \f
1306 /* Emit code to make a call to a constant function or a library call.
1307
1308    INSNS is a list containing all insns emitted in the call.
1309    These insns leave the result in RESULT.  Our block is to copy RESULT
1310    to TARGET, which is logically equivalent to EQUIV.
1311
1312    We first emit any insns that set a pseudo on the assumption that these are
1313    loading constants into registers; doing so allows them to be safely cse'ed
1314    between blocks.  Then we emit all the other insns in the block, followed by
1315    an insn to move RESULT to TARGET.  This last insn will have a REQ_EQUAL
1316    note with an operand of EQUIV.
1317
1318    Moving assignments to pseudos outside of the block is done to improve
1319    the generated code, but is not required to generate correct code,
1320    hence being unable to move an assignment is not grounds for not making
1321    a libcall block.  There are two reasons why it is safe to leave these
1322    insns inside the block: First, we know that these pseudos cannot be
1323    used in generated RTL outside the block since they are created for
1324    temporary purposes within the block.  Second, CSE will not record the
1325    values of anything set inside a libcall block, so we know they must
1326    be dead at the end of the block.
1327
1328    Except for the first group of insns (the ones setting pseudos), the
1329    block is delimited by REG_RETVAL and REG_LIBCALL notes.  */
1330
1331 void
1332 emit_libcall_block (insns, target, result, equiv)
1333      rtx insns;
1334      rtx target;
1335      rtx result;
1336      rtx equiv;
1337 {
1338   rtx prev, next, first, last, insn;
1339
1340   /* First emit all insns that set pseudos.  Remove them from the list as
1341      we go.  Avoid insns that set pseudo which were referenced in previous
1342      insns.  These can be generated by move_by_pieces, for example,
1343      to update an address.  */
1344
1345   for (insn = insns; insn; insn = next)
1346     {
1347       rtx set = single_set (insn);
1348
1349       next = NEXT_INSN (insn);
1350
1351       if (set != 0 && GET_CODE (SET_DEST (set)) == REG
1352           && REGNO (SET_DEST (set)) >= FIRST_PSEUDO_REGISTER
1353           && ! reg_mentioned_p (SET_DEST (set), PATTERN (insns))
1354           && ! reg_used_between_p (SET_DEST (set), insns, insn))
1355         {
1356           if (PREV_INSN (insn))
1357             NEXT_INSN (PREV_INSN (insn)) = next;
1358           else
1359             insns = next;
1360
1361           if (next)
1362             PREV_INSN (next) = PREV_INSN (insn);
1363
1364           add_insn (insn);
1365         }
1366     }
1367
1368   prev = get_last_insn ();
1369
1370   /* Write the remaining insns followed by the final copy.  */
1371
1372   for (insn = insns; insn; insn = next)
1373     {
1374       next = NEXT_INSN (insn);
1375
1376       add_insn (insn);
1377     }
1378
1379   last = emit_move_insn (target, result);
1380   REG_NOTES (last) = gen_rtx (EXPR_LIST, REG_EQUAL, equiv, REG_NOTES (last));
1381
1382   if (prev == 0)
1383     first = get_insns ();
1384   else
1385     first = NEXT_INSN (prev);
1386
1387   /* Encapsulate the block so it gets manipulated as a unit.  */
1388   REG_NOTES (first) = gen_rtx (INSN_LIST, REG_LIBCALL, last,
1389                                REG_NOTES (first));
1390   REG_NOTES (last) = gen_rtx (INSN_LIST, REG_RETVAL, first, REG_NOTES (last));
1391 }
1392 \f
1393 /* Generate code to store zero in X.  */
1394
1395 void
1396 emit_clr_insn (x)
1397      rtx x;
1398 {
1399   emit_move_insn (x, const0_rtx);
1400 }
1401
1402 /* Generate code to store 1 in X
1403    assuming it contains zero beforehand.  */
1404
1405 void
1406 emit_0_to_1_insn (x)
1407      rtx x;
1408 {
1409   emit_move_insn (x, const1_rtx);
1410 }
1411
1412 /* Generate code to compare X with Y
1413    so that the condition codes are set.
1414
1415    MODE is the mode of the inputs (in case they are const_int).
1416    UNSIGNEDP nonzero says that X and Y are unsigned;
1417    this matters if they need to be widened.
1418
1419    If they have mode BLKmode, then SIZE specifies the size of both X and Y,
1420    and ALIGN specifies the known shared alignment of X and Y.
1421
1422    COMPARISON is the rtl operator to compare with (EQ, NE, GT, etc.).
1423    It is ignored for fixed-point and block comparisons;
1424    it is used only for floating-point comparisons.  */
1425
1426 void
1427 emit_cmp_insn (x, y, comparison, size, mode, unsignedp, align)
1428      rtx x, y;
1429      enum rtx_code comparison;
1430      rtx size;
1431      enum machine_mode mode;
1432      int unsignedp;
1433      int align;
1434 {
1435   enum mode_class class;
1436   enum machine_mode wider_mode;
1437
1438   class = GET_MODE_CLASS (mode);
1439
1440   /* They could both be VOIDmode if both args are immediate constants,
1441      but we should fold that at an earlier stage.
1442      With no special code here, this will call abort,
1443      reminding the programmer to implement such folding.  */
1444
1445   if (mode != BLKmode && flag_force_mem)
1446     {
1447       x = force_not_mem (x);
1448       y = force_not_mem (y);
1449     }
1450
1451   /* If we are inside an appropriately-short loop and one operand is an
1452      expensive constant, force it into a register.  */
1453   if (CONSTANT_P (x) && preserve_subexpressions_p () && rtx_cost (x) > 2)
1454     x = force_reg (mode, x);
1455
1456   if (CONSTANT_P (y) && preserve_subexpressions_p () && rtx_cost (y) > 2)
1457     y = force_reg (mode, y);
1458
1459   /* Don't let both operands fail to indicate the mode.  */
1460   if (GET_MODE (x) == VOIDmode && GET_MODE (y) == VOIDmode)
1461     x = force_reg (mode, x);
1462
1463   /* Handle all BLKmode compares.  */
1464
1465   if (mode == BLKmode)
1466     {
1467       emit_queue ();
1468       x = protect_from_queue (x, 0);
1469       y = protect_from_queue (y, 0);
1470
1471       if (size == 0)
1472         abort ();
1473 #ifdef HAVE_cmpstrqi
1474       if (HAVE_cmpstrqi
1475           && GET_CODE (size) == CONST_INT
1476           && INTVAL (size) < (1 << GET_MODE_BITSIZE (QImode)))
1477         {
1478           enum machine_mode result_mode
1479             = insn_operand_mode[(int) CODE_FOR_cmpstrqi][0];
1480           rtx result = gen_reg_rtx (result_mode);
1481           emit_insn (gen_cmpstrqi (result, x, y, size,
1482                                    gen_rtx (CONST_INT, VOIDmode, align)));
1483           emit_cmp_insn (result, const0_rtx, comparison, 0, result_mode, 0, 0);
1484         }
1485       else
1486 #endif
1487 #ifdef HAVE_cmpstrhi
1488       if (HAVE_cmpstrhi
1489           && GET_CODE (size) == CONST_INT
1490           && INTVAL (size) < (1 << GET_MODE_BITSIZE (HImode)))
1491         {
1492           enum machine_mode result_mode
1493             = insn_operand_mode[(int) CODE_FOR_cmpstrhi][0];
1494           rtx result = gen_reg_rtx (result_mode);
1495           emit_insn (gen_cmpstrhi (result, x, y, size,
1496                                    gen_rtx (CONST_INT, VOIDmode, align)));
1497           emit_cmp_insn (result, const0_rtx, comparison, 0, result_mode, 0, 0);
1498         }
1499       else
1500 #endif
1501 #ifdef HAVE_cmpstrsi
1502       if (HAVE_cmpstrsi)
1503         {
1504           enum machine_mode result_mode
1505             = insn_operand_mode[(int) CODE_FOR_cmpstrsi][0];
1506           rtx result = gen_reg_rtx (result_mode);
1507           emit_insn (gen_cmpstrsi (result, x, y,
1508                                    convert_to_mode (SImode, size, 1),
1509                                    gen_rtx (CONST_INT, VOIDmode, align)));
1510           emit_cmp_insn (result, const0_rtx, comparison, 0, result_mode, 0, 0);
1511         }
1512       else
1513 #endif
1514         {
1515 #ifdef TARGET_MEM_FUNCTIONS
1516           emit_library_call (memcmp_libfunc, 1,
1517                              TYPE_MODE (integer_type_node), 3,
1518                              XEXP (x, 0), Pmode, XEXP (y, 0), Pmode,
1519                              size, Pmode);
1520 #else
1521           emit_library_call (bcmp_libfunc, 1,
1522                              TYPE_MODE (integer_type_node), 3,
1523                              XEXP (x, 0), Pmode, XEXP (y, 0), Pmode,
1524                              size, Pmode);
1525 #endif
1526           emit_cmp_insn (hard_libcall_value (TYPE_MODE (integer_type_node)),
1527                          const0_rtx, comparison, 0,
1528                          TYPE_MODE (integer_type_node), 0, 0);
1529         }
1530       return;
1531     }
1532
1533   /* Handle some compares against zero.  */
1534
1535   if (y == CONST0_RTX (mode)
1536       && tst_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
1537     {
1538       int icode = (int) tst_optab->handlers[(int) mode].insn_code;
1539
1540       emit_queue ();
1541       x = protect_from_queue (x, 0);
1542       y = protect_from_queue (y, 0);
1543
1544       /* Now, if insn does accept these operands, put them into pseudos.  */
1545       if (! (*insn_operand_predicate[icode][0])
1546           (x, insn_operand_mode[icode][0]))
1547         x = copy_to_mode_reg (insn_operand_mode[icode][0], x);
1548
1549       emit_insn (GEN_FCN (icode) (x));
1550       return;
1551     }
1552
1553   /* Handle compares for which there is a directly suitable insn.  */
1554
1555   if (cmp_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing)
1556     {
1557       int icode = (int) cmp_optab->handlers[(int) mode].insn_code;
1558
1559       emit_queue ();
1560       x = protect_from_queue (x, 0);
1561       y = protect_from_queue (y, 0);
1562
1563       /* Now, if insn doesn't accept these operands, put them into pseudos.  */
1564       if (! (*insn_operand_predicate[icode][0])
1565           (x, insn_operand_mode[icode][0]))
1566         x = copy_to_mode_reg (insn_operand_mode[icode][0], x);
1567
1568       if (! (*insn_operand_predicate[icode][1])
1569           (y, insn_operand_mode[icode][1]))
1570         y = copy_to_mode_reg (insn_operand_mode[icode][1], y);
1571
1572       emit_insn (GEN_FCN (icode) (x, y));
1573       return;
1574     }
1575
1576   /* Try widening if we can find a direct insn that way.  */
1577
1578   if (class == MODE_INT || class == MODE_FLOAT || class == MODE_COMPLEX_FLOAT)
1579     {
1580       for (wider_mode = GET_MODE_WIDER_MODE (mode); wider_mode != VOIDmode;
1581            wider_mode = GET_MODE_WIDER_MODE (wider_mode))
1582         {
1583           if (cmp_optab->handlers[(int) wider_mode].insn_code
1584               != CODE_FOR_nothing)
1585             {
1586               x = convert_to_mode (wider_mode, x, unsignedp);
1587               y = convert_to_mode (wider_mode, y, unsignedp);
1588               emit_cmp_insn (x, y, comparison, 0,
1589                              wider_mode, unsignedp, align);
1590               return;
1591             }
1592         }
1593     }
1594
1595   /* Handle a lib call just for the mode we are using.  */
1596
1597   if (cmp_optab->handlers[(int) mode].libfunc
1598       && class != MODE_FLOAT)
1599     {
1600       rtx libfunc = cmp_optab->handlers[(int) mode].libfunc;
1601       /* If we want unsigned, and this mode has a distinct unsigned
1602          comparison routine, use that.  */
1603       if (unsignedp && ucmp_optab->handlers[(int) mode].libfunc)
1604         libfunc = ucmp_optab->handlers[(int) mode].libfunc;
1605
1606       emit_library_call (libfunc, 1,
1607                          SImode, 2, x, mode, y, mode);
1608
1609       /* Integer comparison returns a result that must be compared against 1,
1610          so that even if we do an unsigned compare afterward,
1611          there is still a value that can represent the result "less than".  */
1612
1613       emit_cmp_insn (hard_libcall_value (SImode), const1_rtx,
1614                      comparison, 0, SImode, unsignedp, 0);
1615       return;
1616     }
1617
1618   if (class == MODE_FLOAT)
1619     emit_float_lib_cmp (x, y, comparison);
1620
1621   else
1622     abort ();
1623 }
1624
1625 /* Nonzero if a compare of mode MODE can be done straightforwardly
1626    (without splitting it into pieces).  */
1627
1628 int
1629 can_compare_p (mode)
1630      enum machine_mode mode;
1631 {
1632   do
1633     {
1634       if (cmp_optab->handlers[(int)mode].insn_code != CODE_FOR_nothing)
1635         return 1;
1636       mode = GET_MODE_WIDER_MODE (mode);
1637     } while (mode != VOIDmode);
1638
1639   return 0;
1640 }
1641 \f
1642 /* Emit a library call comparison between floating point X and Y.
1643    COMPARISON is the rtl operator to compare with (EQ, NE, GT, etc.).  */
1644
1645 static void
1646 emit_float_lib_cmp (x, y, comparison)
1647      rtx x, y;
1648      enum rtx_code comparison;
1649 {
1650   enum machine_mode mode = GET_MODE (x);
1651   rtx libfunc;
1652
1653   if (mode == SFmode)
1654     switch (comparison)
1655       {
1656       case EQ:
1657         libfunc = eqsf2_libfunc;
1658         break;
1659
1660       case NE:
1661         libfunc = nesf2_libfunc;
1662         break;
1663
1664       case GT:
1665         libfunc = gtsf2_libfunc;
1666         break;
1667
1668       case GE:
1669         libfunc = gesf2_libfunc;
1670         break;
1671
1672       case LT:
1673         libfunc = ltsf2_libfunc;
1674         break;
1675
1676       case LE:
1677         libfunc = lesf2_libfunc;
1678         break;
1679       }
1680   else if (mode == DFmode)
1681     switch (comparison)
1682       {
1683       case EQ:
1684         libfunc = eqdf2_libfunc;
1685         break;
1686
1687       case NE:
1688         libfunc = nedf2_libfunc;
1689         break;
1690
1691       case GT:
1692         libfunc = gtdf2_libfunc;
1693         break;
1694
1695       case GE:
1696         libfunc = gedf2_libfunc;
1697         break;
1698
1699       case LT:
1700         libfunc = ltdf2_libfunc;
1701         break;
1702
1703       case LE:
1704         libfunc = ledf2_libfunc;
1705         break;
1706       }
1707   else
1708     {
1709       enum machine_mode wider_mode;
1710
1711       for (wider_mode = GET_MODE_WIDER_MODE (mode); wider_mode != VOIDmode;
1712            wider_mode = GET_MODE_WIDER_MODE (wider_mode))
1713         {
1714           if ((cmp_optab->handlers[(int) wider_mode].insn_code
1715                != CODE_FOR_nothing)
1716               || (cmp_optab->handlers[(int) wider_mode].libfunc != 0))
1717             {
1718               x = convert_to_mode (wider_mode, x, 0);
1719               y = convert_to_mode (wider_mode, y, 0);
1720               emit_float_lib_cmp (x, y, comparison);
1721               return;
1722             }
1723         }
1724       abort ();
1725     }
1726
1727   emit_library_call (libfunc, 1,
1728                      SImode, 2, x, mode, y, mode);
1729
1730   emit_cmp_insn (hard_libcall_value (SImode), const0_rtx, comparison,
1731                  0, SImode, 0, 0);
1732 }
1733 \f
1734 /* Generate code to indirectly jump to a location given in the rtx LOC.  */
1735
1736 void
1737 emit_indirect_jump (loc)
1738      rtx loc;
1739 {
1740   if (! ((*insn_operand_predicate[(int)CODE_FOR_indirect_jump][0])
1741          (loc, VOIDmode)))
1742     loc = copy_to_mode_reg (insn_operand_mode[(int)CODE_FOR_indirect_jump][0],
1743                             loc);
1744
1745   emit_jump_insn (gen_indirect_jump (loc));
1746 }
1747 \f
1748 /* These three functions generate an insn body and return it
1749    rather than emitting the insn.
1750
1751    They do not protect from queued increments,
1752    because they may be used 1) in protect_from_queue itself
1753    and 2) in other passes where there is no queue.  */
1754
1755 /* Generate and return an insn body to add Y to X.  */
1756
1757 rtx
1758 gen_add2_insn (x, y)
1759      rtx x, y;
1760 {
1761   int icode = (int) add_optab->handlers[(int) GET_MODE (x)].insn_code; 
1762
1763   if (! (*insn_operand_predicate[icode][0]) (x, insn_operand_mode[icode][0])
1764       || ! (*insn_operand_predicate[icode][1]) (x, insn_operand_mode[icode][1])
1765       || ! (*insn_operand_predicate[icode][2]) (y, insn_operand_mode[icode][2]))
1766     abort ();
1767
1768   return (GEN_FCN (icode) (x, x, y));
1769 }
1770
1771 int
1772 have_add2_insn (mode)
1773      enum machine_mode mode;
1774 {
1775   return add_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing;
1776 }
1777
1778 /* Generate and return an insn body to subtract Y from X.  */
1779
1780 rtx
1781 gen_sub2_insn (x, y)
1782      rtx x, y;
1783 {
1784   int icode = (int) sub_optab->handlers[(int) GET_MODE (x)].insn_code; 
1785
1786   if (! (*insn_operand_predicate[icode][0]) (x, insn_operand_mode[icode][0])
1787       || ! (*insn_operand_predicate[icode][1]) (x, insn_operand_mode[icode][1])
1788       || ! (*insn_operand_predicate[icode][2]) (y, insn_operand_mode[icode][2]))
1789     abort ();
1790
1791   return (GEN_FCN (icode) (x, x, y));
1792 }
1793
1794 int
1795 have_sub2_insn (mode)
1796      enum machine_mode mode;
1797 {
1798   return sub_optab->handlers[(int) mode].insn_code != CODE_FOR_nothing;
1799 }
1800
1801 /* Generate the body of an instruction to copy Y into X.  */
1802
1803 rtx
1804 gen_move_insn (x, y)
1805      rtx x, y;
1806 {
1807   register enum machine_mode mode = GET_MODE (x);
1808   enum insn_code insn_code;
1809
1810   if (mode == VOIDmode)
1811     mode = GET_MODE (y); 
1812
1813   insn_code = mov_optab->handlers[(int) mode].insn_code;
1814
1815   /* Handle MODE_CC modes:  If we don't have a special move insn for this mode,
1816      find a mode to do it in.  If we have a movcc, use it.  Otherwise,
1817      find the MODE_INT mode of the same width.  */
1818
1819   if (insn_code == CODE_FOR_nothing)
1820     {
1821       enum machine_mode tmode = VOIDmode;
1822       rtx x1 = x, y1 = y;
1823
1824       if (GET_MODE_CLASS (mode) == MODE_CC && mode != CCmode
1825           && mov_optab->handlers[(int) CCmode].insn_code != CODE_FOR_nothing)
1826         tmode = CCmode;
1827       else if (GET_MODE_CLASS (mode) == MODE_CC)
1828         for (tmode = QImode; tmode != VOIDmode;
1829              tmode = GET_MODE_WIDER_MODE (tmode))
1830           if (GET_MODE_SIZE (tmode) == GET_MODE_SIZE (mode))
1831             break;
1832
1833       if (tmode == VOIDmode)
1834         abort ();
1835
1836       /* Get X and Y in TMODE.  We can't use gen_lowpart here because it
1837          may call change_address which is not appropriate if we were
1838          called when a reload was in progress.  We don't have to worry
1839          about changing the address since the size in bytes is supposed to
1840          be the same.  Copy the MEM to change the mode and move any
1841          substitutions from the old MEM to the new one.  */
1842
1843       if (reload_in_progress)
1844         {
1845           x = gen_lowpart_common (tmode, x1);
1846           if (x == 0 && GET_CODE (x1) == MEM)
1847             {
1848               x = gen_rtx (MEM, tmode, XEXP (x1, 0));
1849               RTX_UNCHANGING_P (x) = RTX_UNCHANGING_P (x1);
1850               MEM_IN_STRUCT_P (x) = MEM_IN_STRUCT_P (x1);
1851               MEM_VOLATILE_P (x) = MEM_VOLATILE_P (x1);
1852               copy_replacements (x1, x);
1853             }
1854
1855           y = gen_lowpart_common (tmode, y1);
1856           if (y == 0 && GET_CODE (y1) == MEM)
1857             {
1858               y = gen_rtx (MEM, tmode, XEXP (y1, 0));
1859               RTX_UNCHANGING_P (y) = RTX_UNCHANGING_P (y1);
1860               MEM_IN_STRUCT_P (y) = MEM_IN_STRUCT_P (y1);
1861               MEM_VOLATILE_P (y) = MEM_VOLATILE_P (y1);
1862               copy_replacements (y1, y);
1863             }
1864         }
1865       else
1866         {
1867           x = gen_lowpart (tmode, x);
1868           y = gen_lowpart (tmode, y);
1869         }
1870           
1871       insn_code = mov_optab->handlers[(int) tmode].insn_code;
1872     }
1873
1874   return (GEN_FCN (insn_code) (x, y));
1875 }
1876 \f
1877 /* Tables of patterns for extending one integer mode to another.  */
1878 static enum insn_code extendtab[MAX_MACHINE_MODE][MAX_MACHINE_MODE][2];
1879
1880 /* Return the insn code used to extend FROM_MODE to TO_MODE.
1881    UNSIGNEDP specifies zero-extension instead of sign-extension.  If
1882    no such operation exists, CODE_FOR_nothing will be returned.  */
1883
1884 enum insn_code
1885 can_extend_p (to_mode, from_mode, unsignedp)
1886      enum machine_mode to_mode, from_mode;
1887      int unsignedp;
1888 {
1889   return extendtab[(int) to_mode][(int) from_mode][unsignedp];
1890 }
1891
1892 /* Generate the body of an insn to extend Y (with mode MFROM)
1893    into X (with mode MTO).  Do zero-extension if UNSIGNEDP is nonzero.  */
1894
1895 rtx
1896 gen_extend_insn (x, y, mto, mfrom, unsignedp)
1897      rtx x, y;
1898      enum machine_mode mto, mfrom;
1899      int unsignedp;
1900 {
1901   return (GEN_FCN (extendtab[(int) mto][(int) mfrom][unsignedp]) (x, y));
1902 }
1903
1904 static void
1905 init_extends ()
1906 {
1907   enum insn_code *p;
1908
1909   for (p = extendtab[0][0];
1910        p < extendtab[0][0] + sizeof extendtab / sizeof extendtab[0][0][0];
1911        p++)
1912     *p = CODE_FOR_nothing;
1913
1914 #ifdef HAVE_extendditi2
1915   if (HAVE_extendditi2)
1916     extendtab[(int) TImode][(int) DImode][0] = CODE_FOR_extendditi2;
1917 #endif
1918 #ifdef HAVE_extendsiti2
1919   if (HAVE_extendsiti2)
1920     extendtab[(int) TImode][(int) SImode][0] = CODE_FOR_extendsiti2;
1921 #endif
1922 #ifdef HAVE_extendhiti2
1923   if (HAVE_extendhiti2)
1924     extendtab[(int) TImode][(int) HImode][0] = CODE_FOR_extendhiti2;
1925 #endif
1926 #ifdef HAVE_extendqiti2
1927   if (HAVE_extendqiti2)
1928     extendtab[(int) TImode][(int) QImode][0] = CODE_FOR_extendqiti2;
1929 #endif
1930 #ifdef HAVE_extendsidi2
1931   if (HAVE_extendsidi2)
1932     extendtab[(int) DImode][(int) SImode][0] = CODE_FOR_extendsidi2;
1933 #endif
1934 #ifdef HAVE_extendhidi2
1935   if (HAVE_extendhidi2)
1936     extendtab[(int) DImode][(int) HImode][0] = CODE_FOR_extendhidi2;
1937 #endif
1938 #ifdef HAVE_extendqidi2
1939   if (HAVE_extendqidi2)
1940     extendtab[(int) DImode][(int) QImode][0] = CODE_FOR_extendqidi2;
1941 #endif
1942 #ifdef HAVE_extendhisi2
1943   if (HAVE_extendhisi2)
1944     extendtab[(int) SImode][(int) HImode][0] = CODE_FOR_extendhisi2;
1945 #endif
1946 #ifdef HAVE_extendqisi2
1947   if (HAVE_extendqisi2)
1948     extendtab[(int) SImode][(int) QImode][0] = CODE_FOR_extendqisi2;
1949 #endif
1950 #ifdef HAVE_extendqihi2
1951   if (HAVE_extendqihi2)
1952     extendtab[(int) HImode][(int) QImode][0] = CODE_FOR_extendqihi2;
1953 #endif
1954
1955 #ifdef HAVE_zero_extendditi2
1956   if (HAVE_zero_extendsiti2)
1957     extendtab[(int) TImode][(int) DImode][1] = CODE_FOR_zero_extendditi2;
1958 #endif
1959 #ifdef HAVE_zero_extendsiti2
1960   if (HAVE_zero_extendsiti2)
1961     extendtab[(int) TImode][(int) SImode][1] = CODE_FOR_zero_extendsiti2;
1962 #endif
1963 #ifdef HAVE_zero_extendhiti2
1964   if (HAVE_zero_extendhiti2)
1965     extendtab[(int) TImode][(int) HImode][1] = CODE_FOR_zero_extendhiti2;
1966 #endif
1967 #ifdef HAVE_zero_extendqiti2
1968   if (HAVE_zero_extendqiti2)
1969     extendtab[(int) TImode][(int) QImode][1] = CODE_FOR_zero_extendqiti2;
1970 #endif
1971 #ifdef HAVE_zero_extendsidi2
1972   if (HAVE_zero_extendsidi2)
1973     extendtab[(int) DImode][(int) SImode][1] = CODE_FOR_zero_extendsidi2;
1974 #endif
1975 #ifdef HAVE_zero_extendhidi2
1976   if (HAVE_zero_extendhidi2)
1977     extendtab[(int) DImode][(int) HImode][1] = CODE_FOR_zero_extendhidi2;
1978 #endif
1979 #ifdef HAVE_zero_extendqidi2
1980   if (HAVE_zero_extendqidi2)
1981     extendtab[(int) DImode][(int) QImode][1] = CODE_FOR_zero_extendqidi2;
1982 #endif
1983 #ifdef HAVE_zero_extendhisi2
1984   if (HAVE_zero_extendhisi2)
1985     extendtab[(int) SImode][(int) HImode][1] = CODE_FOR_zero_extendhisi2;
1986 #endif
1987 #ifdef HAVE_zero_extendqisi2
1988   if (HAVE_zero_extendqisi2)
1989     extendtab[(int) SImode][(int) QImode][1] = CODE_FOR_zero_extendqisi2;
1990 #endif
1991 #ifdef HAVE_zero_extendqihi2
1992   if (HAVE_zero_extendqihi2)
1993     extendtab[(int) HImode][(int) QImode][1] = CODE_FOR_zero_extendqihi2;
1994 #endif
1995 }
1996 \f
1997 /* can_fix_p and can_float_p say whether the target machine
1998    can directly convert a given fixed point type to
1999    a given floating point type, or vice versa.
2000    The returned value is the CODE_FOR_... value to use,
2001    or CODE_FOR_nothing if these modes cannot be directly converted.  */
2002
2003 static enum insn_code fixtab[NUM_MACHINE_MODES][NUM_MACHINE_MODES][2];
2004 static enum insn_code fixtrunctab[NUM_MACHINE_MODES][NUM_MACHINE_MODES][2];
2005 static enum insn_code floattab[NUM_MACHINE_MODES][NUM_MACHINE_MODES][2];
2006
2007 /* *TRUNCP_PTR is set to 1 if it is necessary to output
2008    an explicit FTRUNC insn before the fix insn; otherwise 0.  */
2009
2010 static enum insn_code
2011 can_fix_p (fixmode, fltmode, unsignedp, truncp_ptr)
2012      enum machine_mode fltmode, fixmode;
2013      int unsignedp;
2014      int *truncp_ptr;
2015 {
2016   *truncp_ptr = 0;
2017   if (fixtrunctab[(int) fltmode][(int) fixmode][unsignedp] != CODE_FOR_nothing)
2018     return fixtrunctab[(int) fltmode][(int) fixmode][unsignedp];
2019
2020   if (ftrunc_optab->handlers[(int) fltmode].insn_code != CODE_FOR_nothing)
2021     {
2022       *truncp_ptr = 1;
2023       return fixtab[(int) fltmode][(int) fixmode][unsignedp];
2024     }
2025   return CODE_FOR_nothing;
2026 }
2027
2028 static enum insn_code
2029 can_float_p (fltmode, fixmode, unsignedp)
2030      enum machine_mode fixmode, fltmode;
2031      int unsignedp;
2032 {
2033   return floattab[(int) fltmode][(int) fixmode][unsignedp];
2034 }
2035
2036 void
2037 init_fixtab ()
2038 {
2039   enum insn_code *p;
2040   for (p = fixtab[0][0];
2041        p < fixtab[0][0] + sizeof fixtab / sizeof (fixtab[0][0][0]); 
2042        p++)
2043     *p = CODE_FOR_nothing;
2044   for (p = fixtrunctab[0][0];
2045        p < fixtrunctab[0][0] + sizeof fixtrunctab / sizeof (fixtrunctab[0][0][0]); 
2046        p++)
2047     *p = CODE_FOR_nothing;
2048
2049 #ifdef HAVE_fixsfqi2
2050   if (HAVE_fixsfqi2)
2051     fixtab[(int) SFmode][(int) QImode][0] = CODE_FOR_fixsfqi2;
2052 #endif
2053 #ifdef HAVE_fixsfhi2
2054   if (HAVE_fixsfhi2)
2055     fixtab[(int) SFmode][(int) HImode][0] = CODE_FOR_fixsfhi2;
2056 #endif
2057 #ifdef HAVE_fixsfsi2
2058   if (HAVE_fixsfsi2)
2059     fixtab[(int) SFmode][(int) SImode][0] = CODE_FOR_fixsfsi2;
2060 #endif
2061 #ifdef HAVE_fixsfdi2
2062   if (HAVE_fixsfdi2)
2063     fixtab[(int) SFmode][(int) DImode][0] = CODE_FOR_fixsfdi2;
2064 #endif
2065
2066 #ifdef HAVE_fixdfqi2
2067   if (HAVE_fixdfqi2)
2068     fixtab[(int) DFmode][(int) QImode][0] = CODE_FOR_fixdfqi2;
2069 #endif
2070 #ifdef HAVE_fixdfhi2
2071   if (HAVE_fixdfhi2)
2072     fixtab[(int) DFmode][(int) HImode][0] = CODE_FOR_fixdfhi2;
2073 #endif
2074 #ifdef HAVE_fixdfsi2
2075   if (HAVE_fixdfsi2)
2076     fixtab[(int) DFmode][(int) SImode][0] = CODE_FOR_fixdfsi2;
2077 #endif
2078 #ifdef HAVE_fixdfdi2
2079   if (HAVE_fixdfdi2)
2080     fixtab[(int) DFmode][(int) DImode][0] = CODE_FOR_fixdfdi2;
2081 #endif
2082 #ifdef HAVE_fixdfti2
2083   if (HAVE_fixdfti2)
2084     fixtab[(int) DFmode][(int) TImode][0] = CODE_FOR_fixdfti2;
2085 #endif
2086
2087 #ifdef HAVE_fixtfqi2
2088   if (HAVE_fixtfqi2)
2089     fixtab[(int) TFmode][(int) QImode][0] = CODE_FOR_fixtfqi2;
2090 #endif
2091 #ifdef HAVE_fixtfhi2
2092   if (HAVE_fixtfhi2)
2093     fixtab[(int) TFmode][(int) HImode][0] = CODE_FOR_fixtfhi2;
2094 #endif
2095 #ifdef HAVE_fixtfsi2
2096   if (HAVE_fixtfsi2)
2097     fixtab[(int) TFmode][(int) SImode][0] = CODE_FOR_fixtfsi2;
2098 #endif
2099 #ifdef HAVE_fixtfdi2
2100   if (HAVE_fixtfdi2)
2101     fixtab[(int) TFmode][(int) DImode][0] = CODE_FOR_fixtfdi2;
2102 #endif
2103 #ifdef HAVE_fixtfti2
2104   if (HAVE_fixtfti2)
2105     fixtab[(int) TFmode][(int) TImode][0] = CODE_FOR_fixtfti2;
2106 #endif
2107
2108 #ifdef HAVE_fixunssfqi2
2109   if (HAVE_fixunssfqi2)
2110     fixtab[(int) SFmode][(int) QImode][1] = CODE_FOR_fixunssfqi2;
2111 #endif
2112 #ifdef HAVE_fixunssfhi2
2113   if (HAVE_fixunssfhi2)
2114     fixtab[(int) SFmode][(int) HImode][1] = CODE_FOR_fixunssfhi2;
2115 #endif
2116 #ifdef HAVE_fixunssfsi2
2117   if (HAVE_fixunssfsi2)
2118     fixtab[(int) SFmode][(int) SImode][1] = CODE_FOR_fixunssfsi2;
2119 #endif
2120 #ifdef HAVE_fixunssfdi2
2121   if (HAVE_fixunssfdi2)
2122     fixtab[(int) SFmode][(int) DImode][1] = CODE_FOR_fixunssfdi2;
2123 #endif
2124
2125 #ifdef HAVE_fixunsdfqi2
2126   if (HAVE_fixunsdfqi2)
2127     fixtab[(int) DFmode][(int) QImode][1] = CODE_FOR_fixunsdfqi2;
2128 #endif
2129 #ifdef HAVE_fixunsdfhi2
2130   if (HAVE_fixunsdfhi2)
2131     fixtab[(int) DFmode][(int) HImode][1] = CODE_FOR_fixunsdfhi2;
2132 #endif
2133 #ifdef HAVE_fixunsdfsi2
2134   if (HAVE_fixunsdfsi2)
2135     fixtab[(int) DFmode][(int) SImode][1] = CODE_FOR_fixunsdfsi2;
2136 #endif
2137 #ifdef HAVE_fixunsdfdi2
2138   if (HAVE_fixunsdfdi2)
2139     fixtab[(int) DFmode][(int) DImode][1] = CODE_FOR_fixunsdfdi2;
2140 #endif
2141 #ifdef HAVE_fixunsdfti2
2142   if (HAVE_fixunsdfti2)
2143     fixtab[(int) DFmode][(int) TImode][1] = CODE_FOR_fixunsdfti2;
2144 #endif
2145
2146 #ifdef HAVE_fixunstfqi2
2147   if (HAVE_fixunstfqi2)
2148     fixtab[(int) TFmode][(int) QImode][1] = CODE_FOR_fixunstfqi2;
2149 #endif
2150 #ifdef HAVE_fixunstfhi2
2151   if (HAVE_fixunstfhi2)
2152     fixtab[(int) TFmode][(int) HImode][1] = CODE_FOR_fixunstfhi2;
2153 #endif
2154 #ifdef HAVE_fixunstfsi2
2155   if (HAVE_fixunstfsi2)
2156     fixtab[(int) TFmode][(int) SImode][1] = CODE_FOR_fixunstfsi2;
2157 #endif
2158 #ifdef HAVE_fixunstfdi2
2159   if (HAVE_fixunstfdi2)
2160     fixtab[(int) TFmode][(int) DImode][1] = CODE_FOR_fixunstfdi2;
2161 #endif
2162 #ifdef HAVE_fixunstfti2
2163   if (HAVE_fixunstfti2)
2164     fixtab[(int) TFmode][(int) TImode][1] = CODE_FOR_fixunstfti2;
2165 #endif
2166
2167 #ifdef HAVE_fix_truncsfqi2
2168   if (HAVE_fix_truncsfqi2)
2169     fixtrunctab[(int) SFmode][(int) QImode][0] = CODE_FOR_fix_truncsfqi2;
2170 #endif
2171 #ifdef HAVE_fix_truncsfhi2
2172   if (HAVE_fix_truncsfhi2)
2173     fixtrunctab[(int) SFmode][(int) HImode][0] = CODE_FOR_fix_truncsfhi2;
2174 #endif
2175 #ifdef HAVE_fix_truncsfsi2
2176   if (HAVE_fix_truncsfsi2)
2177     fixtrunctab[(int) SFmode][(int) SImode][0] = CODE_FOR_fix_truncsfsi2;
2178 #endif
2179 #ifdef HAVE_fix_truncsfdi2
2180   if (HAVE_fix_truncsfdi2)
2181     fixtrunctab[(int) SFmode][(int) DImode][0] = CODE_FOR_fix_truncsfdi2;
2182 #endif
2183
2184 #ifdef HAVE_fix_truncdfqi2
2185   if (HAVE_fix_truncdfsi2)
2186     fixtrunctab[(int) DFmode][(int) QImode][0] = CODE_FOR_fix_truncdfqi2;
2187 #endif
2188 #ifdef HAVE_fix_truncdfhi2
2189   if (HAVE_fix_truncdfhi2)
2190     fixtrunctab[(int) DFmode][(int) HImode][0] = CODE_FOR_fix_truncdfhi2;
2191 #endif
2192 #ifdef HAVE_fix_truncdfsi2
2193   if (HAVE_fix_truncdfsi2)
2194     fixtrunctab[(int) DFmode][(int) SImode][0] = CODE_FOR_fix_truncdfsi2;
2195 #endif
2196 #ifdef HAVE_fix_truncdfdi2
2197   if (HAVE_fix_truncdfdi2)
2198     fixtrunctab[(int) DFmode][(int) DImode][0] = CODE_FOR_fix_truncdfdi2;
2199 #endif
2200 #ifdef HAVE_fix_truncdfti2
2201   if (HAVE_fix_truncdfti2)
2202     fixtrunctab[(int) DFmode][(int) TImode][0] = CODE_FOR_fix_truncdfti2;
2203 #endif
2204
2205 #ifdef HAVE_fix_trunctfqi2
2206   if (HAVE_fix_trunctfqi2)
2207     fixtrunctab[(int) TFmode][(int) QImode][0] = CODE_FOR_fix_trunctfqi2;
2208 #endif
2209 #ifdef HAVE_fix_trunctfhi2
2210   if (HAVE_fix_trunctfhi2)
2211     fixtrunctab[(int) TFmode][(int) HImode][0] = CODE_FOR_fix_trunctfhi2;
2212 #endif
2213 #ifdef HAVE_fix_trunctfsi2
2214   if (HAVE_fix_trunctfsi2)
2215     fixtrunctab[(int) TFmode][(int) SImode][0] = CODE_FOR_fix_trunctfsi2;
2216 #endif
2217 #ifdef HAVE_fix_trunctfdi2
2218   if (HAVE_fix_trunctfdi2)
2219     fixtrunctab[(int) TFmode][(int) DImode][0] = CODE_FOR_fix_trunctfdi2;
2220 #endif
2221 #ifdef HAVE_fix_trunctfti2
2222   if (HAVE_fix_trunctfti2)
2223     fixtrunctab[(int) TFmode][(int) TImode][0] = CODE_FOR_fix_trunctfti2;
2224 #endif
2225
2226 #ifdef HAVE_fixuns_truncsfqi2
2227   if (HAVE_fixuns_truncsfqi2)
2228     fixtrunctab[(int) SFmode][(int) QImode][1] = CODE_FOR_fixuns_truncsfqi2;
2229 #endif
2230 #ifdef HAVE_fixuns_truncsfhi2
2231   if (HAVE_fixuns_truncsfhi2)
2232     fixtrunctab[(int) SFmode][(int) HImode][1] = CODE_FOR_fixuns_truncsfhi2;
2233 #endif
2234 #ifdef HAVE_fixuns_truncsfsi2
2235   if (HAVE_fixuns_truncsfsi2)
2236     fixtrunctab[(int) SFmode][(int) SImode][1] = CODE_FOR_fixuns_truncsfsi2;
2237 #endif
2238 #ifdef HAVE_fixuns_truncsfdi2
2239   if (HAVE_fixuns_truncsfdi2)
2240     fixtrunctab[(int) SFmode][(int) DImode][1] = CODE_FOR_fixuns_truncsfdi2;
2241 #endif
2242
2243 #ifdef HAVE_fixuns_truncdfqi2
2244   if (HAVE_fixuns_truncdfqi2)
2245     fixtrunctab[(int) DFmode][(int) QImode][1] = CODE_FOR_fixuns_truncdfqi2;
2246 #endif
2247 #ifdef HAVE_fixuns_truncdfhi2
2248   if (HAVE_fixuns_truncdfhi2)
2249     fixtrunctab[(int) DFmode][(int) HImode][1] = CODE_FOR_fixuns_truncdfhi2;
2250 #endif
2251 #ifdef HAVE_fixuns_truncdfsi2
2252   if (HAVE_fixuns_truncdfsi2)
2253     fixtrunctab[(int) DFmode][(int) SImode][1] = CODE_FOR_fixuns_truncdfsi2;
2254 #endif
2255 #ifdef HAVE_fixuns_truncdfdi2
2256   if (HAVE_fixuns_truncdfdi2)
2257     fixtrunctab[(int) DFmode][(int) DImode][1] = CODE_FOR_fixuns_truncdfdi2;
2258 #endif
2259 #ifdef HAVE_fixuns_truncdfti2
2260   if (HAVE_fixuns_truncdfti2)
2261     fixtrunctab[(int) DFmode][(int) TImode][1] = CODE_FOR_fixuns_truncdfti2;
2262 #endif
2263
2264 #ifdef HAVE_fixuns_trunctfqi2
2265   if (HAVE_fixuns_trunctfqi2)
2266     fixtrunctab[(int) TFmode][(int) QImode][1] = CODE_FOR_fixuns_trunctfqi2;
2267 #endif
2268 #ifdef HAVE_fixuns_trunctfhi2
2269   if (HAVE_fixuns_trunctfhi2)
2270     fixtrunctab[(int) TFmode][(int) HImode][1] = CODE_FOR_fixuns_trunctfhi2;
2271 #endif
2272 #ifdef HAVE_fixuns_trunctfsi2
2273   if (HAVE_fixuns_trunctfsi2)
2274     fixtrunctab[(int) TFmode][(int) SImode][1] = CODE_FOR_fixuns_trunctfsi2;
2275 #endif
2276 #ifdef HAVE_fixuns_trunctfdi2
2277   if (HAVE_fixuns_trunctfdi2)
2278     fixtrunctab[(int) TFmode][(int) DImode][1] = CODE_FOR_fixuns_trunctfdi2;
2279 #endif
2280 #ifdef HAVE_fixuns_trunctfti2
2281   if (HAVE_fixuns_trunctfti2)
2282     fixtrunctab[(int) TFmode][(int) TImode][1] = CODE_FOR_fixuns_trunctfti2;
2283 #endif
2284
2285 #ifdef FIXUNS_TRUNC_LIKE_FIX_TRUNC
2286   /* This flag says the same insns that convert to a signed fixnum
2287      also convert validly to an unsigned one.  */
2288   {
2289     int i;
2290     int j;
2291     for (i = 0; i < NUM_MACHINE_MODES; i++)
2292       for (j = 0; j < NUM_MACHINE_MODES; j++)
2293         fixtrunctab[i][j][1] = fixtrunctab[i][j][0];
2294   }
2295 #endif
2296 }
2297
2298 void
2299 init_floattab ()
2300 {
2301   enum insn_code *p;
2302   for (p = floattab[0][0];
2303        p < floattab[0][0] + sizeof floattab / sizeof (floattab[0][0][0]); 
2304        p++)
2305     *p = CODE_FOR_nothing;
2306
2307 #ifdef HAVE_floatqisf2
2308   if (HAVE_floatqisf2)
2309     floattab[(int) SFmode][(int) QImode][0] = CODE_FOR_floatqisf2;
2310 #endif
2311 #ifdef HAVE_floathisf2
2312   if (HAVE_floathisf2)
2313     floattab[(int) SFmode][(int) HImode][0] = CODE_FOR_floathisf2;
2314 #endif
2315 #ifdef HAVE_floatsisf2
2316   if (HAVE_floatsisf2)
2317     floattab[(int) SFmode][(int) SImode][0] = CODE_FOR_floatsisf2;
2318 #endif
2319 #ifdef HAVE_floatdisf2
2320   if (HAVE_floatdisf2)
2321     floattab[(int) SFmode][(int) DImode][0] = CODE_FOR_floatdisf2;
2322 #endif
2323 #ifdef HAVE_floattisf2
2324   if (HAVE_floattisf2)
2325     floattab[(int) SFmode][(int) TImode][0] = CODE_FOR_floattisf2;
2326 #endif
2327
2328 #ifdef HAVE_floatqidf2
2329   if (HAVE_floatqidf2)
2330     floattab[(int) DFmode][(int) QImode][0] = CODE_FOR_floatqidf2;
2331 #endif
2332 #ifdef HAVE_floathidf2
2333   if (HAVE_floathidf2)
2334     floattab[(int) DFmode][(int) HImode][0] = CODE_FOR_floathidf2;
2335 #endif
2336 #ifdef HAVE_floatsidf2
2337   if (HAVE_floatsidf2)
2338     floattab[(int) DFmode][(int) SImode][0] = CODE_FOR_floatsidf2;
2339 #endif
2340 #ifdef HAVE_floatdidf2
2341   if (HAVE_floatdidf2)
2342     floattab[(int) DFmode][(int) DImode][0] = CODE_FOR_floatdidf2;
2343 #endif
2344 #ifdef HAVE_floattidf2
2345   if (HAVE_floattidf2)
2346     floattab[(int) DFmode][(int) TImode][0] = CODE_FOR_floattidf2;
2347 #endif
2348
2349 #ifdef HAVE_floatqitf2
2350   if (HAVE_floatqitf2)
2351     floattab[(int) TFmode][(int) QImode][0] = CODE_FOR_floatqitf2;
2352 #endif
2353 #ifdef HAVE_floathitf2
2354   if (HAVE_floathitf2)
2355     floattab[(int) TFmode][(int) HImode][0] = CODE_FOR_floathitf2;
2356 #endif
2357 #ifdef HAVE_floatsitf2
2358   if (HAVE_floatsitf2)
2359     floattab[(int) TFmode][(int) SImode][0] = CODE_FOR_floatsitf2;
2360 #endif
2361 #ifdef HAVE_floatditf2
2362   if (HAVE_floatditf2)
2363     floattab[(int) TFmode][(int) DImode][0] = CODE_FOR_floatditf2;
2364 #endif
2365 #ifdef HAVE_floattitf2
2366   if (HAVE_floattitf2)
2367     floattab[(int) TFmode][(int) TImode][0] = CODE_FOR_floattitf2;
2368 #endif
2369
2370 #ifdef HAVE_floatunsqisf2
2371   if (HAVE_floatunsqisf2)
2372     floattab[(int) SFmode][(int) QImode][1] = CODE_FOR_floatunsqisf2;
2373 #endif
2374 #ifdef HAVE_floatunshisf2
2375   if (HAVE_floatunshisf2)
2376     floattab[(int) SFmode][(int) HImode][1] = CODE_FOR_floatunshisf2;
2377 #endif
2378 #ifdef HAVE_floatunssisf2
2379   if (HAVE_floatunssisf2)
2380     floattab[(int) SFmode][(int) SImode][1] = CODE_FOR_floatunssisf2;
2381 #endif
2382 #ifdef HAVE_floatunsdisf2
2383   if (HAVE_floatunsdisf2)
2384     floattab[(int) SFmode][(int) DImode][1] = CODE_FOR_floatunsdisf2;
2385 #endif
2386 #ifdef HAVE_floatunstisf2
2387   if (HAVE_floatunstisf2)
2388     floattab[(int) SFmode][(int) TImode][1] = CODE_FOR_floatunstisf2;
2389 #endif
2390
2391 #ifdef HAVE_floatunsqidf2
2392   if (HAVE_floatunsqidf2)
2393     floattab[(int) DFmode][(int) QImode][1] = CODE_FOR_floatunsqidf2;
2394 #endif
2395 #ifdef HAVE_floatunshidf2
2396   if (HAVE_floatunshidf2)
2397     floattab[(int) DFmode][(int) HImode][1] = CODE_FOR_floatunshidf2;
2398 #endif
2399 #ifdef HAVE_floatunssidf2
2400   if (HAVE_floatunssidf2)
2401     floattab[(int) DFmode][(int) SImode][1] = CODE_FOR_floatunssidf2;
2402 #endif
2403 #ifdef HAVE_floatunsdidf2
2404   if (HAVE_floatunsdidf2)
2405     floattab[(int) DFmode][(int) DImode][1] = CODE_FOR_floatunsdidf2;
2406 #endif
2407 #ifdef HAVE_floatunstidf2
2408   if (HAVE_floatunstidf2)
2409     floattab[(int) DFmode][(int) TImode][1] = CODE_FOR_floatunstidf2;
2410 #endif
2411
2412 #ifdef HAVE_floatunsqitf2
2413   if (HAVE_floatunsqitf2)
2414     floattab[(int) TFmode][(int) QImode][1] = CODE_FOR_floatunsqitf2;
2415 #endif
2416 #ifdef HAVE_floatunshitf2
2417   if (HAVE_floatunshitf2)
2418     floattab[(int) TFmode][(int) HImode][1] = CODE_FOR_floatunshitf2;
2419 #endif
2420 #ifdef HAVE_floatunssitf2
2421   if (HAVE_floatunssitf2)
2422     floattab[(int) TFmode][(int) SImode][1] = CODE_FOR_floatunssitf2;
2423 #endif
2424 #ifdef HAVE_floatunsditf2
2425   if (HAVE_floatunsditf2)
2426     floattab[(int) TFmode][(int) DImode][1] = CODE_FOR_floatunsditf2;
2427 #endif
2428 #ifdef HAVE_floatunstitf2
2429   if (HAVE_floatunstitf2)
2430     floattab[(int) TFmode][(int) TImode][1] = CODE_FOR_floatunstitf2;
2431 #endif
2432 }
2433 \f
2434 /* Generate code to convert FROM to floating point
2435    and store in TO.  FROM must be fixed point and not VOIDmode.
2436    UNSIGNEDP nonzero means regard FROM as unsigned.
2437    Normally this is done by correcting the final value
2438    if it is negative.  */
2439
2440 void
2441 expand_float (to, from, unsignedp)
2442      rtx to, from;
2443      int unsignedp;
2444 {
2445   enum insn_code icode;
2446   register rtx target = to;
2447   enum machine_mode fmode, imode;
2448
2449   /* Crash now, because we won't be able to decide which mode to use.  */
2450   if (GET_MODE (from) == VOIDmode)
2451     abort ();
2452
2453   /* Look for an insn to do the conversion.  Do it in the specified
2454      modes if possible; otherwise convert either input, output or both to
2455      wider mode.  If the integer mode is wider than the mode of FROM,
2456      we can do the conversion signed even if the input is unsigned.  */
2457
2458   for (imode = GET_MODE (from); imode != VOIDmode;
2459        imode = GET_MODE_WIDER_MODE (imode))
2460     for (fmode = GET_MODE (to); fmode != VOIDmode;
2461          fmode = GET_MODE_WIDER_MODE (fmode))
2462       {
2463         int doing_unsigned = unsignedp;
2464
2465         icode = can_float_p (fmode, imode, unsignedp);
2466         if (icode == CODE_FOR_nothing && imode != GET_MODE (from) && unsignedp)
2467           icode = can_float_p (fmode, imode, 0), doing_unsigned = 0;
2468
2469         if (icode != CODE_FOR_nothing)
2470           {
2471             to = protect_from_queue (to, 1);
2472
2473             if (imode != GET_MODE (from))
2474               from = convert_to_mode (imode, from, unsignedp);
2475             else
2476               from = protect_from_queue (from, 0);
2477
2478             if (fmode != GET_MODE (to))
2479               target = gen_reg_rtx (fmode);
2480
2481             emit_unop_insn (icode, target, from,
2482                             doing_unsigned ? UNSIGNED_FLOAT : FLOAT);
2483
2484             if (target != to)
2485               convert_move (to, target, 0);
2486             return;
2487           }
2488     }
2489
2490 #if !defined (REAL_IS_NOT_DOUBLE) || defined (REAL_ARITHMETIC)
2491
2492   /* Unsigned integer, and no way to convert directly.
2493      Convert as signed, then conditionally adjust the result.  */
2494   if (unsignedp)
2495     {
2496       rtx label = gen_label_rtx ();
2497       rtx temp;
2498       REAL_VALUE_TYPE offset;
2499
2500       emit_queue ();
2501
2502       to = protect_from_queue (to, 1);
2503       from = protect_from_queue (from, 0);
2504
2505       if (flag_force_mem)
2506         from = force_not_mem (from);
2507
2508       /* If we are about to do some arithmetic to correct for an
2509          unsigned operand, do it in a pseudo-register.  */
2510
2511       if (GET_CODE (to) != REG || REGNO (to) <= LAST_VIRTUAL_REGISTER)
2512         target = gen_reg_rtx (GET_MODE (to));
2513
2514       /* Convert as signed integer to floating.  */
2515       expand_float (target, from, 0);
2516
2517       /* If FROM is negative (and therefore TO is negative),
2518          correct its value by 2**bitwidth.  */
2519
2520       do_pending_stack_adjust ();
2521       emit_cmp_insn (from, const0_rtx, GE, 0, GET_MODE (from), 0, 0);
2522       emit_jump_insn (gen_bge (label));
2523       /* On SCO 3.2.1, ldexp rejects values outside [0.5, 1).
2524          Rather than setting up a dconst_dot_5, let's hope SCO
2525          fixes the bug.  */
2526       offset = REAL_VALUE_LDEXP (dconst1, GET_MODE_BITSIZE (GET_MODE (from)));
2527       temp = expand_binop (GET_MODE (to), add_optab, target,
2528                            immed_real_const_1 (offset, GET_MODE (to)),
2529                            target, 0, OPTAB_LIB_WIDEN);
2530       if (temp != target)
2531         emit_move_insn (target, temp);
2532       do_pending_stack_adjust ();
2533       emit_label (label);
2534     }
2535   else
2536 #endif
2537
2538   /* No hardware instruction available; call a library
2539      to convert from SImode or DImode into SFmode or DFmode.  */
2540     {
2541       rtx libfcn;
2542       rtx insns;
2543
2544       to = protect_from_queue (to, 1);
2545
2546       if (GET_MODE_SIZE (GET_MODE (from)) < GET_MODE_SIZE (SImode))
2547         from = convert_to_mode (SImode, from, unsignedp);
2548       else
2549         from = protect_from_queue (from, 0);
2550
2551       if (flag_force_mem)
2552         from = force_not_mem (from);
2553
2554       if (GET_MODE (to) == SFmode)
2555         {
2556           if (GET_MODE (from) == SImode)
2557             libfcn = floatsisf_libfunc;
2558           else if (GET_MODE (from) == DImode)
2559             libfcn = floatdisf_libfunc;
2560           else
2561             abort ();
2562         }
2563       else if (GET_MODE (to) == DFmode)
2564         {
2565           if (GET_MODE (from) == SImode)
2566             libfcn = floatsidf_libfunc;
2567           else if (GET_MODE (from) == DImode)
2568             libfcn = floatdidf_libfunc;
2569           else
2570             abort ();
2571         }
2572       else
2573         abort ();
2574
2575       start_sequence ();
2576
2577       emit_library_call (libfcn, 1, GET_MODE (to), 1, from, GET_MODE (from));
2578       insns = get_insns ();
2579       end_sequence ();
2580
2581       emit_libcall_block (insns, target, hard_libcall_value (GET_MODE (to)),
2582                           gen_rtx (FLOAT, GET_MODE (to), from));
2583     }
2584
2585   /* Copy result to requested destination
2586      if we have been computing in a temp location.  */
2587
2588   if (target != to)
2589     {
2590       if (GET_MODE (target) == GET_MODE (to))
2591         emit_move_insn (to, target);
2592       else
2593         convert_move (to, target, 0);
2594     }
2595 }
2596 \f
2597 /* expand_fix: generate code to convert FROM to fixed point
2598    and store in TO.  FROM must be floating point.  */
2599
2600 static rtx
2601 ftruncify (x)
2602      rtx x;
2603 {
2604   rtx temp = gen_reg_rtx (GET_MODE (x));
2605   return expand_unop (GET_MODE (x), ftrunc_optab, x, temp, 0);
2606 }
2607
2608 void
2609 expand_fix (to, from, unsignedp)
2610      register rtx to, from;
2611      int unsignedp;
2612 {
2613   enum insn_code icode;
2614   register rtx target = to;
2615   enum machine_mode fmode, imode;
2616   int must_trunc = 0;
2617   rtx libfcn = 0;
2618
2619   /* We first try to find a pair of modes, one real and one integer, at
2620      least as wide as FROM and TO, respectively, in which we can open-code
2621      this conversion.  If the integer mode is wider than the mode of TO,
2622      we can do the conversion either signed or unsigned.  */
2623
2624   for (imode = GET_MODE (to); imode != VOIDmode;
2625        imode = GET_MODE_WIDER_MODE (imode))
2626     for (fmode = GET_MODE (from); fmode != VOIDmode;
2627          fmode = GET_MODE_WIDER_MODE (fmode))
2628       {
2629         int doing_unsigned = unsignedp;
2630
2631         icode = can_fix_p (imode, fmode, unsignedp, &must_trunc);
2632         if (icode == CODE_FOR_nothing && imode != GET_MODE (to) && unsignedp)
2633           icode = can_fix_p (imode, fmode, 0, &must_trunc), doing_unsigned = 0;
2634
2635         if (icode != CODE_FOR_nothing)
2636           {
2637             to = protect_from_queue (to, 1);
2638
2639             if (fmode != GET_MODE (from))
2640               from = convert_to_mode (fmode, from, 0);
2641             else
2642               from = protect_from_queue (from, 0);
2643
2644             if (must_trunc)
2645               from = ftruncify (from);
2646
2647             if (imode != GET_MODE (to))
2648               target = gen_reg_rtx (imode);
2649
2650             emit_unop_insn (icode, target, from,
2651                             doing_unsigned ? UNSIGNED_FIX : FIX);
2652             if (target != to)
2653               convert_move (to, target, unsignedp);
2654             return;
2655           }
2656       }
2657
2658 #if !defined (REAL_IS_NOT_DOUBLE) || defined (REAL_ARITHMETIC)
2659   /* For an unsigned conversion, there is one more way to do it.
2660      If we have a signed conversion, we generate code that compares
2661      the real value to the largest representable positive number.  If if
2662      is smaller, the conversion is done normally.  Otherwise, subtract
2663      one plus the highest signed number, convert, and add it back.
2664
2665      We only need to check all real modes, since we know we didn't find
2666      anything with a wider inetger mode.  */
2667
2668   if (unsignedp && GET_MODE_BITSIZE (GET_MODE (to)) <= HOST_BITS_PER_INT)
2669     for (fmode = GET_MODE (from); fmode != VOIDmode;
2670          fmode = GET_MODE_WIDER_MODE (fmode))
2671       /* Make sure we won't lose significant bits doing this.  */
2672       if (GET_MODE_BITSIZE (fmode) > GET_MODE_BITSIZE (GET_MODE (to))
2673           && CODE_FOR_nothing != can_fix_p (GET_MODE (to), fmode, 0,
2674                                             &must_trunc))
2675         {
2676           int bitsize = GET_MODE_BITSIZE (GET_MODE (to));
2677           REAL_VALUE_TYPE offset = REAL_VALUE_LDEXP (dconst1, bitsize - 1);
2678           rtx limit = immed_real_const_1 (offset, fmode);
2679           rtx lab1 = gen_label_rtx ();
2680           rtx lab2 = gen_label_rtx ();
2681           rtx insn;
2682
2683           emit_queue ();
2684           to = protect_from_queue (to, 1);
2685           from = protect_from_queue (from, 0);
2686
2687           if (flag_force_mem)
2688             from = force_not_mem (from);
2689
2690           if (fmode != GET_MODE (from))
2691             from = convert_to_mode (fmode, from, 0);
2692
2693           /* See if we need to do the subtraction.  */
2694           do_pending_stack_adjust ();
2695           emit_cmp_insn (from, limit, GE, 0, GET_MODE (from), 0, 0);
2696           emit_jump_insn (gen_bge (lab1));
2697
2698           /* If not, do the signed "fix" and branch around fixup code.  */
2699           expand_fix (to, from, 0);
2700           emit_jump_insn (gen_jump (lab2));
2701           emit_barrier ();
2702
2703           /* Otherwise, subtract 2**(N-1), convert to signed number,
2704              then add 2**(N-1).  Do the addition using XOR since this
2705              will often generate better code.  */
2706           emit_label (lab1);
2707           target = expand_binop (GET_MODE (from), sub_optab, from, limit,
2708                                  0, 0, OPTAB_LIB_WIDEN);
2709           expand_fix (to, target, 0);
2710           target = expand_binop (GET_MODE (to), xor_optab, to,
2711                                  gen_rtx (CONST_INT, VOIDmode,
2712                                         1 << (bitsize - 1)),
2713                                  to, 1, OPTAB_LIB_WIDEN);
2714
2715           if (target != to)
2716             emit_move_insn (to, target);
2717
2718           emit_label (lab2);
2719
2720           /* Make a place for a REG_NOTE and add it.  */
2721           insn = emit_move_insn (to, to);
2722           REG_NOTES (insn) = gen_rtx (EXPR_LIST, REG_EQUAL,
2723                                       gen_rtx (UNSIGNED_FIX, GET_MODE (to),
2724                                                from), REG_NOTES (insn));
2725
2726           return;
2727         }
2728 #endif
2729
2730   /* We can't do it with an insn, so use a library call.  But first ensure
2731      that the mode of TO is at least as wide as SImode, since those are the
2732      only library calls we know about.  */
2733
2734   if (GET_MODE_SIZE (GET_MODE (to)) < GET_MODE_SIZE (SImode))
2735     {
2736       target = gen_reg_rtx (SImode);
2737
2738       expand_fix (target, from, unsignedp);
2739     }
2740   else if (GET_MODE (from) == SFmode)
2741     {
2742       if (GET_MODE (to) == SImode)
2743         libfcn = unsignedp ? fixunssfsi_libfunc : fixsfsi_libfunc;
2744       else if (GET_MODE (to) == DImode)
2745         libfcn = unsignedp ? fixunssfdi_libfunc : fixsfdi_libfunc;
2746       else
2747         abort ();
2748     }
2749   else if (GET_MODE (from) == DFmode)
2750     {
2751       if (GET_MODE (to) == SImode)
2752         libfcn = unsignedp ? fixunsdfsi_libfunc : fixdfsi_libfunc;
2753       else if (GET_MODE (to) == DImode)
2754         libfcn = unsignedp ? fixunsdfdi_libfunc : fixdfdi_libfunc;
2755       else
2756         abort ();
2757     }
2758   else
2759     abort ();
2760
2761   if (libfcn)
2762     {
2763       rtx insns;
2764
2765       to = protect_from_queue (to, 1);
2766       from = protect_from_queue (from, 0);
2767
2768       if (flag_force_mem)
2769         from = force_not_mem (from);
2770
2771       start_sequence ();
2772
2773       emit_library_call (libfcn, 1, GET_MODE (to), 1, from, GET_MODE (from));
2774       insns = get_insns ();
2775       end_sequence ();
2776
2777       emit_libcall_block (insns, target, hard_libcall_value (GET_MODE (to)),
2778                           gen_rtx (unsignedp ? FIX : UNSIGNED_FIX,
2779                                    GET_MODE (to), from));
2780     }
2781       
2782   if (GET_MODE (to) == GET_MODE (target))
2783     emit_move_insn (to, target);
2784   else
2785     convert_move (to, target, 0);
2786 }
2787 \f
2788 static optab
2789 init_optab (code)
2790      enum rtx_code code;
2791 {
2792   int i;
2793   optab op = (optab) xmalloc (sizeof (struct optab));
2794   op->code = code;
2795   for (i = 0; i < NUM_MACHINE_MODES; i++)
2796     {
2797       op->handlers[i].insn_code = CODE_FOR_nothing;
2798       op->handlers[i].libfunc = 0;
2799     }
2800   return op;
2801 }
2802
2803 /* Call this once to initialize the contents of the optabs
2804    appropriately for the current target machine.  */
2805
2806 void
2807 init_optabs ()
2808 {
2809   int i;
2810
2811   init_fixtab ();
2812   init_floattab ();
2813   init_extends ();
2814
2815   add_optab = init_optab (PLUS);
2816   sub_optab = init_optab (MINUS);
2817   smul_optab = init_optab (MULT);
2818   smul_widen_optab = init_optab (UNKNOWN);
2819   umul_widen_optab = init_optab (UNKNOWN);
2820   sdiv_optab = init_optab (DIV);
2821   sdivmod_optab = init_optab (UNKNOWN);
2822   udiv_optab = init_optab (UDIV);
2823   udivmod_optab = init_optab (UNKNOWN);
2824   smod_optab = init_optab (MOD);
2825   umod_optab = init_optab (UMOD);
2826   flodiv_optab = init_optab (DIV);
2827   ftrunc_optab = init_optab (UNKNOWN);
2828   and_optab = init_optab (AND);
2829   ior_optab = init_optab (IOR);
2830   xor_optab = init_optab (XOR);
2831   ashl_optab = init_optab (ASHIFT);
2832   ashr_optab = init_optab (ASHIFTRT);
2833   lshl_optab = init_optab (LSHIFT);
2834   lshr_optab = init_optab (LSHIFTRT);
2835   rotl_optab = init_optab (ROTATE);
2836   rotr_optab = init_optab (ROTATERT);
2837   smin_optab = init_optab (SMIN);
2838   smax_optab = init_optab (SMAX);
2839   umin_optab = init_optab (UMIN);
2840   umax_optab = init_optab (UMAX);
2841   mov_optab = init_optab (UNKNOWN);
2842   movstrict_optab = init_optab (UNKNOWN);
2843   cmp_optab = init_optab (UNKNOWN);
2844   ucmp_optab = init_optab (UNKNOWN);
2845   tst_optab = init_optab (UNKNOWN);
2846   neg_optab = init_optab (NEG);
2847   abs_optab = init_optab (ABS);
2848   one_cmpl_optab = init_optab (NOT);
2849   ffs_optab = init_optab (FFS);
2850   sqrt_optab = init_optab (SQRT);
2851   strlen_optab = init_optab (UNKNOWN);
2852
2853 #ifdef HAVE_addqi3
2854   if (HAVE_addqi3)
2855     add_optab->handlers[(int) QImode].insn_code = CODE_FOR_addqi3;
2856 #endif
2857 #ifdef HAVE_addhi3
2858   if (HAVE_addhi3)
2859     add_optab->handlers[(int) HImode].insn_code = CODE_FOR_addhi3;
2860 #endif
2861 #ifdef HAVE_addpsi3
2862   if (HAVE_addpsi3)
2863     add_optab->handlers[(int) PSImode].insn_code = CODE_FOR_addpsi3;
2864 #endif
2865 #ifdef HAVE_addsi3
2866   if (HAVE_addsi3)
2867     add_optab->handlers[(int) SImode].insn_code = CODE_FOR_addsi3;
2868 #endif
2869 #ifdef HAVE_adddi3
2870   if (HAVE_adddi3)
2871     add_optab->handlers[(int) DImode].insn_code = CODE_FOR_adddi3;
2872 #endif
2873 #ifdef HAVE_addti3
2874   if (HAVE_addti3)
2875     add_optab->handlers[(int) TImode].insn_code = CODE_FOR_addti3;
2876 #endif
2877 #ifdef HAVE_addsf3
2878   if (HAVE_addsf3)
2879     add_optab->handlers[(int) SFmode].insn_code = CODE_FOR_addsf3;
2880 #endif
2881 #ifdef HAVE_adddf3
2882   if (HAVE_adddf3)
2883     add_optab->handlers[(int) DFmode].insn_code = CODE_FOR_adddf3;
2884 #endif
2885 #ifdef HAVE_addtf3
2886   if (HAVE_addtf3)
2887     add_optab->handlers[(int) TFmode].insn_code = CODE_FOR_addtf3;
2888 #endif
2889   add_optab->handlers[(int) SFmode].libfunc
2890     = gen_rtx (SYMBOL_REF, Pmode, "__addsf3");
2891   add_optab->handlers[(int) DFmode].libfunc
2892     = gen_rtx (SYMBOL_REF, Pmode, "__adddf3");
2893
2894 #ifdef HAVE_subqi3
2895   if (HAVE_subqi3)
2896     sub_optab->handlers[(int) QImode].insn_code = CODE_FOR_subqi3;
2897 #endif
2898 #ifdef HAVE_subhi3
2899   if (HAVE_subhi3)
2900     sub_optab->handlers[(int) HImode].insn_code = CODE_FOR_subhi3;
2901 #endif
2902 #ifdef HAVE_subpsi3
2903   if (HAVE_subpsi3)
2904     sub_optab->handlers[(int) PSImode].insn_code = CODE_FOR_subpsi3;
2905 #endif
2906 #ifdef HAVE_subsi3
2907   if (HAVE_subsi3)
2908     sub_optab->handlers[(int) SImode].insn_code = CODE_FOR_subsi3;
2909 #endif
2910 #ifdef HAVE_subdi3
2911   if (HAVE_subdi3)
2912     sub_optab->handlers[(int) DImode].insn_code = CODE_FOR_subdi3;
2913 #endif
2914 #ifdef HAVE_subti3
2915   if (HAVE_subti3)
2916     sub_optab->handlers[(int) TImode].insn_code = CODE_FOR_subti3;
2917 #endif
2918 #ifdef HAVE_subsf3
2919   if (HAVE_subsf3)
2920     sub_optab->handlers[(int) SFmode].insn_code = CODE_FOR_subsf3;
2921 #endif
2922 #ifdef HAVE_subdf3
2923   if (HAVE_subdf3)
2924     sub_optab->handlers[(int) DFmode].insn_code = CODE_FOR_subdf3;
2925 #endif
2926 #ifdef HAVE_subtf3
2927   if (HAVE_subtf3)
2928     sub_optab->handlers[(int) TFmode].insn_code = CODE_FOR_subtf3;
2929 #endif
2930   sub_optab->handlers[(int) SFmode].libfunc
2931     = gen_rtx (SYMBOL_REF, Pmode, "__subsf3");
2932   sub_optab->handlers[(int) DFmode].libfunc
2933     = gen_rtx (SYMBOL_REF, Pmode, "__subdf3");
2934
2935 #ifdef HAVE_mulqi3
2936   if (HAVE_mulqi3)
2937     smul_optab->handlers[(int) QImode].insn_code = CODE_FOR_mulqi3;
2938 #endif
2939 #ifdef HAVE_mulhi3
2940   if (HAVE_mulhi3)
2941     smul_optab->handlers[(int) HImode].insn_code = CODE_FOR_mulhi3;
2942 #endif
2943 #ifdef HAVE_mulpsi3
2944   if (HAVE_mulpsi3)
2945     smul_optab->handlers[(int) PSImode].insn_code = CODE_FOR_mulpsi3;
2946 #endif
2947 #ifdef HAVE_mulsi3
2948   if (HAVE_mulsi3)
2949     smul_optab->handlers[(int) SImode].insn_code = CODE_FOR_mulsi3;
2950 #endif
2951 #ifdef HAVE_muldi3
2952   if (HAVE_muldi3)
2953     smul_optab->handlers[(int) DImode].insn_code = CODE_FOR_muldi3;
2954 #endif
2955 #ifdef HAVE_multi3
2956   if (HAVE_multi3)
2957     smul_optab->handlers[(int) TImode].insn_code = CODE_FOR_multi3;
2958 #endif
2959 #ifdef HAVE_mulsf3
2960   if (HAVE_mulsf3)
2961     smul_optab->handlers[(int) SFmode].insn_code = CODE_FOR_mulsf3;
2962 #endif
2963 #ifdef HAVE_muldf3
2964   if (HAVE_muldf3)
2965     smul_optab->handlers[(int) DFmode].insn_code = CODE_FOR_muldf3;
2966 #endif
2967 #ifdef HAVE_multf3
2968   if (HAVE_multf3)
2969     smul_optab->handlers[(int) TFmode].insn_code = CODE_FOR_multf3;
2970 #endif
2971
2972 #ifdef MULSI3_LIBCALL
2973   smul_optab->handlers[(int) SImode].libfunc
2974     = gen_rtx (SYMBOL_REF, Pmode, MULSI3_LIBCALL);
2975 #else
2976   smul_optab->handlers[(int) SImode].libfunc
2977     = gen_rtx (SYMBOL_REF, Pmode, "__mulsi3");
2978 #endif
2979 #ifdef MULDI3_LIBCALL
2980   smul_optab->handlers[(int) DImode].libfunc
2981     = gen_rtx (SYMBOL_REF, Pmode, MULDI3_LIBCALL);
2982 #else
2983   smul_optab->handlers[(int) DImode].libfunc
2984     = gen_rtx (SYMBOL_REF, Pmode, "__muldi3");
2985 #endif
2986   smul_optab->handlers[(int) SFmode].libfunc
2987     = gen_rtx (SYMBOL_REF, Pmode, "__mulsf3");
2988   smul_optab->handlers[(int) DFmode].libfunc
2989     = gen_rtx (SYMBOL_REF, Pmode, "__muldf3");
2990
2991 #ifdef HAVE_mulqihi3
2992   if (HAVE_mulqihi3)
2993     smul_widen_optab->handlers[(int) HImode].insn_code = CODE_FOR_mulqihi3;
2994 #endif
2995 #ifdef HAVE_mulhisi3
2996   if (HAVE_mulhisi3)
2997     smul_widen_optab->handlers[(int) SImode].insn_code = CODE_FOR_mulhisi3;
2998 #endif
2999 #ifdef HAVE_mulsidi3
3000   if (HAVE_mulsidi3)
3001     smul_widen_optab->handlers[(int) DImode].insn_code = CODE_FOR_mulsidi3;
3002 #endif
3003 #ifdef HAVE_mulditi3
3004   if (HAVE_mulditi3)
3005     smul_widen_optab->handlers[(int) TImode].insn_code = CODE_FOR_mulditi3;
3006 #endif
3007
3008 #ifdef HAVE_umulqihi3
3009   if (HAVE_umulqihi3)
3010     umul_widen_optab->handlers[(int) HImode].insn_code = CODE_FOR_umulqihi3;
3011 #endif
3012 #ifdef HAVE_umulhisi3
3013   if (HAVE_umulhisi3)
3014     umul_widen_optab->handlers[(int) SImode].insn_code = CODE_FOR_umulhisi3;
3015 #endif
3016 #ifdef HAVE_umulsidi3
3017   if (HAVE_umulsidi3)
3018     umul_widen_optab->handlers[(int) DImode].insn_code = CODE_FOR_umulsidi3;
3019 #endif
3020 #ifdef HAVE_umulditi3
3021   if (HAVE_umulditi3)
3022     umul_widen_optab->handlers[(int) TImode].insn_code = CODE_FOR_umulditi3;
3023 #endif
3024
3025 #ifdef HAVE_divqi3
3026   if (HAVE_divqi3)
3027     sdiv_optab->handlers[(int) QImode].insn_code = CODE_FOR_divqi3;
3028 #endif
3029 #ifdef HAVE_divhi3
3030   if (HAVE_divhi3)
3031     sdiv_optab->handlers[(int) HImode].insn_code = CODE_FOR_divhi3;
3032 #endif
3033 #ifdef HAVE_divpsi3
3034   if (HAVE_divpsi3)
3035     sdiv_optab->handlers[(int) PSImode].insn_code = CODE_FOR_divpsi3;
3036 #endif
3037 #ifdef HAVE_divsi3
3038   if (HAVE_divsi3)
3039     sdiv_optab->handlers[(int) SImode].insn_code = CODE_FOR_divsi3;
3040 #endif
3041 #ifdef HAVE_divdi3
3042   if (HAVE_divdi3)
3043     sdiv_optab->handlers[(int) DImode].insn_code = CODE_FOR_divdi3;
3044 #endif
3045 #ifdef HAVE_divti3
3046   if (HAVE_divti3)
3047     sdiv_optab->handlers[(int) TImode].insn_code = CODE_FOR_divti3;
3048 #endif
3049
3050 #ifdef DIVSI3_LIBCALL
3051   sdiv_optab->handlers[(int) SImode].libfunc
3052     = gen_rtx (SYMBOL_REF, Pmode, DIVSI3_LIBCALL);
3053 #else
3054   sdiv_optab->handlers[(int) SImode].libfunc
3055     = gen_rtx (SYMBOL_REF, Pmode, "__divsi3");
3056 #endif
3057 #ifdef DIVDI3_LIBCALL
3058   sdiv_optab->handlers[(int) DImode].libfunc
3059     = gen_rtx (SYMBOL_REF, Pmode, DIVDI3_LIBCALL);
3060 #else
3061   sdiv_optab->handlers[(int) DImode].libfunc
3062     = gen_rtx (SYMBOL_REF, Pmode, "__divdi3");
3063 #endif
3064
3065 #ifdef HAVE_udivqi3
3066   if (HAVE_udivqi3)
3067     udiv_optab->handlers[(int) QImode].insn_code = CODE_FOR_udivqi3;
3068 #endif
3069 #ifdef HAVE_udivhi3
3070   if (HAVE_udivhi3)
3071     udiv_optab->handlers[(int) HImode].insn_code = CODE_FOR_udivhi3;
3072 #endif
3073 #ifdef HAVE_udivpsi3
3074   if (HAVE_udivpsi3)
3075     udiv_optab->handlers[(int) PSImode].insn_code = CODE_FOR_udivpsi3;
3076 #endif
3077 #ifdef HAVE_udivsi3
3078   if (HAVE_udivsi3)
3079     udiv_optab->handlers[(int) SImode].insn_code = CODE_FOR_udivsi3;
3080 #endif
3081 #ifdef HAVE_udivdi3
3082   if (HAVE_udivdi3)
3083     udiv_optab->handlers[(int) DImode].insn_code = CODE_FOR_udivdi3;
3084 #endif
3085 #ifdef HAVE_udivti3
3086   if (HAVE_udivti3)
3087     udiv_optab->handlers[(int) TImode].insn_code = CODE_FOR_udivti3;
3088 #endif
3089
3090 #ifdef UDIVSI3_LIBCALL
3091   udiv_optab->handlers[(int) SImode].libfunc
3092     = gen_rtx (SYMBOL_REF, Pmode, UDIVSI3_LIBCALL);
3093 #else
3094   udiv_optab->handlers[(int) SImode].libfunc
3095     = gen_rtx (SYMBOL_REF, Pmode, "__udivsi3");
3096 #endif
3097 #ifdef UDIVDI3_LIBCALL
3098   udiv_optab->handlers[(int) DImode].libfunc
3099     = gen_rtx (SYMBOL_REF, Pmode, UDIVDI3_LIBCALL);
3100 #else
3101   udiv_optab->handlers[(int) DImode].libfunc
3102     = gen_rtx (SYMBOL_REF, Pmode, "__udivdi3");
3103 #endif
3104
3105 #ifdef HAVE_divmodqi4
3106   if (HAVE_divmodqi4)
3107     sdivmod_optab->handlers[(int) QImode].insn_code = CODE_FOR_divmodqi4;
3108 #endif
3109 #ifdef HAVE_divmodhi4
3110   if (HAVE_divmodhi4)
3111     sdivmod_optab->handlers[(int) HImode].insn_code = CODE_FOR_divmodhi4;
3112 #endif
3113 #ifdef HAVE_divmodsi4
3114   if (HAVE_divmodsi4)
3115     sdivmod_optab->handlers[(int) SImode].insn_code = CODE_FOR_divmodsi4;
3116 #endif
3117 #ifdef HAVE_divmoddi4
3118   if (HAVE_divmoddi4)
3119     sdivmod_optab->handlers[(int) DImode].insn_code = CODE_FOR_divmoddi4;
3120 #endif
3121 #ifdef HAVE_divmodti4
3122   if (HAVE_divmodti4)
3123     sdivmod_optab->handlers[(int) TImode].insn_code = CODE_FOR_divmodti4;
3124 #endif
3125
3126 #ifdef HAVE_udivmodqi4
3127   if (HAVE_udivmodqi4)
3128     udivmod_optab->handlers[(int) QImode].insn_code = CODE_FOR_udivmodqi4;
3129 #endif
3130 #ifdef HAVE_udivmodhi4
3131   if (HAVE_udivmodhi4)
3132     udivmod_optab->handlers[(int) HImode].insn_code = CODE_FOR_udivmodhi4;
3133 #endif
3134 #ifdef HAVE_udivmodsi4
3135   if (HAVE_udivmodsi4)
3136     udivmod_optab->handlers[(int) SImode].insn_code = CODE_FOR_udivmodsi4;
3137 #endif
3138 #ifdef HAVE_udivmoddi4
3139   if (HAVE_udivmoddi4)
3140     udivmod_optab->handlers[(int) DImode].insn_code = CODE_FOR_udivmoddi4;
3141 #endif
3142 #ifdef HAVE_udivmodti4
3143   if (HAVE_udivmodti4)
3144     udivmod_optab->handlers[(int) TImode].insn_code = CODE_FOR_udivmodti4;
3145 #endif
3146
3147 #ifdef HAVE_modqi3
3148   if (HAVE_modqi3)
3149     smod_optab->handlers[(int) QImode].insn_code = CODE_FOR_modqi3;
3150 #endif
3151 #ifdef HAVE_modhi3
3152   if (HAVE_modhi3)
3153     smod_optab->handlers[(int) HImode].insn_code = CODE_FOR_modhi3;
3154 #endif
3155 #ifdef HAVE_modpsi3
3156   if (HAVE_modpsi3)
3157     smod_optab->handlers[(int) PSImode].insn_code = CODE_FOR_modpsi3;
3158 #endif
3159 #ifdef HAVE_modsi3
3160   if (HAVE_modsi3)
3161     smod_optab->handlers[(int) SImode].insn_code = CODE_FOR_modsi3;
3162 #endif
3163 #ifdef HAVE_moddi3
3164   if (HAVE_moddi3)
3165     smod_optab->handlers[(int) DImode].insn_code = CODE_FOR_moddi3;
3166 #endif
3167 #ifdef HAVE_modti3
3168   if (HAVE_modti3)
3169     smod_optab->handlers[(int) TImode].insn_code = CODE_FOR_modti3;
3170 #endif
3171
3172 #ifdef MODSI3_LIBCALL
3173   smod_optab->handlers[(int) SImode].libfunc
3174     = gen_rtx (SYMBOL_REF, Pmode, MODSI3_LIBCALL);
3175 #else
3176   smod_optab->handlers[(int) SImode].libfunc
3177     = gen_rtx (SYMBOL_REF, Pmode, "__modsi3");
3178 #endif
3179 #ifdef MODDI3_LIBCALL
3180   smod_optab->handlers[(int) DImode].libfunc
3181     = gen_rtx (SYMBOL_REF, Pmode, MODDI3_LIBCALL);
3182 #else
3183   smod_optab->handlers[(int) DImode].libfunc
3184     = gen_rtx (SYMBOL_REF, Pmode, "__moddi3");
3185 #endif
3186
3187 #ifdef HAVE_umodqi3
3188   if (HAVE_umodqi3)
3189     umod_optab->handlers[(int) QImode].insn_code = CODE_FOR_umodqi3;
3190 #endif
3191 #ifdef HAVE_umodhi3
3192   if (HAVE_umodhi3)
3193     umod_optab->handlers[(int) HImode].insn_code = CODE_FOR_umodhi3;
3194 #endif
3195 #ifdef HAVE_umodpsi3
3196   if (HAVE_umodpsi3)
3197     umod_optab->handlers[(int) PSImode].insn_code = CODE_FOR_umodpsi3;
3198 #endif
3199 #ifdef HAVE_umodsi3
3200   if (HAVE_umodsi3)
3201     umod_optab->handlers[(int) SImode].insn_code = CODE_FOR_umodsi3;
3202 #endif
3203 #ifdef HAVE_umoddi3
3204   if (HAVE_umoddi3)
3205     umod_optab->handlers[(int) DImode].insn_code = CODE_FOR_umoddi3;
3206 #endif
3207 #ifdef HAVE_umodti3
3208   if (HAVE_umodti3)
3209     umod_optab->handlers[(int) TImode].insn_code = CODE_FOR_umodti3;
3210 #endif
3211
3212 #ifdef UMODSI3_LIBCALL
3213   umod_optab->handlers[(int) SImode].libfunc
3214     = gen_rtx (SYMBOL_REF, Pmode, UMODSI3_LIBCALL);
3215 #else
3216   umod_optab->handlers[(int) SImode].libfunc
3217     = gen_rtx (SYMBOL_REF, Pmode, "__umodsi3");
3218 #endif
3219 #ifdef UMODDI3_LIBCALL
3220   umod_optab->handlers[(int) DImode].libfunc
3221     = gen_rtx (SYMBOL_REF, Pmode, UMODDI3_LIBCALL);
3222 #else
3223   umod_optab->handlers[(int) DImode].libfunc
3224     = gen_rtx (SYMBOL_REF, Pmode, "__umoddi3");
3225 #endif
3226
3227 #ifdef HAVE_divsf3
3228   if (HAVE_divsf3)
3229     flodiv_optab->handlers[(int) SFmode].insn_code = CODE_FOR_divsf3;
3230 #endif
3231 #ifdef HAVE_divdf3
3232   if (HAVE_divdf3)
3233     flodiv_optab->handlers[(int) DFmode].insn_code = CODE_FOR_divdf3;
3234 #endif
3235 #ifdef HAVE_divtf3
3236   if (HAVE_divtf3)
3237     flodiv_optab->handlers[(int) TFmode].insn_code = CODE_FOR_divtf3;
3238 #endif
3239   flodiv_optab->handlers[(int) SFmode].libfunc
3240     = gen_rtx (SYMBOL_REF, Pmode, "__divsf3");
3241   flodiv_optab->handlers[(int) DFmode].libfunc
3242     = gen_rtx (SYMBOL_REF, Pmode, "__divdf3");
3243
3244 #ifdef HAVE_ftruncsf2
3245   if (HAVE_ftruncsf2)
3246     ftrunc_optab->handlers[(int) SFmode].insn_code = CODE_FOR_ftruncsf2;
3247 #endif
3248 #ifdef HAVE_ftruncdf2
3249   if (HAVE_ftruncdf2)
3250     ftrunc_optab->handlers[(int) DFmode].insn_code = CODE_FOR_ftruncdf2;
3251 #endif
3252 #ifdef HAVE_ftrunctf2
3253   if (HAVE_ftrunctf2)
3254     ftrunc_optab->handlers[(int) TFmode].insn_code = CODE_FOR_ftrunctf2;
3255 #endif
3256
3257 #ifdef HAVE_andqi3
3258   if (HAVE_andqi3)
3259     and_optab->handlers[(int) QImode].insn_code = CODE_FOR_andqi3;
3260 #endif
3261 #ifdef HAVE_andhi3
3262   if (HAVE_andhi3)
3263     and_optab->handlers[(int) HImode].insn_code = CODE_FOR_andhi3;
3264 #endif
3265 #ifdef HAVE_andpsi3
3266   if (HAVE_andpsi3)
3267     and_optab->handlers[(int) PSImode].insn_code = CODE_FOR_andpsi3;
3268 #endif
3269 #ifdef HAVE_andsi3
3270   if (HAVE_andsi3)
3271     and_optab->handlers[(int) SImode].insn_code = CODE_FOR_andsi3;
3272 #endif
3273 #ifdef HAVE_anddi3
3274   if (HAVE_anddi3)
3275     and_optab->handlers[(int) DImode].insn_code = CODE_FOR_anddi3;
3276 #endif
3277 #ifdef HAVE_andti3
3278   if (HAVE_andti3)
3279     and_optab->handlers[(int) TImode].insn_code = CODE_FOR_andti3;
3280 #endif
3281
3282 #ifdef HAVE_iorqi3
3283   if (HAVE_iorqi3)
3284     ior_optab->handlers[(int) QImode].insn_code = CODE_FOR_iorqi3;
3285 #endif
3286 #ifdef HAVE_iorhi3
3287   if (HAVE_iorhi3)
3288     ior_optab->handlers[(int) HImode].insn_code = CODE_FOR_iorhi3;
3289 #endif
3290 #ifdef HAVE_iorpsi3
3291   if (HAVE_iorpsi3)
3292     ior_optab->handlers[(int) PSImode].insn_code = CODE_FOR_iorpsi3;
3293 #endif
3294 #ifdef HAVE_iorsi3
3295   if (HAVE_iorsi3)
3296     ior_optab->handlers[(int) SImode].insn_code = CODE_FOR_iorsi3;
3297 #endif
3298 #ifdef HAVE_iordi3
3299   if (HAVE_iordi3)
3300     ior_optab->handlers[(int) DImode].insn_code = CODE_FOR_iordi3;
3301 #endif
3302 #ifdef HAVE_iorti3
3303   if (HAVE_iorti3)
3304     ior_optab->handlers[(int) TImode].insn_code = CODE_FOR_iorti3;
3305 #endif
3306
3307 #ifdef HAVE_xorqi3
3308   if (HAVE_xorqi3)
3309     xor_optab->handlers[(int) QImode].insn_code = CODE_FOR_xorqi3;
3310 #endif
3311 #ifdef HAVE_xorhi3
3312   if (HAVE_xorhi3)
3313     xor_optab->handlers[(int) HImode].insn_code = CODE_FOR_xorhi3;
3314 #endif
3315 #ifdef HAVE_xorpsi3
3316   if (HAVE_xorpsi3)
3317     xor_optab->handlers[(int) PSImode].insn_code = CODE_FOR_xorpsi3;
3318 #endif
3319 #ifdef HAVE_xorsi3
3320   if (HAVE_xorsi3)
3321     xor_optab->handlers[(int) SImode].insn_code = CODE_FOR_xorsi3;
3322 #endif
3323 #ifdef HAVE_xordi3
3324   if (HAVE_xordi3)
3325     xor_optab->handlers[(int) DImode].insn_code = CODE_FOR_xordi3;
3326 #endif
3327 #ifdef HAVE_xorti3
3328   if (HAVE_xorti3)
3329     xor_optab->handlers[(int) TImode].insn_code = CODE_FOR_xorti3;
3330 #endif
3331
3332 #ifdef HAVE_ashlqi3
3333   if (HAVE_ashlqi3)
3334     ashl_optab->handlers[(int) QImode].insn_code = CODE_FOR_ashlqi3;
3335 #endif
3336 #ifdef HAVE_ashlhi3
3337   if (HAVE_ashlhi3)
3338     ashl_optab->handlers[(int) HImode].insn_code = CODE_FOR_ashlhi3;
3339 #endif
3340 #ifdef HAVE_ashlpsi3
3341   if (HAVE_ashlpsi3)
3342     ashl_optab->handlers[(int) PSImode].insn_code = CODE_FOR_ashlpsi3;
3343 #endif
3344 #ifdef HAVE_ashlsi3
3345   if (HAVE_ashlsi3)
3346     ashl_optab->handlers[(int) SImode].insn_code = CODE_FOR_ashlsi3;
3347 #endif
3348 #ifdef HAVE_ashldi3
3349   if (HAVE_ashldi3)
3350     ashl_optab->handlers[(int) DImode].insn_code = CODE_FOR_ashldi3;
3351 #endif
3352 #ifdef HAVE_ashlti3
3353   if (HAVE_ashlti3)
3354     ashl_optab->handlers[(int) TImode].insn_code = CODE_FOR_ashlti3;
3355 #endif
3356   ashl_optab->handlers[(int) SImode].libfunc
3357     = gen_rtx (SYMBOL_REF, Pmode, "__ashlsi3");
3358   ashl_optab->handlers[(int) DImode].libfunc
3359     = gen_rtx (SYMBOL_REF, Pmode, "__ashldi3");
3360
3361 #ifdef HAVE_ashrqi3
3362   if (HAVE_ashrqi3)
3363     ashr_optab->handlers[(int) QImode].insn_code = CODE_FOR_ashrqi3;
3364 #endif
3365 #ifdef HAVE_ashrhi3
3366   if (HAVE_ashrhi3)
3367     ashr_optab->handlers[(int) HImode].insn_code = CODE_FOR_ashrhi3;
3368 #endif
3369 #ifdef HAVE_ashrpsi3
3370   if (HAVE_ashrpsi3)
3371     ashr_optab->handlers[(int) PSImode].insn_code = CODE_FOR_ashrpsi3;
3372 #endif
3373 #ifdef HAVE_ashrsi3
3374   if (HAVE_ashrsi3)
3375     ashr_optab->handlers[(int) SImode].insn_code = CODE_FOR_ashrsi3;
3376 #endif
3377 #ifdef HAVE_ashrdi3
3378   if (HAVE_ashrdi3)
3379     ashr_optab->handlers[(int) DImode].insn_code = CODE_FOR_ashrdi3;
3380 #endif
3381 #ifdef HAVE_ashrti3
3382   if (HAVE_ashrti3)
3383     ashr_optab->handlers[(int) TImode].insn_code = CODE_FOR_ashrti3;
3384 #endif
3385   ashr_optab->handlers[(int) SImode].libfunc
3386     = gen_rtx (SYMBOL_REF, Pmode, "__ashrsi3");
3387   ashr_optab->handlers[(int) DImode].libfunc
3388     = gen_rtx (SYMBOL_REF, Pmode, "__ashrdi3");
3389
3390 #ifdef HAVE_lshlqi3
3391   if (HAVE_lshlqi3)
3392     lshl_optab->handlers[(int) QImode].insn_code = CODE_FOR_lshlqi3;
3393 #endif
3394 #ifdef HAVE_lshlhi3
3395   if (HAVE_lshlhi3)
3396     lshl_optab->handlers[(int) HImode].insn_code = CODE_FOR_lshlhi3;
3397 #endif
3398 #ifdef HAVE_lshlpsi3
3399   if (HAVE_lshlpsi3)
3400     lshl_optab->handlers[(int) PSImode].insn_code = CODE_FOR_lshlpsi3;
3401 #endif
3402 #ifdef HAVE_lshlsi3
3403   if (HAVE_lshlsi3)
3404     lshl_optab->handlers[(int) SImode].insn_code = CODE_FOR_lshlsi3;
3405 #endif
3406 #ifdef HAVE_lshldi3
3407   if (HAVE_lshldi3)
3408     lshl_optab->handlers[(int) DImode].insn_code = CODE_FOR_lshldi3;
3409 #endif
3410 #ifdef HAVE_lshlti3
3411   if (HAVE_lshlti3)
3412     lshl_optab->handlers[(int) TImode].insn_code = CODE_FOR_lshlti3;
3413 #endif
3414   lshl_optab->handlers[(int) SImode].libfunc
3415     = gen_rtx (SYMBOL_REF, Pmode, "__lshlsi3");
3416   lshl_optab->handlers[(int) DImode].libfunc
3417     = gen_rtx (SYMBOL_REF, Pmode, "__lshldi3");
3418
3419 #ifdef HAVE_lshrqi3
3420   if (HAVE_lshrqi3)
3421     lshr_optab->handlers[(int) QImode].insn_code = CODE_FOR_lshrqi3;
3422 #endif
3423 #ifdef HAVE_lshrhi3
3424   if (HAVE_lshrhi3)
3425     lshr_optab->handlers[(int) HImode].insn_code = CODE_FOR_lshrhi3;
3426 #endif
3427 #ifdef HAVE_lshrpsi3
3428   if (HAVE_lshrpsi3)
3429     lshr_optab->handlers[(int) PSImode].insn_code = CODE_FOR_lshrpsi3;
3430 #endif
3431 #ifdef HAVE_lshrsi3
3432   if (HAVE_lshrsi3)
3433     lshr_optab->handlers[(int) SImode].insn_code = CODE_FOR_lshrsi3;
3434 #endif
3435 #ifdef HAVE_lshrdi3
3436   if (HAVE_lshrdi3)
3437     lshr_optab->handlers[(int) DImode].insn_code = CODE_FOR_lshrdi3;
3438 #endif
3439 #ifdef HAVE_lshrti3
3440   if (HAVE_lshrti3)
3441     lshr_optab->handlers[(int) TImode].insn_code = CODE_FOR_lshrti3;
3442 #endif
3443   lshr_optab->handlers[(int) SImode].libfunc
3444     = gen_rtx (SYMBOL_REF, Pmode, "__lshrsi3");
3445   lshr_optab->handlers[(int) DImode].libfunc
3446     = gen_rtx (SYMBOL_REF, Pmode, "__lshrdi3");
3447
3448 #ifdef HAVE_rotlqi3
3449   if (HAVE_rotlqi3)
3450     rotl_optab->handlers[(int) QImode].insn_code = CODE_FOR_rotlqi3;
3451 #endif
3452 #ifdef HAVE_rotlhi3
3453   if (HAVE_rotlhi3)
3454     rotl_optab->handlers[(int) HImode].insn_code = CODE_FOR_rotlhi3;
3455 #endif
3456 #ifdef HAVE_rotlpsi3
3457   if (HAVE_rotlpsi3)
3458     rotl_optab->handlers[(int) PSImode].insn_code = CODE_FOR_rotlpsi3;
3459 #endif
3460 #ifdef HAVE_rotlsi3
3461   if (HAVE_rotlsi3)
3462     rotl_optab->handlers[(int) SImode].insn_code = CODE_FOR_rotlsi3;
3463 #endif
3464 #ifdef HAVE_rotldi3
3465   if (HAVE_rotldi3)
3466     rotl_optab->handlers[(int) DImode].insn_code = CODE_FOR_rotldi3;
3467 #endif
3468 #ifdef HAVE_rotlti3
3469   if (HAVE_rotlti3)
3470     rotl_optab->handlers[(int) TImode].insn_code = CODE_FOR_rotlti3;
3471 #endif
3472   rotl_optab->handlers[(int) SImode].libfunc
3473     = gen_rtx (SYMBOL_REF, Pmode, "__rotlsi3");
3474   rotl_optab->handlers[(int) DImode].libfunc
3475     = gen_rtx (SYMBOL_REF, Pmode, "__rotldi3");
3476
3477 #ifdef HAVE_rotrqi3
3478   if (HAVE_rotrqi3)
3479     rotr_optab->handlers[(int) QImode].insn_code = CODE_FOR_rotrqi3;
3480 #endif
3481 #ifdef HAVE_rotrhi3
3482   if (HAVE_rotrhi3)
3483     rotr_optab->handlers[(int) HImode].insn_code = CODE_FOR_rotrhi3;
3484 #endif
3485 #ifdef HAVE_rotrpsi3
3486   if (HAVE_rotrpsi3)
3487     rotr_optab->handlers[(int) PSImode].insn_code = CODE_FOR_rotrpsi3;
3488 #endif
3489 #ifdef HAVE_rotrsi3
3490   if (HAVE_rotrsi3)
3491     rotr_optab->handlers[(int) SImode].insn_code = CODE_FOR_rotrsi3;
3492 #endif
3493 #ifdef HAVE_rotrdi3
3494   if (HAVE_rotrdi3)
3495     rotr_optab->handlers[(int) DImode].insn_code = CODE_FOR_rotrdi3;
3496 #endif
3497 #ifdef HAVE_rotrti3
3498   if (HAVE_rotrti3)
3499     rotr_optab->handlers[(int) TImode].insn_code = CODE_FOR_rotrti3;
3500 #endif
3501   rotr_optab->handlers[(int) SImode].libfunc
3502     = gen_rtx (SYMBOL_REF, Pmode, "__rotrsi3");
3503   rotr_optab->handlers[(int) DImode].libfunc
3504     = gen_rtx (SYMBOL_REF, Pmode, "__rotrdi3");
3505
3506 #ifdef HAVE_sminqi3
3507   if (HAVE_sminqi3)
3508     smin_optab->handlers[(int) QImode].insn_code = CODE_FOR_sminqi3;
3509 #endif
3510 #ifdef HAVE_sminhi3
3511   if (HAVE_sminhi3)
3512     smin_optab->handlers[(int) HImode].insn_code = CODE_FOR_sminhi3;
3513 #endif
3514 #ifdef HAVE_sminsi3
3515   if (HAVE_sminsi3)
3516     smin_optab->handlers[(int) SImode].insn_code = CODE_FOR_sminsi3;
3517 #endif
3518 #ifdef HAVE_smindi3
3519   if (HAVE_smindi3)
3520     smin_optab->handlers[(int) DImode].insn_code = CODE_FOR_smindi3;
3521 #endif
3522 #ifdef HAVE_sminti3
3523   if (HAVE_sminti3)
3524     smin_optab->handlers[(int) TImode].insn_code = CODE_FOR_sminti3;
3525 #endif
3526 #ifdef HAVE_sminsf3
3527   if (HAVE_sminsf3)
3528     smin_optab->handlers[(int) SFmode].insn_code = CODE_FOR_sminsf3;
3529 #endif
3530 #ifdef HAVE_smindf3
3531   if (HAVE_smindf3)
3532     smin_optab->handlers[(int) DFmode].insn_code = CODE_FOR_smindf3;
3533 #endif
3534 #ifdef HAVE_smintf3
3535   if (HAVE_smintf3)
3536     smin_optab->handlers[(int) TFmode].insn_code = CODE_FOR_smintf3;
3537 #endif
3538
3539 #ifdef HAVE_smaxqi3
3540   if (HAVE_smaxqi3)
3541     smax_optab->handlers[(int) QImode].insn_code = CODE_FOR_smaxqi3;
3542 #endif
3543 #ifdef HAVE_smaxhi3
3544   if (HAVE_smaxhi3)
3545     smax_optab->handlers[(int) HImode].insn_code = CODE_FOR_smaxhi3;
3546 #endif
3547 #ifdef HAVE_smaxsi3
3548   if (HAVE_smaxsi3)
3549     smax_optab->handlers[(int) SImode].insn_code = CODE_FOR_smaxsi3;
3550 #endif
3551 #ifdef HAVE_smaxdi3
3552   if (HAVE_smaxdi3)
3553     smax_optab->handlers[(int) DImode].insn_code = CODE_FOR_smaxdi3;
3554 #endif
3555 #ifdef HAVE_smaxti3
3556   if (HAVE_smaxti3)
3557     smax_optab->handlers[(int) TImode].insn_code = CODE_FOR_smaxti3;
3558 #endif
3559 #ifdef HAVE_smaxsf3
3560   if (HAVE_smaxsf3)
3561     smax_optab->handlers[(int) SFmode].insn_code = CODE_FOR_smaxsf3;
3562 #endif
3563 #ifdef HAVE_smaxdf3
3564   if (HAVE_smaxdf3)
3565     smax_optab->handlers[(int) DFmode].insn_code = CODE_FOR_smaxdf3;
3566 #endif
3567 #ifdef HAVE_smaxtf3
3568   if (HAVE_smaxtf3)
3569     smax_optab->handlers[(int) TFmode].insn_code = CODE_FOR_smaxtf3;
3570 #endif
3571
3572 #ifdef HAVE_uminqi3
3573   if (HAVE_uminqi3)
3574     umin_optab->handlers[(int) QImode].insn_code = CODE_FOR_uminqi3;
3575 #endif
3576 #ifdef HAVE_uminhi3
3577   if (HAVE_uminhi3)
3578     umin_optab->handlers[(int) HImode].insn_code = CODE_FOR_uminhi3;
3579 #endif
3580 #ifdef HAVE_uminsi3
3581   if (HAVE_uminsi3)
3582     umin_optab->handlers[(int) SImode].insn_code = CODE_FOR_uminsi3;
3583 #endif
3584 #ifdef HAVE_umindi3
3585   if (HAVE_umindi3)
3586     umin_optab->handlers[(int) DImode].insn_code = CODE_FOR_umindi3;
3587 #endif
3588 #ifdef HAVE_uminti3
3589   if (HAVE_uminti3)
3590     umin_optab->handlers[(int) TImode].insn_code = CODE_FOR_uminti3;
3591 #endif
3592
3593 #ifdef HAVE_umaxqi3
3594   if (HAVE_umaxqi3)
3595     umax_optab->handlers[(int) QImode].insn_code = CODE_FOR_umaxqi3;
3596 #endif
3597 #ifdef HAVE_umaxhi3
3598   if (HAVE_umaxhi3)
3599     umax_optab->handlers[(int) HImode].insn_code = CODE_FOR_umaxhi3;
3600 #endif
3601 #ifdef HAVE_umaxsi3
3602   if (HAVE_umaxsi3)
3603     umax_optab->handlers[(int) SImode].insn_code = CODE_FOR_umaxsi3;
3604 #endif
3605 #ifdef HAVE_umaxdi3
3606   if (HAVE_umaxdi3)
3607     umax_optab->handlers[(int) DImode].insn_code = CODE_FOR_umaxdi3;
3608 #endif
3609 #ifdef HAVE_umaxti3
3610   if (HAVE_umaxti3)
3611     umax_optab->handlers[(int) TImode].insn_code = CODE_FOR_umaxti3;
3612 #endif
3613
3614 #ifdef HAVE_negqi2
3615   if (HAVE_negqi2)
3616     neg_optab->handlers[(int) QImode].insn_code = CODE_FOR_negqi2;
3617 #endif
3618 #ifdef HAVE_neghi2
3619   if (HAVE_neghi2)
3620     neg_optab->handlers[(int) HImode].insn_code = CODE_FOR_neghi2;
3621 #endif
3622 #ifdef HAVE_negpsi2
3623   if (HAVE_negpsi2)
3624     neg_optab->handlers[(int) PSImode].insn_code = CODE_FOR_negpsi2;
3625 #endif
3626 #ifdef HAVE_negsi2
3627   if (HAVE_negsi2)
3628     neg_optab->handlers[(int) SImode].insn_code = CODE_FOR_negsi2;
3629 #endif
3630 #ifdef HAVE_negdi2
3631   if (HAVE_negdi2)
3632     neg_optab->handlers[(int) DImode].insn_code = CODE_FOR_negdi2;
3633 #endif
3634 #ifdef HAVE_negti2
3635   if (HAVE_negti2)
3636     neg_optab->handlers[(int) TImode].insn_code = CODE_FOR_negti2;
3637 #endif
3638 #ifdef HAVE_negsf2
3639   if (HAVE_negsf2)
3640     neg_optab->handlers[(int) SFmode].insn_code = CODE_FOR_negsf2;
3641 #endif
3642 #ifdef HAVE_negdf2
3643   if (HAVE_negdf2)
3644     neg_optab->handlers[(int) DFmode].insn_code = CODE_FOR_negdf2;
3645 #endif
3646 #ifdef HAVE_negtf2
3647   if (HAVE_negtf2)
3648     neg_optab->handlers[(int) TFmode].insn_code = CODE_FOR_negtf2;
3649 #endif
3650   neg_optab->handlers[(int) SImode].libfunc
3651     = gen_rtx (SYMBOL_REF, Pmode, "__negsi2"); 
3652   neg_optab->handlers[(int) DImode].libfunc
3653     = gen_rtx (SYMBOL_REF, Pmode, "__negdi2");
3654   neg_optab->handlers[(int) SFmode].libfunc
3655     = gen_rtx (SYMBOL_REF, Pmode, "__negsf2");
3656   neg_optab->handlers[(int) DFmode].libfunc
3657     = gen_rtx (SYMBOL_REF, Pmode, "__negdf2");
3658
3659 #ifdef HAVE_absqi2
3660   if (HAVE_absqi2)
3661     abs_optab->handlers[(int) QImode].insn_code = CODE_FOR_absqi2;
3662 #endif
3663 #ifdef HAVE_abshi2
3664   if (HAVE_abshi2)
3665     abs_optab->handlers[(int) HImode].insn_code = CODE_FOR_abshi2;
3666 #endif
3667 #ifdef HAVE_abspsi2
3668   if (HAVE_abspsi2)
3669     abs_optab->handlers[(int) PSImode].insn_code = CODE_FOR_abspsi2;
3670 #endif
3671 #ifdef HAVE_abssi2
3672   if (HAVE_abssi2)
3673     abs_optab->handlers[(int) SImode].insn_code = CODE_FOR_abssi2;
3674 #endif
3675 #ifdef HAVE_absdi2
3676   if (HAVE_absdi2)
3677     abs_optab->handlers[(int) DImode].insn_code = CODE_FOR_absdi2;
3678 #endif
3679 #ifdef HAVE_absti2
3680   if (HAVE_absti2)
3681     abs_optab->handlers[(int) TImode].insn_code = CODE_FOR_absti2;
3682 #endif
3683 #ifdef HAVE_abssf2
3684   if (HAVE_abssf2)
3685     abs_optab->handlers[(int) SFmode].insn_code = CODE_FOR_abssf2;
3686 #endif
3687 #ifdef HAVE_absdf2
3688   if (HAVE_absdf2)
3689     abs_optab->handlers[(int) DFmode].insn_code = CODE_FOR_absdf2;
3690 #endif
3691 #ifdef HAVE_abstf2
3692   if (HAVE_abstf2)
3693     abs_optab->handlers[(int) TFmode].insn_code = CODE_FOR_abstf2;
3694 #endif
3695   /* No library calls here!  If there is no abs instruction,
3696      expand_expr will generate a conditional negation.  */
3697
3698 #ifdef HAVE_sqrtqi2
3699   if (HAVE_sqrtqi2)
3700     sqrt_optab->handlers[(int) QImode].insn_code = CODE_FOR_sqrtqi2;
3701 #endif
3702 #ifdef HAVE_sqrthi2
3703   if (HAVE_sqrthi2)
3704     sqrt_optab->handlers[(int) HImode].insn_code = CODE_FOR_sqrthi2;
3705 #endif
3706 #ifdef HAVE_sqrtpsi2
3707   if (HAVE_sqrtpsi2)
3708     sqrt_optab->handlers[(int) PSImode].insn_code = CODE_FOR_sqrtpsi2;
3709 #endif
3710 #ifdef HAVE_sqrtsi2
3711   if (HAVE_sqrtsi2)
3712     sqrt_optab->handlers[(int) SImode].insn_code = CODE_FOR_sqrtsi2;
3713 #endif
3714 #ifdef HAVE_sqrtdi2
3715   if (HAVE_sqrtdi2)
3716     sqrt_optab->handlers[(int) DImode].insn_code = CODE_FOR_sqrtdi2;
3717 #endif
3718 #ifdef HAVE_sqrtti2
3719   if (HAVE_sqrtti2)
3720     sqrt_optab->handlers[(int) TImode].insn_code = CODE_FOR_sqrtti2;
3721 #endif
3722 #ifdef HAVE_sqrtsf2
3723   if (HAVE_sqrtsf2)
3724     sqrt_optab->handlers[(int) SFmode].insn_code = CODE_FOR_sqrtsf2;
3725 #endif
3726 #ifdef HAVE_sqrtdf2
3727   if (HAVE_sqrtdf2)
3728     sqrt_optab->handlers[(int) DFmode].insn_code = CODE_FOR_sqrtdf2;
3729 #endif
3730 #ifdef HAVE_sqrttf2
3731   if (HAVE_sqrttf2)
3732     sqrt_optab->handlers[(int) TFmode].insn_code = CODE_FOR_sqrttf2;
3733 #endif
3734   /* No library calls here!  If there is no sqrt instruction expand_builtin
3735      should force the library call.  */
3736
3737 #ifdef HAVE_strlenqi
3738   if (HAVE_strlenqi)
3739     strlen_optab->handlers[(int) QImode].insn_code = CODE_FOR_strlenqi;
3740 #endif
3741 #ifdef HAVE_strlenhi
3742   if (HAVE_strlenhi)
3743     strlen_optab->handlers[(int) HImode].insn_code = CODE_FOR_strlenhi;
3744 #endif
3745 #ifdef HAVE_strlenpsi
3746   if (HAVE_strlenpsi)
3747     strlen_optab->handlers[(int) PSImode].insn_code = CODE_FOR_strlenpsi;
3748 #endif
3749 #ifdef HAVE_strlensi
3750   if (HAVE_strlensi)
3751     strlen_optab->handlers[(int) SImode].insn_code = CODE_FOR_strlensi;
3752 #endif
3753 #ifdef HAVE_strlendi
3754   if (HAVE_strlendi)
3755     strlen_optab->handlers[(int) DImode].insn_code = CODE_FOR_strlendi;
3756 #endif
3757 #ifdef HAVE_strlenti
3758   if (HAVE_strlenti)
3759     strlen_optab->handlers[(int) TImode].insn_code = CODE_FOR_strlenti;
3760 #endif
3761   /* No library calls here!  If there is no strlen instruction expand_builtin
3762      should force the library call.  */
3763
3764 #ifdef HAVE_one_cmplqi2
3765   if (HAVE_one_cmplqi2)
3766     one_cmpl_optab->handlers[(int) QImode].insn_code = CODE_FOR_one_cmplqi2;
3767 #endif
3768 #ifdef HAVE_one_cmplhi2
3769   if (HAVE_one_cmplhi2)
3770     one_cmpl_optab->handlers[(int) HImode].insn_code = CODE_FOR_one_cmplhi2;
3771 #endif
3772 #ifdef HAVE_one_cmplpsi2
3773   if (HAVE_one_cmplpsi2)
3774     one_cmpl_optab->handlers[(int) PSImode].insn_code = CODE_FOR_one_cmplpsi2;
3775 #endif
3776 #ifdef HAVE_one_cmplsi2
3777   if (HAVE_one_cmplsi2)
3778     one_cmpl_optab->handlers[(int) SImode].insn_code = CODE_FOR_one_cmplsi2;
3779 #endif
3780 #ifdef HAVE_one_cmpldi2
3781   if (HAVE_one_cmpldi2)
3782     one_cmpl_optab->handlers[(int) DImode].insn_code = CODE_FOR_one_cmpldi2;
3783 #endif
3784 #ifdef HAVE_one_cmplti2
3785   if (HAVE_one_cmplti2)
3786     one_cmpl_optab->handlers[(int) TImode].insn_code = CODE_FOR_one_cmplti2;
3787 #endif
3788   one_cmpl_optab->handlers[(int) SImode].libfunc
3789     = gen_rtx (SYMBOL_REF, Pmode, "__one_cmplsi2"); 
3790
3791 #ifdef HAVE_ffsqi2
3792   if (HAVE_ffsqi2)
3793     ffs_optab->handlers[(int) QImode].insn_code = CODE_FOR_ffsqi2;
3794 #endif
3795 #ifdef HAVE_ffshi2
3796   if (HAVE_ffshi2)
3797     ffs_optab->handlers[(int) HImode].insn_code = CODE_FOR_ffshi2;
3798 #endif
3799 #ifdef HAVE_ffspsi2
3800   if (HAVE_ffspsi2)
3801     ffs_optab->handlers[(int) PSImode].insn_code = CODE_FOR_ffspsi2;
3802 #endif
3803 #ifdef HAVE_ffssi2
3804   if (HAVE_ffssi2)
3805     ffs_optab->handlers[(int) SImode].insn_code = CODE_FOR_ffssi2;
3806 #endif
3807 #ifdef HAVE_ffsdi2
3808   if (HAVE_ffsdi2)
3809     ffs_optab->handlers[(int) DImode].insn_code = CODE_FOR_ffsdi2;
3810 #endif
3811 #ifdef HAVE_ffsti2
3812   if (HAVE_ffsti2)
3813     ffs_optab->handlers[(int) TImode].insn_code = CODE_FOR_ffsti2;
3814 #endif
3815   ffs_optab->handlers[(int) SImode].libfunc
3816     = gen_rtx (SYMBOL_REF, Pmode, "ffs"); 
3817
3818 #ifdef HAVE_movqi
3819   if (HAVE_movqi)
3820     mov_optab->handlers[(int) QImode].insn_code = CODE_FOR_movqi;
3821 #endif
3822 #ifdef HAVE_movhi
3823   if (HAVE_movhi)
3824     mov_optab->handlers[(int) HImode].insn_code = CODE_FOR_movhi;
3825 #endif
3826 #ifdef HAVE_movpsi
3827   if (HAVE_movpsi)
3828     mov_optab->handlers[(int) PSImode].insn_code = CODE_FOR_movpsi;
3829 #endif
3830 #ifdef HAVE_movsi
3831   if (HAVE_movsi)
3832     mov_optab->handlers[(int) SImode].insn_code = CODE_FOR_movsi;
3833 #endif
3834 #ifdef HAVE_movdi
3835   if (HAVE_movdi)
3836     mov_optab->handlers[(int) DImode].insn_code = CODE_FOR_movdi;
3837 #endif
3838 #ifdef HAVE_movti
3839   if (HAVE_movti)
3840     mov_optab->handlers[(int) TImode].insn_code = CODE_FOR_movti;
3841 #endif
3842 #ifdef HAVE_movsf
3843   if (HAVE_movsf)
3844     mov_optab->handlers[(int) SFmode].insn_code = CODE_FOR_movsf;
3845 #endif
3846 #ifdef HAVE_movdf
3847   if (HAVE_movdf)
3848     mov_optab->handlers[(int) DFmode].insn_code = CODE_FOR_movdf;
3849 #endif
3850 #ifdef HAVE_movtf
3851   if (HAVE_movtf)
3852     mov_optab->handlers[(int) TFmode].insn_code = CODE_FOR_movtf;
3853 #endif
3854 #ifdef HAVE_movcc
3855   if (HAVE_movcc)
3856     mov_optab->handlers[(int) CCmode].insn_code = CODE_FOR_movcc;
3857 #endif
3858
3859 #ifdef EXTRA_CC_MODES
3860   init_mov_optab ();
3861 #endif
3862
3863 #ifdef HAVE_movstrictqi
3864   if (HAVE_movstrictqi)
3865     movstrict_optab->handlers[(int) QImode].insn_code = CODE_FOR_movstrictqi;
3866 #endif
3867 #ifdef HAVE_movstricthi
3868   if (HAVE_movstricthi)
3869     movstrict_optab->handlers[(int) HImode].insn_code = CODE_FOR_movstricthi;
3870 #endif
3871 #ifdef HAVE_movstrictpsi
3872   if (HAVE_movstrictpsi)
3873     movstrict_optab->handlers[(int) PSImode].insn_code = CODE_FOR_movstrictpsi;
3874 #endif
3875 #ifdef HAVE_movstrictsi
3876   if (HAVE_movstrictsi)
3877     movstrict_optab->handlers[(int) SImode].insn_code = CODE_FOR_movstrictsi;
3878 #endif
3879 #ifdef HAVE_movstrictdi
3880   if (HAVE_movstrictdi)
3881     movstrict_optab->handlers[(int) DImode].insn_code = CODE_FOR_movstrictdi;
3882 #endif
3883 #ifdef HAVE_movstrictti
3884   if (HAVE_movstrictti)
3885     movstrict_optab->handlers[(int) TImode].insn_code = CODE_FOR_movstrictti;
3886 #endif
3887
3888 #ifdef HAVE_cmpqi
3889   if (HAVE_cmpqi)
3890     cmp_optab->handlers[(int) QImode].insn_code = CODE_FOR_cmpqi;
3891 #endif
3892 #ifdef HAVE_cmphi
3893   if (HAVE_cmphi)
3894     cmp_optab->handlers[(int) HImode].insn_code = CODE_FOR_cmphi;
3895 #endif
3896 #ifdef HAVE_cmppsi
3897   if (HAVE_cmppsi)
3898     cmp_optab->handlers[(int) PSImode].insn_code = CODE_FOR_cmppsi;
3899 #endif
3900 #ifdef HAVE_cmpsi
3901   if (HAVE_cmpsi)
3902     cmp_optab->handlers[(int) SImode].insn_code = CODE_FOR_cmpsi;
3903 #endif
3904 #ifdef HAVE_cmpdi
3905   if (HAVE_cmpdi)
3906     cmp_optab->handlers[(int) DImode].insn_code = CODE_FOR_cmpdi;
3907 #endif
3908 #ifdef HAVE_cmpti
3909   if (HAVE_cmpti)
3910     cmp_optab->handlers[(int) TImode].insn_code = CODE_FOR_cmpti;
3911 #endif
3912 #ifdef HAVE_cmpsf
3913   if (HAVE_cmpsf)
3914     cmp_optab->handlers[(int) SFmode].insn_code = CODE_FOR_cmpsf;
3915 #endif
3916 #ifdef HAVE_cmpdf
3917   if (HAVE_cmpdf)
3918     cmp_optab->handlers[(int) DFmode].insn_code = CODE_FOR_cmpdf;
3919 #endif
3920 #ifdef HAVE_cmptf
3921   if (HAVE_cmptf)
3922     cmp_optab->handlers[(int) TFmode].insn_code = CODE_FOR_cmptf;
3923 #endif
3924 #ifdef HAVE_tstqi
3925   if (HAVE_tstqi)
3926     tst_optab->handlers[(int) QImode].insn_code = CODE_FOR_tstqi;
3927 #endif
3928 #ifdef HAVE_tsthi
3929   if (HAVE_tsthi)
3930     tst_optab->handlers[(int) HImode].insn_code = CODE_FOR_tsthi;
3931 #endif
3932 #ifdef HAVE_tstpsi
3933   if (HAVE_tstpsi)
3934     tst_optab->handlers[(int) PSImode].insn_code = CODE_FOR_tstpsi;
3935 #endif
3936 #ifdef HAVE_tstsi
3937   if (HAVE_tstsi)
3938     tst_optab->handlers[(int) SImode].insn_code = CODE_FOR_tstsi;
3939 #endif
3940 #ifdef HAVE_tstdi
3941   if (HAVE_tstdi)
3942     tst_optab->handlers[(int) DImode].insn_code = CODE_FOR_tstdi;
3943 #endif
3944 #ifdef HAVE_tstti
3945   if (HAVE_tstti)
3946     tst_optab->handlers[(int) TImode].insn_code = CODE_FOR_tstti;
3947 #endif
3948 #ifdef HAVE_tstsf
3949   if (HAVE_tstsf)
3950     tst_optab->handlers[(int) SFmode].insn_code = CODE_FOR_tstsf;
3951 #endif
3952 #ifdef HAVE_tstdf
3953   if (HAVE_tstdf)
3954     tst_optab->handlers[(int) DFmode].insn_code = CODE_FOR_tstdf;
3955 #endif
3956 #ifdef HAVE_tsttf
3957   if (HAVE_tsttf)
3958     tst_optab->handlers[(int) TFmode].insn_code = CODE_FOR_tsttf;
3959 #endif
3960   /* Comparison libcalls for integers MUST come in pairs, signed/unsigned.  */
3961   cmp_optab->handlers[(int) DImode].libfunc
3962     = gen_rtx (SYMBOL_REF, Pmode, "__cmpdi2");
3963   ucmp_optab->handlers[(int) DImode].libfunc
3964     = gen_rtx (SYMBOL_REF, Pmode, "__ucmpdi2");
3965
3966 #ifdef HAVE_beq
3967   if (HAVE_beq)
3968     bcc_gen_fctn[(int) EQ] = gen_beq;
3969 #endif
3970 #ifdef HAVE_bne
3971   if (HAVE_bne)
3972     bcc_gen_fctn[(int) NE] = gen_bne;
3973 #endif
3974 #ifdef HAVE_bgt
3975   if (HAVE_bgt)
3976     bcc_gen_fctn[(int) GT] = gen_bgt;
3977 #endif
3978 #ifdef HAVE_bge
3979   if (HAVE_bge)
3980     bcc_gen_fctn[(int) GE] = gen_bge;
3981 #endif
3982 #ifdef HAVE_bgtu
3983   if (HAVE_bgtu)
3984     bcc_gen_fctn[(int) GTU] = gen_bgtu;
3985 #endif
3986 #ifdef HAVE_bgeu
3987   if (HAVE_bgeu)
3988     bcc_gen_fctn[(int) GEU] = gen_bgeu;
3989 #endif
3990 #ifdef HAVE_blt
3991   if (HAVE_blt)
3992     bcc_gen_fctn[(int) LT] = gen_blt;
3993 #endif
3994 #ifdef HAVE_ble
3995   if (HAVE_ble)
3996     bcc_gen_fctn[(int) LE] = gen_ble;
3997 #endif
3998 #ifdef HAVE_bltu
3999   if (HAVE_bltu)
4000     bcc_gen_fctn[(int) LTU] = gen_bltu;
4001 #endif
4002 #ifdef HAVE_bleu
4003   if (HAVE_bleu)
4004     bcc_gen_fctn[(int) LEU] = gen_bleu;
4005 #endif
4006
4007   for (i = 0; i < NUM_RTX_CODE; i++)
4008     setcc_gen_code[i] = CODE_FOR_nothing;
4009
4010 #ifdef HAVE_seq
4011   if (HAVE_seq)
4012     setcc_gen_code[(int) EQ] = CODE_FOR_seq;
4013 #endif
4014 #ifdef HAVE_sne
4015   if (HAVE_sne)
4016     setcc_gen_code[(int) NE] = CODE_FOR_sne;
4017 #endif
4018 #ifdef HAVE_sgt
4019   if (HAVE_sgt)
4020     setcc_gen_code[(int) GT] = CODE_FOR_sgt;
4021 #endif
4022 #ifdef HAVE_sge
4023   if (HAVE_sge)
4024     setcc_gen_code[(int) GE] = CODE_FOR_sge;
4025 #endif
4026 #ifdef HAVE_sgtu
4027   if (HAVE_sgtu)
4028     setcc_gen_code[(int) GTU] = CODE_FOR_sgtu;
4029 #endif
4030 #ifdef HAVE_sgeu
4031   if (HAVE_sgeu)
4032     setcc_gen_code[(int) GEU] = CODE_FOR_sgeu;
4033 #endif
4034 #ifdef HAVE_slt
4035   if (HAVE_slt)
4036     setcc_gen_code[(int) LT] = CODE_FOR_slt;
4037 #endif
4038 #ifdef HAVE_sle
4039   if (HAVE_sle)
4040     setcc_gen_code[(int) LE] = CODE_FOR_sle;
4041 #endif
4042 #ifdef HAVE_sltu
4043   if (HAVE_sltu)
4044     setcc_gen_code[(int) LTU] = CODE_FOR_sltu;
4045 #endif
4046 #ifdef HAVE_sleu
4047   if (HAVE_sleu)
4048     setcc_gen_code[(int) LEU] = CODE_FOR_sleu;
4049 #endif
4050
4051   extendsfdf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__extendsfdf2");
4052   truncdfsf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__truncdfsf2");
4053   memcpy_libfunc = gen_rtx (SYMBOL_REF, Pmode, "memcpy");
4054   bcopy_libfunc = gen_rtx (SYMBOL_REF, Pmode, "bcopy");
4055   memcmp_libfunc = gen_rtx (SYMBOL_REF, Pmode, "memcmp");
4056   bcmp_libfunc = gen_rtx (SYMBOL_REF, Pmode, "bcmp");
4057   memset_libfunc = gen_rtx (SYMBOL_REF, Pmode, "memset");
4058   bzero_libfunc = gen_rtx (SYMBOL_REF, Pmode, "bzero");
4059   eqsf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__eqsf2");
4060   nesf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__nesf2");
4061   gtsf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__gtsf2");
4062   gesf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__gesf2");
4063   ltsf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__ltsf2");
4064   lesf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__lesf2");
4065   eqdf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__eqdf2");
4066   nedf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__nedf2");
4067   gtdf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__gtdf2");
4068   gedf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__gedf2");
4069   ltdf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__ltdf2");
4070   ledf2_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__ledf2");
4071   floatdisf_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__floatdisf");
4072   floatsisf_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__floatsisf");
4073   floatdidf_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__floatdidf");
4074   floatsidf_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__floatsidf");
4075   fixsfsi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixsfsi");
4076   fixsfdi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixsfdi");
4077   fixdfsi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixdfsi");
4078   fixdfdi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixdfdi");
4079   fixunssfsi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixunssfsi");
4080   fixunssfdi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixunssfdi");
4081   fixunsdfsi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixunsdfsi");
4082   fixunsdfdi_libfunc = gen_rtx (SYMBOL_REF, Pmode, "__fixunsdfdi");
4083 }
4084 \f
4085 #ifdef BROKEN_LDEXP
4086
4087 /* SCO 3.2 apparently has a broken ldexp. */
4088
4089 double
4090 ldexp(x,n)
4091      double x;
4092      int n;
4093 {
4094   if (n > 0)
4095     while (n--)
4096       x *= 2;
4097
4098   return x;
4099 }
4100 #endif /* BROKEN_LDEXP */