1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
203
204
205
206
207
208
209
210
211
212
213
214
215
216
217
218
219
220
221
222
223
224
225
226
227
228
229
230
231
232
233
234
235
236
237
238
239
240
241
|
#!/usr/bin/perl
# Copyright 2012-2022, BlueFANG
use strict;
use warnings;
use Carp;
use feature 'say';
use Getopt::Long;
use Pod::Usage;
use Data::Dumper;
use Cwd;
my $man = 0;
my $help = 0;
my $initem = '';
my @hex_addresses = ();
my $verbose = '';
my $lookup_const = undef;
my @consts_of_interest = ();
my @values_of_interest = ();
#Getopt::Long::Configure ("bundling"); # to allow -abc to set a, b, and c
GetOptions ("help|?" => \$help,
man => \$man,
verbose => \$verbose,
"regaddr=s" => sub {
if ($verbose) {
print "Pushing name $_[1]\n";
}
push @hex_addresses, hex $_[1];
},
"lookup=s" => sub {
if ($verbose) {
print "Pushing const name $_[1]\n";
}
push @values_of_interest, ($_[1] =~ m/0x\d+/ ? hex $_[1] : $_[1]);
},
"const=s" => sub {
if ($verbose) {
print "Pushing const value $_[1]\n";
}
push @consts_of_interest, ($_[1] =~ m/0x\d+/ ? hex $_[1] : $_[1]);
},
) or pod2usage(2);
pod2usage(-exitval => 0, -verbose => 1) if $help;
pod2usage(-exitval => 0, -verbose => 2) if $man;
my $input_db = cwd."/scripts/perl/symdb.lst";
if ($ARGV[0]) {
$input_db = $ARGV[0];
}
open FILE, $input_db or die "Cannot open input file $ARGV[0]\n";
my @offset_names = qw(EM_BLE_TX_BUFFER_DATA_OFFSET EM_BLE_RX_DESC_OFFSET
EM_BLE_RX_BUFFER_OFFSET EM_BLE_WPV_OFFSET EM_BLE_RAL_OFFSET
EM_BLE_WPB_OFFSET EM_BLE_TX_DESC_OFFSET EM_BLE_CS_OFFSET EM_BLE_TX_BUFFER_CNTL_OFFSET);
# EM_BLE_TX_AUDIO_BUFFER_OFFSET
# EM_BLE_RX_AUDIO_BUFFER_OFFSET --- there is no audio configured
my %const_hash = ();
my %value_lookup = ();
while (<FILE>) {
my $inline = $_;
if ( $inline =~ m/^(.+)=(\d+)\{([^{}]*)\}\{([^{}]*)\}$/ ) { #
my $name = $1;
my $value = $2;
my $origin = $4;
my $location = $3;
$const_hash{$name} = {
value => $value,
origin => $origin,
location => $location
};
if ( !(exists $value_lookup{$value}) ) {
$value_lookup{$value} = ["$name\{$location\}"];
} else {
push @{$value_lookup{$value}}, "$name\{$location\}";
}
}
}
my %area_period = (
EM_BLE_CS_OFFSET => $const_hash{REG_BLE_EM_CS_SIZE},
EM_BLE_RAL_OFFSET => $const_hash{REG_BLE_EM_RAL_SIZE},
EM_BLE_WPV_OFFSET => $const_hash{REG_BLE_EM_WPV_SIZE},
EM_BLE_WPB_OFFSET => $const_hash{REG_BLE_EM_WPB_SIZE},
# EM_BLE_TX_AUDIO_BUFFER_OFFSET => $const_hash{REG_BLE_EM_TX_AUDIO_BUFFER_SIZE},
# EM_BLE_RX_AUDIO_BUFFER_OFFSET => $const_hash{REG_BLE_EM_RX_AUDIO_BUFFER_SIZE},
EM_BLE_TX_DESC_OFFSET => $const_hash{REG_BLE_EM_TX_DESC_SIZE},
EM_BLE_RX_DESC_OFFSET => $const_hash{REG_BLE_EM_RX_DESC_SIZE},
EM_BLE_RX_BUFFER_OFFSET => $const_hash{REG_BLE_EM_RX_BUFFER_SIZE},
);
my %offset_subhash = %const_hash{@offset_names};
my %value_subhash;
for my $key (keys %offset_subhash) {
$value_subhash{$offset_subhash{$key}->{value} + $const_hash{REG_COMMON_EM_ET_BASE_ADDR}->{value}} = $key;
}
$value_subhash{$const_hash{REG_BLECORE_BASE_ADDR}->{value}}="...";
my @offset_values = sort numerically keys %value_subhash;
sub fit_value($) {
my $value = shift;
my $lower = '';
foreach my $i (0..$#offset_values) {
if ( $lower and $offset_values[$i] > $value ) {
return $lower;
} elsif ( $offset_values[$i] <= $value ) {
$lower = $value_subhash{$offset_values[$i]};
} else {
return undef;
}
}
return undef;
}
sub numerically {
$a<=>$b;
}
my %reg_addresses = ();
my %reg_names = ();
for my $key (keys %const_hash) {
if ($key =~ m/BLE_(.*)_ADDR/) {
$reg_addresses{$key} = $const_hash{$key}->{value};
$reg_names{$const_hash{$key}->{value}} = $1;
}
}
# output register names
for ( my $addr = 0; $addr < scalar @hex_addresses; $addr++ ) {
my $group;
my $reduced_addr;
my $reg_index;
my $base;
my $reg_name;
my $reg_abs;
$group = fit_value($hex_addresses[$addr]);
if ( $group eq "..." ) {
$base = $const_hash{REG_BLECORE_BASE_ADDR}->{value};
$reduced_addr = $hex_addresses[$addr];
$reg_index = 0;
$reg_abs = $reduced_addr;
$reg_name = $reg_names{$reduced_addr};
} else {
$base = $const_hash{REG_COMMON_EM_ET_BASE_ADDR}->{value};
$reduced_addr = $base + ($hex_addresses[$addr] - $base - $const_hash{$group}->{value}) %
$area_period{$group}->{value};
$reg_index = int ( ($hex_addresses[$addr] - $base - $const_hash{$group}->{value}) /
$area_period{$group}->{value});
$reg_abs = $reduced_addr + $const_hash{$group}->{value};
$reg_name = $reg_names{$reduced_addr + $const_hash{$group}->{value}};
}
printf "name: $reg_name\[$reg_index\], reduced: 0x%08x (after offset: 0x%08x, group: $group)\n", $reduced_addr, $reg_abs;
}
# output constant values
for ( my $addr = 0; $addr < scalar @consts_of_interest; $addr++ ) {
print "$consts_of_interest[$addr]=$const_hash{$consts_of_interest[$addr]}->{value}\n";
}
# output constant names
for ( my $addr = 0; $addr < scalar @values_of_interest; $addr++ ) {
if ( exists $value_lookup{$values_of_interest[$addr]}) {
printf "Value ($values_of_interest[$addr] 0x%x):\n ", $values_of_interest[$addr];
say +(join "\n ", sort @{$value_lookup{$values_of_interest[$addr]}});
}
}
__END__
=head1 DIG_OUT
dig_out.pl - Output register and constant information
=head1 SYNOPSIS
dig_out.pl [options] input_file
Options:
--help|-h|-? brief help message
--man|-m full documentation
--regaddr=<register address> look up the register name
and index
--lookup=<const> look up constant names that
have the given value
=head1 OPTIONS
=over 8
=item B<--help>
Print a brief help message and exit.
=item B<--man>
Print the manual page and exit.
=item B<--regaddr>=<register address>
Look up the register name and index based on the hex address (0x prefix is optional).
=item B<--lookup>=<const>
Look up constant names that have the given value.
=back
=head1 DESCRIPTION
B<dig_out.pl> will read the given <input_file> and output various values
according to the options given.
=cut
|