1 /* ia64-gen.c -- Generate a shrunk set of opcode tables
2 Copyright 1999, 2000 Free Software Foundation, Inc.
3 Written by Bob Manson, Cygnus Solutions, <manson@cygnus.com>
5 This file is part of GDB, GAS, and the GNU binutils.
7 GDB, GAS, and the GNU binutils are free software; you can redistribute
8 them and/or modify them under the terms of the GNU General Public
9 License as published by the Free Software Foundation; either version
10 2, or (at your option) any later version.
12 GDB, GAS, and the GNU binutils are distributed in the hope that they
13 will be useful, but WITHOUT ANY WARRANTY; without even the implied
14 warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
15 the GNU General Public License for more details.
17 You should have received a copy of the GNU General Public License
18 along with this file; see the file COPYING. If not, write to the
19 Free Software Foundation, 59 Temple Place - Suite 330, Boston, MA
22 /* While the ia64-opc-* set of opcode tables are easy to maintain,
23 they waste a tremendous amount of space. ia64-gen rearranges the
24 instructions into a directed acyclic graph (DAG) of instruction opcodes and
25 their possible completers, as well as compacting the set of strings used.
27 The disassembler table consists of a state machine that does
28 branching based on the bits of the opcode being disassembled. The
29 state encodings have been chosen to minimize the amount of space
32 The resource table is constructed based on some text dependency tables,
33 which are also easier to maintain than the final representation.
41 #include "libiberty.h"
44 #include "ia64-opc-a.c"
45 #include "ia64-opc-i.c"
46 #include "ia64-opc-m.c"
47 #include "ia64-opc-b.c"
48 #include "ia64-opc-f.c"
49 #include "ia64-opc-x.c"
50 #include "ia64-opc-d.c"
54 #define tmalloc(X) (X *) xmalloc (sizeof (X))
56 /* The main opcode table entry. Each entry is a unique combination of
57 name and flags (no two entries in the table compare as being equal
61 /* The base name of this opcode. The names of its completers are
62 appended to it to generate the full instruction name. */
63 struct string_entry *name;
64 /* The base opcode entry. Which one to use is a fairly arbitrary choice;
65 it uses the first one passed to add_opcode_entry. */
66 struct ia64_opcode *opcode;
67 /* The list of completers that can be applied to this opcode. */
68 struct completer_entry *completers;
69 /* Next entry in the chain. */
70 struct main_entry *next;
71 /* Index in the main table. */
73 } *maintable, **ordered_table;
78 /* The set of possible completers for an opcode. */
79 struct completer_entry
81 /* This entry's index in the ia64_completer_table[] array. */
84 /* The name of the completer. */
85 struct string_entry *name;
87 /* This entry's parent. */
88 struct completer_entry *parent;
90 /* Set if this is a terminal completer (occurs at the end of an
94 /* An alternative completer. */
95 struct completer_entry *alternative;
97 /* Additional completers that can be appended to this one. */
98 struct completer_entry *addl_entries;
100 /* Before compute_completer_bits () is invoked, this contains the actual
101 instruction opcode for this combination of opcode and completers.
102 Afterwards, it contains those bits that are different from its
106 /* Bits set to 1 correspond to those bits in this completer's opcode
107 that are different from its parent completer's opcode (or from
108 the base opcode if the entry is the root of the opcode's completer
109 list). This field is filled in by compute_completer_bits (). */
112 /* Index into the opcode dependency list, or -1 if none. */
115 /* Remember the order encountered in the opcode tables. */
119 /* One entry in the disassembler name table. */
122 /* The index into the ia64_name_dis array for this entry. */
125 /* The index into the main_table[] array. */
128 /* The disassmbly priority of this entry. */
131 /* The completer_index value for this entry. */
134 /* How many other entries share this decode. */
137 /* The next entry sharing the same decode. */
138 struct disent *nexte;
140 /* The next entry in the name list. */
141 struct disent *next_ent;
142 } *disinsntable = NULL;
144 /* A state machine that will eventually be used to generate the
145 disassembler table. */
148 struct disent *disent;
149 struct bittree *bits[3]; /* 0, 1, and X (don't care) */
154 /* The string table contains all opcodes and completers sorted in
155 alphabetical order. */
157 /* One entry in the string table. */
160 /* The index in the ia64_strings[] array for this entry. */
162 /* And the string. */
164 } **string_table = NULL;
166 int strtabtotlen = 0;
169 /* resource dependency entries */
172 char *name; /* resource name */
174 mode:2, /* RAW, WAW, or WAR */
175 semantics:3; /* dependency semantics */
176 char *extra; /* additional semantics info */
178 int total_chks; /* total #of terminal insns */
179 int *chks; /* insn classes which read (RAW), write
180 (WAW), or write (WAR) this rsrc */
181 int *chknotes; /* dependency notes for each class */
183 int total_regs; /* total #of terminal insns */
184 int *regs; /* insn class which write (RAW), write2
185 (WAW), or read (WAR) this rsrc */
186 int *regnotes; /* dependency notes for each class */
188 int waw_special; /* special WAW dependency note */
191 static int rdepslen = 0;
192 static int rdepstotlen = 0;
194 /* array of all instruction classes */
197 char *name; /* instruction class name */
198 int is_class; /* is a class, not a terminal */
200 int *subs; /* other classes within this class */
202 int xsubs[4]; /* exclusions */
203 char *comment; /* optional comment */
204 int note; /* optional note */
205 int terminal_resolved; /* did we match this with anything? */
206 int orphan; /* detect class orphans */
209 static int iclen = 0;
210 static int ictotlen = 0;
212 /* an opcode dependency (chk/reg pair of dependency lists) */
215 int chk; /* index into dlists */
216 int reg; /* index into dlists */
219 static int opdeplen = 0;
220 static int opdeptotlen = 0;
222 /* a generic list of dependencies w/notes encoded. these may be shared. */
226 unsigned short *deps;
229 static int dlistlen = 0;
230 static int dlisttotlen = 0;
232 /* add NAME to the resource table, where TYPE is RAW or WAW */
234 insert_resource (const char *name, enum ia64_dependency_mode type)
236 if (rdepslen == rdepstotlen)
239 rdeps = (struct rdep **)
240 xrealloc (rdeps, sizeof(struct rdep **) * rdepstotlen);
242 rdeps[rdepslen] = tmalloc(struct rdep);
243 memset((void *)rdeps[rdepslen], 0, sizeof(struct rdep));
244 rdeps[rdepslen]->name = xstrdup (name);
245 rdeps[rdepslen]->mode = type;
246 rdeps[rdepslen]->waw_special = 0;
248 return rdeps[rdepslen++];
251 /* are the lists of dependency indexes equivalent? */
253 deplist_equals (struct deplist *d1, struct deplist *d2)
257 if (d1->len != d2->len)
260 for (i=0;i < d1->len;i++)
262 if (d1->deps[i] != d2->deps[i])
269 /* add the list of dependencies to the list of dependency lists */
271 insert_deplist(int count, unsigned short *deps)
273 /* sort the list, then see if an equivalent list exists already.
274 this results in a much smaller set of dependency lists
276 struct deplist *list;
280 memset ((void *)set, 0, sizeof(set));
281 for (i=0;i < count;i++)
284 for (i=0;i < (int)sizeof(set);i++)
288 list = tmalloc(struct deplist);
290 list->deps = (unsigned short *)malloc (sizeof(unsigned short) * count);
291 for (i=0, count=0;i < (int)sizeof(set);i++)
295 list->deps[count++] = i;
299 /* does this list exist already? */
300 for (i=0;i < dlistlen;i++)
302 if (deplist_equals (list, dlists[i]))
310 if (dlistlen == dlisttotlen)
313 dlists = (struct deplist **)
314 xrealloc (dlists, sizeof(struct deplist **) * dlisttotlen);
316 dlists[dlistlen] = list;
321 /* add the given pair of dependency lists to the opcode dependency list */
323 insert_dependencies (int nchks, unsigned short *chks,
324 int nregs, unsigned short *regs)
332 regind = insert_deplist (nregs, regs);
334 chkind = insert_deplist (nchks, chks);
336 for (i=0;i < opdeplen;i++)
338 if (opdeps[i]->chk == chkind
339 && opdeps[i]->reg == regind)
342 pair = tmalloc(struct opdep);
346 if (opdeplen == opdeptotlen)
349 opdeps = (struct opdep **)
350 xrealloc (opdeps, sizeof(struct opdep **) * opdeptotlen);
352 opdeps[opdeplen] = pair;
358 mark_used (struct iclass *ic, int clear_terminals)
364 ic->terminal_resolved = 1;
366 for (i=0;i < ic->nsubs;i++)
368 mark_used (ics[ic->subs[i]], clear_terminals);
370 for (i=0;i < ic->nxsubs;i++)
372 mark_used (ics[ic->xsubs[i]], clear_terminals);
376 /* look up an instruction class; if CREATE make a new one if none found;
377 returns the index into the insn class array */
379 fetch_insn_class(const char *full_name, int create)
389 if (strncmp (full_name, "IC:", 3) == 0)
391 name = xstrdup (full_name + 3);
395 name = xstrdup (full_name);
397 if ((xsect = strchr(name, '\\')) != NULL)
399 if ((comment = strchr(name, '[')) != NULL)
401 if ((notestr = strchr(name, '+')) != NULL)
404 /* If it is a composite class, then ignore comments and notes that come after
405 the '\\', since they don't apply to the part we are decoding now. */
417 note = atoi (notestr + 1);
418 if ((nextnotestr = strchr (notestr + 1, '+')) != NULL)
420 if (strcmp (notestr, "+1+13") == 0)
422 else if (!xsect || nextnotestr < xsect)
423 fprintf (stderr, "Warning: multiple note %s not handled\n",
428 /* If it's a composite class, leave the notes and comments in place so that
429 we have a unique name for the composite class. Otherwise, we remove
439 for (i=0;i < iclen;i++)
440 if (strcmp(name, ics[i]->name) == 0
441 && ((comment == NULL && ics[i]->comment == NULL)
442 || (comment != NULL && ics[i]->comment != NULL
443 && strncmp (ics[i]->comment, comment,
444 strlen (ics[i]->comment)) == 0))
445 && note == ics[i]->note)
451 /* doesn't exist, so make a new one */
452 if (iclen == ictotlen)
455 ics = (struct iclass **)
456 xrealloc(ics, (ictotlen)*sizeof(struct iclass *));
459 ics[ind] = tmalloc(struct iclass);
460 memset((void *)ics[ind], 0, sizeof(struct iclass));
461 ics[ind]->name = xstrdup(name);
462 ics[ind]->is_class = is_class;
463 ics[ind]->orphan = 1;
467 ics[ind]->comment = xstrdup (comment + 1);
468 ics[ind]->comment[strlen(ics[ind]->comment)-1] = 0;
471 ics[ind]->note = note;
473 /* if it's a composite class, there's a comment or note, look for an
474 existing class or terminal with the same name. */
475 if ((xsect || comment || notestr) && is_class)
477 /* First, populate with the class we're based on. */
478 char *subname = name;
486 ics[ind]->subs = tmalloc(int);
487 ics[ind]->subs[0] = fetch_insn_class (subname, 1);;
492 char *subname = xsect + 1;
493 xsect = strchr (subname, '\\');
496 ics[ind]->xsubs[ics[ind]->nxsubs] = fetch_insn_class (subname,1);
504 /* for sorting a class's sub-class list only; make sure classes appear before
507 sub_compare (const void *e1, const void *e2)
509 struct iclass *ic1 = ics[*(int *)e1];
510 struct iclass *ic2 = ics[*(int *)e2];
517 else if (ic2->is_class)
520 return strcmp (ic1->name, ic2->name);
526 FILE *fp = fopen("ia64-ic.tbl", "r");
530 fprintf (stderr, "Can't find ia64-ic.tbl for reading\n");
534 /* discard first line */
535 fgets (buf, sizeof(buf), fp);
543 if (fgets (buf, sizeof(buf), fp) == NULL)
546 while (isspace(buf[strlen(buf)-1]))
547 buf[strlen(buf)-1] = '\0';
553 if (tmp == buf + sizeof(buf))
558 iclass = fetch_insn_class(name, 1);
559 ics[iclass]->is_class = 1;
561 if (strcmp (name, "none") == 0)
563 ics[iclass]->is_class = 0;
564 ics[iclass]->terminal_resolved = 1;
568 /* for this class, record all sub-classes */
574 while (*tmp && isspace(*tmp))
577 if (tmp == buf + sizeof(buf))
581 while (*tmp && *tmp != ',')
584 if (tmp == buf + sizeof(buf))
590 ics[iclass]->subs = (int *)
591 xrealloc((void *)ics[iclass]->subs,
592 (ics[iclass]->nsubs+1)*sizeof(int));
594 sub = fetch_insn_class(subname, 1);
595 ics[iclass]->subs = (int *)
596 xrealloc(ics[iclass]->subs, (ics[iclass]->nsubs+1)*sizeof(int));
597 ics[iclass]->subs[ics[iclass]->nsubs++] = sub;
599 /* make sure classes come before terminals */
600 qsort ((void *)ics[iclass]->subs,
601 ics[iclass]->nsubs, sizeof(int), sub_compare);
607 printf ("%d classes\n", iclen);
611 /* extract the insn classes from the given line */
613 parse_resource_users(ref, usersp, nusersp, notesp)
620 char *line = xstrdup (ref);
622 int *users = *usersp;
623 int count = *nusersp;
624 int *notes = *notesp;
636 while (isspace(*tmp))
639 while (*tmp && *tmp != ',')
644 xsect = strchr(name, '\\');
645 if ((notestr = strstr(name, "+")) != NULL)
648 note = atoi (notestr + 1);
649 if ((nextnotestr = strchr (notestr + 1, '+')) != NULL)
651 /* note 13 always implies note 1 */
652 if (strcmp (notestr, "+1+13") == 0)
654 else if (!xsect || nextnotestr < xsect)
655 fprintf (stderr, "Warning: multiple note %s not handled\n",
664 /* All classes are created when the insn class table is parsed;
665 Individual instructions might not appear until the dependency tables
666 are read. Only create new classes if it's *not* an insn class,
667 or if it's a composite class (which wouldn't necessarily be in the IC
670 if (strncmp(name, "IC:", 3) != 0 || xsect != NULL)
673 iclass = fetch_insn_class(name, create);
677 xrealloc ((void *)users,(count+1)*sizeof(int));
679 xrealloc ((void *)notes,(count+1)*sizeof(int));
681 users[count++] = iclass;
682 mark_used (ics[iclass], 0);
687 printf("Class %s not found\n", name);
690 /* update the return values */
699 parse_semantics (char *sem)
701 if (strcmp (sem, "none") == 0)
702 return IA64_DVS_NONE;
703 else if (strcmp (sem, "implied") == 0)
704 return IA64_DVS_IMPLIED;
705 else if (strcmp (sem, "impliedF") == 0)
706 return IA64_DVS_IMPLIEDF;
707 else if (strcmp (sem, "data") == 0)
708 return IA64_DVS_DATA;
709 else if (strcmp (sem, "instr") == 0)
710 return IA64_DVS_INSTR;
711 else if (strcmp (sem, "specific") == 0)
712 return IA64_DVS_SPECIFIC;
713 else if (strcmp (sem, "stop") == 0)
714 return IA64_DVS_STOP;
716 return IA64_DVS_OTHER;
720 add_dep (const char *name, const char *chk, const char *reg,
721 int semantics, int mode, char *extra, int flag)
725 rs = insert_resource (name, mode);
726 parse_resource_users (chk, &rs->chks, &rs->nchks,
728 parse_resource_users (reg, &rs->regs, &rs->nregs,
730 rs->semantics = semantics;
732 rs->waw_special = flag;
736 load_depfile (const char *filename, enum ia64_dependency_mode mode)
738 FILE *fp = fopen(filename, "r");
742 fprintf (stderr, "Can't find %s for reading\n", filename);
746 fgets(buf, sizeof(buf), fp);
754 if (fgets (buf, sizeof(buf), fp) == NULL)
757 while (isspace(buf[strlen(buf)-1]))
758 buf[strlen(buf)-1] = '\0';
765 while (isspace (*tmp))
768 tmp = strchr (tmp, ';');
772 while (isspace (*tmp))
775 tmp = strchr (tmp, ';');
779 while (isspace (*tmp))
781 semantics = parse_semantics (tmp);
782 extra = semantics == IA64_DVS_OTHER ? xstrdup (tmp) : NULL;
784 /* For WAW entries, if the chks and regs differ, we need to enter the
785 entries in both positions so that the tables will be parsed properly,
786 without a lot of extra work */
787 if (mode == IA64_DV_WAW && strcmp (regp, chkp) != 0)
789 add_dep (name, chkp, regp, semantics, mode, extra, 0);
790 add_dep (name, regp, chkp, semantics, mode, extra, 1);
794 add_dep (name, chkp, regp, semantics, mode, extra, 0);
803 load_depfile ("ia64-raw.tbl", IA64_DV_RAW);
804 load_depfile ("ia64-waw.tbl", IA64_DV_WAW);
805 load_depfile ("ia64-war.tbl", IA64_DV_WAR);
808 printf ("%d RAW/WAW/WAR dependencies\n", rdepslen);
811 /* is the given operand an indirect register file operand? */
813 irf_operand (int op, const char *field)
817 return op == IA64_OPND_RR_R3 || op == IA64_OPND_DBR_R3
818 || op == IA64_OPND_IBR_R3 || op == IA64_OPND_PKR_R3
819 || op == IA64_OPND_PMC_R3 || op == IA64_OPND_PMD_R3
820 || op == IA64_OPND_MSR_R3 || op == IA64_OPND_CPUID_R3;
824 return ((op == IA64_OPND_RR_R3 && strstr (field, "rr"))
825 || (op == IA64_OPND_DBR_R3 && strstr (field, "dbr"))
826 || (op == IA64_OPND_IBR_R3 && strstr (field, "ibr"))
827 || (op == IA64_OPND_PKR_R3 && strstr (field, "pkr"))
828 || (op == IA64_OPND_PMC_R3 && strstr (field, "pmc"))
829 || (op == IA64_OPND_PMD_R3 && strstr (field, "pmd"))
830 || (op == IA64_OPND_MSR_R3 && strstr (field, "msr"))
831 || (op == IA64_OPND_CPUID_R3 && strstr (field, "cpuid")));
835 /* handle mov_ar, mov_br, mov_cr, mov_indirect, mov_ip, mov_pr, mov_psr, and
836 mov_um insn classes */
838 in_iclass_mov_x (struct ia64_opcode *idesc, struct iclass *ic,
839 const char *format, const char *field)
841 int plain_mov = strcmp (idesc->name, "mov") == 0;
852 int i = strcmp (idesc->name, "mov.i") == 0;
853 int m = strcmp (idesc->name, "mov.m") == 0;
854 int i2627 = i && idesc->operands[0] == IA64_OPND_AR3;
855 int i28 = i && idesc->operands[1] == IA64_OPND_AR3;
856 int m2930 = m && idesc->operands[0] == IA64_OPND_AR3;
857 int m31 = m && idesc->operands[1] == IA64_OPND_AR3;
858 int pseudo0 = plain_mov && idesc->operands[1] == IA64_OPND_AR3;
859 int pseudo1 = plain_mov && idesc->operands[0] == IA64_OPND_AR3;
863 return strstr (format, "I26") || strstr (format, "I27");
865 return strstr (format, "I28") != NULL;
867 return strstr (format, "M29") || strstr (format, "M30");
869 return strstr (format, "M31") != NULL;
870 if (pseudo0 || pseudo1)
876 int i21 = idesc->operands[0] == IA64_OPND_B1;
877 int i22 = plain_mov && idesc->operands[1] == IA64_OPND_B2;
879 return strstr (format, "I22") != NULL;
881 return strstr (format, "I21") != NULL;
886 int m32 = plain_mov && idesc->operands[0] == IA64_OPND_CR3;
887 int m33 = plain_mov && idesc->operands[1] == IA64_OPND_CR3;
889 return strstr (format, "M32") != NULL;
891 return strstr (format, "M33") != NULL;
895 if (ic->name[5] == 'n')
897 int m42 = plain_mov && irf_operand (idesc->operands[0], field);
898 int m43 = plain_mov && irf_operand (idesc->operands[1], field);
900 return strstr (format, "M42") != NULL;
902 return strstr (format, "M43") != NULL;
904 else if (ic->name[5] == 'p')
906 return idesc->operands[1] == IA64_OPND_IP;
912 if (ic->name[5] == 'r')
914 int i25 = plain_mov && idesc->operands[1] == IA64_OPND_PR;
915 int i23 = plain_mov && idesc->operands[0] == IA64_OPND_PR;
916 int i24 = plain_mov && idesc->operands[0] == IA64_OPND_PR_ROT;
918 return strstr (format, "I23") != NULL;
920 return strstr (format, "I24") != NULL;
922 return strstr (format, "I25") != NULL;
924 else if (ic->name[5] == 's')
926 int m35 = plain_mov && idesc->operands[0] == IA64_OPND_PSR_L;
927 int m36 = plain_mov && idesc->operands[1] == IA64_OPND_PSR;
929 return strstr (format, "M35") != NULL;
931 return strstr (format, "M36") != NULL;
938 int m35 = plain_mov && idesc->operands[0] == IA64_OPND_PSR_UM;
939 int m36 = plain_mov && idesc->operands[1] == IA64_OPND_PSR_UM;
941 return strstr (format, "M35") != NULL;
943 return strstr (format, "M36") != NULL;
951 /* is the given opcode in the given insn class? */
953 in_iclass(struct ia64_opcode *idesc, struct iclass *ic,
954 const char *format, const char *field, int *notep)
961 if (!strncmp (ic->comment, "Format", 6))
963 /* assume that the first format seen is the most restrictive, and
964 only keep a later one if it looks like it's more restrictive. */
967 if (strlen (ic->comment) < strlen (format))
969 fprintf (stderr, "Warning: most recent format '%s'\n"
970 "appears more restrictive than '%s'\n",
971 ic->comment, format);
972 format = ic->comment;
976 format = ic->comment;
978 else if (!strncmp (ic->comment, "Field", 5))
981 fprintf (stderr, "Overlapping field %s->%s\n",
987 /* an insn class matches anything that is the same followed by completers,
988 except when the absence and presence of completers constitutes different
990 if (ic->nsubs == 0 && ic->nxsubs == 0)
992 int is_mov = strncmp (idesc->name, "mov", 3) == 0;
993 int plain_mov = strcmp (idesc->name, "mov") == 0;
994 int len = strlen(ic->name);
996 resolved = ((strncmp (ic->name, idesc->name, len) == 0)
997 && (idesc->name[len] == '\0'
998 || idesc->name[len] == '.'));
1000 /* all break and nop variations must match exactly */
1002 (strcmp (ic->name, "break") == 0
1003 || strcmp (ic->name, "nop") == 0))
1004 resolved = strcmp (ic->name, idesc->name) == 0;
1006 /* assume restrictions in the FORMAT/FIELD negate resolution,
1007 unless specifically allowed by clauses in this block */
1008 if (resolved && field)
1010 /* check Field(sf)==sN against opcode sN */
1011 if (strstr(field, "(sf)==") != NULL)
1014 if ((sf = strstr (idesc->name, ".s")) != 0)
1016 resolved = strcmp (sf + 1, strstr (field, "==") + 2) == 0;
1019 /* check Field(lftype)==XXX */
1020 else if (strstr (field, "(lftype)") != NULL)
1022 if (strstr (idesc->name, "fault") != NULL)
1023 resolved = strstr (field, "fault") != NULL;
1025 resolved = strstr (field, "fault") == NULL;
1027 /* handle Field(ctype)==XXX */
1028 else if (strstr (field, "(ctype)") != NULL)
1030 if (strstr (idesc->name, "or.andcm"))
1031 resolved = strstr (field, "or.andcm") != NULL;
1032 else if (strstr (idesc->name, "and.orcm"))
1033 resolved = strstr (field, "and.orcm") != NULL;
1034 else if (strstr (idesc->name, "orcm"))
1035 resolved = strstr (field, "or orcm") != NULL;
1036 else if (strstr (idesc->name, "or"))
1037 resolved = strstr (field, "or orcm") != NULL;
1038 else if (strstr (idesc->name, "andcm"))
1039 resolved = strstr (field, "and andcm") != NULL;
1040 else if (strstr (idesc->name, "and"))
1041 resolved = strstr (field, "and andcm") != NULL;
1042 else if (strstr (idesc->name, "unc"))
1043 resolved = strstr (field, "unc") != NULL;
1045 resolved = strcmp (field, "Field(ctype)==") == 0;
1048 if (resolved && format)
1050 if (strncmp (idesc->name, "dep", 3) == 0
1051 && strstr (format, "I13") != NULL)
1052 resolved = idesc->operands[1] == IA64_OPND_IMM8;
1053 else if (strncmp (idesc->name, "chk", 3) == 0
1054 && strstr (format, "M21") != NULL)
1055 resolved = idesc->operands[0] == IA64_OPND_F2;
1056 else if (strncmp (idesc->name, "lfetch", 6) == 0)
1057 resolved = (strstr (format, "M14 M15") != NULL
1058 && (idesc->operands[1] == IA64_OPND_R2
1059 || idesc->operands[1] == IA64_OPND_IMM9b));
1060 else if (strncmp (idesc->name, "br.call", 7) == 0
1061 && strstr (format, "B5") != NULL)
1062 resolved = idesc->operands[1] == IA64_OPND_B2;
1063 else if (strncmp (idesc->name, "br.call", 7) == 0
1064 && strstr (format, "B3") != NULL)
1065 resolved = idesc->operands[1] == IA64_OPND_TGT25c;
1066 else if (strncmp (idesc->name, "brp", 3) == 0
1067 && strstr (format, "B7") != NULL)
1068 resolved = idesc->operands[0] == IA64_OPND_B2;
1069 else if (strcmp (ic->name, "invala") == 0)
1070 resolved = strcmp (idesc->name, ic->name) == 0;
1071 else if (strncmp (idesc->name, "st", 2) == 0
1072 && strstr (format, "M5") != NULL)
1073 resolved = idesc->flags & IA64_OPCODE_POSTINC;
1078 /* misc brl variations ('.cond' is optional);
1079 plain brl matches brl.cond */
1081 && (strcmp (idesc->name, "brl") == 0
1082 || strncmp (idesc->name, "brl.", 4) == 0)
1083 && strcmp (ic->name, "brl.cond") == 0)
1088 /* misc br variations ('.cond' is optional) */
1090 && (strcmp (idesc->name, "br") == 0
1091 || strncmp (idesc->name, "br.", 3) == 0)
1092 && strcmp (ic->name, "br.cond") == 0)
1095 resolved = (strstr (format, "B4") != NULL
1096 && idesc->operands[0] == IA64_OPND_B2)
1097 || (strstr (format, "B1") != NULL
1098 && idesc->operands[0] == IA64_OPND_TGT25c);
1103 /* probe variations */
1104 if (!resolved && strncmp (idesc->name, "probe", 5) == 0)
1106 resolved = strcmp (ic->name, "probe") == 0
1107 && !((strstr (idesc->name, "fault") != NULL)
1108 ^ (format && strstr (format, "M40") != NULL));
1110 /* mov variations */
1111 if (!resolved && is_mov)
1115 /* mov alias for fmerge */
1116 if (strcmp (ic->name, "fmerge") == 0)
1118 resolved = idesc->operands[0] == IA64_OPND_F1
1119 && idesc->operands[1] == IA64_OPND_F3;
1121 /* mov alias for adds (r3 or imm14) */
1122 else if (strcmp (ic->name, "adds") == 0)
1124 resolved = (idesc->operands[0] == IA64_OPND_R1
1125 && (idesc->operands[1] == IA64_OPND_R3
1126 || (idesc->operands[1] == IA64_OPND_IMM14)));
1128 /* mov alias for addl */
1129 else if (strcmp (ic->name, "addl") == 0)
1131 resolved = idesc->operands[0] == IA64_OPND_R1
1132 && idesc->operands[1] == IA64_OPND_IMM22;
1135 /* some variants of mov and mov.[im] */
1136 if (!resolved && strncmp (ic->name, "mov_", 4) == 0)
1138 resolved = in_iclass_mov_x (idesc, ic, format, field);
1142 /* keep track of this so we can flag any insn classes which aren't
1143 mapped onto at least one real insn */
1146 ic->terminal_resolved = 1;
1149 else for (i=0;i < ic->nsubs;i++)
1151 if (in_iclass(idesc, ics[ic->subs[i]], format, field, notep))
1154 for (j=0;j < ic->nxsubs;j++)
1156 if (in_iclass(idesc, ics[ic->xsubs[j]], NULL, NULL, NULL))
1160 printf ("%s is in IC %s\n",
1161 idesc->name, ic->name);
1167 /* If it's in this IC, add the IC note (if any) to the insn */
1170 if (ic->note && notep)
1172 if (*notep && *notep != ic->note)
1174 fprintf (stderr, "Warning: overwriting note %d with note %d"
1176 *notep, ic->note, ic->name);
1187 lookup_regindex (const char *name, int specifier)
1192 if (strstr (name, "[RSC]"))
1194 if (strstr (name, "[BSP]"))
1196 else if (strstr (name, "[BSPSTORE]"))
1198 else if (strstr (name, "[RNAT]"))
1200 else if (strstr (name, "[CCV]"))
1202 else if (strstr (name, "[ITC]"))
1204 else if (strstr (name, "[PFS]"))
1206 else if (strstr (name, "[LC]"))
1208 else if (strstr (name, "[EC]"))
1212 if (strstr (name, "[DCR]"))
1214 else if (strstr (name, "[ITM]"))
1216 else if (strstr (name, "[IVA]"))
1218 else if (strstr (name, "[PTA]"))
1220 else if (strstr (name, "[GPTA]"))
1222 else if (strstr (name, "[IPSR]"))
1224 else if (strstr (name, "[ISR]"))
1226 else if (strstr (name, "[IIP]"))
1228 else if (strstr (name, "[IFA]"))
1230 else if (strstr (name, "[ITIR]"))
1232 else if (strstr (name, "[IIPA]"))
1234 else if (strstr (name, "[IFS]"))
1236 else if (strstr (name, "[IIM]"))
1238 else if (strstr (name, "[IHA]"))
1240 else if (strstr (name, "[LID]"))
1242 else if (strstr (name, "[IVR]"))
1244 else if (strstr (name, "[TPR]"))
1246 else if (strstr (name, "[EOI]"))
1248 else if (strstr (name, "[ITV]"))
1250 else if (strstr (name, "[PMV]"))
1252 else if (strstr (name, "[CMCV]"))
1256 if (strstr (name, ".be"))
1258 else if (strstr (name, ".up"))
1260 else if (strstr (name, ".ac"))
1262 else if (strstr (name, ".mfl"))
1264 else if (strstr (name, ".mfh"))
1266 else if (strstr (name, ".ic"))
1268 else if (strstr (name, ".i"))
1270 else if (strstr (name, ".pk"))
1272 else if (strstr (name, ".dt"))
1274 else if (strstr (name, ".dfl"))
1276 else if (strstr (name, ".dfh"))
1278 else if (strstr (name, ".sp"))
1280 else if (strstr (name, ".pp"))
1282 else if (strstr (name, ".di"))
1284 else if (strstr (name, ".si"))
1286 else if (strstr (name, ".db"))
1288 else if (strstr (name, ".lp"))
1290 else if (strstr (name, ".tb"))
1292 else if (strstr (name, ".rt"))
1294 else if (strstr (name, ".cpl"))
1296 else if (strstr (name, ".rs"))
1298 else if (strstr (name, ".mc"))
1300 else if (strstr (name, ".it"))
1302 else if (strstr (name, ".id"))
1304 else if (strstr (name, ".da"))
1306 else if (strstr (name, ".dd"))
1308 else if (strstr (name, ".ss"))
1310 else if (strstr (name, ".ri"))
1312 else if (strstr (name, ".ed"))
1314 else if (strstr (name, ".bn"))
1316 else if (strstr (name, ".ia"))
1327 lookup_specifier (const char *name)
1329 if (strchr (name, '%'))
1331 if (strstr (name, "AR[K%]") != NULL)
1332 return IA64_RS_AR_K;
1333 if (strstr (name, "AR[UNAT]") != NULL)
1334 return IA64_RS_AR_UNAT;
1335 if (strstr (name, "AR%, % in 8") != NULL)
1337 if (strstr (name, "AR%, % in 48") != NULL)
1339 if (strstr (name, "BR%") != NULL)
1341 if (strstr (name, "CR[IRR%]") != NULL)
1342 return IA64_RS_CR_IRR;
1343 if (strstr (name, "CR[LRR%]") != NULL)
1344 return IA64_RS_CR_LRR;
1345 if (strstr (name, "CR%") != NULL)
1347 if (strstr (name, "FR%, % in 0") != NULL)
1349 if (strstr (name, "FR%, % in 2") != NULL)
1351 if (strstr (name, "GR%") != NULL)
1353 if (strstr (name, "PR%, % in 1 ") != NULL)
1355 if (strstr (name, "PR%, % in 16 ") != NULL)
1358 fprintf (stderr, "Warning! Don't know how to specify %% dependency %s\n",
1361 else if (strchr (name, '#'))
1363 if (strstr (name, "CPUID#") != NULL)
1364 return IA64_RS_CPUID;
1365 if (strstr (name, "DBR#") != NULL)
1367 if (strstr (name, "IBR#") != NULL)
1369 if (strstr (name, "MSR#") != NULL)
1371 if (strstr (name, "PKR#") != NULL)
1373 if (strstr (name, "PMC#") != NULL)
1375 if (strstr (name, "PMD#") != NULL)
1377 if (strstr (name, "RR#") != NULL)
1380 fprintf (stderr, "Warning! Don't know how to specify # dependency %s\n",
1383 else if (strncmp (name, "AR[FPSR]", 8) == 0)
1384 return IA64_RS_AR_FPSR;
1385 else if (strncmp (name, "AR[", 3) == 0)
1387 else if (strncmp (name, "CR[", 3) == 0)
1389 else if (strncmp (name, "PSR.", 4) == 0)
1391 else if (strcmp (name, "InService*") == 0)
1392 return IA64_RS_INSERVICE;
1393 else if (strcmp (name, "GR0") == 0)
1395 else if (strcmp (name, "CFM") == 0)
1397 else if (strcmp (name, "PR63") == 0)
1398 return IA64_RS_PR63;
1399 else if (strcmp (name, "RSE") == 0)
1406 print_dependency_table ()
1412 for (i=0;i < iclen;i++)
1414 if (ics[i]->is_class)
1418 fprintf (stderr, "Warning: IC:%s", ics[i]->name);
1419 if (ics[i]->comment)
1420 fprintf (stderr, "[%s]", ics[i]->comment);
1421 fprintf (stderr, " has no terminals or sub-classes\n");
1426 if (!ics[i]->terminal_resolved && !ics[i]->orphan)
1428 fprintf(stderr, "Warning: no insns mapped directly to "
1429 "terminal IC %s", ics[i]->name);
1430 if (ics[i]->comment)
1431 fprintf(stderr, "[%s] ", ics[i]->comment);
1432 fprintf(stderr, "\n");
1437 for (i=0;i < iclen;i++)
1441 mark_used (ics[i], 1);
1442 fprintf (stderr, "Warning: class %s is defined but not used\n",
1447 if (debug > 1) for (i=0;i < rdepslen;i++)
1449 static const char *mode_str[] = { "RAW", "WAW", "WAR" };
1450 if (rdeps[i]->total_chks == 0)
1452 fprintf (stderr, "Warning: rsrc %s (%s) has no chks%s\n",
1453 rdeps[i]->name, mode_str[rdeps[i]->mode],
1454 rdeps[i]->total_regs ? "" : " or regs");
1456 else if (rdeps[i]->total_regs == 0)
1458 fprintf (stderr, "Warning: rsrc %s (%s) has no regs\n",
1459 rdeps[i]->name, mode_str[rdeps[i]->mode]);
1464 /* the dependencies themselves */
1465 printf ("static const struct ia64_dependency\ndependencies[] = {\n");
1466 for (i=0;i < rdepslen;i++)
1468 /* '%', '#', AR[], CR[], or PSR. indicates we need to specify the actual
1470 int specifier = lookup_specifier (rdeps[i]->name);
1471 int regindex = lookup_regindex (rdeps[i]->name, specifier);
1473 printf (" { \"%s\", %d, %d, %d, %d, ",
1474 rdeps[i]->name, specifier,
1475 (int)rdeps[i]->mode, (int)rdeps[i]->semantics, regindex);
1476 if (rdeps[i]->semantics == IA64_DVS_OTHER)
1477 printf ("\"%s\", ", rdeps[i]->extra);
1484 /* and dependency lists */
1485 for (i=0;i < dlistlen;i++)
1488 printf ("static const short dep%d[] = {\n ", i);
1489 for (j=0;j < dlists[i]->len; j++)
1491 len += printf ("%d, ", dlists[i]->deps[j]);
1498 printf ("\n};\n\n");
1501 /* and opcode dependency list */
1502 printf ("#define NELS(X) (sizeof(X)/sizeof(X[0]))\n");
1503 printf ("static const struct ia64_opcode_dependency\n");
1504 printf ("op_dependencies[] = {\n");
1505 for (i=0;i < opdeplen;i++)
1508 if (opdeps[i]->chk == -1)
1509 printf ("0, NULL, ");
1511 printf ("NELS(dep%d), dep%d, ", opdeps[i]->chk, opdeps[i]->chk);
1512 if (opdeps[i]->reg == -1)
1513 printf ("0, NULL, ");
1515 printf ("NELS(dep%d), dep%d, ", opdeps[i]->reg, opdeps[i]->reg);
1522 /* Add STR to the string table. */
1524 static struct string_entry *
1528 int start = 0, end = strtablen;
1531 if (strtablen == strtabtotlen)
1534 string_table = (struct string_entry **)
1535 xrealloc (string_table,
1536 sizeof (struct string_entry **) * strtabtotlen);
1542 string_table[0] = tmalloc (struct string_entry);
1543 string_table[0]->s = xstrdup (str);
1544 string_table[0]->num = 0;
1545 return string_table[0];
1548 if (strcmp (str, string_table[strtablen - 1]->s) > 0)
1552 else if (strcmp (str, string_table[0]->s) < 0)
1562 i = (start + end) / 2;
1563 c = strcmp (str, string_table[i]->s);
1570 return string_table[i];
1582 for (; i > 0 && i < strtablen; i--)
1584 if (strcmp (str, string_table[i - 1]->s) > 0)
1589 for (; i < strtablen; i++)
1591 if (strcmp (str, string_table[i]->s) < 0)
1596 for (x = strtablen - 1; x >= i; x--)
1598 string_table[x + 1] = string_table[x];
1599 string_table[x + 1]->num = x + 1;
1601 string_table[i] = tmalloc (struct string_entry);
1602 string_table[i]->s = xstrdup (str);
1603 string_table[i]->num = i;
1605 return string_table[i];
1609 make_bittree_entry ()
1611 struct bittree *res = tmalloc (struct bittree);
1614 res->bits[0] = NULL;
1615 res->bits[1] = NULL;
1616 res->bits[2] = NULL;
1618 res->bits_to_skip = 0;
1623 add_dis_table_ent (which, insn, order, completer_index)
1624 struct disent *which;
1627 int completer_index;
1637 while (ent->nexte != NULL)
1641 ent = (ent->nexte = tmalloc (struct disent));
1645 ent = tmalloc (struct disent);
1646 ent->next_ent = disinsntable;
1653 ent->priority = order;
1655 while (completer_index != 1)
1657 ci = (ci << 1) | (completer_index & 1);
1658 completer_index >>= 1;
1660 ent->completer_index = ci;
1667 struct disent *ent = disinsntable;
1668 struct disent *prev = ent;
1670 ent->ournum = 32768;
1671 while ((ent = ent->next_ent) != NULL)
1673 ent->ournum = prev->ournum + prev->nextcnt + 1;
1679 insert_bit_table_ent (curr_ent, bit, opcode, mask,
1680 opcodenum, order, completer_index)
1681 struct bittree *curr_ent;
1687 int completer_index;
1691 struct bittree *next;
1695 struct disent *nent = add_dis_table_ent (curr_ent->disent,
1698 curr_ent->disent = nent;
1702 m = ((ia64_insn) 1) << bit;
1706 b = (opcode & m) ? 1 : 0;
1712 next = curr_ent->bits[b];
1715 next = make_bittree_entry ();
1716 curr_ent->bits[b] = next;
1718 insert_bit_table_ent (next, bit - 1, opcode, mask, opcodenum, order,
1723 add_dis_entry (first, opcode, mask, opcodenum, ent, completer_index)
1724 struct bittree *first;
1728 struct completer_entry *ent;
1729 int completer_index;
1731 if (completer_index & (1 << 20))
1738 ia64_insn newopcode = (opcode & (~ ent->mask)) | ent->bits;
1739 add_dis_entry (first, newopcode, mask, opcodenum, ent->addl_entries,
1740 (completer_index << 1) | 1);
1741 if (ent->is_terminal)
1743 insert_bit_table_ent (bittree, 40, newopcode, mask,
1744 opcodenum, opcode_count - ent->order - 1,
1745 (completer_index << 1) | 1);
1747 completer_index <<= 1;
1748 ent = ent->alternative;
1752 /* This optimization pass combines multiple "don't care" nodes. */
1754 compact_distree (ent)
1755 struct bittree *ent;
1757 #define IS_SKIP(ent) \
1758 ((ent->bits[2] !=NULL) \
1759 && (ent->bits[0] == NULL && ent->bits[1] == NULL && ent->skip_flag == 0))
1762 struct bittree *nent = ent;
1765 while (IS_SKIP (nent))
1768 nent = nent->bits[2];
1773 struct bittree *next = ent->bits[2];
1775 ent->bits[0] = nent->bits[0];
1776 ent->bits[1] = nent->bits[1];
1777 ent->bits[2] = nent->bits[2];
1778 ent->disent = nent->disent;
1780 ent->bits_to_skip = bitcnt;
1781 while (next != nent)
1783 struct bittree *b = next;
1784 next = next->bits[2];
1790 for (x = 0; x < 3; x++)
1792 struct bittree *i = ent->bits[x];
1795 compact_distree (i);
1800 static unsigned char *insn_list;
1801 static int insn_list_len = 0;
1802 static int tot_insn_list_len = 0;
1804 /* Generate the disassembler state machine corresponding to the tree
1808 struct bittree *ent;
1811 int our_offset = insn_list_len;
1813 int totbits = bitsused;
1816 int zero_dest = 0; /* initialize this with 0 to keep gcc quiet... */
1818 /* If this is a terminal entry, there's no point in skipping any
1820 if (ent->skip_flag && ent->bits[0] == NULL && ent->bits[1] == NULL &&
1821 ent->bits[2] == NULL)
1823 if (ent->disent == NULL)
1833 /* Calculate the amount of space needed for this entry, or at least
1834 a conservatively large approximation. */
1839 for (x = 1; x < 3; x++)
1841 if (ent->bits[x] != NULL)
1847 if (ent->disent != NULL)
1849 if (ent->bits[2] != NULL)
1856 /* Now allocate the space. */
1857 needed_bytes = (totbits + 7) / 8;
1858 if ((needed_bytes + insn_list_len) > tot_insn_list_len)
1860 tot_insn_list_len += 256;
1861 insn_list = (char *) xrealloc (insn_list, tot_insn_list_len);
1863 our_offset = insn_list_len;
1864 insn_list_len += needed_bytes;
1865 memset (insn_list + our_offset, 0, needed_bytes);
1867 /* Encode the skip entry by setting bit 6 set in the state op field,
1868 and store the # of bits to skip immediately after. */
1872 insn_list[our_offset + 0] |= 0x40 | ((ent->bits_to_skip >> 2) & 0xf);
1873 insn_list[our_offset + 1] |= ((ent->bits_to_skip & 3) << 6);
1876 #define IS_ONLY_IFZERO(ENT) \
1877 ((ENT)->bits[0] != NULL && (ENT)->bits[1] == NULL && (ENT)->bits[2] == NULL \
1878 && (ENT)->disent == NULL && (ENT)->skip_flag == 0)
1880 /* Store an "if (bit is zero)" instruction by setting bit 7 in the
1883 if (ent->bits[0] != NULL)
1885 struct bittree *nent = ent->bits[0];
1888 insn_list[our_offset] |= 0x80;
1890 /* We can encode sequences of multiple "if (bit is zero)" tests
1891 by storing the # of zero bits to check in the lower 3 bits of
1892 the instruction. However, this only applies if the state
1893 solely tests for a zero bit. */
1895 if (IS_ONLY_IFZERO (ent))
1897 while (IS_ONLY_IFZERO (nent) && zero_count < 7)
1899 nent = nent->bits[0];
1903 insn_list[our_offset + 0] |= zero_count;
1905 zero_dest = insn_list_len;
1906 gen_dis_table (nent);
1909 /* Now store the remaining tests. We also handle a sole "termination
1910 entry" by storing it as an "any bit" test. */
1912 for (x = 1; x < 3; x++)
1914 if (ent->bits[x] != NULL || (x == 2 && ent->disent != NULL))
1916 struct bittree *i = ent->bits[x];
1922 /* If the instruction being branched to only consists of
1923 a termination entry, use the termination entry as the
1924 place to branch to instead. */
1925 if (i->bits[0] == NULL && i->bits[1] == NULL
1926 && i->bits[2] == NULL && i->disent != NULL)
1928 idest = i->disent->ournum;
1933 idest = insn_list_len - our_offset;
1938 idest = ent->disent->ournum;
1941 /* If the destination offset for the if (bit is 1) test is less
1942 than 256 bytes away, we can store it as 8-bits instead of 16;
1943 the instruction has bit 5 set for the 16-bit address, and bit
1944 4 for the 8-bit address. Since we've already allocated 16
1945 bits for the address we need to deallocate the space.
1947 Note that branchings within the table are relative, and
1948 there are no branches that branch past our instruction yet
1949 so we do not need to adjust any other offsets. */
1955 int start = our_offset + bitsused / 8 + 1;
1957 memmove (insn_list + start,
1958 insn_list + start + 1,
1959 insn_list_len - (start + 1));
1964 insn_list[our_offset] |= 0x10;
1969 insn_list[our_offset] |= 0x20;
1974 /* An instruction which solely consists of a termination
1975 marker and whose disassembly name index is < 4096
1976 can be stored in 16 bits. The encoding is slightly
1977 odd; the upper 4 bits of the instruction are 0x3, and
1978 bit 3 loses its normal meaning. */
1980 if (ent->bits[0] == NULL && ent->bits[1] == NULL
1981 && ent->bits[2] == NULL && ent->skip_flag == 0
1982 && ent->disent != NULL
1983 && ent->disent->ournum < (32768 + 4096))
1985 int start = our_offset + bitsused / 8 + 1;
1987 memmove (insn_list + start,
1988 insn_list + start + 1,
1989 insn_list_len - (start + 1));
1995 insn_list[our_offset] |= 0x30;
2000 insn_list[our_offset] |= 0x08;
2011 else if (! (id & 32768))
2017 printf ("%d: if (1) goto %d\n", our_offset, id);
2021 printf ("%d: try %d\n", our_offset, id);
2025 /* Store the address of the entry being branched to. */
2026 while (currbits >= 0)
2028 char *byte = insn_list + our_offset + bitsused / 8;
2030 if (idest & (1 << currbits))
2032 *byte |= (1 << (7 - (bitsused % 8)));
2038 /* Now generate the states for the entry being branched to. */
2050 printf ("%d: skipping %d\n", our_offset, ent->bits_to_skip);
2053 if (ent->bits[0] != NULL)
2055 printf ("%d: if (0:%d) goto %d\n", our_offset, zero_count + 1,
2059 if (bitsused != totbits)
2069 struct disent *cent = disinsntable;
2071 printf ("static const char dis_table[] = {\n");
2072 for (x = 0; x < insn_list_len; x++)
2074 if ((x > 0) && ((x % 12) == 0))
2078 printf ("0x%02x, ", insn_list[x]);
2080 printf ("\n};\n\n");
2082 printf ("static const struct ia64_dis_names ia64_dis_names[] = {\n");
2083 while (cent != NULL)
2085 struct disent *ent = cent;
2089 printf ("{ 0x%x, %d, %d, %d },\n", ent->completer_index,
2090 ent->insn, (ent->nexte != NULL ? 1 : 0),
2094 cent = cent->next_ent;
2100 generate_disassembler ()
2104 bittree = make_bittree_entry ();
2106 for (i=0; i < otlen;i++)
2108 struct main_entry *ptr = ordered_table[i];
2110 if (ptr->opcode->type != IA64_TYPE_DYN)
2112 add_dis_entry (bittree,
2113 ptr->opcode->opcode, ptr->opcode->mask,
2115 ptr->completers, 1);
2119 compact_distree (bittree);
2121 gen_dis_table (bittree);
2127 print_string_table ()
2130 char lbuf[80], buf[80];
2133 printf ("static const char *ia64_strings[] = {\n");
2135 for (x = 0; x < strtablen; x++)
2139 if (strlen (string_table[x]->s) > 75)
2143 sprintf (buf, " \"%s\",", string_table[x]->s);
2145 if ((blen + len) > 75)
2147 printf (" %s\n", lbuf);
2156 printf (" %s\n", lbuf);
2161 static struct completer_entry **glist;
2162 static int glistlen = 0;
2163 static int glisttotlen = 0;
2165 /* If the completer trees ENT1 and ENT2 are equal, return 1. */
2168 completer_entries_eq (ent1, ent2)
2169 struct completer_entry *ent1, *ent2;
2171 while (ent1 != NULL && ent2 != NULL)
2173 if (ent1->name->num != ent2->name->num
2174 || ent1->bits != ent2->bits
2175 || ent1->mask != ent2->mask
2176 || ent1->is_terminal != ent2->is_terminal
2177 || ent1->dependencies != ent2->dependencies
2178 || ent1->order != ent2->order)
2182 if (! completer_entries_eq (ent1->addl_entries, ent2->addl_entries))
2186 ent1 = ent1->alternative;
2187 ent2 = ent2->alternative;
2189 return ent1 == ent2;
2192 /* Insert ENT into the global list of completers and return it. If an
2193 equivalent entry (according to completer_entries_eq) already exists,
2194 it is returned instead. */
2195 struct completer_entry *
2197 struct completer_entry *ent;
2205 ent->addl_entries = insert_gclist (ent->addl_entries);
2206 ent->alternative = insert_gclist (ent->alternative);
2211 if (glisttotlen == glistlen)
2214 glist = (struct completer_entry **)
2215 xrealloc (glist, sizeof (struct completer_entry *) * glisttotlen);
2225 if (ent->name->num < glist[0]->name->num)
2229 else if (ent->name->num > glist[end - 1]->name->num)
2239 i = (start + end) / 2;
2240 c = ent->name->num - glist[i]->name->num;
2248 && ent->name->num == glist[i - 1]->name->num)
2265 while (i < glistlen)
2267 if (ent->name->num != glist[i]->name->num)
2271 if (completer_entries_eq (ent, glist[i]))
2279 for (; i > 0 && i < glistlen; i--)
2281 if (ent->name->num >= glist[i - 1]->name->num)
2286 for (; i < glistlen; i++)
2288 if (ent->name->num < glist[i]->name->num)
2293 for (x = glistlen - 1; x >= i; x--)
2295 glist[x + 1] = glist[x];
2304 get_prefix_len (name)
2309 if (name[0] == '\0')
2314 c = strchr (name, '.');
2321 return strlen (name);
2326 compute_completer_bits (ment, ent)
2327 struct main_entry *ment;
2328 struct completer_entry *ent;
2332 compute_completer_bits (ment, ent->addl_entries);
2334 if (ent->is_terminal)
2337 ia64_insn our_bits = ent->bits;
2338 struct completer_entry *p = ent->parent;
2342 while (p != NULL && ! p->is_terminal)
2353 p_bits = ment->opcode->opcode;
2356 for (x = 0; x < 64; x++)
2358 ia64_insn m = ((ia64_insn) 1) << x;
2359 if ((p_bits & m) != (our_bits & m))
2368 ent->bits = our_bits;
2377 ent = ent->alternative;
2381 /* Find identical completer trees that are used in different
2382 instructions and collapse their entries. */
2384 collapse_redundant_completers ()
2386 struct main_entry *ptr;
2389 for (ptr = maintable; ptr != NULL; ptr = ptr->next)
2391 if (ptr->completers == NULL)
2395 compute_completer_bits (ptr, ptr->completers);
2396 ptr->completers = insert_gclist (ptr->completers);
2399 /* The table has been finalized, now number the indexes. */
2400 for (x = 0; x < glistlen; x++)
2407 /* attach two lists of dependencies to each opcode.
2408 1) all resources which, when already marked in use, conflict with this
2410 2) all resources which must be marked in use when this opcode is used
2414 insert_opcode_dependencies (opc, cmp)
2415 struct ia64_opcode *opc;
2416 struct completer_entry *cmp ATTRIBUTE_UNUSED;
2418 /* note all resources which point to this opcode. rfi has the most chks
2419 (79) and cmpxchng has the most regs (54) so 100 here should be enough */
2422 unsigned short regs[256];
2424 unsigned short chks[256];
2425 /* flag insns for which no class matched; there should be none */
2426 int no_class_found = 1;
2428 for (i=0;i < rdepslen;i++)
2430 struct rdep *rs = rdeps[i];
2433 if (strcmp (opc->name, "cmp.eq.and") == 0
2434 && strncmp (rs->name, "PR%", 3) == 0
2436 no_class_found = 99;
2438 for (j=0; j < rs->nregs;j++)
2442 if (in_iclass (opc, ics[rs->regs[j]], NULL, NULL, &ic_note))
2444 /* We can ignore ic_note 11 for non PR resources */
2445 if (ic_note == 11 && strncmp (rs->name, "PR", 2) != 0)
2448 if (ic_note != 0 && rs->regnotes[j] != 0
2449 && ic_note != rs->regnotes[j]
2450 && !(ic_note == 11 && rs->regnotes[j] == 1))
2451 fprintf (stderr, "Warning: IC note %d in opcode %s (IC:%s)"
2452 " conflicts with resource %s note %d\n",
2453 ic_note, opc->name, ics[rs->regs[j]]->name,
2454 rs->name, rs->regnotes[j]);
2455 /* Instruction class notes override resource notes.
2456 So far, only note 11 applies to an IC instead of a resource,
2457 and note 11 implies note 1.
2460 regs[nregs++] = RDEP(ic_note, i);
2462 regs[nregs++] = RDEP(rs->regnotes[j], i);
2467 for (j=0;j < rs->nchks;j++)
2471 if (in_iclass (opc, ics[rs->chks[j]], NULL, NULL, &ic_note))
2473 /* We can ignore ic_note 11 for non PR resources */
2474 if (ic_note == 11 && strncmp (rs->name, "PR", 2) != 0)
2477 if (ic_note != 0 && rs->chknotes[j] != 0
2478 && ic_note != rs->chknotes[j]
2479 && !(ic_note == 11 && rs->chknotes[j] == 1))
2480 fprintf (stderr, "Warning: IC note %d for opcode %s (IC:%s)"
2481 " conflicts with resource %s note %d\n",
2482 ic_note, opc->name, ics[rs->chks[j]]->name,
2483 rs->name, rs->chknotes[j]);
2485 chks[nchks++] = RDEP(ic_note, i);
2487 chks[nchks++] = RDEP(rs->chknotes[j], i);
2495 fprintf (stderr, "Warning: opcode %s has no class (ops %d %d %d)\n",
2497 opc->operands[0], opc->operands[1], opc->operands[2]);
2499 return insert_dependencies (nchks, chks, nregs, regs);
2503 insert_completer_entry (opc, tabent, order)
2504 struct ia64_opcode *opc;
2505 struct main_entry *tabent;
2508 struct completer_entry **ptr = &tabent->completers;
2509 struct completer_entry *parent = NULL;
2510 char pcopy[129], *prefix;
2513 if (strlen (opc->name) > 128)
2517 strcpy (pcopy, opc->name);
2518 prefix = pcopy + get_prefix_len (pcopy);
2519 if (prefix[0] != '\0')
2526 int need_new_ent = 1;
2527 int plen = get_prefix_len (prefix);
2528 struct string_entry *sent;
2530 at_end = (prefix[plen] == '\0');
2531 prefix[plen] = '\0';
2532 sent = insert_string (prefix);
2534 while (*ptr != NULL)
2536 int cmpres = sent->num - (*ptr)->name->num;
2545 ptr = &((*ptr)->alternative);
2550 struct completer_entry *nent = tmalloc (struct completer_entry);
2552 nent->parent = parent;
2553 nent->addl_entries = NULL;
2554 nent->alternative = *ptr;
2556 nent->is_terminal = 0;
2557 nent->dependencies = -1;
2563 ptr = &((*ptr)->addl_entries);
2568 if ((*ptr)->is_terminal)
2573 (*ptr)->is_terminal = 1;
2574 (*ptr)->mask = (ia64_insn)-1;
2575 (*ptr)->bits = opc->opcode;
2576 (*ptr)->dependencies = insert_opcode_dependencies (opc, *ptr);
2577 (*ptr)->order = order;
2581 print_completer_entry (ent)
2582 struct completer_entry *ent;
2585 ia64_insn mask = ent->mask, bits = ent->bits;
2589 while (! (mask & 1))
2595 if (bits & 0xffffffff00000000LL)
2601 printf (" { 0x%x, 0x%x, %d, %d, %d, %d, %d, %d },\n",
2605 ent->alternative != NULL ? ent->alternative->num : -1,
2606 ent->addl_entries != NULL ? ent->addl_entries->num : -1,
2608 ent->is_terminal ? 1 : 0,
2613 print_completer_table ()
2617 printf ("static const struct ia64_completer_table\ncompleter_table[] = {\n");
2618 for (x = 0; x < glistlen; x++)
2620 print_completer_entry (glist[x]);
2626 opcodes_eq (opc1, opc2)
2627 struct ia64_opcode *opc1;
2628 struct ia64_opcode *opc2;
2633 if ((opc1->mask != opc2->mask) || (opc1->type != opc2->type)
2634 || (opc1->num_outputs != opc2->num_outputs)
2635 || (opc1->flags != opc2->flags))
2639 for (x = 0; x < 5; x++)
2641 if (opc1->operands[x] != opc2->operands[x])
2646 plen1 = get_prefix_len (opc1->name);
2647 plen2 = get_prefix_len (opc2->name);
2648 if (plen1 == plen2 && (memcmp (opc1->name, opc2->name, plen1) == 0))
2656 add_opcode_entry (opc)
2657 struct ia64_opcode *opc;
2659 struct main_entry **place;
2660 struct string_entry *name;
2664 if (strlen (opc->name) > 128)
2669 strcpy (prefix, opc->name);
2670 prefix[get_prefix_len (prefix)] = '\0';
2671 name = insert_string (prefix);
2673 /* Walk the list of opcode table entries. If it's a new
2674 instruction, allocate and fill in a new entry. Note
2675 the main table is alphabetical by opcode name. */
2677 while (*place != NULL)
2679 if ((*place)->name->num == name->num
2680 && opcodes_eq ((*place)->opcode, opc))
2685 if ((*place)->name->num > name->num)
2689 place = &((*place)->next);
2693 struct main_entry *nent = tmalloc (struct main_entry);
2697 nent->next = *place;
2698 nent->completers = 0;
2701 if (otlen == ottotlen)
2704 ordered_table = (struct main_entry **)
2705 xrealloc (ordered_table, sizeof (struct main_entry *) * ottotlen);
2707 ordered_table[otlen++] = nent;
2710 insert_completer_entry (opc, *place, opcode_count++);
2716 struct main_entry *ptr = maintable;
2719 printf ("static const struct ia64_main_table\nmain_table[] = {\n");
2722 printf (" { %d, %d, %d, 0x",
2725 ptr->opcode->num_outputs);
2726 fprintf_vma (stdout, ptr->opcode->opcode);
2728 fprintf_vma (stdout, ptr->opcode->mask);
2729 printf ("ull, { %d, %d, %d, %d, %d }, 0x%x, %d, },\n",
2730 ptr->opcode->operands[0],
2731 ptr->opcode->operands[1],
2732 ptr->opcode->operands[2],
2733 ptr->opcode->operands[3],
2734 ptr->opcode->operands[4],
2736 ptr->completers->num);
2738 ptr->main_index = index++;
2747 struct ia64_opcode *table;
2751 for (curr_opcode = 0; table[curr_opcode].name != NULL; curr_opcode++)
2753 add_opcode_entry (table + curr_opcode);
2760 char **argv ATTRIBUTE_UNUSED;
2767 load_insn_classes();
2768 load_dependencies();
2770 shrink (ia64_opcodes_a);
2771 shrink (ia64_opcodes_b);
2772 shrink (ia64_opcodes_f);
2773 shrink (ia64_opcodes_i);
2774 shrink (ia64_opcodes_m);
2775 shrink (ia64_opcodes_x);
2776 shrink (ia64_opcodes_d);
2778 collapse_redundant_completers ();
2780 printf ("/* This file is automatically generated by ia64-gen. Do not edit! */\n");
2781 print_string_table ();
2782 print_dependency_table ();
2783 print_completer_table ();
2784 print_main_table ();
2786 generate_disassembler ();