home *** CD-ROM | disk | FTP | other *** search
GNU Info File | 1995-11-26 | 40.0 KB | 971 lines |
- This is Info file gcc.info, produced by Makeinfo-1.55 from the input
- file gcc.texi.
-
- This file documents the use and the internals of the GNU compiler.
-
- Published by the Free Software Foundation 59 Temple Place - Suite 330
- Boston, MA 02111-1307 USA
-
- Copyright (C) 1988, 1989, 1992, 1993, 1994, 1995 Free Software
- Foundation, Inc.
-
- Permission is granted to make and distribute verbatim copies of this
- manual provided the copyright notice and this permission notice are
- preserved on all copies.
-
- Permission is granted to copy and distribute modified versions of
- this manual under the conditions for verbatim copying, provided also
- that the sections entitled "GNU General Public License," "Funding for
- Free Software," and "Protect Your Freedom--Fight `Look And Feel'" are
- included exactly as in the original, and provided that the entire
- resulting derived work is distributed under the terms of a permission
- notice identical to this one.
-
- Permission is granted to copy and distribute translations of this
- manual into another language, under the above conditions for modified
- versions, except that the sections entitled "GNU General Public
- License," "Funding for Free Software," and "Protect Your Freedom--Fight
- `Look And Feel'", and this permission notice, may be included in
- translations approved by the Free Software Foundation instead of in the
- original English.
-
- File: gcc.info, Node: Machine Modes, Next: Constants, Prev: Flags, Up: RTL
-
- Machine Modes
- =============
-
- A machine mode describes a size of data object and the
- representation used for it. In the C code, machine modes are
- represented by an enumeration type, `enum machine_mode', defined in
- `machmode.def'. Each RTL expression has room for a machine mode and so
- do certain kinds of tree expressions (declarations and types, to be
- precise).
-
- In debugging dumps and machine descriptions, the machine mode of an
- RTL expression is written after the expression code with a colon to
- separate them. The letters `mode' which appear at the end of each
- machine mode name are omitted. For example, `(reg:SI 38)' is a `reg'
- expression with machine mode `SImode'. If the mode is `VOIDmode', it
- is not written at all.
-
- Here is a table of machine modes. The term "byte" below refers to an
- object of `BITS_PER_UNIT' bits (*note Storage Layout::.).
-
- `QImode'
- "Quarter-Integer" mode represents a single byte treated as an
- integer.
-
- `HImode'
- "Half-Integer" mode represents a two-byte integer.
-
- `PSImode'
- "Partial Single Integer" mode represents an integer which occupies
- four bytes but which doesn't really use all four. On some
- machines, this is the right mode to use for pointers.
-
- `SImode'
- "Single Integer" mode represents a four-byte integer.
-
- `PDImode'
- "Partial Double Integer" mode represents an integer which occupies
- eight bytes but which doesn't really use all eight. On some
- machines, this is the right mode to use for certain pointers.
-
- `DImode'
- "Double Integer" mode represents an eight-byte integer.
-
- `TImode'
- "Tetra Integer" (?) mode represents a sixteen-byte integer.
-
- `SFmode'
- "Single Floating" mode represents a single-precision (four byte)
- floating point number.
-
- `DFmode'
- "Double Floating" mode represents a double-precision (eight byte)
- floating point number.
-
- `XFmode'
- "Extended Floating" mode represents a triple-precision (twelve
- byte) floating point number. This mode is used for IEEE extended
- floating point. On some systems not all bits within these bytes
- will actually be used.
-
- `TFmode'
- "Tetra Floating" mode represents a quadruple-precision (sixteen
- byte) floating point number.
-
- `CCmode'
- "Condition Code" mode represents the value of a condition code,
- which is a machine-specific set of bits used to represent the
- result of a comparison operation. Other machine-specific modes
- may also be used for the condition code. These modes are not used
- on machines that use `cc0' (see *note Condition Code::.).
-
- `BLKmode'
- "Block" mode represents values that are aggregates to which none of
- the other modes apply. In RTL, only memory references can have
- this mode, and only if they appear in string-move or vector
- instructions. On machines which have no such instructions,
- `BLKmode' will not appear in RTL.
-
- `VOIDmode'
- Void mode means the absence of a mode or an unspecified mode. For
- example, RTL expressions of code `const_int' have mode `VOIDmode'
- because they can be taken to have whatever mode the context
- requires. In debugging dumps of RTL, `VOIDmode' is expressed by
- the absence of any mode.
-
- `SCmode, DCmode, XCmode, TCmode'
- These modes stand for a complex number represented as a pair of
- floating point values. The floating point values are in `SFmode',
- `DFmode', `XFmode', and `TFmode', respectively.
-
- `CQImode, CHImode, CSImode, CDImode, CTImode, COImode'
- These modes stand for a complex number represented as a pair of
- integer values. The integer values are in `QImode', `HImode',
- `SImode', `DImode', `TImode', and `OImode', respectively.
-
- The machine description defines `Pmode' as a C macro which expands
- into the machine mode used for addresses. Normally this is the mode
- whose size is `BITS_PER_WORD', `SImode' on 32-bit machines.
-
- The only modes which a machine description must support are
- `QImode', and the modes corresponding to `BITS_PER_WORD',
- `FLOAT_TYPE_SIZE' and `DOUBLE_TYPE_SIZE'. The compiler will attempt to
- use `DImode' for 8-byte structures and unions, but this can be
- prevented by overriding the definition of `MAX_FIXED_MODE_SIZE'.
- Alternatively, you can have the compiler use `TImode' for 16-byte
- structures and unions. Likewise, you can arrange for the C type `short
- int' to avoid using `HImode'.
-
- Very few explicit references to machine modes remain in the compiler
- and these few references will soon be removed. Instead, the machine
- modes are divided into mode classes. These are represented by the
- enumeration type `enum mode_class' defined in `machmode.h'. The
- possible mode classes are:
-
- `MODE_INT'
- Integer modes. By default these are `QImode', `HImode', `SImode',
- `DImode', and `TImode'.
-
- `MODE_PARTIAL_INT'
- The "partial integer" modes, `PSImode' and `PDImode'.
-
- `MODE_FLOAT'
- floating point modes. By default these are `SFmode', `DFmode',
- `XFmode' and `TFmode'.
-
- `MODE_COMPLEX_INT'
- Complex integer modes. (These are not currently implemented).
-
- `MODE_COMPLEX_FLOAT'
- Complex floating point modes. By default these are `SCmode',
- `DCmode', `XCmode', and `TCmode'.
-
- `MODE_FUNCTION'
- Algol or Pascal function variables including a static chain.
- (These are not currently implemented).
-
- `MODE_CC'
- Modes representing condition code values. These are `CCmode' plus
- any modes listed in the `EXTRA_CC_MODES' macro. *Note Jump
- Patterns::, also see *Note Condition Code::.
-
- `MODE_RANDOM'
- This is a catchall mode class for modes which don't fit into the
- above classes. Currently `VOIDmode' and `BLKmode' are in
- `MODE_RANDOM'.
-
- Here are some C macros that relate to machine modes:
-
- `GET_MODE (X)'
- Returns the machine mode of the RTX X.
-
- `PUT_MODE (X, NEWMODE)'
- Alters the machine mode of the RTX X to be NEWMODE.
-
- `NUM_MACHINE_MODES'
- Stands for the number of machine modes available on the target
- machine. This is one greater than the largest numeric value of any
- machine mode.
-
- `GET_MODE_NAME (M)'
- Returns the name of mode M as a string.
-
- `GET_MODE_CLASS (M)'
- Returns the mode class of mode M.
-
- `GET_MODE_WIDER_MODE (M)'
- Returns the next wider natural mode. For example, the expression
- `GET_MODE_WIDER_MODE (QImode)' returns `HImode'.
-
- `GET_MODE_SIZE (M)'
- Returns the size in bytes of a datum of mode M.
-
- `GET_MODE_BITSIZE (M)'
- Returns the size in bits of a datum of mode M.
-
- `GET_MODE_MASK (M)'
- Returns a bitmask containing 1 for all bits in a word that fit
- within mode M. This macro can only be used for modes whose
- bitsize is less than or equal to `HOST_BITS_PER_INT'.
-
- `GET_MODE_ALIGNMENT (M))'
- Return the required alignment, in bits, for an object of mode M.
-
- `GET_MODE_UNIT_SIZE (M)'
- Returns the size in bytes of the subunits of a datum of mode M.
- This is the same as `GET_MODE_SIZE' except in the case of complex
- modes. For them, the unit size is the size of the real or
- imaginary part.
-
- `GET_MODE_NUNITS (M)'
- Returns the number of units contained in a mode, i.e.,
- `GET_MODE_SIZE' divided by `GET_MODE_UNIT_SIZE'.
-
- `GET_CLASS_NARROWEST_MODE (C)'
- Returns the narrowest mode in mode class C.
-
- The global variables `byte_mode' and `word_mode' contain modes whose
- classes are `MODE_INT' and whose bitsizes are either `BITS_PER_UNIT' or
- `BITS_PER_WORD', respectively. On 32-bit machines, these are `QImode'
- and `SImode', respectively.
-
- File: gcc.info, Node: Constants, Next: Regs and Memory, Prev: Machine Modes, Up: RTL
-
- Constant Expression Types
- =========================
-
- The simplest RTL expressions are those that represent constant
- values.
-
- `(const_int I)'
- This type of expression represents the integer value I. I is
- customarily accessed with the macro `INTVAL' as in `INTVAL (EXP)',
- which is equivalent to `XWINT (EXP, 0)'.
-
- There is only one expression object for the integer value zero; it
- is the value of the variable `const0_rtx'. Likewise, the only
- expression for integer value one is found in `const1_rtx', the only
- expression for integer value two is found in `const2_rtx', and the
- only expression for integer value negative one is found in
- `constm1_rtx'. Any attempt to create an expression of code
- `const_int' and value zero, one, two or negative one will return
- `const0_rtx', `const1_rtx', `const2_rtx' or `constm1_rtx' as
- appropriate.
-
- Similarly, there is only one object for the integer whose value is
- `STORE_FLAG_VALUE'. It is found in `const_true_rtx'. If
- `STORE_FLAG_VALUE' is one, `const_true_rtx' and `const1_rtx' will
- point to the same object. If `STORE_FLAG_VALUE' is -1,
- `const_true_rtx' and `constm1_rtx' will point to the same object.
-
- `(const_double:M ADDR I0 I1 ...)'
- Represents either a floating-point constant of mode M or an
- integer constant too large to fit into `HOST_BITS_PER_WIDE_INT'
- bits but small enough to fit within twice that number of bits (GNU
- CC does not provide a mechanism to represent even larger
- constants). In the latter case, M will be `VOIDmode'.
-
- ADDR is used to contain the `mem' expression that corresponds to
- the location in memory that at which the constant can be found. If
- it has not been allocated a memory location, but is on the chain
- of all `const_double' expressions in this compilation (maintained
- using an undisplayed field), ADDR contains `const0_rtx'. If it is
- not on the chain, ADDR contains `cc0_rtx'. ADDR is customarily
- accessed with the macro `CONST_DOUBLE_MEM' and the chain field via
- `CONST_DOUBLE_CHAIN'.
-
- If M is `VOIDmode', the bits of the value are stored in I0 and I1.
- I0 is customarily accessed with the macro `CONST_DOUBLE_LOW' and
- I1 with `CONST_DOUBLE_HIGH'.
-
- If the constant is floating point (regardless of its precision),
- then the number of integers used to store the value depends on the
- size of `REAL_VALUE_TYPE' (*note Cross-compilation::.). The
- integers represent a floating point number, but not precisely in
- the target machine's or host machine's floating point format. To
- convert them to the precise bit pattern used by the target
- machine, use the macro `REAL_VALUE_TO_TARGET_DOUBLE' and friends
- (*note Data Output::.).
-
- The macro `CONST0_RTX (MODE)' refers to an expression with value 0
- in mode MODE. If mode MODE is of mode class `MODE_INT', it
- returns `const0_rtx'. Otherwise, it returns a `CONST_DOUBLE'
- expression in mode MODE. Similarly, the macro `CONST1_RTX (MODE)'
- refers to an expression with value 1 in mode MODE and similarly
- for `CONST2_RTX'.
-
- `(const_string STR)'
- Represents a constant string with value STR. Currently this is
- used only for insn attributes (*note Insn Attributes::.) since
- constant strings in C are placed in memory.
-
- `(symbol_ref:MODE SYMBOL)'
- Represents the value of an assembler label for data. SYMBOL is a
- string that describes the name of the assembler label. If it
- starts with a `*', the label is the rest of SYMBOL not including
- the `*'. Otherwise, the label is SYMBOL, usually prefixed with
- `_'.
-
- The `symbol_ref' contains a mode, which is usually `Pmode'.
- Usually that is the only mode for which a symbol is directly valid.
-
- `(label_ref LABEL)'
- Represents the value of an assembler label for code. It contains
- one operand, an expression, which must be a `code_label' that
- appears in the instruction sequence to identify the place where
- the label should go.
-
- The reason for using a distinct expression type for code label
- references is so that jump optimization can distinguish them.
-
- `(const:M EXP)'
- Represents a constant that is the result of an assembly-time
- arithmetic computation. The operand, EXP, is an expression that
- contains only constants (`const_int', `symbol_ref' and `label_ref'
- expressions) combined with `plus' and `minus'. However, not all
- combinations are valid, since the assembler cannot do arbitrary
- arithmetic on relocatable symbols.
-
- M should be `Pmode'.
-
- `(high:M EXP)'
- Represents the high-order bits of EXP, usually a `symbol_ref'.
- The number of bits is machine-dependent and is normally the number
- of bits specified in an instruction that initializes the high
- order bits of a register. It is used with `lo_sum' to represent
- the typical two-instruction sequence used in RISC machines to
- reference a global memory location.
-
- M should be `Pmode'.
-
- File: gcc.info, Node: Regs and Memory, Next: Arithmetic, Prev: Constants, Up: RTL
-
- Registers and Memory
- ====================
-
- Here are the RTL expression types for describing access to machine
- registers and to main memory.
-
- `(reg:M N)'
- For small values of the integer N (those that are less than
- `FIRST_PSEUDO_REGISTER'), this stands for a reference to machine
- register number N: a "hard register". For larger values of N, it
- stands for a temporary value or "pseudo register". The compiler's
- strategy is to generate code assuming an unlimited number of such
- pseudo registers, and later convert them into hard registers or
- into memory references.
-
- M is the machine mode of the reference. It is necessary because
- machines can generally refer to each register in more than one
- mode. For example, a register may contain a full word but there
- may be instructions to refer to it as a half word or as a single
- byte, as well as instructions to refer to it as a floating point
- number of various precisions.
-
- Even for a register that the machine can access in only one mode,
- the mode must always be specified.
-
- The symbol `FIRST_PSEUDO_REGISTER' is defined by the machine
- description, since the number of hard registers on the machine is
- an invariant characteristic of the machine. Note, however, that
- not all of the machine registers must be general registers. All
- the machine registers that can be used for storage of data are
- given hard register numbers, even those that can be used only in
- certain instructions or can hold only certain types of data.
-
- A hard register may be accessed in various modes throughout one
- function, but each pseudo register is given a natural mode and is
- accessed only in that mode. When it is necessary to describe an
- access to a pseudo register using a nonnatural mode, a `subreg'
- expression is used.
-
- A `reg' expression with a machine mode that specifies more than
- one word of data may actually stand for several consecutive
- registers. If in addition the register number specifies a
- hardware register, then it actually represents several consecutive
- hardware registers starting with the specified one.
-
- Each pseudo register number used in a function's RTL code is
- represented by a unique `reg' expression.
-
- Some pseudo register numbers, those within the range of
- `FIRST_VIRTUAL_REGISTER' to `LAST_VIRTUAL_REGISTER' only appear
- during the RTL generation phase and are eliminated before the
- optimization phases. These represent locations in the stack frame
- that cannot be determined until RTL generation for the function
- has been completed. The following virtual register numbers are
- defined:
-
- `VIRTUAL_INCOMING_ARGS_REGNUM'
- This points to the first word of the incoming arguments
- passed on the stack. Normally these arguments are placed
- there by the caller, but the callee may have pushed some
- arguments that were previously passed in registers.
-
- When RTL generation is complete, this virtual register is
- replaced by the sum of the register given by
- `ARG_POINTER_REGNUM' and the value of `FIRST_PARM_OFFSET'.
-
- `VIRTUAL_STACK_VARS_REGNUM'
- If `FRAME_GROWS_DOWNWARD' is defined, this points to
- immediately above the first variable on the stack.
- Otherwise, it points to the first variable on the stack.
-
- `VIRTUAL_STACK_VARS_REGNUM' is replaced with the sum of the
- register given by `FRAME_POINTER_REGNUM' and the value
- `STARTING_FRAME_OFFSET'.
-
- `VIRTUAL_STACK_DYNAMIC_REGNUM'
- This points to the location of dynamically allocated memory
- on the stack immediately after the stack pointer has been
- adjusted by the amount of memory desired.
-
- This virtual register is replaced by the sum of the register
- given by `STACK_POINTER_REGNUM' and the value
- `STACK_DYNAMIC_OFFSET'.
-
- `VIRTUAL_OUTGOING_ARGS_REGNUM'
- This points to the location in the stack at which outgoing
- arguments should be written when the stack is pre-pushed
- (arguments pushed using push insns should always use
- `STACK_POINTER_REGNUM').
-
- This virtual register is replaced by the sum of the register
- given by `STACK_POINTER_REGNUM' and the value
- `STACK_POINTER_OFFSET'.
-
- `(subreg:M REG WORDNUM)'
- `subreg' expressions are used to refer to a register in a machine
- mode other than its natural one, or to refer to one register of a
- multi-word `reg' that actually refers to several registers.
-
- Each pseudo-register has a natural mode. If it is necessary to
- operate on it in a different mode--for example, to perform a
- fullword move instruction on a pseudo-register that contains a
- single byte--the pseudo-register must be enclosed in a `subreg'.
- In such a case, WORDNUM is zero.
-
- Usually M is at least as narrow as the mode of REG, in which case
- it is restricting consideration to only the bits of REG that are
- in M.
-
- Sometimes M is wider than the mode of REG. These `subreg'
- expressions are often called "paradoxical". They are used in
- cases where we want to refer to an object in a wider mode but do
- not care what value the additional bits have. The reload pass
- ensures that paradoxical references are only made to hard
- registers.
-
- The other use of `subreg' is to extract the individual registers of
- a multi-register value. Machine modes such as `DImode' and
- `TImode' can indicate values longer than a word, values which
- usually require two or more consecutive registers. To access one
- of the registers, use a `subreg' with mode `SImode' and a WORDNUM
- that says which register.
-
- Storing in a non-paradoxical `subreg' has undefined results for
- bits belonging to the same word as the `subreg'. This laxity makes
- it easier to generate efficient code for such instructions. To
- represent an instruction that preserves all the bits outside of
- those in the `subreg', use `strict_low_part' around the `subreg'.
-
- The compilation parameter `WORDS_BIG_ENDIAN', if set to 1, says
- that word number zero is the most significant part; otherwise, it
- is the least significant part.
-
- Between the combiner pass and the reload pass, it is possible to
- have a paradoxical `subreg' which contains a `mem' instead of a
- `reg' as its first operand. After the reload pass, it is also
- possible to have a non-paradoxical `subreg' which contains a
- `mem'; this usually occurs when the `mem' is a stack slot which
- replaced a pseudo register.
-
- Note that it is not valid to access a `DFmode' value in `SFmode'
- using a `subreg'. On some machines the most significant part of a
- `DFmode' value does not have the same format as a single-precision
- floating value.
-
- It is also not valid to access a single word of a multi-word value
- in a hard register when less registers can hold the value than
- would be expected from its size. For example, some 32-bit
- machines have floating-point registers that can hold an entire
- `DFmode' value. If register 10 were such a register `(subreg:SI
- (reg:DF 10) 1)' would be invalid because there is no way to
- convert that reference to a single machine register. The reload
- pass prevents `subreg' expressions such as these from being formed.
-
- The first operand of a `subreg' expression is customarily accessed
- with the `SUBREG_REG' macro and the second operand is customarily
- accessed with the `SUBREG_WORD' macro.
-
- `(scratch:M)'
- This represents a scratch register that will be required for the
- execution of a single instruction and not used subsequently. It is
- converted into a `reg' by either the local register allocator or
- the reload pass.
-
- `scratch' is usually present inside a `clobber' operation (*note
- Side Effects::.).
-
- `(cc0)'
- This refers to the machine's condition code register. It has no
- operands and may not have a machine mode. There are two ways to
- use it:
-
- * To stand for a complete set of condition code flags. This is
- best on most machines, where each comparison sets the entire
- series of flags.
-
- With this technique, `(cc0)' may be validly used in only two
- contexts: as the destination of an assignment (in test and
- compare instructions) and in comparison operators comparing
- against zero (`const_int' with value zero; that is to say,
- `const0_rtx').
-
- * To stand for a single flag that is the result of a single
- condition. This is useful on machines that have only a
- single flag bit, and in which comparison instructions must
- specify the condition to test.
-
- With this technique, `(cc0)' may be validly used in only two
- contexts: as the destination of an assignment (in test and
- compare instructions) where the source is a comparison
- operator, and as the first operand of `if_then_else' (in a
- conditional branch).
-
- There is only one expression object of code `cc0'; it is the value
- of the variable `cc0_rtx'. Any attempt to create an expression of
- code `cc0' will return `cc0_rtx'.
-
- Instructions can set the condition code implicitly. On many
- machines, nearly all instructions set the condition code based on
- the value that they compute or store. It is not necessary to
- record these actions explicitly in the RTL because the machine
- description includes a prescription for recognizing the
- instructions that do so (by means of the macro
- `NOTICE_UPDATE_CC'). *Note Condition Code::. Only instructions
- whose sole purpose is to set the condition code, and instructions
- that use the condition code, need mention `(cc0)'.
-
- On some machines, the condition code register is given a register
- number and a `reg' is used instead of `(cc0)'. This is usually the
- preferable approach if only a small subset of instructions modify
- the condition code. Other machines store condition codes in
- general registers; in such cases a pseudo register should be used.
-
- Some machines, such as the Sparc and RS/6000, have two sets of
- arithmetic instructions, one that sets and one that does not set
- the condition code. This is best handled by normally generating
- the instruction that does not set the condition code, and making a
- pattern that both performs the arithmetic and sets the condition
- code register (which would not be `(cc0)' in this case). For
- examples, search for `addcc' and `andcc' in `sparc.md'.
-
- `(pc)'
- This represents the machine's program counter. It has no operands
- and may not have a machine mode. `(pc)' may be validly used only
- in certain specific contexts in jump instructions.
-
- There is only one expression object of code `pc'; it is the value
- of the variable `pc_rtx'. Any attempt to create an expression of
- code `pc' will return `pc_rtx'.
-
- All instructions that do not jump alter the program counter
- implicitly by incrementing it, but there is no need to mention
- this in the RTL.
-
- `(mem:M ADDR)'
- This RTX represents a reference to main memory at an address
- represented by the expression ADDR. M specifies how large a unit
- of memory is accessed.
-
- File: gcc.info, Node: Arithmetic, Next: Comparisons, Prev: Regs and Memory, Up: RTL
-
- RTL Expressions for Arithmetic
- ==============================
-
- Unless otherwise specified, all the operands of arithmetic
- expressions must be valid for mode M. An operand is valid for mode M
- if it has mode M, or if it is a `const_int' or `const_double' and M is
- a mode of class `MODE_INT'.
-
- For commutative binary operations, constants should be placed in the
- second operand.
-
- `(plus:M X Y)'
- Represents the sum of the values represented by X and Y carried
- out in machine mode M.
-
- `(lo_sum:M X Y)'
- Like `plus', except that it represents that sum of X and the
- low-order bits of Y. The number of low order bits is
- machine-dependent but is normally the number of bits in a `Pmode'
- item minus the number of bits set by the `high' code (*note
- Constants::.).
-
- M should be `Pmode'.
-
- `(minus:M X Y)'
- Like `plus' but represents subtraction.
-
- `(compare:M X Y)'
- Represents the result of subtracting Y from X for purposes of
- comparison. The result is computed without overflow, as if with
- infinite precision.
-
- Of course, machines can't really subtract with infinite precision.
- However, they can pretend to do so when only the sign of the
- result will be used, which is the case when the result is stored
- in the condition code. And that is the only way this kind of
- expression may validly be used: as a value to be stored in the
- condition codes.
-
- The mode M is not related to the modes of X and Y, but instead is
- the mode of the condition code value. If `(cc0)' is used, it is
- `VOIDmode'. Otherwise it is some mode in class `MODE_CC', often
- `CCmode'. *Note Condition Code::.
-
- Normally, X and Y must have the same mode. Otherwise, `compare'
- is valid only if the mode of X is in class `MODE_INT' and Y is a
- `const_int' or `const_double' with mode `VOIDmode'. The mode of X
- determines what mode the comparison is to be done in; thus it must
- not be `VOIDmode'.
-
- If one of the operands is a constant, it should be placed in the
- second operand and the comparison code adjusted as appropriate.
-
- A `compare' specifying two `VOIDmode' constants is not valid since
- there is no way to know in what mode the comparison is to be
- performed; the comparison must either be folded during the
- compilation or the first operand must be loaded into a register
- while its mode is still known.
-
- `(neg:M X)'
- Represents the negation (subtraction from zero) of the value
- represented by X, carried out in mode M.
-
- `(mult:M X Y)'
- Represents the signed product of the values represented by X and Y
- carried out in machine mode M.
-
- Some machines support a multiplication that generates a product
- wider than the operands. Write the pattern for this as
-
- (mult:M (sign_extend:M X) (sign_extend:M Y))
-
- where M is wider than the modes of X and Y, which need not be the
- same.
-
- Write patterns for unsigned widening multiplication similarly using
- `zero_extend'.
-
- `(div:M X Y)'
- Represents the quotient in signed division of X by Y, carried out
- in machine mode M. If M is a floating point mode, it represents
- the exact quotient; otherwise, the integerized quotient.
-
- Some machines have division instructions in which the operands and
- quotient widths are not all the same; you should represent such
- instructions using `truncate' and `sign_extend' as in,
-
- (truncate:M1 (div:M2 X (sign_extend:M2 Y)))
-
- `(udiv:M X Y)'
- Like `div' but represents unsigned division.
-
- `(mod:M X Y)'
- `(umod:M X Y)'
- Like `div' and `udiv' but represent the remainder instead of the
- quotient.
-
- `(smin:M X Y)'
- `(smax:M X Y)'
- Represents the smaller (for `smin') or larger (for `smax') of X
- and Y, interpreted as signed integers in mode M.
-
- `(umin:M X Y)'
- `(umax:M X Y)'
- Like `smin' and `smax', but the values are interpreted as unsigned
- integers.
-
- `(not:M X)'
- Represents the bitwise complement of the value represented by X,
- carried out in mode M, which must be a fixed-point machine mode.
-
- `(and:M X Y)'
- Represents the bitwise logical-and of the values represented by X
- and Y, carried out in machine mode M, which must be a fixed-point
- machine mode.
-
- `(ior:M X Y)'
- Represents the bitwise inclusive-or of the values represented by X
- and Y, carried out in machine mode M, which must be a fixed-point
- mode.
-
- `(xor:M X Y)'
- Represents the bitwise exclusive-or of the values represented by X
- and Y, carried out in machine mode M, which must be a fixed-point
- mode.
-
- `(ashift:M X C)'
- Represents the result of arithmetically shifting X left by C
- places. X have mode M, a fixed-point machine mode. C be a
- fixed-point mode or be a constant with mode `VOIDmode'; which mode
- is determined by the mode called for in the machine description
- entry for the left-shift instruction. For example, on the Vax,
- the mode of C is `QImode' regardless of M.
-
- `(lshiftrt:M X C)'
- `(ashiftrt:M X C)'
- Like `ashift' but for right shift. Unlike the case for left shift,
- these two operations are distinct.
-
- `(rotate:M X C)'
- `(rotatert:M X C)'
- Similar but represent left and right rotate. If C is a constant,
- use `rotate'.
-
- `(abs:M X)'
- Represents the absolute value of X, computed in mode M.
-
- `(sqrt:M X)'
- Represents the square root of X, computed in mode M. Most often M
- will be a floating point mode.
-
- `(ffs:M X)'
- Represents one plus the index of the least significant 1-bit in X,
- represented as an integer of mode M. (The value is zero if X is
- zero.) The mode of X need not be M; depending on the target
- machine, various mode combinations may be valid.
-
- File: gcc.info, Node: Comparisons, Next: Bit Fields, Prev: Arithmetic, Up: RTL
-
- Comparison Operations
- =====================
-
- Comparison operators test a relation on two operands and are
- considered to represent a machine-dependent nonzero value described by,
- but not necessarily equal to, `STORE_FLAG_VALUE' (*note Misc::.) if the
- relation holds, or zero if it does not. The mode of the comparison
- operation is independent of the mode of the data being compared. If
- the comparison operation is being tested (e.g., the first operand of an
- `if_then_else'), the mode must be `VOIDmode'. If the comparison
- operation is producing data to be stored in some variable, the mode
- must be in class `MODE_INT'. All comparison operations producing data
- must use the same mode, which is machine-specific.
-
- There are two ways that comparison operations may be used. The
- comparison operators may be used to compare the condition codes `(cc0)'
- against zero, as in `(eq (cc0) (const_int 0))'. Such a construct
- actually refers to the result of the preceding instruction in which the
- condition codes were set. The instructing setting the condition code
- must be adjacent to the instruction using the condition code; only
- `note' insns may separate them.
-
- Alternatively, a comparison operation may directly compare two data
- objects. The mode of the comparison is determined by the operands; they
- must both be valid for a common machine mode. A comparison with both
- operands constant would be invalid as the machine mode could not be
- deduced from it, but such a comparison should never exist in RTL due to
- constant folding.
-
- In the example above, if `(cc0)' were last set to `(compare X Y)',
- the comparison operation is identical to `(eq X Y)'. Usually only one
- style of comparisons is supported on a particular machine, but the
- combine pass will try to merge the operations to produce the `eq' shown
- in case it exists in the context of the particular insn involved.
-
- Inequality comparisons come in two flavors, signed and unsigned.
- Thus, there are distinct expression codes `gt' and `gtu' for signed and
- unsigned greater-than. These can produce different results for the same
- pair of integer values: for example, 1 is signed greater-than -1 but not
- unsigned greater-than, because -1 when regarded as unsigned is actually
- `0xffffffff' which is greater than 1.
-
- The signed comparisons are also used for floating point values.
- Floating point comparisons are distinguished by the machine modes of
- the operands.
-
- `(eq:M X Y)'
- 1 if the values represented by X and Y are equal, otherwise 0.
-
- `(ne:M X Y)'
- 1 if the values represented by X and Y are not equal, otherwise 0.
-
- `(gt:M X Y)'
- 1 if the X is greater than Y. If they are fixed-point, the
- comparison is done in a signed sense.
-
- `(gtu:M X Y)'
- Like `gt' but does unsigned comparison, on fixed-point numbers
- only.
-
- `(lt:M X Y)'
- `(ltu:M X Y)'
- Like `gt' and `gtu' but test for "less than".
-
- `(ge:M X Y)'
- `(geu:M X Y)'
- Like `gt' and `gtu' but test for "greater than or equal".
-
- `(le:M X Y)'
- `(leu:M X Y)'
- Like `gt' and `gtu' but test for "less than or equal".
-
- `(if_then_else COND THEN ELSE)'
- This is not a comparison operation but is listed here because it is
- always used in conjunction with a comparison operation. To be
- precise, COND is a comparison expression. This expression
- represents a choice, according to COND, between the value
- represented by THEN and the one represented by ELSE.
-
- On most machines, `if_then_else' expressions are valid only to
- express conditional jumps.
-
- `(cond [TEST1 VALUE1 TEST2 VALUE2 ...] DEFAULT)'
- Similar to `if_then_else', but more general. Each of TEST1,
- TEST2, ... is performed in turn. The result of this expression is
- the VALUE corresponding to the first non-zero test, or DEFAULT if
- none of the tests are non-zero expressions.
-
- This is currently not valid for instruction patterns and is
- supported only for insn attributes. *Note Insn Attributes::.
-
- File: gcc.info, Node: Bit Fields, Next: Conversions, Prev: Comparisons, Up: RTL
-
- Bit Fields
- ==========
-
- Special expression codes exist to represent bitfield instructions.
- These types of expressions are lvalues in RTL; they may appear on the
- left side of an assignment, indicating insertion of a value into the
- specified bit field.
-
- `(sign_extract:M LOC SIZE POS)'
- This represents a reference to a sign-extended bit field contained
- or starting in LOC (a memory or register reference). The bit field
- is SIZE bits wide and starts at bit POS. The compilation option
- `BITS_BIG_ENDIAN' says which end of the memory unit POS counts
- from.
-
- If LOC is in memory, its mode must be a single-byte integer mode.
- If LOC is in a register, the mode to use is specified by the
- operand of the `insv' or `extv' pattern (*note Standard Names::.)
- and is usually a full-word integer mode.
-
- The mode of POS is machine-specific and is also specified in the
- `insv' or `extv' pattern.
-
- The mode M is the same as the mode that would be used for LOC if
- it were a register.
-
- `(zero_extract:M LOC SIZE POS)'
- Like `sign_extract' but refers to an unsigned or zero-extended bit
- field. The same sequence of bits are extracted, but they are
- filled to an entire word with zeros instead of by sign-extension.
-
- File: gcc.info, Node: Conversions, Next: RTL Declarations, Prev: Bit Fields, Up: RTL
-
- Conversions
- ===========
-
- All conversions between machine modes must be represented by
- explicit conversion operations. For example, an expression which is
- the sum of a byte and a full word cannot be written as `(plus:SI
- (reg:QI 34) (reg:SI 80))' because the `plus' operation requires two
- operands of the same machine mode. Therefore, the byte-sized operand
- is enclosed in a conversion operation, as in
-
- (plus:SI (sign_extend:SI (reg:QI 34)) (reg:SI 80))
-
- The conversion operation is not a mere placeholder, because there
- may be more than one way of converting from a given starting mode to
- the desired final mode. The conversion operation code says how to do
- it.
-
- For all conversion operations, X must not be `VOIDmode' because the
- mode in which to do the conversion would not be known. The conversion
- must either be done at compile-time or X must be placed into a register.
-
- `(sign_extend:M X)'
- Represents the result of sign-extending the value X to machine
- mode M. M must be a fixed-point mode and X a fixed-point value of
- a mode narrower than M.
-
- `(zero_extend:M X)'
- Represents the result of zero-extending the value X to machine
- mode M. M must be a fixed-point mode and X a fixed-point value of
- a mode narrower than M.
-
- `(float_extend:M X)'
- Represents the result of extending the value X to machine mode M.
- m must be a floating point mode and X a floating point value of a
- mode narrower than M.
-
- `(truncate:M X)'
- Represents the result of truncating the value X to machine mode M.
- M must be a fixed-point mode and X a fixed-point value of a mode
- wider than M.
-
- `(float_truncate:M X)'
- Represents the result of truncating the value X to machine mode M.
- M must be a floating point mode and X a floating point value of a
- mode wider than M.
-
- `(float:M X)'
- Represents the result of converting fixed point value X, regarded
- as signed, to floating point mode M.
-
- `(unsigned_float:M X)'
- Represents the result of converting fixed point value X, regarded
- as unsigned, to floating point mode M.
-
- `(fix:M X)'
- When M is a fixed point mode, represents the result of converting
- floating point value X to mode M, regarded as signed. How
- rounding is done is not specified, so this operation may be used
- validly in compiling C code only for integer-valued operands.
-
- `(unsigned_fix:M X)'
- Represents the result of converting floating point value X to
- fixed point mode M, regarded as unsigned. How rounding is done is
- not specified.
-
- `(fix:M X)'
- When M is a floating point mode, represents the result of
- converting floating point value X (valid for mode M) to an
- integer, still represented in floating point mode M, by rounding
- towards zero.
-
- File: gcc.info, Node: RTL Declarations, Next: Side Effects, Prev: Conversions, Up: RTL
-
- Declarations
- ============
-
- Declaration expression codes do not represent arithmetic operations
- but rather state assertions about their operands.
-
- `(strict_low_part (subreg:M (reg:N R) 0))'
- This expression code is used in only one context: as the
- destination operand of a `set' expression. In addition, the
- operand of this expression must be a non-paradoxical `subreg'
- expression.
-
- The presence of `strict_low_part' says that the part of the
- register which is meaningful in mode N, but is not part of mode M,
- is not to be altered. Normally, an assignment to such a subreg is
- allowed to have undefined effects on the rest of the register when
- M is less than a word.
-
-