More perl-like idioms for generating regdis.c
[platform/upstream/nasm.git] / regs.pl
1 #!/usr/bin/perl
2 # $Id$
3 #
4 # Read regs.dat and output regs.h and regs.c (included in names.c)
5 #
6
7 $nline = 0;
8
9 sub process_line($) {
10     my($line) = @_;
11     my @v;
12
13     if ( $line !~ /^\s*(\S+)\s*(\S+)\s*(\S+)\s*([0-9]+)\s*$/ ) {
14         die "regs.dat:$nline: invalid input\n";
15     }
16     $reg    = $1;
17     $aclass = $2;
18     $dclass = $3;
19     $regval   = $4;
20
21     $regs{$reg} = $aclass;
22     $regvals{$reg} = $regval;
23
24     if ( !defined($disclass{$dclass}) ) {
25         $disclass{$dclass} = [(undef) x 8];
26     }
27
28     $disclass{$dclass}->[$regval] = $reg;
29 }
30
31 ($fmt, $file) = @ARGV;
32
33 %regs = ();
34 %regvals = ();
35 %disclass = ();
36 open(REGS, "< ${file}") or die "$0: Cannot open $file\n";
37 while ( defined($line = <REGS>) ) {
38     $nline++;
39
40     chomp $line;
41     $line =~ s/\s*(\#.*|)$//;
42     
43     next if ( $line eq '' );
44
45     if ( $line =~ /\*/ ) {
46         for ( $i = 0 ; $i < 8 ; $i++ ) {
47             ($xline = $line) =~ s/\*/$i/g;
48             process_line($xline);
49         }
50     } else {
51         process_line($line);
52     }
53 }
54 close(REGS);
55
56 if ( $fmt eq 'h' ) {
57     # Output regs.h
58     print "/* automatically generated from $file - do not edit */\n";
59     print "enum reg_enum {\n";
60     $attach = ' = EXPR_REG_START'; # EXPR_REG_START == 1
61     foreach $reg ( sort(keys(%regs)) ) {
62         print "    R_\U${reg}\E${attach},\n";
63         $attach = ''; $ch = ',';
64     }
65     print "    REG_ENUM_LIMIT\n";
66     print "};\n\n";
67     foreach $reg ( sort(keys(%regs)) ) {
68         print "#define REG_NUM_\U${reg}     $regvals{$reg}\n";
69     }
70     print "\n";
71 } elsif ( $fmt eq 'c' ) {
72     # Output regs.c
73     print "/* automatically generated from $file - do not edit */\n";
74     print "static const char *reg_names[] = "; $ch = '{';
75     # This one has no dummy entry for 0
76     foreach $reg ( sort(keys(%regs)) ) {
77         print "$ch\n    \"${reg}\"";
78         $ch = ',';
79     }
80     print "\n};\n";
81 } elsif ( $fmt eq 'fc' ) {
82     # Output regflags.c
83     print "/* automatically generated from $file - do not edit */\n";
84     print "static const int32_t reg_flags[] = {\n";
85     print "    0";              # Dummy entry for 0
86     foreach $reg ( sort(keys(%regs)) ) {
87         print ",\n    ", $regs{$reg}; # Print the class of the register
88     }
89     print "\n};\n";
90 } elsif ( $fmt eq 'vc' ) {
91     # Output regvals.c
92     print "/* automatically generated from $file - do not edit */\n";
93     print "static const int regvals[] = {\n";
94     print "    -1";             # Dummy entry for 0
95     foreach $reg ( sort(keys(%regs)) ) {
96         print ",\n    ", $regvals{$reg}; # Print the regval of the register
97     }
98     print "\n};\n";
99 } elsif ( $fmt eq 'dc' ) {
100     # Output regdis.c
101     print "/* automatically generated from $file - do not edit */\n";
102     foreach $class ( sort(keys(%disclass)) ) {
103         printf "static const int %-8s[] = {", $class;
104         @foo = @{$disclass{$class}};
105         @bar = ();
106         for ( $i = 0 ; $i < scalar(@foo) ; $i++ ) {
107             if (defined($foo[$i])) {
108                 push(@bar, "R_\U$foo[$i]\E");
109             }
110         }
111         print join(',', @bar), "};\n";
112     }
113 } else {
114     die "$0: Unknown output format\n";
115 }