]>
Commit | Line | Data |
---|---|---|
64a93ac5 | 1 | /* Declarations for interface to insn recognizer and insn-output.c. |
6fb5fa3c | 2 | Copyright (C) 1987, 1996, 1997, 1998, 1999, 2000, 2001, 2003, 2004, |
cbda7dc6 | 3 | 2005, 2006, 2007, 2008, 2009, 2010 Free Software Foundation, Inc. |
64a93ac5 | 4 | |
1322177d | 5 | This file is part of GCC. |
64a93ac5 | 6 | |
1322177d LB |
7 | GCC is free software; you can redistribute it and/or modify it under |
8 | the terms of the GNU General Public License as published by the Free | |
9dcd6f09 | 9 | Software Foundation; either version 3, or (at your option) any later |
1322177d | 10 | version. |
64a93ac5 | 11 | |
1322177d LB |
12 | GCC is distributed in the hope that it will be useful, but WITHOUT ANY |
13 | WARRANTY; without even the implied warranty of MERCHANTABILITY or | |
14 | FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License | |
15 | for more details. | |
64a93ac5 CH |
16 | |
17 | You should have received a copy of the GNU General Public License | |
9dcd6f09 NC |
18 | along with GCC; see the file COPYING3. If not see |
19 | <http://www.gnu.org/licenses/>. */ | |
64a93ac5 | 20 | |
f62a15e3 BS |
21 | /* Random number that should be large enough for all purposes. */ |
22 | #define MAX_RECOG_ALTERNATIVES 30 | |
23 | ||
0eadeb15 BS |
24 | /* Types of operands. */ |
25 | enum op_type { | |
26 | OP_IN, | |
27 | OP_OUT, | |
28 | OP_INOUT | |
29 | }; | |
30 | ||
f62a15e3 BS |
31 | struct operand_alternative |
32 | { | |
33 | /* Pointer to the beginning of the constraint string for this alternative, | |
34 | for easier access by alternative number. */ | |
9b3142b3 | 35 | const char *constraint; |
f62a15e3 BS |
36 | |
37 | /* The register class valid for this alternative (possibly NO_REGS). */ | |
e3a64162 | 38 | enum reg_class cl; |
f62a15e3 BS |
39 | |
40 | /* "Badness" of this alternative, computed from number of '?' and '!' | |
41 | characters in the constraint string. */ | |
42 | unsigned int reject; | |
43 | ||
44 | /* -1 if no matching constraint was found, or an operand number. */ | |
45 | int matches; | |
46 | /* The same information, but reversed: -1 if this operand is not | |
47 | matched by any other, or the operand number of the operand that | |
48 | matches this one. */ | |
49 | int matched; | |
50 | ||
51 | /* Nonzero if '&' was found in the constraint string. */ | |
52 | unsigned int earlyclobber:1; | |
a4edaf83 AK |
53 | /* Nonzero if TARGET_MEM_CONSTRAINT was found in the constraint |
54 | string. */ | |
0c20a65f | 55 | unsigned int memory_ok:1; |
f62a15e3 | 56 | /* Nonzero if 'o' was found in the constraint string. */ |
0c20a65f | 57 | unsigned int offmem_ok:1; |
f62a15e3 BS |
58 | /* Nonzero if 'V' was found in the constraint string. */ |
59 | unsigned int nonoffmem_ok:1; | |
60 | /* Nonzero if '<' was found in the constraint string. */ | |
61 | unsigned int decmem_ok:1; | |
62 | /* Nonzero if '>' was found in the constraint string. */ | |
63 | unsigned int incmem_ok:1; | |
541f7d56 BS |
64 | /* Nonzero if 'p' was found in the constraint string. */ |
65 | unsigned int is_address:1; | |
f62a15e3 BS |
66 | /* Nonzero if 'X' was found in the constraint string, or if the constraint |
67 | string for this alternative was empty. */ | |
68 | unsigned int anything_ok:1; | |
69 | }; | |
70 | ||
71 | ||
0c20a65f AJ |
72 | extern void init_recog (void); |
73 | extern void init_recog_no_volatile (void); | |
0c20a65f | 74 | extern int check_asm_operands (rtx); |
eca72963 | 75 | extern int asm_operand_ok (rtx, const char *, const char **); |
95e88efd JH |
76 | extern bool validate_change (rtx, rtx *, rtx, bool); |
77 | extern bool validate_unshare_change (rtx, rtx *, rtx, bool); | |
a52b023a | 78 | extern bool canonicalize_change_group (rtx insn, rtx x); |
0c20a65f | 79 | extern int insn_invalid_p (rtx); |
7d22e898 | 80 | extern int verify_changes (int); |
0a634832 | 81 | extern void confirm_change_group (void); |
0c20a65f AJ |
82 | extern int apply_change_group (void); |
83 | extern int num_validated_changes (void); | |
84 | extern void cancel_changes (int); | |
85 | extern int constrain_operands (int); | |
86 | extern int constrain_operands_cached (int); | |
09e881c9 BE |
87 | extern int memory_address_addr_space_p (enum machine_mode, rtx, addr_space_t); |
88 | #define memory_address_p(mode,addr) \ | |
89 | memory_address_addr_space_p ((mode), (addr), ADDR_SPACE_GENERIC) | |
90 | extern int strict_memory_address_addr_space_p (enum machine_mode, rtx, | |
91 | addr_space_t); | |
92 | #define strict_memory_address_p(mode,addr) \ | |
93 | strict_memory_address_addr_space_p ((mode), (addr), ADDR_SPACE_GENERIC) | |
7acf4da6 | 94 | extern int validate_replace_rtx_subexp (rtx, rtx, rtx, rtx *); |
0c20a65f | 95 | extern int validate_replace_rtx (rtx, rtx, rtx); |
e855c69d AB |
96 | extern int validate_replace_rtx_part (rtx, rtx, rtx *, rtx); |
97 | extern int validate_replace_rtx_part_nosimplify (rtx, rtx, rtx *, rtx); | |
0c20a65f | 98 | extern void validate_replace_rtx_group (rtx, rtx, rtx); |
0c20a65f | 99 | extern void validate_replace_src_group (rtx, rtx, rtx); |
8cd37d0b | 100 | extern bool validate_simplify_insn (rtx insn); |
0c20a65f | 101 | extern int num_changes_pending (void); |
523bb0ba | 102 | #ifdef HAVE_cc0 |
0c20a65f | 103 | extern int next_insn_tests_no_inequality (rtx); |
523bb0ba | 104 | #endif |
0c20a65f | 105 | extern int reg_fits_class_p (rtx, enum reg_class, int, enum machine_mode); |
0c20a65f | 106 | |
0c20a65f AJ |
107 | extern int offsettable_memref_p (rtx); |
108 | extern int offsettable_nonstrict_memref_p (rtx); | |
09e881c9 BE |
109 | extern int offsettable_address_addr_space_p (int, enum machine_mode, rtx, |
110 | addr_space_t); | |
111 | #define offsettable_address_p(strict,mode,addr) \ | |
112 | offsettable_address_addr_space_p ((strict), (mode), (addr), \ | |
113 | ADDR_SPACE_GENERIC) | |
cbda7dc6 | 114 | extern bool mode_dependent_address_p (rtx); |
0c20a65f AJ |
115 | |
116 | extern int recog (rtx, rtx, int *); | |
9fcdd891 | 117 | #ifndef GENERATOR_FILE |
f5523e6d | 118 | static inline int recog_memoized (rtx insn); |
9fcdd891 | 119 | #endif |
0c20a65f AJ |
120 | extern void add_clobbers (rtx, int); |
121 | extern int added_clobbers_hard_reg_p (int); | |
122 | extern void insn_extract (rtx); | |
123 | extern void extract_insn (rtx); | |
124 | extern void extract_constrain_insn_cached (rtx); | |
125 | extern void extract_insn_cached (rtx); | |
126 | extern void preprocess_constraints (void); | |
127 | extern rtx peep2_next_insn (int); | |
128 | extern int peep2_regno_dead_p (int, int); | |
129 | extern int peep2_reg_dead_p (int, rtx); | |
23280139 | 130 | #ifdef CLEAR_HARD_REG_SET |
0c20a65f AJ |
131 | extern rtx peep2_find_free_register (int, int, const char *, |
132 | enum machine_mode, HARD_REG_SET *); | |
23280139 | 133 | #endif |
0c20a65f | 134 | extern rtx peephole2_insns (rtx, rtx, int *); |
64a93ac5 | 135 | |
0c20a65f AJ |
136 | extern int store_data_bypass_p (rtx, rtx); |
137 | extern int if_test_bypass_p (rtx, rtx); | |
b37c2614 | 138 | |
9fcdd891 | 139 | #ifndef GENERATOR_FILE |
f5523e6d MA |
140 | /* Try recognizing the instruction INSN, |
141 | and return the code number that results. | |
142 | Remember the code so that repeated calls do not | |
143 | need to spend the time for actual rerecognition. | |
144 | ||
145 | This function is the normal interface to instruction recognition. | |
146 | The automatically-generated function `recog' is normally called | |
425de739 | 147 | through this one. */ |
f5523e6d MA |
148 | |
149 | static inline int | |
150 | recog_memoized (rtx insn) | |
151 | { | |
152 | if (INSN_CODE (insn) < 0) | |
153 | INSN_CODE (insn) = recog (PATTERN (insn), insn, 0); | |
154 | return INSN_CODE (insn); | |
155 | } | |
9fcdd891 | 156 | #endif |
f5523e6d | 157 | |
7ac28727 AK |
158 | /* Skip chars until the next ',' or the end of the string. This is |
159 | useful to skip alternatives in a constraint string. */ | |
160 | static inline const char * | |
161 | skip_alternative (const char *p) | |
162 | { | |
163 | const char *r = p; | |
164 | while (*r != '\0' && *r != ',') | |
165 | r++; | |
166 | if (*r == ',') | |
167 | r++; | |
168 | return r; | |
169 | } | |
170 | ||
64a93ac5 | 171 | /* Nonzero means volatile operands are recognized. */ |
64a93ac5 CH |
172 | extern int volatile_ok; |
173 | ||
0a578fee BS |
174 | /* Set by constrain_operands to the number of the alternative that |
175 | matched. */ | |
176 | extern int which_alternative; | |
177 | ||
64a93ac5 CH |
178 | /* The following vectors hold the results from insn_extract. */ |
179 | ||
1ccbefce RH |
180 | struct recog_data |
181 | { | |
182 | /* It is very tempting to make the 5 operand related arrays into a | |
183 | structure and index on that. However, to be source compatible | |
184 | with all of the existing md file insn constraints and output | |
185 | templates, we need `operand' as a flat array. Without that | |
186 | member, making an array for the rest seems pointless. */ | |
64a93ac5 | 187 | |
1ccbefce RH |
188 | /* Gives value of operand N. */ |
189 | rtx operand[MAX_RECOG_OPERANDS]; | |
64a93ac5 | 190 | |
1ccbefce RH |
191 | /* Gives location where operand N was found. */ |
192 | rtx *operand_loc[MAX_RECOG_OPERANDS]; | |
64a93ac5 | 193 | |
1ccbefce RH |
194 | /* Gives the constraint string for operand N. */ |
195 | const char *constraints[MAX_RECOG_OPERANDS]; | |
64a93ac5 | 196 | |
6ddfdb0f BS |
197 | /* Nonzero if operand N is a match_operator or a match_parallel. */ |
198 | char is_operator[MAX_RECOG_OPERANDS]; | |
199 | ||
1ccbefce RH |
200 | /* Gives the mode of operand N. */ |
201 | enum machine_mode operand_mode[MAX_RECOG_OPERANDS]; | |
0a578fee | 202 | |
1ccbefce RH |
203 | /* Gives the type (in, out, inout) for operand N. */ |
204 | enum op_type operand_type[MAX_RECOG_OPERANDS]; | |
0a578fee | 205 | |
1ccbefce RH |
206 | /* Gives location where the Nth duplicate-appearance of an operand |
207 | was found. This is something that matched MATCH_DUP. */ | |
208 | rtx *dup_loc[MAX_DUP_OPERANDS]; | |
0a578fee | 209 | |
1ccbefce RH |
210 | /* Gives the operand number that was duplicated in the Nth |
211 | duplicate-appearance of an operand. */ | |
88e6fdcb | 212 | char dup_num[MAX_DUP_OPERANDS]; |
0a578fee | 213 | |
88e6fdcb | 214 | /* ??? Note that these are `char' instead of `unsigned char' to (try to) |
0c20a65f | 215 | avoid certain lossage from K&R C, wherein `unsigned char' default |
88e6fdcb RH |
216 | promotes to `unsigned int' instead of `int' as in ISO C. As of 1999, |
217 | the most common places to bootstrap from K&R C are SunOS and HPUX, | |
218 | both of which have signed characters by default. The only other | |
219 | supported natives that have both K&R C and unsigned characters are | |
220 | ROMP and Irix 3, and neither have been seen for a while, but do | |
221 | continue to consider unsignedness when performing arithmetic inside | |
222 | a comparison. */ | |
223 | ||
1ccbefce | 224 | /* The number of operands of the insn. */ |
88e6fdcb | 225 | char n_operands; |
0a578fee | 226 | |
1ccbefce | 227 | /* The number of MATCH_DUPs in the insn. */ |
88e6fdcb | 228 | char n_dups; |
0eadeb15 | 229 | |
1ccbefce | 230 | /* The number of alternatives in the constraints for the insn. */ |
88e6fdcb | 231 | char n_alternatives; |
d90ffc8d | 232 | |
54f044eb JJ |
233 | /* True if insn is ASM_OPERANDS. */ |
234 | bool is_asm; | |
235 | ||
7ac28727 AK |
236 | /* Specifies whether an insn alternative is enabled using the |
237 | `enabled' attribute in the insn pattern definition. For back | |
238 | ends not using the `enabled' attribute the array fields are | |
239 | always set to `true' in expand_insn. */ | |
240 | bool alternative_enabled_p [MAX_RECOG_ALTERNATIVES]; | |
241 | ||
d90ffc8d JH |
242 | /* In case we are caching, hold insn data was generated for. */ |
243 | rtx insn; | |
1ccbefce RH |
244 | }; |
245 | ||
246 | extern struct recog_data recog_data; | |
0a578fee | 247 | |
f62a15e3 BS |
248 | /* Contains a vector of operand_alternative structures for every operand. |
249 | Set up by preprocess_constraints. */ | |
b0983bb9 | 250 | extern struct operand_alternative recog_op_alt[MAX_RECOG_OPERANDS][MAX_RECOG_ALTERNATIVES]; |
f62a15e3 | 251 | |
a995e389 | 252 | /* A table defined in insn-output.c that give information about |
64a93ac5 CH |
253 | each insn-code value. */ |
254 | ||
0c20a65f AJ |
255 | typedef int (*insn_operand_predicate_fn) (rtx, enum machine_mode); |
256 | typedef const char * (*insn_output_fn) (rtx *, rtx); | |
257 | typedef rtx (*insn_gen_fn) (rtx, ...); | |
64a93ac5 | 258 | |
a995e389 RH |
259 | struct insn_operand_data |
260 | { | |
8b60264b | 261 | const insn_operand_predicate_fn predicate; |
64a93ac5 | 262 | |
8b60264b | 263 | const char *const constraint; |
64a93ac5 | 264 | |
7e7c843f | 265 | ENUM_BITFIELD(machine_mode) const mode : 16; |
a995e389 | 266 | |
8b60264b | 267 | const char strict_low; |
dfac187e | 268 | |
6ddfdb0f BS |
269 | const char is_operator; |
270 | ||
8b60264b | 271 | const char eliminable; |
a995e389 | 272 | }; |
64a93ac5 | 273 | |
4bbf910e RH |
274 | /* Legal values for insn_data.output_format. Indicate what type of data |
275 | is stored in insn_data.output. */ | |
276 | #define INSN_OUTPUT_FORMAT_NONE 0 /* abort */ | |
277 | #define INSN_OUTPUT_FORMAT_SINGLE 1 /* const char * */ | |
278 | #define INSN_OUTPUT_FORMAT_MULTI 2 /* const char * const * */ | |
279 | #define INSN_OUTPUT_FORMAT_FUNCTION 3 /* const char * (*)(...) */ | |
280 | ||
f12c802a | 281 | struct insn_data_d |
a995e389 | 282 | { |
8b60264b | 283 | const char *const name; |
3897f229 JM |
284 | #if HAVE_DESIGNATED_INITIALIZERS |
285 | union { | |
286 | const char *single; | |
287 | const char *const *multi; | |
288 | insn_output_fn function; | |
289 | } output; | |
290 | #else | |
291 | struct { | |
292 | const char *single; | |
293 | const char *const *multi; | |
294 | insn_output_fn function; | |
295 | } output; | |
296 | #endif | |
8b60264b KG |
297 | const insn_gen_fn genfun; |
298 | const struct insn_operand_data *const operand; | |
64a93ac5 | 299 | |
8b60264b KG |
300 | const char n_operands; |
301 | const char n_dups; | |
302 | const char n_alternatives; | |
303 | const char output_format; | |
a995e389 | 304 | }; |
64a93ac5 | 305 | |
f12c802a | 306 | extern const struct insn_data_d insn_data[]; |
0cd6c85a | 307 | extern int peep2_current_count; |