xref: /netbsd-src/external/gpl3/binutils.old/dist/include/opcode/cgen.h (revision e992f068c547fd6e84b3f104dc2340adcc955732)
175fd0b74Schristos /* Header file for targets using CGEN: Cpu tools GENerator.
275fd0b74Schristos 
3*e992f068Schristos    Copyright (C) 1996-2022 Free Software Foundation, Inc.
475fd0b74Schristos 
575fd0b74Schristos    This file is part of GDB, the GNU debugger, and the GNU Binutils.
675fd0b74Schristos 
775fd0b74Schristos    This program is free software; you can redistribute it and/or modify
875fd0b74Schristos    it under the terms of the GNU General Public License as published by
975fd0b74Schristos    the Free Software Foundation; either version 3 of the License, or
1075fd0b74Schristos    (at your option) any later version.
1175fd0b74Schristos 
1275fd0b74Schristos    This program is distributed in the hope that it will be useful,
1375fd0b74Schristos    but WITHOUT ANY WARRANTY; without even the implied warranty of
1475fd0b74Schristos    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
1575fd0b74Schristos    GNU General Public License for more details.
1675fd0b74Schristos 
1775fd0b74Schristos    You should have received a copy of the GNU General Public License along
1875fd0b74Schristos    with this program; if not, write to the Free Software Foundation, Inc.,
1975fd0b74Schristos    51 Franklin Street - Fifth Floor, Boston, MA 02110-1301, USA.  */
2075fd0b74Schristos 
2175fd0b74Schristos #ifndef OPCODE_CGEN_H
2275fd0b74Schristos #define OPCODE_CGEN_H
2375fd0b74Schristos 
2475fd0b74Schristos #include "symcat.h"
2575fd0b74Schristos #include "cgen/bitset.h"
2675fd0b74Schristos 
27*e992f068Schristos #include <stdint.h>
2875fd0b74Schristos 
2975fd0b74Schristos #ifdef __cplusplus
3075fd0b74Schristos extern "C" {
3175fd0b74Schristos #endif
3275fd0b74Schristos 
3375fd0b74Schristos /* ??? This file requires bfd.h but only to get bfd_vma.
3475fd0b74Schristos    Seems like an awful lot to require just to get such a fundamental type.
3575fd0b74Schristos    Perhaps the definition of bfd_vma can be moved outside of bfd.h.
3675fd0b74Schristos    Or perhaps one could duplicate its definition in another file.
3775fd0b74Schristos    Until such time, this file conditionally compiles definitions that require
3875fd0b74Schristos    bfd_vma using __BFD_H_SEEN__.  */
3975fd0b74Schristos 
4075fd0b74Schristos /* Enums must be defined before they can be used.
4175fd0b74Schristos    Allow them to be used in struct definitions, even though the enum must
4275fd0b74Schristos    be defined elsewhere.
4375fd0b74Schristos    If CGEN_ARCH isn't defined, this file is being included by something other
4475fd0b74Schristos    than <arch>-desc.h.  */
4575fd0b74Schristos 
4675fd0b74Schristos /* Prepend the arch name, defined in <arch>-desc.h, and _cgen_ to symbol S.
4775fd0b74Schristos    The lack of spaces in the arg list is important for non-stdc systems.
4875fd0b74Schristos    This file is included by <arch>-desc.h.
4975fd0b74Schristos    It can be included independently of <arch>-desc.h, in which case the arch
5075fd0b74Schristos    dependent portions will be declared as "unknown_cgen_foo".  */
5175fd0b74Schristos 
5275fd0b74Schristos #ifndef CGEN_SYM
5375fd0b74Schristos #define CGEN_SYM(s) CONCAT3 (unknown,_cgen_,s)
5475fd0b74Schristos #endif
5575fd0b74Schristos 
5675fd0b74Schristos /* This file contains the static (unchanging) pieces and as much other stuff
5775fd0b74Schristos    as we can reasonably put here.  It's generally cleaner to put stuff here
5875fd0b74Schristos    rather than having it machine generated if possible.  */
5975fd0b74Schristos 
6075fd0b74Schristos /* The assembler syntax is made up of expressions (duh...).
6175fd0b74Schristos    At the lowest level the values are mnemonics, register names, numbers, etc.
6275fd0b74Schristos    Above that are subexpressions, if any (an example might be the
6375fd0b74Schristos    "effective address" in m68k cpus).  Subexpressions are wip.
6475fd0b74Schristos    At the second highest level are the insns themselves.  Above that are
6575fd0b74Schristos    pseudo-insns, synthetic insns, and macros, if any.  */
6675fd0b74Schristos 
6775fd0b74Schristos /* Lots of cpu's have a fixed insn size, or one which rarely changes,
6875fd0b74Schristos    and it's generally easier to handle these by treating the insn as an
6975fd0b74Schristos    integer type, rather than an array of characters.  So we allow targets
7075fd0b74Schristos    to control this.  When an integer type the value is in host byte order,
7175fd0b74Schristos    when an array of characters the value is in target byte order.  */
7275fd0b74Schristos 
7375fd0b74Schristos typedef unsigned int CGEN_INSN_INT;
7475fd0b74Schristos typedef int64_t CGEN_INSN_LGSINT; /* large/long SINT */
7575fd0b74Schristos typedef uint64_t CGEN_INSN_LGUINT; /* large/long UINT */
7675fd0b74Schristos 
7775fd0b74Schristos #if CGEN_INT_INSN_P
7875fd0b74Schristos typedef CGEN_INSN_INT CGEN_INSN_BYTES;
7975fd0b74Schristos typedef CGEN_INSN_INT *CGEN_INSN_BYTES_PTR;
8075fd0b74Schristos #else
8175fd0b74Schristos typedef unsigned char *CGEN_INSN_BYTES;
8275fd0b74Schristos typedef unsigned char *CGEN_INSN_BYTES_PTR;
8375fd0b74Schristos #endif
8475fd0b74Schristos 
8575fd0b74Schristos #ifdef __GNUC__
8675fd0b74Schristos #define CGEN_INLINE __inline__
8775fd0b74Schristos #else
8875fd0b74Schristos #define CGEN_INLINE
8975fd0b74Schristos #endif
9075fd0b74Schristos 
9175fd0b74Schristos enum cgen_endian
9275fd0b74Schristos {
9375fd0b74Schristos   CGEN_ENDIAN_UNKNOWN,
9475fd0b74Schristos   CGEN_ENDIAN_LITTLE,
9575fd0b74Schristos   CGEN_ENDIAN_BIG
9675fd0b74Schristos };
9775fd0b74Schristos 
9875fd0b74Schristos /* Forward decl.  */
9975fd0b74Schristos 
10075fd0b74Schristos typedef struct cgen_insn CGEN_INSN;
10175fd0b74Schristos 
10275fd0b74Schristos /* Opaque pointer version for use by external world.  */
10375fd0b74Schristos 
10475fd0b74Schristos typedef struct cgen_cpu_desc *CGEN_CPU_DESC;
10575fd0b74Schristos 
10675fd0b74Schristos /* Attributes.
10775fd0b74Schristos    Attributes are used to describe various random things associated with
10875fd0b74Schristos    an object (ifield, hardware, operand, insn, whatever) and are specified
10975fd0b74Schristos    as name/value pairs.
11075fd0b74Schristos    Integer attributes computed at compile time are currently all that's
11175fd0b74Schristos    supported, though adding string attributes and run-time computation is
11275fd0b74Schristos    straightforward.  Integer attribute values are always host int's
11375fd0b74Schristos    (signed or unsigned).  For portability, this means 32 bits.
11475fd0b74Schristos    Integer attributes are further categorized as boolean, bitset, integer,
11575fd0b74Schristos    and enum types.  Boolean attributes appear frequently enough that they're
11675fd0b74Schristos    recorded in one host int.  This limits the maximum number of boolean
11775fd0b74Schristos    attributes to 32, though that's a *lot* of attributes.  */
11875fd0b74Schristos 
11975fd0b74Schristos /* Type of attribute values.  */
12075fd0b74Schristos 
12175fd0b74Schristos typedef CGEN_BITSET     CGEN_ATTR_VALUE_BITSET_TYPE;
12275fd0b74Schristos typedef int             CGEN_ATTR_VALUE_ENUM_TYPE;
12375fd0b74Schristos typedef union
12475fd0b74Schristos {
12575fd0b74Schristos   CGEN_ATTR_VALUE_BITSET_TYPE bitset;
12675fd0b74Schristos   CGEN_ATTR_VALUE_ENUM_TYPE   nonbitset;
12775fd0b74Schristos } CGEN_ATTR_VALUE_TYPE;
12875fd0b74Schristos 
12975fd0b74Schristos /* Struct to record attribute information.  */
13075fd0b74Schristos 
13175fd0b74Schristos typedef struct
13275fd0b74Schristos {
13375fd0b74Schristos   /* Boolean attributes.  */
13475fd0b74Schristos   unsigned int bool_;
13575fd0b74Schristos   /* Non-boolean integer attributes.  */
13675fd0b74Schristos   CGEN_ATTR_VALUE_TYPE nonbool[1];
13775fd0b74Schristos } CGEN_ATTR;
13875fd0b74Schristos 
13975fd0b74Schristos /* Define a structure member for attributes with N non-boolean entries.
14075fd0b74Schristos    There is no maximum number of non-boolean attributes.
14175fd0b74Schristos    There is a maximum of 32 boolean attributes (since they are all recorded
14275fd0b74Schristos    in one host int).  */
14375fd0b74Schristos 
14475fd0b74Schristos #define CGEN_ATTR_TYPE(n) \
14575fd0b74Schristos struct { unsigned int bool_; \
14675fd0b74Schristos 	 CGEN_ATTR_VALUE_TYPE nonbool[(n) ? (n) : 1]; }
14775fd0b74Schristos 
14875fd0b74Schristos /* Return the boolean attributes.  */
14975fd0b74Schristos 
15075fd0b74Schristos #define CGEN_ATTR_BOOLS(a) ((a)->bool_)
15175fd0b74Schristos 
15275fd0b74Schristos /* Non-boolean attribute numbers are offset by this much.  */
15375fd0b74Schristos 
15475fd0b74Schristos #define CGEN_ATTR_NBOOL_OFFSET 32
15575fd0b74Schristos 
15675fd0b74Schristos /* Given a boolean attribute number, return its mask.  */
15775fd0b74Schristos 
15875fd0b74Schristos #define CGEN_ATTR_MASK(attr) (1 << (attr))
15975fd0b74Schristos 
16075fd0b74Schristos /* Return the value of boolean attribute ATTR in ATTRS.  */
16175fd0b74Schristos 
16275fd0b74Schristos #define CGEN_BOOL_ATTR(attrs, attr) ((CGEN_ATTR_MASK (attr) & (attrs)) != 0)
16375fd0b74Schristos 
16475fd0b74Schristos /* Return value of attribute ATTR in ATTR_TABLE for OBJ.
16575fd0b74Schristos    OBJ is a pointer to the entity that has the attributes
16675fd0b74Schristos    (??? not used at present but is reserved for future purposes - eventually
16775fd0b74Schristos    the goal is to allow recording attributes in source form and computing
16875fd0b74Schristos    them lazily at runtime, not sure of the details yet).  */
16975fd0b74Schristos 
17075fd0b74Schristos #define CGEN_ATTR_VALUE(obj, attr_table, attr) \
17175fd0b74Schristos ((unsigned int) (attr) < CGEN_ATTR_NBOOL_OFFSET \
17275fd0b74Schristos  ? ((CGEN_ATTR_BOOLS (attr_table) & CGEN_ATTR_MASK (attr)) != 0) \
17375fd0b74Schristos  : ((attr_table)->nonbool[(attr) - CGEN_ATTR_NBOOL_OFFSET].nonbitset))
17475fd0b74Schristos #define CGEN_BITSET_ATTR_VALUE(obj, attr_table, attr) \
17575fd0b74Schristos  ((attr_table)->nonbool[(attr) - CGEN_ATTR_NBOOL_OFFSET].bitset)
17675fd0b74Schristos 
17775fd0b74Schristos /* Attribute name/value tables.
17875fd0b74Schristos    These are used to assist parsing of descriptions at run-time.  */
17975fd0b74Schristos 
18075fd0b74Schristos typedef struct
18175fd0b74Schristos {
18275fd0b74Schristos   const char * name;
18375fd0b74Schristos   unsigned value;
18475fd0b74Schristos } CGEN_ATTR_ENTRY;
18575fd0b74Schristos 
18675fd0b74Schristos /* For each domain (ifld,hw,operand,insn), list of attributes.  */
18775fd0b74Schristos 
18875fd0b74Schristos typedef struct
18975fd0b74Schristos {
19075fd0b74Schristos   const char * name;
19175fd0b74Schristos   const CGEN_ATTR_ENTRY * dfault;
19275fd0b74Schristos   const CGEN_ATTR_ENTRY * vals;
19375fd0b74Schristos } CGEN_ATTR_TABLE;
19475fd0b74Schristos 
19575fd0b74Schristos /* Instruction set variants.  */
19675fd0b74Schristos 
19775fd0b74Schristos typedef struct {
19875fd0b74Schristos   const char *name;
19975fd0b74Schristos 
20075fd0b74Schristos   /* Default instruction size (in bits).
20175fd0b74Schristos      This is used by the assembler when it encounters an unknown insn.  */
20275fd0b74Schristos   unsigned int default_insn_bitsize;
20375fd0b74Schristos 
20475fd0b74Schristos   /* Base instruction size (in bits).
20575fd0b74Schristos      For non-LIW cpus this is generally the length of the smallest insn.
20675fd0b74Schristos      For LIW cpus its wip (work-in-progress).  For the m32r its 32.  */
20775fd0b74Schristos   unsigned int base_insn_bitsize;
20875fd0b74Schristos 
20975fd0b74Schristos   /* Minimum/maximum instruction size (in bits).  */
21075fd0b74Schristos   unsigned int min_insn_bitsize;
21175fd0b74Schristos   unsigned int max_insn_bitsize;
21275fd0b74Schristos } CGEN_ISA;
21375fd0b74Schristos 
21475fd0b74Schristos /* Machine variants.  */
21575fd0b74Schristos 
21675fd0b74Schristos typedef struct {
21775fd0b74Schristos   const char *name;
21875fd0b74Schristos   /* The argument to bfd_arch_info->scan.  */
21975fd0b74Schristos   const char *bfd_name;
22075fd0b74Schristos   /* one of enum mach_attr */
22175fd0b74Schristos   int num;
22275fd0b74Schristos   /* parameter from mach->cpu */
22375fd0b74Schristos   unsigned int insn_chunk_bitsize;
22475fd0b74Schristos } CGEN_MACH;
22575fd0b74Schristos 
22675fd0b74Schristos /* Parse result (also extraction result).
22775fd0b74Schristos 
22875fd0b74Schristos    The result of parsing an insn is stored here.
22975fd0b74Schristos    To generate the actual insn, this is passed to the insert handler.
23075fd0b74Schristos    When printing an insn, the result of extraction is stored here.
23175fd0b74Schristos    To print the insn, this is passed to the print handler.
23275fd0b74Schristos 
23375fd0b74Schristos    It is machine generated so we don't define it here,
23475fd0b74Schristos    but we do need a forward decl for the handler fns.
23575fd0b74Schristos 
23675fd0b74Schristos    There is one member for each possible field in the insn.
23775fd0b74Schristos    The type depends on the field.
23875fd0b74Schristos    Also recorded here is the computed length of the insn for architectures
23975fd0b74Schristos    where it varies.
24075fd0b74Schristos */
24175fd0b74Schristos 
24275fd0b74Schristos typedef struct cgen_fields CGEN_FIELDS;
24375fd0b74Schristos 
24475fd0b74Schristos /* Total length of the insn, as recorded in the `fields' struct.  */
24575fd0b74Schristos /* ??? The field insert handler has lots of opportunities for optimization
24675fd0b74Schristos    if it ever gets inlined.  On architectures where insns all have the same
24775fd0b74Schristos    size, may wish to detect that and make this macro a constant - to allow
24875fd0b74Schristos    further optimizations.  */
24975fd0b74Schristos 
25075fd0b74Schristos #define CGEN_FIELDS_BITSIZE(fields) ((fields)->length)
25175fd0b74Schristos 
25275fd0b74Schristos /* Extraction support for variable length insn sets.  */
25375fd0b74Schristos 
25475fd0b74Schristos /* When disassembling we don't know the number of bytes to read at the start.
25575fd0b74Schristos    So the first CGEN_BASE_INSN_SIZE bytes are read at the start and the rest
25675fd0b74Schristos    are read when needed.  This struct controls this.  It is basically the
25775fd0b74Schristos    disassemble_info stuff, except that we provide a cache for values already
25875fd0b74Schristos    read (since bytes can typically be read several times to fetch multiple
25975fd0b74Schristos    operands that may be in them), and that extraction of fields is needed
26075fd0b74Schristos    in contexts other than disassembly.  */
26175fd0b74Schristos 
26275fd0b74Schristos typedef struct {
26375fd0b74Schristos   /* A pointer to the disassemble_info struct.
26475fd0b74Schristos      We don't require dis-asm.h so we use void * for the type here.
26575fd0b74Schristos      If NULL, BYTES is full of valid data (VALID == -1).  */
26675fd0b74Schristos   void *dis_info;
26775fd0b74Schristos   /* Points to a working buffer of sufficient size.  */
26875fd0b74Schristos   unsigned char *insn_bytes;
26975fd0b74Schristos   /* Mask of bytes that are valid in INSN_BYTES.  */
27075fd0b74Schristos   unsigned int valid;
27175fd0b74Schristos } CGEN_EXTRACT_INFO;
27275fd0b74Schristos 
27375fd0b74Schristos /* Associated with each insn or expression is a set of "handlers" for
27475fd0b74Schristos    performing operations like parsing, printing, etc.  These require a bfd_vma
27575fd0b74Schristos    value to be passed around but we don't want all applications to need bfd.h.
27675fd0b74Schristos    So this stuff is only provided if bfd.h has been included.  */
27775fd0b74Schristos 
27875fd0b74Schristos /* Parse handler.
27975fd0b74Schristos    CD is a cpu table descriptor.
28075fd0b74Schristos    INSN is a pointer to a struct describing the insn being parsed.
28175fd0b74Schristos    STRP is a pointer to a pointer to the text being parsed.
28275fd0b74Schristos    FIELDS is a pointer to a cgen_fields struct in which the results are placed.
28375fd0b74Schristos    If the expression is successfully parsed, *STRP is updated.
28475fd0b74Schristos    If not it is left alone.
28575fd0b74Schristos    The result is NULL if success or an error message.  */
28675fd0b74Schristos typedef const char * (cgen_parse_fn)
28775fd0b74Schristos   (CGEN_CPU_DESC, const CGEN_INSN *insn_,
28875fd0b74Schristos    const char **strp_, CGEN_FIELDS *fields_);
28975fd0b74Schristos 
29075fd0b74Schristos /* Insert handler.
29175fd0b74Schristos    CD is a cpu table descriptor.
29275fd0b74Schristos    INSN is a pointer to a struct describing the insn being parsed.
29375fd0b74Schristos    FIELDS is a pointer to a cgen_fields struct from which the values
29475fd0b74Schristos    are fetched.
29575fd0b74Schristos    INSNP is a pointer to a buffer in which to place the insn.
29675fd0b74Schristos    PC is the pc value of the insn.
29775fd0b74Schristos    The result is an error message or NULL if success.  */
29875fd0b74Schristos 
29975fd0b74Schristos #ifdef __BFD_H_SEEN__
30075fd0b74Schristos typedef const char * (cgen_insert_fn)
30175fd0b74Schristos   (CGEN_CPU_DESC, const CGEN_INSN *insn_,
30275fd0b74Schristos    CGEN_FIELDS *fields_, CGEN_INSN_BYTES_PTR insnp_,
30375fd0b74Schristos    bfd_vma pc_);
30475fd0b74Schristos #else
30575fd0b74Schristos typedef const char * (cgen_insert_fn) ();
30675fd0b74Schristos #endif
30775fd0b74Schristos 
30875fd0b74Schristos /* Extract handler.
30975fd0b74Schristos    CD is a cpu table descriptor.
31075fd0b74Schristos    INSN is a pointer to a struct describing the insn being parsed.
31175fd0b74Schristos    The second argument is a pointer to a struct controlling extraction
31275fd0b74Schristos    (only used for variable length insns).
31375fd0b74Schristos    EX_INFO is a pointer to a struct for controlling reading of further
31475fd0b74Schristos    bytes for the insn.
31575fd0b74Schristos    BASE_INSN is the first CGEN_BASE_INSN_SIZE bytes (host order).
31675fd0b74Schristos    FIELDS is a pointer to a cgen_fields struct in which the results are placed.
31775fd0b74Schristos    PC is the pc value of the insn.
31875fd0b74Schristos    The result is the length of the insn in bits or zero if not recognized.  */
31975fd0b74Schristos 
32075fd0b74Schristos #ifdef __BFD_H_SEEN__
32175fd0b74Schristos typedef int (cgen_extract_fn)
32275fd0b74Schristos   (CGEN_CPU_DESC, const CGEN_INSN *insn_,
32375fd0b74Schristos    CGEN_EXTRACT_INFO *ex_info_, CGEN_INSN_INT base_insn_,
32475fd0b74Schristos    CGEN_FIELDS *fields_, bfd_vma pc_);
32575fd0b74Schristos #else
32675fd0b74Schristos typedef int (cgen_extract_fn) ();
32775fd0b74Schristos #endif
32875fd0b74Schristos 
32975fd0b74Schristos /* Print handler.
33075fd0b74Schristos    CD is a cpu table descriptor.
33175fd0b74Schristos    INFO is a pointer to the disassembly info.
33275fd0b74Schristos    Eg: disassemble_info.  It's defined as `PTR' so this file can be included
33375fd0b74Schristos    without dis-asm.h.
33475fd0b74Schristos    INSN is a pointer to a struct describing the insn being printed.
33575fd0b74Schristos    FIELDS is a pointer to a cgen_fields struct.
33675fd0b74Schristos    PC is the pc value of the insn.
33775fd0b74Schristos    LEN is the length of the insn, in bits.  */
33875fd0b74Schristos 
33975fd0b74Schristos #ifdef __BFD_H_SEEN__
34075fd0b74Schristos typedef void (cgen_print_fn)
34175fd0b74Schristos   (CGEN_CPU_DESC, void * info_, const CGEN_INSN *insn_,
34275fd0b74Schristos    CGEN_FIELDS *fields_, bfd_vma pc_, int len_);
34375fd0b74Schristos #else
34475fd0b74Schristos typedef void (cgen_print_fn) ();
34575fd0b74Schristos #endif
34675fd0b74Schristos 
34775fd0b74Schristos /* Parse/insert/extract/print handlers.
34875fd0b74Schristos 
34975fd0b74Schristos    Indices into the handler tables.
35075fd0b74Schristos    We could use pointers here instead, but 90% of them are generally identical
35175fd0b74Schristos    and that's a lot of redundant data.  Making these unsigned char indices
35275fd0b74Schristos    into tables of pointers saves a bit of space.
35375fd0b74Schristos    Using indices also keeps assembler code out of the disassembler and
35475fd0b74Schristos    vice versa.  */
35575fd0b74Schristos 
35675fd0b74Schristos struct cgen_opcode_handler
35775fd0b74Schristos {
35875fd0b74Schristos   unsigned char parse, insert, extract, print;
35975fd0b74Schristos };
36075fd0b74Schristos 
36175fd0b74Schristos /* Assembler interface.
36275fd0b74Schristos 
36375fd0b74Schristos    The interface to the assembler is intended to be clean in the sense that
36475fd0b74Schristos    libopcodes.a is a standalone entity and could be used with any assembler.
36575fd0b74Schristos    Not that one would necessarily want to do that but rather that it helps
36675fd0b74Schristos    keep a clean interface.  The interface will obviously be slanted towards
36775fd0b74Schristos    GAS, but at least it's a start.
36875fd0b74Schristos    ??? Note that one possible user of the assembler besides GAS is GDB.
36975fd0b74Schristos 
37075fd0b74Schristos    Parsing is controlled by the assembler which calls
37175fd0b74Schristos    CGEN_SYM (assemble_insn).  If it can parse and build the entire insn
37275fd0b74Schristos    it doesn't call back to the assembler.  If it needs/wants to call back
37375fd0b74Schristos    to the assembler, cgen_parse_operand_fn is called which can either
37475fd0b74Schristos 
37575fd0b74Schristos    - return a number to be inserted in the insn
37675fd0b74Schristos    - return a "register" value to be inserted
37775fd0b74Schristos      (the register might not be a register per pe)
37875fd0b74Schristos    - queue the argument and return a marker saying the expression has been
37975fd0b74Schristos      queued (eg: a fix-up)
38075fd0b74Schristos    - return an error message indicating the expression wasn't recognizable
38175fd0b74Schristos 
38275fd0b74Schristos    The result is an error message or NULL for success.
38375fd0b74Schristos    The parsed value is stored in the bfd_vma *.  */
38475fd0b74Schristos 
38575fd0b74Schristos /* Values for indicating what the caller wants.  */
38675fd0b74Schristos 
38775fd0b74Schristos enum cgen_parse_operand_type
38875fd0b74Schristos {
38975fd0b74Schristos   CGEN_PARSE_OPERAND_INIT,
39075fd0b74Schristos   CGEN_PARSE_OPERAND_INTEGER,
39175fd0b74Schristos   CGEN_PARSE_OPERAND_ADDRESS,
39275fd0b74Schristos   CGEN_PARSE_OPERAND_SYMBOLIC
39375fd0b74Schristos };
39475fd0b74Schristos 
39575fd0b74Schristos /* Values for indicating what was parsed.  */
39675fd0b74Schristos 
39775fd0b74Schristos enum cgen_parse_operand_result
39875fd0b74Schristos {
39975fd0b74Schristos   CGEN_PARSE_OPERAND_RESULT_NUMBER,
40075fd0b74Schristos   CGEN_PARSE_OPERAND_RESULT_REGISTER,
40175fd0b74Schristos   CGEN_PARSE_OPERAND_RESULT_QUEUED,
40275fd0b74Schristos   CGEN_PARSE_OPERAND_RESULT_ERROR
40375fd0b74Schristos };
40475fd0b74Schristos 
40575fd0b74Schristos #ifdef __BFD_H_SEEN__ /* Don't require bfd.h unnecessarily.  */
40675fd0b74Schristos typedef const char * (cgen_parse_operand_fn)
40775fd0b74Schristos   (CGEN_CPU_DESC,
40875fd0b74Schristos    enum cgen_parse_operand_type, const char **, int, int,
40975fd0b74Schristos    enum cgen_parse_operand_result *, bfd_vma *);
41075fd0b74Schristos #else
41175fd0b74Schristos typedef const char * (cgen_parse_operand_fn) ();
41275fd0b74Schristos #endif
41375fd0b74Schristos 
41475fd0b74Schristos /* Set the cgen_parse_operand_fn callback.  */
41575fd0b74Schristos 
41675fd0b74Schristos extern void cgen_set_parse_operand_fn
41775fd0b74Schristos   (CGEN_CPU_DESC, cgen_parse_operand_fn);
41875fd0b74Schristos 
41975fd0b74Schristos /* Called before trying to match a table entry with the insn.  */
42075fd0b74Schristos 
42175fd0b74Schristos extern void cgen_init_parse_operand (CGEN_CPU_DESC);
42275fd0b74Schristos 
42375fd0b74Schristos /* Operand values (keywords, integers, symbols, etc.)  */
42475fd0b74Schristos 
42575fd0b74Schristos /* Types of assembler elements.  */
42675fd0b74Schristos 
42775fd0b74Schristos enum cgen_asm_type
42875fd0b74Schristos {
42975fd0b74Schristos   CGEN_ASM_NONE, CGEN_ASM_KEYWORD, CGEN_ASM_MAX
43075fd0b74Schristos };
43175fd0b74Schristos 
43275fd0b74Schristos #ifndef CGEN_ARCH
43375fd0b74Schristos enum cgen_hw_type { CGEN_HW_MAX };
43475fd0b74Schristos #endif
43575fd0b74Schristos 
43675fd0b74Schristos /* List of hardware elements.  */
43775fd0b74Schristos 
43875fd0b74Schristos typedef struct
43975fd0b74Schristos {
44075fd0b74Schristos   char *name;
44175fd0b74Schristos   enum cgen_hw_type type;
44275fd0b74Schristos   /* There is currently no example where both index specs and value specs
44375fd0b74Schristos      are required, so for now both are clumped under "asm_data".  */
44475fd0b74Schristos   enum cgen_asm_type asm_type;
44575fd0b74Schristos   void *asm_data;
44675fd0b74Schristos #ifndef CGEN_HW_NBOOL_ATTRS
44775fd0b74Schristos #define CGEN_HW_NBOOL_ATTRS 1
44875fd0b74Schristos #endif
44975fd0b74Schristos   CGEN_ATTR_TYPE (CGEN_HW_NBOOL_ATTRS) attrs;
45075fd0b74Schristos #define CGEN_HW_ATTRS(hw) (&(hw)->attrs)
45175fd0b74Schristos } CGEN_HW_ENTRY;
45275fd0b74Schristos 
45375fd0b74Schristos /* Return value of attribute ATTR in HW.  */
45475fd0b74Schristos 
45575fd0b74Schristos #define CGEN_HW_ATTR_VALUE(hw, attr) \
45675fd0b74Schristos CGEN_ATTR_VALUE ((hw), CGEN_HW_ATTRS (hw), (attr))
45775fd0b74Schristos 
45875fd0b74Schristos /* Table of hardware elements for selected mach, computed at runtime.
45975fd0b74Schristos    enum cgen_hw_type is an index into this table (specifically `entries').  */
46075fd0b74Schristos 
46175fd0b74Schristos typedef struct {
46275fd0b74Schristos   /* Pointer to null terminated table of all compiled in entries.  */
46375fd0b74Schristos   const CGEN_HW_ENTRY *init_entries;
46475fd0b74Schristos   unsigned int entry_size; /* since the attribute member is variable sized */
46575fd0b74Schristos   /* Array of all entries, initial and run-time added.  */
46675fd0b74Schristos   const CGEN_HW_ENTRY **entries;
46775fd0b74Schristos   /* Number of elements in `entries'.  */
46875fd0b74Schristos   unsigned int num_entries;
46975fd0b74Schristos   /* For now, xrealloc is called each time a new entry is added at runtime.
47075fd0b74Schristos      ??? May wish to keep track of some slop to reduce the number of calls to
47175fd0b74Schristos      xrealloc, except that there's unlikely to be many and not expected to be
47275fd0b74Schristos      in speed critical code.  */
47375fd0b74Schristos } CGEN_HW_TABLE;
47475fd0b74Schristos 
47575fd0b74Schristos extern const CGEN_HW_ENTRY * cgen_hw_lookup_by_name
47675fd0b74Schristos   (CGEN_CPU_DESC, const char *);
47775fd0b74Schristos extern const CGEN_HW_ENTRY * cgen_hw_lookup_by_num
47875fd0b74Schristos   (CGEN_CPU_DESC, unsigned int);
47975fd0b74Schristos 
48075fd0b74Schristos /* This struct is used to describe things like register names, etc.  */
48175fd0b74Schristos 
48275fd0b74Schristos typedef struct cgen_keyword_entry
48375fd0b74Schristos {
48475fd0b74Schristos   /* Name (as in register name).  */
48575fd0b74Schristos   char * name;
48675fd0b74Schristos 
48775fd0b74Schristos   /* Value (as in register number).
48875fd0b74Schristos      The value cannot be -1 as that is used to indicate "not found".
48975fd0b74Schristos      IDEA: Have "FUNCTION" attribute? [function is called to fetch value].  */
49075fd0b74Schristos   int value;
49175fd0b74Schristos 
49275fd0b74Schristos   /* Attributes.
49375fd0b74Schristos      This should, but technically needn't, appear last.  It is a variable sized
49475fd0b74Schristos      array in that one architecture may have 1 nonbool attribute and another
49575fd0b74Schristos      may have more.  Having this last means the non-architecture specific code
49675fd0b74Schristos      needn't care.  The goal is to eventually record
49775fd0b74Schristos      attributes in their raw form, evaluate them at run-time, and cache the
49875fd0b74Schristos      values, so this worry will go away anyway.  */
49975fd0b74Schristos   /* ??? Moving this last should be done by treating keywords like insn lists
50075fd0b74Schristos      and moving the `next' fields into a CGEN_KEYWORD_LIST struct.  */
50175fd0b74Schristos   /* FIXME: Not used yet.  */
50275fd0b74Schristos #ifndef CGEN_KEYWORD_NBOOL_ATTRS
50375fd0b74Schristos #define CGEN_KEYWORD_NBOOL_ATTRS 1
50475fd0b74Schristos #endif
50575fd0b74Schristos   CGEN_ATTR_TYPE (CGEN_KEYWORD_NBOOL_ATTRS) attrs;
50675fd0b74Schristos 
50775fd0b74Schristos   /* ??? Putting these here means compiled in entries can't be const.
50875fd0b74Schristos      Not a really big deal, but something to consider.  */
50975fd0b74Schristos   /* Next name hash table entry.  */
51075fd0b74Schristos   struct cgen_keyword_entry *next_name;
51175fd0b74Schristos   /* Next value hash table entry.  */
51275fd0b74Schristos   struct cgen_keyword_entry *next_value;
51375fd0b74Schristos } CGEN_KEYWORD_ENTRY;
51475fd0b74Schristos 
51575fd0b74Schristos /* Top level struct for describing a set of related keywords
51675fd0b74Schristos    (e.g. register names).
51775fd0b74Schristos 
51875fd0b74Schristos    This struct supports run-time entry of new values, and hashed lookups.  */
51975fd0b74Schristos 
52075fd0b74Schristos typedef struct cgen_keyword
52175fd0b74Schristos {
52275fd0b74Schristos   /* Pointer to initial [compiled in] values.  */
52375fd0b74Schristos   CGEN_KEYWORD_ENTRY *init_entries;
52475fd0b74Schristos 
52575fd0b74Schristos   /* Number of entries in `init_entries'.  */
52675fd0b74Schristos   unsigned int num_init_entries;
52775fd0b74Schristos 
52875fd0b74Schristos   /* Hash table used for name lookup.  */
52975fd0b74Schristos   CGEN_KEYWORD_ENTRY **name_hash_table;
53075fd0b74Schristos 
53175fd0b74Schristos   /* Hash table used for value lookup.  */
53275fd0b74Schristos   CGEN_KEYWORD_ENTRY **value_hash_table;
53375fd0b74Schristos 
53475fd0b74Schristos   /* Number of entries in the hash_tables.  */
53575fd0b74Schristos   unsigned int hash_table_size;
53675fd0b74Schristos 
53775fd0b74Schristos   /* Pointer to null keyword "" entry if present.  */
53875fd0b74Schristos   const CGEN_KEYWORD_ENTRY *null_entry;
53975fd0b74Schristos 
54075fd0b74Schristos   /* String containing non-alphanumeric characters used
54175fd0b74Schristos      in keywords.
54275fd0b74Schristos      At present, the highest number of entries used is 1.  */
54375fd0b74Schristos   char nonalpha_chars[8];
54475fd0b74Schristos } CGEN_KEYWORD;
54575fd0b74Schristos 
54675fd0b74Schristos /* Structure used for searching.  */
54775fd0b74Schristos 
54875fd0b74Schristos typedef struct
54975fd0b74Schristos {
55075fd0b74Schristos   /* Table being searched.  */
55175fd0b74Schristos   const CGEN_KEYWORD *table;
55275fd0b74Schristos 
55375fd0b74Schristos   /* Specification of what is being searched for.  */
55475fd0b74Schristos   const char *spec;
55575fd0b74Schristos 
55675fd0b74Schristos   /* Current index in hash table.  */
55775fd0b74Schristos   unsigned int current_hash;
55875fd0b74Schristos 
55975fd0b74Schristos   /* Current element in current hash chain.  */
56075fd0b74Schristos   CGEN_KEYWORD_ENTRY *current_entry;
56175fd0b74Schristos } CGEN_KEYWORD_SEARCH;
56275fd0b74Schristos 
56375fd0b74Schristos /* Lookup a keyword from its name.  */
56475fd0b74Schristos 
56575fd0b74Schristos const CGEN_KEYWORD_ENTRY *cgen_keyword_lookup_name
56675fd0b74Schristos   (CGEN_KEYWORD *, const char *);
56775fd0b74Schristos 
56875fd0b74Schristos /* Lookup a keyword from its value.  */
56975fd0b74Schristos 
57075fd0b74Schristos const CGEN_KEYWORD_ENTRY *cgen_keyword_lookup_value
57175fd0b74Schristos   (CGEN_KEYWORD *, int);
57275fd0b74Schristos 
57375fd0b74Schristos /* Add a keyword.  */
57475fd0b74Schristos 
57575fd0b74Schristos void cgen_keyword_add (CGEN_KEYWORD *, CGEN_KEYWORD_ENTRY *);
57675fd0b74Schristos 
57775fd0b74Schristos /* Keyword searching.
57875fd0b74Schristos    This can be used to retrieve every keyword, or a subset.  */
57975fd0b74Schristos 
58075fd0b74Schristos CGEN_KEYWORD_SEARCH cgen_keyword_search_init
58175fd0b74Schristos   (CGEN_KEYWORD *, const char *);
58275fd0b74Schristos const CGEN_KEYWORD_ENTRY *cgen_keyword_search_next
58375fd0b74Schristos   (CGEN_KEYWORD_SEARCH *);
58475fd0b74Schristos 
58575fd0b74Schristos /* Operand value support routines.  */
58675fd0b74Schristos 
58775fd0b74Schristos extern const char *cgen_parse_keyword
58875fd0b74Schristos   (CGEN_CPU_DESC, const char **, CGEN_KEYWORD *, long *);
58975fd0b74Schristos #ifdef __BFD_H_SEEN__ /* Don't require bfd.h unnecessarily.  */
59075fd0b74Schristos extern const char *cgen_parse_signed_integer
59175fd0b74Schristos   (CGEN_CPU_DESC, const char **, int, long *);
59275fd0b74Schristos extern const char *cgen_parse_unsigned_integer
59375fd0b74Schristos   (CGEN_CPU_DESC, const char **, int, unsigned long *);
59475fd0b74Schristos extern const char *cgen_parse_address
59575fd0b74Schristos   (CGEN_CPU_DESC, const char **, int, int,
59675fd0b74Schristos    enum cgen_parse_operand_result *, bfd_vma *);
59775fd0b74Schristos extern const char *cgen_validate_signed_integer
59875fd0b74Schristos   (long, long, long);
59975fd0b74Schristos extern const char *cgen_validate_unsigned_integer
60075fd0b74Schristos   (unsigned long, unsigned long, unsigned long);
60175fd0b74Schristos #endif
60275fd0b74Schristos 
60375fd0b74Schristos /* Operand modes.  */
60475fd0b74Schristos 
60575fd0b74Schristos /* ??? This duplicates the values in arch.h.  Revisit.
60675fd0b74Schristos    These however need the CGEN_ prefix [as does everything in this file].  */
60775fd0b74Schristos /* ??? Targets may need to add their own modes so we may wish to move this
60875fd0b74Schristos    to <arch>-opc.h, or add a hook.  */
60975fd0b74Schristos 
61075fd0b74Schristos enum cgen_mode {
61175fd0b74Schristos   CGEN_MODE_VOID, /* ??? rename simulator's VM to VOID? */
61275fd0b74Schristos   CGEN_MODE_BI, CGEN_MODE_QI, CGEN_MODE_HI, CGEN_MODE_SI, CGEN_MODE_DI,
61375fd0b74Schristos   CGEN_MODE_UBI, CGEN_MODE_UQI, CGEN_MODE_UHI, CGEN_MODE_USI, CGEN_MODE_UDI,
61475fd0b74Schristos   CGEN_MODE_SF, CGEN_MODE_DF, CGEN_MODE_XF, CGEN_MODE_TF,
61575fd0b74Schristos   CGEN_MODE_TARGET_MAX,
61675fd0b74Schristos   CGEN_MODE_INT, CGEN_MODE_UINT,
61775fd0b74Schristos   CGEN_MODE_MAX
61875fd0b74Schristos };
61975fd0b74Schristos 
62075fd0b74Schristos /* FIXME: Until simulator is updated.  */
62175fd0b74Schristos 
62275fd0b74Schristos #define CGEN_MODE_VM CGEN_MODE_VOID
62375fd0b74Schristos 
62475fd0b74Schristos /* Operands.  */
62575fd0b74Schristos 
62675fd0b74Schristos #ifndef CGEN_ARCH
62775fd0b74Schristos enum cgen_operand_type { CGEN_OPERAND_MAX };
62875fd0b74Schristos #endif
62975fd0b74Schristos 
63075fd0b74Schristos /* "nil" indicator for the operand instance table */
63175fd0b74Schristos #define CGEN_OPERAND_NIL CGEN_OPERAND_MAX
63275fd0b74Schristos 
63375fd0b74Schristos /* A tree of these structs represents the multi-ifield
63475fd0b74Schristos    structure of an operand's hw-index value, if it exists.  */
63575fd0b74Schristos 
63675fd0b74Schristos struct cgen_ifld;
63775fd0b74Schristos 
63875fd0b74Schristos typedef struct cgen_maybe_multi_ifield
63975fd0b74Schristos {
64075fd0b74Schristos   int count; /* 0: indexed by single cgen_ifld (possibly null: dead entry);
64175fd0b74Schristos 		n: indexed by array of more cgen_maybe_multi_ifields.  */
64275fd0b74Schristos   union
64375fd0b74Schristos   {
64475fd0b74Schristos     const void *p;
64575fd0b74Schristos     const struct cgen_maybe_multi_ifield * multi;
64675fd0b74Schristos     const struct cgen_ifld * leaf;
64775fd0b74Schristos   } val;
64875fd0b74Schristos }
64975fd0b74Schristos CGEN_MAYBE_MULTI_IFLD;
65075fd0b74Schristos 
65175fd0b74Schristos /* This struct defines each entry in the operand table.  */
65275fd0b74Schristos 
65375fd0b74Schristos typedef struct
65475fd0b74Schristos {
65575fd0b74Schristos   /* Name as it appears in the syntax string.  */
65675fd0b74Schristos   char *name;
65775fd0b74Schristos 
65875fd0b74Schristos   /* Operand type.  */
65975fd0b74Schristos   enum cgen_operand_type type;
66075fd0b74Schristos 
66175fd0b74Schristos   /* The hardware element associated with this operand.  */
66275fd0b74Schristos   enum cgen_hw_type hw_type;
66375fd0b74Schristos 
66475fd0b74Schristos   /* FIXME: We don't yet record ifield definitions, which we should.
66575fd0b74Schristos      When we do it might make sense to delete start/length (since they will
66675fd0b74Schristos      be duplicated in the ifield's definition) and replace them with a
66775fd0b74Schristos      pointer to the ifield entry.  */
66875fd0b74Schristos 
66975fd0b74Schristos   /* Bit position.
67075fd0b74Schristos      This is just a hint, and may be unused in more complex operands.
67175fd0b74Schristos      May be unused for a modifier.  */
67275fd0b74Schristos   unsigned char start;
67375fd0b74Schristos 
67475fd0b74Schristos   /* The number of bits in the operand.
67575fd0b74Schristos      This is just a hint, and may be unused in more complex operands.
67675fd0b74Schristos      May be unused for a modifier.  */
67775fd0b74Schristos   unsigned char length;
67875fd0b74Schristos 
67975fd0b74Schristos   /* The (possibly-multi) ifield used as an index for this operand, if it
68075fd0b74Schristos      is indexed by a field at all. This substitutes / extends the start and
68175fd0b74Schristos      length fields above, but unsure at this time whether they are used
68275fd0b74Schristos      anywhere.  */
68375fd0b74Schristos   CGEN_MAYBE_MULTI_IFLD index_fields;
68475fd0b74Schristos #if 0 /* ??? Interesting idea but relocs tend to get too complicated,
68575fd0b74Schristos 	 and ABI dependent, for simple table lookups to work.  */
68675fd0b74Schristos   /* Ideally this would be the internal (external?) reloc type.  */
68775fd0b74Schristos   int reloc_type;
68875fd0b74Schristos #endif
68975fd0b74Schristos 
69075fd0b74Schristos   /* Attributes.
69175fd0b74Schristos      This should, but technically needn't, appear last.  It is a variable sized
69275fd0b74Schristos      array in that one architecture may have 1 nonbool attribute and another
69375fd0b74Schristos      may have more.  Having this last means the non-architecture specific code
69475fd0b74Schristos      needn't care, now or tomorrow.  The goal is to eventually record
69575fd0b74Schristos      attributes in their raw form, evaluate them at run-time, and cache the
69675fd0b74Schristos      values, so this worry will go away anyway.  */
69775fd0b74Schristos #ifndef CGEN_OPERAND_NBOOL_ATTRS
69875fd0b74Schristos #define CGEN_OPERAND_NBOOL_ATTRS 1
69975fd0b74Schristos #endif
70075fd0b74Schristos   CGEN_ATTR_TYPE (CGEN_OPERAND_NBOOL_ATTRS) attrs;
70175fd0b74Schristos #define CGEN_OPERAND_ATTRS(operand) (&(operand)->attrs)
70275fd0b74Schristos } CGEN_OPERAND;
70375fd0b74Schristos 
70475fd0b74Schristos /* Return value of attribute ATTR in OPERAND.  */
70575fd0b74Schristos 
70675fd0b74Schristos #define CGEN_OPERAND_ATTR_VALUE(operand, attr) \
70775fd0b74Schristos CGEN_ATTR_VALUE ((operand), CGEN_OPERAND_ATTRS (operand), (attr))
70875fd0b74Schristos 
70975fd0b74Schristos /* Table of operands for selected mach/isa, computed at runtime.
71075fd0b74Schristos    enum cgen_operand_type is an index into this table (specifically
71175fd0b74Schristos    `entries').  */
71275fd0b74Schristos 
71375fd0b74Schristos typedef struct {
71475fd0b74Schristos   /* Pointer to null terminated table of all compiled in entries.  */
71575fd0b74Schristos   const CGEN_OPERAND *init_entries;
71675fd0b74Schristos   unsigned int entry_size; /* since the attribute member is variable sized */
71775fd0b74Schristos   /* Array of all entries, initial and run-time added.  */
71875fd0b74Schristos   const CGEN_OPERAND **entries;
71975fd0b74Schristos   /* Number of elements in `entries'.  */
72075fd0b74Schristos   unsigned int num_entries;
72175fd0b74Schristos   /* For now, xrealloc is called each time a new entry is added at runtime.
72275fd0b74Schristos      ??? May wish to keep track of some slop to reduce the number of calls to
72375fd0b74Schristos      xrealloc, except that there's unlikely to be many and not expected to be
72475fd0b74Schristos      in speed critical code.  */
72575fd0b74Schristos } CGEN_OPERAND_TABLE;
72675fd0b74Schristos 
72775fd0b74Schristos extern const CGEN_OPERAND * cgen_operand_lookup_by_name
72875fd0b74Schristos   (CGEN_CPU_DESC, const char *);
72975fd0b74Schristos extern const CGEN_OPERAND * cgen_operand_lookup_by_num
73075fd0b74Schristos   (CGEN_CPU_DESC, int);
73175fd0b74Schristos 
73275fd0b74Schristos /* Instruction operand instances.
73375fd0b74Schristos 
73475fd0b74Schristos    For each instruction, a list of the hardware elements that are read and
73575fd0b74Schristos    written are recorded.  */
73675fd0b74Schristos 
73775fd0b74Schristos /* The type of the instance.  */
73875fd0b74Schristos 
73975fd0b74Schristos enum cgen_opinst_type {
74075fd0b74Schristos   /* End of table marker.  */
74175fd0b74Schristos   CGEN_OPINST_END = 0,
74275fd0b74Schristos   CGEN_OPINST_INPUT, CGEN_OPINST_OUTPUT
74375fd0b74Schristos };
74475fd0b74Schristos 
74575fd0b74Schristos typedef struct
74675fd0b74Schristos {
74775fd0b74Schristos   /* Input or output indicator.  */
74875fd0b74Schristos   enum cgen_opinst_type type;
74975fd0b74Schristos 
75075fd0b74Schristos   /* Name of operand.  */
75175fd0b74Schristos   const char *name;
75275fd0b74Schristos 
75375fd0b74Schristos   /* The hardware element referenced.  */
75475fd0b74Schristos   enum cgen_hw_type hw_type;
75575fd0b74Schristos 
75675fd0b74Schristos   /* The mode in which the operand is being used.  */
75775fd0b74Schristos   enum cgen_mode mode;
75875fd0b74Schristos 
75975fd0b74Schristos   /* The operand table entry CGEN_OPERAND_NIL if there is none
76075fd0b74Schristos      (i.e. an explicit hardware reference).  */
76175fd0b74Schristos   enum cgen_operand_type op_type;
76275fd0b74Schristos 
76375fd0b74Schristos   /* If `operand' is "nil", the index (e.g. into array of registers).  */
76475fd0b74Schristos   int index;
76575fd0b74Schristos 
76675fd0b74Schristos   /* Attributes.
76775fd0b74Schristos      ??? This perhaps should be a real attribute struct but there's
76875fd0b74Schristos      no current need, so we save a bit of space and just have a set of
76975fd0b74Schristos      flags.  The interface is such that this can easily be made attributes
77075fd0b74Schristos      should it prove useful.  */
77175fd0b74Schristos   unsigned int attrs;
77275fd0b74Schristos #define CGEN_OPINST_ATTRS(opinst) ((opinst)->attrs)
77375fd0b74Schristos /* Return value of attribute ATTR in OPINST.  */
77475fd0b74Schristos #define CGEN_OPINST_ATTR(opinst, attr) \
77575fd0b74Schristos ((CGEN_OPINST_ATTRS (opinst) & (attr)) != 0)
77675fd0b74Schristos /* Operand is conditionally referenced (read/written).  */
77775fd0b74Schristos #define CGEN_OPINST_COND_REF 1
77875fd0b74Schristos } CGEN_OPINST;
77975fd0b74Schristos 
78075fd0b74Schristos /* Syntax string.
78175fd0b74Schristos 
78275fd0b74Schristos    Each insn format and subexpression has one of these.
78375fd0b74Schristos 
78475fd0b74Schristos    The syntax "string" consists of characters (n > 0 && n < 128), and operand
78575fd0b74Schristos    values (n >= 128), and is terminated by 0.  Operand values are 128 + index
78675fd0b74Schristos    into the operand table.  The operand table doesn't exist in C, per se, as
78775fd0b74Schristos    the data is recorded in the parse/insert/extract/print switch statements. */
78875fd0b74Schristos 
78975fd0b74Schristos /* This should be at least as large as necessary for any target. */
79075fd0b74Schristos #define CGEN_MAX_SYNTAX_ELEMENTS 48
79175fd0b74Schristos 
79275fd0b74Schristos /* A target may know its own precise maximum.  Assert that it falls below
79375fd0b74Schristos    the above limit. */
79475fd0b74Schristos #ifdef CGEN_ACTUAL_MAX_SYNTAX_ELEMENTS
79575fd0b74Schristos #if CGEN_ACTUAL_MAX_SYNTAX_ELEMENTS > CGEN_MAX_SYNTAX_ELEMENTS
79675fd0b74Schristos #error "CGEN_ACTUAL_MAX_SYNTAX_ELEMENTS too high - enlarge CGEN_MAX_SYNTAX_ELEMENTS"
79775fd0b74Schristos #endif
79875fd0b74Schristos #endif
79975fd0b74Schristos 
80075fd0b74Schristos typedef unsigned short CGEN_SYNTAX_CHAR_TYPE;
80175fd0b74Schristos 
80275fd0b74Schristos typedef struct
80375fd0b74Schristos {
80475fd0b74Schristos   CGEN_SYNTAX_CHAR_TYPE syntax[CGEN_MAX_SYNTAX_ELEMENTS];
80575fd0b74Schristos } CGEN_SYNTAX;
80675fd0b74Schristos 
80775fd0b74Schristos #define CGEN_SYNTAX_STRING(syn) (syn->syntax)
80875fd0b74Schristos #define CGEN_SYNTAX_CHAR_P(c) ((c) < 128)
80975fd0b74Schristos #define CGEN_SYNTAX_CHAR(c) ((unsigned char)c)
81075fd0b74Schristos #define CGEN_SYNTAX_FIELD(c) ((c) - 128)
81175fd0b74Schristos #define CGEN_SYNTAX_MAKE_FIELD(c) ((c) + 128)
81275fd0b74Schristos 
81375fd0b74Schristos /* ??? I can't currently think of any case where the mnemonic doesn't come
81475fd0b74Schristos    first [and if one ever doesn't building the hash tables will be tricky].
81575fd0b74Schristos    However, we treat mnemonics as just another operand of the instruction.
81675fd0b74Schristos    A value of 1 means "this is where the mnemonic appears".  1 isn't
81775fd0b74Schristos    special other than it's a non-printable ASCII char.  */
81875fd0b74Schristos 
81975fd0b74Schristos #define CGEN_SYNTAX_MNEMONIC       1
82075fd0b74Schristos #define CGEN_SYNTAX_MNEMONIC_P(ch) ((ch) == CGEN_SYNTAX_MNEMONIC)
82175fd0b74Schristos 
82275fd0b74Schristos /* Instruction fields.
82375fd0b74Schristos 
82475fd0b74Schristos    ??? We currently don't allow adding fields at run-time.
82575fd0b74Schristos    Easy to fix when needed.  */
82675fd0b74Schristos 
82775fd0b74Schristos typedef struct cgen_ifld {
82875fd0b74Schristos   /* Enum of ifield.  */
82975fd0b74Schristos   int num;
83075fd0b74Schristos #define CGEN_IFLD_NUM(f) ((f)->num)
83175fd0b74Schristos 
83275fd0b74Schristos   /* Name of the field, distinguishes it from all other fields.  */
83375fd0b74Schristos   const char *name;
83475fd0b74Schristos #define CGEN_IFLD_NAME(f) ((f)->name)
83575fd0b74Schristos 
83675fd0b74Schristos   /* Default offset, in bits, from the start of the insn to the word
83775fd0b74Schristos      containing the field.  */
83875fd0b74Schristos   int word_offset;
83975fd0b74Schristos #define CGEN_IFLD_WORD_OFFSET(f) ((f)->word_offset)
84075fd0b74Schristos 
84175fd0b74Schristos   /* Default length of the word containing the field.  */
84275fd0b74Schristos   int word_size;
84375fd0b74Schristos #define CGEN_IFLD_WORD_SIZE(f) ((f)->word_size)
84475fd0b74Schristos 
84575fd0b74Schristos   /* Default starting bit number.
84675fd0b74Schristos      Whether lsb=0 or msb=0 is determined by CGEN_INSN_LSB0_P.  */
84775fd0b74Schristos   int start;
84875fd0b74Schristos #define CGEN_IFLD_START(f) ((f)->start)
84975fd0b74Schristos 
85075fd0b74Schristos   /* Length of the field, in bits.  */
85175fd0b74Schristos   int length;
85275fd0b74Schristos #define CGEN_IFLD_LENGTH(f) ((f)->length)
85375fd0b74Schristos 
85475fd0b74Schristos #ifndef CGEN_IFLD_NBOOL_ATTRS
85575fd0b74Schristos #define CGEN_IFLD_NBOOL_ATTRS 1
85675fd0b74Schristos #endif
85775fd0b74Schristos   CGEN_ATTR_TYPE (CGEN_IFLD_NBOOL_ATTRS) attrs;
85875fd0b74Schristos #define CGEN_IFLD_ATTRS(f) (&(f)->attrs)
85975fd0b74Schristos } CGEN_IFLD;
86075fd0b74Schristos 
86175fd0b74Schristos /* Return value of attribute ATTR in IFLD.  */
86275fd0b74Schristos #define CGEN_IFLD_ATTR_VALUE(ifld, attr) \
86375fd0b74Schristos CGEN_ATTR_VALUE ((ifld), CGEN_IFLD_ATTRS (ifld), (attr))
86475fd0b74Schristos 
86575fd0b74Schristos /* Instruction data.  */
86675fd0b74Schristos 
86775fd0b74Schristos /* Instruction formats.
86875fd0b74Schristos 
86975fd0b74Schristos    Instructions are grouped by format.  Associated with an instruction is its
87075fd0b74Schristos    format.  Each insn's opcode table entry contains a format table entry.
87175fd0b74Schristos    ??? There is usually very few formats compared with the number of insns,
87275fd0b74Schristos    so one can reduce the size of the opcode table by recording the format table
87375fd0b74Schristos    as a separate entity.  Given that we currently don't, format table entries
87475fd0b74Schristos    are also distinguished by their operands.  This increases the size of the
87575fd0b74Schristos    table, but reduces the number of tables.  It's all minutiae anyway so it
87675fd0b74Schristos    doesn't really matter [at this point in time].
87775fd0b74Schristos 
87875fd0b74Schristos    ??? Support for variable length ISA's is wip.  */
87975fd0b74Schristos 
88075fd0b74Schristos /* Accompanying each iformat description is a list of its fields.  */
88175fd0b74Schristos 
88275fd0b74Schristos typedef struct {
88375fd0b74Schristos   const CGEN_IFLD *ifld;
88475fd0b74Schristos #define CGEN_IFMT_IFLD_IFLD(ii) ((ii)->ifld)
88575fd0b74Schristos } CGEN_IFMT_IFLD;
88675fd0b74Schristos 
88775fd0b74Schristos /* This should be at least as large as necessary for any target. */
88875fd0b74Schristos #define CGEN_MAX_IFMT_OPERANDS 16
88975fd0b74Schristos 
89075fd0b74Schristos /* A target may know its own precise maximum.  Assert that it falls below
89175fd0b74Schristos    the above limit. */
89275fd0b74Schristos #ifdef CGEN_ACTUAL_MAX_IFMT_OPERANDS
89375fd0b74Schristos #if CGEN_ACTUAL_MAX_IFMT_OPERANDS > CGEN_MAX_IFMT_OPERANDS
89475fd0b74Schristos #error "CGEN_ACTUAL_MAX_IFMT_OPERANDS too high - enlarge CGEN_MAX_IFMT_OPERANDS"
89575fd0b74Schristos #endif
89675fd0b74Schristos #endif
89775fd0b74Schristos 
89875fd0b74Schristos 
89975fd0b74Schristos typedef struct
90075fd0b74Schristos {
90175fd0b74Schristos   /* Length that MASK and VALUE have been calculated to
90275fd0b74Schristos      [VALUE is recorded elsewhere].
90375fd0b74Schristos      Normally it is base_insn_bitsize.  On [V]LIW architectures where the base
90475fd0b74Schristos      insn size may be larger than the size of an insn, this field is less than
90575fd0b74Schristos      base_insn_bitsize.  */
90675fd0b74Schristos   unsigned char mask_length;
90775fd0b74Schristos #define CGEN_IFMT_MASK_LENGTH(ifmt) ((ifmt)->mask_length)
90875fd0b74Schristos 
90975fd0b74Schristos   /* Total length of instruction, in bits.  */
91075fd0b74Schristos   unsigned char length;
91175fd0b74Schristos #define CGEN_IFMT_LENGTH(ifmt) ((ifmt)->length)
91275fd0b74Schristos 
91375fd0b74Schristos   /* Mask to apply to the first MASK_LENGTH bits.
91475fd0b74Schristos      Each insn's value is stored with the insn.
91575fd0b74Schristos      The first step in recognizing an insn for disassembly is
91675fd0b74Schristos      (opcode & mask) == value.  */
91775fd0b74Schristos   CGEN_INSN_INT mask;
91875fd0b74Schristos #define CGEN_IFMT_MASK(ifmt) ((ifmt)->mask)
91975fd0b74Schristos 
92075fd0b74Schristos   /* Instruction fields.
92175fd0b74Schristos      +1 for trailing NULL.  */
92275fd0b74Schristos   CGEN_IFMT_IFLD iflds[CGEN_MAX_IFMT_OPERANDS + 1];
92375fd0b74Schristos #define CGEN_IFMT_IFLDS(ifmt) ((ifmt)->iflds)
92475fd0b74Schristos } CGEN_IFMT;
92575fd0b74Schristos 
92675fd0b74Schristos /* Instruction values.  */
92775fd0b74Schristos 
92875fd0b74Schristos typedef struct
92975fd0b74Schristos {
93075fd0b74Schristos   /* The opcode portion of the base insn.  */
93175fd0b74Schristos   CGEN_INSN_INT base_value;
93275fd0b74Schristos 
93375fd0b74Schristos #ifdef CGEN_MAX_EXTRA_OPCODE_OPERANDS
93475fd0b74Schristos   /* Extra opcode values beyond base_value.  */
93575fd0b74Schristos   unsigned long ifield_values[CGEN_MAX_EXTRA_OPCODE_OPERANDS];
93675fd0b74Schristos #endif
93775fd0b74Schristos } CGEN_IVALUE;
93875fd0b74Schristos 
93975fd0b74Schristos /* Instruction opcode table.
94075fd0b74Schristos    This contains the syntax and format data of an instruction.  */
94175fd0b74Schristos 
94275fd0b74Schristos /* ??? Some ports already have an opcode table yet still need to use the rest
94375fd0b74Schristos    of what cgen_insn has.  Plus keeping the opcode data with the operand
94475fd0b74Schristos    instance data can create a pretty big file.  So we keep them separately.
94575fd0b74Schristos    Not sure this is a good idea in the long run.  */
94675fd0b74Schristos 
94775fd0b74Schristos typedef struct
94875fd0b74Schristos {
94975fd0b74Schristos   /* Indices into parse/insert/extract/print handler tables.  */
95075fd0b74Schristos   struct cgen_opcode_handler handlers;
95175fd0b74Schristos #define CGEN_OPCODE_HANDLERS(opc) (& (opc)->handlers)
95275fd0b74Schristos 
95375fd0b74Schristos   /* Syntax string.  */
95475fd0b74Schristos   CGEN_SYNTAX syntax;
95575fd0b74Schristos #define CGEN_OPCODE_SYNTAX(opc) (& (opc)->syntax)
95675fd0b74Schristos 
95775fd0b74Schristos   /* Format entry.  */
95875fd0b74Schristos   const CGEN_IFMT *format;
95975fd0b74Schristos #define CGEN_OPCODE_FORMAT(opc) ((opc)->format)
96075fd0b74Schristos #define CGEN_OPCODE_MASK_BITSIZE(opc) CGEN_IFMT_MASK_LENGTH (CGEN_OPCODE_FORMAT (opc))
96175fd0b74Schristos #define CGEN_OPCODE_BITSIZE(opc) CGEN_IFMT_LENGTH (CGEN_OPCODE_FORMAT (opc))
96275fd0b74Schristos #define CGEN_OPCODE_IFLDS(opc) CGEN_IFMT_IFLDS (CGEN_OPCODE_FORMAT (opc))
96375fd0b74Schristos 
96475fd0b74Schristos   /* Instruction opcode value.  */
96575fd0b74Schristos   CGEN_IVALUE value;
96675fd0b74Schristos #define CGEN_OPCODE_VALUE(opc) (& (opc)->value)
96775fd0b74Schristos #define CGEN_OPCODE_BASE_VALUE(opc) (CGEN_OPCODE_VALUE (opc)->base_value)
96875fd0b74Schristos #define CGEN_OPCODE_BASE_MASK(opc) CGEN_IFMT_MASK (CGEN_OPCODE_FORMAT (opc))
96975fd0b74Schristos } CGEN_OPCODE;
97075fd0b74Schristos 
97175fd0b74Schristos /* Instruction attributes.
97275fd0b74Schristos    This is made a published type as applications can cache a pointer to
97375fd0b74Schristos    the attributes for speed.  */
97475fd0b74Schristos 
97575fd0b74Schristos #ifndef CGEN_INSN_NBOOL_ATTRS
97675fd0b74Schristos #define CGEN_INSN_NBOOL_ATTRS 1
97775fd0b74Schristos #endif
97875fd0b74Schristos typedef CGEN_ATTR_TYPE (CGEN_INSN_NBOOL_ATTRS) CGEN_INSN_ATTR_TYPE;
97975fd0b74Schristos 
98075fd0b74Schristos /* Enum of architecture independent attributes.  */
98175fd0b74Schristos 
98275fd0b74Schristos #ifndef CGEN_ARCH
98375fd0b74Schristos /* ??? Numbers here are recorded in two places.  */
98475fd0b74Schristos typedef enum cgen_insn_attr {
98575fd0b74Schristos   CGEN_INSN_ALIAS = 0
98675fd0b74Schristos } CGEN_INSN_ATTR;
98775fd0b74Schristos #define CGEN_ATTR_CGEN_INSN_ALIAS_VALUE(attrs) ((attrs)->bool_ & (1 << CGEN_INSN_ALIAS))
98875fd0b74Schristos #endif
98975fd0b74Schristos 
99075fd0b74Schristos /* This struct defines each entry in the instruction table.  */
99175fd0b74Schristos 
99275fd0b74Schristos typedef struct
99375fd0b74Schristos {
99475fd0b74Schristos   /* Each real instruction is enumerated.  */
99575fd0b74Schristos   /* ??? This may go away in time.  */
99675fd0b74Schristos   int num;
99775fd0b74Schristos #define CGEN_INSN_NUM(insn) ((insn)->base->num)
99875fd0b74Schristos 
99975fd0b74Schristos   /* Name of entry (that distinguishes it from all other entries).  */
100075fd0b74Schristos   /* ??? If mnemonics have operands, try to print full mnemonic.  */
100175fd0b74Schristos   const char *name;
100275fd0b74Schristos #define CGEN_INSN_NAME(insn) ((insn)->base->name)
100375fd0b74Schristos 
100475fd0b74Schristos   /* Mnemonic.  This is used when parsing and printing the insn.
100575fd0b74Schristos      In the case of insns that have operands on the mnemonics, this is
100675fd0b74Schristos      only the constant part.  E.g. for conditional execution of an `add' insn,
100775fd0b74Schristos      where the full mnemonic is addeq, addne, etc., and the condition is
100875fd0b74Schristos      treated as an operand, this is only "add".  */
100975fd0b74Schristos   const char *mnemonic;
101075fd0b74Schristos #define CGEN_INSN_MNEMONIC(insn) ((insn)->base->mnemonic)
101175fd0b74Schristos 
101275fd0b74Schristos   /* Total length of instruction, in bits.  */
101375fd0b74Schristos   int bitsize;
101475fd0b74Schristos #define CGEN_INSN_BITSIZE(insn) ((insn)->base->bitsize)
101575fd0b74Schristos 
101675fd0b74Schristos #if 0 /* ??? Disabled for now as there is a problem with embedded newlines
101775fd0b74Schristos 	 and the table is already pretty big.  Should perhaps be moved
101875fd0b74Schristos 	 to a file of its own.  */
101975fd0b74Schristos   /* Semantics, as RTL.  */
102075fd0b74Schristos   /* ??? Plain text or bytecodes?  */
102175fd0b74Schristos   /* ??? Note that the operand instance table could be computed at run-time
102275fd0b74Schristos      if we parse this and cache the results.  Something to eventually do.  */
102375fd0b74Schristos   const char *rtx;
102475fd0b74Schristos #define CGEN_INSN_RTX(insn) ((insn)->base->rtx)
102575fd0b74Schristos #endif
102675fd0b74Schristos 
102775fd0b74Schristos   /* Attributes.
102875fd0b74Schristos      This must appear last.  It is a variable sized array in that one
102975fd0b74Schristos      architecture may have 1 nonbool attribute and another may have more.
103075fd0b74Schristos      Having this last means the non-architecture specific code needn't
103175fd0b74Schristos      care.  The goal is to eventually record attributes in their raw form,
103275fd0b74Schristos      evaluate them at run-time, and cache the values, so this worry will go
103375fd0b74Schristos      away anyway.  */
103475fd0b74Schristos   CGEN_INSN_ATTR_TYPE attrs;
103575fd0b74Schristos #define CGEN_INSN_ATTRS(insn) (&(insn)->base->attrs)
103675fd0b74Schristos /* Return value of attribute ATTR in INSN.  */
103775fd0b74Schristos #define CGEN_INSN_ATTR_VALUE(insn, attr) \
103875fd0b74Schristos CGEN_ATTR_VALUE ((insn), CGEN_INSN_ATTRS (insn), (attr))
103975fd0b74Schristos #define CGEN_INSN_BITSET_ATTR_VALUE(insn, attr) \
104075fd0b74Schristos   CGEN_BITSET_ATTR_VALUE ((insn), CGEN_INSN_ATTRS (insn), (attr))
104175fd0b74Schristos } CGEN_IBASE;
104275fd0b74Schristos 
104375fd0b74Schristos /* Return non-zero if INSN is the "invalid" insn marker.  */
104475fd0b74Schristos 
104575fd0b74Schristos #define CGEN_INSN_INVALID_P(insn) (CGEN_INSN_MNEMONIC (insn) == 0)
104675fd0b74Schristos 
104775fd0b74Schristos /* Main struct contain instruction information.
104875fd0b74Schristos    BASE is always present, the rest is present only if asked for.  */
104975fd0b74Schristos 
105075fd0b74Schristos struct cgen_insn
105175fd0b74Schristos {
105275fd0b74Schristos   /* ??? May be of use to put a type indicator here.
105375fd0b74Schristos      Then this struct could different info for different classes of insns.  */
105475fd0b74Schristos   /* ??? A speedup can be had by moving `base' into this struct.
105575fd0b74Schristos      Maybe later.  */
105675fd0b74Schristos   const CGEN_IBASE *base;
105775fd0b74Schristos   const CGEN_OPCODE *opcode;
105875fd0b74Schristos   const CGEN_OPINST *opinst;
105975fd0b74Schristos 
106075fd0b74Schristos   /* Regex to disambiguate overloaded opcodes */
106175fd0b74Schristos   void *rx;
106275fd0b74Schristos #define CGEN_INSN_RX(insn) ((insn)->rx)
106375fd0b74Schristos #define CGEN_MAX_RX_ELEMENTS (CGEN_MAX_SYNTAX_ELEMENTS * 5)
106475fd0b74Schristos };
106575fd0b74Schristos 
106675fd0b74Schristos /* Instruction lists.
106775fd0b74Schristos    This is used for adding new entries and for creating the hash lists.  */
106875fd0b74Schristos 
106975fd0b74Schristos typedef struct cgen_insn_list
107075fd0b74Schristos {
107175fd0b74Schristos   struct cgen_insn_list *next;
107275fd0b74Schristos   const CGEN_INSN *insn;
107375fd0b74Schristos } CGEN_INSN_LIST;
107475fd0b74Schristos 
107575fd0b74Schristos /* Table of instructions.  */
107675fd0b74Schristos 
107775fd0b74Schristos typedef struct
107875fd0b74Schristos {
107975fd0b74Schristos   const CGEN_INSN *init_entries;
108075fd0b74Schristos   unsigned int entry_size; /* since the attribute member is variable sized */
108175fd0b74Schristos   unsigned int num_init_entries;
108275fd0b74Schristos   CGEN_INSN_LIST *new_entries;
108375fd0b74Schristos } CGEN_INSN_TABLE;
108475fd0b74Schristos 
108575fd0b74Schristos /* Return number of instructions.  This includes any added at run-time.  */
108675fd0b74Schristos 
108775fd0b74Schristos extern int cgen_insn_count (CGEN_CPU_DESC);
108875fd0b74Schristos extern int cgen_macro_insn_count (CGEN_CPU_DESC);
108975fd0b74Schristos 
109075fd0b74Schristos /* Macros to access the other insn elements not recorded in CGEN_IBASE.  */
109175fd0b74Schristos 
109275fd0b74Schristos /* Fetch INSN's operand instance table.  */
109375fd0b74Schristos /* ??? Doesn't handle insns added at runtime.  */
109475fd0b74Schristos #define CGEN_INSN_OPERANDS(insn) ((insn)->opinst)
109575fd0b74Schristos 
109675fd0b74Schristos /* Return INSN's opcode table entry.  */
109775fd0b74Schristos #define CGEN_INSN_OPCODE(insn) ((insn)->opcode)
109875fd0b74Schristos 
109975fd0b74Schristos /* Return INSN's handler data.  */
110075fd0b74Schristos #define CGEN_INSN_HANDLERS(insn) CGEN_OPCODE_HANDLERS (CGEN_INSN_OPCODE (insn))
110175fd0b74Schristos 
110275fd0b74Schristos /* Return INSN's syntax.  */
110375fd0b74Schristos #define CGEN_INSN_SYNTAX(insn) CGEN_OPCODE_SYNTAX (CGEN_INSN_OPCODE (insn))
110475fd0b74Schristos 
110575fd0b74Schristos /* Return size of base mask in bits.  */
110675fd0b74Schristos #define CGEN_INSN_MASK_BITSIZE(insn) \
110775fd0b74Schristos   CGEN_OPCODE_MASK_BITSIZE (CGEN_INSN_OPCODE (insn))
110875fd0b74Schristos 
110975fd0b74Schristos /* Return mask of base part of INSN.  */
111075fd0b74Schristos #define CGEN_INSN_BASE_MASK(insn) \
111175fd0b74Schristos   CGEN_OPCODE_BASE_MASK (CGEN_INSN_OPCODE (insn))
111275fd0b74Schristos 
111375fd0b74Schristos /* Return value of base part of INSN.  */
111475fd0b74Schristos #define CGEN_INSN_BASE_VALUE(insn) \
111575fd0b74Schristos   CGEN_OPCODE_BASE_VALUE (CGEN_INSN_OPCODE (insn))
111675fd0b74Schristos 
111775fd0b74Schristos /* Standard way to test whether INSN is supported by MACH.
111875fd0b74Schristos    MACH is one of enum mach_attr.
111975fd0b74Schristos    The "|1" is because the base mach is always selected.  */
112075fd0b74Schristos #define CGEN_INSN_MACH_HAS_P(insn, mach) \
112175fd0b74Schristos ((CGEN_INSN_ATTR_VALUE ((insn), CGEN_INSN_MACH) & ((1 << (mach)) | 1)) != 0)
112275fd0b74Schristos 
112375fd0b74Schristos /* Macro instructions.
112475fd0b74Schristos    Macro insns aren't real insns, they map to one or more real insns.
112575fd0b74Schristos    E.g. An architecture's "nop" insn may actually be an "mv r0,r0" or
112675fd0b74Schristos    some such.
112775fd0b74Schristos 
112875fd0b74Schristos    Macro insns can expand to nothing (e.g. a nop that is optimized away).
112975fd0b74Schristos    This is useful in multi-insn macros that build a constant in a register.
113075fd0b74Schristos    Of course this isn't the default behaviour and must be explicitly enabled.
113175fd0b74Schristos 
113275fd0b74Schristos    Assembly of macro-insns is relatively straightforward.  Disassembly isn't.
113375fd0b74Schristos    However, disassembly of at least some kinds of macro insns is important
113475fd0b74Schristos    in order that the disassembled code preserve the readability of the original
113575fd0b74Schristos    insn.  What is attempted here is to disassemble all "simple" macro-insns,
113675fd0b74Schristos    where "simple" is currently defined to mean "expands to one real insn".
113775fd0b74Schristos 
113875fd0b74Schristos    Simple macro-insns are handled specially.  They are emitted as ALIAS's
113975fd0b74Schristos    of real insns.  This simplifies their handling since there's usually more
114075fd0b74Schristos    of them than any other kind of macro-insn, and proper disassembly of them
114175fd0b74Schristos    falls out for free.  */
114275fd0b74Schristos 
114375fd0b74Schristos /* For each macro-insn there may be multiple expansion possibilities,
114475fd0b74Schristos    depending on the arguments.  This structure is accessed via the `data'
114575fd0b74Schristos    member of CGEN_INSN.  */
114675fd0b74Schristos 
114775fd0b74Schristos typedef struct cgen_minsn_expansion {
114875fd0b74Schristos   /* Function to do the expansion.
114975fd0b74Schristos      If the expansion fails (e.g. "no match") NULL is returned.
115075fd0b74Schristos      Space for the expansion is obtained with malloc.
115175fd0b74Schristos      It is up to the caller to free it.  */
115275fd0b74Schristos   const char * (* fn)
115375fd0b74Schristos      (const struct cgen_minsn_expansion *,
115475fd0b74Schristos       const char *, const char **, int *,
115575fd0b74Schristos       CGEN_OPERAND **);
115675fd0b74Schristos #define CGEN_MIEXPN_FN(ex) ((ex)->fn)
115775fd0b74Schristos 
115875fd0b74Schristos   /* Instruction(s) the macro expands to.
115975fd0b74Schristos      The format of STR is defined by FN.
116075fd0b74Schristos      It is typically the assembly code of the real insn, but it could also be
116175fd0b74Schristos      the original Scheme expression or a tokenized form of it (with FN being
116275fd0b74Schristos      an appropriate interpreter).  */
116375fd0b74Schristos   const char * str;
116475fd0b74Schristos #define CGEN_MIEXPN_STR(ex) ((ex)->str)
116575fd0b74Schristos } CGEN_MINSN_EXPANSION;
116675fd0b74Schristos 
116775fd0b74Schristos /* Normal expander.
116875fd0b74Schristos    When supported, this function will convert the input string to another
116975fd0b74Schristos    string and the parser will be invoked recursively.  The output string
117075fd0b74Schristos    may contain further macro invocations.  */
117175fd0b74Schristos 
117275fd0b74Schristos extern const char * cgen_expand_macro_insn
117375fd0b74Schristos   (CGEN_CPU_DESC, const struct cgen_minsn_expansion *,
117475fd0b74Schristos    const char *, const char **, int *, CGEN_OPERAND **);
117575fd0b74Schristos 
117675fd0b74Schristos /* The assembler insn table is hashed based on some function of the mnemonic
117775fd0b74Schristos    (the actually hashing done is up to the target, but we provide a few
117875fd0b74Schristos    examples like the first letter or a function of the entire mnemonic).  */
117975fd0b74Schristos 
118075fd0b74Schristos extern CGEN_INSN_LIST * cgen_asm_lookup_insn
118175fd0b74Schristos   (CGEN_CPU_DESC, const char *);
118275fd0b74Schristos #define CGEN_ASM_LOOKUP_INSN(cd, string) cgen_asm_lookup_insn ((cd), (string))
118375fd0b74Schristos #define CGEN_ASM_NEXT_INSN(insn) ((insn)->next)
118475fd0b74Schristos 
118575fd0b74Schristos /* The disassembler insn table is hashed based on some function of machine
118675fd0b74Schristos    instruction (the actually hashing done is up to the target).  */
118775fd0b74Schristos 
118875fd0b74Schristos extern CGEN_INSN_LIST * cgen_dis_lookup_insn
118975fd0b74Schristos   (CGEN_CPU_DESC, const char *, CGEN_INSN_INT);
119075fd0b74Schristos /* FIXME: delete these two */
119175fd0b74Schristos #define CGEN_DIS_LOOKUP_INSN(cd, buf, value) cgen_dis_lookup_insn ((cd), (buf), (value))
119275fd0b74Schristos #define CGEN_DIS_NEXT_INSN(insn) ((insn)->next)
119375fd0b74Schristos 
119475fd0b74Schristos /* The CPU description.
119575fd0b74Schristos    A copy of this is created when the cpu table is "opened".
119675fd0b74Schristos    All global state information is recorded here.
119775fd0b74Schristos    Access macros are provided for "public" members.  */
119875fd0b74Schristos 
119975fd0b74Schristos typedef struct cgen_cpu_desc
120075fd0b74Schristos {
120175fd0b74Schristos   /* Bitmap of selected machine(s) (a la BFD machine number).  */
120275fd0b74Schristos   int machs;
120375fd0b74Schristos 
120475fd0b74Schristos   /* Bitmap of selected isa(s).  */
120575fd0b74Schristos   CGEN_BITSET *isas;
120675fd0b74Schristos #define CGEN_CPU_ISAS(cd) ((cd)->isas)
120775fd0b74Schristos 
120875fd0b74Schristos   /* Current endian.  */
120975fd0b74Schristos   enum cgen_endian endian;
121075fd0b74Schristos #define CGEN_CPU_ENDIAN(cd) ((cd)->endian)
121175fd0b74Schristos 
121275fd0b74Schristos   /* Current insn endian.  */
121375fd0b74Schristos   enum cgen_endian insn_endian;
121475fd0b74Schristos #define CGEN_CPU_INSN_ENDIAN(cd) ((cd)->insn_endian)
121575fd0b74Schristos 
121675fd0b74Schristos   /* Word size (in bits).  */
121775fd0b74Schristos   /* ??? Or maybe maximum word size - might we ever need to allow a cpu table
121875fd0b74Schristos      to be opened for both sparc32/sparc64?
121975fd0b74Schristos      ??? Another alternative is to create a table of selected machs and
122075fd0b74Schristos      lazily fetch the data from there.  */
122175fd0b74Schristos   unsigned int word_bitsize;
122275fd0b74Schristos 
122375fd0b74Schristos   /* Instruction chunk size (in bits), for purposes of endianness
122475fd0b74Schristos      conversion.  */
122575fd0b74Schristos   unsigned int insn_chunk_bitsize;
122675fd0b74Schristos 
122775fd0b74Schristos   /* Indicator if sizes are unknown.
122875fd0b74Schristos      This is used by default_insn_bitsize,base_insn_bitsize if there is a
122975fd0b74Schristos      difference between the selected isa's.  */
123075fd0b74Schristos #define CGEN_SIZE_UNKNOWN 65535
123175fd0b74Schristos 
123275fd0b74Schristos   /* Default instruction size (in bits).
123375fd0b74Schristos      This is used by the assembler when it encounters an unknown insn.  */
123475fd0b74Schristos   unsigned int default_insn_bitsize;
123575fd0b74Schristos 
123675fd0b74Schristos   /* Base instruction size (in bits).
123775fd0b74Schristos      For non-LIW cpus this is generally the length of the smallest insn.
123875fd0b74Schristos      For LIW cpus its wip (work-in-progress).  For the m32r its 32.  */
123975fd0b74Schristos   unsigned int base_insn_bitsize;
124075fd0b74Schristos 
124175fd0b74Schristos   /* Minimum/maximum instruction size (in bits).  */
124275fd0b74Schristos   unsigned int min_insn_bitsize;
124375fd0b74Schristos   unsigned int max_insn_bitsize;
124475fd0b74Schristos 
124575fd0b74Schristos   /* Instruction set variants.  */
124675fd0b74Schristos   const CGEN_ISA *isa_table;
124775fd0b74Schristos 
124875fd0b74Schristos   /* Machine variants.  */
124975fd0b74Schristos   const CGEN_MACH *mach_table;
125075fd0b74Schristos 
125175fd0b74Schristos   /* Hardware elements.  */
125275fd0b74Schristos   CGEN_HW_TABLE hw_table;
125375fd0b74Schristos 
125475fd0b74Schristos   /* Instruction fields.  */
125575fd0b74Schristos   const CGEN_IFLD *ifld_table;
125675fd0b74Schristos 
125775fd0b74Schristos   /* Operands.  */
125875fd0b74Schristos   CGEN_OPERAND_TABLE operand_table;
125975fd0b74Schristos 
126075fd0b74Schristos   /* Main instruction table.  */
126175fd0b74Schristos   CGEN_INSN_TABLE insn_table;
126275fd0b74Schristos #define CGEN_CPU_INSN_TABLE(cd) (& (cd)->insn_table)
126375fd0b74Schristos 
126475fd0b74Schristos   /* Macro instructions are defined separately and are combined with real
126575fd0b74Schristos      insns during hash table computation.  */
126675fd0b74Schristos   CGEN_INSN_TABLE macro_insn_table;
126775fd0b74Schristos 
126875fd0b74Schristos   /* Copy of CGEN_INT_INSN_P.  */
126975fd0b74Schristos   int int_insn_p;
127075fd0b74Schristos 
127175fd0b74Schristos   /* Called to rebuild the tables after something has changed.  */
127275fd0b74Schristos   void (*rebuild_tables) (CGEN_CPU_DESC);
127375fd0b74Schristos 
127475fd0b74Schristos   /* Operand parser callback.  */
127575fd0b74Schristos   cgen_parse_operand_fn * parse_operand_fn;
127675fd0b74Schristos 
127775fd0b74Schristos   /* Parse/insert/extract/print cover fns for operands.  */
127875fd0b74Schristos   const char * (*parse_operand)
127975fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, const char **, CGEN_FIELDS *fields_);
128075fd0b74Schristos #ifdef __BFD_H_SEEN__
128175fd0b74Schristos   const char * (*insert_operand)
128275fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, CGEN_FIELDS *fields_,
128375fd0b74Schristos      CGEN_INSN_BYTES_PTR, bfd_vma pc_);
128475fd0b74Schristos   int (*extract_operand)
128575fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, CGEN_EXTRACT_INFO *, CGEN_INSN_INT,
128675fd0b74Schristos      CGEN_FIELDS *fields_, bfd_vma pc_);
128775fd0b74Schristos   void (*print_operand)
128875fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, void * info_, CGEN_FIELDS * fields_,
128975fd0b74Schristos      void const *attrs_, bfd_vma pc_, int length_);
129075fd0b74Schristos #else
129175fd0b74Schristos   const char * (*insert_operand) ();
129275fd0b74Schristos   int (*extract_operand) ();
129375fd0b74Schristos   void (*print_operand) ();
129475fd0b74Schristos #endif
129575fd0b74Schristos #define CGEN_CPU_PARSE_OPERAND(cd) ((cd)->parse_operand)
129675fd0b74Schristos #define CGEN_CPU_INSERT_OPERAND(cd) ((cd)->insert_operand)
129775fd0b74Schristos #define CGEN_CPU_EXTRACT_OPERAND(cd) ((cd)->extract_operand)
129875fd0b74Schristos #define CGEN_CPU_PRINT_OPERAND(cd) ((cd)->print_operand)
129975fd0b74Schristos 
130075fd0b74Schristos   /* Size of CGEN_FIELDS struct.  */
130175fd0b74Schristos   unsigned int sizeof_fields;
130275fd0b74Schristos #define CGEN_CPU_SIZEOF_FIELDS(cd) ((cd)->sizeof_fields)
130375fd0b74Schristos 
130475fd0b74Schristos   /* Set the bitsize field.  */
130575fd0b74Schristos   void (*set_fields_bitsize) (CGEN_FIELDS *fields_, int size_);
130675fd0b74Schristos #define CGEN_CPU_SET_FIELDS_BITSIZE(cd) ((cd)->set_fields_bitsize)
130775fd0b74Schristos 
130875fd0b74Schristos   /* CGEN_FIELDS accessors.  */
130975fd0b74Schristos   int (*get_int_operand)
131075fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, const CGEN_FIELDS *fields_);
131175fd0b74Schristos   void (*set_int_operand)
131275fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, CGEN_FIELDS *fields_, int value_);
131375fd0b74Schristos #ifdef __BFD_H_SEEN__
131475fd0b74Schristos   bfd_vma (*get_vma_operand)
131575fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, const CGEN_FIELDS *fields_);
131675fd0b74Schristos   void (*set_vma_operand)
131775fd0b74Schristos     (CGEN_CPU_DESC, int opindex_, CGEN_FIELDS *fields_, bfd_vma value_);
131875fd0b74Schristos #else
131975fd0b74Schristos   long (*get_vma_operand) ();
132075fd0b74Schristos   void (*set_vma_operand) ();
132175fd0b74Schristos #endif
132275fd0b74Schristos #define CGEN_CPU_GET_INT_OPERAND(cd) ((cd)->get_int_operand)
132375fd0b74Schristos #define CGEN_CPU_SET_INT_OPERAND(cd) ((cd)->set_int_operand)
132475fd0b74Schristos #define CGEN_CPU_GET_VMA_OPERAND(cd) ((cd)->get_vma_operand)
132575fd0b74Schristos #define CGEN_CPU_SET_VMA_OPERAND(cd) ((cd)->set_vma_operand)
132675fd0b74Schristos 
132775fd0b74Schristos   /* Instruction parse/insert/extract/print handlers.  */
132875fd0b74Schristos   /* FIXME: make these types uppercase.  */
132975fd0b74Schristos   cgen_parse_fn * const *parse_handlers;
133075fd0b74Schristos   cgen_insert_fn * const *insert_handlers;
133175fd0b74Schristos   cgen_extract_fn * const *extract_handlers;
133275fd0b74Schristos   cgen_print_fn * const *print_handlers;
133375fd0b74Schristos #define CGEN_PARSE_FN(cd, insn)   (cd->parse_handlers[(insn)->opcode->handlers.parse])
133475fd0b74Schristos #define CGEN_INSERT_FN(cd, insn)  (cd->insert_handlers[(insn)->opcode->handlers.insert])
133575fd0b74Schristos #define CGEN_EXTRACT_FN(cd, insn) (cd->extract_handlers[(insn)->opcode->handlers.extract])
133675fd0b74Schristos #define CGEN_PRINT_FN(cd, insn)   (cd->print_handlers[(insn)->opcode->handlers.print])
133775fd0b74Schristos 
133875fd0b74Schristos   /* Return non-zero if insn should be added to hash table.  */
133975fd0b74Schristos   int (* asm_hash_p) (const CGEN_INSN *);
134075fd0b74Schristos 
134175fd0b74Schristos   /* Assembler hash function.  */
134275fd0b74Schristos   unsigned int (* asm_hash) (const char *);
134375fd0b74Schristos 
134475fd0b74Schristos   /* Number of entries in assembler hash table.  */
134575fd0b74Schristos   unsigned int asm_hash_size;
134675fd0b74Schristos 
134775fd0b74Schristos   /* Return non-zero if insn should be added to hash table.  */
134875fd0b74Schristos   int (* dis_hash_p) (const CGEN_INSN *);
134975fd0b74Schristos 
135075fd0b74Schristos   /* Disassembler hash function.  */
135175fd0b74Schristos   unsigned int (* dis_hash) (const char *, CGEN_INSN_INT);
135275fd0b74Schristos 
135375fd0b74Schristos   /* Number of entries in disassembler hash table.  */
135475fd0b74Schristos   unsigned int dis_hash_size;
135575fd0b74Schristos 
135675fd0b74Schristos   /* Assembler instruction hash table.  */
135775fd0b74Schristos   CGEN_INSN_LIST **asm_hash_table;
135875fd0b74Schristos   CGEN_INSN_LIST *asm_hash_table_entries;
135975fd0b74Schristos 
136075fd0b74Schristos   /* Disassembler instruction hash table.  */
136175fd0b74Schristos   CGEN_INSN_LIST **dis_hash_table;
136275fd0b74Schristos   CGEN_INSN_LIST *dis_hash_table_entries;
136375fd0b74Schristos 
136475fd0b74Schristos   /* This field could be turned into a bitfield if room for other flags is needed.  */
136575fd0b74Schristos   unsigned int signed_overflow_ok_p;
136675fd0b74Schristos 
136775fd0b74Schristos } CGEN_CPU_TABLE;
136875fd0b74Schristos 
136975fd0b74Schristos /* wip */
137075fd0b74Schristos #ifndef CGEN_WORD_ENDIAN
137175fd0b74Schristos #define CGEN_WORD_ENDIAN(cd) CGEN_CPU_ENDIAN (cd)
137275fd0b74Schristos #endif
137375fd0b74Schristos #ifndef CGEN_INSN_WORD_ENDIAN
137475fd0b74Schristos #define CGEN_INSN_WORD_ENDIAN(cd) CGEN_CPU_INSN_ENDIAN (cd)
137575fd0b74Schristos #endif
137675fd0b74Schristos 
137775fd0b74Schristos /* Prototypes of major functions.  */
137875fd0b74Schristos /* FIXME: Move more CGEN_SYM-defined functions into CGEN_CPU_DESC.
137975fd0b74Schristos    Not the init fns though, as that would drag in things that mightn't be
138075fd0b74Schristos    used and might not even exist.  */
138175fd0b74Schristos 
138275fd0b74Schristos /* Argument types to cpu_open.  */
138375fd0b74Schristos 
138475fd0b74Schristos enum cgen_cpu_open_arg {
138575fd0b74Schristos   CGEN_CPU_OPEN_END,
138675fd0b74Schristos   /* Select instruction set(s), arg is bitmap or 0 meaning "unspecified".  */
138775fd0b74Schristos   CGEN_CPU_OPEN_ISAS,
138875fd0b74Schristos   /* Select machine(s), arg is bitmap or 0 meaning "unspecified".  */
138975fd0b74Schristos   CGEN_CPU_OPEN_MACHS,
139075fd0b74Schristos   /* Select machine, arg is mach's bfd name.
139175fd0b74Schristos      Multiple machines can be specified by repeated use.  */
139275fd0b74Schristos   CGEN_CPU_OPEN_BFDMACH,
139375fd0b74Schristos   /* Select endian, arg is CGEN_ENDIAN_*.  */
1394*e992f068Schristos   CGEN_CPU_OPEN_ENDIAN,
1395*e992f068Schristos   /* Select instruction endian, arg is CGEN_ENDIAN_*.  */
1396*e992f068Schristos   CGEN_CPU_OPEN_INSN_ENDIAN,
139775fd0b74Schristos };
139875fd0b74Schristos 
139975fd0b74Schristos /* Open a cpu descriptor table for use.
140075fd0b74Schristos    ??? We only support ISO C stdargs here, not K&R.
140175fd0b74Schristos    Laziness, plus experiment to see if anything requires K&R - eventually
140275fd0b74Schristos    K&R will no longer be supported - e.g. GDB is currently trying this.  */
140375fd0b74Schristos 
140475fd0b74Schristos extern CGEN_CPU_DESC CGEN_SYM (cpu_open) (enum cgen_cpu_open_arg, ...);
140575fd0b74Schristos 
140675fd0b74Schristos /* Cover fn to handle simple case.  */
140775fd0b74Schristos 
140875fd0b74Schristos extern CGEN_CPU_DESC CGEN_SYM (cpu_open_1)
140975fd0b74Schristos    (const char *mach_name_, enum cgen_endian endian_);
141075fd0b74Schristos 
141175fd0b74Schristos /* Close it.  */
141275fd0b74Schristos 
141375fd0b74Schristos extern void CGEN_SYM (cpu_close) (CGEN_CPU_DESC);
141475fd0b74Schristos 
141575fd0b74Schristos /* Initialize the opcode table for use.
141675fd0b74Schristos    Called by init_asm/init_dis.  */
141775fd0b74Schristos 
141875fd0b74Schristos extern void CGEN_SYM (init_opcode_table) (CGEN_CPU_DESC cd_);
141975fd0b74Schristos 
142075fd0b74Schristos /* build the insn selection regex.
142175fd0b74Schristos    called by init_opcode_table */
142275fd0b74Schristos 
142375fd0b74Schristos extern char * CGEN_SYM(build_insn_regex) (CGEN_INSN *insn_);
142475fd0b74Schristos 
142575fd0b74Schristos /* Initialize the ibld table for use.
142675fd0b74Schristos    Called by init_asm/init_dis.  */
142775fd0b74Schristos 
142875fd0b74Schristos extern void CGEN_SYM (init_ibld_table) (CGEN_CPU_DESC cd_);
142975fd0b74Schristos 
143075fd0b74Schristos /* Initialize an cpu table for assembler or disassembler use.
143175fd0b74Schristos    These must be called immediately after cpu_open.  */
143275fd0b74Schristos 
143375fd0b74Schristos extern void CGEN_SYM (init_asm) (CGEN_CPU_DESC);
143475fd0b74Schristos extern void CGEN_SYM (init_dis) (CGEN_CPU_DESC);
143575fd0b74Schristos 
143675fd0b74Schristos /* Initialize the operand instance table for use.  */
143775fd0b74Schristos 
143875fd0b74Schristos extern void CGEN_SYM (init_opinst_table) (CGEN_CPU_DESC cd_);
143975fd0b74Schristos 
144075fd0b74Schristos /* Assemble an instruction.  */
144175fd0b74Schristos 
144275fd0b74Schristos extern const CGEN_INSN * CGEN_SYM (assemble_insn)
144375fd0b74Schristos   (CGEN_CPU_DESC, const char *, CGEN_FIELDS *,
144475fd0b74Schristos    CGEN_INSN_BYTES_PTR, char **);
144575fd0b74Schristos 
144675fd0b74Schristos extern const CGEN_KEYWORD CGEN_SYM (operand_mach);
144775fd0b74Schristos extern int CGEN_SYM (get_mach) (const char *);
144875fd0b74Schristos 
144975fd0b74Schristos /* Operand index computation.  */
145075fd0b74Schristos extern const CGEN_INSN * cgen_lookup_insn
145175fd0b74Schristos   (CGEN_CPU_DESC, const CGEN_INSN * insn_,
145275fd0b74Schristos    CGEN_INSN_INT int_value_, unsigned char *bytes_value_,
145375fd0b74Schristos    int length_, CGEN_FIELDS *fields_, int alias_p_);
145475fd0b74Schristos extern void cgen_get_insn_operands
145575fd0b74Schristos   (CGEN_CPU_DESC, const CGEN_INSN * insn_,
145675fd0b74Schristos    const CGEN_FIELDS *fields_, int *indices_);
145775fd0b74Schristos extern const CGEN_INSN * cgen_lookup_get_insn_operands
145875fd0b74Schristos   (CGEN_CPU_DESC, const CGEN_INSN *insn_,
145975fd0b74Schristos    CGEN_INSN_INT int_value_, unsigned char *bytes_value_,
146075fd0b74Schristos    int length_, int *indices_, CGEN_FIELDS *fields_);
146175fd0b74Schristos 
146275fd0b74Schristos /* Cover fns to bfd_get/set.  */
146375fd0b74Schristos 
146475fd0b74Schristos extern CGEN_INSN_INT cgen_get_insn_value
1465*e992f068Schristos   (CGEN_CPU_DESC, unsigned char *, int, int);
146675fd0b74Schristos extern void cgen_put_insn_value
1467*e992f068Schristos   (CGEN_CPU_DESC, unsigned char *, int, CGEN_INSN_INT, int);
1468*e992f068Schristos 
1469*e992f068Schristos extern CGEN_INSN_INT cgen_get_base_insn_value
1470*e992f068Schristos   (CGEN_CPU_DESC, unsigned char *, int);
1471*e992f068Schristos extern void cgen_put_base_insn_value
147275fd0b74Schristos   (CGEN_CPU_DESC, unsigned char *, int, CGEN_INSN_INT);
147375fd0b74Schristos 
147475fd0b74Schristos /* Read in a cpu description file.
147575fd0b74Schristos    ??? For future concerns, including adding instructions to the assembler/
147675fd0b74Schristos    disassembler at run-time.  */
147775fd0b74Schristos 
147875fd0b74Schristos extern const char * cgen_read_cpu_file (CGEN_CPU_DESC, const char * filename_);
147975fd0b74Schristos 
148075fd0b74Schristos /* Allow signed overflow of instruction fields.  */
148175fd0b74Schristos extern void cgen_set_signed_overflow_ok (CGEN_CPU_DESC);
148275fd0b74Schristos 
148375fd0b74Schristos /* Generate an error message if a signed field in an instruction overflows.  */
148475fd0b74Schristos extern void cgen_clear_signed_overflow_ok (CGEN_CPU_DESC);
148575fd0b74Schristos 
148675fd0b74Schristos /* Will an error message be generated if a signed field in an instruction overflows ? */
148775fd0b74Schristos extern unsigned int cgen_signed_overflow_ok_p (CGEN_CPU_DESC);
148875fd0b74Schristos 
148975fd0b74Schristos #ifdef __cplusplus
149075fd0b74Schristos }
149175fd0b74Schristos #endif
149275fd0b74Schristos 
149375fd0b74Schristos #endif /* OPCODE_CGEN_H */
1494