Annotation of gcc/config/i370/mvs.h, revision 1.1.1.3

1.1       root        1: /* Definitions of target machine for GNU compiler.  System/370 version.
1.1.1.3 ! root        2:    Copyright (C) 1989, 1993, 1995 Free Software Foundation, Inc.
1.1       root        3:    Contributed by Jan Stein ([email protected]).
1.1.1.3 ! root        4:    Modified for C/370 MVS by Dave Pitts ([email protected])
1.1       root        5: 
                      6: This file is part of GNU CC.
                      7: 
                      8: GNU CC is free software; you can redistribute it and/or modify
                      9: it under the terms of the GNU General Public License as published by
                     10: the Free Software Foundation; either version 2, or (at your option)
                     11: any later version.
                     12: 
                     13: GNU CC is distributed in the hope that it will be useful,
                     14: but WITHOUT ANY WARRANTY; without even the implied warranty of
                     15: MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
                     16: GNU General Public License for more details.
                     17: 
                     18: You should have received a copy of the GNU General Public License
                     19: along with GNU CC; see the file COPYING.  If not, write to
1.1.1.3 ! root       20: the Free Software Foundation, 59 Temple Place - Suite 330,
        !            21: Boston, MA 02111-1307, USA.  */
1.1       root       22: 
                     23: #ifdef sun
                     24: #include <sys/types.h>
                     25: #include <ctype.h>
                     26: #endif
                     27: #include <time.h>
                     28: 
                     29: #define TARGET_VERSION printf (" (370/MVS)");
                     30: 
                     31: /* Names to predefine in the preprocessor for this target machine.  */
                     32: 
                     33: #define CPP_PREDEFINES "-DGCC -Dgcc -DMVS -Dmvs -Asystem(mvs) -Acpu(i370) -Amachine(i370)"
                     34: 
                     35: /* Run-time compilation parameters selecting different hardware subsets.  */
                     36: 
                     37: extern int target_flags;
                     38: 
                     39: /* The sizes of the code and literals on the current page.  */
                     40: 
                     41: extern int mvs_page_code, mvs_page_lit;
                     42: 
                     43: /* The current page number and the base page number for the function.  */
                     44: 
                     45: extern int mvs_page_num, function_base_page;
                     46: 
                     47: /* True if a label has been emitted.  */
                     48: 
1.1.1.3 ! root       49: extern int mvs_label_emitted;
1.1       root       50: 
                     51: /* The name of the current function.  */
                     52: 
                     53: extern char *mvs_function_name;
                     54: 
                     55: /* The length of the function name malloc'd area.  */
                     56: 
                     57: extern int mvs_function_name_length;
                     58: 
                     59: /* The amount of space used for outgoing arguments.  */
                     60: 
                     61: extern int current_function_outgoing_args_size;
                     62: 
1.1.1.3 ! root       63: /* Compile using char instructions (mvc, nc, oc, xc).  On 4341 use this since
1.1       root       64:    these are more than twice as fast as load-op-store.
                     65:    On 3090 don't use this since load-op-store is much faster.  */
                     66: 
                     67: #define TARGET_CHAR_INSTRUCTIONS (target_flags & 1)
                     68: 
                     69: /* Default target switches */
                     70: 
                     71: #define TARGET_DEFAULT 1
                     72: 
                     73: /* Macro to define tables used to set the flags.  This is a list in braces
                     74:    of pairs in braces, each pair being { "NAME", VALUE }
                     75:    where VALUE is the bits to set or minus the bits to clear.
                     76:    An empty string NAME is used to identify the default VALUE.  */
                     77: 
                     78: #define TARGET_SWITCHES                                                        \
                     79: { { "char-instructions", 1},                                           \
                     80:   { "no-char-instructions", -1},                                       \
                     81:   { "", TARGET_DEFAULT} }
                     82: 
1.1.1.3 ! root       83: /* To use IBM supplied macro function prologue and epilogue, define the
        !            84:    following to 1.  Should only be needed if IBM changes the definition
        !            85:    of their prologue and epilogue.  */
        !            86: 
        !            87: #define MACROPROLOGUE 0
        !            88: #define MACROEPILOGUE 0
        !            89: 
1.1       root       90: /* Target machine storage layout */
                     91: 
                     92: /* Define this if most significant bit is lowest numbered in instructions
                     93:    that operate on numbered bit-fields.  */
                     94: 
                     95: #define BITS_BIG_ENDIAN 1
                     96: 
                     97: /* Define this if most significant byte of a word is the lowest numbered.  */
                     98: 
                     99: #define BYTES_BIG_ENDIAN 1
                    100: 
                    101: /* Define this if MS word of a multiword is the lowest numbered.  */
                    102: 
                    103: #define WORDS_BIG_ENDIAN 1
                    104: 
1.1.1.3 ! root      105: /* Number of bits in an addressable storage unit.  */
1.1       root      106: 
                    107: #define BITS_PER_UNIT 8
                    108: 
                    109: /* Width in bits of a "word", which is the contents of a machine register.  */
                    110: 
                    111: #define BITS_PER_WORD 32
                    112: 
                    113: /* Width of a word, in units (bytes).  */
                    114: 
                    115: #define UNITS_PER_WORD 4
                    116: 
                    117: /* Width in bits of a pointer.  See also the macro `Pmode' defined below.  */
                    118: 
                    119: #define POINTER_SIZE 32
                    120: 
                    121: /* Allocation boundary (in *bits*) for storing pointers in memory.  */
                    122: 
                    123: #define POINTER_BOUNDARY 32
                    124: 
                    125: /* Allocation boundary (in *bits*) for storing arguments in argument list.  */
                    126: 
                    127: #define PARM_BOUNDARY 32
                    128: 
                    129: /* Boundary (in *bits*) on which stack pointer should be aligned.  */
                    130: 
                    131: #define STACK_BOUNDARY 32
                    132: 
                    133: /* Allocation boundary (in *bits*) for the code of a function.  */
                    134: 
                    135: #define FUNCTION_BOUNDARY 32
                    136: 
                    137: /* There is no point aligning anything to a rounder boundary than this.  */
                    138: 
                    139: #define BIGGEST_ALIGNMENT 64
                    140: 
                    141: /* Alignment of field after `int : 0' in a structure.  */
                    142: 
                    143: #define EMPTY_FIELD_BOUNDARY 32
                    144: 
                    145: /* Define this if move instructions will actually fail to work when given
                    146:    unaligned data.  */
                    147: 
                    148: #define STRICT_ALIGNMENT 0
                    149: 
                    150: /* Define target floating point format.  */
                    151: 
                    152: #define TARGET_FLOAT_FORMAT IBM_FLOAT_FORMAT
                    153: 
                    154: /* Define character mapping for cross-compiling.  */
                    155: 
                    156: #define TARGET_EBCDIC 1
                    157: 
                    158: #ifdef HOST_EBCDIC
                    159: #define MAP_CHARACTER(c) ((char)(c))
                    160: #else
                    161: #define MAP_CHARACTER(c) ((char)mvs_map_char (c))
                    162: #endif
                    163: 
                    164: /* Define maximum length of page minus page escape overhead.  */
                    165: 
                    166: #define MAX_MVS_PAGE_LENGTH 4080
                    167: 
                    168: /* Define if special allocation order desired.  */
                    169: 
                    170: #define REG_ALLOC_ORDER                                                        \
                    171: { 0, 1, 2, 3, 14, 15, 12, 10, 9, 8, 7, 6, 5, 4, 16, 17, 18, 19, 11, 13 }
                    172: 
                    173: /* Standard register usage.  */
                    174: 
                    175: /* Number of actual hardware registers.  The hardware registers are
                    176:    assigned numbers for the compiler from 0 to just below
                    177:    FIRST_PSEUDO_REGISTER.
                    178:    All registers that the compiler knows about must be given numbers,
                    179:    even those that are not normally considered general registers.
                    180:    For the 370, we give the data registers numbers 0-15,
                    181:    and the floating point registers numbers 16-19.  */
                    182: 
                    183: #define FIRST_PSEUDO_REGISTER 20
                    184: 
                    185: /* Define base and page registers.  */
                    186: 
                    187: #define BASE_REGISTER 3
                    188: #define PAGE_REGISTER 4
                    189: 
                    190: /* 1 for registers that have pervasive standard uses and are not available
                    191:    for the register allocator.  On the 370 under C/370, R13 is stack (DSA)
                    192:    pointer, R12 is the TCA pointer, R3 is the base register, R4 is the page
                    193:    origin table pointer and R11 is the arg pointer.  */
                    194: 
                    195: #define FIXED_REGISTERS                                                \
                    196: { 0, 0, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 0, 0, 0, 0, 0 }
                    197: /*0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19*/
                    198: 
                    199: /* 1 for registers not available across function calls.  These must include
                    200:    the FIXED_REGISTERS and also any registers that can be used without being
                    201:    saved.
                    202:    The latter must include the registers where values are returned
                    203:    and the register where structure-value addresses are passed.
                    204:    NOTE: all floating registers are undefined across calls.  */
                    205: 
                    206: #define CALL_USED_REGISTERS                                            \
                    207: { 1, 1, 0, 1, 1, 0, 0, 0, 0, 0, 0, 1, 1, 1, 1, 1, 1, 1, 1, 1 }
                    208: /*0  1  2  3  4  5  6  7  8  9 10 11 12 13 14 15 16 17 18 19*/
                    209: 
                    210: /* Return number of consecutive hard regs needed starting at reg REGNO
                    211:    to hold something of mode MODE.
                    212:    This is ordinarily the length in words of a value of mode MODE
                    213:    but can be less for certain modes in special long registers.  */
                    214: 
                    215: #define HARD_REGNO_NREGS(REGNO, MODE)                                  \
                    216:   ((REGNO) > 15 ? 1 : (GET_MODE_SIZE(MODE)+UNITS_PER_WORD-1) / UNITS_PER_WORD)
                    217: 
                    218: /* Value is 1 if hard register REGNO can hold a value of machine-mode MODE.
                    219:    On the 370, the cpu registers can hold QI, HI, SI, SF and DF.  The
                    220:    even registers can hold DI.  The floating point registers can hold
                    221:    either SF or DF.  */
                    222: 
                    223: #define HARD_REGNO_MODE_OK(REGNO, MODE)                                        \
                    224:   ((REGNO) < 16 ? ((REGNO) & 1) == 0 || (MODE) != DImode               \
                    225:                : (MODE) == SFmode || (MODE) == DFmode)
                    226: 
                    227: /* Value is 1 if it is a good idea to tie two pseudo registers when one has
                    228:    mode MODE1 and one has mode MODE2.
                    229:    If HARD_REGNO_MODE_OK could produce different values for MODE1 and MODE2,
                    230:    for any hard reg, then this must be 0 for correct output.  */
                    231: 
                    232: #define MODES_TIEABLE_P(MODE1, MODE2)                                  \
                    233:   (((MODE1) == SFmode || (MODE1) == DFmode)                            \
                    234:    == ((MODE2) == SFmode || (MODE2) == DFmode))
                    235: 
                    236: /* Mark external references.  */
                    237: 
                    238: #define ENCODE_SECTION_INFO(decl)                                      \
                    239:   if (DECL_EXTERNAL (decl) && TREE_PUBLIC (decl))                      \
                    240:     SYMBOL_REF_FLAG (XEXP (DECL_RTL (decl), 0)) = 1;
                    241: 
                    242: /* Specify the registers used for certain standard purposes.
                    243:    The values of these macros are register numbers.  */
                    244: 
                    245: /* 370 PC isn't overloaded on a register.  */
                    246: 
                    247: /* #define PC_REGNUM */
                    248: 
                    249: /* Register to use for pushing function arguments.  */
                    250: 
                    251: #define STACK_POINTER_REGNUM 13
                    252: 
                    253: /* Base register for access to local variables of the function.  */
                    254: 
                    255: #define FRAME_POINTER_REGNUM 13
                    256: 
                    257: /* Value should be nonzero if functions must have frame pointers.
                    258:    Zero means the frame pointer need not be set up (and parms may be
                    259:    accessed via the stack pointer) in functions that seem suitable.
                    260:    This is computed in `reload', in reload1.c.  */
                    261: 
                    262: #define FRAME_POINTER_REQUIRED 1
                    263: 
                    264: /* Base register for access to arguments of the function.  */
                    265: 
                    266: #define ARG_POINTER_REGNUM 11
                    267: 
                    268: /* Register in which static-chain is passed to a function.  */
                    269: 
                    270: #define STATIC_CHAIN_REGNUM 10
                    271: 
                    272: /* Register in which address to store a structure value is passed to
                    273:    a function.  */
                    274: 
                    275: #define STRUCT_VALUE_REGNUM 1
                    276: 
                    277: /* Define the classes of registers for register constraints in the
                    278:    machine description.  Also define ranges of constants.
                    279: 
                    280:    One of the classes must always be named ALL_REGS and include all hard regs.
                    281:    If there is more than one class, another class must be named NO_REGS
                    282:    and contain no registers.
                    283: 
                    284:    The name GENERAL_REGS must be the name of a class (or an alias for
                    285:    another name such as ALL_REGS).  This is the class of registers
                    286:    that is allowed by "g" or "r" in a register constraint.
                    287:    Also, registers outside this class are allocated only when
                    288:    instructions express preferences for them.
                    289: 
                    290:    The classes must be numbered in nondecreasing order; that is,
                    291:    a larger-numbered class must never be contained completely
                    292:    in a smaller-numbered class.
                    293: 
                    294:    For any two classes, it is very desirable that there be another
                    295:    class that represents their union.  */
                    296: 
                    297: enum reg_class
                    298:   {
                    299:     NO_REGS, ADDR_REGS, DATA_REGS,
                    300:     FP_REGS, ALL_REGS, LIM_REG_CLASSES
                    301:   };
                    302: 
                    303: #define GENERAL_REGS DATA_REGS
                    304: #define N_REG_CLASSES (int) LIM_REG_CLASSES
                    305: 
                    306: /* Give names of register classes as strings for dump file.  */
                    307: 
                    308: #define REG_CLASS_NAMES                                                \
                    309: { "NO_REGS", "ADDR_REGS", "DATA_REGS", "FP_REGS", "ALL_REGS" }
                    310: 
                    311: /* Define which registers fit in which classes.  This is an initializer for
                    312:    a vector of HARD_REG_SET of length N_REG_CLASSES.  */
                    313: 
                    314: #define REG_CLASS_CONTENTS {0, 0x0fffe, 0x0ffff, 0xf0000, 0xfffff}
                    315: 
                    316: /* The same information, inverted:
                    317:    Return the class number of the smallest class containing
                    318:    reg number REGNO.  This could be a conditional expression
                    319:    or could index an array.  */
                    320: 
                    321: #define REGNO_REG_CLASS(REGNO)                                                 \
                    322:   ((REGNO) >= 16 ? FP_REGS : (REGNO) != 0 ? ADDR_REGS : DATA_REGS)
                    323: 
                    324: /* The class value for index registers, and the one for base regs.  */
                    325: 
                    326: #define INDEX_REG_CLASS ADDR_REGS
                    327: #define BASE_REG_CLASS ADDR_REGS
                    328: 
                    329: /* Get reg_class from a letter such as appears in the machine description.  */
                    330: 
                    331: #define REG_CLASS_FROM_LETTER(C)                                       \
                    332:   ((C) == 'a' ? ADDR_REGS :                                            \
                    333:   ((C) == 'd' ? DATA_REGS :                                            \
                    334:   ((C) == 'f' ? FP_REGS   : NO_REGS)))
                    335: 
                    336: /* The letters I, J, K, L and M in a register constraint string can be used
                    337:    to stand for particular ranges of immediate operands.
                    338:    This macro defines what the ranges are.
                    339:    C is the letter, and VALUE is a constant value.
                    340:    Return 1 if VALUE is in the range specified by C.  */
                    341: 
                    342: #define CONST_OK_FOR_LETTER_P(VALUE, C)                                        \
                    343:   ((C) == 'I' ? (unsigned) (VALUE) < 256 :                             \
                    344:    (C) == 'J' ? (unsigned) (VALUE) < 4096 :                            \
                    345:    (C) == 'K' ? (VALUE) >= -32768 && (VALUE) < 32768 : 0)
                    346: 
                    347: /* Similar, but for floating constants, and defining letters G and H.
                    348:    Here VALUE is the CONST_DOUBLE rtx itself.  */
                    349: 
                    350: #define CONST_DOUBLE_OK_FOR_LETTER_P(VALUE, C)  1
                    351: 
                    352: /* Given an rtx X being reloaded into a reg required to be in class CLASS,
                    353:    return the class of reg to actually use.  In general this is just CLASS;
                    354:    but on some machines in some cases it is preferable to use a more
                    355:    restrictive class.  */
                    356: 
                    357: #define PREFERRED_RELOAD_CLASS(X, CLASS)                               \
                    358:     (GET_CODE(X) == CONST_DOUBLE ? FP_REGS :                           \
                    359:      GET_CODE(X) == CONST_INT ? DATA_REGS :                            \
                    360:      GET_CODE(X) == LABEL_REF ||                                       \
                    361:      GET_CODE(X) == SYMBOL_REF ||                                      \
                    362:      GET_CODE(X) == CONST ? ADDR_REGS : (CLASS))
                    363: 
                    364: /* Return the maximum number of consecutive registers needed to represent
                    365:    mode MODE in a register of class CLASS.  */
                    366: 
                    367: #define CLASS_MAX_NREGS(CLASS, MODE)                                   \
                    368:   ((CLASS) == FP_REGS ? 1 :                                            \
                    369:    (GET_MODE_SIZE (MODE) + UNITS_PER_WORD - 1) / UNITS_PER_WORD)
                    370: 
                    371: /* Stack layout; function entry, exit and calling.  */
                    372: 
                    373: /* Define this if pushing a word on the stack makes the stack pointer a
                    374:    smaller address.  */
                    375: 
                    376: /* #define STACK_GROWS_DOWNWARD */
                    377: 
                    378: /* Define this if the nominal address of the stack frame is at the
                    379:    high-address end of the local variables; that is, each additional local
                    380:    variable allocated goes at a more negative offset in the frame.  */
                    381: 
                    382: /* #define FRAME_GROWS_DOWNWARD */
                    383: 
                    384: /* Offset within stack frame to start allocating local variables at.
                    385:    If FRAME_GROWS_DOWNWARD, this is the offset to the END of the
                    386:    first local allocated.  Otherwise, it is the offset to the BEGINNING
                    387:    of the first local allocated.  */
                    388: 
                    389: #define STARTING_FRAME_OFFSET                                                  \
                    390:      (STACK_POINTER_OFFSET + current_function_outgoing_args_size)
                    391: 
                    392: #define INITIAL_FRAME_POINTER_OFFSET(DEPTH) (DEPTH) = STARTING_FRAME_OFFSET
                    393: 
                    394: /* If we generate an insn to push BYTES bytes, this says how many the stack
                    395:    pointer really advances by.  On the 370, we have no push instruction.  */
                    396: 
                    397: /* #define PUSH_ROUNDING(BYTES) */
                    398: 
                    399: /* Accumulate the outgoing argument count so we can request the right
                    400:    DSA size and determine stack offset.  */
                    401: 
                    402: #define ACCUMULATE_OUTGOING_ARGS
                    403: 
                    404: /* Define offset from stack pointer, to location where a parm can be
                    405:    pushed.  */
                    406: 
                    407: #define STACK_POINTER_OFFSET 148
                    408: 
                    409: /* Offset of first parameter from the argument pointer register value.  */
                    410: 
                    411: #define FIRST_PARM_OFFSET(FNDECL) 0
                    412: 
                    413: /* 1 if N is a possible register number for function argument passing.
                    414:    On the 370, no registers are used in this way.  */
                    415: 
                    416: #define FUNCTION_ARG_REGNO_P(N) 0
                    417: 
                    418: /* Define a data type for recording info about an argument list during
                    419:    the scan of that argument list.  This data type should hold all
                    420:    necessary information about the function itself and about the args
                    421:    processed so far, enough to enable macros such as FUNCTION_ARG to
                    422:    determine where the next arg should go.  */
                    423: 
                    424: #define CUMULATIVE_ARGS int
                    425: 
                    426: /* Initialize a variable CUM of type CUMULATIVE_ARGS for a call to
                    427:    a function whose data type is FNTYPE.
                    428:    For a library call, FNTYPE is 0.  */
                    429: 
                    430: #define INIT_CUMULATIVE_ARGS(CUM, FNTYPE, LIBNAME)  ((CUM) = 0)
                    431: 
                    432: /* Update the data in CUM to advance over an argument of mode MODE and
                    433:    data type TYPE.  (TYPE is null for libcalls where that information
                    434:    may not be available.) */
                    435: 
                    436: #define FUNCTION_ARG_ADVANCE(CUM, MODE, TYPE, NAMED)                   \
                    437:  ((CUM) += ((MODE) == DFmode || (MODE) == SFmode                       \
                    438:            ? 256                                                       \
                    439:            : (MODE) != BLKmode                                         \
                    440:            ? (GET_MODE_SIZE (MODE) + 3) / 4                            \
                    441:            : (int_size_in_bytes (TYPE) + 3) / 4))
                    442: 
                    443: /* Define where to put the arguments to a function.  Value is zero to push
                    444:    the argument on the stack, or a hard register in which to store the
                    445:    argument.  */
                    446: 
                    447: #define FUNCTION_ARG(CUM, MODE, TYPE, NAMED) 0
                    448: 
                    449: /* For an arg passed partly in registers and partly in memory, this is the
                    450:    number of registers used.  For args passed entirely in registers or
                    451:    entirely in memory, zero.  */
                    452: 
                    453: #define FUNCTION_ARG_PARTIAL_NREGS(CUM, MODE, TYPE, NAMED) 0
                    454: 
                    455: /* Define if returning from a function call automatically pops the
                    456:    arguments described by the number-of-args field in the call.  */
                    457: 
1.1.1.3 ! root      458: #define RETURN_POPS_ARGS(FUNDECL,FUNTYPE,SIZE) 0
1.1       root      459: 
                    460: /* Define how to find the value returned by a function.  VALTYPE is the
                    461:    data type of the value (as a tree).
                    462:    If the precise function being called is known, FUNC is its FUNCTION_DECL;
                    463:    otherwise, FUNC is 15.  */
                    464: 
                    465: #define RET_REG(MODE)  ((MODE) == DFmode || (MODE) == SFmode ? 16 : 15)
                    466: 
                    467: /* On the 370 the return value is in R15 or R16.  */
                    468: 
                    469: #define FUNCTION_VALUE(VALTYPE, FUNC)                                          \
                    470:   gen_rtx(REG, TYPE_MODE (VALTYPE), RET_REG(TYPE_MODE(VALTYPE)))
                    471: 
                    472: /* Define how to find the value returned by a library function assuming
                    473:    the value has mode MODE.  */
                    474: 
                    475: #define LIBCALL_VALUE(MODE)  gen_rtx(REG, MODE, RET_REG(MODE))
                    476: 
                    477: /* 1 if N is a possible register number for a function value.
                    478:    On the 370 under C/370, R15 and R16 are thus used.  */
                    479: 
                    480: #define FUNCTION_VALUE_REGNO_P(N) ((N) == 15 || (N) == 16)
                    481: 
                    482: /* This macro definition sets up a default value for `main' to return.  */
                    483: 
                    484: #define DEFAULT_MAIN_RETURN  c_expand_return (integer_zero_node)
                    485: 
                    486: /* This macro generates the assembly code for function entry.
                    487:    All of the C/370 environment is preserved.  */
                    488: 
1.1.1.3 ! root      489: #if MACROPROLOGUE == 1
        !           490: #define FUNCTION_PROLOGUE(FILE, LSIZE)                                 \
        !           491: {                                                                      \
        !           492:   fprintf (FILE, "\tEDCPRLG USRDSAL=%d,BASEREG=%d\n",                  \
        !           493:           STACK_POINTER_OFFSET + LSIZE +                               \
        !           494:           current_function_outgoing_args_size, BASE_REGISTER);         \
        !           495:   fprintf (FILE, "PG%d\tEQU\t*\n", mvs_page_num );                     \
        !           496:   fprintf (FILE, "\tLR\t11,1\n");                                      \
        !           497:   fprintf (FILE, "\tL\t%d,=A(PGT%d)\n", PAGE_REGISTER, mvs_page_num);  \
        !           498:   mvs_page_code = 6;                                                   \
        !           499:   mvs_page_lit = 4;                                                    \
        !           500:   mvs_check_page (FILE, 0, 0);                                         \
        !           501:   function_base_page = mvs_page_num;                                   \
        !           502: }
        !           503: #else /* MACROPROLOGUE != 1 */
1.1       root      504: #define FUNCTION_PROLOGUE(FILE, LSIZE)                                 \
                    505: {                                                                      \
                    506:   static int function_label_index = 1;                                 \
                    507:   static int function_first = 0;                                       \
                    508:   static int function_year, function_month, function_day;              \
                    509:   static int function_hour, function_minute, function_second;          \
                    510:   int i;                                                               \
                    511:   if (!function_first)                                                 \
                    512:     {                                                                  \
                    513:       struct tm *function_time;                                                \
                    514:       time_t lcltime;                                                  \
                    515:       time (&lcltime);                                                 \
                    516:       function_time = localtime (&lcltime);                            \
                    517:       function_year = function_time->tm_year + 1900;                   \
                    518:       function_month = function_time->tm_mon + 1;                      \
                    519:       function_day = function_time->tm_mday;                           \
                    520:       function_hour = function_time->tm_hour;                          \
                    521:       function_minute = function_time->tm_min;                         \
                    522:       function_second = function_time->tm_sec;                         \
                    523:     }                                                                  \
1.1.1.3 ! root      524:   fprintf (FILE, "$DSD%03d\tDSECT\n", function_label_index);           \
        !           525:   fprintf (FILE, "\tDS\tD\n");                                         \
        !           526:   fprintf (FILE, "\tDS\tCL(120+%d)\n", STACK_POINTER_OFFSET + LSIZE    \
        !           527:                        + current_function_outgoing_args_size);         \
        !           528:   fprintf (FILE, "\tORG\t$DSD%03d\n", function_label_index);           \
        !           529:   fprintf (FILE, "\tDS\tCL(120+8)\n");                                 \
        !           530:   fprintf (FILE, "\tORG\n");                                           \
        !           531:   fprintf (FILE, "\tDS\t0D\n");                                                \
        !           532:   fprintf (FILE, "$DSL%03d\tEQU\t*-$DSD%03d-8\n", function_label_index, \
        !           533:           function_label_index);                                       \
        !           534:   fprintf (FILE, "\tDS\t0H\n");                                                \
        !           535:   assemble_name (FILE, mvs_function_name);                             \
        !           536:   fprintf (FILE, "\tCSECT\n");                                         \
1.1       root      537:   fprintf (FILE, "\tUSING\t*,15\n");                                   \
                    538:   fprintf (FILE, "\tB\tFPL%03d\n", function_label_index);              \
                    539:   fprintf (FILE, "\tDC\tAL1(FPL%03d+4-*)\n", function_label_index + 1);        \
1.1.1.3 ! root      540:   fprintf (FILE, "\tDC\tX'CE',X'A0',AL1(16)\n");                       \
        !           541:   fprintf (FILE, "\tDC\tAL4($PPA%03d)\n",function_label_index);                \
        !           542:   fprintf (FILE, "\tDC\tAL4(0)\n");                                    \
        !           543:   fprintf (FILE, "\tDC\tAL4($DSL%03d)\n", function_label_index);       \
1.1       root      544:   fprintf (FILE, "FPL%03d\tEQU\t*\n", function_label_index + 1);       \
                    545:   fprintf (FILE, "\tDC\tAL2(%d),C'%s'\n", strlen (mvs_function_name),  \
                    546:        mvs_function_name);                                             \
1.1.1.3 ! root      547:   fprintf (FILE, "$PPA%03d\tDS\t0F\n", function_label_index);          \
        !           548:   fprintf (FILE, "\tDC\tX'03',X'00',X'33',X'00'\n");                   \
        !           549:   fprintf (FILE, "\tDC\tV(CEESTART),A(0)\n");                          \
        !           550:   fprintf (FILE, "\tDC\tA($TIM%03d)\n", function_label_index);         \
        !           551:   fprintf (FILE, "$TIM%03d\tDS\t0F\n", function_label_index);          \
        !           552:   fprintf (FILE, "\tDC\tCL4'%d',CL4'%02d%02d',CL6'%02d%02d00'\n",      \
        !           553:                 function_year, function_month, function_day,           \
        !           554:                 function_hour, function_minute, function_second);      \
        !           555:   fprintf (FILE, "\tDC\tCL2'01',CL4'0100'\n");                         \
        !           556:   fprintf (FILE, "FPL%03d\tDS\t0H\n", function_label_index);           \
1.1       root      557:   fprintf (FILE, "\tSTM\t14,12,12(13)\n");                             \
                    558:   fprintf (FILE, "\tL\t2,76(,13)\n");                                  \
                    559:   fprintf (FILE, "\tL\t0,16(,15)\n");                                  \
                    560:   fprintf (FILE, "\tALR\t0,2\n");                                      \
                    561:   fprintf (FILE, "\tCL\t0,12(,12)\n");                                 \
                    562:   fprintf (FILE, "\tBNH\t*+10\n");                                     \
                    563:   fprintf (FILE, "\tL\t15,116(,12)\n");                                        \
                    564:   fprintf (FILE, "\tBALR\t14,15\n");                                   \
                    565:   fprintf (FILE, "\tL\t15,72(,13)\n");                                 \
                    566:   fprintf (FILE, "\tSTM\t15,0,72(2)\n");                               \
                    567:   fprintf (FILE, "\tMVI\t0(2),X'10'\n");                               \
1.1.1.3 ! root      568:   fprintf (FILE, "\tST\t2,8(,13)\n ");                                  \
1.1       root      569:   fprintf (FILE, "\tST\t13,4(,2)\n ");                                 \
                    570:   fprintf (FILE, "\tLR\t13,2\n");                                      \
                    571:   fprintf (FILE, "\tDROP\t15\n");                                      \
                    572:   fprintf (FILE, "\tBALR\t%d,0\n", BASE_REGISTER);                     \
                    573:   fprintf (FILE, "PG%d\tEQU\t*\n", mvs_page_num );                     \
                    574:   fprintf (FILE, "\tUSING\t*,%d\n", BASE_REGISTER);                    \
1.1.1.3 ! root      575:   fprintf (FILE, "\tLR\t11,1\n");                                      \
1.1       root      576:   fprintf (FILE, "\tL\t%d,=A(PGT%d)\n", PAGE_REGISTER, mvs_page_num);  \
                    577:   mvs_page_code = 4;                                                   \
                    578:   mvs_page_lit = 4;                                                    \
                    579:   mvs_check_page (FILE, 0, 0);                                         \
                    580:   function_base_page = mvs_page_num;                                   \
                    581:   function_first = 1;                                                  \
                    582:   function_label_index += 2;                                           \
                    583: }
1.1.1.3 ! root      584: #endif /* MACROPROLOGUE */
1.1       root      585: 
                    586: #define ASM_DECLARE_FUNCTION_NAME(FILE, NAME, DECL)                    \
                    587: {                                                                      \
                    588:   if (strlen (NAME) * 2 > mvs_function_name_length)                    \
                    589:     {                                                                  \
                    590:       if (mvs_function_name)                                           \
                    591:        free (mvs_function_name);                                       \
                    592:       mvs_function_name = 0;                                           \
                    593:     }                                                                  \
                    594:   if (!mvs_function_name)                                              \
                    595:     {                                                                  \
                    596:       mvs_function_name_length = strlen (NAME) * 2;                    \
                    597:       mvs_function_name = (char *) malloc (mvs_function_name_length);  \
                    598:       if (mvs_function_name == 0)                                      \
                    599:        {                                                               \
                    600:          fatal ("virtual memory exceeded");                            \
                    601:          abort ();                                                     \
                    602:        }                                                               \
                    603:     }                                                                  \
                    604:   if (!strcmp (NAME, "main"))                                          \
                    605:     strcpy (mvs_function_name, "gccmain");                             \
                    606:   else                                                                 \
                    607:     strcpy (mvs_function_name, NAME);                                  \
1.1.1.3 ! root      608:   fprintf (FILE, "\tDS\t0F\n");                                                \
1.1       root      609:   assemble_name (FILE, mvs_function_name);                             \
                    610:   fputs ("\tCSECT\n", FILE);                                           \
                    611: }
                    612: 
                    613: /* This macro generates the assembly code for function exit, on machines
                    614:    that need it.  If FUNCTION_EPILOGUE is not defined then individual
                    615:    return instructions are generated for each return statement.  Args are
                    616:    same as for FUNCTION_PROLOGUE.
                    617: 
                    618:    The function epilogue should not depend on the current stack pointer!
                    619:    It should use the frame pointer only.  This is mandatory because
                    620:    of alloca; we also take advantage of it to omit stack adjustments
                    621:    before returning.  */
                    622: 
1.1.1.3 ! root      623: #if MACROEPILOGUE == 1
        !           624: #define FUNCTION_EPILOGUE(FILE, LSIZE)                                 \
        !           625: {                                                                      \
        !           626:   int i;                                                               \
        !           627:   check_label_emit();                                                  \
        !           628:   mvs_check_page (FILE,14,0);                                          \
        !           629:   fprintf (FILE, "\tEDCEPIL\n");                                       \
        !           630:   mvs_page_num++;                                                      \
        !           631:   fprintf (FILE, "\tDS\t0F\n" );                                       \
        !           632:   fprintf (FILE, "\tLTORG\n");                                         \
        !           633:   fprintf (FILE, "\tDS\t0F\n");                                                \
        !           634:   fprintf (FILE, "PGT%d\tEQU\t*\n", function_base_page);               \
        !           635:   mvs_free_label();                                                    \
        !           636:   for ( i = function_base_page; i < mvs_page_num; i++ )                        \
        !           637:     fprintf (FILE, "\tDC\tA(PG%d)\n", i);                              \
        !           638: }
        !           639: #else /* MACROEPILOGUE != 1 */
1.1       root      640: #define FUNCTION_EPILOGUE(FILE, LSIZE)                                 \
                    641: {                                                                      \
                    642:   int i;                                                               \
                    643:   check_label_emit();                                                  \
                    644:   mvs_check_page (FILE,14,0);                                          \
                    645:   fprintf (FILE, "\tL\t13,4(,13)\n");                                  \
                    646:   fprintf (FILE, "\tL\t14,12(,13)\n");                                 \
                    647:   fprintf (FILE, "\tLM\t2,12,28(13)\n");                               \
                    648:   fprintf (FILE, "\tBALR\t1,14\n");                                    \
                    649:   fprintf (FILE, "\tDC\tA(");                                          \
                    650:   mvs_page_num++;                                                      \
                    651:   assemble_name (FILE, mvs_function_name);                             \
                    652:   fprintf (FILE, ")\n" );                                              \
                    653:   fprintf (FILE, "\tDS\t0F\n" );                                       \
                    654:   fprintf (FILE, "\tLTORG\n");                                         \
                    655:   fprintf (FILE, "\tDS\t0F\n");                                                \
                    656:   fprintf (FILE, "PGT%d\tEQU\t*\n", function_base_page);               \
                    657:   mvs_free_label();                                                    \
                    658:   for ( i = function_base_page; i < mvs_page_num; i++ )                        \
                    659:     fprintf (FILE, "\tDC\tA(PG%d)\n", i);                              \
                    660: }
1.1.1.3 ! root      661: #endif /* MACROEPILOGUE */
        !           662: 
1.1       root      663: 
                    664: /* Output assembler code for a block containing the constant parts of a
                    665:    trampoline, leaving space for the variable parts.
                    666: 
                    667:    On the 370, the trampoline contains these instructions:
                    668: 
                    669:         BALR  14,0
                    670:         USING *,14
                    671:         L     STATIC_CHAIN_REGISTER,X
                    672:         L     15,Y
                    673:         BR    15
                    674:    X    DS    0F
                    675:    Y    DS    0F  */
                    676: 
                    677: #define TRAMPOLINE_TEMPLATE(FILE)                                      \
                    678: {                                                                      \
                    679:   ASM_OUTPUT_SHORT (FILE, gen_rtx (CONST_INT, VOIDmode, 0x05E0));      \
                    680:   ASM_OUTPUT_SHORT (FILE, gen_rtx (CONST_INT, VOIDmode, 0x5800 |       \
                    681:                           STATIC_CHAIN_REGNUM << 4));                  \
                    682:   ASM_OUTPUT_SHORT (FILE, gen_rtx (CONST_INT, VOIDmode, 0xE00A));      \
                    683:   ASM_OUTPUT_SHORT (FILE, gen_rtx (CONST_INT, VOIDmode, 0x58F0));      \
                    684:   ASM_OUTPUT_SHORT (FILE, gen_rtx (CONST_INT, VOIDmode, 0xE00E));      \
                    685:   ASM_OUTPUT_SHORT (FILE, gen_rtx (CONST_INT, VOIDmode, 0x07FF));      \
                    686:   ASM_OUTPUT_SHORT (FILE, const0_rtx);                                 \
                    687:   ASM_OUTPUT_SHORT (FILE, const0_rtx);                                 \
                    688:   ASM_OUTPUT_SHORT (FILE, const0_rtx);                                 \
                    689:   ASM_OUTPUT_SHORT (FILE, const0_rtx);                                 \
                    690: }
                    691: 
                    692: /* Length in units of the trampoline for entering a nested function.  */
                    693: 
                    694: #define TRAMPOLINE_SIZE 20
                    695: 
                    696: /* Emit RTL insns to initialize the variable parts of a trampoline.  */
                    697: 
                    698: #define INITIALIZE_TRAMPOLINE(TRAMP, FNADDR, CXT)                      \
                    699: {                                                                      \
                    700:   emit_move_insn (gen_rtx (MEM, SImode, plus_constant (TRAMP, 12)), CXT); \
                    701:   emit_move_insn (gen_rtx (MEM, SImode, plus_constant (TRAMP, 16)), FNADDR); \
                    702: }
                    703: 
                    704: /* Output assembler code to FILE to increment profiler label # LABELNO
                    705:    for profiling a function entry.  */
                    706: 
                    707: #define FUNCTION_PROFILER(FILE, LABELNO)                               \
1.1.1.3 ! root      708:   fprintf (FILE, "Error: No profiling available.\n")
1.1       root      709: 
                    710: /* Define EXIT_IGNORE_STACK if, when returning from a function, the stack
                    711:    pointer does not matter (provided there is a frame pointer).  */
                    712: 
                    713: #define EXIT_IGNORE_STACK      1
                    714: 
                    715: /* Addressing modes, and classification of registers for them.  */
                    716: 
                    717: /* #define HAVE_POST_INCREMENT */
                    718: /* #define HAVE_POST_DECREMENT */
                    719: 
                    720: /* #define HAVE_PRE_DECREMENT */
                    721: /* #define HAVE_PRE_INCREMENT */
                    722: 
                    723: /* These assume that REGNO is a hard or pseudo reg number.  They give
                    724:    nonzero only if REGNO is a hard reg of the suitable class or a pseudo
                    725:    reg currently allocated to a suitable hard reg.
                    726:    These definitions are NOT overridden anywhere.  */
                    727: 
                    728: #define REGNO_OK_FOR_INDEX_P(REGNO)                                    \
                    729:   (((REGNO) > 0 && (REGNO) < 16)                                       \
                    730:     || (reg_renumber[REGNO] > 0 && reg_renumber[REGNO] < 16))
                    731: 
                    732: #define REGNO_OK_FOR_BASE_P(REGNO) REGNO_OK_FOR_INDEX_P(REGNO)
                    733: 
                    734: #define REGNO_OK_FOR_DATA_P(REGNO)                                     \
                    735:   ((REGNO) < 16 || (unsigned) reg_renumber[REGNO] < 16)
                    736: 
                    737: #define REGNO_OK_FOR_FP_P(REGNO)                                       \
                    738:   ((unsigned) ((REGNO) - 16) < 4 || (unsigned) (reg_renumber[REGNO] - 16) < 4)
                    739: 
                    740: /* Now macros that check whether X is a register and also,
                    741:    strictly, whether it is in a specified class.  */
                    742: 
                    743: /* 1 if X is a data register.  */
                    744: 
                    745: #define DATA_REG_P(X) (REG_P (X) && REGNO_OK_FOR_DATA_P (REGNO (X)))
                    746: 
                    747: /* 1 if X is an fp register.  */
                    748: 
                    749: #define FP_REG_P(X) (REG_P (X) && REGNO_OK_FOR_FP_P (REGNO (X)))
                    750: 
                    751: /* 1 if X is an address register.  */
                    752: 
                    753: #define ADDRESS_REG_P(X) (REG_P (X) && REGNO_OK_FOR_BASE_P (REGNO (X)))
                    754: 
                    755: /* Maximum number of registers that can appear in a valid memory address.  */
                    756: 
                    757: #define MAX_REGS_PER_ADDRESS 2
                    758: 
                    759: /* Recognize any constant value that is a valid address.  */
                    760: 
                    761: #define CONSTANT_ADDRESS_P(X)                                          \
                    762:   (GET_CODE (X) == LABEL_REF || GET_CODE (X) == SYMBOL_REF             \
                    763:   || GET_CODE (X) == CONST_INT || GET_CODE (X) == CONST_DOUBLE         \
                    764:   || (GET_CODE (X) == CONST                                            \
                    765:          && GET_CODE (XEXP (XEXP (X, 0), 0)) == LABEL_REF)             \
                    766:   || (GET_CODE (X) == CONST                                            \
                    767:          && GET_CODE (XEXP (XEXP (X, 0), 0)) == SYMBOL_REF             \
                    768:          && !SYMBOL_REF_FLAG (XEXP (XEXP (X, 0), 0))))
                    769: 
                    770: /* Nonzero if the constant value X is a legitimate general operand.
                    771:    It is given that X satisfies CONSTANT_P or is a CONST_DOUBLE.  */
                    772: 
                    773: #define LEGITIMATE_CONSTANT_P(X) 1
                    774: 
                    775: /* The macros REG_OK_FOR..._P assume that the arg is a REG rtx and check
                    776:    its validity for a certain class.  We have two alternate definitions
                    777:    for each of them.  The usual definition accepts all pseudo regs; the
                    778:    other rejects them all.  The symbol REG_OK_STRICT causes the latter
                    779:    definition to be used.
                    780: 
                    781:    Most source files want to accept pseudo regs in the hope that they will
                    782:    get allocated to the class that the insn wants them to be in.
                    783:    Some source files that are used after register allocation
                    784:    need to be strict.  */
                    785: 
                    786: #ifndef REG_OK_STRICT
                    787: 
                    788: /* Nonzero if X is a hard reg that can be used as an index or if it is
                    789:   a pseudo reg.  */
                    790: 
                    791: #define REG_OK_FOR_INDEX_P(X)                                          \
                    792:   ((REGNO(X) > 0 && REGNO(X) < 16) || REGNO(X) >= 20)
                    793: 
                    794: /* Nonzero if X is a hard reg that can be used as a base reg or if it is
                    795:    a pseudo reg.  */
                    796: 
                    797: #define REG_OK_FOR_BASE_P(X)   REG_OK_FOR_INDEX_P(X)
                    798: 
                    799: #else /* REG_OK_STRICT */
                    800: 
                    801: /* Nonzero if X is a hard reg that can be used as an index.  */
                    802: 
                    803: #define REG_OK_FOR_INDEX_P(X) REGNO_OK_FOR_INDEX_P(REGNO(X))
                    804: 
                    805: /* Nonzero if X is a hard reg that can be used as a base reg.  */
                    806: 
                    807: #define REG_OK_FOR_BASE_P(X) REGNO_OK_FOR_BASE_P(REGNO(X))
                    808: 
                    809: #endif /* REG_OK_STRICT */
                    810: 
                    811: /* GO_IF_LEGITIMATE_ADDRESS recognizes an RTL expression that is a
                    812:    valid memory address for an instruction.
                    813:    The MODE argument is the machine mode for the MEM expression
                    814:    that wants to use this address.
                    815: 
                    816:    The other macros defined here are used only in GO_IF_LEGITIMATE_ADDRESS,
                    817:    except for CONSTANT_ADDRESS_P which is actually machine-independent.  */
                    818: 
                    819: #define COUNT_REGS(X, REGS, FAIL)                                      \
                    820:  if (REG_P (X) && REG_OK_FOR_BASE_P (X))                               \
                    821:    REGS += 1;                                                          \
                    822:  else if (GET_CODE (X) != CONST_INT || (unsigned) INTVAL (X) >= 4096)  \
                    823:    goto FAIL;
                    824: 
                    825: #define GO_IF_LEGITIMATE_ADDRESS(MODE, X, ADDR)                                \
                    826: {                                                                      \
                    827:   if (REG_P (X) && REG_OK_FOR_BASE_P (X))                              \
                    828:     goto ADDR;                                                         \
                    829:   if (GET_CODE (X) == PLUS)                                            \
                    830:     {                                                                  \
                    831:       int regs = 0;                                                    \
                    832:       rtx x0 = XEXP (X, 0);                                            \
                    833:       rtx x1 = XEXP (X, 1);                                            \
                    834:       if (GET_CODE (x0) == PLUS)                                       \
                    835:        {                                                               \
                    836:          COUNT_REGS (XEXP (x0, 0), regs, FAIL);                        \
                    837:          COUNT_REGS (XEXP (x0, 1), regs, FAIL);                        \
                    838:          COUNT_REGS (x1, regs, FAIL);                                  \
                    839:          if (regs == 2)                                                \
                    840:            goto ADDR;                                                  \
                    841:        }                                                               \
                    842:       else if (GET_CODE (x1) == PLUS)                                  \
                    843:        {                                                               \
                    844:          COUNT_REGS (x0, regs, FAIL);                                  \
                    845:          COUNT_REGS (XEXP (x1, 0), regs, FAIL);                        \
                    846:          COUNT_REGS (XEXP (x1, 1), regs, FAIL);                        \
                    847:          if (regs == 2)                                                \
                    848:            goto ADDR;                                                  \
                    849:        }                                                               \
                    850:       else                                                             \
                    851:        {                                                               \
                    852:          COUNT_REGS (x0, regs, FAIL);                                  \
                    853:          COUNT_REGS (x1, regs, FAIL);                                  \
                    854:          if (regs != 0)                                                \
                    855:            goto ADDR;                                                  \
                    856:        }                                                               \
                    857:     }                                                                  \
                    858:   FAIL: ;                                                              \
                    859: }
                    860: 
                    861: /* The 370 has no mode dependent addresses.  */
                    862: 
                    863: #define GO_IF_MODE_DEPENDENT_ADDRESS(ADDR, LABEL)
                    864: 
                    865: /* Try machine-dependent ways of modifying an illegitimate address
                    866:    to be legitimate.  If we find one, return the new, valid address.
                    867:    This macro is used in only one place: `memory_address' in explow.c.  */
                    868: 
                    869: #define LEGITIMIZE_ADDRESS(X, OLDX, MODE, WIN)                         \
                    870: {                                                                      \
                    871:   if (GET_CODE (X) == PLUS && CONSTANT_ADDRESS_P (XEXP (X, 1)))                \
                    872:     (X) = gen_rtx (PLUS, SImode, XEXP (X, 0),                          \
                    873:                   copy_to_mode_reg (SImode, XEXP (X, 1)));             \
                    874:   if (GET_CODE (X) == PLUS && CONSTANT_ADDRESS_P (XEXP (X, 0)))                \
                    875:     (X) = gen_rtx (PLUS, SImode, XEXP (X, 1),                          \
                    876:                   copy_to_mode_reg (SImode, XEXP (X, 0)));             \
                    877:   if (GET_CODE (X) == PLUS && GET_CODE (XEXP (X, 0)) == MULT)          \
                    878:     (X) = gen_rtx (PLUS, SImode, XEXP (X, 1),                          \
                    879:                   force_operand (XEXP (X, 0), 0));                     \
                    880:   if (GET_CODE (X) == PLUS && GET_CODE (XEXP (X, 1)) == MULT)          \
                    881:     (X) = gen_rtx (PLUS, SImode, XEXP (X, 0),                          \
                    882:                   force_operand (XEXP (X, 1), 0));                     \
                    883:   if (memory_address_p (MODE, X))                                      \
                    884:     goto WIN;                                                          \
                    885: }
                    886: 
                    887: /* Specify the machine mode that this machine uses for the index in the
                    888:    tablejump instruction.  */
                    889: 
                    890: #define CASE_VECTOR_MODE SImode
                    891: 
                    892: /* Define this if the tablejump instruction expects the table to contain
                    893:    offsets from the address of the table.
                    894:    Do not define this if the table should contain absolute addresses.  */
                    895: 
                    896: /* #define CASE_VECTOR_PC_RELATIVE */
                    897: 
                    898: /* Specify the tree operation to be used to convert reals to integers.  */
                    899: 
                    900: #define IMPLICIT_FIX_EXPR FIX_ROUND_EXPR
                    901: 
                    902: /* Define this if fixuns_trunc is the same as fix_trunc.  */
                    903: 
                    904: #define FIXUNS_TRUNC_LIKE_FIX_TRUNC
                    905: 
                    906: /* We use "unsigned char" as default.  */
                    907: 
                    908: #define DEFAULT_SIGNED_CHAR 0
                    909: 
                    910: /* This is the kind of divide that is easiest to do in the general case.  */
                    911: 
                    912: #define EASY_DIV_EXPR TRUNC_DIV_EXPR
                    913: 
                    914: /* Max number of bytes we can move from memory to memory in one reasonably
                    915:    fast instruction.  */
                    916: 
                    917: #define MOVE_MAX 256
                    918: 
                    919: /* Define this if zero-extension is slow (more than one real instruction).  */
                    920: 
                    921: #define SLOW_ZERO_EXTEND
                    922: 
                    923: /* Nonzero if access to memory by bytes is slow and undesirable.  */
                    924: 
                    925: #define SLOW_BYTE_ACCESS 1
                    926: 
                    927: /* Define if shifts truncate the shift count which implies one can omit
                    928:    a sign-extension or zero-extension of a shift count.  */
                    929: 
                    930: /* #define SHIFT_COUNT_TRUNCATED */
                    931: 
                    932: /* Value is 1 if truncating an integer of INPREC bits to OUTPREC bits
                    933:    is done just by pretending it is already truncated.  */
                    934: 
                    935: #define TRULY_NOOP_TRUNCATION(OUTPREC, INPREC) (OUTPREC != 16)
                    936: 
                    937: /* We assume that the store-condition-codes instructions store 0 for false
                    938:    and some other value for true.  This is the value stored for true.  */
                    939: 
                    940: /* #define STORE_FLAG_VALUE -1 */
                    941: 
                    942: /* When a prototype says `char' or `short', really pass an `int'.  */
                    943: 
                    944: #define PROMOTE_PROTOTYPES
                    945: 
                    946: /* Don't perform CSE on function addresses.  */
                    947: 
                    948: #define NO_FUNCTION_CSE
                    949: 
                    950: /* Specify the machine mode that pointers have.
                    951:    After generation of rtl, the compiler makes no further distinction
                    952:    between pointers and any other objects of this machine mode.  */
                    953: 
                    954: #define Pmode SImode
                    955: 
                    956: /* A function address in a call instruction is a byte address (for
                    957:    indexing purposes) so give the MEM rtx a byte's mode.  */
                    958: 
                    959: #define FUNCTION_MODE QImode
                    960: 
                    961: /* Compute the cost of computing a constant rtl expression RTX whose
                    962:    rtx-code is CODE.  The body of this macro is a portion of a switch
                    963:    statement.  If the code is computed here, return it with a return
                    964:    statement.  Otherwise, break from the switch.  */
                    965: 
                    966: #define CONST_COSTS(RTX, CODE, OUTERCODE)                              \
                    967:   case CONST_INT:                                                      \
                    968:     if ((unsigned) INTVAL (RTX) < 0xfff) return 1;                     \
                    969:   case CONST:                                                          \
                    970:   case LABEL_REF:                                                      \
                    971:   case SYMBOL_REF:                                                     \
                    972:     return 2;                                                          \
                    973:   case CONST_DOUBLE:                                                   \
                    974:     return 4;
                    975: 
                    976: /* Tell final.c how to eliminate redundant test instructions.  */
                    977: 
                    978: /* Here we define machine-dependent flags and fields in cc_status
                    979:    (see `conditions.h').  */
                    980: 
                    981: /* Store in cc_status the expressions that the condition codes will
                    982:    describe after execution of an instruction whose pattern is EXP.
                    983:    Do not alter them if the instruction would not alter the cc's.
                    984: 
                    985:    On the 370, load insns do not alter the cc's.  However, in some
                    986:    cases these instructions can make it possibly invalid to use the
                    987:    saved cc's.  In those cases we clear out some or all of the saved
                    988:    cc's so they won't be used.  */
                    989: 
                    990: #define NOTICE_UPDATE_CC(EXP, INSN)                                    \
                    991: {                                                                      \
                    992:   rtx exp = (EXP);                                                     \
                    993:   if (GET_CODE (exp) == PARALLEL) /* Check this */                     \
                    994:     exp = XVECEXP (exp, 0, 0);                                         \
                    995:   if (GET_CODE (exp) != SET)                                           \
                    996:     CC_STATUS_INIT;                                                    \
                    997:   else                                                                 \
                    998:     {                                                                  \
                    999:       if (XEXP (exp, 0) == cc0_rtx)                                    \
                   1000:        {                                                               \
                   1001:          cc_status.value1 = XEXP (exp, 0);                             \
                   1002:          cc_status.value2 = XEXP (exp, 1);                             \
                   1003:          cc_status.flags = 0;                                          \
                   1004:        }                                                               \
                   1005:       else                                                             \
                   1006:        {                                                               \
                   1007:          if (cc_status.value1                                          \
                   1008:              && reg_mentioned_p (XEXP (exp, 0), cc_status.value1))     \
                   1009:            cc_status.value1 = 0;                                       \
                   1010:          if (cc_status.value2                                          \
                   1011:              && reg_mentioned_p (XEXP (exp, 0), cc_status.value2))     \
                   1012:            cc_status.value2 = 0;                                       \
                   1013:          switch (GET_CODE (XEXP (exp, 1)))                             \
                   1014:            {                                                           \
                   1015:              case PLUS:     case MINUS: case MULT:   /* case UMULT: */ \
                   1016:              case DIV:      case UDIV:  case NEG:    case ASHIFT:      \
                   1017:              case ASHIFTRT: case AND:   case IOR:    case XOR:         \
                   1018:              case ABS:      case NOT:                                  \
                   1019:                CC_STATUS_SET (XEXP (exp, 0), XEXP (exp, 1));           \
                   1020:            }                                                           \
                   1021:        }                                                               \
                   1022:     }                                                                  \
                   1023: }
                   1024: 
                   1025: 
                   1026: #define CC_STATUS_SET(V1, V2)                                          \
                   1027: {                                                                      \
                   1028:   cc_status.flags = 0;                                                 \
                   1029:   cc_status.value1 = (V1);                                             \
                   1030:   cc_status.value2 = (V2);                                             \
                   1031:   if (cc_status.value1                                                 \
                   1032:       && reg_mentioned_p (cc_status.value1, cc_status.value2))         \
                   1033:     cc_status.value2 = 0;                                              \
                   1034: }
                   1035: 
                   1036: #define OUTPUT_JUMP(NORMAL, FLOAT, NO_OV)                              \
                   1037: { if (cc_status.flags & CC_NO_OVERFLOW)        return NO_OV; return NORMAL; }
                   1038: 
                   1039: /* Control the assembler format that we output.  */
                   1040: 
                   1041: #define TEXT_SECTION_ASM_OP "* Program text area"
                   1042: #define DATA_SECTION_ASM_OP "* Program data area"
                   1043: #define INIT_SECTION_ASM_OP "* Program initialization area"
                   1044: #define CTOR_LIST_BEGIN                /* NO OP */
                   1045: #define CTOR_LIST_END          /* NO OP */
                   1046: 
                   1047: /* How to refer to registers in assembler output.  This sequence is
                   1048:    indexed by compiler's hard-register-number (see above).  */
                   1049: 
                   1050: #define REGISTER_NAMES                                                 \
                   1051: { "0",  "1",  "2",  "3",  "4",  "5",  "6",  "7",                       \
                   1052:   "8",  "9", "10", "11", "12", "13", "14", "15",                       \
                   1053:   "0",  "2",  "4",  "6"                                                        \
                   1054: }
                   1055: 
                   1056: /* How to renumber registers for dbx and gdb.  */
                   1057: 
                   1058: #define DBX_REGISTER_NUMBER(REGNO) (REGNO)
                   1059: 
                   1060: #define ASM_FILE_START(FILE) fputs ("\tCSECT\n", FILE);
                   1061: #define ASM_FILE_END(FILE) fputs ("\tEND\n", FILE);
                   1062: #define ASM_IDENTIFY_GCC(FILE)
                   1063: #define ASM_COMMENT_START "*"
                   1064: #define ASM_APP_OFF ""
                   1065: #define ASM_APP_ON ""
                   1066: 
                   1067: #define ASM_OUTPUT_LABEL(FILE, NAME)                                   \
                   1068: { assemble_name (FILE, NAME); fputs ("\tEQU\t*\n", FILE); }
                   1069: 
                   1070: #define ASM_OUTPUT_EXTERNAL(FILE, DECL, NAME)  /* NO OP */
                   1071: 
                   1072: #define ASM_GLOBALIZE_LABEL(FILE, NAME)                                        \
                   1073: { fputs ("\tENTRY\t", FILE); assemble_name (FILE, NAME); fputs ("\n", FILE); }
                   1074: 
                   1075: /* MVS externals are limited to 8 characters, upper case only.
                   1076:    The '_' is mapped to '@', except for MVS functions, then '#'.  */
                   1077: 
                   1078: #define MAX_MVS_LABEL_SIZE 8
                   1079: 
                   1080: #define ASM_OUTPUT_LABELREF(FILE, NAME)                                        \
                   1081: {                                                                      \
                   1082:   char *bp, ch, temp[MAX_MVS_LABEL_SIZE + 1];                          \
                   1083:   if (strlen (NAME) > MAX_MVS_LABEL_SIZE)                              \
                   1084:     {                                                                  \
                   1085:       strncpy (temp, NAME, MAX_MVS_LABEL_SIZE);                                \
                   1086:       temp[MAX_MVS_LABEL_SIZE] = '\0';                                 \
                   1087:     }                                                                  \
                   1088:   else                                                                 \
                   1089:     strcpy (temp,NAME);                                                        \
                   1090:   if (!strcmp (temp,"main"))                                           \
                   1091:     strcpy (temp,"gccmain");                                           \
                   1092:   if (mvs_function_check (temp))                                       \
                   1093:     ch = '#';                                                          \
                   1094:   else                                                                 \
                   1095:     ch = '@';                                                          \
                   1096:   for (bp = temp; *bp; bp++)                                           \
                   1097:     {                                                                  \
                   1098:       if (islower (*bp)) *bp = toupper (*bp);                          \
                   1099:       if (*bp == '_') *bp = ch;                                                \
                   1100:     }                                                                  \
                   1101:   fprintf (FILE, "%s", temp);                                          \
                   1102: }
                   1103: 
                   1104: #define ASM_GENERATE_INTERNAL_LABEL(LABEL, PREFIX, NUM)                        \
                   1105:   sprintf (LABEL, "*%s%d", PREFIX, NUM)
                   1106: 
                   1107: /* Generate internal label.  Since we can branch here from off page, we
                   1108:    must reload the base register.  */
                   1109: 
                   1110: #define ASM_OUTPUT_INTERNAL_LABEL(FILE, PREFIX, NUM)                   \
                   1111: {                                                                      \
                   1112:   if (!strcmp (PREFIX,"L"))                                            \
                   1113:     {                                                                  \
                   1114:       mvs_add_label(NUM);                                              \
1.1.1.3 ! root     1115:       mvs_label_emitted = 1;                                           \
1.1       root     1116:     }                                                                  \
                   1117:   fprintf (FILE, "%s%d\tEQU\t*\n", PREFIX, NUM);                       \
                   1118: }
                   1119: 
                   1120: /* Generate case label.  */
                   1121: 
                   1122: #define ASM_OUTPUT_CASE_LABEL(FILE, PREFIX, NUM, TABLE)                        \
                   1123:    fprintf (FILE, "%s%d\tEQU\t*\n", PREFIX, NUM)
                   1124: 
                   1125: /* This is how to output an element of a case-vector that is absolute.  */
                   1126: 
                   1127: #define ASM_OUTPUT_ADDR_VEC_ELT(FILE, VALUE)                           \
                   1128:   mvs_check_page (FILE, 4, 0);                                         \
                   1129:   fprintf (FILE, "\tDC\tA(L%d)\n", VALUE)
                   1130: 
                   1131: /* This is how to output an element of a case-vector that is relative.  */
                   1132: 
                   1133: #define ASM_OUTPUT_ADDR_DIFF_ELT(FILE, VALUE, REL)                     \
                   1134:   mvs_check_page (FILE, 4, 0);                                         \
                   1135:   fprintf (FILE, "\tDC\tA(L%d-L%d)\n", VALUE, REL)
                   1136: 
                   1137: /* This is how to output an insn to push a register on the stack.
                   1138:    It need not be very fast code.  */
                   1139: 
                   1140: #define ASM_OUTPUT_REG_PUSH(FILE, REGNO)                               \
                   1141:   mvs_check_page (FILE, 8, 4);                                         \
                   1142:   fprintf (FILE, "\tS\t13,=F'4'\n\tST\t%s,%d(13)\n",                   \
                   1143:      reg_names[REGNO], STACK_POINTER_OFFSET)
                   1144: 
                   1145: /* This is how to output an insn to pop a register from the stack.
                   1146:    It need not be very fast code.  */
                   1147: 
                   1148: #define ASM_OUTPUT_REG_POP(FILE, REGNO)                                        \
                   1149:   mvs_check_page (FILE, 8, 0);                                         \
                   1150:   fprintf (FILE, "\tL\t%s,%d(13)\n\tLA\t13,4(13)\n",                   \
                   1151:      reg_names[REGNO], STACK_POINTER_OFFSET)
                   1152: 
                   1153: /* This is how to output an assembler line defining a `double' constant.  */
                   1154: 
                   1155: #define ASM_OUTPUT_DOUBLE(FILE, VALUE)                                 \
                   1156:   fprintf (FILE, "\tDC\tD'%.18G'\n", (VALUE))
                   1157: 
                   1158: /* This is how to output an assembler line defining a `float' constant.  */
                   1159: 
                   1160: #define ASM_OUTPUT_FLOAT(FILE, VALUE)                                  \
                   1161:   fprintf (FILE, "\tDC\tE'%.9G'\n", (VALUE))
                   1162: 
                   1163: /* This outputs an integer, if not a CONST_INT must be address constant.  */
                   1164: 
                   1165: #define ASM_OUTPUT_INT(FILE, EXP)                                      \
                   1166: {                                                                      \
                   1167:   if (GET_CODE (EXP) == CONST_INT)                                     \
                   1168:     {                                                                  \
                   1169:       fprintf (FILE, "\tDC\tF'");                                      \
                   1170:       output_addr_const (FILE, EXP);                                   \
                   1171:       fprintf (FILE, "'\n");                                           \
                   1172:     }                                                                  \
                   1173:   else                                                                 \
                   1174:     {                                                                  \
                   1175:       fprintf (FILE, "\tDC\tA(");                                      \
                   1176:       output_addr_const (FILE, EXP);                                   \
                   1177:       fprintf (FILE, ")\n");                                           \
                   1178:     }                                                                  \
                   1179: }
                   1180: 
                   1181: /* This outputs a short integer.  */
                   1182: 
                   1183: #define ASM_OUTPUT_SHORT(FILE, EXP)                                    \
                   1184: {                                                                      \
1.1.1.3 ! root     1185:   fprintf (FILE, "\tDC\tX'%04X'\n", INTVAL(EXP) & 0xFFFF);             \
1.1       root     1186: }
                   1187: 
                   1188: /* This outputs a byte sized integer.  */
                   1189: 
                   1190: #define ASM_OUTPUT_CHAR(FILE, EXP)                                     \
                   1191:   fprintf (FILE, "\tDC\tX'%02X'\n", INTVAL (EXP) )
                   1192: 
                   1193: #define ASM_OUTPUT_BYTE(FILE, VALUE)                                   \
                   1194:   fprintf (FILE, "\tDC\tX'%02X'\n", VALUE)
                   1195: 
                   1196: /* This outputs a text string.  The string are chopped up to fit into
                   1197:    an 80 byte record.  Also, control and special characters, interpreted
                   1198:    by the IBM assembler, are output numerically.  */
                   1199: 
                   1200: #define MVS_ASCII_TEXT_LENGTH 48
                   1201: 
                   1202: #define ASM_OUTPUT_ASCII(FILE, PTR, LEN)                               \
                   1203: {                                                                      \
                   1204:   int i, j;                                                            \
                   1205:   int c;                                                               \
                   1206:   for (j = 0, i = 0; i < LEN; j++, i++)                                        \
                   1207:     {                                                                  \
                   1208:       c = PTR[i];                                                      \
                   1209:       if (iscntrl (c) || c == '&')                                     \
                   1210:        {                                                               \
                   1211:          if (j % MVS_ASCII_TEXT_LENGTH != 0 )                          \
                   1212:            fprintf (FILE, "'\n");                                      \
                   1213:          j = -1;                                                       \
                   1214:          if (c == '&') c = MAP_CHARACTER (c);                          \
                   1215:          fprintf (FILE, "\tDC\tX'%X'\n", c );                          \
                   1216:        }                                                               \
                   1217:       else                                                             \
                   1218:        {                                                               \
                   1219:          if (j % MVS_ASCII_TEXT_LENGTH == 0)                           \
1.1.1.3 ! root     1220:             fprintf (FILE, "\tDC\tC'");                                        \
1.1.1.2   root     1221:           if ( c == '\'' )                                             \
                   1222:            fprintf (FILE, "%c%c", c, c);                               \
                   1223:          else                                                          \
                   1224:            fprintf (FILE, "%c", c);                                    \
                   1225:          if (j % MVS_ASCII_TEXT_LENGTH == MVS_ASCII_TEXT_LENGTH - 1)   \
                   1226:            fprintf (FILE, "'\n" );                                     \
1.1       root     1227:        }                                                               \
                   1228:     }                                                                  \
                   1229:   if (j % MVS_ASCII_TEXT_LENGTH != 0)                                  \
                   1230:     fprintf (FILE, "'\n");                                             \
                   1231: }
                   1232: 
                   1233: /* This is how to output an assembler line that says to advance the
                   1234:    location counter to a multiple of 2**LOG bytes.  */
                   1235: 
                   1236: #define ASM_OUTPUT_ALIGN(FILE, LOG)                                    \
                   1237:   if (LOG)                                                             \
                   1238:     {                                                                  \
                   1239:       if ((LOG) == 1)                                                  \
                   1240:         fprintf (FILE, "\tDS\t0H\n" );                                 \
                   1241:       else                                                             \
                   1242:         fprintf (FILE, "\tDS\t0F\n" );                                 \
                   1243:     }                                                                  \
                   1244: 
                   1245: /* The maximum length of memory that the IBM assembler will allow in one
                   1246:    DS operation.  */
                   1247: 
                   1248: #define MAX_CHUNK 32767
                   1249: 
                   1250: /* A C statement to output to the stdio stream FILE an assembler
                   1251:    instruction to advance the location counter by SIZE bytes. Those
                   1252:    bytes should be zero when loaded.  */
                   1253: 
                   1254: #define ASM_OUTPUT_SKIP(FILE, SIZE)                                    \
                   1255: {                                                                      \
                   1256:   int s, k;                                                            \
                   1257:   for (s = (SIZE); s > 0; s -= MAX_CHUNK)                              \
                   1258:     {                                                                  \
                   1259:       if (s > MAX_CHUNK)                                               \
                   1260:        k = MAX_CHUNK;                                                  \
                   1261:       else                                                             \
                   1262:        k = s;                                                          \
                   1263:       fprintf (FILE, "\tDS\tXL%d\n", k);                               \
                   1264:     }                                                                  \
                   1265: }
                   1266: 
                   1267: /* A C statement (sans semicolon) to output to the stdio stream
                   1268:    FILE the assembler definition of a common-label named NAME whose
                   1269:    size is SIZE bytes.  The variable ROUNDED is the size rounded up
                   1270:    to whatever alignment the caller wants.  */
                   1271: 
                   1272: #define ASM_OUTPUT_COMMON(FILE, NAME, SIZE, ROUNDED)                   \
                   1273: {                                                                      \
                   1274:   fputs ("\tENTRY\t", FILE);                                           \
                   1275:   assemble_name (FILE, NAME);                                          \
                   1276:   fputs ("\n", FILE);                                                  \
                   1277:   fprintf (FILE, "\tDS\t0F\n");                                                \
                   1278:   ASM_OUTPUT_LABEL (FILE,NAME);                                                \
                   1279:   ASM_OUTPUT_SKIP (FILE,SIZE);                                         \
                   1280: }
                   1281: 
                   1282: /* A C statement (sans semicolon) to output to the stdio stream
                   1283:    FILE the assembler definition of a local-common-label named NAME
                   1284:    whose size is SIZE bytes.  The variable ROUNDED is the size
                   1285:    rounded up to whatever alignment the caller wants.  */
                   1286: 
                   1287: #define ASM_OUTPUT_LOCAL(FILE, NAME, SIZE, ROUNDED)                    \
                   1288: {                                                                      \
                   1289:   fprintf (FILE, "\tDS\t0F\n");                                                \
                   1290:   ASM_OUTPUT_LABEL (FILE,NAME);                                                \
                   1291:   ASM_OUTPUT_SKIP (FILE,SIZE);                                         \
                   1292: }
                   1293: 
                   1294: /* Store in OUTPUT a string (made with alloca) containing an
                   1295:    assembler-name for a local static variable named NAME.
                   1296:    LABELNO is an integer which is different for each call.  */
                   1297: 
                   1298: #define ASM_FORMAT_PRIVATE_NAME(OUTPUT, NAME, LABELNO)                 \
                   1299: {                                                                      \
                   1300:   (OUTPUT) = (char *) alloca (strlen ((NAME)) + 10);                   \
                   1301:   sprintf ((OUTPUT), "%s%d", (NAME), (LABELNO));                       \
                   1302: }
                   1303: 
                   1304: /* Define the parentheses used to group arithmetic operations
                   1305:    in assembler code.  */
                   1306: 
                   1307: #define ASM_OPEN_PAREN "("
                   1308: #define ASM_CLOSE_PAREN ")"
                   1309: 
                   1310: /* Define results of standard character escape sequences.  */
                   1311: 
                   1312: #define TARGET_BELL    47
                   1313: #define TARGET_BS      22
                   1314: #define TARGET_TAB     5
                   1315: #define TARGET_NEWLINE 21
                   1316: #define TARGET_VT      11
                   1317: #define TARGET_FF      12
                   1318: #define TARGET_CR      13
                   1319: 
                   1320: /* Print operand X (an rtx) in assembler syntax to file FILE.
                   1321:    CODE is a letter or dot (`z' in `%z0') or 0 if no letter was specified.
                   1322:    For `%' followed by punctuation, CODE is the punctuation and X is null.  */
                   1323: 
                   1324: #define PRINT_OPERAND(FILE, X, CODE)                                   \
                   1325: {                                                                      \
                   1326:   switch (GET_CODE (X))                                                        \
                   1327:     {                                                                  \
                   1328:       static char curreg[4];                                           \
                   1329:       case REG:                                                                \
                   1330:        if (CODE == 'N')                                                \
                   1331:            strcpy (curreg, reg_names[REGNO (X) + 1]);                  \
                   1332:        else                                                            \
                   1333:            strcpy (curreg, reg_names[REGNO (X)]);                      \
                   1334:        fprintf (FILE, "%s", curreg);                                   \
                   1335:        break;                                                          \
                   1336:       case MEM:                                                                \
                   1337:        {                                                               \
                   1338:          rtx addr = XEXP (X, 0);                                       \
                   1339:          if (CODE == 'O')                                              \
                   1340:            {                                                           \
                   1341:              if (GET_CODE (addr) == PLUS)                              \
                   1342:                fprintf (FILE, "%d", INTVAL (XEXP (addr, 1)));          \
                   1343:              else                                                      \
                   1344:                fprintf (FILE, "0");                                    \
                   1345:            }                                                           \
                   1346:          else if (CODE == 'R')                                         \
                   1347:            {                                                           \
                   1348:              if (GET_CODE (addr) == PLUS)                              \
                   1349:                fprintf (FILE, "%s", reg_names[REGNO (XEXP (addr, 0))]);\
                   1350:              else                                                      \
                   1351:                fprintf (FILE, "%s", reg_names[REGNO (addr)]);          \
                   1352:            }                                                           \
                   1353:          else                                                          \
                   1354:            output_address (XEXP (X, 0));                               \
                   1355:        }                                                               \
                   1356:        break;                                                          \
                   1357:       case SYMBOL_REF:                                                 \
                   1358:       case LABEL_REF:                                                  \
                   1359:        mvs_page_lit += 4;                                              \
                   1360:        if (SYMBOL_REF_FLAG (X)) fprintf (FILE, "=V(");                 \
                   1361:        else                     fprintf (FILE, "=A(");                 \
                   1362:        output_addr_const (FILE, X);                                    \
                   1363:        fprintf (FILE, ")");                                            \
                   1364:        break;                                                          \
                   1365:       case CONST_INT:                                                  \
                   1366:        if (CODE == 'B')                                                \
                   1367:          fprintf (FILE, "%d", INTVAL (X) & 0xff);                      \
                   1368:        else if (CODE == 'X')                                           \
                   1369:          fprintf (FILE, "%02X", INTVAL (X) & 0xff);                    \
                   1370:        else if (CODE == 'h')                                           \
                   1371:          fprintf (FILE, "%d", (INTVAL (X) << 16) >> 16);               \
                   1372:        else if (CODE == 'H')                                           \
                   1373:          {                                                             \
1.1.1.3 ! root     1374:            mvs_page_lit += 2;                                          \
        !          1375:            fprintf (FILE, "=H'%d'", (INTVAL (X) << 16) >> 16);         \
1.1       root     1376:          }                                                             \
                   1377:        else                                                            \
                   1378:          {                                                             \
                   1379:            mvs_page_lit += 4;                                          \
                   1380:            fprintf (FILE, "=F'%d'", INTVAL (X));                       \
                   1381:          }                                                             \
                   1382:        break;                                                          \
                   1383:       case CONST_DOUBLE:                                               \
                   1384:        if (GET_MODE (X) == DImode)                                     \
                   1385:          {                                                             \
                   1386:            if (CODE == 'M')                                            \
                   1387:              {                                                         \
                   1388:                mvs_page_lit += 4;                                      \
                   1389:                fprintf (FILE, "=XL4'%08X'", CONST_DOUBLE_LOW (X));     \
                   1390:              }                                                         \
                   1391:            else if (CODE == 'L')                                       \
                   1392:              {                                                         \
                   1393:                mvs_page_lit += 4;                                      \
                   1394:                fprintf (FILE, "=XL4'%08X'", CONST_DOUBLE_HIGH (X));    \
                   1395:              }                                                         \
                   1396:            else                                                        \
                   1397:              {                                                         \
                   1398:                mvs_page_lit += 8;                                      \
                   1399:                fprintf (FILE, "=XL8'%08X%08X'", CONST_DOUBLE_LOW (X),  \
                   1400:                        CONST_DOUBLE_HIGH (X));                         \
                   1401:              }                                                         \
                   1402:          }                                                             \
                   1403:        else                                                            \
                   1404:          {                                                             \
                   1405:            union { double d; int i[2]; } u;                            \
                   1406:            u.i[0] = CONST_DOUBLE_LOW (X);                              \
                   1407:            u.i[1] = CONST_DOUBLE_HIGH (X);                             \
                   1408:            if (GET_MODE (X) == SFmode)                                 \
                   1409:              {                                                         \
                   1410:                mvs_page_lit += 4;                                      \
                   1411:                fprintf (FILE, "=E'%.9G'", u.d);                        \
                   1412:              }                                                         \
                   1413:            else                                                        \
                   1414:              {                                                         \
                   1415:                mvs_page_lit += 8;                                      \
                   1416:                fprintf (FILE, "=D'%.18G'", u.d);                       \
                   1417:              }                                                         \
                   1418:          }                                                             \
                   1419:        break;                                                          \
                   1420:       case CONST:                                                      \
                   1421:        if (GET_CODE (XEXP (X, 0)) == PLUS                              \
                   1422:           && GET_CODE (XEXP (XEXP (X, 0), 0)) == SYMBOL_REF)           \
                   1423:          {                                                             \
                   1424:            mvs_page_lit += 4;                                          \
                   1425:            if (SYMBOL_REF_FLAG (XEXP (XEXP (X, 0), 0)))                \
                   1426:              {                                                         \
                   1427:                fprintf (FILE, "=V(");                                  \
                   1428:                ASM_OUTPUT_LABELREF (FILE,                              \
                   1429:                                  XSTR (XEXP (XEXP (X, 0), 0), 0));     \
                   1430:                fprintf (FILE, ")\n\tA\t%s,=F'%d'", curreg,             \
                   1431:                                  INTVAL (XEXP (XEXP (X, 0), 1)));      \
                   1432:              }                                                         \
                   1433:            else                                                        \
                   1434:              {                                                         \
                   1435:                fprintf (FILE, "=A(");                                  \
                   1436:                output_addr_const (FILE, X);                            \
                   1437:                fprintf (FILE, ")");                                    \
                   1438:              }                                                         \
                   1439:          }                                                             \
                   1440:        else                                                            \
                   1441:          {                                                             \
                   1442:            mvs_page_lit += 4;                                          \
                   1443:            fprintf (FILE, "=F'");                                      \
                   1444:            output_addr_const (FILE, X);                                \
                   1445:            fprintf (FILE, "'");                                        \
                   1446:          }                                                             \
                   1447:        break;                                                          \
                   1448:       default:                                                         \
                   1449:        abort();                                                        \
                   1450:     }                                                                  \
                   1451: }
                   1452: 
                   1453: #define PRINT_OPERAND_ADDRESS(FILE, ADDR)                              \
                   1454: {                                                                      \
                   1455:   rtx breg, xreg, offset, plus;                                                \
                   1456:                                                                        \
                   1457:   switch (GET_CODE (ADDR))                                             \
                   1458:     {                                                                  \
                   1459:       case REG:                                                                \
                   1460:        fprintf (FILE, "0(%s)", reg_names[REGNO (ADDR)]);               \
                   1461:        break;                                                          \
                   1462:       case PLUS:                                                       \
                   1463:        breg = 0;                                                       \
                   1464:        xreg = 0;                                                       \
                   1465:        offset = 0;                                                     \
                   1466:        if (GET_CODE (XEXP (ADDR, 0)) == PLUS)                          \
                   1467:          {                                                             \
                   1468:            if (GET_CODE (XEXP (ADDR, 1)) == REG)                       \
                   1469:              breg = XEXP (ADDR, 1);                                    \
                   1470:            else                                                        \
                   1471:              offset = XEXP (ADDR, 1);                                  \
                   1472:            plus = XEXP (ADDR, 0);                                      \
                   1473:          }                                                             \
                   1474:        else                                                            \
                   1475:          {                                                             \
                   1476:            if (GET_CODE (XEXP (ADDR, 0)) == REG)                       \
                   1477:              breg = XEXP (ADDR, 0);                                    \
                   1478:            else                                                        \
                   1479:              offset = XEXP (ADDR, 0);                                  \
                   1480:            plus = XEXP (ADDR, 1);                                      \
                   1481:          }                                                             \
                   1482:        if (GET_CODE (plus) == PLUS)                                    \
                   1483:          {                                                             \
                   1484:            if (GET_CODE (XEXP (plus, 0)) == REG)                       \
                   1485:              {                                                         \
                   1486:                if (breg)                                               \
                   1487:                  xreg = XEXP (plus, 0);                                \
                   1488:                else                                                    \
                   1489:                  breg = XEXP (plus, 0);                                \
                   1490:              }                                                         \
                   1491:            else                                                        \
                   1492:              {                                                         \
                   1493:                offset = XEXP (plus, 0);                                \
                   1494:              }                                                         \
                   1495:            if (GET_CODE (XEXP (plus, 1)) == REG)                       \
                   1496:              {                                                         \
                   1497:                if (breg)                                               \
                   1498:                  xreg = XEXP (plus, 1);                                \
                   1499:                else                                                    \
                   1500:                  breg = XEXP (plus, 1);                                \
                   1501:              }                                                         \
                   1502:            else                                                        \
                   1503:              {                                                         \
                   1504:                offset = XEXP (plus, 1);                                \
                   1505:              }                                                         \
                   1506:          }                                                             \
                   1507:        else if (GET_CODE (plus) == REG)                                \
                   1508:          {                                                             \
                   1509:            if (breg)                                                   \
                   1510:              xreg = plus;                                              \
                   1511:            else                                                        \
                   1512:              breg = plus;                                              \
                   1513:          }                                                             \
                   1514:        else                                                            \
                   1515:          {                                                             \
                   1516:            offset = plus;                                              \
                   1517:          }                                                             \
                   1518:        if (offset)                                                     \
                   1519:          {                                                             \
                   1520:            if (GET_CODE (offset) == LABEL_REF)                         \
                   1521:              fprintf (FILE, "L%d",                                     \
                   1522:                        CODE_LABEL_NUMBER (XEXP (offset, 0)));          \
                   1523:            else                                                        \
                   1524:              output_addr_const (FILE, offset);                         \
                   1525:          }                                                             \
                   1526:        else                                                            \
                   1527:          fprintf (FILE, "0");                                          \
                   1528:        if (xreg)                                                       \
                   1529:            fprintf (FILE, "(%s,%s)",                                   \
                   1530:                    reg_names[REGNO (xreg)], reg_names[REGNO (breg)]);  \
                   1531:        else                                                            \
                   1532:          fprintf (FILE, "(%s)", reg_names[REGNO (breg)]);              \
                   1533:        break;                                                          \
                   1534:       default:                                                         \
                   1535:        mvs_page_lit += 4;                                              \
                   1536:        if (SYMBOL_REF_FLAG (ADDR)) fprintf (FILE, "=V(");              \
                   1537:        else                        fprintf (FILE, "=A(");              \
                   1538:        output_addr_const (FILE, ADDR);                                 \
                   1539:        fprintf (FILE, ")");                                            \
                   1540:        break;                                                          \
                   1541:     }                                                                  \
                   1542: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.