OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [gdb-5.3/] [sim/] [igen/] [gen.c] - Blame information for rev 1765

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1181 sfurman
/* The IGEN simulator generator for GDB, the GNU Debugger.
2
 
3
   Copyright 2002 Free Software Foundation, Inc.
4
 
5
   Contributed by Andrew Cagney.
6
 
7
   This file is part of GDB.
8
 
9
   This program is free software; you can redistribute it and/or modify
10
   it under the terms of the GNU General Public License as published by
11
   the Free Software Foundation; either version 2 of the License, or
12
   (at your option) any later version.
13
 
14
   This program is distributed in the hope that it will be useful,
15
   but WITHOUT ANY WARRANTY; without even the implied warranty of
16
   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
17
   GNU General Public License for more details.
18
 
19
   You should have received a copy of the GNU General Public License
20
   along with this program; if not, write to the Free Software
21
   Foundation, Inc., 59 Temple Place - Suite 330,
22
   Boston, MA 02111-1307, USA.  */
23
 
24
 
25
#include "misc.h"
26
#include "lf.h"
27
#include "table.h"
28
#include "filter.h"
29
 
30
#include "igen.h"
31
#include "ld-insn.h"
32
#include "ld-decode.h"
33
#include "gen.h"
34
 
35
static insn_uint
36
sub_val (insn_uint val, int val_last_pos, int first_pos, int last_pos)
37
{
38
  return ((val >> (val_last_pos - last_pos))
39
          & (((insn_uint) 1 << (last_pos - first_pos + 1)) - 1));
40
}
41
 
42
static void
43
update_depth (lf *file, gen_entry *entry, int depth, void *data)
44
{
45
  int *max_depth = (int *) data;
46
  if (*max_depth < depth)
47
    *max_depth = depth;
48
}
49
 
50
 
51
int
52
gen_entry_depth (gen_entry *table)
53
{
54
  int depth = 0;
55
  gen_entry_traverse_tree (NULL, table, 1, NULL,        /*start */
56
                           update_depth, NULL,  /*end */
57
                           &depth);     /* data */
58
  return depth;
59
}
60
 
61
 
62
static void
63
print_gen_entry_path (line_ref *line, gen_entry *table, error_func *print)
64
{
65
  if (table->parent == NULL)
66
    {
67
      if (table->top->model != NULL)
68
        print (line, "%s", table->top->model->name);
69
      else
70
        print (line, "");
71
    }
72
  else
73
    {
74
      print_gen_entry_path (line, table->parent, print);
75
      print (NULL, ".%d", table->opcode_nr);
76
    }
77
}
78
 
79
static void
80
print_gen_entry_insns (gen_entry *table,
81
                       error_func *print,
82
                       char *first_message, char *next_message)
83
{
84
  insn_list *i;
85
  char *message;
86
  message = first_message;
87
  for (i = table->insns; i != NULL; i = i->next)
88
    {
89
      insn_entry *insn = i->insn;
90
      print_gen_entry_path (insn->line, table, print);
91
      print (NULL, ": %s.%s %s\n", insn->format_name, insn->name, message);
92
      if (next_message != NULL)
93
        message = next_message;
94
    }
95
}
96
 
97
/* same as strcmp */
98
static int
99
insn_field_cmp (insn_word_entry *l, insn_word_entry *r)
100
{
101
  while (1)
102
    {
103
      int bit_nr;
104
      if (l == NULL && r == NULL)
105
        return 0;                /* all previous fields the same */
106
      if (l == NULL)
107
        return -1;              /* left shorter than right */
108
      if (r == NULL)
109
        return +1;              /* left longer than right */
110
      for (bit_nr = 0; bit_nr < options.insn_bit_size; bit_nr++)
111
        {
112
          if (l->bit[bit_nr]->field->type != insn_field_string)
113
            continue;
114
          if (r->bit[bit_nr]->field->type != insn_field_string)
115
            continue;
116
          if (l->bit[bit_nr]->field->conditions == NULL)
117
            continue;
118
          if (r->bit[bit_nr]->field->conditions == NULL)
119
            continue;
120
          if (0)
121
            printf ("%s%s%s VS %s%s%s\n",
122
                    l->bit[bit_nr]->field->val_string,
123
                    l->bit[bit_nr]->field->conditions->test ==
124
                    insn_field_cond_eq ? "=" : "!",
125
                    l->bit[bit_nr]->field->conditions->string,
126
                    r->bit[bit_nr]->field->val_string,
127
                    r->bit[bit_nr]->field->conditions->test ==
128
                    insn_field_cond_eq ? "=" : "!",
129
                    r->bit[bit_nr]->field->conditions->string);
130
          if (l->bit[bit_nr]->field->conditions->test == insn_field_cond_eq
131
              && r->bit[bit_nr]->field->conditions->test ==
132
              insn_field_cond_eq)
133
            {
134
              if (l->bit[bit_nr]->field->conditions->type ==
135
                  insn_field_cond_field
136
                  && r->bit[bit_nr]->field->conditions->type ==
137
                  insn_field_cond_field)
138
                /* somewhat arbitrary */
139
                {
140
                  int cmp = strcmp (l->bit[bit_nr]->field->conditions->string,
141
                                    r->bit[bit_nr]->field->conditions->
142
                                    string);
143
                  if (cmp != 0)
144
                    return cmp;
145
                  else
146
                    continue;
147
                }
148
              if (l->bit[bit_nr]->field->conditions->type ==
149
                  insn_field_cond_field)
150
                return +1;
151
              if (r->bit[bit_nr]->field->conditions->type ==
152
                  insn_field_cond_field)
153
                return -1;
154
              /* The case of both fields having constant values should have
155
                 already have been handled because such fields are converted
156
                 into normal constant fields. */
157
              continue;
158
            }
159
          if (l->bit[bit_nr]->field->conditions->test == insn_field_cond_eq)
160
            return +1;          /* left = only */
161
          if (r->bit[bit_nr]->field->conditions->test == insn_field_cond_eq)
162
            return -1;          /* right = only */
163
          /* FIXME: Need to some what arbitrarily order conditional lists */
164
          continue;
165
        }
166
      l = l->next;
167
      r = r->next;
168
    }
169
}
170
 
171
/* same as strcmp */
172
static int
173
insn_word_cmp (insn_word_entry *l, insn_word_entry *r)
174
{
175
  while (1)
176
    {
177
      int bit_nr;
178
      if (l == NULL && r == NULL)
179
        return 0;                /* all previous fields the same */
180
      if (l == NULL)
181
        return -1;              /* left shorter than right */
182
      if (r == NULL)
183
        return +1;              /* left longer than right */
184
      for (bit_nr = 0; bit_nr < options.insn_bit_size; bit_nr++)
185
        {
186
          if (l->bit[bit_nr]->mask < r->bit[bit_nr]->mask)
187
            return -1;
188
          if (l->bit[bit_nr]->mask > r->bit[bit_nr]->mask)
189
            return 1;
190
          if (l->bit[bit_nr]->value < r->bit[bit_nr]->value)
191
            return -1;
192
          if (l->bit[bit_nr]->value > r->bit[bit_nr]->value)
193
            return 1;
194
        }
195
      l = l->next;
196
      r = r->next;
197
    }
198
}
199
 
200
/* same as strcmp */
201
static int
202
opcode_bit_cmp (opcode_bits *l, opcode_bits *r)
203
{
204
  if (l == NULL && r == NULL)
205
    return 0;                    /* all previous bits the same */
206
  if (l == NULL)
207
    return -1;                  /* left shorter than right */
208
  if (r == NULL)
209
    return +1;                  /* left longer than right */
210
  /* most significant word */
211
  if (l->field->word_nr < r->field->word_nr)
212
    return +1;                  /* left has more significant word */
213
  if (l->field->word_nr > r->field->word_nr)
214
    return -1;                  /* right has more significant word */
215
  /* most significant bit? */
216
  if (l->first < r->first)
217
    return +1;                  /* left as more significant bit */
218
  if (l->first > r->first)
219
    return -1;                  /* right as more significant bit */
220
  /* nr bits? */
221
  if (l->last < r->last)
222
    return +1;                  /* left as less bits */
223
  if (l->last > r->last)
224
    return -1;                  /* right as less bits */
225
  /* value? */
226
  if (l->value < r->value)
227
    return -1;
228
  if (l->value > r->value)
229
    return 1;
230
  return 0;
231
}
232
 
233
 
234
/* same as strcmp */
235
static int
236
opcode_bits_cmp (opcode_bits *l, opcode_bits *r)
237
{
238
  while (1)
239
    {
240
      int cmp;
241
      if (l == NULL && r == NULL)
242
        return 0;                /* all previous bits the same */
243
      cmp = opcode_bit_cmp (l, r);
244
      if (cmp != 0)
245
        return cmp;
246
      l = l->next;
247
      r = r->next;
248
    }
249
}
250
 
251
/* same as strcmp */
252
static opcode_bits *
253
new_opcode_bits (opcode_bits *old_bits,
254
                 int value,
255
                 int first,
256
                 int last, insn_field_entry *field, opcode_field *opcode)
257
{
258
  opcode_bits *new_bits = ZALLOC (opcode_bits);
259
  new_bits->field = field;
260
  new_bits->value = value;
261
  new_bits->first = first;
262
  new_bits->last = last;
263
  new_bits->opcode = opcode;
264
 
265
  if (old_bits != NULL)
266
    {
267
      opcode_bits *new_list;
268
      opcode_bits **last = &new_list;
269
      new_list = new_opcode_bits (old_bits->next,
270
                                  old_bits->value,
271
                                  old_bits->first,
272
                                  old_bits->last,
273
                                  old_bits->field, old_bits->opcode);
274
      while (*last != NULL)
275
        {
276
          int cmp = opcode_bit_cmp (new_bits, *last);
277
          if (cmp < 0)           /* new < new_list */
278
            {
279
              break;
280
            }
281
          if (cmp == 0)
282
            {
283
              ERROR ("Duplicated insn bits in list");
284
            }
285
          last = &(*last)->next;
286
        }
287
      new_bits->next = *last;
288
      *last = new_bits;
289
      return new_list;
290
    }
291
  else
292
    {
293
      return new_bits;
294
    }
295
}
296
 
297
/* Same as strcmp().  */
298
static int
299
format_name_cmp (const char *l, const char *r)
300
{
301
  if (l == NULL && r == NULL)
302
    return 0;
303
  if (l != NULL && r == NULL)
304
    return -1;
305
  if (l == NULL && r != NULL)
306
    return +1;
307
  return strcmp (l, r);
308
}
309
 
310
 
311
typedef enum
312
{
313
  merge_duplicate_insns,
314
  report_duplicate_insns,
315
}
316
duplicate_insn_actions;
317
 
318
static insn_list *
319
insn_list_insert (insn_list **cur_insn_ptr,
320
                  int *nr_insns,
321
                  insn_entry * insn,
322
                  opcode_bits *expanded_bits,
323
                  opcode_field *opcodes,
324
                  int nr_prefetched_words,
325
                  duplicate_insn_actions duplicate_action)
326
{
327
  /* insert it according to the order of the fields & bits */
328
  for (; (*cur_insn_ptr) != NULL; cur_insn_ptr = &(*cur_insn_ptr)->next)
329
    {
330
      int cmp;
331
 
332
      /* key#1 sort according to the constant fields of each instruction */
333
      cmp = insn_word_cmp (insn->words, (*cur_insn_ptr)->insn->words);
334
      if (cmp < 0)
335
        break;
336
      else if (cmp > 0)
337
        continue;
338
 
339
      /* key#2 sort according to the expanded bits of each instruction */
340
      cmp = opcode_bits_cmp (expanded_bits, (*cur_insn_ptr)->expanded_bits);
341
      if (cmp < 0)
342
        break;
343
      else if (cmp > 0)
344
        continue;
345
 
346
      /* key#3 sort according to the non-constant fields of each instruction */
347
      cmp = insn_field_cmp (insn->words, (*cur_insn_ptr)->insn->words);
348
      if (cmp < 0)
349
        break;
350
      else if (cmp > 0)
351
        continue;
352
 
353
      /* key#4 sort according to the format-name.  If two apparently
354
         identical instructions have unique format-names, then the
355
         instructions are different.  This is because the
356
         format-name's use is overloaded, it not only indicates the
357
         format name but also provides a unique semantic name for the
358
         function.  */
359
      cmp =
360
        format_name_cmp (insn->format_name,
361
                         (*cur_insn_ptr)->insn->format_name);
362
      if (cmp < 0)
363
        break;
364
      else if (cmp > 0)
365
        continue;
366
 
367
      /* duplicate keys, report problem */
368
      switch (duplicate_action)
369
        {
370
        case report_duplicate_insns:
371
          /* It would appear that we have two instructions with the
372
             same constant field values across all words and bits.
373
             This error can also occure when insn_field_cmp() is
374
             failing to differentiate between two instructions that
375
             differ only in their conditional fields. */
376
          warning (insn->line,
377
                   "Two instructions with identical constant fields\n");
378
          error ((*cur_insn_ptr)->insn->line,
379
                 "Location of duplicate instruction\n");
380
        case merge_duplicate_insns:
381
          /* Add the opcode path to the instructions list */
382
          if (opcodes != NULL)
383
            {
384
              insn_opcodes **last = &(*cur_insn_ptr)->opcodes;
385
              while (*last != NULL)
386
                {
387
                  last = &(*last)->next;
388
                }
389
              (*last) = ZALLOC (insn_opcodes);
390
              (*last)->opcode = opcodes;
391
            }
392
          /* Use the larger nr_prefetched_words */
393
          if ((*cur_insn_ptr)->nr_prefetched_words < nr_prefetched_words)
394
            (*cur_insn_ptr)->nr_prefetched_words = nr_prefetched_words;
395
          return (*cur_insn_ptr);
396
        }
397
 
398
    }
399
 
400
  /* create a new list entry and insert it */
401
  {
402
    insn_list *new_insn = ZALLOC (insn_list);
403
    new_insn->insn = insn;
404
    new_insn->expanded_bits = expanded_bits;
405
    new_insn->next = (*cur_insn_ptr);
406
    new_insn->nr_prefetched_words = nr_prefetched_words;
407
    if (opcodes != NULL)
408
      {
409
        new_insn->opcodes = ZALLOC (insn_opcodes);
410
        new_insn->opcodes->opcode = opcodes;
411
      }
412
    (*cur_insn_ptr) = new_insn;
413
  }
414
 
415
  *nr_insns += 1;
416
 
417
  return (*cur_insn_ptr);
418
}
419
 
420
 
421
extern void
422
gen_entry_traverse_tree (lf *file,
423
                         gen_entry *table,
424
                         int depth,
425
                         gen_entry_handler * start,
426
                         gen_entry_handler * leaf,
427
                         gen_entry_handler * end, void *data)
428
{
429
  gen_entry *entry;
430
 
431
  ASSERT (table !=NULL);
432
  ASSERT (table->opcode != NULL);
433
  ASSERT (table->nr_entries > 0);
434
  ASSERT (table->entries != 0);
435
 
436
  /* prefix */
437
  if (start != NULL && depth >= 0)
438
    {
439
      start (file, table, depth, data);
440
    }
441
  /* infix leaves */
442
  for (entry = table->entries; entry != NULL; entry = entry->sibling)
443
    {
444
      if (entry->entries != NULL && depth != 0)
445
        {
446
          gen_entry_traverse_tree (file, entry, depth + 1,
447
                                   start, leaf, end, data);
448
        }
449
      else if (depth >= 0)
450
        {
451
          if (leaf != NULL)
452
            {
453
              leaf (file, entry, depth, data);
454
            }
455
        }
456
    }
457
  /* postfix */
458
  if (end != NULL && depth >= 0)
459
    {
460
      end (file, table, depth, data);
461
    }
462
}
463
 
464
 
465
 
466
/* create a list element containing a single gen_table entry */
467
 
468
static gen_list *
469
make_table (insn_table *isa, decode_table *rules, model_entry *model)
470
{
471
  insn_entry *insn;
472
  gen_list *entry = ZALLOC (gen_list);
473
  entry->table = ZALLOC (gen_entry);
474
  entry->table->top = entry;
475
  entry->model = model;
476
  entry->isa = isa;
477
  for (insn = isa->insns; insn != NULL; insn = insn->next)
478
    {
479
      if (model == NULL
480
          || insn->processors == NULL
481
          || filter_is_member (insn->processors, model->name))
482
        {
483
          insn_list_insert (&entry->table->insns, &entry->table->nr_insns, insn, NULL,  /* expanded_bits - none yet */
484
                            NULL,       /* opcodes - none yet */
485
                            0,   /* nr_prefetched_words - none yet */
486
                            report_duplicate_insns);
487
        }
488
    }
489
  entry->table->opcode_rule = rules;
490
  return entry;
491
}
492
 
493
 
494
gen_table *
495
make_gen_tables (insn_table *isa, decode_table *rules)
496
{
497
  gen_table *gen = ZALLOC (gen_table);
498
  gen->isa = isa;
499
  gen->rules = rules;
500
  if (options.gen.multi_sim)
501
    {
502
      gen_list **last = &gen->tables;
503
      model_entry *model;
504
      filter *processors;
505
      if (options.model_filter != NULL)
506
        processors = options.model_filter;
507
      else
508
        processors = isa->model->processors;
509
      for (model = isa->model->models; model != NULL; model = model->next)
510
        {
511
          if (filter_is_member (processors, model->name))
512
            {
513
              *last = make_table (isa, rules, model);
514
              last = &(*last)->next;
515
            }
516
        }
517
    }
518
  else
519
    {
520
      gen->tables = make_table (isa, rules, NULL);
521
    }
522
  return gen;
523
}
524
 
525
 
526
/****************************************************************/
527
 
528
#if 0
529
typedef enum
530
{
531
  field_is_not_constant = 0,
532
  field_constant_int = 1,
533
  field_constant_reserved = 2,
534
  field_constant_string = 3
535
}
536
constant_field_types;
537
 
538
static constant_field_types
539
insn_field_is_constant (insn_field * field, decode_table *rule)
540
{
541
  switch (field->type)
542
    {
543
    case insn_field_int:
544
      /* field is an integer */
545
      return field_constant_int;
546
    case insn_field_reserved:
547
      /* field is `/' and treating that as a constant */
548
      if (rule->with_zero_reserved)
549
        return field_constant_reserved;
550
      else
551
        return field_is_not_constant;
552
    case insn_field_wild:
553
      return field_is_not_constant;     /* never constant */
554
    case insn_field_string:
555
      /* field, though variable, is on the list of forced constants */
556
      if (filter_is_member (rule->constant_field_names, field->val_string))
557
        return field_constant_string;
558
      else
559
        return field_is_not_constant;
560
    }
561
  ERROR ("Internal error");
562
  return field_is_not_constant;
563
}
564
#endif
565
 
566
 
567
/****************************************************************/
568
 
569
 
570
/* Is the bit, according to the decode rule, identical across all the
571
   instructions? */
572
static int
573
insns_bit_useless (insn_list *insns, decode_table *rule, int bit_nr)
574
{
575
  insn_list *entry;
576
  int value = -1;
577
  int is_useless = 1;           /* cleared if something actually found */
578
 
579
  /* check the instructions for some constant value in at least one of
580
     the bit fields */
581
  for (entry = insns; entry != NULL; entry = entry->next)
582
    {
583
      insn_word_entry *word = entry->insn->word[rule->word_nr];
584
      insn_bit_entry *bit = word->bit[bit_nr];
585
      switch (bit->field->type)
586
        {
587
        case insn_field_invalid:
588
          ASSERT (0);
589
          break;
590
        case insn_field_wild:
591
        case insn_field_reserved:
592
          /* neither useless or useful - ignore */
593
          break;
594
        case insn_field_int:
595
          switch (rule->search)
596
            {
597
            case decode_find_strings:
598
              /* an integer isn't a string */
599
              return 1;
600
            case decode_find_constants:
601
            case decode_find_mixed:
602
              /* an integer is useful if its value isn't the same
603
                 between all instructions.  The first time through the
604
                 value is saved, the second time through (if the
605
                 values differ) it is marked as useful. */
606
              if (value < 0)
607
                value = bit->value;
608
              else if (value != bit->value)
609
                is_useless = 0;
610
              break;
611
            }
612
          break;
613
        case insn_field_string:
614
          switch (rule->search)
615
            {
616
            case decode_find_strings:
617
              /* at least one string, keep checking */
618
              is_useless = 0;
619
              break;
620
            case decode_find_constants:
621
            case decode_find_mixed:
622
              if (filter_is_member (rule->constant_field_names,
623
                                    bit->field->val_string))
624
                /* a string field forced to constant? */
625
                is_useless = 0;
626
              else if (rule->search == decode_find_constants)
627
                /* the string field isn't constant */
628
                return 1;
629
              break;
630
            }
631
        }
632
    }
633
 
634
  /* Given only one constant value has been found, check through all
635
     the instructions to see if at least one conditional makes it
636
     usefull */
637
  if (value >= 0 && is_useless)
638
    {
639
      for (entry = insns; entry != NULL; entry = entry->next)
640
        {
641
          insn_word_entry *word = entry->insn->word[rule->word_nr];
642
          insn_bit_entry *bit = word->bit[bit_nr];
643
          switch (bit->field->type)
644
            {
645
            case insn_field_invalid:
646
              ASSERT (0);
647
              break;
648
            case insn_field_wild:
649
            case insn_field_reserved:
650
            case insn_field_int:
651
              /* already processed */
652
              break;
653
            case insn_field_string:
654
              switch (rule->search)
655
                {
656
                case decode_find_strings:
657
                case decode_find_constants:
658
                  /* already processed */
659
                  break;
660
                case decode_find_mixed:
661
                  /* string field with conditions.  If this condition
662
                     eliminates the value then the compare is useful */
663
                  if (bit->field->conditions != NULL)
664
                    {
665
                      insn_field_cond *condition;
666
                      int shift = bit->field->last - bit_nr;
667
                      for (condition = bit->field->conditions;
668
                           condition != NULL; condition = condition->next)
669
                        {
670
                          switch (condition->type)
671
                            {
672
                            case insn_field_cond_value:
673
                              switch (condition->test)
674
                                {
675
                                case insn_field_cond_ne:
676
                                  if (((condition->value >> shift) & 1)
677
                                      == (unsigned) value)
678
                                    /* conditional field excludes the
679
                                       current value */
680
                                    is_useless = 0;
681
                                  break;
682
                                case insn_field_cond_eq:
683
                                  if (((condition->value >> shift) & 1)
684
                                      != (unsigned) value)
685
                                    /* conditional field requires the
686
                                       current value */
687
                                    is_useless = 0;
688
                                  break;
689
                                }
690
                              break;
691
                            case insn_field_cond_field:
692
                              /* are these handled separatly? */
693
                              break;
694
                            }
695
                        }
696
                    }
697
                }
698
            }
699
        }
700
    }
701
 
702
  return is_useless;
703
}
704
 
705
 
706
/* go through a gen-table's list of instruction formats looking for a
707
   range of bits that meet the decode table RULEs requirements */
708
 
709
static opcode_field *
710
gen_entry_find_opcode_field (insn_list *insns,
711
                             decode_table *rule, int string_only)
712
{
713
  opcode_field curr_opcode;
714
  ASSERT (rule != NULL);
715
 
716
  memset (&curr_opcode, 0, sizeof (curr_opcode));
717
  curr_opcode.word_nr = rule->word_nr;
718
  curr_opcode.first = rule->first;
719
  curr_opcode.last = rule->last;
720
 
721
  /* Try to reduce the size of first..last in accordance with the
722
     decode rules */
723
 
724
  while (curr_opcode.first <= rule->last)
725
    {
726
      if (insns_bit_useless (insns, rule, curr_opcode.first))
727
        curr_opcode.first++;
728
      else
729
        break;
730
    }
731
  while (curr_opcode.last >= rule->first)
732
    {
733
      if (insns_bit_useless (insns, rule, curr_opcode.last))
734
        curr_opcode.last--;
735
      else
736
        break;
737
    }
738
 
739
 
740
#if 0
741
  for (entry = insns; entry != NULL; entry = entry->next)
742
    {
743
      insn_word_entry *fields = entry->insn->word[rule->word_nr];
744
      opcode_field new_opcode;
745
 
746
      ASSERT (fields != NULL);
747
 
748
      /* find a start point for the opcode field */
749
      new_opcode.first = rule->first;
750
      while (new_opcode.first <= rule->last
751
             && (!string_only
752
                 ||
753
                 (insn_field_is_constant (fields->bit[new_opcode.first], rule)
754
                  != field_constant_string)) && (string_only
755
                                                 ||
756
                                                 (insn_field_is_constant
757
                                                  (fields->
758
                                                   bit[new_opcode.first],
759
                                                   rule) ==
760
                                                  field_is_not_constant)))
761
        {
762
          int new_first = fields->bit[new_opcode.first]->last + 1;
763
          ASSERT (new_first > new_opcode.first);
764
          new_opcode.first = new_first;
765
        }
766
      ASSERT (new_opcode.first > rule->last
767
              || (string_only
768
                  && insn_field_is_constant (fields->bit[new_opcode.first],
769
                                             rule) == field_constant_string)
770
              || (!string_only
771
                  && insn_field_is_constant (fields->bit[new_opcode.first],
772
                                             rule)));
773
 
774
      /* find the end point for the opcode field */
775
      new_opcode.last = rule->last;
776
      while (new_opcode.last >= rule->first
777
             && (!string_only
778
                 || insn_field_is_constant (fields->bit[new_opcode.last],
779
                                            rule) != field_constant_string)
780
             && (string_only
781
                 || !insn_field_is_constant (fields->bit[new_opcode.last],
782
                                             rule)))
783
        {
784
          int new_last = fields->bit[new_opcode.last]->first - 1;
785
          ASSERT (new_last < new_opcode.last);
786
          new_opcode.last = new_last;
787
        }
788
      ASSERT (new_opcode.last < rule->first
789
              || (string_only
790
                  && insn_field_is_constant (fields->bit[new_opcode.last],
791
                                             rule) == field_constant_string)
792
              || (!string_only
793
                  && insn_field_is_constant (fields->bit[new_opcode.last],
794
                                             rule)));
795
 
796
      /* now see if our current opcode needs expanding to include the
797
         interesting fields within this instruction */
798
      if (new_opcode.first <= rule->last
799
          && curr_opcode.first > new_opcode.first)
800
        curr_opcode.first = new_opcode.first;
801
      if (new_opcode.last >= rule->first
802
          && curr_opcode.last < new_opcode.last)
803
        curr_opcode.last = new_opcode.last;
804
 
805
    }
806
#endif
807
 
808
  /* did the final opcode field end up being empty? */
809
  if (curr_opcode.first > curr_opcode.last)
810
    {
811
      return NULL;
812
    }
813
  ASSERT (curr_opcode.last >= rule->first);
814
  ASSERT (curr_opcode.first <= rule->last);
815
  ASSERT (curr_opcode.first <= curr_opcode.last);
816
 
817
  /* Ensure that, for the non string only case, the opcode includes
818
     the range forced_first .. forced_last */
819
  if (!string_only && curr_opcode.first > rule->force_first)
820
    {
821
      curr_opcode.first = rule->force_first;
822
    }
823
  if (!string_only && curr_opcode.last < rule->force_last)
824
    {
825
      curr_opcode.last = rule->force_last;
826
    }
827
 
828
  /* For the string only case, force just the lower bound (so that the
829
     shift can be eliminated) */
830
  if (string_only && rule->force_last == options.insn_bit_size - 1)
831
    {
832
      curr_opcode.last = options.insn_bit_size - 1;
833
    }
834
 
835
  /* handle any special cases */
836
  switch (rule->type)
837
    {
838
    case normal_decode_rule:
839
      /* let the above apply */
840
      curr_opcode.nr_opcodes =
841
        (1 << (curr_opcode.last - curr_opcode.first + 1));
842
      break;
843
    case boolean_rule:
844
      curr_opcode.is_boolean = 1;
845
      curr_opcode.boolean_constant = rule->constant;
846
      curr_opcode.nr_opcodes = 2;
847
      break;
848
    }
849
 
850
  {
851
    opcode_field *new_field = ZALLOC (opcode_field);
852
    memcpy (new_field, &curr_opcode, sizeof (opcode_field));
853
    return new_field;
854
  }
855
}
856
 
857
 
858
static void
859
gen_entry_insert_insn (gen_entry *table,
860
                       insn_entry * old_insn,
861
                       int new_word_nr,
862
                       int new_nr_prefetched_words,
863
                       int new_opcode_nr, opcode_bits *new_bits)
864
{
865
  gen_entry **entry = &table->entries;
866
 
867
  /* find the new table for this entry */
868
  while ((*entry) != NULL && (*entry)->opcode_nr < new_opcode_nr)
869
    {
870
      entry = &(*entry)->sibling;
871
    }
872
 
873
  if ((*entry) == NULL || (*entry)->opcode_nr != new_opcode_nr)
874
    {
875
      /* insert the missing entry */
876
      gen_entry *new_entry = ZALLOC (gen_entry);
877
      new_entry->sibling = (*entry);
878
      (*entry) = new_entry;
879
      table->nr_entries++;
880
      /* fill it in */
881
      new_entry->top = table->top;
882
      new_entry->opcode_nr = new_opcode_nr;
883
      new_entry->word_nr = new_word_nr;
884
      new_entry->expanded_bits = new_bits;
885
      new_entry->opcode_rule = table->opcode_rule->next;
886
      new_entry->parent = table;
887
      new_entry->nr_prefetched_words = new_nr_prefetched_words;
888
    }
889
  /* ASSERT new_bits == cur_entry bits */
890
  ASSERT ((*entry) != NULL && (*entry)->opcode_nr == new_opcode_nr);
891
  insn_list_insert (&(*entry)->insns, &(*entry)->nr_insns, old_insn, NULL,      /* expanded_bits - only in final list */
892
                    NULL,       /* opcodes - only in final list */
893
                    new_nr_prefetched_words,    /* for this table */
894
                    report_duplicate_insns);
895
}
896
 
897
 
898
static void
899
gen_entry_expand_opcode (gen_entry *table,
900
                         insn_entry * instruction,
901
                         int bit_nr, int opcode_nr, opcode_bits *bits)
902
{
903
  if (bit_nr > table->opcode->last)
904
    {
905
      /* Only include the hardwired bit information with an entry IF
906
         that entry (and hence its functions) are being duplicated.  */
907
      if (options.trace.insn_expansion)
908
        {
909
          print_gen_entry_path (table->opcode_rule->line, table, notify);
910
          notify (NULL, ": insert %d - %s.%s%s\n",
911
                  opcode_nr,
912
                  instruction->format_name,
913
                  instruction->name,
914
                  (table->opcode_rule->
915
                   with_duplicates ? " (duplicated)" : ""));
916
        }
917
      if (table->opcode_rule->with_duplicates)
918
        {
919
          gen_entry_insert_insn (table, instruction,
920
                                 table->opcode->word_nr,
921
                                 table->nr_prefetched_words, opcode_nr, bits);
922
        }
923
      else
924
        {
925
          gen_entry_insert_insn (table, instruction,
926
                                 table->opcode->word_nr,
927
                                 table->nr_prefetched_words, opcode_nr, NULL);
928
        }
929
    }
930
  else
931
    {
932
      insn_word_entry *word = instruction->word[table->opcode->word_nr];
933
      insn_field_entry *field = word->bit[bit_nr]->field;
934
      int last_pos = ((field->last < table->opcode->last)
935
                      ? field->last : table->opcode->last);
936
      int first_pos = ((field->first > table->opcode->first)
937
                       ? field->first : table->opcode->first);
938
      int width = last_pos - first_pos + 1;
939
      switch (field->type)
940
        {
941
        case insn_field_int:
942
          {
943
            int val;
944
            val = sub_val (field->val_int, field->last, first_pos, last_pos);
945
            gen_entry_expand_opcode (table, instruction,
946
                                     last_pos + 1,
947
                                     ((opcode_nr << width) | val), bits);
948
            break;
949
          }
950
        default:
951
          {
952
            if (field->type == insn_field_reserved)
953
              gen_entry_expand_opcode (table, instruction,
954
                                       last_pos + 1,
955
                                       ((opcode_nr << width)), bits);
956
            else
957
              {
958
                int val;
959
                int last_val = (table->opcode->is_boolean ? 2 : (1 << width));
960
                for (val = 0; val < last_val; val++)
961
                  {
962
                    /* check to see if the value has been precluded
963
                       (by a conditional) in some way */
964
                    int is_precluded;
965
                    insn_field_cond *condition;
966
                    for (condition = field->conditions, is_precluded = 0;
967
                         condition != NULL && !is_precluded;
968
                         condition = condition->next)
969
                      {
970
                        switch (condition->type)
971
                          {
972
                          case insn_field_cond_value:
973
                            {
974
                              int value =
975
                                sub_val (condition->value, field->last,
976
                                         first_pos, last_pos);
977
                              switch (condition->test)
978
                                {
979
                                case insn_field_cond_ne:
980
                                  if (value == val)
981
                                    is_precluded = 1;
982
                                  break;
983
                                case insn_field_cond_eq:
984
                                  if (value != val)
985
                                    is_precluded = 1;
986
                                  break;
987
                                }
988
                              break;
989
                            }
990
                          case insn_field_cond_field:
991
                            {
992
                              int value = -1;
993
                              opcode_bits *bit;
994
                              gen_entry *t = NULL;
995
                              /* Try to find a value for the
996
                                 conditional by looking back through
997
                                 the previously defined bits for one
998
                                 that covers the designated
999
                                 conditional field */
1000
                              for (bit = bits; bit != NULL; bit = bit->next)
1001
                                {
1002
                                  if (bit->field->word_nr ==
1003
                                      condition->field->word_nr
1004
                                      && bit->first <= condition->field->first
1005
                                      && bit->last >= condition->field->last)
1006
                                    {
1007
                                      /* the bit field fully specified
1008
                                         the conditional field's value */
1009
                                      value = sub_val (bit->value, bit->last,
1010
                                                       condition->field->
1011
                                                       first,
1012
                                                       condition->field->
1013
                                                       last);
1014
                                    }
1015
                                }
1016
                              /* Try to find a value by looking
1017
                                 through this and previous tables */
1018
                              if (bit == NULL)
1019
                                {
1020
                                  for (t = table;
1021
                                       t->parent != NULL; t = t->parent)
1022
                                    {
1023
                                      if (t->parent->opcode->word_nr ==
1024
                                          condition->field->word_nr
1025
                                          && t->parent->opcode->first <=
1026
                                          condition->field->first
1027
                                          && t->parent->opcode->last >=
1028
                                          condition->field->last)
1029
                                        {
1030
                                          /* the table entry fully
1031
                                             specified the condition
1032
                                             field's value */
1033
                                          /* extract the field's value
1034
                                             from the opcode */
1035
                                          value =
1036
                                            sub_val (t->opcode_nr,
1037
                                                     t->parent->opcode->last,
1038
                                                     condition->field->first,
1039
                                                     condition->field->last);
1040
                                          /* this is a requirement of
1041
                                             a conditonal field
1042
                                             refering to another field */
1043
                                          ASSERT ((condition->field->first -
1044
                                                   condition->field->last) ==
1045
                                                  (first_pos - last_pos));
1046
                                          printf
1047
                                            ("value=%d, opcode_nr=%d, last=%d, [%d..%d]\n",
1048
                                             value, t->opcode_nr,
1049
                                             t->parent->opcode->last,
1050
                                             condition->field->first,
1051
                                             condition->field->last);
1052
                                        }
1053
                                    }
1054
                                }
1055
                              if (bit == NULL && t == NULL)
1056
                                error (instruction->line,
1057
                                       "Conditional `%s' of field `%s' isn't expanded",
1058
                                       condition->string, field->val_string);
1059
                              switch (condition->test)
1060
                                {
1061
                                case insn_field_cond_ne:
1062
                                  if (value == val)
1063
                                    is_precluded = 1;
1064
                                  break;
1065
                                case insn_field_cond_eq:
1066
                                  if (value != val)
1067
                                    is_precluded = 1;
1068
                                  break;
1069
                                }
1070
                              break;
1071
                            }
1072
                          }
1073
                      }
1074
                    if (!is_precluded)
1075
                      {
1076
                        /* Only add additional hardwired bit
1077
                           information if the entry is not going to
1078
                           later be combined */
1079
                        if (table->opcode_rule->with_combine)
1080
                          {
1081
                            gen_entry_expand_opcode (table, instruction,
1082
                                                     last_pos + 1,
1083
                                                     ((opcode_nr << width) |
1084
                                                      val), bits);
1085
                          }
1086
                        else
1087
                          {
1088
                            opcode_bits *new_bits =
1089
                              new_opcode_bits (bits, val,
1090
                                               first_pos, last_pos,
1091
                                               field,
1092
                                               table->opcode);
1093
                            gen_entry_expand_opcode (table, instruction,
1094
                                                     last_pos + 1,
1095
                                                     ((opcode_nr << width) |
1096
                                                      val), new_bits);
1097
                          }
1098
                      }
1099
                  }
1100
              }
1101
          }
1102
        }
1103
    }
1104
}
1105
 
1106
static void
1107
gen_entry_insert_expanding (gen_entry *table, insn_entry * instruction)
1108
{
1109
  gen_entry_expand_opcode (table,
1110
                           instruction,
1111
                           table->opcode->first, 0, table->expanded_bits);
1112
}
1113
 
1114
 
1115
static int
1116
insns_match_format_names (insn_list *insns, filter *format_names)
1117
{
1118
  if (format_names != NULL)
1119
    {
1120
      insn_list *i;
1121
      for (i = insns; i != NULL; i = i->next)
1122
        {
1123
          if (i->insn->format_name != NULL
1124
              && !filter_is_member (format_names, i->insn->format_name))
1125
            return 0;
1126
        }
1127
    }
1128
  return 1;
1129
}
1130
 
1131
static int
1132
table_matches_path (gen_entry *table, decode_path_list *paths)
1133
{
1134
  if (paths == NULL)
1135
    return 1;
1136
  while (paths != NULL)
1137
    {
1138
      gen_entry *entry = table;
1139
      decode_path *path = paths->path;
1140
      while (1)
1141
        {
1142
          if (entry == NULL && path == NULL)
1143
            return 1;
1144
          if (entry == NULL || path == NULL)
1145
            break;
1146
          if (entry->opcode_nr != path->opcode_nr)
1147
            break;
1148
          entry = entry->parent;
1149
          path = path->parent;
1150
        }
1151
      paths = paths->next;
1152
    }
1153
  return 0;
1154
}
1155
 
1156
 
1157
static int
1158
insns_match_conditions (insn_list *insns, decode_cond *conditions)
1159
{
1160
  if (conditions != NULL)
1161
    {
1162
      insn_list *i;
1163
      for (i = insns; i != NULL; i = i->next)
1164
        {
1165
          decode_cond *cond;
1166
          for (cond = conditions; cond != NULL; cond = cond->next)
1167
            {
1168
              int bit_nr;
1169
              if (i->insn->nr_words <= cond->word_nr)
1170
                return 0;
1171
              for (bit_nr = 0; bit_nr < options.insn_bit_size; bit_nr++)
1172
                {
1173
                  if (!cond->mask[bit_nr])
1174
                    continue;
1175
                  if (!i->insn->word[cond->word_nr]->bit[bit_nr]->mask)
1176
                    return 0;
1177
                  if ((i->insn->word[cond->word_nr]->bit[bit_nr]->value
1178
                       == cond->value[bit_nr]) == !cond->is_equal)
1179
                    return 0;
1180
                }
1181
            }
1182
        }
1183
    }
1184
  return 1;
1185
}
1186
 
1187
static int
1188
insns_match_nr_words (insn_list *insns, int nr_words)
1189
{
1190
  insn_list *i;
1191
  for (i = insns; i != NULL; i = i->next)
1192
    {
1193
      if (i->insn->nr_words < nr_words)
1194
        return 0;
1195
    }
1196
  return 1;
1197
}
1198
 
1199
static int
1200
insn_list_cmp (insn_list *l, insn_list *r)
1201
{
1202
  while (1)
1203
    {
1204
      insn_entry *insn;
1205
      if (l == NULL && r == NULL)
1206
        return 0;
1207
      if (l == NULL)
1208
        return -1;
1209
      if (r == NULL)
1210
        return 1;
1211
      if (l->insn != r->insn)
1212
        return -1;              /* somewhat arbitrary at present */
1213
      /* skip this insn */
1214
      insn = l->insn;
1215
      while (l != NULL && l->insn == insn)
1216
        l = l->next;
1217
      while (r != NULL && r->insn == insn)
1218
        r = r->next;
1219
    }
1220
}
1221
 
1222
 
1223
 
1224
static void
1225
gen_entry_expand_insns (gen_entry *table)
1226
{
1227
  decode_table *opcode_rule;
1228
 
1229
  ASSERT (table->nr_insns >= 1);
1230
 
1231
  /* determine a valid opcode */
1232
  for (opcode_rule = table->opcode_rule;
1233
       opcode_rule != NULL; opcode_rule = opcode_rule->next)
1234
    {
1235
      char *discard_reason;
1236
      if (table->top->model != NULL
1237
          && opcode_rule->model_names != NULL
1238
          && !filter_is_member (opcode_rule->model_names,
1239
                                table->top->model->name))
1240
        {
1241
          /* the rule isn't applicable to this processor */
1242
          discard_reason = "wrong model";
1243
        }
1244
      else if (table->nr_insns == 1 && opcode_rule->conditions == NULL)
1245
        {
1246
          /* for safety, require a pre-codition when attempting to
1247
             apply a rule to a single instruction */
1248
          discard_reason = "need pre-condition when nr-insn == 1";
1249
        }
1250
      else if (table->nr_insns == 1 && !opcode_rule->with_duplicates)
1251
        {
1252
          /* Little point in expanding a single instruction when we're
1253
             not duplicating the semantic functions that this table
1254
             calls */
1255
          discard_reason = "need duplication with nr-insns == 1";
1256
        }
1257
      else
1258
        if (!insns_match_format_names
1259
            (table->insns, opcode_rule->format_names))
1260
        {
1261
          discard_reason = "wrong format name";
1262
        }
1263
      else if (!insns_match_nr_words (table->insns, opcode_rule->word_nr + 1))
1264
        {
1265
          discard_reason = "wrong nr words";
1266
        }
1267
      else if (!table_matches_path (table, opcode_rule->paths))
1268
        {
1269
          discard_reason = "path failed";
1270
        }
1271
      else
1272
        if (!insns_match_conditions (table->insns, opcode_rule->conditions))
1273
        {
1274
          discard_reason = "condition failed";
1275
        }
1276
      else
1277
        {
1278
          discard_reason = "no opcode field";
1279
          table->opcode = gen_entry_find_opcode_field (table->insns,
1280
                                                       opcode_rule,
1281
                                                       table->nr_insns == 1     /*string-only */
1282
            );
1283
          if (table->opcode != NULL)
1284
            {
1285
              table->opcode_rule = opcode_rule;
1286
              break;
1287
            }
1288
        }
1289
 
1290
      if (options.trace.rule_rejection)
1291
        {
1292
          print_gen_entry_path (opcode_rule->line, table, notify);
1293
          notify (NULL, ": rule discarded - %s\n", discard_reason);
1294
        }
1295
    }
1296
 
1297
  /* did we find anything */
1298
  if (opcode_rule == NULL)
1299
    {
1300
      /* the decode table failed, this set of instructions haven't
1301
         been uniquely identified */
1302
      if (table->nr_insns > 1)
1303
        {
1304
          print_gen_entry_insns (table, warning,
1305
                                 "was not uniquely decoded",
1306
                                 "decodes to the same entry");
1307
          error (NULL, "");
1308
        }
1309
      return;
1310
    }
1311
 
1312
  /* Determine the number of words that must have been prefetched for
1313
     this table to function */
1314
  if (table->parent == NULL)
1315
    table->nr_prefetched_words = table->opcode_rule->word_nr + 1;
1316
  else if (table->opcode_rule->word_nr + 1 >
1317
           table->parent->nr_prefetched_words)
1318
    table->nr_prefetched_words = table->opcode_rule->word_nr + 1;
1319
  else
1320
    table->nr_prefetched_words = table->parent->nr_prefetched_words;
1321
 
1322
  /* back link what we found to its parent */
1323
  if (table->parent != NULL)
1324
    {
1325
      ASSERT (table->parent->opcode != NULL);
1326
      table->opcode->parent = table->parent->opcode;
1327
    }
1328
 
1329
  /* report the rule being used to expand the instructions */
1330
  if (options.trace.rule_selection)
1331
    {
1332
      print_gen_entry_path (table->opcode_rule->line, table, notify);
1333
      notify (NULL,
1334
              ": decode - word %d, bits [%d..%d] in [%d..%d], opcodes %d, entries %d\n",
1335
              table->opcode->word_nr,
1336
              i2target (options.hi_bit_nr, table->opcode->first),
1337
              i2target (options.hi_bit_nr, table->opcode->last),
1338
              i2target (options.hi_bit_nr, table->opcode_rule->first),
1339
              i2target (options.hi_bit_nr, table->opcode_rule->last),
1340
              table->opcode->nr_opcodes, table->nr_entries);
1341
    }
1342
 
1343
  /* expand the raw instructions according to the opcode */
1344
  {
1345
    insn_list *entry;
1346
    for (entry = table->insns; entry != NULL; entry = entry->next)
1347
      {
1348
        if (options.trace.insn_expansion)
1349
          {
1350
            print_gen_entry_path (table->opcode_rule->line, table, notify);
1351
            notify (NULL, ": expand - %s.%s\n",
1352
                    entry->insn->format_name, entry->insn->name);
1353
          }
1354
        gen_entry_insert_expanding (table, entry->insn);
1355
      }
1356
  }
1357
 
1358
  /* dump the results */
1359
  if (options.trace.entries)
1360
    {
1361
      gen_entry *entry;
1362
      for (entry = table->entries; entry != NULL; entry = entry->sibling)
1363
        {
1364
          insn_list *l;
1365
          print_gen_entry_path (table->opcode_rule->line, entry, notify);
1366
          notify (NULL, ": %d - entries %d -",
1367
                  entry->opcode_nr, entry->nr_insns);
1368
          for (l = entry->insns; l != NULL; l = l->next)
1369
            notify (NULL, " %s.%s", l->insn->format_name, l->insn->name);
1370
          notify (NULL, "\n");
1371
        }
1372
    }
1373
 
1374
  /* perform a combine pass if needed */
1375
  if (table->opcode_rule->with_combine)
1376
    {
1377
      gen_entry *entry;
1378
      for (entry = table->entries; entry != NULL; entry = entry->sibling)
1379
        {
1380
          if (entry->combined_parent == NULL)
1381
            {
1382
              gen_entry **last = &entry->combined_next;
1383
              gen_entry *alt;
1384
              for (alt = entry->sibling; alt != NULL; alt = alt->sibling)
1385
                {
1386
                  if (alt->combined_parent == NULL
1387
                      && insn_list_cmp (entry->insns, alt->insns) == 0)
1388
                    {
1389
                      alt->combined_parent = entry;
1390
                      *last = alt;
1391
                      last = &alt->combined_next;
1392
                    }
1393
                }
1394
            }
1395
        }
1396
      if (options.trace.combine)
1397
        {
1398
          int nr_unique = 0;
1399
          gen_entry *entry;
1400
          for (entry = table->entries; entry != NULL; entry = entry->sibling)
1401
            {
1402
              if (entry->combined_parent == NULL)
1403
                {
1404
                  insn_list *l;
1405
                  gen_entry *duplicate;
1406
                  nr_unique++;
1407
                  print_gen_entry_path (table->opcode_rule->line, entry,
1408
                                        notify);
1409
                  for (duplicate = entry->combined_next; duplicate != NULL;
1410
                       duplicate = duplicate->combined_next)
1411
                    {
1412
                      notify (NULL, "+%d", duplicate->opcode_nr);
1413
                    }
1414
                  notify (NULL, ": entries %d -", entry->nr_insns);
1415
                  for (l = entry->insns; l != NULL; l = l->next)
1416
                    {
1417
                      notify (NULL, " %s.%s",
1418
                              l->insn->format_name, l->insn->name);
1419
                    }
1420
                  notify (NULL, "\n");
1421
                }
1422
            }
1423
          print_gen_entry_path (table->opcode_rule->line, table, notify);
1424
          notify (NULL,
1425
                  ": combine - word %d, bits [%d..%d] in [%d..%d], opcodes %d, entries %d, unique %d\n",
1426
                  table->opcode->word_nr, i2target (options.hi_bit_nr,
1427
                                                    table->opcode->first),
1428
                  i2target (options.hi_bit_nr, table->opcode->last),
1429
                  i2target (options.hi_bit_nr, table->opcode_rule->first),
1430
                  i2target (options.hi_bit_nr, table->opcode_rule->last),
1431
                  table->opcode->nr_opcodes, table->nr_entries, nr_unique);
1432
        }
1433
    }
1434
 
1435
  /* Check that the rule did more than re-arange the order of the
1436
     instructions */
1437
  {
1438
    gen_entry *entry;
1439
    for (entry = table->entries; entry != NULL; entry = entry->sibling)
1440
      {
1441
        if (entry->combined_parent == NULL)
1442
          {
1443
            if (insn_list_cmp (table->insns, entry->insns) == 0)
1444
              {
1445
                print_gen_entry_path (table->opcode_rule->line, table,
1446
                                      warning);
1447
                warning (NULL,
1448
                         ": Applying rule just copied all instructions\n");
1449
                print_gen_entry_insns (entry, warning, "Copied", NULL);
1450
                error (NULL, "");
1451
              }
1452
          }
1453
      }
1454
  }
1455
 
1456
  /* if some form of expanded table, fill in the missing dots */
1457
  switch (table->opcode_rule->gen)
1458
    {
1459
    case padded_switch_gen:
1460
    case array_gen:
1461
    case goto_switch_gen:
1462
      if (!table->opcode->is_boolean)
1463
        {
1464
          gen_entry **entry = &table->entries;
1465
          gen_entry *illegals = NULL;
1466
          gen_entry **last_illegal = &illegals;
1467
          int opcode_nr = 0;
1468
          while (opcode_nr < table->opcode->nr_opcodes)
1469
            {
1470
              if ((*entry) == NULL || (*entry)->opcode_nr != opcode_nr)
1471
                {
1472
                  /* missing - insert it under our feet at *entry */
1473
                  gen_entry_insert_insn (table, table->top->isa->illegal_insn, table->opcode->word_nr, 0,        /* nr_prefetched_words == 0 for invalid */
1474
                                         opcode_nr, NULL);
1475
                  ASSERT ((*entry) != NULL);
1476
                  ASSERT ((*entry)->opcode_nr == opcode_nr);
1477
                  (*last_illegal) = *entry;
1478
                  (*last_illegal)->combined_parent = illegals;
1479
                  last_illegal = &(*last_illegal)->combined_next;
1480
                }
1481
              entry = &(*entry)->sibling;
1482
              opcode_nr++;
1483
            }
1484
          /* oops, will have pointed the first illegal insn back to
1485
             its self.  Fix this */
1486
          if (illegals != NULL)
1487
            illegals->combined_parent = NULL;
1488
        }
1489
      break;
1490
    case switch_gen:
1491
    case invalid_gen:
1492
      /* ignore */
1493
      break;
1494
    }
1495
 
1496
  /* and do the same for the newly created sub entries but *only*
1497
     expand entries that haven't been combined. */
1498
  {
1499
    gen_entry *entry;
1500
    for (entry = table->entries; entry != NULL; entry = entry->sibling)
1501
      {
1502
        if (entry->combined_parent == NULL)
1503
          {
1504
            gen_entry_expand_insns (entry);
1505
          }
1506
      }
1507
  }
1508
}
1509
 
1510
void
1511
gen_tables_expand_insns (gen_table *gen)
1512
{
1513
  gen_list *entry;
1514
  for (entry = gen->tables; entry != NULL; entry = entry->next)
1515
    {
1516
      gen_entry_expand_insns (entry->table);
1517
    }
1518
}
1519
 
1520
 
1521
/* create a list of all the semantic functions that need to be
1522
   generated.  Eliminate any duplicates. Verify that the decode stage
1523
   worked. */
1524
 
1525
static void
1526
make_gen_semantics_list (lf *file, gen_entry *entry, int depth, void *data)
1527
{
1528
  gen_table *gen = (gen_table *) data;
1529
  insn_list *insn;
1530
  /* Not interested in an entrie that have been combined into some
1531
     other entry at the same level */
1532
  if (entry->combined_parent != NULL)
1533
    return;
1534
 
1535
  /* a leaf should contain exactly one instruction. If not the decode
1536
     stage failed. */
1537
  ASSERT (entry->nr_insns == 1);
1538
 
1539
  /* Enter this instruction into the list of semantic functions. */
1540
  insn = insn_list_insert (&gen->semantics, &gen->nr_semantics,
1541
                           entry->insns->insn,
1542
                           entry->expanded_bits,
1543
                           entry->parent->opcode,
1544
                           entry->insns->nr_prefetched_words,
1545
                           merge_duplicate_insns);
1546
  /* point the table entry at the real semantic function */
1547
  ASSERT (insn != NULL);
1548
  entry->insns->semantic = insn;
1549
}
1550
 
1551
 
1552
void
1553
gen_tables_expand_semantics (gen_table *gen)
1554
{
1555
  gen_list *entry;
1556
  for (entry = gen->tables; entry != NULL; entry = entry->next)
1557
    {
1558
      gen_entry_traverse_tree (NULL, entry->table, 1,   /* depth */
1559
                               NULL,    /* start-handler */
1560
                               make_gen_semantics_list, /* leaf-handler */
1561
                               NULL,    /* end-handler */
1562
                               gen);    /* data */
1563
    }
1564
}
1565
 
1566
 
1567
 
1568
#ifdef MAIN
1569
 
1570
 
1571
static void
1572
dump_opcode_field (lf *file,
1573
                   char *prefix,
1574
                   opcode_field *field, char *suffix, int levels)
1575
{
1576
  lf_printf (file, "%s(opcode_field *) 0x%lx", prefix, (long) field);
1577
  if (levels && field != NULL)
1578
    {
1579
      lf_indent (file, +1);
1580
      lf_printf (file, "\n(first %d)", field->first);
1581
      lf_printf (file, "\n(last %d)", field->last);
1582
      lf_printf (file, "\n(nr_opcodes %d)", field->nr_opcodes);
1583
      lf_printf (file, "\n(is_boolean %d)", field->is_boolean);
1584
      lf_printf (file, "\n(boolean_constant %d)", field->boolean_constant);
1585
      dump_opcode_field (file, "\n(parent ", field->parent, ")", levels - 1);
1586
      lf_indent (file, -1);
1587
    }
1588
  lf_printf (file, "%s", suffix);
1589
}
1590
 
1591
 
1592
static void
1593
dump_opcode_bits (lf *file,
1594
                  char *prefix, opcode_bits *bits, char *suffix, int levels)
1595
{
1596
  lf_printf (file, "%s(opcode_bits *) 0x%lx", prefix, (long) bits);
1597
 
1598
  if (levels && bits != NULL)
1599
    {
1600
      lf_indent (file, +1);
1601
      lf_printf (file, "\n(value %d)", bits->value);
1602
      dump_opcode_field (file, "\n(opcode ", bits->opcode, ")", 0);
1603
      dump_insn_field (file, "\n(field ", bits->field, ")");
1604
      dump_opcode_bits (file, "\n(next ", bits->next, ")", levels - 1);
1605
      lf_indent (file, -1);
1606
    }
1607
  lf_printf (file, "%s", suffix);
1608
}
1609
 
1610
 
1611
 
1612
static void
1613
dump_insn_list (lf *file, char *prefix, insn_list *entry, char *suffix)
1614
{
1615
  lf_printf (file, "%s(insn_list *) 0x%lx", prefix, (long) entry);
1616
 
1617
  if (entry != NULL)
1618
    {
1619
      lf_indent (file, +1);
1620
      dump_insn_entry (file, "\n(insn ", entry->insn, ")");
1621
      lf_printf (file, "\n(next 0x%lx)", (long) entry->next);
1622
      lf_indent (file, -1);
1623
    }
1624
  lf_printf (file, "%s", suffix);
1625
}
1626
 
1627
 
1628
static void
1629
dump_insn_word_entry_list_entries (lf *file,
1630
                                   char *prefix,
1631
                                   insn_list *entry, char *suffix)
1632
{
1633
  lf_printf (file, "%s", prefix);
1634
  while (entry != NULL)
1635
    {
1636
      dump_insn_list (file, "\n(", entry, ")");
1637
      entry = entry->next;
1638
    }
1639
  lf_printf (file, "%s", suffix);
1640
}
1641
 
1642
 
1643
static void
1644
dump_gen_entry (lf *file,
1645
                char *prefix, gen_entry *table, char *suffix, int levels)
1646
{
1647
 
1648
  lf_printf (file, "%s(gen_entry *) 0x%lx", prefix, (long) table);
1649
 
1650
  if (levels && table !=NULL)
1651
    {
1652
 
1653
      lf_indent (file, +1);
1654
      lf_printf (file, "\n(opcode_nr %d)", table->opcode_nr);
1655
      lf_printf (file, "\n(word_nr %d)", table->word_nr);
1656
      dump_opcode_bits (file, "\n(expanded_bits ", table->expanded_bits, ")",
1657
                        -1);
1658
      lf_printf (file, "\n(nr_insns %d)", table->nr_insns);
1659
      dump_insn_word_entry_list_entries (file, "\n(insns ", table->insns,
1660
                                         ")");
1661
      dump_decode_rule (file, "\n(opcode_rule ", table->opcode_rule, ")");
1662
      dump_opcode_field (file, "\n(opcode ", table->opcode, ")", 0);
1663
      lf_printf (file, "\n(nr_entries %d)", table->nr_entries);
1664
      dump_gen_entry (file, "\n(entries ", table->entries, ")",
1665
                      table->nr_entries);
1666
      dump_gen_entry (file, "\n(sibling ", table->sibling, ")", levels - 1);
1667
      dump_gen_entry (file, "\n(parent ", table->parent, ")", 0);
1668
      lf_indent (file, -1);
1669
    }
1670
  lf_printf (file, "%s", suffix);
1671
}
1672
 
1673
static void
1674
dump_gen_list (lf *file,
1675
               char *prefix, gen_list *entry, char *suffix, int levels)
1676
{
1677
  while (entry != NULL)
1678
    {
1679
      lf_printf (file, "%s(gen_list *) 0x%lx", prefix, (long) entry);
1680
      dump_gen_entry (file, "\n(", entry->table, ")", levels);
1681
      lf_printf (file, "\n(next (gen_list *) 0x%lx)", (long) entry->next);
1682
      lf_printf (file, "%s", suffix);
1683
    }
1684
}
1685
 
1686
 
1687
static void
1688
dump_gen_table (lf *file,
1689
                char *prefix, gen_table *gen, char *suffix, int levels)
1690
{
1691
  lf_printf (file, "%s(gen_table *) 0x%lx", prefix, (long) gen);
1692
  lf_printf (file, "\n(isa (insn_table *) 0x%lx)", (long) gen->isa);
1693
  lf_printf (file, "\n(rules (decode_table *) 0x%lx)", (long) gen->rules);
1694
  dump_gen_list (file, "\n(", gen->tables, ")", levels);
1695
  lf_printf (file, "%s", suffix);
1696
}
1697
 
1698
 
1699
igen_options options;
1700
 
1701
int
1702
main (int argc, char **argv)
1703
{
1704
  decode_table *decode_rules;
1705
  insn_table *instructions;
1706
  gen_table *gen;
1707
  lf *l;
1708
 
1709
  if (argc != 7)
1710
    error (NULL,
1711
           "Usage: insn <filter-in> <hi-bit-nr> <insn-bit-size> <widths> <decode-table> <insn-table>\n");
1712
 
1713
  INIT_OPTIONS (options);
1714
 
1715
  filter_parse (&options.flags_filter, argv[1]);
1716
 
1717
  options.hi_bit_nr = a2i (argv[2]);
1718
  options.insn_bit_size = a2i (argv[3]);
1719
  options.insn_specifying_widths = a2i (argv[4]);
1720
  ASSERT (options.hi_bit_nr < options.insn_bit_size);
1721
 
1722
  instructions = load_insn_table (argv[6], NULL);
1723
  decode_rules = load_decode_table (argv[5]);
1724
  gen = make_gen_tables (instructions, decode_rules);
1725
 
1726
  gen_tables_expand_insns (gen);
1727
 
1728
  l = lf_open ("-", "stdout", lf_omit_references, lf_is_text, "tmp-ld-insn");
1729
 
1730
  dump_gen_table (l, "(", gen, ")\n", -1);
1731
  return 0;
1732
}
1733
 
1734
#endif

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.