source: ProjectBuilder/devel/pb/bin/pb.pl@ 16

Last change on this file since 16 was 16, checked in by Bruno Cornec, 17 years ago

Works for build files generation wtih filter and variable expansion. Happy ;-)

  • Property svn:executable set to *
File size: 8.0 KB
Line 
1#!/usr/bin/perl -w
2#
3# Project Builder main application
4#
5# $Id$
6#
7# Copyright B. Cornec 2007
8# Provided under the GPL v2
9
10# Syntax: pb [-p project] <action> [<params>...]
11
12use strict;
13use Switch;
14use Getopt::Std;
15use Data::Dumper;
16use English;
17use AppConfig qw(:argcount :expand);
18use File::Basename;
19use Time::localtime qw(localtime);
20use POSIX qw(strftime);
21
22use lib qw (lib etc);
23use vars qw (%defpkgdir %extpkgdir %version @filteredfiles);
24use common qw (env_init);
25use pb qw (defpkgdir extpkgdir version filteredfiles pb_init);
26use distro qw (distro_init);
27use cms;
28
29my %opts; # CLI Options
30my $action; # action to realize
31my $test = "FALSE";
32my $option = "";
33my @pkgs;
34my $pbtag; # Global TAG variable
35my $pbver; # Global VERSION variable
36my $pbrev; # GLOBAL REVISION variable
37my @date=(localtime->sec(), localtime->min(), localtime->hour(), localtime->mday(), localtime->mon(), localtime->year(), localtime->wday(), localtime->yday(), localtime->isdst());
38my $pbdate = strftime("%Y-%m-%d", @date);
39
40getopts('p:t',\%opts);
41
42# Handles project name if any
43if (defined $opts{'p'}) {
44 $ENV{'PBPROJ'} = env_init($opts{'p'});
45} else {
46 $ENV{'PBPROJ'} = env_init();
47}
48# Handles test option
49if (defined $opts{'t'}) {
50 $test = "TRUE";
51 # Works only for SVN
52 $option = "-r BASE";
53}
54
55# Get Action
56$action = shift @ARGV;
57die "Syntax: pb [-p project] <action> [<params>...]" if (not defined $action);
58
59print "Project $ENV{'PBPROJ'}\n";
60#print "Action: $action - ARGV:".Dumper(\@ARGV);
61
62# Act depending on action
63if ($action =~ /^cms2build$/) {
64 print "Action: cms2build\n";
65 # Get packages list
66 if (not defined $ARGV[0]) {
67 @pkgs = keys %defpkgdir;
68 } elsif ($ARGV[0] =~ /^all$/) {
69 @pkgs = keys %defpkgdir;
70 push(@pkgs, keys %extpkgdir);
71 } else {
72 @pkgs = @ARGV;
73 }
74 print "Packages:\n";
75 print Dumper(@pkgs);
76 cms_init();
77
78 foreach my $p (@pkgs) {
79
80 if (-f "$ENV{'PBROOT'}/$p/VERSION") {
81 open(V,"$ENV{'PBROOT'}/$p/VERSION") || die "Unable to open $ENV{'PBROOT'}/$p/VERSION";
82 $pbver = <V>;
83 chomp($pbver);
84 close(V);
85 } else {
86 $pbver = $ENV{'PBVER'};
87 }
88
89 if (-f "$ENV{'PBROOT'}/$p/TAG") {
90 open(T,"$ENV{'PBROOT'}/$p/TAG") || die "Unable to open $ENV{'PBROOT'}/$p/TAG";
91 $pbtag = <T>;
92 chomp($pbtag);
93 close(T);
94 } else {
95 $pbtag = $ENV{'PBTAG'};
96 }
97 $pbrev = $ENV{'PBREVISION'};
98 print "Management of $p $pbver-$pbtag (rev $pbrev)\n";
99 die "Unable to get env var PBDESTDIR" if (not defined $ENV{'PBDESTDIR'});
100 # Clean up dest if necessary. The export will recreate it
101 my $dest = "$ENV{'PBDESTDIR'}/$p-$pbver";
102 pbrm_rf($dest) if (-d $dest);
103
104 # Export CMS tree for the concerned package to dest
105 # And generate some additional files
106 $OUTPUT_AUTOFLUSH=1;
107 print "$ENV{'PBCMSEXP'} of $p...";
108 # computes in which dir we have to work
109 my $dir = $defpkgdir{$p};
110 $dir = $extpkgdir{$p} if (not defined $dir);
111 system("$ENV{'PBCMSEXP'} $option $ENV{'PBROOT'}/$dir $dest 1>/dev/null");
112 if ($? == -1) {
113 print "failed to execute: $!\n";
114 } elsif ($? & 127) {
115 printf "child died with signal %d, %s coredump\n", ($? & 127), ($? & 128) ? 'with' : 'without';
116 } else {
117 print " Done under $dest\n";
118 }
119
120 # Creates a REVISION file
121 open(R,"> $dest/REVISION") || die "Unable to create $dest/REVISION";
122 print R "$pbrev\n";
123 close(R);
124
125 # Extract cms log history and store it
126 system("$ENV{'PBCMSLOG'} $option $ENV{'PBROOT'}/$dir > $dest/$ENV{'PBCMSLOGFILE'}");
127 print "$ENV{'PBCMSLOG'} of $p...";
128 if ($? == -1) {
129 print "failed to execute: $!\n";
130 } elsif ($? & 127) {
131 printf "child died with signal %d, %s coredump\n", ($? & 127), ($? & 128) ? 'with' : 'without';
132 } else {
133 print " OK\n";
134 }
135 open(D,"$ENV{'PBCONF'}/DISTROS") || die "Unable to find $ENV{'PBCONF'}/DISTROS\n";
136 while (<D>) {
137 my $d = $_;
138 my ($dir,$ver) = split(/_/,$d);
139 chomp($ver);
140 print "Generating build files for $dir ($ver)\n";
141 my ($ddir, $dver, $dfam, $dtype, $dsuf) = distro_init($dir,$ver);
142 #print Dumper($ddir, $dver, $dfam, $dtype, $dsuf);
143 #print "Filtering DDD => $pbdate, TTT => $pbtag, RRR => $pbtag$dsuf, VVV => $pbver\n";
144
145 # Filter build files from the less precise up to the most with overloading
146 # Filter all files found, keeping the name, and generating in dest
147
148 # Find all build files first relatively to PBROOT
149 my %bfiles;
150 #print "dir: $ENV{'PBCONF'}/$p\n";
151 if (-d "$ENV{'PBCONF'}/$p/$dtype") {
152 opendir(BDIR,"$ENV{'PBCONF'}/$p/$dtype" || die "Unable to open dir $ENV{'PBCONF'}/$p/$dtype: $!");
153 foreach my $f (readdir(BDIR)) {
154 next if ($f =~ /^\./);
155 $bfiles{$f} = "$ENV{'PBCONF'}/$p/$dtype/$f";
156 $bfiles{$f} =~ s~$ENV{'PBROOT'}~~;
157 }
158 closedir(BDIR);
159 } elsif (-d "$ENV{'PBCONF'}/$p/$dfam") {
160 opendir(BDIR,"$ENV{'PBCONF'}/$p/$dfam" || die "Unable to open dir $ENV{'PBCONF'}/$p/$dfam: $!");
161 foreach my $f (readdir(BDIR)) {
162 next if ($f =~ /^\./);
163 $bfiles{$f} = "$ENV{'PBCONF'}/$p/$dfam/$f";
164 $bfiles{$f} =~ s~$ENV{'PBROOT'}~~;
165 }
166 closedir(BDIR);
167 } elsif (-d "$ENV{'PBCONF'}/$p/$ddir") {
168 opendir(BDIR,"$ENV{'PBCONF'}/$p/$ddir" || die "Unable to open dir $ENV{'PBCONF'}/$p/$ddir: $!");
169 foreach my $f (readdir(BDIR)) {
170 next if ($f =~ /^\./);
171 $bfiles{$f} = "$ENV{'PBCONF'}/$p/$ddir/$f";
172 $bfiles{$f} =~ s~$ENV{'PBROOT'}~~;
173 }
174 closedir(BDIR);
175 } elsif (-d "$ENV{'PBCONF'}/$p/$ddir-$dver") {
176 opendir(BDIR,"$ENV{'PBCONF'}/$p/$ddir-$dver" || die "Unable to open dir $ENV{'PBCONF'}/$p/$ddir-$dver: $!");
177 foreach my $f (readdir(BDIR)) {
178 next if ($f =~ /^\./);
179 $bfiles{$f} = "$ENV{'PBCONF'}/$p/$ddir-$dver/$f";
180 $bfiles{$f} =~ s~$ENV{'PBROOT'}~~;
181 }
182 closedir(BDIR);
183 } else {
184 print "No Build Files found for $ddir-$dver\n";
185 next;
186 }
187 print "bfiles: ".Dumper(\%bfiles)."\n";
188
189 # Get all filters to apply
190 # They're cumulative from less specific to most specific
191 # suffix is .pbf
192 my @ffiles;
193 my ($ffile0, $ffile1, $ffile2, $ffile3);
194 if (-d "$ENV{'PBCONF'}/$p/pbfilter") {
195 $ffile0 = "$ENV{'PBCONF'}/$p/pbfilter/$dtype.pbf" if (-f "$ENV{'PBCONF'}/$p/pbfilter/$dtype.pbf");
196 $ffile1 = "$ENV{'PBCONF'}/$p/pbfilter/$dfam.pbf" if (-f "$ENV{'PBCONF'}/$p/pbfilter/$dfam.pbf");
197 $ffile2 = "$ENV{'PBCONF'}/$p/pbfilter/$ddir.pbf" if (-f "$ENV{'PBCONF'}/$p/pbfilter/$ddir.pbf");
198 $ffile3 = "$ENV{'PBCONF'}/$p/pbfilter/$ddir-$dver.pbf" if (-f "$ENV{'PBCONF'}/$p/pbfilter/$ddir-$dver.pbf");
199 push @ffiles,$ffile0 if (defined $ffile0);
200 push @ffiles,$ffile1 if (defined $ffile1);
201 push @ffiles,$ffile2 if (defined $ffile2);
202 push @ffiles,$ffile3 if (defined $ffile3);
203 }
204 my $config = AppConfig->new({
205 # Auto Create variables mentioned in Conf file
206 CREATE => 1,
207 DEBUG => 0,
208 GLOBAL => {
209 # Each conf item is a hash
210 ARGCOUNT => AppConfig::ARGCOUNT_HASH
211 }
212 });
213 print "ffiles: ".Dumper(\@ffiles)."\n";
214 if (@ffiles) {
215 $config->file(@ffiles);
216 my $ptr = $config->get("filter");
217 print "f:".Dumper($ptr)."\n";
218
219 # Apply now all the filters on all the files concerned
220 # All files are relative to PBROOT
221 # destination dir depends on the type of file
222 if (defined $ptr) {
223 foreach my $f (values %bfiles) {
224 filter_file($f,$ptr,"$dest/pbconf/$ddir-$dver/".basename($f));
225 }
226 foreach my $f (@filteredfiles) {
227 filter_file($f,$ptr,"$dest/$f");
228 }
229 }
230 }
231 }
232 close(D);
233 }
234} else {
235 print "'$action' is not available\n";
236 print "Available actions are:\n";
237 print " cms2build\n";
238}
239
240sub filter_file {
241
242my $f=shift;
243my $ptr=shift;
244my %filter=%$ptr;
245my $destfile=shift;
246
247print "From $f to $destfile\n";
248pbmkdir_p(dirname($destfile)) if (! -d dirname($destfile));
249open(DEST,"> $destfile") || die "Unable to create $destfile";
250open(FILE,"$ENV{'PBROOT'}/$f") || die "Unable to open $f: $!";
251while (<FILE>) {
252 my $line = $_;
253 foreach my $s (keys %filter) {
254 # Process single variables
255 #print "debug: $filter{$s}\n";
256 my $tmp = $filter{$s};
257 next if (not defined $tmp);
258 # Expand variables if any single one found
259 if ($tmp =~ /\$/) {
260 eval { $tmp =~ s/(\$\w+)/$1/eeg };
261 }
262 $line =~ s|$s|$tmp|;
263 }
264 print DEST $line;
265 }
266close(FILE);
267close(DEST);
268}
Note: See TracBrowser for help on using the repository browser.