daf4a09e409171cb1433b068aa9aa9a8c1d218c6
[spider.git] / perl / create_prefix.pl
1 #!/usr/bin/env perl
2 # a program to create a prefix file from a wpxloc.raw file
3 #
4 # Copyright (c) - Dirk Koopman G1TLH
5 #
6 #
7 #
8
9 require 5.004;
10
11 # search local then perl directories
12 BEGIN {
13         # root of directory tree for this system
14         $root = "/spider"; 
15         $root = $ENV{'DXSPIDER_ROOT'} if $ENV{'DXSPIDER_ROOT'};
16
17         mkdir "$root/local_data", 02777 unless -d "$root/local_data";
18
19         unshift @INC, "$root/perl";     # this IS the right way round!
20         unshift @INC, "$root/local";
21 }
22
23 use SysVar;
24
25 use Data::Dumper;
26 use DXUtil;
27
28 use strict;
29
30 my %loc = ();                                           # the location unique hash
31 my $nextloc = 1;                                        # the next location number
32 my %locn = ();                                          # the inverse of the above
33 my %pre = ();                                           # the prefix hash
34 my %pren = ();                                          # the inverse
35
36 if (@ARGV && $ARVG[0] =~ /^--system$/) {
37         $prefix = $main::data;
38         shift;
39 } else {
40         $prefix = $main:local_data;
41 }
42
43 # open the input file
44 my $ifn = $ARGV[0] if $ARGV[0];
45
46 $ifn = "$prefix/wpxloc.raw" if !$ifn;
47 open (IN, $ifn) or die "can't open $ifn ($!)";
48
49 # first pass, find all the 'master' location records
50 while (<IN>) {
51         next if /^\!/;                          # ignore comment lines
52         chomp;
53         my @f  = split;                         # get each 'word'
54         next if @f == 0;                        # ignore blank lines
55
56         if (($f[14] && $f[14] eq '@') || ($f[15] && $f[15] eq '@')) {
57                 my $locstr = join ' ', @f[1..13];
58                 my $loc = $loc{$locstr};
59                 $loc = addloc($locstr) if !$loc;
60         }
61 }
62
63 #foreach $loc (sort {$a <=> $b;} keys %locn) {
64 #  print "loc: $loc data: $locn{$loc}\n";
65 #}
66
67 # go back to the beginning and this time add prefixes (adding new location entries, if required)
68 seek(IN, 0, 0);
69
70 my $line;
71 while (<IN>) {
72         $line++;
73         chomp;
74         next if /^\s*\!/;                               # ignore comment lines
75         next if /^\s*$/;
76         
77         my @f  = split;                         # get each 'word'
78         next if @f == 0;                        # ignore blank lines
79   
80         # location record
81         my $locstr = join ' ', @f[1..13];
82         my $loc = $loc{$locstr};
83         $loc = addloc($locstr) if !$loc;
84   
85         my @prefixes = split /,/, $f[0];
86         foreach my $p (@prefixes) {
87                 my $ref;
88         
89                 if ($p =~ /#/) {
90                         my $i;
91                         for ($i = 0; $i < 9; ++$i) {
92                                 my $t = $p;
93                                 $t =~ s/#/$i/;
94                                 addpre($t, $loc);
95                         }
96                 } else {
97                         addpre($p, $loc);
98                 }       
99         }
100 }
101
102 close(IN);
103
104 #print Data::Dumper->Dump([\%pre, \%locn], [qw(pre locn)]);
105
106 # now open the cty.dat file if it is there
107 my @f;
108 my @a;
109 $line = 0;
110 if (open(IN, "$prefix/cty.dat")) {
111         my $state = 0;
112         while (<IN>) {
113                 $line++;
114                 s/\r$//;
115                 next if /^\s*\#/;
116                 next if /^\s*$/;
117                 chomp;
118                 if ($state == 0) {
119                         s/:$//;
120                         @f = split /:\s+/;
121                         @a = ();
122                         $state = 1;
123                 } elsif ($state == 1) {
124                         s/^\s+//;
125                         if (/;$/) {
126                                 $state = 0;
127                                 s/[,;]$//;
128                                 push @a, split /\s*,/;
129                                 $f[7] =~ s/^\*\s*//;   # remove any preceeding '*' before a callsign
130                                 ct($_, uc $f[7], @a) if @a;
131                         } else {
132                                 s/,$//;
133                                 push @a, split /\s*,/;
134                         }
135                 }
136         }
137 }
138 close IN;
139
140
141 open(OUT, ">$prefix/prefix_data.pl") or die "Can't open $prefix/prefix_data.pl ($!)";
142
143 print OUT "\%pre = (\n";
144 foreach my $k (sort keys %pre) {
145         my $ans = printpre($k);
146         print OUT "  '$k' => '$ans',\n";
147 }
148 print OUT ");\n\n";
149
150 print OUT "\n\%prefix_loc = (\n";
151 foreach my $l (sort {$a <=> $b} keys %locn) {
152         print OUT "   $l => bless( {";
153         my ($name, $dxcc, $itu, $cq, $utcoff, $latd, $latm, $lats, $latl, $longd, $longm, $longs, $longl) = split /\s+/, $locn{$l};
154   
155         $longd += ($longm/60);
156         $longd = 0-$longd if (uc $longl) eq 'W'; 
157         $latd += ($latm/60);
158         $latd = 0-$latd if (uc $latl) eq 'S';
159         print OUT " name => '$name',";
160         print OUT " dxcc => $dxcc,";
161         print OUT " itu => $itu,";
162         print OUT " cq => $cq,";
163         print OUT " utcoff => $utcoff,";
164         print OUT " lat => $latd,";
165         print OUT " long => $longd";
166         print OUT " }, 'Prefix'),\n";
167 }
168 print OUT ");\n\n";
169
170 close(OUT);
171
172 sub addpre
173 {
174         my ($p, $ent) = @_;
175         my $ref = $pre{$p};
176         $ref = $pre{$p} = [] if !$ref;
177         push @{$ref}, $ent;;
178 }
179
180 sub printpre
181 {
182         my $p = shift;
183         my $ref = $pre{$p};
184         my $out;
185         my $r;
186   
187         foreach $r (@{$ref}) {
188                 $out .= "$r,";
189         }
190         chop $out;
191         return $out;
192 }
193
194 sub ct
195 {
196         my $l = shift;
197         my $p = shift; 
198         my @a = @_;
199         my $ref = $pre{$p};
200         if ($ref) {
201                 my $a;
202                 foreach $a (@a) {
203                         # for now remove (nn) [nn]
204                         my ($itu) = $a =~ /(\(\d+\))/; $a =~ s/(\(\d+\))//g;
205                         my ($cq) = $a =~ /(\[\d+\])/; $a =~ s/(\[\d+\])//g;
206                         my ($lat, $long) = $a =~ m{(<[-+\d.]+/[-+\d.]+>)}; $a =~ s{(<[-+\d.]+/[-+\d.]+>)}{}g;
207                         my ($cont) = $a =~ /(\{[A-Z]{2}\})/; $a =~ s/(\{[A-Z]{2}\})//g;
208
209                         unless ($a) {
210                                 print "line $line: blank prefix on $l in cty.dat\n";
211                                 next;
212                         }
213                         next if $a eq $p;       # ignore if we have it already
214                         my $nref = $pre{$a};
215                         $pre{$a} = $ref if !$nref; # copy the original ref if new 
216                 }
217         } else {
218                 print "line $line: unknown prefix '$p' on $l in cty.dat\n";
219         }
220 }
221
222 sub addloc
223 {
224         my $locstr = shift;
225         $locstr =~ s/\'/\\'/g;
226         my $loc = $loc{$locstr} = $nextloc++;
227         $locn{$loc} = $locstr;
228         return $loc;
229 }
230